Skip to content

Commit

Permalink
drivers/ieee802154/at86rf230: rework irq handler
Browse files Browse the repository at this point in the history
Fix LOCKDEP bug message for the irq handler spinlock.
Make the irq processing code more explicit and stable.

Signed-off-by: Alexander Smirnov <[email protected]>
Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
alex-bluesman authored and davem330 committed Jul 12, 2012
1 parent 4d27de1 commit 5b00f2e
Showing 1 changed file with 18 additions and 14 deletions.
32 changes: 18 additions & 14 deletions drivers/ieee802154/at86rf230.c
Original file line number Diff line number Diff line change
Expand Up @@ -543,6 +543,13 @@ at86rf230_xmit(struct ieee802154_dev *dev, struct sk_buff *skb)
int rc;
unsigned long flags;

spin_lock(&lp->lock);
if (lp->irq_disabled) {
spin_unlock(&lp->lock);
return -EBUSY;
}
spin_unlock(&lp->lock);

might_sleep();

rc = at86rf230_state(dev, STATE_FORCE_TX_ON);
Expand Down Expand Up @@ -592,12 +599,8 @@ static int at86rf230_rx(struct at86rf230_local *lp)
if (!skb)
return -ENOMEM;

if (at86rf230_write_subreg(lp, SR_RX_PDT_DIS, 1) ||
at86rf230_read_fbuf(lp, skb_put(skb, len), &len, &lqi) ||
at86rf230_write_subreg(lp, SR_RX_SAFE_MODE, 1) ||
at86rf230_write_subreg(lp, SR_RX_PDT_DIS, 0)) {
if (at86rf230_read_fbuf(lp, skb_put(skb, len), &len, &lqi))
goto err;
}

if (len < 2)
goto err;
Expand Down Expand Up @@ -633,7 +636,6 @@ static void at86rf230_irqwork(struct work_struct *work)
int rc;
unsigned long flags;

spin_lock_irqsave(&lp->lock, flags);
rc = at86rf230_read_subreg(lp, RG_IRQ_STATUS, 0xff, 0, &val);
status |= val;

Expand All @@ -643,31 +645,33 @@ static void at86rf230_irqwork(struct work_struct *work)
status &= ~IRQ_TRX_UR; /* FIXME: possibly handle ???*/

if (status & IRQ_TRX_END) {
spin_lock_irqsave(&lp->lock, flags);
status &= ~IRQ_TRX_END;
if (lp->is_tx) {
lp->is_tx = 0;
spin_unlock_irqrestore(&lp->lock, flags);
complete(&lp->tx_complete);
} else {
spin_unlock_irqrestore(&lp->lock, flags);
at86rf230_rx(lp);
}
}

if (lp->irq_disabled) {
lp->irq_disabled = 0;
enable_irq(lp->spi->irq);
}
spin_lock_irqsave(&lp->lock, flags);
lp->irq_disabled = 0;
spin_unlock_irqrestore(&lp->lock, flags);

enable_irq(lp->spi->irq);
}

static irqreturn_t at86rf230_isr(int irq, void *data)
{
struct at86rf230_local *lp = data;

disable_irq_nosync(irq);

spin_lock(&lp->lock);
if (!lp->irq_disabled) {
disable_irq_nosync(irq);
lp->irq_disabled = 1;
}
lp->irq_disabled = 1;
spin_unlock(&lp->lock);

schedule_work(&lp->irqwork);
Expand Down

0 comments on commit 5b00f2e

Please sign in to comment.