Message ID | 1472628817-3145-1-git-send-email-wnhuang@google.com (mailing list archive) |
---|---|
State | Not Applicable, archived |
Headers | show |
On 三, 2016-08-31 at 15:33 +0800, Wei-Ning Huang wrote: > From: Wei-Ning Huang <wnhuang@chromium.org> > > ACPI PNP device HID 'PNP0C60' is a device that indicates tablet mode > status. Add support for mapping this device to the SW_TABLET_MODE > input > event. > > Signed-off-by: Wei-Ning Huang <wnhuang@chromium.org> > --- > drivers/acpi/button.c | 36 ++++++++++++++++++++++++++++++++++++ > 1 file changed, 36 insertions(+) > > diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c > index 148f4e5..50e9de6 100644 > --- a/drivers/acpi/button.c > +++ b/drivers/acpi/button.c > @@ -53,6 +53,11 @@ > #define ACPI_BUTTON_DEVICE_NAME_LID "Lid Switch" > #define ACPI_BUTTON_TYPE_LID 0x05 > > +#define ACPI_BUTTON_SUBCLASS_TABLET "tablet" > +#define ACPI_BUTTON_HID_TABLET "PNP0C60" > +#define ACPI_BUTTON_DEVICE_NAME_TABLET "Tablet Mode Switch" > +#define ACPI_BUTTON_TYPE_TABLET 0x07 > + > #define ACPI_BUTTON_LID_INIT_IGNORE 0x00 > #define ACPI_BUTTON_LID_INIT_OPEN 0x01 > #define ACPI_BUTTON_LID_INIT_METHOD 0x02 > @@ -70,6 +75,7 @@ static const struct acpi_device_id > button_device_ids[] = { > {ACPI_BUTTON_HID_SLEEPF, 0}, > {ACPI_BUTTON_HID_POWER, 0}, > {ACPI_BUTTON_HID_POWERF, 0}, > + {ACPI_BUTTON_HID_TABLET, 0}, > {"", 0}, > }; > MODULE_DEVICE_TABLE(acpi, button_device_ids); > @@ -305,6 +311,23 @@ static void acpi_lid_initialize_state(struct > acpi_device *device) > } > } > > +static int acpi_tablet_send_state(struct acpi_device *device) > +{ > + struct acpi_button *button = acpi_driver_data(device); > + unsigned long long state; > + acpi_status status; > + > + status = acpi_evaluate_integer(device->handle, "_TBL", NULL, > &state); Control methods with prefix "_" suggests this is an ACPI predefined control method, but I can not find it in ACPI spec 6.1. Can you illustrate me where I can find the definition of _TBL? thanks, rui > + if (ACPI_FAILURE(status)) > + return -ENODEV; > + > + /* input layer checks if event is redundant */ > + input_report_switch(button->input, SW_TABLET_MODE, state); > + input_sync(button->input); > + > + return 0; > +} > + > static void acpi_button_notify(struct acpi_device *device, u32 > event) > { > struct acpi_button *button = acpi_driver_data(device); > @@ -318,6 +341,8 @@ static void acpi_button_notify(struct acpi_device > *device, u32 event) > input = button->input; > if (button->type == ACPI_BUTTON_TYPE_LID) { > acpi_lid_update_state(device); > + } else if (button->type == ACPI_BUTTON_TYPE_TABLET) > { > + acpi_tablet_send_state(device); > } else { > int keycode; > > @@ -407,6 +432,11 @@ static int acpi_button_add(struct acpi_device > *device) > strcpy(name, ACPI_BUTTON_DEVICE_NAME_LID); > sprintf(class, "%s/%s", > ACPI_BUTTON_CLASS, > ACPI_BUTTON_SUBCLASS_LID); > + } else if (!strcmp(hid, ACPI_BUTTON_HID_TABLET)) { > + button->type = ACPI_BUTTON_TYPE_TABLET; > + strcpy(name, ACPI_BUTTON_DEVICE_NAME_TABLET); > + sprintf(class, "%s/%s", > + ACPI_BUTTON_CLASS, > ACPI_BUTTON_SUBCLASS_TABLET); > } else { > printk(KERN_ERR PREFIX "Unsupported hid [%s]\n", > hid); > error = -ENODEV; > @@ -437,6 +467,10 @@ static int acpi_button_add(struct acpi_device > *device) > case ACPI_BUTTON_TYPE_LID: > input_set_capability(input, EV_SW, SW_LID); > break; > + > + case ACPI_BUTTON_TYPE_TABLET: > + input_set_capability(input, EV_SW, SW_TABLET_MODE); > + break; > } > > error = input_register_device(input); > @@ -450,6 +484,8 @@ static int acpi_button_add(struct acpi_device > *device) > */ > lid_device = device; > } > + if (button->type == ACPI_BUTTON_TYPE_TABLET) > + acpi_tablet_send_state(device); > > printk(KERN_INFO PREFIX "%s [%s]\n", name, > acpi_device_bid(device)); > return 0; -- To unsubscribe from this list: send the line "unsubscribe linux-acpi" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Wed, Aug 31, 2016 at 4:01 PM, Zhang Rui <rui.zhang@intel.com> wrote: > On 三, 2016-08-31 at 15:33 +0800, Wei-Ning Huang wrote: >> From: Wei-Ning Huang <wnhuang@chromium.org> >> >> ACPI PNP device HID 'PNP0C60' is a device that indicates tablet mode >> status. Add support for mapping this device to the SW_TABLET_MODE >> input >> event. >> >> Signed-off-by: Wei-Ning Huang <wnhuang@chromium.org> >> --- >> drivers/acpi/button.c | 36 ++++++++++++++++++++++++++++++++++++ >> 1 file changed, 36 insertions(+) >> >> diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c >> index 148f4e5..50e9de6 100644 >> --- a/drivers/acpi/button.c >> +++ b/drivers/acpi/button.c >> @@ -53,6 +53,11 @@ >> #define ACPI_BUTTON_DEVICE_NAME_LID "Lid Switch" >> #define ACPI_BUTTON_TYPE_LID 0x05 >> >> +#define ACPI_BUTTON_SUBCLASS_TABLET "tablet" >> +#define ACPI_BUTTON_HID_TABLET "PNP0C60" >> +#define ACPI_BUTTON_DEVICE_NAME_TABLET "Tablet Mode Switch" >> +#define ACPI_BUTTON_TYPE_TABLET 0x07 >> + >> #define ACPI_BUTTON_LID_INIT_IGNORE 0x00 >> #define ACPI_BUTTON_LID_INIT_OPEN 0x01 >> #define ACPI_BUTTON_LID_INIT_METHOD 0x02 >> @@ -70,6 +75,7 @@ static const struct acpi_device_id >> button_device_ids[] = { >> {ACPI_BUTTON_HID_SLEEPF, 0}, >> {ACPI_BUTTON_HID_POWER, 0}, >> {ACPI_BUTTON_HID_POWERF, 0}, >> + {ACPI_BUTTON_HID_TABLET, 0}, >> {"", 0}, >> }; >> MODULE_DEVICE_TABLE(acpi, button_device_ids); >> @@ -305,6 +311,23 @@ static void acpi_lid_initialize_state(struct >> acpi_device *device) >> } >> } >> >> +static int acpi_tablet_send_state(struct acpi_device *device) >> +{ >> + struct acpi_button *button = acpi_driver_data(device); >> + unsigned long long state; >> + acpi_status status; >> + >> + status = acpi_evaluate_integer(device->handle, "_TBL", NULL, >> &state); > > Control methods with prefix "_" suggests this is an ACPI predefined > control method, but I can not find it in ACPI spec 6.1. > Can you illustrate me where I can find the definition of _TBL? Sorry, I'm not very familiar with ACPI's control method. '_TBL' is not a predefined ACPI control method according to the ACPI 6.1 spec. Maybe I should change it to '_LID'? As a tablet switch is sort of a 'inverted' lid switch. Wei-Ning > > thanks, > rui >> + if (ACPI_FAILURE(status)) >> + return -ENODEV; >> + >> + /* input layer checks if event is redundant */ >> + input_report_switch(button->input, SW_TABLET_MODE, state); >> + input_sync(button->input); >> + >> + return 0; >> +} >> + >> static void acpi_button_notify(struct acpi_device *device, u32 >> event) >> { >> struct acpi_button *button = acpi_driver_data(device); >> @@ -318,6 +341,8 @@ static void acpi_button_notify(struct acpi_device >> *device, u32 event) >> input = button->input; >> if (button->type == ACPI_BUTTON_TYPE_LID) { >> acpi_lid_update_state(device); >> + } else if (button->type == ACPI_BUTTON_TYPE_TABLET) >> { >> + acpi_tablet_send_state(device); >> } else { >> int keycode; >> >> @@ -407,6 +432,11 @@ static int acpi_button_add(struct acpi_device >> *device) >> strcpy(name, ACPI_BUTTON_DEVICE_NAME_LID); >> sprintf(class, "%s/%s", >> ACPI_BUTTON_CLASS, >> ACPI_BUTTON_SUBCLASS_LID); >> + } else if (!strcmp(hid, ACPI_BUTTON_HID_TABLET)) { >> + button->type = ACPI_BUTTON_TYPE_TABLET; >> + strcpy(name, ACPI_BUTTON_DEVICE_NAME_TABLET); >> + sprintf(class, "%s/%s", >> + ACPI_BUTTON_CLASS, >> ACPI_BUTTON_SUBCLASS_TABLET); >> } else { >> printk(KERN_ERR PREFIX "Unsupported hid [%s]\n", >> hid); >> error = -ENODEV; >> @@ -437,6 +467,10 @@ static int acpi_button_add(struct acpi_device >> *device) >> case ACPI_BUTTON_TYPE_LID: >> input_set_capability(input, EV_SW, SW_LID); >> break; >> + >> + case ACPI_BUTTON_TYPE_TABLET: >> + input_set_capability(input, EV_SW, SW_TABLET_MODE); >> + break; >> } >> >> error = input_register_device(input); >> @@ -450,6 +484,8 @@ static int acpi_button_add(struct acpi_device >> *device) >> */ >> lid_device = device; >> } >> + if (button->type == ACPI_BUTTON_TYPE_TABLET) >> + acpi_tablet_send_state(device); >> >> printk(KERN_INFO PREFIX "%s [%s]\n", name, >> acpi_device_bid(device)); >> return 0;
On Wed, Aug 31, 2016 at 10:52 AM, Wei-Ning Huang <wnhuang@google.com> wrote: > On Wed, Aug 31, 2016 at 4:01 PM, Zhang Rui <rui.zhang@intel.com> wrote: >> On 三, 2016-08-31 at 15:33 +0800, Wei-Ning Huang wrote: >>> From: Wei-Ning Huang <wnhuang@chromium.org> >>> >>> ACPI PNP device HID 'PNP0C60' is a device that indicates tablet mode >>> status. Add support for mapping this device to the SW_TABLET_MODE >>> input >>> event. >>> >>> Signed-off-by: Wei-Ning Huang <wnhuang@chromium.org> >>> --- >>> drivers/acpi/button.c | 36 ++++++++++++++++++++++++++++++++++++ >>> 1 file changed, 36 insertions(+) >>> >>> diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c >>> index 148f4e5..50e9de6 100644 >>> --- a/drivers/acpi/button.c >>> +++ b/drivers/acpi/button.c >>> @@ -53,6 +53,11 @@ >>> #define ACPI_BUTTON_DEVICE_NAME_LID "Lid Switch" >>> #define ACPI_BUTTON_TYPE_LID 0x05 >>> >>> +#define ACPI_BUTTON_SUBCLASS_TABLET "tablet" >>> +#define ACPI_BUTTON_HID_TABLET "PNP0C60" >>> +#define ACPI_BUTTON_DEVICE_NAME_TABLET "Tablet Mode Switch" >>> +#define ACPI_BUTTON_TYPE_TABLET 0x07 >>> + >>> #define ACPI_BUTTON_LID_INIT_IGNORE 0x00 >>> #define ACPI_BUTTON_LID_INIT_OPEN 0x01 >>> #define ACPI_BUTTON_LID_INIT_METHOD 0x02 >>> @@ -70,6 +75,7 @@ static const struct acpi_device_id >>> button_device_ids[] = { >>> {ACPI_BUTTON_HID_SLEEPF, 0}, >>> {ACPI_BUTTON_HID_POWER, 0}, >>> {ACPI_BUTTON_HID_POWERF, 0}, >>> + {ACPI_BUTTON_HID_TABLET, 0}, >>> {"", 0}, >>> }; >>> MODULE_DEVICE_TABLE(acpi, button_device_ids); >>> @@ -305,6 +311,23 @@ static void acpi_lid_initialize_state(struct >>> acpi_device *device) >>> } >>> } >>> >>> +static int acpi_tablet_send_state(struct acpi_device *device) >>> +{ >>> + struct acpi_button *button = acpi_driver_data(device); >>> + unsigned long long state; >>> + acpi_status status; >>> + >>> + status = acpi_evaluate_integer(device->handle, "_TBL", NULL, >>> &state); >> >> Control methods with prefix "_" suggests this is an ACPI predefined >> control method, but I can not find it in ACPI spec 6.1. >> Can you illustrate me where I can find the definition of _TBL? > > Sorry, I'm not very familiar with ACPI's control method. So apparently you don't really know what the patch you've posted is doing. > '_TBL' is not a predefined ACPI control method according to the ACPI 6.1 spec. > Maybe I should change it to '_LID'? As a tablet switch is sort of a > 'inverted' lid switch. Is that _TBL thing documented anywhere? Thanks, Rafael -- To unsubscribe from this list: send the line "unsubscribe linux-acpi" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c index 148f4e5..50e9de6 100644 --- a/drivers/acpi/button.c +++ b/drivers/acpi/button.c @@ -53,6 +53,11 @@ #define ACPI_BUTTON_DEVICE_NAME_LID "Lid Switch" #define ACPI_BUTTON_TYPE_LID 0x05 +#define ACPI_BUTTON_SUBCLASS_TABLET "tablet" +#define ACPI_BUTTON_HID_TABLET "PNP0C60" +#define ACPI_BUTTON_DEVICE_NAME_TABLET "Tablet Mode Switch" +#define ACPI_BUTTON_TYPE_TABLET 0x07 + #define ACPI_BUTTON_LID_INIT_IGNORE 0x00 #define ACPI_BUTTON_LID_INIT_OPEN 0x01 #define ACPI_BUTTON_LID_INIT_METHOD 0x02 @@ -70,6 +75,7 @@ static const struct acpi_device_id button_device_ids[] = { {ACPI_BUTTON_HID_SLEEPF, 0}, {ACPI_BUTTON_HID_POWER, 0}, {ACPI_BUTTON_HID_POWERF, 0}, + {ACPI_BUTTON_HID_TABLET, 0}, {"", 0}, }; MODULE_DEVICE_TABLE(acpi, button_device_ids); @@ -305,6 +311,23 @@ static void acpi_lid_initialize_state(struct acpi_device *device) } } +static int acpi_tablet_send_state(struct acpi_device *device) +{ + struct acpi_button *button = acpi_driver_data(device); + unsigned long long state; + acpi_status status; + + status = acpi_evaluate_integer(device->handle, "_TBL", NULL, &state); + if (ACPI_FAILURE(status)) + return -ENODEV; + + /* input layer checks if event is redundant */ + input_report_switch(button->input, SW_TABLET_MODE, state); + input_sync(button->input); + + return 0; +} + static void acpi_button_notify(struct acpi_device *device, u32 event) { struct acpi_button *button = acpi_driver_data(device); @@ -318,6 +341,8 @@ static void acpi_button_notify(struct acpi_device *device, u32 event) input = button->input; if (button->type == ACPI_BUTTON_TYPE_LID) { acpi_lid_update_state(device); + } else if (button->type == ACPI_BUTTON_TYPE_TABLET) { + acpi_tablet_send_state(device); } else { int keycode; @@ -407,6 +432,11 @@ static int acpi_button_add(struct acpi_device *device) strcpy(name, ACPI_BUTTON_DEVICE_NAME_LID); sprintf(class, "%s/%s", ACPI_BUTTON_CLASS, ACPI_BUTTON_SUBCLASS_LID); + } else if (!strcmp(hid, ACPI_BUTTON_HID_TABLET)) { + button->type = ACPI_BUTTON_TYPE_TABLET; + strcpy(name, ACPI_BUTTON_DEVICE_NAME_TABLET); + sprintf(class, "%s/%s", + ACPI_BUTTON_CLASS, ACPI_BUTTON_SUBCLASS_TABLET); } else { printk(KERN_ERR PREFIX "Unsupported hid [%s]\n", hid); error = -ENODEV; @@ -437,6 +467,10 @@ static int acpi_button_add(struct acpi_device *device) case ACPI_BUTTON_TYPE_LID: input_set_capability(input, EV_SW, SW_LID); break; + + case ACPI_BUTTON_TYPE_TABLET: + input_set_capability(input, EV_SW, SW_TABLET_MODE); + break; } error = input_register_device(input); @@ -450,6 +484,8 @@ static int acpi_button_add(struct acpi_device *device) */ lid_device = device; } + if (button->type == ACPI_BUTTON_TYPE_TABLET) + acpi_tablet_send_state(device); printk(KERN_INFO PREFIX "%s [%s]\n", name, acpi_device_bid(device)); return 0;