1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * eeepc-laptop.c - Asus Eee PC extras
5 * Based on asus_acpi.c as patched for the Eee PC by Asus:
6 * ftp://ftp.asus.com/pub/ASUS/EeePC/701/ASUS_ACPI_071126.rar
7 * Based on eee.c from eeepc-linux
10 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
12 #include <linux/kernel.h>
13 #include <linux/module.h>
14 #include <linux/init.h>
15 #include <linux/types.h>
16 #include <linux/platform_device.h>
17 #include <linux/backlight.h>
18 #include <linux/hwmon.h>
19 #include <linux/hwmon-sysfs.h>
20 #include <linux/slab.h>
21 #include <linux/acpi.h>
22 #include <linux/uaccess.h>
23 #include <linux/input.h>
24 #include <linux/input/sparse-keymap.h>
25 #include <linux/rfkill.h>
26 #include <linux/pci.h>
27 #include <linux/pci_hotplug.h>
28 #include <linux/leds.h>
29 #include <linux/dmi.h>
30 #include <acpi/video.h>
32 #define EEEPC_LAPTOP_VERSION "0.1"
33 #define EEEPC_LAPTOP_NAME "Eee PC Hotkey Driver"
34 #define EEEPC_LAPTOP_FILE "eeepc"
36 #define EEEPC_ACPI_CLASS "hotkey"
37 #define EEEPC_ACPI_DEVICE_NAME "Hotkey"
38 #define EEEPC_ACPI_HID "ASUS010"
40 MODULE_AUTHOR("Corentin Chary, Eric Cooper");
41 MODULE_DESCRIPTION(EEEPC_LAPTOP_NAME);
42 MODULE_LICENSE("GPL");
44 static bool hotplug_disabled;
46 module_param(hotplug_disabled, bool, 0444);
47 MODULE_PARM_DESC(hotplug_disabled,
48 "Disable hotplug for wireless device. "
49 "If your laptop need that, please report to "
53 * Definitions for Asus EeePC
55 #define NOTIFY_BRN_MIN 0x20
56 #define NOTIFY_BRN_MAX 0x2f
59 DISABLE_ASL_WLAN = 0x0001,
60 DISABLE_ASL_BLUETOOTH = 0x0002,
61 DISABLE_ASL_IRDA = 0x0004,
62 DISABLE_ASL_CAMERA = 0x0008,
63 DISABLE_ASL_TV = 0x0010,
64 DISABLE_ASL_GPS = 0x0020,
65 DISABLE_ASL_DISPLAYSWITCH = 0x0040,
66 DISABLE_ASL_MODEM = 0x0080,
67 DISABLE_ASL_CARDREADER = 0x0100,
68 DISABLE_ASL_3G = 0x0200,
69 DISABLE_ASL_WIMAX = 0x0400,
70 DISABLE_ASL_HWCF = 0x0800
87 CM_ASL_CPUTEMPERATURE,
100 CM_ASL_PANELPOWER, /*P901*/
104 static const char *cm_getv[] = {
105 "WLDG", "BTHG", NULL, NULL,
106 "CAMG", NULL, NULL, NULL,
107 NULL, "PBLG", NULL, NULL,
108 "CFVG", NULL, NULL, NULL,
109 "USBG", NULL, NULL, "MODG",
110 "CRDG", "M3GG", "WIMG", "HWCF",
111 "LIDG", "TYPE", "PBPG", "TPDG"
114 static const char *cm_setv[] = {
115 "WLDS", "BTHS", NULL, NULL,
116 "CAMS", NULL, NULL, NULL,
117 "SDSP", "PBLS", "HDPS", NULL,
118 "CFVS", NULL, NULL, NULL,
119 "USBG", NULL, NULL, "MODS",
120 "CRDS", "M3GS", "WIMS", NULL,
121 NULL, NULL, "PBPS", "TPDS"
124 static const struct key_entry eeepc_keymap[] = {
125 { KE_KEY, 0x10, { KEY_WLAN } },
126 { KE_KEY, 0x11, { KEY_WLAN } },
127 { KE_KEY, 0x12, { KEY_PROG1 } },
128 { KE_KEY, 0x13, { KEY_MUTE } },
129 { KE_KEY, 0x14, { KEY_VOLUMEDOWN } },
130 { KE_KEY, 0x15, { KEY_VOLUMEUP } },
131 { KE_KEY, 0x16, { KEY_DISPLAY_OFF } },
132 { KE_KEY, 0x1a, { KEY_COFFEE } },
133 { KE_KEY, 0x1b, { KEY_ZOOM } },
134 { KE_KEY, 0x1c, { KEY_PROG2 } },
135 { KE_KEY, 0x1d, { KEY_PROG3 } },
136 { KE_KEY, NOTIFY_BRN_MIN, { KEY_BRIGHTNESSDOWN } },
137 { KE_KEY, NOTIFY_BRN_MAX, { KEY_BRIGHTNESSUP } },
138 { KE_KEY, 0x30, { KEY_SWITCHVIDEOMODE } },
139 { KE_KEY, 0x31, { KEY_SWITCHVIDEOMODE } },
140 { KE_KEY, 0x32, { KEY_SWITCHVIDEOMODE } },
141 { KE_KEY, 0x37, { KEY_F13 } }, /* Disable Touchpad */
142 { KE_KEY, 0x38, { KEY_F14 } },
143 { KE_IGNORE, 0x50, { KEY_RESERVED } }, /* AC plugged */
144 { KE_IGNORE, 0x51, { KEY_RESERVED } }, /* AC unplugged */
149 * This is the main structure, we can use it to store useful information
151 struct eeepc_laptop {
152 acpi_handle handle; /* the handle of the acpi device */
153 u32 cm_supported; /* the control methods supported
156 bool hotplug_disabled;
157 u16 event_count[128]; /* count for each event */
159 struct platform_device *platform_device;
160 struct acpi_device *device; /* the device we are in */
161 struct backlight_device *backlight_device;
163 struct input_dev *inputdev;
165 struct rfkill *wlan_rfkill;
166 struct rfkill *bluetooth_rfkill;
167 struct rfkill *wwan3g_rfkill;
168 struct rfkill *wimax_rfkill;
170 struct hotplug_slot hotplug_slot;
171 struct mutex hotplug_lock;
173 struct led_classdev tpd_led;
175 struct workqueue_struct *led_workqueue;
176 struct work_struct tpd_led_work;
182 static int write_acpi_int(acpi_handle handle, const char *method, int val)
186 status = acpi_execute_simple_method(handle, (char *)method, val);
188 return (status == AE_OK ? 0 : -1);
191 static int read_acpi_int(acpi_handle handle, const char *method, int *val)
194 unsigned long long result;
196 status = acpi_evaluate_integer(handle, (char *)method, NULL, &result);
197 if (ACPI_FAILURE(status)) {
206 static int set_acpi(struct eeepc_laptop *eeepc, int cm, int value)
208 const char *method = cm_setv[cm];
212 if ((eeepc->cm_supported & (0x1 << cm)) == 0)
215 if (write_acpi_int(eeepc->handle, method, value))
216 pr_warn("Error writing %s\n", method);
220 static int get_acpi(struct eeepc_laptop *eeepc, int cm)
222 const char *method = cm_getv[cm];
227 if ((eeepc->cm_supported & (0x1 << cm)) == 0)
230 if (read_acpi_int(eeepc->handle, method, &value))
231 pr_warn("Error reading %s\n", method);
235 static int acpi_setter_handle(struct eeepc_laptop *eeepc, int cm,
238 const char *method = cm_setv[cm];
243 if ((eeepc->cm_supported & (0x1 << cm)) == 0)
246 status = acpi_get_handle(eeepc->handle, (char *)method,
248 if (status != AE_OK) {
249 pr_warn("Error finding %s\n", method);
259 static int parse_arg(const char *buf, int *val)
261 if (sscanf(buf, "%i", val) != 1)
266 static ssize_t store_sys_acpi(struct device *dev, int cm,
267 const char *buf, size_t count)
269 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
272 rv = parse_arg(buf, &value);
275 rv = set_acpi(eeepc, cm, value);
281 static ssize_t show_sys_acpi(struct device *dev, int cm, char *buf)
283 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
284 int value = get_acpi(eeepc, cm);
288 return sprintf(buf, "%d\n", value);
291 #define EEEPC_ACPI_SHOW_FUNC(_name, _cm) \
292 static ssize_t _name##_show(struct device *dev, \
293 struct device_attribute *attr, \
296 return show_sys_acpi(dev, _cm, buf); \
299 #define EEEPC_ACPI_STORE_FUNC(_name, _cm) \
300 static ssize_t _name##_store(struct device *dev, \
301 struct device_attribute *attr, \
302 const char *buf, size_t count) \
304 return store_sys_acpi(dev, _cm, buf, count); \
307 #define EEEPC_CREATE_DEVICE_ATTR_RW(_name, _cm) \
308 EEEPC_ACPI_SHOW_FUNC(_name, _cm) \
309 EEEPC_ACPI_STORE_FUNC(_name, _cm) \
310 static DEVICE_ATTR_RW(_name)
312 #define EEEPC_CREATE_DEVICE_ATTR_WO(_name, _cm) \
313 EEEPC_ACPI_STORE_FUNC(_name, _cm) \
314 static DEVICE_ATTR_WO(_name)
316 EEEPC_CREATE_DEVICE_ATTR_RW(camera, CM_ASL_CAMERA);
317 EEEPC_CREATE_DEVICE_ATTR_RW(cardr, CM_ASL_CARDREADER);
318 EEEPC_CREATE_DEVICE_ATTR_WO(disp, CM_ASL_DISPLAYSWITCH);
325 static int get_cpufv(struct eeepc_laptop *eeepc, struct eeepc_cpufv *c)
327 c->cur = get_acpi(eeepc, CM_ASL_CPUFV);
331 c->num = (c->cur >> 8) & 0xff;
333 if (c->num == 0 || c->num > 12)
338 static ssize_t available_cpufv_show(struct device *dev,
339 struct device_attribute *attr,
342 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
343 struct eeepc_cpufv c;
347 if (get_cpufv(eeepc, &c))
349 for (i = 0; i < c.num; i++)
350 len += sprintf(buf + len, "%d ", i);
351 len += sprintf(buf + len, "\n");
355 static ssize_t cpufv_show(struct device *dev,
356 struct device_attribute *attr,
359 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
360 struct eeepc_cpufv c;
362 if (get_cpufv(eeepc, &c))
364 return sprintf(buf, "%#x\n", (c.num << 8) | c.cur);
367 static ssize_t cpufv_store(struct device *dev,
368 struct device_attribute *attr,
369 const char *buf, size_t count)
371 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
372 struct eeepc_cpufv c;
375 if (eeepc->cpufv_disabled)
377 if (get_cpufv(eeepc, &c))
379 rv = parse_arg(buf, &value);
382 if (value < 0 || value >= c.num)
384 rv = set_acpi(eeepc, CM_ASL_CPUFV, value);
390 static ssize_t cpufv_disabled_show(struct device *dev,
391 struct device_attribute *attr,
394 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
396 return sprintf(buf, "%d\n", eeepc->cpufv_disabled);
399 static ssize_t cpufv_disabled_store(struct device *dev,
400 struct device_attribute *attr,
401 const char *buf, size_t count)
403 struct eeepc_laptop *eeepc = dev_get_drvdata(dev);
406 rv = parse_arg(buf, &value);
412 if (eeepc->cpufv_disabled)
413 pr_warn("cpufv enabled (not officially supported on this model)\n");
414 eeepc->cpufv_disabled = false;
424 static DEVICE_ATTR_RW(cpufv);
425 static DEVICE_ATTR_RO(available_cpufv);
426 static DEVICE_ATTR_RW(cpufv_disabled);
428 static struct attribute *platform_attributes[] = {
429 &dev_attr_camera.attr,
430 &dev_attr_cardr.attr,
432 &dev_attr_cpufv.attr,
433 &dev_attr_available_cpufv.attr,
434 &dev_attr_cpufv_disabled.attr,
438 static const struct attribute_group platform_attribute_group = {
439 .attrs = platform_attributes
442 static int eeepc_platform_init(struct eeepc_laptop *eeepc)
446 eeepc->platform_device = platform_device_alloc(EEEPC_LAPTOP_FILE, PLATFORM_DEVID_NONE);
447 if (!eeepc->platform_device)
449 platform_set_drvdata(eeepc->platform_device, eeepc);
451 result = platform_device_add(eeepc->platform_device);
453 goto fail_platform_device;
455 result = sysfs_create_group(&eeepc->platform_device->dev.kobj,
456 &platform_attribute_group);
462 platform_device_del(eeepc->platform_device);
463 fail_platform_device:
464 platform_device_put(eeepc->platform_device);
468 static void eeepc_platform_exit(struct eeepc_laptop *eeepc)
470 sysfs_remove_group(&eeepc->platform_device->dev.kobj,
471 &platform_attribute_group);
472 platform_device_unregister(eeepc->platform_device);
479 * These functions actually update the LED's, and are called from a
480 * workqueue. By doing this as separate work rather than when the LED
481 * subsystem asks, we avoid messing with the Asus ACPI stuff during a
482 * potentially bad time, such as a timer interrupt.
484 static void tpd_led_update(struct work_struct *work)
486 struct eeepc_laptop *eeepc;
488 eeepc = container_of(work, struct eeepc_laptop, tpd_led_work);
490 set_acpi(eeepc, CM_ASL_TPD, eeepc->tpd_led_wk);
493 static void tpd_led_set(struct led_classdev *led_cdev,
494 enum led_brightness value)
496 struct eeepc_laptop *eeepc;
498 eeepc = container_of(led_cdev, struct eeepc_laptop, tpd_led);
500 eeepc->tpd_led_wk = (value > 0) ? 1 : 0;
501 queue_work(eeepc->led_workqueue, &eeepc->tpd_led_work);
504 static enum led_brightness tpd_led_get(struct led_classdev *led_cdev)
506 struct eeepc_laptop *eeepc;
508 eeepc = container_of(led_cdev, struct eeepc_laptop, tpd_led);
510 return get_acpi(eeepc, CM_ASL_TPD);
513 static int eeepc_led_init(struct eeepc_laptop *eeepc)
517 if (get_acpi(eeepc, CM_ASL_TPD) == -ENODEV)
520 eeepc->led_workqueue = create_singlethread_workqueue("led_workqueue");
521 if (!eeepc->led_workqueue)
523 INIT_WORK(&eeepc->tpd_led_work, tpd_led_update);
525 eeepc->tpd_led.name = "eeepc::touchpad";
526 eeepc->tpd_led.brightness_set = tpd_led_set;
527 if (get_acpi(eeepc, CM_ASL_TPD) >= 0) /* if method is available */
528 eeepc->tpd_led.brightness_get = tpd_led_get;
529 eeepc->tpd_led.max_brightness = 1;
531 rv = led_classdev_register(&eeepc->platform_device->dev,
534 destroy_workqueue(eeepc->led_workqueue);
541 static void eeepc_led_exit(struct eeepc_laptop *eeepc)
543 led_classdev_unregister(&eeepc->tpd_led);
544 if (eeepc->led_workqueue)
545 destroy_workqueue(eeepc->led_workqueue);
549 * PCI hotplug (for wlan rfkill)
551 static bool eeepc_wlan_rfkill_blocked(struct eeepc_laptop *eeepc)
553 if (get_acpi(eeepc, CM_ASL_WLAN) == 1)
558 static void eeepc_rfkill_hotplug(struct eeepc_laptop *eeepc, acpi_handle handle)
560 struct pci_dev *port;
563 bool blocked = eeepc_wlan_rfkill_blocked(eeepc);
567 if (eeepc->wlan_rfkill)
568 rfkill_set_sw_state(eeepc->wlan_rfkill, blocked);
570 mutex_lock(&eeepc->hotplug_lock);
571 pci_lock_rescan_remove();
573 if (!eeepc->hotplug_slot.ops)
576 port = acpi_get_pci_dev(handle);
578 pr_warn("Unable to find port\n");
582 bus = port->subordinate;
585 pr_warn("Unable to find PCI bus 1?\n");
589 if (pci_bus_read_config_dword(bus, 0, PCI_VENDOR_ID, &l)) {
590 pr_err("Unable to read PCI config space?\n");
594 absent = (l == 0xffffffff);
596 if (blocked != absent) {
597 pr_warn("BIOS says wireless lan is %s, but the pci device is %s\n",
598 blocked ? "blocked" : "unblocked",
599 absent ? "absent" : "present");
600 pr_warn("skipped wireless hotplug as probably inappropriate for this model\n");
605 dev = pci_get_slot(bus, 0);
607 /* Device already present */
611 dev = pci_scan_single_device(bus, 0);
613 pci_bus_assign_resources(bus);
614 pci_bus_add_device(dev);
617 dev = pci_get_slot(bus, 0);
619 pci_stop_and_remove_bus_device(dev);
627 pci_unlock_rescan_remove();
628 mutex_unlock(&eeepc->hotplug_lock);
631 static void eeepc_rfkill_hotplug_update(struct eeepc_laptop *eeepc, char *node)
633 acpi_status status = AE_OK;
636 status = acpi_get_handle(NULL, node, &handle);
638 if (ACPI_SUCCESS(status))
639 eeepc_rfkill_hotplug(eeepc, handle);
642 static void eeepc_rfkill_notify(acpi_handle handle, u32 event, void *data)
644 struct eeepc_laptop *eeepc = data;
646 if (event != ACPI_NOTIFY_BUS_CHECK)
649 eeepc_rfkill_hotplug(eeepc, handle);
652 static int eeepc_register_rfkill_notifier(struct eeepc_laptop *eeepc,
658 status = acpi_get_handle(NULL, node, &handle);
660 if (ACPI_FAILURE(status))
663 status = acpi_install_notify_handler(handle,
667 if (ACPI_FAILURE(status))
668 pr_warn("Failed to register notify on %s\n", node);
671 * Refresh pci hotplug in case the rfkill state was
672 * changed during setup.
674 eeepc_rfkill_hotplug(eeepc, handle);
678 static void eeepc_unregister_rfkill_notifier(struct eeepc_laptop *eeepc,
681 acpi_status status = AE_OK;
684 status = acpi_get_handle(NULL, node, &handle);
686 if (ACPI_FAILURE(status))
689 status = acpi_remove_notify_handler(handle,
691 eeepc_rfkill_notify);
692 if (ACPI_FAILURE(status))
693 pr_err("Error removing rfkill notify handler %s\n",
696 * Refresh pci hotplug in case the rfkill
697 * state was changed after
698 * eeepc_unregister_rfkill_notifier()
700 eeepc_rfkill_hotplug(eeepc, handle);
703 static int eeepc_get_adapter_status(struct hotplug_slot *hotplug_slot,
706 struct eeepc_laptop *eeepc;
709 eeepc = container_of(hotplug_slot, struct eeepc_laptop, hotplug_slot);
710 val = get_acpi(eeepc, CM_ASL_WLAN);
712 if (val == 1 || val == 0)
720 static const struct hotplug_slot_ops eeepc_hotplug_slot_ops = {
721 .get_adapter_status = eeepc_get_adapter_status,
722 .get_power_status = eeepc_get_adapter_status,
725 static int eeepc_setup_pci_hotplug(struct eeepc_laptop *eeepc)
728 struct pci_bus *bus = pci_find_bus(0, 1);
731 pr_err("Unable to find wifi PCI bus\n");
735 eeepc->hotplug_slot.ops = &eeepc_hotplug_slot_ops;
737 ret = pci_hp_register(&eeepc->hotplug_slot, bus, 0, "eeepc-wifi");
739 pr_err("Unable to register hotplug slot - %d\n", ret);
746 eeepc->hotplug_slot.ops = NULL;
753 static int eeepc_rfkill_set(void *data, bool blocked)
755 acpi_handle handle = data;
757 return write_acpi_int(handle, NULL, !blocked);
760 static const struct rfkill_ops eeepc_rfkill_ops = {
761 .set_block = eeepc_rfkill_set,
764 static int eeepc_new_rfkill(struct eeepc_laptop *eeepc,
765 struct rfkill **rfkill,
767 enum rfkill_type type, int cm)
772 result = acpi_setter_handle(eeepc, cm, &handle);
776 *rfkill = rfkill_alloc(name, &eeepc->platform_device->dev, type,
777 &eeepc_rfkill_ops, handle);
782 rfkill_init_sw_state(*rfkill, get_acpi(eeepc, cm) != 1);
783 result = rfkill_register(*rfkill);
785 rfkill_destroy(*rfkill);
792 static char EEEPC_RFKILL_NODE_1[] = "\\_SB.PCI0.P0P5";
793 static char EEEPC_RFKILL_NODE_2[] = "\\_SB.PCI0.P0P6";
794 static char EEEPC_RFKILL_NODE_3[] = "\\_SB.PCI0.P0P7";
796 static void eeepc_rfkill_exit(struct eeepc_laptop *eeepc)
798 eeepc_unregister_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_1);
799 eeepc_unregister_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_2);
800 eeepc_unregister_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_3);
801 if (eeepc->wlan_rfkill) {
802 rfkill_unregister(eeepc->wlan_rfkill);
803 rfkill_destroy(eeepc->wlan_rfkill);
804 eeepc->wlan_rfkill = NULL;
807 if (eeepc->hotplug_slot.ops)
808 pci_hp_deregister(&eeepc->hotplug_slot);
810 if (eeepc->bluetooth_rfkill) {
811 rfkill_unregister(eeepc->bluetooth_rfkill);
812 rfkill_destroy(eeepc->bluetooth_rfkill);
813 eeepc->bluetooth_rfkill = NULL;
815 if (eeepc->wwan3g_rfkill) {
816 rfkill_unregister(eeepc->wwan3g_rfkill);
817 rfkill_destroy(eeepc->wwan3g_rfkill);
818 eeepc->wwan3g_rfkill = NULL;
820 if (eeepc->wimax_rfkill) {
821 rfkill_unregister(eeepc->wimax_rfkill);
822 rfkill_destroy(eeepc->wimax_rfkill);
823 eeepc->wimax_rfkill = NULL;
827 static int eeepc_rfkill_init(struct eeepc_laptop *eeepc)
831 mutex_init(&eeepc->hotplug_lock);
833 result = eeepc_new_rfkill(eeepc, &eeepc->wlan_rfkill,
834 "eeepc-wlan", RFKILL_TYPE_WLAN,
837 if (result && result != -ENODEV)
840 result = eeepc_new_rfkill(eeepc, &eeepc->bluetooth_rfkill,
841 "eeepc-bluetooth", RFKILL_TYPE_BLUETOOTH,
844 if (result && result != -ENODEV)
847 result = eeepc_new_rfkill(eeepc, &eeepc->wwan3g_rfkill,
848 "eeepc-wwan3g", RFKILL_TYPE_WWAN,
851 if (result && result != -ENODEV)
854 result = eeepc_new_rfkill(eeepc, &eeepc->wimax_rfkill,
855 "eeepc-wimax", RFKILL_TYPE_WIMAX,
858 if (result && result != -ENODEV)
861 if (eeepc->hotplug_disabled)
864 result = eeepc_setup_pci_hotplug(eeepc);
866 * If we get -EBUSY then something else is handling the PCI hotplug -
867 * don't fail in this case
869 if (result == -EBUSY)
872 eeepc_register_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_1);
873 eeepc_register_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_2);
874 eeepc_register_rfkill_notifier(eeepc, EEEPC_RFKILL_NODE_3);
877 if (result && result != -ENODEV)
878 eeepc_rfkill_exit(eeepc);
883 * Platform driver - hibernate/resume callbacks
885 static int eeepc_hotk_thaw(struct device *device)
887 struct eeepc_laptop *eeepc = dev_get_drvdata(device);
889 if (eeepc->wlan_rfkill) {
893 * Work around bios bug - acpi _PTS turns off the wireless led
894 * during suspend. Normally it restores it on resume, but
895 * we should kick it ourselves in case hibernation is aborted.
897 wlan = get_acpi(eeepc, CM_ASL_WLAN);
899 set_acpi(eeepc, CM_ASL_WLAN, wlan);
905 static int eeepc_hotk_restore(struct device *device)
907 struct eeepc_laptop *eeepc = dev_get_drvdata(device);
909 /* Refresh both wlan rfkill state and pci hotplug */
910 if (eeepc->wlan_rfkill) {
911 eeepc_rfkill_hotplug_update(eeepc, EEEPC_RFKILL_NODE_1);
912 eeepc_rfkill_hotplug_update(eeepc, EEEPC_RFKILL_NODE_2);
913 eeepc_rfkill_hotplug_update(eeepc, EEEPC_RFKILL_NODE_3);
916 if (eeepc->bluetooth_rfkill)
917 rfkill_set_sw_state(eeepc->bluetooth_rfkill,
918 get_acpi(eeepc, CM_ASL_BLUETOOTH) != 1);
919 if (eeepc->wwan3g_rfkill)
920 rfkill_set_sw_state(eeepc->wwan3g_rfkill,
921 get_acpi(eeepc, CM_ASL_3G) != 1);
922 if (eeepc->wimax_rfkill)
923 rfkill_set_sw_state(eeepc->wimax_rfkill,
924 get_acpi(eeepc, CM_ASL_WIMAX) != 1);
929 static const struct dev_pm_ops eeepc_pm_ops = {
930 .thaw = eeepc_hotk_thaw,
931 .restore = eeepc_hotk_restore,
934 static struct platform_driver platform_driver = {
936 .name = EEEPC_LAPTOP_FILE,
945 #define EEEPC_EC_SC00 0x61
946 #define EEEPC_EC_FAN_PWM (EEEPC_EC_SC00 + 2) /* Fan PWM duty cycle (%) */
947 #define EEEPC_EC_FAN_HRPM (EEEPC_EC_SC00 + 5) /* High byte, fan speed (RPM) */
948 #define EEEPC_EC_FAN_LRPM (EEEPC_EC_SC00 + 6) /* Low byte, fan speed (RPM) */
950 #define EEEPC_EC_SFB0 0xD0
951 #define EEEPC_EC_FAN_CTRL (EEEPC_EC_SFB0 + 3) /* Byte containing SF25 */
953 static inline int eeepc_pwm_to_lmsensors(int value)
955 return value * 255 / 100;
958 static inline int eeepc_lmsensors_to_pwm(int value)
960 value = clamp_val(value, 0, 255);
961 return value * 100 / 255;
964 static int eeepc_get_fan_pwm(void)
968 ec_read(EEEPC_EC_FAN_PWM, &value);
969 return eeepc_pwm_to_lmsensors(value);
972 static void eeepc_set_fan_pwm(int value)
974 value = eeepc_lmsensors_to_pwm(value);
975 ec_write(EEEPC_EC_FAN_PWM, value);
978 static int eeepc_get_fan_rpm(void)
983 ec_read(EEEPC_EC_FAN_HRPM, &high);
984 ec_read(EEEPC_EC_FAN_LRPM, &low);
985 return high << 8 | low;
988 #define EEEPC_EC_FAN_CTRL_BIT 0x02
989 #define EEEPC_FAN_CTRL_MANUAL 1
990 #define EEEPC_FAN_CTRL_AUTO 2
992 static int eeepc_get_fan_ctrl(void)
996 ec_read(EEEPC_EC_FAN_CTRL, &value);
997 if (value & EEEPC_EC_FAN_CTRL_BIT)
998 return EEEPC_FAN_CTRL_MANUAL;
1000 return EEEPC_FAN_CTRL_AUTO;
1003 static void eeepc_set_fan_ctrl(int manual)
1007 ec_read(EEEPC_EC_FAN_CTRL, &value);
1008 if (manual == EEEPC_FAN_CTRL_MANUAL)
1009 value |= EEEPC_EC_FAN_CTRL_BIT;
1011 value &= ~EEEPC_EC_FAN_CTRL_BIT;
1012 ec_write(EEEPC_EC_FAN_CTRL, value);
1015 static ssize_t store_sys_hwmon(void (*set)(int), const char *buf, size_t count)
1019 rv = parse_arg(buf, &value);
1026 static ssize_t show_sys_hwmon(int (*get)(void), char *buf)
1028 return sprintf(buf, "%d\n", get());
1031 #define EEEPC_SENSOR_SHOW_FUNC(_name, _get) \
1032 static ssize_t _name##_show(struct device *dev, \
1033 struct device_attribute *attr, \
1036 return show_sys_hwmon(_get, buf); \
1039 #define EEEPC_SENSOR_STORE_FUNC(_name, _set) \
1040 static ssize_t _name##_store(struct device *dev, \
1041 struct device_attribute *attr, \
1042 const char *buf, size_t count) \
1044 return store_sys_hwmon(_set, buf, count); \
1047 #define EEEPC_CREATE_SENSOR_ATTR_RW(_name, _get, _set) \
1048 EEEPC_SENSOR_SHOW_FUNC(_name, _get) \
1049 EEEPC_SENSOR_STORE_FUNC(_name, _set) \
1050 static DEVICE_ATTR_RW(_name)
1052 #define EEEPC_CREATE_SENSOR_ATTR_RO(_name, _get) \
1053 EEEPC_SENSOR_SHOW_FUNC(_name, _get) \
1054 static DEVICE_ATTR_RO(_name)
1056 EEEPC_CREATE_SENSOR_ATTR_RO(fan1_input, eeepc_get_fan_rpm);
1057 EEEPC_CREATE_SENSOR_ATTR_RW(pwm1, eeepc_get_fan_pwm,
1059 EEEPC_CREATE_SENSOR_ATTR_RW(pwm1_enable, eeepc_get_fan_ctrl,
1060 eeepc_set_fan_ctrl);
1062 static struct attribute *hwmon_attrs[] = {
1063 &dev_attr_pwm1.attr,
1064 &dev_attr_fan1_input.attr,
1065 &dev_attr_pwm1_enable.attr,
1068 ATTRIBUTE_GROUPS(hwmon);
1070 static int eeepc_hwmon_init(struct eeepc_laptop *eeepc)
1072 struct device *dev = &eeepc->platform_device->dev;
1073 struct device *hwmon;
1075 hwmon = devm_hwmon_device_register_with_groups(dev, "eeepc", NULL,
1077 if (IS_ERR(hwmon)) {
1078 pr_err("Could not register eeepc hwmon device\n");
1079 return PTR_ERR(hwmon);
1087 static int read_brightness(struct backlight_device *bd)
1089 struct eeepc_laptop *eeepc = bl_get_data(bd);
1091 return get_acpi(eeepc, CM_ASL_PANELBRIGHT);
1094 static int set_brightness(struct backlight_device *bd, int value)
1096 struct eeepc_laptop *eeepc = bl_get_data(bd);
1098 return set_acpi(eeepc, CM_ASL_PANELBRIGHT, value);
1101 static int update_bl_status(struct backlight_device *bd)
1103 return set_brightness(bd, bd->props.brightness);
1106 static const struct backlight_ops eeepcbl_ops = {
1107 .get_brightness = read_brightness,
1108 .update_status = update_bl_status,
1111 static int eeepc_backlight_notify(struct eeepc_laptop *eeepc)
1113 struct backlight_device *bd = eeepc->backlight_device;
1114 int old = bd->props.brightness;
1116 backlight_force_update(bd, BACKLIGHT_UPDATE_HOTKEY);
1121 static int eeepc_backlight_init(struct eeepc_laptop *eeepc)
1123 struct backlight_properties props;
1124 struct backlight_device *bd;
1126 memset(&props, 0, sizeof(struct backlight_properties));
1127 props.type = BACKLIGHT_PLATFORM;
1128 props.max_brightness = 15;
1129 bd = backlight_device_register(EEEPC_LAPTOP_FILE,
1130 &eeepc->platform_device->dev, eeepc,
1131 &eeepcbl_ops, &props);
1133 pr_err("Could not register eeepc backlight device\n");
1134 eeepc->backlight_device = NULL;
1137 eeepc->backlight_device = bd;
1138 bd->props.brightness = read_brightness(bd);
1139 bd->props.power = BACKLIGHT_POWER_ON;
1140 backlight_update_status(bd);
1144 static void eeepc_backlight_exit(struct eeepc_laptop *eeepc)
1146 backlight_device_unregister(eeepc->backlight_device);
1147 eeepc->backlight_device = NULL;
1152 * Input device (i.e. hotkeys)
1154 static int eeepc_input_init(struct eeepc_laptop *eeepc)
1156 struct input_dev *input;
1159 input = input_allocate_device();
1163 input->name = "Asus EeePC extra buttons";
1164 input->phys = EEEPC_LAPTOP_FILE "/input0";
1165 input->id.bustype = BUS_HOST;
1166 input->dev.parent = &eeepc->platform_device->dev;
1168 error = sparse_keymap_setup(input, eeepc_keymap, NULL);
1170 pr_err("Unable to setup input device keymap\n");
1174 error = input_register_device(input);
1176 pr_err("Unable to register input device\n");
1180 eeepc->inputdev = input;
1184 input_free_device(input);
1188 static void eeepc_input_exit(struct eeepc_laptop *eeepc)
1190 if (eeepc->inputdev)
1191 input_unregister_device(eeepc->inputdev);
1192 eeepc->inputdev = NULL;
1198 static void eeepc_input_notify(struct eeepc_laptop *eeepc, int event)
1200 if (!eeepc->inputdev)
1202 if (!sparse_keymap_report_event(eeepc->inputdev, event, 1, true))
1203 pr_info("Unknown key %x pressed\n", event);
1206 static void eeepc_acpi_notify(struct acpi_device *device, u32 event)
1208 struct eeepc_laptop *eeepc = acpi_driver_data(device);
1209 int old_brightness, new_brightness;
1212 if (event > ACPI_MAX_SYS_NOTIFY)
1214 count = eeepc->event_count[event % 128]++;
1215 acpi_bus_generate_netlink_event(device->pnp.device_class,
1216 dev_name(&device->dev), event,
1219 /* Brightness events are special */
1220 if (event < NOTIFY_BRN_MIN || event > NOTIFY_BRN_MAX) {
1221 eeepc_input_notify(eeepc, event);
1225 /* Ignore them completely if the acpi video driver is used */
1226 if (!eeepc->backlight_device)
1229 /* Update the backlight device. */
1230 old_brightness = eeepc_backlight_notify(eeepc);
1232 /* Convert event to keypress (obsolescent hack) */
1233 new_brightness = event - NOTIFY_BRN_MIN;
1235 if (new_brightness < old_brightness) {
1236 event = NOTIFY_BRN_MIN; /* brightness down */
1237 } else if (new_brightness > old_brightness) {
1238 event = NOTIFY_BRN_MAX; /* brightness up */
1241 * no change in brightness - already at min/max,
1242 * event will be desired value (or else ignored)
1245 eeepc_input_notify(eeepc, event);
1248 static void eeepc_dmi_check(struct eeepc_laptop *eeepc)
1252 model = dmi_get_system_info(DMI_PRODUCT_NAME);
1257 * Blacklist for setting cpufv (cpu speed).
1259 * EeePC 4G ("701") implements CFVS, but it is not supported
1260 * by the pre-installed OS, and the original option to change it
1261 * in the BIOS setup screen was removed in later versions.
1263 * Judging by the lack of "Super Hybrid Engine" on Asus product pages,
1264 * this applies to all "701" models (4G/4G Surf/2G Surf).
1266 * So Asus made a deliberate decision not to support it on this model.
1267 * We have several reports that using it can cause the system to hang
1269 * The hang has also been reported on a "702" (Model name "8G"?).
1271 * We avoid dmi_check_system() / dmi_match(), because they use
1272 * substring matching. We don't want to affect the "701SD"
1273 * and "701SDX" models, because they do support S.H.E.
1275 if (strcmp(model, "701") == 0 || strcmp(model, "702") == 0) {
1276 eeepc->cpufv_disabled = true;
1277 pr_info("model %s does not officially support setting cpu speed\n",
1279 pr_info("cpufv disabled to avoid instability\n");
1283 * Blacklist for wlan hotplug
1285 * Eeepc 1005HA doesn't work like others models and don't need the
1286 * hotplug code. In fact, current hotplug code seems to unplug another
1289 if (strcmp(model, "1005HA") == 0 || strcmp(model, "1201N") == 0 ||
1290 strcmp(model, "1005PE") == 0) {
1291 eeepc->hotplug_disabled = true;
1292 pr_info("wlan hotplug disabled\n");
1296 static void cmsg_quirk(struct eeepc_laptop *eeepc, int cm, const char *name)
1300 /* Some BIOSes do not report cm although it is available.
1301 Check if cm_getv[cm] works and, if yes, assume cm should be set. */
1302 if (!(eeepc->cm_supported & (1 << cm))
1303 && !read_acpi_int(eeepc->handle, cm_getv[cm], &dummy)) {
1304 pr_info("%s (%x) not reported by BIOS, enabling anyway\n",
1306 eeepc->cm_supported |= 1 << cm;
1310 static void cmsg_quirks(struct eeepc_laptop *eeepc)
1312 cmsg_quirk(eeepc, CM_ASL_LID, "LID");
1313 cmsg_quirk(eeepc, CM_ASL_TYPE, "TYPE");
1314 cmsg_quirk(eeepc, CM_ASL_PANELPOWER, "PANELPOWER");
1315 cmsg_quirk(eeepc, CM_ASL_TPD, "TPD");
1318 static int eeepc_acpi_init(struct eeepc_laptop *eeepc)
1320 unsigned int init_flags;
1323 result = acpi_bus_get_status(eeepc->device);
1326 if (!eeepc->device->status.present) {
1327 pr_err("Hotkey device not present, aborting\n");
1331 init_flags = DISABLE_ASL_WLAN | DISABLE_ASL_DISPLAYSWITCH;
1332 pr_notice("Hotkey init flags 0x%x\n", init_flags);
1334 if (write_acpi_int(eeepc->handle, "INIT", init_flags)) {
1335 pr_err("Hotkey initialization failed\n");
1339 /* get control methods supported */
1340 if (read_acpi_int(eeepc->handle, "CMSG", &eeepc->cm_supported)) {
1341 pr_err("Get control methods supported failed\n");
1345 pr_info("Get control methods supported: 0x%x\n", eeepc->cm_supported);
1350 static void eeepc_enable_camera(struct eeepc_laptop *eeepc)
1353 * If the following call to set_acpi() fails, it's because there's no
1354 * camera so we can ignore the error.
1356 if (get_acpi(eeepc, CM_ASL_CAMERA) == 0)
1357 set_acpi(eeepc, CM_ASL_CAMERA, 1);
1360 static bool eeepc_device_present;
1362 static int eeepc_acpi_add(struct acpi_device *device)
1364 struct eeepc_laptop *eeepc;
1367 pr_notice(EEEPC_LAPTOP_NAME "\n");
1368 eeepc = kzalloc(sizeof(struct eeepc_laptop), GFP_KERNEL);
1371 eeepc->handle = device->handle;
1372 strcpy(acpi_device_name(device), EEEPC_ACPI_DEVICE_NAME);
1373 strcpy(acpi_device_class(device), EEEPC_ACPI_CLASS);
1374 device->driver_data = eeepc;
1375 eeepc->device = device;
1377 eeepc->hotplug_disabled = hotplug_disabled;
1379 eeepc_dmi_check(eeepc);
1381 result = eeepc_acpi_init(eeepc);
1384 eeepc_enable_camera(eeepc);
1387 * Register the platform device first. It is used as a parent for the
1388 * sub-devices below.
1390 * Note that if there are multiple instances of this ACPI device it
1391 * will bail out, because the platform device is registered with a
1392 * fixed name. Of course it doesn't make sense to have more than one,
1393 * and machine-specific scripts find the fixed name convenient. But
1394 * It's also good for us to exclude multiple instances because both
1395 * our hwmon and our wlan rfkill subdevice use global ACPI objects
1396 * (the EC and the PCI wlan slot respectively).
1398 result = eeepc_platform_init(eeepc);
1402 if (acpi_video_get_backlight_type() == acpi_backlight_vendor) {
1403 result = eeepc_backlight_init(eeepc);
1405 goto fail_backlight;
1408 result = eeepc_input_init(eeepc);
1412 result = eeepc_hwmon_init(eeepc);
1416 result = eeepc_led_init(eeepc);
1420 result = eeepc_rfkill_init(eeepc);
1424 eeepc_device_present = true;
1428 eeepc_led_exit(eeepc);
1431 eeepc_input_exit(eeepc);
1433 eeepc_backlight_exit(eeepc);
1435 eeepc_platform_exit(eeepc);
1442 static void eeepc_acpi_remove(struct acpi_device *device)
1444 struct eeepc_laptop *eeepc = acpi_driver_data(device);
1446 eeepc_backlight_exit(eeepc);
1447 eeepc_rfkill_exit(eeepc);
1448 eeepc_input_exit(eeepc);
1449 eeepc_led_exit(eeepc);
1450 eeepc_platform_exit(eeepc);
1456 static const struct acpi_device_id eeepc_device_ids[] = {
1457 {EEEPC_ACPI_HID, 0},
1460 MODULE_DEVICE_TABLE(acpi, eeepc_device_ids);
1462 static struct acpi_driver eeepc_acpi_driver = {
1463 .name = EEEPC_LAPTOP_NAME,
1464 .class = EEEPC_ACPI_CLASS,
1465 .ids = eeepc_device_ids,
1466 .flags = ACPI_DRIVER_ALL_NOTIFY_EVENTS,
1468 .add = eeepc_acpi_add,
1469 .remove = eeepc_acpi_remove,
1470 .notify = eeepc_acpi_notify,
1475 static int __init eeepc_laptop_init(void)
1479 result = platform_driver_register(&platform_driver);
1483 result = acpi_bus_register_driver(&eeepc_acpi_driver);
1485 goto fail_acpi_driver;
1487 if (!eeepc_device_present) {
1489 goto fail_no_device;
1495 acpi_bus_unregister_driver(&eeepc_acpi_driver);
1497 platform_driver_unregister(&platform_driver);
1501 static void __exit eeepc_laptop_exit(void)
1503 acpi_bus_unregister_driver(&eeepc_acpi_driver);
1504 platform_driver_unregister(&platform_driver);
1507 module_init(eeepc_laptop_init);
1508 module_exit(eeepc_laptop_exit);