diff options
Diffstat (limited to 'drivers/gpu/drm/radeon')
-rw-r--r-- | drivers/gpu/drm/radeon/radeon.h | 1 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_mn.c | 2 | ||||
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_ttm.c | 31 |
3 files changed, 33 insertions, 1 deletions
diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h index df6f0b49836b..a6d8de01194a 100644 --- a/drivers/gpu/drm/radeon/radeon.h +++ b/drivers/gpu/drm/radeon/radeon.h @@ -2820,6 +2820,7 @@ extern int radeon_ttm_tt_set_userptr(struct radeon_device *rdev, uint32_t flags); extern bool radeon_ttm_tt_has_userptr(struct radeon_device *rdev, struct ttm_tt *ttm); extern bool radeon_ttm_tt_is_readonly(struct radeon_device *rdev, struct ttm_tt *ttm); +bool radeon_ttm_tt_is_bound(struct ttm_bo_device *bdev, struct ttm_tt *ttm); extern void radeon_vram_location(struct radeon_device *rdev, struct radeon_mc *mc, u64 base); extern void radeon_gtt_location(struct radeon_device *rdev, struct radeon_mc *mc); extern int radeon_resume_kms(struct drm_device *dev, bool resume, bool fbcon); diff --git a/drivers/gpu/drm/radeon/radeon_mn.c b/drivers/gpu/drm/radeon/radeon_mn.c index eb46d2220236..97b9b6dd6dd3 100644 --- a/drivers/gpu/drm/radeon/radeon_mn.c +++ b/drivers/gpu/drm/radeon/radeon_mn.c @@ -53,7 +53,7 @@ static bool radeon_mn_invalidate(struct mmu_interval_notifier *mn, struct ttm_operation_ctx ctx = { false, false }; long r; - if (!bo->tbo.ttm || !ttm_bo_tt_is_bound(&bo->tbo)) + if (!bo->tbo.ttm || !radeon_ttm_tt_is_bound(bo->tbo.bdev, bo->tbo.ttm)) return true; if (!mmu_notifier_range_blockable(range)) diff --git a/drivers/gpu/drm/radeon/radeon_ttm.c b/drivers/gpu/drm/radeon/radeon_ttm.c index c6c1008fefd2..fc8bbca28b34 100644 --- a/drivers/gpu/drm/radeon/radeon_ttm.c +++ b/drivers/gpu/drm/radeon/radeon_ttm.c @@ -420,6 +420,7 @@ struct radeon_ttm_tt { uint64_t userptr; struct mm_struct *usermm; uint32_t userflags; + bool bound; }; /* prepare the sg table with the user pages */ @@ -513,6 +514,13 @@ static void radeon_ttm_tt_unpin_userptr(struct ttm_bo_device *bdev, struct ttm_t sg_free_table(ttm->sg); } +static bool radeon_ttm_backend_is_bound(struct ttm_tt *ttm) +{ + struct radeon_ttm_tt *gtt = (void*)ttm; + + return (gtt->bound); +} + static int radeon_ttm_backend_bind(struct ttm_bo_device *bdev, struct ttm_tt *ttm, struct ttm_resource *bo_mem) @@ -523,6 +531,9 @@ static int radeon_ttm_backend_bind(struct ttm_bo_device *bdev, RADEON_GART_PAGE_WRITE; int r; + if (gtt->bound) + return 0; + if (gtt->userptr) { radeon_ttm_tt_pin_userptr(bdev, ttm); flags &= ~RADEON_GART_PAGE_WRITE; @@ -542,6 +553,7 @@ static int radeon_ttm_backend_bind(struct ttm_bo_device *bdev, ttm->num_pages, (unsigned)gtt->offset); return r; } + gtt->bound = true; return 0; } @@ -550,10 +562,14 @@ static void radeon_ttm_backend_unbind(struct ttm_bo_device *bdev, struct ttm_tt struct radeon_ttm_tt *gtt = (void *)ttm; struct radeon_device *rdev = radeon_get_rdev(bdev); + if (!gtt->bound) + return; + radeon_gart_unbind(rdev, gtt->offset, ttm->num_pages); if (gtt->userptr) radeon_ttm_tt_unpin_userptr(bdev, ttm); + gtt->bound = false; } static void radeon_ttm_backend_destroy(struct ttm_bo_device *bdev, struct ttm_tt *ttm) @@ -689,12 +705,27 @@ int radeon_ttm_tt_set_userptr(struct radeon_device *rdev, return 0; } +bool radeon_ttm_tt_is_bound(struct ttm_bo_device *bdev, + struct ttm_tt *ttm) +{ +#if IS_ENABLED(CONFIG_AGP) + struct radeon_device *rdev = radeon_get_rdev(bdev); + if (rdev->flags & RADEON_IS_AGP) + return ttm_agp_is_bound(ttm); +#endif + return radeon_ttm_backend_is_bound(ttm); +} + static int radeon_ttm_tt_bind(struct ttm_bo_device *bdev, struct ttm_tt *ttm, struct ttm_resource *bo_mem) { +#if IS_ENABLED(CONFIG_AGP) struct radeon_device *rdev = radeon_get_rdev(bdev); +#endif + if (!bo_mem) + return -EINVAL; #if IS_ENABLED(CONFIG_AGP) if (rdev->flags & RADEON_IS_AGP) return ttm_agp_bind(ttm, bo_mem); |