mirror of
https://github.com/Fishwaldo/build.git
synced 2025-03-22 23:01:56 +00:00
189 lines
5.4 KiB
Diff
189 lines
5.4 KiB
Diff
From 063d7ebf17304fe8a7b85ecb4662f20c4839b6af Mon Sep 17 00:00:00 2001
|
|
From: Qiang Yu <yuq825@gmail.com>
|
|
Date: Wed, 30 May 2018 19:18:03 +0800
|
|
Subject: [PATCH 069/146] drm/lima: vm alloc buffer with multi page table
|
|
|
|
Signed-off-by: Qiang Yu <yuq825@gmail.com>
|
|
---
|
|
drivers/gpu/drm/lima/lima_vm.c | 95 ++++++++++++++++++++++------------
|
|
drivers/gpu/drm/lima/lima_vm.h | 6 ++-
|
|
2 files changed, 66 insertions(+), 35 deletions(-)
|
|
|
|
diff --git a/drivers/gpu/drm/lima/lima_vm.c b/drivers/gpu/drm/lima/lima_vm.c
|
|
index 19a683c2921b..ab7438685234 100644
|
|
--- a/drivers/gpu/drm/lima/lima_vm.c
|
|
+++ b/drivers/gpu/drm/lima/lima_vm.c
|
|
@@ -28,8 +28,18 @@ struct lima_bo_va {
|
|
struct lima_vm *vm;
|
|
};
|
|
|
|
-#define LIMA_PDE(va) (va >> 22)
|
|
-#define LIMA_PTE(va) ((va & 0x3FFFFF) >> 12)
|
|
+#define LIMA_VM_PD_SHIFT 22
|
|
+#define LIMA_VM_PT_SHIFT 12
|
|
+#define LIMA_VM_PB_SHIFT (LIMA_VM_PD_SHIFT + LIMA_VM_NUM_PT_PER_BT_SHIFT)
|
|
+#define LIMA_VM_BT_SHIFT LIMA_VM_PT_SHIFT
|
|
+
|
|
+#define LIMA_VM_PT_MASK ((1 << LIMA_VM_PD_SHIFT) - 1)
|
|
+#define LIMA_VM_BT_MASK ((1 << LIMA_VM_PB_SHIFT) - 1)
|
|
+
|
|
+#define LIMA_PDE(va) (va >> LIMA_VM_PD_SHIFT)
|
|
+#define LIMA_PTE(va) ((va & LIMA_VM_PT_MASK) >> LIMA_VM_PT_SHIFT)
|
|
+#define LIMA_PBE(va) (va >> LIMA_VM_PB_SHIFT)
|
|
+#define LIMA_BTE(va) ((va & LIMA_VM_BT_MASK) >> LIMA_VM_BT_SHIFT)
|
|
|
|
#define START(node) ((node)->start)
|
|
#define LAST(node) ((node)->last)
|
|
@@ -45,12 +55,12 @@ static void lima_vm_unmap_page_table(struct lima_vm *vm, u32 start, u32 end)
|
|
u32 addr;
|
|
|
|
for (addr = start; addr <= end; addr += LIMA_PAGE_SIZE) {
|
|
- u32 pde = LIMA_PDE(addr);
|
|
- u32 pte = LIMA_PTE(addr);
|
|
- u32 *pt;
|
|
+ u32 pbe = LIMA_PBE(addr);
|
|
+ u32 bte = LIMA_BTE(addr);
|
|
+ u32 *bt;
|
|
|
|
- pt = lima_bo_kmap(vm->pt[pde]);
|
|
- pt[pte] = 0;
|
|
+ bt = lima_bo_kmap(vm->bts[pbe]);
|
|
+ bt[bte] = 0;
|
|
}
|
|
}
|
|
|
|
@@ -61,32 +71,43 @@ static int lima_vm_map_page_table(struct lima_vm *vm, dma_addr_t *dma,
|
|
int err, i = 0;
|
|
|
|
for (addr = start; addr <= end; addr += LIMA_PAGE_SIZE) {
|
|
- u32 pde = LIMA_PDE(addr);
|
|
- u32 pte = LIMA_PTE(addr);
|
|
- u32 *pd, *pt;
|
|
+ u32 pbe = LIMA_PBE(addr);
|
|
+ u32 bte = LIMA_BTE(addr);
|
|
+ u32 *bt;
|
|
|
|
- if (vm->pt[pde])
|
|
- pt = lima_bo_kmap(vm->pt[pde]);
|
|
+ if (vm->bts[pbe])
|
|
+ bt = lima_bo_kmap(vm->bts[pbe]);
|
|
else {
|
|
- vm->pt[pde] = lima_bo_create(
|
|
- vm->dev, LIMA_PAGE_SIZE, 0, ttm_bo_type_kernel,
|
|
+ struct lima_bo *bt_bo;
|
|
+ dma_addr_t *pts;
|
|
+ u32 *pd;
|
|
+ int j;
|
|
+
|
|
+ bt_bo = lima_bo_create(
|
|
+ vm->dev, LIMA_PAGE_SIZE << LIMA_VM_NUM_PT_PER_BT_SHIFT,
|
|
+ 0, ttm_bo_type_kernel,
|
|
NULL, vm->pd->tbo.resv);
|
|
- if (IS_ERR(vm->pt[pde])) {
|
|
- err = PTR_ERR(vm->pt[pde]);
|
|
+ if (IS_ERR(bt_bo)) {
|
|
+ err = PTR_ERR(bt_bo);
|
|
goto err_out;
|
|
}
|
|
|
|
- pt = lima_bo_kmap(vm->pt[pde]);
|
|
- if (IS_ERR(pt)) {
|
|
- err = PTR_ERR(pt);
|
|
+ bt = lima_bo_kmap(bt_bo);
|
|
+ if (IS_ERR(bt)) {
|
|
+ lima_bo_unref(bt_bo);
|
|
+ err = PTR_ERR(bt);
|
|
goto err_out;
|
|
}
|
|
|
|
+ vm->bts[pbe] = bt_bo;
|
|
pd = lima_bo_kmap(vm->pd);
|
|
- pd[pde] = *lima_bo_get_pages(vm->pt[pde]) | LIMA_VM_FLAG_PRESENT;
|
|
+ pd += pbe << LIMA_VM_NUM_PT_PER_BT_SHIFT;
|
|
+ pts = lima_bo_get_pages(bt_bo);
|
|
+ for (j = 0; j < LIMA_VM_NUM_PT_PER_BT; j++)
|
|
+ *pd++ = *pts++ | LIMA_VM_FLAG_PRESENT;
|
|
}
|
|
|
|
- pt[pte] = dma[i++] | LIMA_VM_FLAGS_CACHE;
|
|
+ bt[bte] = dma[i++] | LIMA_VM_FLAGS_CACHE;
|
|
}
|
|
|
|
return 0;
|
|
@@ -293,9 +314,9 @@ void lima_vm_release(struct kref *kref)
|
|
dev_err(dev->dev, "still active bo inside vm\n");
|
|
}
|
|
|
|
- for (i = 0; i < LIMA_PAGE_ENT_NUM; i++) {
|
|
- if (vm->pt[i])
|
|
- lima_bo_unref(vm->pt[i]);
|
|
+ for (i = 0; i < LIMA_VM_NUM_BT; i++) {
|
|
+ if (vm->bts[i])
|
|
+ lima_bo_unref(vm->bts[i]);
|
|
}
|
|
|
|
if (vm->pd)
|
|
@@ -306,20 +327,26 @@ void lima_vm_release(struct kref *kref)
|
|
|
|
void lima_vm_print(struct lima_vm *vm)
|
|
{
|
|
- int i, j;
|
|
- u32 *pd = lima_bo_kmap(vm->pd);
|
|
+ int i, j, k;
|
|
+ u32 *pd, *pt;
|
|
|
|
/* to avoid the defined by not used warning */
|
|
(void)&lima_vm_it_iter_next;
|
|
|
|
- for (i = 0; i < LIMA_PAGE_ENT_NUM; i++) {
|
|
- if (pd[i]) {
|
|
- u32 *pt = lima_bo_kmap(vm->pt[i]);
|
|
-
|
|
- printk(KERN_INFO "lima vm pd %03x:%08x\n", i, pd[i]);
|
|
- for (j = 0; j < LIMA_PAGE_ENT_NUM; j++) {
|
|
- if (pt[j])
|
|
- printk(KERN_INFO " pt %03x:%08x\n", j, pt[j]);
|
|
+ pd = lima_bo_kmap(vm->pd);
|
|
+ for (i = 0; i < LIMA_VM_NUM_BT; i++) {
|
|
+ if (!vm->bts[i])
|
|
+ continue;
|
|
+
|
|
+ pt = lima_bo_kmap(vm->bts[i]);
|
|
+ for (j = 0; j < LIMA_VM_NUM_PT_PER_BT; j++) {
|
|
+ int idx = (i << LIMA_VM_NUM_PT_PER_BT_SHIFT) + j;
|
|
+ printk(KERN_INFO "lima vm pd %03x:%08x\n", idx, pd[idx]);
|
|
+
|
|
+ for (k = 0; k < LIMA_PAGE_ENT_NUM; k++) {
|
|
+ u32 pte = *pt++;
|
|
+ if (pte)
|
|
+ printk(KERN_INFO " pt %03x:%08x\n", k, pte);
|
|
}
|
|
}
|
|
}
|
|
diff --git a/drivers/gpu/drm/lima/lima_vm.h b/drivers/gpu/drm/lima/lima_vm.h
|
|
index c891a1ee95df..598708ac0d31 100644
|
|
--- a/drivers/gpu/drm/lima/lima_vm.h
|
|
+++ b/drivers/gpu/drm/lima/lima_vm.h
|
|
@@ -12,6 +12,10 @@
|
|
#define LIMA_PAGE_MASK (LIMA_PAGE_SIZE - 1)
|
|
#define LIMA_PAGE_ENT_NUM (LIMA_PAGE_SIZE / sizeof(u32))
|
|
|
|
+#define LIMA_VM_NUM_PT_PER_BT_SHIFT 3
|
|
+#define LIMA_VM_NUM_PT_PER_BT (1 << LIMA_VM_NUM_PT_PER_BT_SHIFT)
|
|
+#define LIMA_VM_NUM_BT (LIMA_PAGE_ENT_NUM >> LIMA_VM_NUM_PT_PER_BT_SHIFT)
|
|
+
|
|
#define LIMA_VA_RESERVE_START 0xFFF00000
|
|
#define LIMA_VA_RESERVE_DLBU LIMA_VA_RESERVE_START
|
|
#define LIMA_VA_RESERVE_END 0x100000000
|
|
@@ -28,7 +32,7 @@ struct lima_vm {
|
|
struct lima_device *dev;
|
|
|
|
struct lima_bo *pd;
|
|
- struct lima_bo *pt[LIMA_PAGE_ENT_NUM];
|
|
+ struct lima_bo *bts[LIMA_VM_NUM_BT];
|
|
};
|
|
|
|
int lima_vm_bo_map(struct lima_vm *vm, struct lima_bo *bo, u32 start);
|
|
--
|
|
2.17.1
|
|
|