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

Configure Feed

Select the types of activity you want to include in your feed.

Input: iqs269a - configure device with a single block write

Unless it is being done as part of servicing a soft reset interrupt,
configuring channels on-the-fly (as is the case when writing to the
ati_trigger attribute) may cause GPIO3 (which reflects the state of
touch for a selected channel) to be inadvertently asserted.

To solve this problem, follow the vendor's recommendation and write
all channel configuration as well as the REDO_ATI register field as
part of a single block write. This ensures the device has been told
to re-calibrate itself following an I2C stop condition, after which
sensing resumes and GPIO3 may be asserted.

Fixes: 04e49867fad1 ("Input: add support for Azoteq IQS269A")
Signed-off-by: Jeff LaBundy <jeff@labundy.com>
Reviewed-by: Mattijs Korpershoek <mkorpershoek@baylibre.com>
Link: https://lore.kernel.org/r/Y7Rs8GyV7g0nF5Yy@nixie71
Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com>

authored by

Jeff LaBundy and committed by
Dmitry Torokhov
3689abfc e023cc4a

+39 -59
+39 -59
drivers/input/misc/iqs269a.c
··· 96 96 #define IQS269_MISC_B_TRACKING_UI_ENABLE BIT(4) 97 97 #define IQS269_MISC_B_FILT_STR_SLIDER GENMASK(1, 0) 98 98 99 - #define IQS269_CHx_SETTINGS 0x8C 100 - 101 99 #define IQS269_CHx_ENG_A_MEAS_CAP_SIZE BIT(15) 102 100 #define IQS269_CHx_ENG_A_RX_GND_INACTIVE BIT(13) 103 101 #define IQS269_CHx_ENG_A_LOCAL_CAP_SIZE BIT(12) ··· 243 245 u8 padding; 244 246 } __packed; 245 247 248 + struct iqs269_ch_reg { 249 + u8 rx_enable; 250 + u8 tx_enable; 251 + __be16 engine_a; 252 + __be16 engine_b; 253 + __be16 ati_comp; 254 + u8 thresh[3]; 255 + u8 hyst; 256 + u8 assoc_select; 257 + u8 assoc_weight; 258 + } __packed; 259 + 246 260 struct iqs269_sys_reg { 247 261 __be16 general; 248 262 u8 active; ··· 276 266 u8 timeout_swipe; 277 267 u8 thresh_swipe; 278 268 u8 redo_ati; 279 - } __packed; 280 - 281 - struct iqs269_ch_reg { 282 - u8 rx_enable; 283 - u8 tx_enable; 284 - __be16 engine_a; 285 - __be16 engine_b; 286 - __be16 ati_comp; 287 - u8 thresh[3]; 288 - u8 hyst; 289 - u8 assoc_select; 290 - u8 assoc_weight; 269 + struct iqs269_ch_reg ch_reg[IQS269_NUM_CH]; 291 270 } __packed; 292 271 293 272 struct iqs269_flags { ··· 291 292 struct regmap *regmap; 292 293 struct mutex lock; 293 294 struct iqs269_switch_desc switches[ARRAY_SIZE(iqs269_events)]; 294 - struct iqs269_ch_reg ch_reg[IQS269_NUM_CH]; 295 295 struct iqs269_sys_reg sys_reg; 296 296 struct input_dev *keypad; 297 297 struct input_dev *slider[IQS269_NUM_SL]; ··· 305 307 static int iqs269_ati_mode_set(struct iqs269_private *iqs269, 306 308 unsigned int ch_num, unsigned int mode) 307 309 { 310 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 308 311 u16 engine_a; 309 312 310 313 if (ch_num >= IQS269_NUM_CH) ··· 316 317 317 318 mutex_lock(&iqs269->lock); 318 319 319 - engine_a = be16_to_cpu(iqs269->ch_reg[ch_num].engine_a); 320 + engine_a = be16_to_cpu(ch_reg[ch_num].engine_a); 320 321 321 322 engine_a &= ~IQS269_CHx_ENG_A_ATI_MODE_MASK; 322 323 engine_a |= (mode << IQS269_CHx_ENG_A_ATI_MODE_SHIFT); 323 324 324 - iqs269->ch_reg[ch_num].engine_a = cpu_to_be16(engine_a); 325 + ch_reg[ch_num].engine_a = cpu_to_be16(engine_a); 325 326 iqs269->ati_current = false; 326 327 327 328 mutex_unlock(&iqs269->lock); ··· 332 333 static int iqs269_ati_mode_get(struct iqs269_private *iqs269, 333 334 unsigned int ch_num, unsigned int *mode) 334 335 { 336 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 335 337 u16 engine_a; 336 338 337 339 if (ch_num >= IQS269_NUM_CH) 338 340 return -EINVAL; 339 341 340 342 mutex_lock(&iqs269->lock); 341 - engine_a = be16_to_cpu(iqs269->ch_reg[ch_num].engine_a); 343 + engine_a = be16_to_cpu(ch_reg[ch_num].engine_a); 342 344 mutex_unlock(&iqs269->lock); 343 345 344 346 engine_a &= IQS269_CHx_ENG_A_ATI_MODE_MASK; ··· 351 351 static int iqs269_ati_base_set(struct iqs269_private *iqs269, 352 352 unsigned int ch_num, unsigned int base) 353 353 { 354 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 354 355 u16 engine_b; 355 356 356 357 if (ch_num >= IQS269_NUM_CH) ··· 380 379 381 380 mutex_lock(&iqs269->lock); 382 381 383 - engine_b = be16_to_cpu(iqs269->ch_reg[ch_num].engine_b); 382 + engine_b = be16_to_cpu(ch_reg[ch_num].engine_b); 384 383 385 384 engine_b &= ~IQS269_CHx_ENG_B_ATI_BASE_MASK; 386 385 engine_b |= base; 387 386 388 - iqs269->ch_reg[ch_num].engine_b = cpu_to_be16(engine_b); 387 + ch_reg[ch_num].engine_b = cpu_to_be16(engine_b); 389 388 iqs269->ati_current = false; 390 389 391 390 mutex_unlock(&iqs269->lock); ··· 396 395 static int iqs269_ati_base_get(struct iqs269_private *iqs269, 397 396 unsigned int ch_num, unsigned int *base) 398 397 { 398 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 399 399 u16 engine_b; 400 400 401 401 if (ch_num >= IQS269_NUM_CH) 402 402 return -EINVAL; 403 403 404 404 mutex_lock(&iqs269->lock); 405 - engine_b = be16_to_cpu(iqs269->ch_reg[ch_num].engine_b); 405 + engine_b = be16_to_cpu(ch_reg[ch_num].engine_b); 406 406 mutex_unlock(&iqs269->lock); 407 407 408 408 switch (engine_b & IQS269_CHx_ENG_B_ATI_BASE_MASK) { ··· 431 429 static int iqs269_ati_target_set(struct iqs269_private *iqs269, 432 430 unsigned int ch_num, unsigned int target) 433 431 { 432 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 434 433 u16 engine_b; 435 434 436 435 if (ch_num >= IQS269_NUM_CH) ··· 442 439 443 440 mutex_lock(&iqs269->lock); 444 441 445 - engine_b = be16_to_cpu(iqs269->ch_reg[ch_num].engine_b); 442 + engine_b = be16_to_cpu(ch_reg[ch_num].engine_b); 446 443 447 444 engine_b &= ~IQS269_CHx_ENG_B_ATI_TARGET_MASK; 448 445 engine_b |= target / 32; 449 446 450 - iqs269->ch_reg[ch_num].engine_b = cpu_to_be16(engine_b); 447 + ch_reg[ch_num].engine_b = cpu_to_be16(engine_b); 451 448 iqs269->ati_current = false; 452 449 453 450 mutex_unlock(&iqs269->lock); ··· 458 455 static int iqs269_ati_target_get(struct iqs269_private *iqs269, 459 456 unsigned int ch_num, unsigned int *target) 460 457 { 458 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 461 459 u16 engine_b; 462 460 463 461 if (ch_num >= IQS269_NUM_CH) 464 462 return -EINVAL; 465 463 466 464 mutex_lock(&iqs269->lock); 467 - engine_b = be16_to_cpu(iqs269->ch_reg[ch_num].engine_b); 465 + engine_b = be16_to_cpu(ch_reg[ch_num].engine_b); 468 466 mutex_unlock(&iqs269->lock); 469 467 470 468 *target = (engine_b & IQS269_CHx_ENG_B_ATI_TARGET_MASK) * 32; ··· 535 531 if (fwnode_property_present(ch_node, "azoteq,slider1-select")) 536 532 iqs269->sys_reg.slider_select[1] |= BIT(reg); 537 533 538 - ch_reg = &iqs269->ch_reg[reg]; 539 - 540 - error = regmap_raw_read(iqs269->regmap, 541 - IQS269_CHx_SETTINGS + reg * sizeof(*ch_reg) / 2, 542 - ch_reg, sizeof(*ch_reg)); 543 - if (error) 544 - return error; 534 + ch_reg = &iqs269->sys_reg.ch_reg[reg]; 545 535 546 536 error = iqs269_parse_mask(ch_node, "azoteq,rx-enable", 547 537 &ch_reg->rx_enable); ··· 1040 1042 1041 1043 static int iqs269_dev_init(struct iqs269_private *iqs269) 1042 1044 { 1043 - struct iqs269_sys_reg *sys_reg = &iqs269->sys_reg; 1044 - struct iqs269_ch_reg *ch_reg; 1045 1045 unsigned int val; 1046 - int error, i; 1046 + int error; 1047 1047 1048 1048 mutex_lock(&iqs269->lock); 1049 1049 ··· 1051 1055 if (error) 1052 1056 goto err_mutex; 1053 1057 1054 - for (i = 0; i < IQS269_NUM_CH; i++) { 1055 - if (!(sys_reg->active & BIT(i))) 1056 - continue; 1057 - 1058 - ch_reg = &iqs269->ch_reg[i]; 1059 - 1060 - error = regmap_raw_write(iqs269->regmap, 1061 - IQS269_CHx_SETTINGS + i * 1062 - sizeof(*ch_reg) / 2, ch_reg, 1063 - sizeof(*ch_reg)); 1064 - if (error) 1065 - goto err_mutex; 1066 - } 1067 - 1068 - /* 1069 - * The REDO-ATI and ATI channel selection fields must be written in the 1070 - * same block write, so every field between registers 0x80 through 0x8B 1071 - * (inclusive) must be written as well. 1072 - */ 1073 - error = regmap_raw_write(iqs269->regmap, IQS269_SYS_SETTINGS, sys_reg, 1074 - sizeof(*sys_reg)); 1058 + error = regmap_raw_write(iqs269->regmap, IQS269_SYS_SETTINGS, 1059 + &iqs269->sys_reg, sizeof(iqs269->sys_reg)); 1075 1060 if (error) 1076 1061 goto err_mutex; 1077 1062 ··· 1326 1349 struct device_attribute *attr, char *buf) 1327 1350 { 1328 1351 struct iqs269_private *iqs269 = dev_get_drvdata(dev); 1352 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 1329 1353 struct i2c_client *client = iqs269->client; 1330 1354 unsigned int val; 1331 1355 int error; ··· 1341 1363 if (error) 1342 1364 return error; 1343 1365 1344 - switch (iqs269->ch_reg[IQS269_CHx_HALL_ACTIVE].rx_enable & 1345 - iqs269->ch_reg[IQS269_CHx_HALL_INACTIVE].rx_enable) { 1366 + switch (ch_reg[IQS269_CHx_HALL_ACTIVE].rx_enable & 1367 + ch_reg[IQS269_CHx_HALL_INACTIVE].rx_enable) { 1346 1368 case IQS269_HALL_PAD_R: 1347 1369 val &= IQS269_CAL_DATA_A_HALL_BIN_R_MASK; 1348 1370 val >>= IQS269_CAL_DATA_A_HALL_BIN_R_SHIFT; ··· 1422 1444 struct device_attribute *attr, char *buf) 1423 1445 { 1424 1446 struct iqs269_private *iqs269 = dev_get_drvdata(dev); 1447 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 1425 1448 1426 1449 return scnprintf(buf, PAGE_SIZE, "%u\n", 1427 - iqs269->ch_reg[iqs269->ch_num].rx_enable); 1450 + ch_reg[iqs269->ch_num].rx_enable); 1428 1451 } 1429 1452 1430 1453 static ssize_t rx_enable_store(struct device *dev, ··· 1433 1454 size_t count) 1434 1455 { 1435 1456 struct iqs269_private *iqs269 = dev_get_drvdata(dev); 1457 + struct iqs269_ch_reg *ch_reg = iqs269->sys_reg.ch_reg; 1436 1458 unsigned int val; 1437 1459 int error; 1438 1460 ··· 1446 1466 1447 1467 mutex_lock(&iqs269->lock); 1448 1468 1449 - iqs269->ch_reg[iqs269->ch_num].rx_enable = val; 1469 + ch_reg[iqs269->ch_num].rx_enable = val; 1450 1470 iqs269->ati_current = false; 1451 1471 1452 1472 mutex_unlock(&iqs269->lock);