Skip to content

Commit 6564e5d

Browse files
dtorij-intel
authored andcommitted
platform/x86: x86-android-tablets: convert gpio_keys devices to GPIO references
Now that gpiolib supports software nodes to describe GPIOs, switch the driver away from using GPIO lookup tables for gpio_keys devices to using PROPERTY_ENTRY_GPIO(). Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com> Tested-by: Hans de Goede <hansg@kernel.org> Reviewed-by: Hans de Goede <hansg@kernel.org> Reviewed-by: Andy Shevchenko <andy@kernel.org> Signed-off-by: Hans de Goede <hansg@kernel.org> Link: https://patch.msgid.link/20250920200713.20193-12-hansg@kernel.org Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com>
1 parent 74ff0b6 commit 6564e5d

5 files changed

Lines changed: 177 additions & 136 deletions

File tree

drivers/platform/x86/x86-android-tablets/asus.c

Lines changed: 26 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010

1111
#include <linux/gpio/machine.h>
1212
#include <linux/gpio/property.h>
13-
#include <linux/input.h>
13+
#include <linux/input-event-codes.h>
1414
#include <linux/platform_device.h>
1515

1616
#include "shared-psy-info.h"
@@ -31,17 +31,29 @@ static const struct platform_device_info asus_me176c_tf103c_pdevs[] __initconst
3131
},
3232
};
3333

34-
static const struct x86_gpio_button asus_me176c_tf103c_lid __initconst = {
35-
.button = {
36-
.code = SW_LID,
37-
.active_low = true,
38-
.desc = "lid_sw",
39-
.type = EV_SW,
40-
.wakeup = true,
41-
.debounce_interval = 50,
42-
},
43-
.chip = "INT33FC:02",
44-
.pin = 12,
34+
static const struct software_node asus_me176c_tf103c_gpio_keys_node = {
35+
.name = "lid_sw",
36+
};
37+
38+
static const struct property_entry asus_me176c_tf103c_lid_props[] = {
39+
PROPERTY_ENTRY_U32("linux,input-type", EV_SW),
40+
PROPERTY_ENTRY_U32("linux,code", SW_LID),
41+
PROPERTY_ENTRY_STRING("label", "lid_sw"),
42+
PROPERTY_ENTRY_GPIO("gpios", &baytrail_gpiochip_nodes[2], 12, GPIO_ACTIVE_LOW),
43+
PROPERTY_ENTRY_U32("debounce-interval", 50),
44+
PROPERTY_ENTRY_BOOL("wakeup-source"),
45+
{ }
46+
};
47+
48+
static const struct software_node asus_me176c_tf103c_lid_node = {
49+
.parent = &asus_me176c_tf103c_gpio_keys_node,
50+
.properties = asus_me176c_tf103c_lid_props,
51+
};
52+
53+
static const struct software_node *asus_me176c_tf103c_lid_swnodes[] = {
54+
&asus_me176c_tf103c_gpio_keys_node,
55+
&asus_me176c_tf103c_lid_node,
56+
NULL
4557
};
4658

4759
/* Asus ME176C tablets have an Android factory image with everything hardcoded */
@@ -177,8 +189,7 @@ const struct x86_dev_info asus_me176c_info __initconst = {
177189
.pdev_count = ARRAY_SIZE(asus_me176c_tf103c_pdevs),
178190
.serdev_info = asus_me176c_serdevs,
179191
.serdev_count = ARRAY_SIZE(asus_me176c_serdevs),
180-
.gpio_button = &asus_me176c_tf103c_lid,
181-
.gpio_button_count = 1,
192+
.gpio_button_swnodes = asus_me176c_tf103c_lid_swnodes,
182193
.bat_swnode = &generic_lipo_hv_4v35_battery_node,
183194
.modules = bq24190_modules,
184195
.gpiochip_type = X86_GPIOCHIP_BAYTRAIL,
@@ -301,8 +312,7 @@ const struct x86_dev_info asus_tf103c_info __initconst = {
301312
.i2c_client_count = ARRAY_SIZE(asus_tf103c_i2c_clients),
302313
.pdev_info = asus_me176c_tf103c_pdevs,
303314
.pdev_count = ARRAY_SIZE(asus_me176c_tf103c_pdevs),
304-
.gpio_button = &asus_me176c_tf103c_lid,
305-
.gpio_button_count = 1,
315+
.gpio_button_swnodes = asus_me176c_tf103c_lid_swnodes,
306316
.bat_swnode = &generic_lipo_4v2_battery_node,
307317
.modules = bq24190_modules,
308318
.gpiochip_type = X86_GPIOCHIP_BAYTRAIL,

drivers/platform/x86/x86-android-tablets/core.c

Lines changed: 15 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -152,7 +152,7 @@ static struct i2c_client **i2c_clients;
152152
static struct spi_device **spi_devs;
153153
static struct platform_device **pdevs;
154154
static struct serdev_device **serdevs;
155-
static struct gpio_keys_button *buttons;
155+
static const struct software_node **gpio_button_swnodes;
156156
static const struct software_node *bat_swnode;
157157
static const struct software_node **gpiochip_node_group;
158158
static void (*exit_handler)(void);
@@ -373,7 +373,6 @@ static void x86_android_tablet_remove(struct platform_device *pdev)
373373
platform_device_unregister(pdevs[i]);
374374

375375
kfree(pdevs);
376-
kfree(buttons);
377376

378377
for (i = spi_dev_count - 1; i >= 0; i--)
379378
spi_unregister_device(spi_devs[i]);
@@ -388,6 +387,9 @@ static void x86_android_tablet_remove(struct platform_device *pdev)
388387
if (exit_handler)
389388
exit_handler();
390389

390+
if (gpio_button_swnodes)
391+
software_node_unregister_node_group(gpio_button_swnodes);
392+
391393
if (bat_swnode)
392394
software_node_unregister(bat_swnode);
393395

@@ -514,38 +516,22 @@ static __init int x86_android_tablet_probe(struct platform_device *pdev)
514516
}
515517
}
516518

517-
if (dev_info->gpio_button_count) {
518-
struct gpio_keys_platform_data pdata = { };
519-
struct gpio_desc *gpiod;
519+
if (dev_info->gpio_button_swnodes) {
520+
struct platform_device_info button_info = {
521+
.name = "gpio-keys",
522+
.id = PLATFORM_DEVID_AUTO,
523+
};
520524

521-
buttons = kcalloc(dev_info->gpio_button_count, sizeof(*buttons), GFP_KERNEL);
522-
if (!buttons) {
525+
ret = software_node_register_node_group(dev_info->gpio_button_swnodes);
526+
if (ret < 0) {
523527
x86_android_tablet_remove(pdev);
524-
return -ENOMEM;
525-
}
526-
527-
for (i = 0; i < dev_info->gpio_button_count; i++) {
528-
ret = x86_android_tablet_get_gpiod(dev_info->gpio_button[i].chip,
529-
dev_info->gpio_button[i].pin,
530-
dev_info->gpio_button[i].button.desc,
531-
false, GPIOD_IN, &gpiod);
532-
if (ret < 0) {
533-
x86_android_tablet_remove(pdev);
534-
return ret;
535-
}
536-
537-
buttons[i] = dev_info->gpio_button[i].button;
538-
buttons[i].gpio = desc_to_gpio(gpiod);
539-
/* Release GPIO descriptor so that gpio-keys can request it */
540-
devm_gpiod_put(&x86_android_tablet_device->dev, gpiod);
528+
return ret;
541529
}
542530

543-
pdata.buttons = buttons;
544-
pdata.nbuttons = dev_info->gpio_button_count;
531+
gpio_button_swnodes = dev_info->gpio_button_swnodes;
545532

546-
pdevs[pdev_count] = platform_device_register_data(&pdev->dev, "gpio-keys",
547-
PLATFORM_DEVID_AUTO,
548-
&pdata, sizeof(pdata));
533+
button_info.fwnode = software_node_fwnode(dev_info->gpio_button_swnodes[0]);
534+
pdevs[pdev_count] = platform_device_register_full(&button_info);
549535
if (IS_ERR(pdevs[pdev_count])) {
550536
ret = PTR_ERR(pdevs[pdev_count]);
551537
x86_android_tablet_remove(pdev);

drivers/platform/x86/x86-android-tablets/lenovo.c

Lines changed: 51 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#include <linux/efi.h>
1414
#include <linux/gpio/machine.h>
1515
#include <linux/gpio/property.h>
16+
#include <linux/input-event-codes.h>
1617
#include <linux/mfd/arizona/pdata.h>
1718
#include <linux/mfd/arizona/registers.h>
1819
#include <linux/mfd/intel_soc_pmic.h>
@@ -207,17 +208,34 @@ static const struct x86_serdev_info lenovo_yb1_x90_serdevs[] __initconst = {
207208
},
208209
};
209210

210-
static const struct x86_gpio_button lenovo_yb1_x90_lid __initconst = {
211-
.button = {
212-
.code = SW_LID,
213-
.active_low = true,
214-
.desc = "lid_sw",
215-
.type = EV_SW,
216-
.wakeup = true,
217-
.debounce_interval = 50,
218-
},
219-
.chip = "INT33FF:02",
220-
.pin = 19,
211+
/*
212+
* Software node attached to gpio-keys device representing the LID and
213+
* serving as a parent to software nodes representing individual keys/buttons
214+
* as required by the device tree binding.
215+
*/
216+
static const struct software_node lenovo_lid_gpio_keys_node = {
217+
.name = "lid_sw",
218+
};
219+
220+
static const struct property_entry lenovo_yb1_x90_lid_props[] = {
221+
PROPERTY_ENTRY_U32("linux,input-type", EV_SW),
222+
PROPERTY_ENTRY_U32("linux,code", SW_LID),
223+
PROPERTY_ENTRY_STRING("label", "lid_sw"),
224+
PROPERTY_ENTRY_GPIO("gpios", &cherryview_gpiochip_nodes[2], 19, GPIO_ACTIVE_LOW),
225+
PROPERTY_ENTRY_U32("debounce-interval", 50),
226+
PROPERTY_ENTRY_BOOL("wakeup-source"),
227+
{ }
228+
};
229+
230+
static const struct software_node lenovo_yb1_x90_lid_node = {
231+
.parent = &lenovo_lid_gpio_keys_node,
232+
.properties = lenovo_yb1_x90_lid_props,
233+
};
234+
235+
static const struct software_node *lenovo_yb1_x90_lid_swnodes[] = {
236+
&lenovo_lid_gpio_keys_node,
237+
&lenovo_yb1_x90_lid_node,
238+
NULL
221239
};
222240

223241
static int __init lenovo_yb1_x90_init(struct device *dev)
@@ -246,8 +264,7 @@ const struct x86_dev_info lenovo_yogabook_x90_info __initconst = {
246264
.pdev_count = ARRAY_SIZE(lenovo_yb1_x90_pdevs),
247265
.serdev_info = lenovo_yb1_x90_serdevs,
248266
.serdev_count = ARRAY_SIZE(lenovo_yb1_x90_serdevs),
249-
.gpio_button = &lenovo_yb1_x90_lid,
250-
.gpio_button_count = 1,
267+
.gpio_button_swnodes = lenovo_yb1_x90_lid_swnodes,
251268
.gpiochip_type = X86_GPIOCHIP_CHERRYVIEW,
252269
.init = lenovo_yb1_x90_init,
253270
};
@@ -284,17 +301,25 @@ static const struct software_node lenovo_yoga_tab2_830_1050_bq24190_node = {
284301
.properties = lenovo_yoga_tab2_830_1050_bq24190_props,
285302
};
286303

287-
static const struct x86_gpio_button lenovo_yoga_tab2_830_1050_lid __initconst = {
288-
.button = {
289-
.code = SW_LID,
290-
.active_low = true,
291-
.desc = "lid_sw",
292-
.type = EV_SW,
293-
.wakeup = true,
294-
.debounce_interval = 50,
295-
},
296-
.chip = "INT33FC:02",
297-
.pin = 26,
304+
static const struct property_entry lenovo_yoga_tab2_830_1050_lid_props[] = {
305+
PROPERTY_ENTRY_U32("linux,input-type", EV_SW),
306+
PROPERTY_ENTRY_U32("linux,code", SW_LID),
307+
PROPERTY_ENTRY_STRING("label", "lid_sw"),
308+
PROPERTY_ENTRY_GPIO("gpios", &baytrail_gpiochip_nodes[2], 26, GPIO_ACTIVE_LOW),
309+
PROPERTY_ENTRY_U32("debounce-interval", 50),
310+
PROPERTY_ENTRY_BOOL("wakeup-source"),
311+
{ }
312+
};
313+
314+
static const struct software_node lenovo_yoga_tab2_830_1050_lid_node = {
315+
.parent = &lenovo_lid_gpio_keys_node,
316+
.properties = lenovo_yoga_tab2_830_1050_lid_props,
317+
};
318+
319+
static const struct software_node *lenovo_yoga_tab2_830_1050_lid_swnodes[] = {
320+
&lenovo_lid_gpio_keys_node,
321+
&lenovo_yoga_tab2_830_1050_lid_node,
322+
NULL
298323
};
299324

300325
/* This gets filled by lenovo_yoga_tab2_830_1050_init() */
@@ -422,8 +447,7 @@ const struct x86_dev_info lenovo_yoga_tab2_830_1050_info __initconst = {
422447
.i2c_client_count = ARRAY_SIZE(lenovo_yoga_tab2_830_1050_i2c_clients),
423448
.pdev_info = lenovo_yoga_tab2_830_1050_pdevs,
424449
.pdev_count = ARRAY_SIZE(lenovo_yoga_tab2_830_1050_pdevs),
425-
.gpio_button = &lenovo_yoga_tab2_830_1050_lid,
426-
.gpio_button_count = 1,
450+
.gpio_button_swnodes = lenovo_yoga_tab2_830_1050_lid_swnodes,
427451
.bat_swnode = &generic_lipo_hv_4v35_battery_node,
428452
.modules = bq24190_modules,
429453
.gpiochip_type = X86_GPIOCHIP_BAYTRAIL,
@@ -787,8 +811,7 @@ const struct x86_dev_info lenovo_yoga_tab2_1380_info __initconst = {
787811
.i2c_client_count = ARRAY_SIZE(lenovo_yoga_tab2_1380_i2c_clients),
788812
.pdev_info = lenovo_yoga_tab2_1380_pdevs,
789813
.pdev_count = ARRAY_SIZE(lenovo_yoga_tab2_1380_pdevs),
790-
.gpio_button = &lenovo_yoga_tab2_830_1050_lid,
791-
.gpio_button_count = 1,
814+
.gpio_button_swnodes = lenovo_yoga_tab2_830_1050_lid_swnodes,
792815
.bat_swnode = &generic_lipo_hv_4v35_battery_node,
793816
.modules = lenovo_yoga_tab2_1380_modules,
794817
.gpiochip_type = X86_GPIOCHIP_BAYTRAIL,

0 commit comments

Comments
 (0)