aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/spi
diff options
context:
space:
mode:
authorRicardo Ribalda Delgado <ricardo.ribalda@gmail.com>2015-01-28 07:23:44 -0500
committerMark Brown <broonie@kernel.org>2015-01-28 14:42:42 -0500
commit5fe11cc09ce81b000b1deadcdec3813fcb423c8c (patch)
tree030a436c3e6e28e80579c629aa398fc0655605e8 /drivers/spi
parent5b74d7a3b888fd3db6dce77eb11b3d55b64f6833 (diff)
spi/xilinx: Support cores with no interrupt
The core can run in polling mode. In fact, the performance of the core is similar (or even better), due to the fact most of the spi transactions are just a couple of bytes and there is one irq per transactions. When an mtd device is connected via spi, reading 8MB of data produces more than 80K interrupts (with irq disabling, context swith....) Signed-off-by: Ricardo Ribalda Delgado <ricardo.ribalda@gmail.com> Signed-off-by: Mark Brown <broonie@kernel.org>
Diffstat (limited to 'drivers/spi')
-rw-r--r--drivers/spi/spi-xilinx.c33
1 files changed, 19 insertions, 14 deletions
diff --git a/drivers/spi/spi-xilinx.c b/drivers/spi/spi-xilinx.c
index 12b311ed9bfa..f21e857d54b1 100644
--- a/drivers/spi/spi-xilinx.c
+++ b/drivers/spi/spi-xilinx.c
@@ -173,8 +173,11 @@ static void xspi_init_hw(struct xilinx_spi *xspi)
173 xspi->write_fn(XSPI_INTR_TX_EMPTY, 173 xspi->write_fn(XSPI_INTR_TX_EMPTY,
174 regs_base + XIPIF_V123B_IIER_OFFSET); 174 regs_base + XIPIF_V123B_IIER_OFFSET);
175 /* Enable the global IPIF interrupt */ 175 /* Enable the global IPIF interrupt */
176 xspi->write_fn(XIPIF_V123B_GINTR_ENABLE, 176 if (xspi->irq >= 0)
177 regs_base + XIPIF_V123B_DGIER_OFFSET); 177 xspi->write_fn(XIPIF_V123B_GINTR_ENABLE,
178 regs_base + XIPIF_V123B_DGIER_OFFSET);
179 else
180 xspi->write_fn(0, regs_base + XIPIF_V123B_DGIER_OFFSET);
178 /* Deselect the slave on the SPI bus */ 181 /* Deselect the slave on the SPI bus */
179 xspi->write_fn(0xffff, regs_base + XSPI_SSR_OFFSET); 182 xspi->write_fn(0xffff, regs_base + XSPI_SSR_OFFSET);
180 /* Disable the transmitter, enable Manual Slave Select Assertion, 183 /* Disable the transmitter, enable Manual Slave Select Assertion,
@@ -264,7 +267,12 @@ static int xilinx_spi_txrx_bufs(struct spi_device *spi, struct spi_transfer *t)
264 ~XSPI_CR_TRANS_INHIBIT; 267 ~XSPI_CR_TRANS_INHIBIT;
265 xspi->write_fn(cr, xspi->regs + XSPI_CR_OFFSET); 268 xspi->write_fn(cr, xspi->regs + XSPI_CR_OFFSET);
266 269
267 wait_for_completion(&xspi->done); 270 if (xspi->irq >= 0)
271 wait_for_completion(&xspi->done);
272 else
273 while (!(xspi->read_fn(xspi->regs + XSPI_SR_OFFSET) &
274 XSPI_SR_TX_EMPTY_MASK))
275 ;
268 276
269 /* A transmit has just completed. Process received data and 277 /* A transmit has just completed. Process received data and
270 * check for more data to transmit. Always inhibit the 278 * check for more data to transmit. Always inhibit the
@@ -419,20 +427,17 @@ static int xilinx_spi_probe(struct platform_device *pdev)
419 427
420 xspi->buffer_size = xilinx_spi_find_buffer_size(xspi); 428 xspi->buffer_size = xilinx_spi_find_buffer_size(xspi);
421 429
422 /* SPI controller initializations */
423 xspi_init_hw(xspi);
424
425 xspi->irq = platform_get_irq(pdev, 0); 430 xspi->irq = platform_get_irq(pdev, 0);
426 if (xspi->irq < 0) { 431 if (xspi->irq >= 0) {
427 ret = xspi->irq; 432 /* Register for SPI Interrupt */
428 goto put_master; 433 ret = devm_request_irq(&pdev->dev, xspi->irq, xilinx_spi_irq, 0,
434 dev_name(&pdev->dev), xspi);
435 if (ret)
436 goto put_master;
429 } 437 }
430 438
431 /* Register for SPI Interrupt */ 439 /* SPI controller initializations */
432 ret = devm_request_irq(&pdev->dev, xspi->irq, xilinx_spi_irq, 0, 440 xspi_init_hw(xspi);
433 dev_name(&pdev->dev), xspi);
434 if (ret)
435 goto put_master;
436 441
437 ret = spi_bitbang_start(&xspi->bitbang); 442 ret = spi_bitbang_start(&xspi->bitbang);
438 if (ret) { 443 if (ret) {