diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2019-09-19 14:10:54 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2019-09-19 14:10:54 -0700 |
commit | c6cfaf4f86d9d15e5541adb3bb899d0b80f89ec7 (patch) | |
tree | 4d6906d1ac94afee030934116d304e9a5bbf311f /drivers/input/keyboard | |
parent | Merge tag 'for-linus-5.4-1' of git://github.com/cminyard/linux-ipmi (diff) | |
parent | Merge branch 'next' into for-linus (diff) | |
download | linux-dev-c6cfaf4f86d9d15e5541adb3bb899d0b80f89ec7.tar.xz linux-dev-c6cfaf4f86d9d15e5541adb3bb899d0b80f89ec7.zip |
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input
Pull input updates from Dmitry Torokhov:
- input core allows hardware drivers to specify a [more precise]
timestamp (normally taken in top half) to better track velocity of
contacts
- input_dev instances now support "polling" mode so that drivers could
use the same object for polled and interrupt-driven operation. The
plan is to convert existing drivers and retire input_polled_dev API
- a new driver for the FlySky FS-iA6B RC receiver
- a refresh of BU21013 touchpad driver
- w90x900 keyboard and touchpad drivers are removed as the platform is
gone
- assorted fixes
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input: (45 commits)
Input: sidewinder - make array seq static const, makes object smaller
Input: reset device timestamp on sync
Input: bu21013_ts - switch to using standard touchscreen properties
Input: bu21013_ts - switch to using MT-B (slotted) protocol
Input: bu21013_ts - fix suspend when wake source
Input: bu21013_ts - use interrupt from I2C client
Input: bu21013_ts - remove support for platform data
Input: bu21013_ts - convert to using managed resources
Input: bu21013_ts - remove useless comments
Input: bu21013_ts - annotate supend/resume methods as __maybe_unused
Input: bu21013_ts - rename some variables
Input: bu21013_ts - convert to use GPIO descriptors
ARM: ux500: improve BU21013 touchpad bindings
Input: i8042 - enable wakeup on a stable struct device
Input: soc_button_array - use platform_device_register_resndata()
Input: psmouse - drop all unneeded functions from mouse headers
Input: add support for polling to input devices
Input: wacom_w8001 - allocate additional space for 'phys'
Input: cros_ec_keyb - add back missing mask for event_type
Input: remove dev_err() usage after platform_get_irq()
...
Diffstat (limited to 'drivers/input/keyboard')
22 files changed, 28 insertions, 361 deletions
diff --git a/drivers/input/keyboard/Kconfig b/drivers/input/keyboard/Kconfig index 90e8a7f2f07c..2e6d2887eec1 100644 --- a/drivers/input/keyboard/Kconfig +++ b/drivers/input/keyboard/Kconfig @@ -733,17 +733,6 @@ config KEYBOARD_XTKBD To compile this driver as a module, choose M here: the module will be called xtkbd. -config KEYBOARD_W90P910 - tristate "W90P910 Matrix Keypad support" - depends on ARCH_W90X900 - select INPUT_MATRIXKMAP - help - Say Y here to enable the matrix keypad on evaluation board - based on W90P910. - - To compile this driver as a module, choose M here: the - module will be called w90p910_keypad. - config KEYBOARD_CROS_EC tristate "ChromeOS EC keyboard" select INPUT_MATRIXKMAP diff --git a/drivers/input/keyboard/Makefile b/drivers/input/keyboard/Makefile index 06a0af6efeae..9510325c0c5d 100644 --- a/drivers/input/keyboard/Makefile +++ b/drivers/input/keyboard/Makefile @@ -68,4 +68,3 @@ obj-$(CONFIG_KEYBOARD_TEGRA) += tegra-kbc.o obj-$(CONFIG_KEYBOARD_TM2_TOUCHKEY) += tm2-touchkey.o obj-$(CONFIG_KEYBOARD_TWL4030) += twl4030_keypad.o obj-$(CONFIG_KEYBOARD_XTKBD) += xtkbd.o -obj-$(CONFIG_KEYBOARD_W90P910) += w90p910_keypad.o diff --git a/drivers/input/keyboard/applespi.c b/drivers/input/keyboard/applespi.c index 584289b67fb3..d38398526965 100644 --- a/drivers/input/keyboard/applespi.c +++ b/drivers/input/keyboard/applespi.c @@ -1797,30 +1797,12 @@ static int applespi_probe(struct spi_device *spi) /* set up debugfs entries for touchpad dimensions logging */ applespi->debugfs_root = debugfs_create_dir("applespi", NULL); - if (IS_ERR(applespi->debugfs_root)) { - if (PTR_ERR(applespi->debugfs_root) != -ENODEV) - dev_warn(&applespi->spi->dev, - "Error creating debugfs root entry (%ld)\n", - PTR_ERR(applespi->debugfs_root)); - } else { - struct dentry *ret; - - ret = debugfs_create_bool("enable_tp_dim", 0600, - applespi->debugfs_root, - &applespi->debug_tp_dim); - if (IS_ERR(ret)) - dev_dbg(&applespi->spi->dev, - "Error creating debugfs entry enable_tp_dim (%ld)\n", - PTR_ERR(ret)); - - ret = debugfs_create_file("tp_dim", 0400, - applespi->debugfs_root, applespi, - &applespi_tp_dim_fops); - if (IS_ERR(ret)) - dev_dbg(&applespi->spi->dev, - "Error creating debugfs entry tp_dim (%ld)\n", - PTR_ERR(ret)); - } + + debugfs_create_bool("enable_tp_dim", 0600, applespi->debugfs_root, + &applespi->debug_tp_dim); + + debugfs_create_file("tp_dim", 0400, applespi->debugfs_root, applespi, + &applespi_tp_dim_fops); return 0; } diff --git a/drivers/input/keyboard/bcm-keypad.c b/drivers/input/keyboard/bcm-keypad.c index e1cf63ee148f..2b771c3a5578 100644 --- a/drivers/input/keyboard/bcm-keypad.c +++ b/drivers/input/keyboard/bcm-keypad.c @@ -413,10 +413,8 @@ static int bcm_kp_probe(struct platform_device *pdev) bcm_kp_stop(kp); kp->irq = platform_get_irq(pdev, 0); - if (kp->irq < 0) { - dev_err(&pdev->dev, "no IRQ specified\n"); + if (kp->irq < 0) return -EINVAL; - } error = devm_request_threaded_irq(&pdev->dev, kp->irq, NULL, bcm_kp_isr_thread, diff --git a/drivers/input/keyboard/cros_ec_keyb.c b/drivers/input/keyboard/cros_ec_keyb.c index 38cb6d82d8fe..bef7bee6f05e 100644 --- a/drivers/input/keyboard/cros_ec_keyb.c +++ b/drivers/input/keyboard/cros_ec_keyb.c @@ -226,6 +226,8 @@ static int cros_ec_keyb_work(struct notifier_block *nb, { struct cros_ec_keyb *ckdev = container_of(nb, struct cros_ec_keyb, notifier); + uint8_t mkbp_event_type = ckdev->ec->event_data.event_type & + EC_MKBP_EVENT_TYPE_MASK; u32 val; unsigned int ev_type; @@ -237,7 +239,7 @@ static int cros_ec_keyb_work(struct notifier_block *nb, if (queued_during_suspend && !device_may_wakeup(ckdev->dev)) return NOTIFY_OK; - switch (ckdev->ec->event_data.event_type & EC_MKBP_EVENT_TYPE_MASK) { + switch (mkbp_event_type) { case EC_MKBP_EVENT_KEY_MATRIX: pm_wakeup_event(ckdev->dev, 0); @@ -264,7 +266,7 @@ static int cros_ec_keyb_work(struct notifier_block *nb, case EC_MKBP_EVENT_SWITCH: pm_wakeup_event(ckdev->dev, 0); - if (ckdev->ec->event_data.event_type == EC_MKBP_EVENT_BUTTON) { + if (mkbp_event_type == EC_MKBP_EVENT_BUTTON) { val = get_unaligned_le32( &ckdev->ec->event_data.data.buttons); ev_type = EV_KEY; diff --git a/drivers/input/keyboard/davinci_keyscan.c b/drivers/input/keyboard/davinci_keyscan.c index 1d94928db922..f489cd585b33 100644 --- a/drivers/input/keyboard/davinci_keyscan.c +++ b/drivers/input/keyboard/davinci_keyscan.c @@ -192,7 +192,6 @@ static int __init davinci_ks_probe(struct platform_device *pdev) davinci_ks->irq = platform_get_irq(pdev, 0); if (davinci_ks->irq < 0) { - dev_err(dev, "no key scan irq\n"); error = davinci_ks->irq; goto fail2; } diff --git a/drivers/input/keyboard/gpio_keys.c b/drivers/input/keyboard/gpio_keys.c index 03f4d152f6b7..1373dc5b0765 100644 --- a/drivers/input/keyboard/gpio_keys.c +++ b/drivers/input/keyboard/gpio_keys.c @@ -351,10 +351,7 @@ static struct attribute *gpio_keys_attrs[] = { &dev_attr_disabled_switches.attr, NULL, }; - -static const struct attribute_group gpio_keys_attr_group = { - .attrs = gpio_keys_attrs, -}; +ATTRIBUTE_GROUPS(gpio_keys); static void gpio_keys_gpio_report_event(struct gpio_button_data *bdata) { @@ -851,13 +848,6 @@ static int gpio_keys_probe(struct platform_device *pdev) fwnode_handle_put(child); - error = devm_device_add_group(dev, &gpio_keys_attr_group); - if (error) { - dev_err(dev, "Unable to export keys/switches, error: %d\n", - error); - return error; - } - error = input_register_device(input); if (error) { dev_err(dev, "Unable to register input device, error: %d\n", @@ -1026,6 +1016,7 @@ static struct platform_driver gpio_keys_device_driver = { .name = "gpio-keys", .pm = &gpio_keys_pm_ops, .of_match_table = gpio_keys_of_match, + .dev_groups = gpio_keys_groups, } }; diff --git a/drivers/input/keyboard/imx_keypad.c b/drivers/input/keyboard/imx_keypad.c index 97500a2de2d5..5a46d113e909 100644 --- a/drivers/input/keyboard/imx_keypad.c +++ b/drivers/input/keyboard/imx_keypad.c @@ -430,10 +430,8 @@ static int imx_keypad_probe(struct platform_device *pdev) } irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "no irq defined in platform data\n"); + if (irq < 0) return irq; - } input_dev = devm_input_allocate_device(&pdev->dev); if (!input_dev) { diff --git a/drivers/input/keyboard/lpc32xx-keys.c b/drivers/input/keyboard/lpc32xx-keys.c index a34e3271b0c9..348af2aeb5de 100644 --- a/drivers/input/keyboard/lpc32xx-keys.c +++ b/drivers/input/keyboard/lpc32xx-keys.c @@ -172,10 +172,8 @@ static int lpc32xx_kscan_probe(struct platform_device *pdev) } irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get platform irq\n"); + if (irq < 0) return -EINVAL; - } kscandat = devm_kzalloc(&pdev->dev, sizeof(*kscandat), GFP_KERNEL); diff --git a/drivers/input/keyboard/mpr121_touchkey.c b/drivers/input/keyboard/mpr121_touchkey.c index e9ceaa16b46a..ee80de44ce3f 100644 --- a/drivers/input/keyboard/mpr121_touchkey.c +++ b/drivers/input/keyboard/mpr121_touchkey.c @@ -253,8 +253,7 @@ static int mpr_touchkey_probe(struct i2c_client *client, mpr121->client = client; mpr121->input_dev = input_dev; - mpr121->keycount = device_property_read_u32_array(dev, "linux,keycodes", - NULL, 0); + mpr121->keycount = device_property_count_u32(dev, "linux,keycodes"); if (mpr121->keycount > MPR121_MAX_KEY_COUNT) { dev_err(dev, "too many keys defined (%d)\n", mpr121->keycount); return -EINVAL; diff --git a/drivers/input/keyboard/nomadik-ske-keypad.c b/drivers/input/keyboard/nomadik-ske-keypad.c index fa265fdce2c4..608446e14614 100644 --- a/drivers/input/keyboard/nomadik-ske-keypad.c +++ b/drivers/input/keyboard/nomadik-ske-keypad.c @@ -235,10 +235,8 @@ static int __init ske_keypad_probe(struct platform_device *pdev) } irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get keypad irq\n"); + if (irq < 0) return -EINVAL; - } res = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (!res) { diff --git a/drivers/input/keyboard/nspire-keypad.c b/drivers/input/keyboard/nspire-keypad.c index 57eac91ecd76..63d5e488137d 100644 --- a/drivers/input/keyboard/nspire-keypad.c +++ b/drivers/input/keyboard/nspire-keypad.c @@ -165,10 +165,8 @@ static int nspire_keypad_probe(struct platform_device *pdev) int error; irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get keypad irq\n"); + if (irq < 0) return -EINVAL; - } keypad = devm_kzalloc(&pdev->dev, sizeof(struct nspire_keypad), GFP_KERNEL); diff --git a/drivers/input/keyboard/opencores-kbd.c b/drivers/input/keyboard/opencores-kbd.c index 159346cb4060..b0ea387414c1 100644 --- a/drivers/input/keyboard/opencores-kbd.c +++ b/drivers/input/keyboard/opencores-kbd.c @@ -49,10 +49,8 @@ static int opencores_kbd_probe(struct platform_device *pdev) } irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "missing board IRQ resource\n"); + if (irq < 0) return -EINVAL; - } opencores_kbd = devm_kzalloc(&pdev->dev, sizeof(*opencores_kbd), GFP_KERNEL); diff --git a/drivers/input/keyboard/pmic8xxx-keypad.c b/drivers/input/keyboard/pmic8xxx-keypad.c index d529768a1d06..91d5811d6f0e 100644 --- a/drivers/input/keyboard/pmic8xxx-keypad.c +++ b/drivers/input/keyboard/pmic8xxx-keypad.c @@ -544,16 +544,12 @@ static int pmic8xxx_kp_probe(struct platform_device *pdev) } kp->key_sense_irq = platform_get_irq(pdev, 0); - if (kp->key_sense_irq < 0) { - dev_err(&pdev->dev, "unable to get keypad sense irq\n"); + if (kp->key_sense_irq < 0) return kp->key_sense_irq; - } kp->key_stuck_irq = platform_get_irq(pdev, 1); - if (kp->key_stuck_irq < 0) { - dev_err(&pdev->dev, "unable to get keypad stuck irq\n"); + if (kp->key_stuck_irq < 0) return kp->key_stuck_irq; - } kp->input->name = "PMIC8XXX keypad"; kp->input->phys = "pmic8xxx_keypad/input0"; diff --git a/drivers/input/keyboard/pxa27x_keypad.c b/drivers/input/keyboard/pxa27x_keypad.c index 39023664d2f2..7e65708b25a4 100644 --- a/drivers/input/keyboard/pxa27x_keypad.c +++ b/drivers/input/keyboard/pxa27x_keypad.c @@ -727,10 +727,8 @@ static int pxa27x_keypad_probe(struct platform_device *pdev) return -EINVAL; irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get keypad irq\n"); + if (irq < 0) return -ENXIO; - } res = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (res == NULL) { diff --git a/drivers/input/keyboard/pxa930_rotary.c b/drivers/input/keyboard/pxa930_rotary.c index 585e7765cbf0..f7414091d94e 100644 --- a/drivers/input/keyboard/pxa930_rotary.c +++ b/drivers/input/keyboard/pxa930_rotary.c @@ -89,10 +89,8 @@ static int pxa930_rotary_probe(struct platform_device *pdev) int err; irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "no irq for rotary controller\n"); + if (irq < 0) return -ENXIO; - } res = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (!res) { diff --git a/drivers/input/keyboard/sh_keysc.c b/drivers/input/keyboard/sh_keysc.c index 08ba41a81f14..27ad73f43451 100644 --- a/drivers/input/keyboard/sh_keysc.c +++ b/drivers/input/keyboard/sh_keysc.c @@ -181,10 +181,8 @@ static int sh_keysc_probe(struct platform_device *pdev) } irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get irq\n"); + if (irq < 0) goto err0; - } priv = kzalloc(sizeof(*priv), GFP_KERNEL); if (priv == NULL) { diff --git a/drivers/input/keyboard/snvs_pwrkey.c b/drivers/input/keyboard/snvs_pwrkey.c index 5342d8d45f81..e76b7a400a1c 100644 --- a/drivers/input/keyboard/snvs_pwrkey.c +++ b/drivers/input/keyboard/snvs_pwrkey.c @@ -118,10 +118,8 @@ static int imx_snvs_pwrkey_probe(struct platform_device *pdev) pdata->wakeup = of_property_read_bool(np, "wakeup-source"); pdata->irq = platform_get_irq(pdev, 0); - if (pdata->irq < 0) { - dev_err(&pdev->dev, "no irq defined in platform data\n"); + if (pdata->irq < 0) return -EINVAL; - } regmap_update_bits(pdata->snvs, SNVS_LPCR_REG, SNVS_LPCR_DEP_EN, SNVS_LPCR_DEP_EN); diff --git a/drivers/input/keyboard/spear-keyboard.c b/drivers/input/keyboard/spear-keyboard.c index 7d25fa338ab4..9b8d78f87253 100644 --- a/drivers/input/keyboard/spear-keyboard.c +++ b/drivers/input/keyboard/spear-keyboard.c @@ -191,10 +191,8 @@ static int spear_kbd_probe(struct platform_device *pdev) int error; irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "not able to get irq for the device\n"); + if (irq < 0) return irq; - } kbd = devm_kzalloc(&pdev->dev, sizeof(*kbd), GFP_KERNEL); if (!kbd) { diff --git a/drivers/input/keyboard/st-keyscan.c b/drivers/input/keyboard/st-keyscan.c index f097128b93fe..27562cd67fb6 100644 --- a/drivers/input/keyboard/st-keyscan.c +++ b/drivers/input/keyboard/st-keyscan.c @@ -187,10 +187,8 @@ static int keyscan_probe(struct platform_device *pdev) keyscan_stop(keypad_data); keypad_data->irq = platform_get_irq(pdev, 0); - if (keypad_data->irq < 0) { - dev_err(&pdev->dev, "no IRQ specified\n"); + if (keypad_data->irq < 0) return -EINVAL; - } error = devm_request_irq(&pdev->dev, keypad_data->irq, keyscan_isr, 0, pdev->name, keypad_data); diff --git a/drivers/input/keyboard/tegra-kbc.c b/drivers/input/keyboard/tegra-kbc.c index a37a7a9e9171..d34d6947960f 100644 --- a/drivers/input/keyboard/tegra-kbc.c +++ b/drivers/input/keyboard/tegra-kbc.c @@ -631,10 +631,8 @@ static int tegra_kbc_probe(struct platform_device *pdev) return -EINVAL; kbc->irq = platform_get_irq(pdev, 0); - if (kbc->irq < 0) { - dev_err(&pdev->dev, "failed to get keyboard IRQ\n"); + if (kbc->irq < 0) return -ENXIO; - } kbc->idev = devm_input_allocate_device(&pdev->dev); if (!kbc->idev) { diff --git a/drivers/input/keyboard/w90p910_keypad.c b/drivers/input/keyboard/w90p910_keypad.c deleted file mode 100644 index c88d05d6108a..000000000000 --- a/drivers/input/keyboard/w90p910_keypad.c +++ /dev/null @@ -1,264 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0-only -/* - * Copyright (c) 2008-2009 Nuvoton technology corporation. - * - * Wan ZongShun <mcuos.com@gmail.com> - */ - -#include <linux/kernel.h> -#include <linux/module.h> -#include <linux/interrupt.h> -#include <linux/input.h> -#include <linux/device.h> -#include <linux/platform_device.h> -#include <linux/clk.h> -#include <linux/err.h> -#include <linux/io.h> -#include <linux/slab.h> - -#include <linux/platform_data/keypad-w90p910.h> - -/* Keypad Interface Control Registers */ -#define KPI_CONF 0x00 -#define KPI_3KCONF 0x04 -#define KPI_LPCONF 0x08 -#define KPI_STATUS 0x0C - -#define IS1KEY (0x01 << 16) -#define INTTR (0x01 << 21) -#define KEY0R (0x0f << 3) -#define KEY0C 0x07 -#define DEBOUNCE_BIT 0x08 -#define KSIZE0 (0x01 << 16) -#define KSIZE1 (0x01 << 17) -#define KPSEL (0x01 << 19) -#define ENKP (0x01 << 18) - -#define KGET_RAW(n) (((n) & KEY0R) >> 3) -#define KGET_COLUMN(n) ((n) & KEY0C) - -#define W90P910_NUM_ROWS 8 -#define W90P910_NUM_COLS 8 -#define W90P910_ROW_SHIFT 3 - -struct w90p910_keypad { - const struct w90p910_keypad_platform_data *pdata; - struct clk *clk; - struct input_dev *input_dev; - void __iomem *mmio_base; - int irq; - unsigned short keymap[W90P910_NUM_ROWS * W90P910_NUM_COLS]; -}; - -static void w90p910_keypad_scan_matrix(struct w90p910_keypad *keypad, - unsigned int status) -{ - struct input_dev *input_dev = keypad->input_dev; - unsigned int row = KGET_RAW(status); - unsigned int col = KGET_COLUMN(status); - unsigned int code = MATRIX_SCAN_CODE(row, col, W90P910_ROW_SHIFT); - unsigned int key = keypad->keymap[code]; - - input_event(input_dev, EV_MSC, MSC_SCAN, code); - input_report_key(input_dev, key, 1); - input_sync(input_dev); - - input_event(input_dev, EV_MSC, MSC_SCAN, code); - input_report_key(input_dev, key, 0); - input_sync(input_dev); -} - -static irqreturn_t w90p910_keypad_irq_handler(int irq, void *dev_id) -{ - struct w90p910_keypad *keypad = dev_id; - unsigned int kstatus, val; - - kstatus = __raw_readl(keypad->mmio_base + KPI_STATUS); - - val = INTTR | IS1KEY; - - if (kstatus & val) - w90p910_keypad_scan_matrix(keypad, kstatus); - - return IRQ_HANDLED; -} - -static int w90p910_keypad_open(struct input_dev *dev) -{ - struct w90p910_keypad *keypad = input_get_drvdata(dev); - const struct w90p910_keypad_platform_data *pdata = keypad->pdata; - unsigned int val, config; - - /* Enable unit clock */ - clk_enable(keypad->clk); - - val = __raw_readl(keypad->mmio_base + KPI_CONF); - val |= (KPSEL | ENKP); - val &= ~(KSIZE0 | KSIZE1); - - config = pdata->prescale | (pdata->debounce << DEBOUNCE_BIT); - - val |= config; - - __raw_writel(val, keypad->mmio_base + KPI_CONF); - - return 0; -} - -static void w90p910_keypad_close(struct input_dev *dev) -{ - struct w90p910_keypad *keypad = input_get_drvdata(dev); - - /* Disable clock unit */ - clk_disable(keypad->clk); -} - -static int w90p910_keypad_probe(struct platform_device *pdev) -{ - const struct w90p910_keypad_platform_data *pdata = - dev_get_platdata(&pdev->dev); - const struct matrix_keymap_data *keymap_data; - struct w90p910_keypad *keypad; - struct input_dev *input_dev; - struct resource *res; - int irq; - int error; - - if (!pdata) { - dev_err(&pdev->dev, "no platform data defined\n"); - return -EINVAL; - } - - keymap_data = pdata->keymap_data; - - irq = platform_get_irq(pdev, 0); - if (irq < 0) { - dev_err(&pdev->dev, "failed to get keypad irq\n"); - return -ENXIO; - } - - keypad = kzalloc(sizeof(struct w90p910_keypad), GFP_KERNEL); - input_dev = input_allocate_device(); - if (!keypad || !input_dev) { - dev_err(&pdev->dev, "failed to allocate driver data\n"); - error = -ENOMEM; - goto failed_free; - } - - keypad->pdata = pdata; - keypad->input_dev = input_dev; - keypad->irq = irq; - - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (res == NULL) { - dev_err(&pdev->dev, "failed to get I/O memory\n"); - error = -ENXIO; - goto failed_free; - } - - res = request_mem_region(res->start, resource_size(res), pdev->name); - if (res == NULL) { - dev_err(&pdev->dev, "failed to request I/O memory\n"); - error = -EBUSY; - goto failed_free; - } - - keypad->mmio_base = ioremap(res->start, resource_size(res)); - if (keypad->mmio_base == NULL) { - dev_err(&pdev->dev, "failed to remap I/O memory\n"); - error = -ENXIO; - goto failed_free_res; - } - - keypad->clk = clk_get(&pdev->dev, NULL); - if (IS_ERR(keypad->clk)) { - dev_err(&pdev->dev, "failed to get keypad clock\n"); - error = PTR_ERR(keypad->clk); - goto failed_free_io; - } - - /* set multi-function pin for w90p910 kpi. */ - mfp_set_groupi(&pdev->dev); - - input_dev->name = pdev->name; - input_dev->id.bustype = BUS_HOST; - input_dev->open = w90p910_keypad_open; - input_dev->close = w90p910_keypad_close; - input_dev->dev.parent = &pdev->dev; - - error = matrix_keypad_build_keymap(keymap_data, NULL, - W90P910_NUM_ROWS, W90P910_NUM_COLS, - keypad->keymap, input_dev); - if (error) { - dev_err(&pdev->dev, "failed to build keymap\n"); - goto failed_put_clk; - } - - error = request_irq(keypad->irq, w90p910_keypad_irq_handler, - 0, pdev->name, keypad); - if (error) { - dev_err(&pdev->dev, "failed to request IRQ\n"); - goto failed_put_clk; - } - - __set_bit(EV_REP, input_dev->evbit); - input_set_capability(input_dev, EV_MSC, MSC_SCAN); - input_set_drvdata(input_dev, keypad); - - /* Register the input device */ - error = input_register_device(input_dev); - if (error) { - dev_err(&pdev->dev, "failed to register input device\n"); - goto failed_free_irq; - } - - platform_set_drvdata(pdev, keypad); - return 0; - -failed_free_irq: - free_irq(irq, keypad); -failed_put_clk: - clk_put(keypad->clk); -failed_free_io: - iounmap(keypad->mmio_base); -failed_free_res: - release_mem_region(res->start, resource_size(res)); -failed_free: - input_free_device(input_dev); - kfree(keypad); - return error; -} - -static int w90p910_keypad_remove(struct platform_device *pdev) -{ - struct w90p910_keypad *keypad = platform_get_drvdata(pdev); - struct resource *res; - - free_irq(keypad->irq, keypad); - - clk_put(keypad->clk); - - input_unregister_device(keypad->input_dev); - - iounmap(keypad->mmio_base); - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - release_mem_region(res->start, resource_size(res)); - - kfree(keypad); - - return 0; -} - -static struct platform_driver w90p910_keypad_driver = { - .probe = w90p910_keypad_probe, - .remove = w90p910_keypad_remove, - .driver = { - .name = "nuc900-kpi", - }, -}; -module_platform_driver(w90p910_keypad_driver); - -MODULE_AUTHOR("Wan ZongShun <mcuos.com@gmail.com>"); -MODULE_DESCRIPTION("w90p910 keypad driver"); -MODULE_LICENSE("GPL"); -MODULE_ALIAS("platform:nuc900-keypad"); |