Re: [PATCH] spi: spacemit: prepare both DMA descriptors before submitting
Alex Elder <[email protected]> Wed, 22 Jul 2026 07:14:13 -0500
| Newsgroups | dev.linux.lists.spacemit,org.infradead.lists.linux-riscv,org.kernel.vger.linux-kernel,org.kernel.vger.linux-spi |
|---|---|
| Message-ID | <[email protected]> |
On 7/21/26 10:41 PM, [email protected] wrote: > From: surendra <[email protected]> Do you have a more complete identity? > k1_spi_dma_one() currently submits the TX DMA descriptor to the DMA engine > before preparing the RX DMA descriptor. If preparing the RX descriptor > subsequently fails, the function jumps to the fallback error path without > canceling or aborting the already submitted TX DMA descriptor. > > Fix this by preparing both the TX and RX descriptors before submitting > either of them to the DMA engine. > > Fixes: efcd8b9d1111 ("spi: spacemit: introduce SpacemiT K1 SPI controller driver") > Signed-off-by: surendra <[email protected]> This looks good to me. Reviewed-by: Alex Elder <[email protected]> > --- > drivers/spi/spi-spacemit-k1.c | 22 +++++++++++----------- > 1 file changed, 11 insertions(+), 11 deletions(-) > > diff --git a/drivers/spi/spi-spacemit-k1.c b/drivers/spi/spi-spacemit-k1.c > index 215fe66d27b4..96b41b67fcbf 100644 > --- a/drivers/spi/spi-spacemit-k1.c > +++ b/drivers/spi/spi-spacemit-k1.c > @@ -278,25 +278,25 @@ static int k1_spi_dma_one(struct spi_controller *host, struct spi_device *spi, > struct spi_transfer *transfer) > { > struct k1_spi_driver_data *drv_data = spi_controller_get_devdata(host); > - struct dma_async_tx_descriptor *desc; > + struct dma_async_tx_descriptor *txdesc, *rxdesc; > u32 val; > > - /* Prepare the TX descriptor and submit it */ > - desc = k1_spi_dma_prep(drv_data, transfer, true); > - if (!desc) > + /* Prepare the TX descriptor */ > + txdesc = k1_spi_dma_prep(drv_data, transfer, true); > + if (!txdesc) > goto fallback; > - dmaengine_submit(desc); > > - /* Prepare the RX descriptor and submit it */ > - desc = k1_spi_dma_prep(drv_data, transfer, false); > - if (!desc) > + /* Prepare the RX descriptor */ > + rxdesc = k1_spi_dma_prep(drv_data, transfer, false); > + if (!rxdesc) > goto fallback; > > /* When RX is complete we also know TX has completed */ > - desc->callback = k1_spi_dma_callback; > - desc->callback_param = drv_data; > + rxdesc->callback = k1_spi_dma_callback; > + rxdesc->callback_param = drv_data; > > - dmaengine_submit(desc); > + dmaengine_submit(txdesc); > + dmaengine_submit(rxdesc); > > val = readl(drv_data->base + SSP_TOP_CTRL); > val |= TOP_TRAIL; /* Trailing bytes handled by DMA */