From mboxrd@z Thu Jan 1 00:00:00 1970 From: Jesse Barnes Subject: [PATCH 02/16] drm/i915: split irq handling into per-chipset functions Date: Tue, 26 Apr 2011 16:38:40 -0700 Message-ID: <1303861134-8762-3-git-send-email-jbarnes@virtuousgeek.org> References: <1303861134-8762-1-git-send-email-jbarnes@virtuousgeek.org> Mime-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Return-path: Received: from oproxy2-pub.bluehost.com (oproxy2-pub.bluehost.com [67.222.39.60]) by gabe.freedesktop.org (Postfix) with SMTP id CD9E59E8B1 for ; Tue, 26 Apr 2011 16:39:00 -0700 (PDT) In-Reply-To: <1303861134-8762-1-git-send-email-jbarnes@virtuousgeek.org> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: intel-gfx-bounces+gcfxdi-intel-gfx=m.gmane.org@lists.freedesktop.org Errors-To: intel-gfx-bounces+gcfxdi-intel-gfx=m.gmane.org@lists.freedesktop.org To: intel-gfx@lists.freedesktop.org List-Id: intel-gfx@lists.freedesktop.org Set the IRQ handling functions in driver load so they'll just be used directly, rather than branching over most of the code in the chipset functions. Signed-off-by: Jesse Barnes --- drivers/gpu/drm/i915/i915_dma.c | 12 ++++++++++ drivers/gpu/drm/i915/i915_drv.h | 6 +++++ drivers/gpu/drm/i915/i915_irq.c | 45 +++++++++++++++++++++----------------- 3 files changed, 43 insertions(+), 20 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_dma.c b/drivers/gpu/drm/i915/i915_dma.c index 3b69f38..2f653c2 100644 --- a/drivers/gpu/drm/i915/i915_dma.c +++ b/drivers/gpu/drm/i915/i915_dma.c @@ -1253,6 +1253,18 @@ static int i915_load_modeset_init(struct drm_device *dev) intel_modeset_init(dev); + if (HAS_PCH_SPLIT(dev)) { + dev->driver->irq_handler = ironlake_irq_handler; + dev->driver->irq_preinstall = ironlake_irq_preinstall; + dev->driver->irq_postinstall = ironlake_irq_postinstall; + dev->driver->irq_uninstall = ironlake_irq_uninstall; + } else { + dev->driver->irq_preinstall = i915_driver_irq_preinstall; + dev->driver->irq_postinstall = i915_driver_irq_postinstall; + dev->driver->irq_uninstall = i915_driver_irq_uninstall; + dev->driver->irq_handler = i915_driver_irq_handler; + } + ret = drm_irq_install(dev); if (ret) goto cleanup_vga_switcheroo; diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index c10d7e9..44d24fb 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -1024,6 +1024,12 @@ extern irqreturn_t i915_driver_irq_handler(DRM_IRQ_ARGS); extern void i915_driver_irq_preinstall(struct drm_device * dev); extern int i915_driver_irq_postinstall(struct drm_device *dev); extern void i915_driver_irq_uninstall(struct drm_device * dev); + +extern irqreturn_t ironlake_irq_handler(DRM_IRQ_ARGS); +extern void ironlake_irq_preinstall(struct drm_device *dev); +extern int ironlake_irq_postinstall(struct drm_device *dev); +extern void ironlake_irq_uninstall(struct drm_device *dev); + extern int i915_vblank_pipe_set(struct drm_device *dev, void *data, struct drm_file *file_priv); extern int i915_vblank_pipe_get(struct drm_device *dev, void *data, diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 5c0466e..a58d477 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -448,8 +448,9 @@ static void pch_irq_handler(struct drm_device *dev) DRM_DEBUG_DRIVER("PCH transcoder A underrun interrupt\n"); } -static irqreturn_t ironlake_irq_handler(struct drm_device *dev) +irqreturn_t ironlake_irq_handler(DRM_IRQ_ARGS) { + struct drm_device *dev = (struct drm_device *) arg; drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; int ret = IRQ_NONE; u32 de_iir, gt_iir, de_ier, pch_iir, pm_iir; @@ -457,6 +458,8 @@ static irqreturn_t ironlake_irq_handler(struct drm_device *dev) struct drm_i915_master_private *master_priv; u32 bsd_usr_interrupt = GT_BSD_USER_INTERRUPT; + atomic_inc(&dev_priv->irq_received); + if (IS_GEN6(dev)) bsd_usr_interrupt = GT_GEN6_BSD_USER_INTERRUPT; @@ -1103,9 +1106,6 @@ irqreturn_t i915_driver_irq_handler(DRM_IRQ_ARGS) atomic_inc(&dev_priv->irq_received); - if (HAS_PCH_SPLIT(dev)) - return ironlake_irq_handler(dev); - iir = I915_READ(IIR); if (INTEL_INFO(dev)->gen >= 4) @@ -1562,10 +1562,15 @@ repeat: /* drm_dma.h hooks */ -static void ironlake_irq_preinstall(struct drm_device *dev) +void ironlake_irq_preinstall(struct drm_device *dev) { drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; + atomic_set(&dev_priv->irq_received, 0); + + INIT_WORK(&dev_priv->hotplug_work, i915_hotplug_work_func); + INIT_WORK(&dev_priv->error_work, i915_error_work_func); + I915_WRITE(HWSTAM, 0xeffe); /* XXX hotplug from PCH */ @@ -1585,7 +1590,7 @@ static void ironlake_irq_preinstall(struct drm_device *dev) POSTING_READ(SDEIER); } -static int ironlake_irq_postinstall(struct drm_device *dev) +int ironlake_irq_postinstall(struct drm_device *dev) { drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; /* enable kind of interrupts always enabled */ @@ -1594,6 +1599,13 @@ static int ironlake_irq_postinstall(struct drm_device *dev) u32 render_irqs; u32 hotplug_mask; + DRM_INIT_WAITQUEUE(&dev_priv->ring[RCS].irq_queue); + if (HAS_BSD(dev)) + DRM_INIT_WAITQUEUE(&dev_priv->ring[VCS].irq_queue); + if (HAS_BLT(dev)) + DRM_INIT_WAITQUEUE(&dev_priv->ring[BCS].irq_queue); + + dev_priv->vblank_pipe = DRM_I915_VBLANK_PIPE_A | DRM_I915_VBLANK_PIPE_B; dev_priv->irq_mask = ~display_mask; /* should always can generate irq */ @@ -1660,11 +1672,6 @@ void i915_driver_irq_preinstall(struct drm_device * dev) INIT_WORK(&dev_priv->hotplug_work, i915_hotplug_work_func); INIT_WORK(&dev_priv->error_work, i915_error_work_func); - if (HAS_PCH_SPLIT(dev)) { - ironlake_irq_preinstall(dev); - return; - } - if (I915_HAS_HOTPLUG(dev)) { I915_WRITE(PORT_HOTPLUG_EN, 0); I915_WRITE(PORT_HOTPLUG_STAT, I915_READ(PORT_HOTPLUG_STAT)); @@ -1696,9 +1703,6 @@ int i915_driver_irq_postinstall(struct drm_device *dev) dev_priv->vblank_pipe = DRM_I915_VBLANK_PIPE_A | DRM_I915_VBLANK_PIPE_B; - if (HAS_PCH_SPLIT(dev)) - return ironlake_irq_postinstall(dev); - /* Unmask the interrupts that we always want on. */ dev_priv->irq_mask = ~I915_INTERRUPT_ENABLE_FIX; @@ -1767,9 +1771,15 @@ int i915_driver_irq_postinstall(struct drm_device *dev) return 0; } -static void ironlake_irq_uninstall(struct drm_device *dev) +void ironlake_irq_uninstall(struct drm_device *dev) { drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; + + if (!dev_priv) + return; + + dev_priv->vblank_pipe = 0; + I915_WRITE(HWSTAM, 0xffffffff); I915_WRITE(DEIMR, 0xffffffff); @@ -1791,11 +1801,6 @@ void i915_driver_irq_uninstall(struct drm_device * dev) dev_priv->vblank_pipe = 0; - if (HAS_PCH_SPLIT(dev)) { - ironlake_irq_uninstall(dev); - return; - } - if (I915_HAS_HOTPLUG(dev)) { I915_WRITE(PORT_HOTPLUG_EN, 0); I915_WRITE(PORT_HOTPLUG_STAT, I915_READ(PORT_HOTPLUG_STAT)); -- 1.7.4.1