[PATCH 11/16 v2] Input: atmel_mxt_ts - refactor reading object table
From: Daniel Kurtz
Date: Thu Mar 29 2012 - 12:50:32 EST
Instead of reading each object separately, fetch the whole table in one
large i2c transaction. A 6 byte table object requires 10 bytes to read,
so doing this dramatically reduces overhead.
Also, as a cleanup, move object_table allocation (and post-fw-update
reallocation) into mxt_get_object_table().
Signed-off-by: Daniel Kurtz <djkurtz@xxxxxxxxxxxx>
---
drivers/input/touchscreen/atmel_mxt_ts.c | 66 +++++++++++++++---------------
1 files changed, 33 insertions(+), 33 deletions(-)
diff --git a/drivers/input/touchscreen/atmel_mxt_ts.c b/drivers/input/touchscreen/atmel_mxt_ts.c
index 9d88faf..0d0dab6 100644
--- a/drivers/input/touchscreen/atmel_mxt_ts.c
+++ b/drivers/input/touchscreen/atmel_mxt_ts.c
@@ -437,14 +437,7 @@ static int mxt_write_reg(struct i2c_client *client, u16 reg, u16 len,
return 0;
}
-static int mxt_read_object_table(struct i2c_client *client,
- u16 reg, u8 *object_buf)
-{
- return mxt_read_reg(client, reg, MXT_OBJECT_SIZE, object_buf);
-}
-
-static struct mxt_object *
-mxt_get_object(struct mxt_data *data, u8 type)
+static struct mxt_object *mxt_get_object(struct mxt_data *data, u8 type)
{
struct mxt_object *object;
int i;
@@ -733,25 +726,41 @@ static void mxt_handle_pdata(struct mxt_data *data)
static int mxt_get_object_table(struct mxt_data *data)
{
+ struct i2c_client *client = data->client;
+ struct device *dev = &client->dev;
int error;
int i;
- u16 reg;
u8 reportid = 0;
- u8 buf[MXT_OBJECT_SIZE];
+ u8 *buf;
+ size_t buf_size;
- for (i = 0; i < data->info.object_num; i++) {
- struct mxt_object *object = data->object_table + i;
+ /* Free old object table, if there was one. */
+ kfree(data->object_table);
+ data->object_table = kcalloc(data->info.object_num,
+ sizeof(struct mxt_object), GFP_KERNEL);
+ if (!data->object_table) {
+ dev_err(dev, "Failed to allocate object table\n");
+ return -ENOMEM;
+ }
- reg = MXT_OBJECT_START + MXT_OBJECT_SIZE * i;
- error = mxt_read_object_table(data->client, reg, buf);
- if (error)
- return error;
+ buf_size = MXT_OBJECT_SIZE * data->info.object_num;
+ buf = kmalloc(buf_size, GFP_KERNEL);
+ if (!buf)
+ return -ENOMEM;
- object->type = buf[0];
- object->start_address = (buf[2] << 8) | buf[1];
- object->size = buf[3] + 1;
- object->instances = buf[4] + 1;
- object->num_report_ids = buf[5];
+ error = mxt_read_reg(client, MXT_OBJECT_START, buf_size, buf);
+ if (error)
+ goto done;
+
+ for (i = 0; i < data->info.object_num; i++) {
+ struct mxt_object *object = &data->object_table[i];
+ u8 *obj_buf = &buf[i * MXT_OBJECT_SIZE];
+
+ object->type = obj_buf[0];
+ object->start_address = (obj_buf[2] << 8) | obj_buf[1];
+ object->size = obj_buf[3] + 1;
+ object->instances = obj_buf[4] + 1;
+ object->num_report_ids = obj_buf[5];
if (object->num_report_ids) {
reportid += object->num_report_ids * object->instances;
@@ -759,7 +768,9 @@ static int mxt_get_object_table(struct mxt_data *data)
}
}
- return 0;
+done:
+ kfree(buf);
+ return error;
}
static int mxt_initialize(struct mxt_data *data)
@@ -774,14 +785,6 @@ static int mxt_initialize(struct mxt_data *data)
if (error)
return error;
- data->object_table = kcalloc(info->object_num,
- sizeof(struct mxt_object),
- GFP_KERNEL);
- if (!data->object_table) {
- dev_err(&client->dev, "Failed to allocate memory\n");
- return -ENOMEM;
- }
-
/* Get object table information */
error = mxt_get_object_table(data);
if (error)
@@ -971,9 +974,6 @@ static ssize_t mxt_update_fw_store(struct device *dev,
/* Wait for reset */
msleep(MXT_FWRESET_TIME);
- kfree(data->object_table);
- data->object_table = NULL;
-
mxt_initialize(data);
}
--
1.7.7.3
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/