aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMatej Groma <matejgroma@gmail.com>2016-06-21 04:09:21 -0400
committerDarren Hart <dvhart@linux.intel.com>2016-06-29 01:18:34 -0400
commitd6b88f64b0d460c400b1db2d9556bc6a37d29415 (patch)
tree6615cf75a3b59f4be2d65c7cfa27becb13df6ff9
parent1879e69f4c57ead5ff696eb309a0422d01c1cc06 (diff)
fujitsu-laptop: Add support for eco LED
There is an indicator LED signaling activated power saving mode on certain Fujitsu laptop models. This has currently no use on Linux. Export it to userspace. Signed-off-by: Matej Groma <matejgroma@gmail.com> Acked-by: Jonathan Woithe <jwoithe@just42.net> Signed-off-by: Darren Hart <dvhart@linux.intel.com>
-rw-r--r--drivers/platform/x86/fujitsu-laptop.c56
1 files changed, 56 insertions, 0 deletions
diff --git a/drivers/platform/x86/fujitsu-laptop.c b/drivers/platform/x86/fujitsu-laptop.c
index 5144c353fa14..6ce8e7860013 100644
--- a/drivers/platform/x86/fujitsu-laptop.c
+++ b/drivers/platform/x86/fujitsu-laptop.c
@@ -105,6 +105,8 @@
105#define LOGOLAMP_POWERON 0x2000 105#define LOGOLAMP_POWERON 0x2000
106#define LOGOLAMP_ALWAYS 0x4000 106#define LOGOLAMP_ALWAYS 0x4000
107#define RADIO_LED_ON 0x20 107#define RADIO_LED_ON 0x20
108#define ECO_LED 0x10000
109#define ECO_LED_ON 0x80000
108#endif 110#endif
109 111
110/* Hotkey details */ 112/* Hotkey details */
@@ -166,6 +168,7 @@ struct fujitsu_hotkey_t {
166 int logolamp_registered; 168 int logolamp_registered;
167 int kblamps_registered; 169 int kblamps_registered;
168 int radio_led_registered; 170 int radio_led_registered;
171 int eco_led_registered;
169}; 172};
170 173
171static struct fujitsu_hotkey_t *fujitsu_hotkey; 174static struct fujitsu_hotkey_t *fujitsu_hotkey;
@@ -202,6 +205,17 @@ static struct led_classdev radio_led = {
202 .brightness_get = radio_led_get, 205 .brightness_get = radio_led_get,
203 .brightness_set = radio_led_set 206 .brightness_set = radio_led_set
204}; 207};
208
209static enum led_brightness eco_led_get(struct led_classdev *cdev);
210static void eco_led_set(struct led_classdev *cdev,
211 enum led_brightness brightness);
212
213static struct led_classdev eco_led = {
214 .name = "fujitsu::eco_led",
215 .max_brightness = 1,
216 .brightness_get = eco_led_get,
217 .brightness_set = eco_led_set
218};
205#endif 219#endif
206 220
207#ifdef CONFIG_FUJITSU_LAPTOP_DEBUG 221#ifdef CONFIG_FUJITSU_LAPTOP_DEBUG
@@ -286,6 +300,18 @@ static void radio_led_set(struct led_classdev *cdev,
286 call_fext_func(FUNC_RFKILL, 0x5, RADIO_LED_ON, 0x0); 300 call_fext_func(FUNC_RFKILL, 0x5, RADIO_LED_ON, 0x0);
287} 301}
288 302
303static void eco_led_set(struct led_classdev *cdev,
304 enum led_brightness brightness)
305{
306 int curr;
307
308 curr = call_fext_func(FUNC_LEDS, 0x2, ECO_LED, 0x0);
309 if (brightness)
310 call_fext_func(FUNC_LEDS, 0x1, ECO_LED, curr | ECO_LED_ON);
311 else
312 call_fext_func(FUNC_LEDS, 0x1, ECO_LED, curr & ~ECO_LED_ON);
313}
314
289static enum led_brightness logolamp_get(struct led_classdev *cdev) 315static enum led_brightness logolamp_get(struct led_classdev *cdev)
290{ 316{
291 enum led_brightness brightness = LED_OFF; 317 enum led_brightness brightness = LED_OFF;
@@ -320,6 +346,16 @@ static enum led_brightness radio_led_get(struct led_classdev *cdev)
320 346
321 return brightness; 347 return brightness;
322} 348}
349
350static enum led_brightness eco_led_get(struct led_classdev *cdev)
351{
352 enum led_brightness brightness = LED_OFF;
353
354 if (call_fext_func(FUNC_LEDS, 0x2, ECO_LED, 0x0) & ECO_LED_ON)
355 brightness = cdev->max_brightness;
356
357 return brightness;
358}
323#endif 359#endif
324 360
325/* Hardware access for LCD brightness control */ 361/* Hardware access for LCD brightness control */
@@ -934,6 +970,23 @@ static int acpi_fujitsu_hotkey_add(struct acpi_device *device)
934 result); 970 result);
935 } 971 }
936 } 972 }
973
974 /* Support for eco led is not always signaled in bit corresponding
975 * to the bit used to control the led. According to the DSDT table,
976 * bit 14 seems to indicate presence of said led as well.
977 * Confirm by testing the status.
978 */
979 if ((call_fext_func(FUNC_LEDS, 0x0, 0x0, 0x0) & BIT(14)) &&
980 (call_fext_func(FUNC_LEDS, 0x2, ECO_LED, 0x0) != UNSUPPORTED_CMD)) {
981 result = led_classdev_register(&fujitsu->pf_device->dev,
982 &eco_led);
983 if (result == 0) {
984 fujitsu_hotkey->eco_led_registered = 1;
985 } else {
986 pr_err("Could not register LED handler for eco LED, error %i\n",
987 result);
988 }
989 }
937#endif 990#endif
938 991
939 return result; 992 return result;
@@ -963,6 +1016,9 @@ static int acpi_fujitsu_hotkey_remove(struct acpi_device *device)
963 1016
964 if (fujitsu_hotkey->radio_led_registered) 1017 if (fujitsu_hotkey->radio_led_registered)
965 led_classdev_unregister(&radio_led); 1018 led_classdev_unregister(&radio_led);
1019
1020 if (fujitsu_hotkey->eco_led_registered)
1021 led_classdev_unregister(&eco_led);
966#endif 1022#endif
967 1023
968 input_unregister_device(input); 1024 input_unregister_device(input);