[PATCH 43/59] track-engine

Chris Wilson chris at chris-wilson.co.uk
Thu Dec 27 14:19:10 UTC 2018


---
 drivers/gpu/drm/i915/i915_request.c           | 28 ++++++++---------
 drivers/gpu/drm/i915/i915_request.h           |  1 +
 drivers/gpu/drm/i915/intel_breadcrumbs.c      |  8 ++---
 drivers/gpu/drm/i915/intel_ringbuffer.h       | 31 +++++++++++--------
 .../drm/i915/selftests/intel_breadcrumbs.c    | 18 +++++------
 5 files changed, 46 insertions(+), 40 deletions(-)

diff --git a/drivers/gpu/drm/i915/i915_request.c b/drivers/gpu/drm/i915/i915_request.c
index 003054bef445..3f1e343bdf16 100644
--- a/drivers/gpu/drm/i915/i915_request.c
+++ b/drivers/gpu/drm/i915/i915_request.c
@@ -998,13 +998,13 @@ static bool busywait_stop(unsigned long timeout, unsigned int cpu)
 	return this_cpu != cpu;
 }
 
-static bool __i915_spin_request(const struct i915_request *rq,
-				u64 seqno, int state, unsigned long timeout_us)
+static bool __i915_spin_request(const struct i915_request * const rq,
+				const struct intel_wait * const w,
+				int state, unsigned long timeout_us)
 {
-	struct intel_engine_cs *engine = rq->engine;
 	unsigned int irq, cpu;
 
-	GEM_BUG_ON(!seqno);
+	GEM_BUG_ON(!w->global_seqno);
 
 	/*
 	 * Only wait for the request if we know it is likely to complete.
@@ -1017,7 +1017,7 @@ static bool __i915_spin_request(const struct i915_request *rq,
 	 * it is a fair assumption that it will not complete within our
 	 * relatively short timeout.
 	 */
-	if (!intel_engine_has_started(engine, seqno))
+	if (!intel_engine_has_started(w->engine, w->global_seqno))
 		return false;
 
 	/*
@@ -1031,11 +1031,11 @@ static bool __i915_spin_request(const struct i915_request *rq,
 	 * takes to sleep on a request, on the order of a microsecond.
 	 */
 
-	irq = READ_ONCE(engine->breadcrumbs.irq_count);
+	irq = READ_ONCE(w->engine->breadcrumbs.irq_count);
 	timeout_us += local_clock_us(&cpu);
 	do {
-		if (intel_engine_has_completed(engine, seqno))
-			return seqno == i915_request_global_seqno(rq);
+		if (intel_engine_has_completed(w->engine, w->global_seqno))
+			return w->global_seqno == i915_request_global_seqno(rq);
 
 		/*
 		 * Seqno are meant to be ordered *before* the interrupt. If
@@ -1043,7 +1043,7 @@ static bool __i915_spin_request(const struct i915_request *rq,
 		 * assume we won't see one in the near future but require
 		 * the engine->seqno_barrier() to fixup coherency.
 		 */
-		if (READ_ONCE(engine->breadcrumbs.irq_count) != irq)
+		if (READ_ONCE(w->engine->breadcrumbs.irq_count) != irq)
 			break;
 
 		if (signal_pending_state(state, current))
@@ -1151,11 +1151,11 @@ long i915_request_wait(struct i915_request *rq,
 	GEM_BUG_ON(!i915_sw_fence_signaled(&rq->submit));
 
 	/* Optimistic short spin before touching IRQs */
-	if (__i915_spin_request(rq, wait.global_seqno, state, 5))
+	if (__i915_spin_request(rq, &wait, state, 5))
 		goto complete;
 
 	set_current_state(state);
-	if (intel_engine_add_wait(rq->engine, &wait))
+	if (intel_engine_add_wait(&wait))
 		/*
 		 * In order to check that we haven't missed the interrupt
 		 * as we enabled it, we need to kick ourselves to do a
@@ -1205,16 +1205,16 @@ long i915_request_wait(struct i915_request *rq,
 			continue;
 
 		/* Only spin if we know the GPU is processing this request */
-		if (__i915_spin_request(rq, wait.global_seqno, state, 2))
+		if (__i915_spin_request(rq, &wait, state, 2))
 			break;
 
 		if (!intel_wait_check_request(&wait, rq)) {
-			intel_engine_remove_wait(rq->engine, &wait);
+			intel_engine_remove_wait(&wait);
 			goto restart;
 		}
 	}
 
-	intel_engine_remove_wait(rq->engine, &wait);
+	intel_engine_remove_wait(&wait);
 complete:
 	__set_current_state(TASK_RUNNING);
 	if (flags & I915_WAIT_LOCKED)
diff --git a/drivers/gpu/drm/i915/i915_request.h b/drivers/gpu/drm/i915/i915_request.h
index b5ecd4724cec..2a86c9626662 100644
--- a/drivers/gpu/drm/i915/i915_request.h
+++ b/drivers/gpu/drm/i915/i915_request.h
@@ -43,6 +43,7 @@ struct intel_wait {
 	struct rb_node node;
 	struct task_struct *tsk;
 	struct i915_request *request;
+	struct intel_engine_cs *engine;
 	u64 global_seqno;
 };
 
diff --git a/drivers/gpu/drm/i915/intel_breadcrumbs.c b/drivers/gpu/drm/i915/intel_breadcrumbs.c
index f706b7f92835..963f88aa9101 100644
--- a/drivers/gpu/drm/i915/intel_breadcrumbs.c
+++ b/drivers/gpu/drm/i915/intel_breadcrumbs.c
@@ -485,9 +485,9 @@ static bool __intel_engine_add_wait(struct intel_engine_cs *engine,
 	return armed;
 }
 
-bool intel_engine_add_wait(struct intel_engine_cs *engine,
-			   struct intel_wait *wait)
+bool intel_engine_add_wait(struct intel_wait *wait)
 {
+	struct intel_engine_cs *engine = wait->engine;
 	struct intel_breadcrumbs *b = &engine->breadcrumbs;
 	bool armed;
 
@@ -577,9 +577,9 @@ static void __intel_engine_remove_wait(struct intel_engine_cs *engine,
 		   (b->irq_wait ? &b->irq_wait->node : NULL));
 }
 
-void intel_engine_remove_wait(struct intel_engine_cs *engine,
-			      struct intel_wait *wait)
+void intel_engine_remove_wait(struct intel_wait *wait)
 {
+	struct intel_engine_cs *engine = wait->engine;
 	struct intel_breadcrumbs *b = &engine->breadcrumbs;
 
 	/* Quick check to see if this waiter was already decoupled from
diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.h b/drivers/gpu/drm/i915/intel_ringbuffer.h
index e610d7f161fa..a38b310a1a5c 100644
--- a/drivers/gpu/drm/i915/intel_ringbuffer.h
+++ b/drivers/gpu/drm/i915/intel_ringbuffer.h
@@ -903,9 +903,12 @@ static inline void intel_wait_init(struct intel_wait *wait)
 	wait->request = NULL;
 }
 
-static inline void intel_wait_init_for_seqno(struct intel_wait *wait, u64 seqno)
+static inline void intel_wait_init_for_seqno(struct intel_wait *wait,
+					     struct intel_engine_cs *engine,
+					     u64 seqno)
 {
 	wait->tsk = current;
+	wait->engine = engine;
 	wait->global_seqno = seqno;
 }
 
@@ -914,18 +917,21 @@ static inline bool intel_wait_has_seqno(const struct intel_wait *wait)
 	return wait->global_seqno;
 }
 
-static inline bool
-intel_wait_update_seqno(struct intel_wait *wait, u64 seqno)
-{
-	wait->global_seqno = seqno;
-	return intel_wait_has_seqno(wait);
-}
-
 static inline bool
 intel_wait_update_request(struct intel_wait *wait,
 			  const struct i915_request *rq)
 {
-	return intel_wait_update_seqno(wait, i915_request_global_seqno(rq));
+	u64 seqno, check;
+
+	seqno = i915_request_global_seqno(rq);
+	do {
+		check = seqno;
+		wait->engine = rq->engine;
+		barrier();
+	} while ((seqno = i915_request_global_seqno(rq)) != check);
+	wait->global_seqno = seqno;
+
+	return seqno;
 }
 
 static inline bool
@@ -946,10 +952,9 @@ static inline bool intel_wait_complete(const struct intel_wait *wait)
 	return RB_EMPTY_NODE(&wait->node);
 }
 
-bool intel_engine_add_wait(struct intel_engine_cs *engine,
-			   struct intel_wait *wait);
-void intel_engine_remove_wait(struct intel_engine_cs *engine,
-			      struct intel_wait *wait);
+bool intel_engine_add_wait(struct intel_wait *wait);
+void intel_engine_remove_wait(struct intel_wait *wait);
+
 bool intel_engine_enable_signaling(struct i915_request *request, bool wakeup);
 void intel_engine_cancel_signaling(struct i915_request *request);
 
diff --git a/drivers/gpu/drm/i915/selftests/intel_breadcrumbs.c b/drivers/gpu/drm/i915/selftests/intel_breadcrumbs.c
index 8bd05a99340d..083b0cb331e4 100644
--- a/drivers/gpu/drm/i915/selftests/intel_breadcrumbs.c
+++ b/drivers/gpu/drm/i915/selftests/intel_breadcrumbs.c
@@ -131,7 +131,7 @@ static int igt_random_insert_remove(void *arg)
 		goto out_bitmap;
 
 	for (n = 0; n < count; n++)
-		intel_wait_init_for_seqno(&waiters[n], seqno_bias + n);
+		intel_wait_init_for_seqno(&waiters[n], engine, seqno_bias + n);
 
 	err = check_rbtree(engine, bitmap, waiters, count);
 	if (err)
@@ -143,7 +143,7 @@ static int igt_random_insert_remove(void *arg)
 	for (n = 0; n < count; n++) {
 		int i = order[n];
 
-		intel_engine_add_wait(engine, &waiters[i]);
+		intel_engine_add_wait(&waiters[i]);
 		__set_bit(i, bitmap);
 
 		err = check_rbtree(engine, bitmap, waiters, count);
@@ -155,7 +155,7 @@ static int igt_random_insert_remove(void *arg)
 	for (n = 0; n < count; n++) {
 		int i = order[n];
 
-		intel_engine_remove_wait(engine, &waiters[i]);
+		intel_engine_remove_wait(&waiters[i]);
 		__clear_bit(i, bitmap);
 
 		err = check_rbtree(engine, bitmap, waiters, count);
@@ -197,8 +197,8 @@ static int igt_insert_complete(void *arg)
 		goto out_waiters;
 
 	for (n = 0; n < count; n++) {
-		intel_wait_init_for_seqno(&waiters[n], n + seqno_bias);
-		intel_engine_add_wait(engine, &waiters[n]);
+		intel_wait_init_for_seqno(&waiters[n], engine, n + seqno_bias);
+		intel_engine_add_wait(&waiters[n]);
 		__set_bit(n, bitmap);
 	}
 	err = check_rbtree(engine, bitmap, waiters, count);
@@ -232,7 +232,7 @@ static int igt_insert_complete(void *arg)
 			__clear_bit(m, bitmap);
 		}
 
-		intel_engine_remove_wait(engine, &waiters[n]);
+		intel_engine_remove_wait(&waiters[n]);
 		RB_CLEAR_NODE(&waiters[n].node);
 
 		err = check_rbtree(engine, bitmap, waiters, count);
@@ -307,8 +307,8 @@ static int igt_wakeup_thread(void *arg)
 	while (wait_for_ready(w)) {
 		GEM_BUG_ON(kthread_should_stop());
 
-		intel_wait_init_for_seqno(&wait, w->seqno);
-		intel_engine_add_wait(w->engine, &wait);
+		intel_wait_init_for_seqno(&wait, w->engine, w->seqno);
+		intel_engine_add_wait(&wait);
 		for (;;) {
 			set_current_state(TASK_UNINTERRUPTIBLE);
 			if (i915_seqno_passed(intel_engine_get_seqno(w->engine),
@@ -320,7 +320,7 @@ static int igt_wakeup_thread(void *arg)
 
 			schedule();
 		}
-		intel_engine_remove_wait(w->engine, &wait);
+		intel_engine_remove_wait(&wait);
 		__set_current_state(TASK_RUNNING);
 	}
 
-- 
2.20.1



More information about the Intel-gfx-trybot mailing list