summaryrefslogtreecommitdiff
path: root/drivers/dma
diff options
context:
space:
mode:
authorFancy Fang <chen.fang@freescale.com>2015-06-04 16:19:06 +0800
committerNitin Garg <nitin.garg@freescale.com>2015-09-17 09:23:32 -0500
commit7778f11634fdb149cbc4e5c6f55215044ba2b93e (patch)
tree4773ecca985a9fbd9b56137d6a67946cc7af3836 /drivers/dma
parenta1b2f9936808ccc32127f6e195ab365609c08396 (diff)
MLK-10607 dma: pxp-v3: fix race condition issue in pxp irq handler
Add pxp_chan spin lock calling in the pxp irq handler to avoid the simultaneous accesses of the pxp_chan lists data. Signed-off-by: Fancy Fang <chen.fang@freescale.com>
Diffstat (limited to 'drivers/dma')
-rw-r--r--drivers/dma/pxp/pxp_dma_v3.c5
1 files changed, 4 insertions, 1 deletions
diff --git a/drivers/dma/pxp/pxp_dma_v3.c b/drivers/dma/pxp/pxp_dma_v3.c
index 975258ecfcbd..68dc9f07f275 100644
--- a/drivers/dma/pxp/pxp_dma_v3.c
+++ b/drivers/dma/pxp/pxp_dma_v3.c
@@ -1594,7 +1594,7 @@ static irqreturn_t pxp_irq(int irq, void *dev_id)
struct pxp_tx_desc *desc;
dma_async_tx_callback callback;
void *callback_param;
- unsigned long flags;
+ unsigned long flags, flags0;
u32 hist_status;
int pxp_irq_status = 0;
@@ -1657,12 +1657,14 @@ static irqreturn_t pxp_irq(int irq, void *dev_id)
}
pxp_chan = list_entry(head.next, struct pxp_channel, list);
+ spin_lock_irqsave(&pxp_chan->lock, flags0);
list_del_init(&pxp_chan->list);
if (list_empty(&pxp_chan->active_list)) {
pr_debug("PXP_IRQ pxp_chan->active_list empty. chan_id %d\n",
pxp_chan->dma_chan.chan_id);
pxp->pxp_ongoing = 0;
+ spin_unlock_irqrestore(&pxp_chan->lock, flags0);
spin_unlock_irqrestore(&pxp->lock, flags);
return IRQ_NONE;
}
@@ -1685,6 +1687,7 @@ static irqreturn_t pxp_irq(int irq, void *dev_id)
list_splice_init(&desc->tx_list, &pxp_chan->free_list);
list_move(&desc->list, &pxp_chan->free_list);
+ spin_unlock_irqrestore(&pxp_chan->lock, flags0);
mutex_unlock(&hard_lock);
pxp->pxp_ongoing = 0;