diff options
author | Ricardo Ribalda <ricardo.ribalda@gmail.com> | 2017-11-21 04:09:02 -0500 |
---|---|---|
committer | Mark Brown <broonie@kernel.org> | 2017-11-24 08:09:22 -0500 |
commit | 5a1314fa697fc65cefaba64cd4699bfc3e6882a6 (patch) | |
tree | a124f65cf82d4ae9b9ccf6b1a891224cdb1b46d3 /drivers/spi/spi-xilinx.c | |
parent | abbdb5ce31c21a4b3c3922c56030f3d487497933 (diff) |
spi: xilinx: Detect stall with Unknown commands
When the core is configured in C_SPI_MODE > 0, it integrates a
lookup table that automatically configures the core in dual or quad mode
based on the command (first byte on the tx fifo).
Unfortunately, that list mode_?_memoy_*.mif does not contain all the
supported commands by the flash.
Since 4.14 spi-nor automatically tries to probe the flash using SFDP
(command 0x5a), and that command is not part of the list_mode table.
Whit the right combination of C_SPI_MODE and C_SPI_MEMORY this leads
into a stall that can only be recovered with a soft rest.
This patch detects this kind of stall and returns -EIO to the caller on
those commands. spi-nor can handle this error properly:
m25p80 spi0.0: Detected stall. Check C_SPI_MODE and C_SPI_MEMORY. 0x21 0x2404
m25p80 spi0.0: SPI transfer failed: -5
spi_master spi0: failed to transfer one message from queue
m25p80 spi0.0: s25sl064p (8192 Kbytes)
Signed-off-by: Ricardo Ribalda Delgado <ricardo.ribalda@gmail.com>
Signed-off-by: Mark Brown <broonie@kernel.org>
Cc: stable@vger.kernel.org
Diffstat (limited to 'drivers/spi/spi-xilinx.c')
-rw-r--r-- | drivers/spi/spi-xilinx.c | 11 |
1 files changed, 11 insertions, 0 deletions
diff --git a/drivers/spi/spi-xilinx.c b/drivers/spi/spi-xilinx.c index bc7100b93dfc..e0b9fe1d0e37 100644 --- a/drivers/spi/spi-xilinx.c +++ b/drivers/spi/spi-xilinx.c | |||
@@ -271,6 +271,7 @@ static int xilinx_spi_txrx_bufs(struct spi_device *spi, struct spi_transfer *t) | |||
271 | while (remaining_words) { | 271 | while (remaining_words) { |
272 | int n_words, tx_words, rx_words; | 272 | int n_words, tx_words, rx_words; |
273 | u32 sr; | 273 | u32 sr; |
274 | int stalled; | ||
274 | 275 | ||
275 | n_words = min(remaining_words, xspi->buffer_size); | 276 | n_words = min(remaining_words, xspi->buffer_size); |
276 | 277 | ||
@@ -299,7 +300,17 @@ static int xilinx_spi_txrx_bufs(struct spi_device *spi, struct spi_transfer *t) | |||
299 | 300 | ||
300 | /* Read out all the data from the Rx FIFO */ | 301 | /* Read out all the data from the Rx FIFO */ |
301 | rx_words = n_words; | 302 | rx_words = n_words; |
303 | stalled = 10; | ||
302 | while (rx_words) { | 304 | while (rx_words) { |
305 | if (rx_words == n_words && !(stalled--) && | ||
306 | !(sr & XSPI_SR_TX_EMPTY_MASK) && | ||
307 | (sr & XSPI_SR_RX_EMPTY_MASK)) { | ||
308 | dev_err(&spi->dev, | ||
309 | "Detected stall. Check C_SPI_MODE and C_SPI_MEMORY\n"); | ||
310 | xspi_init_hw(xspi); | ||
311 | return -EIO; | ||
312 | } | ||
313 | |||
303 | if ((sr & XSPI_SR_TX_EMPTY_MASK) && (rx_words > 1)) { | 314 | if ((sr & XSPI_SR_TX_EMPTY_MASK) && (rx_words > 1)) { |
304 | xilinx_spi_rx(xspi); | 315 | xilinx_spi_rx(xspi); |
305 | rx_words--; | 316 | rx_words--; |