All of lore.kernel.org
 help / color / mirror / Atom feed
From: Tvrtko Ursulin <tursulin@ursulin.net>
To: igt-dev@lists.freedesktop.org
Cc: Intel-gfx@lists.freedesktop.org,
	Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Subject: [igt-dev] [CI i-g-t 1/2] tests/gem_exec_latency: New subtests for checking submission from RT tasks
Date: Tue, 17 Apr 2018 09:41:11 +0100	[thread overview]
Message-ID: <20180417084112.8352-1-tvrtko.ursulin@linux.intel.com> (raw)

From: Tvrtko Ursulin <tvrtko.ursulin@intel.com>

We want to make sure RT tasks which use a lot of CPU times can submit
batch buffers with roughly the same latency (and certainly not worse)
compared to normal tasks.

Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Cc: Chris Wilson <chris@chris-wilson.co.uk>
---
 tests/gem_exec_latency.c | 176 +++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 176 insertions(+)

diff --git a/tests/gem_exec_latency.c b/tests/gem_exec_latency.c
index 9498c0921e60..420ede0f83a0 100644
--- a/tests/gem_exec_latency.c
+++ b/tests/gem_exec_latency.c
@@ -36,11 +36,15 @@
 #include <sys/time.h>
 #include <sys/signal.h>
 #include <time.h>
+#include <sched.h>
 
 #include "drm.h"
 
 #include "igt_sysfs.h"
 #include "igt_vgem.h"
+#include "igt_dummyload.h"
+#include "igt_stats.h"
+
 #include "i915/gem_ring.h"
 
 #define LOCAL_I915_EXEC_NO_RELOC (1<<11)
@@ -351,6 +355,172 @@ static void latency_from_ring(int fd,
 	}
 }
 
+static void __rearm_spin_batch(igt_spin_t *spin)
+{
+	const uint32_t mi_arb_chk = 0x5 << 23;
+
+       *spin->batch = mi_arb_chk;
+       *spin->running = 0;
+       __sync_synchronize();
+}
+
+static void
+__submit_spin_batch(int fd, igt_spin_t *spin, unsigned int flags)
+{
+	struct drm_i915_gem_execbuffer2 eb = spin->execbuf;
+
+	eb.flags &= ~(0x3f | I915_EXEC_BSD_MASK);
+	eb.flags |= flags | I915_EXEC_NO_RELOC;
+
+	gem_execbuf(fd, &eb);
+}
+
+struct rt_pkt
+{
+#define RT_OK (0)
+#define RT_FAIL (1)
+#define RT_TIMEOUT (2)
+	int status;
+	struct igt_mean mean;
+	double max;
+};
+
+static void __spin_wait(struct rt_pkt *msg, igt_spin_t *spin, double *t_wait)
+{
+	struct timespec ts = { };
+	uint64_t t_last = 0;
+
+	igt_nsec_elapsed(&ts);
+
+	while (!READ_ONCE(*spin->running)) {
+		uint64_t t = igt_nsec_elapsed(&ts);
+
+		if ((t - t_last) > 5UL * NSEC_PER_SEC) {
+			 /* Absolute timeout to save time. */
+			msg->status = RT_TIMEOUT;
+		} else if ((t - t_last) > NSEC_PER_SEC / 10) {
+			/* Backoff every 100ms to give it chance to complete. */
+			t_last = t;
+			usleep(1);
+		}
+	}
+
+	*t_wait = igt_nsec_elapsed(&ts) / 1e9;
+
+	msg->status = RT_OK;
+}
+
+/*
+ * Test whether RT thread which hogs the CPU a lot can submit work with
+ * reasonable latency.
+ */
+static void
+rthog_latency_on_ring(int fd, unsigned int ring, const char *name)
+{
+	const char *passname[] = { "warmup", "normal", "rt" };
+	struct rt_pkt res[3];
+	unsigned int i;
+	int link[2];
+	int ret;
+
+	igt_require(gem_can_store_dword(fd, ring));
+
+	igt_assert(pipe(link) == 0);
+
+	memset(res, 0, sizeof(res));
+
+        igt_fork(child, 1) {
+		unsigned int pass = 0; /* Three passes: warmup, normal, rt. */
+
+		do {
+			struct rt_pkt msg = { };
+			igt_spin_t *spin;
+
+			igt_mean_init(&msg.mean);
+
+			if (pass == 2) {
+				struct sched_param rt =
+						{ .sched_priority = 99 };
+
+				ret = sched_setscheduler(0,
+							SCHED_FIFO | SCHED_RESET_ON_FORK,
+							&rt);
+				if (ret) {
+					igt_warn("Failed to set scheduling policy!\n");
+					msg.status = RT_FAIL;
+					write(link[1], &msg, sizeof(msg));
+					exit(1);
+				}
+			}
+
+			spin = __igt_spin_batch_new_poll(fd, 0, ring);
+			if (!spin) {
+				igt_warn("Failed to create spinner! (%s)\n",
+					 passname[pass]);
+				msg.status = RT_FAIL;
+				write(link[1], &msg, sizeof(msg));
+				exit(1);
+			}
+			igt_spin_busywait_until_running(spin);
+
+			igt_until_timeout(pass > 0 ? 5 : 2) {
+				double t;
+
+				igt_spin_batch_end(spin);
+				gem_sync(fd, spin->handle);
+
+				__rearm_spin_batch(spin);
+				__submit_spin_batch(fd, spin, ring);
+
+				__spin_wait(&msg, spin, &t);
+				if (msg.status != RT_OK) {
+					igt_warn("Wait timeout! (%s)\n",
+						 passname[pass]);
+					write(link[1], &msg, sizeof(msg));
+					exit(1);
+				}
+
+				if (t > msg.max)
+					msg.max = t;
+
+				igt_mean_add(&msg.mean, t);
+			}
+
+			igt_spin_batch_free(fd, spin);
+
+			igt_info("%10s: mean=%.2fus variance=%.2fus max=%.2fus (n=%lu)\n",
+				 passname[pass],
+				 igt_mean_get(&msg.mean) * 1e6,
+				 igt_mean_get_variance(&msg.mean) * 1e6,
+				 msg.max * 1e6,
+				 msg.mean.count);
+
+			write(link[1], &msg, sizeof(msg));
+		} while (++pass < 3);
+
+		exit(0);
+	}
+
+	for (i = 0; i < 3; i++) {
+		ret = read(link[0], &res[i], sizeof(res[0]));
+		igt_assert_eq(ret, sizeof(res[0]));
+
+		igt_assert_eq(res[i].status, RT_OK);
+	}
+
+	close(link[0]);
+	close(link[1]);
+
+	igt_waitchildren();
+
+	/*
+	 * Check that the submission latency variance for a task with RT
+	 * priority is no larger than three times the same of a normal task.
+	 */
+	igt_assert(igt_mean_get_variance(&res[2].mean) <
+		   igt_mean_get_variance(&res[1].mean) * 3);
+}
+
 igt_main
 {
 	const struct intel_execution_engine *e;
@@ -391,6 +561,12 @@ igt_main
 							e->exec_id | e->flags,
 							e->name, 0);
 
+				igt_subtest_f("%s-rthog-submit", e->name)
+					rthog_latency_on_ring(device,
+							      e->exec_id |
+							      e->flags,
+							      e->name);
+
 				igt_subtest_f("%s-dispatch-queued", e->name)
 					latency_on_ring(device,
 							e->exec_id | e->flags,
-- 
2.14.1

_______________________________________________
igt-dev mailing list
igt-dev@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/igt-dev

WARNING: multiple messages have this Message-ID (diff)
From: Tvrtko Ursulin <tursulin@ursulin.net>
To: igt-dev@lists.freedesktop.org
Cc: Intel-gfx@lists.freedesktop.org
Subject: [CI i-g-t 1/2] tests/gem_exec_latency: New subtests for checking submission from RT tasks
Date: Tue, 17 Apr 2018 09:41:11 +0100	[thread overview]
Message-ID: <20180417084112.8352-1-tvrtko.ursulin@linux.intel.com> (raw)

From: Tvrtko Ursulin <tvrtko.ursulin@intel.com>

We want to make sure RT tasks which use a lot of CPU times can submit
batch buffers with roughly the same latency (and certainly not worse)
compared to normal tasks.

Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Cc: Chris Wilson <chris@chris-wilson.co.uk>
---
 tests/gem_exec_latency.c | 176 +++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 176 insertions(+)

diff --git a/tests/gem_exec_latency.c b/tests/gem_exec_latency.c
index 9498c0921e60..420ede0f83a0 100644
--- a/tests/gem_exec_latency.c
+++ b/tests/gem_exec_latency.c
@@ -36,11 +36,15 @@
 #include <sys/time.h>
 #include <sys/signal.h>
 #include <time.h>
+#include <sched.h>
 
 #include "drm.h"
 
 #include "igt_sysfs.h"
 #include "igt_vgem.h"
+#include "igt_dummyload.h"
+#include "igt_stats.h"
+
 #include "i915/gem_ring.h"
 
 #define LOCAL_I915_EXEC_NO_RELOC (1<<11)
@@ -351,6 +355,172 @@ static void latency_from_ring(int fd,
 	}
 }
 
+static void __rearm_spin_batch(igt_spin_t *spin)
+{
+	const uint32_t mi_arb_chk = 0x5 << 23;
+
+       *spin->batch = mi_arb_chk;
+       *spin->running = 0;
+       __sync_synchronize();
+}
+
+static void
+__submit_spin_batch(int fd, igt_spin_t *spin, unsigned int flags)
+{
+	struct drm_i915_gem_execbuffer2 eb = spin->execbuf;
+
+	eb.flags &= ~(0x3f | I915_EXEC_BSD_MASK);
+	eb.flags |= flags | I915_EXEC_NO_RELOC;
+
+	gem_execbuf(fd, &eb);
+}
+
+struct rt_pkt
+{
+#define RT_OK (0)
+#define RT_FAIL (1)
+#define RT_TIMEOUT (2)
+	int status;
+	struct igt_mean mean;
+	double max;
+};
+
+static void __spin_wait(struct rt_pkt *msg, igt_spin_t *spin, double *t_wait)
+{
+	struct timespec ts = { };
+	uint64_t t_last = 0;
+
+	igt_nsec_elapsed(&ts);
+
+	while (!READ_ONCE(*spin->running)) {
+		uint64_t t = igt_nsec_elapsed(&ts);
+
+		if ((t - t_last) > 5UL * NSEC_PER_SEC) {
+			 /* Absolute timeout to save time. */
+			msg->status = RT_TIMEOUT;
+		} else if ((t - t_last) > NSEC_PER_SEC / 10) {
+			/* Backoff every 100ms to give it chance to complete. */
+			t_last = t;
+			usleep(1);
+		}
+	}
+
+	*t_wait = igt_nsec_elapsed(&ts) / 1e9;
+
+	msg->status = RT_OK;
+}
+
+/*
+ * Test whether RT thread which hogs the CPU a lot can submit work with
+ * reasonable latency.
+ */
+static void
+rthog_latency_on_ring(int fd, unsigned int ring, const char *name)
+{
+	const char *passname[] = { "warmup", "normal", "rt" };
+	struct rt_pkt res[3];
+	unsigned int i;
+	int link[2];
+	int ret;
+
+	igt_require(gem_can_store_dword(fd, ring));
+
+	igt_assert(pipe(link) == 0);
+
+	memset(res, 0, sizeof(res));
+
+        igt_fork(child, 1) {
+		unsigned int pass = 0; /* Three passes: warmup, normal, rt. */
+
+		do {
+			struct rt_pkt msg = { };
+			igt_spin_t *spin;
+
+			igt_mean_init(&msg.mean);
+
+			if (pass == 2) {
+				struct sched_param rt =
+						{ .sched_priority = 99 };
+
+				ret = sched_setscheduler(0,
+							SCHED_FIFO | SCHED_RESET_ON_FORK,
+							&rt);
+				if (ret) {
+					igt_warn("Failed to set scheduling policy!\n");
+					msg.status = RT_FAIL;
+					write(link[1], &msg, sizeof(msg));
+					exit(1);
+				}
+			}
+
+			spin = __igt_spin_batch_new_poll(fd, 0, ring);
+			if (!spin) {
+				igt_warn("Failed to create spinner! (%s)\n",
+					 passname[pass]);
+				msg.status = RT_FAIL;
+				write(link[1], &msg, sizeof(msg));
+				exit(1);
+			}
+			igt_spin_busywait_until_running(spin);
+
+			igt_until_timeout(pass > 0 ? 5 : 2) {
+				double t;
+
+				igt_spin_batch_end(spin);
+				gem_sync(fd, spin->handle);
+
+				__rearm_spin_batch(spin);
+				__submit_spin_batch(fd, spin, ring);
+
+				__spin_wait(&msg, spin, &t);
+				if (msg.status != RT_OK) {
+					igt_warn("Wait timeout! (%s)\n",
+						 passname[pass]);
+					write(link[1], &msg, sizeof(msg));
+					exit(1);
+				}
+
+				if (t > msg.max)
+					msg.max = t;
+
+				igt_mean_add(&msg.mean, t);
+			}
+
+			igt_spin_batch_free(fd, spin);
+
+			igt_info("%10s: mean=%.2fus variance=%.2fus max=%.2fus (n=%lu)\n",
+				 passname[pass],
+				 igt_mean_get(&msg.mean) * 1e6,
+				 igt_mean_get_variance(&msg.mean) * 1e6,
+				 msg.max * 1e6,
+				 msg.mean.count);
+
+			write(link[1], &msg, sizeof(msg));
+		} while (++pass < 3);
+
+		exit(0);
+	}
+
+	for (i = 0; i < 3; i++) {
+		ret = read(link[0], &res[i], sizeof(res[0]));
+		igt_assert_eq(ret, sizeof(res[0]));
+
+		igt_assert_eq(res[i].status, RT_OK);
+	}
+
+	close(link[0]);
+	close(link[1]);
+
+	igt_waitchildren();
+
+	/*
+	 * Check that the submission latency variance for a task with RT
+	 * priority is no larger than three times the same of a normal task.
+	 */
+	igt_assert(igt_mean_get_variance(&res[2].mean) <
+		   igt_mean_get_variance(&res[1].mean) * 3);
+}
+
 igt_main
 {
 	const struct intel_execution_engine *e;
@@ -391,6 +561,12 @@ igt_main
 							e->exec_id | e->flags,
 							e->name, 0);
 
+				igt_subtest_f("%s-rthog-submit", e->name)
+					rthog_latency_on_ring(device,
+							      e->exec_id |
+							      e->flags,
+							      e->name);
+
 				igt_subtest_f("%s-dispatch-queued", e->name)
 					latency_on_ring(device,
 							e->exec_id | e->flags,
-- 
2.14.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

             reply	other threads:[~2018-04-17  8:41 UTC|newest]

Thread overview: 15+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-04-17  8:41 Tvrtko Ursulin [this message]
2018-04-17  8:41 ` [CI i-g-t 1/2] tests/gem_exec_latency: New subtests for checking submission from RT tasks Tvrtko Ursulin
2018-04-17  8:41 ` [igt-dev] [CI i-g-t 2/2] HACK enable new test Tvrtko Ursulin
2018-04-17  8:41   ` Tvrtko Ursulin
2018-04-17 10:12 ` [igt-dev] [CI i-g-t 1/2] tests/gem_exec_latency: New subtests for checking submission from RT tasks Chris Wilson
2018-04-17 10:12   ` Chris Wilson
2018-04-18  8:17 ` [igt-dev] " Chris Wilson
2018-04-18  8:17   ` Chris Wilson
2018-04-19 10:48 ` [igt-dev] ✓ Fi.CI.BAT: success for series starting with [CI,i-g-t,1/2] " Patchwork
2018-04-19 11:30 ` Patchwork
2018-04-19 13:37 ` [igt-dev] ✗ Fi.CI.IGT: failure " Patchwork
2018-04-19 14:53 ` [igt-dev] ✓ Fi.CI.IGT: success " Patchwork
2018-05-10  9:30 ` [igt-dev] [PATCH i-g-t] igt/gem_exec_latency: Report stddev for rthog Chris Wilson
2018-05-10  9:30   ` Chris Wilson
2018-05-10  9:34 ` [igt-dev] ✗ Fi.CI.BAT: failure for series starting with [i-g-t] igt/gem_exec_latency: Report stddev for rthog (rev2) Patchwork

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20180417084112.8352-1-tvrtko.ursulin@linux.intel.com \
    --to=tursulin@ursulin.net \
    --cc=Intel-gfx@lists.freedesktop.org \
    --cc=igt-dev@lists.freedesktop.org \
    --cc=tvrtko.ursulin@intel.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.