From patchwork Thu Jul 28 23:49:46 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Keith Packard X-Patchwork-Id: 1018462 Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) by demeter2.kernel.org (8.14.4/8.14.4) with ESMTP id p6SNoNap019932 for ; Thu, 28 Jul 2011 23:50:44 GMT Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id F06199E796 for ; Thu, 28 Jul 2011 16:50:22 -0700 (PDT) X-Original-To: intel-gfx@lists.freedesktop.org Delivered-To: intel-gfx@lists.freedesktop.org Received: from keithp.com (home.keithp.com [63.227.221.253]) by gabe.freedesktop.org (Postfix) with ESMTP id 194E59E796 for ; Thu, 28 Jul 2011 16:50:00 -0700 (PDT) Received: from localhost (localhost [127.0.0.1]) by keithp.com (Postfix) with ESMTP id F087DB78008 for ; Thu, 28 Jul 2011 16:49:59 -0700 (PDT) X-Virus-Scanned: Debian amavisd-new at keithp.com Received: from keithp.com ([127.0.0.1]) by localhost (keithp.com [127.0.0.1]) (amavisd-new, port 10024) with LMTP id L7w0SMRy4CCn; Thu, 28 Jul 2011 16:49:56 -0700 (PDT) Received: by keithp.com (Postfix, from userid 1033) id ACC12B78003; Thu, 28 Jul 2011 16:49:56 -0700 (PDT) Received: from koto.keithp.com (localhost [127.0.0.1]) by keithp.com (Postfix) with ESMTP id 12579B7C019; Thu, 28 Jul 2011 16:49:56 -0700 (PDT) Received: by koto.keithp.com (Postfix, from userid 1488) id 7CC3F642766; Thu, 28 Jul 2011 16:49:50 -0700 (PDT) From: Keith Packard To: intel-gfx@lists.freedesktop.org Date: Thu, 28 Jul 2011 16:49:46 -0700 Message-Id: <1311896986-2829-1-git-send-email-keithp@keithp.com> X-Mailer: git-send-email 1.7.5.4 Subject: [Intel-gfx] [PATCH] drm/i915: Delay 250ms before running the hotplug code X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.11 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Sender: intel-gfx-bounces+patchwork-intel-gfx=patchwork.kernel.org@lists.freedesktop.org Errors-To: intel-gfx-bounces+patchwork-intel-gfx=patchwork.kernel.org@lists.freedesktop.org X-Greylist: IP, sender and recipient auto-whitelisted, not delayed by milter-greylist-4.2.6 (demeter2.kernel.org [140.211.167.43]); Thu, 28 Jul 2011 23:50:44 +0000 (UTC) If the connector is inserted or removed slowly, the hotplug line may well change state before the data lines do. So, assume the user isn't trying to fool us and give them 250ms to get the connector plugged or unplugged. v2: use queue_delayed_work instead of msleep Signed-off-by: Keith Packard --- drivers/gpu/drm/i915/i915_drv.h | 2 +- drivers/gpu/drm/i915/i915_irq.c | 17 +++++++++-------- drivers/gpu/drm/i915/intel_display.c | 2 +- 3 files changed, 11 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 6867e19..0e57ebc 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -315,7 +315,7 @@ typedef struct drm_i915_private { u32 pch_irq_mask; u32 hotplug_supported_mask; - struct work_struct hotplug_work; + struct delayed_work hotplug_delayed_work; int tex_lru_log_granularity; int allow_batchbuffer; diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 02f96fd..11fe413 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -300,8 +300,9 @@ static int i915_get_vblank_timestamp(struct drm_device *dev, int pipe, */ static void i915_hotplug_work_func(struct work_struct *work) { - drm_i915_private_t *dev_priv = container_of(work, drm_i915_private_t, - hotplug_work); + struct delayed_work *delayed_work = to_delayed_work(work); + drm_i915_private_t *dev_priv = container_of(delayed_work, drm_i915_private_t, + hotplug_delayed_work); struct drm_device *dev = dev_priv->dev; struct drm_mode_config *mode_config = &dev->mode_config; struct intel_encoder *encoder; @@ -528,7 +529,7 @@ static irqreturn_t ivybridge_irq_handler(DRM_IRQ_ARGS) /* check event from PCH */ if (de_iir & DE_PCH_EVENT_IVB) { if (pch_iir & SDE_HOTPLUG_MASK_CPT) - queue_work(dev_priv->wq, &dev_priv->hotplug_work); + queue_delayed_work(dev_priv->wq, &dev_priv->hotplug_delayed_work, HZ/4); pch_irq_handler(dev); } @@ -627,7 +628,7 @@ static irqreturn_t ironlake_irq_handler(DRM_IRQ_ARGS) /* check event from PCH */ if (de_iir & DE_PCH_EVENT) { if (pch_iir & hotplug_mask) - queue_work(dev_priv->wq, &dev_priv->hotplug_work); + queue_delayed_work(dev_priv->wq, &dev_priv->hotplug_delayed_work, HZ/4); pch_irq_handler(dev); } @@ -1279,8 +1280,8 @@ static irqreturn_t i915_driver_irq_handler(DRM_IRQ_ARGS) DRM_DEBUG_DRIVER("hotplug event received, stat 0x%08x\n", hotplug_status); if (hotplug_status & dev_priv->hotplug_supported_mask) - queue_work(dev_priv->wq, - &dev_priv->hotplug_work); + queue_delayed_work(dev_priv->wq, + &dev_priv->hotplug_delayed_work, HZ/4); I915_WRITE(PORT_HOTPLUG_STAT, hotplug_status); I915_READ(PORT_HOTPLUG_STAT); @@ -1742,7 +1743,7 @@ static void ironlake_irq_preinstall(struct drm_device *dev) atomic_set(&dev_priv->irq_received, 0); - INIT_WORK(&dev_priv->hotplug_work, i915_hotplug_work_func); + INIT_DELAYED_WORK(&dev_priv->hotplug_delayed_work, i915_hotplug_work_func); INIT_WORK(&dev_priv->error_work, i915_error_work_func); if (IS_GEN6(dev) || IS_IVYBRIDGE(dev)) INIT_WORK(&dev_priv->rps_work, gen6_pm_rps_work); @@ -1906,7 +1907,7 @@ static void i915_driver_irq_preinstall(struct drm_device * dev) atomic_set(&dev_priv->irq_received, 0); - INIT_WORK(&dev_priv->hotplug_work, i915_hotplug_work_func); + INIT_DELAYED_WORK(&dev_priv->hotplug_delayed_work, i915_hotplug_work_func); INIT_WORK(&dev_priv->error_work, i915_error_work_func); if (I915_HAS_HOTPLUG(dev)) { diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index ce908ec..d36e7fc 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -8361,7 +8361,7 @@ void intel_modeset_cleanup(struct drm_device *dev) /* Disable the irq before mode object teardown, for the irq might * enqueue unpin/hotplug work. */ drm_irq_uninstall(dev); - cancel_work_sync(&dev_priv->hotplug_work); + cancel_delayed_work_sync(&dev_priv->hotplug_delayed_work); /* flush any delayed tasks or pending work */ flush_scheduled_work();