On Fri, 30 Apr 2021 at 10:25, Christian König <ckoenig.leichtzumerken@xxxxxxxxx> wrote: > > Similar to the TTM range manager. > > Signed-off-by: Christian König <christian.koenig@xxxxxxx> > --- > drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c | 51 ++++++++++++-------- > 1 file changed, 30 insertions(+), 21 deletions(-) > > diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c > index bb01e0fc621c..d59ec07c77bb 100644 > --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c > +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c > @@ -23,6 +23,8 @@ > */ > > #include <linux/dma-mapping.h> > +#include <drm/ttm/ttm_range_manager.h> > + > #include "amdgpu.h" > #include "amdgpu_vm.h" > #include "amdgpu_res_cursor.h" > @@ -367,9 +369,9 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > struct amdgpu_vram_mgr *mgr = to_vram_mgr(man); > struct amdgpu_device *adev = to_amdgpu_device(mgr); > uint64_t vis_usage = 0, mem_bytes, max_bytes; > + struct ttm_range_mgr_node *node; > struct drm_mm *mm = &mgr->mm; > enum drm_mm_insert_mode mode; > - struct drm_mm_node *nodes; > unsigned i; > int r; > > @@ -384,8 +386,8 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > /* bail out quickly if there's likely not enough VRAM for this BO */ > mem_bytes = (u64)mem->num_pages << PAGE_SHIFT; > if (atomic64_add_return(mem_bytes, &mgr->usage) > max_bytes) { > - atomic64_sub(mem_bytes, &mgr->usage); > - return -ENOSPC; > + r = -ENOSPC; > + goto error_sub; > } > > if (place->flags & TTM_PL_FLAG_CONTIGUOUS) { > @@ -403,13 +405,15 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > num_nodes = DIV_ROUND_UP(mem->num_pages, pages_per_node); > } > > - nodes = kvmalloc_array((uint32_t)num_nodes, sizeof(*nodes), > - GFP_KERNEL | __GFP_ZERO); > - if (!nodes) { > - atomic64_sub(mem_bytes, &mgr->usage); > - return -ENOMEM; > + node = kvmalloc(struct_size(node, mm_nodes, num_nodes), > + GFP_KERNEL | __GFP_ZERO); Alignment. > + if (!node) { > + r = -ENOMEM; > + goto error_sub; > } > > + ttm_resource_init(tbo, place, &node->base); > + > mode = DRM_MM_INSERT_BEST; > if (place->flags & TTM_PL_FLAG_TOPDOWN) > mode = DRM_MM_INSERT_HIGH; > @@ -428,8 +432,9 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > if (pages >= pages_per_node) > alignment = pages_per_node; > > - r = drm_mm_insert_node_in_range(mm, &nodes[i], pages, alignment, > - 0, place->fpfn, lpfn, mode); > + r = drm_mm_insert_node_in_range(mm, &node->mm_nodes[i], pages, > + alignment, 0, place->fpfn, > + lpfn, mode); > if (unlikely(r)) { > if (pages > pages_per_node) { > if (is_power_of_2(pages)) > @@ -438,11 +443,11 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > pages = rounddown_pow_of_two(pages); > continue; > } > - goto error; > + goto error_free; > } > > - vis_usage += amdgpu_vram_mgr_vis_size(adev, &nodes[i]); > - amdgpu_vram_mgr_virt_start(mem, &nodes[i]); > + vis_usage += amdgpu_vram_mgr_vis_size(adev, &node->mm_nodes[i]); > + amdgpu_vram_mgr_virt_start(mem, &node->mm_nodes[i]); > pages_left -= pages; > ++i; > > @@ -455,16 +460,17 @@ static int amdgpu_vram_mgr_new(struct ttm_resource_manager *man, > mem->placement |= TTM_PL_FLAG_CONTIGUOUS; > > atomic64_add(vis_usage, &mgr->vis_usage); > - mem->mm_node = nodes; > + mem->mm_node = &node->mm_nodes[0]; > return 0; > > -error: > +error_free: > while (i--) > - drm_mm_remove_node(&nodes[i]); > + drm_mm_remove_node(&node->mm_nodes[i]); > spin_unlock(&mgr->lock); > - atomic64_sub(mem->num_pages << PAGE_SHIFT, &mgr->usage); > + kvfree(node); > > - kvfree(nodes); > +error_sub: > + atomic64_sub(mem_bytes, &mgr->usage); > return r; > } > > @@ -481,13 +487,17 @@ static void amdgpu_vram_mgr_del(struct ttm_resource_manager *man, > { > struct amdgpu_vram_mgr *mgr = to_vram_mgr(man); > struct amdgpu_device *adev = to_amdgpu_device(mgr); > - struct drm_mm_node *nodes = mem->mm_node; > + struct ttm_range_mgr_node *node; > uint64_t usage = 0, vis_usage = 0; > unsigned pages = mem->num_pages; > + struct drm_mm_node *nodes; > > if (!mem->mm_node) > return; > > + node = to_ttm_range_mgr_node(mem); > + nodes = &node->mm_nodes[0]; > + > spin_lock(&mgr->lock); > while (pages) { > pages -= nodes->size; > @@ -502,8 +512,7 @@ static void amdgpu_vram_mgr_del(struct ttm_resource_manager *man, > atomic64_sub(usage, &mgr->usage); > atomic64_sub(vis_usage, &mgr->vis_usage); > > - kvfree(mem->mm_node); > - mem->mm_node = NULL; Not worth keeping the mm_node = NULL? Reviewed-by: Matthew Auld <matthew.auld@xxxxxxxxx> > + kvfree(node); > } > > /** > -- > 2.25.1 > _______________________________________________ dri-devel mailing list dri-devel@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/dri-devel