Commit aef01aad authored by Dmitry Torokhov's avatar Dmitry Torokhov

Input: matrix-keypad - switch to using generic device properties

Instead of being OF-specific, let's switch to using generic device
properties, which will make this code usable on ACPI, device tree and
legacy boards that use property sets.

As part of the change let's rename matrix_keypad_parse_of_params() to
matrix_keypad_parse_properties().
Signed-off-by: default avatarDmitry Torokhov <dmitry.torokhov@gmail.com>
parent b1fe0cf0
...@@ -213,7 +213,7 @@ static int bcm_kp_matrix_key_parse_dt(struct bcm_kp *kp) ...@@ -213,7 +213,7 @@ static int bcm_kp_matrix_key_parse_dt(struct bcm_kp *kp)
/* Initialize the KPCR Keypad Configuration Register */ /* Initialize the KPCR Keypad Configuration Register */
kp->kpcr = KPCR_STATUSFILTERENABLE | KPCR_COLFILTERENABLE; kp->kpcr = KPCR_STATUSFILTERENABLE | KPCR_COLFILTERENABLE;
error = matrix_keypad_parse_of_params(dev, &kp->n_rows, &kp->n_cols); error = matrix_keypad_parse_properties(dev, &kp->n_rows, &kp->n_cols);
if (error) { if (error) {
dev_err(dev, "failed to parse kp params\n"); dev_err(dev, "failed to parse kp params\n");
return error; return error;
......
...@@ -229,7 +229,8 @@ static int cros_ec_keyb_probe(struct platform_device *pdev) ...@@ -229,7 +229,8 @@ static int cros_ec_keyb_probe(struct platform_device *pdev)
ckdev = devm_kzalloc(dev, sizeof(*ckdev), GFP_KERNEL); ckdev = devm_kzalloc(dev, sizeof(*ckdev), GFP_KERNEL);
if (!ckdev) if (!ckdev)
return -ENOMEM; return -ENOMEM;
err = matrix_keypad_parse_of_params(dev, &ckdev->rows, &ckdev->cols);
err = matrix_keypad_parse_properties(dev, &ckdev->rows, &ckdev->cols);
if (err) if (err)
return err; return err;
......
...@@ -145,7 +145,7 @@ static int lpc32xx_parse_dt(struct device *dev, ...@@ -145,7 +145,7 @@ static int lpc32xx_parse_dt(struct device *dev,
u32 rows = 0, columns = 0; u32 rows = 0, columns = 0;
int err; int err;
err = matrix_keypad_parse_of_params(dev, &rows, &columns); err = matrix_keypad_parse_properties(dev, &rows, &columns);
if (err) if (err)
return err; return err;
if (rows != columns) { if (rows != columns) {
......
...@@ -223,8 +223,8 @@ static int omap4_keypad_parse_dt(struct device *dev, ...@@ -223,8 +223,8 @@ static int omap4_keypad_parse_dt(struct device *dev,
struct device_node *np = dev->of_node; struct device_node *np = dev->of_node;
int err; int err;
err = matrix_keypad_parse_of_params(dev, &keypad_data->rows, err = matrix_keypad_parse_properties(dev, &keypad_data->rows,
&keypad_data->cols); &keypad_data->cols);
if (err) if (err)
return err; return err;
......
...@@ -515,7 +515,7 @@ static int pmic8xxx_kp_probe(struct platform_device *pdev) ...@@ -515,7 +515,7 @@ static int pmic8xxx_kp_probe(struct platform_device *pdev)
int rc; int rc;
unsigned int ctrl_val; unsigned int ctrl_val;
rc = matrix_keypad_parse_of_params(&pdev->dev, &rows, &cols); rc = matrix_keypad_parse_properties(&pdev->dev, &rows, &cols);
if (rc) if (rc)
return rc; return rc;
......
...@@ -126,7 +126,7 @@ static int pxa27x_keypad_matrix_key_parse_dt(struct pxa27x_keypad *keypad, ...@@ -126,7 +126,7 @@ static int pxa27x_keypad_matrix_key_parse_dt(struct pxa27x_keypad *keypad,
u32 rows, cols; u32 rows, cols;
int error; int error;
error = matrix_keypad_parse_of_params(dev, &rows, &cols); error = matrix_keypad_parse_properties(dev, &rows, &cols);
if (error) if (error)
return error; return error;
......
...@@ -106,8 +106,8 @@ static int keypad_matrix_key_parse_dt(struct st_keyscan *keypad_data) ...@@ -106,8 +106,8 @@ static int keypad_matrix_key_parse_dt(struct st_keyscan *keypad_data)
struct device_node *np = dev->of_node; struct device_node *np = dev->of_node;
int error; int error;
error = matrix_keypad_parse_of_params(dev, &keypad_data->n_rows, error = matrix_keypad_parse_properties(dev, &keypad_data->n_rows,
&keypad_data->n_cols); &keypad_data->n_cols);
if (error) { if (error) {
dev_err(dev, "failed to parse keypad params\n"); dev_err(dev, "failed to parse keypad params\n");
return error; return error;
......
...@@ -354,7 +354,7 @@ static int stmpe_keypad_probe(struct platform_device *pdev) ...@@ -354,7 +354,7 @@ static int stmpe_keypad_probe(struct platform_device *pdev)
input->id.bustype = BUS_I2C; input->id.bustype = BUS_I2C;
input->dev.parent = &pdev->dev; input->dev.parent = &pdev->dev;
error = matrix_keypad_parse_of_params(&pdev->dev, &rows, &cols); error = matrix_keypad_parse_properties(&pdev->dev, &rows, &cols);
if (error) if (error)
return error; return error;
......
...@@ -295,7 +295,7 @@ static int tca8418_keypad_probe(struct i2c_client *client, ...@@ -295,7 +295,7 @@ static int tca8418_keypad_probe(struct i2c_client *client,
struct device_node *np = dev->of_node; struct device_node *np = dev->of_node;
int err; int err;
err = matrix_keypad_parse_of_params(dev, &rows, &cols); err = matrix_keypad_parse_properties(dev, &rows, &cols);
if (err) if (err)
return err; return err;
rep = of_property_read_bool(np, "keypad,autorepeat"); rep = of_property_read_bool(np, "keypad,autorepeat");
......
...@@ -374,8 +374,8 @@ static int twl4030_kp_probe(struct platform_device *pdev) ...@@ -374,8 +374,8 @@ static int twl4030_kp_probe(struct platform_device *pdev)
kp->autorepeat = pdata->rep; kp->autorepeat = pdata->rep;
keymap_data = pdata->keymap_data; keymap_data = pdata->keymap_data;
} else { } else {
error = matrix_keypad_parse_of_params(&pdev->dev, &kp->n_rows, error = matrix_keypad_parse_properties(&pdev->dev, &kp->n_rows,
&kp->n_cols); &kp->n_cols);
if (error) if (error)
return error; return error;
......
...@@ -14,18 +14,18 @@ ...@@ -14,18 +14,18 @@
* but WITHOUT ANY WARRANTY; without even the implied warranty of * but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details. * GNU General Public License for more details.
*
*/ */
#include <linux/device.h> #include <linux/device.h>
#include <linux/export.h>
#include <linux/gfp.h> #include <linux/gfp.h>
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/input.h> #include <linux/input.h>
#include <linux/of.h>
#include <linux/export.h>
#include <linux/module.h>
#include <linux/input/matrix_keypad.h> #include <linux/input/matrix_keypad.h>
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/property.h>
#include <linux/slab.h>
#include <linux/types.h>
static bool matrix_keypad_map_key(struct input_dev *input_dev, static bool matrix_keypad_map_key(struct input_dev *input_dev,
unsigned int rows, unsigned int cols, unsigned int rows, unsigned int cols,
...@@ -49,18 +49,22 @@ static bool matrix_keypad_map_key(struct input_dev *input_dev, ...@@ -49,18 +49,22 @@ static bool matrix_keypad_map_key(struct input_dev *input_dev,
return true; return true;
} }
#ifdef CONFIG_OF /**
int matrix_keypad_parse_of_params(struct device *dev, * matrix_keypad_parse_properties() - Read properties of matrix keypad
unsigned int *rows, unsigned int *cols) *
* @dev: Device containing properties
* @rows: Returns number of matrix rows
* @cols: Returns number of matrix columns
* @return 0 if OK, <0 on error
*/
int matrix_keypad_parse_properties(struct device *dev,
unsigned int *rows, unsigned int *cols)
{ {
struct device_node *np = dev->of_node; *rows = *cols = 0;
device_property_read_u32(dev, "keypad,num-rows", rows);
device_property_read_u32(dev, "keypad,num-columns", cols);
if (!np) {
dev_err(dev, "missing DT data");
return -EINVAL;
}
of_property_read_u32(np, "keypad,num-rows", rows);
of_property_read_u32(np, "keypad,num-columns", cols);
if (!*rows || !*cols) { if (!*rows || !*cols) {
dev_err(dev, "number of keypad rows/columns not specified\n"); dev_err(dev, "number of keypad rows/columns not specified\n");
return -EINVAL; return -EINVAL;
...@@ -68,62 +72,61 @@ int matrix_keypad_parse_of_params(struct device *dev, ...@@ -68,62 +72,61 @@ int matrix_keypad_parse_of_params(struct device *dev,
return 0; return 0;
} }
EXPORT_SYMBOL_GPL(matrix_keypad_parse_of_params); EXPORT_SYMBOL_GPL(matrix_keypad_parse_properties);
static int matrix_keypad_parse_of_keymap(const char *propname, static int matrix_keypad_parse_keymap(const char *propname,
unsigned int rows, unsigned int cols, unsigned int rows, unsigned int cols,
struct input_dev *input_dev) struct input_dev *input_dev)
{ {
struct device *dev = input_dev->dev.parent; struct device *dev = input_dev->dev.parent;
struct device_node *np = dev->of_node;
unsigned int row_shift = get_count_order(cols); unsigned int row_shift = get_count_order(cols);
unsigned int max_keys = rows << row_shift; unsigned int max_keys = rows << row_shift;
unsigned int proplen, i, size; u32 *keys;
const __be32 *prop; int i;
int size;
if (!np) int retval;
return -ENOENT;
if (!propname) if (!propname)
propname = "linux,keymap"; propname = "linux,keymap";
prop = of_get_property(np, propname, &proplen); size = device_property_read_u32_array(dev, propname, NULL, 0);
if (!prop) { if (size <= 0) {
dev_err(dev, "OF: %s property not defined in %s\n", dev_err(dev, "missing or malformed property %s: %d\n",
propname, np->full_name); propname, size);
return -ENOENT; return size < 0 ? size : -EINVAL;
} }
if (proplen % sizeof(u32)) { if (size > max_keys) {
dev_err(dev, "OF: Malformed keycode property %s in %s\n", dev_err(dev, "%s size overflow (%d vs max %u)\n",
propname, np->full_name); propname, size, max_keys);
return -EINVAL; return -EINVAL;
} }
size = proplen / sizeof(u32); keys = kmalloc_array(size, sizeof(u32), GFP_KERNEL);
if (size > max_keys) { if (!keys)
dev_err(dev, "OF: %s size overflow\n", propname); return -ENOMEM;
return -EINVAL;
retval = device_property_read_u32_array(dev, propname, keys, size);
if (retval) {
dev_err(dev, "failed to read %s property: %d\n",
propname, retval);
goto out;
} }
for (i = 0; i < size; i++) { for (i = 0; i < size; i++) {
unsigned int key = be32_to_cpup(prop + i);
if (!matrix_keypad_map_key(input_dev, rows, cols, if (!matrix_keypad_map_key(input_dev, rows, cols,
row_shift, key)) row_shift, keys[i])) {
return -EINVAL; retval = -EINVAL;
goto out;
}
} }
return 0; retval = 0;
}
#else out:
static int matrix_keypad_parse_of_keymap(const char *propname, kfree(keys);
unsigned int rows, unsigned int cols, return retval;
struct input_dev *input_dev)
{
return -ENOSYS;
} }
#endif
/** /**
* matrix_keypad_build_keymap - convert platform keymap into matrix keymap * matrix_keypad_build_keymap - convert platform keymap into matrix keymap
...@@ -192,8 +195,8 @@ int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data, ...@@ -192,8 +195,8 @@ int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
return -EINVAL; return -EINVAL;
} }
} else { } else {
error = matrix_keypad_parse_of_keymap(keymap_name, rows, cols, error = matrix_keypad_parse_keymap(keymap_name, rows, cols,
input_dev); input_dev);
if (error) if (error)
return error; return error;
} }
......
...@@ -80,24 +80,9 @@ int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data, ...@@ -80,24 +80,9 @@ int matrix_keypad_build_keymap(const struct matrix_keymap_data *keymap_data,
unsigned int rows, unsigned int cols, unsigned int rows, unsigned int cols,
unsigned short *keymap, unsigned short *keymap,
struct input_dev *input_dev); struct input_dev *input_dev);
int matrix_keypad_parse_properties(struct device *dev,
unsigned int *rows, unsigned int *cols);
#ifdef CONFIG_OF #define matrix_keypad_parse_of_params matrix_keypad_parse_properties
/**
* matrix_keypad_parse_of_params() - Read parameters from matrix-keypad node
*
* @dev: Device containing of_node
* @rows: Returns number of matrix rows
* @cols: Returns number of matrix columns
* @return 0 if OK, <0 on error
*/
int matrix_keypad_parse_of_params(struct device *dev,
unsigned int *rows, unsigned int *cols);
#else
static inline int matrix_keypad_parse_of_params(struct device *dev,
unsigned int *rows, unsigned int *cols)
{
return -ENOSYS;
}
#endif /* CONFIG_OF */
#endif /* _MATRIX_KEYPAD_H */ #endif /* _MATRIX_KEYPAD_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment