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

[media] ite-cir: 8709 needs to use pnp resource 2

Thanks to the intrepid testing and debugging of Matthijs van Drunen, it
was uncovered that at least some variants of the ITE8709 need to use pnp
resource 2, rather than 0, for things to function properly. Resource 0
has a length of only 1, and if you try to bypass the pnp_port_len check
and use it anyway (with either a length of 1 or 2), the system in
question's trackpad ceased to function.

The circa lirc 0.8.7 lirc_ite8709 driver used resource 2, but the value
was (amusingly) changed to 0 by way of a patch from ITE themselves, so I
don't know if there may be variants where 0 actually *is* correct, but
at least in this case and in the original lirc_ite8709 driver author's
case, it sure looks like 2 is the right value.

This fix should probably be applied to all stable kernels with the
ite-cir driver, lest we nuke more people's trackpads.

Tested-by: Matthijs van Drunen
CC: Juan Jesús García de Soria <skandalfo@gmail.com>
CC: stable@kernel.org
Signed-off-by: Jarod Wilson <jarod@redhat.com>
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>

authored by

Jarod Wilson and committed by
Mauro Carvalho Chehab
35d136c8 258c0563

+12 -3
+9 -3
drivers/media/rc/ite-cir.c
··· 1347 1347 { /* 0: ITE8704 */ 1348 1348 .model = "ITE8704 CIR transceiver", 1349 1349 .io_region_size = IT87_IOREG_LENGTH, 1350 + .io_rsrc_no = 0, 1350 1351 .hw_tx_capable = true, 1351 1352 .sample_period = (u32) (1000000000ULL / 115200), 1352 1353 .tx_carrier_freq = 38000, ··· 1372 1371 { /* 1: ITE8713 */ 1373 1372 .model = "ITE8713 CIR transceiver", 1374 1373 .io_region_size = IT87_IOREG_LENGTH, 1374 + .io_rsrc_no = 0, 1375 1375 .hw_tx_capable = true, 1376 1376 .sample_period = (u32) (1000000000ULL / 115200), 1377 1377 .tx_carrier_freq = 38000, ··· 1397 1395 { /* 2: ITE8708 */ 1398 1396 .model = "ITE8708 CIR transceiver", 1399 1397 .io_region_size = IT8708_IOREG_LENGTH, 1398 + .io_rsrc_no = 0, 1400 1399 .hw_tx_capable = true, 1401 1400 .sample_period = (u32) (1000000000ULL / 115200), 1402 1401 .tx_carrier_freq = 38000, ··· 1423 1420 { /* 3: ITE8709 */ 1424 1421 .model = "ITE8709 CIR transceiver", 1425 1422 .io_region_size = IT8709_IOREG_LENGTH, 1423 + .io_rsrc_no = 2, 1426 1424 .hw_tx_capable = true, 1427 1425 .sample_period = (u32) (1000000000ULL / 115200), 1428 1426 .tx_carrier_freq = 38000, ··· 1465 1461 struct rc_dev *rdev = NULL; 1466 1462 int ret = -ENOMEM; 1467 1463 int model_no; 1464 + int io_rsrc_no; 1468 1465 1469 1466 ite_dbg("%s called", __func__); 1470 1467 ··· 1495 1490 1496 1491 /* get the description for the device */ 1497 1492 dev_desc = &ite_dev_descs[model_no]; 1493 + io_rsrc_no = dev_desc->io_rsrc_no; 1498 1494 1499 1495 /* validate pnp resources */ 1500 - if (!pnp_port_valid(pdev, 0) || 1501 - pnp_port_len(pdev, 0) != dev_desc->io_region_size) { 1496 + if (!pnp_port_valid(pdev, io_rsrc_no) || 1497 + pnp_port_len(pdev, io_rsrc_no) != dev_desc->io_region_size) { 1502 1498 dev_err(&pdev->dev, "IR PNP Port not valid!\n"); 1503 1499 goto failure; 1504 1500 } ··· 1510 1504 } 1511 1505 1512 1506 /* store resource values */ 1513 - itdev->cir_addr = pnp_port_start(pdev, 0); 1507 + itdev->cir_addr = pnp_port_start(pdev, io_rsrc_no); 1514 1508 itdev->cir_irq = pnp_irq(pdev, 0); 1515 1509 1516 1510 /* initialize spinlocks */
+3
drivers/media/rc/ite-cir.h
··· 57 57 /* size of the I/O region */ 58 58 int io_region_size; 59 59 60 + /* IR pnp I/O resource number */ 61 + int io_rsrc_no; 62 + 60 63 /* true if the hardware supports transmission */ 61 64 bool hw_tx_capable; 62 65