Skip to content

Commit

Permalink
ARM: PL08x: fix deadlock in terminate_all
Browse files Browse the repository at this point in the history
Trying to disable a tasklet while holding a spinlock which the tasklet
will take is a recipe for deadlock - tasklet_disable() will wait for the
tasklet to finish running, which it will never do.  In any case, there
is not a corresponding tasklet_enable(), so once the tasklet is disabled,
it will never run again until reboot.

It's safe to just remove the tasklet_disable() as we remove all current
and pending descriptors before releasing this spinlock.  This means that
the tasklet will find no remaining work if it subsequently runs.

The only remaining issue is that the callback for an already submitted
txd may be in progress, or even called after terminate_all() returns.
There's not much that can be done about that as waiting for the callback
to complete before returning will also lead to deadlocks.

Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Acked-by: Linus Walleij <linus.walleij@stericsson.com>
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
  • Loading branch information
Russell King - ARM Linux authored and Dan Williams committed Jan 5, 2011
1 parent 9c0bb43 commit 98838f9
Showing 1 changed file with 0 additions and 2 deletions.
2 changes: 0 additions & 2 deletions drivers/dma/amba-pl08x.c
Original file line number Diff line number Diff line change
Expand Up @@ -1560,8 +1560,6 @@ static int pl08x_control(struct dma_chan *chan, enum dma_ctrl_cmd cmd,
pl08x_put_phy_channel(pl08x, plchan->phychan);
plchan->phychan = NULL;
}
/* Stop any pending tasklet */
tasklet_disable(&plchan->tasklet);
/* Dequeue jobs and free LLIs */
if (plchan->at) {
pl08x_free_txd(pl08x, plchan->at);
Expand Down

0 comments on commit 98838f9

Please sign in to comment.