All of lore.kernel.org
 help / color / mirror / Atom feed
From: Hans de Goede <hdegoede@redhat.com>
To: Darren Hart <dvhart@infradead.org>,
	"Rafael J. Wysocki" <rjw@rjwysocki.net>
Cc: "Ben Skeggs" <bskeggs@redhat.com>,
	"Azael Avalos" <coproscefalo@gmail.com>,
	"Corentin Chary" <corentin.chary@gmail.com>,
	"Lee Chun-Yi" <jlee@suse.com>,
	"Cezary Jackiewicz" <cezary.jackiewicz@gmail.com>,
	"Matthew Garrett" <mjg59@srcf.ucam.org>,
	"Pali Rohár" <pali.rohar@gmail.com>,
	"Ike Panhc" <ike.pan@canonical.com>,
	"Anisse Astier" <anisse@astier.eu>,
	"Mattia Dongili" <malattia@linux.it>,
	"Henrique de Moraes Holschuh" <ibm-acpi@hmh.eng.br>,
	platform-driver-x86@vger.kernel.org,
	ibm-acpi-devel@lists.sourceforge.net,
	acpi4asus-user@lists.sourceforge.net,
	dri-devel@lists.freedesktop.org, "Aaron Lu" <aaron.lu@intel.com>,
	linux-acpi@vger.kernel.org, "Hans de Goede" <hdegoede@redhat.com>
Subject: [PATCH v2 07/32] acpi-video-detect: Rewrite backlight interface selection logic
Date: Fri, 12 Jun 2015 13:23:26 +0200	[thread overview]
Message-ID: <1434108231-12323-8-git-send-email-hdegoede@redhat.com> (raw)
In-Reply-To: <1434108231-12323-1-git-send-email-hdegoede@redhat.com>

Currently we have 2 kernel commandline options + dmi-quirks in 3 places all
interacting (in interesting ways) to select which which backlight interface
to use. On the commandline we've acpi_backlight=[video|vendor] and
video.use_native_backlight=[0|1]. DMI quirks we have in
acpi/video-detect.c, acpi/video.c and drivers/platform/x86/*.c .

This commit is the first step to cleaning this up, replacing the 2 cmdline
options with just acpi_backlight=[video|vendor|native|none], and adds a
new API to video_detect.c to reflect this.

Follow up commits will also move other related code, like unregistering the
acpi_video backlight interface if it was registered before other drivers
which take priority over it are loaded, to video_detect.c where this
logic really belongs.

Signed-off-by: Hans de Goede <hdegoede@redhat.com>
---
 drivers/acpi/video_detect.c | 171 +++++++++++++++++++++-----------------------
 include/acpi/video.h        |  17 +++++
 2 files changed, 100 insertions(+), 88 deletions(-)

diff --git a/drivers/acpi/video_detect.c b/drivers/acpi/video_detect.c
index 9af6768..1ae7536 100644
--- a/drivers/acpi/video_detect.c
+++ b/drivers/acpi/video_detect.c
@@ -1,4 +1,6 @@
 /*
+ *  Copyright (C) 2015       Red Hat Inc.
+ *                           Hans de Goede <hdegoede@redhat.com>
  *  Copyright (C) 2008       SuSE Linux Products GmbH
  *                           Thomas Renninger <trenn@suse.de>
  *
@@ -9,44 +11,45 @@
  * acpi_get_pci_dev() can be called to identify ACPI graphics
  * devices for which a real graphics card is plugged in
  *
- * Now acpi_video_get_capabilities() can be called to check which
- * capabilities the graphics cards plugged in support. The check for general
- * video capabilities will be triggered by the first caller of
- * acpi_video_get_capabilities(NULL); which will happen when the first
- * backlight switching supporting driver calls:
- * acpi_video_backlight_support();
- *
  * Depending on whether ACPI graphics extensions (cmp. ACPI spec Appendix B)
  * are available, video.ko should be used to handle the device.
  *
  * Otherwise vendor specific drivers like thinkpad_acpi, asus-laptop,
  * sony_acpi,... can take care about backlight brightness.
  *
- * If CONFIG_ACPI_VIDEO is neither set as "compiled in" (y) nor as a module (m)
- * this file will not be compiled, acpi_video_get_capabilities() and
- * acpi_video_backlight_support() will always return 0 and vendor specific
- * drivers always can handle backlight.
+ * Backlight drivers can use acpi_video_get_backlight_type() to determine
+ * which driver should handle the backlight.
  *
+ * If CONFIG_ACPI_VIDEO is neither set as "compiled in" (y) nor as a module (m)
+ * this file will not be compiled and acpi_video_get_backlight_type() will
+ * always return acpi_backlight_vendor.
  */
 
 #include <linux/export.h>
 #include <linux/acpi.h>
+#include <linux/backlight.h>
 #include <linux/dmi.h>
 #include <linux/module.h>
 #include <linux/pci.h>
+#include <linux/types.h>
+#include <acpi/video.h>
 
 ACPI_MODULE_NAME("video");
 #define _COMPONENT		ACPI_VIDEO_COMPONENT
 
-static long acpi_video_support;
-static bool acpi_video_caps_checked;
+static enum acpi_backlight_type acpi_backlight_cmdline = acpi_backlight_undef;
+static enum acpi_backlight_type acpi_backlight_dmi = acpi_backlight_undef;
 
 static void acpi_video_parse_cmdline(void)
 {
 	if (!strcmp("vendor", acpi_video_backlight_string))
-		acpi_video_support |= ACPI_VIDEO_BACKLIGHT_FORCE_VENDOR;
+		acpi_backlight_cmdline = acpi_backlight_vendor;
 	if (!strcmp("video", acpi_video_backlight_string))
-		acpi_video_support |= ACPI_VIDEO_BACKLIGHT_FORCE_VIDEO;
+		acpi_backlight_cmdline = acpi_backlight_video;
+	if (!strcmp("native", acpi_video_backlight_string))
+		acpi_backlight_cmdline = acpi_backlight_native;
+	if (!strcmp("none", acpi_video_backlight_string))
+		acpi_backlight_cmdline = acpi_backlight_none;
 }
 
 static acpi_status
@@ -77,7 +80,7 @@ find_video(acpi_handle handle, u32 lvl, void *context, void **rv)
  * buggy */
 static int video_detect_force_vendor(const struct dmi_system_id *d)
 {
-	acpi_video_support |= ACPI_VIDEO_BACKLIGHT_DMI_VENDOR;
+	acpi_backlight_dmi = acpi_backlight_vendor;
 	return 0;
 }
 
@@ -125,99 +128,91 @@ static struct dmi_system_id video_detect_dmi_table[] = {
 };
 
 /*
- * Returns the video capabilities of a specific ACPI graphics device
+ * Determine which type of backlight interface to use on this system,
+ * First check cmdline, then dmi quirks, then do autodetect.
+ *
+ * The autodetect order is:
+ * 1) Is the acpi-video backlight interface supported ->
+ *  no, use a vendor interface
+ * 2) Is this a win8 "ready" BIOS and do we have a native interface ->
+ *  yes, use a native interface
+ * 3) Else use the acpi-video interface
  *
- * if NULL is passed as argument all ACPI devices are enumerated and
- * all graphics capabilities of physically present devices are
- * summarized and returned. This is cached and done only once.
+ * Arguably the native on win8 check should be done first, but that would
+ * be a behavior change, which may causes issues.
  */
-static long acpi_video_get_capabilities(acpi_handle graphics_handle)
+enum acpi_backlight_type acpi_video_get_backlight_type(void)
 {
-	long caps = 0;
-	struct acpi_device *tmp_dev;
-	acpi_status status;
-
-	if (acpi_video_caps_checked && graphics_handle == NULL)
-		return acpi_video_support;
-
-	if (!graphics_handle) {
-		/* Only do the global walk through all graphics devices once */
-		acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT,
-				    ACPI_UINT32_MAX, find_video, NULL,
-				    &caps, NULL);
-		/* There might be boot param flags set already... */
-		acpi_video_support |= caps;
-		acpi_video_caps_checked = 1;
-		/* Add blacklists here. Be careful to use the right *DMI* bits
-		 * to still be able to override logic via boot params, e.g.:
-		 *
-		 *   if (dmi_name_in_vendors("XY")) {
-		 *	acpi_video_support |=
-		 *		ACPI_VIDEO_BACKLIGHT_DMI_VENDOR;
-		 *}
-		 */
+	static DEFINE_MUTEX(init_mutex);
+	static bool init_done;
+	static long video_caps;
 
+	/* Parse cmdline, dmi and acpi only once */
+	mutex_lock(&init_mutex);
+	if (!init_done) {
+		acpi_video_parse_cmdline();
 		dmi_check_system(video_detect_dmi_table);
-	} else {
-		status = acpi_bus_get_device(graphics_handle, &tmp_dev);
-		if (ACPI_FAILURE(status)) {
-			ACPI_EXCEPTION((AE_INFO, status, "Invalid device"));
-			return 0;
-		}
-		acpi_walk_namespace(ACPI_TYPE_DEVICE, graphics_handle,
+		acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT,
 				    ACPI_UINT32_MAX, find_video, NULL,
-				    &caps, NULL);
+				    &video_caps, NULL);
+		init_done = true;
 	}
-	ACPI_DEBUG_PRINT((ACPI_DB_INFO, "We have 0x%lX video support %s %s\n",
-			  graphics_handle ? caps : acpi_video_support,
-			  graphics_handle ? "on device " : "in general",
-			  graphics_handle ? acpi_device_bid(tmp_dev) : ""));
-	return caps;
+	mutex_unlock(&init_mutex);
+
+	if (acpi_backlight_cmdline != acpi_backlight_undef)
+		return acpi_backlight_cmdline;
+
+	if (acpi_backlight_dmi != acpi_backlight_undef)
+		return acpi_backlight_dmi;
+
+	if (!(video_caps & ACPI_VIDEO_BACKLIGHT))
+		return acpi_backlight_vendor;
+
+	if (acpi_osi_is_win8() && backlight_device_registered(BACKLIGHT_RAW))
+		return acpi_backlight_native;
+
+	return acpi_backlight_video;
 }
+EXPORT_SYMBOL(acpi_video_get_backlight_type);
 
-static void acpi_video_caps_check(void)
+/*
+ * Set the preferred backlight interface type based on DMI info.
+ * This function allows DMI blacklists to be implemented by external
+ * platform drivers instead of putting a big blacklist in video_detect.c
+ */
+void acpi_video_set_dmi_backlight_type(enum acpi_backlight_type type)
 {
-	/*
-	 * We must check whether the ACPI graphics device is physically plugged
-	 * in. Therefore this must be called after binding PCI and ACPI devices
-	 */
-	if (!acpi_video_caps_checked) {
-		acpi_video_parse_cmdline();
-		acpi_video_get_capabilities(NULL);
-	}
+	acpi_backlight_dmi = type;
 }
+EXPORT_SYMBOL(acpi_video_set_dmi_backlight_type);
 
-/* Promote the vendor interface instead of the generic video module.
- * This function allow DMI blacklists to be implemented by externals
- * platform drivers instead of putting a big blacklist in video_detect.c
+/*
+ * Compatiblity function, this is going away as soon as all drivers are
+ * converted to acpi_video_set_dmi_backlight_type().
+ *
+ * Promote the vendor interface instead of the generic video module.
  * After calling this function you will probably want to call
  * acpi_video_unregister() to make sure the video module is not loaded
  */
 void acpi_video_dmi_promote_vendor(void)
 {
-	acpi_video_caps_check();
-	acpi_video_support |= ACPI_VIDEO_BACKLIGHT_DMI_VENDOR;
+	acpi_video_set_dmi_backlight_type(acpi_backlight_vendor);
 }
 EXPORT_SYMBOL(acpi_video_dmi_promote_vendor);
 
-/* Returns true if video.ko can do backlight switching */
+/*
+ * Compatiblity function, this is going away as soon as all drivers are
+ * converted to acpi_video_get_backlight_type().
+ *
+ * Returns true if video.ko can do backlight switching.
+ */
 int acpi_video_backlight_support(void)
 {
-	acpi_video_caps_check();
-
-	/* First check for boot param -> highest prio */
-	if (acpi_video_support & ACPI_VIDEO_BACKLIGHT_FORCE_VENDOR)
-		return 0;
-	else if (acpi_video_support & ACPI_VIDEO_BACKLIGHT_FORCE_VIDEO)
-		return 1;
-
-	/* Then check for DMI blacklist -> second highest prio */
-	if (acpi_video_support & ACPI_VIDEO_BACKLIGHT_DMI_VENDOR)
-		return 0;
-	else if (acpi_video_support & ACPI_VIDEO_BACKLIGHT_DMI_VIDEO)
-		return 1;
-
-	/* Then go the default way */
-	return acpi_video_support & ACPI_VIDEO_BACKLIGHT;
+	/*
+	 * This is done this way since vendor drivers call this to see
+	 * if they should load, and we do not want them to load for both
+	 * the acpi_backlight_video and acpi_backlight_native cases.
+	 */
+	return acpi_video_get_backlight_type() != acpi_backlight_vendor;
 }
 EXPORT_SYMBOL(acpi_video_backlight_support);
diff --git a/include/acpi/video.h b/include/acpi/video.h
index 843ef1a..01b5cc7 100644
--- a/include/acpi/video.h
+++ b/include/acpi/video.h
@@ -16,6 +16,14 @@ struct acpi_device;
 #define ACPI_VIDEO_DISPLAY_LEGACY_PANEL   0x0110
 #define ACPI_VIDEO_DISPLAY_LEGACY_TV      0x0200
 
+enum acpi_backlight_type {
+	acpi_backlight_undef = -1,
+	acpi_backlight_none = 0,
+	acpi_backlight_video,
+	acpi_backlight_vendor,
+	acpi_backlight_native,
+};
+
 #if (defined CONFIG_ACPI_VIDEO || defined CONFIG_ACPI_VIDEO_MODULE)
 extern int acpi_video_register(void);
 extern void acpi_video_unregister(void);
@@ -23,6 +31,8 @@ extern void acpi_video_unregister_backlight(void);
 extern int acpi_video_get_edid(struct acpi_device *device, int type,
 			       int device_id, void **edid);
 extern bool acpi_video_verify_backlight_support(void);
+extern enum acpi_backlight_type acpi_video_get_backlight_type(void);
+extern void acpi_video_set_dmi_backlight_type(enum acpi_backlight_type type);
 #else
 static inline int acpi_video_register(void) { return 0; }
 static inline void acpi_video_unregister(void) { return; }
@@ -33,6 +43,13 @@ static inline int acpi_video_get_edid(struct acpi_device *device, int type,
 	return -ENODEV;
 }
 static inline bool acpi_video_verify_backlight_support(void) { return false; }
+static inline enum acpi_backlight_type acpi_video_get_backlight_type(void)
+{
+	return acpi_backlight_vendor;
+}
+static void acpi_video_set_dmi_backlight_type(enum acpi_backlight_type type)
+{
+}
 #endif
 
 #endif
-- 
2.4.2

  parent reply	other threads:[~2015-06-12 11:23 UTC|newest]

Thread overview: 39+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-06-12 11:23 [PATCH v2 00/32] acpi-video: Rewrite backlight interface selection logic Hans de Goede
2015-06-12 11:23 ` [PATCH v2 01/32] apple-gmux: Stop using acpi_video_dmi_demote_vendor() Hans de Goede
2015-06-12 11:23 ` [PATCH v2 02/32] acpi-video-detect: Remove the unused acpi_video_dmi_demote_vendor() function Hans de Goede
2015-06-12 11:23 ` [PATCH v2 03/32] acpi-video-detect: Make acpi_video_get_capabilities a private function Hans de Goede
2015-06-12 11:23 ` [PATCH v2 04/32] acpi-video-detect: Move acpi_is_video_device() to acpi/scan.c Hans de Goede
2015-06-12 11:23 ` [PATCH v2 05/32] acpi-video-detect: Move acpi_osi_is_win8 to osl.c Hans de Goede
2015-06-12 11:23 ` [PATCH v2 06/32] acpi-video-detect: video: Make video_detect code part of the video module Hans de Goede
2015-06-12 11:23 ` Hans de Goede [this message]
2015-06-12 11:23 ` [PATCH v2 08/32] acpi-video-detect: Unregister acpi_video backlight when dmi quirks are added Hans de Goede
2015-06-12 11:23 ` [PATCH v2 09/32] drm: i915: Port to new backlight interface selection API Hans de Goede
2015-06-12 11:23 ` [PATCH v2 10/32] acpi-video: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 11/32] acpi-video: Move backlight notifier to video_detect.c Hans de Goede
2015-06-12 11:23 ` [PATCH v2 12/32] acpi-video: Move dmi_check_system from module_init to acpi_video_register Hans de Goede
2015-06-12 11:23 ` [PATCH v2 13/32] acpi-video: Fix acpi_video _register vs _unregister_backlight race Hans de Goede
2015-06-12 11:23 ` [PATCH v2 14/32] acer-wmi: Port to new backlight interface selection API Hans de Goede
2015-06-12 11:23 ` [PATCH v2 15/32] apple-gmux: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 16/32] asus-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 17/32] asus-wmi: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 18/32] compal-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 19/32] dell-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 20/32] dell-wmi: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 21/32] eeepc-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 22/32] fujitsu-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 23/32] ideapad-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 24/32] intel-oaktrail: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 25/32] msi-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 26/32] msi-wmi: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 27/32] samsung-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 28/32] sony-laptop: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 29/32] thinkpad-acpi: " Hans de Goede
2015-06-12 11:23 ` [PATCH v2 30/32] toshiba-acpi: " Hans de Goede
2015-06-14  3:15   ` Azael Avalos
2015-06-16 12:53     ` Hans de Goede
2015-06-12 11:23 ` [PATCH v2 31/32] acpi-video-detect: Remove old API Hans de Goede
2015-06-12 11:23 ` [PATCH v2 32/32] acpi-video: Make acpi_video_unregister_backlight() private Hans de Goede
2015-06-15 23:22 ` [PATCH v2 00/32] acpi-video: Rewrite backlight interface selection logic Rafael J. Wysocki
2015-06-17  3:39   ` Darren Hart
2015-06-17  9:36     ` Rafael J. Wysocki
2015-06-18 21:05       ` Darren Hart

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1434108231-12323-8-git-send-email-hdegoede@redhat.com \
    --to=hdegoede@redhat.com \
    --cc=aaron.lu@intel.com \
    --cc=acpi4asus-user@lists.sourceforge.net \
    --cc=anisse@astier.eu \
    --cc=bskeggs@redhat.com \
    --cc=cezary.jackiewicz@gmail.com \
    --cc=coproscefalo@gmail.com \
    --cc=corentin.chary@gmail.com \
    --cc=dri-devel@lists.freedesktop.org \
    --cc=dvhart@infradead.org \
    --cc=ibm-acpi-devel@lists.sourceforge.net \
    --cc=ibm-acpi@hmh.eng.br \
    --cc=ike.pan@canonical.com \
    --cc=jlee@suse.com \
    --cc=linux-acpi@vger.kernel.org \
    --cc=malattia@linux.it \
    --cc=mjg59@srcf.ucam.org \
    --cc=pali.rohar@gmail.com \
    --cc=platform-driver-x86@vger.kernel.org \
    --cc=rjw@rjwysocki.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.