7b5ee494cdf75510855219e39c9acafc219de293
[sfrench/cifs-2.6.git] / drivers / platform / x86 / eeepc-laptop.c
1 /*
2  *  eepc-laptop.c - Asus Eee PC extras
3  *
4  *  Based on asus_acpi.c as patched for the Eee PC by Asus:
5  *  ftp://ftp.asus.com/pub/ASUS/EeePC/701/ASUS_ACPI_071126.rar
6  *  Based on eee.c from eeepc-linux
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
19 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
20
21 #include <linux/kernel.h>
22 #include <linux/module.h>
23 #include <linux/init.h>
24 #include <linux/types.h>
25 #include <linux/platform_device.h>
26 #include <linux/backlight.h>
27 #include <linux/fb.h>
28 #include <linux/hwmon.h>
29 #include <linux/hwmon-sysfs.h>
30 #include <acpi/acpi_drivers.h>
31 #include <acpi/acpi_bus.h>
32 #include <linux/uaccess.h>
33 #include <linux/input.h>
34 #include <linux/rfkill.h>
35 #include <linux/pci.h>
36 #include <linux/pci_hotplug.h>
37
38 #define EEEPC_LAPTOP_VERSION    "0.1"
39
40 #define EEEPC_HOTK_NAME         "Eee PC Hotkey Driver"
41 #define EEEPC_HOTK_FILE         "eeepc"
42 #define EEEPC_HOTK_CLASS        "hotkey"
43 #define EEEPC_HOTK_DEVICE_NAME  "Hotkey"
44 #define EEEPC_HOTK_HID          "ASUS010"
45
46
47 /*
48  * Definitions for Asus EeePC
49  */
50 #define NOTIFY_WLAN_ON  0x10
51 #define NOTIFY_BRN_MIN  0x20
52 #define NOTIFY_BRN_MAX  0x2f
53
54 enum {
55         DISABLE_ASL_WLAN = 0x0001,
56         DISABLE_ASL_BLUETOOTH = 0x0002,
57         DISABLE_ASL_IRDA = 0x0004,
58         DISABLE_ASL_CAMERA = 0x0008,
59         DISABLE_ASL_TV = 0x0010,
60         DISABLE_ASL_GPS = 0x0020,
61         DISABLE_ASL_DISPLAYSWITCH = 0x0040,
62         DISABLE_ASL_MODEM = 0x0080,
63         DISABLE_ASL_CARDREADER = 0x0100,
64         DISABLE_ASL_3G = 0x0200,
65         DISABLE_ASL_WIMAX = 0x0400,
66         DISABLE_ASL_HWCF = 0x0800
67 };
68
69 enum {
70         CM_ASL_WLAN = 0,
71         CM_ASL_BLUETOOTH,
72         CM_ASL_IRDA,
73         CM_ASL_1394,
74         CM_ASL_CAMERA,
75         CM_ASL_TV,
76         CM_ASL_GPS,
77         CM_ASL_DVDROM,
78         CM_ASL_DISPLAYSWITCH,
79         CM_ASL_PANELBRIGHT,
80         CM_ASL_BIOSFLASH,
81         CM_ASL_ACPIFLASH,
82         CM_ASL_CPUFV,
83         CM_ASL_CPUTEMPERATURE,
84         CM_ASL_FANCPU,
85         CM_ASL_FANCHASSIS,
86         CM_ASL_USBPORT1,
87         CM_ASL_USBPORT2,
88         CM_ASL_USBPORT3,
89         CM_ASL_MODEM,
90         CM_ASL_CARDREADER,
91         CM_ASL_3G,
92         CM_ASL_WIMAX,
93         CM_ASL_HWCF,
94         CM_ASL_LID,
95         CM_ASL_TYPE,
96         CM_ASL_PANELPOWER,      /*P901*/
97         CM_ASL_TPD
98 };
99
100 static const char *cm_getv[] = {
101         "WLDG", "BTHG", NULL, NULL,
102         "CAMG", NULL, NULL, NULL,
103         NULL, "PBLG", NULL, NULL,
104         "CFVG", NULL, NULL, NULL,
105         "USBG", NULL, NULL, "MODG",
106         "CRDG", "M3GG", "WIMG", "HWCF",
107         "LIDG", "TYPE", "PBPG", "TPDG"
108 };
109
110 static const char *cm_setv[] = {
111         "WLDS", "BTHS", NULL, NULL,
112         "CAMS", NULL, NULL, NULL,
113         "SDSP", "PBLS", "HDPS", NULL,
114         "CFVS", NULL, NULL, NULL,
115         "USBG", NULL, NULL, "MODS",
116         "CRDS", "M3GS", "WIMS", NULL,
117         NULL, NULL, "PBPS", "TPDS"
118 };
119
120 #define EEEPC_EC        "\\_SB.PCI0.SBRG.EC0."
121
122 #define EEEPC_EC_FAN_PWM        EEEPC_EC "SC02" /* Fan PWM duty cycle (%) */
123 #define EEEPC_EC_SC02           0x63
124 #define EEEPC_EC_FAN_HRPM       EEEPC_EC "SC05" /* High byte, fan speed (RPM) */
125 #define EEEPC_EC_FAN_LRPM       EEEPC_EC "SC06" /* Low byte, fan speed (RPM) */
126 #define EEEPC_EC_FAN_CTRL       EEEPC_EC "SFB3" /* Byte containing SF25  */
127 #define EEEPC_EC_SFB3           0xD3
128
129 /*
130  * This is the main structure, we can use it to store useful information
131  * about the hotk device
132  */
133 struct eeepc_hotk {
134         struct acpi_device *device;     /* the device we are in */
135         acpi_handle handle;             /* the handle of the hotk device */
136         u32 cm_supported;               /* the control methods supported
137                                            by this BIOS */
138         uint init_flag;                 /* Init flags */
139         u16 event_count[128];           /* count for each event */
140         struct input_dev *inputdev;
141         u16 *keycode_map;
142         struct rfkill *wlan_rfkill;
143         struct rfkill *bluetooth_rfkill;
144         struct rfkill *wwan3g_rfkill;
145         struct hotplug_slot *hotplug_slot;
146         struct work_struct hotplug_work;
147 };
148
149 /* The actual device the driver binds to */
150 static struct eeepc_hotk *ehotk;
151
152 /* Platform device/driver */
153 static struct platform_driver platform_driver = {
154         .driver = {
155                 .name = EEEPC_HOTK_FILE,
156                 .owner = THIS_MODULE,
157         }
158 };
159
160 static struct platform_device *platform_device;
161
162 struct key_entry {
163         char type;
164         u8 code;
165         u16 keycode;
166 };
167
168 enum { KE_KEY, KE_END };
169
170 static struct key_entry eeepc_keymap[] = {
171         /* Sleep already handled via generic ACPI code */
172         {KE_KEY, 0x10, KEY_WLAN },
173         {KE_KEY, 0x11, KEY_WLAN },
174         {KE_KEY, 0x12, KEY_PROG1 },
175         {KE_KEY, 0x13, KEY_MUTE },
176         {KE_KEY, 0x14, KEY_VOLUMEDOWN },
177         {KE_KEY, 0x15, KEY_VOLUMEUP },
178         {KE_KEY, 0x1a, KEY_COFFEE },
179         {KE_KEY, 0x1b, KEY_ZOOM },
180         {KE_KEY, 0x1c, KEY_PROG2 },
181         {KE_KEY, 0x1d, KEY_PROG3 },
182         {KE_KEY, NOTIFY_BRN_MIN,     KEY_BRIGHTNESSDOWN },
183         {KE_KEY, NOTIFY_BRN_MIN + 2, KEY_BRIGHTNESSUP },
184         {KE_KEY, 0x30, KEY_SWITCHVIDEOMODE },
185         {KE_KEY, 0x31, KEY_SWITCHVIDEOMODE },
186         {KE_KEY, 0x32, KEY_SWITCHVIDEOMODE },
187         {KE_END, 0},
188 };
189
190 /*
191  * The hotkey driver declaration
192  */
193 static int eeepc_hotk_add(struct acpi_device *device);
194 static int eeepc_hotk_remove(struct acpi_device *device, int type);
195 static int eeepc_hotk_resume(struct acpi_device *device);
196 static void eeepc_hotk_notify(struct acpi_device *device, u32 event);
197
198 static const struct acpi_device_id eeepc_device_ids[] = {
199         {EEEPC_HOTK_HID, 0},
200         {"", 0},
201 };
202 MODULE_DEVICE_TABLE(acpi, eeepc_device_ids);
203
204 static struct acpi_driver eeepc_hotk_driver = {
205         .name = EEEPC_HOTK_NAME,
206         .class = EEEPC_HOTK_CLASS,
207         .ids = eeepc_device_ids,
208         .flags = ACPI_DRIVER_ALL_NOTIFY_EVENTS,
209         .ops = {
210                 .add = eeepc_hotk_add,
211                 .remove = eeepc_hotk_remove,
212                 .resume = eeepc_hotk_resume,
213                 .notify = eeepc_hotk_notify,
214         },
215 };
216
217 /* PCI hotplug ops */
218 static int eeepc_get_adapter_status(struct hotplug_slot *slot, u8 *value);
219
220 static struct hotplug_slot_ops eeepc_hotplug_slot_ops = {
221         .owner = THIS_MODULE,
222         .get_adapter_status = eeepc_get_adapter_status,
223         .get_power_status = eeepc_get_adapter_status,
224 };
225
226 /* The backlight device /sys/class/backlight */
227 static struct backlight_device *eeepc_backlight_device;
228
229 /* The hwmon device */
230 static struct device *eeepc_hwmon_device;
231
232 /*
233  * The backlight class declaration
234  */
235 static int read_brightness(struct backlight_device *bd);
236 static int update_bl_status(struct backlight_device *bd);
237 static struct backlight_ops eeepcbl_ops = {
238         .get_brightness = read_brightness,
239         .update_status = update_bl_status,
240 };
241
242 MODULE_AUTHOR("Corentin Chary, Eric Cooper");
243 MODULE_DESCRIPTION(EEEPC_HOTK_NAME);
244 MODULE_LICENSE("GPL");
245
246 /*
247  * ACPI Helpers
248  */
249 static int write_acpi_int(acpi_handle handle, const char *method, int val,
250                           struct acpi_buffer *output)
251 {
252         struct acpi_object_list params;
253         union acpi_object in_obj;
254         acpi_status status;
255
256         params.count = 1;
257         params.pointer = &in_obj;
258         in_obj.type = ACPI_TYPE_INTEGER;
259         in_obj.integer.value = val;
260
261         status = acpi_evaluate_object(handle, (char *)method, &params, output);
262         return (status == AE_OK ? 0 : -1);
263 }
264
265 static int read_acpi_int(acpi_handle handle, const char *method, int *val)
266 {
267         acpi_status status;
268         unsigned long long result;
269
270         status = acpi_evaluate_integer(handle, (char *)method, NULL, &result);
271         if (ACPI_FAILURE(status)) {
272                 *val = -1;
273                 return -1;
274         } else {
275                 *val = result;
276                 return 0;
277         }
278 }
279
280 static int set_acpi(int cm, int value)
281 {
282         if (ehotk->cm_supported & (0x1 << cm)) {
283                 const char *method = cm_setv[cm];
284                 if (method == NULL)
285                         return -ENODEV;
286                 if (write_acpi_int(ehotk->handle, method, value, NULL))
287                         pr_warning("Error writing %s\n", method);
288         }
289         return 0;
290 }
291
292 static int get_acpi(int cm)
293 {
294         int value = -ENODEV;
295         if ((ehotk->cm_supported & (0x1 << cm))) {
296                 const char *method = cm_getv[cm];
297                 if (method == NULL)
298                         return -ENODEV;
299                 if (read_acpi_int(ehotk->handle, method, &value))
300                         pr_warning("Error reading %s\n", method);
301         }
302         return value;
303 }
304
305 /*
306  * Backlight
307  */
308 static int read_brightness(struct backlight_device *bd)
309 {
310         return get_acpi(CM_ASL_PANELBRIGHT);
311 }
312
313 static int set_brightness(struct backlight_device *bd, int value)
314 {
315         value = max(0, min(15, value));
316         return set_acpi(CM_ASL_PANELBRIGHT, value);
317 }
318
319 static int update_bl_status(struct backlight_device *bd)
320 {
321         return set_brightness(bd, bd->props.brightness);
322 }
323
324 /*
325  * Rfkill helpers
326  */
327
328 static bool eeepc_wlan_rfkill_blocked(void)
329 {
330         if (get_acpi(CM_ASL_WLAN) == 1)
331                 return false;
332         return true;
333 }
334
335 static int eeepc_rfkill_set(void *data, bool blocked)
336 {
337         unsigned long asl = (unsigned long)data;
338         return set_acpi(asl, !blocked);
339 }
340
341 static const struct rfkill_ops eeepc_rfkill_ops = {
342         .set_block = eeepc_rfkill_set,
343 };
344
345 static void __init eeepc_enable_camera(void)
346 {
347         /*
348          * If the following call to set_acpi() fails, it's because there's no
349          * camera so we can ignore the error.
350          */
351         set_acpi(CM_ASL_CAMERA, 1);
352 }
353
354 /*
355  * Sys helpers
356  */
357 static int parse_arg(const char *buf, unsigned long count, int *val)
358 {
359         if (!count)
360                 return 0;
361         if (sscanf(buf, "%i", val) != 1)
362                 return -EINVAL;
363         return count;
364 }
365
366 static ssize_t store_sys_acpi(int cm, const char *buf, size_t count)
367 {
368         int rv, value;
369
370         rv = parse_arg(buf, count, &value);
371         if (rv > 0)
372                 value = set_acpi(cm, value);
373         if (value < 0)
374                 return value;
375         return rv;
376 }
377
378 static ssize_t show_sys_acpi(int cm, char *buf)
379 {
380         int value = get_acpi(cm);
381
382         if (value < 0)
383                 return value;
384         return sprintf(buf, "%d\n", value);
385 }
386
387 #define EEEPC_CREATE_DEVICE_ATTR(_name, _cm)                            \
388         static ssize_t show_##_name(struct device *dev,                 \
389                                     struct device_attribute *attr,      \
390                                     char *buf)                          \
391         {                                                               \
392                 return show_sys_acpi(_cm, buf);                         \
393         }                                                               \
394         static ssize_t store_##_name(struct device *dev,                \
395                                      struct device_attribute *attr,     \
396                                      const char *buf, size_t count)     \
397         {                                                               \
398                 return store_sys_acpi(_cm, buf, count);                 \
399         }                                                               \
400         static struct device_attribute dev_attr_##_name = {             \
401                 .attr = {                                               \
402                         .name = __stringify(_name),                     \
403                         .mode = 0644 },                                 \
404                 .show   = show_##_name,                                 \
405                 .store  = store_##_name,                                \
406         }
407
408 EEEPC_CREATE_DEVICE_ATTR(camera, CM_ASL_CAMERA);
409 EEEPC_CREATE_DEVICE_ATTR(cardr, CM_ASL_CARDREADER);
410 EEEPC_CREATE_DEVICE_ATTR(disp, CM_ASL_DISPLAYSWITCH);
411
412 struct eeepc_cpufv {
413         int num;
414         int cur;
415 };
416
417 static int get_cpufv(struct eeepc_cpufv *c)
418 {
419         c->cur = get_acpi(CM_ASL_CPUFV);
420         c->num = (c->cur >> 8) & 0xff;
421         c->cur &= 0xff;
422         if (c->cur < 0 || c->num <= 0 || c->num > 12)
423                 return -ENODEV;
424         return 0;
425 }
426
427 static ssize_t show_available_cpufv(struct device *dev,
428                                     struct device_attribute *attr,
429                                     char *buf)
430 {
431         struct eeepc_cpufv c;
432         int i;
433         ssize_t len = 0;
434
435         if (get_cpufv(&c))
436                 return -ENODEV;
437         for (i = 0; i < c.num; i++)
438                 len += sprintf(buf + len, "%d ", i);
439         len += sprintf(buf + len, "\n");
440         return len;
441 }
442
443 static ssize_t show_cpufv(struct device *dev,
444                           struct device_attribute *attr,
445                           char *buf)
446 {
447         struct eeepc_cpufv c;
448
449         if (get_cpufv(&c))
450                 return -ENODEV;
451         return sprintf(buf, "%#x\n", (c.num << 8) | c.cur);
452 }
453
454 static ssize_t store_cpufv(struct device *dev,
455                            struct device_attribute *attr,
456                            const char *buf, size_t count)
457 {
458         struct eeepc_cpufv c;
459         int rv, value;
460
461         if (get_cpufv(&c))
462                 return -ENODEV;
463         rv = parse_arg(buf, count, &value);
464         if (rv < 0)
465                 return rv;
466         if (!rv || value < 0 || value >= c.num)
467                 return -EINVAL;
468         set_acpi(CM_ASL_CPUFV, value);
469         return rv;
470 }
471
472 static struct device_attribute dev_attr_cpufv = {
473         .attr = {
474                 .name = "cpufv",
475                 .mode = 0644 },
476         .show   = show_cpufv,
477         .store  = store_cpufv
478 };
479
480 static struct device_attribute dev_attr_available_cpufv = {
481         .attr = {
482                 .name = "available_cpufv",
483                 .mode = 0444 },
484         .show   = show_available_cpufv
485 };
486
487 static struct attribute *platform_attributes[] = {
488         &dev_attr_camera.attr,
489         &dev_attr_cardr.attr,
490         &dev_attr_disp.attr,
491         &dev_attr_cpufv.attr,
492         &dev_attr_available_cpufv.attr,
493         NULL
494 };
495
496 static struct attribute_group platform_attribute_group = {
497         .attrs = platform_attributes
498 };
499
500 /*
501  * Hotkey functions
502  */
503 static struct key_entry *eepc_get_entry_by_scancode(int code)
504 {
505         struct key_entry *key;
506
507         for (key = eeepc_keymap; key->type != KE_END; key++)
508                 if (code == key->code)
509                         return key;
510
511         return NULL;
512 }
513
514 static struct key_entry *eepc_get_entry_by_keycode(int code)
515 {
516         struct key_entry *key;
517
518         for (key = eeepc_keymap; key->type != KE_END; key++)
519                 if (code == key->keycode && key->type == KE_KEY)
520                         return key;
521
522         return NULL;
523 }
524
525 static int eeepc_getkeycode(struct input_dev *dev, int scancode, int *keycode)
526 {
527         struct key_entry *key = eepc_get_entry_by_scancode(scancode);
528
529         if (key && key->type == KE_KEY) {
530                 *keycode = key->keycode;
531                 return 0;
532         }
533
534         return -EINVAL;
535 }
536
537 static int eeepc_setkeycode(struct input_dev *dev, int scancode, int keycode)
538 {
539         struct key_entry *key;
540         int old_keycode;
541
542         if (keycode < 0 || keycode > KEY_MAX)
543                 return -EINVAL;
544
545         key = eepc_get_entry_by_scancode(scancode);
546         if (key && key->type == KE_KEY) {
547                 old_keycode = key->keycode;
548                 key->keycode = keycode;
549                 set_bit(keycode, dev->keybit);
550                 if (!eepc_get_entry_by_keycode(old_keycode))
551                         clear_bit(old_keycode, dev->keybit);
552                 return 0;
553         }
554
555         return -EINVAL;
556 }
557
558 static void cmsg_quirk(int cm, const char *name)
559 {
560         int dummy;
561
562         /* Some BIOSes do not report cm although it is avaliable.
563            Check if cm_getv[cm] works and, if yes, assume cm should be set. */
564         if (!(ehotk->cm_supported & (1 << cm))
565             && !read_acpi_int(ehotk->handle, cm_getv[cm], &dummy)) {
566                 pr_info("%s (%x) not reported by BIOS,"
567                         " enabling anyway\n", name, 1 << cm);
568                 ehotk->cm_supported |= 1 << cm;
569         }
570 }
571
572 static void cmsg_quirks(void)
573 {
574         cmsg_quirk(CM_ASL_LID, "LID");
575         cmsg_quirk(CM_ASL_TYPE, "TYPE");
576         cmsg_quirk(CM_ASL_PANELPOWER, "PANELPOWER");
577         cmsg_quirk(CM_ASL_TPD, "TPD");
578 }
579
580 static int eeepc_hotk_check(void)
581 {
582         const struct key_entry *key;
583         struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL };
584         int result;
585
586         result = acpi_bus_get_status(ehotk->device);
587         if (result)
588                 return result;
589         if (ehotk->device->status.present) {
590                 if (write_acpi_int(ehotk->handle, "INIT", ehotk->init_flag,
591                                     &buffer)) {
592                         pr_err("Hotkey initialization failed\n");
593                         return -ENODEV;
594                 } else {
595                         pr_notice("Hotkey init flags 0x%x\n", ehotk->init_flag);
596                 }
597                 /* get control methods supported */
598                 if (read_acpi_int(ehotk->handle, "CMSG"
599                                    , &ehotk->cm_supported)) {
600                         pr_err("Get control methods supported failed\n");
601                         return -ENODEV;
602                 } else {
603                         cmsg_quirks();
604                         pr_info("Get control methods supported: 0x%x\n",
605                                 ehotk->cm_supported);
606                 }
607                 ehotk->inputdev = input_allocate_device();
608                 if (!ehotk->inputdev) {
609                         pr_info("Unable to allocate input device\n");
610                         return 0;
611                 }
612                 ehotk->inputdev->name = "Asus EeePC extra buttons";
613                 ehotk->inputdev->phys = EEEPC_HOTK_FILE "/input0";
614                 ehotk->inputdev->id.bustype = BUS_HOST;
615                 ehotk->inputdev->getkeycode = eeepc_getkeycode;
616                 ehotk->inputdev->setkeycode = eeepc_setkeycode;
617
618                 for (key = eeepc_keymap; key->type != KE_END; key++) {
619                         switch (key->type) {
620                         case KE_KEY:
621                                 set_bit(EV_KEY, ehotk->inputdev->evbit);
622                                 set_bit(key->keycode, ehotk->inputdev->keybit);
623                                 break;
624                         }
625                 }
626                 result = input_register_device(ehotk->inputdev);
627                 if (result) {
628                         pr_info("Unable to register input device\n");
629                         input_free_device(ehotk->inputdev);
630                         return 0;
631                 }
632         } else {
633                 pr_err("Hotkey device not present, aborting\n");
634                 return -EINVAL;
635         }
636         return 0;
637 }
638
639 static int notify_brn(void)
640 {
641         /* returns the *previous* brightness, or -1 */
642         struct backlight_device *bd = eeepc_backlight_device;
643         if (bd) {
644                 int old = bd->props.brightness;
645                 backlight_force_update(bd, BACKLIGHT_UPDATE_HOTKEY);
646                 return old;
647         }
648         return -1;
649 }
650
651 static int eeepc_get_adapter_status(struct hotplug_slot *hotplug_slot,
652                                     u8 *value)
653 {
654         int val = get_acpi(CM_ASL_WLAN);
655
656         if (val == 1 || val == 0)
657                 *value = val;
658         else
659                 return -EINVAL;
660
661         return 0;
662 }
663
664 static void eeepc_hotplug_work(struct work_struct *work)
665 {
666         struct pci_dev *dev;
667         struct pci_bus *bus = pci_find_bus(0, 1);
668         bool blocked;
669
670         if (!bus) {
671                 pr_warning("Unable to find PCI bus 1?\n");
672                 return;
673         }
674
675         blocked = eeepc_wlan_rfkill_blocked();
676         if (!blocked) {
677                 dev = pci_get_slot(bus, 0);
678                 if (dev) {
679                         /* Device already present */
680                         pci_dev_put(dev);
681                         return;
682                 }
683                 dev = pci_scan_single_device(bus, 0);
684                 if (dev) {
685                         pci_bus_assign_resources(bus);
686                         if (pci_bus_add_device(dev))
687                                 pr_err("Unable to hotplug wifi\n");
688                 }
689         } else {
690                 dev = pci_get_slot(bus, 0);
691                 if (dev) {
692                         pci_remove_bus_device(dev);
693                         pci_dev_put(dev);
694                 }
695         }
696
697         rfkill_set_sw_state(ehotk->wlan_rfkill, blocked);
698 }
699
700 static void eeepc_rfkill_notify(acpi_handle handle, u32 event, void *data)
701 {
702         if (event != ACPI_NOTIFY_BUS_CHECK)
703                 return;
704
705         schedule_work(&ehotk->hotplug_work);
706 }
707
708 static void eeepc_hotk_notify(struct acpi_device *device, u32 event)
709 {
710         static struct key_entry *key;
711         u16 count;
712         int brn = -ENODEV;
713
714         if (!ehotk)
715                 return;
716         if (event > ACPI_MAX_SYS_NOTIFY)
717                 return;
718         if (event >= NOTIFY_BRN_MIN && event <= NOTIFY_BRN_MAX)
719                 brn = notify_brn();
720         count = ehotk->event_count[event % 128]++;
721         acpi_bus_generate_proc_event(ehotk->device, event, count);
722         acpi_bus_generate_netlink_event(ehotk->device->pnp.device_class,
723                                         dev_name(&ehotk->device->dev), event,
724                                         count);
725         if (ehotk->inputdev) {
726                 if (brn != -ENODEV) {
727                         /* brightness-change events need special
728                          * handling for conversion to key events
729                          */
730                         if (brn < 0)
731                                 brn = event;
732                         else
733                                 brn += NOTIFY_BRN_MIN;
734                         if (event < brn)
735                                 event = NOTIFY_BRN_MIN; /* brightness down */
736                         else if (event > brn)
737                                 event = NOTIFY_BRN_MIN + 2; /* ... up */
738                         else
739                                 event = NOTIFY_BRN_MIN + 1; /* ... unchanged */
740                 }
741                 key = eepc_get_entry_by_scancode(event);
742                 if (key) {
743                         switch (key->type) {
744                         case KE_KEY:
745                                 input_report_key(ehotk->inputdev, key->keycode,
746                                                  1);
747                                 input_sync(ehotk->inputdev);
748                                 input_report_key(ehotk->inputdev, key->keycode,
749                                                  0);
750                                 input_sync(ehotk->inputdev);
751                                 break;
752                         }
753                 }
754         }
755 }
756
757 static int eeepc_register_rfkill_notifier(char *node)
758 {
759         acpi_status status = AE_OK;
760         acpi_handle handle;
761
762         status = acpi_get_handle(NULL, node, &handle);
763
764         if (ACPI_SUCCESS(status)) {
765                 status = acpi_install_notify_handler(handle,
766                                                      ACPI_SYSTEM_NOTIFY,
767                                                      eeepc_rfkill_notify,
768                                                      NULL);
769                 if (ACPI_FAILURE(status))
770                         pr_warning("Failed to register notify on %s\n", node);
771         } else
772                 return -ENODEV;
773
774         return 0;
775 }
776
777 static void eeepc_unregister_rfkill_notifier(char *node)
778 {
779         acpi_status status = AE_OK;
780         acpi_handle handle;
781
782         status = acpi_get_handle(NULL, node, &handle);
783
784         if (ACPI_SUCCESS(status)) {
785                 status = acpi_remove_notify_handler(handle,
786                                                      ACPI_SYSTEM_NOTIFY,
787                                                      eeepc_rfkill_notify);
788                 if (ACPI_FAILURE(status))
789                         pr_err("Error removing rfkill notify handler %s\n",
790                                 node);
791         }
792 }
793
794 static void eeepc_cleanup_pci_hotplug(struct hotplug_slot *hotplug_slot)
795 {
796         kfree(hotplug_slot->info);
797         kfree(hotplug_slot);
798 }
799
800 static int eeepc_setup_pci_hotplug(void)
801 {
802         int ret = -ENOMEM;
803         struct pci_bus *bus = pci_find_bus(0, 1);
804
805         if (!bus) {
806                 pr_err("Unable to find wifi PCI bus\n");
807                 return -ENODEV;
808         }
809
810         ehotk->hotplug_slot = kzalloc(sizeof(struct hotplug_slot), GFP_KERNEL);
811         if (!ehotk->hotplug_slot)
812                 goto error_slot;
813
814         ehotk->hotplug_slot->info = kzalloc(sizeof(struct hotplug_slot_info),
815                                             GFP_KERNEL);
816         if (!ehotk->hotplug_slot->info)
817                 goto error_info;
818
819         ehotk->hotplug_slot->private = ehotk;
820         ehotk->hotplug_slot->release = &eeepc_cleanup_pci_hotplug;
821         ehotk->hotplug_slot->ops = &eeepc_hotplug_slot_ops;
822         eeepc_get_adapter_status(ehotk->hotplug_slot,
823                                  &ehotk->hotplug_slot->info->adapter_status);
824
825         ret = pci_hp_register(ehotk->hotplug_slot, bus, 0, "eeepc-wifi");
826         if (ret) {
827                 pr_err("Unable to register hotplug slot - %d\n", ret);
828                 goto error_register;
829         }
830
831         return 0;
832
833 error_register:
834         kfree(ehotk->hotplug_slot->info);
835 error_info:
836         kfree(ehotk->hotplug_slot);
837         ehotk->hotplug_slot = NULL;
838 error_slot:
839         return ret;
840 }
841
842 static int eeepc_hotk_add(struct acpi_device *device)
843 {
844         int result;
845
846         if (!device)
847                  return -EINVAL;
848         pr_notice(EEEPC_HOTK_NAME "\n");
849         ehotk = kzalloc(sizeof(struct eeepc_hotk), GFP_KERNEL);
850         if (!ehotk)
851                 return -ENOMEM;
852         ehotk->init_flag = DISABLE_ASL_WLAN | DISABLE_ASL_DISPLAYSWITCH;
853         ehotk->handle = device->handle;
854         strcpy(acpi_device_name(device), EEEPC_HOTK_DEVICE_NAME);
855         strcpy(acpi_device_class(device), EEEPC_HOTK_CLASS);
856         device->driver_data = ehotk;
857         ehotk->device = device;
858         result = eeepc_hotk_check();
859         if (result)
860                 goto ehotk_fail;
861
862         return 0;
863
864  ehotk_fail:
865         kfree(ehotk);
866         ehotk = NULL;
867
868         return result;
869 }
870
871 static int eeepc_hotk_remove(struct acpi_device *device, int type)
872 {
873         if (!device || !acpi_driver_data(device))
874                  return -EINVAL;
875
876         kfree(ehotk);
877         return 0;
878 }
879
880 static int eeepc_hotk_resume(struct acpi_device *device)
881 {
882         if (ehotk->wlan_rfkill) {
883                 bool wlan;
884
885                 /* Workaround - it seems that _PTS disables the wireless
886                    without notification or changing the value read by WLAN.
887                    Normally this is fine because the correct value is restored
888                    from the non-volatile storage on resume, but we need to do
889                    it ourself if case suspend is aborted, or we lose wireless.
890                  */
891                 wlan = get_acpi(CM_ASL_WLAN);
892                 set_acpi(CM_ASL_WLAN, wlan);
893
894                 rfkill_set_sw_state(ehotk->wlan_rfkill, wlan != 1);
895
896                 schedule_work(&ehotk->hotplug_work);
897         }
898
899         if (ehotk->bluetooth_rfkill)
900                 rfkill_set_sw_state(ehotk->bluetooth_rfkill,
901                                     get_acpi(CM_ASL_BLUETOOTH) != 1);
902
903         return 0;
904 }
905
906 /*
907  * Hwmon
908  */
909 static int eeepc_get_fan_pwm(void)
910 {
911         int value = 0;
912
913         read_acpi_int(NULL, EEEPC_EC_FAN_PWM, &value);
914         value = value * 255 / 100;
915         return (value);
916 }
917
918 static void eeepc_set_fan_pwm(int value)
919 {
920         value = SENSORS_LIMIT(value, 0, 255);
921         value = value * 100 / 255;
922         ec_write(EEEPC_EC_SC02, value);
923 }
924
925 static int eeepc_get_fan_rpm(void)
926 {
927         int high = 0;
928         int low = 0;
929
930         read_acpi_int(NULL, EEEPC_EC_FAN_HRPM, &high);
931         read_acpi_int(NULL, EEEPC_EC_FAN_LRPM, &low);
932         return (high << 8 | low);
933 }
934
935 static int eeepc_get_fan_ctrl(void)
936 {
937         int value = 0;
938
939         read_acpi_int(NULL, EEEPC_EC_FAN_CTRL, &value);
940         return ((value & 0x02 ? 1 : 0));
941 }
942
943 static void eeepc_set_fan_ctrl(int manual)
944 {
945         int value = 0;
946
947         read_acpi_int(NULL, EEEPC_EC_FAN_CTRL, &value);
948         if (manual)
949                 value |= 0x02;
950         else
951                 value &= ~0x02;
952         ec_write(EEEPC_EC_SFB3, value);
953 }
954
955 static ssize_t store_sys_hwmon(void (*set)(int), const char *buf, size_t count)
956 {
957         int rv, value;
958
959         rv = parse_arg(buf, count, &value);
960         if (rv > 0)
961                 set(value);
962         return rv;
963 }
964
965 static ssize_t show_sys_hwmon(int (*get)(void), char *buf)
966 {
967         return sprintf(buf, "%d\n", get());
968 }
969
970 #define EEEPC_CREATE_SENSOR_ATTR(_name, _mode, _set, _get)              \
971         static ssize_t show_##_name(struct device *dev,                 \
972                                     struct device_attribute *attr,      \
973                                     char *buf)                          \
974         {                                                               \
975                 return show_sys_hwmon(_set, buf);                       \
976         }                                                               \
977         static ssize_t store_##_name(struct device *dev,                \
978                                      struct device_attribute *attr,     \
979                                      const char *buf, size_t count)     \
980         {                                                               \
981                 return store_sys_hwmon(_get, buf, count);               \
982         }                                                               \
983         static SENSOR_DEVICE_ATTR(_name, _mode, show_##_name, store_##_name, 0);
984
985 EEEPC_CREATE_SENSOR_ATTR(fan1_input, S_IRUGO, eeepc_get_fan_rpm, NULL);
986 EEEPC_CREATE_SENSOR_ATTR(pwm1, S_IRUGO | S_IWUSR,
987                          eeepc_get_fan_pwm, eeepc_set_fan_pwm);
988 EEEPC_CREATE_SENSOR_ATTR(pwm1_enable, S_IRUGO | S_IWUSR,
989                          eeepc_get_fan_ctrl, eeepc_set_fan_ctrl);
990
991 static ssize_t
992 show_name(struct device *dev, struct device_attribute *attr, char *buf)
993 {
994         return sprintf(buf, "eeepc\n");
995 }
996 static SENSOR_DEVICE_ATTR(name, S_IRUGO, show_name, NULL, 0);
997
998 static struct attribute *hwmon_attributes[] = {
999         &sensor_dev_attr_pwm1.dev_attr.attr,
1000         &sensor_dev_attr_fan1_input.dev_attr.attr,
1001         &sensor_dev_attr_pwm1_enable.dev_attr.attr,
1002         &sensor_dev_attr_name.dev_attr.attr,
1003         NULL
1004 };
1005
1006 static struct attribute_group hwmon_attribute_group = {
1007         .attrs = hwmon_attributes
1008 };
1009
1010 /*
1011  * exit/init
1012  */
1013 static void eeepc_backlight_exit(void)
1014 {
1015         if (eeepc_backlight_device)
1016                 backlight_device_unregister(eeepc_backlight_device);
1017         eeepc_backlight_device = NULL;
1018 }
1019
1020 static void eeepc_rfkill_exit(void)
1021 {
1022         eeepc_unregister_rfkill_notifier("\\_SB.PCI0.P0P6");
1023         eeepc_unregister_rfkill_notifier("\\_SB.PCI0.P0P7");
1024         if (ehotk->wlan_rfkill)
1025                 rfkill_unregister(ehotk->wlan_rfkill);
1026         if (ehotk->bluetooth_rfkill)
1027                 rfkill_unregister(ehotk->bluetooth_rfkill);
1028         if (ehotk->wwan3g_rfkill)
1029                 rfkill_unregister(ehotk->wwan3g_rfkill);
1030         if (ehotk->hotplug_slot)
1031                 pci_hp_deregister(ehotk->hotplug_slot);
1032 }
1033
1034 static void eeepc_input_exit(void)
1035 {
1036         if (ehotk->inputdev)
1037                 input_unregister_device(ehotk->inputdev);
1038 }
1039
1040 static void eeepc_hwmon_exit(void)
1041 {
1042         struct device *hwmon;
1043
1044         hwmon = eeepc_hwmon_device;
1045         if (!hwmon)
1046                 return ;
1047         sysfs_remove_group(&hwmon->kobj,
1048                            &hwmon_attribute_group);
1049         hwmon_device_unregister(hwmon);
1050         eeepc_hwmon_device = NULL;
1051 }
1052
1053 static void __exit eeepc_laptop_exit(void)
1054 {
1055         eeepc_backlight_exit();
1056         eeepc_rfkill_exit();
1057         eeepc_input_exit();
1058         eeepc_hwmon_exit();
1059         acpi_bus_unregister_driver(&eeepc_hotk_driver);
1060         sysfs_remove_group(&platform_device->dev.kobj,
1061                            &platform_attribute_group);
1062         platform_device_unregister(platform_device);
1063         platform_driver_unregister(&platform_driver);
1064 }
1065
1066 static int eeepc_new_rfkill(struct rfkill **rfkill,
1067                             const char *name, struct device *dev,
1068                             enum rfkill_type type, int cm)
1069 {
1070         int result;
1071
1072         result = get_acpi(cm);
1073         if (result < 0)
1074                 return result;
1075
1076         *rfkill = rfkill_alloc(name, dev, type,
1077                                &eeepc_rfkill_ops, (void *)(unsigned long)cm);
1078
1079         if (!*rfkill)
1080                 return -EINVAL;
1081
1082         rfkill_init_sw_state(*rfkill, get_acpi(cm) != 1);
1083         result = rfkill_register(*rfkill);
1084         if (result) {
1085                 rfkill_destroy(*rfkill);
1086                 *rfkill = NULL;
1087                 return result;
1088         }
1089         return 0;
1090 }
1091
1092
1093 static int eeepc_rfkill_init(struct device *dev)
1094 {
1095         int result = 0;
1096
1097         INIT_WORK(&ehotk->hotplug_work, eeepc_hotplug_work);
1098
1099         eeepc_register_rfkill_notifier("\\_SB.PCI0.P0P6");
1100         eeepc_register_rfkill_notifier("\\_SB.PCI0.P0P7");
1101
1102         result = eeepc_new_rfkill(&ehotk->wlan_rfkill,
1103                                   "eeepc-wlan", dev,
1104                                   RFKILL_TYPE_WLAN, CM_ASL_WLAN);
1105
1106         if (result && result != -ENODEV)
1107                 goto exit;
1108
1109         result = eeepc_new_rfkill(&ehotk->bluetooth_rfkill,
1110                                   "eeepc-bluetooth", dev,
1111                                   RFKILL_TYPE_BLUETOOTH, CM_ASL_BLUETOOTH);
1112
1113         if (result && result != -ENODEV)
1114                 goto exit;
1115
1116         result = eeepc_new_rfkill(&ehotk->wwan3g_rfkill,
1117                                   "eeepc-wwan3g", dev,
1118                                   RFKILL_TYPE_WWAN, CM_ASL_3G);
1119
1120         if (result && result != -ENODEV)
1121                 goto exit;
1122
1123         result = eeepc_setup_pci_hotplug();
1124         /*
1125          * If we get -EBUSY then something else is handling the PCI hotplug -
1126          * don't fail in this case
1127          */
1128         if (result == -EBUSY)
1129                 result = 0;
1130
1131 exit:
1132         if (result && result != -ENODEV)
1133                 eeepc_rfkill_exit();
1134         return result;
1135 }
1136
1137 static int eeepc_backlight_init(struct device *dev)
1138 {
1139         struct backlight_device *bd;
1140
1141         bd = backlight_device_register(EEEPC_HOTK_FILE, dev,
1142                                        NULL, &eeepcbl_ops);
1143         if (IS_ERR(bd)) {
1144                 pr_err("Could not register eeepc backlight device\n");
1145                 eeepc_backlight_device = NULL;
1146                 return PTR_ERR(bd);
1147         }
1148         eeepc_backlight_device = bd;
1149         bd->props.max_brightness = 15;
1150         bd->props.brightness = read_brightness(NULL);
1151         bd->props.power = FB_BLANK_UNBLANK;
1152         backlight_update_status(bd);
1153         return 0;
1154 }
1155
1156 static int eeepc_hwmon_init(struct device *dev)
1157 {
1158         struct device *hwmon;
1159         int result;
1160
1161         hwmon = hwmon_device_register(dev);
1162         if (IS_ERR(hwmon)) {
1163                 pr_err("Could not register eeepc hwmon device\n");
1164                 eeepc_hwmon_device = NULL;
1165                 return PTR_ERR(hwmon);
1166         }
1167         eeepc_hwmon_device = hwmon;
1168         result = sysfs_create_group(&hwmon->kobj,
1169                                     &hwmon_attribute_group);
1170         if (result)
1171                 eeepc_hwmon_exit();
1172         return result;
1173 }
1174
1175 static int __init eeepc_laptop_init(void)
1176 {
1177         struct device *dev;
1178         int result;
1179
1180         if (acpi_disabled)
1181                 return -ENODEV;
1182         result = acpi_bus_register_driver(&eeepc_hotk_driver);
1183         if (result < 0)
1184                 return result;
1185         if (!ehotk) {
1186                 acpi_bus_unregister_driver(&eeepc_hotk_driver);
1187                 return -ENODEV;
1188         }
1189
1190         eeepc_enable_camera();
1191
1192         /* Register platform stuff */
1193         result = platform_driver_register(&platform_driver);
1194         if (result)
1195                 goto fail_platform_driver;
1196         platform_device = platform_device_alloc(EEEPC_HOTK_FILE, -1);
1197         if (!platform_device) {
1198                 result = -ENOMEM;
1199                 goto fail_platform_device1;
1200         }
1201         result = platform_device_add(platform_device);
1202         if (result)
1203                 goto fail_platform_device2;
1204         result = sysfs_create_group(&platform_device->dev.kobj,
1205                                     &platform_attribute_group);
1206         if (result)
1207                 goto fail_sysfs;
1208
1209         dev = &platform_device->dev;
1210
1211         if (!acpi_video_backlight_support()) {
1212                 result = eeepc_backlight_init(dev);
1213                 if (result)
1214                         goto fail_backlight;
1215         } else
1216                 pr_info("Backlight controlled by ACPI video "
1217                         "driver\n");
1218
1219         result = eeepc_hwmon_init(dev);
1220         if (result)
1221                 goto fail_hwmon;
1222
1223         result = eeepc_rfkill_init(dev);
1224         if (result)
1225                 goto fail_rfkill;
1226
1227         return 0;
1228 fail_rfkill:
1229         eeepc_hwmon_exit();
1230 fail_hwmon:
1231         eeepc_backlight_exit();
1232 fail_backlight:
1233         sysfs_remove_group(&platform_device->dev.kobj,
1234                            &platform_attribute_group);
1235 fail_sysfs:
1236         platform_device_del(platform_device);
1237 fail_platform_device2:
1238         platform_device_put(platform_device);
1239 fail_platform_device1:
1240         platform_driver_unregister(&platform_driver);
1241 fail_platform_driver:
1242         eeepc_input_exit();
1243         return result;
1244 }
1245
1246 module_init(eeepc_laptop_init);
1247 module_exit(eeepc_laptop_exit);