summaryrefslogtreecommitdiff
path: root/shared-core/i915_irq.c
diff options
context:
space:
mode:
authorThomas Hellstrom <thomas-at-tungstengraphics-dot-com>2006-09-05 14:23:18 +0200
committerThomas Hellstrom <thomas-at-tungstengraphics-dot-com>2006-09-05 14:23:18 +0200
commit034fc31292edaa25779a938ab3e92ef34697eaf9 (patch)
tree5a8c1accd82521750a64f8140b273a3f06d95e6c /shared-core/i915_irq.c
parent8c613a8363963330fbf701186f654007d6208bba (diff)
i915: Only turn on user IRQs when they are needed.
Diffstat (limited to 'shared-core/i915_irq.c')
-rw-r--r--shared-core/i915_irq.c34
1 files changed, 32 insertions, 2 deletions
diff --git a/shared-core/i915_irq.c b/shared-core/i915_irq.c
index 4195555e..a3f6a03b 100644
--- a/shared-core/i915_irq.c
+++ b/shared-core/i915_irq.c
@@ -102,6 +102,29 @@ int i915_emit_irq(drm_device_t * dev)
}
+void i915_user_irq_on(drm_i915_private_t *dev_priv)
+{
+
+ spin_lock(&dev_priv->user_irq_lock);
+ if (dev_priv->irq_enabled && (++dev_priv->user_irq_refcount > 0)){
+ dev_priv->irq_enable_reg |= USER_INT_FLAG;
+ I915_WRITE16(I915REG_INT_ENABLE_R, dev_priv->irq_enable_reg);
+ }
+ spin_unlock(&dev_priv->user_irq_lock);
+
+}
+
+void i915_user_irq_off(drm_i915_private_t *dev_priv)
+{
+ spin_lock(&dev_priv->user_irq_lock);
+ if (dev_priv->irq_enabled && (--dev_priv->user_irq_refcount == 0)) {
+ dev_priv->irq_enable_reg &= ~USER_INT_FLAG;
+ I915_WRITE16(I915REG_INT_ENABLE_R, dev_priv->irq_enable_reg);
+ }
+ spin_unlock(&dev_priv->user_irq_lock);
+}
+
+
static int i915_wait_irq(drm_device_t * dev, int irq_nr)
{
drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;
@@ -114,9 +137,11 @@ static int i915_wait_irq(drm_device_t * dev, int irq_nr)
return 0;
dev_priv->sarea_priv->perf_boxes |= I915_BOX_WAIT;
-
+
+ i915_user_irq_on(dev_priv);
DRM_WAIT_ON(ret, dev_priv->irq_queue, 3 * DRM_HZ,
READ_BREADCRUMB(dev_priv) >= irq_nr);
+ i915_user_irq_off(dev_priv);
if (ret == DRM_ERR(EBUSY)) {
DRM_ERROR("%s: EBUSY -- rec: %d emitted: %d\n",
@@ -211,7 +236,11 @@ static int i915_enable_interrupt (drm_device_t *dev)
__FUNCTION__, dev_priv->vblank_pipe);
return DRM_ERR(EINVAL);
}
- I915_WRITE16(I915REG_INT_ENABLE_R, USER_INT_FLAG | flag);
+ dev_priv->user_irq_lock = SPIN_LOCK_UNLOCKED;
+ dev_priv->user_irq_refcount = 0;
+ dev_priv->irq_enable_reg = flag;
+ I915_WRITE16(I915REG_INT_ENABLE_R, flag);
+ dev_priv->irq_enabled = 1;
return 0;
}
@@ -290,6 +319,7 @@ void i915_driver_irq_uninstall(drm_device_t * dev)
if (!dev_priv)
return;
+ dev_priv->irq_enabled = 0;
I915_WRITE16(I915REG_HWSTAM, 0xffff);
I915_WRITE16(I915REG_INT_MASK_R, 0xffff);
I915_WRITE16(I915REG_INT_ENABLE_R, 0x0);