@@ -291,6 +291,10 @@ struct atmel_spi {
291291 struct spi_transfer * current_transfer ;
292292 int current_remaining_bytes ;
293293 int done_status ;
294+ dma_addr_t dma_addr_rx_bbuf ;
295+ dma_addr_t dma_addr_tx_bbuf ;
296+ void * addr_rx_bbuf ;
297+ void * addr_tx_bbuf ;
294298
295299 struct completion xfer_completion ;
296300
@@ -436,6 +440,11 @@ static void atmel_spi_unlock(struct atmel_spi *as) __releases(&as->lock)
436440 spin_unlock_irqrestore (& as -> lock , as -> flags );
437441}
438442
443+ static inline bool atmel_spi_is_vmalloc_xfer (struct spi_transfer * xfer )
444+ {
445+ return is_vmalloc_addr (xfer -> tx_buf ) || is_vmalloc_addr (xfer -> rx_buf );
446+ }
447+
439448static inline bool atmel_spi_use_dma (struct atmel_spi * as ,
440449 struct spi_transfer * xfer )
441450{
@@ -448,7 +457,12 @@ static bool atmel_spi_can_dma(struct spi_master *master,
448457{
449458 struct atmel_spi * as = spi_master_get_devdata (master );
450459
451- return atmel_spi_use_dma (as , xfer );
460+ if (IS_ENABLED (CONFIG_SOC_SAM_V4_V5 ))
461+ return atmel_spi_use_dma (as , xfer ) &&
462+ !atmel_spi_is_vmalloc_xfer (xfer );
463+ else
464+ return atmel_spi_use_dma (as , xfer );
465+
452466}
453467
454468static int atmel_spi_dma_slave_config (struct atmel_spi * as ,
@@ -594,6 +608,11 @@ static void dma_callback(void *data)
594608 struct spi_master * master = data ;
595609 struct atmel_spi * as = spi_master_get_devdata (master );
596610
611+ if (is_vmalloc_addr (as -> current_transfer -> rx_buf ) &&
612+ IS_ENABLED (CONFIG_SOC_SAM_V4_V5 )) {
613+ memcpy (as -> current_transfer -> rx_buf , as -> addr_rx_bbuf ,
614+ as -> current_transfer -> len );
615+ }
597616 complete (& as -> xfer_completion );
598617}
599618
@@ -744,17 +763,41 @@ static int atmel_spi_next_xfer_dma_submit(struct spi_master *master,
744763 goto err_exit ;
745764
746765 /* Send both scatterlists */
747- rxdesc = dmaengine_prep_slave_sg (rxchan ,
748- xfer -> rx_sg .sgl , xfer -> rx_sg .nents ,
749- DMA_FROM_DEVICE ,
750- DMA_PREP_INTERRUPT | DMA_CTRL_ACK );
766+ if (atmel_spi_is_vmalloc_xfer (xfer ) &&
767+ IS_ENABLED (CONFIG_SOC_SAM_V4_V5 )) {
768+ rxdesc = dmaengine_prep_slave_single (rxchan ,
769+ as -> dma_addr_rx_bbuf ,
770+ xfer -> len ,
771+ DMA_FROM_DEVICE ,
772+ DMA_PREP_INTERRUPT |
773+ DMA_CTRL_ACK );
774+ } else {
775+ rxdesc = dmaengine_prep_slave_sg (rxchan ,
776+ xfer -> rx_sg .sgl ,
777+ xfer -> rx_sg .nents ,
778+ DMA_FROM_DEVICE ,
779+ DMA_PREP_INTERRUPT |
780+ DMA_CTRL_ACK );
781+ }
751782 if (!rxdesc )
752783 goto err_dma ;
753784
754- txdesc = dmaengine_prep_slave_sg (txchan ,
755- xfer -> tx_sg .sgl , xfer -> tx_sg .nents ,
756- DMA_TO_DEVICE ,
757- DMA_PREP_INTERRUPT | DMA_CTRL_ACK );
785+ if (atmel_spi_is_vmalloc_xfer (xfer ) &&
786+ IS_ENABLED (CONFIG_SOC_SAM_V4_V5 )) {
787+ memcpy (as -> addr_tx_bbuf , xfer -> tx_buf , xfer -> len );
788+ txdesc = dmaengine_prep_slave_single (txchan ,
789+ as -> dma_addr_tx_bbuf ,
790+ xfer -> len , DMA_TO_DEVICE ,
791+ DMA_PREP_INTERRUPT |
792+ DMA_CTRL_ACK );
793+ } else {
794+ txdesc = dmaengine_prep_slave_sg (txchan ,
795+ xfer -> tx_sg .sgl ,
796+ xfer -> tx_sg .nents ,
797+ DMA_TO_DEVICE ,
798+ DMA_PREP_INTERRUPT |
799+ DMA_CTRL_ACK );
800+ }
758801 if (!txdesc )
759802 goto err_dma ;
760803
@@ -1426,27 +1469,7 @@ static void atmel_get_caps(struct atmel_spi *as)
14261469
14271470 as -> caps .is_spi2 = version > 0x121 ;
14281471 as -> caps .has_wdrbt = version >= 0x210 ;
1429- #ifdef CONFIG_SOC_SAM_V4_V5
1430- /*
1431- * Atmel SoCs based on ARM9 (SAM9x) cores should not use spi_map_buf()
1432- * since this later function tries to map buffers with dma_map_sg()
1433- * even if they have not been allocated inside DMA-safe areas.
1434- * On SoCs based on Cortex A5 (SAMA5Dx), it works anyway because for
1435- * those ARM cores, the data cache follows the PIPT model.
1436- * Also the L2 cache controller of SAMA5D2 uses the PIPT model too.
1437- * In case of PIPT caches, there cannot be cache aliases.
1438- * However on ARM9 cores, the data cache follows the VIVT model, hence
1439- * the cache aliases issue can occur when buffers are allocated from
1440- * DMA-unsafe areas, by vmalloc() for instance, where cache coherency is
1441- * not taken into account or at least not handled completely (cache
1442- * lines of aliases are not invalidated).
1443- * This is not a theorical issue: it was reproduced when trying to mount
1444- * a UBI file-system on a at91sam9g35ek board.
1445- */
1446- as -> caps .has_dma_support = false;
1447- #else
14481472 as -> caps .has_dma_support = version >= 0x212 ;
1449- #endif
14501473 as -> caps .has_pdc_support = version < 0x212 ;
14511474}
14521475
@@ -1573,6 +1596,30 @@ static int atmel_spi_probe(struct platform_device *pdev)
15731596 as -> use_pdc = true;
15741597 }
15751598
1599+ if (IS_ENABLED (CONFIG_SOC_SAM_V4_V5 )) {
1600+ as -> addr_rx_bbuf = dma_alloc_coherent (& pdev -> dev ,
1601+ SPI_MAX_DMA_XFER ,
1602+ & as -> dma_addr_rx_bbuf ,
1603+ GFP_KERNEL | GFP_DMA );
1604+ if (!as -> addr_rx_bbuf ) {
1605+ as -> use_dma = false;
1606+ } else {
1607+ as -> addr_tx_bbuf = dma_alloc_coherent (& pdev -> dev ,
1608+ SPI_MAX_DMA_XFER ,
1609+ & as -> dma_addr_tx_bbuf ,
1610+ GFP_KERNEL | GFP_DMA );
1611+ if (!as -> addr_tx_bbuf ) {
1612+ as -> use_dma = false;
1613+ dma_free_coherent (& pdev -> dev , SPI_MAX_DMA_XFER ,
1614+ as -> addr_rx_bbuf ,
1615+ as -> dma_addr_rx_bbuf );
1616+ }
1617+ }
1618+ if (!as -> use_dma )
1619+ dev_info (master -> dev .parent ,
1620+ " can not allocate dma coherent memory\n" );
1621+ }
1622+
15761623 if (as -> caps .has_dma_support && !as -> use_dma )
15771624 dev_info (& pdev -> dev , "Atmel SPI Controller using PIO only\n" );
15781625
@@ -1657,6 +1704,14 @@ static int atmel_spi_remove(struct platform_device *pdev)
16571704 if (as -> use_dma ) {
16581705 atmel_spi_stop_dma (master );
16591706 atmel_spi_release_dma (master );
1707+ if (IS_ENABLED (CONFIG_SOC_SAM_V4_V5 )) {
1708+ dma_free_coherent (& pdev -> dev , SPI_MAX_DMA_XFER ,
1709+ as -> addr_tx_bbuf ,
1710+ as -> dma_addr_tx_bbuf );
1711+ dma_free_coherent (& pdev -> dev , SPI_MAX_DMA_XFER ,
1712+ as -> addr_rx_bbuf ,
1713+ as -> dma_addr_rx_bbuf );
1714+ }
16601715 }
16611716
16621717 spin_lock_irq (& as -> lock );
0 commit comments