]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
.32 patches
authorGreg Kroah-Hartman <gregkh@suse.de>
Thu, 5 Aug 2010 23:55:57 +0000 (16:55 -0700)
committerGreg Kroah-Hartman <gregkh@suse.de>
Thu, 5 Aug 2010 23:55:57 +0000 (16:55 -0700)
queue-2.6.32/drm-i915-Fix-LVDS-presence-check [new file with mode: 0644]
queue-2.6.32/drm-i915-parse-child-device-from-vbt.patch [new file with mode: 0644]
queue-2.6.32/series

diff --git a/queue-2.6.32/drm-i915-Fix-LVDS-presence-check b/queue-2.6.32/drm-i915-Fix-LVDS-presence-check
new file mode 100644 (file)
index 0000000..5874902
--- /dev/null
@@ -0,0 +1,141 @@
+From 38b3037ee47fbd65a36bc7c39f60a900fbbe3b8e Mon Sep 17 00:00:00 2001
+From: Adam Jackson <ajax@redhat.com>
+Date: Tue, 24 Nov 2009 10:07:00 -0500
+Subject: drm/i915: Fix LVDS presence check
+
+Combined patches from 2.6.33 for fixing LVDS detection.
+7cf4f69d3f4511f443473954456cb91d5514756d
+    drm/i915: Don't set up the LVDS if it isn't in the BIOS device table.
+38b3037ee47fbd65a36bc7c39f60a900fbbe3b8e
+    drm/i915: Fix LVDS presence check
+6e36595a2131e7ed5ee2674be54b2713ba7f0490
+    drm/i915: Declare the new VBT parsing functions as static
+11ba159288f1bfc1a475c994e598f5fe423fde9d
+    drm/i915: Don't check for lid presence when detecting LVDS
+
+Acked-by: Takashi Iwai <tiwai@suse.de>
+Cc: Matthew Garrett <mjg@redhat.com>
+Cc: Adam Jackson <ajax@redhat.com>
+Cc: Eric Anholt <eric@anholt.net>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/gpu/drm/i915/intel_lvds.c |   90 +++++++++++++-------------------------
+ 1 file changed, 33 insertions(+), 57 deletions(-)
+
+--- a/drivers/gpu/drm/i915/intel_lvds.c
++++ b/drivers/gpu/drm/i915/intel_lvds.c
+@@ -901,64 +901,45 @@ static const struct dmi_system_id intel_
+       { }     /* terminating entry */
+ };
+-#ifdef CONFIG_ACPI
+ /*
+- * check_lid_device -- check whether @handle is an ACPI LID device.
+- * @handle: ACPI device handle
+- * @level : depth in the ACPI namespace tree
+- * @context: the number of LID device when we find the device
+- * @rv: a return value to fill if desired (Not use)
++ * Enumerate the child dev array parsed from VBT to check whether
++ * the LVDS is present.
++ * If it is present, return 1.
++ * If it is not present, return false.
++ * If no child dev is parsed from VBT, it assumes that the LVDS is present.
++ * Note: The addin_offset should also be checked for LVDS panel.
++ * Only when it is non-zero, it is assumed that it is present.
+  */
+-static acpi_status
+-check_lid_device(acpi_handle handle, u32 level, void *context,
+-                      void **return_value)
++static int lvds_is_present_in_vbt(struct drm_device *dev)
+ {
+-      struct acpi_device *acpi_dev;
+-      int *lid_present = context;
+-
+-      acpi_dev = NULL;
+-      /* Get the acpi device for device handle */
+-      if (acpi_bus_get_device(handle, &acpi_dev) || !acpi_dev) {
+-              /* If there is no ACPI device for handle, return */
+-              return AE_OK;
+-      }
+-
+-      if (!strncmp(acpi_device_hid(acpi_dev), "PNP0C0D", 7))
+-              *lid_present = 1;
++      struct drm_i915_private *dev_priv = dev->dev_private;
++      struct child_device_config *p_child;
++      int i, ret;
+-      return AE_OK;
+-}
++      if (!dev_priv->child_dev_num)
++              return 1;
+-/**
+- * check whether there exists the ACPI LID device by enumerating the ACPI
+- * device tree.
+- */
+-static int intel_lid_present(void)
+-{
+-      int lid_present = 0;
++      ret = 0;
++      for (i = 0; i < dev_priv->child_dev_num; i++) {
++              p_child = dev_priv->child_dev + i;
++              /*
++               * If the device type is not LFP, continue.
++               * If the device type is 0x22, it is also regarded as LFP.
++               */
++              if (p_child->device_type != DEVICE_TYPE_INT_LFP &&
++                      p_child->device_type != DEVICE_TYPE_LFP)
++                      continue;
+-      if (acpi_disabled) {
+-              /* If ACPI is disabled, there is no ACPI device tree to
+-               * check, so assume the LID device would have been present.
++              /* The addin_offset should be checked. Only when it is
++               * non-zero, it is regarded as present.
+                */
+-              return 1;
++              if (p_child->addin_offset) {
++                      ret = 1;
++                      break;
++              }
+       }
+-
+-      acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT,
+-                              ACPI_UINT32_MAX,
+-                              check_lid_device, &lid_present, NULL);
+-
+-      return lid_present;
+-}
+-#else
+-static int intel_lid_present(void)
+-{
+-      /* In the absence of ACPI built in, assume that the LID device would
+-       * have been present.
+-       */
+-      return 1;
++      return ret;
+ }
+-#endif
+ /**
+  * intel_lvds_init - setup LVDS connectors on this device
+@@ -983,15 +964,10 @@ void intel_lvds_init(struct drm_device *
+       if (dmi_check_system(intel_no_lvds))
+               return;
+-      /* Assume that any device without an ACPI LID device also doesn't
+-       * have an integrated LVDS.  We would be better off parsing the BIOS
+-       * to get a reliable indicator, but that code isn't written yet.
+-       *
+-       * In the case of all-in-one desktops using LVDS that we've seen,
+-       * they're using SDVO LVDS.
+-       */
+-      if (!intel_lid_present())
++      if (!lvds_is_present_in_vbt(dev)) {
++              DRM_DEBUG_KMS("LVDS is not present in VBT\n");
+               return;
++      }
+       if (IS_IGDNG(dev)) {
+               if ((I915_READ(PCH_LVDS) & LVDS_DETECTED) == 0)
diff --git a/queue-2.6.32/drm-i915-parse-child-device-from-vbt.patch b/queue-2.6.32/drm-i915-parse-child-device-from-vbt.patch
new file mode 100644 (file)
index 0000000..8c618b9
--- /dev/null
@@ -0,0 +1,174 @@
+From 6363ee6f496eb7e3b3f78dc105e522c7b496089b Mon Sep 17 00:00:00 2001
+From: Zhao Yakui <yakui.zhao@intel.com>
+Date: Tue, 24 Nov 2009 09:48:44 +0800
+Subject: drm/i915: parse child device from VBT
+
+From: Zhao Yakui <yakui.zhao@intel.com>
+
+commit 6363ee6f496eb7e3b3f78dc105e522c7b496089b upstream.
+
+On some laptops there is no HDMI/DP. But the xrandr still reports
+several disconnected HDMI/display ports. In such case the user will be
+confused.
+ >DVI1 disconnected (normal left inverted right x axis y axis)
+ >DP1 disconnected (normal left inverted right x axis y axis)
+ >DVI2 disconnected (normal left inverted right x axis y axis)
+ >DP2 disconnected (normal left inverted right x axis y axis)
+ >DP3 disconnected (normal left inverted right x axis y axis)
+
+This patch set is to use the child device parsed in VBT to decide whether
+the HDMI/DP/LVDS/TV should be initialized.
+
+Parse the child device from VBT.
+
+The device class type is also added for LFP, TV, HDMI, DP output.
+
+https://bugs.freedesktop.org/show_bug.cgi?id=22785
+
+Signed-off-by: Zhao Yakui <yakui.zhao@intel.com>
+Reviewed-by: Adam Jackson <ajax@redhat.com>
+Signed-off-by: Eric Anholt <eric@anholt.net>
+Acked-by: Takashi Iwai <tiwai@suse.de>
+Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
+
+---
+ drivers/gpu/drm/i915/i915_dma.c   |    9 +++++
+ drivers/gpu/drm/i915/i915_drv.h   |    2 +
+ drivers/gpu/drm/i915/intel_bios.c |   65 ++++++++++++++++++++++++++++++++++++++
+ drivers/gpu/drm/i915/intel_bios.h |   17 +++++++++
+ 4 files changed, 93 insertions(+)
+
+--- a/drivers/gpu/drm/i915/i915_dma.c
++++ b/drivers/gpu/drm/i915/i915_dma.c
+@@ -1526,6 +1526,15 @@ int i915_driver_unload(struct drm_device
+       }
+       if (drm_core_check_feature(dev, DRIVER_MODESET)) {
++              /*
++               * free the memory space allocated for the child device
++               * config parsed from VBT
++               */
++              if (dev_priv->child_dev && dev_priv->child_dev_num) {
++                      kfree(dev_priv->child_dev);
++                      dev_priv->child_dev = NULL;
++                      dev_priv->child_dev_num = 0;
++              }
+               drm_irq_uninstall(dev);
+               vga_client_register(dev->pdev, NULL, NULL, NULL);
+       }
+--- a/drivers/gpu/drm/i915/i915_drv.h
++++ b/drivers/gpu/drm/i915/i915_drv.h
+@@ -555,6 +555,8 @@ typedef struct drm_i915_private {
+       struct timer_list idle_timer;
+       bool busy;
+       u16 orig_clock;
++      int child_dev_num;
++      struct child_device_config *child_dev;
+       struct drm_connector *int_lvds_connector;
+ } drm_i915_private_t;
+--- a/drivers/gpu/drm/i915/intel_bios.c
++++ b/drivers/gpu/drm/i915/intel_bios.c
+@@ -362,6 +362,70 @@ parse_driver_features(struct drm_i915_pr
+               dev_priv->render_reclock_avail = true;
+ }
++static void
++parse_device_mapping(struct drm_i915_private *dev_priv,
++                     struct bdb_header *bdb)
++{
++      struct bdb_general_definitions *p_defs;
++      struct child_device_config *p_child, *child_dev_ptr;
++      int i, child_device_num, count;
++      u16     block_size;
++
++      p_defs = find_section(bdb, BDB_GENERAL_DEFINITIONS);
++      if (!p_defs) {
++              DRM_DEBUG_KMS("No general definition block is found\n");
++              return;
++      }
++      /* judge whether the size of child device meets the requirements.
++       * If the child device size obtained from general definition block
++       * is different with sizeof(struct child_device_config), skip the
++       * parsing of sdvo device info
++       */
++      if (p_defs->child_dev_size != sizeof(*p_child)) {
++              /* different child dev size . Ignore it */
++              DRM_DEBUG_KMS("different child size is found. Invalid.\n");
++              return;
++      }
++      /* get the block size of general definitions */
++      block_size = get_blocksize(p_defs);
++      /* get the number of child device */
++      child_device_num = (block_size - sizeof(*p_defs)) /
++                              sizeof(*p_child);
++      count = 0;
++      /* get the number of child device that is present */
++      for (i = 0; i < child_device_num; i++) {
++              p_child = &(p_defs->devices[i]);
++              if (!p_child->device_type) {
++                      /* skip the device block if device type is invalid */
++                      continue;
++              }
++              count++;
++      }
++      if (!count) {
++              DRM_DEBUG_KMS("no child dev is parsed from VBT \n");
++              return;
++      }
++      dev_priv->child_dev = kzalloc(sizeof(*p_child) * count, GFP_KERNEL);
++      if (!dev_priv->child_dev) {
++              DRM_DEBUG_KMS("No memory space for child device\n");
++              return;
++      }
++
++      dev_priv->child_dev_num = count;
++      count = 0;
++      for (i = 0; i < child_device_num; i++) {
++              p_child = &(p_defs->devices[i]);
++              if (!p_child->device_type) {
++                      /* skip the device block if device type is invalid */
++                      continue;
++              }
++              child_dev_ptr = dev_priv->child_dev + count;
++              count++;
++              memcpy((void *)child_dev_ptr, (void *)p_child,
++                                      sizeof(*p_child));
++      }
++      return;
++}
+ /**
+  * intel_init_bios - initialize VBIOS settings & find VBT
+  * @dev: DRM device
+@@ -413,6 +477,7 @@ intel_init_bios(struct drm_device *dev)
+       parse_lfp_panel_data(dev_priv, bdb);
+       parse_sdvo_panel_data(dev_priv, bdb);
+       parse_sdvo_device_mapping(dev_priv, bdb);
++      parse_device_mapping(dev_priv, bdb);
+       parse_driver_features(dev_priv, bdb);
+       pci_unmap_rom(pdev, bios);
+--- a/drivers/gpu/drm/i915/intel_bios.h
++++ b/drivers/gpu/drm/i915/intel_bios.h
+@@ -549,4 +549,21 @@ bool intel_init_bios(struct drm_device *
+ #define   SWF14_APM_STANDBY   0x1
+ #define   SWF14_APM_RESTORE   0x0
++/* Add the device class for LFP, TV, HDMI */
++#define        DEVICE_TYPE_INT_LFP    0x1022
++#define        DEVICE_TYPE_INT_TV     0x1009
++#define        DEVICE_TYPE_HDMI       0x60D2
++#define        DEVICE_TYPE_DP         0x68C6
++#define        DEVICE_TYPE_eDP        0x78C6
++
++/* define the DVO port for HDMI output type */
++#define               DVO_B           1
++#define               DVO_C           2
++#define               DVO_D           3
++
++/* define the PORT for DP output type */
++#define               PORT_IDPB       7
++#define               PORT_IDPC       8
++#define               PORT_IDPD       9
++
+ #endif /* _I830_BIOS_H_ */
index 03f3ecfbf5b43b6c452653c101d3443a9fb1774a..43514852340553fa1990d6058014160b91a0c524 100644 (file)
@@ -25,3 +25,5 @@ slow-work-use-get_ref-wrapper-instead-of-directly-calling-get_ref.patch
 cifs-remove-__exit-mark-from-cifs_exit_dns_resolver.patch
 cifs-fix-compile-error-with-__init-in-cifs_init_dns_resolver-definition.patch
 xen-drop-xen_sched_clock-in-favour-of-using-plain-wallclock-time.patch
+drm-i915-Fix-LVDS-presence-check
+drm-i915-parse-child-device-from-vbt.patch