Skip to content

Commit 456a39b

Browse files
r-vigneshgregkh
authored andcommitted
spi: ti-qspi: Fix data corruption seen on r/w stress test
commit bc27a53 upstream. Writing invalid command to QSPI_SPI_CMD_REG will terminate current transfer and de-assert the chip select. This has to be done before calling spi_finalize_current_message(). Because spi_finalize_current_message() will mark the end of current message transfer and schedule the next transfer. If the chipselect is not de-asserted before calling spi_finalize_current_message() then the next transfer will overlap with the previous transfer leading to data corruption. __spi_pump_message() can be called either from kthread worker context or directly from the calling process's context. It is possible that these two calls can race against each other. But race is serialized by checking whether master->cur_msg == NULL (pointer to msg being handled by transfer_one() at present). The master->cur_msg is set to NULL when spi_finalize_current_message() is called on that message, which means calling spi_finalize_current_message() allows __spi_sync() to pump next message in calling process context. Now if spi-ti-qspi calls spi_finalize_current_message() before we terminate transfer at hardware side, if __spi_pump_message() is called from process context then the successive transactions can overlap. Fix this by moving writing invalid command to QSPI_SPI_CMD_REG to before calling spi_finalize_current_message() call. Signed-off-by: Vignesh R <[email protected]> Signed-off-by: Mark Brown <[email protected]> Signed-off-by: Greg Kroah-Hartman <[email protected]>
1 parent 1156eaf commit 456a39b

File tree

1 file changed

+1
-2
lines changed

1 file changed

+1
-2
lines changed

drivers/spi/spi-ti-qspi.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -364,11 +364,10 @@ static int ti_qspi_start_transfer_one(struct spi_master *master,
364364

365365
mutex_unlock(&qspi->list_lock);
366366

367+
ti_qspi_write(qspi, qspi->cmd | QSPI_INVAL, QSPI_SPI_CMD_REG);
367368
m->status = status;
368369
spi_finalize_current_message(master);
369370

370-
ti_qspi_write(qspi, qspi->cmd | QSPI_INVAL, QSPI_SPI_CMD_REG);
371-
372371
return status;
373372
}
374373

0 commit comments

Comments
 (0)