drm/i915/icl: Handle rps interrupts without irq lock
authorMika Kuoppala <mika.kuoppala@linux.intel.com>
Wed, 10 Apr 2019 13:21:23 +0000 (16:21 +0300)
committerChris Wilson <chris@chris-wilson.co.uk>
Wed, 10 Apr 2019 15:23:18 +0000 (16:23 +0100)
Unlike previous gens, we already hold the irq_lock on
entering the rps handler so we can't use it as it is.

Make a gen11 specific rps interrupt handler without
locking.

v2: return early (Chris)

Cc: Chris Wilson <chris@chris-wilson.co.uk>
Signed-off-by: Mika Kuoppala <mika.kuoppala@linux.intel.com>
Reviewed-by: Chris Wilson <chris@chris-wilson.co.uk>
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Link: https://patchwork.freedesktop.org/patch/msgid/20190410132124.21795-1-mika.kuoppala@linux.intel.com
drivers/gpu/drm/i915/i915_irq.c

index 6454ddc37f8b561871d93a25cfc5bb8b53369192..eb0eb96ac751154e8c3289549c997097a008e0a4 100644 (file)
@@ -1796,6 +1796,25 @@ static void i9xx_pipe_crc_irq_handler(struct drm_i915_private *dev_priv,
 /* The RPS events need forcewake, so we add them to a work queue and mask their
  * IMR bits until the work is done. Other interrupts can be processed without
  * the work queue. */
+static void gen11_rps_irq_handler(struct drm_i915_private *i915, u32 pm_iir)
+{
+       struct intel_rps *rps = &i915->gt_pm.rps;
+       const u32 events = i915->pm_rps_events & pm_iir;
+
+       lockdep_assert_held(&i915->irq_lock);
+
+       if (unlikely(!events))
+               return;
+
+       gen6_mask_pm_irq(i915, events);
+
+       if (!rps->interrupts_enabled)
+               return;
+
+       rps->pm_iir |= events;
+       schedule_work(&rps->work);
+}
+
 static void gen6_rps_irq_handler(struct drm_i915_private *dev_priv, u32 pm_iir)
 {
        struct intel_rps *rps = &dev_priv->gt_pm.rps;
@@ -2949,7 +2968,7 @@ gen11_other_irq_handler(struct drm_i915_private * const i915,
                        const u8 instance, const u16 iir)
 {
        if (instance == OTHER_GTPM_INSTANCE)
-               return gen6_rps_irq_handler(i915, iir);
+               return gen11_rps_irq_handler(i915, iir);
 
        WARN_ONCE(1, "unhandled other interrupt instance=0x%x, iir=0x%x\n",
                  instance, iir);