Merge remote-tracking branches 'spi/fix/omap2' and 'spi/fix/rockchip' into spi-linus
authorMark Brown <broonie@kernel.org>
Mon, 4 Apr 2016 17:05:49 +0000 (10:05 -0700)
committerMark Brown <broonie@kernel.org>
Mon, 4 Apr 2016 17:05:49 +0000 (10:05 -0700)
drivers/spi/spi-omap2-mcspi.c
drivers/spi/spi-rockchip.c

index 0caa3c8..43a02e3 100644 (file)
@@ -423,16 +423,12 @@ static void omap2_mcspi_tx_dma(struct spi_device *spi,
 
        if (mcspi_dma->dma_tx) {
                struct dma_async_tx_descriptor *tx;
-               struct scatterlist sg;
 
                dmaengine_slave_config(mcspi_dma->dma_tx, &cfg);
 
-               sg_init_table(&sg, 1);
-               sg_dma_address(&sg) = xfer->tx_dma;
-               sg_dma_len(&sg) = xfer->len;
-
-               tx = dmaengine_prep_slave_sg(mcspi_dma->dma_tx, &sg, 1,
-               DMA_MEM_TO_DEV, DMA_PREP_INTERRUPT | DMA_CTRL_ACK);
+               tx = dmaengine_prep_slave_sg(mcspi_dma->dma_tx, xfer->tx_sg.sgl,
+                                            xfer->tx_sg.nents, DMA_MEM_TO_DEV,
+                                            DMA_PREP_INTERRUPT | DMA_CTRL_ACK);
                if (tx) {
                        tx->callback = omap2_mcspi_tx_callback;
                        tx->callback_param = spi;
@@ -478,20 +474,15 @@ omap2_mcspi_rx_dma(struct spi_device *spi, struct spi_transfer *xfer,
 
        if (mcspi_dma->dma_rx) {
                struct dma_async_tx_descriptor *tx;
-               struct scatterlist sg;
 
                dmaengine_slave_config(mcspi_dma->dma_rx, &cfg);
 
                if ((l & OMAP2_MCSPI_CHCONF_TURBO) && mcspi->fifo_depth == 0)
                        dma_count -= es;
 
-               sg_init_table(&sg, 1);
-               sg_dma_address(&sg) = xfer->rx_dma;
-               sg_dma_len(&sg) = dma_count;
-
-               tx = dmaengine_prep_slave_sg(mcspi_dma->dma_rx, &sg, 1,
-                               DMA_DEV_TO_MEM, DMA_PREP_INTERRUPT |
-                               DMA_CTRL_ACK);
+               tx = dmaengine_prep_slave_sg(mcspi_dma->dma_rx, xfer->rx_sg.sgl,
+                                            xfer->rx_sg.nents, DMA_DEV_TO_MEM,
+                                            DMA_PREP_INTERRUPT | DMA_CTRL_ACK);
                if (tx) {
                        tx->callback = omap2_mcspi_rx_callback;
                        tx->callback_param = spi;
@@ -505,8 +496,6 @@ omap2_mcspi_rx_dma(struct spi_device *spi, struct spi_transfer *xfer,
        omap2_mcspi_set_dma_req(spi, 1, 1);
 
        wait_for_completion(&mcspi_dma->dma_rx_completion);
-       dma_unmap_single(mcspi->dev, xfer->rx_dma, count,
-                        DMA_FROM_DEVICE);
 
        if (mcspi->fifo_depth > 0)
                return count;
@@ -619,8 +608,6 @@ omap2_mcspi_txrx_dma(struct spi_device *spi, struct spi_transfer *xfer)
 
        if (tx != NULL) {
                wait_for_completion(&mcspi_dma->dma_tx_completion);
-               dma_unmap_single(mcspi->dev, xfer->tx_dma, xfer->len,
-                                DMA_TO_DEVICE);
 
                if (mcspi->fifo_depth > 0) {
                        irqstat_reg = mcspi->base + OMAP2_MCSPI_IRQSTATUS;
@@ -1087,6 +1074,16 @@ static void omap2_mcspi_cleanup(struct spi_device *spi)
                gpio_free(spi->cs_gpio);
 }
 
+static bool omap2_mcspi_can_dma(struct spi_master *master,
+                               struct spi_device *spi,
+                               struct spi_transfer *xfer)
+{
+       if (xfer->len < DMA_MIN_BYTES)
+               return false;
+
+       return true;
+}
+
 static int omap2_mcspi_work_one(struct omap2_mcspi *mcspi,
                struct spi_device *spi, struct spi_transfer *t)
 {
@@ -1268,32 +1265,6 @@ static int omap2_mcspi_transfer_one(struct spi_master *master,
                return -EINVAL;
        }
 
-       if (len < DMA_MIN_BYTES)
-               goto skip_dma_map;
-
-       if (mcspi_dma->dma_tx && tx_buf != NULL) {
-               t->tx_dma = dma_map_single(mcspi->dev, (void *) tx_buf,
-                               len, DMA_TO_DEVICE);
-               if (dma_mapping_error(mcspi->dev, t->tx_dma)) {
-                       dev_dbg(mcspi->dev, "dma %cX %d bytes error\n",
-                                       'T', len);
-                       return -EINVAL;
-               }
-       }
-       if (mcspi_dma->dma_rx && rx_buf != NULL) {
-               t->rx_dma = dma_map_single(mcspi->dev, rx_buf, t->len,
-                               DMA_FROM_DEVICE);
-               if (dma_mapping_error(mcspi->dev, t->rx_dma)) {
-                       dev_dbg(mcspi->dev, "dma %cX %d bytes error\n",
-                                       'R', len);
-                       if (tx_buf != NULL)
-                               dma_unmap_single(mcspi->dev, t->tx_dma,
-                                               len, DMA_TO_DEVICE);
-                       return -EINVAL;
-               }
-       }
-
-skip_dma_map:
        return omap2_mcspi_work_one(mcspi, spi, t);
 }
 
@@ -1377,6 +1348,7 @@ static int omap2_mcspi_probe(struct platform_device *pdev)
        master->transfer_one = omap2_mcspi_transfer_one;
        master->set_cs = omap2_mcspi_set_cs;
        master->cleanup = omap2_mcspi_cleanup;
+       master->can_dma = omap2_mcspi_can_dma;
        master->dev.of_node = node;
        master->max_speed_hz = OMAP2_MCSPI_MAX_FREQ;
        master->min_speed_hz = OMAP2_MCSPI_MAX_FREQ >> 15;
index 8f50a40..6c6c001 100644 (file)
@@ -534,7 +534,7 @@ static void rockchip_spi_config(struct rockchip_spi *rs)
        if (WARN_ON(rs->speed > MAX_SCLK_OUT))
                rs->speed = MAX_SCLK_OUT;
 
-       /* the minimum divsor is 2 */
+       /* the minimum divisor is 2 */
        if (rs->max_freq < 2 * rs->speed) {
                clk_set_rate(rs->spiclk, 2 * rs->speed);
                rs->max_freq = clk_get_rate(rs->spiclk);
@@ -730,23 +730,27 @@ static int rockchip_spi_probe(struct platform_device *pdev)
        master->transfer_one = rockchip_spi_transfer_one;
        master->handle_err = rockchip_spi_handle_err;
 
-       rs->dma_tx.ch = dma_request_slave_channel(rs->dev, "tx");
-       if (IS_ERR_OR_NULL(rs->dma_tx.ch)) {
+       rs->dma_tx.ch = dma_request_chan(rs->dev, "tx");
+       if (IS_ERR(rs->dma_tx.ch)) {
                /* Check tx to see if we need defer probing driver */
                if (PTR_ERR(rs->dma_tx.ch) == -EPROBE_DEFER) {
                        ret = -EPROBE_DEFER;
                        goto err_get_fifo_len;
                }
                dev_warn(rs->dev, "Failed to request TX DMA channel\n");
+               rs->dma_tx.ch = NULL;
        }
 
-       rs->dma_rx.ch = dma_request_slave_channel(rs->dev, "rx");
-       if (!rs->dma_rx.ch) {
-               if (rs->dma_tx.ch) {
+       rs->dma_rx.ch = dma_request_chan(rs->dev, "rx");
+       if (IS_ERR(rs->dma_rx.ch)) {
+               if (PTR_ERR(rs->dma_rx.ch) == -EPROBE_DEFER) {
                        dma_release_channel(rs->dma_tx.ch);
                        rs->dma_tx.ch = NULL;
+                       ret = -EPROBE_DEFER;
+                       goto err_get_fifo_len;
                }
                dev_warn(rs->dev, "Failed to request RX DMA channel\n");
+               rs->dma_rx.ch = NULL;
        }
 
        if (rs->dma_tx.ch && rs->dma_rx.ch) {