Netdev List
 help / color / mirror / Atom feed
* [PATCH] drivers/net: using spin_lock_irqsave() in net_send_packet()
@ 2009-07-13  6:27 Dongdong Deng
  2009-07-14 19:35 ` David Miller
  0 siblings, 1 reply; 2+ messages in thread
From: Dongdong Deng @ 2009-07-13  6:27 UTC (permalink / raw)
  To: davem; +Cc: netdev

spin_unlock_irq() will enable interrupt in net_send_packet(),
this patch changes it to spin_lock_irqsave/spin_lock_irqrestore,
so that it doesn't enable interrupts when already disabled,
and netconsole would work properly over cs89x0/isa-skeleton.

Call trace:
netconsole write_msg()
{
 ...
 -> spin_lock_irqsave();
        -> netpoll_send_udp()
          -> netpoll_send_skb()
            -> net_send_packet()
              ->...

 -> spin_unlock_irqrestore();
 ...
}

Signed-off-by: Dongdong Deng <dongdong.deng@windriver.com>
---
 drivers/net/cs89x0.c       |    7 ++++---
 drivers/net/isa-skeleton.c |    5 +++--
 2 files changed, 7 insertions(+), 5 deletions(-)

diff --git a/drivers/net/cs89x0.c b/drivers/net/cs89x0.c
index 3eee666..5d619ae 100644
--- a/drivers/net/cs89x0.c
+++ b/drivers/net/cs89x0.c
@@ -1523,6 +1523,7 @@ static void net_timeout(struct net_device *dev)
 
 static int net_send_packet(struct sk_buff *skb, struct net_device *dev)
 {
+	unsigned long flags;
 	struct net_local *lp = netdev_priv(dev);
 
 	if (net_debug > 3) {
@@ -1535,7 +1536,7 @@ static int net_send_packet(struct sk_buff *skb, struct net_device *dev)
                   ask the chip to start transmitting before the
                   whole packet has been completely uploaded. */
 
-	spin_lock_irq(&lp->lock);
+	spin_lock_irqsave(&lp->lock, flags);
 	netif_stop_queue(dev);
 
 	/* initiate a transmit sequence */
@@ -1549,13 +1550,13 @@ static int net_send_packet(struct sk_buff *skb, struct net_device *dev)
 		 * we're waiting for TxOk, so return 1 and requeue this packet.
 		 */
 
-		spin_unlock_irq(&lp->lock);
+		spin_unlock_irqrestore(&lp->lock, flags);
 		if (net_debug) printk("cs89x0: Tx buffer not free!\n");
 		return NETDEV_TX_BUSY;
 	}
 	/* Write the contents of the packet */
 	writewords(dev->base_addr, TX_FRAME_PORT,skb->data,(skb->len+1) >>1);
-	spin_unlock_irq(&lp->lock);
+	spin_unlock_irqrestore(&lp->lock, flags);
 	lp->stats.tx_bytes += skb->len;
 	dev->trans_start = jiffies;
 	dev_kfree_skb (skb);
diff --git a/drivers/net/isa-skeleton.c b/drivers/net/isa-skeleton.c
index 73585fd..d12377b 100644
--- a/drivers/net/isa-skeleton.c
+++ b/drivers/net/isa-skeleton.c
@@ -430,7 +430,8 @@ static int net_send_packet(struct sk_buff *skb, struct net_device *dev)
 	 * hardware interrupt handler.  Queue flow control is
 	 * thus managed under this lock as well.
 	 */
-	spin_lock_irq(&np->lock);
+	unsigned long flags;
+	spin_lock_irqsave(&np->lock, flags);
 
 	add_to_tx_ring(np, skb, length);
 	dev->trans_start = jiffies;
@@ -446,7 +447,7 @@ static int net_send_packet(struct sk_buff *skb, struct net_device *dev)
 	 * is when the transmit statistics are updated.
 	 */
 
-	spin_unlock_irq(&np->lock);
+	spin_unlock_irqrestore(&np->lock, flags);
 #else
 	/* This is the case for older hardware which takes
 	 * a single transmit buffer at a time, and it is
-- 
1.6.0.4


^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2009-07-14 19:34 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-07-13  6:27 [PATCH] drivers/net: using spin_lock_irqsave() in net_send_packet() Dongdong Deng
2009-07-14 19:35 ` David Miller

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox