[i-g-t] i915/gem_exec_reloc: Check that relocations do not block
diff mbox series

Message ID 20191113225920.7279-1-chris@chris-wilson.co.uk
State New
Headers show
Series
  • [i-g-t] i915/gem_exec_reloc: Check that relocations do not block
Related show

Commit Message

Chris Wilson Nov. 13, 2019, 10:59 p.m. UTC
With GPU relocations we avoid blocking inside execbuf and prevent
priority inversions where a low priority client can cause a denial of
service to higher priority clients.

Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Cc: Mika Kuoppala <mika.kuoppala@linux.intel.com>
---
 tests/i915/gem_exec_reloc.c | 45 +++++++++++++++++++++++++++++++++++++
 1 file changed, 45 insertions(+)

Patch
diff mbox series

diff --git a/tests/i915/gem_exec_reloc.c b/tests/i915/gem_exec_reloc.c
index 5f59fe99f..3c2c7d31d 100644
--- a/tests/i915/gem_exec_reloc.c
+++ b/tests/i915/gem_exec_reloc.c
@@ -324,6 +324,49 @@  static void active(int fd, unsigned engine)
 	gem_close(fd, obj[0].handle);
 }
 
+static unsigned int offset_in_page(void *addr)
+{
+	return (uintptr_t)addr & 4095;
+}
+
+static void active_spin(int fd, unsigned engine)
+{
+	const uint32_t bbe = MI_BATCH_BUFFER_END;
+	struct drm_i915_gem_relocation_entry reloc;
+	struct drm_i915_gem_exec_object2 obj[2];
+	struct drm_i915_gem_execbuffer2 execbuf;
+	igt_spin_t *spin;
+
+	spin = igt_spin_new(fd, .engine = engine);
+
+	memset(obj, 0, sizeof(obj));
+	obj[0] = spin->obj[IGT_SPIN_BATCH];
+	obj[0].relocs_ptr = to_user_pointer(&reloc);
+	obj[0].relocation_count = 1;
+	obj[1].handle = gem_create(fd, 4096);
+	gem_write(fd, obj[1].handle, 0, &bbe, sizeof(bbe));
+
+	memset(&reloc, 0, sizeof(reloc));
+	reloc.presumed_offset = -1;
+	reloc.offset = offset_in_page(spin->condition);
+	reloc.target_handle = obj[0].handle;
+
+	memset(&execbuf, 0, sizeof(execbuf));
+	execbuf.buffers_ptr = to_user_pointer(obj);
+	execbuf.buffer_count = 2;
+	execbuf.flags = engine;
+
+	gem_execbuf(fd, &execbuf);
+	gem_close(fd, obj[1].handle);
+	igt_assert_eq(*spin->condition, spin->cmd_precondition);
+
+	igt_spin_end(spin);
+	gem_sync(fd, spin->handle);
+
+	igt_assert_eq(*spin->condition, obj[0].offset);
+	igt_spin_free(fd, spin);
+}
+
 static bool has_64b_reloc(int fd)
 {
 	return intel_gen(intel_get_drm_devid(fd)) >= 8;
@@ -755,6 +798,8 @@  igt_main
 	     e->name; e++) {
 		igt_subtest_f("active-%s", e->name)
 			active(fd, eb_ring(e));
+		igt_subtest_f("spin-%s", e->name)
+			active_spin(fd, eb_ring(e));
 	}
 	igt_fixture
 		close(fd);