aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/acpi
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/acpi')
-rw-r--r--drivers/acpi/Kconfig34
-rw-r--r--drivers/acpi/Makefile10
-rw-r--r--drivers/acpi/acpi_memhotplug.c13
-rw-r--r--drivers/acpi/blacklist.c10
-rw-r--r--drivers/acpi/bus.c4
-rw-r--r--drivers/acpi/container.c6
-rw-r--r--drivers/acpi/dock.c25
-rw-r--r--drivers/acpi/ec.c527
-rw-r--r--drivers/acpi/events/evmisc.c33
-rw-r--r--drivers/acpi/events/evregion.c15
-rw-r--r--drivers/acpi/events/evxface.c6
-rw-r--r--drivers/acpi/executer/excreate.c5
-rw-r--r--drivers/acpi/executer/exsystem.c30
-rw-r--r--drivers/acpi/executer/exutils.c104
-rw-r--r--drivers/acpi/glue.c46
-rw-r--r--drivers/acpi/hardware/hwsleep.c5
-rw-r--r--drivers/acpi/i2c_ec.c403
-rw-r--r--drivers/acpi/i2c_ec.h23
-rw-r--r--drivers/acpi/ibm_acpi.c2761
-rw-r--r--drivers/acpi/namespace/nseval.c11
-rw-r--r--drivers/acpi/namespace/nsinit.c7
-rw-r--r--drivers/acpi/namespace/nsxfeval.c11
-rw-r--r--drivers/acpi/osl.c1
-rw-r--r--drivers/acpi/power.c20
-rw-r--r--drivers/acpi/processor_core.c4
-rw-r--r--drivers/acpi/processor_idle.c15
-rw-r--r--drivers/acpi/processor_perflib.c46
-rw-r--r--drivers/acpi/resources/rscreate.c25
-rw-r--r--drivers/acpi/sbs.c1291
-rw-r--r--drivers/acpi/scan.c6
-rw-r--r--drivers/acpi/sleep/main.c80
-rw-r--r--drivers/acpi/sleep/proc.c37
-rw-r--r--drivers/acpi/tables.c57
-rw-r--r--drivers/acpi/tables/tbfadt.c12
-rw-r--r--drivers/acpi/thermal.c3
-rw-r--r--drivers/acpi/video.c38
36 files changed, 1308 insertions, 4416 deletions
diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig
index 7c49e103cf8f..139f41f033d8 100644
--- a/drivers/acpi/Kconfig
+++ b/drivers/acpi/Kconfig
@@ -7,6 +7,7 @@ menu "ACPI (Advanced Configuration and Power Interface) Support"
7 depends on !X86_VISWS 7 depends on !X86_VISWS
8 depends on !IA64_HP_SIM 8 depends on !IA64_HP_SIM
9 depends on IA64 || X86 9 depends on IA64 || X86
10 depends on PM
10 11
11config ACPI 12config ACPI
12 bool "ACPI Support" 13 bool "ACPI Support"
@@ -84,8 +85,8 @@ config ACPI_PROCFS
84 depends on ACPI 85 depends on ACPI
85 default y 86 default y
86 ---help--- 87 ---help---
87 Procfs interface for ACPI is made optional for back-compatible. 88 The Procfs interface for ACPI is made optional for backward compatibility.
88 As the same functions are duplicated in sysfs interface 89 As the same functions are duplicated in the sysfs interface
89 and this proc interface will be removed some time later, 90 and this proc interface will be removed some time later,
90 it's marked as deprecated. 91 it's marked as deprecated.
91 ( /proc/acpi/debug_layer && debug_level are deprecated by 92 ( /proc/acpi/debug_layer && debug_level are deprecated by
@@ -217,32 +218,6 @@ config ACPI_ASUS
217 NOTE: This driver is deprecated and will probably be removed soon, 218 NOTE: This driver is deprecated and will probably be removed soon,
218 use asus-laptop instead. 219 use asus-laptop instead.
219 220
220config ACPI_IBM
221 tristate "IBM ThinkPad Laptop Extras"
222 depends on X86
223 select BACKLIGHT_CLASS_DEVICE
224 ---help---
225 This is a Linux ACPI driver for the IBM ThinkPad laptops. It adds
226 support for Fn-Fx key combinations, Bluetooth control, video
227 output switching, ThinkLight control, UltraBay eject and more.
228 For more information about this driver see <file:Documentation/ibm-acpi.txt>
229 and <http://ibm-acpi.sf.net/> .
230
231 If you have an IBM ThinkPad laptop, say Y or M here.
232
233config ACPI_IBM_DOCK
234 bool "Legacy Docking Station Support"
235 depends on ACPI_IBM
236 depends on ACPI_DOCK=n
237 default n
238 ---help---
239 Allows the ibm_acpi driver to handle docking station events.
240 This support is obsoleted by CONFIG_HOTPLUG_PCI_ACPI. It will
241 allow locking and removing the laptop from the docking station,
242 but will not properly connect PCI devices.
243
244 If you are not sure, say N here.
245
246config ACPI_TOSHIBA 221config ACPI_TOSHIBA
247 tristate "Toshiba Laptop Extras" 222 tristate "Toshiba Laptop Extras"
248 depends on X86 223 depends on X86
@@ -376,11 +351,10 @@ config ACPI_HOTPLUG_MEMORY
376 351
377config ACPI_SBS 352config ACPI_SBS
378 tristate "Smart Battery System (EXPERIMENTAL)" 353 tristate "Smart Battery System (EXPERIMENTAL)"
379 depends on X86 && I2C 354 depends on X86
380 depends on EXPERIMENTAL 355 depends on EXPERIMENTAL
381 help 356 help
382 This driver adds support for the Smart Battery System. 357 This driver adds support for the Smart Battery System.
383 Depends on I2C (Device Drivers ---> I2C support)
384 A "Smart Battery" is quite old and quite rare compared 358 A "Smart Battery" is quite old and quite rare compared
385 to today's ACPI "Control Method" battery. 359 to today's ACPI "Control Method" battery.
386 360
diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile
index 5956e9f64a8b..d4336f1730e9 100644
--- a/drivers/acpi/Makefile
+++ b/drivers/acpi/Makefile
@@ -1,6 +1,6 @@
1# 1#
2# Makefile for the Linux ACPI interpreter 2# Makefile for the Linux ACPI interpreter
3# 3#
4 4
5export ACPI_CFLAGS 5export ACPI_CFLAGS
6 6
@@ -32,16 +32,17 @@ obj-y += osl.o utils.o \
32processor-objs += processor_core.o processor_throttling.o \ 32processor-objs += processor_core.o processor_throttling.o \
33 processor_idle.o processor_thermal.o 33 processor_idle.o processor_thermal.o
34ifdef CONFIG_CPU_FREQ 34ifdef CONFIG_CPU_FREQ
35processor-objs += processor_perflib.o 35processor-objs += processor_perflib.o
36endif 36endif
37 37
38obj-y += sleep/ 38obj-y += sleep/
39obj-y += bus.o glue.o 39obj-y += bus.o glue.o
40obj-y += scan.o 40obj-y += scan.o
41# Keep EC driver first. Initialization of others depend on it.
42obj-$(CONFIG_ACPI_EC) += ec.o
41obj-$(CONFIG_ACPI_AC) += ac.o 43obj-$(CONFIG_ACPI_AC) += ac.o
42obj-$(CONFIG_ACPI_BATTERY) += battery.o 44obj-$(CONFIG_ACPI_BATTERY) += battery.o
43obj-$(CONFIG_ACPI_BUTTON) += button.o 45obj-$(CONFIG_ACPI_BUTTON) += button.o
44obj-$(CONFIG_ACPI_EC) += ec.o
45obj-$(CONFIG_ACPI_FAN) += fan.o 46obj-$(CONFIG_ACPI_FAN) += fan.o
46obj-$(CONFIG_ACPI_DOCK) += dock.o 47obj-$(CONFIG_ACPI_DOCK) += dock.o
47obj-$(CONFIG_ACPI_BAY) += bay.o 48obj-$(CONFIG_ACPI_BAY) += bay.o
@@ -55,8 +56,7 @@ obj-$(CONFIG_ACPI_SYSTEM) += system.o event.o
55obj-$(CONFIG_ACPI_DEBUG) += debug.o 56obj-$(CONFIG_ACPI_DEBUG) += debug.o
56obj-$(CONFIG_ACPI_NUMA) += numa.o 57obj-$(CONFIG_ACPI_NUMA) += numa.o
57obj-$(CONFIG_ACPI_ASUS) += asus_acpi.o 58obj-$(CONFIG_ACPI_ASUS) += asus_acpi.o
58obj-$(CONFIG_ACPI_IBM) += ibm_acpi.o
59obj-$(CONFIG_ACPI_TOSHIBA) += toshiba_acpi.o 59obj-$(CONFIG_ACPI_TOSHIBA) += toshiba_acpi.o
60obj-$(CONFIG_ACPI_HOTPLUG_MEMORY) += acpi_memhotplug.o 60obj-$(CONFIG_ACPI_HOTPLUG_MEMORY) += acpi_memhotplug.o
61obj-y += cm_sbs.o 61obj-y += cm_sbs.o
62obj-$(CONFIG_ACPI_SBS) += i2c_ec.o sbs.o 62obj-$(CONFIG_ACPI_SBS) += sbs.o
diff --git a/drivers/acpi/acpi_memhotplug.c b/drivers/acpi/acpi_memhotplug.c
index c26172671fd8..e65628a03085 100644
--- a/drivers/acpi/acpi_memhotplug.c
+++ b/drivers/acpi/acpi_memhotplug.c
@@ -44,11 +44,6 @@ MODULE_AUTHOR("Naveen B S <naveen.b.s@intel.com>");
44MODULE_DESCRIPTION("Hotplug Mem Driver"); 44MODULE_DESCRIPTION("Hotplug Mem Driver");
45MODULE_LICENSE("GPL"); 45MODULE_LICENSE("GPL");
46 46
47/* ACPI _STA method values */
48#define ACPI_MEMORY_STA_PRESENT (0x00000001UL)
49#define ACPI_MEMORY_STA_ENABLED (0x00000002UL)
50#define ACPI_MEMORY_STA_FUNCTIONAL (0x00000008UL)
51
52/* Memory Device States */ 47/* Memory Device States */
53#define MEMORY_INVALID_STATE 0 48#define MEMORY_INVALID_STATE 0
54#define MEMORY_POWER_ON_STATE 1 49#define MEMORY_POWER_ON_STATE 1
@@ -204,9 +199,9 @@ static int acpi_memory_check_device(struct acpi_memory_device *mem_device)
204 * Check for device status. Device should be 199 * Check for device status. Device should be
205 * present/enabled/functioning. 200 * present/enabled/functioning.
206 */ 201 */
207 if (!((current_status & ACPI_MEMORY_STA_PRESENT) 202 if (!((current_status & ACPI_STA_DEVICE_PRESENT)
208 && (current_status & ACPI_MEMORY_STA_ENABLED) 203 && (current_status & ACPI_STA_DEVICE_ENABLED)
209 && (current_status & ACPI_MEMORY_STA_FUNCTIONAL))) 204 && (current_status & ACPI_STA_DEVICE_FUNCTIONING)))
210 return -ENODEV; 205 return -ENODEV;
211 206
212 return 0; 207 return 0;
@@ -286,7 +281,7 @@ static int acpi_memory_powerdown_device(struct acpi_memory_device *mem_device)
286 return -ENODEV; 281 return -ENODEV;
287 282
288 /* Check for device status. Device should be disabled */ 283 /* Check for device status. Device should be disabled */
289 if (current_status & ACPI_MEMORY_STA_ENABLED) 284 if (current_status & ACPI_STA_DEVICE_ENABLED)
290 return -EINVAL; 285 return -EINVAL;
291 286
292 return 0; 287 return 0;
diff --git a/drivers/acpi/blacklist.c b/drivers/acpi/blacklist.c
index f289fd41e77d..3ec110ce00c8 100644
--- a/drivers/acpi/blacklist.c
+++ b/drivers/acpi/blacklist.c
@@ -79,11 +79,17 @@ static int __init blacklist_by_year(void)
79{ 79{
80 int year = dmi_get_year(DMI_BIOS_DATE); 80 int year = dmi_get_year(DMI_BIOS_DATE);
81 /* Doesn't exist? Likely an old system */ 81 /* Doesn't exist? Likely an old system */
82 if (year == -1) 82 if (year == -1) {
83 printk(KERN_ERR PREFIX "no DMI BIOS year, "
84 "acpi=force is required to enable ACPI\n" );
83 return 1; 85 return 1;
86 }
84 /* 0? Likely a buggy new BIOS */ 87 /* 0? Likely a buggy new BIOS */
85 if (year == 0) 88 if (year == 0) {
89 printk(KERN_ERR PREFIX "DMI BIOS year==0, "
90 "assuming ACPI-capable machine\n" );
86 return 0; 91 return 0;
92 }
87 if (year < CONFIG_ACPI_BLACKLIST_YEAR) { 93 if (year < CONFIG_ACPI_BLACKLIST_YEAR) {
88 printk(KERN_ERR PREFIX "BIOS age (%d) fails cutoff (%d), " 94 printk(KERN_ERR PREFIX "BIOS age (%d) fails cutoff (%d), "
89 "acpi=force is required to enable ACPI\n", 95 "acpi=force is required to enable ACPI\n",
diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c
index dd49ea0d0ed3..e5084ececb6f 100644
--- a/drivers/acpi/bus.c
+++ b/drivers/acpi/bus.c
@@ -103,7 +103,9 @@ int acpi_bus_get_status(struct acpi_device *device)
103 else if (device->parent) 103 else if (device->parent)
104 device->status = device->parent->status; 104 device->status = device->parent->status;
105 else 105 else
106 STRUCT_TO_INT(device->status) = 0x0F; 106 STRUCT_TO_INT(device->status) =
107 ACPI_STA_DEVICE_PRESENT | ACPI_STA_DEVICE_ENABLED |
108 ACPI_STA_DEVICE_UI | ACPI_STA_DEVICE_FUNCTIONING;
107 109
108 if (device->status.functional && !device->status.present) { 110 if (device->status.functional && !device->status.present) {
109 printk(KERN_WARNING PREFIX "Device [%s] status [%08x]: " 111 printk(KERN_WARNING PREFIX "Device [%s] status [%08x]: "
diff --git a/drivers/acpi/container.c b/drivers/acpi/container.c
index 0930d9413dfa..0dd3bf7c0ed1 100644
--- a/drivers/acpi/container.c
+++ b/drivers/acpi/container.c
@@ -49,8 +49,6 @@ MODULE_AUTHOR("Anil S Keshavamurthy");
49MODULE_DESCRIPTION("ACPI container driver"); 49MODULE_DESCRIPTION("ACPI container driver");
50MODULE_LICENSE("GPL"); 50MODULE_LICENSE("GPL");
51 51
52#define ACPI_STA_PRESENT (0x00000001)
53
54static int acpi_container_add(struct acpi_device *device); 52static int acpi_container_add(struct acpi_device *device);
55static int acpi_container_remove(struct acpi_device *device, int type); 53static int acpi_container_remove(struct acpi_device *device, int type);
56 54
@@ -75,13 +73,13 @@ static int is_device_present(acpi_handle handle)
75 73
76 status = acpi_get_handle(handle, "_STA", &temp); 74 status = acpi_get_handle(handle, "_STA", &temp);
77 if (ACPI_FAILURE(status)) 75 if (ACPI_FAILURE(status))
78 return 1; /* _STA not found, assmue device present */ 76 return 1; /* _STA not found, assume device present */
79 77
80 status = acpi_evaluate_integer(handle, "_STA", NULL, &sta); 78 status = acpi_evaluate_integer(handle, "_STA", NULL, &sta);
81 if (ACPI_FAILURE(status)) 79 if (ACPI_FAILURE(status))
82 return 0; /* Firmware error */ 80 return 0; /* Firmware error */
83 81
84 return ((sta & ACPI_STA_PRESENT) == ACPI_STA_PRESENT); 82 return ((sta & ACPI_STA_DEVICE_PRESENT) == ACPI_STA_DEVICE_PRESENT);
85} 83}
86 84
87/*******************************************************************/ 85/*******************************************************************/
diff --git a/drivers/acpi/dock.c b/drivers/acpi/dock.c
index 54a697f9aa18..4546bf873aea 100644
--- a/drivers/acpi/dock.c
+++ b/drivers/acpi/dock.c
@@ -29,6 +29,7 @@
29#include <linux/notifier.h> 29#include <linux/notifier.h>
30#include <linux/platform_device.h> 30#include <linux/platform_device.h>
31#include <linux/jiffies.h> 31#include <linux/jiffies.h>
32#include <linux/stddef.h>
32#include <acpi/acpi_bus.h> 33#include <acpi/acpi_bus.h>
33#include <acpi/acpi_drivers.h> 34#include <acpi/acpi_drivers.h>
34 35
@@ -667,6 +668,23 @@ static ssize_t write_undock(struct device *dev, struct device_attribute *attr,
667} 668}
668DEVICE_ATTR(undock, S_IWUSR, NULL, write_undock); 669DEVICE_ATTR(undock, S_IWUSR, NULL, write_undock);
669 670
671/*
672 * show_dock_uid - read method for "uid" file in sysfs
673 */
674static ssize_t show_dock_uid(struct device *dev,
675 struct device_attribute *attr, char *buf)
676{
677 unsigned long lbuf;
678 acpi_status status = acpi_evaluate_integer(dock_station->handle, "_UID", NULL, &lbuf);
679 if(ACPI_FAILURE(status)) {
680 return 0;
681 }
682 return snprintf(buf, PAGE_SIZE, "%lx\n", lbuf);
683}
684DEVICE_ATTR(uid, S_IRUGO, show_dock_uid, NULL);
685
686
687
670/** 688/**
671 * dock_add - add a new dock station 689 * dock_add - add a new dock station
672 * @handle: the dock station handle 690 * @handle: the dock station handle
@@ -715,6 +733,13 @@ static int dock_add(acpi_handle handle)
715 kfree(dock_station); 733 kfree(dock_station);
716 return ret; 734 return ret;
717 } 735 }
736 ret = device_create_file(&dock_device.dev, &dev_attr_uid);
737 if (ret) {
738 printk("Error %d adding sysfs file\n", ret);
739 platform_device_unregister(&dock_device);
740 kfree(dock_station);
741 return ret;
742 }
718 743
719 /* Find dependent devices */ 744 /* Find dependent devices */
720 acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT, 745 acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT,
diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c
index ab6888373795..e08cf98f504f 100644
--- a/drivers/acpi/ec.c
+++ b/drivers/acpi/ec.c
@@ -1,6 +1,8 @@
1/* 1/*
2 * acpi_ec.c - ACPI Embedded Controller Driver ($Revision: 38 $) 2 * ec.c - ACPI Embedded Controller Driver (v2.0)
3 * 3 *
4 * Copyright (C) 2006, 2007 Alexey Starikovskiy <alexey.y.starikovskiy@intel.com>
5 * Copyright (C) 2006 Denis Sadykov <denis.m.sadykov@intel.com>
4 * Copyright (C) 2004 Luming Yu <luming.yu@intel.com> 6 * Copyright (C) 2004 Luming Yu <luming.yu@intel.com>
5 * Copyright (C) 2001, 2002 Andy Grover <andrew.grover@intel.com> 7 * Copyright (C) 2001, 2002 Andy Grover <andrew.grover@intel.com>
6 * Copyright (C) 2001, 2002 Paul Diefenbaugh <paul.s.diefenbaugh@intel.com> 8 * Copyright (C) 2001, 2002 Paul Diefenbaugh <paul.s.diefenbaugh@intel.com>
@@ -91,21 +93,18 @@ static struct acpi_driver acpi_ec_driver = {
91}; 93};
92 94
93/* If we find an EC via the ECDT, we need to keep a ptr to its context */ 95/* If we find an EC via the ECDT, we need to keep a ptr to its context */
96/* External interfaces use first EC only, so remember */
94static struct acpi_ec { 97static struct acpi_ec {
95 acpi_handle handle; 98 acpi_handle handle;
96 unsigned long uid;
97 unsigned long gpe; 99 unsigned long gpe;
98 unsigned long command_addr; 100 unsigned long command_addr;
99 unsigned long data_addr; 101 unsigned long data_addr;
100 unsigned long global_lock; 102 unsigned long global_lock;
101 struct mutex lock; 103 struct mutex lock;
102 atomic_t query_pending; 104 atomic_t query_pending;
103 atomic_t leaving_burst; /* 0 : No, 1 : Yes, 2: abort */ 105 atomic_t event_count;
104 wait_queue_head_t wait; 106 wait_queue_head_t wait;
105} *ec_ecdt; 107} *boot_ec, *first_ec;
106
107/* External interfaces use first EC only, so remember */
108static struct acpi_device *first_ec;
109 108
110/* -------------------------------------------------------------------------- 109/* --------------------------------------------------------------------------
111 Transaction Management 110 Transaction Management
@@ -131,10 +130,12 @@ static inline void acpi_ec_write_data(struct acpi_ec *ec, u8 data)
131 outb(data, ec->data_addr); 130 outb(data, ec->data_addr);
132} 131}
133 132
134static inline int acpi_ec_check_status(struct acpi_ec *ec, enum ec_event event) 133static inline int acpi_ec_check_status(struct acpi_ec *ec, enum ec_event event,
134 unsigned old_count)
135{ 135{
136 u8 status = acpi_ec_read_status(ec); 136 u8 status = acpi_ec_read_status(ec);
137 137 if (old_count == atomic_read(&ec->event_count))
138 return 0;
138 if (event == ACPI_EC_EVENT_OBF_1) { 139 if (event == ACPI_EC_EVENT_OBF_1) {
139 if (status & ACPI_EC_FLAG_OBF) 140 if (status & ACPI_EC_FLAG_OBF)
140 return 1; 141 return 1;
@@ -146,19 +147,19 @@ static inline int acpi_ec_check_status(struct acpi_ec *ec, enum ec_event event)
146 return 0; 147 return 0;
147} 148}
148 149
149static int acpi_ec_wait(struct acpi_ec *ec, enum ec_event event) 150static int acpi_ec_wait(struct acpi_ec *ec, enum ec_event event, unsigned count)
150{ 151{
151 if (acpi_ec_mode == EC_POLL) { 152 if (acpi_ec_mode == EC_POLL) {
152 unsigned long delay = jiffies + msecs_to_jiffies(ACPI_EC_DELAY); 153 unsigned long delay = jiffies + msecs_to_jiffies(ACPI_EC_DELAY);
153 while (time_before(jiffies, delay)) { 154 while (time_before(jiffies, delay)) {
154 if (acpi_ec_check_status(ec, event)) 155 if (acpi_ec_check_status(ec, event, 0))
155 return 0; 156 return 0;
156 } 157 }
157 } else { 158 } else {
158 if (wait_event_timeout(ec->wait, 159 if (wait_event_timeout(ec->wait,
159 acpi_ec_check_status(ec, event), 160 acpi_ec_check_status(ec, event, count),
160 msecs_to_jiffies(ACPI_EC_DELAY)) || 161 msecs_to_jiffies(ACPI_EC_DELAY)) ||
161 acpi_ec_check_status(ec, event)) { 162 acpi_ec_check_status(ec, event, 0)) {
162 return 0; 163 return 0;
163 } else { 164 } else {
164 printk(KERN_ERR PREFIX "acpi_ec_wait timeout," 165 printk(KERN_ERR PREFIX "acpi_ec_wait timeout,"
@@ -170,76 +171,27 @@ static int acpi_ec_wait(struct acpi_ec *ec, enum ec_event event)
170 return -ETIME; 171 return -ETIME;
171} 172}
172 173
173#ifdef ACPI_FUTURE_USAGE
174/*
175 * Note: samsung nv5000 doesn't work with ec burst mode.
176 * http://bugzilla.kernel.org/show_bug.cgi?id=4980
177 */
178int acpi_ec_enter_burst_mode(struct acpi_ec *ec)
179{
180 u8 tmp = 0;
181 u8 status = 0;
182
183 status = acpi_ec_read_status(ec);
184 if (status != -EINVAL && !(status & ACPI_EC_FLAG_BURST)) {
185 status = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0);
186 if (status)
187 goto end;
188 acpi_ec_write_cmd(ec, ACPI_EC_BURST_ENABLE);
189 status = acpi_ec_wait(ec, ACPI_EC_EVENT_OBF_1);
190 tmp = acpi_ec_read_data(ec);
191 if (tmp != 0x90) { /* Burst ACK byte */
192 return -EINVAL;
193 }
194 }
195
196 atomic_set(&ec->leaving_burst, 0);
197 return 0;
198 end:
199 ACPI_EXCEPTION((AE_INFO, status, "EC wait, burst mode"));
200 return -1;
201}
202
203int acpi_ec_leave_burst_mode(struct acpi_ec *ec)
204{
205 u8 status = 0;
206
207 status = acpi_ec_read_status(ec);
208 if (status != -EINVAL && (status & ACPI_EC_FLAG_BURST)) {
209 status = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0);
210 if (status)
211 goto end;
212 acpi_ec_write_cmd(ec, ACPI_EC_BURST_DISABLE);
213 acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0);
214 }
215 atomic_set(&ec->leaving_burst, 1);
216 return 0;
217 end:
218 ACPI_EXCEPTION((AE_INFO, status, "EC leave burst mode"));
219 return -1;
220}
221#endif /* ACPI_FUTURE_USAGE */
222
223static int acpi_ec_transaction_unlocked(struct acpi_ec *ec, u8 command, 174static int acpi_ec_transaction_unlocked(struct acpi_ec *ec, u8 command,
224 const u8 * wdata, unsigned wdata_len, 175 const u8 * wdata, unsigned wdata_len,
225 u8 * rdata, unsigned rdata_len) 176 u8 * rdata, unsigned rdata_len)
226{ 177{
227 int result = 0; 178 int result = 0;
228 179 unsigned count = atomic_read(&ec->event_count);
229 acpi_ec_write_cmd(ec, command); 180 acpi_ec_write_cmd(ec, command);
230 181
231 for (; wdata_len > 0; --wdata_len) { 182 for (; wdata_len > 0; --wdata_len) {
232 result = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0); 183 result = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0, count);
233 if (result) { 184 if (result) {
234 printk(KERN_ERR PREFIX 185 printk(KERN_ERR PREFIX
235 "write_cmd timeout, command = %d\n", command); 186 "write_cmd timeout, command = %d\n", command);
236 goto end; 187 goto end;
237 } 188 }
189 count = atomic_read(&ec->event_count);
238 acpi_ec_write_data(ec, *(wdata++)); 190 acpi_ec_write_data(ec, *(wdata++));
239 } 191 }
240 192
241 if (!rdata_len) { 193 if (!rdata_len) {
242 result = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0); 194 result = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0, count);
243 if (result) { 195 if (result) {
244 printk(KERN_ERR PREFIX 196 printk(KERN_ERR PREFIX
245 "finish-write timeout, command = %d\n", command); 197 "finish-write timeout, command = %d\n", command);
@@ -250,13 +202,13 @@ static int acpi_ec_transaction_unlocked(struct acpi_ec *ec, u8 command,
250 } 202 }
251 203
252 for (; rdata_len > 0; --rdata_len) { 204 for (; rdata_len > 0; --rdata_len) {
253 result = acpi_ec_wait(ec, ACPI_EC_EVENT_OBF_1); 205 result = acpi_ec_wait(ec, ACPI_EC_EVENT_OBF_1, count);
254 if (result) { 206 if (result) {
255 printk(KERN_ERR PREFIX "read timeout, command = %d\n", 207 printk(KERN_ERR PREFIX "read timeout, command = %d\n",
256 command); 208 command);
257 goto end; 209 goto end;
258 } 210 }
259 211 count = atomic_read(&ec->event_count);
260 *(rdata++) = acpi_ec_read_data(ec); 212 *(rdata++) = acpi_ec_read_data(ec);
261 } 213 }
262 end: 214 end:
@@ -288,7 +240,7 @@ static int acpi_ec_transaction(struct acpi_ec *ec, u8 command,
288 /* Make sure GPE is enabled before doing transaction */ 240 /* Make sure GPE is enabled before doing transaction */
289 acpi_enable_gpe(NULL, ec->gpe, ACPI_NOT_ISR); 241 acpi_enable_gpe(NULL, ec->gpe, ACPI_NOT_ISR);
290 242
291 status = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0); 243 status = acpi_ec_wait(ec, ACPI_EC_EVENT_IBF_0, 0);
292 if (status) { 244 if (status) {
293 printk(KERN_DEBUG PREFIX 245 printk(KERN_DEBUG PREFIX
294 "input buffer is not empty, aborting transaction\n"); 246 "input buffer is not empty, aborting transaction\n");
@@ -308,6 +260,21 @@ static int acpi_ec_transaction(struct acpi_ec *ec, u8 command,
308 return status; 260 return status;
309} 261}
310 262
263/*
264 * Note: samsung nv5000 doesn't work with ec burst mode.
265 * http://bugzilla.kernel.org/show_bug.cgi?id=4980
266 */
267int acpi_ec_burst_enable(struct acpi_ec *ec)
268{
269 u8 d;
270 return acpi_ec_transaction(ec, ACPI_EC_BURST_ENABLE, NULL, 0, &d, 1);
271}
272
273int acpi_ec_burst_disable(struct acpi_ec *ec)
274{
275 return acpi_ec_transaction(ec, ACPI_EC_BURST_DISABLE, NULL, 0, NULL, 0);
276}
277
311static int acpi_ec_read(struct acpi_ec *ec, u8 address, u8 * data) 278static int acpi_ec_read(struct acpi_ec *ec, u8 address, u8 * data)
312{ 279{
313 int result; 280 int result;
@@ -329,18 +296,33 @@ static int acpi_ec_write(struct acpi_ec *ec, u8 address, u8 data)
329/* 296/*
330 * Externally callable EC access functions. For now, assume 1 EC only 297 * Externally callable EC access functions. For now, assume 1 EC only
331 */ 298 */
299int ec_burst_enable(void)
300{
301 if (!first_ec)
302 return -ENODEV;
303 return acpi_ec_burst_enable(first_ec);
304}
305
306EXPORT_SYMBOL(ec_burst_enable);
307
308int ec_burst_disable(void)
309{
310 if (!first_ec)
311 return -ENODEV;
312 return acpi_ec_burst_disable(first_ec);
313}
314
315EXPORT_SYMBOL(ec_burst_disable);
316
332int ec_read(u8 addr, u8 * val) 317int ec_read(u8 addr, u8 * val)
333{ 318{
334 struct acpi_ec *ec;
335 int err; 319 int err;
336 u8 temp_data; 320 u8 temp_data;
337 321
338 if (!first_ec) 322 if (!first_ec)
339 return -ENODEV; 323 return -ENODEV;
340 324
341 ec = acpi_driver_data(first_ec); 325 err = acpi_ec_read(first_ec, addr, &temp_data);
342
343 err = acpi_ec_read(ec, addr, &temp_data);
344 326
345 if (!err) { 327 if (!err) {
346 *val = temp_data; 328 *val = temp_data;
@@ -353,15 +335,12 @@ EXPORT_SYMBOL(ec_read);
353 335
354int ec_write(u8 addr, u8 val) 336int ec_write(u8 addr, u8 val)
355{ 337{
356 struct acpi_ec *ec;
357 int err; 338 int err;
358 339
359 if (!first_ec) 340 if (!first_ec)
360 return -ENODEV; 341 return -ENODEV;
361 342
362 ec = acpi_driver_data(first_ec); 343 err = acpi_ec_write(first_ec, addr, val);
363
364 err = acpi_ec_write(ec, addr, val);
365 344
366 return err; 345 return err;
367} 346}
@@ -369,17 +348,13 @@ int ec_write(u8 addr, u8 val)
369EXPORT_SYMBOL(ec_write); 348EXPORT_SYMBOL(ec_write);
370 349
371int ec_transaction(u8 command, 350int ec_transaction(u8 command,
372 const u8 * wdata, unsigned wdata_len, 351 const u8 * wdata, unsigned wdata_len,
373 u8 * rdata, unsigned rdata_len) 352 u8 * rdata, unsigned rdata_len)
374{ 353{
375 struct acpi_ec *ec;
376
377 if (!first_ec) 354 if (!first_ec)
378 return -ENODEV; 355 return -ENODEV;
379 356
380 ec = acpi_driver_data(first_ec); 357 return acpi_ec_transaction(first_ec, command, wdata,
381
382 return acpi_ec_transaction(ec, command, wdata,
383 wdata_len, rdata, rdata_len); 358 wdata_len, rdata, rdata_len);
384} 359}
385 360
@@ -416,7 +391,7 @@ static int acpi_ec_query(struct acpi_ec *ec, u8 * data)
416 391
417static void acpi_ec_gpe_query(void *ec_cxt) 392static void acpi_ec_gpe_query(void *ec_cxt)
418{ 393{
419 struct acpi_ec *ec = (struct acpi_ec *)ec_cxt; 394 struct acpi_ec *ec = ec_cxt;
420 u8 value = 0; 395 u8 value = 0;
421 char object_name[8]; 396 char object_name[8];
422 397
@@ -434,7 +409,8 @@ static u32 acpi_ec_gpe_handler(void *data)
434{ 409{
435 acpi_status status = AE_OK; 410 acpi_status status = AE_OK;
436 u8 value; 411 u8 value;
437 struct acpi_ec *ec = (struct acpi_ec *)data; 412 struct acpi_ec *ec = data;
413 atomic_inc(&ec->event_count);
438 414
439 if (acpi_ec_mode == EC_INTR) { 415 if (acpi_ec_mode == EC_INTR) {
440 wake_up(&ec->wait); 416 wake_up(&ec->wait);
@@ -478,7 +454,7 @@ acpi_ec_space_handler(u32 function,
478 void *handler_context, void *region_context) 454 void *handler_context, void *region_context)
479{ 455{
480 int result = 0; 456 int result = 0;
481 struct acpi_ec *ec = NULL; 457 struct acpi_ec *ec = handler_context;
482 u64 temp = *value; 458 u64 temp = *value;
483 acpi_integer f_v = 0; 459 acpi_integer f_v = 0;
484 int i = 0; 460 int i = 0;
@@ -490,8 +466,6 @@ acpi_ec_space_handler(u32 function,
490 return AE_BAD_PARAMETER; 466 return AE_BAD_PARAMETER;
491 } 467 }
492 468
493 ec = (struct acpi_ec *)handler_context;
494
495 next_byte: 469 next_byte:
496 switch (function) { 470 switch (function) {
497 case ACPI_READ: 471 case ACPI_READ:
@@ -547,18 +521,16 @@ static struct proc_dir_entry *acpi_ec_dir;
547 521
548static int acpi_ec_read_info(struct seq_file *seq, void *offset) 522static int acpi_ec_read_info(struct seq_file *seq, void *offset)
549{ 523{
550 struct acpi_ec *ec = (struct acpi_ec *)seq->private; 524 struct acpi_ec *ec = seq->private;
551 525
552 if (!ec) 526 if (!ec)
553 goto end; 527 goto end;
554 528
555 seq_printf(seq, "gpe: 0x%02x\n", (u32) ec->gpe); 529 seq_printf(seq, "gpe:\t\t\t0x%02x\n", (u32) ec->gpe);
556 seq_printf(seq, "ports: 0x%02x, 0x%02x\n", 530 seq_printf(seq, "ports:\t\t\t0x%02x, 0x%02x\n",
557 (u32) ec->command_addr, (u32) ec->data_addr); 531 (unsigned)ec->command_addr, (unsigned)ec->data_addr);
558 seq_printf(seq, "use global lock: %s\n", 532 seq_printf(seq, "use global lock:\t%s\n",
559 ec->global_lock ? "yes" : "no"); 533 ec->global_lock ? "yes" : "no");
560 acpi_enable_gpe(NULL, ec->gpe, ACPI_NOT_ISR);
561
562 end: 534 end:
563 return 0; 535 return 0;
564} 536}
@@ -615,153 +587,122 @@ static int acpi_ec_remove_fs(struct acpi_device *device)
615/* -------------------------------------------------------------------------- 587/* --------------------------------------------------------------------------
616 Driver Interface 588 Driver Interface
617 -------------------------------------------------------------------------- */ 589 -------------------------------------------------------------------------- */
590static acpi_status
591ec_parse_io_ports(struct acpi_resource *resource, void *context);
592
593static acpi_status
594ec_parse_device(acpi_handle handle, u32 Level, void *context, void **retval);
595
596static struct acpi_ec *make_acpi_ec(void)
597{
598 struct acpi_ec *ec = kzalloc(sizeof(struct acpi_ec), GFP_KERNEL);
599 if (!ec)
600 return NULL;
601
602 atomic_set(&ec->query_pending, 1);
603 atomic_set(&ec->event_count, 1);
604 mutex_init(&ec->lock);
605 init_waitqueue_head(&ec->wait);
606
607 return ec;
608}
618 609
619static int acpi_ec_add(struct acpi_device *device) 610static int acpi_ec_add(struct acpi_device *device)
620{ 611{
621 int result = 0;
622 acpi_status status = AE_OK; 612 acpi_status status = AE_OK;
623 struct acpi_ec *ec = NULL; 613 struct acpi_ec *ec = NULL;
624 614
625 if (!device) 615 if (!device)
626 return -EINVAL; 616 return -EINVAL;
627 617
628 ec = kzalloc(sizeof(struct acpi_ec), GFP_KERNEL);
629 if (!ec)
630 return -ENOMEM;
631
632 ec->handle = device->handle;
633 ec->uid = -1;
634 mutex_init(&ec->lock);
635 atomic_set(&ec->query_pending, 0);
636 if (acpi_ec_mode == EC_INTR) {
637 atomic_set(&ec->leaving_burst, 1);
638 init_waitqueue_head(&ec->wait);
639 }
640 strcpy(acpi_device_name(device), ACPI_EC_DEVICE_NAME); 618 strcpy(acpi_device_name(device), ACPI_EC_DEVICE_NAME);
641 strcpy(acpi_device_class(device), ACPI_EC_CLASS); 619 strcpy(acpi_device_class(device), ACPI_EC_CLASS);
642 acpi_driver_data(device) = ec;
643
644 /* Use the global lock for all EC transactions? */
645 acpi_evaluate_integer(ec->handle, "_GLK", NULL, &ec->global_lock);
646
647 /* XXX we don't test uids, because on some boxes ecdt uid = 0, see:
648 http://bugzilla.kernel.org/show_bug.cgi?id=6111 */
649 if (ec_ecdt) {
650 acpi_remove_address_space_handler(ACPI_ROOT_OBJECT,
651 ACPI_ADR_SPACE_EC,
652 &acpi_ec_space_handler);
653 620
654 acpi_remove_gpe_handler(NULL, ec_ecdt->gpe, 621 ec = make_acpi_ec();
655 &acpi_ec_gpe_handler); 622 if (!ec)
623 return -ENOMEM;
656 624
657 kfree(ec_ecdt); 625 status = ec_parse_device(device->handle, 0, ec, NULL);
626 if (status != AE_CTRL_TERMINATE) {
627 kfree(ec);
628 return -EINVAL;
658 } 629 }
659 630
660 /* Get GPE bit assignment (EC events). */ 631 /* Check if we found the boot EC */
661 /* TODO: Add support for _GPE returning a package */ 632 if (boot_ec) {
662 status = acpi_evaluate_integer(ec->handle, "_GPE", NULL, &ec->gpe); 633 if (boot_ec->gpe == ec->gpe) {
663 if (ACPI_FAILURE(status)) { 634 /* We might have incorrect info for GL at boot time */
664 ACPI_EXCEPTION((AE_INFO, status, 635 mutex_lock(&boot_ec->lock);
665 "Obtaining GPE bit assignment")); 636 boot_ec->global_lock = ec->global_lock;
666 result = -ENODEV; 637 mutex_unlock(&boot_ec->lock);
667 goto end; 638 kfree(ec);
668 } 639 ec = boot_ec;
640 }
641 } else
642 first_ec = ec;
643 ec->handle = device->handle;
644 acpi_driver_data(device) = ec;
669 645
670 result = acpi_ec_add_fs(device); 646 acpi_ec_add_fs(device);
671 if (result)
672 goto end;
673 647
674 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "%s [%s] (gpe %d) interrupt mode.", 648 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "%s [%s] (gpe %d) interrupt mode.",
675 acpi_device_name(device), acpi_device_bid(device), 649 acpi_device_name(device), acpi_device_bid(device),
676 (u32) ec->gpe)); 650 (u32) ec->gpe));
677 651
678 if (!first_ec) 652 return 0;
679 first_ec = device;
680
681 end:
682 if (result)
683 kfree(ec);
684
685 return result;
686} 653}
687 654
688static int acpi_ec_remove(struct acpi_device *device, int type) 655static int acpi_ec_remove(struct acpi_device *device, int type)
689{ 656{
690 struct acpi_ec *ec = NULL; 657 struct acpi_ec *ec;
691 658
692 if (!device) 659 if (!device)
693 return -EINVAL; 660 return -EINVAL;
694 661
695 ec = acpi_driver_data(device); 662 ec = acpi_driver_data(device);
696
697 acpi_ec_remove_fs(device); 663 acpi_ec_remove_fs(device);
664 acpi_driver_data(device) = NULL;
665 if (ec == first_ec)
666 first_ec = NULL;
698 667
699 kfree(ec); 668 /* Don't touch boot EC */
700 669 if (boot_ec != ec)
670 kfree(ec);
701 return 0; 671 return 0;
702} 672}
703 673
704static acpi_status 674static acpi_status
705acpi_ec_io_ports(struct acpi_resource *resource, void *context) 675ec_parse_io_ports(struct acpi_resource *resource, void *context)
706{ 676{
707 struct acpi_ec *ec = (struct acpi_ec *)context; 677 struct acpi_ec *ec = context;
708 678
709 if (resource->type != ACPI_RESOURCE_TYPE_IO) { 679 if (resource->type != ACPI_RESOURCE_TYPE_IO)
710 return AE_OK; 680 return AE_OK;
711 }
712 681
713 /* 682 /*
714 * The first address region returned is the data port, and 683 * The first address region returned is the data port, and
715 * the second address region returned is the status/command 684 * the second address region returned is the status/command
716 * port. 685 * port.
717 */ 686 */
718 if (ec->data_addr == 0) { 687 if (ec->data_addr == 0)
719 ec->data_addr = resource->data.io.minimum; 688 ec->data_addr = resource->data.io.minimum;
720 } else if (ec->command_addr == 0) { 689 else if (ec->command_addr == 0)
721 ec->command_addr = resource->data.io.minimum; 690 ec->command_addr = resource->data.io.minimum;
722 } else { 691 else
723 return AE_CTRL_TERMINATE; 692 return AE_CTRL_TERMINATE;
724 }
725 693
726 return AE_OK; 694 return AE_OK;
727} 695}
728 696
729static int acpi_ec_start(struct acpi_device *device) 697static int ec_install_handlers(struct acpi_ec *ec)
730{ 698{
731 acpi_status status = AE_OK; 699 acpi_status status;
732 struct acpi_ec *ec = NULL;
733
734 if (!device)
735 return -EINVAL;
736
737 ec = acpi_driver_data(device);
738
739 if (!ec)
740 return -EINVAL;
741
742 /*
743 * Get I/O port addresses. Convert to GAS format.
744 */
745 status = acpi_walk_resources(ec->handle, METHOD_NAME__CRS,
746 acpi_ec_io_ports, ec);
747 if (ACPI_FAILURE(status) || ec->command_addr == 0) {
748 ACPI_EXCEPTION((AE_INFO, status,
749 "Error getting I/O port addresses"));
750 return -ENODEV;
751 }
752
753 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "gpe=0x%02lx, ports=0x%2lx,0x%2lx",
754 ec->gpe, ec->command_addr, ec->data_addr));
755
756 /*
757 * Install GPE handler
758 */
759 status = acpi_install_gpe_handler(NULL, ec->gpe, 700 status = acpi_install_gpe_handler(NULL, ec->gpe,
760 ACPI_GPE_EDGE_TRIGGERED, 701 ACPI_GPE_EDGE_TRIGGERED,
761 &acpi_ec_gpe_handler, ec); 702 &acpi_ec_gpe_handler, ec);
762 if (ACPI_FAILURE(status)) { 703 if (ACPI_FAILURE(status))
763 return -ENODEV; 704 return -ENODEV;
764 } 705
765 acpi_set_gpe_type(NULL, ec->gpe, ACPI_GPE_TYPE_RUNTIME); 706 acpi_set_gpe_type(NULL, ec->gpe, ACPI_GPE_TYPE_RUNTIME);
766 acpi_enable_gpe(NULL, ec->gpe, ACPI_NOT_ISR); 707 acpi_enable_gpe(NULL, ec->gpe, ACPI_NOT_ISR);
767 708
@@ -774,18 +715,49 @@ static int acpi_ec_start(struct acpi_device *device)
774 return -ENODEV; 715 return -ENODEV;
775 } 716 }
776 717
777 return AE_OK; 718 /* EC is fully operational, allow queries */
719 atomic_set(&ec->query_pending, 0);
720
721 return 0;
722}
723
724static int acpi_ec_start(struct acpi_device *device)
725{
726 struct acpi_ec *ec;
727
728 if (!device)
729 return -EINVAL;
730
731 ec = acpi_driver_data(device);
732
733 if (!ec)
734 return -EINVAL;
735
736 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "gpe=0x%02lx, ports=0x%2lx,0x%2lx",
737 ec->gpe, ec->command_addr, ec->data_addr));
738
739 /* Boot EC is already working */
740 if (ec == boot_ec)
741 return 0;
742
743 return ec_install_handlers(ec);
778} 744}
779 745
780static int acpi_ec_stop(struct acpi_device *device, int type) 746static int acpi_ec_stop(struct acpi_device *device, int type)
781{ 747{
782 acpi_status status = AE_OK; 748 acpi_status status;
783 struct acpi_ec *ec = NULL; 749 struct acpi_ec *ec;
784 750
785 if (!device) 751 if (!device)
786 return -EINVAL; 752 return -EINVAL;
787 753
788 ec = acpi_driver_data(device); 754 ec = acpi_driver_data(device);
755 if (!ec)
756 return -EINVAL;
757
758 /* Don't touch boot EC */
759 if (ec == boot_ec)
760 return 0;
789 761
790 status = acpi_remove_address_space_handler(ec->handle, 762 status = acpi_remove_address_space_handler(ec->handle,
791 ACPI_ADR_SPACE_EC, 763 ACPI_ADR_SPACE_EC,
@@ -800,162 +772,67 @@ static int acpi_ec_stop(struct acpi_device *device, int type)
800 return 0; 772 return 0;
801} 773}
802 774
803static acpi_status __init 775static acpi_status
804acpi_fake_ecdt_callback(acpi_handle handle, 776ec_parse_device(acpi_handle handle, u32 Level, void *context, void **retval)
805 u32 Level, void *context, void **retval)
806{ 777{
807 acpi_status status; 778 acpi_status status;
808 779
809 mutex_init(&ec_ecdt->lock); 780 struct acpi_ec *ec = context;
810 if (acpi_ec_mode == EC_INTR) {
811 init_waitqueue_head(&ec_ecdt->wait);
812 }
813 status = acpi_walk_resources(handle, METHOD_NAME__CRS, 781 status = acpi_walk_resources(handle, METHOD_NAME__CRS,
814 acpi_ec_io_ports, ec_ecdt); 782 ec_parse_io_ports, ec);
815 if (ACPI_FAILURE(status)) 783 if (ACPI_FAILURE(status))
816 return status; 784 return status;
817 785
818 ec_ecdt->uid = -1; 786 /* Get GPE bit assignment (EC events). */
819 acpi_evaluate_integer(handle, "_UID", NULL, &ec_ecdt->uid); 787 /* TODO: Add support for _GPE returning a package */
820 788 status = acpi_evaluate_integer(handle, "_GPE", NULL, &ec->gpe);
821 status = acpi_evaluate_integer(handle, "_GPE", NULL, &ec_ecdt->gpe);
822 if (ACPI_FAILURE(status)) 789 if (ACPI_FAILURE(status))
823 return status; 790 return status;
824 ec_ecdt->global_lock = TRUE;
825 ec_ecdt->handle = handle;
826
827 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "GPE=0x%02lx, ports=0x%2lx, 0x%2lx",
828 ec_ecdt->gpe, ec_ecdt->command_addr,
829 ec_ecdt->data_addr));
830 791
831 return AE_CTRL_TERMINATE; 792 /* Use the global lock for all EC transactions? */
832} 793 acpi_evaluate_integer(handle, "_GLK", NULL, &ec->global_lock);
833
834/*
835 * Some BIOS (such as some from Gateway laptops) access EC region very early
836 * such as in BAT0._INI or EC._INI before an EC device is found and
837 * do not provide an ECDT. According to ACPI spec, ECDT isn't mandatorily
838 * required, but if EC regison is accessed early, it is required.
839 * The routine tries to workaround the BIOS bug by pre-scan EC device
840 * It assumes that _CRS, _HID, _GPE, _UID methods of EC don't touch any
841 * op region (since _REG isn't invoked yet). The assumption is true for
842 * all systems found.
843 */
844static int __init acpi_ec_fake_ecdt(void)
845{
846 acpi_status status;
847 int ret = 0;
848 794
849 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Try to make an fake ECDT")); 795 ec->handle = handle;
850 796
851 ec_ecdt = kzalloc(sizeof(struct acpi_ec), GFP_KERNEL); 797 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "GPE=0x%02lx, ports=0x%2lx, 0x%2lx",
852 if (!ec_ecdt) { 798 ec->gpe, ec->command_addr, ec->data_addr));
853 ret = -ENOMEM;
854 goto error;
855 }
856 799
857 status = acpi_get_devices(ACPI_EC_HID, 800 return AE_CTRL_TERMINATE;
858 acpi_fake_ecdt_callback, NULL, NULL);
859 if (ACPI_FAILURE(status)) {
860 kfree(ec_ecdt);
861 ec_ecdt = NULL;
862 ret = -ENODEV;
863 ACPI_EXCEPTION((AE_INFO, status, "Can't make an fake ECDT"));
864 goto error;
865 }
866 return 0;
867 error:
868 return ret;
869} 801}
870 802
871static int __init acpi_ec_get_real_ecdt(void) 803int __init acpi_ec_ecdt_probe(void)
872{ 804{
805 int ret;
873 acpi_status status; 806 acpi_status status;
874 struct acpi_table_ecdt *ecdt_ptr; 807 struct acpi_table_ecdt *ecdt_ptr;
875 808
876 status = acpi_get_table(ACPI_SIG_ECDT, 1, 809 boot_ec = make_acpi_ec();
877 (struct acpi_table_header **)&ecdt_ptr); 810 if (!boot_ec)
878 if (ACPI_FAILURE(status)) 811 return -ENOMEM;
879 return -ENODEV;
880
881 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Found ECDT"));
882
883 /* 812 /*
884 * Generate a temporary ec context to use until the namespace is scanned 813 * Generate a boot ec context
885 */ 814 */
886 ec_ecdt = kzalloc(sizeof(struct acpi_ec), GFP_KERNEL);
887 if (!ec_ecdt)
888 return -ENOMEM;
889 815
890 mutex_init(&ec_ecdt->lock); 816 status = acpi_get_table(ACPI_SIG_ECDT, 1,
891 if (acpi_ec_mode == EC_INTR) { 817 (struct acpi_table_header **)&ecdt_ptr);
892 init_waitqueue_head(&ec_ecdt->wait); 818 if (ACPI_FAILURE(status))
893 }
894 ec_ecdt->command_addr = ecdt_ptr->control.address;
895 ec_ecdt->data_addr = ecdt_ptr->data.address;
896 ec_ecdt->gpe = ecdt_ptr->gpe;
897 /* use the GL just to be safe */
898 ec_ecdt->global_lock = TRUE;
899 ec_ecdt->uid = ecdt_ptr->uid;
900
901 status = acpi_get_handle(NULL, ecdt_ptr->id, &ec_ecdt->handle);
902 if (ACPI_FAILURE(status)) {
903 goto error; 819 goto error;
904 }
905
906 return 0;
907 error:
908 ACPI_EXCEPTION((AE_INFO, status, "Could not use ECDT"));
909 kfree(ec_ecdt);
910 ec_ecdt = NULL;
911 820
912 return -ENODEV; 821 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Found ECDT"));
913}
914
915static int __initdata acpi_fake_ecdt_enabled;
916int __init acpi_ec_ecdt_probe(void)
917{
918 acpi_status status;
919 int ret;
920 822
921 ret = acpi_ec_get_real_ecdt(); 823 boot_ec->command_addr = ecdt_ptr->control.address;
922 /* Try to make a fake ECDT */ 824 boot_ec->data_addr = ecdt_ptr->data.address;
923 if (ret && acpi_fake_ecdt_enabled) { 825 boot_ec->gpe = ecdt_ptr->gpe;
924 ret = acpi_ec_fake_ecdt(); 826 boot_ec->handle = ACPI_ROOT_OBJECT;
925 }
926 827
927 if (ret) 828 ret = ec_install_handlers(boot_ec);
829 if (!ret) {
830 first_ec = boot_ec;
928 return 0; 831 return 0;
929
930 /*
931 * Install GPE handler
932 */
933 status = acpi_install_gpe_handler(NULL, ec_ecdt->gpe,
934 ACPI_GPE_EDGE_TRIGGERED,
935 &acpi_ec_gpe_handler, ec_ecdt);
936 if (ACPI_FAILURE(status)) {
937 goto error;
938 } 832 }
939 acpi_set_gpe_type(NULL, ec_ecdt->gpe, ACPI_GPE_TYPE_RUNTIME);
940 acpi_enable_gpe(NULL, ec_ecdt->gpe, ACPI_NOT_ISR);
941
942 status = acpi_install_address_space_handler(ACPI_ROOT_OBJECT,
943 ACPI_ADR_SPACE_EC,
944 &acpi_ec_space_handler,
945 &acpi_ec_space_setup,
946 ec_ecdt);
947 if (ACPI_FAILURE(status)) {
948 acpi_remove_gpe_handler(NULL, ec_ecdt->gpe,
949 &acpi_ec_gpe_handler);
950 goto error;
951 }
952
953 return 0;
954
955 error: 833 error:
956 ACPI_EXCEPTION((AE_INFO, status, "Could not use ECDT")); 834 kfree(boot_ec);
957 kfree(ec_ecdt); 835 boot_ec = NULL;
958 ec_ecdt = NULL;
959 836
960 return -ENODEV; 837 return -ENODEV;
961} 838}
@@ -996,13 +873,6 @@ static void __exit acpi_ec_exit(void)
996} 873}
997#endif /* 0 */ 874#endif /* 0 */
998 875
999static int __init acpi_fake_ecdt_setup(char *str)
1000{
1001 acpi_fake_ecdt_enabled = 1;
1002 return 1;
1003}
1004
1005__setup("acpi_fake_ecdt", acpi_fake_ecdt_setup);
1006static int __init acpi_ec_set_intr_mode(char *str) 876static int __init acpi_ec_set_intr_mode(char *str)
1007{ 877{
1008 int intr; 878 int intr;
@@ -1010,14 +880,9 @@ static int __init acpi_ec_set_intr_mode(char *str)
1010 if (!get_option(&str, &intr)) 880 if (!get_option(&str, &intr))
1011 return 0; 881 return 0;
1012 882
1013 if (intr) { 883 acpi_ec_mode = (intr) ? EC_INTR : EC_POLL;
1014 acpi_ec_mode = EC_INTR; 884
1015 } else { 885 printk(KERN_NOTICE PREFIX "%s mode.\n", intr ? "interrupt" : "polling");
1016 acpi_ec_mode = EC_POLL;
1017 }
1018 acpi_ec_driver.ops.add = acpi_ec_add;
1019 printk(KERN_NOTICE PREFIX "%s mode.\n",
1020 intr ? "interrupt" : "polling");
1021 886
1022 return 1; 887 return 1;
1023} 888}
diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c
index d572700197f3..cae786ca8600 100644
--- a/drivers/acpi/events/evmisc.c
+++ b/drivers/acpi/events/evmisc.c
@@ -196,11 +196,15 @@ acpi_ev_queue_notify_request(struct acpi_namespace_node * node,
196 notify_info->notify.value = (u16) notify_value; 196 notify_info->notify.value = (u16) notify_value;
197 notify_info->notify.handler_obj = handler_obj; 197 notify_info->notify.handler_obj = handler_obj;
198 198
199 acpi_ex_relinquish_interpreter(); 199 acpi_ex_exit_interpreter();
200 200
201 acpi_ev_notify_dispatch(notify_info); 201 acpi_ev_notify_dispatch(notify_info);
202 202
203 acpi_ex_reacquire_interpreter(); 203 status = acpi_ex_enter_interpreter();
204 if (ACPI_FAILURE(status)) {
205 return_ACPI_STATUS(status);
206 }
207
204 } 208 }
205 209
206 if (!handler_obj) { 210 if (!handler_obj) {
@@ -423,6 +427,8 @@ static acpi_status acpi_ev_remove_global_lock_handler(void)
423 * the global lock appear as a standard mutex on the OS side. 427 * the global lock appear as a standard mutex on the OS side.
424 * 428 *
425 *****************************************************************************/ 429 *****************************************************************************/
430static acpi_thread_id acpi_ev_global_lock_thread_id;
431static int acpi_ev_global_lock_acquired;
426 432
427acpi_status acpi_ev_acquire_global_lock(u16 timeout) 433acpi_status acpi_ev_acquire_global_lock(u16 timeout)
428{ 434{
@@ -435,11 +441,24 @@ acpi_status acpi_ev_acquire_global_lock(u16 timeout)
435 * Only one thread can acquire the GL at a time, the global_lock_mutex 441 * Only one thread can acquire the GL at a time, the global_lock_mutex
436 * enforces this. This interface releases the interpreter if we must wait. 442 * enforces this. This interface releases the interpreter if we must wait.
437 */ 443 */
438 status = acpi_ex_system_wait_mutex(acpi_gbl_global_lock_mutex, timeout); 444 status = acpi_ex_system_wait_mutex(acpi_gbl_global_lock_mutex, 0);
445 if (status == AE_TIME) {
446 if (acpi_ev_global_lock_thread_id == acpi_os_get_thread_id()) {
447 acpi_ev_global_lock_acquired++;
448 return AE_OK;
449 }
450 }
451
452 if (ACPI_FAILURE(status)) {
453 status = acpi_ex_system_wait_mutex(acpi_gbl_global_lock_mutex, timeout);
454 }
439 if (ACPI_FAILURE(status)) { 455 if (ACPI_FAILURE(status)) {
440 return_ACPI_STATUS(status); 456 return_ACPI_STATUS(status);
441 } 457 }
442 458
459 acpi_ev_global_lock_thread_id = acpi_os_get_thread_id();
460 acpi_ev_global_lock_acquired++;
461
443 /* 462 /*
444 * Make sure that a global lock actually exists. If not, just treat 463 * Make sure that a global lock actually exists. If not, just treat
445 * the lock as a standard mutex. 464 * the lock as a standard mutex.
@@ -506,6 +525,11 @@ acpi_status acpi_ev_release_global_lock(void)
506 return_ACPI_STATUS(AE_NOT_ACQUIRED); 525 return_ACPI_STATUS(AE_NOT_ACQUIRED);
507 } 526 }
508 527
528 acpi_ev_global_lock_acquired--;
529 if (acpi_ev_global_lock_acquired > 0) {
530 return AE_OK;
531 }
532
509 if (acpi_gbl_global_lock_present) { 533 if (acpi_gbl_global_lock_present) {
510 534
511 /* Allow any thread to release the lock */ 535 /* Allow any thread to release the lock */
@@ -529,7 +553,8 @@ acpi_status acpi_ev_release_global_lock(void)
529 acpi_gbl_global_lock_acquired = FALSE; 553 acpi_gbl_global_lock_acquired = FALSE;
530 554
531 /* Release the local GL mutex */ 555 /* Release the local GL mutex */
532 556 acpi_ev_global_lock_thread_id = NULL;
557 acpi_ev_global_lock_acquired = 0;
533 acpi_os_release_mutex(acpi_gbl_global_lock_mutex); 558 acpi_os_release_mutex(acpi_gbl_global_lock_mutex);
534 return_ACPI_STATUS(status); 559 return_ACPI_STATUS(status);
535} 560}
diff --git a/drivers/acpi/events/evregion.c b/drivers/acpi/events/evregion.c
index e99f0c435a47..96b0e8431748 100644
--- a/drivers/acpi/events/evregion.c
+++ b/drivers/acpi/events/evregion.c
@@ -291,6 +291,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj,
291 u32 bit_width, acpi_integer * value) 291 u32 bit_width, acpi_integer * value)
292{ 292{
293 acpi_status status; 293 acpi_status status;
294 acpi_status status2;
294 acpi_adr_space_handler handler; 295 acpi_adr_space_handler handler;
295 acpi_adr_space_setup region_setup; 296 acpi_adr_space_setup region_setup;
296 union acpi_operand_object *handler_desc; 297 union acpi_operand_object *handler_desc;
@@ -344,7 +345,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj,
344 * setup will potentially execute control methods 345 * setup will potentially execute control methods
345 * (e.g., _REG method for this region) 346 * (e.g., _REG method for this region)
346 */ 347 */
347 acpi_ex_relinquish_interpreter(); 348 acpi_ex_exit_interpreter();
348 349
349 status = region_setup(region_obj, ACPI_REGION_ACTIVATE, 350 status = region_setup(region_obj, ACPI_REGION_ACTIVATE,
350 handler_desc->address_space.context, 351 handler_desc->address_space.context,
@@ -352,7 +353,10 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj,
352 353
353 /* Re-enter the interpreter */ 354 /* Re-enter the interpreter */
354 355
355 acpi_ex_reacquire_interpreter(); 356 status2 = acpi_ex_enter_interpreter();
357 if (ACPI_FAILURE(status2)) {
358 return_ACPI_STATUS(status2);
359 }
356 360
357 /* Check for failure of the Region Setup */ 361 /* Check for failure of the Region Setup */
358 362
@@ -405,7 +409,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj,
405 * exit the interpreter because the handler *might* block -- we don't 409 * exit the interpreter because the handler *might* block -- we don't
406 * know what it will do, so we can't hold the lock on the intepreter. 410 * know what it will do, so we can't hold the lock on the intepreter.
407 */ 411 */
408 acpi_ex_relinquish_interpreter(); 412 acpi_ex_exit_interpreter();
409 } 413 }
410 414
411 /* Call the handler */ 415 /* Call the handler */
@@ -426,7 +430,10 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj,
426 * We just returned from a non-default handler, we must re-enter the 430 * We just returned from a non-default handler, we must re-enter the
427 * interpreter 431 * interpreter
428 */ 432 */
429 acpi_ex_reacquire_interpreter(); 433 status2 = acpi_ex_enter_interpreter();
434 if (ACPI_FAILURE(status2)) {
435 return_ACPI_STATUS(status2);
436 }
430 } 437 }
431 438
432 return_ACPI_STATUS(status); 439 return_ACPI_STATUS(status);
diff --git a/drivers/acpi/events/evxface.c b/drivers/acpi/events/evxface.c
index 685a103a3587..a3379bafa676 100644
--- a/drivers/acpi/events/evxface.c
+++ b/drivers/acpi/events/evxface.c
@@ -768,9 +768,11 @@ acpi_status acpi_acquire_global_lock(u16 timeout, u32 * handle)
768 return (AE_BAD_PARAMETER); 768 return (AE_BAD_PARAMETER);
769 } 769 }
770 770
771 /* Must lock interpreter to prevent race conditions */ 771 status = acpi_ex_enter_interpreter();
772 if (ACPI_FAILURE(status)) {
773 return (status);
774 }
772 775
773 acpi_ex_enter_interpreter();
774 status = acpi_ev_acquire_global_lock(timeout); 776 status = acpi_ev_acquire_global_lock(timeout);
775 acpi_ex_exit_interpreter(); 777 acpi_ex_exit_interpreter();
776 778
diff --git a/drivers/acpi/executer/excreate.c b/drivers/acpi/executer/excreate.c
index 7c38528a7e83..ae97812681a3 100644
--- a/drivers/acpi/executer/excreate.c
+++ b/drivers/acpi/executer/excreate.c
@@ -583,7 +583,10 @@ acpi_ex_create_method(u8 * aml_start,
583 * Get the sync_level. If method is serialized, a mutex will be 583 * Get the sync_level. If method is serialized, a mutex will be
584 * created for this method when it is parsed. 584 * created for this method when it is parsed.
585 */ 585 */
586 if (method_flags & AML_METHOD_SERIALIZED) { 586 if (acpi_gbl_all_methods_serialized) {
587 obj_desc->method.sync_level = 0;
588 obj_desc->method.method_flags |= AML_METHOD_SERIALIZED;
589 } else if (method_flags & AML_METHOD_SERIALIZED) {
587 /* 590 /*
588 * ACPI 1.0: sync_level = 0 591 * ACPI 1.0: sync_level = 0
589 * ACPI 2.0: sync_level = sync_level in method declaration 592 * ACPI 2.0: sync_level = sync_level in method declaration
diff --git a/drivers/acpi/executer/exsystem.c b/drivers/acpi/executer/exsystem.c
index 9460baff3032..b2edf620ba89 100644
--- a/drivers/acpi/executer/exsystem.c
+++ b/drivers/acpi/executer/exsystem.c
@@ -66,6 +66,7 @@ ACPI_MODULE_NAME("exsystem")
66acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout) 66acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout)
67{ 67{
68 acpi_status status; 68 acpi_status status;
69 acpi_status status2;
69 70
70 ACPI_FUNCTION_TRACE(ex_system_wait_semaphore); 71 ACPI_FUNCTION_TRACE(ex_system_wait_semaphore);
71 72
@@ -78,7 +79,7 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout)
78 79
79 /* We must wait, so unlock the interpreter */ 80 /* We must wait, so unlock the interpreter */
80 81
81 acpi_ex_relinquish_interpreter(); 82 acpi_ex_exit_interpreter();
82 83
83 status = acpi_os_wait_semaphore(semaphore, 1, timeout); 84 status = acpi_os_wait_semaphore(semaphore, 1, timeout);
84 85
@@ -88,7 +89,13 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout)
88 89
89 /* Reacquire the interpreter */ 90 /* Reacquire the interpreter */
90 91
91 acpi_ex_reacquire_interpreter(); 92 status2 = acpi_ex_enter_interpreter();
93 if (ACPI_FAILURE(status2)) {
94
95 /* Report fatal error, could not acquire interpreter */
96
97 return_ACPI_STATUS(status2);
98 }
92 } 99 }
93 100
94 return_ACPI_STATUS(status); 101 return_ACPI_STATUS(status);
@@ -112,6 +119,7 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout)
112acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout) 119acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout)
113{ 120{
114 acpi_status status; 121 acpi_status status;
122 acpi_status status2;
115 123
116 ACPI_FUNCTION_TRACE(ex_system_wait_mutex); 124 ACPI_FUNCTION_TRACE(ex_system_wait_mutex);
117 125
@@ -124,7 +132,7 @@ acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout)
124 132
125 /* We must wait, so unlock the interpreter */ 133 /* We must wait, so unlock the interpreter */
126 134
127 acpi_ex_relinquish_interpreter(); 135 acpi_ex_exit_interpreter();
128 136
129 status = acpi_os_acquire_mutex(mutex, timeout); 137 status = acpi_os_acquire_mutex(mutex, timeout);
130 138
@@ -134,7 +142,13 @@ acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout)
134 142
135 /* Reacquire the interpreter */ 143 /* Reacquire the interpreter */
136 144
137 acpi_ex_reacquire_interpreter(); 145 status2 = acpi_ex_enter_interpreter();
146 if (ACPI_FAILURE(status2)) {
147
148 /* Report fatal error, could not acquire interpreter */
149
150 return_ACPI_STATUS(status2);
151 }
138 } 152 }
139 153
140 return_ACPI_STATUS(status); 154 return_ACPI_STATUS(status);
@@ -195,18 +209,20 @@ acpi_status acpi_ex_system_do_stall(u32 how_long)
195 209
196acpi_status acpi_ex_system_do_suspend(acpi_integer how_long) 210acpi_status acpi_ex_system_do_suspend(acpi_integer how_long)
197{ 211{
212 acpi_status status;
213
198 ACPI_FUNCTION_ENTRY(); 214 ACPI_FUNCTION_ENTRY();
199 215
200 /* Since this thread will sleep, we must release the interpreter */ 216 /* Since this thread will sleep, we must release the interpreter */
201 217
202 acpi_ex_relinquish_interpreter(); 218 acpi_ex_exit_interpreter();
203 219
204 acpi_os_sleep(how_long); 220 acpi_os_sleep(how_long);
205 221
206 /* And now we must get the interpreter again */ 222 /* And now we must get the interpreter again */
207 223
208 acpi_ex_reacquire_interpreter(); 224 status = acpi_ex_enter_interpreter();
209 return (AE_OK); 225 return (status);
210} 226}
211 227
212/******************************************************************************* 228/*******************************************************************************
diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c
index 6b0aeccbb69b..aea461f3a48c 100644
--- a/drivers/acpi/executer/exutils.c
+++ b/drivers/acpi/executer/exutils.c
@@ -76,15 +76,14 @@ static u32 acpi_ex_digits_needed(acpi_integer value, u32 base);
76 * 76 *
77 * PARAMETERS: None 77 * PARAMETERS: None
78 * 78 *
79 * RETURN: None 79 * RETURN: Status
80 * 80 *
81 * DESCRIPTION: Enter the interpreter execution region. Failure to enter 81 * DESCRIPTION: Enter the interpreter execution region. Failure to enter
82 * the interpreter region is a fatal system error. Used in 82 * the interpreter region is a fatal system error
83 * conjunction with exit_interpreter.
84 * 83 *
85 ******************************************************************************/ 84 ******************************************************************************/
86 85
87void acpi_ex_enter_interpreter(void) 86acpi_status acpi_ex_enter_interpreter(void)
88{ 87{
89 acpi_status status; 88 acpi_status status;
90 89
@@ -92,42 +91,10 @@ void acpi_ex_enter_interpreter(void)
92 91
93 status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER); 92 status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER);
94 if (ACPI_FAILURE(status)) { 93 if (ACPI_FAILURE(status)) {
95 ACPI_ERROR((AE_INFO, 94 ACPI_ERROR((AE_INFO, "Could not acquire interpreter mutex"));
96 "Could not acquire AML Interpreter mutex"));
97 } 95 }
98 96
99 return_VOID; 97 return_ACPI_STATUS(status);
100}
101
102/*******************************************************************************
103 *
104 * FUNCTION: acpi_ex_reacquire_interpreter
105 *
106 * PARAMETERS: None
107 *
108 * RETURN: None
109 *
110 * DESCRIPTION: Reacquire the interpreter execution region from within the
111 * interpreter code. Failure to enter the interpreter region is a
112 * fatal system error. Used in conjuction with
113 * relinquish_interpreter
114 *
115 ******************************************************************************/
116
117void acpi_ex_reacquire_interpreter(void)
118{
119 ACPI_FUNCTION_TRACE(ex_reacquire_interpreter);
120
121 /*
122 * If the global serialized flag is set, do not release the interpreter,
123 * since it was not actually released by acpi_ex_relinquish_interpreter.
124 * This forces the interpreter to be single threaded.
125 */
126 if (!acpi_gbl_all_methods_serialized) {
127 acpi_ex_enter_interpreter();
128 }
129
130 return_VOID;
131} 98}
132 99
133/******************************************************************************* 100/*******************************************************************************
@@ -138,9 +105,17 @@ void acpi_ex_reacquire_interpreter(void)
138 * 105 *
139 * RETURN: None 106 * RETURN: None
140 * 107 *
141 * DESCRIPTION: Exit the interpreter execution region. This is the top level 108 * DESCRIPTION: Exit the interpreter execution region
142 * routine used to exit the interpreter when all processing has 109 *
143 * been completed. 110 * Cases where the interpreter is unlocked:
111 * 1) Completion of the execution of a control method
112 * 2) Method blocked on a Sleep() AML opcode
113 * 3) Method blocked on an Acquire() AML opcode
114 * 4) Method blocked on a Wait() AML opcode
115 * 5) Method blocked to acquire the global lock
116 * 6) Method blocked to execute a serialized control method that is
117 * already executing
118 * 7) About to invoke a user-installed opregion handler
144 * 119 *
145 ******************************************************************************/ 120 ******************************************************************************/
146 121
@@ -152,46 +127,7 @@ void acpi_ex_exit_interpreter(void)
152 127
153 status = acpi_ut_release_mutex(ACPI_MTX_INTERPRETER); 128 status = acpi_ut_release_mutex(ACPI_MTX_INTERPRETER);
154 if (ACPI_FAILURE(status)) { 129 if (ACPI_FAILURE(status)) {
155 ACPI_ERROR((AE_INFO, 130 ACPI_ERROR((AE_INFO, "Could not release interpreter mutex"));
156 "Could not release AML Interpreter mutex"));
157 }
158
159 return_VOID;
160}
161
162/*******************************************************************************
163 *
164 * FUNCTION: acpi_ex_relinquish_interpreter
165 *
166 * PARAMETERS: None
167 *
168 * RETURN: None
169 *
170 * DESCRIPTION: Exit the interpreter execution region, from within the
171 * interpreter - before attempting an operation that will possibly
172 * block the running thread.
173 *
174 * Cases where the interpreter is unlocked internally
175 * 1) Method to be blocked on a Sleep() AML opcode
176 * 2) Method to be blocked on an Acquire() AML opcode
177 * 3) Method to be blocked on a Wait() AML opcode
178 * 4) Method to be blocked to acquire the global lock
179 * 5) Method to be blocked waiting to execute a serialized control method
180 * that is currently executing
181 * 6) About to invoke a user-installed opregion handler
182 *
183 ******************************************************************************/
184
185void acpi_ex_relinquish_interpreter(void)
186{
187 ACPI_FUNCTION_TRACE(ex_relinquish_interpreter);
188
189 /*
190 * If the global serialized flag is set, do not release the interpreter.
191 * This forces the interpreter to be single threaded.
192 */
193 if (!acpi_gbl_all_methods_serialized) {
194 acpi_ex_exit_interpreter();
195 } 131 }
196 132
197 return_VOID; 133 return_VOID;
@@ -205,8 +141,8 @@ void acpi_ex_relinquish_interpreter(void)
205 * 141 *
206 * RETURN: none 142 * RETURN: none
207 * 143 *
208 * DESCRIPTION: Truncate an ACPI Integer to 32 bits if the execution mode is 144 * DESCRIPTION: Truncate a number to 32-bits if the currently executing method
209 * 32-bit, as determined by the revision of the DSDT. 145 * belongs to a 32-bit ACPI table.
210 * 146 *
211 ******************************************************************************/ 147 ******************************************************************************/
212 148
diff --git a/drivers/acpi/glue.c b/drivers/acpi/glue.c
index 4334c208841a..41427a41f620 100644
--- a/drivers/acpi/glue.c
+++ b/drivers/acpi/glue.c
@@ -245,6 +245,35 @@ arch_initcall(init_acpi_device_notify);
245 245
246#if defined(CONFIG_RTC_DRV_CMOS) || defined(CONFIG_RTC_DRV_CMOS_MODULE) 246#if defined(CONFIG_RTC_DRV_CMOS) || defined(CONFIG_RTC_DRV_CMOS_MODULE)
247 247
248#ifdef CONFIG_PM
249static u32 rtc_handler(void *context)
250{
251 acpi_clear_event(ACPI_EVENT_RTC);
252 acpi_disable_event(ACPI_EVENT_RTC, 0);
253 return ACPI_INTERRUPT_HANDLED;
254}
255
256static inline void rtc_wake_setup(void)
257{
258 acpi_install_fixed_event_handler(ACPI_EVENT_RTC, rtc_handler, NULL);
259}
260
261static void rtc_wake_on(struct device *dev)
262{
263 acpi_clear_event(ACPI_EVENT_RTC);
264 acpi_enable_event(ACPI_EVENT_RTC, 0);
265}
266
267static void rtc_wake_off(struct device *dev)
268{
269 acpi_disable_event(ACPI_EVENT_RTC, 0);
270}
271#else
272#define rtc_wake_setup() do{}while(0)
273#define rtc_wake_on NULL
274#define rtc_wake_off NULL
275#endif
276
248/* Every ACPI platform has a mc146818 compatible "cmos rtc". Here we find 277/* Every ACPI platform has a mc146818 compatible "cmos rtc". Here we find
249 * its device node and pass extra config data. This helps its driver use 278 * its device node and pass extra config data. This helps its driver use
250 * capabilities that the now-obsolete mc146818 didn't have, and informs it 279 * capabilities that the now-obsolete mc146818 didn't have, and informs it
@@ -283,11 +312,24 @@ static int __init acpi_rtc_init(void)
283 struct device *dev = get_rtc_dev(); 312 struct device *dev = get_rtc_dev();
284 313
285 if (dev) { 314 if (dev) {
315 rtc_wake_setup();
316 rtc_info.wake_on = rtc_wake_on;
317 rtc_info.wake_off = rtc_wake_off;
318
319 /* workaround bug in some ACPI tables */
320 if (acpi_gbl_FADT.month_alarm && !acpi_gbl_FADT.day_alarm) {
321 DBG("bogus FADT month_alarm\n");
322 acpi_gbl_FADT.month_alarm = 0;
323 }
324
286 rtc_info.rtc_day_alarm = acpi_gbl_FADT.day_alarm; 325 rtc_info.rtc_day_alarm = acpi_gbl_FADT.day_alarm;
287 rtc_info.rtc_mon_alarm = acpi_gbl_FADT.month_alarm; 326 rtc_info.rtc_mon_alarm = acpi_gbl_FADT.month_alarm;
288 rtc_info.rtc_century = acpi_gbl_FADT.century; 327 rtc_info.rtc_century = acpi_gbl_FADT.century;
289 328
290 /* NOTE: acpi_gbl_FADT->rtcs4 is NOT currently useful */ 329 /* NOTE: S4_RTC_WAKE is NOT currently useful to Linux */
330 if (acpi_gbl_FADT.flags & ACPI_FADT_S4_RTC_WAKE)
331 printk(PREFIX "RTC can wake from S4\n");
332
291 333
292 dev->platform_data = &rtc_info; 334 dev->platform_data = &rtc_info;
293 335
@@ -296,7 +338,7 @@ static int __init acpi_rtc_init(void)
296 338
297 put_device(dev); 339 put_device(dev);
298 } else 340 } else
299 pr_debug("ACPI: RTC unavailable?\n"); 341 DBG("RTC unavailable?\n");
300 return 0; 342 return 0;
301} 343}
302/* do this between RTC subsys_initcall() and rtc_cmos driver_initcall() */ 344/* do this between RTC subsys_initcall() and rtc_cmos driver_initcall() */
diff --git a/drivers/acpi/hardware/hwsleep.c b/drivers/acpi/hardware/hwsleep.c
index 8fa93125fd4c..c84b1faba28c 100644
--- a/drivers/acpi/hardware/hwsleep.c
+++ b/drivers/acpi/hardware/hwsleep.c
@@ -300,6 +300,11 @@ acpi_status asmlinkage acpi_enter_sleep_state(u8 sleep_state)
300 /* 300 /*
301 * 2) Enable all wakeup GPEs 301 * 2) Enable all wakeup GPEs
302 */ 302 */
303 status = acpi_hw_disable_all_gpes();
304 if (ACPI_FAILURE(status)) {
305 return_ACPI_STATUS(status);
306 }
307
303 acpi_gbl_system_awake_and_running = FALSE; 308 acpi_gbl_system_awake_and_running = FALSE;
304 309
305 status = acpi_hw_enable_all_wakeup_gpes(); 310 status = acpi_hw_enable_all_wakeup_gpes();
diff --git a/drivers/acpi/i2c_ec.c b/drivers/acpi/i2c_ec.c
deleted file mode 100644
index acab4a481897..000000000000
--- a/drivers/acpi/i2c_ec.c
+++ /dev/null
@@ -1,403 +0,0 @@
1/*
2 * SMBus driver for ACPI Embedded Controller ($Revision: 1.3 $)
3 *
4 * Copyright (c) 2002, 2005 Ducrot Bruno
5 * Copyright (c) 2005 Rich Townsend (tiny hacks & tweaks)
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation version 2.
10 */
11
12#include <linux/version.h>
13#include <linux/module.h>
14#include <linux/slab.h>
15#include <linux/kernel.h>
16#include <linux/stddef.h>
17#include <linux/init.h>
18#include <linux/i2c.h>
19#include <linux/acpi.h>
20#include <linux/delay.h>
21
22#include "i2c_ec.h"
23
24#define xudelay(t) udelay(t)
25#define xmsleep(t) msleep(t)
26
27#define ACPI_EC_HC_COMPONENT 0x00080000
28#define ACPI_EC_HC_CLASS "ec_hc_smbus"
29#define ACPI_EC_HC_HID "ACPI0001"
30#define ACPI_EC_HC_DEVICE_NAME "EC HC smbus"
31
32#define _COMPONENT ACPI_EC_HC_COMPONENT
33
34ACPI_MODULE_NAME("i2c_ec");
35
36static int acpi_ec_hc_add(struct acpi_device *device);
37static int acpi_ec_hc_remove(struct acpi_device *device, int type);
38
39static struct acpi_driver acpi_ec_hc_driver = {
40 .name = "i2c_ec",
41 .class = ACPI_EC_HC_CLASS,
42 .ids = ACPI_EC_HC_HID,
43 .ops = {
44 .add = acpi_ec_hc_add,
45 .remove = acpi_ec_hc_remove,
46 },
47};
48
49/* Various bit mask for EC_SC (R) */
50#define OBF 0x01
51#define IBF 0x02
52#define CMD 0x08
53#define BURST 0x10
54#define SCI_EVT 0x20
55#define SMI_EVT 0x40
56
57/* Commands for EC_SC (W) */
58#define RD_EC 0x80
59#define WR_EC 0x81
60#define BE_EC 0x82
61#define BD_EC 0x83
62#define QR_EC 0x84
63
64/*
65 * ACPI 2.0 chapter 13 SMBus 2.0 EC register model
66 */
67
68#define ACPI_EC_SMB_PRTCL 0x00 /* protocol, PEC */
69#define ACPI_EC_SMB_STS 0x01 /* status */
70#define ACPI_EC_SMB_ADDR 0x02 /* address */
71#define ACPI_EC_SMB_CMD 0x03 /* command */
72#define ACPI_EC_SMB_DATA 0x04 /* 32 data registers */
73#define ACPI_EC_SMB_BCNT 0x24 /* number of data bytes */
74#define ACPI_EC_SMB_ALRM_A 0x25 /* alarm address */
75#define ACPI_EC_SMB_ALRM_D 0x26 /* 2 bytes alarm data */
76
77#define ACPI_EC_SMB_STS_DONE 0x80
78#define ACPI_EC_SMB_STS_ALRM 0x40
79#define ACPI_EC_SMB_STS_RES 0x20
80#define ACPI_EC_SMB_STS_STATUS 0x1f
81
82#define ACPI_EC_SMB_STATUS_OK 0x00
83#define ACPI_EC_SMB_STATUS_FAIL 0x07
84#define ACPI_EC_SMB_STATUS_DNAK 0x10
85#define ACPI_EC_SMB_STATUS_DERR 0x11
86#define ACPI_EC_SMB_STATUS_CMD_DENY 0x12
87#define ACPI_EC_SMB_STATUS_UNKNOWN 0x13
88#define ACPI_EC_SMB_STATUS_ACC_DENY 0x17
89#define ACPI_EC_SMB_STATUS_TIMEOUT 0x18
90#define ACPI_EC_SMB_STATUS_NOTSUP 0x19
91#define ACPI_EC_SMB_STATUS_BUSY 0x1A
92#define ACPI_EC_SMB_STATUS_PEC 0x1F
93
94#define ACPI_EC_SMB_PRTCL_WRITE 0x00
95#define ACPI_EC_SMB_PRTCL_READ 0x01
96#define ACPI_EC_SMB_PRTCL_QUICK 0x02
97#define ACPI_EC_SMB_PRTCL_BYTE 0x04
98#define ACPI_EC_SMB_PRTCL_BYTE_DATA 0x06
99#define ACPI_EC_SMB_PRTCL_WORD_DATA 0x08
100#define ACPI_EC_SMB_PRTCL_BLOCK_DATA 0x0a
101#define ACPI_EC_SMB_PRTCL_PROC_CALL 0x0c
102#define ACPI_EC_SMB_PRTCL_BLOCK_PROC_CALL 0x0d
103#define ACPI_EC_SMB_PRTCL_I2C_BLOCK_DATA 0x4a
104#define ACPI_EC_SMB_PRTCL_PEC 0x80
105
106/* Length of pre/post transaction sleep (msec) */
107#define ACPI_EC_SMB_TRANSACTION_SLEEP 1
108#define ACPI_EC_SMB_ACCESS_SLEEP1 1
109#define ACPI_EC_SMB_ACCESS_SLEEP2 10
110
111static int acpi_ec_smb_read(struct acpi_ec_smbus *smbus, u8 address, u8 * data)
112{
113 u8 val;
114 int err;
115
116 err = ec_read(smbus->base + address, &val);
117 if (!err) {
118 *data = val;
119 }
120 xmsleep(ACPI_EC_SMB_TRANSACTION_SLEEP);
121 return (err);
122}
123
124static int acpi_ec_smb_write(struct acpi_ec_smbus *smbus, u8 address, u8 data)
125{
126 int err;
127
128 err = ec_write(smbus->base + address, data);
129 return (err);
130}
131
132static int
133acpi_ec_smb_access(struct i2c_adapter *adap, u16 addr, unsigned short flags,
134 char read_write, u8 command, int size,
135 union i2c_smbus_data *data)
136{
137 struct acpi_ec_smbus *smbus = adap->algo_data;
138 unsigned char protocol, len = 0, pec, temp[2] = { 0, 0 };
139 int i;
140
141 if (read_write == I2C_SMBUS_READ) {
142 protocol = ACPI_EC_SMB_PRTCL_READ;
143 } else {
144 protocol = ACPI_EC_SMB_PRTCL_WRITE;
145 }
146 pec = (flags & I2C_CLIENT_PEC) ? ACPI_EC_SMB_PRTCL_PEC : 0;
147
148 switch (size) {
149
150 case I2C_SMBUS_QUICK:
151 protocol |= ACPI_EC_SMB_PRTCL_QUICK;
152 read_write = I2C_SMBUS_WRITE;
153 break;
154
155 case I2C_SMBUS_BYTE:
156 if (read_write == I2C_SMBUS_WRITE) {
157 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA, data->byte);
158 }
159 protocol |= ACPI_EC_SMB_PRTCL_BYTE;
160 break;
161
162 case I2C_SMBUS_BYTE_DATA:
163 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
164 if (read_write == I2C_SMBUS_WRITE) {
165 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA, data->byte);
166 }
167 protocol |= ACPI_EC_SMB_PRTCL_BYTE_DATA;
168 break;
169
170 case I2C_SMBUS_WORD_DATA:
171 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
172 if (read_write == I2C_SMBUS_WRITE) {
173 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA, data->word);
174 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA + 1,
175 data->word >> 8);
176 }
177 protocol |= ACPI_EC_SMB_PRTCL_WORD_DATA | pec;
178 break;
179
180 case I2C_SMBUS_BLOCK_DATA:
181 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
182 if (read_write == I2C_SMBUS_WRITE) {
183 len = min_t(u8, data->block[0], 32);
184 acpi_ec_smb_write(smbus, ACPI_EC_SMB_BCNT, len);
185 for (i = 0; i < len; i++)
186 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA + i,
187 data->block[i + 1]);
188 }
189 protocol |= ACPI_EC_SMB_PRTCL_BLOCK_DATA | pec;
190 break;
191
192 case I2C_SMBUS_I2C_BLOCK_DATA:
193 len = min_t(u8, data->block[0], 32);
194 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
195 acpi_ec_smb_write(smbus, ACPI_EC_SMB_BCNT, len);
196 if (read_write == I2C_SMBUS_WRITE) {
197 for (i = 0; i < len; i++) {
198 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA + i,
199 data->block[i + 1]);
200 }
201 }
202 protocol |= ACPI_EC_SMB_PRTCL_I2C_BLOCK_DATA;
203 break;
204
205 case I2C_SMBUS_PROC_CALL:
206 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
207 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA, data->word);
208 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA + 1, data->word >> 8);
209 protocol = ACPI_EC_SMB_PRTCL_PROC_CALL | pec;
210 read_write = I2C_SMBUS_READ;
211 break;
212
213 case I2C_SMBUS_BLOCK_PROC_CALL:
214 protocol |= pec;
215 len = min_t(u8, data->block[0], 31);
216 acpi_ec_smb_write(smbus, ACPI_EC_SMB_CMD, command);
217 acpi_ec_smb_write(smbus, ACPI_EC_SMB_BCNT, len);
218 for (i = 0; i < len; i++)
219 acpi_ec_smb_write(smbus, ACPI_EC_SMB_DATA + i,
220 data->block[i + 1]);
221 protocol = ACPI_EC_SMB_PRTCL_BLOCK_PROC_CALL | pec;
222 read_write = I2C_SMBUS_READ;
223 break;
224
225 default:
226 ACPI_DEBUG_PRINT((ACPI_DB_WARN, "EC SMBus adapter: "
227 "Unsupported transaction %d\n", size));
228 return (-1);
229 }
230
231 acpi_ec_smb_write(smbus, ACPI_EC_SMB_ADDR, addr << 1);
232 acpi_ec_smb_write(smbus, ACPI_EC_SMB_PRTCL, protocol);
233
234 acpi_ec_smb_read(smbus, ACPI_EC_SMB_STS, temp + 0);
235
236 if (~temp[0] & ACPI_EC_SMB_STS_DONE) {
237 xudelay(500);
238 acpi_ec_smb_read(smbus, ACPI_EC_SMB_STS, temp + 0);
239 }
240 if (~temp[0] & ACPI_EC_SMB_STS_DONE) {
241 xmsleep(ACPI_EC_SMB_ACCESS_SLEEP2);
242 acpi_ec_smb_read(smbus, ACPI_EC_SMB_STS, temp + 0);
243 }
244 if ((~temp[0] & ACPI_EC_SMB_STS_DONE)
245 || (temp[0] & ACPI_EC_SMB_STS_STATUS)) {
246 return (-1);
247 }
248
249 if (read_write == I2C_SMBUS_WRITE) {
250 return (0);
251 }
252
253 switch (size) {
254
255 case I2C_SMBUS_BYTE:
256 case I2C_SMBUS_BYTE_DATA:
257 acpi_ec_smb_read(smbus, ACPI_EC_SMB_DATA, &data->byte);
258 break;
259
260 case I2C_SMBUS_WORD_DATA:
261 case I2C_SMBUS_PROC_CALL:
262 acpi_ec_smb_read(smbus, ACPI_EC_SMB_DATA, temp + 0);
263 acpi_ec_smb_read(smbus, ACPI_EC_SMB_DATA + 1, temp + 1);
264 data->word = (temp[1] << 8) | temp[0];
265 break;
266
267 case I2C_SMBUS_BLOCK_DATA:
268 case I2C_SMBUS_BLOCK_PROC_CALL:
269 len = 0;
270 acpi_ec_smb_read(smbus, ACPI_EC_SMB_BCNT, &len);
271 len = min_t(u8, len, 32);
272 case I2C_SMBUS_I2C_BLOCK_DATA:
273 for (i = 0; i < len; i++)
274 acpi_ec_smb_read(smbus, ACPI_EC_SMB_DATA + i,
275 data->block + i + 1);
276 data->block[0] = len;
277 break;
278 }
279
280 return (0);
281}
282
283static u32 acpi_ec_smb_func(struct i2c_adapter *adapter)
284{
285
286 return (I2C_FUNC_SMBUS_QUICK | I2C_FUNC_SMBUS_BYTE |
287 I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA |
288 I2C_FUNC_SMBUS_BLOCK_DATA |
289 I2C_FUNC_SMBUS_PROC_CALL |
290 I2C_FUNC_SMBUS_BLOCK_PROC_CALL |
291 I2C_FUNC_SMBUS_I2C_BLOCK | I2C_FUNC_SMBUS_HWPEC_CALC);
292}
293
294static const struct i2c_algorithm acpi_ec_smbus_algorithm = {
295 .smbus_xfer = acpi_ec_smb_access,
296 .functionality = acpi_ec_smb_func,
297};
298
299static int acpi_ec_hc_add(struct acpi_device *device)
300{
301 int status;
302 unsigned long val;
303 struct acpi_ec_hc *ec_hc;
304 struct acpi_ec_smbus *smbus;
305
306 if (!device) {
307 return -EINVAL;
308 }
309
310 ec_hc = kzalloc(sizeof(struct acpi_ec_hc), GFP_KERNEL);
311 if (!ec_hc) {
312 return -ENOMEM;
313 }
314
315 smbus = kzalloc(sizeof(struct acpi_ec_smbus), GFP_KERNEL);
316 if (!smbus) {
317 kfree(ec_hc);
318 return -ENOMEM;
319 }
320
321 ec_hc->handle = device->handle;
322 strcpy(acpi_device_name(device), ACPI_EC_HC_DEVICE_NAME);
323 strcpy(acpi_device_class(device), ACPI_EC_HC_CLASS);
324 acpi_driver_data(device) = ec_hc;
325
326 status = acpi_evaluate_integer(ec_hc->handle, "_EC", NULL, &val);
327 if (ACPI_FAILURE(status)) {
328 ACPI_DEBUG_PRINT((ACPI_DB_WARN, "Error obtaining _EC\n"));
329 kfree(ec_hc);
330 kfree(smbus);
331 return -EIO;
332 }
333
334 smbus->ec = acpi_driver_data(device->parent);
335 smbus->base = (val & 0xff00ull) >> 8;
336 smbus->alert = val & 0xffull;
337
338 smbus->adapter.owner = THIS_MODULE;
339 smbus->adapter.algo = &acpi_ec_smbus_algorithm;
340 smbus->adapter.algo_data = smbus;
341 smbus->adapter.dev.parent = &device->dev;
342
343 if (i2c_add_adapter(&smbus->adapter)) {
344 ACPI_DEBUG_PRINT((ACPI_DB_WARN,
345 "EC SMBus adapter: Failed to register adapter\n"));
346 kfree(smbus);
347 kfree(ec_hc);
348 return -EIO;
349 }
350
351 ec_hc->smbus = smbus;
352
353 printk(KERN_INFO PREFIX "%s [%s]\n",
354 acpi_device_name(device), acpi_device_bid(device));
355
356 return AE_OK;
357}
358
359static int acpi_ec_hc_remove(struct acpi_device *device, int type)
360{
361 struct acpi_ec_hc *ec_hc;
362
363 if (!device) {
364 return -EINVAL;
365 }
366 ec_hc = acpi_driver_data(device);
367
368 i2c_del_adapter(&ec_hc->smbus->adapter);
369 kfree(ec_hc->smbus);
370 kfree(ec_hc);
371
372 return AE_OK;
373}
374
375static int __init acpi_ec_hc_init(void)
376{
377 int result;
378
379 result = acpi_bus_register_driver(&acpi_ec_hc_driver);
380 if (result < 0) {
381 return -ENODEV;
382 }
383 return 0;
384}
385
386static void __exit acpi_ec_hc_exit(void)
387{
388 acpi_bus_unregister_driver(&acpi_ec_hc_driver);
389}
390
391struct acpi_ec_hc *acpi_get_ec_hc(struct acpi_device *device)
392{
393 return acpi_driver_data(device->parent);
394}
395
396EXPORT_SYMBOL(acpi_get_ec_hc);
397
398module_init(acpi_ec_hc_init);
399module_exit(acpi_ec_hc_exit);
400
401MODULE_LICENSE("GPL");
402MODULE_AUTHOR("Ducrot Bruno");
403MODULE_DESCRIPTION("ACPI EC SMBus driver");
diff --git a/drivers/acpi/i2c_ec.h b/drivers/acpi/i2c_ec.h
deleted file mode 100644
index 7c53fb732d61..000000000000
--- a/drivers/acpi/i2c_ec.h
+++ /dev/null
@@ -1,23 +0,0 @@
1/*
2 * SMBus driver for ACPI Embedded Controller ($Revision: 1.2 $)
3 *
4 * Copyright (c) 2002, 2005 Ducrot Bruno
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation version 2.
9 */
10
11struct acpi_ec_smbus {
12 struct i2c_adapter adapter;
13 union acpi_ec *ec;
14 int base;
15 int alert;
16};
17
18struct acpi_ec_hc {
19 acpi_handle handle;
20 struct acpi_ec_smbus *smbus;
21};
22
23struct acpi_ec_hc *acpi_get_ec_hc(struct acpi_device *device);
diff --git a/drivers/acpi/ibm_acpi.c b/drivers/acpi/ibm_acpi.c
deleted file mode 100644
index 4cc534e36e81..000000000000
--- a/drivers/acpi/ibm_acpi.c
+++ /dev/null
@@ -1,2761 +0,0 @@
1/*
2 * ibm_acpi.c - IBM ThinkPad ACPI Extras
3 *
4 *
5 * Copyright (C) 2004-2005 Borislav Deianov <borislav@users.sf.net>
6 * Copyright (C) 2006 Henrique de Moraes Holschuh <hmh@hmh.eng.br>
7 *
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
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 */
22
23#define IBM_VERSION "0.13"
24
25/*
26 * Changelog:
27 *
28 * 2006-11-22 0.13 new maintainer
29 * changelog now lives in git commit history, and will
30 * not be updated further in-file.
31 *
32 * 2005-08-17 0.12 fix compilation on 2.6.13-rc kernels
33 * 2005-03-17 0.11 support for 600e, 770x
34 * thanks to Jamie Lentin <lentinj@dial.pipex.com>
35 * support for 770e, G41
36 * G40 and G41 don't have a thinklight
37 * temperatures no longer experimental
38 * experimental brightness control
39 * experimental volume control
40 * experimental fan enable/disable
41 * 2005-01-16 0.10 fix module loading on R30, R31
42 * 2005-01-16 0.9 support for 570, R30, R31
43 * ultrabay support on A22p, A3x
44 * limit arg for cmos, led, beep, drop experimental status
45 * more capable led control on A21e, A22p, T20-22, X20
46 * experimental temperatures and fan speed
47 * experimental embedded controller register dump
48 * mark more functions as __init, drop incorrect __exit
49 * use MODULE_VERSION
50 * thanks to Henrik Brix Andersen <brix@gentoo.org>
51 * fix parameter passing on module loading
52 * thanks to Rusty Russell <rusty@rustcorp.com.au>
53 * thanks to Jim Radford <radford@blackbean.org>
54 * 2004-11-08 0.8 fix init error case, don't return from a macro
55 * thanks to Chris Wright <chrisw@osdl.org>
56 * 2004-10-23 0.7 fix module loading on A21e, A22p, T20, T21, X20
57 * fix led control on A21e
58 * 2004-10-19 0.6 use acpi_bus_register_driver() to claim HKEY device
59 * 2004-10-18 0.5 thinklight support on A21e, G40, R32, T20, T21, X20
60 * proc file format changed
61 * video_switch command
62 * experimental cmos control
63 * experimental led control
64 * experimental acpi sounds
65 * 2004-09-16 0.4 support for module parameters
66 * hotkey mask can be prefixed by 0x
67 * video output switching
68 * video expansion control
69 * ultrabay eject support
70 * removed lcd brightness/on/off control, didn't work
71 * 2004-08-17 0.3 support for R40
72 * lcd off, brightness control
73 * thinklight on/off
74 * 2004-08-14 0.2 support for T series, X20
75 * bluetooth enable/disable
76 * hotkey events disabled by default
77 * removed fan control, currently useless
78 * 2004-08-09 0.1 initial release, support for X series
79 */
80
81#include <linux/kernel.h>
82#include <linux/module.h>
83#include <linux/init.h>
84#include <linux/types.h>
85#include <linux/string.h>
86
87#include <linux/proc_fs.h>
88#include <linux/backlight.h>
89#include <asm/uaccess.h>
90
91#include <linux/dmi.h>
92#include <linux/jiffies.h>
93#include <linux/workqueue.h>
94
95#include <acpi/acpi_drivers.h>
96#include <acpi/acnamesp.h>
97
98#define IBM_NAME "ibm"
99#define IBM_DESC "IBM ThinkPad ACPI Extras"
100#define IBM_FILE "ibm_acpi"
101#define IBM_URL "http://ibm-acpi.sf.net/"
102
103MODULE_AUTHOR("Borislav Deianov, Henrique de Moraes Holschuh");
104MODULE_DESCRIPTION(IBM_DESC);
105MODULE_VERSION(IBM_VERSION);
106MODULE_LICENSE("GPL");
107
108#define IBM_DIR IBM_NAME
109
110#define IBM_LOG IBM_FILE ": "
111#define IBM_ERR KERN_ERR IBM_LOG
112#define IBM_NOTICE KERN_NOTICE IBM_LOG
113#define IBM_INFO KERN_INFO IBM_LOG
114#define IBM_DEBUG KERN_DEBUG IBM_LOG
115
116#define IBM_MAX_ACPI_ARGS 3
117
118#define __unused __attribute__ ((unused))
119
120static int experimental;
121module_param(experimental, int, 0);
122
123static acpi_handle root_handle = NULL;
124
125#define IBM_HANDLE(object, parent, paths...) \
126 static acpi_handle object##_handle; \
127 static acpi_handle *object##_parent = &parent##_handle; \
128 static char *object##_path; \
129 static char *object##_paths[] = { paths }
130
131IBM_HANDLE(ec, root, "\\_SB.PCI0.ISA.EC0", /* 240, 240x */
132 "\\_SB.PCI.ISA.EC", /* 570 */
133 "\\_SB.PCI0.ISA0.EC0", /* 600e/x, 770e, 770x */
134 "\\_SB.PCI0.ISA.EC", /* A21e, A2xm/p, T20-22, X20-21 */
135 "\\_SB.PCI0.AD4S.EC0", /* i1400, R30 */
136 "\\_SB.PCI0.ICH3.EC0", /* R31 */
137 "\\_SB.PCI0.LPC.EC", /* all others */
138 );
139
140IBM_HANDLE(vid, root, "\\_SB.PCI.AGP.VGA", /* 570 */
141 "\\_SB.PCI0.AGP0.VID0", /* 600e/x, 770x */
142 "\\_SB.PCI0.VID0", /* 770e */
143 "\\_SB.PCI0.VID", /* A21e, G4x, R50e, X30, X40 */
144 "\\_SB.PCI0.AGP.VID", /* all others */
145 ); /* R30, R31 */
146
147IBM_HANDLE(vid2, root, "\\_SB.PCI0.AGPB.VID"); /* G41 */
148
149IBM_HANDLE(cmos, root, "\\UCMS", /* R50, R50e, R50p, R51, T4x, X31, X40 */
150 "\\CMOS", /* A3x, G4x, R32, T23, T30, X22-24, X30 */
151 "\\CMS", /* R40, R40e */
152 ); /* all others */
153#ifdef CONFIG_ACPI_IBM_DOCK
154IBM_HANDLE(dock, root, "\\_SB.GDCK", /* X30, X31, X40 */
155 "\\_SB.PCI0.DOCK", /* 600e/x,770e,770x,A2xm/p,T20-22,X20-21 */
156 "\\_SB.PCI0.PCI1.DOCK", /* all others */
157 "\\_SB.PCI.ISA.SLCE", /* 570 */
158 ); /* A21e,G4x,R30,R31,R32,R40,R40e,R50e */
159#endif
160IBM_HANDLE(bay, root, "\\_SB.PCI.IDE.SECN.MAST", /* 570 */
161 "\\_SB.PCI0.IDE0.IDES.IDSM", /* 600e/x, 770e, 770x */
162 "\\_SB.PCI0.SATA.SCND.MSTR", /* T60, X60, Z60 */
163 "\\_SB.PCI0.IDE0.SCND.MSTR", /* all others */
164 ); /* A21e, R30, R31 */
165
166IBM_HANDLE(bay_ej, bay, "_EJ3", /* 600e/x, A2xm/p, A3x */
167 "_EJ0", /* all others */
168 ); /* 570,A21e,G4x,R30,R31,R32,R40e,R50e */
169
170IBM_HANDLE(bay2, root, "\\_SB.PCI0.IDE0.PRIM.SLAV", /* A3x, R32 */
171 "\\_SB.PCI0.IDE0.IDEP.IDPS", /* 600e/x, 770e, 770x */
172 ); /* all others */
173
174IBM_HANDLE(bay2_ej, bay2, "_EJ3", /* 600e/x, 770e, A3x */
175 "_EJ0", /* 770x */
176 ); /* all others */
177
178/* don't list other alternatives as we install a notify handler on the 570 */
179IBM_HANDLE(pci, root, "\\_SB.PCI"); /* 570 */
180
181IBM_HANDLE(hkey, ec, "\\_SB.HKEY", /* 600e/x, 770e, 770x */
182 "^HKEY", /* R30, R31 */
183 "HKEY", /* all others */
184 ); /* 570 */
185
186IBM_HANDLE(lght, root, "\\LGHT"); /* A21e, A2xm/p, T20-22, X20-21 */
187IBM_HANDLE(ledb, ec, "LEDB"); /* G4x */
188
189IBM_HANDLE(led, ec, "SLED", /* 570 */
190 "SYSL", /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20-21 */
191 "LED", /* all others */
192 ); /* R30, R31 */
193
194IBM_HANDLE(beep, ec, "BEEP"); /* all except R30, R31 */
195IBM_HANDLE(ecrd, ec, "ECRD"); /* 570 */
196IBM_HANDLE(ecwr, ec, "ECWR"); /* 570 */
197IBM_HANDLE(fans, ec, "FANS"); /* X31, X40, X41 */
198
199IBM_HANDLE(gfan, ec, "GFAN", /* 570 */
200 "\\FSPD", /* 600e/x, 770e, 770x */
201 ); /* all others */
202
203IBM_HANDLE(sfan, ec, "SFAN", /* 570 */
204 "JFNS", /* 770x-JL */
205 ); /* all others */
206
207#define IBM_HKEY_HID "IBM0068"
208#define IBM_PCI_HID "PNP0A03"
209
210enum thermal_access_mode {
211 IBMACPI_THERMAL_NONE = 0, /* No thermal support */
212 IBMACPI_THERMAL_ACPI_TMP07, /* Use ACPI TMP0-7 */
213 IBMACPI_THERMAL_ACPI_UPDT, /* Use ACPI TMP0-7 with UPDT */
214 IBMACPI_THERMAL_TPEC_8, /* Use ACPI EC regs, 8 sensors */
215 IBMACPI_THERMAL_TPEC_16, /* Use ACPI EC regs, 16 sensors */
216};
217
218#define IBMACPI_MAX_THERMAL_SENSORS 16 /* Max thermal sensors supported */
219struct ibm_thermal_sensors_struct {
220 s32 temp[IBMACPI_MAX_THERMAL_SENSORS];
221};
222
223/*
224 * FAN ACCESS MODES
225 *
226 * IBMACPI_FAN_RD_ACPI_GFAN:
227 * ACPI GFAN method: returns fan level
228 *
229 * see IBMACPI_FAN_WR_ACPI_SFAN
230 * EC 0x2f not available if GFAN exists
231 *
232 * IBMACPI_FAN_WR_ACPI_SFAN:
233 * ACPI SFAN method: sets fan level, 0 (stop) to 7 (max)
234 *
235 * EC 0x2f might be available *for reading*, but never for writing.
236 *
237 * IBMACPI_FAN_WR_TPEC:
238 * ThinkPad EC register 0x2f (HFSP): fan control loop mode Supported
239 * on almost all ThinkPads
240 *
241 * Fan speed changes of any sort (including those caused by the
242 * disengaged mode) are usually done slowly by the firmware as the
243 * maximum ammount of fan duty cycle change per second seems to be
244 * limited.
245 *
246 * Reading is not available if GFAN exists.
247 * Writing is not available if SFAN exists.
248 *
249 * Bits
250 * 7 automatic mode engaged;
251 * (default operation mode of the ThinkPad)
252 * fan level is ignored in this mode.
253 * 6 disengage mode (takes precedence over bit 7);
254 * not available on all thinkpads. May disable
255 * the tachometer, and speeds up fan to 100% duty-cycle,
256 * which speeds it up far above the standard RPM
257 * levels. It is not impossible that it could cause
258 * hardware damage.
259 * 5-3 unused in some models. Extra bits for fan level
260 * in others, but still useless as all values above
261 * 7 map to the same speed as level 7 in these models.
262 * 2-0 fan level (0..7 usually)
263 * 0x00 = stop
264 * 0x07 = max (set when temperatures critical)
265 * Some ThinkPads may have other levels, see
266 * IBMACPI_FAN_WR_ACPI_FANS (X31/X40/X41)
267 *
268 * FIRMWARE BUG: on some models, EC 0x2f might not be initialized at
269 * boot. Apparently the EC does not intialize it, so unless ACPI DSDT
270 * does so, its initial value is meaningless (0x07).
271 *
272 * For firmware bugs, refer to:
273 * http://thinkwiki.org/wiki/Embedded_Controller_Firmware#Firmware_Issues
274 *
275 * ----
276 *
277 * ThinkPad EC register 0x84 (LSB), 0x85 (MSB):
278 * Main fan tachometer reading (in RPM)
279 *
280 * This register is present on all ThinkPads with a new-style EC, and
281 * it is known not to be present on the A21m/e, and T22, as there is
282 * something else in offset 0x84 according to the ACPI DSDT. Other
283 * ThinkPads from this same time period (and earlier) probably lack the
284 * tachometer as well.
285 *
286 * Unfortunately a lot of ThinkPads with new-style ECs but whose firwmare
287 * was never fixed by IBM to report the EC firmware version string
288 * probably support the tachometer (like the early X models), so
289 * detecting it is quite hard. We need more data to know for sure.
290 *
291 * FIRMWARE BUG: always read 0x84 first, otherwise incorrect readings
292 * might result.
293 *
294 * FIRMWARE BUG: when EC 0x2f bit 6 is set (disengaged mode), this
295 * register is not invalidated in ThinkPads that disable tachometer
296 * readings. Thus, the tachometer readings go stale.
297 *
298 * For firmware bugs, refer to:
299 * http://thinkwiki.org/wiki/Embedded_Controller_Firmware#Firmware_Issues
300 *
301 * IBMACPI_FAN_WR_ACPI_FANS:
302 * ThinkPad X31, X40, X41. Not available in the X60.
303 *
304 * FANS ACPI handle: takes three arguments: low speed, medium speed,
305 * high speed. ACPI DSDT seems to map these three speeds to levels
306 * as follows: STOP LOW LOW MED MED HIGH HIGH HIGH HIGH
307 * (this map is stored on FAN0..FAN8 as "0,1,1,2,2,3,3,3,3")
308 *
309 * The speeds are stored on handles
310 * (FANA:FAN9), (FANC:FANB), (FANE:FAND).
311 *
312 * There are three default speed sets, acessible as handles:
313 * FS1L,FS1M,FS1H; FS2L,FS2M,FS2H; FS3L,FS3M,FS3H
314 *
315 * ACPI DSDT switches which set is in use depending on various
316 * factors.
317 *
318 * IBMACPI_FAN_WR_TPEC is also available and should be used to
319 * command the fan. The X31/X40/X41 seems to have 8 fan levels,
320 * but the ACPI tables just mention level 7.
321 */
322
323enum fan_status_access_mode {
324 IBMACPI_FAN_NONE = 0, /* No fan status or control */
325 IBMACPI_FAN_RD_ACPI_GFAN, /* Use ACPI GFAN */
326 IBMACPI_FAN_RD_TPEC, /* Use ACPI EC regs 0x2f, 0x84-0x85 */
327};
328
329enum fan_control_access_mode {
330 IBMACPI_FAN_WR_NONE = 0, /* No fan control */
331 IBMACPI_FAN_WR_ACPI_SFAN, /* Use ACPI SFAN */
332 IBMACPI_FAN_WR_TPEC, /* Use ACPI EC reg 0x2f */
333 IBMACPI_FAN_WR_ACPI_FANS, /* Use ACPI FANS and EC reg 0x2f */
334};
335
336enum fan_control_commands {
337 IBMACPI_FAN_CMD_SPEED = 0x0001, /* speed command */
338 IBMACPI_FAN_CMD_LEVEL = 0x0002, /* level command */
339 IBMACPI_FAN_CMD_ENABLE = 0x0004, /* enable/disable cmd,
340 * and also watchdog cmd */
341};
342
343enum { /* Fan control constants */
344 fan_status_offset = 0x2f, /* EC register 0x2f */
345 fan_rpm_offset = 0x84, /* EC register 0x84: LSB, 0x85 MSB (RPM)
346 * 0x84 must be read before 0x85 */
347
348 IBMACPI_FAN_EC_DISENGAGED = 0x40, /* EC mode: tachometer
349 * disengaged */
350 IBMACPI_FAN_EC_AUTO = 0x80, /* EC mode: auto fan
351 * control */
352};
353
354static char *ibm_thinkpad_ec_found = NULL;
355
356struct ibm_struct {
357 char *name;
358 char param[32];
359
360 char *hid;
361 struct acpi_driver *driver;
362
363 int (*init) (void);
364 int (*read) (char *);
365 int (*write) (char *);
366 void (*exit) (void);
367
368 void (*notify) (struct ibm_struct *, u32);
369 acpi_handle *handle;
370 int type;
371 struct acpi_device *device;
372
373 int driver_registered;
374 int proc_created;
375 int init_called;
376 int notify_installed;
377
378 int experimental;
379};
380
381static struct proc_dir_entry *proc_dir = NULL;
382
383static struct backlight_device *ibm_backlight_device = NULL;
384
385#define onoff(status,bit) ((status) & (1 << (bit)) ? "on" : "off")
386#define enabled(status,bit) ((status) & (1 << (bit)) ? "enabled" : "disabled")
387#define strlencmp(a,b) (strncmp((a), (b), strlen(b)))
388
389static int acpi_evalf(acpi_handle handle,
390 void *res, char *method, char *fmt, ...)
391{
392 char *fmt0 = fmt;
393 struct acpi_object_list params;
394 union acpi_object in_objs[IBM_MAX_ACPI_ARGS];
395 struct acpi_buffer result, *resultp;
396 union acpi_object out_obj;
397 acpi_status status;
398 va_list ap;
399 char res_type;
400 int success;
401 int quiet;
402
403 if (!*fmt) {
404 printk(IBM_ERR "acpi_evalf() called with empty format\n");
405 return 0;
406 }
407
408 if (*fmt == 'q') {
409 quiet = 1;
410 fmt++;
411 } else
412 quiet = 0;
413
414 res_type = *(fmt++);
415
416 params.count = 0;
417 params.pointer = &in_objs[0];
418
419 va_start(ap, fmt);
420 while (*fmt) {
421 char c = *(fmt++);
422 switch (c) {
423 case 'd': /* int */
424 in_objs[params.count].integer.value = va_arg(ap, int);
425 in_objs[params.count++].type = ACPI_TYPE_INTEGER;
426 break;
427 /* add more types as needed */
428 default:
429 printk(IBM_ERR "acpi_evalf() called "
430 "with invalid format character '%c'\n", c);
431 return 0;
432 }
433 }
434 va_end(ap);
435
436 if (res_type != 'v') {
437 result.length = sizeof(out_obj);
438 result.pointer = &out_obj;
439 resultp = &result;
440 } else
441 resultp = NULL;
442
443 status = acpi_evaluate_object(handle, method, &params, resultp);
444
445 switch (res_type) {
446 case 'd': /* int */
447 if (res)
448 *(int *)res = out_obj.integer.value;
449 success = status == AE_OK && out_obj.type == ACPI_TYPE_INTEGER;
450 break;
451 case 'v': /* void */
452 success = status == AE_OK;
453 break;
454 /* add more types as needed */
455 default:
456 printk(IBM_ERR "acpi_evalf() called "
457 "with invalid format character '%c'\n", res_type);
458 return 0;
459 }
460
461 if (!success && !quiet)
462 printk(IBM_ERR "acpi_evalf(%s, %s, ...) failed: %d\n",
463 method, fmt0, status);
464
465 return success;
466}
467
468static void __unused acpi_print_int(acpi_handle handle, char *method)
469{
470 int i;
471
472 if (acpi_evalf(handle, &i, method, "d"))
473 printk(IBM_INFO "%s = 0x%x\n", method, i);
474 else
475 printk(IBM_ERR "error calling %s\n", method);
476}
477
478static char *next_cmd(char **cmds)
479{
480 char *start = *cmds;
481 char *end;
482
483 while ((end = strchr(start, ',')) && end == start)
484 start = end + 1;
485
486 if (!end)
487 return NULL;
488
489 *end = 0;
490 *cmds = end + 1;
491 return start;
492}
493
494static int ibm_acpi_driver_init(void)
495{
496 printk(IBM_INFO "%s v%s\n", IBM_DESC, IBM_VERSION);
497 printk(IBM_INFO "%s\n", IBM_URL);
498
499 if (ibm_thinkpad_ec_found)
500 printk(IBM_INFO "ThinkPad EC firmware %s\n",
501 ibm_thinkpad_ec_found);
502
503 return 0;
504}
505
506static int driver_read(char *p)
507{
508 int len = 0;
509
510 len += sprintf(p + len, "driver:\t\t%s\n", IBM_DESC);
511 len += sprintf(p + len, "version:\t%s\n", IBM_VERSION);
512
513 return len;
514}
515
516static int hotkey_supported;
517static int hotkey_mask_supported;
518static int hotkey_orig_status;
519static int hotkey_orig_mask;
520
521static int hotkey_get(int *status, int *mask)
522{
523 if (!acpi_evalf(hkey_handle, status, "DHKC", "d"))
524 return 0;
525
526 if (hotkey_mask_supported)
527 if (!acpi_evalf(hkey_handle, mask, "DHKN", "d"))
528 return 0;
529
530 return 1;
531}
532
533static int hotkey_set(int status, int mask)
534{
535 int i;
536
537 if (!acpi_evalf(hkey_handle, NULL, "MHKC", "vd", status))
538 return 0;
539
540 if (hotkey_mask_supported)
541 for (i = 0; i < 32; i++) {
542 int bit = ((1 << i) & mask) != 0;
543 if (!acpi_evalf(hkey_handle,
544 NULL, "MHKM", "vdd", i + 1, bit))
545 return 0;
546 }
547
548 return 1;
549}
550
551static int hotkey_init(void)
552{
553 /* hotkey not supported on 570 */
554 hotkey_supported = hkey_handle != NULL;
555
556 if (hotkey_supported) {
557 /* mask not supported on 570, 600e/x, 770e, 770x, A21e, A2xm/p,
558 A30, R30, R31, T20-22, X20-21, X22-24 */
559 hotkey_mask_supported =
560 acpi_evalf(hkey_handle, NULL, "DHKN", "qv");
561
562 if (!hotkey_get(&hotkey_orig_status, &hotkey_orig_mask))
563 return -ENODEV;
564 }
565
566 return 0;
567}
568
569static int hotkey_read(char *p)
570{
571 int status, mask;
572 int len = 0;
573
574 if (!hotkey_supported) {
575 len += sprintf(p + len, "status:\t\tnot supported\n");
576 return len;
577 }
578
579 if (!hotkey_get(&status, &mask))
580 return -EIO;
581
582 len += sprintf(p + len, "status:\t\t%s\n", enabled(status, 0));
583 if (hotkey_mask_supported) {
584 len += sprintf(p + len, "mask:\t\t0x%04x\n", mask);
585 len += sprintf(p + len,
586 "commands:\tenable, disable, reset, <mask>\n");
587 } else {
588 len += sprintf(p + len, "mask:\t\tnot supported\n");
589 len += sprintf(p + len, "commands:\tenable, disable, reset\n");
590 }
591
592 return len;
593}
594
595static int hotkey_write(char *buf)
596{
597 int status, mask;
598 char *cmd;
599 int do_cmd = 0;
600
601 if (!hotkey_supported)
602 return -ENODEV;
603
604 if (!hotkey_get(&status, &mask))
605 return -EIO;
606
607 while ((cmd = next_cmd(&buf))) {
608 if (strlencmp(cmd, "enable") == 0) {
609 status = 1;
610 } else if (strlencmp(cmd, "disable") == 0) {
611 status = 0;
612 } else if (strlencmp(cmd, "reset") == 0) {
613 status = hotkey_orig_status;
614 mask = hotkey_orig_mask;
615 } else if (sscanf(cmd, "0x%x", &mask) == 1) {
616 /* mask set */
617 } else if (sscanf(cmd, "%x", &mask) == 1) {
618 /* mask set */
619 } else
620 return -EINVAL;
621 do_cmd = 1;
622 }
623
624 if (do_cmd && !hotkey_set(status, mask))
625 return -EIO;
626
627 return 0;
628}
629
630static void hotkey_exit(void)
631{
632 if (hotkey_supported)
633 hotkey_set(hotkey_orig_status, hotkey_orig_mask);
634}
635
636static void hotkey_notify(struct ibm_struct *ibm, u32 event)
637{
638 int hkey;
639
640 if (acpi_evalf(hkey_handle, &hkey, "MHKP", "d"))
641 acpi_bus_generate_event(ibm->device, event, hkey);
642 else {
643 printk(IBM_ERR "unknown hotkey event %d\n", event);
644 acpi_bus_generate_event(ibm->device, event, 0);
645 }
646}
647
648static int bluetooth_supported;
649
650static int bluetooth_init(void)
651{
652 /* bluetooth not supported on 570, 600e/x, 770e, 770x, A21e, A2xm/p,
653 G4x, R30, R31, R40e, R50e, T20-22, X20-21 */
654 bluetooth_supported = hkey_handle &&
655 acpi_evalf(hkey_handle, NULL, "GBDC", "qv");
656
657 return 0;
658}
659
660static int bluetooth_status(void)
661{
662 int status;
663
664 if (!bluetooth_supported ||
665 !acpi_evalf(hkey_handle, &status, "GBDC", "d"))
666 status = 0;
667
668 return status;
669}
670
671static int bluetooth_read(char *p)
672{
673 int len = 0;
674 int status = bluetooth_status();
675
676 if (!bluetooth_supported)
677 len += sprintf(p + len, "status:\t\tnot supported\n");
678 else if (!(status & 1))
679 len += sprintf(p + len, "status:\t\tnot installed\n");
680 else {
681 len += sprintf(p + len, "status:\t\t%s\n", enabled(status, 1));
682 len += sprintf(p + len, "commands:\tenable, disable\n");
683 }
684
685 return len;
686}
687
688static int bluetooth_write(char *buf)
689{
690 int status = bluetooth_status();
691 char *cmd;
692 int do_cmd = 0;
693
694 if (!bluetooth_supported)
695 return -ENODEV;
696
697 while ((cmd = next_cmd(&buf))) {
698 if (strlencmp(cmd, "enable") == 0) {
699 status |= 2;
700 } else if (strlencmp(cmd, "disable") == 0) {
701 status &= ~2;
702 } else
703 return -EINVAL;
704 do_cmd = 1;
705 }
706
707 if (do_cmd && !acpi_evalf(hkey_handle, NULL, "SBDC", "vd", status))
708 return -EIO;
709
710 return 0;
711}
712
713static int wan_supported;
714
715static int wan_init(void)
716{
717 wan_supported = hkey_handle &&
718 acpi_evalf(hkey_handle, NULL, "GWAN", "qv");
719
720 return 0;
721}
722
723static int wan_status(void)
724{
725 int status;
726
727 if (!wan_supported || !acpi_evalf(hkey_handle, &status, "GWAN", "d"))
728 status = 0;
729
730 return status;
731}
732
733static int wan_read(char *p)
734{
735 int len = 0;
736 int status = wan_status();
737
738 if (!wan_supported)
739 len += sprintf(p + len, "status:\t\tnot supported\n");
740 else if (!(status & 1))
741 len += sprintf(p + len, "status:\t\tnot installed\n");
742 else {
743 len += sprintf(p + len, "status:\t\t%s\n", enabled(status, 1));
744 len += sprintf(p + len, "commands:\tenable, disable\n");
745 }
746
747 return len;
748}
749
750static int wan_write(char *buf)
751{
752 int status = wan_status();
753 char *cmd;
754 int do_cmd = 0;
755
756 if (!wan_supported)
757 return -ENODEV;
758
759 while ((cmd = next_cmd(&buf))) {
760 if (strlencmp(cmd, "enable") == 0) {
761 status |= 2;
762 } else if (strlencmp(cmd, "disable") == 0) {
763 status &= ~2;
764 } else
765 return -EINVAL;
766 do_cmd = 1;
767 }
768
769 if (do_cmd && !acpi_evalf(hkey_handle, NULL, "SWAN", "vd", status))
770 return -EIO;
771
772 return 0;
773}
774
775enum video_access_mode {
776 IBMACPI_VIDEO_NONE = 0,
777 IBMACPI_VIDEO_570, /* 570 */
778 IBMACPI_VIDEO_770, /* 600e/x, 770e, 770x */
779 IBMACPI_VIDEO_NEW, /* all others */
780};
781
782static enum video_access_mode video_supported;
783static int video_orig_autosw;
784
785static int video_init(void)
786{
787 int ivga;
788
789 if (vid2_handle && acpi_evalf(NULL, &ivga, "\\IVGA", "d") && ivga)
790 /* G41, assume IVGA doesn't change */
791 vid_handle = vid2_handle;
792
793 if (!vid_handle)
794 /* video switching not supported on R30, R31 */
795 video_supported = IBMACPI_VIDEO_NONE;
796 else if (acpi_evalf(vid_handle, &video_orig_autosw, "SWIT", "qd"))
797 /* 570 */
798 video_supported = IBMACPI_VIDEO_570;
799 else if (acpi_evalf(vid_handle, &video_orig_autosw, "^VADL", "qd"))
800 /* 600e/x, 770e, 770x */
801 video_supported = IBMACPI_VIDEO_770;
802 else
803 /* all others */
804 video_supported = IBMACPI_VIDEO_NEW;
805
806 return 0;
807}
808
809static int video_status(void)
810{
811 int status = 0;
812 int i;
813
814 if (video_supported == IBMACPI_VIDEO_570) {
815 if (acpi_evalf(NULL, &i, "\\_SB.PHS", "dd", 0x87))
816 status = i & 3;
817 } else if (video_supported == IBMACPI_VIDEO_770) {
818 if (acpi_evalf(NULL, &i, "\\VCDL", "d"))
819 status |= 0x01 * i;
820 if (acpi_evalf(NULL, &i, "\\VCDC", "d"))
821 status |= 0x02 * i;
822 } else if (video_supported == IBMACPI_VIDEO_NEW) {
823 acpi_evalf(NULL, NULL, "\\VUPS", "vd", 1);
824 if (acpi_evalf(NULL, &i, "\\VCDC", "d"))
825 status |= 0x02 * i;
826
827 acpi_evalf(NULL, NULL, "\\VUPS", "vd", 0);
828 if (acpi_evalf(NULL, &i, "\\VCDL", "d"))
829 status |= 0x01 * i;
830 if (acpi_evalf(NULL, &i, "\\VCDD", "d"))
831 status |= 0x08 * i;
832 }
833
834 return status;
835}
836
837static int video_autosw(void)
838{
839 int autosw = 0;
840
841 if (video_supported == IBMACPI_VIDEO_570)
842 acpi_evalf(vid_handle, &autosw, "SWIT", "d");
843 else if (video_supported == IBMACPI_VIDEO_770 ||
844 video_supported == IBMACPI_VIDEO_NEW)
845 acpi_evalf(vid_handle, &autosw, "^VDEE", "d");
846
847 return autosw & 1;
848}
849
850static int video_read(char *p)
851{
852 int status = video_status();
853 int autosw = video_autosw();
854 int len = 0;
855
856 if (!video_supported) {
857 len += sprintf(p + len, "status:\t\tnot supported\n");
858 return len;
859 }
860
861 len += sprintf(p + len, "status:\t\tsupported\n");
862 len += sprintf(p + len, "lcd:\t\t%s\n", enabled(status, 0));
863 len += sprintf(p + len, "crt:\t\t%s\n", enabled(status, 1));
864 if (video_supported == IBMACPI_VIDEO_NEW)
865 len += sprintf(p + len, "dvi:\t\t%s\n", enabled(status, 3));
866 len += sprintf(p + len, "auto:\t\t%s\n", enabled(autosw, 0));
867 len += sprintf(p + len, "commands:\tlcd_enable, lcd_disable\n");
868 len += sprintf(p + len, "commands:\tcrt_enable, crt_disable\n");
869 if (video_supported == IBMACPI_VIDEO_NEW)
870 len += sprintf(p + len, "commands:\tdvi_enable, dvi_disable\n");
871 len += sprintf(p + len, "commands:\tauto_enable, auto_disable\n");
872 len += sprintf(p + len, "commands:\tvideo_switch, expand_toggle\n");
873
874 return len;
875}
876
877static int video_switch(void)
878{
879 int autosw = video_autosw();
880 int ret;
881
882 if (!acpi_evalf(vid_handle, NULL, "_DOS", "vd", 1))
883 return -EIO;
884 ret = video_supported == IBMACPI_VIDEO_570 ?
885 acpi_evalf(ec_handle, NULL, "_Q16", "v") :
886 acpi_evalf(vid_handle, NULL, "VSWT", "v");
887 acpi_evalf(vid_handle, NULL, "_DOS", "vd", autosw);
888
889 return ret;
890}
891
892static int video_expand(void)
893{
894 if (video_supported == IBMACPI_VIDEO_570)
895 return acpi_evalf(ec_handle, NULL, "_Q17", "v");
896 else if (video_supported == IBMACPI_VIDEO_770)
897 return acpi_evalf(vid_handle, NULL, "VEXP", "v");
898 else
899 return acpi_evalf(NULL, NULL, "\\VEXP", "v");
900}
901
902static int video_switch2(int status)
903{
904 int ret;
905
906 if (video_supported == IBMACPI_VIDEO_570) {
907 ret = acpi_evalf(NULL, NULL,
908 "\\_SB.PHS2", "vdd", 0x8b, status | 0x80);
909 } else if (video_supported == IBMACPI_VIDEO_770) {
910 int autosw = video_autosw();
911 if (!acpi_evalf(vid_handle, NULL, "_DOS", "vd", 1))
912 return -EIO;
913
914 ret = acpi_evalf(vid_handle, NULL,
915 "ASWT", "vdd", status * 0x100, 0);
916
917 acpi_evalf(vid_handle, NULL, "_DOS", "vd", autosw);
918 } else {
919 ret = acpi_evalf(NULL, NULL, "\\VUPS", "vd", 0x80) &&
920 acpi_evalf(NULL, NULL, "\\VSDS", "vdd", status, 1);
921 }
922
923 return ret;
924}
925
926static int video_write(char *buf)
927{
928 char *cmd;
929 int enable, disable, status;
930
931 if (!video_supported)
932 return -ENODEV;
933
934 enable = disable = 0;
935
936 while ((cmd = next_cmd(&buf))) {
937 if (strlencmp(cmd, "lcd_enable") == 0) {
938 enable |= 0x01;
939 } else if (strlencmp(cmd, "lcd_disable") == 0) {
940 disable |= 0x01;
941 } else if (strlencmp(cmd, "crt_enable") == 0) {
942 enable |= 0x02;
943 } else if (strlencmp(cmd, "crt_disable") == 0) {
944 disable |= 0x02;
945 } else if (video_supported == IBMACPI_VIDEO_NEW &&
946 strlencmp(cmd, "dvi_enable") == 0) {
947 enable |= 0x08;
948 } else if (video_supported == IBMACPI_VIDEO_NEW &&
949 strlencmp(cmd, "dvi_disable") == 0) {
950 disable |= 0x08;
951 } else if (strlencmp(cmd, "auto_enable") == 0) {
952 if (!acpi_evalf(vid_handle, NULL, "_DOS", "vd", 1))
953 return -EIO;
954 } else if (strlencmp(cmd, "auto_disable") == 0) {
955 if (!acpi_evalf(vid_handle, NULL, "_DOS", "vd", 0))
956 return -EIO;
957 } else if (strlencmp(cmd, "video_switch") == 0) {
958 if (!video_switch())
959 return -EIO;
960 } else if (strlencmp(cmd, "expand_toggle") == 0) {
961 if (!video_expand())
962 return -EIO;
963 } else
964 return -EINVAL;
965 }
966
967 if (enable || disable) {
968 status = (video_status() & 0x0f & ~disable) | enable;
969 if (!video_switch2(status))
970 return -EIO;
971 }
972
973 return 0;
974}
975
976static void video_exit(void)
977{
978 acpi_evalf(vid_handle, NULL, "_DOS", "vd", video_orig_autosw);
979}
980
981static int light_supported;
982static int light_status_supported;
983
984static int light_init(void)
985{
986 /* light not supported on 570, 600e/x, 770e, 770x, G4x, R30, R31 */
987 light_supported = (cmos_handle || lght_handle) && !ledb_handle;
988
989 if (light_supported)
990 /* light status not supported on
991 570, 600e/x, 770e, 770x, G4x, R30, R31, R32, X20 */
992 light_status_supported = acpi_evalf(ec_handle, NULL,
993 "KBLT", "qv");
994
995 return 0;
996}
997
998static int light_read(char *p)
999{
1000 int len = 0;
1001 int status = 0;
1002
1003 if (!light_supported) {
1004 len += sprintf(p + len, "status:\t\tnot supported\n");
1005 } else if (!light_status_supported) {
1006 len += sprintf(p + len, "status:\t\tunknown\n");
1007 len += sprintf(p + len, "commands:\ton, off\n");
1008 } else {
1009 if (!acpi_evalf(ec_handle, &status, "KBLT", "d"))
1010 return -EIO;
1011 len += sprintf(p + len, "status:\t\t%s\n", onoff(status, 0));
1012 len += sprintf(p + len, "commands:\ton, off\n");
1013 }
1014
1015 return len;
1016}
1017
1018static int light_write(char *buf)
1019{
1020 int cmos_cmd, lght_cmd;
1021 char *cmd;
1022 int success;
1023
1024 if (!light_supported)
1025 return -ENODEV;
1026
1027 while ((cmd = next_cmd(&buf))) {
1028 if (strlencmp(cmd, "on") == 0) {
1029 cmos_cmd = 0x0c;
1030 lght_cmd = 1;
1031 } else if (strlencmp(cmd, "off") == 0) {
1032 cmos_cmd = 0x0d;
1033 lght_cmd = 0;
1034 } else
1035 return -EINVAL;
1036
1037 success = cmos_handle ?
1038 acpi_evalf(cmos_handle, NULL, NULL, "vd", cmos_cmd) :
1039 acpi_evalf(lght_handle, NULL, NULL, "vd", lght_cmd);
1040 if (!success)
1041 return -EIO;
1042 }
1043
1044 return 0;
1045}
1046
1047static int _sta(acpi_handle handle)
1048{
1049 int status;
1050
1051 if (!handle || !acpi_evalf(handle, &status, "_STA", "d"))
1052 status = 0;
1053
1054 return status;
1055}
1056
1057#ifdef CONFIG_ACPI_IBM_DOCK
1058#define dock_docked() (_sta(dock_handle) & 1)
1059
1060static int dock_read(char *p)
1061{
1062 int len = 0;
1063 int docked = dock_docked();
1064
1065 if (!dock_handle)
1066 len += sprintf(p + len, "status:\t\tnot supported\n");
1067 else if (!docked)
1068 len += sprintf(p + len, "status:\t\tundocked\n");
1069 else {
1070 len += sprintf(p + len, "status:\t\tdocked\n");
1071 len += sprintf(p + len, "commands:\tdock, undock\n");
1072 }
1073
1074 return len;
1075}
1076
1077static int dock_write(char *buf)
1078{
1079 char *cmd;
1080
1081 if (!dock_docked())
1082 return -ENODEV;
1083
1084 while ((cmd = next_cmd(&buf))) {
1085 if (strlencmp(cmd, "undock") == 0) {
1086 if (!acpi_evalf(dock_handle, NULL, "_DCK", "vd", 0) ||
1087 !acpi_evalf(dock_handle, NULL, "_EJ0", "vd", 1))
1088 return -EIO;
1089 } else if (strlencmp(cmd, "dock") == 0) {
1090 if (!acpi_evalf(dock_handle, NULL, "_DCK", "vd", 1))
1091 return -EIO;
1092 } else
1093 return -EINVAL;
1094 }
1095
1096 return 0;
1097}
1098
1099static void dock_notify(struct ibm_struct *ibm, u32 event)
1100{
1101 int docked = dock_docked();
1102 int pci = ibm->hid && strstr(ibm->hid, IBM_PCI_HID);
1103
1104 if (event == 1 && !pci) /* 570 */
1105 acpi_bus_generate_event(ibm->device, event, 1); /* button */
1106 else if (event == 1 && pci) /* 570 */
1107 acpi_bus_generate_event(ibm->device, event, 3); /* dock */
1108 else if (event == 3 && docked)
1109 acpi_bus_generate_event(ibm->device, event, 1); /* button */
1110 else if (event == 3 && !docked)
1111 acpi_bus_generate_event(ibm->device, event, 2); /* undock */
1112 else if (event == 0 && docked)
1113 acpi_bus_generate_event(ibm->device, event, 3); /* dock */
1114 else {
1115 printk(IBM_ERR "unknown dock event %d, status %d\n",
1116 event, _sta(dock_handle));
1117 acpi_bus_generate_event(ibm->device, event, 0); /* unknown */
1118 }
1119}
1120#endif
1121
1122static int bay_status_supported;
1123static int bay_status2_supported;
1124static int bay_eject_supported;
1125static int bay_eject2_supported;
1126
1127static int bay_init(void)
1128{
1129 bay_status_supported = bay_handle &&
1130 acpi_evalf(bay_handle, NULL, "_STA", "qv");
1131 bay_status2_supported = bay2_handle &&
1132 acpi_evalf(bay2_handle, NULL, "_STA", "qv");
1133
1134 bay_eject_supported = bay_handle && bay_ej_handle &&
1135 (strlencmp(bay_ej_path, "_EJ0") == 0 || experimental);
1136 bay_eject2_supported = bay2_handle && bay2_ej_handle &&
1137 (strlencmp(bay2_ej_path, "_EJ0") == 0 || experimental);
1138
1139 return 0;
1140}
1141
1142#define bay_occupied(b) (_sta(b##_handle) & 1)
1143
1144static int bay_read(char *p)
1145{
1146 int len = 0;
1147 int occupied = bay_occupied(bay);
1148 int occupied2 = bay_occupied(bay2);
1149 int eject, eject2;
1150
1151 len += sprintf(p + len, "status:\t\t%s\n", bay_status_supported ?
1152 (occupied ? "occupied" : "unoccupied") :
1153 "not supported");
1154 if (bay_status2_supported)
1155 len += sprintf(p + len, "status2:\t%s\n", occupied2 ?
1156 "occupied" : "unoccupied");
1157
1158 eject = bay_eject_supported && occupied;
1159 eject2 = bay_eject2_supported && occupied2;
1160
1161 if (eject && eject2)
1162 len += sprintf(p + len, "commands:\teject, eject2\n");
1163 else if (eject)
1164 len += sprintf(p + len, "commands:\teject\n");
1165 else if (eject2)
1166 len += sprintf(p + len, "commands:\teject2\n");
1167
1168 return len;
1169}
1170
1171static int bay_write(char *buf)
1172{
1173 char *cmd;
1174
1175 if (!bay_eject_supported && !bay_eject2_supported)
1176 return -ENODEV;
1177
1178 while ((cmd = next_cmd(&buf))) {
1179 if (bay_eject_supported && strlencmp(cmd, "eject") == 0) {
1180 if (!acpi_evalf(bay_ej_handle, NULL, NULL, "vd", 1))
1181 return -EIO;
1182 } else if (bay_eject2_supported &&
1183 strlencmp(cmd, "eject2") == 0) {
1184 if (!acpi_evalf(bay2_ej_handle, NULL, NULL, "vd", 1))
1185 return -EIO;
1186 } else
1187 return -EINVAL;
1188 }
1189
1190 return 0;
1191}
1192
1193static void bay_notify(struct ibm_struct *ibm, u32 event)
1194{
1195 acpi_bus_generate_event(ibm->device, event, 0);
1196}
1197
1198static int cmos_read(char *p)
1199{
1200 int len = 0;
1201
1202 /* cmos not supported on 570, 600e/x, 770e, 770x, A21e, A2xm/p,
1203 R30, R31, T20-22, X20-21 */
1204 if (!cmos_handle)
1205 len += sprintf(p + len, "status:\t\tnot supported\n");
1206 else {
1207 len += sprintf(p + len, "status:\t\tsupported\n");
1208 len += sprintf(p + len, "commands:\t<cmd> (<cmd> is 0-21)\n");
1209 }
1210
1211 return len;
1212}
1213
1214static int cmos_eval(int cmos_cmd)
1215{
1216 if (cmos_handle)
1217 return acpi_evalf(cmos_handle, NULL, NULL, "vd", cmos_cmd);
1218 else
1219 return 1;
1220}
1221
1222static int cmos_write(char *buf)
1223{
1224 char *cmd;
1225 int cmos_cmd;
1226
1227 if (!cmos_handle)
1228 return -EINVAL;
1229
1230 while ((cmd = next_cmd(&buf))) {
1231 if (sscanf(cmd, "%u", &cmos_cmd) == 1 &&
1232 cmos_cmd >= 0 && cmos_cmd <= 21) {
1233 /* cmos_cmd set */
1234 } else
1235 return -EINVAL;
1236
1237 if (!cmos_eval(cmos_cmd))
1238 return -EIO;
1239 }
1240
1241 return 0;
1242}
1243
1244enum led_access_mode {
1245 IBMACPI_LED_NONE = 0,
1246 IBMACPI_LED_570, /* 570 */
1247 IBMACPI_LED_OLD, /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20-21 */
1248 IBMACPI_LED_NEW, /* all others */
1249};
1250static enum led_access_mode led_supported;
1251
1252static int led_init(void)
1253{
1254 if (!led_handle)
1255 /* led not supported on R30, R31 */
1256 led_supported = IBMACPI_LED_NONE;
1257 else if (strlencmp(led_path, "SLED") == 0)
1258 /* 570 */
1259 led_supported = IBMACPI_LED_570;
1260 else if (strlencmp(led_path, "SYSL") == 0)
1261 /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20-21 */
1262 led_supported = IBMACPI_LED_OLD;
1263 else
1264 /* all others */
1265 led_supported = IBMACPI_LED_NEW;
1266
1267 return 0;
1268}
1269
1270#define led_status(s) ((s) == 0 ? "off" : ((s) == 1 ? "on" : "blinking"))
1271
1272static int led_read(char *p)
1273{
1274 int len = 0;
1275
1276 if (!led_supported) {
1277 len += sprintf(p + len, "status:\t\tnot supported\n");
1278 return len;
1279 }
1280 len += sprintf(p + len, "status:\t\tsupported\n");
1281
1282 if (led_supported == IBMACPI_LED_570) {
1283 /* 570 */
1284 int i, status;
1285 for (i = 0; i < 8; i++) {
1286 if (!acpi_evalf(ec_handle,
1287 &status, "GLED", "dd", 1 << i))
1288 return -EIO;
1289 len += sprintf(p + len, "%d:\t\t%s\n",
1290 i, led_status(status));
1291 }
1292 }
1293
1294 len += sprintf(p + len, "commands:\t"
1295 "<led> on, <led> off, <led> blink (<led> is 0-7)\n");
1296
1297 return len;
1298}
1299
1300/* off, on, blink */
1301static const int led_sled_arg1[] = { 0, 1, 3 };
1302static const int led_exp_hlbl[] = { 0, 0, 1 }; /* led# * */
1303static const int led_exp_hlcl[] = { 0, 1, 1 }; /* led# * */
1304static const int led_led_arg1[] = { 0, 0x80, 0xc0 };
1305
1306#define EC_HLCL 0x0c
1307#define EC_HLBL 0x0d
1308#define EC_HLMS 0x0e
1309
1310static int led_write(char *buf)
1311{
1312 char *cmd;
1313 int led, ind, ret;
1314
1315 if (!led_supported)
1316 return -ENODEV;
1317
1318 while ((cmd = next_cmd(&buf))) {
1319 if (sscanf(cmd, "%d", &led) != 1 || led < 0 || led > 7)
1320 return -EINVAL;
1321
1322 if (strstr(cmd, "off")) {
1323 ind = 0;
1324 } else if (strstr(cmd, "on")) {
1325 ind = 1;
1326 } else if (strstr(cmd, "blink")) {
1327 ind = 2;
1328 } else
1329 return -EINVAL;
1330
1331 if (led_supported == IBMACPI_LED_570) {
1332 /* 570 */
1333 led = 1 << led;
1334 if (!acpi_evalf(led_handle, NULL, NULL, "vdd",
1335 led, led_sled_arg1[ind]))
1336 return -EIO;
1337 } else if (led_supported == IBMACPI_LED_OLD) {
1338 /* 600e/x, 770e, 770x, A21e, A2xm/p, T20-22, X20 */
1339 led = 1 << led;
1340 ret = ec_write(EC_HLMS, led);
1341 if (ret >= 0)
1342 ret =
1343 ec_write(EC_HLBL, led * led_exp_hlbl[ind]);
1344 if (ret >= 0)
1345 ret =
1346 ec_write(EC_HLCL, led * led_exp_hlcl[ind]);
1347 if (ret < 0)
1348 return ret;
1349 } else {
1350 /* all others */
1351 if (!acpi_evalf(led_handle, NULL, NULL, "vdd",
1352 led, led_led_arg1[ind]))
1353 return -EIO;
1354 }
1355 }
1356
1357 return 0;
1358}
1359
1360static int beep_read(char *p)
1361{
1362 int len = 0;
1363
1364 if (!beep_handle)
1365 len += sprintf(p + len, "status:\t\tnot supported\n");
1366 else {
1367 len += sprintf(p + len, "status:\t\tsupported\n");
1368 len += sprintf(p + len, "commands:\t<cmd> (<cmd> is 0-17)\n");
1369 }
1370
1371 return len;
1372}
1373
1374static int beep_write(char *buf)
1375{
1376 char *cmd;
1377 int beep_cmd;
1378
1379 if (!beep_handle)
1380 return -ENODEV;
1381
1382 while ((cmd = next_cmd(&buf))) {
1383 if (sscanf(cmd, "%u", &beep_cmd) == 1 &&
1384 beep_cmd >= 0 && beep_cmd <= 17) {
1385 /* beep_cmd set */
1386 } else
1387 return -EINVAL;
1388 if (!acpi_evalf(beep_handle, NULL, NULL, "vdd", beep_cmd, 0))
1389 return -EIO;
1390 }
1391
1392 return 0;
1393}
1394
1395static int acpi_ec_read(int i, u8 * p)
1396{
1397 int v;
1398
1399 if (ecrd_handle) {
1400 if (!acpi_evalf(ecrd_handle, &v, NULL, "dd", i))
1401 return 0;
1402 *p = v;
1403 } else {
1404 if (ec_read(i, p) < 0)
1405 return 0;
1406 }
1407
1408 return 1;
1409}
1410
1411static int acpi_ec_write(int i, u8 v)
1412{
1413 if (ecwr_handle) {
1414 if (!acpi_evalf(ecwr_handle, NULL, NULL, "vdd", i, v))
1415 return 0;
1416 } else {
1417 if (ec_write(i, v) < 0)
1418 return 0;
1419 }
1420
1421 return 1;
1422}
1423
1424static enum thermal_access_mode thermal_read_mode;
1425
1426static int thermal_init(void)
1427{
1428 u8 t, ta1, ta2;
1429 int i;
1430 int acpi_tmp7 = acpi_evalf(ec_handle, NULL, "TMP7", "qv");
1431
1432 if (ibm_thinkpad_ec_found && experimental) {
1433 /*
1434 * Direct EC access mode: sensors at registers
1435 * 0x78-0x7F, 0xC0-0xC7. Registers return 0x00 for
1436 * non-implemented, thermal sensors return 0x80 when
1437 * not available
1438 */
1439
1440 ta1 = ta2 = 0;
1441 for (i = 0; i < 8; i++) {
1442 if (likely(acpi_ec_read(0x78 + i, &t))) {
1443 ta1 |= t;
1444 } else {
1445 ta1 = 0;
1446 break;
1447 }
1448 if (likely(acpi_ec_read(0xC0 + i, &t))) {
1449 ta2 |= t;
1450 } else {
1451 ta1 = 0;
1452 break;
1453 }
1454 }
1455 if (ta1 == 0) {
1456 /* This is sheer paranoia, but we handle it anyway */
1457 if (acpi_tmp7) {
1458 printk(IBM_ERR
1459 "ThinkPad ACPI EC access misbehaving, "
1460 "falling back to ACPI TMPx access mode\n");
1461 thermal_read_mode = IBMACPI_THERMAL_ACPI_TMP07;
1462 } else {
1463 printk(IBM_ERR
1464 "ThinkPad ACPI EC access misbehaving, "
1465 "disabling thermal sensors access\n");
1466 thermal_read_mode = IBMACPI_THERMAL_NONE;
1467 }
1468 } else {
1469 thermal_read_mode =
1470 (ta2 != 0) ?
1471 IBMACPI_THERMAL_TPEC_16 : IBMACPI_THERMAL_TPEC_8;
1472 }
1473 } else if (acpi_tmp7) {
1474 if (acpi_evalf(ec_handle, NULL, "UPDT", "qv")) {
1475 /* 600e/x, 770e, 770x */
1476 thermal_read_mode = IBMACPI_THERMAL_ACPI_UPDT;
1477 } else {
1478 /* Standard ACPI TMPx access, max 8 sensors */
1479 thermal_read_mode = IBMACPI_THERMAL_ACPI_TMP07;
1480 }
1481 } else {
1482 /* temperatures not supported on 570, G4x, R30, R31, R32 */
1483 thermal_read_mode = IBMACPI_THERMAL_NONE;
1484 }
1485
1486 return 0;
1487}
1488
1489static int thermal_get_sensors(struct ibm_thermal_sensors_struct *s)
1490{
1491 int i, t;
1492 s8 tmp;
1493 char tmpi[] = "TMPi";
1494
1495 if (!s)
1496 return -EINVAL;
1497
1498 switch (thermal_read_mode) {
1499#if IBMACPI_MAX_THERMAL_SENSORS >= 16
1500 case IBMACPI_THERMAL_TPEC_16:
1501 for (i = 0; i < 8; i++) {
1502 if (!acpi_ec_read(0xC0 + i, &tmp))
1503 return -EIO;
1504 s->temp[i + 8] = tmp * 1000;
1505 }
1506 /* fallthrough */
1507#endif
1508 case IBMACPI_THERMAL_TPEC_8:
1509 for (i = 0; i < 8; i++) {
1510 if (!acpi_ec_read(0x78 + i, &tmp))
1511 return -EIO;
1512 s->temp[i] = tmp * 1000;
1513 }
1514 return (thermal_read_mode == IBMACPI_THERMAL_TPEC_16) ? 16 : 8;
1515
1516 case IBMACPI_THERMAL_ACPI_UPDT:
1517 if (!acpi_evalf(ec_handle, NULL, "UPDT", "v"))
1518 return -EIO;
1519 for (i = 0; i < 8; i++) {
1520 tmpi[3] = '0' + i;
1521 if (!acpi_evalf(ec_handle, &t, tmpi, "d"))
1522 return -EIO;
1523 s->temp[i] = (t - 2732) * 100;
1524 }
1525 return 8;
1526
1527 case IBMACPI_THERMAL_ACPI_TMP07:
1528 for (i = 0; i < 8; i++) {
1529 tmpi[3] = '0' + i;
1530 if (!acpi_evalf(ec_handle, &t, tmpi, "d"))
1531 return -EIO;
1532 s->temp[i] = t * 1000;
1533 }
1534 return 8;
1535
1536 case IBMACPI_THERMAL_NONE:
1537 default:
1538 return 0;
1539 }
1540}
1541
1542static int thermal_read(char *p)
1543{
1544 int len = 0;
1545 int n, i;
1546 struct ibm_thermal_sensors_struct t;
1547
1548 n = thermal_get_sensors(&t);
1549 if (unlikely(n < 0))
1550 return n;
1551
1552 len += sprintf(p + len, "temperatures:\t");
1553
1554 if (n > 0) {
1555 for (i = 0; i < (n - 1); i++)
1556 len += sprintf(p + len, "%d ", t.temp[i] / 1000);
1557 len += sprintf(p + len, "%d\n", t.temp[i] / 1000);
1558 } else
1559 len += sprintf(p + len, "not supported\n");
1560
1561 return len;
1562}
1563
1564static u8 ecdump_regs[256];
1565
1566static int ecdump_read(char *p)
1567{
1568 int len = 0;
1569 int i, j;
1570 u8 v;
1571
1572 len += sprintf(p + len, "EC "
1573 " +00 +01 +02 +03 +04 +05 +06 +07"
1574 " +08 +09 +0a +0b +0c +0d +0e +0f\n");
1575 for (i = 0; i < 256; i += 16) {
1576 len += sprintf(p + len, "EC 0x%02x:", i);
1577 for (j = 0; j < 16; j++) {
1578 if (!acpi_ec_read(i + j, &v))
1579 break;
1580 if (v != ecdump_regs[i + j])
1581 len += sprintf(p + len, " *%02x", v);
1582 else
1583 len += sprintf(p + len, " %02x", v);
1584 ecdump_regs[i + j] = v;
1585 }
1586 len += sprintf(p + len, "\n");
1587 if (j != 16)
1588 break;
1589 }
1590
1591 /* These are way too dangerous to advertise openly... */
1592#if 0
1593 len += sprintf(p + len, "commands:\t0x<offset> 0x<value>"
1594 " (<offset> is 00-ff, <value> is 00-ff)\n");
1595 len += sprintf(p + len, "commands:\t0x<offset> <value> "
1596 " (<offset> is 00-ff, <value> is 0-255)\n");
1597#endif
1598 return len;
1599}
1600
1601static int ecdump_write(char *buf)
1602{
1603 char *cmd;
1604 int i, v;
1605
1606 while ((cmd = next_cmd(&buf))) {
1607 if (sscanf(cmd, "0x%x 0x%x", &i, &v) == 2) {
1608 /* i and v set */
1609 } else if (sscanf(cmd, "0x%x %u", &i, &v) == 2) {
1610 /* i and v set */
1611 } else
1612 return -EINVAL;
1613 if (i >= 0 && i < 256 && v >= 0 && v < 256) {
1614 if (!acpi_ec_write(i, v))
1615 return -EIO;
1616 } else
1617 return -EINVAL;
1618 }
1619
1620 return 0;
1621}
1622
1623static int brightness_offset = 0x31;
1624
1625static int brightness_get(struct backlight_device *bd)
1626{
1627 u8 level;
1628 if (!acpi_ec_read(brightness_offset, &level))
1629 return -EIO;
1630
1631 level &= 0x7;
1632
1633 return level;
1634}
1635
1636static int brightness_read(char *p)
1637{
1638 int len = 0;
1639 int level;
1640
1641 if ((level = brightness_get(NULL)) < 0) {
1642 len += sprintf(p + len, "level:\t\tunreadable\n");
1643 } else {
1644 len += sprintf(p + len, "level:\t\t%d\n", level & 0x7);
1645 len += sprintf(p + len, "commands:\tup, down\n");
1646 len += sprintf(p + len, "commands:\tlevel <level>"
1647 " (<level> is 0-7)\n");
1648 }
1649
1650 return len;
1651}
1652
1653#define BRIGHTNESS_UP 4
1654#define BRIGHTNESS_DOWN 5
1655
1656static int brightness_set(int value)
1657{
1658 int cmos_cmd, inc, i;
1659 int current_value = brightness_get(NULL);
1660
1661 value &= 7;
1662
1663 cmos_cmd = value > current_value ? BRIGHTNESS_UP : BRIGHTNESS_DOWN;
1664 inc = value > current_value ? 1 : -1;
1665 for (i = current_value; i != value; i += inc) {
1666 if (!cmos_eval(cmos_cmd))
1667 return -EIO;
1668 if (!acpi_ec_write(brightness_offset, i + inc))
1669 return -EIO;
1670 }
1671
1672 return 0;
1673}
1674
1675static int brightness_write(char *buf)
1676{
1677 int level;
1678 int new_level;
1679 char *cmd;
1680
1681 while ((cmd = next_cmd(&buf))) {
1682 if ((level = brightness_get(NULL)) < 0)
1683 return level;
1684 level &= 7;
1685
1686 if (strlencmp(cmd, "up") == 0) {
1687 new_level = level == 7 ? 7 : level + 1;
1688 } else if (strlencmp(cmd, "down") == 0) {
1689 new_level = level == 0 ? 0 : level - 1;
1690 } else if (sscanf(cmd, "level %d", &new_level) == 1 &&
1691 new_level >= 0 && new_level <= 7) {
1692 /* new_level set */
1693 } else
1694 return -EINVAL;
1695
1696 brightness_set(new_level);
1697 }
1698
1699 return 0;
1700}
1701
1702static int brightness_update_status(struct backlight_device *bd)
1703{
1704 return brightness_set(bd->props.brightness);
1705}
1706
1707static struct backlight_ops ibm_backlight_data = {
1708 .get_brightness = brightness_get,
1709 .update_status = brightness_update_status,
1710};
1711
1712static int brightness_init(void)
1713{
1714 ibm_backlight_device = backlight_device_register("ibm", NULL, NULL,
1715 &ibm_backlight_data);
1716 if (IS_ERR(ibm_backlight_device)) {
1717 printk(IBM_ERR "Could not register backlight device\n");
1718 return PTR_ERR(ibm_backlight_device);
1719 }
1720
1721 ibm_backlight_device->props.max_brightness = 7;
1722
1723 return 0;
1724}
1725
1726static void brightness_exit(void)
1727{
1728 if (ibm_backlight_device) {
1729 backlight_device_unregister(ibm_backlight_device);
1730 ibm_backlight_device = NULL;
1731 }
1732}
1733
1734static int volume_offset = 0x30;
1735
1736static int volume_read(char *p)
1737{
1738 int len = 0;
1739 u8 level;
1740
1741 if (!acpi_ec_read(volume_offset, &level)) {
1742 len += sprintf(p + len, "level:\t\tunreadable\n");
1743 } else {
1744 len += sprintf(p + len, "level:\t\t%d\n", level & 0xf);
1745 len += sprintf(p + len, "mute:\t\t%s\n", onoff(level, 6));
1746 len += sprintf(p + len, "commands:\tup, down, mute\n");
1747 len += sprintf(p + len, "commands:\tlevel <level>"
1748 " (<level> is 0-15)\n");
1749 }
1750
1751 return len;
1752}
1753
1754#define VOLUME_DOWN 0
1755#define VOLUME_UP 1
1756#define VOLUME_MUTE 2
1757
1758static int volume_write(char *buf)
1759{
1760 int cmos_cmd, inc, i;
1761 u8 level, mute;
1762 int new_level, new_mute;
1763 char *cmd;
1764
1765 while ((cmd = next_cmd(&buf))) {
1766 if (!acpi_ec_read(volume_offset, &level))
1767 return -EIO;
1768 new_mute = mute = level & 0x40;
1769 new_level = level = level & 0xf;
1770
1771 if (strlencmp(cmd, "up") == 0) {
1772 if (mute)
1773 new_mute = 0;
1774 else
1775 new_level = level == 15 ? 15 : level + 1;
1776 } else if (strlencmp(cmd, "down") == 0) {
1777 if (mute)
1778 new_mute = 0;
1779 else
1780 new_level = level == 0 ? 0 : level - 1;
1781 } else if (sscanf(cmd, "level %d", &new_level) == 1 &&
1782 new_level >= 0 && new_level <= 15) {
1783 /* new_level set */
1784 } else if (strlencmp(cmd, "mute") == 0) {
1785 new_mute = 0x40;
1786 } else
1787 return -EINVAL;
1788
1789 if (new_level != level) { /* mute doesn't change */
1790 cmos_cmd = new_level > level ? VOLUME_UP : VOLUME_DOWN;
1791 inc = new_level > level ? 1 : -1;
1792
1793 if (mute && (!cmos_eval(cmos_cmd) ||
1794 !acpi_ec_write(volume_offset, level)))
1795 return -EIO;
1796
1797 for (i = level; i != new_level; i += inc)
1798 if (!cmos_eval(cmos_cmd) ||
1799 !acpi_ec_write(volume_offset, i + inc))
1800 return -EIO;
1801
1802 if (mute && (!cmos_eval(VOLUME_MUTE) ||
1803 !acpi_ec_write(volume_offset,
1804 new_level + mute)))
1805 return -EIO;
1806 }
1807
1808 if (new_mute != mute) { /* level doesn't change */
1809 cmos_cmd = new_mute ? VOLUME_MUTE : VOLUME_UP;
1810
1811 if (!cmos_eval(cmos_cmd) ||
1812 !acpi_ec_write(volume_offset, level + new_mute))
1813 return -EIO;
1814 }
1815 }
1816
1817 return 0;
1818}
1819
1820static enum fan_status_access_mode fan_status_access_mode;
1821static enum fan_control_access_mode fan_control_access_mode;
1822static enum fan_control_commands fan_control_commands;
1823
1824static int fan_control_status_known;
1825static u8 fan_control_initial_status;
1826
1827static void fan_watchdog_fire(struct work_struct *ignored);
1828static int fan_watchdog_maxinterval;
1829static DECLARE_DELAYED_WORK(fan_watchdog_task, fan_watchdog_fire);
1830
1831static int fan_init(void)
1832{
1833 fan_status_access_mode = IBMACPI_FAN_NONE;
1834 fan_control_access_mode = IBMACPI_FAN_WR_NONE;
1835 fan_control_commands = 0;
1836 fan_control_status_known = 1;
1837 fan_watchdog_maxinterval = 0;
1838
1839 if (gfan_handle) {
1840 /* 570, 600e/x, 770e, 770x */
1841 fan_status_access_mode = IBMACPI_FAN_RD_ACPI_GFAN;
1842 } else {
1843 /* all other ThinkPads: note that even old-style
1844 * ThinkPad ECs supports the fan control register */
1845 if (likely(acpi_ec_read(fan_status_offset,
1846 &fan_control_initial_status))) {
1847 fan_status_access_mode = IBMACPI_FAN_RD_TPEC;
1848
1849 /* In some ThinkPads, neither the EC nor the ACPI
1850 * DSDT initialize the fan status, and it ends up
1851 * being set to 0x07 when it *could* be either
1852 * 0x07 or 0x80.
1853 *
1854 * Enable for TP-1Y (T43), TP-78 (R51e),
1855 * TP-76 (R52), TP-70 (T43, R52), which are known
1856 * to be buggy. */
1857 if (fan_control_initial_status == 0x07 &&
1858 ibm_thinkpad_ec_found &&
1859 ((ibm_thinkpad_ec_found[0] == '1' &&
1860 ibm_thinkpad_ec_found[1] == 'Y') ||
1861 (ibm_thinkpad_ec_found[0] == '7' &&
1862 (ibm_thinkpad_ec_found[1] == '6' ||
1863 ibm_thinkpad_ec_found[1] == '8' ||
1864 ibm_thinkpad_ec_found[1] == '0'))
1865 )) {
1866 printk(IBM_NOTICE
1867 "fan_init: initial fan status is "
1868 "unknown, assuming it is in auto "
1869 "mode\n");
1870 fan_control_status_known = 0;
1871 }
1872 } else {
1873 printk(IBM_ERR
1874 "ThinkPad ACPI EC access misbehaving, "
1875 "fan status and control unavailable\n");
1876 return 0;
1877 }
1878 }
1879
1880 if (sfan_handle) {
1881 /* 570, 770x-JL */
1882 fan_control_access_mode = IBMACPI_FAN_WR_ACPI_SFAN;
1883 fan_control_commands |=
1884 IBMACPI_FAN_CMD_LEVEL | IBMACPI_FAN_CMD_ENABLE;
1885 } else {
1886 if (!gfan_handle) {
1887 /* gfan without sfan means no fan control */
1888 /* all other models implement TP EC 0x2f control */
1889
1890 if (fans_handle) {
1891 /* X31, X40, X41 */
1892 fan_control_access_mode =
1893 IBMACPI_FAN_WR_ACPI_FANS;
1894 fan_control_commands |=
1895 IBMACPI_FAN_CMD_SPEED |
1896 IBMACPI_FAN_CMD_LEVEL |
1897 IBMACPI_FAN_CMD_ENABLE;
1898 } else {
1899 fan_control_access_mode = IBMACPI_FAN_WR_TPEC;
1900 fan_control_commands |=
1901 IBMACPI_FAN_CMD_LEVEL |
1902 IBMACPI_FAN_CMD_ENABLE;
1903 }
1904 }
1905 }
1906
1907 return 0;
1908}
1909
1910static int fan_get_status(u8 *status)
1911{
1912 u8 s;
1913
1914 /* TODO:
1915 * Add IBMACPI_FAN_RD_ACPI_FANS ? */
1916
1917 switch (fan_status_access_mode) {
1918 case IBMACPI_FAN_RD_ACPI_GFAN:
1919 /* 570, 600e/x, 770e, 770x */
1920
1921 if (unlikely(!acpi_evalf(gfan_handle, &s, NULL, "d")))
1922 return -EIO;
1923
1924 if (likely(status))
1925 *status = s & 0x07;
1926
1927 break;
1928
1929 case IBMACPI_FAN_RD_TPEC:
1930 /* all except 570, 600e/x, 770e, 770x */
1931 if (unlikely(!acpi_ec_read(fan_status_offset, &s)))
1932 return -EIO;
1933
1934 if (likely(status))
1935 *status = s;
1936
1937 break;
1938
1939 default:
1940 return -ENXIO;
1941 }
1942
1943 return 0;
1944}
1945
1946static int fan_get_speed(unsigned int *speed)
1947{
1948 u8 hi, lo;
1949
1950 switch (fan_status_access_mode) {
1951 case IBMACPI_FAN_RD_TPEC:
1952 /* all except 570, 600e/x, 770e, 770x */
1953 if (unlikely(!acpi_ec_read(fan_rpm_offset, &lo) ||
1954 !acpi_ec_read(fan_rpm_offset + 1, &hi)))
1955 return -EIO;
1956
1957 if (likely(speed))
1958 *speed = (hi << 8) | lo;
1959
1960 break;
1961
1962 default:
1963 return -ENXIO;
1964 }
1965
1966 return 0;
1967}
1968
1969static void fan_exit(void)
1970{
1971 cancel_delayed_work(&fan_watchdog_task);
1972 flush_scheduled_work();
1973}
1974
1975static void fan_watchdog_reset(void)
1976{
1977 static int fan_watchdog_active = 0;
1978
1979 if (fan_watchdog_active)
1980 cancel_delayed_work(&fan_watchdog_task);
1981
1982 if (fan_watchdog_maxinterval > 0) {
1983 fan_watchdog_active = 1;
1984 if (!schedule_delayed_work(&fan_watchdog_task,
1985 msecs_to_jiffies(fan_watchdog_maxinterval
1986 * 1000))) {
1987 printk(IBM_ERR "failed to schedule the fan watchdog, "
1988 "watchdog will not trigger\n");
1989 }
1990 } else
1991 fan_watchdog_active = 0;
1992}
1993
1994static int fan_read(char *p)
1995{
1996 int len = 0;
1997 int rc;
1998 u8 status;
1999 unsigned int speed = 0;
2000
2001 switch (fan_status_access_mode) {
2002 case IBMACPI_FAN_RD_ACPI_GFAN:
2003 /* 570, 600e/x, 770e, 770x */
2004 if ((rc = fan_get_status(&status)) < 0)
2005 return rc;
2006
2007 len += sprintf(p + len, "status:\t\t%s\n"
2008 "level:\t\t%d\n",
2009 (status != 0) ? "enabled" : "disabled", status);
2010 break;
2011
2012 case IBMACPI_FAN_RD_TPEC:
2013 /* all except 570, 600e/x, 770e, 770x */
2014 if ((rc = fan_get_status(&status)) < 0)
2015 return rc;
2016
2017 if (unlikely(!fan_control_status_known)) {
2018 if (status != fan_control_initial_status)
2019 fan_control_status_known = 1;
2020 else
2021 /* Return most likely status. In fact, it
2022 * might be the only possible status */
2023 status = IBMACPI_FAN_EC_AUTO;
2024 }
2025
2026 len += sprintf(p + len, "status:\t\t%s\n",
2027 (status != 0) ? "enabled" : "disabled");
2028
2029 /* No ThinkPad boots on disengaged mode, we can safely
2030 * assume the tachometer is online if fan control status
2031 * was unknown */
2032 if ((rc = fan_get_speed(&speed)) < 0)
2033 return rc;
2034
2035 len += sprintf(p + len, "speed:\t\t%d\n", speed);
2036
2037 if (status & IBMACPI_FAN_EC_DISENGAGED)
2038 /* Disengaged mode takes precedence */
2039 len += sprintf(p + len, "level:\t\tdisengaged\n");
2040 else if (status & IBMACPI_FAN_EC_AUTO)
2041 len += sprintf(p + len, "level:\t\tauto\n");
2042 else
2043 len += sprintf(p + len, "level:\t\t%d\n", status);
2044 break;
2045
2046 case IBMACPI_FAN_NONE:
2047 default:
2048 len += sprintf(p + len, "status:\t\tnot supported\n");
2049 }
2050
2051 if (fan_control_commands & IBMACPI_FAN_CMD_LEVEL) {
2052 len += sprintf(p + len, "commands:\tlevel <level>");
2053
2054 switch (fan_control_access_mode) {
2055 case IBMACPI_FAN_WR_ACPI_SFAN:
2056 len += sprintf(p + len, " (<level> is 0-7)\n");
2057 break;
2058
2059 default:
2060 len += sprintf(p + len, " (<level> is 0-7, "
2061 "auto, disengaged)\n");
2062 break;
2063 }
2064 }
2065
2066 if (fan_control_commands & IBMACPI_FAN_CMD_ENABLE)
2067 len += sprintf(p + len, "commands:\tenable, disable\n"
2068 "commands:\twatchdog <timeout> (<timeout> is 0 (off), "
2069 "1-120 (seconds))\n");
2070
2071 if (fan_control_commands & IBMACPI_FAN_CMD_SPEED)
2072 len += sprintf(p + len, "commands:\tspeed <speed>"
2073 " (<speed> is 0-65535)\n");
2074
2075 return len;
2076}
2077
2078static int fan_set_level(int level)
2079{
2080 switch (fan_control_access_mode) {
2081 case IBMACPI_FAN_WR_ACPI_SFAN:
2082 if (level >= 0 && level <= 7) {
2083 if (!acpi_evalf(sfan_handle, NULL, NULL, "vd", level))
2084 return -EIO;
2085 } else
2086 return -EINVAL;
2087 break;
2088
2089 case IBMACPI_FAN_WR_ACPI_FANS:
2090 case IBMACPI_FAN_WR_TPEC:
2091 if ((level != IBMACPI_FAN_EC_AUTO) &&
2092 (level != IBMACPI_FAN_EC_DISENGAGED) &&
2093 ((level < 0) || (level > 7)))
2094 return -EINVAL;
2095
2096 if (!acpi_ec_write(fan_status_offset, level))
2097 return -EIO;
2098 else
2099 fan_control_status_known = 1;
2100 break;
2101
2102 default:
2103 return -ENXIO;
2104 }
2105 return 0;
2106}
2107
2108static int fan_set_enable(void)
2109{
2110 u8 s;
2111 int rc;
2112
2113 switch (fan_control_access_mode) {
2114 case IBMACPI_FAN_WR_ACPI_FANS:
2115 case IBMACPI_FAN_WR_TPEC:
2116 if ((rc = fan_get_status(&s)) < 0)
2117 return rc;
2118
2119 /* Don't go out of emergency fan mode */
2120 if (s != 7)
2121 s = IBMACPI_FAN_EC_AUTO;
2122
2123 if (!acpi_ec_write(fan_status_offset, s))
2124 return -EIO;
2125 else
2126 fan_control_status_known = 1;
2127 break;
2128
2129 case IBMACPI_FAN_WR_ACPI_SFAN:
2130 if ((rc = fan_get_status(&s)) < 0)
2131 return rc;
2132
2133 s &= 0x07;
2134
2135 /* Set fan to at least level 4 */
2136 if (s < 4)
2137 s = 4;
2138
2139 if (!acpi_evalf(sfan_handle, NULL, NULL, "vd", s))
2140 return -EIO;
2141 break;
2142
2143 default:
2144 return -ENXIO;
2145 }
2146 return 0;
2147}
2148
2149static int fan_set_disable(void)
2150{
2151 switch (fan_control_access_mode) {
2152 case IBMACPI_FAN_WR_ACPI_FANS:
2153 case IBMACPI_FAN_WR_TPEC:
2154 if (!acpi_ec_write(fan_status_offset, 0x00))
2155 return -EIO;
2156 else
2157 fan_control_status_known = 1;
2158 break;
2159
2160 case IBMACPI_FAN_WR_ACPI_SFAN:
2161 if (!acpi_evalf(sfan_handle, NULL, NULL, "vd", 0x00))
2162 return -EIO;
2163 break;
2164
2165 default:
2166 return -ENXIO;
2167 }
2168 return 0;
2169}
2170
2171static int fan_set_speed(int speed)
2172{
2173 switch (fan_control_access_mode) {
2174 case IBMACPI_FAN_WR_ACPI_FANS:
2175 if (speed >= 0 && speed <= 65535) {
2176 if (!acpi_evalf(fans_handle, NULL, NULL, "vddd",
2177 speed, speed, speed))
2178 return -EIO;
2179 } else
2180 return -EINVAL;
2181 break;
2182
2183 default:
2184 return -ENXIO;
2185 }
2186 return 0;
2187}
2188
2189static int fan_write_cmd_level(const char *cmd, int *rc)
2190{
2191 int level;
2192
2193 if (strlencmp(cmd, "level auto") == 0)
2194 level = IBMACPI_FAN_EC_AUTO;
2195 else if (strlencmp(cmd, "level disengaged") == 0)
2196 level = IBMACPI_FAN_EC_DISENGAGED;
2197 else if (sscanf(cmd, "level %d", &level) != 1)
2198 return 0;
2199
2200 if ((*rc = fan_set_level(level)) == -ENXIO)
2201 printk(IBM_ERR "level command accepted for unsupported "
2202 "access mode %d", fan_control_access_mode);
2203
2204 return 1;
2205}
2206
2207static int fan_write_cmd_enable(const char *cmd, int *rc)
2208{
2209 if (strlencmp(cmd, "enable") != 0)
2210 return 0;
2211
2212 if ((*rc = fan_set_enable()) == -ENXIO)
2213 printk(IBM_ERR "enable command accepted for unsupported "
2214 "access mode %d", fan_control_access_mode);
2215
2216 return 1;
2217}
2218
2219static int fan_write_cmd_disable(const char *cmd, int *rc)
2220{
2221 if (strlencmp(cmd, "disable") != 0)
2222 return 0;
2223
2224 if ((*rc = fan_set_disable()) == -ENXIO)
2225 printk(IBM_ERR "disable command accepted for unsupported "
2226 "access mode %d", fan_control_access_mode);
2227
2228 return 1;
2229}
2230
2231static int fan_write_cmd_speed(const char *cmd, int *rc)
2232{
2233 int speed;
2234
2235 /* TODO:
2236 * Support speed <low> <medium> <high> ? */
2237
2238 if (sscanf(cmd, "speed %d", &speed) != 1)
2239 return 0;
2240
2241 if ((*rc = fan_set_speed(speed)) == -ENXIO)
2242 printk(IBM_ERR "speed command accepted for unsupported "
2243 "access mode %d", fan_control_access_mode);
2244
2245 return 1;
2246}
2247
2248static int fan_write_cmd_watchdog(const char *cmd, int *rc)
2249{
2250 int interval;
2251
2252 if (sscanf(cmd, "watchdog %d", &interval) != 1)
2253 return 0;
2254
2255 if (interval < 0 || interval > 120)
2256 *rc = -EINVAL;
2257 else
2258 fan_watchdog_maxinterval = interval;
2259
2260 return 1;
2261}
2262
2263static int fan_write(char *buf)
2264{
2265 char *cmd;
2266 int rc = 0;
2267
2268 while (!rc && (cmd = next_cmd(&buf))) {
2269 if (!((fan_control_commands & IBMACPI_FAN_CMD_LEVEL) &&
2270 fan_write_cmd_level(cmd, &rc)) &&
2271 !((fan_control_commands & IBMACPI_FAN_CMD_ENABLE) &&
2272 (fan_write_cmd_enable(cmd, &rc) ||
2273 fan_write_cmd_disable(cmd, &rc) ||
2274 fan_write_cmd_watchdog(cmd, &rc))) &&
2275 !((fan_control_commands & IBMACPI_FAN_CMD_SPEED) &&
2276 fan_write_cmd_speed(cmd, &rc))
2277 )
2278 rc = -EINVAL;
2279 else if (!rc)
2280 fan_watchdog_reset();
2281 }
2282
2283 return rc;
2284}
2285
2286static void fan_watchdog_fire(struct work_struct *ignored)
2287{
2288 printk(IBM_NOTICE "fan watchdog: enabling fan\n");
2289 if (fan_set_enable()) {
2290 printk(IBM_ERR "fan watchdog: error while enabling fan\n");
2291 /* reschedule for later */
2292 fan_watchdog_reset();
2293 }
2294}
2295
2296static struct ibm_struct ibms[] = {
2297 {
2298 .name = "driver",
2299 .init = ibm_acpi_driver_init,
2300 .read = driver_read,
2301 },
2302 {
2303 .name = "hotkey",
2304 .hid = IBM_HKEY_HID,
2305 .init = hotkey_init,
2306 .read = hotkey_read,
2307 .write = hotkey_write,
2308 .exit = hotkey_exit,
2309 .notify = hotkey_notify,
2310 .handle = &hkey_handle,
2311 .type = ACPI_DEVICE_NOTIFY,
2312 },
2313 {
2314 .name = "bluetooth",
2315 .init = bluetooth_init,
2316 .read = bluetooth_read,
2317 .write = bluetooth_write,
2318 },
2319 {
2320 .name = "wan",
2321 .init = wan_init,
2322 .read = wan_read,
2323 .write = wan_write,
2324 .experimental = 1,
2325 },
2326 {
2327 .name = "video",
2328 .init = video_init,
2329 .read = video_read,
2330 .write = video_write,
2331 .exit = video_exit,
2332 },
2333 {
2334 .name = "light",
2335 .init = light_init,
2336 .read = light_read,
2337 .write = light_write,
2338 },
2339#ifdef CONFIG_ACPI_IBM_DOCK
2340 {
2341 .name = "dock",
2342 .read = dock_read,
2343 .write = dock_write,
2344 .notify = dock_notify,
2345 .handle = &dock_handle,
2346 .type = ACPI_SYSTEM_NOTIFY,
2347 },
2348 {
2349 .name = "dock",
2350 .hid = IBM_PCI_HID,
2351 .notify = dock_notify,
2352 .handle = &pci_handle,
2353 .type = ACPI_SYSTEM_NOTIFY,
2354 },
2355#endif
2356 {
2357 .name = "bay",
2358 .init = bay_init,
2359 .read = bay_read,
2360 .write = bay_write,
2361 .notify = bay_notify,
2362 .handle = &bay_handle,
2363 .type = ACPI_SYSTEM_NOTIFY,
2364 },
2365 {
2366 .name = "cmos",
2367 .read = cmos_read,
2368 .write = cmos_write,
2369 },
2370 {
2371 .name = "led",
2372 .init = led_init,
2373 .read = led_read,
2374 .write = led_write,
2375 },
2376 {
2377 .name = "beep",
2378 .read = beep_read,
2379 .write = beep_write,
2380 },
2381 {
2382 .name = "thermal",
2383 .init = thermal_init,
2384 .read = thermal_read,
2385 },
2386 {
2387 .name = "ecdump",
2388 .read = ecdump_read,
2389 .write = ecdump_write,
2390 .experimental = 1,
2391 },
2392 {
2393 .name = "brightness",
2394 .read = brightness_read,
2395 .write = brightness_write,
2396 .init = brightness_init,
2397 .exit = brightness_exit,
2398 },
2399 {
2400 .name = "volume",
2401 .read = volume_read,
2402 .write = volume_write,
2403 },
2404 {
2405 .name = "fan",
2406 .read = fan_read,
2407 .write = fan_write,
2408 .init = fan_init,
2409 .exit = fan_exit,
2410 .experimental = 1,
2411 },
2412};
2413
2414static int dispatch_read(char *page, char **start, off_t off, int count,
2415 int *eof, void *data)
2416{
2417 struct ibm_struct *ibm = data;
2418 int len;
2419
2420 if (!ibm || !ibm->read)
2421 return -EINVAL;
2422
2423 len = ibm->read(page);
2424 if (len < 0)
2425 return len;
2426
2427 if (len <= off + count)
2428 *eof = 1;
2429 *start = page + off;
2430 len -= off;
2431 if (len > count)
2432 len = count;
2433 if (len < 0)
2434 len = 0;
2435
2436 return len;
2437}
2438
2439static int dispatch_write(struct file *file, const char __user * userbuf,
2440 unsigned long count, void *data)
2441{
2442 struct ibm_struct *ibm = data;
2443 char *kernbuf;
2444 int ret;
2445
2446 if (!ibm || !ibm->write)
2447 return -EINVAL;
2448
2449 kernbuf = kmalloc(count + 2, GFP_KERNEL);
2450 if (!kernbuf)
2451 return -ENOMEM;
2452
2453 if (copy_from_user(kernbuf, userbuf, count)) {
2454 kfree(kernbuf);
2455 return -EFAULT;
2456 }
2457
2458 kernbuf[count] = 0;
2459 strcat(kernbuf, ",");
2460 ret = ibm->write(kernbuf);
2461 if (ret == 0)
2462 ret = count;
2463
2464 kfree(kernbuf);
2465
2466 return ret;
2467}
2468
2469static void dispatch_notify(acpi_handle handle, u32 event, void *data)
2470{
2471 struct ibm_struct *ibm = data;
2472
2473 if (!ibm || !ibm->notify)
2474 return;
2475
2476 ibm->notify(ibm, event);
2477}
2478
2479static int __init setup_notify(struct ibm_struct *ibm)
2480{
2481 acpi_status status;
2482 int ret;
2483
2484 if (!*ibm->handle)
2485 return 0;
2486
2487 ret = acpi_bus_get_device(*ibm->handle, &ibm->device);
2488 if (ret < 0) {
2489 printk(IBM_ERR "%s device not present\n", ibm->name);
2490 return 0;
2491 }
2492
2493 acpi_driver_data(ibm->device) = ibm;
2494 sprintf(acpi_device_class(ibm->device), "%s/%s", IBM_NAME, ibm->name);
2495
2496 status = acpi_install_notify_handler(*ibm->handle, ibm->type,
2497 dispatch_notify, ibm);
2498 if (ACPI_FAILURE(status)) {
2499 printk(IBM_ERR "acpi_install_notify_handler(%s) failed: %d\n",
2500 ibm->name, status);
2501 return -ENODEV;
2502 }
2503 ibm->notify_installed = 1;
2504 return 0;
2505}
2506
2507static int __init ibm_device_add(struct acpi_device *device)
2508{
2509 return 0;
2510}
2511
2512static int __init register_driver(struct ibm_struct *ibm)
2513{
2514 int ret;
2515
2516 ibm->driver = kzalloc(sizeof(struct acpi_driver), GFP_KERNEL);
2517 if (!ibm->driver) {
2518 printk(IBM_ERR "kmalloc(ibm->driver) failed\n");
2519 return -1;
2520 }
2521
2522 sprintf(ibm->driver->name, "%s_%s", IBM_NAME, ibm->name);
2523 ibm->driver->ids = ibm->hid;
2524 ibm->driver->ops.add = &ibm_device_add;
2525
2526 ret = acpi_bus_register_driver(ibm->driver);
2527 if (ret < 0) {
2528 printk(IBM_ERR "acpi_bus_register_driver(%s) failed: %d\n",
2529 ibm->hid, ret);
2530 kfree(ibm->driver);
2531 }
2532
2533 return ret;
2534}
2535
2536static int __init ibm_init(struct ibm_struct *ibm)
2537{
2538 int ret;
2539 struct proc_dir_entry *entry;
2540
2541 if (ibm->experimental && !experimental)
2542 return 0;
2543
2544 if (ibm->hid) {
2545 ret = register_driver(ibm);
2546 if (ret < 0)
2547 return ret;
2548 ibm->driver_registered = 1;
2549 }
2550
2551 if (ibm->init) {
2552 ret = ibm->init();
2553 if (ret != 0)
2554 return ret;
2555 ibm->init_called = 1;
2556 }
2557
2558 if (ibm->read) {
2559 entry = create_proc_entry(ibm->name,
2560 S_IFREG | S_IRUGO | S_IWUSR,
2561 proc_dir);
2562 if (!entry) {
2563 printk(IBM_ERR "unable to create proc entry %s\n",
2564 ibm->name);
2565 return -ENODEV;
2566 }
2567 entry->owner = THIS_MODULE;
2568 entry->data = ibm;
2569 entry->read_proc = &dispatch_read;
2570 if (ibm->write)
2571 entry->write_proc = &dispatch_write;
2572 ibm->proc_created = 1;
2573 }
2574
2575 if (ibm->notify) {
2576 ret = setup_notify(ibm);
2577 if (ret < 0)
2578 return ret;
2579 }
2580
2581 return 0;
2582}
2583
2584static void ibm_exit(struct ibm_struct *ibm)
2585{
2586 if (ibm->notify_installed)
2587 acpi_remove_notify_handler(*ibm->handle, ibm->type,
2588 dispatch_notify);
2589
2590 if (ibm->proc_created)
2591 remove_proc_entry(ibm->name, proc_dir);
2592
2593 if (ibm->init_called && ibm->exit)
2594 ibm->exit();
2595
2596 if (ibm->driver_registered) {
2597 acpi_bus_unregister_driver(ibm->driver);
2598 kfree(ibm->driver);
2599 }
2600}
2601
2602static void __init ibm_handle_init(char *name,
2603 acpi_handle * handle, acpi_handle parent,
2604 char **paths, int num_paths, char **path)
2605{
2606 int i;
2607 acpi_status status;
2608
2609 for (i = 0; i < num_paths; i++) {
2610 status = acpi_get_handle(parent, paths[i], handle);
2611 if (ACPI_SUCCESS(status)) {
2612 *path = paths[i];
2613 return;
2614 }
2615 }
2616
2617 *handle = NULL;
2618}
2619
2620#define IBM_HANDLE_INIT(object) \
2621 ibm_handle_init(#object, &object##_handle, *object##_parent, \
2622 object##_paths, ARRAY_SIZE(object##_paths), &object##_path)
2623
2624static int __init set_ibm_param(const char *val, struct kernel_param *kp)
2625{
2626 unsigned int i;
2627
2628 for (i = 0; i < ARRAY_SIZE(ibms); i++)
2629 if (strcmp(ibms[i].name, kp->name) == 0 && ibms[i].write) {
2630 if (strlen(val) > sizeof(ibms[i].param) - 2)
2631 return -ENOSPC;
2632 strcpy(ibms[i].param, val);
2633 strcat(ibms[i].param, ",");
2634 return 0;
2635 }
2636
2637 return -EINVAL;
2638}
2639
2640#define IBM_PARAM(feature) \
2641 module_param_call(feature, set_ibm_param, NULL, NULL, 0)
2642
2643IBM_PARAM(hotkey);
2644IBM_PARAM(bluetooth);
2645IBM_PARAM(video);
2646IBM_PARAM(light);
2647#ifdef CONFIG_ACPI_IBM_DOCK
2648IBM_PARAM(dock);
2649#endif
2650IBM_PARAM(bay);
2651IBM_PARAM(cmos);
2652IBM_PARAM(led);
2653IBM_PARAM(beep);
2654IBM_PARAM(ecdump);
2655IBM_PARAM(brightness);
2656IBM_PARAM(volume);
2657IBM_PARAM(fan);
2658
2659static void acpi_ibm_exit(void)
2660{
2661 int i;
2662
2663 for (i = ARRAY_SIZE(ibms) - 1; i >= 0; i--)
2664 ibm_exit(&ibms[i]);
2665
2666 if (proc_dir)
2667 remove_proc_entry(IBM_DIR, acpi_root_dir);
2668
2669 if (ibm_thinkpad_ec_found)
2670 kfree(ibm_thinkpad_ec_found);
2671}
2672
2673static char* __init check_dmi_for_ec(void)
2674{
2675 struct dmi_device *dev = NULL;
2676 char ec_fw_string[18];
2677
2678 /*
2679 * ThinkPad T23 or newer, A31 or newer, R50e or newer,
2680 * X32 or newer, all Z series; Some models must have an
2681 * up-to-date BIOS or they will not be detected.
2682 *
2683 * See http://thinkwiki.org/wiki/List_of_DMI_IDs
2684 */
2685 while ((dev = dmi_find_device(DMI_DEV_TYPE_OEM_STRING, NULL, dev))) {
2686 if (sscanf(dev->name,
2687 "IBM ThinkPad Embedded Controller -[%17c",
2688 ec_fw_string) == 1) {
2689 ec_fw_string[sizeof(ec_fw_string) - 1] = 0;
2690 ec_fw_string[strcspn(ec_fw_string, " ]")] = 0;
2691 return kstrdup(ec_fw_string, GFP_KERNEL);
2692 }
2693 }
2694 return NULL;
2695}
2696
2697static int __init acpi_ibm_init(void)
2698{
2699 int ret, i;
2700
2701 if (acpi_disabled)
2702 return -ENODEV;
2703
2704 /* ec is required because many other handles are relative to it */
2705 IBM_HANDLE_INIT(ec);
2706 if (!ec_handle) {
2707 printk(IBM_ERR "ec object not found\n");
2708 return -ENODEV;
2709 }
2710
2711 /* Models with newer firmware report the EC in DMI */
2712 ibm_thinkpad_ec_found = check_dmi_for_ec();
2713
2714 /* these handles are not required */
2715 IBM_HANDLE_INIT(vid);
2716 IBM_HANDLE_INIT(vid2);
2717 IBM_HANDLE_INIT(ledb);
2718 IBM_HANDLE_INIT(led);
2719 IBM_HANDLE_INIT(hkey);
2720 IBM_HANDLE_INIT(lght);
2721 IBM_HANDLE_INIT(cmos);
2722#ifdef CONFIG_ACPI_IBM_DOCK
2723 IBM_HANDLE_INIT(dock);
2724#endif
2725 IBM_HANDLE_INIT(pci);
2726 IBM_HANDLE_INIT(bay);
2727 if (bay_handle)
2728 IBM_HANDLE_INIT(bay_ej);
2729 IBM_HANDLE_INIT(bay2);
2730 if (bay2_handle)
2731 IBM_HANDLE_INIT(bay2_ej);
2732 IBM_HANDLE_INIT(beep);
2733 IBM_HANDLE_INIT(ecrd);
2734 IBM_HANDLE_INIT(ecwr);
2735 IBM_HANDLE_INIT(fans);
2736 IBM_HANDLE_INIT(gfan);
2737 IBM_HANDLE_INIT(sfan);
2738
2739 proc_dir = proc_mkdir(IBM_DIR, acpi_root_dir);
2740 if (!proc_dir) {
2741 printk(IBM_ERR "unable to create proc dir %s", IBM_DIR);
2742 acpi_ibm_exit();
2743 return -ENODEV;
2744 }
2745 proc_dir->owner = THIS_MODULE;
2746
2747 for (i = 0; i < ARRAY_SIZE(ibms); i++) {
2748 ret = ibm_init(&ibms[i]);
2749 if (ret >= 0 && *ibms[i].param)
2750 ret = ibms[i].write(ibms[i].param);
2751 if (ret < 0) {
2752 acpi_ibm_exit();
2753 return ret;
2754 }
2755 }
2756
2757 return 0;
2758}
2759
2760module_init(acpi_ibm_init);
2761module_exit(acpi_ibm_exit);
diff --git a/drivers/acpi/namespace/nseval.c b/drivers/acpi/namespace/nseval.c
index aa6370c67ec1..26fd0dd6953d 100644
--- a/drivers/acpi/namespace/nseval.c
+++ b/drivers/acpi/namespace/nseval.c
@@ -154,7 +154,11 @@ acpi_status acpi_ns_evaluate(struct acpi_evaluate_info *info)
154 * Execute the method via the interpreter. The interpreter is locked 154 * Execute the method via the interpreter. The interpreter is locked
155 * here before calling into the AML parser 155 * here before calling into the AML parser
156 */ 156 */
157 acpi_ex_enter_interpreter(); 157 status = acpi_ex_enter_interpreter();
158 if (ACPI_FAILURE(status)) {
159 return_ACPI_STATUS(status);
160 }
161
158 status = acpi_ps_execute_method(info); 162 status = acpi_ps_execute_method(info);
159 acpi_ex_exit_interpreter(); 163 acpi_ex_exit_interpreter();
160 } else { 164 } else {
@@ -178,7 +182,10 @@ acpi_status acpi_ns_evaluate(struct acpi_evaluate_info *info)
178 * resolution, we must lock it because we could access an opregion. 182 * resolution, we must lock it because we could access an opregion.
179 * The opregion access code assumes that the interpreter is locked. 183 * The opregion access code assumes that the interpreter is locked.
180 */ 184 */
181 acpi_ex_enter_interpreter(); 185 status = acpi_ex_enter_interpreter();
186 if (ACPI_FAILURE(status)) {
187 return_ACPI_STATUS(status);
188 }
182 189
183 /* Function has a strange interface */ 190 /* Function has a strange interface */
184 191
diff --git a/drivers/acpi/namespace/nsinit.c b/drivers/acpi/namespace/nsinit.c
index 33db2241044e..c4ab615f77fe 100644
--- a/drivers/acpi/namespace/nsinit.c
+++ b/drivers/acpi/namespace/nsinit.c
@@ -214,7 +214,7 @@ acpi_ns_init_one_object(acpi_handle obj_handle,
214 u32 level, void *context, void **return_value) 214 u32 level, void *context, void **return_value)
215{ 215{
216 acpi_object_type type; 216 acpi_object_type type;
217 acpi_status status = AE_OK; 217 acpi_status status;
218 struct acpi_init_walk_info *info = 218 struct acpi_init_walk_info *info =
219 (struct acpi_init_walk_info *)context; 219 (struct acpi_init_walk_info *)context;
220 struct acpi_namespace_node *node = 220 struct acpi_namespace_node *node =
@@ -268,7 +268,10 @@ acpi_ns_init_one_object(acpi_handle obj_handle,
268 /* 268 /*
269 * Must lock the interpreter before executing AML code 269 * Must lock the interpreter before executing AML code
270 */ 270 */
271 acpi_ex_enter_interpreter(); 271 status = acpi_ex_enter_interpreter();
272 if (ACPI_FAILURE(status)) {
273 return (status);
274 }
272 275
273 /* 276 /*
274 * Each of these types can contain executable AML code within the 277 * Each of these types can contain executable AML code within the
diff --git a/drivers/acpi/namespace/nsxfeval.c b/drivers/acpi/namespace/nsxfeval.c
index 7ac6ace50059..8904d0fae6a2 100644
--- a/drivers/acpi/namespace/nsxfeval.c
+++ b/drivers/acpi/namespace/nsxfeval.c
@@ -170,6 +170,7 @@ acpi_evaluate_object(acpi_handle handle,
170 struct acpi_buffer *return_buffer) 170 struct acpi_buffer *return_buffer)
171{ 171{
172 acpi_status status; 172 acpi_status status;
173 acpi_status status2;
173 struct acpi_evaluate_info *info; 174 struct acpi_evaluate_info *info;
174 acpi_size buffer_space_needed; 175 acpi_size buffer_space_needed;
175 u32 i; 176 u32 i;
@@ -328,12 +329,14 @@ acpi_evaluate_object(acpi_handle handle,
328 * Delete the internal return object. NOTE: Interpreter must be 329 * Delete the internal return object. NOTE: Interpreter must be
329 * locked to avoid race condition. 330 * locked to avoid race condition.
330 */ 331 */
331 acpi_ex_enter_interpreter(); 332 status2 = acpi_ex_enter_interpreter();
333 if (ACPI_SUCCESS(status2)) {
332 334
333 /* Remove one reference on the return object (should delete it) */ 335 /* Remove one reference on the return object (should delete it) */
334 336
335 acpi_ut_remove_reference(info->return_object); 337 acpi_ut_remove_reference(info->return_object);
336 acpi_ex_exit_interpreter(); 338 acpi_ex_exit_interpreter();
339 }
337 } 340 }
338 341
339 cleanup: 342 cleanup:
diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c
index 971eca4864fa..c2bed56915e1 100644
--- a/drivers/acpi/osl.c
+++ b/drivers/acpi/osl.c
@@ -30,7 +30,6 @@
30#include <linux/slab.h> 30#include <linux/slab.h>
31#include <linux/mm.h> 31#include <linux/mm.h>
32#include <linux/pci.h> 32#include <linux/pci.h>
33#include <linux/smp_lock.h>
34#include <linux/interrupt.h> 33#include <linux/interrupt.h>
35#include <linux/kmod.h> 34#include <linux/kmod.h>
36#include <linux/delay.h> 35#include <linux/delay.h>
diff --git a/drivers/acpi/power.c b/drivers/acpi/power.c
index 1ef338545dfe..4ffecd179702 100644
--- a/drivers/acpi/power.c
+++ b/drivers/acpi/power.c
@@ -436,8 +436,6 @@ int acpi_power_transition(struct acpi_device *device, int state)
436 cl = &device->power.states[device->power.state].resources; 436 cl = &device->power.states[device->power.state].resources;
437 tl = &device->power.states[state].resources; 437 tl = &device->power.states[state].resources;
438 438
439 device->power.state = ACPI_STATE_UNKNOWN;
440
441 if (!cl->count && !tl->count) { 439 if (!cl->count && !tl->count) {
442 result = -ENODEV; 440 result = -ENODEV;
443 goto end; 441 goto end;
@@ -468,12 +466,15 @@ int acpi_power_transition(struct acpi_device *device, int state)
468 goto end; 466 goto end;
469 } 467 }
470 468
471 /* We shouldn't change the state till all above operations succeed */ 469 end:
472 device->power.state = state; 470 if (result) {
473 end: 471 device->power.state = ACPI_STATE_UNKNOWN;
474 if (result)
475 printk(KERN_WARNING PREFIX "Transitioning device [%s] to D%d\n", 472 printk(KERN_WARNING PREFIX "Transitioning device [%s] to D%d\n",
476 device->pnp.bus_id, state); 473 device->pnp.bus_id, state);
474 } else {
475 /* We shouldn't change the state till all above operations succeed */
476 device->power.state = state;
477 }
477 478
478 return result; 479 return result;
479} 480}
@@ -687,13 +688,6 @@ static int acpi_power_resume(struct acpi_device *device)
687 return result; 688 return result;
688 689
689 mutex_lock(&resource->resource_lock); 690 mutex_lock(&resource->resource_lock);
690 if ((resource->state == ACPI_POWER_RESOURCE_STATE_ON) &&
691 list_empty(&resource->reference)) {
692 mutex_unlock(&resource->resource_lock);
693 result = acpi_power_off_device(device->handle, NULL);
694 return result;
695 }
696
697 if ((resource->state == ACPI_POWER_RESOURCE_STATE_OFF) && 691 if ((resource->state == ACPI_POWER_RESOURCE_STATE_OFF) &&
698 !list_empty(&resource->reference)) { 692 !list_empty(&resource->reference)) {
699 ref = container_of(resource->reference.next, struct acpi_power_reference, node); 693 ref = container_of(resource->reference.next, struct acpi_power_reference, node);
diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c
index 99d1516d1e70..f7de02a6f497 100644
--- a/drivers/acpi/processor_core.c
+++ b/drivers/acpi/processor_core.c
@@ -70,8 +70,6 @@
70#define ACPI_PROCESSOR_LIMIT_USER 0 70#define ACPI_PROCESSOR_LIMIT_USER 0
71#define ACPI_PROCESSOR_LIMIT_THERMAL 1 71#define ACPI_PROCESSOR_LIMIT_THERMAL 1
72 72
73#define ACPI_STA_PRESENT 0x00000001
74
75#define _COMPONENT ACPI_PROCESSOR_COMPONENT 73#define _COMPONENT ACPI_PROCESSOR_COMPONENT
76ACPI_MODULE_NAME("processor_core"); 74ACPI_MODULE_NAME("processor_core");
77 75
@@ -779,7 +777,7 @@ static int is_processor_present(acpi_handle handle)
779 777
780 778
781 status = acpi_evaluate_integer(handle, "_STA", NULL, &sta); 779 status = acpi_evaluate_integer(handle, "_STA", NULL, &sta);
782 if (ACPI_FAILURE(status) || !(sta & ACPI_STA_PRESENT)) { 780 if (ACPI_FAILURE(status) || !(sta & ACPI_STA_DEVICE_PRESENT)) {
783 ACPI_EXCEPTION((AE_INFO, status, "Processor Device is not present")); 781 ACPI_EXCEPTION((AE_INFO, status, "Processor Device is not present"));
784 return 0; 782 return 0;
785 } 783 }
diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c
index 60773005b8af..ee5759bef945 100644
--- a/drivers/acpi/processor_idle.c
+++ b/drivers/acpi/processor_idle.c
@@ -51,14 +51,6 @@
51#include <asm/apic.h> 51#include <asm/apic.h>
52#endif 52#endif
53 53
54/*
55 * Include the apic definitions for x86 to have the APIC timer related defines
56 * available also for UP (on SMP it gets magically included via linux/smp.h).
57 */
58#ifdef CONFIG_X86
59#include <asm/apic.h>
60#endif
61
62#include <asm/io.h> 54#include <asm/io.h>
63#include <asm/uaccess.h> 55#include <asm/uaccess.h>
64 56
@@ -268,6 +260,7 @@ static void acpi_timer_check_state(int state, struct acpi_processor *pr,
268 struct acpi_processor_cx *cx) 260 struct acpi_processor_cx *cx)
269{ 261{
270 struct acpi_processor_power *pwr = &pr->power; 262 struct acpi_processor_power *pwr = &pr->power;
263 u8 type = local_apic_timer_c2_ok ? ACPI_STATE_C3 : ACPI_STATE_C2;
271 264
272 /* 265 /*
273 * Check, if one of the previous states already marked the lapic 266 * Check, if one of the previous states already marked the lapic
@@ -276,7 +269,7 @@ static void acpi_timer_check_state(int state, struct acpi_processor *pr,
276 if (pwr->timer_broadcast_on_state < state) 269 if (pwr->timer_broadcast_on_state < state)
277 return; 270 return;
278 271
279 if (cx->type >= ACPI_STATE_C2) 272 if (cx->type >= type)
280 pr->power.timer_broadcast_on_state = state; 273 pr->power.timer_broadcast_on_state = state;
281} 274}
282 275
@@ -482,7 +475,7 @@ static void acpi_processor_idle(void)
482 475
483#ifdef CONFIG_GENERIC_TIME 476#ifdef CONFIG_GENERIC_TIME
484 /* TSC halts in C2, so notify users */ 477 /* TSC halts in C2, so notify users */
485 mark_tsc_unstable(); 478 mark_tsc_unstable("possible TSC halt in C2");
486#endif 479#endif
487 /* Re-enable interrupts */ 480 /* Re-enable interrupts */
488 local_irq_enable(); 481 local_irq_enable();
@@ -524,7 +517,7 @@ static void acpi_processor_idle(void)
524 517
525#ifdef CONFIG_GENERIC_TIME 518#ifdef CONFIG_GENERIC_TIME
526 /* TSC halts in C3, so notify users */ 519 /* TSC halts in C3, so notify users */
527 mark_tsc_unstable(); 520 mark_tsc_unstable("TSC halts in C3");
528#endif 521#endif
529 /* Re-enable interrupts */ 522 /* Re-enable interrupts */
530 local_irq_enable(); 523 local_irq_enable();
diff --git a/drivers/acpi/processor_perflib.c b/drivers/acpi/processor_perflib.c
index 2f2e7964226d..c4efc0c17f8f 100644
--- a/drivers/acpi/processor_perflib.c
+++ b/drivers/acpi/processor_perflib.c
@@ -433,49 +433,6 @@ static int acpi_processor_perf_open_fs(struct inode *inode, struct file *file)
433 PDE(inode)->data); 433 PDE(inode)->data);
434} 434}
435 435
436static ssize_t
437acpi_processor_write_performance(struct file *file,
438 const char __user * buffer,
439 size_t count, loff_t * data)
440{
441 int result = 0;
442 struct seq_file *m = file->private_data;
443 struct acpi_processor *pr = m->private;
444 struct acpi_processor_performance *perf;
445 char state_string[12] = { '\0' };
446 unsigned int new_state = 0;
447 struct cpufreq_policy policy;
448
449
450 if (!pr || (count > sizeof(state_string) - 1))
451 return -EINVAL;
452
453 perf = pr->performance;
454 if (!perf)
455 return -EINVAL;
456
457 if (copy_from_user(state_string, buffer, count))
458 return -EFAULT;
459
460 state_string[count] = '\0';
461 new_state = simple_strtoul(state_string, NULL, 0);
462
463 if (new_state >= perf->state_count)
464 return -EINVAL;
465
466 cpufreq_get_policy(&policy, pr->id);
467
468 policy.cpu = pr->id;
469 policy.min = perf->states[new_state].core_frequency * 1000;
470 policy.max = perf->states[new_state].core_frequency * 1000;
471
472 result = cpufreq_set_policy(&policy);
473 if (result)
474 return result;
475
476 return count;
477}
478
479static void acpi_cpufreq_add_file(struct acpi_processor *pr) 436static void acpi_cpufreq_add_file(struct acpi_processor *pr)
480{ 437{
481 struct proc_dir_entry *entry = NULL; 438 struct proc_dir_entry *entry = NULL;
@@ -487,10 +444,9 @@ static void acpi_cpufreq_add_file(struct acpi_processor *pr)
487 444
488 /* add file 'performance' [R/W] */ 445 /* add file 'performance' [R/W] */
489 entry = create_proc_entry(ACPI_PROCESSOR_FILE_PERFORMANCE, 446 entry = create_proc_entry(ACPI_PROCESSOR_FILE_PERFORMANCE,
490 S_IFREG | S_IRUGO | S_IWUSR, 447 S_IFREG | S_IRUGO,
491 acpi_device_dir(device)); 448 acpi_device_dir(device));
492 if (entry){ 449 if (entry){
493 acpi_processor_perf_fops.write = acpi_processor_write_performance;
494 entry->proc_fops = &acpi_processor_perf_fops; 450 entry->proc_fops = &acpi_processor_perf_fops;
495 entry->data = acpi_driver_data(device); 451 entry->data = acpi_driver_data(device);
496 entry->owner = THIS_MODULE; 452 entry->owner = THIS_MODULE;
diff --git a/drivers/acpi/resources/rscreate.c b/drivers/acpi/resources/rscreate.c
index 1358c06a969c..cc48ab05676c 100644
--- a/drivers/acpi/resources/rscreate.c
+++ b/drivers/acpi/resources/rscreate.c
@@ -191,6 +191,9 @@ acpi_rs_create_pci_routing_table(union acpi_operand_object *package_object,
191 user_prt = ACPI_CAST_PTR(struct acpi_pci_routing_table, buffer); 191 user_prt = ACPI_CAST_PTR(struct acpi_pci_routing_table, buffer);
192 192
193 for (index = 0; index < number_of_elements; index++) { 193 for (index = 0; index < number_of_elements; index++) {
194 int source_name_index = 2;
195 int source_index_index = 3;
196
194 /* 197 /*
195 * Point user_prt past this current structure 198 * Point user_prt past this current structure
196 * 199 *
@@ -261,10 +264,28 @@ acpi_rs_create_pci_routing_table(union acpi_operand_object *package_object,
261 } 264 }
262 265
263 /* 266 /*
267 * If BIOS erroneously reversed the _PRT source_name and source_index,
268 * then reverse them back.
269 */
270 if (ACPI_GET_OBJECT_TYPE (sub_object_list[3]) != ACPI_TYPE_INTEGER) {
271 if (acpi_gbl_enable_interpreter_slack) {
272 source_name_index = 3;
273 source_index_index = 2;
274 printk(KERN_WARNING "ACPI: Handling Garbled _PRT entry\n");
275 } else {
276 ACPI_ERROR((AE_INFO,
277 "(PRT[%X].source_index) Need Integer, found %s",
278 index,
279 acpi_ut_get_object_type_name(sub_object_list[3])));
280 return_ACPI_STATUS(AE_BAD_DATA);
281 }
282 }
283
284 /*
264 * 3) Third subobject: Dereference the PRT.source_name 285 * 3) Third subobject: Dereference the PRT.source_name
265 * The name may be unresolved (slack mode), so allow a null object 286 * The name may be unresolved (slack mode), so allow a null object
266 */ 287 */
267 obj_desc = sub_object_list[2]; 288 obj_desc = sub_object_list[source_name_index];
268 if (obj_desc) { 289 if (obj_desc) {
269 switch (ACPI_GET_OBJECT_TYPE(obj_desc)) { 290 switch (ACPI_GET_OBJECT_TYPE(obj_desc)) {
270 case ACPI_TYPE_LOCAL_REFERENCE: 291 case ACPI_TYPE_LOCAL_REFERENCE:
@@ -339,7 +360,7 @@ acpi_rs_create_pci_routing_table(union acpi_operand_object *package_object,
339 360
340 /* 4) Fourth subobject: Dereference the PRT.source_index */ 361 /* 4) Fourth subobject: Dereference the PRT.source_index */
341 362
342 obj_desc = sub_object_list[3]; 363 obj_desc = sub_object_list[source_index_index];
343 if (ACPI_GET_OBJECT_TYPE(obj_desc) == ACPI_TYPE_INTEGER) { 364 if (ACPI_GET_OBJECT_TYPE(obj_desc) == ACPI_TYPE_INTEGER) {
344 user_prt->source_index = (u32) obj_desc->integer.value; 365 user_prt->source_index = (u32) obj_desc->integer.value;
345 } else { 366 } else {
diff --git a/drivers/acpi/sbs.c b/drivers/acpi/sbs.c
index 59640d9a0acc..c1bae106833c 100644
--- a/drivers/acpi/sbs.c
+++ b/drivers/acpi/sbs.c
@@ -30,30 +30,10 @@
30#include <linux/seq_file.h> 30#include <linux/seq_file.h>
31#include <asm/uaccess.h> 31#include <asm/uaccess.h>
32#include <linux/acpi.h> 32#include <linux/acpi.h>
33#include <linux/i2c.h> 33#include <linux/timer.h>
34#include <linux/jiffies.h>
34#include <linux/delay.h> 35#include <linux/delay.h>
35 36
36#include "i2c_ec.h"
37
38#define DEF_CAPACITY_UNIT 3
39#define MAH_CAPACITY_UNIT 1
40#define MWH_CAPACITY_UNIT 2
41#define CAPACITY_UNIT DEF_CAPACITY_UNIT
42
43#define REQUEST_UPDATE_MODE 1
44#define QUEUE_UPDATE_MODE 2
45
46#define DATA_TYPE_COMMON 0
47#define DATA_TYPE_INFO 1
48#define DATA_TYPE_STATE 2
49#define DATA_TYPE_ALARM 3
50#define DATA_TYPE_AC_STATE 4
51
52extern struct proc_dir_entry *acpi_lock_ac_dir(void);
53extern struct proc_dir_entry *acpi_lock_battery_dir(void);
54extern void acpi_unlock_ac_dir(struct proc_dir_entry *acpi_ac_dir);
55extern void acpi_unlock_battery_dir(struct proc_dir_entry *acpi_battery_dir);
56
57#define ACPI_SBS_COMPONENT 0x00080000 37#define ACPI_SBS_COMPONENT 0x00080000
58#define ACPI_SBS_CLASS "sbs" 38#define ACPI_SBS_CLASS "sbs"
59#define ACPI_AC_CLASS "ac_adapter" 39#define ACPI_AC_CLASS "ac_adapter"
@@ -74,39 +54,75 @@ extern void acpi_unlock_battery_dir(struct proc_dir_entry *acpi_battery_dir);
74 54
75#define _COMPONENT ACPI_SBS_COMPONENT 55#define _COMPONENT ACPI_SBS_COMPONENT
76 56
77#define MAX_SBS_BAT 4
78#define MAX_SMBUS_ERR 1
79
80ACPI_MODULE_NAME("sbs"); 57ACPI_MODULE_NAME("sbs");
81 58
82MODULE_AUTHOR("Rich Townsend"); 59MODULE_AUTHOR("Rich Townsend");
83MODULE_DESCRIPTION("Smart Battery System ACPI interface driver"); 60MODULE_DESCRIPTION("Smart Battery System ACPI interface driver");
84MODULE_LICENSE("GPL"); 61MODULE_LICENSE("GPL");
85 62
86static struct semaphore sbs_sem; 63#define xmsleep(t) msleep(t)
64
65#define ACPI_EC_SMB_PRTCL 0x00 /* protocol, PEC */
66
67#define ACPI_EC_SMB_STS 0x01 /* status */
68#define ACPI_EC_SMB_ADDR 0x02 /* address */
69#define ACPI_EC_SMB_CMD 0x03 /* command */
70#define ACPI_EC_SMB_DATA 0x04 /* 32 data registers */
71#define ACPI_EC_SMB_BCNT 0x24 /* number of data bytes */
87 72
88#define UPDATE_MODE QUEUE_UPDATE_MODE 73#define ACPI_EC_SMB_STS_DONE 0x80
89/* REQUEST_UPDATE_MODE QUEUE_UPDATE_MODE */ 74#define ACPI_EC_SMB_STS_STATUS 0x1f
90#define UPDATE_INFO_MODE 0
91#define UPDATE_TIME 60
92#define UPDATE_TIME2 0
93 75
94static int capacity_mode = CAPACITY_UNIT; 76#define ACPI_EC_SMB_PRTCL_WRITE 0x00
95static int update_mode = UPDATE_MODE; 77#define ACPI_EC_SMB_PRTCL_READ 0x01
96static int update_info_mode = UPDATE_INFO_MODE; 78#define ACPI_EC_SMB_PRTCL_WORD_DATA 0x08
97static int update_time = UPDATE_TIME; 79#define ACPI_EC_SMB_PRTCL_BLOCK_DATA 0x0a
98static int update_time2 = UPDATE_TIME2;
99 80
100module_param(capacity_mode, int, 0); 81#define ACPI_EC_SMB_TRANSACTION_SLEEP 1
101module_param(update_mode, int, 0); 82#define ACPI_EC_SMB_ACCESS_SLEEP1 1
102module_param(update_info_mode, int, 0); 83#define ACPI_EC_SMB_ACCESS_SLEEP2 10
103module_param(update_time, int, 0); 84
104module_param(update_time2, int, 0); 85#define DEF_CAPACITY_UNIT 3
86#define MAH_CAPACITY_UNIT 1
87#define MWH_CAPACITY_UNIT 2
88#define CAPACITY_UNIT DEF_CAPACITY_UNIT
89
90#define REQUEST_UPDATE_MODE 1
91#define QUEUE_UPDATE_MODE 2
92
93#define DATA_TYPE_COMMON 0
94#define DATA_TYPE_INFO 1
95#define DATA_TYPE_STATE 2
96#define DATA_TYPE_ALARM 3
97#define DATA_TYPE_AC_STATE 4
98
99extern struct proc_dir_entry *acpi_lock_ac_dir(void);
100extern struct proc_dir_entry *acpi_lock_battery_dir(void);
101extern void acpi_unlock_ac_dir(struct proc_dir_entry *acpi_ac_dir);
102extern void acpi_unlock_battery_dir(struct proc_dir_entry *acpi_battery_dir);
103
104#define MAX_SBS_BAT 4
105#define ACPI_SBS_BLOCK_MAX 32
106
107#define ACPI_SBS_SMBUS_READ 1
108#define ACPI_SBS_SMBUS_WRITE 2
109
110#define ACPI_SBS_WORD_DATA 1
111#define ACPI_SBS_BLOCK_DATA 2
112
113#define UPDATE_DELAY 10
114
115/* 0 - every time, > 0 - by update_time */
116static unsigned int update_time = 120;
117
118static unsigned int capacity_mode = CAPACITY_UNIT;
119
120module_param(update_time, uint, 0644);
121module_param(capacity_mode, uint, 0444);
105 122
106static int acpi_sbs_add(struct acpi_device *device); 123static int acpi_sbs_add(struct acpi_device *device);
107static int acpi_sbs_remove(struct acpi_device *device, int type); 124static int acpi_sbs_remove(struct acpi_device *device, int type);
108static void acpi_battery_smbus_err_handler(struct acpi_ec_smbus *smbus); 125static int acpi_sbs_resume(struct acpi_device *device);
109static void acpi_sbs_update_queue(void *data);
110 126
111static struct acpi_driver acpi_sbs_driver = { 127static struct acpi_driver acpi_sbs_driver = {
112 .name = "sbs", 128 .name = "sbs",
@@ -115,9 +131,14 @@ static struct acpi_driver acpi_sbs_driver = {
115 .ops = { 131 .ops = {
116 .add = acpi_sbs_add, 132 .add = acpi_sbs_add,
117 .remove = acpi_sbs_remove, 133 .remove = acpi_sbs_remove,
134 .resume = acpi_sbs_resume,
118 }, 135 },
119}; 136};
120 137
138struct acpi_ac {
139 int ac_present;
140};
141
121struct acpi_battery_info { 142struct acpi_battery_info {
122 int capacity_mode; 143 int capacity_mode;
123 s16 full_charge_capacity; 144 s16 full_charge_capacity;
@@ -126,18 +147,16 @@ struct acpi_battery_info {
126 int vscale; 147 int vscale;
127 int ipscale; 148 int ipscale;
128 s16 serial_number; 149 s16 serial_number;
129 char manufacturer_name[I2C_SMBUS_BLOCK_MAX + 3]; 150 char manufacturer_name[ACPI_SBS_BLOCK_MAX + 3];
130 char device_name[I2C_SMBUS_BLOCK_MAX + 3]; 151 char device_name[ACPI_SBS_BLOCK_MAX + 3];
131 char device_chemistry[I2C_SMBUS_BLOCK_MAX + 3]; 152 char device_chemistry[ACPI_SBS_BLOCK_MAX + 3];
132}; 153};
133 154
134struct acpi_battery_state { 155struct acpi_battery_state {
135 s16 voltage; 156 s16 voltage;
136 s16 amperage; 157 s16 amperage;
137 s16 remaining_capacity; 158 s16 remaining_capacity;
138 s16 average_time_to_empty; 159 s16 battery_state;
139 s16 average_time_to_full;
140 s16 battery_status;
141}; 160};
142 161
143struct acpi_battery_alarm { 162struct acpi_battery_alarm {
@@ -146,9 +165,9 @@ struct acpi_battery_alarm {
146 165
147struct acpi_battery { 166struct acpi_battery {
148 int alive; 167 int alive;
149 int battery_present;
150 int id; 168 int id;
151 int init_state; 169 int init_state;
170 int battery_present;
152 struct acpi_sbs *sbs; 171 struct acpi_sbs *sbs;
153 struct acpi_battery_info info; 172 struct acpi_battery_info info;
154 struct acpi_battery_state state; 173 struct acpi_battery_state state;
@@ -158,186 +177,251 @@ struct acpi_battery {
158 177
159struct acpi_sbs { 178struct acpi_sbs {
160 acpi_handle handle; 179 acpi_handle handle;
180 int base;
161 struct acpi_device *device; 181 struct acpi_device *device;
162 struct acpi_ec_smbus *smbus; 182 struct acpi_ec_smbus *smbus;
183 struct mutex mutex;
163 int sbsm_present; 184 int sbsm_present;
164 int sbsm_batteries_supported; 185 int sbsm_batteries_supported;
165 int ac_present;
166 struct proc_dir_entry *ac_entry; 186 struct proc_dir_entry *ac_entry;
187 struct acpi_ac ac;
167 struct acpi_battery battery[MAX_SBS_BAT]; 188 struct acpi_battery battery[MAX_SBS_BAT];
168 int update_info_mode;
169 int zombie; 189 int zombie;
170 int update_time;
171 int update_time2;
172 struct timer_list update_timer; 190 struct timer_list update_timer;
191 int run_cnt;
192 int update_proc_flg;
173}; 193};
174 194
175static void acpi_update_delay(struct acpi_sbs *sbs); 195static int acpi_sbs_update_run(struct acpi_sbs *sbs, int id, int data_type);
176static int acpi_sbs_update_run(struct acpi_sbs *sbs, int data_type); 196static void acpi_sbs_update_time(void *data);
197
198union sbs_rw_data {
199 u16 word;
200 u8 block[ACPI_SBS_BLOCK_MAX + 2];
201};
202
203static int acpi_ec_sbs_access(struct acpi_sbs *sbs, u16 addr,
204 char read_write, u8 command, int size,
205 union sbs_rw_data *data);
177 206
178/* -------------------------------------------------------------------------- 207/* --------------------------------------------------------------------------
179 SMBus Communication 208 SMBus Communication
180 -------------------------------------------------------------------------- */ 209 -------------------------------------------------------------------------- */
181 210
182static void acpi_battery_smbus_err_handler(struct acpi_ec_smbus *smbus) 211static int acpi_ec_sbs_read(struct acpi_sbs *sbs, u8 address, u8 * data)
183{ 212{
184 union i2c_smbus_data data; 213 u8 val;
185 int result = 0; 214 int err;
186 char *err_str;
187 int err_number;
188 215
189 data.word = 0; 216 err = ec_read(sbs->base + address, &val);
217 if (!err) {
218 *data = val;
219 }
220 xmsleep(ACPI_EC_SMB_TRANSACTION_SLEEP);
221 return (err);
222}
190 223
191 result = smbus->adapter.algo-> 224static int acpi_ec_sbs_write(struct acpi_sbs *sbs, u8 address, u8 data)
192 smbus_xfer(&smbus->adapter, 225{
193 ACPI_SB_SMBUS_ADDR, 226 int err;
194 0, I2C_SMBUS_READ, 0x16, I2C_SMBUS_BLOCK_DATA, &data);
195 227
196 err_number = (data.word & 0x000f); 228 err = ec_write(sbs->base + address, data);
229 return (err);
230}
197 231
198 switch (data.word & 0x000f) { 232static int
199 case 0x0000: 233acpi_ec_sbs_access(struct acpi_sbs *sbs, u16 addr,
200 err_str = "unexpected bus error"; 234 char read_write, u8 command, int size,
201 break; 235 union sbs_rw_data *data)
202 case 0x0001: 236{
203 err_str = "busy"; 237 unsigned char protocol, len = 0, temp[2] = { 0, 0 };
204 break; 238 int i;
205 case 0x0002: 239
206 err_str = "reserved command"; 240 if (read_write == ACPI_SBS_SMBUS_READ) {
207 break; 241 protocol = ACPI_EC_SMB_PRTCL_READ;
208 case 0x0003: 242 } else {
209 err_str = "unsupported command"; 243 protocol = ACPI_EC_SMB_PRTCL_WRITE;
210 break; 244 }
211 case 0x0004: 245
212 err_str = "access denied"; 246 switch (size) {
247
248 case ACPI_SBS_WORD_DATA:
249 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_CMD, command);
250 if (read_write == ACPI_SBS_SMBUS_WRITE) {
251 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_DATA, data->word);
252 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_DATA + 1,
253 data->word >> 8);
254 }
255 protocol |= ACPI_EC_SMB_PRTCL_WORD_DATA;
213 break; 256 break;
214 case 0x0005: 257 case ACPI_SBS_BLOCK_DATA:
215 err_str = "overflow/underflow"; 258 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_CMD, command);
259 if (read_write == ACPI_SBS_SMBUS_WRITE) {
260 len = min_t(u8, data->block[0], 32);
261 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_BCNT, len);
262 for (i = 0; i < len; i++)
263 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_DATA + i,
264 data->block[i + 1]);
265 }
266 protocol |= ACPI_EC_SMB_PRTCL_BLOCK_DATA;
216 break; 267 break;
217 case 0x0006: 268 default:
218 err_str = "bad size"; 269 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
270 "unsupported transaction %d", size));
271 return (-1);
272 }
273
274 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_ADDR, addr << 1);
275 acpi_ec_sbs_write(sbs, ACPI_EC_SMB_PRTCL, protocol);
276
277 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_STS, temp);
278
279 if (~temp[0] & ACPI_EC_SMB_STS_DONE) {
280 xmsleep(ACPI_EC_SMB_ACCESS_SLEEP1);
281 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_STS, temp);
282 }
283 if (~temp[0] & ACPI_EC_SMB_STS_DONE) {
284 xmsleep(ACPI_EC_SMB_ACCESS_SLEEP2);
285 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_STS, temp);
286 }
287 if ((~temp[0] & ACPI_EC_SMB_STS_DONE)
288 || (temp[0] & ACPI_EC_SMB_STS_STATUS)) {
289 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
290 "transaction %d error", size));
291 return (-1);
292 }
293
294 if (read_write == ACPI_SBS_SMBUS_WRITE) {
295 return (0);
296 }
297
298 switch (size) {
299
300 case ACPI_SBS_WORD_DATA:
301 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_DATA, temp);
302 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_DATA + 1, temp + 1);
303 data->word = (temp[1] << 8) | temp[0];
219 break; 304 break;
220 case 0x0007: 305
221 err_str = "unknown error"; 306 case ACPI_SBS_BLOCK_DATA:
307 len = 0;
308 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_BCNT, &len);
309 len = min_t(u8, len, 32);
310 for (i = 0; i < len; i++)
311 acpi_ec_sbs_read(sbs, ACPI_EC_SMB_DATA + i,
312 data->block + i + 1);
313 data->block[0] = len;
222 break; 314 break;
223 default: 315 default:
224 err_str = "unrecognized error"; 316 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
317 "unsupported transaction %d", size));
318 return (-1);
225 } 319 }
226 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 320
227 "%s: ret %i, err %i\n", err_str, result, err_number)); 321 return (0);
228} 322}
229 323
230static int 324static int
231acpi_sbs_smbus_read_word(struct acpi_ec_smbus *smbus, int addr, int func, 325acpi_sbs_read_word(struct acpi_sbs *sbs, int addr, int func, u16 * word)
232 u16 * word,
233 void (*err_handler) (struct acpi_ec_smbus * smbus))
234{ 326{
235 union i2c_smbus_data data; 327 union sbs_rw_data data;
236 int result = 0; 328 int result = 0;
237 int i;
238 329
239 if (err_handler == NULL) { 330 result = acpi_ec_sbs_access(sbs, addr,
240 err_handler = acpi_battery_smbus_err_handler; 331 ACPI_SBS_SMBUS_READ, func,
241 } 332 ACPI_SBS_WORD_DATA, &data);
242 333 if (result) {
243 for (i = 0; i < MAX_SMBUS_ERR; i++) { 334 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
244 result = 335 "acpi_ec_sbs_access() failed"));
245 smbus->adapter.algo->smbus_xfer(&smbus->adapter, addr, 0, 336 } else {
246 I2C_SMBUS_READ, func, 337 *word = data.word;
247 I2C_SMBUS_WORD_DATA, &data);
248 if (result) {
249 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
250 "try %i: smbus->adapter.algo->smbus_xfer() failed\n",
251 i));
252 if (err_handler) {
253 err_handler(smbus);
254 }
255 } else {
256 *word = data.word;
257 break;
258 }
259 } 338 }
260 339
261 return result; 340 return result;
262} 341}
263 342
264static int 343static int
265acpi_sbs_smbus_read_str(struct acpi_ec_smbus *smbus, int addr, int func, 344acpi_sbs_read_str(struct acpi_sbs *sbs, int addr, int func, char *str)
266 char *str,
267 void (*err_handler) (struct acpi_ec_smbus * smbus))
268{ 345{
269 union i2c_smbus_data data; 346 union sbs_rw_data data;
270 int result = 0; 347 int result = 0;
271 int i;
272
273 if (err_handler == NULL) {
274 err_handler = acpi_battery_smbus_err_handler;
275 }
276 348
277 for (i = 0; i < MAX_SMBUS_ERR; i++) { 349 result = acpi_ec_sbs_access(sbs, addr,
278 result = 350 ACPI_SBS_SMBUS_READ, func,
279 smbus->adapter.algo->smbus_xfer(&smbus->adapter, addr, 0, 351 ACPI_SBS_BLOCK_DATA, &data);
280 I2C_SMBUS_READ, func, 352 if (result) {
281 I2C_SMBUS_BLOCK_DATA, 353 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
282 &data); 354 "acpi_ec_sbs_access() failed"));
283 if (result) { 355 } else {
284 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 356 strncpy(str, (const char *)data.block + 1, data.block[0]);
285 "try %i: smbus->adapter.algo->smbus_xfer() failed\n", 357 str[data.block[0]] = 0;
286 i));
287 if (err_handler) {
288 err_handler(smbus);
289 }
290 } else {
291 strncpy(str, (const char *)data.block + 1,
292 data.block[0]);
293 str[data.block[0]] = 0;
294 break;
295 }
296 } 358 }
297 359
298 return result; 360 return result;
299} 361}
300 362
301static int 363static int
302acpi_sbs_smbus_write_word(struct acpi_ec_smbus *smbus, int addr, int func, 364acpi_sbs_write_word(struct acpi_sbs *sbs, int addr, int func, int word)
303 int word,
304 void (*err_handler) (struct acpi_ec_smbus * smbus))
305{ 365{
306 union i2c_smbus_data data; 366 union sbs_rw_data data;
307 int result = 0; 367 int result = 0;
308 int i;
309
310 if (err_handler == NULL) {
311 err_handler = acpi_battery_smbus_err_handler;
312 }
313 368
314 data.word = word; 369 data.word = word;
315 370
316 for (i = 0; i < MAX_SMBUS_ERR; i++) { 371 result = acpi_ec_sbs_access(sbs, addr,
317 result = 372 ACPI_SBS_SMBUS_WRITE, func,
318 smbus->adapter.algo->smbus_xfer(&smbus->adapter, addr, 0, 373 ACPI_SBS_WORD_DATA, &data);
319 I2C_SMBUS_WRITE, func, 374 if (result) {
320 I2C_SMBUS_WORD_DATA, &data); 375 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
321 if (result) { 376 "acpi_ec_sbs_access() failed"));
322 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
323 "try %i: smbus->adapter.algo"
324 "->smbus_xfer() failed\n", i));
325 if (err_handler) {
326 err_handler(smbus);
327 }
328 } else {
329 break;
330 }
331 } 377 }
332 378
333 return result; 379 return result;
334} 380}
335 381
382static int sbs_zombie(struct acpi_sbs *sbs)
383{
384 return (sbs->zombie);
385}
386
387static int sbs_mutex_lock(struct acpi_sbs *sbs)
388{
389 if (sbs_zombie(sbs)) {
390 return -ENODEV;
391 }
392 mutex_lock(&sbs->mutex);
393 return 0;
394}
395
396static void sbs_mutex_unlock(struct acpi_sbs *sbs)
397{
398 mutex_unlock(&sbs->mutex);
399}
400
336/* -------------------------------------------------------------------------- 401/* --------------------------------------------------------------------------
337 Smart Battery System Management 402 Smart Battery System Management
338 -------------------------------------------------------------------------- */ 403 -------------------------------------------------------------------------- */
339 404
340/* Smart Battery */ 405static int acpi_check_update_proc(struct acpi_sbs *sbs)
406{
407 acpi_status status = AE_OK;
408
409 if (update_time == 0) {
410 sbs->update_proc_flg = 0;
411 return 0;
412 }
413 if (sbs->update_proc_flg == 0) {
414 status = acpi_os_execute(OSL_GPE_HANDLER,
415 acpi_sbs_update_time, sbs);
416 if (status != AE_OK) {
417 ACPI_EXCEPTION((AE_INFO, status,
418 "acpi_os_execute() failed"));
419 return 1;
420 }
421 sbs->update_proc_flg = 1;
422 }
423 return 0;
424}
341 425
342static int acpi_sbs_generate_event(struct acpi_device *device, 426static int acpi_sbs_generate_event(struct acpi_device *device,
343 int event, int state, char *bid, char *class) 427 int event, int state, char *bid, char *class)
@@ -366,12 +450,11 @@ static int acpi_battery_get_present(struct acpi_battery *battery)
366 int result = 0; 450 int result = 0;
367 int is_present = 0; 451 int is_present = 0;
368 452
369 result = acpi_sbs_smbus_read_word(battery->sbs->smbus, 453 result = acpi_sbs_read_word(battery->sbs,
370 ACPI_SBSM_SMBUS_ADDR, 0x01, 454 ACPI_SBSM_SMBUS_ADDR, 0x01, &state);
371 &state, NULL);
372 if (result) { 455 if (result) {
373 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 456 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
374 "acpi_sbs_smbus_read_word() failed")); 457 "acpi_sbs_read_word() failed"));
375 } 458 }
376 if (!result) { 459 if (!result) {
377 is_present = (state & 0x000f) & (1 << battery->id); 460 is_present = (state & 0x000f) & (1 << battery->id);
@@ -381,45 +464,33 @@ static int acpi_battery_get_present(struct acpi_battery *battery)
381 return result; 464 return result;
382} 465}
383 466
384static int acpi_battery_is_present(struct acpi_battery *battery)
385{
386 return (battery->battery_present);
387}
388
389static int acpi_ac_is_present(struct acpi_sbs *sbs)
390{
391 return (sbs->ac_present);
392}
393
394static int acpi_battery_select(struct acpi_battery *battery) 467static int acpi_battery_select(struct acpi_battery *battery)
395{ 468{
396 struct acpi_ec_smbus *smbus = battery->sbs->smbus; 469 struct acpi_sbs *sbs = battery->sbs;
397 int result = 0; 470 int result = 0;
398 s16 state; 471 s16 state;
399 int foo; 472 int foo;
400 473
401 if (battery->sbs->sbsm_present) { 474 if (sbs->sbsm_present) {
402 475
403 /* Take special care not to knobble other nibbles of 476 /* Take special care not to knobble other nibbles of
404 * state (aka selector_state), since 477 * state (aka selector_state), since
405 * it causes charging to halt on SBSELs */ 478 * it causes charging to halt on SBSELs */
406 479
407 result = 480 result =
408 acpi_sbs_smbus_read_word(smbus, ACPI_SBSM_SMBUS_ADDR, 0x01, 481 acpi_sbs_read_word(sbs, ACPI_SBSM_SMBUS_ADDR, 0x01, &state);
409 &state, NULL);
410 if (result) { 482 if (result) {
411 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 483 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
412 "acpi_sbs_smbus_read_word() failed\n")); 484 "acpi_sbs_read_word() failed"));
413 goto end; 485 goto end;
414 } 486 }
415 487
416 foo = (state & 0x0fff) | (1 << (battery->id + 12)); 488 foo = (state & 0x0fff) | (1 << (battery->id + 12));
417 result = 489 result =
418 acpi_sbs_smbus_write_word(smbus, ACPI_SBSM_SMBUS_ADDR, 0x01, 490 acpi_sbs_write_word(sbs, ACPI_SBSM_SMBUS_ADDR, 0x01, foo);
419 foo, NULL);
420 if (result) { 491 if (result) {
421 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 492 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
422 "acpi_sbs_smbus_write_word() failed\n")); 493 "acpi_sbs_write_word() failed"));
423 goto end; 494 goto end;
424 } 495 }
425 } 496 }
@@ -430,15 +501,14 @@ static int acpi_battery_select(struct acpi_battery *battery)
430 501
431static int acpi_sbsm_get_info(struct acpi_sbs *sbs) 502static int acpi_sbsm_get_info(struct acpi_sbs *sbs)
432{ 503{
433 struct acpi_ec_smbus *smbus = sbs->smbus;
434 int result = 0; 504 int result = 0;
435 s16 battery_system_info; 505 s16 battery_system_info;
436 506
437 result = acpi_sbs_smbus_read_word(smbus, ACPI_SBSM_SMBUS_ADDR, 0x04, 507 result = acpi_sbs_read_word(sbs, ACPI_SBSM_SMBUS_ADDR, 0x04,
438 &battery_system_info, NULL); 508 &battery_system_info);
439 if (result) { 509 if (result) {
440 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 510 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
441 "acpi_sbs_smbus_read_word() failed\n")); 511 "acpi_sbs_read_word() failed"));
442 goto end; 512 goto end;
443 } 513 }
444 514
@@ -451,53 +521,50 @@ static int acpi_sbsm_get_info(struct acpi_sbs *sbs)
451 521
452static int acpi_battery_get_info(struct acpi_battery *battery) 522static int acpi_battery_get_info(struct acpi_battery *battery)
453{ 523{
454 struct acpi_ec_smbus *smbus = battery->sbs->smbus; 524 struct acpi_sbs *sbs = battery->sbs;
455 int result = 0; 525 int result = 0;
456 s16 battery_mode; 526 s16 battery_mode;
457 s16 specification_info; 527 s16 specification_info;
458 528
459 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x03, 529 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x03,
460 &battery_mode, 530 &battery_mode);
461 &acpi_battery_smbus_err_handler);
462 if (result) { 531 if (result) {
463 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 532 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
464 "acpi_sbs_smbus_read_word() failed\n")); 533 "acpi_sbs_read_word() failed"));
465 goto end; 534 goto end;
466 } 535 }
467 battery->info.capacity_mode = (battery_mode & 0x8000) >> 15; 536 battery->info.capacity_mode = (battery_mode & 0x8000) >> 15;
468 537
469 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x10, 538 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x10,
470 &battery->info.full_charge_capacity, 539 &battery->info.full_charge_capacity);
471 &acpi_battery_smbus_err_handler);
472 if (result) { 540 if (result) {
473 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 541 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
474 "acpi_sbs_smbus_read_word() failed\n")); 542 "acpi_sbs_read_word() failed"));
475 goto end; 543 goto end;
476 } 544 }
477 545
478 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x18, 546 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x18,
479 &battery->info.design_capacity, 547 &battery->info.design_capacity);
480 &acpi_battery_smbus_err_handler);
481 548
482 if (result) { 549 if (result) {
550 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
551 "acpi_sbs_read_word() failed"));
483 goto end; 552 goto end;
484 } 553 }
485 554
486 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x19, 555 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x19,
487 &battery->info.design_voltage, 556 &battery->info.design_voltage);
488 &acpi_battery_smbus_err_handler);
489 if (result) { 557 if (result) {
490 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 558 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
491 "acpi_sbs_smbus_read_word() failed\n")); 559 "acpi_sbs_read_word() failed"));
492 goto end; 560 goto end;
493 } 561 }
494 562
495 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x1a, 563 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x1a,
496 &specification_info, 564 &specification_info);
497 &acpi_battery_smbus_err_handler);
498 if (result) { 565 if (result) {
499 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 566 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
500 "acpi_sbs_smbus_read_word() failed\n")); 567 "acpi_sbs_read_word() failed"));
501 goto end; 568 goto end;
502 } 569 }
503 570
@@ -529,37 +596,35 @@ static int acpi_battery_get_info(struct acpi_battery *battery)
529 battery->info.ipscale = 1; 596 battery->info.ipscale = 1;
530 } 597 }
531 598
532 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x1c, 599 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x1c,
533 &battery->info.serial_number, 600 &battery->info.serial_number);
534 &acpi_battery_smbus_err_handler);
535 if (result) { 601 if (result) {
602 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
603 "acpi_sbs_read_word() failed"));
536 goto end; 604 goto end;
537 } 605 }
538 606
539 result = acpi_sbs_smbus_read_str(smbus, ACPI_SB_SMBUS_ADDR, 0x20, 607 result = acpi_sbs_read_str(sbs, ACPI_SB_SMBUS_ADDR, 0x20,
540 battery->info.manufacturer_name, 608 battery->info.manufacturer_name);
541 &acpi_battery_smbus_err_handler);
542 if (result) { 609 if (result) {
543 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 610 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
544 "acpi_sbs_smbus_read_str() failed\n")); 611 "acpi_sbs_read_str() failed"));
545 goto end; 612 goto end;
546 } 613 }
547 614
548 result = acpi_sbs_smbus_read_str(smbus, ACPI_SB_SMBUS_ADDR, 0x21, 615 result = acpi_sbs_read_str(sbs, ACPI_SB_SMBUS_ADDR, 0x21,
549 battery->info.device_name, 616 battery->info.device_name);
550 &acpi_battery_smbus_err_handler);
551 if (result) { 617 if (result) {
552 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 618 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
553 "acpi_sbs_smbus_read_str() failed\n")); 619 "acpi_sbs_read_str() failed"));
554 goto end; 620 goto end;
555 } 621 }
556 622
557 result = acpi_sbs_smbus_read_str(smbus, ACPI_SB_SMBUS_ADDR, 0x22, 623 result = acpi_sbs_read_str(sbs, ACPI_SB_SMBUS_ADDR, 0x22,
558 battery->info.device_chemistry, 624 battery->info.device_chemistry);
559 &acpi_battery_smbus_err_handler);
560 if (result) { 625 if (result) {
561 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 626 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
562 "acpi_sbs_smbus_read_str() failed\n")); 627 "acpi_sbs_read_str() failed"));
563 goto end; 628 goto end;
564 } 629 }
565 630
@@ -567,103 +632,60 @@ static int acpi_battery_get_info(struct acpi_battery *battery)
567 return result; 632 return result;
568} 633}
569 634
570static void acpi_update_delay(struct acpi_sbs *sbs)
571{
572 if (sbs->zombie) {
573 return;
574 }
575 if (sbs->update_time2 > 0) {
576 msleep(sbs->update_time2 * 1000);
577 }
578}
579
580static int acpi_battery_get_state(struct acpi_battery *battery) 635static int acpi_battery_get_state(struct acpi_battery *battery)
581{ 636{
582 struct acpi_ec_smbus *smbus = battery->sbs->smbus; 637 struct acpi_sbs *sbs = battery->sbs;
583 int result = 0; 638 int result = 0;
584 639
585 acpi_update_delay(battery->sbs); 640 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x09,
586 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x09, 641 &battery->state.voltage);
587 &battery->state.voltage,
588 &acpi_battery_smbus_err_handler);
589 if (result) { 642 if (result) {
590 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 643 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
591 "acpi_sbs_smbus_read_word() failed\n")); 644 "acpi_sbs_read_word() failed"));
592 goto end; 645 goto end;
593 } 646 }
594 647
595 acpi_update_delay(battery->sbs); 648 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x0a,
596 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x0a, 649 &battery->state.amperage);
597 &battery->state.amperage,
598 &acpi_battery_smbus_err_handler);
599 if (result) { 650 if (result) {
600 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 651 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
601 "acpi_sbs_smbus_read_word() failed\n")); 652 "acpi_sbs_read_word() failed"));
602 goto end; 653 goto end;
603 } 654 }
604 655
605 acpi_update_delay(battery->sbs); 656 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x0f,
606 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x0f, 657 &battery->state.remaining_capacity);
607 &battery->state.remaining_capacity,
608 &acpi_battery_smbus_err_handler);
609 if (result) { 658 if (result) {
610 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 659 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
611 "acpi_sbs_smbus_read_word() failed\n")); 660 "acpi_sbs_read_word() failed"));
612 goto end; 661 goto end;
613 } 662 }
614 663
615 acpi_update_delay(battery->sbs); 664 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x16,
616 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x12, 665 &battery->state.battery_state);
617 &battery->state.average_time_to_empty,
618 &acpi_battery_smbus_err_handler);
619 if (result) { 666 if (result) {
620 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 667 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
621 "acpi_sbs_smbus_read_word() failed\n")); 668 "acpi_sbs_read_word() failed"));
622 goto end; 669 goto end;
623 } 670 }
624 671
625 acpi_update_delay(battery->sbs);
626 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x13,
627 &battery->state.average_time_to_full,
628 &acpi_battery_smbus_err_handler);
629 if (result) {
630 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
631 "acpi_sbs_smbus_read_word() failed\n"));
632 goto end;
633 }
634
635 acpi_update_delay(battery->sbs);
636 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x16,
637 &battery->state.battery_status,
638 &acpi_battery_smbus_err_handler);
639 if (result) {
640 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
641 "acpi_sbs_smbus_read_word() failed\n"));
642 goto end;
643 }
644
645 acpi_update_delay(battery->sbs);
646
647 end: 672 end:
648 return result; 673 return result;
649} 674}
650 675
651static int acpi_battery_get_alarm(struct acpi_battery *battery) 676static int acpi_battery_get_alarm(struct acpi_battery *battery)
652{ 677{
653 struct acpi_ec_smbus *smbus = battery->sbs->smbus; 678 struct acpi_sbs *sbs = battery->sbs;
654 int result = 0; 679 int result = 0;
655 680
656 result = acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x01, 681 result = acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x01,
657 &battery->alarm.remaining_capacity, 682 &battery->alarm.remaining_capacity);
658 &acpi_battery_smbus_err_handler);
659 if (result) { 683 if (result) {
660 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 684 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
661 "acpi_sbs_smbus_read_word() failed\n")); 685 "acpi_sbs_read_word() failed"));
662 goto end; 686 goto end;
663 } 687 }
664 688
665 acpi_update_delay(battery->sbs);
666
667 end: 689 end:
668 690
669 return result; 691 return result;
@@ -672,15 +694,15 @@ static int acpi_battery_get_alarm(struct acpi_battery *battery)
672static int acpi_battery_set_alarm(struct acpi_battery *battery, 694static int acpi_battery_set_alarm(struct acpi_battery *battery,
673 unsigned long alarm) 695 unsigned long alarm)
674{ 696{
675 struct acpi_ec_smbus *smbus = battery->sbs->smbus; 697 struct acpi_sbs *sbs = battery->sbs;
676 int result = 0; 698 int result = 0;
677 s16 battery_mode; 699 s16 battery_mode;
678 int foo; 700 int foo;
679 701
680 result = acpi_battery_select(battery); 702 result = acpi_battery_select(battery);
681 if (result) { 703 if (result) {
682 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 704 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
683 "acpi_battery_select() failed\n")); 705 "acpi_battery_select() failed"));
684 goto end; 706 goto end;
685 } 707 }
686 708
@@ -688,33 +710,29 @@ static int acpi_battery_set_alarm(struct acpi_battery *battery,
688 710
689 if (alarm > 0) { 711 if (alarm > 0) {
690 result = 712 result =
691 acpi_sbs_smbus_read_word(smbus, ACPI_SB_SMBUS_ADDR, 0x03, 713 acpi_sbs_read_word(sbs, ACPI_SB_SMBUS_ADDR, 0x03,
692 &battery_mode, 714 &battery_mode);
693 &acpi_battery_smbus_err_handler);
694 if (result) { 715 if (result) {
695 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 716 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
696 "acpi_sbs_smbus_read_word() failed\n")); 717 "acpi_sbs_read_word() failed"));
697 goto end; 718 goto end;
698 } 719 }
699 720
700 result = 721 result =
701 acpi_sbs_smbus_write_word(smbus, ACPI_SB_SMBUS_ADDR, 0x01, 722 acpi_sbs_write_word(sbs, ACPI_SB_SMBUS_ADDR, 0x01,
702 battery_mode & 0xbfff, 723 battery_mode & 0xbfff);
703 &acpi_battery_smbus_err_handler);
704 if (result) { 724 if (result) {
705 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 725 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
706 "acpi_sbs_smbus_write_word() failed\n")); 726 "acpi_sbs_write_word() failed"));
707 goto end; 727 goto end;
708 } 728 }
709 } 729 }
710 730
711 foo = alarm / (battery->info.capacity_mode ? 10 : 1); 731 foo = alarm / (battery->info.capacity_mode ? 10 : 1);
712 result = acpi_sbs_smbus_write_word(smbus, ACPI_SB_SMBUS_ADDR, 0x01, 732 result = acpi_sbs_write_word(sbs, ACPI_SB_SMBUS_ADDR, 0x01, foo);
713 foo,
714 &acpi_battery_smbus_err_handler);
715 if (result) { 733 if (result) {
716 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 734 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
717 "acpi_sbs_smbus_write_word() failed\n")); 735 "acpi_sbs_write_word() failed"));
718 goto end; 736 goto end;
719 } 737 }
720 738
@@ -725,6 +743,7 @@ static int acpi_battery_set_alarm(struct acpi_battery *battery,
725 743
726static int acpi_battery_set_mode(struct acpi_battery *battery) 744static int acpi_battery_set_mode(struct acpi_battery *battery)
727{ 745{
746 struct acpi_sbs *sbs = battery->sbs;
728 int result = 0; 747 int result = 0;
729 s16 battery_mode; 748 s16 battery_mode;
730 749
@@ -732,12 +751,11 @@ static int acpi_battery_set_mode(struct acpi_battery *battery)
732 goto end; 751 goto end;
733 } 752 }
734 753
735 result = acpi_sbs_smbus_read_word(battery->sbs->smbus, 754 result = acpi_sbs_read_word(sbs,
736 ACPI_SB_SMBUS_ADDR, 0x03, 755 ACPI_SB_SMBUS_ADDR, 0x03, &battery_mode);
737 &battery_mode, NULL);
738 if (result) { 756 if (result) {
739 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 757 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
740 "acpi_sbs_smbus_read_word() failed\n")); 758 "acpi_sbs_read_word() failed"));
741 goto end; 759 goto end;
742 } 760 }
743 761
@@ -746,21 +764,19 @@ static int acpi_battery_set_mode(struct acpi_battery *battery)
746 } else { 764 } else {
747 battery_mode |= 0x8000; 765 battery_mode |= 0x8000;
748 } 766 }
749 result = acpi_sbs_smbus_write_word(battery->sbs->smbus, 767 result = acpi_sbs_write_word(sbs,
750 ACPI_SB_SMBUS_ADDR, 0x03, 768 ACPI_SB_SMBUS_ADDR, 0x03, battery_mode);
751 battery_mode, NULL);
752 if (result) { 769 if (result) {
753 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 770 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
754 "acpi_sbs_smbus_write_word() failed\n")); 771 "acpi_sbs_write_word() failed"));
755 goto end; 772 goto end;
756 } 773 }
757 774
758 result = acpi_sbs_smbus_read_word(battery->sbs->smbus, 775 result = acpi_sbs_read_word(sbs,
759 ACPI_SB_SMBUS_ADDR, 0x03, 776 ACPI_SB_SMBUS_ADDR, 0x03, &battery_mode);
760 &battery_mode, NULL);
761 if (result) { 777 if (result) {
762 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 778 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
763 "acpi_sbs_smbus_read_word() failed\n")); 779 "acpi_sbs_read_word() failed"));
764 goto end; 780 goto end;
765 } 781 }
766 782
@@ -774,36 +790,36 @@ static int acpi_battery_init(struct acpi_battery *battery)
774 790
775 result = acpi_battery_select(battery); 791 result = acpi_battery_select(battery);
776 if (result) { 792 if (result) {
777 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 793 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
778 "acpi_battery_init() failed\n")); 794 "acpi_battery_select() failed"));
779 goto end; 795 goto end;
780 } 796 }
781 797
782 result = acpi_battery_set_mode(battery); 798 result = acpi_battery_set_mode(battery);
783 if (result) { 799 if (result) {
784 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 800 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
785 "acpi_battery_set_mode() failed\n")); 801 "acpi_battery_set_mode() failed"));
786 goto end; 802 goto end;
787 } 803 }
788 804
789 result = acpi_battery_get_info(battery); 805 result = acpi_battery_get_info(battery);
790 if (result) { 806 if (result) {
791 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 807 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
792 "acpi_battery_get_info() failed\n")); 808 "acpi_battery_get_info() failed"));
793 goto end; 809 goto end;
794 } 810 }
795 811
796 result = acpi_battery_get_state(battery); 812 result = acpi_battery_get_state(battery);
797 if (result) { 813 if (result) {
798 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 814 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
799 "acpi_battery_get_state() failed\n")); 815 "acpi_battery_get_state() failed"));
800 goto end; 816 goto end;
801 } 817 }
802 818
803 result = acpi_battery_get_alarm(battery); 819 result = acpi_battery_get_alarm(battery);
804 if (result) { 820 if (result) {
805 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 821 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
806 "acpi_battery_get_alarm() failed\n")); 822 "acpi_battery_get_alarm() failed"));
807 goto end; 823 goto end;
808 } 824 }
809 825
@@ -813,20 +829,19 @@ static int acpi_battery_init(struct acpi_battery *battery)
813 829
814static int acpi_ac_get_present(struct acpi_sbs *sbs) 830static int acpi_ac_get_present(struct acpi_sbs *sbs)
815{ 831{
816 struct acpi_ec_smbus *smbus = sbs->smbus;
817 int result = 0; 832 int result = 0;
818 s16 charger_status; 833 s16 charger_status;
819 834
820 result = acpi_sbs_smbus_read_word(smbus, ACPI_SBC_SMBUS_ADDR, 0x13, 835 result = acpi_sbs_read_word(sbs, ACPI_SBC_SMBUS_ADDR, 0x13,
821 &charger_status, NULL); 836 &charger_status);
822 837
823 if (result) { 838 if (result) {
824 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 839 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
825 "acpi_sbs_smbus_read_word() failed\n")); 840 "acpi_sbs_read_word() failed"));
826 goto end; 841 goto end;
827 } 842 }
828 843
829 sbs->ac_present = (charger_status & 0x8000) >> 15; 844 sbs->ac.ac_present = (charger_status & 0x8000) >> 15;
830 845
831 end: 846 end:
832 847
@@ -852,8 +867,8 @@ acpi_sbs_generic_add_fs(struct proc_dir_entry **dir,
852 if (!*dir) { 867 if (!*dir) {
853 *dir = proc_mkdir(dir_name, parent_dir); 868 *dir = proc_mkdir(dir_name, parent_dir);
854 if (!*dir) { 869 if (!*dir) {
855 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 870 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
856 "proc_mkdir() failed\n")); 871 "proc_mkdir() failed"));
857 return -ENODEV; 872 return -ENODEV;
858 } 873 }
859 (*dir)->owner = THIS_MODULE; 874 (*dir)->owner = THIS_MODULE;
@@ -863,8 +878,8 @@ acpi_sbs_generic_add_fs(struct proc_dir_entry **dir,
863 if (info_fops) { 878 if (info_fops) {
864 entry = create_proc_entry(ACPI_SBS_FILE_INFO, S_IRUGO, *dir); 879 entry = create_proc_entry(ACPI_SBS_FILE_INFO, S_IRUGO, *dir);
865 if (!entry) { 880 if (!entry) {
866 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 881 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
867 "create_proc_entry() failed\n")); 882 "create_proc_entry() failed"));
868 } else { 883 } else {
869 entry->proc_fops = info_fops; 884 entry->proc_fops = info_fops;
870 entry->data = data; 885 entry->data = data;
@@ -876,8 +891,8 @@ acpi_sbs_generic_add_fs(struct proc_dir_entry **dir,
876 if (state_fops) { 891 if (state_fops) {
877 entry = create_proc_entry(ACPI_SBS_FILE_STATE, S_IRUGO, *dir); 892 entry = create_proc_entry(ACPI_SBS_FILE_STATE, S_IRUGO, *dir);
878 if (!entry) { 893 if (!entry) {
879 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 894 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
880 "create_proc_entry() failed\n")); 895 "create_proc_entry() failed"));
881 } else { 896 } else {
882 entry->proc_fops = state_fops; 897 entry->proc_fops = state_fops;
883 entry->data = data; 898 entry->data = data;
@@ -889,8 +904,8 @@ acpi_sbs_generic_add_fs(struct proc_dir_entry **dir,
889 if (alarm_fops) { 904 if (alarm_fops) {
890 entry = create_proc_entry(ACPI_SBS_FILE_ALARM, S_IRUGO, *dir); 905 entry = create_proc_entry(ACPI_SBS_FILE_ALARM, S_IRUGO, *dir);
891 if (!entry) { 906 if (!entry) {
892 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 907 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
893 "create_proc_entry() failed\n")); 908 "create_proc_entry() failed"));
894 } else { 909 } else {
895 entry->proc_fops = alarm_fops; 910 entry->proc_fops = alarm_fops;
896 entry->data = data; 911 entry->data = data;
@@ -923,24 +938,27 @@ static struct proc_dir_entry *acpi_battery_dir = NULL;
923static int acpi_battery_read_info(struct seq_file *seq, void *offset) 938static int acpi_battery_read_info(struct seq_file *seq, void *offset)
924{ 939{
925 struct acpi_battery *battery = seq->private; 940 struct acpi_battery *battery = seq->private;
941 struct acpi_sbs *sbs = battery->sbs;
926 int cscale; 942 int cscale;
927 int result = 0; 943 int result = 0;
928 944
929 if (battery->sbs->zombie) { 945 if (sbs_mutex_lock(sbs)) {
930 return -ENODEV; 946 return -ENODEV;
931 } 947 }
932 948
933 down(&sbs_sem); 949 result = acpi_check_update_proc(sbs);
950 if (result)
951 goto end;
934 952
935 if (update_mode == REQUEST_UPDATE_MODE) { 953 if (update_time == 0) {
936 result = acpi_sbs_update_run(battery->sbs, DATA_TYPE_INFO); 954 result = acpi_sbs_update_run(sbs, battery->id, DATA_TYPE_INFO);
937 if (result) { 955 if (result) {
938 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 956 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
939 "acpi_sbs_update_run() failed\n")); 957 "acpi_sbs_update_run() failed"));
940 } 958 }
941 } 959 }
942 960
943 if (acpi_battery_is_present(battery)) { 961 if (battery->battery_present) {
944 seq_printf(seq, "present: yes\n"); 962 seq_printf(seq, "present: yes\n");
945 } else { 963 } else {
946 seq_printf(seq, "present: no\n"); 964 seq_printf(seq, "present: no\n");
@@ -952,13 +970,13 @@ static int acpi_battery_read_info(struct seq_file *seq, void *offset)
952 } else { 970 } else {
953 cscale = battery->info.ipscale; 971 cscale = battery->info.ipscale;
954 } 972 }
955 seq_printf(seq, "design capacity: %i%s", 973 seq_printf(seq, "design capacity: %i%s\n",
956 battery->info.design_capacity * cscale, 974 battery->info.design_capacity * cscale,
957 battery->info.capacity_mode ? "0 mWh\n" : " mAh\n"); 975 battery->info.capacity_mode ? "0 mWh" : " mAh");
958 976
959 seq_printf(seq, "last full capacity: %i%s", 977 seq_printf(seq, "last full capacity: %i%s\n",
960 battery->info.full_charge_capacity * cscale, 978 battery->info.full_charge_capacity * cscale,
961 battery->info.capacity_mode ? "0 mWh\n" : " mAh\n"); 979 battery->info.capacity_mode ? "0 mWh" : " mAh");
962 980
963 seq_printf(seq, "battery technology: rechargeable\n"); 981 seq_printf(seq, "battery technology: rechargeable\n");
964 982
@@ -984,7 +1002,7 @@ static int acpi_battery_read_info(struct seq_file *seq, void *offset)
984 1002
985 end: 1003 end:
986 1004
987 up(&sbs_sem); 1005 sbs_mutex_unlock(sbs);
988 1006
989 return result; 1007 return result;
990} 1008}
@@ -996,26 +1014,29 @@ static int acpi_battery_info_open_fs(struct inode *inode, struct file *file)
996 1014
997static int acpi_battery_read_state(struct seq_file *seq, void *offset) 1015static int acpi_battery_read_state(struct seq_file *seq, void *offset)
998{ 1016{
999 struct acpi_battery *battery = (struct acpi_battery *)seq->private; 1017 struct acpi_battery *battery = seq->private;
1018 struct acpi_sbs *sbs = battery->sbs;
1000 int result = 0; 1019 int result = 0;
1001 int cscale; 1020 int cscale;
1002 int foo; 1021 int foo;
1003 1022
1004 if (battery->sbs->zombie) { 1023 if (sbs_mutex_lock(sbs)) {
1005 return -ENODEV; 1024 return -ENODEV;
1006 } 1025 }
1007 1026
1008 down(&sbs_sem); 1027 result = acpi_check_update_proc(sbs);
1028 if (result)
1029 goto end;
1009 1030
1010 if (update_mode == REQUEST_UPDATE_MODE) { 1031 if (update_time == 0) {
1011 result = acpi_sbs_update_run(battery->sbs, DATA_TYPE_STATE); 1032 result = acpi_sbs_update_run(sbs, battery->id, DATA_TYPE_STATE);
1012 if (result) { 1033 if (result) {
1013 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1034 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1014 "acpi_sbs_update_run() failed\n")); 1035 "acpi_sbs_update_run() failed"));
1015 } 1036 }
1016 } 1037 }
1017 1038
1018 if (acpi_battery_is_present(battery)) { 1039 if (battery->battery_present) {
1019 seq_printf(seq, "present: yes\n"); 1040 seq_printf(seq, "present: yes\n");
1020 } else { 1041 } else {
1021 seq_printf(seq, "present: no\n"); 1042 seq_printf(seq, "present: no\n");
@@ -1028,7 +1049,7 @@ static int acpi_battery_read_state(struct seq_file *seq, void *offset)
1028 cscale = battery->info.ipscale; 1049 cscale = battery->info.ipscale;
1029 } 1050 }
1030 1051
1031 if (battery->state.battery_status & 0x0010) { 1052 if (battery->state.battery_state & 0x0010) {
1032 seq_printf(seq, "capacity state: critical\n"); 1053 seq_printf(seq, "capacity state: critical\n");
1033 } else { 1054 } else {
1034 seq_printf(seq, "capacity state: ok\n"); 1055 seq_printf(seq, "capacity state: ok\n");
@@ -1052,16 +1073,16 @@ static int acpi_battery_read_state(struct seq_file *seq, void *offset)
1052 battery->info.capacity_mode ? "mW" : "mA"); 1073 battery->info.capacity_mode ? "mW" : "mA");
1053 } 1074 }
1054 1075
1055 seq_printf(seq, "remaining capacity: %i%s", 1076 seq_printf(seq, "remaining capacity: %i%s\n",
1056 battery->state.remaining_capacity * cscale, 1077 battery->state.remaining_capacity * cscale,
1057 battery->info.capacity_mode ? "0 mWh\n" : " mAh\n"); 1078 battery->info.capacity_mode ? "0 mWh" : " mAh");
1058 1079
1059 seq_printf(seq, "present voltage: %i mV\n", 1080 seq_printf(seq, "present voltage: %i mV\n",
1060 battery->state.voltage * battery->info.vscale); 1081 battery->state.voltage * battery->info.vscale);
1061 1082
1062 end: 1083 end:
1063 1084
1064 up(&sbs_sem); 1085 sbs_mutex_unlock(sbs);
1065 1086
1066 return result; 1087 return result;
1067} 1088}
@@ -1074,24 +1095,27 @@ static int acpi_battery_state_open_fs(struct inode *inode, struct file *file)
1074static int acpi_battery_read_alarm(struct seq_file *seq, void *offset) 1095static int acpi_battery_read_alarm(struct seq_file *seq, void *offset)
1075{ 1096{
1076 struct acpi_battery *battery = seq->private; 1097 struct acpi_battery *battery = seq->private;
1098 struct acpi_sbs *sbs = battery->sbs;
1077 int result = 0; 1099 int result = 0;
1078 int cscale; 1100 int cscale;
1079 1101
1080 if (battery->sbs->zombie) { 1102 if (sbs_mutex_lock(sbs)) {
1081 return -ENODEV; 1103 return -ENODEV;
1082 } 1104 }
1083 1105
1084 down(&sbs_sem); 1106 result = acpi_check_update_proc(sbs);
1107 if (result)
1108 goto end;
1085 1109
1086 if (update_mode == REQUEST_UPDATE_MODE) { 1110 if (update_time == 0) {
1087 result = acpi_sbs_update_run(battery->sbs, DATA_TYPE_ALARM); 1111 result = acpi_sbs_update_run(sbs, battery->id, DATA_TYPE_ALARM);
1088 if (result) { 1112 if (result) {
1089 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1113 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1090 "acpi_sbs_update_run() failed\n")); 1114 "acpi_sbs_update_run() failed"));
1091 } 1115 }
1092 } 1116 }
1093 1117
1094 if (!acpi_battery_is_present(battery)) { 1118 if (!battery->battery_present) {
1095 seq_printf(seq, "present: no\n"); 1119 seq_printf(seq, "present: no\n");
1096 goto end; 1120 goto end;
1097 } 1121 }
@@ -1104,16 +1128,16 @@ static int acpi_battery_read_alarm(struct seq_file *seq, void *offset)
1104 1128
1105 seq_printf(seq, "alarm: "); 1129 seq_printf(seq, "alarm: ");
1106 if (battery->alarm.remaining_capacity) { 1130 if (battery->alarm.remaining_capacity) {
1107 seq_printf(seq, "%i%s", 1131 seq_printf(seq, "%i%s\n",
1108 battery->alarm.remaining_capacity * cscale, 1132 battery->alarm.remaining_capacity * cscale,
1109 battery->info.capacity_mode ? "0 mWh\n" : " mAh\n"); 1133 battery->info.capacity_mode ? "0 mWh" : " mAh");
1110 } else { 1134 } else {
1111 seq_printf(seq, "disabled\n"); 1135 seq_printf(seq, "disabled\n");
1112 } 1136 }
1113 1137
1114 end: 1138 end:
1115 1139
1116 up(&sbs_sem); 1140 sbs_mutex_unlock(sbs);
1117 1141
1118 return result; 1142 return result;
1119} 1143}
@@ -1124,16 +1148,19 @@ acpi_battery_write_alarm(struct file *file, const char __user * buffer,
1124{ 1148{
1125 struct seq_file *seq = file->private_data; 1149 struct seq_file *seq = file->private_data;
1126 struct acpi_battery *battery = seq->private; 1150 struct acpi_battery *battery = seq->private;
1151 struct acpi_sbs *sbs = battery->sbs;
1127 char alarm_string[12] = { '\0' }; 1152 char alarm_string[12] = { '\0' };
1128 int result, old_alarm, new_alarm; 1153 int result, old_alarm, new_alarm;
1129 1154
1130 if (battery->sbs->zombie) { 1155 if (sbs_mutex_lock(sbs)) {
1131 return -ENODEV; 1156 return -ENODEV;
1132 } 1157 }
1133 1158
1134 down(&sbs_sem); 1159 result = acpi_check_update_proc(sbs);
1160 if (result)
1161 goto end;
1135 1162
1136 if (!acpi_battery_is_present(battery)) { 1163 if (!battery->battery_present) {
1137 result = -ENODEV; 1164 result = -ENODEV;
1138 goto end; 1165 goto end;
1139 } 1166 }
@@ -1155,21 +1182,21 @@ acpi_battery_write_alarm(struct file *file, const char __user * buffer,
1155 1182
1156 result = acpi_battery_set_alarm(battery, new_alarm); 1183 result = acpi_battery_set_alarm(battery, new_alarm);
1157 if (result) { 1184 if (result) {
1158 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1185 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1159 "acpi_battery_set_alarm() failed\n")); 1186 "acpi_battery_set_alarm() failed"));
1160 acpi_battery_set_alarm(battery, old_alarm); 1187 acpi_battery_set_alarm(battery, old_alarm);
1161 goto end; 1188 goto end;
1162 } 1189 }
1163 result = acpi_battery_get_alarm(battery); 1190 result = acpi_battery_get_alarm(battery);
1164 if (result) { 1191 if (result) {
1165 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1192 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1166 "acpi_battery_get_alarm() failed\n")); 1193 "acpi_battery_get_alarm() failed"));
1167 acpi_battery_set_alarm(battery, old_alarm); 1194 acpi_battery_set_alarm(battery, old_alarm);
1168 goto end; 1195 goto end;
1169 } 1196 }
1170 1197
1171 end: 1198 end:
1172 up(&sbs_sem); 1199 sbs_mutex_unlock(sbs);
1173 1200
1174 if (result) { 1201 if (result) {
1175 return result; 1202 return result;
@@ -1217,24 +1244,22 @@ static int acpi_ac_read_state(struct seq_file *seq, void *offset)
1217 struct acpi_sbs *sbs = seq->private; 1244 struct acpi_sbs *sbs = seq->private;
1218 int result; 1245 int result;
1219 1246
1220 if (sbs->zombie) { 1247 if (sbs_mutex_lock(sbs)) {
1221 return -ENODEV; 1248 return -ENODEV;
1222 } 1249 }
1223 1250
1224 down(&sbs_sem); 1251 if (update_time == 0) {
1225 1252 result = acpi_sbs_update_run(sbs, -1, DATA_TYPE_AC_STATE);
1226 if (update_mode == REQUEST_UPDATE_MODE) {
1227 result = acpi_sbs_update_run(sbs, DATA_TYPE_AC_STATE);
1228 if (result) { 1253 if (result) {
1229 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1254 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1230 "acpi_sbs_update_run() failed\n")); 1255 "acpi_sbs_update_run() failed"));
1231 } 1256 }
1232 } 1257 }
1233 1258
1234 seq_printf(seq, "state: %s\n", 1259 seq_printf(seq, "state: %s\n",
1235 sbs->ac_present ? "on-line" : "off-line"); 1260 sbs->ac.ac_present ? "on-line" : "off-line");
1236 1261
1237 up(&sbs_sem); 1262 sbs_mutex_unlock(sbs);
1238 1263
1239 return 0; 1264 return 0;
1240} 1265}
@@ -1275,25 +1300,25 @@ static int acpi_battery_add(struct acpi_sbs *sbs, int id)
1275 1300
1276 result = acpi_battery_select(battery); 1301 result = acpi_battery_select(battery);
1277 if (result) { 1302 if (result) {
1278 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1303 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1279 "acpi_battery_select() failed\n")); 1304 "acpi_battery_select() failed"));
1280 goto end; 1305 goto end;
1281 } 1306 }
1282 1307
1283 result = acpi_battery_get_present(battery); 1308 result = acpi_battery_get_present(battery);
1284 if (result) { 1309 if (result) {
1285 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1310 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1286 "acpi_battery_get_present() failed\n")); 1311 "acpi_battery_get_present() failed"));
1287 goto end; 1312 goto end;
1288 } 1313 }
1289 1314
1290 is_present = acpi_battery_is_present(battery); 1315 is_present = battery->battery_present;
1291 1316
1292 if (is_present) { 1317 if (is_present) {
1293 result = acpi_battery_init(battery); 1318 result = acpi_battery_init(battery);
1294 if (result) { 1319 if (result) {
1295 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1320 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1296 "acpi_battery_init() failed\n")); 1321 "acpi_battery_init() failed"));
1297 goto end; 1322 goto end;
1298 } 1323 }
1299 battery->init_state = 1; 1324 battery->init_state = 1;
@@ -1308,12 +1333,16 @@ static int acpi_battery_add(struct acpi_sbs *sbs, int id)
1308 &acpi_battery_state_fops, 1333 &acpi_battery_state_fops,
1309 &acpi_battery_alarm_fops, battery); 1334 &acpi_battery_alarm_fops, battery);
1310 if (result) { 1335 if (result) {
1311 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1336 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1312 "acpi_sbs_generic_add_fs() failed\n")); 1337 "acpi_sbs_generic_add_fs() failed"));
1313 goto end; 1338 goto end;
1314 } 1339 }
1315 battery->alive = 1; 1340 battery->alive = 1;
1316 1341
1342 printk(KERN_INFO PREFIX "%s [%s]: Battery Slot [%s] (battery %s)\n",
1343 ACPI_SBS_DEVICE_NAME, acpi_device_bid(sbs->device), dir_name,
1344 sbs->battery->battery_present ? "present" : "absent");
1345
1317 end: 1346 end:
1318 return result; 1347 return result;
1319} 1348}
@@ -1333,8 +1362,8 @@ static int acpi_ac_add(struct acpi_sbs *sbs)
1333 1362
1334 result = acpi_ac_get_present(sbs); 1363 result = acpi_ac_get_present(sbs);
1335 if (result) { 1364 if (result) {
1336 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1365 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1337 "acpi_ac_get_present() failed\n")); 1366 "acpi_ac_get_present() failed"));
1338 goto end; 1367 goto end;
1339 } 1368 }
1340 1369
@@ -1343,11 +1372,15 @@ static int acpi_ac_add(struct acpi_sbs *sbs)
1343 ACPI_AC_DIR_NAME, 1372 ACPI_AC_DIR_NAME,
1344 NULL, &acpi_ac_state_fops, NULL, sbs); 1373 NULL, &acpi_ac_state_fops, NULL, sbs);
1345 if (result) { 1374 if (result) {
1346 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1375 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1347 "acpi_sbs_generic_add_fs() failed\n")); 1376 "acpi_sbs_generic_add_fs() failed"));
1348 goto end; 1377 goto end;
1349 } 1378 }
1350 1379
1380 printk(KERN_INFO PREFIX "%s [%s]: AC Adapter [%s] (%s)\n",
1381 ACPI_SBS_DEVICE_NAME, acpi_device_bid(sbs->device),
1382 ACPI_AC_DIR_NAME, sbs->ac.ac_present ? "on-line" : "off-line");
1383
1351 end: 1384 end:
1352 1385
1353 return result; 1386 return result;
@@ -1361,45 +1394,85 @@ static void acpi_ac_remove(struct acpi_sbs *sbs)
1361 } 1394 }
1362} 1395}
1363 1396
1364static void acpi_sbs_update_queue_run(unsigned long data) 1397static void acpi_sbs_update_time_run(unsigned long data)
1365{ 1398{
1366 acpi_os_execute(OSL_GPE_HANDLER, acpi_sbs_update_queue, (void *)data); 1399 acpi_os_execute(OSL_GPE_HANDLER, acpi_sbs_update_time, (void *)data);
1367} 1400}
1368 1401
1369static int acpi_sbs_update_run(struct acpi_sbs *sbs, int data_type) 1402static int acpi_sbs_update_run(struct acpi_sbs *sbs, int id, int data_type)
1370{ 1403{
1371 struct acpi_battery *battery; 1404 struct acpi_battery *battery;
1372 int result = 0; 1405 int result = 0, cnt;
1373 int old_ac_present; 1406 int old_ac_present = -1;
1374 int old_battery_present; 1407 int old_battery_present = -1;
1375 int new_ac_present; 1408 int new_ac_present = -1;
1376 int new_battery_present; 1409 int new_battery_present = -1;
1377 int id; 1410 int id_min = 0, id_max = MAX_SBS_BAT - 1;
1378 char dir_name[32]; 1411 char dir_name[32];
1379 int do_battery_init, do_ac_init; 1412 int do_battery_init = 0, do_ac_init = 0;
1380 s16 old_remaining_capacity; 1413 int old_remaining_capacity = 0;
1414 int update_ac = 1, update_battery = 1;
1415 int up_tm = update_time;
1381 1416
1382 if (sbs->zombie) { 1417 if (sbs_zombie(sbs)) {
1383 goto end; 1418 goto end;
1384 } 1419 }
1385 1420
1386 old_ac_present = acpi_ac_is_present(sbs); 1421 if (id >= 0) {
1422 id_min = id_max = id;
1423 }
1424
1425 if (data_type == DATA_TYPE_COMMON && up_tm > 0) {
1426 cnt = up_tm / (up_tm > UPDATE_DELAY ? UPDATE_DELAY : up_tm);
1427 if (sbs->run_cnt % cnt != 0) {
1428 update_battery = 0;
1429 }
1430 }
1431
1432 sbs->run_cnt++;
1433
1434 if (!update_ac && !update_battery) {
1435 goto end;
1436 }
1437
1438 old_ac_present = sbs->ac.ac_present;
1387 1439
1388 result = acpi_ac_get_present(sbs); 1440 result = acpi_ac_get_present(sbs);
1389 if (result) { 1441 if (result) {
1390 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1442 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1391 "acpi_ac_get_present() failed\n")); 1443 "acpi_ac_get_present() failed"));
1392 } 1444 }
1393 1445
1394 new_ac_present = acpi_ac_is_present(sbs); 1446 new_ac_present = sbs->ac.ac_present;
1395 1447
1396 do_ac_init = (old_ac_present != new_ac_present); 1448 do_ac_init = (old_ac_present != new_ac_present);
1449 if (sbs->run_cnt == 1 && data_type == DATA_TYPE_COMMON) {
1450 do_ac_init = 1;
1451 }
1397 1452
1398 if (data_type == DATA_TYPE_AC_STATE) { 1453 if (do_ac_init) {
1454 result = acpi_sbs_generate_event(sbs->device,
1455 ACPI_SBS_AC_NOTIFY_STATUS,
1456 new_ac_present,
1457 ACPI_AC_DIR_NAME,
1458 ACPI_AC_CLASS);
1459 if (result) {
1460 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1461 "acpi_sbs_generate_event() failed"));
1462 }
1463 }
1464
1465 if (data_type == DATA_TYPE_COMMON) {
1466 if (!do_ac_init && !update_battery) {
1467 goto end;
1468 }
1469 }
1470
1471 if (data_type == DATA_TYPE_AC_STATE && !do_ac_init) {
1399 goto end; 1472 goto end;
1400 } 1473 }
1401 1474
1402 for (id = 0; id < MAX_SBS_BAT; id++) { 1475 for (id = id_min; id <= id_max; id++) {
1403 battery = &sbs->battery[id]; 1476 battery = &sbs->battery[id];
1404 if (battery->alive == 0) { 1477 if (battery->alive == 0) {
1405 continue; 1478 continue;
@@ -1407,94 +1480,92 @@ static int acpi_sbs_update_run(struct acpi_sbs *sbs, int data_type)
1407 1480
1408 old_remaining_capacity = battery->state.remaining_capacity; 1481 old_remaining_capacity = battery->state.remaining_capacity;
1409 1482
1410 old_battery_present = acpi_battery_is_present(battery); 1483 old_battery_present = battery->battery_present;
1411 1484
1412 result = acpi_battery_select(battery); 1485 result = acpi_battery_select(battery);
1413 if (result) { 1486 if (result) {
1414 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1487 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1415 "acpi_battery_select() failed\n")); 1488 "acpi_battery_select() failed"));
1416 }
1417 if (sbs->zombie) {
1418 goto end;
1419 } 1489 }
1420 1490
1421 result = acpi_battery_get_present(battery); 1491 result = acpi_battery_get_present(battery);
1422 if (result) { 1492 if (result) {
1423 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1493 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1424 "acpi_battery_get_present() failed\n")); 1494 "acpi_battery_get_present() failed"));
1425 }
1426 if (sbs->zombie) {
1427 goto end;
1428 } 1495 }
1429 1496
1430 new_battery_present = acpi_battery_is_present(battery); 1497 new_battery_present = battery->battery_present;
1431 1498
1432 do_battery_init = ((old_battery_present != new_battery_present) 1499 do_battery_init = ((old_battery_present != new_battery_present)
1433 && new_battery_present); 1500 && new_battery_present);
1434 1501 if (!new_battery_present)
1435 if (sbs->zombie) { 1502 goto event;
1503 if (do_ac_init || do_battery_init) {
1504 result = acpi_battery_init(battery);
1505 if (result) {
1506 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1507 "acpi_battery_init() "
1508 "failed"));
1509 }
1510 }
1511 if (sbs_zombie(sbs)) {
1436 goto end; 1512 goto end;
1437 } 1513 }
1438 if (do_ac_init || do_battery_init || 1514
1439 update_info_mode || sbs->update_info_mode) { 1515 if ((data_type == DATA_TYPE_COMMON
1440 if (sbs->update_info_mode) { 1516 || data_type == DATA_TYPE_INFO)
1441 sbs->update_info_mode = 0; 1517 && new_battery_present) {
1442 } else { 1518 result = acpi_battery_get_info(battery);
1443 sbs->update_info_mode = 1;
1444 }
1445 result = acpi_battery_init(battery);
1446 if (result) { 1519 if (result) {
1447 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1520 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1448 "acpi_battery_init() " 1521 "acpi_battery_get_info() failed"));
1449 "failed\n"));
1450 } 1522 }
1451 } 1523 }
1452 if (data_type == DATA_TYPE_INFO) { 1524 if (data_type == DATA_TYPE_INFO) {
1453 continue; 1525 continue;
1454 } 1526 }
1455 1527 if (sbs_zombie(sbs)) {
1456 if (sbs->zombie) {
1457 goto end; 1528 goto end;
1458 } 1529 }
1459 if (new_battery_present) {
1460 result = acpi_battery_get_alarm(battery);
1461 if (result) {
1462 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
1463 "acpi_battery_get_alarm() "
1464 "failed\n"));
1465 }
1466 if (data_type == DATA_TYPE_ALARM) {
1467 continue;
1468 }
1469 1530
1531 if ((data_type == DATA_TYPE_COMMON
1532 || data_type == DATA_TYPE_STATE)
1533 && new_battery_present) {
1470 result = acpi_battery_get_state(battery); 1534 result = acpi_battery_get_state(battery);
1471 if (result) { 1535 if (result) {
1472 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1536 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1473 "acpi_battery_get_state() " 1537 "acpi_battery_get_state() failed"));
1474 "failed\n"));
1475 } 1538 }
1476 } 1539 }
1477 if (sbs->zombie) { 1540 if (data_type == DATA_TYPE_STATE) {
1478 goto end; 1541 goto event;
1479 } 1542 }
1480 if (data_type != DATA_TYPE_COMMON) { 1543 if (sbs_zombie(sbs)) {
1481 continue; 1544 goto end;
1482 } 1545 }
1483 1546
1484 if (old_battery_present != new_battery_present) { 1547 if ((data_type == DATA_TYPE_COMMON
1485 sprintf(dir_name, ACPI_BATTERY_DIR_NAME, id); 1548 || data_type == DATA_TYPE_ALARM)
1486 result = acpi_sbs_generate_event(sbs->device, 1549 && new_battery_present) {
1487 ACPI_SBS_BATTERY_NOTIFY_STATUS, 1550 result = acpi_battery_get_alarm(battery);
1488 new_battery_present,
1489 dir_name,
1490 ACPI_BATTERY_CLASS);
1491 if (result) { 1551 if (result) {
1492 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1552 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1493 "acpi_sbs_generate_event() " 1553 "acpi_battery_get_alarm() "
1494 "failed\n")); 1554 "failed"));
1495 } 1555 }
1496 } 1556 }
1497 if (old_remaining_capacity != battery->state.remaining_capacity) { 1557 if (data_type == DATA_TYPE_ALARM) {
1558 continue;
1559 }
1560 if (sbs_zombie(sbs)) {
1561 goto end;
1562 }
1563
1564 event:
1565
1566 if (old_battery_present != new_battery_present || do_ac_init ||
1567 old_remaining_capacity !=
1568 battery->state.remaining_capacity) {
1498 sprintf(dir_name, ACPI_BATTERY_DIR_NAME, id); 1569 sprintf(dir_name, ACPI_BATTERY_DIR_NAME, id);
1499 result = acpi_sbs_generate_event(sbs->device, 1570 result = acpi_sbs_generate_event(sbs->device,
1500 ACPI_SBS_BATTERY_NOTIFY_STATUS, 1571 ACPI_SBS_BATTERY_NOTIFY_STATUS,
@@ -1502,138 +1573,120 @@ static int acpi_sbs_update_run(struct acpi_sbs *sbs, int data_type)
1502 dir_name, 1573 dir_name,
1503 ACPI_BATTERY_CLASS); 1574 ACPI_BATTERY_CLASS);
1504 if (result) { 1575 if (result) {
1505 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1576 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1506 "acpi_sbs_generate_event() failed\n")); 1577 "acpi_sbs_generate_event() "
1578 "failed"));
1507 } 1579 }
1508 } 1580 }
1509
1510 }
1511 if (sbs->zombie) {
1512 goto end;
1513 }
1514 if (data_type != DATA_TYPE_COMMON) {
1515 goto end;
1516 }
1517
1518 if (old_ac_present != new_ac_present) {
1519 result = acpi_sbs_generate_event(sbs->device,
1520 ACPI_SBS_AC_NOTIFY_STATUS,
1521 new_ac_present,
1522 ACPI_AC_DIR_NAME,
1523 ACPI_AC_CLASS);
1524 if (result) {
1525 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
1526 "acpi_sbs_generate_event() failed\n"));
1527 }
1528 } 1581 }
1529 1582
1530 end: 1583 end:
1584
1531 return result; 1585 return result;
1532} 1586}
1533 1587
1534static void acpi_sbs_update_queue(void *data) 1588static void acpi_sbs_update_time(void *data)
1535{ 1589{
1536 struct acpi_sbs *sbs = data; 1590 struct acpi_sbs *sbs = data;
1537 unsigned long delay = -1; 1591 unsigned long delay = -1;
1538 int result; 1592 int result;
1593 unsigned int up_tm = update_time;
1539 1594
1540 if (sbs->zombie) { 1595 if (sbs_mutex_lock(sbs))
1541 goto end; 1596 return;
1542 }
1543 1597
1544 result = acpi_sbs_update_run(sbs, DATA_TYPE_COMMON); 1598 result = acpi_sbs_update_run(sbs, -1, DATA_TYPE_COMMON);
1545 if (result) { 1599 if (result) {
1546 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1600 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1547 "acpi_sbs_update_run() failed\n")); 1601 "acpi_sbs_update_run() failed"));
1548 } 1602 }
1549 1603
1550 if (sbs->zombie) { 1604 if (sbs_zombie(sbs)) {
1551 goto end; 1605 goto end;
1552 } 1606 }
1553 1607
1554 if (update_mode == REQUEST_UPDATE_MODE) { 1608 if (!up_tm) {
1555 goto end; 1609 if (timer_pending(&sbs->update_timer))
1610 del_timer(&sbs->update_timer);
1611 } else {
1612 delay = (up_tm > UPDATE_DELAY ? UPDATE_DELAY : up_tm);
1613 delay = jiffies + HZ * delay;
1614 if (timer_pending(&sbs->update_timer)) {
1615 mod_timer(&sbs->update_timer, delay);
1616 } else {
1617 sbs->update_timer.data = (unsigned long)data;
1618 sbs->update_timer.function = acpi_sbs_update_time_run;
1619 sbs->update_timer.expires = delay;
1620 add_timer(&sbs->update_timer);
1621 }
1556 } 1622 }
1557 1623
1558 delay = jiffies + HZ * update_time;
1559 sbs->update_timer.data = (unsigned long)data;
1560 sbs->update_timer.function = acpi_sbs_update_queue_run;
1561 sbs->update_timer.expires = delay;
1562 add_timer(&sbs->update_timer);
1563 end: 1624 end:
1564 ; 1625
1626 sbs_mutex_unlock(sbs);
1565} 1627}
1566 1628
1567static int acpi_sbs_add(struct acpi_device *device) 1629static int acpi_sbs_add(struct acpi_device *device)
1568{ 1630{
1569 struct acpi_sbs *sbs = NULL; 1631 struct acpi_sbs *sbs = NULL;
1570 struct acpi_ec_hc *ec_hc = NULL; 1632 int result = 0, remove_result = 0;
1571 int result, remove_result = 0;
1572 unsigned long sbs_obj; 1633 unsigned long sbs_obj;
1573 int id, cnt; 1634 int id;
1574 acpi_status status = AE_OK; 1635 acpi_status status = AE_OK;
1636 unsigned long val;
1637
1638 status =
1639 acpi_evaluate_integer(device->parent->handle, "_EC", NULL, &val);
1640 if (ACPI_FAILURE(status)) {
1641 ACPI_EXCEPTION((AE_INFO, AE_ERROR, "Error obtaining _EC"));
1642 return -EIO;
1643 }
1575 1644
1576 sbs = kzalloc(sizeof(struct acpi_sbs), GFP_KERNEL); 1645 sbs = kzalloc(sizeof(struct acpi_sbs), GFP_KERNEL);
1577 if (!sbs) { 1646 if (!sbs) {
1578 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, "kmalloc() failed\n")); 1647 ACPI_EXCEPTION((AE_INFO, AE_ERROR, "kzalloc() failed"));
1579 return -ENOMEM; 1648 result = -ENOMEM;
1649 goto end;
1580 } 1650 }
1581 1651
1582 cnt = 0; 1652 mutex_init(&sbs->mutex);
1583 while (cnt < 10) {
1584 cnt++;
1585 ec_hc = acpi_get_ec_hc(device);
1586 if (ec_hc) {
1587 break;
1588 }
1589 msleep(1000);
1590 }
1591 1653
1592 if (!ec_hc) { 1654 sbs_mutex_lock(sbs);
1593 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
1594 "acpi_get_ec_hc() failed: "
1595 "NO driver found for EC HC SMBus\n"));
1596 result = -ENODEV;
1597 goto end;
1598 }
1599 1655
1656 sbs->base = (val & 0xff00ull) >> 8;
1600 sbs->device = device; 1657 sbs->device = device;
1601 sbs->smbus = ec_hc->smbus;
1602 1658
1603 strcpy(acpi_device_name(device), ACPI_SBS_DEVICE_NAME); 1659 strcpy(acpi_device_name(device), ACPI_SBS_DEVICE_NAME);
1604 strcpy(acpi_device_class(device), ACPI_SBS_CLASS); 1660 strcpy(acpi_device_class(device), ACPI_SBS_CLASS);
1605 acpi_driver_data(device) = sbs; 1661 acpi_driver_data(device) = sbs;
1606 1662
1607 sbs->update_time = 0;
1608 sbs->update_time2 = 0;
1609
1610 result = acpi_ac_add(sbs); 1663 result = acpi_ac_add(sbs);
1611 if (result) { 1664 if (result) {
1612 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, "acpi_ac_add() failed\n")); 1665 ACPI_EXCEPTION((AE_INFO, AE_ERROR, "acpi_ac_add() failed"));
1613 goto end; 1666 goto end;
1614 } 1667 }
1615 result = acpi_evaluate_integer(device->handle, "_SBS", NULL, &sbs_obj); 1668 status = acpi_evaluate_integer(device->handle, "_SBS", NULL, &sbs_obj);
1616 if (ACPI_FAILURE(result)) { 1669 if (status) {
1617 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1670 ACPI_EXCEPTION((AE_INFO, status,
1618 "acpi_evaluate_integer() failed\n")); 1671 "acpi_evaluate_integer() failed"));
1619 result = -EIO; 1672 result = -EIO;
1620 goto end; 1673 goto end;
1621 } 1674 }
1622
1623 if (sbs_obj > 0) { 1675 if (sbs_obj > 0) {
1624 result = acpi_sbsm_get_info(sbs); 1676 result = acpi_sbsm_get_info(sbs);
1625 if (result) { 1677 if (result) {
1626 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1678 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1627 "acpi_sbsm_get_info() failed\n")); 1679 "acpi_sbsm_get_info() failed"));
1628 goto end; 1680 goto end;
1629 } 1681 }
1630 sbs->sbsm_present = 1; 1682 sbs->sbsm_present = 1;
1631 } 1683 }
1684
1632 if (sbs->sbsm_present == 0) { 1685 if (sbs->sbsm_present == 0) {
1633 result = acpi_battery_add(sbs, 0); 1686 result = acpi_battery_add(sbs, 0);
1634 if (result) { 1687 if (result) {
1635 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1688 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1636 "acpi_battery_add() failed\n")); 1689 "acpi_battery_add() failed"));
1637 goto end; 1690 goto end;
1638 } 1691 }
1639 } else { 1692 } else {
@@ -1641,9 +1694,8 @@ static int acpi_sbs_add(struct acpi_device *device)
1641 if ((sbs->sbsm_batteries_supported & (1 << id))) { 1694 if ((sbs->sbsm_batteries_supported & (1 << id))) {
1642 result = acpi_battery_add(sbs, id); 1695 result = acpi_battery_add(sbs, id);
1643 if (result) { 1696 if (result) {
1644 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1697 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1645 "acpi_battery_add() " 1698 "acpi_battery_add() failed"));
1646 "failed\n"));
1647 goto end; 1699 goto end;
1648 } 1700 }
1649 } 1701 }
@@ -1653,33 +1705,26 @@ static int acpi_sbs_add(struct acpi_device *device)
1653 sbs->handle = device->handle; 1705 sbs->handle = device->handle;
1654 1706
1655 init_timer(&sbs->update_timer); 1707 init_timer(&sbs->update_timer);
1656 if (update_mode == QUEUE_UPDATE_MODE) { 1708 result = acpi_check_update_proc(sbs);
1657 status = acpi_os_execute(OSL_GPE_HANDLER, 1709 if (result)
1658 acpi_sbs_update_queue, sbs); 1710 goto end;
1659 if (status != AE_OK) {
1660 ACPI_DEBUG_PRINT((ACPI_DB_ERROR,
1661 "acpi_os_execute() failed\n"));
1662 }
1663 }
1664 sbs->update_time = update_time;
1665 sbs->update_time2 = update_time2;
1666
1667 printk(KERN_INFO PREFIX "%s [%s]\n",
1668 acpi_device_name(device), acpi_device_bid(device));
1669 1711
1670 end: 1712 end:
1713
1714 sbs_mutex_unlock(sbs);
1715
1671 if (result) { 1716 if (result) {
1672 remove_result = acpi_sbs_remove(device, 0); 1717 remove_result = acpi_sbs_remove(device, 0);
1673 if (remove_result) { 1718 if (remove_result) {
1674 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1719 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1675 "acpi_sbs_remove() failed\n")); 1720 "acpi_sbs_remove() failed"));
1676 } 1721 }
1677 } 1722 }
1678 1723
1679 return result; 1724 return result;
1680} 1725}
1681 1726
1682int acpi_sbs_remove(struct acpi_device *device, int type) 1727static int acpi_sbs_remove(struct acpi_device *device, int type)
1683{ 1728{
1684 struct acpi_sbs *sbs; 1729 struct acpi_sbs *sbs;
1685 int id; 1730 int id;
@@ -1688,15 +1733,14 @@ int acpi_sbs_remove(struct acpi_device *device, int type)
1688 return -EINVAL; 1733 return -EINVAL;
1689 } 1734 }
1690 1735
1691 sbs = (struct acpi_sbs *)acpi_driver_data(device); 1736 sbs = acpi_driver_data(device);
1692
1693 if (!sbs) { 1737 if (!sbs) {
1694 return -EINVAL; 1738 return -EINVAL;
1695 } 1739 }
1696 1740
1741 sbs_mutex_lock(sbs);
1742
1697 sbs->zombie = 1; 1743 sbs->zombie = 1;
1698 sbs->update_time = 0;
1699 sbs->update_time2 = 0;
1700 del_timer_sync(&sbs->update_timer); 1744 del_timer_sync(&sbs->update_timer);
1701 acpi_os_wait_events_complete(NULL); 1745 acpi_os_wait_events_complete(NULL);
1702 del_timer_sync(&sbs->update_timer); 1746 del_timer_sync(&sbs->update_timer);
@@ -1707,11 +1751,41 @@ int acpi_sbs_remove(struct acpi_device *device, int type)
1707 1751
1708 acpi_ac_remove(sbs); 1752 acpi_ac_remove(sbs);
1709 1753
1754 sbs_mutex_unlock(sbs);
1755
1756 mutex_destroy(&sbs->mutex);
1757
1710 kfree(sbs); 1758 kfree(sbs);
1711 1759
1712 return 0; 1760 return 0;
1713} 1761}
1714 1762
1763static void acpi_sbs_rmdirs(void)
1764{
1765 if (acpi_ac_dir) {
1766 acpi_unlock_ac_dir(acpi_ac_dir);
1767 acpi_ac_dir = NULL;
1768 }
1769 if (acpi_battery_dir) {
1770 acpi_unlock_battery_dir(acpi_battery_dir);
1771 acpi_battery_dir = NULL;
1772 }
1773}
1774
1775static int acpi_sbs_resume(struct acpi_device *device)
1776{
1777 struct acpi_sbs *sbs;
1778
1779 if (!device)
1780 return -EINVAL;
1781
1782 sbs = device->driver_data;
1783
1784 sbs->run_cnt = 0;
1785
1786 return 0;
1787}
1788
1715static int __init acpi_sbs_init(void) 1789static int __init acpi_sbs_init(void)
1716{ 1790{
1717 int result = 0; 1791 int result = 0;
@@ -1719,35 +1793,34 @@ static int __init acpi_sbs_init(void)
1719 if (acpi_disabled) 1793 if (acpi_disabled)
1720 return -ENODEV; 1794 return -ENODEV;
1721 1795
1722 init_MUTEX(&sbs_sem);
1723
1724 if (capacity_mode != DEF_CAPACITY_UNIT 1796 if (capacity_mode != DEF_CAPACITY_UNIT
1725 && capacity_mode != MAH_CAPACITY_UNIT 1797 && capacity_mode != MAH_CAPACITY_UNIT
1726 && capacity_mode != MWH_CAPACITY_UNIT) { 1798 && capacity_mode != MWH_CAPACITY_UNIT) {
1727 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, "acpi_sbs_init: " 1799 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1728 "invalid capacity_mode = %d\n", 1800 "invalid capacity_mode = %d", capacity_mode));
1729 capacity_mode));
1730 return -EINVAL; 1801 return -EINVAL;
1731 } 1802 }
1732 1803
1733 acpi_ac_dir = acpi_lock_ac_dir(); 1804 acpi_ac_dir = acpi_lock_ac_dir();
1734 if (!acpi_ac_dir) { 1805 if (!acpi_ac_dir) {
1735 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1806 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1736 "acpi_lock_ac_dir() failed\n")); 1807 "acpi_lock_ac_dir() failed"));
1737 return -ENODEV; 1808 return -ENODEV;
1738 } 1809 }
1739 1810
1740 acpi_battery_dir = acpi_lock_battery_dir(); 1811 acpi_battery_dir = acpi_lock_battery_dir();
1741 if (!acpi_battery_dir) { 1812 if (!acpi_battery_dir) {
1742 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1813 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1743 "acpi_lock_battery_dir() failed\n")); 1814 "acpi_lock_battery_dir() failed"));
1815 acpi_sbs_rmdirs();
1744 return -ENODEV; 1816 return -ENODEV;
1745 } 1817 }
1746 1818
1747 result = acpi_bus_register_driver(&acpi_sbs_driver); 1819 result = acpi_bus_register_driver(&acpi_sbs_driver);
1748 if (result < 0) { 1820 if (result < 0) {
1749 ACPI_DEBUG_PRINT((ACPI_DB_ERROR, 1821 ACPI_EXCEPTION((AE_INFO, AE_ERROR,
1750 "acpi_bus_register_driver() failed\n")); 1822 "acpi_bus_register_driver() failed"));
1823 acpi_sbs_rmdirs();
1751 return -ENODEV; 1824 return -ENODEV;
1752 } 1825 }
1753 1826
@@ -1756,13 +1829,9 @@ static int __init acpi_sbs_init(void)
1756 1829
1757static void __exit acpi_sbs_exit(void) 1830static void __exit acpi_sbs_exit(void)
1758{ 1831{
1759
1760 acpi_bus_unregister_driver(&acpi_sbs_driver); 1832 acpi_bus_unregister_driver(&acpi_sbs_driver);
1761 1833
1762 acpi_unlock_ac_dir(acpi_ac_dir); 1834 acpi_sbs_rmdirs();
1763 acpi_ac_dir = NULL;
1764 acpi_unlock_battery_dir(acpi_battery_dir);
1765 acpi_battery_dir = NULL;
1766 1835
1767 return; 1836 return;
1768} 1837}
diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c
index bb0e0da39fb1..6b3b8a522476 100644
--- a/drivers/acpi/scan.c
+++ b/drivers/acpi/scan.c
@@ -302,7 +302,7 @@ static void acpi_device_shutdown(struct device *dev)
302 return ; 302 return ;
303} 303}
304 304
305static struct bus_type acpi_bus_type = { 305struct bus_type acpi_bus_type = {
306 .name = "acpi", 306 .name = "acpi",
307 .suspend = acpi_device_suspend, 307 .suspend = acpi_device_suspend,
308 .resume = acpi_device_resume, 308 .resume = acpi_device_resume,
@@ -1068,7 +1068,9 @@ acpi_add_single_object(struct acpi_device **child,
1068 } 1068 }
1069 break; 1069 break;
1070 default: 1070 default:
1071 STRUCT_TO_INT(device->status) = 0x0F; 1071 STRUCT_TO_INT(device->status) =
1072 ACPI_STA_DEVICE_PRESENT | ACPI_STA_DEVICE_ENABLED |
1073 ACPI_STA_DEVICE_UI | ACPI_STA_DEVICE_FUNCTIONING;
1072 break; 1074 break;
1073 } 1075 }
1074 1076
diff --git a/drivers/acpi/sleep/main.c b/drivers/acpi/sleep/main.c
index 37a0930fc0a6..52b23471dd69 100644
--- a/drivers/acpi/sleep/main.c
+++ b/drivers/acpi/sleep/main.c
@@ -29,7 +29,6 @@ static u32 acpi_suspend_states[] = {
29 [PM_SUSPEND_ON] = ACPI_STATE_S0, 29 [PM_SUSPEND_ON] = ACPI_STATE_S0,
30 [PM_SUSPEND_STANDBY] = ACPI_STATE_S1, 30 [PM_SUSPEND_STANDBY] = ACPI_STATE_S1,
31 [PM_SUSPEND_MEM] = ACPI_STATE_S3, 31 [PM_SUSPEND_MEM] = ACPI_STATE_S3,
32 [PM_SUSPEND_DISK] = ACPI_STATE_S4,
33 [PM_SUSPEND_MAX] = ACPI_STATE_S5 32 [PM_SUSPEND_MAX] = ACPI_STATE_S5
34}; 33};
35 34
@@ -94,14 +93,6 @@ static int acpi_pm_enter(suspend_state_t pm_state)
94 do_suspend_lowlevel(); 93 do_suspend_lowlevel();
95 break; 94 break;
96 95
97 case PM_SUSPEND_DISK:
98 if (acpi_pm_ops.pm_disk_mode == PM_DISK_PLATFORM)
99 status = acpi_enter_sleep_state(acpi_state);
100 break;
101 case PM_SUSPEND_MAX:
102 acpi_power_off();
103 break;
104
105 default: 96 default:
106 return -EINVAL; 97 return -EINVAL;
107 } 98 }
@@ -157,20 +148,30 @@ int acpi_suspend(u32 acpi_state)
157 suspend_state_t states[] = { 148 suspend_state_t states[] = {
158 [1] = PM_SUSPEND_STANDBY, 149 [1] = PM_SUSPEND_STANDBY,
159 [3] = PM_SUSPEND_MEM, 150 [3] = PM_SUSPEND_MEM,
160 [4] = PM_SUSPEND_DISK,
161 [5] = PM_SUSPEND_MAX 151 [5] = PM_SUSPEND_MAX
162 }; 152 };
163 153
164 if (acpi_state < 6 && states[acpi_state]) 154 if (acpi_state < 6 && states[acpi_state])
165 return pm_suspend(states[acpi_state]); 155 return pm_suspend(states[acpi_state]);
156 if (acpi_state == 4)
157 return hibernate();
166 return -EINVAL; 158 return -EINVAL;
167} 159}
168 160
169static int acpi_pm_state_valid(suspend_state_t pm_state) 161static int acpi_pm_state_valid(suspend_state_t pm_state)
170{ 162{
171 u32 acpi_state = acpi_suspend_states[pm_state]; 163 u32 acpi_state;
172 164
173 return sleep_states[acpi_state]; 165 switch (pm_state) {
166 case PM_SUSPEND_ON:
167 case PM_SUSPEND_STANDBY:
168 case PM_SUSPEND_MEM:
169 acpi_state = acpi_suspend_states[pm_state];
170
171 return sleep_states[acpi_state];
172 default:
173 return 0;
174 }
174} 175}
175 176
176static struct pm_ops acpi_pm_ops = { 177static struct pm_ops acpi_pm_ops = {
@@ -180,6 +181,49 @@ static struct pm_ops acpi_pm_ops = {
180 .finish = acpi_pm_finish, 181 .finish = acpi_pm_finish,
181}; 182};
182 183
184#ifdef CONFIG_SOFTWARE_SUSPEND
185static int acpi_hibernation_prepare(void)
186{
187 return acpi_sleep_prepare(ACPI_STATE_S4);
188}
189
190static int acpi_hibernation_enter(void)
191{
192 acpi_status status = AE_OK;
193 unsigned long flags = 0;
194
195 ACPI_FLUSH_CPU_CACHE();
196
197 local_irq_save(flags);
198 acpi_enable_wakeup_device(ACPI_STATE_S4);
199 /* This shouldn't return. If it returns, we have a problem */
200 status = acpi_enter_sleep_state(ACPI_STATE_S4);
201 local_irq_restore(flags);
202
203 return ACPI_SUCCESS(status) ? 0 : -EFAULT;
204}
205
206static void acpi_hibernation_finish(void)
207{
208 acpi_leave_sleep_state(ACPI_STATE_S4);
209 acpi_disable_wakeup_device(ACPI_STATE_S4);
210
211 /* reset firmware waking vector */
212 acpi_set_firmware_waking_vector((acpi_physical_address) 0);
213
214 if (init_8259A_after_S1) {
215 printk("Broken toshiba laptop -> kicking interrupts\n");
216 init_8259A(0);
217 }
218}
219
220static struct hibernation_ops acpi_hibernation_ops = {
221 .prepare = acpi_hibernation_prepare,
222 .enter = acpi_hibernation_enter,
223 .finish = acpi_hibernation_finish,
224};
225#endif /* CONFIG_SOFTWARE_SUSPEND */
226
183/* 227/*
184 * Toshiba fails to preserve interrupts over S1, reinitialization 228 * Toshiba fails to preserve interrupts over S1, reinitialization
185 * of 8259 is needed after S1 resume. 229 * of 8259 is needed after S1 resume.
@@ -218,14 +262,18 @@ int __init acpi_sleep_init(void)
218 sleep_states[i] = 1; 262 sleep_states[i] = 1;
219 printk(" S%d", i); 263 printk(" S%d", i);
220 } 264 }
221 if (i == ACPI_STATE_S4) {
222 if (sleep_states[i])
223 acpi_pm_ops.pm_disk_mode = PM_DISK_PLATFORM;
224 }
225 } 265 }
226 printk(")\n"); 266 printk(")\n");
227 267
228 pm_set_ops(&acpi_pm_ops); 268 pm_set_ops(&acpi_pm_ops);
269
270#ifdef CONFIG_SOFTWARE_SUSPEND
271 if (sleep_states[ACPI_STATE_S4])
272 hibernation_set_ops(&acpi_hibernation_ops);
273#else
274 sleep_states[ACPI_STATE_S4] = 0;
275#endif
276
229 return 0; 277 return 0;
230} 278}
231 279
diff --git a/drivers/acpi/sleep/proc.c b/drivers/acpi/sleep/proc.c
index ccc11b33d89c..76b45f0b8341 100644
--- a/drivers/acpi/sleep/proc.c
+++ b/drivers/acpi/sleep/proc.c
@@ -60,7 +60,7 @@ acpi_system_write_sleep(struct file *file,
60 state = simple_strtoul(str, NULL, 0); 60 state = simple_strtoul(str, NULL, 0);
61#ifdef CONFIG_SOFTWARE_SUSPEND 61#ifdef CONFIG_SOFTWARE_SUSPEND
62 if (state == 4) { 62 if (state == 4) {
63 error = software_suspend(); 63 error = hibernate();
64 goto Done; 64 goto Done;
65 } 65 }
66#endif 66#endif
@@ -70,6 +70,14 @@ acpi_system_write_sleep(struct file *file,
70} 70}
71#endif /* CONFIG_ACPI_SLEEP_PROC_SLEEP */ 71#endif /* CONFIG_ACPI_SLEEP_PROC_SLEEP */
72 72
73#if defined(CONFIG_RTC_DRV_CMOS) || defined(CONFIG_RTC_DRV_CMOS_MODULE)
74/* use /sys/class/rtc/rtcX/wakealarm instead; it's not ACPI-specific */
75#else
76#define HAVE_ACPI_LEGACY_ALARM
77#endif
78
79#ifdef HAVE_ACPI_LEGACY_ALARM
80
73static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset) 81static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset)
74{ 82{
75 u32 sec, min, hr; 83 u32 sec, min, hr;
@@ -341,6 +349,8 @@ acpi_system_write_alarm(struct file *file,
341 end: 349 end:
342 return_VALUE(result ? result : count); 350 return_VALUE(result ? result : count);
343} 351}
352#endif /* HAVE_ACPI_LEGACY_ALARM */
353
344 354
345extern struct list_head acpi_wakeup_device_list; 355extern struct list_head acpi_wakeup_device_list;
346extern spinlock_t acpi_device_lock; 356extern spinlock_t acpi_device_lock;
@@ -350,21 +360,31 @@ acpi_system_wakeup_device_seq_show(struct seq_file *seq, void *offset)
350{ 360{
351 struct list_head *node, *next; 361 struct list_head *node, *next;
352 362
353 seq_printf(seq, "Device Sleep state Status\n"); 363 seq_printf(seq, "Device\tS-state\t Status Sysfs node\n");
354 364
355 spin_lock(&acpi_device_lock); 365 spin_lock(&acpi_device_lock);
356 list_for_each_safe(node, next, &acpi_wakeup_device_list) { 366 list_for_each_safe(node, next, &acpi_wakeup_device_list) {
357 struct acpi_device *dev = 367 struct acpi_device *dev =
358 container_of(node, struct acpi_device, wakeup_list); 368 container_of(node, struct acpi_device, wakeup_list);
369 struct device *ldev;
359 370
360 if (!dev->wakeup.flags.valid) 371 if (!dev->wakeup.flags.valid)
361 continue; 372 continue;
362 spin_unlock(&acpi_device_lock); 373 spin_unlock(&acpi_device_lock);
363 seq_printf(seq, "%4s %4d %s%8s\n", 374
375 ldev = acpi_get_physical_device(dev->handle);
376 seq_printf(seq, "%s\t S%d\t%c%-8s ",
364 dev->pnp.bus_id, 377 dev->pnp.bus_id,
365 (u32) dev->wakeup.sleep_state, 378 (u32) dev->wakeup.sleep_state,
366 dev->wakeup.flags.run_wake ? "*" : "", 379 dev->wakeup.flags.run_wake ? '*' : ' ',
367 dev->wakeup.state.enabled ? "enabled" : "disabled"); 380 dev->wakeup.state.enabled ? "enabled" : "disabled");
381 if (ldev)
382 seq_printf(seq, "%s:%s",
383 ldev->bus ? ldev->bus->name : "no-bus",
384 ldev->bus_id);
385 seq_printf(seq, "\n");
386 put_device(ldev);
387
368 spin_lock(&acpi_device_lock); 388 spin_lock(&acpi_device_lock);
369 } 389 }
370 spin_unlock(&acpi_device_lock); 390 spin_unlock(&acpi_device_lock);
@@ -454,6 +474,7 @@ static const struct file_operations acpi_system_sleep_fops = {
454}; 474};
455#endif /* CONFIG_ACPI_SLEEP_PROC_SLEEP */ 475#endif /* CONFIG_ACPI_SLEEP_PROC_SLEEP */
456 476
477#ifdef HAVE_ACPI_LEGACY_ALARM
457static const struct file_operations acpi_system_alarm_fops = { 478static const struct file_operations acpi_system_alarm_fops = {
458 .open = acpi_system_alarm_open_fs, 479 .open = acpi_system_alarm_open_fs,
459 .read = seq_read, 480 .read = seq_read,
@@ -469,8 +490,9 @@ static u32 rtc_handler(void *context)
469 490
470 return ACPI_INTERRUPT_HANDLED; 491 return ACPI_INTERRUPT_HANDLED;
471} 492}
493#endif /* HAVE_ACPI_LEGACY_ALARM */
472 494
473static int acpi_sleep_proc_init(void) 495static int __init acpi_sleep_proc_init(void)
474{ 496{
475 struct proc_dir_entry *entry = NULL; 497 struct proc_dir_entry *entry = NULL;
476 498
@@ -486,6 +508,7 @@ static int acpi_sleep_proc_init(void)
486 entry->proc_fops = &acpi_system_sleep_fops; 508 entry->proc_fops = &acpi_system_sleep_fops;
487#endif 509#endif
488 510
511#ifdef HAVE_ACPI_LEGACY_ALARM
489 /* 'alarm' [R/W] */ 512 /* 'alarm' [R/W] */
490 entry = 513 entry =
491 create_proc_entry("alarm", S_IFREG | S_IRUGO | S_IWUSR, 514 create_proc_entry("alarm", S_IFREG | S_IRUGO | S_IWUSR,
@@ -493,6 +516,9 @@ static int acpi_sleep_proc_init(void)
493 if (entry) 516 if (entry)
494 entry->proc_fops = &acpi_system_alarm_fops; 517 entry->proc_fops = &acpi_system_alarm_fops;
495 518
519 acpi_install_fixed_event_handler(ACPI_EVENT_RTC, rtc_handler, NULL);
520#endif /* HAVE_ACPI_LEGACY_ALARM */
521
496 /* 'wakeup device' [R/W] */ 522 /* 'wakeup device' [R/W] */
497 entry = 523 entry =
498 create_proc_entry("wakeup", S_IFREG | S_IRUGO | S_IWUSR, 524 create_proc_entry("wakeup", S_IFREG | S_IRUGO | S_IWUSR,
@@ -500,7 +526,6 @@ static int acpi_sleep_proc_init(void)
500 if (entry) 526 if (entry)
501 entry->proc_fops = &acpi_system_wakeup_device_fops; 527 entry->proc_fops = &acpi_system_wakeup_device_fops;
502 528
503 acpi_install_fixed_event_handler(ACPI_EVENT_RTC, rtc_handler, NULL);
504 return 0; 529 return 0;
505} 530}
506 531
diff --git a/drivers/acpi/tables.c b/drivers/acpi/tables.c
index 849e2c361804..c3419182c9a7 100644
--- a/drivers/acpi/tables.c
+++ b/drivers/acpi/tables.c
@@ -42,7 +42,9 @@ static char *mps_inti_flags_trigger[] = { "dfl", "edge", "res", "level" };
42 42
43static struct acpi_table_desc initial_tables[ACPI_MAX_TABLES] __initdata; 43static struct acpi_table_desc initial_tables[ACPI_MAX_TABLES] __initdata;
44 44
45void acpi_table_print_madt_entry(struct acpi_subtable_header * header) 45static int acpi_apic_instance __initdata;
46
47void acpi_table_print_madt_entry(struct acpi_subtable_header *header)
46{ 48{
47 if (!header) 49 if (!header)
48 return; 50 return;
@@ -183,8 +185,10 @@ acpi_table_parse_entries(char *id,
183 if (!handler) 185 if (!handler)
184 return -EINVAL; 186 return -EINVAL;
185 187
186 /* Locate the table (if exists). There should only be one. */ 188 if (strncmp(id, ACPI_SIG_MADT, 4) == 0)
187 acpi_get_table(id, 0, &table_header); 189 acpi_get_table(id, acpi_apic_instance, &table_header);
190 else
191 acpi_get_table(id, 0, &table_header);
188 192
189 if (!table_header) { 193 if (!table_header) {
190 printk(KERN_WARNING PREFIX "%4.4s not present\n", id); 194 printk(KERN_WARNING PREFIX "%4.4s not present\n", id);
@@ -237,10 +241,15 @@ acpi_table_parse_madt(enum acpi_madt_type id,
237int __init acpi_table_parse(char *id, acpi_table_handler handler) 241int __init acpi_table_parse(char *id, acpi_table_handler handler)
238{ 242{
239 struct acpi_table_header *table = NULL; 243 struct acpi_table_header *table = NULL;
244
240 if (!handler) 245 if (!handler)
241 return -EINVAL; 246 return -EINVAL;
242 247
243 acpi_get_table(id, 0, &table); 248 if (strncmp(id, ACPI_SIG_MADT, 4) == 0)
249 acpi_get_table(id, acpi_apic_instance, &table);
250 else
251 acpi_get_table(id, 0, &table);
252
244 if (table) { 253 if (table) {
245 handler(table); 254 handler(table);
246 return 0; 255 return 0;
@@ -248,6 +257,31 @@ int __init acpi_table_parse(char *id, acpi_table_handler handler)
248 return 1; 257 return 1;
249} 258}
250 259
260/*
261 * The BIOS is supposed to supply a single APIC/MADT,
262 * but some report two. Provide a knob to use either.
263 * (don't you wish instance 0 and 1 were not the same?)
264 */
265static void __init check_multiple_madt(void)
266{
267 struct acpi_table_header *table = NULL;
268
269 acpi_get_table(ACPI_SIG_MADT, 2, &table);
270 if (table) {
271 printk(KERN_WARNING PREFIX
272 "BIOS bug: multiple APIC/MADT found,"
273 " using %d\n", acpi_apic_instance);
274 printk(KERN_WARNING PREFIX
275 "If \"acpi_apic_instance=%d\" works better, "
276 "notify linux-acpi@vger.kernel.org\n",
277 acpi_apic_instance ? 0 : 2);
278
279 } else
280 acpi_apic_instance = 0;
281
282 return;
283}
284
251/* 285/*
252 * acpi_table_init() 286 * acpi_table_init()
253 * 287 *
@@ -257,9 +291,22 @@ int __init acpi_table_parse(char *id, acpi_table_handler handler)
257 * result: sdt_entry[] is initialized 291 * result: sdt_entry[] is initialized
258 */ 292 */
259 293
260
261int __init acpi_table_init(void) 294int __init acpi_table_init(void)
262{ 295{
263 acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); 296 acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0);
297 check_multiple_madt();
298 return 0;
299}
300
301static int __init acpi_parse_apic_instance(char *str)
302{
303
304 acpi_apic_instance = simple_strtoul(str, NULL, 0);
305
306 printk(KERN_NOTICE PREFIX "Shall use APIC/MADT table %d\n",
307 acpi_apic_instance);
308
264 return 0; 309 return 0;
265} 310}
311
312early_param("acpi_apic_instance", acpi_parse_apic_instance);
diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c
index 807c7116e94b..1db833eb2417 100644
--- a/drivers/acpi/tables/tbfadt.c
+++ b/drivers/acpi/tables/tbfadt.c
@@ -347,6 +347,18 @@ static void acpi_tb_convert_fadt(void)
347 acpi_gbl_xpm1b_enable.space_id = acpi_gbl_FADT.xpm1a_event_block.space_id; 347 acpi_gbl_xpm1b_enable.space_id = acpi_gbl_FADT.xpm1a_event_block.space_id;
348 348
349 } 349 }
350
351 /*
352 * For ACPI 1.0 FADTs, ensure that reserved fields (which should be zero)
353 * are indeed zero. This will workaround BIOSs that inadvertently placed
354 * values in these fields.
355 */
356 if (acpi_gbl_FADT.header.revision < 3) {
357 acpi_gbl_FADT.preferred_profile = 0;
358 acpi_gbl_FADT.pstate_control = 0;
359 acpi_gbl_FADT.cst_control = 0;
360 acpi_gbl_FADT.boot_flags = 0;
361 }
350} 362}
351 363
352/****************************************************************************** 364/******************************************************************************
diff --git a/drivers/acpi/thermal.c b/drivers/acpi/thermal.c
index 0ae8b9310cbf..589b98b7b216 100644
--- a/drivers/acpi/thermal.c
+++ b/drivers/acpi/thermal.c
@@ -758,7 +758,8 @@ static void acpi_thermal_check(void *data)
758 del_timer(&(tz->timer)); 758 del_timer(&(tz->timer));
759 } else { 759 } else {
760 if (timer_pending(&(tz->timer))) 760 if (timer_pending(&(tz->timer)))
761 mod_timer(&(tz->timer), (HZ * sleep_time) / 1000); 761 mod_timer(&(tz->timer),
762 jiffies + (HZ * sleep_time) / 1000);
762 else { 763 else {
763 tz->timer.data = (unsigned long)tz; 764 tz->timer.data = (unsigned long)tz;
764 tz->timer.function = acpi_thermal_run; 765 tz->timer.function = acpi_thermal_run;
diff --git a/drivers/acpi/video.c b/drivers/acpi/video.c
index 0771b434feb2..00d25b347255 100644
--- a/drivers/acpi/video.c
+++ b/drivers/acpi/video.c
@@ -102,9 +102,9 @@ struct acpi_video_bus_cap {
102 102
103struct acpi_video_device_attrib { 103struct acpi_video_device_attrib {
104 u32 display_index:4; /* A zero-based instance of the Display */ 104 u32 display_index:4; /* A zero-based instance of the Display */
105 u32 display_port_attachment:4; /*This field differenates displays type */ 105 u32 display_port_attachment:4; /*This field differentiates the display type */
106 u32 display_type:4; /*Describe the specific type in use */ 106 u32 display_type:4; /*Describe the specific type in use */
107 u32 vendor_specific:4; /*Chipset Vendor Specifi */ 107 u32 vendor_specific:4; /*Chipset Vendor Specific */
108 u32 bios_can_detect:1; /*BIOS can detect the device */ 108 u32 bios_can_detect:1; /*BIOS can detect the device */
109 u32 depend_on_vga:1; /*Non-VGA output device whose power is related to 109 u32 depend_on_vga:1; /*Non-VGA output device whose power is related to
110 the VGA device. */ 110 the VGA device. */
@@ -484,16 +484,16 @@ acpi_video_bus_POST_options(struct acpi_video_bus *video,
484 * 0. The system BIOS should NOT automatically switch(toggle) 484 * 0. The system BIOS should NOT automatically switch(toggle)
485 * the active display output. 485 * the active display output.
486 * 1. The system BIOS should automatically switch (toggle) the 486 * 1. The system BIOS should automatically switch (toggle) the
487 * active display output. No swich event. 487 * active display output. No switch event.
488 * 2. The _DGS value should be locked. 488 * 2. The _DGS value should be locked.
489 * 3. The system BIOS should not automatically switch (toggle) the 489 * 3. The system BIOS should not automatically switch (toggle) the
490 * active display output, but instead generate the display switch 490 * active display output, but instead generate the display switch
491 * event notify code. 491 * event notify code.
492 * lcd_flag : 492 * lcd_flag :
493 * 0. The system BIOS should automatically control the brightness level 493 * 0. The system BIOS should automatically control the brightness level
494 * of the LCD, when the power changes from AC to DC 494 * of the LCD when the power changes from AC to DC
495 * 1. The system BIOS should NOT automatically control the brightness 495 * 1. The system BIOS should NOT automatically control the brightness
496 * level of the LCD, when the power changes from AC to DC. 496 * level of the LCD when the power changes from AC to DC.
497 * Return Value: 497 * Return Value:
498 * -1 wrong arg. 498 * -1 wrong arg.
499 */ 499 */
@@ -525,7 +525,7 @@ acpi_video_bus_DOS(struct acpi_video_bus *video, int bios_flag, int lcd_flag)
525 * Return Value: 525 * Return Value:
526 * None 526 * None
527 * 527 *
528 * Find out all required AML method defined under the output 528 * Find out all required AML methods defined under the output
529 * device. 529 * device.
530 */ 530 */
531 531
@@ -636,7 +636,7 @@ static void acpi_video_device_find_cap(struct acpi_video_device *device)
636 * Return Value: 636 * Return Value:
637 * None 637 * None
638 * 638 *
639 * Find out all required AML method defined under the video bus device. 639 * Find out all required AML methods defined under the video bus device.
640 */ 640 */
641 641
642static void acpi_video_bus_find_cap(struct acpi_video_bus *video) 642static void acpi_video_bus_find_cap(struct acpi_video_bus *video)
@@ -681,19 +681,19 @@ static int acpi_video_bus_check(struct acpi_video_bus *video)
681 * to check well known required nodes. 681 * to check well known required nodes.
682 */ 682 */
683 683
684 /* Does this device able to support video switching ? */ 684 /* Does this device support video switching? */
685 if (video->cap._DOS) { 685 if (video->cap._DOS) {
686 video->flags.multihead = 1; 686 video->flags.multihead = 1;
687 status = 0; 687 status = 0;
688 } 688 }
689 689
690 /* Does this device able to retrieve a retrieve a video ROM ? */ 690 /* Does this device support retrieving a video ROM? */
691 if (video->cap._ROM) { 691 if (video->cap._ROM) {
692 video->flags.rom = 1; 692 video->flags.rom = 1;
693 status = 0; 693 status = 0;
694 } 694 }
695 695
696 /* Does this device able to configure which video device to POST ? */ 696 /* Does this device support configuring which video device to POST? */
697 if (video->cap._GPD && video->cap._SPD && video->cap._VPO) { 697 if (video->cap._GPD && video->cap._SPD && video->cap._VPO) {
698 video->flags.post = 1; 698 video->flags.post = 1;
699 status = 0; 699 status = 0;
@@ -860,7 +860,7 @@ acpi_video_device_write_brightness(struct file *file,
860 if (level > 100) 860 if (level > 100)
861 return -EFAULT; 861 return -EFAULT;
862 862
863 /* validate though the list of available levels */ 863 /* validate through the list of available levels */
864 for (i = 0; i < dev->brightness->count; i++) 864 for (i = 0; i < dev->brightness->count; i++)
865 if (level == dev->brightness->levels[i]) { 865 if (level == dev->brightness->levels[i]) {
866 if (ACPI_SUCCESS 866 if (ACPI_SUCCESS
@@ -1065,10 +1065,10 @@ static int acpi_video_bus_POST_info_seq_show(struct seq_file *seq, void *offset)
1065 printk(KERN_WARNING PREFIX 1065 printk(KERN_WARNING PREFIX
1066 "The motherboard VGA device is not listed as a possible POST device.\n"); 1066 "The motherboard VGA device is not listed as a possible POST device.\n");
1067 printk(KERN_WARNING PREFIX 1067 printk(KERN_WARNING PREFIX
1068 "This indicate a BIOS bug. Please contact the manufacturer.\n"); 1068 "This indicates a BIOS bug. Please contact the manufacturer.\n");
1069 } 1069 }
1070 printk("%lx\n", options); 1070 printk("%lx\n", options);
1071 seq_printf(seq, "can POST: <intgrated video>"); 1071 seq_printf(seq, "can POST: <integrated video>");
1072 if (options & 2) 1072 if (options & 2)
1073 seq_printf(seq, " <PCI video>"); 1073 seq_printf(seq, " <PCI video>");
1074 if (options & 4) 1074 if (options & 4)
@@ -1102,7 +1102,7 @@ static int acpi_video_bus_POST_seq_show(struct seq_file *seq, void *offset)
1102 seq_printf(seq, "<not supported>\n"); 1102 seq_printf(seq, "<not supported>\n");
1103 goto end; 1103 goto end;
1104 } 1104 }
1105 seq_printf(seq, "device posted is <%s>\n", device_decode[id & 3]); 1105 seq_printf(seq, "device POSTed is <%s>\n", device_decode[id & 3]);
1106 1106
1107 end: 1107 end:
1108 return 0; 1108 return 0;
@@ -1156,7 +1156,7 @@ acpi_video_bus_write_POST(struct file *file,
1156 if (opt > 3) 1156 if (opt > 3)
1157 return -EFAULT; 1157 return -EFAULT;
1158 1158
1159 /* just in case an OEM 'forget' the motherboard... */ 1159 /* just in case an OEM 'forgot' the motherboard... */
1160 options |= 1; 1160 options |= 1;
1161 1161
1162 if (options & (1ul << opt)) { 1162 if (options & (1ul << opt)) {
@@ -1527,13 +1527,13 @@ static int acpi_video_device_enumerate(struct acpi_video_bus *video)
1527/* 1527/*
1528 * Arg: 1528 * Arg:
1529 * video : video bus device 1529 * video : video bus device
1530 * event : Nontify Event 1530 * event : notify event
1531 * 1531 *
1532 * Return: 1532 * Return:
1533 * < 0 : error 1533 * < 0 : error
1534 * 1534 *
1535 * 1. Find out the current active output device. 1535 * 1. Find out the current active output device.
1536 * 2. Identify the next output device to switch 1536 * 2. Identify the next output device to switch to.
1537 * 3. call _DSS to do actual switch. 1537 * 3. call _DSS to do actual switch.
1538 */ 1538 */
1539 1539
@@ -1723,12 +1723,12 @@ static void acpi_video_bus_notify(acpi_handle handle, u32 event, void *data)
1723 device = video->device; 1723 device = video->device;
1724 1724
1725 switch (event) { 1725 switch (event) {
1726 case ACPI_VIDEO_NOTIFY_SWITCH: /* User request that a switch occur, 1726 case ACPI_VIDEO_NOTIFY_SWITCH: /* User requested a switch,
1727 * most likely via hotkey. */ 1727 * most likely via hotkey. */
1728 acpi_bus_generate_event(device, event, 0); 1728 acpi_bus_generate_event(device, event, 0);
1729 break; 1729 break;
1730 1730
1731 case ACPI_VIDEO_NOTIFY_PROBE: /* User plug or remove a video 1731 case ACPI_VIDEO_NOTIFY_PROBE: /* User plugged in or removed a video
1732 * connector. */ 1732 * connector. */
1733 acpi_video_device_enumerate(video); 1733 acpi_video_device_enumerate(video);
1734 acpi_video_device_rebind(video); 1734 acpi_video_device_rebind(video);