commit c4429d03fd6bffd51eb5b47dfb173ecd6c015e10 Author: Simon Budig Date: Wed Apr 4 23:21:51 2012 +0200 incorporate a set of fixes from Dmitry Torokhov diff --git a/drivers/input/touchscreen/edt-ft5x06.c b/drivers/input/touchscreen/edt-ft5x06.c index 58e35c3..d96eb8f 100644 --- a/drivers/input/touchscreen/edt-ft5x06.c +++ b/drivers/input/touchscreen/edt-ft5x06.c @@ -62,6 +62,7 @@ struct edt_ft5x06_i2c_ts_data { int gain; int offset; int report_rate; + char name[24]; }; static int edt_ft5x06_ts_readwrite(struct i2c_client *client, @@ -102,7 +103,7 @@ static irqreturn_t edt_ft5x06_ts_isr(int irq, void *dev_id) struct edt_ft5x06_i2c_ts_data *tsdata = dev_id; unsigned char touching = 0; unsigned char rdbuf[26], wrbuf[1]; - int i, have_abs, type, ret; + int i, have_abs, type, x, y, id, ret; memset(wrbuf, 0, sizeof(wrbuf)); memset(rdbuf, 0, sizeof(rdbuf)); @@ -126,7 +127,7 @@ static irqreturn_t edt_ft5x06_ts_isr(int irq, void *dev_id) rdbuf[0], rdbuf[1], rdbuf[2]); } - have_abs = 0; + have_abs = false; touching = rdbuf[3]; for (i = 0; i < touching; i++) { type = rdbuf[i*4+5] >> 6; @@ -134,23 +135,20 @@ static irqreturn_t edt_ft5x06_ts_isr(int irq, void *dev_id) if (type == 0x01 || type == 0x03) continue; + x = ((rdbuf[i*4+5] << 8) | rdbuf[i*4+6]) & 0x0fff; + y = ((rdbuf[i*4+7] << 8) | rdbuf[i*4+8]) & 0x0fff; + id = (rdbuf[i*4+7] >> 4) & 0x0f; + if (!have_abs) { input_report_key(tsdata->input, BTN_TOUCH, 1); input_report_abs(tsdata->input, ABS_PRESSURE, 1); - input_report_abs(tsdata->input, ABS_X, - ((rdbuf[i*4+5] << 8) | - rdbuf[i*4+6]) & 0x0fff); - input_report_abs(tsdata->input, ABS_Y, - ((rdbuf[i*4+7] << 8) | - rdbuf[i*4+8]) & 0x0fff); - have_abs = 1; + input_report_abs(tsdata->input, ABS_X, x); + input_report_abs(tsdata->input, ABS_Y, y); + have_abs = true; } - input_report_abs(tsdata->input, ABS_MT_POSITION_X, - ((rdbuf[i*4+5] << 8) | rdbuf[i*4+6]) & 0x0fff); - input_report_abs(tsdata->input, ABS_MT_POSITION_Y, - ((rdbuf[i*4+7] << 8) | rdbuf[i*4+8]) & 0x0fff); - input_report_abs(tsdata->input, ABS_MT_TRACKING_ID, - (rdbuf[i*4+7] >> 4) & 0x0f); + input_report_abs(tsdata->input, ABS_MT_POSITION_X, x); + input_report_abs(tsdata->input, ABS_MT_POSITION_Y, y); + input_report_abs(tsdata->input, ABS_MT_TRACKING_ID, id); input_mt_sync(tsdata->input); } if (!have_abs) { @@ -378,7 +376,7 @@ static ssize_t edt_ft5x06_i2c_mode_store(struct device *dev, dev_err(dev, "failed to switch to factory mode (%d)\n", ret); } else { - tsdata->factory_mode = 1; + tsdata->factory_mode = true; for (i = 0; i < 10; i++) { mdelay(5); /* mode register is 0x01 when in factory mode */ @@ -400,7 +398,7 @@ static ssize_t edt_ft5x06_i2c_mode_store(struct device *dev, dev_err(dev, "failed to switch to work mode (%d)\n", ret); } else { - tsdata->factory_mode = 0; + tsdata->factory_mode = false; for (i = 0; i < 10; i++) { mdelay(5); /* mode register is 0x01 when in factory mode */ @@ -515,8 +513,8 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, const struct i2c_device_id *id) { + const struct edt_ft5x06_platform_data *pdata = client->dev.platform_data; struct edt_ft5x06_i2c_ts_data *tsdata; - struct edt_ft5x06_platform_data *pdata; struct input_dev *input; int error; u8 rdbuf[23]; @@ -524,7 +522,7 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, dev_dbg(&client->dev, "probing for EDT FT5x06 I2C\n"); - if (!client->dev.platform_data) { + if (!pdata) { dev_err(&client->dev, "no platform data?\n"); return -ENODEV; } @@ -538,7 +536,6 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, dev_set_drvdata(&client->dev, tsdata); tsdata->client = client; - pdata = client->dev.platform_data; tsdata->reset_pin = pdata->reset_pin; mutex_init(&tsdata->mutex); @@ -581,7 +578,7 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, mutex_lock(&tsdata->mutex); - tsdata->factory_mode = 0; + tsdata->factory_mode = false; if (edt_ft5x06_ts_readwrite(client, 1, "\xbb", 22, rdbuf) < 0) { dev_err(&client->dev, "probing failed\n"); @@ -622,6 +619,7 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, } else { dev_info(&client->dev, "Product ID \"%s\"\n", model_name); } + strncpy (tsdata->name, model_name, sizeof (tsdata->name) - 1); input = input_allocate_device(); if (!input) { @@ -643,7 +641,7 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, 0, tsdata->num_y * 64 - 1, 0, 0); input_set_abs_params(input, ABS_MT_TRACKING_ID, 0, 15, 0, 0); - input->name = kstrdup(model_name, GFP_NOIO); + input->name = tsdata->name; input->id.bustype = BUS_I2C; input->dev.parent = &client->dev; @@ -659,7 +657,6 @@ static int edt_ft5x06_i2c_ts_probe(struct i2c_client *client, IRQF_TRIGGER_FALLING | IRQF_ONESHOT, client->name, tsdata)) { dev_err(&client->dev, "Unable to request touchscreen IRQ.\n"); - input = NULL; error = -ENOMEM; goto err_unregister_device; } @@ -683,10 +680,8 @@ err_unregister_device: input_unregister_device(input); input = NULL; err_free_input_device: - if (input) { - kfree(input->name); + if (input) input_free_device(input); - } err_free_irq_pin: gpio_free(tsdata->irq_pin); err_free_reset_pin: @@ -704,7 +699,6 @@ static int edt_ft5x06_i2c_ts_remove(struct i2c_client *client) sysfs_remove_group(&client->dev.kobj, &edt_ft5x06_i2c_attr_group); free_irq(tsdata->irq, tsdata); - kfree(tsdata->input->name); input_unregister_device(tsdata->input); gpio_free(tsdata->irq_pin); if (tsdata->reset_pin >= 0) @@ -714,6 +708,7 @@ static int edt_ft5x06_i2c_ts_remove(struct i2c_client *client) return 0; } +#ifdef CONFIG_PM_SLEEP static int edt_ft5x06_i2c_ts_suspend(struct device *dev) { struct edt_ft5x06_i2c_ts_data *tsdata = dev_get_drvdata(dev); @@ -733,6 +728,7 @@ static int edt_ft5x06_i2c_ts_resume(struct device *dev) return 0; } +#endif static SIMPLE_DEV_PM_OPS(edt_ft5x06_i2c_ts_pm_ops, edt_ft5x06_i2c_ts_suspend, edt_ft5x06_i2c_ts_resume);