aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBenson Leung <bleung@chromium.org>2014-05-19 02:02:52 -0400
committerDmitry Torokhov <dmitry.torokhov@gmail.com>2014-05-19 02:27:24 -0400
commitd79e7e47a9442abfcc252c8363521fe84c6b5783 (patch)
treef7b78e6367482baff48077ecbf4916ce6020649a
parent82c2c0d6296526c27379f47194caf26e543b766f (diff)
Input: atmel_mxt_ts - wait for CHG assert in mxt_check_bootloader
The driver should not immediately read bootloader status when in Application Update Mode. The CHG line will assert when the device has made a state transition and is ready to report a new status via i2c. This change adds a wait for completion in mxt_check_bootloader, and changes the mxt_interrupt handler to signal the completion. Signed-off-by: Benson Leung <bleung@chromium.org> Signed-off-by: Daniel Kurtz <djkurtz@chromium.org> Signed-off-by: Nick Dyer <nick.dyer@itdev.co.uk> Acked-by: Yufeng Shen <miletus@chromium.org> Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com>
-rw-r--r--drivers/input/touchscreen/atmel_mxt_ts.c102
1 files changed, 81 insertions, 21 deletions
diff --git a/drivers/input/touchscreen/atmel_mxt_ts.c b/drivers/input/touchscreen/atmel_mxt_ts.c
index 40af02c26113..7f51d39ce2fb 100644
--- a/drivers/input/touchscreen/atmel_mxt_ts.c
+++ b/drivers/input/touchscreen/atmel_mxt_ts.c
@@ -14,6 +14,8 @@
14 */ 14 */
15 15
16#include <linux/module.h> 16#include <linux/module.h>
17#include <linux/init.h>
18#include <linux/completion.h>
17#include <linux/delay.h> 19#include <linux/delay.h>
18#include <linux/firmware.h> 20#include <linux/firmware.h>
19#include <linux/i2c.h> 21#include <linux/i2c.h>
@@ -246,16 +248,19 @@ struct mxt_data {
246 const struct mxt_platform_data *pdata; 248 const struct mxt_platform_data *pdata;
247 struct mxt_object *object_table; 249 struct mxt_object *object_table;
248 struct mxt_info info; 250 struct mxt_info info;
249
250 unsigned int irq; 251 unsigned int irq;
251 unsigned int max_x; 252 unsigned int max_x;
252 unsigned int max_y; 253 unsigned int max_y;
254 bool in_bootloader;
253 255
254 /* Cached parameters from object table */ 256 /* Cached parameters from object table */
255 u8 T6_reportid; 257 u8 T6_reportid;
256 u8 T9_reportid_min; 258 u8 T9_reportid_min;
257 u8 T9_reportid_max; 259 u8 T9_reportid_max;
258 u8 T19_reportid; 260 u8 T19_reportid;
261
262 /* for fw update in bootloader */
263 struct completion bl_completion;
259}; 264};
260 265
261static size_t mxt_obj_size(const struct mxt_object *obj) 266static size_t mxt_obj_size(const struct mxt_object *obj)
@@ -339,12 +344,50 @@ static void mxt_dump_message(struct device *dev,
339 message->reportid, 7, message->message); 344 message->reportid, 7, message->message);
340} 345}
341 346
342static int mxt_check_bootloader(struct i2c_client *client, 347static int mxt_wait_for_chg(struct mxt_data *data, unsigned int timeout_ms)
343 unsigned int state)
344{ 348{
349 struct device *dev = &data->client->dev;
350 struct completion *comp = &data->bl_completion;
351 unsigned long timeout = msecs_to_jiffies(timeout_ms);
352 long ret;
353
354 ret = wait_for_completion_interruptible_timeout(comp, timeout);
355 if (ret < 0) {
356 return ret;
357 } else if (ret == 0) {
358 dev_err(dev, "Wait for completion timed out.\n");
359 return -ETIMEDOUT;
360 }
361 return 0;
362}
363
364static int mxt_check_bootloader(struct mxt_data *data, unsigned int state)
365{
366 struct i2c_client *client = data->client;
345 u8 val; 367 u8 val;
368 int ret;
346 369
347recheck: 370recheck:
371 if (state != MXT_WAITING_BOOTLOAD_CMD) {
372 /*
373 * In application update mode, the interrupt
374 * line signals state transitions. We must wait for the
375 * CHG assertion before reading the status byte.
376 * Once the status byte has been read, the line is deasserted.
377 */
378 ret = mxt_wait_for_chg(data, 300);
379 if (ret) {
380 /*
381 * TODO: handle -ERESTARTSYS better by terminating
382 * fw update process before returning to userspace
383 * by writing length 0x000 to device (iff we are in
384 * WAITING_FRAME_DATA state).
385 */
386 dev_err(&client->dev, "Update wait error %d\n", ret);
387 return ret;
388 }
389 }
390
348 if (i2c_master_recv(client, &val, 1) != 1) { 391 if (i2c_master_recv(client, &val, 1) != 1) {
349 dev_err(&client->dev, "%s: i2c recv failed\n", __func__); 392 dev_err(&client->dev, "%s: i2c recv failed\n", __func__);
350 return -EIO; 393 return -EIO;
@@ -590,9 +633,8 @@ static bool mxt_is_T9_message(struct mxt_data *data, struct mxt_message *msg)
590 return (id >= data->T9_reportid_min && id <= data->T9_reportid_max); 633 return (id >= data->T9_reportid_min && id <= data->T9_reportid_max);
591} 634}
592 635
593static irqreturn_t mxt_interrupt(int irq, void *dev_id) 636static irqreturn_t mxt_process_messages_until_invalid(struct mxt_data *data)
594{ 637{
595 struct mxt_data *data = dev_id;
596 struct mxt_message message; 638 struct mxt_message message;
597 const u8 *payload = &message.message[0]; 639 const u8 *payload = &message.message[0];
598 struct device *dev = &data->client->dev; 640 struct device *dev = &data->client->dev;
@@ -632,6 +674,19 @@ static irqreturn_t mxt_interrupt(int irq, void *dev_id)
632 return IRQ_HANDLED; 674 return IRQ_HANDLED;
633} 675}
634 676
677static irqreturn_t mxt_interrupt(int irq, void *dev_id)
678{
679 struct mxt_data *data = dev_id;
680
681 if (data->in_bootloader) {
682 /* bootloader state transition completion */
683 complete(&data->bl_completion);
684 return IRQ_HANDLED;
685 }
686
687 return mxt_process_messages_until_invalid(data);
688}
689
635static int mxt_check_reg_init(struct mxt_data *data) 690static int mxt_check_reg_init(struct mxt_data *data)
636{ 691{
637 const struct mxt_platform_data *pdata = data->pdata; 692 const struct mxt_platform_data *pdata = data->pdata;
@@ -947,6 +1002,8 @@ static int mxt_load_fw(struct device *dev, const char *fn)
947 } 1002 }
948 1003
949 /* Change to the bootloader mode */ 1004 /* Change to the bootloader mode */
1005 data->in_bootloader = true;
1006
950 mxt_write_object(data, MXT_GEN_COMMAND_T6, 1007 mxt_write_object(data, MXT_GEN_COMMAND_T6,
951 MXT_COMMAND_RESET, MXT_BOOT_VALUE); 1008 MXT_COMMAND_RESET, MXT_BOOT_VALUE);
952 msleep(MXT_RESET_TIME); 1009 msleep(MXT_RESET_TIME);
@@ -957,18 +1014,19 @@ static int mxt_load_fw(struct device *dev, const char *fn)
957 else 1014 else
958 client->addr = MXT_BOOT_HIGH; 1015 client->addr = MXT_BOOT_HIGH;
959 1016
960 ret = mxt_check_bootloader(client, MXT_WAITING_BOOTLOAD_CMD); 1017 reinit_completion(&data->bl_completion);
1018
1019 ret = mxt_check_bootloader(data, MXT_WAITING_BOOTLOAD_CMD);
961 if (ret) 1020 if (ret)
962 goto out; 1021 goto disable_irq;
963 1022
964 /* Unlock bootloader */ 1023 /* Unlock bootloader */
965 mxt_unlock_bootloader(client); 1024 mxt_unlock_bootloader(client);
966 1025
967 while (pos < fw->size) { 1026 while (pos < fw->size) {
968 ret = mxt_check_bootloader(client, 1027 ret = mxt_check_bootloader(data, MXT_WAITING_FRAME_DATA);
969 MXT_WAITING_FRAME_DATA);
970 if (ret) 1028 if (ret)
971 goto out; 1029 goto disable_irq;
972 1030
973 frame_size = ((*(fw->data + pos) << 8) | *(fw->data + pos + 1)); 1031 frame_size = ((*(fw->data + pos) << 8) | *(fw->data + pos + 1));
974 1032
@@ -980,17 +1038,19 @@ static int mxt_load_fw(struct device *dev, const char *fn)
980 /* Write one frame to device */ 1038 /* Write one frame to device */
981 mxt_fw_write(client, fw->data + pos, frame_size); 1039 mxt_fw_write(client, fw->data + pos, frame_size);
982 1040
983 ret = mxt_check_bootloader(client, 1041 ret = mxt_check_bootloader(data, MXT_FRAME_CRC_PASS);
984 MXT_FRAME_CRC_PASS);
985 if (ret) 1042 if (ret)
986 goto out; 1043 goto disable_irq;
987 1044
988 pos += frame_size; 1045 pos += frame_size;
989 1046
990 dev_dbg(dev, "Updated %d bytes / %zd bytes\n", pos, fw->size); 1047 dev_dbg(dev, "Updated %d bytes / %zd bytes\n", pos, fw->size);
991 } 1048 }
992 1049
993out: 1050 data->in_bootloader = false;
1051
1052disable_irq:
1053 disable_irq(data->irq);
994 release_firmware(fw); 1054 release_firmware(fw);
995 1055
996 /* Change to slave address of application */ 1056 /* Change to slave address of application */
@@ -1009,8 +1069,6 @@ static ssize_t mxt_update_fw_store(struct device *dev,
1009 struct mxt_data *data = dev_get_drvdata(dev); 1069 struct mxt_data *data = dev_get_drvdata(dev);
1010 int error; 1070 int error;
1011 1071
1012 disable_irq(data->irq);
1013
1014 error = mxt_load_fw(dev, MXT_FW_NAME); 1072 error = mxt_load_fw(dev, MXT_FW_NAME);
1015 if (error) { 1073 if (error) {
1016 dev_err(dev, "The firmware update failed(%d)\n", error); 1074 dev_err(dev, "The firmware update failed(%d)\n", error);
@@ -1024,13 +1082,13 @@ static ssize_t mxt_update_fw_store(struct device *dev,
1024 mxt_free_object_table(data); 1082 mxt_free_object_table(data);
1025 1083
1026 mxt_initialize(data); 1084 mxt_initialize(data);
1027 }
1028 1085
1029 enable_irq(data->irq); 1086 enable_irq(data->irq);
1030 1087
1031 error = mxt_make_highchg(data); 1088 error = mxt_make_highchg(data);
1032 if (error) 1089 if (error)
1033 return error; 1090 return error;
1091 }
1034 1092
1035 return count; 1093 return count;
1036} 1094}
@@ -1120,6 +1178,8 @@ static int mxt_probe(struct i2c_client *client,
1120 data->pdata = pdata; 1178 data->pdata = pdata;
1121 data->irq = client->irq; 1179 data->irq = client->irq;
1122 1180
1181 init_completion(&data->bl_completion);
1182
1123 mxt_calc_resolution(data); 1183 mxt_calc_resolution(data);
1124 1184
1125 error = mxt_initialize(data); 1185 error = mxt_initialize(data);