Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Input: edt-ft5x06 - add support for Evervision FT5726

Evervision displays are using different Focaltech touchscreen
controllers. This commit adds the initial support for the ones using the
FT5726 controller. Receiving the touch data is the same as for the
GENERIC_FT but the x and y cooridnates are swapped. The main differences
are the register addresses where the GAIN and THRESHOLD parameters are
stored.

Signed-off-by: Marco Felsch <m.felsch@pengutronix.de>
Reviewed-by: Rob Herring <robh@kernel.org>
Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com>

authored by

Marco Felsch and committed by
Dmitry Torokhov
a2f39dac 1eb7ea26

+44 -4
+3 -1
Documentation/devicetree/bindings/input/touchscreen/edt-ft5x06.txt
··· 1 1 FocalTech EDT-FT5x06 Polytouch driver 2 2 ===================================== 3 3 4 - There are 3 variants of the chip for various touch panel sizes 4 + There are 5 variants of the chip for various touch panel sizes 5 5 FT5206GE1 2.8" .. 3.8" 6 6 FT5306DE4 4.3" .. 7" 7 7 FT5406EE8 7" .. 8.9" 8 8 FT5506EEG 7" .. 8.9" 9 + FT5726NEI 5.7” .. 11.6" 9 10 10 11 The software interface is identical for all those chips, so that 11 12 currently there is no need for the driver to distinguish between the ··· 20 19 or: "edt,edt-ft5306" 21 20 or: "edt,edt-ft5406" 22 21 or: "edt,edt-ft5506" 22 + or: "evervision,ev-ft5726" 23 23 or: "focaltech,ft6236" 24 24 25 25 - reg: I2C slave address of the chip (0x38)
+41 -3
drivers/input/touchscreen/edt-ft5x06.c
··· 31 31 #include <linux/interrupt.h> 32 32 #include <linux/input.h> 33 33 #include <linux/i2c.h> 34 + #include <linux/kernel.h> 34 35 #include <linux/uaccess.h> 35 36 #include <linux/delay.h> 36 37 #include <linux/debugfs.h> ··· 54 53 #define M09_REGISTER_NUM_X 0x94 55 54 #define M09_REGISTER_NUM_Y 0x95 56 55 56 + #define EV_REGISTER_THRESHOLD 0x40 57 + #define EV_REGISTER_GAIN 0x41 58 + 57 59 #define NO_REGISTER 0xff 58 60 59 61 #define WORK_REGISTER_OPMODE 0x3c ··· 77 73 EDT_M06, 78 74 EDT_M09, 79 75 EDT_M12, 76 + EV_FT, 80 77 GENERIC_FT, 81 78 }; 82 79 ··· 195 190 196 191 case EDT_M09: 197 192 case EDT_M12: 193 + case EV_FT: 198 194 case GENERIC_FT: 199 195 cmd = 0x0; 200 196 offset = 3; ··· 248 242 249 243 x = ((buf[0] << 8) | buf[1]) & 0x0fff; 250 244 y = ((buf[2] << 8) | buf[3]) & 0x0fff; 245 + /* The FT5x26 send the y coordinate first */ 246 + if (tsdata->version == EV_FT) 247 + swap(x, y); 248 + 251 249 id = (buf[2] >> 4) & 0x0f; 252 250 down = type != TOUCH_EVENT_UP; 253 251 ··· 285 275 wrbuf[3] = wrbuf[0] ^ wrbuf[1] ^ wrbuf[2]; 286 276 return edt_ft5x06_ts_readwrite(tsdata->client, 4, 287 277 wrbuf, 0, NULL); 278 + /* fallthrough */ 288 279 case EDT_M09: 289 280 case EDT_M12: 281 + case EV_FT: 290 282 case GENERIC_FT: 291 283 wrbuf[0] = addr; 292 284 wrbuf[1] = value; ··· 327 315 } 328 316 break; 329 317 318 + /* fallthrough */ 330 319 case EDT_M09: 331 320 case EDT_M12: 321 + case EV_FT: 332 322 case GENERIC_FT: 333 323 wrbuf[0] = addr; 334 324 error = edt_ft5x06_ts_readwrite(tsdata->client, 1, ··· 619 605 tsdata->threshold); 620 606 edt_ft5x06_register_write(tsdata, reg_addr->reg_gain, 621 607 tsdata->gain); 622 - edt_ft5x06_register_write(tsdata, reg_addr->reg_offset, 623 - tsdata->offset); 608 + if (reg_addr->reg_offset != NO_REGISTER) 609 + edt_ft5x06_register_write(tsdata, reg_addr->reg_offset, 610 + tsdata->offset); 624 611 if (reg_addr->reg_report_rate != NO_REGISTER) 625 612 edt_ft5x06_register_write(tsdata, reg_addr->reg_report_rate, 626 613 tsdata->report_rate); ··· 882 867 case 0x5a: /* Solomon Goldentek Display */ 883 868 snprintf(model_name, EDT_NAME_LEN, "GKTW50SCED1R0"); 884 869 break; 870 + case 0x59: /* Evervision Display with FT5xx6 TS */ 871 + tsdata->version = EV_FT; 872 + error = edt_ft5x06_ts_readwrite(client, 1, "\x53", 873 + 1, rdbuf); 874 + if (error) 875 + return error; 876 + strlcpy(fw_version, rdbuf, 1); 877 + snprintf(model_name, EDT_NAME_LEN, 878 + "EVERVISION-FT5726NEi"); 879 + break; 885 880 default: 886 881 snprintf(model_name, EDT_NAME_LEN, 887 882 "generic ft5x06 (%02x)", ··· 937 912 tsdata->threshold = edt_ft5x06_register_read(tsdata, 938 913 reg_addr->reg_threshold); 939 914 tsdata->gain = edt_ft5x06_register_read(tsdata, reg_addr->reg_gain); 940 - tsdata->offset = edt_ft5x06_register_read(tsdata, reg_addr->reg_offset); 915 + if (reg_addr->reg_offset != NO_REGISTER) 916 + tsdata->offset = 917 + edt_ft5x06_register_read(tsdata, reg_addr->reg_offset); 941 918 if (reg_addr->reg_report_rate != NO_REGISTER) 942 919 tsdata->report_rate = edt_ft5x06_register_read(tsdata, 943 920 reg_addr->reg_report_rate); ··· 979 952 reg_addr->reg_offset = M09_REGISTER_OFFSET; 980 953 reg_addr->reg_num_x = M09_REGISTER_NUM_X; 981 954 reg_addr->reg_num_y = M09_REGISTER_NUM_Y; 955 + break; 956 + 957 + case EV_FT: 958 + reg_addr->reg_threshold = EV_REGISTER_THRESHOLD; 959 + reg_addr->reg_gain = EV_REGISTER_GAIN; 960 + reg_addr->reg_offset = NO_REGISTER; 961 + reg_addr->reg_num_x = NO_REGISTER; 962 + reg_addr->reg_num_y = NO_REGISTER; 963 + reg_addr->reg_report_rate = NO_REGISTER; 982 964 break; 983 965 984 966 case GENERIC_FT: ··· 1191 1155 static const struct i2c_device_id edt_ft5x06_ts_id[] = { 1192 1156 { .name = "edt-ft5x06", .driver_data = (long)&edt_ft5x06_data }, 1193 1157 { .name = "edt-ft5506", .driver_data = (long)&edt_ft5506_data }, 1158 + { .name = "ev-ft5726", .driver_data = (long)&edt_ft5506_data }, 1194 1159 /* Note no edt- prefix for compatibility with the ft6236.c driver */ 1195 1160 { .name = "ft6236", .driver_data = (long)&edt_ft6236_data }, 1196 1161 { /* sentinel */ } ··· 1204 1167 { .compatible = "edt,edt-ft5306", .data = &edt_ft5x06_data }, 1205 1168 { .compatible = "edt,edt-ft5406", .data = &edt_ft5x06_data }, 1206 1169 { .compatible = "edt,edt-ft5506", .data = &edt_ft5506_data }, 1170 + { .compatible = "evervision,ev-ft5726", .data = &edt_ft5506_data }, 1207 1171 /* Note focaltech vendor prefix for compatibility with ft6236.c */ 1208 1172 { .compatible = "focaltech,ft6236", .data = &edt_ft6236_data }, 1209 1173 { /* sentinel */ }