Record the initial active element we use when building the next ELSP
submission, so that we can compare against it latter to see if there's
no change.

Fixes: 44d0a9c05bc0 ("drm/i915/execlists: Skip redundant resubmission")
Signed-off-by: Chris Wilson <ch...@chris-wilson.co.uk>
---
 drivers/gpu/drm/i915/gt/intel_lrc.c | 17 ++++++++++++-----
 1 file changed, 12 insertions(+), 5 deletions(-)

diff --git a/drivers/gpu/drm/i915/gt/intel_lrc.c 
b/drivers/gpu/drm/i915/gt/intel_lrc.c
index 6266ef2ae6a0..a9d77b0e4e27 100644
--- a/drivers/gpu/drm/i915/gt/intel_lrc.c
+++ b/drivers/gpu/drm/i915/gt/intel_lrc.c
@@ -1674,16 +1674,21 @@ static void virtual_xfer_breadcrumbs(struct 
virtual_engine *ve,
 }
 
 static struct i915_request *
-last_active(const struct intel_engine_execlists *execlists)
+__last_active(const struct intel_engine_execlists *execlists,
+             struct i915_request * const *last)
 {
-       struct i915_request * const *last = READ_ONCE(execlists->active);
-
        while (*last && i915_request_completed(*last))
                last++;
 
        return *last;
 }
 
+static struct i915_request *
+last_active(const struct intel_engine_execlists *execlists)
+{
+       return __last_active(execlists, READ_ONCE(execlists->active));
+}
+
 #define for_each_waiter(p__, rq__) \
        list_for_each_entry_lockless(p__, \
                                     &(rq__)->sched.waiters_list, \
@@ -1852,6 +1857,7 @@ static void execlists_dequeue(struct intel_engine_cs 
*engine)
        struct intel_engine_execlists * const execlists = &engine->execlists;
        struct i915_request **port = execlists->pending;
        struct i915_request ** const last_port = port + execlists->port_mask;
+       struct i915_request * const *active;
        struct i915_request *last;
        struct rb_node *rb;
        bool submit = false;
@@ -1906,7 +1912,8 @@ static void execlists_dequeue(struct intel_engine_cs 
*engine)
         * i.e. we will retrigger preemption following the ack in case
         * of trouble.
         */
-       last = last_active(execlists);
+       active = READ_ONCE(execlists->active);
+       last = __last_active(execlists, active);
        if (last) {
                if (need_preempt(engine, last, rb)) {
                        ENGINE_TRACE(engine,
@@ -2191,7 +2198,7 @@ static void execlists_dequeue(struct intel_engine_cs 
*engine)
                 * Skip if we ended up with exactly the same set of requests,
                 * e.g. trying to timeslice a pair of ordered contexts
                 */
-               if (!memcmp(execlists->active, execlists->pending,
+               if (!memcmp(active, execlists->pending,
                            (port - execlists->pending + 1) * sizeof(*port))) {
                        do
                                execlists_schedule_out(fetch_and_zero(port));
-- 
2.20.1

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

Reply via email to