diff options
Diffstat (limited to 'drivers/gpu/drm/ttm')
-rw-r--r-- | drivers/gpu/drm/ttm/ttm_bo.c | 20 | ||||
-rw-r--r-- | drivers/gpu/drm/ttm/ttm_bo_vm.c | 19 |
2 files changed, 19 insertions, 20 deletions
diff --git a/drivers/gpu/drm/ttm/ttm_bo.c b/drivers/gpu/drm/ttm/ttm_bo.c index 0ec08394e17a..3f56647cdb35 100644 --- a/drivers/gpu/drm/ttm/ttm_bo.c +++ b/drivers/gpu/drm/ttm/ttm_bo.c @@ -198,19 +198,22 @@ static void ttm_bo_ref_bug(struct kref *list_kref) void ttm_bo_del_from_lru(struct ttm_buffer_object *bo) { + struct ttm_bo_device *bdev = bo->bdev; + bool notify = false; + if (!list_empty(&bo->swap)) { list_del_init(&bo->swap); kref_put(&bo->list_kref, ttm_bo_ref_bug); + notify = true; } if (!list_empty(&bo->lru)) { list_del_init(&bo->lru); kref_put(&bo->list_kref, ttm_bo_ref_bug); + notify = true; } - /* - * TODO: Add a driver hook to delete from - * driver-specific LRU's here. - */ + if (notify && bdev->driver->del_from_lru_notify) + bdev->driver->del_from_lru_notify(bo); } void ttm_bo_del_sub_from_lru(struct ttm_buffer_object *bo) @@ -676,15 +679,6 @@ void ttm_bo_put(struct ttm_buffer_object *bo) } EXPORT_SYMBOL(ttm_bo_put); -void ttm_bo_unref(struct ttm_buffer_object **p_bo) -{ - struct ttm_buffer_object *bo = *p_bo; - - *p_bo = NULL; - ttm_bo_put(bo); -} -EXPORT_SYMBOL(ttm_bo_unref); - int ttm_bo_lock_delayed_workqueue(struct ttm_bo_device *bdev) { return cancel_delayed_work_sync(&bdev->wq); diff --git a/drivers/gpu/drm/ttm/ttm_bo_vm.c b/drivers/gpu/drm/ttm/ttm_bo_vm.c index a1d977fbade5..e86a29a1e51f 100644 --- a/drivers/gpu/drm/ttm/ttm_bo_vm.c +++ b/drivers/gpu/drm/ttm/ttm_bo_vm.c @@ -71,7 +71,7 @@ static vm_fault_t ttm_bo_vm_fault_idle(struct ttm_buffer_object *bo, ttm_bo_get(bo); up_read(&vmf->vma->vm_mm->mmap_sem); (void) dma_fence_wait(bo->moving, true); - ttm_bo_unreserve(bo); + reservation_object_unlock(bo->resv); ttm_bo_put(bo); goto out_unlock; } @@ -131,11 +131,7 @@ static vm_fault_t ttm_bo_vm_fault(struct vm_fault *vmf) * for reserve, and if it fails, retry the fault after waiting * for the buffer to become unreserved. */ - err = ttm_bo_reserve(bo, true, true, NULL); - if (unlikely(err != 0)) { - if (err != -EBUSY) - return VM_FAULT_NOPAGE; - + if (unlikely(!reservation_object_trylock(bo->resv))) { if (vmf->flags & FAULT_FLAG_ALLOW_RETRY) { if (!(vmf->flags & FAULT_FLAG_RETRY_NOWAIT)) { ttm_bo_get(bo); @@ -165,6 +161,8 @@ static vm_fault_t ttm_bo_vm_fault(struct vm_fault *vmf) } if (bdev->driver->fault_reserve_notify) { + struct dma_fence *moving = dma_fence_get(bo->moving); + err = bdev->driver->fault_reserve_notify(bo); switch (err) { case 0: @@ -177,6 +175,13 @@ static vm_fault_t ttm_bo_vm_fault(struct vm_fault *vmf) ret = VM_FAULT_SIGBUS; goto out_unlock; } + + if (bo->moving != moving) { + spin_lock(&bdev->glob->lru_lock); + ttm_bo_move_to_lru_tail(bo, NULL); + spin_unlock(&bdev->glob->lru_lock); + } + dma_fence_put(moving); } /* @@ -291,7 +296,7 @@ static vm_fault_t ttm_bo_vm_fault(struct vm_fault *vmf) out_io_unlock: ttm_mem_io_unlock(man); out_unlock: - ttm_bo_unreserve(bo); + reservation_object_unlock(bo->resv); return ret; } |