drm/i915: Remove superfluous worker wakeups when RPS is already boosted
authorChris Wilson <chris@chris-wilson.co.uk>
Tue, 6 Feb 2018 14:31:37 +0000 (14:31 +0000)
committerChris Wilson <chris@chris-wilson.co.uk>
Thu, 8 Feb 2018 11:27:40 +0000 (11:27 +0000)
We only need to wake up the RPS worker once when initially enabling the
client boost, it remains in effect then until the last client no longer
requires the boost.

References: https://bugs.freedesktop.org/show_bug.cgi?id=102250
References: 7b92c1bd0540 ("drm/i915: Avoid keeping waitboost active for signaling threads")
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Cc: Michał Winiarski <michal.winiarski@intel.com>
Reviewed-by: Michał Winiarski <michal.winiarski@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20180206143137.15509-1-chris@chris-wilson.co.uk
drivers/gpu/drm/i915/i915_gem_request.c
drivers/gpu/drm/i915/intel_pm.c

index a8eb22a..8a35b55 100644 (file)
@@ -443,12 +443,14 @@ static void i915_gem_request_retire(struct drm_i915_gem_request *request)
        engine->last_retired_context = request->ctx;
 
        spin_lock_irq(&request->lock);
-       if (request->waitboost)
-               atomic_dec(&request->i915->gt_pm.rps.num_waiters);
        if (!test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, &request->fence.flags))
                dma_fence_signal_locked(&request->fence);
        if (test_bit(DMA_FENCE_FLAG_ENABLE_SIGNAL_BIT, &request->fence.flags))
                intel_engine_cancel_signaling(request);
+       if (request->waitboost) {
+               GEM_BUG_ON(!atomic_read(&request->i915->gt_pm.rps.num_waiters));
+               atomic_dec(&request->i915->gt_pm.rps.num_waiters);
+       }
        spin_unlock_irq(&request->lock);
 
        i915_priotree_fini(request->i915, &request->priotree);
index 41f26ab..b2f5e3b 100644 (file)
@@ -6374,12 +6374,15 @@ void gen6_rps_boost(struct drm_i915_gem_request *rq,
        if (!rps->enabled)
                return;
 
+       if (test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, &rq->fence.flags))
+               return;
+
+       /* Serializes with i915_gem_request_retire() */
        boost = false;
        spin_lock_irqsave(&rq->lock, flags);
-       if (!rq->waitboost && !i915_gem_request_completed(rq)) {
-               atomic_inc(&rps->num_waiters);
+       if (!rq->waitboost && !dma_fence_is_signaled_locked(&rq->fence)) {
+               boost = !atomic_fetch_inc(&rps->num_waiters);
                rq->waitboost = true;
-               boost = true;
        }
        spin_unlock_irqrestore(&rq->lock, flags);
        if (!boost)