diff options
author | Alan Cox <alan@linux.intel.com> | 2012-04-25 09:38:32 -0400 |
---|---|---|
committer | Dave Airlie <airlied@redhat.com> | 2012-04-27 04:24:21 -0400 |
commit | ae0a246aef0d185db2947912fe9cf7dae1d91b7a (patch) | |
tree | 05c7256420a977a3dc3d1792de34d5be47a51060 /drivers/gpu/drm/gma500/cdv_device.c | |
parent | 68cb638f9219eeb4967adf08587f4aba64923c3a (diff) |
gma500: Add the base elements of CDV hotplug support
Signed-off-by: Alan Cox <alan@linux.intel.com>
Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/gma500/cdv_device.c')
-rw-r--r-- | drivers/gpu/drm/gma500/cdv_device.c | 41 |
1 files changed, 39 insertions, 2 deletions
diff --git a/drivers/gpu/drm/gma500/cdv_device.c b/drivers/gpu/drm/gma500/cdv_device.c index 5cc06a8fcb7a..62f9b735459b 100644 --- a/drivers/gpu/drm/gma500/cdv_device.c +++ b/drivers/gpu/drm/gma500/cdv_device.c | |||
@@ -462,13 +462,48 @@ static void cdv_get_core_freq(struct drm_device *dev) | |||
462 | } | 462 | } |
463 | } | 463 | } |
464 | 464 | ||
465 | static void cdv_hotplug_work_func(struct work_struct *work) | ||
466 | { | ||
467 | struct drm_psb_private *dev_priv = container_of(work, struct drm_psb_private, | ||
468 | hotplug_work); | ||
469 | struct drm_device *dev = dev_priv->dev; | ||
470 | |||
471 | /* Just fire off a uevent and let userspace tell us what to do */ | ||
472 | drm_helper_hpd_irq_event(dev); | ||
473 | } | ||
474 | |||
475 | /* The core driver has received a hotplug IRQ. We are in IRQ context | ||
476 | so extract the needed information and kick off queued processing */ | ||
477 | |||
478 | static int cdv_hotplug_event(struct drm_device *dev) | ||
479 | { | ||
480 | struct drm_psb_private *dev_priv = dev->dev_private; | ||
481 | schedule_work(&dev_priv->hotplug_work); | ||
482 | REG_WRITE(PORT_HOTPLUG_STAT, REG_READ(PORT_HOTPLUG_STAT)); | ||
483 | return 1; | ||
484 | } | ||
485 | |||
486 | static void cdv_hotplug_enable(struct drm_device *dev, bool on) | ||
487 | { | ||
488 | if (on) { | ||
489 | u32 hotplug = REG_READ(PORT_HOTPLUG_EN); | ||
490 | hotplug |= HDMIB_HOTPLUG_INT_EN | HDMIC_HOTPLUG_INT_EN | | ||
491 | HDMID_HOTPLUG_INT_EN | CRT_HOTPLUG_INT_EN; | ||
492 | REG_WRITE(PORT_HOTPLUG_EN, hotplug); | ||
493 | } else { | ||
494 | REG_WRITE(PORT_HOTPLUG_EN, 0); | ||
495 | REG_WRITE(PORT_HOTPLUG_STAT, REG_READ(PORT_HOTPLUG_STAT)); | ||
496 | } | ||
497 | } | ||
498 | |||
465 | static int cdv_chip_setup(struct drm_device *dev) | 499 | static int cdv_chip_setup(struct drm_device *dev) |
466 | { | 500 | { |
501 | struct drm_psb_private *dev_priv = dev->dev_private; | ||
502 | INIT_WORK(&dev_priv->hotplug_work, cdv_hotplug_work_func); | ||
467 | cdv_get_core_freq(dev); | 503 | cdv_get_core_freq(dev); |
468 | gma_intel_opregion_init(dev); | 504 | gma_intel_opregion_init(dev); |
469 | psb_intel_init_bios(dev); | 505 | psb_intel_init_bios(dev); |
470 | REG_WRITE(PORT_HOTPLUG_EN, 0); | 506 | cdv_hotplug_enable(dev, false); |
471 | REG_WRITE(PORT_HOTPLUG_STAT, REG_READ(PORT_HOTPLUG_STAT)); | ||
472 | return 0; | 507 | return 0; |
473 | } | 508 | } |
474 | 509 | ||
@@ -489,6 +524,8 @@ const struct psb_ops cdv_chip_ops = { | |||
489 | .crtc_funcs = &cdv_intel_crtc_funcs, | 524 | .crtc_funcs = &cdv_intel_crtc_funcs, |
490 | 525 | ||
491 | .output_init = cdv_output_init, | 526 | .output_init = cdv_output_init, |
527 | .hotplug = cdv_hotplug_event, | ||
528 | .hotplug_enable = cdv_hotplug_enable, | ||
492 | 529 | ||
493 | #ifdef CONFIG_BACKLIGHT_CLASS_DEVICE | 530 | #ifdef CONFIG_BACKLIGHT_CLASS_DEVICE |
494 | .backlight_init = cdv_backlight_init, | 531 | .backlight_init = cdv_backlight_init, |