1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * Acer WMI Laptop Extras 4 * 5 * Copyright (C) 2007-2009 Carlos Corbacho <carlos@strangeworlds.co.uk> 6 * 7 * Based on acer_acpi: 8 * Copyright (C) 2005-2007 E.M. Smith 9 * Copyright (C) 2007-2008 Carlos Corbacho <cathectic@gmail.com> 10 */ 11 12 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 13 14 #include <linux/kernel.h> 15 #include <linux/module.h> 16 #include <linux/init.h> 17 #include <linux/types.h> 18 #include <linux/dmi.h> 19 #include <linux/fb.h> 20 #include <linux/backlight.h> 21 #include <linux/leds.h> 22 #include <linux/platform_device.h> 23 #include <linux/acpi.h> 24 #include <linux/i8042.h> 25 #include <linux/rfkill.h> 26 #include <linux/workqueue.h> 27 #include <linux/debugfs.h> 28 #include <linux/slab.h> 29 #include <linux/input.h> 30 #include <linux/input/sparse-keymap.h> 31 #include <acpi/video.h> 32 33 MODULE_AUTHOR("Carlos Corbacho"); 34 MODULE_DESCRIPTION("Acer Laptop WMI Extras Driver"); 35 MODULE_LICENSE("GPL"); 36 37 /* 38 * Magic Number 39 * Meaning is unknown - this number is required for writing to ACPI for AMW0 40 * (it's also used in acerhk when directly accessing the BIOS) 41 */ 42 #define ACER_AMW0_WRITE 0x9610 43 44 /* 45 * Bit masks for the AMW0 interface 46 */ 47 #define ACER_AMW0_WIRELESS_MASK 0x35 48 #define ACER_AMW0_BLUETOOTH_MASK 0x34 49 #define ACER_AMW0_MAILLED_MASK 0x31 50 51 /* 52 * Method IDs for WMID interface 53 */ 54 #define ACER_WMID_GET_WIRELESS_METHODID 1 55 #define ACER_WMID_GET_BLUETOOTH_METHODID 2 56 #define ACER_WMID_GET_BRIGHTNESS_METHODID 3 57 #define ACER_WMID_SET_WIRELESS_METHODID 4 58 #define ACER_WMID_SET_BLUETOOTH_METHODID 5 59 #define ACER_WMID_SET_BRIGHTNESS_METHODID 6 60 #define ACER_WMID_GET_THREEG_METHODID 10 61 #define ACER_WMID_SET_THREEG_METHODID 11 62 63 /* 64 * Acer ACPI method GUIDs 65 */ 66 #define AMW0_GUID1 "67C3371D-95A3-4C37-BB61-DD47B491DAAB" 67 #define AMW0_GUID2 "431F16ED-0C2B-444C-B267-27DEB140CF9C" 68 #define WMID_GUID1 "6AF4F258-B401-42FD-BE91-3D4AC2D7C0D3" 69 #define WMID_GUID2 "95764E09-FB56-4E83-B31A-37761F60994A" 70 #define WMID_GUID3 "61EF69EA-865C-4BC3-A502-A0DEBA0CB531" 71 72 /* 73 * Acer ACPI event GUIDs 74 */ 75 #define ACERWMID_EVENT_GUID "676AA15E-6A47-4D9F-A2CC-1E6D18D14026" 76 77 MODULE_ALIAS("wmi:67C3371D-95A3-4C37-BB61-DD47B491DAAB"); 78 MODULE_ALIAS("wmi:6AF4F258-B401-42FD-BE91-3D4AC2D7C0D3"); 79 MODULE_ALIAS("wmi:676AA15E-6A47-4D9F-A2CC-1E6D18D14026"); 80 81 enum acer_wmi_event_ids { 82 WMID_HOTKEY_EVENT = 0x1, 83 WMID_ACCEL_EVENT = 0x5, 84 }; 85 86 static const struct key_entry acer_wmi_keymap[] __initconst = { 87 {KE_KEY, 0x01, {KEY_WLAN} }, /* WiFi */ 88 {KE_KEY, 0x03, {KEY_WLAN} }, /* WiFi */ 89 {KE_KEY, 0x04, {KEY_WLAN} }, /* WiFi */ 90 {KE_KEY, 0x12, {KEY_BLUETOOTH} }, /* BT */ 91 {KE_KEY, 0x21, {KEY_PROG1} }, /* Backup */ 92 {KE_KEY, 0x22, {KEY_PROG2} }, /* Arcade */ 93 {KE_KEY, 0x23, {KEY_PROG3} }, /* P_Key */ 94 {KE_KEY, 0x24, {KEY_PROG4} }, /* Social networking_Key */ 95 {KE_KEY, 0x29, {KEY_PROG3} }, /* P_Key for TM8372 */ 96 {KE_IGNORE, 0x41, {KEY_MUTE} }, 97 {KE_IGNORE, 0x42, {KEY_PREVIOUSSONG} }, 98 {KE_IGNORE, 0x4d, {KEY_PREVIOUSSONG} }, 99 {KE_IGNORE, 0x43, {KEY_NEXTSONG} }, 100 {KE_IGNORE, 0x4e, {KEY_NEXTSONG} }, 101 {KE_IGNORE, 0x44, {KEY_PLAYPAUSE} }, 102 {KE_IGNORE, 0x4f, {KEY_PLAYPAUSE} }, 103 {KE_IGNORE, 0x45, {KEY_STOP} }, 104 {KE_IGNORE, 0x50, {KEY_STOP} }, 105 {KE_IGNORE, 0x48, {KEY_VOLUMEUP} }, 106 {KE_IGNORE, 0x49, {KEY_VOLUMEDOWN} }, 107 {KE_IGNORE, 0x4a, {KEY_VOLUMEDOWN} }, 108 {KE_IGNORE, 0x61, {KEY_SWITCHVIDEOMODE} }, 109 {KE_IGNORE, 0x62, {KEY_BRIGHTNESSUP} }, 110 {KE_IGNORE, 0x63, {KEY_BRIGHTNESSDOWN} }, 111 {KE_KEY, 0x64, {KEY_SWITCHVIDEOMODE} }, /* Display Switch */ 112 {KE_IGNORE, 0x81, {KEY_SLEEP} }, 113 {KE_KEY, 0x82, {KEY_TOUCHPAD_TOGGLE} }, /* Touch Pad Toggle */ 114 {KE_KEY, KEY_TOUCHPAD_ON, {KEY_TOUCHPAD_ON} }, 115 {KE_KEY, KEY_TOUCHPAD_OFF, {KEY_TOUCHPAD_OFF} }, 116 {KE_IGNORE, 0x83, {KEY_TOUCHPAD_TOGGLE} }, 117 {KE_KEY, 0x85, {KEY_TOUCHPAD_TOGGLE} }, 118 {KE_KEY, 0x86, {KEY_WLAN} }, 119 {KE_KEY, 0x87, {KEY_POWER} }, 120 {KE_END, 0} 121 }; 122 123 static struct input_dev *acer_wmi_input_dev; 124 static struct input_dev *acer_wmi_accel_dev; 125 126 struct event_return_value { 127 u8 function; 128 u8 key_num; 129 u16 device_state; 130 u32 reserved; 131 } __attribute__((packed)); 132 133 /* 134 * GUID3 Get Device Status device flags 135 */ 136 #define ACER_WMID3_GDS_WIRELESS (1<<0) /* WiFi */ 137 #define ACER_WMID3_GDS_THREEG (1<<6) /* 3G */ 138 #define ACER_WMID3_GDS_WIMAX (1<<7) /* WiMAX */ 139 #define ACER_WMID3_GDS_BLUETOOTH (1<<11) /* BT */ 140 #define ACER_WMID3_GDS_RFBTN (1<<14) /* RF Button */ 141 142 #define ACER_WMID3_GDS_TOUCHPAD (1<<1) /* Touchpad */ 143 144 /* Hotkey Customized Setting and Acer Application Status. 145 * Set Device Default Value and Report Acer Application Status. 146 * When Acer Application starts, it will run this method to inform 147 * BIOS/EC that Acer Application is on. 148 * App Status 149 * Bit[0]: Launch Manager Status 150 * Bit[1]: ePM Status 151 * Bit[2]: Device Control Status 152 * Bit[3]: Acer Power Button Utility Status 153 * Bit[4]: RF Button Status 154 * Bit[5]: ODD PM Status 155 * Bit[6]: Device Default Value Control 156 * Bit[7]: Hall Sensor Application Status 157 */ 158 struct func_input_params { 159 u8 function_num; /* Function Number */ 160 u16 commun_devices; /* Communication type devices default status */ 161 u16 devices; /* Other type devices default status */ 162 u8 app_status; /* Acer Device Status. LM, ePM, RF Button... */ 163 u8 app_mask; /* Bit mask to app_status */ 164 u8 reserved; 165 } __attribute__((packed)); 166 167 struct func_return_value { 168 u8 error_code; /* Error Code */ 169 u8 ec_return_value; /* EC Return Value */ 170 u16 reserved; 171 } __attribute__((packed)); 172 173 struct wmid3_gds_set_input_param { /* Set Device Status input parameter */ 174 u8 function_num; /* Function Number */ 175 u8 hotkey_number; /* Hotkey Number */ 176 u16 devices; /* Set Device */ 177 u8 volume_value; /* Volume Value */ 178 } __attribute__((packed)); 179 180 struct wmid3_gds_get_input_param { /* Get Device Status input parameter */ 181 u8 function_num; /* Function Number */ 182 u8 hotkey_number; /* Hotkey Number */ 183 u16 devices; /* Get Device */ 184 } __attribute__((packed)); 185 186 struct wmid3_gds_return_value { /* Get Device Status return value*/ 187 u8 error_code; /* Error Code */ 188 u8 ec_return_value; /* EC Return Value */ 189 u16 devices; /* Current Device Status */ 190 u32 reserved; 191 } __attribute__((packed)); 192 193 struct hotkey_function_type_aa { 194 u8 type; 195 u8 length; 196 u16 handle; 197 u16 commun_func_bitmap; 198 u16 application_func_bitmap; 199 u16 media_func_bitmap; 200 u16 display_func_bitmap; 201 u16 others_func_bitmap; 202 u8 commun_fn_key_number; 203 } __attribute__((packed)); 204 205 /* 206 * Interface capability flags 207 */ 208 #define ACER_CAP_MAILLED (1<<0) 209 #define ACER_CAP_WIRELESS (1<<1) 210 #define ACER_CAP_BLUETOOTH (1<<2) 211 #define ACER_CAP_BRIGHTNESS (1<<3) 212 #define ACER_CAP_THREEG (1<<4) 213 #define ACER_CAP_ACCEL (1<<5) 214 #define ACER_CAP_RFBTN (1<<6) 215 #define ACER_CAP_ANY (0xFFFFFFFF) 216 217 /* 218 * Interface type flags 219 */ 220 enum interface_flags { 221 ACER_AMW0, 222 ACER_AMW0_V2, 223 ACER_WMID, 224 ACER_WMID_v2, 225 }; 226 227 #define ACER_DEFAULT_WIRELESS 0 228 #define ACER_DEFAULT_BLUETOOTH 0 229 #define ACER_DEFAULT_MAILLED 0 230 #define ACER_DEFAULT_THREEG 0 231 232 static int max_brightness = 0xF; 233 234 static int mailled = -1; 235 static int brightness = -1; 236 static int threeg = -1; 237 static int force_series; 238 static bool ec_raw_mode; 239 static bool has_type_aa; 240 static u16 commun_func_bitmap; 241 static u8 commun_fn_key_number; 242 243 module_param(mailled, int, 0444); 244 module_param(brightness, int, 0444); 245 module_param(threeg, int, 0444); 246 module_param(force_series, int, 0444); 247 module_param(ec_raw_mode, bool, 0444); 248 MODULE_PARM_DESC(mailled, "Set initial state of Mail LED"); 249 MODULE_PARM_DESC(brightness, "Set initial LCD backlight brightness"); 250 MODULE_PARM_DESC(threeg, "Set initial state of 3G hardware"); 251 MODULE_PARM_DESC(force_series, "Force a different laptop series"); 252 MODULE_PARM_DESC(ec_raw_mode, "Enable EC raw mode"); 253 254 struct acer_data { 255 int mailled; 256 int threeg; 257 int brightness; 258 }; 259 260 struct acer_debug { 261 struct dentry *root; 262 struct dentry *devices; 263 u32 wmid_devices; 264 }; 265 266 static struct rfkill *wireless_rfkill; 267 static struct rfkill *bluetooth_rfkill; 268 static struct rfkill *threeg_rfkill; 269 static bool rfkill_inited; 270 271 /* Each low-level interface must define at least some of the following */ 272 struct wmi_interface { 273 /* The WMI device type */ 274 u32 type; 275 276 /* The capabilities this interface provides */ 277 u32 capability; 278 279 /* Private data for the current interface */ 280 struct acer_data data; 281 282 /* debugfs entries associated with this interface */ 283 struct acer_debug debug; 284 }; 285 286 /* The static interface pointer, points to the currently detected interface */ 287 static struct wmi_interface *interface; 288 289 /* 290 * Embedded Controller quirks 291 * Some laptops require us to directly access the EC to either enable or query 292 * features that are not available through WMI. 293 */ 294 295 struct quirk_entry { 296 u8 wireless; 297 u8 mailled; 298 s8 brightness; 299 u8 bluetooth; 300 }; 301 302 static struct quirk_entry *quirks; 303 304 static void __init set_quirks(void) 305 { 306 if (!interface) 307 return; 308 309 if (quirks->mailled) 310 interface->capability |= ACER_CAP_MAILLED; 311 312 if (quirks->brightness) 313 interface->capability |= ACER_CAP_BRIGHTNESS; 314 } 315 316 static int __init dmi_matched(const struct dmi_system_id *dmi) 317 { 318 quirks = dmi->driver_data; 319 return 1; 320 } 321 322 static struct quirk_entry quirk_unknown = { 323 }; 324 325 static struct quirk_entry quirk_acer_aspire_1520 = { 326 .brightness = -1, 327 }; 328 329 static struct quirk_entry quirk_acer_travelmate_2490 = { 330 .mailled = 1, 331 }; 332 333 /* This AMW0 laptop has no bluetooth */ 334 static struct quirk_entry quirk_medion_md_98300 = { 335 .wireless = 1, 336 }; 337 338 static struct quirk_entry quirk_fujitsu_amilo_li_1718 = { 339 .wireless = 2, 340 }; 341 342 static struct quirk_entry quirk_lenovo_ideapad_s205 = { 343 .wireless = 3, 344 }; 345 346 /* The Aspire One has a dummy ACPI-WMI interface - disable it */ 347 static const struct dmi_system_id acer_blacklist[] __initconst = { 348 { 349 .ident = "Acer Aspire One (SSD)", 350 .matches = { 351 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 352 DMI_MATCH(DMI_PRODUCT_NAME, "AOA110"), 353 }, 354 }, 355 { 356 .ident = "Acer Aspire One (HDD)", 357 .matches = { 358 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 359 DMI_MATCH(DMI_PRODUCT_NAME, "AOA150"), 360 }, 361 }, 362 {} 363 }; 364 365 static const struct dmi_system_id amw0_whitelist[] __initconst = { 366 { 367 .ident = "Acer", 368 .matches = { 369 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 370 }, 371 }, 372 { 373 .ident = "Gateway", 374 .matches = { 375 DMI_MATCH(DMI_SYS_VENDOR, "Gateway"), 376 }, 377 }, 378 { 379 .ident = "Packard Bell", 380 .matches = { 381 DMI_MATCH(DMI_SYS_VENDOR, "Packard Bell"), 382 }, 383 }, 384 {} 385 }; 386 387 /* 388 * This quirk table is only for Acer/Gateway/Packard Bell family 389 * that those machines are supported by acer-wmi driver. 390 */ 391 static const struct dmi_system_id acer_quirks[] __initconst = { 392 { 393 .callback = dmi_matched, 394 .ident = "Acer Aspire 1360", 395 .matches = { 396 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 397 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 1360"), 398 }, 399 .driver_data = &quirk_acer_aspire_1520, 400 }, 401 { 402 .callback = dmi_matched, 403 .ident = "Acer Aspire 1520", 404 .matches = { 405 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 406 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 1520"), 407 }, 408 .driver_data = &quirk_acer_aspire_1520, 409 }, 410 { 411 .callback = dmi_matched, 412 .ident = "Acer Aspire 3100", 413 .matches = { 414 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 415 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 3100"), 416 }, 417 .driver_data = &quirk_acer_travelmate_2490, 418 }, 419 { 420 .callback = dmi_matched, 421 .ident = "Acer Aspire 3610", 422 .matches = { 423 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 424 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 3610"), 425 }, 426 .driver_data = &quirk_acer_travelmate_2490, 427 }, 428 { 429 .callback = dmi_matched, 430 .ident = "Acer Aspire 5100", 431 .matches = { 432 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 433 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5100"), 434 }, 435 .driver_data = &quirk_acer_travelmate_2490, 436 }, 437 { 438 .callback = dmi_matched, 439 .ident = "Acer Aspire 5610", 440 .matches = { 441 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 442 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5610"), 443 }, 444 .driver_data = &quirk_acer_travelmate_2490, 445 }, 446 { 447 .callback = dmi_matched, 448 .ident = "Acer Aspire 5630", 449 .matches = { 450 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 451 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5630"), 452 }, 453 .driver_data = &quirk_acer_travelmate_2490, 454 }, 455 { 456 .callback = dmi_matched, 457 .ident = "Acer Aspire 5650", 458 .matches = { 459 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 460 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5650"), 461 }, 462 .driver_data = &quirk_acer_travelmate_2490, 463 }, 464 { 465 .callback = dmi_matched, 466 .ident = "Acer Aspire 5680", 467 .matches = { 468 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 469 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5680"), 470 }, 471 .driver_data = &quirk_acer_travelmate_2490, 472 }, 473 { 474 .callback = dmi_matched, 475 .ident = "Acer Aspire 9110", 476 .matches = { 477 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 478 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 9110"), 479 }, 480 .driver_data = &quirk_acer_travelmate_2490, 481 }, 482 { 483 .callback = dmi_matched, 484 .ident = "Acer TravelMate 2490", 485 .matches = { 486 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 487 DMI_MATCH(DMI_PRODUCT_NAME, "TravelMate 2490"), 488 }, 489 .driver_data = &quirk_acer_travelmate_2490, 490 }, 491 { 492 .callback = dmi_matched, 493 .ident = "Acer TravelMate 4200", 494 .matches = { 495 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 496 DMI_MATCH(DMI_PRODUCT_NAME, "TravelMate 4200"), 497 }, 498 .driver_data = &quirk_acer_travelmate_2490, 499 }, 500 {} 501 }; 502 503 /* 504 * This quirk list is for those non-acer machines that have AMW0_GUID1 505 * but supported by acer-wmi in past days. Keeping this quirk list here 506 * is only for backward compatible. Please do not add new machine to 507 * here anymore. Those non-acer machines should be supported by 508 * appropriate wmi drivers. 509 */ 510 static const struct dmi_system_id non_acer_quirks[] __initconst = { 511 { 512 .callback = dmi_matched, 513 .ident = "Fujitsu Siemens Amilo Li 1718", 514 .matches = { 515 DMI_MATCH(DMI_SYS_VENDOR, "FUJITSU SIEMENS"), 516 DMI_MATCH(DMI_PRODUCT_NAME, "AMILO Li 1718"), 517 }, 518 .driver_data = &quirk_fujitsu_amilo_li_1718, 519 }, 520 { 521 .callback = dmi_matched, 522 .ident = "Medion MD 98300", 523 .matches = { 524 DMI_MATCH(DMI_SYS_VENDOR, "MEDION"), 525 DMI_MATCH(DMI_PRODUCT_NAME, "WAM2030"), 526 }, 527 .driver_data = &quirk_medion_md_98300, 528 }, 529 { 530 .callback = dmi_matched, 531 .ident = "Lenovo Ideapad S205", 532 .matches = { 533 DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), 534 DMI_MATCH(DMI_PRODUCT_NAME, "10382LG"), 535 }, 536 .driver_data = &quirk_lenovo_ideapad_s205, 537 }, 538 { 539 .callback = dmi_matched, 540 .ident = "Lenovo Ideapad S205 (Brazos)", 541 .matches = { 542 DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), 543 DMI_MATCH(DMI_PRODUCT_NAME, "Brazos"), 544 }, 545 .driver_data = &quirk_lenovo_ideapad_s205, 546 }, 547 { 548 .callback = dmi_matched, 549 .ident = "Lenovo 3000 N200", 550 .matches = { 551 DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), 552 DMI_MATCH(DMI_PRODUCT_NAME, "0687A31"), 553 }, 554 .driver_data = &quirk_fujitsu_amilo_li_1718, 555 }, 556 { 557 .callback = dmi_matched, 558 .ident = "Lenovo Ideapad S205-10382JG", 559 .matches = { 560 DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), 561 DMI_MATCH(DMI_PRODUCT_NAME, "10382JG"), 562 }, 563 .driver_data = &quirk_lenovo_ideapad_s205, 564 }, 565 { 566 .callback = dmi_matched, 567 .ident = "Lenovo Ideapad S205-1038DPG", 568 .matches = { 569 DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), 570 DMI_MATCH(DMI_PRODUCT_NAME, "1038DPG"), 571 }, 572 .driver_data = &quirk_lenovo_ideapad_s205, 573 }, 574 {} 575 }; 576 577 static int __init 578 video_set_backlight_video_vendor(const struct dmi_system_id *d) 579 { 580 interface->capability &= ~ACER_CAP_BRIGHTNESS; 581 pr_info("Brightness must be controlled by generic video driver\n"); 582 return 0; 583 } 584 585 static const struct dmi_system_id video_vendor_dmi_table[] __initconst = { 586 { 587 .callback = video_set_backlight_video_vendor, 588 .ident = "Acer TravelMate 4750", 589 .matches = { 590 DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), 591 DMI_MATCH(DMI_PRODUCT_NAME, "TravelMate 4750"), 592 }, 593 }, 594 { 595 .callback = video_set_backlight_video_vendor, 596 .ident = "Acer Extensa 5235", 597 .matches = { 598 DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), 599 DMI_MATCH(DMI_PRODUCT_NAME, "Extensa 5235"), 600 }, 601 }, 602 { 603 .callback = video_set_backlight_video_vendor, 604 .ident = "Acer TravelMate 5760", 605 .matches = { 606 DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), 607 DMI_MATCH(DMI_PRODUCT_NAME, "TravelMate 5760"), 608 }, 609 }, 610 { 611 .callback = video_set_backlight_video_vendor, 612 .ident = "Acer Aspire 5750", 613 .matches = { 614 DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), 615 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5750"), 616 }, 617 }, 618 { 619 .callback = video_set_backlight_video_vendor, 620 .ident = "Acer Aspire 5741", 621 .matches = { 622 DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), 623 DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5741"), 624 }, 625 }, 626 { 627 /* 628 * Note no video_set_backlight_video_vendor, we must use the 629 * acer interface, as there is no native backlight interface. 630 */ 631 .ident = "Acer KAV80", 632 .matches = { 633 DMI_MATCH(DMI_SYS_VENDOR, "Acer"), 634 DMI_MATCH(DMI_PRODUCT_NAME, "KAV80"), 635 }, 636 }, 637 {} 638 }; 639 640 /* Find which quirks are needed for a particular vendor/ model pair */ 641 static void __init find_quirks(void) 642 { 643 if (!force_series) { 644 dmi_check_system(acer_quirks); 645 dmi_check_system(non_acer_quirks); 646 } else if (force_series == 2490) { 647 quirks = &quirk_acer_travelmate_2490; 648 } 649 650 if (quirks == NULL) 651 quirks = &quirk_unknown; 652 653 set_quirks(); 654 } 655 656 /* 657 * General interface convenience methods 658 */ 659 660 static bool has_cap(u32 cap) 661 { 662 return interface->capability & cap; 663 } 664 665 /* 666 * AMW0 (V1) interface 667 */ 668 struct wmab_args { 669 u32 eax; 670 u32 ebx; 671 u32 ecx; 672 u32 edx; 673 }; 674 675 struct wmab_ret { 676 u32 eax; 677 u32 ebx; 678 u32 ecx; 679 u32 edx; 680 u32 eex; 681 }; 682 683 static acpi_status wmab_execute(struct wmab_args *regbuf, 684 struct acpi_buffer *result) 685 { 686 struct acpi_buffer input; 687 acpi_status status; 688 input.length = sizeof(struct wmab_args); 689 input.pointer = (u8 *)regbuf; 690 691 status = wmi_evaluate_method(AMW0_GUID1, 0, 1, &input, result); 692 693 return status; 694 } 695 696 static acpi_status AMW0_get_u32(u32 *value, u32 cap) 697 { 698 int err; 699 u8 result; 700 701 switch (cap) { 702 case ACER_CAP_MAILLED: 703 switch (quirks->mailled) { 704 default: 705 err = ec_read(0xA, &result); 706 if (err) 707 return AE_ERROR; 708 *value = (result >> 7) & 0x1; 709 return AE_OK; 710 } 711 break; 712 case ACER_CAP_WIRELESS: 713 switch (quirks->wireless) { 714 case 1: 715 err = ec_read(0x7B, &result); 716 if (err) 717 return AE_ERROR; 718 *value = result & 0x1; 719 return AE_OK; 720 case 2: 721 err = ec_read(0x71, &result); 722 if (err) 723 return AE_ERROR; 724 *value = result & 0x1; 725 return AE_OK; 726 case 3: 727 err = ec_read(0x78, &result); 728 if (err) 729 return AE_ERROR; 730 *value = result & 0x1; 731 return AE_OK; 732 default: 733 err = ec_read(0xA, &result); 734 if (err) 735 return AE_ERROR; 736 *value = (result >> 2) & 0x1; 737 return AE_OK; 738 } 739 break; 740 case ACER_CAP_BLUETOOTH: 741 switch (quirks->bluetooth) { 742 default: 743 err = ec_read(0xA, &result); 744 if (err) 745 return AE_ERROR; 746 *value = (result >> 4) & 0x1; 747 return AE_OK; 748 } 749 break; 750 case ACER_CAP_BRIGHTNESS: 751 switch (quirks->brightness) { 752 default: 753 err = ec_read(0x83, &result); 754 if (err) 755 return AE_ERROR; 756 *value = result; 757 return AE_OK; 758 } 759 break; 760 default: 761 return AE_ERROR; 762 } 763 return AE_OK; 764 } 765 766 static acpi_status AMW0_set_u32(u32 value, u32 cap) 767 { 768 struct wmab_args args; 769 770 args.eax = ACER_AMW0_WRITE; 771 args.ebx = value ? (1<<8) : 0; 772 args.ecx = args.edx = 0; 773 774 switch (cap) { 775 case ACER_CAP_MAILLED: 776 if (value > 1) 777 return AE_BAD_PARAMETER; 778 args.ebx |= ACER_AMW0_MAILLED_MASK; 779 break; 780 case ACER_CAP_WIRELESS: 781 if (value > 1) 782 return AE_BAD_PARAMETER; 783 args.ebx |= ACER_AMW0_WIRELESS_MASK; 784 break; 785 case ACER_CAP_BLUETOOTH: 786 if (value > 1) 787 return AE_BAD_PARAMETER; 788 args.ebx |= ACER_AMW0_BLUETOOTH_MASK; 789 break; 790 case ACER_CAP_BRIGHTNESS: 791 if (value > max_brightness) 792 return AE_BAD_PARAMETER; 793 switch (quirks->brightness) { 794 default: 795 return ec_write(0x83, value); 796 break; 797 } 798 default: 799 return AE_ERROR; 800 } 801 802 /* Actually do the set */ 803 return wmab_execute(&args, NULL); 804 } 805 806 static acpi_status __init AMW0_find_mailled(void) 807 { 808 struct wmab_args args; 809 struct wmab_ret ret; 810 acpi_status status = AE_OK; 811 struct acpi_buffer out = { ACPI_ALLOCATE_BUFFER, NULL }; 812 union acpi_object *obj; 813 814 args.eax = 0x86; 815 args.ebx = args.ecx = args.edx = 0; 816 817 status = wmab_execute(&args, &out); 818 if (ACPI_FAILURE(status)) 819 return status; 820 821 obj = (union acpi_object *) out.pointer; 822 if (obj && obj->type == ACPI_TYPE_BUFFER && 823 obj->buffer.length == sizeof(struct wmab_ret)) { 824 ret = *((struct wmab_ret *) obj->buffer.pointer); 825 } else { 826 kfree(out.pointer); 827 return AE_ERROR; 828 } 829 830 if (ret.eex & 0x1) 831 interface->capability |= ACER_CAP_MAILLED; 832 833 kfree(out.pointer); 834 835 return AE_OK; 836 } 837 838 static const struct acpi_device_id norfkill_ids[] __initconst = { 839 { "VPC2004", 0}, 840 { "IBM0068", 0}, 841 { "LEN0068", 0}, 842 { "SNY5001", 0}, /* sony-laptop in charge */ 843 { "HPQ6601", 0}, 844 { "", 0}, 845 }; 846 847 static int __init AMW0_set_cap_acpi_check_device(void) 848 { 849 const struct acpi_device_id *id; 850 851 for (id = norfkill_ids; id->id[0]; id++) 852 if (acpi_dev_found(id->id)) 853 return true; 854 855 return false; 856 } 857 858 static acpi_status __init AMW0_set_capabilities(void) 859 { 860 struct wmab_args args; 861 struct wmab_ret ret; 862 acpi_status status; 863 struct acpi_buffer out = { ACPI_ALLOCATE_BUFFER, NULL }; 864 union acpi_object *obj; 865 866 /* 867 * On laptops with this strange GUID (non Acer), normal probing doesn't 868 * work. 869 */ 870 if (wmi_has_guid(AMW0_GUID2)) { 871 if ((quirks != &quirk_unknown) || 872 !AMW0_set_cap_acpi_check_device()) 873 interface->capability |= ACER_CAP_WIRELESS; 874 return AE_OK; 875 } 876 877 args.eax = ACER_AMW0_WRITE; 878 args.ecx = args.edx = 0; 879 880 args.ebx = 0xa2 << 8; 881 args.ebx |= ACER_AMW0_WIRELESS_MASK; 882 883 status = wmab_execute(&args, &out); 884 if (ACPI_FAILURE(status)) 885 return status; 886 887 obj = out.pointer; 888 if (obj && obj->type == ACPI_TYPE_BUFFER && 889 obj->buffer.length == sizeof(struct wmab_ret)) { 890 ret = *((struct wmab_ret *) obj->buffer.pointer); 891 } else { 892 status = AE_ERROR; 893 goto out; 894 } 895 896 if (ret.eax & 0x1) 897 interface->capability |= ACER_CAP_WIRELESS; 898 899 args.ebx = 2 << 8; 900 args.ebx |= ACER_AMW0_BLUETOOTH_MASK; 901 902 /* 903 * It's ok to use existing buffer for next wmab_execute call. 904 * But we need to kfree(out.pointer) if next wmab_execute fail. 905 */ 906 status = wmab_execute(&args, &out); 907 if (ACPI_FAILURE(status)) 908 goto out; 909 910 obj = (union acpi_object *) out.pointer; 911 if (obj && obj->type == ACPI_TYPE_BUFFER 912 && obj->buffer.length == sizeof(struct wmab_ret)) { 913 ret = *((struct wmab_ret *) obj->buffer.pointer); 914 } else { 915 status = AE_ERROR; 916 goto out; 917 } 918 919 if (ret.eax & 0x1) 920 interface->capability |= ACER_CAP_BLUETOOTH; 921 922 /* 923 * This appears to be safe to enable, since all Wistron based laptops 924 * appear to use the same EC register for brightness, even if they 925 * differ for wireless, etc 926 */ 927 if (quirks->brightness >= 0) 928 interface->capability |= ACER_CAP_BRIGHTNESS; 929 930 status = AE_OK; 931 out: 932 kfree(out.pointer); 933 return status; 934 } 935 936 static struct wmi_interface AMW0_interface = { 937 .type = ACER_AMW0, 938 }; 939 940 static struct wmi_interface AMW0_V2_interface = { 941 .type = ACER_AMW0_V2, 942 }; 943 944 /* 945 * New interface (The WMID interface) 946 */ 947 static acpi_status 948 WMI_execute_u32(u32 method_id, u32 in, u32 *out) 949 { 950 struct acpi_buffer input = { (acpi_size) sizeof(u32), (void *)(&in) }; 951 struct acpi_buffer result = { ACPI_ALLOCATE_BUFFER, NULL }; 952 union acpi_object *obj; 953 u32 tmp = 0; 954 acpi_status status; 955 956 status = wmi_evaluate_method(WMID_GUID1, 0, method_id, &input, &result); 957 958 if (ACPI_FAILURE(status)) 959 return status; 960 961 obj = (union acpi_object *) result.pointer; 962 if (obj) { 963 if (obj->type == ACPI_TYPE_BUFFER && 964 (obj->buffer.length == sizeof(u32) || 965 obj->buffer.length == sizeof(u64))) { 966 tmp = *((u32 *) obj->buffer.pointer); 967 } else if (obj->type == ACPI_TYPE_INTEGER) { 968 tmp = (u32) obj->integer.value; 969 } 970 } 971 972 if (out) 973 *out = tmp; 974 975 kfree(result.pointer); 976 977 return status; 978 } 979 980 static acpi_status WMID_get_u32(u32 *value, u32 cap) 981 { 982 acpi_status status; 983 u8 tmp; 984 u32 result, method_id = 0; 985 986 switch (cap) { 987 case ACER_CAP_WIRELESS: 988 method_id = ACER_WMID_GET_WIRELESS_METHODID; 989 break; 990 case ACER_CAP_BLUETOOTH: 991 method_id = ACER_WMID_GET_BLUETOOTH_METHODID; 992 break; 993 case ACER_CAP_BRIGHTNESS: 994 method_id = ACER_WMID_GET_BRIGHTNESS_METHODID; 995 break; 996 case ACER_CAP_THREEG: 997 method_id = ACER_WMID_GET_THREEG_METHODID; 998 break; 999 case ACER_CAP_MAILLED: 1000 if (quirks->mailled == 1) { 1001 ec_read(0x9f, &tmp); 1002 *value = tmp & 0x1; 1003 return 0; 1004 } 1005 default: 1006 return AE_ERROR; 1007 } 1008 status = WMI_execute_u32(method_id, 0, &result); 1009 1010 if (ACPI_SUCCESS(status)) 1011 *value = (u8)result; 1012 1013 return status; 1014 } 1015 1016 static acpi_status WMID_set_u32(u32 value, u32 cap) 1017 { 1018 u32 method_id = 0; 1019 char param; 1020 1021 switch (cap) { 1022 case ACER_CAP_BRIGHTNESS: 1023 if (value > max_brightness) 1024 return AE_BAD_PARAMETER; 1025 method_id = ACER_WMID_SET_BRIGHTNESS_METHODID; 1026 break; 1027 case ACER_CAP_WIRELESS: 1028 if (value > 1) 1029 return AE_BAD_PARAMETER; 1030 method_id = ACER_WMID_SET_WIRELESS_METHODID; 1031 break; 1032 case ACER_CAP_BLUETOOTH: 1033 if (value > 1) 1034 return AE_BAD_PARAMETER; 1035 method_id = ACER_WMID_SET_BLUETOOTH_METHODID; 1036 break; 1037 case ACER_CAP_THREEG: 1038 if (value > 1) 1039 return AE_BAD_PARAMETER; 1040 method_id = ACER_WMID_SET_THREEG_METHODID; 1041 break; 1042 case ACER_CAP_MAILLED: 1043 if (value > 1) 1044 return AE_BAD_PARAMETER; 1045 if (quirks->mailled == 1) { 1046 param = value ? 0x92 : 0x93; 1047 i8042_lock_chip(); 1048 i8042_command(¶m, 0x1059); 1049 i8042_unlock_chip(); 1050 return 0; 1051 } 1052 break; 1053 default: 1054 return AE_ERROR; 1055 } 1056 return WMI_execute_u32(method_id, (u32)value, NULL); 1057 } 1058 1059 static acpi_status wmid3_get_device_status(u32 *value, u16 device) 1060 { 1061 struct wmid3_gds_return_value return_value; 1062 acpi_status status; 1063 union acpi_object *obj; 1064 struct wmid3_gds_get_input_param params = { 1065 .function_num = 0x1, 1066 .hotkey_number = commun_fn_key_number, 1067 .devices = device, 1068 }; 1069 struct acpi_buffer input = { 1070 sizeof(struct wmid3_gds_get_input_param), 1071 ¶ms 1072 }; 1073 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 1074 1075 status = wmi_evaluate_method(WMID_GUID3, 0, 0x2, &input, &output); 1076 if (ACPI_FAILURE(status)) 1077 return status; 1078 1079 obj = output.pointer; 1080 1081 if (!obj) 1082 return AE_ERROR; 1083 else if (obj->type != ACPI_TYPE_BUFFER) { 1084 kfree(obj); 1085 return AE_ERROR; 1086 } 1087 if (obj->buffer.length != 8) { 1088 pr_warn("Unknown buffer length %d\n", obj->buffer.length); 1089 kfree(obj); 1090 return AE_ERROR; 1091 } 1092 1093 return_value = *((struct wmid3_gds_return_value *)obj->buffer.pointer); 1094 kfree(obj); 1095 1096 if (return_value.error_code || return_value.ec_return_value) 1097 pr_warn("Get 0x%x Device Status failed: 0x%x - 0x%x\n", 1098 device, 1099 return_value.error_code, 1100 return_value.ec_return_value); 1101 else 1102 *value = !!(return_value.devices & device); 1103 1104 return status; 1105 } 1106 1107 static acpi_status wmid_v2_get_u32(u32 *value, u32 cap) 1108 { 1109 u16 device; 1110 1111 switch (cap) { 1112 case ACER_CAP_WIRELESS: 1113 device = ACER_WMID3_GDS_WIRELESS; 1114 break; 1115 case ACER_CAP_BLUETOOTH: 1116 device = ACER_WMID3_GDS_BLUETOOTH; 1117 break; 1118 case ACER_CAP_THREEG: 1119 device = ACER_WMID3_GDS_THREEG; 1120 break; 1121 default: 1122 return AE_ERROR; 1123 } 1124 return wmid3_get_device_status(value, device); 1125 } 1126 1127 static acpi_status wmid3_set_device_status(u32 value, u16 device) 1128 { 1129 struct wmid3_gds_return_value return_value; 1130 acpi_status status; 1131 union acpi_object *obj; 1132 u16 devices; 1133 struct wmid3_gds_get_input_param get_params = { 1134 .function_num = 0x1, 1135 .hotkey_number = commun_fn_key_number, 1136 .devices = commun_func_bitmap, 1137 }; 1138 struct acpi_buffer get_input = { 1139 sizeof(struct wmid3_gds_get_input_param), 1140 &get_params 1141 }; 1142 struct wmid3_gds_set_input_param set_params = { 1143 .function_num = 0x2, 1144 .hotkey_number = commun_fn_key_number, 1145 .devices = commun_func_bitmap, 1146 }; 1147 struct acpi_buffer set_input = { 1148 sizeof(struct wmid3_gds_set_input_param), 1149 &set_params 1150 }; 1151 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 1152 struct acpi_buffer output2 = { ACPI_ALLOCATE_BUFFER, NULL }; 1153 1154 status = wmi_evaluate_method(WMID_GUID3, 0, 0x2, &get_input, &output); 1155 if (ACPI_FAILURE(status)) 1156 return status; 1157 1158 obj = output.pointer; 1159 1160 if (!obj) 1161 return AE_ERROR; 1162 else if (obj->type != ACPI_TYPE_BUFFER) { 1163 kfree(obj); 1164 return AE_ERROR; 1165 } 1166 if (obj->buffer.length != 8) { 1167 pr_warn("Unknown buffer length %d\n", obj->buffer.length); 1168 kfree(obj); 1169 return AE_ERROR; 1170 } 1171 1172 return_value = *((struct wmid3_gds_return_value *)obj->buffer.pointer); 1173 kfree(obj); 1174 1175 if (return_value.error_code || return_value.ec_return_value) { 1176 pr_warn("Get Current Device Status failed: 0x%x - 0x%x\n", 1177 return_value.error_code, 1178 return_value.ec_return_value); 1179 return status; 1180 } 1181 1182 devices = return_value.devices; 1183 set_params.devices = (value) ? (devices | device) : (devices & ~device); 1184 1185 status = wmi_evaluate_method(WMID_GUID3, 0, 0x1, &set_input, &output2); 1186 if (ACPI_FAILURE(status)) 1187 return status; 1188 1189 obj = output2.pointer; 1190 1191 if (!obj) 1192 return AE_ERROR; 1193 else if (obj->type != ACPI_TYPE_BUFFER) { 1194 kfree(obj); 1195 return AE_ERROR; 1196 } 1197 if (obj->buffer.length != 4) { 1198 pr_warn("Unknown buffer length %d\n", obj->buffer.length); 1199 kfree(obj); 1200 return AE_ERROR; 1201 } 1202 1203 return_value = *((struct wmid3_gds_return_value *)obj->buffer.pointer); 1204 kfree(obj); 1205 1206 if (return_value.error_code || return_value.ec_return_value) 1207 pr_warn("Set Device Status failed: 0x%x - 0x%x\n", 1208 return_value.error_code, 1209 return_value.ec_return_value); 1210 1211 return status; 1212 } 1213 1214 static acpi_status wmid_v2_set_u32(u32 value, u32 cap) 1215 { 1216 u16 device; 1217 1218 switch (cap) { 1219 case ACER_CAP_WIRELESS: 1220 device = ACER_WMID3_GDS_WIRELESS; 1221 break; 1222 case ACER_CAP_BLUETOOTH: 1223 device = ACER_WMID3_GDS_BLUETOOTH; 1224 break; 1225 case ACER_CAP_THREEG: 1226 device = ACER_WMID3_GDS_THREEG; 1227 break; 1228 default: 1229 return AE_ERROR; 1230 } 1231 return wmid3_set_device_status(value, device); 1232 } 1233 1234 static void __init type_aa_dmi_decode(const struct dmi_header *header, void *d) 1235 { 1236 struct hotkey_function_type_aa *type_aa; 1237 1238 /* We are looking for OEM-specific Type AAh */ 1239 if (header->type != 0xAA) 1240 return; 1241 1242 has_type_aa = true; 1243 type_aa = (struct hotkey_function_type_aa *) header; 1244 1245 pr_info("Function bitmap for Communication Button: 0x%x\n", 1246 type_aa->commun_func_bitmap); 1247 commun_func_bitmap = type_aa->commun_func_bitmap; 1248 1249 if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_WIRELESS) 1250 interface->capability |= ACER_CAP_WIRELESS; 1251 if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_THREEG) 1252 interface->capability |= ACER_CAP_THREEG; 1253 if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_BLUETOOTH) 1254 interface->capability |= ACER_CAP_BLUETOOTH; 1255 if (type_aa->commun_func_bitmap & ACER_WMID3_GDS_RFBTN) { 1256 interface->capability |= ACER_CAP_RFBTN; 1257 commun_func_bitmap &= ~ACER_WMID3_GDS_RFBTN; 1258 } 1259 1260 commun_fn_key_number = type_aa->commun_fn_key_number; 1261 } 1262 1263 static acpi_status __init WMID_set_capabilities(void) 1264 { 1265 struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL}; 1266 union acpi_object *obj; 1267 acpi_status status; 1268 u32 devices; 1269 1270 status = wmi_query_block(WMID_GUID2, 0, &out); 1271 if (ACPI_FAILURE(status)) 1272 return status; 1273 1274 obj = (union acpi_object *) out.pointer; 1275 if (obj) { 1276 if (obj->type == ACPI_TYPE_BUFFER && 1277 (obj->buffer.length == sizeof(u32) || 1278 obj->buffer.length == sizeof(u64))) { 1279 devices = *((u32 *) obj->buffer.pointer); 1280 } else if (obj->type == ACPI_TYPE_INTEGER) { 1281 devices = (u32) obj->integer.value; 1282 } else { 1283 kfree(out.pointer); 1284 return AE_ERROR; 1285 } 1286 } else { 1287 kfree(out.pointer); 1288 return AE_ERROR; 1289 } 1290 1291 pr_info("Function bitmap for Communication Device: 0x%x\n", devices); 1292 if (devices & 0x07) 1293 interface->capability |= ACER_CAP_WIRELESS; 1294 if (devices & 0x40) 1295 interface->capability |= ACER_CAP_THREEG; 1296 if (devices & 0x10) 1297 interface->capability |= ACER_CAP_BLUETOOTH; 1298 1299 if (!(devices & 0x20)) 1300 max_brightness = 0x9; 1301 1302 kfree(out.pointer); 1303 return status; 1304 } 1305 1306 static struct wmi_interface wmid_interface = { 1307 .type = ACER_WMID, 1308 }; 1309 1310 static struct wmi_interface wmid_v2_interface = { 1311 .type = ACER_WMID_v2, 1312 }; 1313 1314 /* 1315 * Generic Device (interface-independent) 1316 */ 1317 1318 static acpi_status get_u32(u32 *value, u32 cap) 1319 { 1320 acpi_status status = AE_ERROR; 1321 1322 switch (interface->type) { 1323 case ACER_AMW0: 1324 status = AMW0_get_u32(value, cap); 1325 break; 1326 case ACER_AMW0_V2: 1327 if (cap == ACER_CAP_MAILLED) { 1328 status = AMW0_get_u32(value, cap); 1329 break; 1330 } 1331 case ACER_WMID: 1332 status = WMID_get_u32(value, cap); 1333 break; 1334 case ACER_WMID_v2: 1335 if (cap & (ACER_CAP_WIRELESS | 1336 ACER_CAP_BLUETOOTH | 1337 ACER_CAP_THREEG)) 1338 status = wmid_v2_get_u32(value, cap); 1339 else if (wmi_has_guid(WMID_GUID2)) 1340 status = WMID_get_u32(value, cap); 1341 break; 1342 } 1343 1344 return status; 1345 } 1346 1347 static acpi_status set_u32(u32 value, u32 cap) 1348 { 1349 acpi_status status; 1350 1351 if (interface->capability & cap) { 1352 switch (interface->type) { 1353 case ACER_AMW0: 1354 return AMW0_set_u32(value, cap); 1355 case ACER_AMW0_V2: 1356 if (cap == ACER_CAP_MAILLED) 1357 return AMW0_set_u32(value, cap); 1358 1359 /* 1360 * On some models, some WMID methods don't toggle 1361 * properly. For those cases, we want to run the AMW0 1362 * method afterwards to be certain we've really toggled 1363 * the device state. 1364 */ 1365 if (cap == ACER_CAP_WIRELESS || 1366 cap == ACER_CAP_BLUETOOTH) { 1367 status = WMID_set_u32(value, cap); 1368 if (ACPI_FAILURE(status)) 1369 return status; 1370 1371 return AMW0_set_u32(value, cap); 1372 } 1373 case ACER_WMID: 1374 return WMID_set_u32(value, cap); 1375 case ACER_WMID_v2: 1376 if (cap & (ACER_CAP_WIRELESS | 1377 ACER_CAP_BLUETOOTH | 1378 ACER_CAP_THREEG)) 1379 return wmid_v2_set_u32(value, cap); 1380 else if (wmi_has_guid(WMID_GUID2)) 1381 return WMID_set_u32(value, cap); 1382 default: 1383 return AE_BAD_PARAMETER; 1384 } 1385 } 1386 return AE_BAD_PARAMETER; 1387 } 1388 1389 static void __init acer_commandline_init(void) 1390 { 1391 /* 1392 * These will all fail silently if the value given is invalid, or the 1393 * capability isn't available on the given interface 1394 */ 1395 if (mailled >= 0) 1396 set_u32(mailled, ACER_CAP_MAILLED); 1397 if (!has_type_aa && threeg >= 0) 1398 set_u32(threeg, ACER_CAP_THREEG); 1399 if (brightness >= 0) 1400 set_u32(brightness, ACER_CAP_BRIGHTNESS); 1401 } 1402 1403 /* 1404 * LED device (Mail LED only, no other LEDs known yet) 1405 */ 1406 static void mail_led_set(struct led_classdev *led_cdev, 1407 enum led_brightness value) 1408 { 1409 set_u32(value, ACER_CAP_MAILLED); 1410 } 1411 1412 static struct led_classdev mail_led = { 1413 .name = "acer-wmi::mail", 1414 .brightness_set = mail_led_set, 1415 }; 1416 1417 static int acer_led_init(struct device *dev) 1418 { 1419 return led_classdev_register(dev, &mail_led); 1420 } 1421 1422 static void acer_led_exit(void) 1423 { 1424 set_u32(LED_OFF, ACER_CAP_MAILLED); 1425 led_classdev_unregister(&mail_led); 1426 } 1427 1428 /* 1429 * Backlight device 1430 */ 1431 static struct backlight_device *acer_backlight_device; 1432 1433 static int read_brightness(struct backlight_device *bd) 1434 { 1435 u32 value; 1436 get_u32(&value, ACER_CAP_BRIGHTNESS); 1437 return value; 1438 } 1439 1440 static int update_bl_status(struct backlight_device *bd) 1441 { 1442 int intensity = bd->props.brightness; 1443 1444 if (bd->props.power != FB_BLANK_UNBLANK) 1445 intensity = 0; 1446 if (bd->props.fb_blank != FB_BLANK_UNBLANK) 1447 intensity = 0; 1448 1449 set_u32(intensity, ACER_CAP_BRIGHTNESS); 1450 1451 return 0; 1452 } 1453 1454 static const struct backlight_ops acer_bl_ops = { 1455 .get_brightness = read_brightness, 1456 .update_status = update_bl_status, 1457 }; 1458 1459 static int acer_backlight_init(struct device *dev) 1460 { 1461 struct backlight_properties props; 1462 struct backlight_device *bd; 1463 1464 memset(&props, 0, sizeof(struct backlight_properties)); 1465 props.type = BACKLIGHT_PLATFORM; 1466 props.max_brightness = max_brightness; 1467 bd = backlight_device_register("acer-wmi", dev, NULL, &acer_bl_ops, 1468 &props); 1469 if (IS_ERR(bd)) { 1470 pr_err("Could not register Acer backlight device\n"); 1471 acer_backlight_device = NULL; 1472 return PTR_ERR(bd); 1473 } 1474 1475 acer_backlight_device = bd; 1476 1477 bd->props.power = FB_BLANK_UNBLANK; 1478 bd->props.brightness = read_brightness(bd); 1479 backlight_update_status(bd); 1480 return 0; 1481 } 1482 1483 static void acer_backlight_exit(void) 1484 { 1485 backlight_device_unregister(acer_backlight_device); 1486 } 1487 1488 /* 1489 * Accelerometer device 1490 */ 1491 static acpi_handle gsensor_handle; 1492 1493 static int acer_gsensor_init(void) 1494 { 1495 acpi_status status; 1496 struct acpi_buffer output; 1497 union acpi_object out_obj; 1498 1499 output.length = sizeof(out_obj); 1500 output.pointer = &out_obj; 1501 status = acpi_evaluate_object(gsensor_handle, "_INI", NULL, &output); 1502 if (ACPI_FAILURE(status)) 1503 return -1; 1504 1505 return 0; 1506 } 1507 1508 static int acer_gsensor_open(struct input_dev *input) 1509 { 1510 return acer_gsensor_init(); 1511 } 1512 1513 static int acer_gsensor_event(void) 1514 { 1515 acpi_status status; 1516 struct acpi_buffer output; 1517 union acpi_object out_obj[5]; 1518 1519 if (!has_cap(ACER_CAP_ACCEL)) 1520 return -1; 1521 1522 output.length = sizeof(out_obj); 1523 output.pointer = out_obj; 1524 1525 status = acpi_evaluate_object(gsensor_handle, "RDVL", NULL, &output); 1526 if (ACPI_FAILURE(status)) 1527 return -1; 1528 1529 if (out_obj->package.count != 4) 1530 return -1; 1531 1532 input_report_abs(acer_wmi_accel_dev, ABS_X, 1533 (s16)out_obj->package.elements[0].integer.value); 1534 input_report_abs(acer_wmi_accel_dev, ABS_Y, 1535 (s16)out_obj->package.elements[1].integer.value); 1536 input_report_abs(acer_wmi_accel_dev, ABS_Z, 1537 (s16)out_obj->package.elements[2].integer.value); 1538 input_sync(acer_wmi_accel_dev); 1539 return 0; 1540 } 1541 1542 /* 1543 * Rfkill devices 1544 */ 1545 static void acer_rfkill_update(struct work_struct *ignored); 1546 static DECLARE_DELAYED_WORK(acer_rfkill_work, acer_rfkill_update); 1547 static void acer_rfkill_update(struct work_struct *ignored) 1548 { 1549 u32 state; 1550 acpi_status status; 1551 1552 if (has_cap(ACER_CAP_WIRELESS)) { 1553 status = get_u32(&state, ACER_CAP_WIRELESS); 1554 if (ACPI_SUCCESS(status)) { 1555 if (quirks->wireless == 3) 1556 rfkill_set_hw_state(wireless_rfkill, !state); 1557 else 1558 rfkill_set_sw_state(wireless_rfkill, !state); 1559 } 1560 } 1561 1562 if (has_cap(ACER_CAP_BLUETOOTH)) { 1563 status = get_u32(&state, ACER_CAP_BLUETOOTH); 1564 if (ACPI_SUCCESS(status)) 1565 rfkill_set_sw_state(bluetooth_rfkill, !state); 1566 } 1567 1568 if (has_cap(ACER_CAP_THREEG) && wmi_has_guid(WMID_GUID3)) { 1569 status = get_u32(&state, ACER_WMID3_GDS_THREEG); 1570 if (ACPI_SUCCESS(status)) 1571 rfkill_set_sw_state(threeg_rfkill, !state); 1572 } 1573 1574 schedule_delayed_work(&acer_rfkill_work, round_jiffies_relative(HZ)); 1575 } 1576 1577 static int acer_rfkill_set(void *data, bool blocked) 1578 { 1579 acpi_status status; 1580 u32 cap = (unsigned long)data; 1581 1582 if (rfkill_inited) { 1583 status = set_u32(!blocked, cap); 1584 if (ACPI_FAILURE(status)) 1585 return -ENODEV; 1586 } 1587 1588 return 0; 1589 } 1590 1591 static const struct rfkill_ops acer_rfkill_ops = { 1592 .set_block = acer_rfkill_set, 1593 }; 1594 1595 static struct rfkill *acer_rfkill_register(struct device *dev, 1596 enum rfkill_type type, 1597 char *name, u32 cap) 1598 { 1599 int err; 1600 struct rfkill *rfkill_dev; 1601 u32 state; 1602 acpi_status status; 1603 1604 rfkill_dev = rfkill_alloc(name, dev, type, 1605 &acer_rfkill_ops, 1606 (void *)(unsigned long)cap); 1607 if (!rfkill_dev) 1608 return ERR_PTR(-ENOMEM); 1609 1610 status = get_u32(&state, cap); 1611 1612 err = rfkill_register(rfkill_dev); 1613 if (err) { 1614 rfkill_destroy(rfkill_dev); 1615 return ERR_PTR(err); 1616 } 1617 1618 if (ACPI_SUCCESS(status)) 1619 rfkill_set_sw_state(rfkill_dev, !state); 1620 1621 return rfkill_dev; 1622 } 1623 1624 static int acer_rfkill_init(struct device *dev) 1625 { 1626 int err; 1627 1628 if (has_cap(ACER_CAP_WIRELESS)) { 1629 wireless_rfkill = acer_rfkill_register(dev, RFKILL_TYPE_WLAN, 1630 "acer-wireless", ACER_CAP_WIRELESS); 1631 if (IS_ERR(wireless_rfkill)) { 1632 err = PTR_ERR(wireless_rfkill); 1633 goto error_wireless; 1634 } 1635 } 1636 1637 if (has_cap(ACER_CAP_BLUETOOTH)) { 1638 bluetooth_rfkill = acer_rfkill_register(dev, 1639 RFKILL_TYPE_BLUETOOTH, "acer-bluetooth", 1640 ACER_CAP_BLUETOOTH); 1641 if (IS_ERR(bluetooth_rfkill)) { 1642 err = PTR_ERR(bluetooth_rfkill); 1643 goto error_bluetooth; 1644 } 1645 } 1646 1647 if (has_cap(ACER_CAP_THREEG)) { 1648 threeg_rfkill = acer_rfkill_register(dev, 1649 RFKILL_TYPE_WWAN, "acer-threeg", 1650 ACER_CAP_THREEG); 1651 if (IS_ERR(threeg_rfkill)) { 1652 err = PTR_ERR(threeg_rfkill); 1653 goto error_threeg; 1654 } 1655 } 1656 1657 rfkill_inited = true; 1658 1659 if ((ec_raw_mode || !wmi_has_guid(ACERWMID_EVENT_GUID)) && 1660 has_cap(ACER_CAP_WIRELESS | ACER_CAP_BLUETOOTH | ACER_CAP_THREEG)) 1661 schedule_delayed_work(&acer_rfkill_work, 1662 round_jiffies_relative(HZ)); 1663 1664 return 0; 1665 1666 error_threeg: 1667 if (has_cap(ACER_CAP_BLUETOOTH)) { 1668 rfkill_unregister(bluetooth_rfkill); 1669 rfkill_destroy(bluetooth_rfkill); 1670 } 1671 error_bluetooth: 1672 if (has_cap(ACER_CAP_WIRELESS)) { 1673 rfkill_unregister(wireless_rfkill); 1674 rfkill_destroy(wireless_rfkill); 1675 } 1676 error_wireless: 1677 return err; 1678 } 1679 1680 static void acer_rfkill_exit(void) 1681 { 1682 if ((ec_raw_mode || !wmi_has_guid(ACERWMID_EVENT_GUID)) && 1683 has_cap(ACER_CAP_WIRELESS | ACER_CAP_BLUETOOTH | ACER_CAP_THREEG)) 1684 cancel_delayed_work_sync(&acer_rfkill_work); 1685 1686 if (has_cap(ACER_CAP_WIRELESS)) { 1687 rfkill_unregister(wireless_rfkill); 1688 rfkill_destroy(wireless_rfkill); 1689 } 1690 1691 if (has_cap(ACER_CAP_BLUETOOTH)) { 1692 rfkill_unregister(bluetooth_rfkill); 1693 rfkill_destroy(bluetooth_rfkill); 1694 } 1695 1696 if (has_cap(ACER_CAP_THREEG)) { 1697 rfkill_unregister(threeg_rfkill); 1698 rfkill_destroy(threeg_rfkill); 1699 } 1700 return; 1701 } 1702 1703 static void acer_wmi_notify(u32 value, void *context) 1704 { 1705 struct acpi_buffer response = { ACPI_ALLOCATE_BUFFER, NULL }; 1706 union acpi_object *obj; 1707 struct event_return_value return_value; 1708 acpi_status status; 1709 u16 device_state; 1710 const struct key_entry *key; 1711 u32 scancode; 1712 1713 status = wmi_get_event_data(value, &response); 1714 if (status != AE_OK) { 1715 pr_warn("bad event status 0x%x\n", status); 1716 return; 1717 } 1718 1719 obj = (union acpi_object *)response.pointer; 1720 1721 if (!obj) 1722 return; 1723 if (obj->type != ACPI_TYPE_BUFFER) { 1724 pr_warn("Unknown response received %d\n", obj->type); 1725 kfree(obj); 1726 return; 1727 } 1728 if (obj->buffer.length != 8) { 1729 pr_warn("Unknown buffer length %d\n", obj->buffer.length); 1730 kfree(obj); 1731 return; 1732 } 1733 1734 return_value = *((struct event_return_value *)obj->buffer.pointer); 1735 kfree(obj); 1736 1737 switch (return_value.function) { 1738 case WMID_HOTKEY_EVENT: 1739 device_state = return_value.device_state; 1740 pr_debug("device state: 0x%x\n", device_state); 1741 1742 key = sparse_keymap_entry_from_scancode(acer_wmi_input_dev, 1743 return_value.key_num); 1744 if (!key) { 1745 pr_warn("Unknown key number - 0x%x\n", 1746 return_value.key_num); 1747 } else { 1748 scancode = return_value.key_num; 1749 switch (key->keycode) { 1750 case KEY_WLAN: 1751 case KEY_BLUETOOTH: 1752 if (has_cap(ACER_CAP_WIRELESS)) 1753 rfkill_set_sw_state(wireless_rfkill, 1754 !(device_state & ACER_WMID3_GDS_WIRELESS)); 1755 if (has_cap(ACER_CAP_THREEG)) 1756 rfkill_set_sw_state(threeg_rfkill, 1757 !(device_state & ACER_WMID3_GDS_THREEG)); 1758 if (has_cap(ACER_CAP_BLUETOOTH)) 1759 rfkill_set_sw_state(bluetooth_rfkill, 1760 !(device_state & ACER_WMID3_GDS_BLUETOOTH)); 1761 break; 1762 case KEY_TOUCHPAD_TOGGLE: 1763 scancode = (device_state & ACER_WMID3_GDS_TOUCHPAD) ? 1764 KEY_TOUCHPAD_ON : KEY_TOUCHPAD_OFF; 1765 } 1766 sparse_keymap_report_event(acer_wmi_input_dev, scancode, 1, true); 1767 } 1768 break; 1769 case WMID_ACCEL_EVENT: 1770 acer_gsensor_event(); 1771 break; 1772 default: 1773 pr_warn("Unknown function number - %d - %d\n", 1774 return_value.function, return_value.key_num); 1775 break; 1776 } 1777 } 1778 1779 static acpi_status __init 1780 wmid3_set_function_mode(struct func_input_params *params, 1781 struct func_return_value *return_value) 1782 { 1783 acpi_status status; 1784 union acpi_object *obj; 1785 1786 struct acpi_buffer input = { sizeof(struct func_input_params), params }; 1787 struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; 1788 1789 status = wmi_evaluate_method(WMID_GUID3, 0, 0x1, &input, &output); 1790 if (ACPI_FAILURE(status)) 1791 return status; 1792 1793 obj = output.pointer; 1794 1795 if (!obj) 1796 return AE_ERROR; 1797 else if (obj->type != ACPI_TYPE_BUFFER) { 1798 kfree(obj); 1799 return AE_ERROR; 1800 } 1801 if (obj->buffer.length != 4) { 1802 pr_warn("Unknown buffer length %d\n", obj->buffer.length); 1803 kfree(obj); 1804 return AE_ERROR; 1805 } 1806 1807 *return_value = *((struct func_return_value *)obj->buffer.pointer); 1808 kfree(obj); 1809 1810 return status; 1811 } 1812 1813 static int __init acer_wmi_enable_ec_raw(void) 1814 { 1815 struct func_return_value return_value; 1816 acpi_status status; 1817 struct func_input_params params = { 1818 .function_num = 0x1, 1819 .commun_devices = 0xFFFF, 1820 .devices = 0xFFFF, 1821 .app_status = 0x00, /* Launch Manager Deactive */ 1822 .app_mask = 0x01, 1823 }; 1824 1825 status = wmid3_set_function_mode(¶ms, &return_value); 1826 1827 if (return_value.error_code || return_value.ec_return_value) 1828 pr_warn("Enabling EC raw mode failed: 0x%x - 0x%x\n", 1829 return_value.error_code, 1830 return_value.ec_return_value); 1831 else 1832 pr_info("Enabled EC raw mode\n"); 1833 1834 return status; 1835 } 1836 1837 static int __init acer_wmi_enable_lm(void) 1838 { 1839 struct func_return_value return_value; 1840 acpi_status status; 1841 struct func_input_params params = { 1842 .function_num = 0x1, 1843 .commun_devices = 0xFFFF, 1844 .devices = 0xFFFF, 1845 .app_status = 0x01, /* Launch Manager Active */ 1846 .app_mask = 0x01, 1847 }; 1848 1849 status = wmid3_set_function_mode(¶ms, &return_value); 1850 1851 if (return_value.error_code || return_value.ec_return_value) 1852 pr_warn("Enabling Launch Manager failed: 0x%x - 0x%x\n", 1853 return_value.error_code, 1854 return_value.ec_return_value); 1855 1856 return status; 1857 } 1858 1859 static int __init acer_wmi_enable_rf_button(void) 1860 { 1861 struct func_return_value return_value; 1862 acpi_status status; 1863 struct func_input_params params = { 1864 .function_num = 0x1, 1865 .commun_devices = 0xFFFF, 1866 .devices = 0xFFFF, 1867 .app_status = 0x10, /* RF Button Active */ 1868 .app_mask = 0x10, 1869 }; 1870 1871 status = wmid3_set_function_mode(¶ms, &return_value); 1872 1873 if (return_value.error_code || return_value.ec_return_value) 1874 pr_warn("Enabling RF Button failed: 0x%x - 0x%x\n", 1875 return_value.error_code, 1876 return_value.ec_return_value); 1877 1878 return status; 1879 } 1880 1881 #define ACER_WMID_ACCEL_HID "BST0001" 1882 1883 static acpi_status __init acer_wmi_get_handle_cb(acpi_handle ah, u32 level, 1884 void *ctx, void **retval) 1885 { 1886 struct acpi_device *dev; 1887 1888 if (!strcmp(ctx, "SENR")) { 1889 if (acpi_bus_get_device(ah, &dev)) 1890 return AE_OK; 1891 if (strcmp(ACER_WMID_ACCEL_HID, acpi_device_hid(dev))) 1892 return AE_OK; 1893 } else 1894 return AE_OK; 1895 1896 *(acpi_handle *)retval = ah; 1897 1898 return AE_CTRL_TERMINATE; 1899 } 1900 1901 static int __init acer_wmi_get_handle(const char *name, const char *prop, 1902 acpi_handle *ah) 1903 { 1904 acpi_status status; 1905 acpi_handle handle; 1906 1907 BUG_ON(!name || !ah); 1908 1909 handle = NULL; 1910 status = acpi_get_devices(prop, acer_wmi_get_handle_cb, 1911 (void *)name, &handle); 1912 if (ACPI_SUCCESS(status) && handle) { 1913 *ah = handle; 1914 return 0; 1915 } else { 1916 return -ENODEV; 1917 } 1918 } 1919 1920 static int __init acer_wmi_accel_setup(void) 1921 { 1922 int err; 1923 1924 err = acer_wmi_get_handle("SENR", ACER_WMID_ACCEL_HID, &gsensor_handle); 1925 if (err) 1926 return err; 1927 1928 interface->capability |= ACER_CAP_ACCEL; 1929 1930 acer_wmi_accel_dev = input_allocate_device(); 1931 if (!acer_wmi_accel_dev) 1932 return -ENOMEM; 1933 1934 acer_wmi_accel_dev->open = acer_gsensor_open; 1935 1936 acer_wmi_accel_dev->name = "Acer BMA150 accelerometer"; 1937 acer_wmi_accel_dev->phys = "wmi/input1"; 1938 acer_wmi_accel_dev->id.bustype = BUS_HOST; 1939 acer_wmi_accel_dev->evbit[0] = BIT_MASK(EV_ABS); 1940 input_set_abs_params(acer_wmi_accel_dev, ABS_X, -16384, 16384, 0, 0); 1941 input_set_abs_params(acer_wmi_accel_dev, ABS_Y, -16384, 16384, 0, 0); 1942 input_set_abs_params(acer_wmi_accel_dev, ABS_Z, -16384, 16384, 0, 0); 1943 1944 err = input_register_device(acer_wmi_accel_dev); 1945 if (err) 1946 goto err_free_dev; 1947 1948 return 0; 1949 1950 err_free_dev: 1951 input_free_device(acer_wmi_accel_dev); 1952 return err; 1953 } 1954 1955 static void acer_wmi_accel_destroy(void) 1956 { 1957 input_unregister_device(acer_wmi_accel_dev); 1958 } 1959 1960 static int __init acer_wmi_input_setup(void) 1961 { 1962 acpi_status status; 1963 int err; 1964 1965 acer_wmi_input_dev = input_allocate_device(); 1966 if (!acer_wmi_input_dev) 1967 return -ENOMEM; 1968 1969 acer_wmi_input_dev->name = "Acer WMI hotkeys"; 1970 acer_wmi_input_dev->phys = "wmi/input0"; 1971 acer_wmi_input_dev->id.bustype = BUS_HOST; 1972 1973 err = sparse_keymap_setup(acer_wmi_input_dev, acer_wmi_keymap, NULL); 1974 if (err) 1975 goto err_free_dev; 1976 1977 status = wmi_install_notify_handler(ACERWMID_EVENT_GUID, 1978 acer_wmi_notify, NULL); 1979 if (ACPI_FAILURE(status)) { 1980 err = -EIO; 1981 goto err_free_dev; 1982 } 1983 1984 err = input_register_device(acer_wmi_input_dev); 1985 if (err) 1986 goto err_uninstall_notifier; 1987 1988 return 0; 1989 1990 err_uninstall_notifier: 1991 wmi_remove_notify_handler(ACERWMID_EVENT_GUID); 1992 err_free_dev: 1993 input_free_device(acer_wmi_input_dev); 1994 return err; 1995 } 1996 1997 static void acer_wmi_input_destroy(void) 1998 { 1999 wmi_remove_notify_handler(ACERWMID_EVENT_GUID); 2000 input_unregister_device(acer_wmi_input_dev); 2001 } 2002 2003 /* 2004 * debugfs functions 2005 */ 2006 static u32 get_wmid_devices(void) 2007 { 2008 struct acpi_buffer out = {ACPI_ALLOCATE_BUFFER, NULL}; 2009 union acpi_object *obj; 2010 acpi_status status; 2011 u32 devices = 0; 2012 2013 status = wmi_query_block(WMID_GUID2, 0, &out); 2014 if (ACPI_FAILURE(status)) 2015 return 0; 2016 2017 obj = (union acpi_object *) out.pointer; 2018 if (obj) { 2019 if (obj->type == ACPI_TYPE_BUFFER && 2020 (obj->buffer.length == sizeof(u32) || 2021 obj->buffer.length == sizeof(u64))) { 2022 devices = *((u32 *) obj->buffer.pointer); 2023 } else if (obj->type == ACPI_TYPE_INTEGER) { 2024 devices = (u32) obj->integer.value; 2025 } 2026 } 2027 2028 kfree(out.pointer); 2029 return devices; 2030 } 2031 2032 /* 2033 * Platform device 2034 */ 2035 static int acer_platform_probe(struct platform_device *device) 2036 { 2037 int err; 2038 2039 if (has_cap(ACER_CAP_MAILLED)) { 2040 err = acer_led_init(&device->dev); 2041 if (err) 2042 goto error_mailled; 2043 } 2044 2045 if (has_cap(ACER_CAP_BRIGHTNESS)) { 2046 err = acer_backlight_init(&device->dev); 2047 if (err) 2048 goto error_brightness; 2049 } 2050 2051 err = acer_rfkill_init(&device->dev); 2052 if (err) 2053 goto error_rfkill; 2054 2055 return err; 2056 2057 error_rfkill: 2058 if (has_cap(ACER_CAP_BRIGHTNESS)) 2059 acer_backlight_exit(); 2060 error_brightness: 2061 if (has_cap(ACER_CAP_MAILLED)) 2062 acer_led_exit(); 2063 error_mailled: 2064 return err; 2065 } 2066 2067 static int acer_platform_remove(struct platform_device *device) 2068 { 2069 if (has_cap(ACER_CAP_MAILLED)) 2070 acer_led_exit(); 2071 if (has_cap(ACER_CAP_BRIGHTNESS)) 2072 acer_backlight_exit(); 2073 2074 acer_rfkill_exit(); 2075 return 0; 2076 } 2077 2078 #ifdef CONFIG_PM_SLEEP 2079 static int acer_suspend(struct device *dev) 2080 { 2081 u32 value; 2082 struct acer_data *data = &interface->data; 2083 2084 if (!data) 2085 return -ENOMEM; 2086 2087 if (has_cap(ACER_CAP_MAILLED)) { 2088 get_u32(&value, ACER_CAP_MAILLED); 2089 set_u32(LED_OFF, ACER_CAP_MAILLED); 2090 data->mailled = value; 2091 } 2092 2093 if (has_cap(ACER_CAP_BRIGHTNESS)) { 2094 get_u32(&value, ACER_CAP_BRIGHTNESS); 2095 data->brightness = value; 2096 } 2097 2098 return 0; 2099 } 2100 2101 static int acer_resume(struct device *dev) 2102 { 2103 struct acer_data *data = &interface->data; 2104 2105 if (!data) 2106 return -ENOMEM; 2107 2108 if (has_cap(ACER_CAP_MAILLED)) 2109 set_u32(data->mailled, ACER_CAP_MAILLED); 2110 2111 if (has_cap(ACER_CAP_BRIGHTNESS)) 2112 set_u32(data->brightness, ACER_CAP_BRIGHTNESS); 2113 2114 if (has_cap(ACER_CAP_ACCEL)) 2115 acer_gsensor_init(); 2116 2117 return 0; 2118 } 2119 #else 2120 #define acer_suspend NULL 2121 #define acer_resume NULL 2122 #endif 2123 2124 static SIMPLE_DEV_PM_OPS(acer_pm, acer_suspend, acer_resume); 2125 2126 static void acer_platform_shutdown(struct platform_device *device) 2127 { 2128 struct acer_data *data = &interface->data; 2129 2130 if (!data) 2131 return; 2132 2133 if (has_cap(ACER_CAP_MAILLED)) 2134 set_u32(LED_OFF, ACER_CAP_MAILLED); 2135 } 2136 2137 static struct platform_driver acer_platform_driver = { 2138 .driver = { 2139 .name = "acer-wmi", 2140 .pm = &acer_pm, 2141 }, 2142 .probe = acer_platform_probe, 2143 .remove = acer_platform_remove, 2144 .shutdown = acer_platform_shutdown, 2145 }; 2146 2147 static struct platform_device *acer_platform_device; 2148 2149 static void remove_debugfs(void) 2150 { 2151 debugfs_remove(interface->debug.devices); 2152 debugfs_remove(interface->debug.root); 2153 } 2154 2155 static int __init create_debugfs(void) 2156 { 2157 interface->debug.root = debugfs_create_dir("acer-wmi", NULL); 2158 if (!interface->debug.root) { 2159 pr_err("Failed to create debugfs directory"); 2160 return -ENOMEM; 2161 } 2162 2163 interface->debug.devices = debugfs_create_u32("devices", S_IRUGO, 2164 interface->debug.root, 2165 &interface->debug.wmid_devices); 2166 if (!interface->debug.devices) 2167 goto error_debugfs; 2168 2169 return 0; 2170 2171 error_debugfs: 2172 remove_debugfs(); 2173 return -ENOMEM; 2174 } 2175 2176 static int __init acer_wmi_init(void) 2177 { 2178 int err; 2179 2180 pr_info("Acer Laptop ACPI-WMI Extras\n"); 2181 2182 if (dmi_check_system(acer_blacklist)) { 2183 pr_info("Blacklisted hardware detected - not loading\n"); 2184 return -ENODEV; 2185 } 2186 2187 find_quirks(); 2188 2189 /* 2190 * The AMW0_GUID1 wmi is not only found on Acer family but also other 2191 * machines like Lenovo, Fujitsu and Medion. In the past days, 2192 * acer-wmi driver handled those non-Acer machines by quirks list. 2193 * But actually acer-wmi driver was loaded on any machines that have 2194 * AMW0_GUID1. This behavior is strange because those machines should 2195 * be supported by appropriate wmi drivers. e.g. fujitsu-laptop, 2196 * ideapad-laptop. So, here checks the machine that has AMW0_GUID1 2197 * should be in Acer/Gateway/Packard Bell white list, or it's already 2198 * in the past quirk list. 2199 */ 2200 if (wmi_has_guid(AMW0_GUID1) && 2201 !dmi_check_system(amw0_whitelist) && 2202 quirks == &quirk_unknown) { 2203 pr_debug("Unsupported machine has AMW0_GUID1, unable to load\n"); 2204 return -ENODEV; 2205 } 2206 2207 /* 2208 * Detect which ACPI-WMI interface we're using. 2209 */ 2210 if (wmi_has_guid(AMW0_GUID1) && wmi_has_guid(WMID_GUID1)) 2211 interface = &AMW0_V2_interface; 2212 2213 if (!wmi_has_guid(AMW0_GUID1) && wmi_has_guid(WMID_GUID1)) 2214 interface = &wmid_interface; 2215 2216 if (wmi_has_guid(WMID_GUID3)) 2217 interface = &wmid_v2_interface; 2218 2219 if (interface) 2220 dmi_walk(type_aa_dmi_decode, NULL); 2221 2222 if (wmi_has_guid(WMID_GUID2) && interface) { 2223 if (!has_type_aa && ACPI_FAILURE(WMID_set_capabilities())) { 2224 pr_err("Unable to detect available WMID devices\n"); 2225 return -ENODEV; 2226 } 2227 /* WMID always provides brightness methods */ 2228 interface->capability |= ACER_CAP_BRIGHTNESS; 2229 } else if (!wmi_has_guid(WMID_GUID2) && interface && !has_type_aa) { 2230 pr_err("No WMID device detection method found\n"); 2231 return -ENODEV; 2232 } 2233 2234 if (wmi_has_guid(AMW0_GUID1) && !wmi_has_guid(WMID_GUID1)) { 2235 interface = &AMW0_interface; 2236 2237 if (ACPI_FAILURE(AMW0_set_capabilities())) { 2238 pr_err("Unable to detect available AMW0 devices\n"); 2239 return -ENODEV; 2240 } 2241 } 2242 2243 if (wmi_has_guid(AMW0_GUID1)) 2244 AMW0_find_mailled(); 2245 2246 if (!interface) { 2247 pr_err("No or unsupported WMI interface, unable to load\n"); 2248 return -ENODEV; 2249 } 2250 2251 set_quirks(); 2252 2253 if (dmi_check_system(video_vendor_dmi_table)) 2254 acpi_video_set_dmi_backlight_type(acpi_backlight_vendor); 2255 2256 if (acpi_video_get_backlight_type() != acpi_backlight_vendor) 2257 interface->capability &= ~ACER_CAP_BRIGHTNESS; 2258 2259 if (wmi_has_guid(WMID_GUID3)) { 2260 if (ACPI_FAILURE(acer_wmi_enable_rf_button())) 2261 pr_warn("Cannot enable RF Button Driver\n"); 2262 2263 if (ec_raw_mode) { 2264 if (ACPI_FAILURE(acer_wmi_enable_ec_raw())) { 2265 pr_err("Cannot enable EC raw mode\n"); 2266 return -ENODEV; 2267 } 2268 } else if (ACPI_FAILURE(acer_wmi_enable_lm())) { 2269 pr_err("Cannot enable Launch Manager mode\n"); 2270 return -ENODEV; 2271 } 2272 } else if (ec_raw_mode) { 2273 pr_info("No WMID EC raw mode enable method\n"); 2274 } 2275 2276 if (wmi_has_guid(ACERWMID_EVENT_GUID)) { 2277 err = acer_wmi_input_setup(); 2278 if (err) 2279 return err; 2280 err = acer_wmi_accel_setup(); 2281 if (err && err != -ENODEV) 2282 pr_warn("Cannot enable accelerometer\n"); 2283 } 2284 2285 err = platform_driver_register(&acer_platform_driver); 2286 if (err) { 2287 pr_err("Unable to register platform driver\n"); 2288 goto error_platform_register; 2289 } 2290 2291 acer_platform_device = platform_device_alloc("acer-wmi", -1); 2292 if (!acer_platform_device) { 2293 err = -ENOMEM; 2294 goto error_device_alloc; 2295 } 2296 2297 err = platform_device_add(acer_platform_device); 2298 if (err) 2299 goto error_device_add; 2300 2301 if (wmi_has_guid(WMID_GUID2)) { 2302 interface->debug.wmid_devices = get_wmid_devices(); 2303 err = create_debugfs(); 2304 if (err) 2305 goto error_create_debugfs; 2306 } 2307 2308 /* Override any initial settings with values from the commandline */ 2309 acer_commandline_init(); 2310 2311 return 0; 2312 2313 error_create_debugfs: 2314 platform_device_del(acer_platform_device); 2315 error_device_add: 2316 platform_device_put(acer_platform_device); 2317 error_device_alloc: 2318 platform_driver_unregister(&acer_platform_driver); 2319 error_platform_register: 2320 if (wmi_has_guid(ACERWMID_EVENT_GUID)) 2321 acer_wmi_input_destroy(); 2322 if (has_cap(ACER_CAP_ACCEL)) 2323 acer_wmi_accel_destroy(); 2324 2325 return err; 2326 } 2327 2328 static void __exit acer_wmi_exit(void) 2329 { 2330 if (wmi_has_guid(ACERWMID_EVENT_GUID)) 2331 acer_wmi_input_destroy(); 2332 2333 if (has_cap(ACER_CAP_ACCEL)) 2334 acer_wmi_accel_destroy(); 2335 2336 remove_debugfs(); 2337 platform_device_unregister(acer_platform_device); 2338 platform_driver_unregister(&acer_platform_driver); 2339 2340 pr_info("Acer Laptop WMI Extras unloaded\n"); 2341 return; 2342 } 2343 2344 module_init(acer_wmi_init); 2345 module_exit(acer_wmi_exit); 2346