drm/ttm: Fix unmap of buffer object

Add a new ttm_bo_release_mmap() function to unmap pages in a
vm_object_t. Pages are freed when the buffer object is later released.

This function is called in ttm_bo_unmap_virtual_locked(), replacing
Linux' unmap_mapping_range(). In particular this is called when a buffer
object is about to be moved, so that its mapping is invalidated.

However, we don't use this function in ttm_bo_vm_dtor(), because the
vm_object_t is already marked as OBJ_DEAD and the pages will be
unmapped.

Approved by:	kib@
This commit is contained in:
Jean-Sébastien Pédron 2013-08-25 15:15:55 +00:00
parent 39db4184ec
commit 970c941acb
2 changed files with 28 additions and 6 deletions

View File

@ -1634,13 +1634,8 @@ bool ttm_mem_reg_is_pci(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem)
void ttm_bo_unmap_virtual_locked(struct ttm_buffer_object *bo)
{
struct ttm_bo_device *bdev = bo->bdev;
/* off_t offset = (off_t)bo->addr_space_offset;XXXKIB */
/* off_t holelen = ((off_t)bo->mem.num_pages) << PAGE_SHIFT;XXXKIB */
if (!bdev->dev_mapping)
return;
/* unmap_mapping_range(bdev->dev_mapping, offset, holelen, 1); XXXKIB */
ttm_bo_release_mmap(bo);
ttm_mem_io_free_vm(bo);
}

View File

@ -361,6 +361,33 @@ out_unref:
return ret;
}
void
ttm_bo_release_mmap(struct ttm_buffer_object *bo)
{
vm_object_t vm_obj;
vm_page_t m;
int i;
vm_obj = cdev_pager_lookup(bo);
if (vm_obj == NULL) {
return;
}
VM_OBJECT_WLOCK(vm_obj);
retry:
for (i = 0; i < bo->num_pages; i++) {
m = vm_page_lookup(vm_obj, i);
if (m == NULL)
continue;
if (vm_page_sleep_if_busy(m, "ttm_unm"))
goto retry;
cdev_pager_free_page(vm_obj, m);
}
VM_OBJECT_WUNLOCK(vm_obj);
vm_object_deallocate(vm_obj);
}
#if 0
int ttm_fbdev_mmap(struct vm_area_struct *vma, struct ttm_buffer_object *bo)
{