Commit 4b5cc48a5e712baa87a58ac3e565f09c1c169a84

Authored by Texas Instruments Auto Merger

Merge branch 'connectivity-ti-linux-4.1.y' of git://git.ti.com/connectivity-inte…

…gration-tree/connectivity-ti-linux-kernel into ti-linux-4.1.y

TI-Feature: connectivity
TI-Tree: git://git.ti.com/connectivity-integration-tree/connectivity-ti-linux-kernel.git
TI-Branch: connectivity-ti-linux-4.1.y

* 'connectivity-ti-linux-4.1.y' of git://git.ti.com/connectivity-integration-tree/connectivity-ti-linux-kernel:
  Input: edt-ft5x06 - Work around FT5506 firmware bug
  Input: edt-ft5x06 - Add support for 10 touch points for FT5506
  Input: edt-ft5x06 - Add support for variable amount of max support points
  Input: edt-ft5x06 - Use max support points to determine read length
  Input: edt-ft5x06 - do not call desc_to_gpio for invalid gpios

Signed-off-by: Texas Instruments Auto Merger <lcpd_integration@list.ti.com>

Showing 1 changed file Side-by-side Diff

drivers/input/touchscreen/edt-ft5x06.c
... ... @@ -36,12 +36,11 @@
36 36 #include <linux/slab.h>
37 37 #include <linux/gpio.h>
38 38 #include <linux/of_gpio.h>
  39 +#include <linux/of_device.h>
39 40 #include <linux/input/mt.h>
40 41 #include <linux/input/touchscreen.h>
41 42 #include <linux/input/edt-ft5x06.h>
42 43  
43   -#define MAX_SUPPORT_POINTS 5
44   -
45 44 #define WORK_REGISTER_THRESHOLD 0x00
46 45 #define WORK_REGISTER_REPORT_RATE 0x08
47 46 #define WORK_REGISTER_GAIN 0x30
... ... @@ -107,6 +106,7 @@
107 106 int gain;
108 107 int offset;
109 108 int report_rate;
  109 + int max_support_points;
110 110  
111 111 char name[EDT_NAME_LEN];
112 112  
... ... @@ -114,6 +114,10 @@
114 114 enum edt_ver version;
115 115 };
116 116  
  117 +struct edt_i2c_chip_data {
  118 + int max_support_points;
  119 +};
  120 +
117 121 static int edt_ft5x06_ts_readwrite(struct i2c_client *client,
118 122 u16 wr_len, u8 *wr_buf,
119 123 u16 rd_len, u8 *rd_buf)
... ... @@ -170,7 +174,7 @@
170 174 struct edt_ft5x06_ts_data *tsdata = dev_id;
171 175 struct device *dev = &tsdata->client->dev;
172 176 u8 cmd;
173   - u8 rdbuf[29];
  177 + u8 rdbuf[61];
174 178 int i, type, x, y, id;
175 179 int offset, tplen, datalen;
176 180 int error;
177 181  
178 182  
... ... @@ -180,14 +184,16 @@
180 184 cmd = 0xf9; /* tell the controller to send touch data */
181 185 offset = 5; /* where the actual touch data starts */
182 186 tplen = 4; /* data comes in so called frames */
183   - datalen = 26; /* how much bytes to listen for */
  187 +
  188 + /* how many bytes to listen for */
  189 + datalen = tplen * tsdata->max_support_points + offset + 1;
184 190 break;
185 191  
186 192 case M09:
187   - cmd = 0x02;
188   - offset = 1;
  193 + cmd = 0x0;
  194 + offset = 3;
189 195 tplen = 6;
190   - datalen = 29;
  196 + datalen = tplen * tsdata->max_support_points + 1 - cmd;
191 197 break;
192 198  
193 199 default:
... ... @@ -219,7 +225,7 @@
219 225 goto out;
220 226 }
221 227  
222   - for (i = 0; i < MAX_SUPPORT_POINTS; i++) {
  228 + for (i = 0; i < tsdata->max_support_points; i++) {
223 229 u8 *buf = &rdbuf[i * tplen + offset];
224 230 bool down;
225 231  
226 232  
... ... @@ -892,11 +898,39 @@
892 898 }
893 899 }
894 900  
  901 +#ifdef CONFIG_OF
  902 +
  903 +static const struct of_device_id edt_ft5x06_of_match[];
  904 +
  905 +static void edt_ft5x06_ts_set_max_support_points(struct device *dev,
  906 + struct edt_ft5x06_ts_data *tsdata)
  907 +{
  908 + struct edt_i2c_chip_data *chip_data;
  909 + const struct of_device_id *match;
  910 +
  911 + match = of_match_device(of_match_ptr(edt_ft5x06_of_match), dev);
  912 +
  913 + if (match) {
  914 + chip_data = (struct edt_i2c_chip_data *)match->data;
  915 + tsdata->max_support_points = chip_data->max_support_points;
  916 + } else {
  917 + tsdata->max_support_points = 5;
  918 + }
  919 +
  920 +}
  921 +#else
  922 +static void edt_ft5x06_ts_set_max_support_points(struct device *dev,
  923 + struct edt_ft5x06_ts_data *tsdata)
  924 +{
  925 +}
  926 +#endif
  927 +
895 928 static int edt_ft5x06_ts_probe(struct i2c_client *client,
896 929 const struct i2c_device_id *id)
897 930 {
898 931 const struct edt_ft5x06_platform_data *pdata =
899 932 dev_get_platdata(&client->dev);
  933 + struct device *dev = &client->dev;
900 934 struct edt_ft5x06_ts_data *tsdata;
901 935 struct input_dev *input;
902 936 int error;
... ... @@ -911,6 +945,8 @@
911 945 return -ENOMEM;
912 946 }
913 947  
  948 + edt_ft5x06_ts_set_max_support_points(dev, tsdata);
  949 +
914 950 gpio = devm_gpiod_get_optional(&client->dev, "reset", GPIOD_OUT_HIGH);
915 951 if (IS_ERR(gpio)) {
916 952 error = PTR_ERR(gpio);
... ... @@ -1001,7 +1037,7 @@
1001 1037 if (!pdata)
1002 1038 touchscreen_parse_properties(input, true);
1003 1039  
1004   - error = input_mt_init_slots(input, MAX_SUPPORT_POINTS, 0);
  1040 + error = input_mt_init_slots(input, tsdata->max_support_points, 0);
1005 1041 if (error) {
1006 1042 dev_err(&client->dev, "Unable to init MT slots.\n");
1007 1043 return error;
... ... @@ -1032,8 +1068,9 @@
1032 1068  
1033 1069 dev_dbg(&client->dev,
1034 1070 "EDT FT5x06 initialized: IRQ %d, WAKE pin %d, Reset pin %d.\n",
1035   - client->irq, desc_to_gpio(tsdata->wake_pin),
1036   - desc_to_gpio(tsdata->reset_pin));
  1071 + client->irq,
  1072 + tsdata->wake_pin ? desc_to_gpio(tsdata->wake_pin) : -1,
  1073 + tsdata->reset_pin ? desc_to_gpio(tsdata->reset_pin) : -1);
1037 1074  
1038 1075 return 0;
1039 1076  
1040 1077  
... ... @@ -1082,11 +1119,20 @@
1082 1119 MODULE_DEVICE_TABLE(i2c, edt_ft5x06_ts_id);
1083 1120  
1084 1121 #ifdef CONFIG_OF
  1122 +
  1123 +static const struct edt_i2c_chip_data edt_ft5x06_data = {
  1124 + .max_support_points = 5,
  1125 +};
  1126 +
  1127 +static const struct edt_i2c_chip_data edt_ft5506_data = {
  1128 + .max_support_points = 10,
  1129 +};
  1130 +
1085 1131 static const struct of_device_id edt_ft5x06_of_match[] = {
1086   - { .compatible = "edt,edt-ft5206", },
1087   - { .compatible = "edt,edt-ft5306", },
1088   - { .compatible = "edt,edt-ft5406", },
1089   - { .compatible = "edt,edt-ft5506", },
  1132 + { .compatible = "edt,edt-ft5206", .data = &edt_ft5x06_data},
  1133 + { .compatible = "edt,edt-ft5306", .data = &edt_ft5x06_data},
  1134 + { .compatible = "edt,edt-ft5406", .data = &edt_ft5x06_data},
  1135 + { .compatible = "edt,edt-ft5506", .data = &edt_ft5506_data},
1090 1136 { /* sentinel */ }
1091 1137 };
1092 1138 MODULE_DEVICE_TABLE(of, edt_ft5x06_of_match);