From bf072af461c166964fb110cfcafccd752fbb4c64 Mon Sep 17 00:00:00 2001 From: Russell King - ARM Linux Date: Mon, 3 Jan 2011 22:31:24 +0000 Subject: ARM: PL08x: fix locking in tasklet Tasklets are run from an interruptible context. The slave DMA functions can be called from within IRQ handlers. Taking the spinlock without disabling interrupts allows an interrupt handler to run, which may try to take the spinlock again, resulting in deadlock. Fix this by using the irqsave spinlocks. Signed-off-by: Russell King Acked-by: Linus Walleij Signed-off-by: Dan Williams --- drivers/dma/amba-pl08x.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'drivers/dma/amba-pl08x.c') diff --git a/drivers/dma/amba-pl08x.c b/drivers/dma/amba-pl08x.c index 5d9a156..69cfb05 100644 --- a/drivers/dma/amba-pl08x.c +++ b/drivers/dma/amba-pl08x.c @@ -1627,11 +1627,12 @@ static void pl08x_tasklet(unsigned long data) struct pl08x_dma_chan *plchan = (struct pl08x_dma_chan *) data; struct pl08x_phy_chan *phychan = plchan->phychan; struct pl08x_driver_data *pl08x = plchan->host; + unsigned long flags; if (!plchan) BUG(); - spin_lock(&plchan->lock); + spin_lock_irqsave(&plchan->lock, flags); if (plchan->at) { dma_async_tx_callback callback = @@ -1728,7 +1729,7 @@ static void pl08x_tasklet(unsigned long data) } } - spin_unlock(&plchan->lock); + spin_unlock_irqrestore(&plchan->lock, flags); } static irqreturn_t pl08x_irq(int irq, void *dev) -- cgit v1.1