From: DDD <Dongdong.deng@windriver.com>
To: Nicolas Pitre <nico@cam.org>, David Miller <davem@davemloft.net>
Cc: Matt Mackall <mpm@selenic.com>,
lkml <linux-kernel@vger.kernel.org>,
netdev@vger.kernel.org, Jason Wessel <jason.wessel@windriver.com>
Subject: [PATCH] [net] smc91x: let smc91x work well under netpoll
Date: Mon, 24 Aug 2009 11:42:31 +0800 [thread overview]
Message-ID: <1251085351.6588.21.camel@dengdd-desktop> (raw)
In-Reply-To: <alpine.LFD.2.00.0908211304000.6044@xanadu.home>
The NETPOLL requires that interrupts remain disabled in its callbacks.
Using *_irq_save()/irq_restore() to replace *_irq_disable()/irq_enable()
functions in NETPOLL's callbacks of smc91x, so that it doesn't enable
interrupts when already disabled, and kgdboe/netconsole would work
properly over smc91x.
Signed-off-by: Dongdong Deng <dongdong.deng@windriver.com>
Acked-by: Nicolas Pitre <nico@cam.org>
---
drivers/net/smc91x.c | 40 ++++++++++++++++++++++------------------
1 files changed, 22 insertions(+), 18 deletions(-)
diff --git a/drivers/net/smc91x.c b/drivers/net/smc91x.c
index 1c70e99..9da1fa1 100644
--- a/drivers/net/smc91x.c
+++ b/drivers/net/smc91x.c
@@ -196,21 +196,23 @@ static void PRINT_PKT(u_char *buf, int length)
/* this enables an interrupt in the interrupt mask register */
#define SMC_ENABLE_INT(lp, x) do { \
unsigned char mask; \
- spin_lock_irq(&lp->lock); \
+ unsigned long smc_enable_flags; \
+ spin_lock_irqsave(&lp->lock, smc_enable_flags); \
mask = SMC_GET_INT_MASK(lp); \
mask |= (x); \
SMC_SET_INT_MASK(lp, mask); \
- spin_unlock_irq(&lp->lock); \
+ spin_unlock_irqrestore(&lp->lock, smc_enable_flags); \
} while (0)
/* this disables an interrupt from the interrupt mask register */
#define SMC_DISABLE_INT(lp, x) do { \
unsigned char mask; \
- spin_lock_irq(&lp->lock); \
+ unsigned long smc_disable_flags; \
+ spin_lock_irqsave(&lp->lock, smc_disable_flags); \
mask = SMC_GET_INT_MASK(lp); \
mask &= ~(x); \
SMC_SET_INT_MASK(lp, mask); \
- spin_unlock_irq(&lp->lock); \
+ spin_unlock_irqrestore(&lp->lock, smc_disable_flags); \
} while (0)
/*
@@ -520,21 +522,21 @@ static inline void smc_rcv(struct net_device *dev)
* any other concurrent access and C would always interrupt B. But life
* isn't that easy in a SMP world...
*/
-#define smc_special_trylock(lock) \
+#define smc_special_trylock(lock, flags) \
({ \
int __ret; \
- local_irq_disable(); \
+ local_irq_save(flags); \
__ret = spin_trylock(lock); \
if (!__ret) \
- local_irq_enable(); \
+ local_irq_restore(flags); \
__ret; \
})
-#define smc_special_lock(lock) spin_lock_irq(lock)
-#define smc_special_unlock(lock) spin_unlock_irq(lock)
+#define smc_special_lock(lock, flags) spin_lock_irq(lock, flags)
+#define smc_special_unlock(lock, flags) spin_unlock_irqrestore(lock, flags)
#else
-#define smc_special_trylock(lock) (1)
-#define smc_special_lock(lock) do { } while (0)
-#define smc_special_unlock(lock) do { } while (0)
+#define smc_special_trylock(lock, flags) (1)
+#define smc_special_lock(lock, flags) do { } while (0)
+#define smc_special_unlock(lock, flags) do { } while (0)
#endif
/*
@@ -548,10 +550,11 @@ static void smc_hardware_send_pkt(unsigned long data)
struct sk_buff *skb;
unsigned int packet_no, len;
unsigned char *buf;
+ unsigned long flags;
DBG(3, "%s: %s\n", dev->name, __func__);
- if (!smc_special_trylock(&lp->lock)) {
+ if (!smc_special_trylock(&lp->lock, flags)) {
netif_stop_queue(dev);
tasklet_schedule(&lp->tx_task);
return;
@@ -559,7 +562,7 @@ static void smc_hardware_send_pkt(unsigned long data)
skb = lp->pending_tx_skb;
if (unlikely(!skb)) {
- smc_special_unlock(&lp->lock);
+ smc_special_unlock(&lp->lock, flags);
return;
}
lp->pending_tx_skb = NULL;
@@ -569,7 +572,7 @@ static void smc_hardware_send_pkt(unsigned long data)
printk("%s: Memory allocation failed.\n", dev->name);
dev->stats.tx_errors++;
dev->stats.tx_fifo_errors++;
- smc_special_unlock(&lp->lock);
+ smc_special_unlock(&lp->lock, flags);
goto done;
}
@@ -608,7 +611,7 @@ static void smc_hardware_send_pkt(unsigned long data)
/* queue the packet for TX */
SMC_SET_MMU_CMD(lp, MC_ENQUEUE);
- smc_special_unlock(&lp->lock);
+ smc_special_unlock(&lp->lock, flags);
dev->trans_start = jiffies;
dev->stats.tx_packets++;
@@ -633,6 +636,7 @@ static int smc_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
struct smc_local *lp = netdev_priv(dev);
void __iomem *ioaddr = lp->base;
unsigned int numPages, poll_count, status;
+ unsigned long flags;
DBG(3, "%s: %s\n", dev->name, __func__);
@@ -658,7 +662,7 @@ static int smc_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
return 0;
}
- smc_special_lock(&lp->lock);
+ smc_special_lock(&lp->lock, flags);
/* now, try to allocate the memory */
SMC_SET_MMU_CMD(lp, MC_ALLOC | numPages);
@@ -676,7 +680,7 @@ static int smc_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
}
} while (--poll_count);
- smc_special_unlock(&lp->lock);
+ smc_special_unlock(&lp->lock, flags);
lp->pending_tx_skb = skb;
if (!poll_count) {
--
1.6.0.4
next prev parent reply other threads:[~2009-08-24 3:30 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-08-21 13:33 [PATCH 1/2] netpoll: warning for ndo_start_xmit returns with interrupts enabled DDD
2009-08-21 13:34 ` [PATCH 2/2] drivers/net: fixed drivers that support netpoll use ndo_start_xmit() DDD
2009-08-21 15:26 ` Matt Mackall
2009-08-24 2:50 ` David Miller
2009-08-21 13:40 ` [RFC][PATCH] smc91x: let smc91x work well with netpoll DDD
2009-08-21 17:13 ` Nicolas Pitre
2009-08-24 3:42 ` DDD [this message]
2009-08-24 5:59 ` [PATCH] [net] smc91x: let smc91x work well under netpoll David Miller
2009-08-24 2:50 ` [PATCH 1/2] netpoll: warning for ndo_start_xmit returns with interrupts enabled David Miller
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1251085351.6588.21.camel@dengdd-desktop \
--to=dongdong.deng@windriver.com \
--cc=davem@davemloft.net \
--cc=jason.wessel@windriver.com \
--cc=linux-kernel@vger.kernel.org \
--cc=mpm@selenic.com \
--cc=netdev@vger.kernel.org \
--cc=nico@cam.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox