From e8f3b572884fa1f95d70f7acf2272745db7f1009 Mon Sep 17 00:00:00 2001 From: Christian Koenig Date: Fri, 23 Feb 2018 16:08:51 +0100 Subject: [PATCH 3694/4131] drm/amdgpu: stop allocating a page array for prime shared BOs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We don't need the page array for prime shared BOs, stop allocating it. Signed-off-by: Christian König Reviewed-by: Roger He Signed-off-by: Kalyan Alle --- drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c | 4 --- drivers/gpu/drm/amd/amdgpu/amdgpu_gart.c | 2 +- drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | 5 +-- drivers/gpu/drm/ttm/ttm_tt.c | 45 +++++++++++++++++++++++- include/drm/drm_prime.h | 4 --- include/drm/ttm/ttm_bo_driver.h | 2 ++ 6 files changed, 50 insertions(+), 12 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c index f42a891..da1842a 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c @@ -1846,10 +1846,6 @@ int amdgpu_amdkfd_gpuvm_import_dmabuf(struct kgd_dev *kgd, struct amdgpu_bo *bo; struct amdgpu_vm *avm = (struct amdgpu_vm *)vm; - if (dma_buf->ops != &drm_gem_prime_dmabuf_ops) - /* Can't handle non-graphics buffers */ - return -EINVAL; - obj = dma_buf->priv; if (obj->dev->dev_private != adev) /* Can't handle buffers from other devices */ diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_gart.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_gart.c index 137145d..dc8d9f3 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_gart.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_gart.c @@ -315,7 +315,7 @@ int amdgpu_gart_bind(struct amdgpu_device *adev, uint64_t offset, t = offset / AMDGPU_GPU_PAGE_SIZE; p = t / (PAGE_SIZE / AMDGPU_GPU_PAGE_SIZE); for (i = 0; i < pages; i++, p++) - adev->gart.pages[p] = pagelist[i]; + adev->gart.pages[p] = pagelist ? pagelist[i] : NULL; #endif if (!adev->gart.ptr) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index 5208b25..15b7339 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c @@ -1063,7 +1063,7 @@ static struct ttm_tt *amdgpu_ttm_tt_create(struct ttm_bo_device *bdev, } gtt->ttm.ttm.func = &amdgpu_backend_func; gtt->adev = adev; - if (ttm_dma_tt_init(>t->ttm, bdev, size, page_flags)) { + if (ttm_sg_tt_init(>t->ttm, bdev, size, page_flags)) { kfree(gtt); return NULL; } @@ -1088,7 +1088,8 @@ static int amdgpu_ttm_tt_populate(struct ttm_tt *ttm) if (slave && ttm->sg) { drm_prime_sg_to_page_addr_arrays(ttm->sg, ttm->pages, - gtt->ttm.dma_address, ttm->num_pages); + gtt->ttm.dma_address, + ttm->num_pages); ttm->state = tt_unbound; return 0; } diff --git a/drivers/gpu/drm/ttm/ttm_tt.c b/drivers/gpu/drm/ttm/ttm_tt.c index 52ef502..b2426cb 100644 --- a/drivers/gpu/drm/ttm/ttm_tt.c +++ b/drivers/gpu/drm/ttm/ttm_tt.c @@ -56,7 +56,7 @@ static void ttm_tt_alloc_page_directory(struct ttm_tt *ttm) GFP_KERNEL | __GFP_ZERO); } -static void ttm_dma_tt_alloc_page_directory(struct ttm_dma_tt *ttm) +static int ttm_dma_tt_alloc_page_directory(struct ttm_dma_tt *ttm) { ttm->ttm.pages = kvmalloc_array(ttm->ttm.num_pages, sizeof(*ttm->ttm.pages) + @@ -65,6 +65,16 @@ static void ttm_dma_tt_alloc_page_directory(struct ttm_dma_tt *ttm) ttm->dma_address = (void *) (ttm->ttm.pages + ttm->ttm.num_pages); } +static int ttm_sg_tt_alloc_page_directory(struct ttm_dma_tt *ttm) +{ + ttm->dma_address = kvmalloc_array(ttm->ttm.num_pages, + sizeof(*ttm->dma_address), + GFP_KERNEL | __GFP_ZERO); + if (!ttm->dma_address) + return -ENOMEM; + return 0; +} + #ifdef CONFIG_X86 static inline int ttm_tt_set_page_caching(struct page *p, enum ttm_caching_state c_old, @@ -184,6 +194,17 @@ void ttm_tt_destroy(struct ttm_tt *ttm) ttm->func->destroy(ttm); } +void ttm_tt_init_fields(struct ttm_tt *ttm, struct ttm_bo_device *bdev, + unsigned long size, uint32_t page_flags) +{ + ttm->bdev = bdev; + ttm->num_pages = (size + PAGE_SIZE - 1) >> PAGE_SHIFT; + ttm->caching_state = tt_cached; + ttm->page_flags = page_flags; + ttm->state = tt_unpopulated; + ttm->swap_storage = NULL; +} + int ttm_tt_init(struct ttm_tt *ttm, struct ttm_bo_device *bdev, unsigned long size, uint32_t page_flags) { @@ -236,6 +257,28 @@ int ttm_dma_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_bo_device *bdev, } EXPORT_SYMBOL(ttm_dma_tt_init); +int ttm_sg_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_bo_device *bdev, + unsigned long size, uint32_t page_flags) +{ + struct ttm_tt *ttm = &ttm_dma->ttm; + int ret; + + ttm_tt_init_fields(ttm, bdev, size, page_flags); + + INIT_LIST_HEAD(&ttm_dma->pages_list); + if (page_flags & TTM_PAGE_FLAG_SG) + ret = ttm_sg_tt_alloc_page_directory(ttm_dma); + else + ret = ttm_dma_tt_alloc_page_directory(ttm_dma); + if (ret) { + ttm_tt_destroy(ttm); + pr_err("Failed allocating page table\n"); + return -ENOMEM; + } + return 0; +} +EXPORT_SYMBOL(ttm_sg_tt_init); + void ttm_dma_tt_fini(struct ttm_dma_tt *ttm_dma) { struct ttm_tt *ttm = &ttm_dma->ttm; diff --git a/include/drm/drm_prime.h b/include/drm/drm_prime.h index 5dd0089..3ceecca 100644 --- a/include/drm/drm_prime.h +++ b/include/drm/drm_prime.h @@ -81,10 +81,6 @@ int drm_gem_prime_fd_to_handle(struct drm_device *dev, struct dma_buf *drm_gem_dmabuf_export(struct drm_device *dev, struct dma_buf_export_info *exp_info); void drm_gem_dmabuf_release(struct dma_buf *dma_buf); -int drm_gem_map_attach(struct dma_buf *dma_buf, struct device *target_dev, - struct dma_buf_attachment *attach); -void drm_gem_map_detach(struct dma_buf *dma_buf, - struct dma_buf_attachment *attach); int drm_prime_sg_to_page_addr_arrays(struct sg_table *sgt, struct page **pages, dma_addr_t *addrs, int max_pages); struct sg_table *drm_prime_pages_to_sg(struct page **pages, unsigned int nr_pages); diff --git a/include/drm/ttm/ttm_bo_driver.h b/include/drm/ttm/ttm_bo_driver.h index 0a3b1bf..329adaf 100644 --- a/include/drm/ttm/ttm_bo_driver.h +++ b/include/drm/ttm/ttm_bo_driver.h @@ -631,6 +631,8 @@ extern int ttm_tt_init(struct ttm_tt *ttm, struct ttm_bo_device *bdev, unsigned long size, uint32_t page_flags); extern int ttm_dma_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_bo_device *bdev, unsigned long size, uint32_t page_flags); +extern int ttm_sg_tt_init(struct ttm_dma_tt *ttm_dma, struct ttm_bo_device *bdev, + unsigned long size, uint32_t page_flags); /** * ttm_tt_fini -- 2.7.4