Skip to content

Commit

Permalink
drm/i915/ttm: Use TTM for system memory
Browse files Browse the repository at this point in the history
For discrete, use TTM for both cached and WC system memory. That means
we currently rely on the TTM memory accounting / shrinker. For cached
system memory we should consider remaining shmem-backed, which can be
implemented from our ttm_tt_populate callback. We can then also reuse our
own very elaborate shrinker for that memory.

If an object is evicted to a gem allowable region, we will now consider
the object migrated, and we flip the gem region and move the object to a
different region list. Since we are now changing gem regions, we can't
any longer rely on the CONTIGUOUS flag being set based on the region
min page size, so remove that flag update. If we want to reintroduce it,
we need to put it in the mutable flags.

Signed-off-by: Thomas Hellström <thomas.hellstrom@linux.intel.com>
Reviewed-by: Matthew Auld <matthew.auld@intel.com>
Signed-off-by: Matthew Auld <matthew.auld@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20210624084240.270219-4-thomas.hellstrom@linux.intel.com
  • Loading branch information
Thomas Hellström authored and Matthew Auld committed Jun 24, 2021
1 parent 3c2b8f3 commit 32b7cf5
Show file tree
Hide file tree
Showing 6 changed files with 58 additions and 18 deletions.
4 changes: 0 additions & 4 deletions drivers/gpu/drm/i915/gem/i915_gem_region.c
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,7 @@ void i915_gem_object_init_memory_region(struct drm_i915_gem_object *obj,
{
obj->mm.region = intel_memory_region_get(mem);

if (obj->base.size <= mem->min_page_size)
obj->flags |= I915_BO_ALLOC_CONTIGUOUS;

mutex_lock(&mem->objects.lock);

list_add(&obj->mm.region_link, &mem->objects.list);
mutex_unlock(&mem->objects.lock);
}
Expand Down
2 changes: 2 additions & 0 deletions drivers/gpu/drm/i915/gem/i915_gem_shmem.c
Original file line number Diff line number Diff line change
Expand Up @@ -302,6 +302,7 @@ void i915_gem_object_put_pages_shmem(struct drm_i915_gem_object *obj, struct sg_
struct pagevec pvec;
struct page *page;

GEM_WARN_ON(IS_DGFX(to_i915(obj->base.dev)));
__i915_gem_object_release_shmem(obj, pages, true);

i915_gem_gtt_finish_pages(obj, pages);
Expand Down Expand Up @@ -560,6 +561,7 @@ i915_gem_object_create_shmem_from_data(struct drm_i915_private *dev_priv,
resource_size_t offset;
int err;

GEM_WARN_ON(IS_DGFX(dev_priv));
obj = i915_gem_object_create_shmem(dev_priv, round_up(size, PAGE_SIZE));
if (IS_ERR(obj))
return obj;
Expand Down
52 changes: 42 additions & 10 deletions drivers/gpu/drm/i915/gem/i915_gem_ttm.c
Original file line number Diff line number Diff line change
Expand Up @@ -286,6 +286,26 @@ static void i915_ttm_adjust_gem_after_move(struct drm_i915_gem_object *obj)
{
struct ttm_buffer_object *bo = i915_gem_to_ttm(obj);
unsigned int cache_level;
unsigned int i;

/*
* If object was moved to an allowable region, update the object
* region to consider it migrated. Note that if it's currently not
* in an allowable region, it's evicted and we don't update the
* object region.
*/
if (intel_region_to_ttm_type(obj->mm.region) != bo->resource->mem_type) {
for (i = 0; i < obj->mm.n_placements; ++i) {
struct intel_memory_region *mr = obj->mm.placements[i];

if (intel_region_to_ttm_type(mr) == bo->resource->mem_type &&
mr != obj->mm.region) {
i915_gem_object_release_memory_region(obj);
i915_gem_object_init_memory_region(obj, mr);
break;
}
}
}

obj->mem_flags &= ~(I915_BO_FLAG_STRUCT_PAGE | I915_BO_FLAG_IOMEM);

Expand Down Expand Up @@ -615,13 +635,6 @@ static int i915_ttm_get_pages(struct drm_i915_gem_object *obj)
/* Move to the requested placement. */
i915_ttm_placement_from_obj(obj, &requested, busy, &placement);

/*
* For now we support LMEM only with TTM.
* TODO: Remove with system support
*/
GEM_BUG_ON(requested.mem_type < I915_PL_LMEM0 ||
busy[0].mem_type < I915_PL_LMEM0);

/* First try only the requested placement. No eviction. */
real_num_busy = fetch_and_zero(&placement.num_busy_placement);
ret = ttm_bo_validate(bo, &placement, &ctx);
Expand All @@ -635,9 +648,6 @@ static int i915_ttm_get_pages(struct drm_i915_gem_object *obj)
ret == -EAGAIN)
return ret;

/* TODO: Remove this when we support system as TTM. */
real_num_busy = 1;

/*
* If the initial attempt fails, allow all accepted placements,
* evicting if necessary.
Expand Down Expand Up @@ -873,3 +883,25 @@ int __i915_gem_ttm_object_init(struct intel_memory_region *mem,

return 0;
}

static const struct intel_memory_region_ops ttm_system_region_ops = {
.init_object = __i915_gem_ttm_object_init,
};

struct intel_memory_region *
i915_gem_ttm_system_setup(struct drm_i915_private *i915,
u16 type, u16 instance)
{
struct intel_memory_region *mr;

mr = intel_memory_region_create(i915, 0,
totalram_pages() << PAGE_SHIFT,
PAGE_SIZE, 0,
type, instance,
&ttm_system_region_ops);
if (IS_ERR(mr))
return mr;

intel_memory_region_set_name(mr, "system-ttm");
return mr;
}
3 changes: 0 additions & 3 deletions drivers/gpu/drm/i915/i915_drv.h
Original file line number Diff line number Diff line change
Expand Up @@ -1751,9 +1751,6 @@ void i915_gem_cleanup_userptr(struct drm_i915_private *dev_priv);
void i915_gem_init_early(struct drm_i915_private *dev_priv);
void i915_gem_cleanup_early(struct drm_i915_private *dev_priv);

struct intel_memory_region *i915_gem_shmem_setup(struct drm_i915_private *i915,
u16 type, u16 instance);

static inline void i915_gem_drain_freed_objects(struct drm_i915_private *i915)
{
/*
Expand Down
7 changes: 6 additions & 1 deletion drivers/gpu/drm/i915/intel_memory_region.c
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,12 @@ int intel_memory_regions_hw_probe(struct drm_i915_private *i915)
instance = intel_region_map[i].instance;
switch (type) {
case INTEL_MEMORY_SYSTEM:
mem = i915_gem_shmem_setup(i915, type, instance);
if (IS_DGFX(i915))
mem = i915_gem_ttm_system_setup(i915, type,
instance);
else
mem = i915_gem_shmem_setup(i915, type,
instance);
break;
case INTEL_MEMORY_STOLEN_LOCAL:
mem = i915_gem_stolen_lmem_setup(i915, type, instance);
Expand Down
8 changes: 8 additions & 0 deletions drivers/gpu/drm/i915/intel_memory_region.h
Original file line number Diff line number Diff line change
Expand Up @@ -125,4 +125,12 @@ intel_memory_region_set_name(struct intel_memory_region *mem,
int intel_memory_region_reserve(struct intel_memory_region *mem,
resource_size_t offset,
resource_size_t size);

struct intel_memory_region *
i915_gem_ttm_system_setup(struct drm_i915_private *i915,
u16 type, u16 instance);
struct intel_memory_region *
i915_gem_shmem_setup(struct drm_i915_private *i915,
u16 type, u16 instance);

#endif

0 comments on commit 32b7cf5

Please sign in to comment.