Same test as previously for the per-process GTT instead applied to the global GTT. Signed-off-by: Chris Wilson <chris@xxxxxxxxxxxxxxxxxx> --- drivers/gpu/drm/i915/selftests/i915_gem_gtt.c | 118 +++++++++++++++++++------- 1 file changed, 88 insertions(+), 30 deletions(-) diff --git a/drivers/gpu/drm/i915/selftests/i915_gem_gtt.c b/drivers/gpu/drm/i915/selftests/i915_gem_gtt.c index 5d0e6f60bea7..8ed88f438eef 100644 --- a/drivers/gpu/drm/i915/selftests/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/selftests/i915_gem_gtt.c @@ -25,6 +25,7 @@ #include <linux/prime_numbers.h> #include "i915_selftest.h" +#include "fake_drm.h" #include "huge_gem_object.h" static int igt_ppgtt_alloc(void *arg) @@ -94,35 +95,25 @@ static struct i915_vma *vma_lookup(struct drm_i915_gem_object *obj, return i915_gem_obj_lookup_or_create_vma(obj, vm, NULL); } -static int igt_ppgtt_fill(void *arg) +static int fill_hole(struct drm_i915_private *i915, + struct i915_address_space *vm, + u64 hole_start, u64 hole_end) { - struct drm_i915_private *dev_priv = arg; unsigned long npages, max_pages = 1 << 20, prime; + u64 hole_size = hole_end - hole_start; struct drm_i915_gem_object *obj, *on; - struct i915_hw_ppgtt *ppgtt; struct i915_vma *vma; LIST_HEAD(objects); - int err = 0; - - if (!USES_FULL_PPGTT(dev_priv)) - return 0; - - mutex_lock(&dev_priv->drm.struct_mutex); - ppgtt = i915_ppgtt_create(dev_priv, NULL, "mock"); - if (IS_ERR(ppgtt)) { - err = PTR_ERR(ppgtt); - goto err_unlock; - } - GEM_BUG_ON(ppgtt->base.total & ~PAGE_MASK); + int err; - max_pages = min_t(u64, max_pages, ppgtt->base.total/2 >> PAGE_SHIFT); + max_pages = min_t(u64, max_pages, hole_size/2 >> PAGE_SHIFT); for_each_prime_number_from(prime, 2, 13) { for (npages = 1; npages <= max_pages; npages *= prime) { u64 flags; GEM_BUG_ON(!npages); - obj = huge_gem_object(dev_priv, + obj = huge_gem_object(i915, PAGE_SIZE, npages << PAGE_SHIFT); if (IS_ERR(obj)) @@ -131,9 +122,9 @@ static int igt_ppgtt_fill(void *arg) list_add(&obj->batch_pool_link, &objects); /* Fill the GTT top down - hope we don't overstep the end */ - flags = ppgtt->base.total | PIN_OFFSET_FIXED | PIN_USER; + flags = hole_end | PIN_OFFSET_FIXED | PIN_USER; list_for_each_entry(obj, &objects, batch_pool_link) { - vma = vma_lookup(obj, &ppgtt->base); + vma = vma_lookup(obj, vm); if (IS_ERR(vma)) continue; @@ -147,9 +138,9 @@ static int igt_ppgtt_fill(void *arg) i915_vma_unpin(vma); } - flags = ppgtt->base.total | PIN_OFFSET_FIXED | PIN_USER; + flags = hole_end | PIN_OFFSET_FIXED | PIN_USER; list_for_each_entry(obj, &objects, batch_pool_link) { - vma = vma_lookup(obj, &ppgtt->base); + vma = vma_lookup(obj, vm); if (IS_ERR(vma)) continue; @@ -173,9 +164,9 @@ static int igt_ppgtt_fill(void *arg) } /* And again from the bottom */ - flags = PIN_OFFSET_FIXED | PIN_USER; + flags = hole_start | PIN_OFFSET_FIXED | PIN_USER; list_for_each_entry(obj, &objects, batch_pool_link) { - vma = vma_lookup(obj, &ppgtt->base); + vma = vma_lookup(obj, vm); if (IS_ERR(vma)) continue; @@ -189,9 +180,9 @@ static int igt_ppgtt_fill(void *arg) flags += obj->base.size; } - flags = PIN_OFFSET_FIXED | PIN_USER; + flags = hole_start | PIN_OFFSET_FIXED | PIN_USER; list_for_each_entry(obj, &objects, batch_pool_link) { - vma = vma_lookup(obj, &ppgtt->base); + vma = vma_lookup(obj, vm); if (IS_ERR(vma)) continue; @@ -218,28 +209,94 @@ static int igt_ppgtt_fill(void *arg) list_for_each_entry_safe(obj, on, &objects, batch_pool_link) { list_del(&obj->batch_pool_link); - vma = vma_lookup(obj, &ppgtt->base); - if (!IS_ERR(vma)) + vma = vma_lookup(obj, vm); + if (!IS_ERR(vma) && !i915_vma_is_ggtt(vma)) i915_vma_close(vma); i915_gem_object_put(obj); } } -err: + return 0; + +err: list_for_each_entry_safe(obj, on, &objects, batch_pool_link) { list_del(&obj->batch_pool_link); - vma = vma_lookup(obj, &ppgtt->base); - if (!IS_ERR(vma)) + vma = vma_lookup(obj, vm); + if (!IS_ERR(vma) && !i915_vma_is_ggtt(vma)) i915_vma_close(vma); i915_gem_object_put(obj); } + return err; +} + +static int igt_ppgtt_fill(void *arg) +{ + struct drm_i915_private *dev_priv = arg; + struct drm_file *file; + struct i915_hw_ppgtt *ppgtt; + int err; + + if (!USES_FULL_PPGTT(dev_priv)) + return 0; + + file = fake_file(dev_priv); + if (IS_ERR(file)) + return PTR_ERR(file); + + mutex_lock(&dev_priv->drm.struct_mutex); + ppgtt = i915_ppgtt_create(dev_priv, file->driver_priv, "mock"); + if (IS_ERR(ppgtt)) { + err = PTR_ERR(ppgtt); + goto err_unlock; + } + GEM_BUG_ON(ppgtt->base.total & ~PAGE_MASK); + + err = fill_hole(dev_priv, &ppgtt->base, 0, ppgtt->base.total); i915_ppgtt_close(&ppgtt->base); i915_ppgtt_put(ppgtt); err_unlock: mutex_unlock(&dev_priv->drm.struct_mutex); + + fake_file_free(dev_priv, file); + return err; +} + +static int igt_ggtt_fill(void *arg) +{ + struct drm_i915_private *i915 = arg; + struct i915_ggtt *ggtt = &i915->ggtt; + u64 hole_start = U64_MAX, hole_end = 0, hole_size = 0; + u64 this_start, this_end; + struct drm_mm_node *node; + int err; + + GEM_BUG_ON(ggtt->base.total & ~PAGE_MASK); + + mutex_lock(&i915->drm.struct_mutex); + drm_mm_for_each_hole(node, &ggtt->base.mm, this_start, this_end) { + u64 this_size; + + if (ggtt->base.mm.color_adjust) + ggtt->base. mm.color_adjust(node, 0, + &this_start, &this_end); + + this_size = this_end - this_start; + if (this_size > hole_size) { + hole_size = this_size; + hole_start = this_start; + hole_end = this_end; + } + } + pr_info("Found GGTT hole [%llx, %llx], size %llx\n", + hole_start, hole_end, hole_size); + GEM_BUG_ON(hole_start >= hole_end); + + err = fill_hole(i915, &ggtt->base, hole_start, hole_end); + mutex_unlock(&i915->drm.struct_mutex); + return err; } @@ -248,6 +305,7 @@ int i915_gem_gtt_live_selftests(struct drm_i915_private *i915) static const struct i915_subtest tests[] = { SUBTEST(igt_ppgtt_alloc), SUBTEST(igt_ppgtt_fill), + SUBTEST(igt_ggtt_fill), }; return i915_subtests(tests, i915); -- 2.11.0 _______________________________________________ Intel-gfx mailing list Intel-gfx@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/intel-gfx