diff options
author | Paulo Zanoni <paulo.r.zanoni@intel.com> | 2013-08-15 10:50:01 -0400 |
---|---|---|
committer | Daniel Vetter <daniel.vetter@ffwll.ch> | 2013-08-23 08:52:29 -0400 |
commit | 60611c137641af41895828cfc74f5be64ed69b49 (patch) | |
tree | 151ed550b03b1555fb982ffbe6148074db22bae1 /drivers/gpu/drm/i915/i915_irq.c | |
parent | 333a820416ccb0e24974b6ebe7d447c0c28c7b76 (diff) |
drm/i915: don't queue PM events we won't process
On SNB/IVB/VLV we only call gen6_rps_irq_handler if one of the IIR
bits set is part of GEN6_PM_RPS_EVENTS, but at gen6_rps_irq_handler we
add all the enabled IIR bits to the work queue, not only the ones that
are part of GEN6_PM_RPS_EVENTS. But then gen6_pm_rps_work only
processes GEN6_PM_RPS_EVENTS, so it's useless to add anything that's
not GEN6_PM_RPS_EVENTS to the work queue.
As a bonus, gen6_rps_irq_handler looks more similar to
hsw_pm_irq_handler, so we may be able to merge them in the future.
v2: - Add a WARN in case we queued something we're not going to
process.
Signed-off-by: Paulo Zanoni <paulo.r.zanoni@intel.com>
Reviewed-by: Ben Widawsky <ben@bwidawsk.net> (v1)
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm/i915/i915_irq.c')
-rw-r--r-- | drivers/gpu/drm/i915/i915_irq.c | 9 |
1 files changed, 6 insertions, 3 deletions
diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 976113af1859..c10d2f1af0be 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c | |||
@@ -789,6 +789,9 @@ static void gen6_pm_rps_work(struct work_struct *work) | |||
789 | snb_enable_pm_irq(dev_priv, GEN6_PM_RPS_EVENTS); | 789 | snb_enable_pm_irq(dev_priv, GEN6_PM_RPS_EVENTS); |
790 | spin_unlock_irq(&dev_priv->irq_lock); | 790 | spin_unlock_irq(&dev_priv->irq_lock); |
791 | 791 | ||
792 | /* Make sure we didn't queue anything we're not going to process. */ | ||
793 | WARN_ON(pm_iir & ~GEN6_PM_RPS_EVENTS); | ||
794 | |||
792 | if ((pm_iir & GEN6_PM_RPS_EVENTS) == 0) | 795 | if ((pm_iir & GEN6_PM_RPS_EVENTS) == 0) |
793 | return; | 796 | return; |
794 | 797 | ||
@@ -959,7 +962,7 @@ static void gen6_rps_irq_handler(struct drm_i915_private *dev_priv, | |||
959 | */ | 962 | */ |
960 | 963 | ||
961 | spin_lock(&dev_priv->irq_lock); | 964 | spin_lock(&dev_priv->irq_lock); |
962 | dev_priv->rps.pm_iir |= pm_iir; | 965 | dev_priv->rps.pm_iir |= pm_iir & GEN6_PM_RPS_EVENTS; |
963 | snb_set_pm_irq(dev_priv, dev_priv->rps.pm_iir); | 966 | snb_set_pm_irq(dev_priv, dev_priv->rps.pm_iir); |
964 | spin_unlock(&dev_priv->irq_lock); | 967 | spin_unlock(&dev_priv->irq_lock); |
965 | 968 | ||
@@ -1128,7 +1131,7 @@ static irqreturn_t valleyview_irq_handler(int irq, void *arg) | |||
1128 | if (pipe_stats[0] & PIPE_GMBUS_INTERRUPT_STATUS) | 1131 | if (pipe_stats[0] & PIPE_GMBUS_INTERRUPT_STATUS) |
1129 | gmbus_irq_handler(dev); | 1132 | gmbus_irq_handler(dev); |
1130 | 1133 | ||
1131 | if (pm_iir & GEN6_PM_RPS_EVENTS) | 1134 | if (pm_iir) |
1132 | gen6_rps_irq_handler(dev_priv, pm_iir); | 1135 | gen6_rps_irq_handler(dev_priv, pm_iir); |
1133 | 1136 | ||
1134 | I915_WRITE(GTIIR, gt_iir); | 1137 | I915_WRITE(GTIIR, gt_iir); |
@@ -1433,7 +1436,7 @@ static irqreturn_t ironlake_irq_handler(int irq, void *arg) | |||
1433 | if (pm_iir) { | 1436 | if (pm_iir) { |
1434 | if (IS_HASWELL(dev)) | 1437 | if (IS_HASWELL(dev)) |
1435 | hsw_pm_irq_handler(dev_priv, pm_iir); | 1438 | hsw_pm_irq_handler(dev_priv, pm_iir); |
1436 | else if (pm_iir & GEN6_PM_RPS_EVENTS) | 1439 | else |
1437 | gen6_rps_irq_handler(dev_priv, pm_iir); | 1440 | gen6_rps_irq_handler(dev_priv, pm_iir); |
1438 | I915_WRITE(GEN6_PMIIR, pm_iir); | 1441 | I915_WRITE(GEN6_PMIIR, pm_iir); |
1439 | ret = IRQ_HANDLED; | 1442 | ret = IRQ_HANDLED; |