Skip to content

Commit 7dbfa44

Browse files
ccpalexbroonie
authored andcommitted
spi: spidev: mask SPI_CS_HIGH in SPI_IOC_RD_MODE
Commit f3186dd ("spi: Optionally use GPIO descriptors for CS GPIOs") has changed the user-space interface so that bogus SPI_CS_HIGH started to appear in the mask returned by SPI_IOC_RD_MODE even for active-low CS pins. Commit 138c9c3 ("spi: spidev: Fix CS polarity if GPIO descriptors are used") fixed only SPI_IOC_WR_MODE part of the problem. Let's fix SPI_IOC_RD_MODE symmetrically. Test case: #include <sys/ioctl.h> #include <fcntl.h> #include <linux/spi/spidev.h> int main(int argc, char **argv) { char modew = SPI_CPHA; char moder; int f = open("/dev/spidev0.0", O_RDWR); if (f < 0) return 1; ioctl(f, SPI_IOC_WR_MODE, &modew); ioctl(f, SPI_IOC_RD_MODE, &moder); return moder == modew ? 0 : 2; } Fixes: f3186dd ("spi: Optionally use GPIO descriptors for CS GPIOs") Signed-off-by: Alexander Sverdlin <alexander.sverdlin@siemens.com> Link: https://lore.kernel.org/r/20221130162927.539512-1-alexander.sverdlin@siemens.com Signed-off-by: Mark Brown <broonie@kernel.org>
1 parent f8fc65e commit 7dbfa44

File tree

1 file changed

+16
-5
lines changed

1 file changed

+16
-5
lines changed

drivers/spi/spidev.c

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -377,12 +377,23 @@ spidev_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
377377
switch (cmd) {
378378
/* read requests */
379379
case SPI_IOC_RD_MODE:
380-
retval = put_user(spi->mode & SPI_MODE_MASK,
381-
(__u8 __user *)arg);
382-
break;
383380
case SPI_IOC_RD_MODE32:
384-
retval = put_user(spi->mode & SPI_MODE_MASK,
385-
(__u32 __user *)arg);
381+
tmp = spi->mode;
382+
383+
{
384+
struct spi_controller *ctlr = spi->controller;
385+
386+
if (ctlr->use_gpio_descriptors && ctlr->cs_gpiods &&
387+
ctlr->cs_gpiods[spi->chip_select])
388+
tmp &= ~SPI_CS_HIGH;
389+
}
390+
391+
if (cmd == SPI_IOC_RD_MODE)
392+
retval = put_user(tmp & SPI_MODE_MASK,
393+
(__u8 __user *)arg);
394+
else
395+
retval = put_user(tmp & SPI_MODE_MASK,
396+
(__u32 __user *)arg);
386397
break;
387398
case SPI_IOC_RD_LSB_FIRST:
388399
retval = put_user((spi->mode & SPI_LSB_FIRST) ? 1 : 0,

0 commit comments

Comments
 (0)