diff options
author | Ben Skeggs <bskeggs@redhat.com> | 2012-01-12 15:34:54 +1000 |
---|---|---|
committer | Ben Skeggs <bskeggs@redhat.com> | 2012-03-13 17:14:06 +1000 |
commit | 990449c77cafb77e7468722262c049675ab03e30 (patch) | |
tree | d6ed4aea5b2ce93eb294dfae870be30c7418527a /drivers/gpu/drm | |
parent | 4abb410a13eec3f49863be2e84ad062fef00dac0 (diff) | |
download | blackbird-op-linux-990449c77cafb77e7468722262c049675ab03e30.tar.gz blackbird-op-linux-990449c77cafb77e7468722262c049675ab03e30.zip |
drm/nv50-nvc0/vm: support unsnooped system memory
v2 (Emil Velikov <emil.l.velikov@gmail.com>):
- Fixed a regression on certain nv50 IGP due to not passing the correct
target type to nv50_vm_addr()
Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
Signed-off-by: Emil Velikov <emil.l.velikov@gmail.com>
Tested-by: Johannes Obermayr <johannesobermayr@gmx.de>
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_drv.h | 1 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nv50_vm.c | 29 | ||||
-rw-r--r-- | drivers/gpu/drm/nouveau/nvc0_vm.c | 4 |
3 files changed, 17 insertions, 17 deletions
diff --git a/drivers/gpu/drm/nouveau/nouveau_drv.h b/drivers/gpu/drm/nouveau/nouveau_drv.h index 63e77fc282f2..3a69a4aabd35 100644 --- a/drivers/gpu/drm/nouveau/nouveau_drv.h +++ b/drivers/gpu/drm/nouveau/nouveau_drv.h @@ -1759,6 +1759,7 @@ nv44_graph_class(struct drm_device *dev) #define NV_MEM_ACCESS_RW (NV_MEM_ACCESS_RO | NV_MEM_ACCESS_WO) #define NV_MEM_ACCESS_SYS 4 #define NV_MEM_ACCESS_VM 8 +#define NV_MEM_ACCESS_NOSNOOP 16 #define NV_MEM_TARGET_VRAM 0 #define NV_MEM_TARGET_PCI 1 diff --git a/drivers/gpu/drm/nouveau/nv50_vm.c b/drivers/gpu/drm/nouveau/nv50_vm.c index 6f38ceae3aa4..44fbac9c7d93 100644 --- a/drivers/gpu/drm/nouveau/nv50_vm.c +++ b/drivers/gpu/drm/nouveau/nv50_vm.c @@ -57,27 +57,15 @@ nv50_vm_map_pgt(struct nouveau_gpuobj *pgd, u32 pde, } static inline u64 -nv50_vm_addr(struct nouveau_vma *vma, u64 phys, u32 memtype, u32 target) +vm_addr(struct nouveau_vma *vma, u64 phys, u32 memtype, u32 target) { - struct drm_nouveau_private *dev_priv = vma->vm->dev->dev_private; - phys |= 1; /* present */ phys |= (u64)memtype << 40; - - /* IGPs don't have real VRAM, re-target to stolen system memory */ - if (target == 0 && dev_priv->vram_sys_base) { - phys += dev_priv->vram_sys_base; - target = 3; - } - phys |= target << 4; - if (vma->access & NV_MEM_ACCESS_SYS) phys |= (1 << 6); - if (!(vma->access & NV_MEM_ACCESS_WO)) phys |= (1 << 3); - return phys; } @@ -85,11 +73,19 @@ void nv50_vm_map(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt, struct nouveau_mem *mem, u32 pte, u32 cnt, u64 phys, u64 delta) { + struct drm_nouveau_private *dev_priv = vma->vm->dev->dev_private; u32 comp = (mem->memtype & 0x180) >> 7; - u32 block; + u32 block, target; int i; - phys = nv50_vm_addr(vma, phys, mem->memtype, 0); + /* IGPs don't have real VRAM, re-target to stolen system memory */ + target = 0; + if (dev_priv->vram_sys_base) { + phys += dev_priv->vram_sys_base; + target = 3; + } + + phys = vm_addr(vma, phys, mem->memtype, target); pte <<= 3; cnt <<= 3; @@ -125,9 +121,10 @@ void nv50_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt, struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list) { + u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 3 : 2; pte <<= 3; while (cnt--) { - u64 phys = nv50_vm_addr(vma, (u64)*list++, mem->memtype, 2); + u64 phys = vm_addr(vma, (u64)*list++, mem->memtype, target); nv_wo32(pgt, pte + 0, lower_32_bits(phys)); nv_wo32(pgt, pte + 4, upper_32_bits(phys)); pte += 8; diff --git a/drivers/gpu/drm/nouveau/nvc0_vm.c b/drivers/gpu/drm/nouveau/nvc0_vm.c index 9e352944a35a..30d2bd58828f 100644 --- a/drivers/gpu/drm/nouveau/nvc0_vm.c +++ b/drivers/gpu/drm/nouveau/nvc0_vm.c @@ -77,9 +77,11 @@ void nvc0_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt, struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list) { + u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 7 : 5; + pte <<= 3; while (cnt--) { - u64 phys = nvc0_vm_addr(vma, *list++, mem->memtype, 5); + u64 phys = nvc0_vm_addr(vma, *list++, mem->memtype, target); nv_wo32(pgt, pte + 0, lower_32_bits(phys)); nv_wo32(pgt, pte + 4, upper_32_bits(phys)); pte += 8; |