aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/platform/x86/thinkpad_acpi.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/platform/x86/thinkpad_acpi.c')
-rw-r--r--drivers/platform/x86/thinkpad_acpi.c735
1 files changed, 536 insertions, 199 deletions
diff --git a/drivers/platform/x86/thinkpad_acpi.c b/drivers/platform/x86/thinkpad_acpi.c
index d2433204a40..ba3682c5cde 100644
--- a/drivers/platform/x86/thinkpad_acpi.c
+++ b/drivers/platform/x86/thinkpad_acpi.c
@@ -3,7 +3,7 @@
3 * 3 *
4 * 4 *
5 * Copyright (C) 2004-2005 Borislav Deianov <borislav@users.sf.net> 5 * Copyright (C) 2004-2005 Borislav Deianov <borislav@users.sf.net>
6 * Copyright (C) 2006-2008 Henrique de Moraes Holschuh <hmh@hmh.eng.br> 6 * Copyright (C) 2006-2009 Henrique de Moraes Holschuh <hmh@hmh.eng.br>
7 * 7 *
8 * This program is free software; you can redistribute it and/or modify 8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by 9 * it under the terms of the GNU General Public License as published by
@@ -22,7 +22,7 @@
22 */ 22 */
23 23
24#define TPACPI_VERSION "0.22" 24#define TPACPI_VERSION "0.22"
25#define TPACPI_SYSFS_VERSION 0x020200 25#define TPACPI_SYSFS_VERSION 0x020300
26 26
27/* 27/*
28 * Changelog: 28 * Changelog:
@@ -54,6 +54,7 @@
54#include <linux/string.h> 54#include <linux/string.h>
55#include <linux/list.h> 55#include <linux/list.h>
56#include <linux/mutex.h> 56#include <linux/mutex.h>
57#include <linux/sched.h>
57#include <linux/kthread.h> 58#include <linux/kthread.h>
58#include <linux/freezer.h> 59#include <linux/freezer.h>
59#include <linux/delay.h> 60#include <linux/delay.h>
@@ -172,29 +173,26 @@ enum {
172 TPACPI_RFK_UWB_SW_ID, 173 TPACPI_RFK_UWB_SW_ID,
173}; 174};
174 175
175/* Debugging */ 176/* printk headers */
176#define TPACPI_LOG TPACPI_FILE ": " 177#define TPACPI_LOG TPACPI_FILE ": "
177#define TPACPI_ALERT KERN_ALERT TPACPI_LOG 178#define TPACPI_EMERG KERN_EMERG TPACPI_LOG
178#define TPACPI_CRIT KERN_CRIT TPACPI_LOG 179#define TPACPI_ALERT KERN_ALERT TPACPI_LOG
179#define TPACPI_ERR KERN_ERR TPACPI_LOG 180#define TPACPI_CRIT KERN_CRIT TPACPI_LOG
180#define TPACPI_NOTICE KERN_NOTICE TPACPI_LOG 181#define TPACPI_ERR KERN_ERR TPACPI_LOG
181#define TPACPI_INFO KERN_INFO TPACPI_LOG 182#define TPACPI_WARN KERN_WARNING TPACPI_LOG
182#define TPACPI_DEBUG KERN_DEBUG TPACPI_LOG 183#define TPACPI_NOTICE KERN_NOTICE TPACPI_LOG
183 184#define TPACPI_INFO KERN_INFO TPACPI_LOG
185#define TPACPI_DEBUG KERN_DEBUG TPACPI_LOG
186
187/* Debugging printk groups */
184#define TPACPI_DBG_ALL 0xffff 188#define TPACPI_DBG_ALL 0xffff
189#define TPACPI_DBG_DISCLOSETASK 0x8000
185#define TPACPI_DBG_INIT 0x0001 190#define TPACPI_DBG_INIT 0x0001
186#define TPACPI_DBG_EXIT 0x0002 191#define TPACPI_DBG_EXIT 0x0002
187#define dbg_printk(a_dbg_level, format, arg...) \ 192#define TPACPI_DBG_RFKILL 0x0004
188 do { if (dbg_level & a_dbg_level) \ 193#define TPACPI_DBG_HKEY 0x0008
189 printk(TPACPI_DEBUG "%s: " format, __func__ , ## arg); \ 194#define TPACPI_DBG_FAN 0x0010
190 } while (0) 195#define TPACPI_DBG_BRGHT 0x0020
191#ifdef CONFIG_THINKPAD_ACPI_DEBUG
192#define vdbg_printk(a_dbg_level, format, arg...) \
193 dbg_printk(a_dbg_level, format, ## arg)
194static const char *str_supported(int is_supported);
195#else
196#define vdbg_printk(a_dbg_level, format, arg...)
197#endif
198 196
199#define onoff(status, bit) ((status) & (1 << (bit)) ? "on" : "off") 197#define onoff(status, bit) ((status) & (1 << (bit)) ? "on" : "off")
200#define enabled(status, bit) ((status) & (1 << (bit)) ? "enabled" : "disabled") 198#define enabled(status, bit) ((status) & (1 << (bit)) ? "enabled" : "disabled")
@@ -277,7 +275,6 @@ static struct {
277 275
278static struct { 276static struct {
279 u16 hotkey_mask_ff:1; 277 u16 hotkey_mask_ff:1;
280 u16 bright_cmos_ec_unsync:1;
281} tp_warned; 278} tp_warned;
282 279
283struct thinkpad_id_data { 280struct thinkpad_id_data {
@@ -326,6 +323,39 @@ static int tpacpi_uwb_emulstate;
326#endif 323#endif
327 324
328 325
326/*************************************************************************
327 * Debugging helpers
328 */
329
330#define dbg_printk(a_dbg_level, format, arg...) \
331 do { if (dbg_level & (a_dbg_level)) \
332 printk(TPACPI_DEBUG "%s: " format, __func__ , ## arg); \
333 } while (0)
334
335#ifdef CONFIG_THINKPAD_ACPI_DEBUG
336#define vdbg_printk dbg_printk
337static const char *str_supported(int is_supported);
338#else
339#define vdbg_printk(a_dbg_level, format, arg...) \
340 do { } while (0)
341#endif
342
343static void tpacpi_log_usertask(const char * const what)
344{
345 printk(TPACPI_DEBUG "%s: access by process with PID %d\n",
346 what, task_tgid_vnr(current));
347}
348
349#define tpacpi_disclose_usertask(what, format, arg...) \
350 do { \
351 if (unlikely( \
352 (dbg_level & TPACPI_DBG_DISCLOSETASK) && \
353 (tpacpi_lifecycle == TPACPI_LIFE_RUNNING))) { \
354 printk(TPACPI_DEBUG "%s: PID %d: " format, \
355 what, task_tgid_vnr(current), ## arg); \
356 } \
357 } while (0)
358
329/**************************************************************************** 359/****************************************************************************
330 **************************************************************************** 360 ****************************************************************************
331 * 361 *
@@ -989,10 +1019,13 @@ static int __init tpacpi_new_rfkill(const unsigned int id,
989 /* try to set the initial state as the default for the rfkill 1019 /* try to set the initial state as the default for the rfkill
990 * type, since we ask the firmware to preserve it across S5 in 1020 * type, since we ask the firmware to preserve it across S5 in
991 * NVRAM */ 1021 * NVRAM */
992 rfkill_set_default(rfktype, 1022 if (rfkill_set_default(rfktype,
993 (initial_state == RFKILL_STATE_UNBLOCKED) ? 1023 (initial_state == RFKILL_STATE_UNBLOCKED) ?
994 RFKILL_STATE_UNBLOCKED : 1024 RFKILL_STATE_UNBLOCKED :
995 RFKILL_STATE_SOFT_BLOCKED); 1025 RFKILL_STATE_SOFT_BLOCKED) == -EPERM)
1026 vdbg_printk(TPACPI_DBG_RFKILL,
1027 "Default state for %s cannot be changed\n",
1028 name);
996 } 1029 }
997 1030
998 *rfk = rfkill_allocate(&tpacpi_pdev->dev, rfktype); 1031 *rfk = rfkill_allocate(&tpacpi_pdev->dev, rfktype);
@@ -1020,6 +1053,21 @@ static int __init tpacpi_new_rfkill(const unsigned int id,
1020 return 0; 1053 return 0;
1021} 1054}
1022 1055
1056static void printk_deprecated_attribute(const char * const what,
1057 const char * const details)
1058{
1059 tpacpi_log_usertask("deprecated sysfs attribute");
1060 printk(TPACPI_WARN "WARNING: sysfs attribute %s is deprecated and "
1061 "will be removed. %s\n",
1062 what, details);
1063}
1064
1065static void printk_deprecated_rfkill_attribute(const char * const what)
1066{
1067 printk_deprecated_attribute(what,
1068 "Please switch to generic rfkill before year 2010");
1069}
1070
1023/************************************************************************* 1071/*************************************************************************
1024 * thinkpad-acpi driver attributes 1072 * thinkpad-acpi driver attributes
1025 */ 1073 */
@@ -1382,7 +1430,6 @@ static enum { /* Reasons for waking up */
1382 1430
1383static int hotkey_autosleep_ack; 1431static int hotkey_autosleep_ack;
1384 1432
1385static int hotkey_orig_status;
1386static u32 hotkey_orig_mask; 1433static u32 hotkey_orig_mask;
1387static u32 hotkey_all_mask; 1434static u32 hotkey_all_mask;
1388static u32 hotkey_reserved_mask; 1435static u32 hotkey_reserved_mask;
@@ -1529,9 +1576,9 @@ static int hotkey_status_get(int *status)
1529 return 0; 1576 return 0;
1530} 1577}
1531 1578
1532static int hotkey_status_set(int status) 1579static int hotkey_status_set(bool enable)
1533{ 1580{
1534 if (!acpi_evalf(hkey_handle, NULL, "MHKC", "vd", status)) 1581 if (!acpi_evalf(hkey_handle, NULL, "MHKC", "vd", enable ? 1 : 0))
1535 return -EIO; 1582 return -EIO;
1536 1583
1537 return 0; 1584 return 0;
@@ -1847,6 +1894,9 @@ static ssize_t hotkey_enable_show(struct device *dev,
1847{ 1894{
1848 int res, status; 1895 int res, status;
1849 1896
1897 printk_deprecated_attribute("hotkey_enable",
1898 "Hotkey reporting is always enabled");
1899
1850 res = hotkey_status_get(&status); 1900 res = hotkey_status_get(&status);
1851 if (res) 1901 if (res)
1852 return res; 1902 return res;
@@ -1859,14 +1909,17 @@ static ssize_t hotkey_enable_store(struct device *dev,
1859 const char *buf, size_t count) 1909 const char *buf, size_t count)
1860{ 1910{
1861 unsigned long t; 1911 unsigned long t;
1862 int res; 1912
1913 printk_deprecated_attribute("hotkey_enable",
1914 "Hotkeys can be disabled through hotkey_mask");
1863 1915
1864 if (parse_strtoul(buf, 1, &t)) 1916 if (parse_strtoul(buf, 1, &t))
1865 return -EINVAL; 1917 return -EINVAL;
1866 1918
1867 res = hotkey_status_set(t); 1919 if (t == 0)
1920 return -EPERM;
1868 1921
1869 return (res) ? res : count; 1922 return count;
1870} 1923}
1871 1924
1872static struct device_attribute dev_attr_hotkey_enable = 1925static struct device_attribute dev_attr_hotkey_enable =
@@ -1910,6 +1963,8 @@ static ssize_t hotkey_mask_store(struct device *dev,
1910 1963
1911 mutex_unlock(&hotkey_mutex); 1964 mutex_unlock(&hotkey_mutex);
1912 1965
1966 tpacpi_disclose_usertask("hotkey_mask", "set to 0x%08lx\n", t);
1967
1913 return (res) ? res : count; 1968 return (res) ? res : count;
1914} 1969}
1915 1970
@@ -1922,7 +1977,7 @@ static ssize_t hotkey_bios_enabled_show(struct device *dev,
1922 struct device_attribute *attr, 1977 struct device_attribute *attr,
1923 char *buf) 1978 char *buf)
1924{ 1979{
1925 return snprintf(buf, PAGE_SIZE, "%d\n", hotkey_orig_status); 1980 return sprintf(buf, "0\n");
1926} 1981}
1927 1982
1928static struct device_attribute dev_attr_hotkey_bios_enabled = 1983static struct device_attribute dev_attr_hotkey_bios_enabled =
@@ -1996,6 +2051,8 @@ static ssize_t hotkey_source_mask_store(struct device *dev,
1996 2051
1997 mutex_unlock(&hotkey_mutex); 2052 mutex_unlock(&hotkey_mutex);
1998 2053
2054 tpacpi_disclose_usertask("hotkey_source_mask", "set to 0x%08lx\n", t);
2055
1999 return count; 2056 return count;
2000} 2057}
2001 2058
@@ -2028,6 +2085,8 @@ static ssize_t hotkey_poll_freq_store(struct device *dev,
2028 hotkey_poll_setup(1); 2085 hotkey_poll_setup(1);
2029 mutex_unlock(&hotkey_mutex); 2086 mutex_unlock(&hotkey_mutex);
2030 2087
2088 tpacpi_disclose_usertask("hotkey_poll_freq", "set to %lu\n", t);
2089
2031 return count; 2090 return count;
2032} 2091}
2033 2092
@@ -2197,11 +2256,11 @@ static void hotkey_exit(void)
2197 kfree(hotkey_keycode_map); 2256 kfree(hotkey_keycode_map);
2198 2257
2199 if (tp_features.hotkey) { 2258 if (tp_features.hotkey) {
2200 dbg_printk(TPACPI_DBG_EXIT, 2259 dbg_printk(TPACPI_DBG_EXIT | TPACPI_DBG_HKEY,
2201 "restoring original hot key mask\n"); 2260 "restoring original hot key mask\n");
2202 /* no short-circuit boolean operator below! */ 2261 /* no short-circuit boolean operator below! */
2203 if ((hotkey_mask_set(hotkey_orig_mask) | 2262 if ((hotkey_mask_set(hotkey_orig_mask) |
2204 hotkey_status_set(hotkey_orig_status)) != 0) 2263 hotkey_status_set(false)) != 0)
2205 printk(TPACPI_ERR 2264 printk(TPACPI_ERR
2206 "failed to restore hot key mask " 2265 "failed to restore hot key mask "
2207 "to BIOS defaults\n"); 2266 "to BIOS defaults\n");
@@ -2327,7 +2386,8 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2327 int status; 2386 int status;
2328 int hkeyv; 2387 int hkeyv;
2329 2388
2330 vdbg_printk(TPACPI_DBG_INIT, "initializing hotkey subdriver\n"); 2389 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2390 "initializing hotkey subdriver\n");
2331 2391
2332 BUG_ON(!tpacpi_inputdev); 2392 BUG_ON(!tpacpi_inputdev);
2333 BUG_ON(tpacpi_inputdev->open != NULL || 2393 BUG_ON(tpacpi_inputdev->open != NULL ||
@@ -2344,7 +2404,8 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2344 /* hotkey not supported on 570 */ 2404 /* hotkey not supported on 570 */
2345 tp_features.hotkey = hkey_handle != NULL; 2405 tp_features.hotkey = hkey_handle != NULL;
2346 2406
2347 vdbg_printk(TPACPI_DBG_INIT, "hotkeys are %s\n", 2407 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2408 "hotkeys are %s\n",
2348 str_supported(tp_features.hotkey)); 2409 str_supported(tp_features.hotkey));
2349 2410
2350 if (!tp_features.hotkey) 2411 if (!tp_features.hotkey)
@@ -2376,10 +2437,14 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2376 * T4x, X31, and later 2437 * T4x, X31, and later
2377 */ 2438 */
2378 tp_features.hotkey_mask = 1; 2439 tp_features.hotkey_mask = 1;
2440 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2441 "firmware HKEY interface version: 0x%x\n",
2442 hkeyv);
2379 } 2443 }
2380 } 2444 }
2381 2445
2382 vdbg_printk(TPACPI_DBG_INIT, "hotkey masks are %s\n", 2446 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2447 "hotkey masks are %s\n",
2383 str_supported(tp_features.hotkey_mask)); 2448 str_supported(tp_features.hotkey_mask));
2384 2449
2385 if (tp_features.hotkey_mask) { 2450 if (tp_features.hotkey_mask) {
@@ -2396,10 +2461,6 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2396 2461
2397 /* hotkey_source_mask *must* be zero for 2462 /* hotkey_source_mask *must* be zero for
2398 * the first hotkey_mask_get */ 2463 * the first hotkey_mask_get */
2399 res = hotkey_status_get(&hotkey_orig_status);
2400 if (res)
2401 goto err_exit;
2402
2403 if (tp_features.hotkey_mask) { 2464 if (tp_features.hotkey_mask) {
2404 res = hotkey_mask_get(); 2465 res = hotkey_mask_get();
2405 if (res) 2466 if (res)
@@ -2422,7 +2483,7 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2422 hotkey_source_mask = TPACPI_HKEY_NVRAM_GOOD_MASK; 2483 hotkey_source_mask = TPACPI_HKEY_NVRAM_GOOD_MASK;
2423 } 2484 }
2424 2485
2425 vdbg_printk(TPACPI_DBG_INIT, 2486 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2426 "hotkey source mask 0x%08x, polling freq %d\n", 2487 "hotkey source mask 0x%08x, polling freq %d\n",
2427 hotkey_source_mask, hotkey_poll_freq); 2488 hotkey_source_mask, hotkey_poll_freq);
2428#endif 2489#endif
@@ -2476,12 +2537,12 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2476 } 2537 }
2477 2538
2478 if (thinkpad_id.vendor == PCI_VENDOR_ID_LENOVO) { 2539 if (thinkpad_id.vendor == PCI_VENDOR_ID_LENOVO) {
2479 dbg_printk(TPACPI_DBG_INIT, 2540 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2480 "using Lenovo default hot key map\n"); 2541 "using Lenovo default hot key map\n");
2481 memcpy(hotkey_keycode_map, &lenovo_keycode_map, 2542 memcpy(hotkey_keycode_map, &lenovo_keycode_map,
2482 TPACPI_HOTKEY_MAP_SIZE); 2543 TPACPI_HOTKEY_MAP_SIZE);
2483 } else { 2544 } else {
2484 dbg_printk(TPACPI_DBG_INIT, 2545 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2485 "using IBM default hot key map\n"); 2546 "using IBM default hot key map\n");
2486 memcpy(hotkey_keycode_map, &ibm_keycode_map, 2547 memcpy(hotkey_keycode_map, &ibm_keycode_map,
2487 TPACPI_HOTKEY_MAP_SIZE); 2548 TPACPI_HOTKEY_MAP_SIZE);
@@ -2538,8 +2599,9 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2538 | (1 << TP_ACPI_HOTKEYSCAN_FNEND); 2599 | (1 << TP_ACPI_HOTKEYSCAN_FNEND);
2539 } 2600 }
2540 2601
2541 dbg_printk(TPACPI_DBG_INIT, "enabling hot key handling\n"); 2602 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2542 res = hotkey_status_set(1); 2603 "enabling firmware HKEY event interface...\n");
2604 res = hotkey_status_set(true);
2543 if (res) { 2605 if (res) {
2544 hotkey_exit(); 2606 hotkey_exit();
2545 return res; 2607 return res;
@@ -2552,8 +2614,8 @@ static int __init hotkey_init(struct ibm_init_struct *iibm)
2552 return res; 2614 return res;
2553 } 2615 }
2554 2616
2555 dbg_printk(TPACPI_DBG_INIT, 2617 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_HKEY,
2556 "legacy hot key reporting over procfs %s\n", 2618 "legacy ibm/hotkey event reporting over procfs %s\n",
2557 (hotkey_report_mode < 2) ? 2619 (hotkey_report_mode < 2) ?
2558 "enabled" : "disabled"); 2620 "enabled" : "disabled");
2559 2621
@@ -2884,9 +2946,17 @@ static int hotkey_read(char *p)
2884 return len; 2946 return len;
2885} 2947}
2886 2948
2949static void hotkey_enabledisable_warn(void)
2950{
2951 tpacpi_log_usertask("procfs hotkey enable/disable");
2952 WARN(1, TPACPI_WARN
2953 "hotkey enable/disable functionality has been "
2954 "removed from the driver. Hotkeys are always enabled.\n");
2955}
2956
2887static int hotkey_write(char *buf) 2957static int hotkey_write(char *buf)
2888{ 2958{
2889 int res, status; 2959 int res;
2890 u32 mask; 2960 u32 mask;
2891 char *cmd; 2961 char *cmd;
2892 2962
@@ -2896,17 +2966,16 @@ static int hotkey_write(char *buf)
2896 if (mutex_lock_killable(&hotkey_mutex)) 2966 if (mutex_lock_killable(&hotkey_mutex))
2897 return -ERESTARTSYS; 2967 return -ERESTARTSYS;
2898 2968
2899 status = -1;
2900 mask = hotkey_mask; 2969 mask = hotkey_mask;
2901 2970
2902 res = 0; 2971 res = 0;
2903 while ((cmd = next_cmd(&buf))) { 2972 while ((cmd = next_cmd(&buf))) {
2904 if (strlencmp(cmd, "enable") == 0) { 2973 if (strlencmp(cmd, "enable") == 0) {
2905 status = 1; 2974 hotkey_enabledisable_warn();
2906 } else if (strlencmp(cmd, "disable") == 0) { 2975 } else if (strlencmp(cmd, "disable") == 0) {
2907 status = 0; 2976 hotkey_enabledisable_warn();
2977 res = -EPERM;
2908 } else if (strlencmp(cmd, "reset") == 0) { 2978 } else if (strlencmp(cmd, "reset") == 0) {
2909 status = hotkey_orig_status;
2910 mask = hotkey_orig_mask; 2979 mask = hotkey_orig_mask;
2911 } else if (sscanf(cmd, "0x%x", &mask) == 1) { 2980 } else if (sscanf(cmd, "0x%x", &mask) == 1) {
2912 /* mask set */ 2981 /* mask set */
@@ -2917,8 +2986,10 @@ static int hotkey_write(char *buf)
2917 goto errexit; 2986 goto errexit;
2918 } 2987 }
2919 } 2988 }
2920 if (status != -1) 2989
2921 res = hotkey_status_set(status); 2990 if (!res)
2991 tpacpi_disclose_usertask("procfs hotkey",
2992 "set mask to 0x%08x\n", mask);
2922 2993
2923 if (!res && mask != hotkey_mask) 2994 if (!res && mask != hotkey_mask)
2924 res = hotkey_mask_set(mask); 2995 res = hotkey_mask_set(mask);
@@ -2971,13 +3042,17 @@ enum {
2971 TP_ACPI_BLTH_SAVE_STATE = 0x05, /* Save state for S4/S5 */ 3042 TP_ACPI_BLTH_SAVE_STATE = 0x05, /* Save state for S4/S5 */
2972}; 3043};
2973 3044
3045#define TPACPI_RFK_BLUETOOTH_SW_NAME "tpacpi_bluetooth_sw"
3046
2974static struct rfkill *tpacpi_bluetooth_rfkill; 3047static struct rfkill *tpacpi_bluetooth_rfkill;
2975 3048
2976static void bluetooth_suspend(pm_message_t state) 3049static void bluetooth_suspend(pm_message_t state)
2977{ 3050{
2978 /* Try to make sure radio will resume powered off */ 3051 /* Try to make sure radio will resume powered off */
2979 acpi_evalf(NULL, NULL, "\\BLTH", "vd", 3052 if (!acpi_evalf(NULL, NULL, "\\BLTH", "vd",
2980 TP_ACPI_BLTH_PWR_OFF_ON_RESUME); 3053 TP_ACPI_BLTH_PWR_OFF_ON_RESUME))
3054 vdbg_printk(TPACPI_DBG_RFKILL,
3055 "bluetooth power down on resume request failed\n");
2981} 3056}
2982 3057
2983static int bluetooth_get_radiosw(void) 3058static int bluetooth_get_radiosw(void)
@@ -3015,6 +3090,10 @@ static void bluetooth_update_rfk(void)
3015 if (status < 0) 3090 if (status < 0)
3016 return; 3091 return;
3017 rfkill_force_state(tpacpi_bluetooth_rfkill, status); 3092 rfkill_force_state(tpacpi_bluetooth_rfkill, status);
3093
3094 vdbg_printk(TPACPI_DBG_RFKILL,
3095 "forced rfkill state to %d\n",
3096 status);
3018} 3097}
3019 3098
3020static int bluetooth_set_radiosw(int radio_on, int update_rfk) 3099static int bluetooth_set_radiosw(int radio_on, int update_rfk)
@@ -3030,6 +3109,9 @@ static int bluetooth_set_radiosw(int radio_on, int update_rfk)
3030 && radio_on) 3109 && radio_on)
3031 return -EPERM; 3110 return -EPERM;
3032 3111
3112 vdbg_printk(TPACPI_DBG_RFKILL,
3113 "will %s bluetooth\n", radio_on ? "enable" : "disable");
3114
3033#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES 3115#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES
3034 if (dbg_bluetoothemul) { 3116 if (dbg_bluetoothemul) {
3035 tpacpi_bluetooth_emulstate = !!radio_on; 3117 tpacpi_bluetooth_emulstate = !!radio_on;
@@ -3060,6 +3142,8 @@ static ssize_t bluetooth_enable_show(struct device *dev,
3060{ 3142{
3061 int status; 3143 int status;
3062 3144
3145 printk_deprecated_rfkill_attribute("bluetooth_enable");
3146
3063 status = bluetooth_get_radiosw(); 3147 status = bluetooth_get_radiosw();
3064 if (status < 0) 3148 if (status < 0)
3065 return status; 3149 return status;
@@ -3075,9 +3159,13 @@ static ssize_t bluetooth_enable_store(struct device *dev,
3075 unsigned long t; 3159 unsigned long t;
3076 int res; 3160 int res;
3077 3161
3162 printk_deprecated_rfkill_attribute("bluetooth_enable");
3163
3078 if (parse_strtoul(buf, 1, &t)) 3164 if (parse_strtoul(buf, 1, &t))
3079 return -EINVAL; 3165 return -EINVAL;
3080 3166
3167 tpacpi_disclose_usertask("bluetooth_enable", "set to %ld\n", t);
3168
3081 res = bluetooth_set_radiosw(t, 1); 3169 res = bluetooth_set_radiosw(t, 1);
3082 3170
3083 return (res) ? res : count; 3171 return (res) ? res : count;
@@ -3111,6 +3199,8 @@ static int tpacpi_bluetooth_rfk_get(void *data, enum rfkill_state *state)
3111 3199
3112static int tpacpi_bluetooth_rfk_set(void *data, enum rfkill_state state) 3200static int tpacpi_bluetooth_rfk_set(void *data, enum rfkill_state state)
3113{ 3201{
3202 dbg_printk(TPACPI_DBG_RFKILL,
3203 "request to change radio state to %d\n", state);
3114 return bluetooth_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0); 3204 return bluetooth_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0);
3115} 3205}
3116 3206
@@ -3121,6 +3211,9 @@ static void bluetooth_shutdown(void)
3121 TP_ACPI_BLTH_SAVE_STATE)) 3211 TP_ACPI_BLTH_SAVE_STATE))
3122 printk(TPACPI_NOTICE 3212 printk(TPACPI_NOTICE
3123 "failed to save bluetooth state to NVRAM\n"); 3213 "failed to save bluetooth state to NVRAM\n");
3214 else
3215 vdbg_printk(TPACPI_DBG_RFKILL,
3216 "bluestooth state saved to NVRAM\n");
3124} 3217}
3125 3218
3126static void bluetooth_exit(void) 3219static void bluetooth_exit(void)
@@ -3139,7 +3232,8 @@ static int __init bluetooth_init(struct ibm_init_struct *iibm)
3139 int res; 3232 int res;
3140 int status = 0; 3233 int status = 0;
3141 3234
3142 vdbg_printk(TPACPI_DBG_INIT, "initializing bluetooth subdriver\n"); 3235 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3236 "initializing bluetooth subdriver\n");
3143 3237
3144 TPACPI_ACPIHANDLE_INIT(hkey); 3238 TPACPI_ACPIHANDLE_INIT(hkey);
3145 3239
@@ -3148,7 +3242,8 @@ static int __init bluetooth_init(struct ibm_init_struct *iibm)
3148 tp_features.bluetooth = hkey_handle && 3242 tp_features.bluetooth = hkey_handle &&
3149 acpi_evalf(hkey_handle, &status, "GBDC", "qd"); 3243 acpi_evalf(hkey_handle, &status, "GBDC", "qd");
3150 3244
3151 vdbg_printk(TPACPI_DBG_INIT, "bluetooth is %s, status 0x%02x\n", 3245 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3246 "bluetooth is %s, status 0x%02x\n",
3152 str_supported(tp_features.bluetooth), 3247 str_supported(tp_features.bluetooth),
3153 status); 3248 status);
3154 3249
@@ -3163,7 +3258,7 @@ static int __init bluetooth_init(struct ibm_init_struct *iibm)
3163 !(status & TP_ACPI_BLUETOOTH_HWPRESENT)) { 3258 !(status & TP_ACPI_BLUETOOTH_HWPRESENT)) {
3164 /* no bluetooth hardware present in system */ 3259 /* no bluetooth hardware present in system */
3165 tp_features.bluetooth = 0; 3260 tp_features.bluetooth = 0;
3166 dbg_printk(TPACPI_DBG_INIT, 3261 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3167 "bluetooth hardware not installed\n"); 3262 "bluetooth hardware not installed\n");
3168 } 3263 }
3169 3264
@@ -3178,7 +3273,7 @@ static int __init bluetooth_init(struct ibm_init_struct *iibm)
3178 res = tpacpi_new_rfkill(TPACPI_RFK_BLUETOOTH_SW_ID, 3273 res = tpacpi_new_rfkill(TPACPI_RFK_BLUETOOTH_SW_ID,
3179 &tpacpi_bluetooth_rfkill, 3274 &tpacpi_bluetooth_rfkill,
3180 RFKILL_TYPE_BLUETOOTH, 3275 RFKILL_TYPE_BLUETOOTH,
3181 "tpacpi_bluetooth_sw", 3276 TPACPI_RFK_BLUETOOTH_SW_NAME,
3182 true, 3277 true,
3183 tpacpi_bluetooth_rfk_set, 3278 tpacpi_bluetooth_rfk_set,
3184 tpacpi_bluetooth_rfk_get); 3279 tpacpi_bluetooth_rfk_get);
@@ -3211,19 +3306,27 @@ static int bluetooth_read(char *p)
3211static int bluetooth_write(char *buf) 3306static int bluetooth_write(char *buf)
3212{ 3307{
3213 char *cmd; 3308 char *cmd;
3309 int state = -1;
3214 3310
3215 if (!tp_features.bluetooth) 3311 if (!tp_features.bluetooth)
3216 return -ENODEV; 3312 return -ENODEV;
3217 3313
3218 while ((cmd = next_cmd(&buf))) { 3314 while ((cmd = next_cmd(&buf))) {
3219 if (strlencmp(cmd, "enable") == 0) { 3315 if (strlencmp(cmd, "enable") == 0) {
3220 bluetooth_set_radiosw(1, 1); 3316 state = 1;
3221 } else if (strlencmp(cmd, "disable") == 0) { 3317 } else if (strlencmp(cmd, "disable") == 0) {
3222 bluetooth_set_radiosw(0, 1); 3318 state = 0;
3223 } else 3319 } else
3224 return -EINVAL; 3320 return -EINVAL;
3225 } 3321 }
3226 3322
3323 if (state != -1) {
3324 tpacpi_disclose_usertask("procfs bluetooth",
3325 "attempt to %s\n",
3326 state ? "enable" : "disable");
3327 bluetooth_set_radiosw(state, 1);
3328 }
3329
3227 return 0; 3330 return 0;
3228} 3331}
3229 3332
@@ -3248,13 +3351,17 @@ enum {
3248 off / last state */ 3351 off / last state */
3249}; 3352};
3250 3353
3354#define TPACPI_RFK_WWAN_SW_NAME "tpacpi_wwan_sw"
3355
3251static struct rfkill *tpacpi_wan_rfkill; 3356static struct rfkill *tpacpi_wan_rfkill;
3252 3357
3253static void wan_suspend(pm_message_t state) 3358static void wan_suspend(pm_message_t state)
3254{ 3359{
3255 /* Try to make sure radio will resume powered off */ 3360 /* Try to make sure radio will resume powered off */
3256 acpi_evalf(NULL, NULL, "\\WGSV", "qvd", 3361 if (!acpi_evalf(NULL, NULL, "\\WGSV", "qvd",
3257 TP_ACPI_WGSV_PWR_OFF_ON_RESUME); 3362 TP_ACPI_WGSV_PWR_OFF_ON_RESUME))
3363 vdbg_printk(TPACPI_DBG_RFKILL,
3364 "WWAN power down on resume request failed\n");
3258} 3365}
3259 3366
3260static int wan_get_radiosw(void) 3367static int wan_get_radiosw(void)
@@ -3292,6 +3399,10 @@ static void wan_update_rfk(void)
3292 if (status < 0) 3399 if (status < 0)
3293 return; 3400 return;
3294 rfkill_force_state(tpacpi_wan_rfkill, status); 3401 rfkill_force_state(tpacpi_wan_rfkill, status);
3402
3403 vdbg_printk(TPACPI_DBG_RFKILL,
3404 "forced rfkill state to %d\n",
3405 status);
3295} 3406}
3296 3407
3297static int wan_set_radiosw(int radio_on, int update_rfk) 3408static int wan_set_radiosw(int radio_on, int update_rfk)
@@ -3307,6 +3418,9 @@ static int wan_set_radiosw(int radio_on, int update_rfk)
3307 && radio_on) 3418 && radio_on)
3308 return -EPERM; 3419 return -EPERM;
3309 3420
3421 vdbg_printk(TPACPI_DBG_RFKILL,
3422 "will %s WWAN\n", radio_on ? "enable" : "disable");
3423
3310#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES 3424#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES
3311 if (dbg_wwanemul) { 3425 if (dbg_wwanemul) {
3312 tpacpi_wwan_emulstate = !!radio_on; 3426 tpacpi_wwan_emulstate = !!radio_on;
@@ -3337,6 +3451,8 @@ static ssize_t wan_enable_show(struct device *dev,
3337{ 3451{
3338 int status; 3452 int status;
3339 3453
3454 printk_deprecated_rfkill_attribute("wwan_enable");
3455
3340 status = wan_get_radiosw(); 3456 status = wan_get_radiosw();
3341 if (status < 0) 3457 if (status < 0)
3342 return status; 3458 return status;
@@ -3352,9 +3468,13 @@ static ssize_t wan_enable_store(struct device *dev,
3352 unsigned long t; 3468 unsigned long t;
3353 int res; 3469 int res;
3354 3470
3471 printk_deprecated_rfkill_attribute("wwan_enable");
3472
3355 if (parse_strtoul(buf, 1, &t)) 3473 if (parse_strtoul(buf, 1, &t))
3356 return -EINVAL; 3474 return -EINVAL;
3357 3475
3476 tpacpi_disclose_usertask("wwan_enable", "set to %ld\n", t);
3477
3358 res = wan_set_radiosw(t, 1); 3478 res = wan_set_radiosw(t, 1);
3359 3479
3360 return (res) ? res : count; 3480 return (res) ? res : count;
@@ -3388,6 +3508,8 @@ static int tpacpi_wan_rfk_get(void *data, enum rfkill_state *state)
3388 3508
3389static int tpacpi_wan_rfk_set(void *data, enum rfkill_state state) 3509static int tpacpi_wan_rfk_set(void *data, enum rfkill_state state)
3390{ 3510{
3511 dbg_printk(TPACPI_DBG_RFKILL,
3512 "request to change radio state to %d\n", state);
3391 return wan_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0); 3513 return wan_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0);
3392} 3514}
3393 3515
@@ -3398,6 +3520,9 @@ static void wan_shutdown(void)
3398 TP_ACPI_WGSV_SAVE_STATE)) 3520 TP_ACPI_WGSV_SAVE_STATE))
3399 printk(TPACPI_NOTICE 3521 printk(TPACPI_NOTICE
3400 "failed to save WWAN state to NVRAM\n"); 3522 "failed to save WWAN state to NVRAM\n");
3523 else
3524 vdbg_printk(TPACPI_DBG_RFKILL,
3525 "WWAN state saved to NVRAM\n");
3401} 3526}
3402 3527
3403static void wan_exit(void) 3528static void wan_exit(void)
@@ -3416,14 +3541,16 @@ static int __init wan_init(struct ibm_init_struct *iibm)
3416 int res; 3541 int res;
3417 int status = 0; 3542 int status = 0;
3418 3543
3419 vdbg_printk(TPACPI_DBG_INIT, "initializing wan subdriver\n"); 3544 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3545 "initializing wan subdriver\n");
3420 3546
3421 TPACPI_ACPIHANDLE_INIT(hkey); 3547 TPACPI_ACPIHANDLE_INIT(hkey);
3422 3548
3423 tp_features.wan = hkey_handle && 3549 tp_features.wan = hkey_handle &&
3424 acpi_evalf(hkey_handle, &status, "GWAN", "qd"); 3550 acpi_evalf(hkey_handle, &status, "GWAN", "qd");
3425 3551
3426 vdbg_printk(TPACPI_DBG_INIT, "wan is %s, status 0x%02x\n", 3552 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3553 "wan is %s, status 0x%02x\n",
3427 str_supported(tp_features.wan), 3554 str_supported(tp_features.wan),
3428 status); 3555 status);
3429 3556
@@ -3438,7 +3565,7 @@ static int __init wan_init(struct ibm_init_struct *iibm)
3438 !(status & TP_ACPI_WANCARD_HWPRESENT)) { 3565 !(status & TP_ACPI_WANCARD_HWPRESENT)) {
3439 /* no wan hardware present in system */ 3566 /* no wan hardware present in system */
3440 tp_features.wan = 0; 3567 tp_features.wan = 0;
3441 dbg_printk(TPACPI_DBG_INIT, 3568 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3442 "wan hardware not installed\n"); 3569 "wan hardware not installed\n");
3443 } 3570 }
3444 3571
@@ -3453,7 +3580,7 @@ static int __init wan_init(struct ibm_init_struct *iibm)
3453 res = tpacpi_new_rfkill(TPACPI_RFK_WWAN_SW_ID, 3580 res = tpacpi_new_rfkill(TPACPI_RFK_WWAN_SW_ID,
3454 &tpacpi_wan_rfkill, 3581 &tpacpi_wan_rfkill,
3455 RFKILL_TYPE_WWAN, 3582 RFKILL_TYPE_WWAN,
3456 "tpacpi_wwan_sw", 3583 TPACPI_RFK_WWAN_SW_NAME,
3457 true, 3584 true,
3458 tpacpi_wan_rfk_set, 3585 tpacpi_wan_rfk_set,
3459 tpacpi_wan_rfk_get); 3586 tpacpi_wan_rfk_get);
@@ -3471,6 +3598,8 @@ static int wan_read(char *p)
3471 int len = 0; 3598 int len = 0;
3472 int status = wan_get_radiosw(); 3599 int status = wan_get_radiosw();
3473 3600
3601 tpacpi_disclose_usertask("procfs wan", "read");
3602
3474 if (!tp_features.wan) 3603 if (!tp_features.wan)
3475 len += sprintf(p + len, "status:\t\tnot supported\n"); 3604 len += sprintf(p + len, "status:\t\tnot supported\n");
3476 else { 3605 else {
@@ -3486,19 +3615,27 @@ static int wan_read(char *p)
3486static int wan_write(char *buf) 3615static int wan_write(char *buf)
3487{ 3616{
3488 char *cmd; 3617 char *cmd;
3618 int state = -1;
3489 3619
3490 if (!tp_features.wan) 3620 if (!tp_features.wan)
3491 return -ENODEV; 3621 return -ENODEV;
3492 3622
3493 while ((cmd = next_cmd(&buf))) { 3623 while ((cmd = next_cmd(&buf))) {
3494 if (strlencmp(cmd, "enable") == 0) { 3624 if (strlencmp(cmd, "enable") == 0) {
3495 wan_set_radiosw(1, 1); 3625 state = 1;
3496 } else if (strlencmp(cmd, "disable") == 0) { 3626 } else if (strlencmp(cmd, "disable") == 0) {
3497 wan_set_radiosw(0, 1); 3627 state = 0;
3498 } else 3628 } else
3499 return -EINVAL; 3629 return -EINVAL;
3500 } 3630 }
3501 3631
3632 if (state != -1) {
3633 tpacpi_disclose_usertask("procfs wan",
3634 "attempt to %s\n",
3635 state ? "enable" : "disable");
3636 wan_set_radiosw(state, 1);
3637 }
3638
3502 return 0; 3639 return 0;
3503} 3640}
3504 3641
@@ -3521,6 +3658,8 @@ enum {
3521 TP_ACPI_UWB_RADIOSSW = 0x02, /* UWB radio enabled */ 3658 TP_ACPI_UWB_RADIOSSW = 0x02, /* UWB radio enabled */
3522}; 3659};
3523 3660
3661#define TPACPI_RFK_UWB_SW_NAME "tpacpi_uwb_sw"
3662
3524static struct rfkill *tpacpi_uwb_rfkill; 3663static struct rfkill *tpacpi_uwb_rfkill;
3525 3664
3526static int uwb_get_radiosw(void) 3665static int uwb_get_radiosw(void)
@@ -3558,6 +3697,10 @@ static void uwb_update_rfk(void)
3558 if (status < 0) 3697 if (status < 0)
3559 return; 3698 return;
3560 rfkill_force_state(tpacpi_uwb_rfkill, status); 3699 rfkill_force_state(tpacpi_uwb_rfkill, status);
3700
3701 vdbg_printk(TPACPI_DBG_RFKILL,
3702 "forced rfkill state to %d\n",
3703 status);
3561} 3704}
3562 3705
3563static int uwb_set_radiosw(int radio_on, int update_rfk) 3706static int uwb_set_radiosw(int radio_on, int update_rfk)
@@ -3573,6 +3716,9 @@ static int uwb_set_radiosw(int radio_on, int update_rfk)
3573 && radio_on) 3716 && radio_on)
3574 return -EPERM; 3717 return -EPERM;
3575 3718
3719 vdbg_printk(TPACPI_DBG_RFKILL,
3720 "will %s UWB\n", radio_on ? "enable" : "disable");
3721
3576#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES 3722#ifdef CONFIG_THINKPAD_ACPI_DEBUGFACILITIES
3577 if (dbg_uwbemul) { 3723 if (dbg_uwbemul) {
3578 tpacpi_uwb_emulstate = !!radio_on; 3724 tpacpi_uwb_emulstate = !!radio_on;
@@ -3607,6 +3753,8 @@ static int tpacpi_uwb_rfk_get(void *data, enum rfkill_state *state)
3607 3753
3608static int tpacpi_uwb_rfk_set(void *data, enum rfkill_state state) 3754static int tpacpi_uwb_rfk_set(void *data, enum rfkill_state state)
3609{ 3755{
3756 dbg_printk(TPACPI_DBG_RFKILL,
3757 "request to change radio state to %d\n", state);
3610 return uwb_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0); 3758 return uwb_set_radiosw((state == RFKILL_STATE_UNBLOCKED), 0);
3611} 3759}
3612 3760
@@ -3621,14 +3769,16 @@ static int __init uwb_init(struct ibm_init_struct *iibm)
3621 int res; 3769 int res;
3622 int status = 0; 3770 int status = 0;
3623 3771
3624 vdbg_printk(TPACPI_DBG_INIT, "initializing uwb subdriver\n"); 3772 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3773 "initializing uwb subdriver\n");
3625 3774
3626 TPACPI_ACPIHANDLE_INIT(hkey); 3775 TPACPI_ACPIHANDLE_INIT(hkey);
3627 3776
3628 tp_features.uwb = hkey_handle && 3777 tp_features.uwb = hkey_handle &&
3629 acpi_evalf(hkey_handle, &status, "GUWB", "qd"); 3778 acpi_evalf(hkey_handle, &status, "GUWB", "qd");
3630 3779
3631 vdbg_printk(TPACPI_DBG_INIT, "uwb is %s, status 0x%02x\n", 3780 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_RFKILL,
3781 "uwb is %s, status 0x%02x\n",
3632 str_supported(tp_features.uwb), 3782 str_supported(tp_features.uwb),
3633 status); 3783 status);
3634 3784
@@ -3653,7 +3803,7 @@ static int __init uwb_init(struct ibm_init_struct *iibm)
3653 res = tpacpi_new_rfkill(TPACPI_RFK_UWB_SW_ID, 3803 res = tpacpi_new_rfkill(TPACPI_RFK_UWB_SW_ID,
3654 &tpacpi_uwb_rfkill, 3804 &tpacpi_uwb_rfkill,
3655 RFKILL_TYPE_UWB, 3805 RFKILL_TYPE_UWB,
3656 "tpacpi_uwb_sw", 3806 TPACPI_RFK_UWB_SW_NAME,
3657 false, 3807 false,
3658 tpacpi_uwb_rfk_set, 3808 tpacpi_uwb_rfk_set,
3659 tpacpi_uwb_rfk_get); 3809 tpacpi_uwb_rfk_get);
@@ -4602,6 +4752,16 @@ static const char * const tpacpi_led_names[TPACPI_LED_NUMLEDS] = {
4602 "tpacpi::unknown_led", 4752 "tpacpi::unknown_led",
4603 "tpacpi::standby", 4753 "tpacpi::standby",
4604}; 4754};
4755#define TPACPI_SAFE_LEDS 0x0081U
4756
4757static inline bool tpacpi_is_led_restricted(const unsigned int led)
4758{
4759#ifdef CONFIG_THINKPAD_ACPI_UNSAFE_LEDS
4760 return false;
4761#else
4762 return (TPACPI_SAFE_LEDS & (1 << led)) == 0;
4763#endif
4764}
4605 4765
4606static int led_get_status(const unsigned int led) 4766static int led_get_status(const unsigned int led)
4607{ 4767{
@@ -4639,16 +4799,20 @@ static int led_set_status(const unsigned int led,
4639 switch (led_supported) { 4799 switch (led_supported) {
4640 case TPACPI_LED_570: 4800 case TPACPI_LED_570:
4641 /* 570 */ 4801 /* 570 */
4642 if (led > 7) 4802 if (unlikely(led > 7))
4643 return -EINVAL; 4803 return -EINVAL;
4804 if (unlikely(tpacpi_is_led_restricted(led)))
4805 return -EPERM;
4644 if (!acpi_evalf(led_handle, NULL, NULL, "vdd", 4806 if (!acpi_evalf(led_handle, NULL, NULL, "vdd",
4645 (1 << led), led_sled_arg1[ledstatus])) 4807 (1 << led), led_sled_arg1[ledstatus]))
4646 rc = -EIO; 4808 rc = -EIO;
4647 break; 4809 break;
4648 case TPACPI_LED_OLD: 4810 case TPACPI_LED_OLD:
4649 /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20 */ 4811 /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20 */
4650 if (led > 7) 4812 if (unlikely(led > 7))
4651 return -EINVAL; 4813 return -EINVAL;
4814 if (unlikely(tpacpi_is_led_restricted(led)))
4815 return -EPERM;
4652 rc = ec_write(TPACPI_LED_EC_HLMS, (1 << led)); 4816 rc = ec_write(TPACPI_LED_EC_HLMS, (1 << led));
4653 if (rc >= 0) 4817 if (rc >= 0)
4654 rc = ec_write(TPACPI_LED_EC_HLBL, 4818 rc = ec_write(TPACPI_LED_EC_HLBL,
@@ -4659,6 +4823,10 @@ static int led_set_status(const unsigned int led,
4659 break; 4823 break;
4660 case TPACPI_LED_NEW: 4824 case TPACPI_LED_NEW:
4661 /* all others */ 4825 /* all others */
4826 if (unlikely(led >= TPACPI_LED_NUMLEDS))
4827 return -EINVAL;
4828 if (unlikely(tpacpi_is_led_restricted(led)))
4829 return -EPERM;
4662 if (!acpi_evalf(led_handle, NULL, NULL, "vdd", 4830 if (!acpi_evalf(led_handle, NULL, NULL, "vdd",
4663 led, led_led_arg1[ledstatus])) 4831 led, led_led_arg1[ledstatus]))
4664 rc = -EIO; 4832 rc = -EIO;
@@ -4751,6 +4919,30 @@ static void led_exit(void)
4751 kfree(tpacpi_leds); 4919 kfree(tpacpi_leds);
4752} 4920}
4753 4921
4922static int __init tpacpi_init_led(unsigned int led)
4923{
4924 int rc;
4925
4926 tpacpi_leds[led].led = led;
4927
4928 tpacpi_leds[led].led_classdev.brightness_set = &led_sysfs_set;
4929 tpacpi_leds[led].led_classdev.blink_set = &led_sysfs_blink_set;
4930 if (led_supported == TPACPI_LED_570)
4931 tpacpi_leds[led].led_classdev.brightness_get =
4932 &led_sysfs_get;
4933
4934 tpacpi_leds[led].led_classdev.name = tpacpi_led_names[led];
4935
4936 INIT_WORK(&tpacpi_leds[led].work, led_set_status_worker);
4937
4938 rc = led_classdev_register(&tpacpi_pdev->dev,
4939 &tpacpi_leds[led].led_classdev);
4940 if (rc < 0)
4941 tpacpi_leds[led].led_classdev.name = NULL;
4942
4943 return rc;
4944}
4945
4754static int __init led_init(struct ibm_init_struct *iibm) 4946static int __init led_init(struct ibm_init_struct *iibm)
4755{ 4947{
4756 unsigned int i; 4948 unsigned int i;
@@ -4784,27 +4976,21 @@ static int __init led_init(struct ibm_init_struct *iibm)
4784 } 4976 }
4785 4977
4786 for (i = 0; i < TPACPI_LED_NUMLEDS; i++) { 4978 for (i = 0; i < TPACPI_LED_NUMLEDS; i++) {
4787 tpacpi_leds[i].led = i; 4979 if (!tpacpi_is_led_restricted(i)) {
4788 4980 rc = tpacpi_init_led(i);
4789 tpacpi_leds[i].led_classdev.brightness_set = &led_sysfs_set; 4981 if (rc < 0) {
4790 tpacpi_leds[i].led_classdev.blink_set = &led_sysfs_blink_set; 4982 led_exit();
4791 if (led_supported == TPACPI_LED_570) 4983 return rc;
4792 tpacpi_leds[i].led_classdev.brightness_get = 4984 }
4793 &led_sysfs_get;
4794
4795 tpacpi_leds[i].led_classdev.name = tpacpi_led_names[i];
4796
4797 INIT_WORK(&tpacpi_leds[i].work, led_set_status_worker);
4798
4799 rc = led_classdev_register(&tpacpi_pdev->dev,
4800 &tpacpi_leds[i].led_classdev);
4801 if (rc < 0) {
4802 tpacpi_leds[i].led_classdev.name = NULL;
4803 led_exit();
4804 return rc;
4805 } 4985 }
4806 } 4986 }
4807 4987
4988#ifdef CONFIG_THINKPAD_ACPI_UNSAFE_LEDS
4989 if (led_supported != TPACPI_LED_NONE)
4990 printk(TPACPI_NOTICE
4991 "warning: userspace override of important "
4992 "firmware LEDs is enabled\n");
4993#endif
4808 return (led_supported != TPACPI_LED_NONE)? 0 : 1; 4994 return (led_supported != TPACPI_LED_NONE)? 0 : 1;
4809} 4995}
4810 4996
@@ -5340,6 +5526,20 @@ static struct ibm_struct ecdump_driver_data = {
5340 5526
5341#define TPACPI_BACKLIGHT_DEV_NAME "thinkpad_screen" 5527#define TPACPI_BACKLIGHT_DEV_NAME "thinkpad_screen"
5342 5528
5529/*
5530 * ThinkPads can read brightness from two places: EC HBRV (0x31), or
5531 * CMOS NVRAM byte 0x5E, bits 0-3.
5532 *
5533 * EC HBRV (0x31) has the following layout
5534 * Bit 7: unknown function
5535 * Bit 6: unknown function
5536 * Bit 5: Z: honour scale changes, NZ: ignore scale changes
5537 * Bit 4: must be set to zero to avoid problems
5538 * Bit 3-0: backlight brightness level
5539 *
5540 * brightness_get_raw returns status data in the HBRV layout
5541 */
5542
5343enum { 5543enum {
5344 TP_EC_BACKLIGHT = 0x31, 5544 TP_EC_BACKLIGHT = 0x31,
5345 5545
@@ -5349,108 +5549,164 @@ enum {
5349 TP_EC_BACKLIGHT_MAPSW = 0x20, 5549 TP_EC_BACKLIGHT_MAPSW = 0x20,
5350}; 5550};
5351 5551
5552enum tpacpi_brightness_access_mode {
5553 TPACPI_BRGHT_MODE_AUTO = 0, /* Not implemented yet */
5554 TPACPI_BRGHT_MODE_EC, /* EC control */
5555 TPACPI_BRGHT_MODE_UCMS_STEP, /* UCMS step-based control */
5556 TPACPI_BRGHT_MODE_ECNVRAM, /* EC control w/ NVRAM store */
5557 TPACPI_BRGHT_MODE_MAX
5558};
5559
5352static struct backlight_device *ibm_backlight_device; 5560static struct backlight_device *ibm_backlight_device;
5353static int brightness_mode; 5561
5562static enum tpacpi_brightness_access_mode brightness_mode =
5563 TPACPI_BRGHT_MODE_MAX;
5564
5354static unsigned int brightness_enable = 2; /* 2 = auto, 0 = no, 1 = yes */ 5565static unsigned int brightness_enable = 2; /* 2 = auto, 0 = no, 1 = yes */
5355 5566
5356static struct mutex brightness_mutex; 5567static struct mutex brightness_mutex;
5357 5568
5358/* 5569/* NVRAM brightness access,
5359 * ThinkPads can read brightness from two places: EC 0x31, or 5570 * call with brightness_mutex held! */
5360 * CMOS NVRAM byte 0x5E, bits 0-3. 5571static unsigned int tpacpi_brightness_nvram_get(void)
5361 *
5362 * EC 0x31 has the following layout
5363 * Bit 7: unknown function
5364 * Bit 6: unknown function
5365 * Bit 5: Z: honour scale changes, NZ: ignore scale changes
5366 * Bit 4: must be set to zero to avoid problems
5367 * Bit 3-0: backlight brightness level
5368 *
5369 * brightness_get_raw returns status data in the EC 0x31 layout
5370 */
5371static int brightness_get_raw(int *status)
5372{ 5572{
5373 u8 lec = 0, lcmos = 0, level = 0; 5573 u8 lnvram;
5374 5574
5375 if (brightness_mode & 1) { 5575 lnvram = (nvram_read_byte(TP_NVRAM_ADDR_BRIGHTNESS)
5376 if (!acpi_ec_read(TP_EC_BACKLIGHT, &lec)) 5576 & TP_NVRAM_MASK_LEVEL_BRIGHTNESS)
5377 return -EIO; 5577 >> TP_NVRAM_POS_LEVEL_BRIGHTNESS;
5378 level = lec & TP_EC_BACKLIGHT_LVLMSK; 5578 lnvram &= (tp_features.bright_16levels) ? 0x0f : 0x07;
5379 }; 5579
5380 if (brightness_mode & 2) { 5580 return lnvram;
5381 lcmos = (nvram_read_byte(TP_NVRAM_ADDR_BRIGHTNESS) 5581}
5382 & TP_NVRAM_MASK_LEVEL_BRIGHTNESS) 5582
5383 >> TP_NVRAM_POS_LEVEL_BRIGHTNESS; 5583static void tpacpi_brightness_checkpoint_nvram(void)
5384 lcmos &= (tp_features.bright_16levels)? 0x0f : 0x07; 5584{
5385 level = lcmos; 5585 u8 lec = 0;
5386 } 5586 u8 b_nvram;
5387 5587
5388 if (brightness_mode == 3) { 5588 if (brightness_mode != TPACPI_BRGHT_MODE_ECNVRAM)
5389 *status = lec; /* Prefer EC, CMOS is just a backing store */ 5589 return;
5390 lec &= TP_EC_BACKLIGHT_LVLMSK; 5590
5391 if (lec == lcmos) 5591 vdbg_printk(TPACPI_DBG_BRGHT,
5392 tp_warned.bright_cmos_ec_unsync = 0; 5592 "trying to checkpoint backlight level to NVRAM...\n");
5393 else { 5593
5394 if (!tp_warned.bright_cmos_ec_unsync) { 5594 if (mutex_lock_killable(&brightness_mutex) < 0)
5395 printk(TPACPI_ERR 5595 return;
5396 "CMOS NVRAM (%u) and EC (%u) do not " 5596
5397 "agree on display brightness level\n", 5597 if (unlikely(!acpi_ec_read(TP_EC_BACKLIGHT, &lec)))
5398 (unsigned int) lcmos, 5598 goto unlock;
5399 (unsigned int) lec); 5599 lec &= TP_EC_BACKLIGHT_LVLMSK;
5400 tp_warned.bright_cmos_ec_unsync = 1; 5600 b_nvram = nvram_read_byte(TP_NVRAM_ADDR_BRIGHTNESS);
5401 } 5601
5602 if (lec != ((b_nvram & TP_NVRAM_MASK_LEVEL_BRIGHTNESS)
5603 >> TP_NVRAM_POS_LEVEL_BRIGHTNESS)) {
5604 /* NVRAM needs update */
5605 b_nvram &= ~(TP_NVRAM_MASK_LEVEL_BRIGHTNESS <<
5606 TP_NVRAM_POS_LEVEL_BRIGHTNESS);
5607 b_nvram |= lec;
5608 nvram_write_byte(b_nvram, TP_NVRAM_ADDR_BRIGHTNESS);
5609 dbg_printk(TPACPI_DBG_BRGHT,
5610 "updated NVRAM backlight level to %u (0x%02x)\n",
5611 (unsigned int) lec, (unsigned int) b_nvram);
5612 } else
5613 vdbg_printk(TPACPI_DBG_BRGHT,
5614 "NVRAM backlight level already is %u (0x%02x)\n",
5615 (unsigned int) lec, (unsigned int) b_nvram);
5616
5617unlock:
5618 mutex_unlock(&brightness_mutex);
5619}
5620
5621
5622/* call with brightness_mutex held! */
5623static int tpacpi_brightness_get_raw(int *status)
5624{
5625 u8 lec = 0;
5626
5627 switch (brightness_mode) {
5628 case TPACPI_BRGHT_MODE_UCMS_STEP:
5629 *status = tpacpi_brightness_nvram_get();
5630 return 0;
5631 case TPACPI_BRGHT_MODE_EC:
5632 case TPACPI_BRGHT_MODE_ECNVRAM:
5633 if (unlikely(!acpi_ec_read(TP_EC_BACKLIGHT, &lec)))
5402 return -EIO; 5634 return -EIO;
5403 } 5635 *status = lec;
5404 } else { 5636 return 0;
5405 *status = level; 5637 default:
5638 return -ENXIO;
5406 } 5639 }
5640}
5641
5642/* call with brightness_mutex held! */
5643/* do NOT call with illegal backlight level value */
5644static int tpacpi_brightness_set_ec(unsigned int value)
5645{
5646 u8 lec = 0;
5647
5648 if (unlikely(!acpi_ec_read(TP_EC_BACKLIGHT, &lec)))
5649 return -EIO;
5650
5651 if (unlikely(!acpi_ec_write(TP_EC_BACKLIGHT,
5652 (lec & TP_EC_BACKLIGHT_CMDMSK) |
5653 (value & TP_EC_BACKLIGHT_LVLMSK))))
5654 return -EIO;
5655
5656 return 0;
5657}
5658
5659/* call with brightness_mutex held! */
5660static int tpacpi_brightness_set_ucmsstep(unsigned int value)
5661{
5662 int cmos_cmd, inc;
5663 unsigned int current_value, i;
5664
5665 current_value = tpacpi_brightness_nvram_get();
5666
5667 if (value == current_value)
5668 return 0;
5669
5670 cmos_cmd = (value > current_value) ?
5671 TP_CMOS_BRIGHTNESS_UP :
5672 TP_CMOS_BRIGHTNESS_DOWN;
5673 inc = (value > current_value) ? 1 : -1;
5674
5675 for (i = current_value; i != value; i += inc)
5676 if (issue_thinkpad_cmos_command(cmos_cmd))
5677 return -EIO;
5407 5678
5408 return 0; 5679 return 0;
5409} 5680}
5410 5681
5411/* May return EINTR which can always be mapped to ERESTARTSYS */ 5682/* May return EINTR which can always be mapped to ERESTARTSYS */
5412static int brightness_set(int value) 5683static int brightness_set(unsigned int value)
5413{ 5684{
5414 int cmos_cmd, inc, i, res; 5685 int res;
5415 int current_value;
5416 int command_bits;
5417 5686
5418 if (value > ((tp_features.bright_16levels)? 15 : 7) || 5687 if (value > ((tp_features.bright_16levels)? 15 : 7) ||
5419 value < 0) 5688 value < 0)
5420 return -EINVAL; 5689 return -EINVAL;
5421 5690
5691 vdbg_printk(TPACPI_DBG_BRGHT,
5692 "set backlight level to %d\n", value);
5693
5422 res = mutex_lock_killable(&brightness_mutex); 5694 res = mutex_lock_killable(&brightness_mutex);
5423 if (res < 0) 5695 if (res < 0)
5424 return res; 5696 return res;
5425 5697
5426 res = brightness_get_raw(&current_value); 5698 switch (brightness_mode) {
5427 if (res < 0) 5699 case TPACPI_BRGHT_MODE_EC:
5428 goto errout; 5700 case TPACPI_BRGHT_MODE_ECNVRAM:
5429 5701 res = tpacpi_brightness_set_ec(value);
5430 command_bits = current_value & TP_EC_BACKLIGHT_CMDMSK; 5702 break;
5431 current_value &= TP_EC_BACKLIGHT_LVLMSK; 5703 case TPACPI_BRGHT_MODE_UCMS_STEP:
5432 5704 res = tpacpi_brightness_set_ucmsstep(value);
5433 cmos_cmd = value > current_value ? 5705 break;
5434 TP_CMOS_BRIGHTNESS_UP : 5706 default:
5435 TP_CMOS_BRIGHTNESS_DOWN; 5707 res = -ENXIO;
5436 inc = (value > current_value)? 1 : -1;
5437
5438 res = 0;
5439 for (i = current_value; i != value; i += inc) {
5440 if ((brightness_mode & 2) &&
5441 issue_thinkpad_cmos_command(cmos_cmd)) {
5442 res = -EIO;
5443 goto errout;
5444 }
5445 if ((brightness_mode & 1) &&
5446 !acpi_ec_write(TP_EC_BACKLIGHT,
5447 (i + inc) | command_bits)) {
5448 res = -EIO;
5449 goto errout;;
5450 }
5451 } 5708 }
5452 5709
5453errout:
5454 mutex_unlock(&brightness_mutex); 5710 mutex_unlock(&brightness_mutex);
5455 return res; 5711 return res;
5456} 5712}
@@ -5459,21 +5715,34 @@ errout:
5459 5715
5460static int brightness_update_status(struct backlight_device *bd) 5716static int brightness_update_status(struct backlight_device *bd)
5461{ 5717{
5462 /* it is the backlight class's job (caller) to handle 5718 unsigned int level =
5463 * EINTR and other errors properly */
5464 return brightness_set(
5465 (bd->props.fb_blank == FB_BLANK_UNBLANK && 5719 (bd->props.fb_blank == FB_BLANK_UNBLANK &&
5466 bd->props.power == FB_BLANK_UNBLANK) ? 5720 bd->props.power == FB_BLANK_UNBLANK) ?
5467 bd->props.brightness : 0); 5721 bd->props.brightness : 0;
5722
5723 dbg_printk(TPACPI_DBG_BRGHT,
5724 "backlight: attempt to set level to %d\n",
5725 level);
5726
5727 /* it is the backlight class's job (caller) to handle
5728 * EINTR and other errors properly */
5729 return brightness_set(level);
5468} 5730}
5469 5731
5470static int brightness_get(struct backlight_device *bd) 5732static int brightness_get(struct backlight_device *bd)
5471{ 5733{
5472 int status, res; 5734 int status, res;
5473 5735
5474 res = brightness_get_raw(&status); 5736 res = mutex_lock_killable(&brightness_mutex);
5475 if (res < 0) 5737 if (res < 0)
5476 return 0; /* FIXME: teach backlight about error handling */ 5738 return 0;
5739
5740 res = tpacpi_brightness_get_raw(&status);
5741
5742 mutex_unlock(&brightness_mutex);
5743
5744 if (res < 0)
5745 return 0;
5477 5746
5478 return status & TP_EC_BACKLIGHT_LVLMSK; 5747 return status & TP_EC_BACKLIGHT_LVLMSK;
5479} 5748}
@@ -5523,7 +5792,7 @@ static int __init brightness_init(struct ibm_init_struct *iibm)
5523 } 5792 }
5524 5793
5525 if (!brightness_enable) { 5794 if (!brightness_enable) {
5526 dbg_printk(TPACPI_DBG_INIT, 5795 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_BRGHT,
5527 "brightness support disabled by " 5796 "brightness support disabled by "
5528 "module parameter\n"); 5797 "module parameter\n");
5529 return 1; 5798 return 1;
@@ -5538,20 +5807,38 @@ static int __init brightness_init(struct ibm_init_struct *iibm)
5538 if (b == 16) 5807 if (b == 16)
5539 tp_features.bright_16levels = 1; 5808 tp_features.bright_16levels = 1;
5540 5809
5541 if (!brightness_mode) { 5810 /*
5542 if (thinkpad_id.vendor == PCI_VENDOR_ID_LENOVO) 5811 * Check for module parameter bogosity, note that we
5543 brightness_mode = 2; 5812 * init brightness_mode to TPACPI_BRGHT_MODE_MAX in order to be
5544 else 5813 * able to detect "unspecified"
5545 brightness_mode = 3; 5814 */
5815 if (brightness_mode > TPACPI_BRGHT_MODE_MAX)
5816 return -EINVAL;
5546 5817
5547 dbg_printk(TPACPI_DBG_INIT, "selected brightness_mode=%d\n", 5818 /* TPACPI_BRGHT_MODE_AUTO not implemented yet, just use default */
5548 brightness_mode); 5819 if (brightness_mode == TPACPI_BRGHT_MODE_AUTO ||
5549 } 5820 brightness_mode == TPACPI_BRGHT_MODE_MAX) {
5821 if (thinkpad_id.vendor == PCI_VENDOR_ID_IBM) {
5822 /*
5823 * IBM models that define HBRV probably have
5824 * EC-based backlight level control
5825 */
5826 if (acpi_evalf(ec_handle, NULL, "HBRV", "qd"))
5827 /* T40-T43, R50-R52, R50e, R51e, X31-X41 */
5828 brightness_mode = TPACPI_BRGHT_MODE_ECNVRAM;
5829 else
5830 /* all other IBM ThinkPads */
5831 brightness_mode = TPACPI_BRGHT_MODE_UCMS_STEP;
5832 } else
5833 /* All Lenovo ThinkPads */
5834 brightness_mode = TPACPI_BRGHT_MODE_UCMS_STEP;
5550 5835
5551 if (brightness_mode > 3) 5836 dbg_printk(TPACPI_DBG_BRGHT,
5552 return -EINVAL; 5837 "selected brightness_mode=%d\n",
5838 brightness_mode);
5839 }
5553 5840
5554 if (brightness_get_raw(&b) < 0) 5841 if (tpacpi_brightness_get_raw(&b) < 0)
5555 return 1; 5842 return 1;
5556 5843
5557 if (tp_features.bright_16levels) 5844 if (tp_features.bright_16levels)
@@ -5565,7 +5852,8 @@ static int __init brightness_init(struct ibm_init_struct *iibm)
5565 printk(TPACPI_ERR "Could not register backlight device\n"); 5852 printk(TPACPI_ERR "Could not register backlight device\n");
5566 return PTR_ERR(ibm_backlight_device); 5853 return PTR_ERR(ibm_backlight_device);
5567 } 5854 }
5568 vdbg_printk(TPACPI_DBG_INIT, "brightness is supported\n"); 5855 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_BRGHT,
5856 "brightness is supported\n");
5569 5857
5570 ibm_backlight_device->props.max_brightness = 5858 ibm_backlight_device->props.max_brightness =
5571 (tp_features.bright_16levels)? 15 : 7; 5859 (tp_features.bright_16levels)? 15 : 7;
@@ -5575,13 +5863,25 @@ static int __init brightness_init(struct ibm_init_struct *iibm)
5575 return 0; 5863 return 0;
5576} 5864}
5577 5865
5866static void brightness_suspend(pm_message_t state)
5867{
5868 tpacpi_brightness_checkpoint_nvram();
5869}
5870
5871static void brightness_shutdown(void)
5872{
5873 tpacpi_brightness_checkpoint_nvram();
5874}
5875
5578static void brightness_exit(void) 5876static void brightness_exit(void)
5579{ 5877{
5580 if (ibm_backlight_device) { 5878 if (ibm_backlight_device) {
5581 vdbg_printk(TPACPI_DBG_EXIT, 5879 vdbg_printk(TPACPI_DBG_EXIT | TPACPI_DBG_BRGHT,
5582 "calling backlight_device_unregister()\n"); 5880 "calling backlight_device_unregister()\n");
5583 backlight_device_unregister(ibm_backlight_device); 5881 backlight_device_unregister(ibm_backlight_device);
5584 } 5882 }
5883
5884 tpacpi_brightness_checkpoint_nvram();
5585} 5885}
5586 5886
5587static int brightness_read(char *p) 5887static int brightness_read(char *p)
@@ -5628,6 +5928,9 @@ static int brightness_write(char *buf)
5628 return -EINVAL; 5928 return -EINVAL;
5629 } 5929 }
5630 5930
5931 tpacpi_disclose_usertask("procfs brightness",
5932 "set level to %d\n", level);
5933
5631 /* 5934 /*
5632 * Now we know what the final level should be, so we try to set it. 5935 * Now we know what the final level should be, so we try to set it.
5633 * Doing it this way makes the syscall restartable in case of EINTR 5936 * Doing it this way makes the syscall restartable in case of EINTR
@@ -5641,6 +5944,8 @@ static struct ibm_struct brightness_driver_data = {
5641 .read = brightness_read, 5944 .read = brightness_read,
5642 .write = brightness_write, 5945 .write = brightness_write,
5643 .exit = brightness_exit, 5946 .exit = brightness_exit,
5947 .suspend = brightness_suspend,
5948 .shutdown = brightness_shutdown,
5644}; 5949};
5645 5950
5646/************************************************************************* 5951/*************************************************************************
@@ -6086,6 +6391,9 @@ static int fan_set_level(int level)
6086 default: 6391 default:
6087 return -ENXIO; 6392 return -ENXIO;
6088 } 6393 }
6394
6395 vdbg_printk(TPACPI_DBG_FAN,
6396 "fan control: set fan control register to 0x%02x\n", level);
6089 return 0; 6397 return 0;
6090} 6398}
6091 6399
@@ -6163,6 +6471,11 @@ static int fan_set_enable(void)
6163 } 6471 }
6164 6472
6165 mutex_unlock(&fan_mutex); 6473 mutex_unlock(&fan_mutex);
6474
6475 if (!rc)
6476 vdbg_printk(TPACPI_DBG_FAN,
6477 "fan control: set fan control register to 0x%02x\n",
6478 s);
6166 return rc; 6479 return rc;
6167} 6480}
6168 6481
@@ -6199,6 +6512,9 @@ static int fan_set_disable(void)
6199 rc = -ENXIO; 6512 rc = -ENXIO;
6200 } 6513 }
6201 6514
6515 if (!rc)
6516 vdbg_printk(TPACPI_DBG_FAN,
6517 "fan control: set fan control register to 0\n");
6202 6518
6203 mutex_unlock(&fan_mutex); 6519 mutex_unlock(&fan_mutex);
6204 return rc; 6520 return rc;
@@ -6327,6 +6643,9 @@ static ssize_t fan_pwm1_enable_store(struct device *dev,
6327 if (parse_strtoul(buf, 2, &t)) 6643 if (parse_strtoul(buf, 2, &t))
6328 return -EINVAL; 6644 return -EINVAL;
6329 6645
6646 tpacpi_disclose_usertask("hwmon pwm1_enable",
6647 "set fan mode to %lu\n", t);
6648
6330 switch (t) { 6649 switch (t) {
6331 case 0: 6650 case 0:
6332 level = TP_EC_FAN_FULLSPEED; 6651 level = TP_EC_FAN_FULLSPEED;
@@ -6392,6 +6711,9 @@ static ssize_t fan_pwm1_store(struct device *dev,
6392 if (parse_strtoul(buf, 255, &s)) 6711 if (parse_strtoul(buf, 255, &s))
6393 return -EINVAL; 6712 return -EINVAL;
6394 6713
6714 tpacpi_disclose_usertask("hwmon pwm1",
6715 "set fan speed to %lu\n", s);
6716
6395 /* scale down from 0-255 to 0-7 */ 6717 /* scale down from 0-255 to 0-7 */
6396 newlevel = (s >> 5) & 0x07; 6718 newlevel = (s >> 5) & 0x07;
6397 6719
@@ -6458,6 +6780,8 @@ static ssize_t fan_fan_watchdog_store(struct device_driver *drv,
6458 fan_watchdog_maxinterval = t; 6780 fan_watchdog_maxinterval = t;
6459 fan_watchdog_reset(); 6781 fan_watchdog_reset();
6460 6782
6783 tpacpi_disclose_usertask("fan_watchdog", "set to %lu\n", t);
6784
6461 return count; 6785 return count;
6462} 6786}
6463 6787
@@ -6479,7 +6803,8 @@ static int __init fan_init(struct ibm_init_struct *iibm)
6479{ 6803{
6480 int rc; 6804 int rc;
6481 6805
6482 vdbg_printk(TPACPI_DBG_INIT, "initializing fan subdriver\n"); 6806 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_FAN,
6807 "initializing fan subdriver\n");
6483 6808
6484 mutex_init(&fan_mutex); 6809 mutex_init(&fan_mutex);
6485 fan_status_access_mode = TPACPI_FAN_NONE; 6810 fan_status_access_mode = TPACPI_FAN_NONE;
@@ -6538,7 +6863,8 @@ static int __init fan_init(struct ibm_init_struct *iibm)
6538 } 6863 }
6539 } 6864 }
6540 6865
6541 vdbg_printk(TPACPI_DBG_INIT, "fan is %s, modes %d, %d\n", 6866 vdbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_FAN,
6867 "fan is %s, modes %d, %d\n",
6542 str_supported(fan_status_access_mode != TPACPI_FAN_NONE || 6868 str_supported(fan_status_access_mode != TPACPI_FAN_NONE ||
6543 fan_control_access_mode != TPACPI_FAN_WR_NONE), 6869 fan_control_access_mode != TPACPI_FAN_WR_NONE),
6544 fan_status_access_mode, fan_control_access_mode); 6870 fan_status_access_mode, fan_control_access_mode);
@@ -6547,7 +6873,7 @@ static int __init fan_init(struct ibm_init_struct *iibm)
6547 if (!fan_control_allowed) { 6873 if (!fan_control_allowed) {
6548 fan_control_access_mode = TPACPI_FAN_WR_NONE; 6874 fan_control_access_mode = TPACPI_FAN_WR_NONE;
6549 fan_control_commands = 0; 6875 fan_control_commands = 0;
6550 dbg_printk(TPACPI_DBG_INIT, 6876 dbg_printk(TPACPI_DBG_INIT | TPACPI_DBG_FAN,
6551 "fan control features disabled by parameter\n"); 6877 "fan control features disabled by parameter\n");
6552 } 6878 }
6553 6879
@@ -6576,7 +6902,7 @@ static int __init fan_init(struct ibm_init_struct *iibm)
6576 6902
6577static void fan_exit(void) 6903static void fan_exit(void)
6578{ 6904{
6579 vdbg_printk(TPACPI_DBG_EXIT, 6905 vdbg_printk(TPACPI_DBG_EXIT | TPACPI_DBG_FAN,
6580 "cancelling any pending fan watchdog tasks\n"); 6906 "cancelling any pending fan watchdog tasks\n");
6581 6907
6582 /* FIXME: can we really do this unconditionally? */ 6908 /* FIXME: can we really do this unconditionally? */
@@ -6757,6 +7083,9 @@ static int fan_write_cmd_level(const char *cmd, int *rc)
6757 if (*rc == -ENXIO) 7083 if (*rc == -ENXIO)
6758 printk(TPACPI_ERR "level command accepted for unsupported " 7084 printk(TPACPI_ERR "level command accepted for unsupported "
6759 "access mode %d", fan_control_access_mode); 7085 "access mode %d", fan_control_access_mode);
7086 else if (!*rc)
7087 tpacpi_disclose_usertask("procfs fan",
7088 "set level to %d\n", level);
6760 7089
6761 return 1; 7090 return 1;
6762} 7091}
@@ -6770,6 +7099,8 @@ static int fan_write_cmd_enable(const char *cmd, int *rc)
6770 if (*rc == -ENXIO) 7099 if (*rc == -ENXIO)
6771 printk(TPACPI_ERR "enable command accepted for unsupported " 7100 printk(TPACPI_ERR "enable command accepted for unsupported "
6772 "access mode %d", fan_control_access_mode); 7101 "access mode %d", fan_control_access_mode);
7102 else if (!*rc)
7103 tpacpi_disclose_usertask("procfs fan", "enable\n");
6773 7104
6774 return 1; 7105 return 1;
6775} 7106}
@@ -6783,6 +7114,8 @@ static int fan_write_cmd_disable(const char *cmd, int *rc)
6783 if (*rc == -ENXIO) 7114 if (*rc == -ENXIO)
6784 printk(TPACPI_ERR "disable command accepted for unsupported " 7115 printk(TPACPI_ERR "disable command accepted for unsupported "
6785 "access mode %d", fan_control_access_mode); 7116 "access mode %d", fan_control_access_mode);
7117 else if (!*rc)
7118 tpacpi_disclose_usertask("procfs fan", "disable\n");
6786 7119
6787 return 1; 7120 return 1;
6788} 7121}
@@ -6801,6 +7134,9 @@ static int fan_write_cmd_speed(const char *cmd, int *rc)
6801 if (*rc == -ENXIO) 7134 if (*rc == -ENXIO)
6802 printk(TPACPI_ERR "speed command accepted for unsupported " 7135 printk(TPACPI_ERR "speed command accepted for unsupported "
6803 "access mode %d", fan_control_access_mode); 7136 "access mode %d", fan_control_access_mode);
7137 else if (!*rc)
7138 tpacpi_disclose_usertask("procfs fan",
7139 "set speed to %d\n", speed);
6804 7140
6805 return 1; 7141 return 1;
6806} 7142}
@@ -6814,8 +7150,12 @@ static int fan_write_cmd_watchdog(const char *cmd, int *rc)
6814 7150
6815 if (interval < 0 || interval > 120) 7151 if (interval < 0 || interval > 120)
6816 *rc = -EINVAL; 7152 *rc = -EINVAL;
6817 else 7153 else {
6818 fan_watchdog_maxinterval = interval; 7154 fan_watchdog_maxinterval = interval;
7155 tpacpi_disclose_usertask("procfs fan",
7156 "set watchdog timer to %d\n",
7157 interval);
7158 }
6819 7159
6820 return 1; 7160 return 1;
6821} 7161}
@@ -7244,10 +7584,10 @@ module_param_named(fan_control, fan_control_allowed, bool, 0);
7244MODULE_PARM_DESC(fan_control, 7584MODULE_PARM_DESC(fan_control,
7245 "Enables setting fan parameters features when true"); 7585 "Enables setting fan parameters features when true");
7246 7586
7247module_param_named(brightness_mode, brightness_mode, int, 0); 7587module_param_named(brightness_mode, brightness_mode, uint, 0);
7248MODULE_PARM_DESC(brightness_mode, 7588MODULE_PARM_DESC(brightness_mode,
7249 "Selects brightness control strategy: " 7589 "Selects brightness control strategy: "
7250 "0=auto, 1=EC, 2=CMOS, 3=both"); 7590 "0=auto, 1=EC, 2=UCMS, 3=EC+NVRAM");
7251 7591
7252module_param(brightness_enable, uint, 0); 7592module_param(brightness_enable, uint, 0);
7253MODULE_PARM_DESC(brightness_enable, 7593MODULE_PARM_DESC(brightness_enable,
@@ -7517,9 +7857,6 @@ static int __init thinkpad_acpi_module_init(void)
7517 return 0; 7857 return 0;
7518} 7858}
7519 7859
7520/* Please remove this in year 2009 */
7521MODULE_ALIAS("ibm_acpi");
7522
7523MODULE_ALIAS(TPACPI_DRVR_SHORTNAME); 7860MODULE_ALIAS(TPACPI_DRVR_SHORTNAME);
7524 7861
7525/* 7862/*