[PATCH 5/7] Detect ACPI BIOS brightness capabilities early

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Detect ACPI BIOS brightness capabilities early

Detect whether an ACPI graphics device supports ACPI video
or the Integrated Graphics Device (IGD) extensions.
Only check physically plugged, not the dummy devices.
Depending on whether the kernel supports the IGD device, drivers
can decide whether native vendor specific or a generic driver should
take brightness or display switching control.

Introduce a boot parameter: acpi_brightness_by_vendor
If set, the ACPI video driver will not control brightness

Signed-off-by: Thomas Renninger <trenn@xxxxxxx>

---
 drivers/acpi/scan.c  |   95 +++++++++++++++++++++++++++++++++++++++++++++++----
 include/linux/acpi.h |    9 ++++
 2 files changed, 97 insertions(+), 7 deletions(-)

Index: linux-acpi-2.6_video_native_vs_vendor/drivers/acpi/scan.c
===================================================================
--- linux-acpi-2.6_video_native_vs_vendor.orig/drivers/acpi/scan.c
+++ linux-acpi-2.6_video_native_vs_vendor/drivers/acpi/scan.c
@@ -879,10 +879,61 @@ static void acpi_device_get_busid(struct
 	}
 }
 
+/*
+ * Indicates which video capabilities are available in BIOS and follow the
+ * ACPI spec.
+ * If CONFIG_ACPI_VIDEO is not defined, the variable stays 0 and vendor
+ * specific drivers will always take over..., otherwise they want to take
+ * over some parts, e.g. if we have an IGD device, but no IGD driver yet,
+ * or if user explicitly requests native driver brightness support
+*/
+u8 acpi_video_support;
+EXPORT_SYMBOL(acpi_video_support);
+
+#if defined(CONFIG_ACPI_VIDEO) || defined(CONFIG_ACPI_VIDEO_MODULE)
+
+static int __init acpi_brightness_force_vendor(char *str)
+{
+	acpi_video_support &= ACPI_VIDEO_FORCE_VENDOR_SPECIFIC;
+	return 1;
+}
+__setup("acpi_video_by_vendor", acpi_brightness_force_vendor);
+
+static acpi_status
+acpi_brightness_cap_match(acpi_handle handle, u32 level, void *context,
+			  void **return_value)
+{
+       acpi_handle h_dummy;
+
+       if (ACPI_SUCCESS(acpi_get_handle(handle, "_BCM", &h_dummy)) &&
+	   ACPI_SUCCESS(acpi_get_handle(handle, "_BCL", &h_dummy))) {
+	       printk(KERN_INFO "Brightness switching support detected\n");
+	       acpi_video_support |= ACPI_VIDEO_BRIGHTNESS;
+	       return 0;
+       }
+       return -ENODEV;
+}
+
+static void acpi_video_igd_match(struct acpi_device *device)
+{
+
+	acpi_handle h_dummy;
+
+	/* We should check for all mandatory IGD functions here */
+	if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DRDY", &h_dummy))) {
+		acpi_video_support |= ACPI_VIDEO_IGD;
+	}
+}
+
+/*
+ * If this one returns 0, the device will be marked as a video device
+ * and the ACPI video driver module will be autoloaded
+ */
 static int
 acpi_video_bus_match(struct acpi_device *device)
 {
 	acpi_handle h_dummy;
+	struct device *dev;
 
 	if (!device)
 		return -EINVAL;
@@ -893,22 +944,52 @@ acpi_video_bus_match(struct acpi_device 
 
 	/* Does this device able to support video switching ? */
 	if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOD", &h_dummy)) &&
-	    ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOS", &h_dummy)))
-		return 0;
-
+	    ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOS", &h_dummy))) {
+		acpi_video_support |= ACPI_VIDEO_OUTPUT_SWITCHING;
+		goto success;
+	}
 	/* Does this device able to retrieve a video ROM ? */
-	if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_ROM", &h_dummy)))
-		return 0;
+	if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_ROM", &h_dummy))) {
+		acpi_video_support |= ACPI_VIDEO_ROM_AVAILABLE;
+		goto success;
+	}
 
 	/* Does this device able to configure which video head to be POSTed ? */
 	if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_VPO", &h_dummy)) &&
 	    ACPI_SUCCESS(acpi_get_handle(device->handle, "_GPD", &h_dummy)) &&
-	    ACPI_SUCCESS(acpi_get_handle(device->handle, "_SPD", &h_dummy)))
+	    ACPI_SUCCESS(acpi_get_handle(device->handle, "_SPD", &h_dummy))) {
+		acpi_video_support |= ACPI_VIDEO_DEVICE_POSTING;
+		goto success;
+	}
+	return -ENODEV;
+
+ success:
+	dev = acpi_get_physical_pci_device(device->handle);
+	if (!dev)
+		/* An ACPI dummy device, no card is plugged in, still return
+		 * true so that this device can later be identified as a video
+		 * device via CID list
+		 */
 		return 0;
+	put_device(dev);
 
-	return -ENODEV;
+	/* This device is a video device which is really plugged in,
+	   now also check for IGD and brightness support */
+	acpi_walk_namespace(ACPI_TYPE_DEVICE, device->handle, ACPI_UINT32_MAX,
+			    acpi_brightness_cap_match, NULL, NULL);
+	/* IGD testing might not be necessary if no brightness functions
+	   are available */
+	acpi_video_igd_match(device);
+	return 0;
 }
 
+#else /* CONFIG_ACPI_VIDEO || CONFIG_ACPI_VIDEO_MODULE */
+
+static int
+acpi_video_bus_match(struct acpi_device *device) { return 0; }
+
+#endif
+
 /*
  * acpi_bay_match - see if a device is an ejectable driver bay
  *
Index: linux-acpi-2.6_video_native_vs_vendor/include/linux/acpi.h
===================================================================
--- linux-acpi-2.6_video_native_vs_vendor.orig/include/linux/acpi.h
+++ linux-acpi-2.6_video_native_vs_vendor/include/linux/acpi.h
@@ -169,6 +169,15 @@ struct acpi_pci_driver {
 int acpi_pci_register_driver(struct acpi_pci_driver *driver);
 void acpi_pci_unregister_driver(struct acpi_pci_driver *driver);
 
+/* video/brightness support */
+#define ACPI_VIDEO_OUTPUT_SWITCHING		1
+#define ACPI_VIDEO_DEVICE_POSTING		2
+#define ACPI_VIDEO_ROM_AVAILABLE		4
+#define ACPI_VIDEO_BRIGHTNESS			8
+#define ACPI_VIDEO_IGD				16
+#define ACPI_VIDEO_FORCE_VENDOR_SPECIFIC	32
+extern u8 acpi_video_support;
+
 #ifdef CONFIG_ACPI_EC
 
 extern int ec_read(u8 addr, u8 *val);


--
To unsubscribe from this list: send the line "unsubscribe linux-acpi" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux IBM ACPI]     [Linux Power Management]     [Linux Kernel]     [Linux Laptop]     [Kernel Newbies]     [Share Photos]     [Security]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Samba]     [Video 4 Linux]     [Device Mapper]     [Linux Resources]

  Powered by Linux