[PATCH 23/23] ACPI: thinkpad-acpi: add locking to brightness subdriver

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

 



The backlight class does all the locking needed for sysfs access, but
offers no API to interface to that locking without an layer violation.

Since we need to mutex-lock procfs access, implement in-driver locking for
brightness.  It will go away the day thinkpad-acpi procfs goes away, or the
backlight class gives us a way to use its locks without a layer violation.

Signed-off-by: Henrique de Moraes Holschuh <hmh@xxxxxxxxxx>
---
 drivers/misc/thinkpad_acpi.c |   35 ++++++++++++++++++++++++++++-------
 1 files changed, 28 insertions(+), 7 deletions(-)

diff --git a/drivers/misc/thinkpad_acpi.c b/drivers/misc/thinkpad_acpi.c
index 01bed93..f15a58f 100644
--- a/drivers/misc/thinkpad_acpi.c
+++ b/drivers/misc/thinkpad_acpi.c
@@ -3000,12 +3000,16 @@ static struct backlight_ops ibm_backlight_data = {
         .update_status  = brightness_update_status,
 };
 
+static struct mutex brightness_mutex;
+
 static int __init brightness_init(struct ibm_init_struct *iibm)
 {
 	int b;
 
 	vdbg_printk(TPACPI_DBG_INIT, "initializing brightness subdriver\n");
 
+	mutex_init(&brightness_mutex);
+
 	if (!brightness_mode) {
 		if (thinkpad_id.vendor == PCI_VENDOR_ID_LENOVO)
 			brightness_mode = 2;
@@ -3092,27 +3096,44 @@ static int brightness_get(struct backlight_device *bd)
 
 static int brightness_set(int value)
 {
-	int cmos_cmd, inc, i;
-	int current_value = brightness_get(NULL);
+	int cmos_cmd, inc, i, res;
+	int current_value;
 
 	if (value > 7)
 		return -EINVAL;
 
+	res = mutex_lock_interruptible(&brightness_mutex);
+	if (res < 0)
+		return res;
+
+	current_value = brightness_get(NULL);
+	if (current_value < 0) {
+		res = current_value;
+		goto errout;
+	}
+
 	cmos_cmd = value > current_value ?
 			TP_CMOS_BRIGHTNESS_UP :
 			TP_CMOS_BRIGHTNESS_DOWN;
 	inc = value > current_value ? 1 : -1;
 
+	res = 0;
 	for (i = current_value; i != value; i += inc) {
 		if ((brightness_mode & 2) &&
-		    issue_thinkpad_cmos_command(cmos_cmd))
-			return -EIO;
+		    issue_thinkpad_cmos_command(cmos_cmd)) {
+			res = -EIO;
+			goto errout;
+		}
 		if ((brightness_mode & 1) &&
-		    !acpi_ec_write(brightness_offset, i + inc))
-			return -EIO;
+		    !acpi_ec_write(brightness_offset, i + inc)) {
+			res = -EIO;
+			goto errout;;
+		}
 	}
 
-	return 0;
+errout:
+	mutex_unlock(&brightness_mutex);
+	return res;
 }
 
 static int brightness_read(char *p)
-- 
1.5.2.1

-
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