Commit b2694260 authored by Sebastian von Ohr's avatar Sebastian von Ohr Committed by Vinod Koul

dmaengine: xilinx_dma: Add missing check for empty list

The DMA transfer might finish just after checking the state with
dma_cookie_status, but before the lock is acquired. Not checking
for an empty list in xilinx_dma_tx_status may result in reading
random data or data corruption when desc is written to. This can
be reliably triggered by using dma_sync_wait to wait for DMA
completion.
Signed-off-by: default avatarSebastian von Ohr <vonohr@smaract.com>
Tested-by: default avatarRadhey Shyam Pandey <radhey.shyam.pandey@xilinx.com>
Link: https://lore.kernel.org/r/20200303130518.333-1-vonohr@smaract.comSigned-off-by: default avatarVinod Koul <vkoul@kernel.org>
parent 172d59ec
...@@ -1230,16 +1230,16 @@ static enum dma_status xilinx_dma_tx_status(struct dma_chan *dchan, ...@@ -1230,16 +1230,16 @@ static enum dma_status xilinx_dma_tx_status(struct dma_chan *dchan,
return ret; return ret;
spin_lock_irqsave(&chan->lock, flags); spin_lock_irqsave(&chan->lock, flags);
if (!list_empty(&chan->active_list)) {
desc = list_last_entry(&chan->active_list, desc = list_last_entry(&chan->active_list,
struct xilinx_dma_tx_descriptor, node); struct xilinx_dma_tx_descriptor, node);
/* /*
* VDMA and simple mode do not support residue reporting, so the * VDMA and simple mode do not support residue reporting, so the
* residue field will always be 0. * residue field will always be 0.
*/ */
if (chan->has_sg && chan->xdev->dma_config->dmatype != XDMA_TYPE_VDMA) if (chan->has_sg && chan->xdev->dma_config->dmatype != XDMA_TYPE_VDMA)
residue = xilinx_dma_get_residue(chan, desc); residue = xilinx_dma_get_residue(chan, desc);
}
spin_unlock_irqrestore(&chan->lock, flags); spin_unlock_irqrestore(&chan->lock, flags);
dma_set_residue(txstate, residue); dma_set_residue(txstate, residue);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment