Lenovo IdeaPAD ACPI driver
PATCH 1/1 Lenovo IdeaPAD ACPI driver
--- drivers/platform/x86/Kconfig | 7 + drivers/platform/x86/Makefile | 1 + drivers/platform/x86/ideapad_acpi.c | 284 +++++++++++++++++++++++++++++++++++ 3 files changed, 292 insertions(+), 0 deletions(-) create mode 100644 drivers/platform/x86/ideapad_acpi.c
drivers/platform/x86/Kconfig +7 -0
@@ -219,6 +219,13 @@ config SONYPI_COMPAT ---help--- Build the sonypi driver compatibility code into the sony-laptop driver. +config IDEAPAD_ACPI + tristate "Lenovo IdeaPad ACPI Laptop Extras" + depends on ACPI + depends on RFKILL + help + This is a driver for the rfkill switches on Lenovo IdeaPad netbooks. + config THINKPAD_ACPI tristate "ThinkPad ACPI Laptop Extras" depends on ACPI
drivers/platform/x86/Makefile +1 -0
@@ -15,6 +15,7 @@ obj-$(CONFIG_ACERHDF) += acerhdf.o obj-$(CONFIG_HP_WMI) += hp-wmi.o obj-$(CONFIG_TC1100_WMI) += tc1100-wmi.o obj-$(CONFIG_SONY_LAPTOP) += sony-laptop.o +obj-$(CONFIG_IDEAPAD_ACPI) += ideapad_acpi.o obj-$(CONFIG_THINKPAD_ACPI) += thinkpad_acpi.o obj-$(CONFIG_FUJITSU_LAPTOP) += fujitsu-laptop.o obj-$(CONFIG_PANASONIC_LAPTOP) += panasonic-laptop.o
drivers/platform/x86/ideapad_acpi.c new file +284 -0
284 lines not on this page · raw message
Signature · 6 lines
1.7.2.1 -- David Woodhouse Open Source Technology Centre [email protected] Intel Corporation
Quoted 17 lines · David Woodhouse
Signed-off-by David Woodhouse <[email protected]>---
drivers/platform/x86/Kconfig | 7 +drivers/platform/x86/Makefile| 1 +drivers/platform/x86/ideapad_acpi.c| 284 +++++++++++++++++++++++++++++++++++3 files changed, 292 insertions(+), 0 deletions(-)create mode 100644
drivers/platform/x86/ideapad_acpi.cdrivers/platform/x86/Kconfig +0
-0@@ -219,6 +219,13 @@ config SONYPI_COMPAT---help---
Build the sonypi driver compatibility code into the sony-laptop driver.
drivers/platform/x86/Kconfig config SONYPI_COMPAT · line 228
Quoted 7 lines
drivers/platform/x86/Kconfig +7
-0+config IDEAPAD_ACPI + tristate "Lenovo IdeaPad ACPI Laptop Extras" + depends on ACPI + depends on RFKILL + help + This is a driver for the rfkill switches on Lenovo IdeaPad netbooks. +
I'd suggest to name it ideapad-laptop (IDEAPAD_LAPTOP). We try to use that name for laptop related drivers.
But ... new WMI drivers are named with the *-wmi suffix. So I'm not really sure. Anyway, it's not really important.
Quoted 46 lines
config
THINKPAD_ACPI
tristate "ThinkPad ACPI Laptop Extras"
depends on ACPIdrivers/platform/x86/Makefile +0
-0@@ -15,6 +15,7 @@ obj-$(CONFIG_ACERHDF) += acerhdf.oobj-$(CONFIG_HP_WMI) += hp-wmi.o obj-$(CONFIG_TC1100_WMI) += tc1100-wmi.o obj-$(CONFIG_SONY_LAPTOP) += sony-laptop.o +obj-$(CONFIG_IDEAPAD_ACPI) += ideapad_acpi.o obj-$(CONFIG_THINKPAD_ACPI) += thinkpad_acpi.o obj-$(CONFIG_FUJITSU_LAPTOP) += fujitsu-laptop.o obj-$(CONFIG_PANASONIC_LAPTOP) += panasonic-laptop.o
drivers/platform/x86/ideapad_acpi.c new file +25
-0@@ -0,0 +1,284 @@ +/* +* ideapad_acpi.c - Lenovo IdeaPad ACPI Extras +* +* Copyright © 2010 Intel Corporation +* Copyright © 2010 David Woodhouse <[email protected]> +* +* This program is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License as published by +* the Free Software Foundation; either version 2 of the License, or +* (at your option) any later version. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program; if not, write to the Free Software +* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA +* 02110-1301, USA. +*/ + +#include <linux/kernel.h> +#include <linux/module.h> +#include <linux/init.h>
drivers/platform/x86/ideapad_acpi.c line 35
Quoted 10 lines
drivers/platform/x86/ideapad_acpi.c new file +10
-0+#include <linux/types.h> +#include <acpi/acpi_bus.h> +#include <acpi/acpi_drivers.h> +#include <linux/rfkill.h> + +#define IDEAPAD_DEV_CAMERA 0 +#define IDEAPAD_DEV_WLAN 1 +#define IDEAPAD_DEV_BLUETOOTH 2 +#define IDEAPAD_DEV_3G 3 +#define IDEAPAD_DEV_KILLSW 4
What's DEV_KILLSW ? a global kill switch ?
drivers/platform/x86/ideapad_acpi.c line 41
Quoted 5 lines
drivers/platform/x86/ideapad_acpi.c new file +5
-0+static struct rfkill *ideapad_rfkill[5 ]; + +static const char *ideapad_rfk_names[] = { + "ideapad_camera", "ideapad_wlan", "ideapad_bluetooth", "ideapad_3g", "ideapad_rfkill" +};
Hum, ideapad_camera inside rfkill stuff ?
Quoted 86 lines
drivers/platform/x86/ideapad_acpi.c new file +86
-0+static const int ideapad_rfk_types[] = { + 0, RFKILL_TYPE_WLAN, RFKILL_TYPE_BLUETOOTH, RFKILL_TYPE_WWAN, RFKILL_TYPE_WLAN +}; + +static int ideapad_dev_exists (int device) +{ + acpi_status status; + union acpi_object in_param; + struct acpi_object_list input = { 1, &in_param }; + struct acpi_buffer output; + union acpi_object out_obj; + + output.length = sizeof(out_obj); + output.pointer = &out_obj; + + in_param.type = ACPI_TYPE_INTEGER; + in_param.integer.value = device + 1; + + status = acpi_evaluate_object(NULL, "\\_SB_.DECN", &input, &output); + if (ACPI_FAILURE(status)) { + printk(KERN_WARNING "IdeaPAD \\_SB_.DECN method failed %d. Is this an IdeaPAD?\n", status); + return -ENODEV; + } + if (out_obj.type != ACPI_TYPE_INTEGER) { + printk(KERN_WARNING "IdeaPAD \\_SB_.DECN method returned unexpected type\n"); + return -ENODEV; + } + return out_obj.integer.value; +} + +static int ideapad_dev_get_state (int device) +{ + acpi_status status; + union acpi_object in_param; + struct acpi_object_list input = { 1, &in_param }; + struct acpi_buffer output; + union acpi_object out_obj; + + output.length = sizeof(out_obj); + output.pointer = &out_obj; + + in_param.type = ACPI_TYPE_INTEGER; + in_param.integer.value = device + 1; + + status = acpi_evaluate_object(NULL, "\\_SB_.GECN", &input, &output); + if (ACPI_FAILURE(status)) { + printk(KERN_WARNING "IdeaPAD \\_SB_.GECN method failed %d\n", status); + return -ENODEV; + } + if (out_obj.type != ACPI_TYPE_INTEGER) { + printk(KERN_WARNING "IdeaPAD \\_SB_.GECN method returned unexpected type\n"); + return -ENODEV; + } + return out_obj.integer.value; +} + +static int ideapad_dev_set_state (int device,int state) +{ + acpi_status status; + union acpi_object in_params[2]; + struct acpi_object_list input = { 2, in_params }; + + in_params[0].type = ACPI_TYPE_INTEGER; + in_params[0].integer.value = device + 1; + in_params[1].type = ACPI_TYPE_INTEGER; + in_params[1].integer.value = state; + + status = acpi_evaluate_object(NULL, "\\_SB_.SECN", &input, NULL); + if (ACPI_FAILURE(status)) { + printk(KERN_WARNING "IdeaPAD \\_SB_.SECN method failed %d\n", status); + return -ENODEV; + } + return 0; +} +static ssize_t show_ideapad_cam (struct device *dev, + struct device_attribute *attr, + char *buf) +{ + int state = ideapad_dev_get_state(IDEAPAD_DEV_CAMERA); + if (state < 0) + return state; + + return sprintf(buf, "%d\n", state); +} + +static ssize_t store_ideapad_cam(struct device *dev,
drivers/platform/x86/ideapad_acpi.c line 137
Quoted 10 lines
drivers/platform/x86/ideapad_acpi.c new file +10
-0+ struct device_attribute *attr, + const char *buf, size_t count) +{ + int ret, state; + + if (!count) + return 0; + if (sscanf(buf, "%i", &state) != 1) + return -EINVAL; + ret = ideapad_dev_set_state(IDEAPAD_DEV_CAMERA, state);
What does it do with values other than 1 and 0 ? maybe you could send !!state instead
Quoted 148 lines
drivers/platform/x86/ideapad_acpi.c new file +147
-1+ if (ret < 0) + return ret; + return count; +} + +static DEVICE_ATTR(camera_power, 0644, show_ideapad_cam, store_ideapad_cam); + +static int ideapad_rfk_set (void *data,bool blocked) +{ + int device = (unsigned long)data; + + if (device == IDEAPAD_DEV_KILLSW) + return -EINVAL; + return ideapad_dev_set_state(device, !blocked); +} + +static struct rfkill_ops ideapad_rfk_ops = { + .set_block = ideapad_rfk_set, +}; + +static void ideapad_sync_rfk_state (void ) +{ + int hw_blocked = !ideapad_dev_get_state(IDEAPAD_DEV_KILLSW); + int i; + + rfkill_set_hw_state(ideapad_rfkill[IDEAPAD_DEV_KILLSW], hw_blocked); + for (i = IDEAPAD_DEV_WLAN; i < IDEAPAD_DEV_KILLSW; i++) + if (ideapad_rfkill[i]) + rfkill_set_hw_state(ideapad_rfkill[i], hw_blocked); + if (hw_blocked) + return; + + for (i = IDEAPAD_DEV_WLAN; i < IDEAPAD_DEV_KILLSW; i++) + if (ideapad_rfkill[i]) + rfkill_set_sw_state(ideapad_rfkill[i], !ideapad_dev_get_state(i)); +} + +static int __init ideapad_register_rfkill (struct acpi_device *device,int dev) +{ + int ret; + + ideapad_rfkill[dev] = rfkill_alloc(ideapad_rfk_names[dev], &device->dev, + ideapad_rfk_types[dev], &ideapad_rfk_ops, + (void *)(long)dev); + if (!ideapad_rfkill[dev]) + return -ENOMEM; + + ret = rfkill_register(ideapad_rfkill[dev]); + if (ret) { + rfkill_destroy(ideapad_rfkill[dev]); + return ret; + } + return 0; +} + +static void __exit ideapad_unregister_rfkill(int dev) +{ + if (!ideapad_rfkill[dev]) + return; + + rfkill_unregister(ideapad_rfkill[dev]); + rfkill_destroy(ideapad_rfkill[dev]); +} + +static const struct acpi_device_id ideapad_device_ids[] = { + { "VPC2004", 0}, + { "", 0}, +}; +MODULE_DEVICE_TABLE (acpi, ideapad_device_ids); + +static int ideapad_acpi_add (struct acpi_device *device) +{ + int i; + int devs_present[5]; + + for (i = IDEAPAD_DEV_CAMERA; i < IDEAPAD_DEV_KILLSW; i++) { + devs_present[i] = ideapad_dev_exists(i); + if (devs_present[i] < 0) + return devs_present[i]; + } + + /* The hardware switch is always present */ + devs_present[IDEAPAD_DEV_KILLSW] = 1; + + if (devs_present[IDEAPAD_DEV_CAMERA]) { + int ret = device_create_file(&device->dev, &dev_attr_camera_power); + if (ret) + return ret; + } + + for (i = IDEAPAD_DEV_WLAN; i <= IDEAPAD_DEV_KILLSW; i++) { + if (!devs_present[i]) + continue; + + ideapad_register_rfkill(device, i); + } + ideapad_sync_rfk_state(); + return 0; +} + +static int ideapad_acpi_remove (struct acpi_device *device,int type) +{ + int i; + device_remove_file(&device->dev, &dev_attr_camera_power); + for (i = 0; i < 5; i++) + ideapad_unregister_rfkill(i); + return 0; +} + +static void ideapad_acpi_notify (struct acpi_device *device,u32 event) +{ + ideapad_sync_rfk_state(); +} + +static struct acpi_driver ideapad_acpi_driver = { + .name = "ideapad_acpi", + .class = "IdeaPad", + .ids = ideapad_device_ids, + .ops.add = ideapad_acpi_add, + .ops.remove = ideapad_acpi_remove, + .ops.notify = ideapad_acpi_notify, + .owner = THIS_MODULE, +}; + + +static int __init ideapad_acpi_module_init (void ) +{ + acpi_bus_register_driver(&ideapad_acpi_driver); + + return 0; +} + + +static void ideapad_acpi_module_exit (void ) +{ + acpi_bus_unregister_driver(&ideapad_acpi_driver); + +} +/* Support only the S10-3 for now, until we verify other models */ +MODULE_ALIAS ("dmi:bvnLENOVO*:pnS10-3:*" ); + +MODULE_AUTHOR ("David Woodhouse <[email protected]>" ); +MODULE_DESCRIPTION ("IdeaPad ACPI Extras" ); +MODULE_LICENSE ("GPL" ); + +module_init (ideapad_acpi_module_init); +module_exit (ideapad_acpi_module_exit); --
Quoted 2 lines
1.7.2.1
Also, it would be great not to use the "there will only be one of these device" anti-pattern.
Of course, it will work, but I think it's better to get a clean, fully-reentrant driver.
Signature · 2 lines
Corentin Chary http://xf.iksaif.net
Quoted 2 lines · Corentin Chary
I'd suggest to name it ideapad-laptop (
IDEAPAD_LAPTOP). We try to use that name for laptop related drivers.
OK.
Quoted 2 lines
But ... new WMI drivers are named with the *-wmi suffix. So I'm not really sure. Anyway, it's not really important.
It doesn't do any WMI stuff... yet. I was looking at your discussion from April and hoping you'd help make it work...
Quoted 1 line
What's
DEV_KILLSW? a global kill switch ?
Yes, that's a physical switch on the side of the laptop which automatically kills all of wifi, bluetooth and 3g.
Quoted 7 lines
drivers/platform/x86/ideapad_acpi.c line 41
Quoted 5 lines
drivers/platform/x86/ideapad_acpi.c new file +5
-0+static struct rfkill *ideapad_rfkill[5 ]; + +static const char *ideapad_rfk_names[] = { +"ideapad_camera" ,"ideapad_wlan" ,"ideapad_bluetooth" ,"ideapad_3g" ,"ideapad_rfkill" +};Hum,
ideapad_camerainside rfkill stuff ?
Element zero of the array doesn't get used. It was that or add a bunch of '-1' in various places. I am entirely unconvinced which I like least. It's the same for the types:
Quoted 3 lines
Quoted 3 lines
drivers/platform/x86/ideapad_acpi.c new file +3
-0+static const int ideapad_rfk_types[] = { +0 ,RFKILL_TYPE_WLAN ,RFKILL_TYPE_BLUETOOTH ,RFKILL_TYPE_WWAN ,RFKILL_TYPE_WLAN +};
...
Quoted 6 lines
Quoted 6 lines
drivers/platform/x86/ideapad_acpi.c new file +6
-0+static ssize_t store_ideapad_cam (struct device *dev, +struct device_attribute *attr, +const char *buf,size_t count) +{ +int ret, state; +
Quoted 8 lines
drivers/platform/x86/ideapad_acpi.c line 137
Quoted 5 lines
drivers/platform/x86/ideapad_acpi.c new file +5
-0+if (!count) +return 0 ; +if (sscanf (buf,"%i" , &state) !=1 ) +return -EINVAL ; + ret =ideapad_dev_set_state (IDEAPAD_DEV_CAMERA , state);What does it do with values other than 1 and 0 ? maybe you could send !!state instead
I could do. The ACPI code does so for itself anyway:
If (Arg1)
{
Store (0x01, Local1)
}
Else
{
Store (0x00, Local1)
}Quoted 4 lines
Also, it would be great not to use the "there will only be one of these device" anti-pattern.
Of course, it will work, but I think it's better to get a clean, fully-reentrant driver.
Agreed. Will fix.
Signature · 2 lines
David Woodhouse Open Source Technology Centre [email protected] Intel Corporation
Quoted 11 lines · David Woodhouse
Quoted 2 lines · Corentin Chary
I'd suggest to name it ideapad-laptop (
IDEAPAD_LAPTOP). We try to use that name for laptop related drivers.OK.
Quoted 2 lines
But ... new WMI drivers are named with the *-wmi suffix. So I'm not really sure. Anyway, it's not really important.
It doesn't do any WMI stuff... yet. I was looking at your discussion from April and hoping you'd help make it work...
I'd suggest you to read http://lwn.net/Articles/391230/ :)
Quoted 47 lines
Quoted 1 line
What's
DEV_KILLSW? a global kill switch ?Yes, that's a physical switch on the side of the laptop which automatically kills all of wifi, bluetooth and 3g.
Quoted 7 lines
drivers/platform/x86/ideapad_acpi.c line 41
Quoted 5 lines
drivers/platform/x86/ideapad_acpi.c new file +5
-0+static struct rfkill *ideapad_rfkill[5 ]; + +static const char *ideapad_rfk_names[] = { + "ideapad_camera", "ideapad_wlan", "ideapad_bluetooth", "ideapad_3g", "ideapad_rfkill" +};Hum,
ideapad_camerainside rfkill stuff ?Element zero of the array doesn't get used. It was that or add a bunch of '-1' in various places. I am entirely unconvinced which I like least. It's the same for the types:
Quoted 3 lines
Quoted 3 lines
drivers/platform/x86/ideapad_acpi.c new file +3
-0+static const int ideapad_rfk_types[] = { + 0, RFKILL_TYPE_WLAN, RFKILL_TYPE_BLUETOOTH, RFKILL_TYPE_WWAN, RFKILL_TYPE_WLAN +};...
Quoted 6 lines
Quoted 6 lines
drivers/platform/x86/ideapad_acpi.c new file +6
-0+static ssize_t store_ideapad_cam (struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + int ret, state; +Quoted 8 lines
Quoted 5 lines
+ if (!count)
+ return 0;
+ if (sscanf(buf, "%i", &state)!= 1)
+ return-EINVAL;
+ ret =ideapad_dev_set_state(IDEAPAD_DEV_CAMERA, state);What does it do with values other than 1 and 0 ? maybe you could send !!state instead
I could do. The ACPI code does so for itself anyway:
If (Arg1)
{
Store (0x01, Local1)
}
Else
{
Store (0x00, Local1)
}
Quoted 6 lines
Quoted 4 lines
Also, it would be great not to use the "there will only be one of these device" anti-pattern.
Of course, it will work, but I think it's better to get a clean, fully-reentrant driver.Agreed. Will fix.
Alan did a great work on that for eeepc-laptop, and the new eeepc-wmi should be clean.
You can take a look a these.
And you should probably make it a platform driver (being the parent of acpi, wmi, input, backlight, rfkill, etc..).
Is there a lot of thing hidden in ACPI / WMI on these models (like hotkeys, backlight, light sensors) ?
Thanks,
Signature · 2 lines
Corentin Chary http://xf.iksaif.net
Quoted 7 lines · Corentin Chary
Quoted 6 lines · David Woodhouse
Quoted 2 lines · Corentin Chary
I'd suggest to name it ideapad-laptop (
IDEAPAD_LAPTOP). We try to use that name for laptop related drivers.OK.
Quoted 7 lines
Quoted 5 lines
Quoted 2 lines
But ... new WMI drivers are named with the *-wmi suffix. So I'm not really sure. Anyway, it's not really important.
It doesn't do any WMI stuff... yet. I was looking at your discussion from April and hoping you'd help make it work...
I'd suggest you to read http://lwn.net/Articles/391230/ :)
Ah, thanks. I'd seen Matthew's article on basic ACPI drivers, but hadn't seen this one.
Quoted 2 lines
And you should probably make it a platform driver (being the parent of acpi, wmi, input, backlight, rfkill, etc..).
I had faked a platform device to start with, but got rid of it as soon as I had the acpi_device to use instead.
Quoted 2 lines
Is there a lot of thing hidden in ACPI / WMI on these models (like hotkeys, backlight, light sensors) ?
I think so, yes. My primary focus was the rfkill, which was breaking wireless connectivity unless we have a way to turn it off -- but now I'm here I may as well see what else I can do with it.
Signature · 2 lines
David Woodhouse Open Source Technology Centre [email protected] Intel Corporation
Quoted 5 lines · Corentin Chary
And you should probably make it a platform driver (being the parent of acpi, wmi, input, backlight, rfkill, etc..).
Is there a lot of thing hidden in ACPI / WMI on these models (like hotkeys, backlight, light sensors) ?
I hooked up something (below) to dump the AE or IO WMI blocks each time we get a notification on the VPC2004 device. Although the notification happens when we press a key, nothing ever changes in either of them.
I *did* notice that we're actually getting proper keycodes for the hotkeys though, so for now I've lost what little interest I already had in doing anything with WMI. If anyone (Florian?) wants to do more, I'd be happy to do some testing.
As I said, my main reason for looking at this was to implement the rkfill support, without which some people can't get the wireless working on these devices at all (without booting to Windows to unblock it). And that much is working in git://git.infradead.org/~dwmw2/ideapad-2.6.git
drivers/platform/x86/ideapad-wmi.c +39 -0
@@ -28,6 +28,10 @@#include <acpi/acpi_drivers.h> #include <linux/rfkill.h> +#define IDEAPAD_EVENT_GUID "ABBC0F20-8EA1-11D1-00A0-C90629100000" +#define IDEAPAD_IO_GUID "ABBC0F40-8EA1-11D1-00A0-C90629100000" +#define IDEAPAD_AE_GUID "05901221-D566-11D1-B2F0-00A0C9062910" +#define IDEAPAD_DEV_CAMERA 0#define IDEAPAD_DEV_WLAN 1#define IDEAPAD_DEV_BLUETOOTH 2
@@ -268,9 +272,44 @@ static int ideapad_acpi_remove(struct acpi_device *adevice, int type)return 0 ; } +static int oldlen; +static unsigned char oldresponse[4096 ]; +static void ideapad_acpi_notify (struct acpi_device *adevice,u32 event) { +struct acpi_buffer response = {ACPI_ALLOCATE_BUFFER ,NULL }; +union acpi_object *obj; +acpi_status status; +ideapad_sync_rfk_state (adevice); + + status =wmi_query_block (IDEAPAD_AE_GUID ,1 , &response); +if (ACPI_FAILURE (status)) +return ; + + obj = response.pointer; +if (obj && obj->type ==ACPI_TYPE_BUFFER ) { +int i; +#if 1 +for (i=0 ; i<obj->buffer.length; i++) { +if (!(i&0xf )) { +if (i) +printk ("\n" ); +printk (KERN_INFO "%04x:" , i); + } +printk (" %02x" , ((unsigned char *)obj->buffer.pointer)[i]); + } +printk ("\n" ); +#endif +for (i=0 ; i < obj->buffer.length && i < oldlen; i++) { +if (oldresponse[i] != obj->buffer.pointer[i]) +printk (KERN_INFO "Byte %04x: %02x->%02x\n" , + i, oldresponse[i], obj->buffer.pointer[i]); + } + oldlen =min (sizeof (oldresponse), obj->buffer.length); +memcpy (oldresponse, obj->buffer.pointer, oldlen); + } +kfree (obj); }static struct acpi_driver ideapad_acpi_driver = {
Signature · 2 lines
David Woodhouse Open Source Technology Centre [email protected] Intel Corporation
Quoted 10 lines · David Woodhouse
Quoted 5 lines · Corentin Chary
And you should probably make it a platform driver (being the parent of acpi, wmi, input, backlight, rfkill, etc..).
Is there a lot of thing hidden in ACPI / WMI on these models (like hotkeys, backlight, light sensors) ?
I hooked up something (below) to dump the AE or IO WMI blocks each time we get a notification on the VPC2004 device. Although the notification happens when we press a key, nothing ever changes in either of them.
They is probably something interesting in the u32 event var. To get wmi events, you need to use wmi_install_notify_handler.
For example, the hardware rfkill state may change due to some keypress, and an event may be sent via acpi or wmi, but if you don't catch it, the rfkill class won't be updated.
Could you send the output of acpidump ?
Quoted 4 lines
I *did* notice that we're actually getting proper keycodes for the hotkeys though, so for now I've lost what little interest I already had in doing anything with WMI. If anyone (Florian?) wants to do more, I'd be happy to do some testing.
keycodes are sent from the keyboard input device for all specials keys ? (especially Fn+Fx keys) ?
Thanks,
Signature · 2 lines
Corentin Chary http://xf.iksaif.net
Quoted 5 lines · Corentin Chary
Quoted 4 lines · David Woodhouse
Quoted 3 lines · Corentin Chary
And you should probably make it a platform driver (being the parent of acpi, wmi, input, backlight, rfkill, etc..).
Quoted 8 lines
Quoted 6 lines
Quoted 2 lines
Is there a lot of thing hidden in ACPI / WMI on these models (like hotkeys, backlight, light sensors) ?
I hooked up something (below) to dump the AE or IO WMI blocks each time we get a notification on the VPC2004 device. Although the notification happens when we press a key, nothing ever changes in either of them.
They is probably something interesting in the u32 event var.
It's always 0x80.
Quoted 1 line
To get wmi events, you need to use
wmi_install_notify_handler.
I didn't bother hooking that up -- according to the discussion back in April, the WMI is never triggered.
http://www.mail-archive.com/[email protected]/msg00034.html
Quoted 3 lines
For example, the hardware rfkill state may change due to some keypress, and an event may be sent via acpi or wmi, but if you don't catch it, the rfkill class won't be updated.
The notify gets called then too, and we resync the rfkill state.
Quoted 1 line
Could you send the output of acpidump ?
Attached to http://bugs.meego.com/show_bug.cgi?id=4086 --
http://bugs.meego.com/attachment.cgi?id=1860
It's much the same as what you were looking at before on the S10-3t, as far as I can tell.
Quoted 7 lines
Quoted 4 lines
I *did* notice that we're actually getting proper keycodes for the hotkeys though, so for now I've lost what little interest I already had in doing anything with WMI. If anyone (Florian?) wants to do more, I'd be happy to do some testing.
keycodes are sent from the keyboard input device for all specials keys ? (especially Fn+Fx keys) ?
All but the external display hotkey.
The brightness up/down (Fn-up, Fn-down) don't do anything but they do report:
[10608.863641] atkbd.c: Unknown key pressed (translated set 2, code 0xb9 on isa0060/serio0). [10608.863655] atkbd.c: Use 'setkeycodes e039 <keycode>' to make it known. [10609.002143] atkbd.c: Unknown key released (translated set 2, code 0xb9 on isa0060/serio0). [10609.002157] atkbd.c: Use 'setkeycodes e039 <keycode>' to make it known. [10609.225721] atkbd.c: Unknown key pressed (translated set 2, code 0xba on isa0060/serio0). [10609.225735] atkbd.c: Use 'setkeycodes e03a <keycode>' to make it known. [10609.332264] atkbd.c: Unknown key released (translated set 2, code 0xba on isa0060/serio0). [10609.332278] atkbd.c: Use 'setkeycodes e03a <keycode>' to make it known.
The camera enable/disable (Fn-Esc) toggles the camera power (which is also readable/writable through sysfs with my driver) and also reports:
[10633.222832] atkbd.c: Unknown key pressed (translated set 2, code 0xf1 on isa0060/serio0). [10633.222846] atkbd.c: Use 'setkeycodes e071 <keycode>' to make it known. [10633.329105] atkbd.c: Unknown key released (translated set 2, code 0xf1 on isa0060/serio0). [10633.329119] atkbd.c: Use 'setkeycodes e071 <keycode>' to make it known. [10633.451208] usb 1-8: USB disconnect, address 5
The sleep button (Fn-F1) just puts it to sleep; that'll be reported through a separate ACPI event. I haven't investigated but I assume that's working correctly.
The 'display off' button (Fn-F2) works and:
[10788.130877] atkbd.c: Unknown key pressed (translated set 2, code 0x83 on isa0060/serio0). [10788.130891] atkbd.c: Use 'setkeycodes e003 <keycode>' to make it known. [10788.269195] atkbd.c: Unknown key released (translated set 2, code 0x83 on isa0060/serio0). [10788.269209] atkbd.c: Use 'setkeycodes e003 <keycode>' to make it known.
What I assume is the external display key (Fn-F3) seems to do nothing, whether I have an external display connected or not. If I connect an external display (even if it's powered off), X switches over to it automatically. That's probably just X under MeeGo doing that though.
Fn-F4 has no special marking
The rfkill hotkey (Fn-F5) which under Windows just brings up the Lenovo GUI tool, does nothing except:
[10835.095618] atkbd.c: Unknown key pressed (translated set 2, code 0x81 on isa0060/serio0). [10835.095631] atkbd.c: Use 'setkeycodes e001 <keycode>' to make it known. [10835.233979] atkbd.c: Unknown key released (translated set 2, code 0x81 on isa0060/serio0). [10835.233994] atkbd.c: Use 'setkeycodes e001 <keycode>' to make it known.
What looks like a 'trackpad kill' (Fn-F6) just does:
[10910.931021] atkbd.c: Unknown key pressed (translated set 2, code 0xf2 on isa0060/serio0). [10910.931036] atkbd.c: Use 'setkeycodes e072 <keycode>' to make it known. [10911.048135] atkbd.c: Unknown key released (translated set 2, code 0xf2 on isa0060/serio0). [10911.048148] atkbd.c: Use 'setkeycodes e072 <keycode>' to make it known.
The multimedia keys on Fn-F{7,8,9,10} seems to be generating 'known' keycodes which don't cause a complaint, although they don't seem to show up as anything useful in 'xev'.
[11135.784840] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11135374] [11135.789916] drivers/input/serio/i8042.c: 22 <- i8042 (interrupt, 0, 1) [11135379] [11135.901911] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11135491] [11135.907035] drivers/input/serio/i8042.c: a2 <- i8042 (interrupt, 0, 1) [11135497] [11135.949906] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11135539] [11135.954976] drivers/input/serio/i8042.c: 24 <- i8042 (interrupt, 0, 1) [11135544] [11136.125383] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11135715] [11136.130516] drivers/input/serio/i8042.c: a4 <- i8042 (interrupt, 0, 1) [11135720] [11136.395678] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11135985] [11136.400910] drivers/input/serio/i8042.c: 10 <- i8042 (interrupt, 0, 1) [11135990] [11136.523555] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11136113] [11136.528676] drivers/input/serio/i8042.c: 90 <- i8042 (interrupt, 0, 1) [11136118] [11136.864389] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11136454] [11136.869477] drivers/input/serio/i8042.c: 19 <- i8042 (interrupt, 0, 1) [11136459] [11136.944201] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11136534] [11136.949322] drivers/input/serio/i8042.c: 99 <- i8042 (interrupt, 0, 1) [11136539]
If I press and hold the Fn key, after a while I get a stream of
[11231.859281] drivers/input/serio/i8042.c: e0 <- i8042 (interrupt, 0, 1) [11231449] [11231.864363] drivers/input/serio/i8042.c: 63 <- i8042 (interrupt, 0, 1) [11231454]
Signature · 2 lines
David Woodhouse Open Source Technology Centre [email protected] Intel Corporation