diff options
-rw-r--r-- | drivers/net/skge.c | 22 |
1 files changed, 15 insertions, 7 deletions
diff --git a/drivers/net/skge.c b/drivers/net/skge.c index ea68d4d3d57c..389d0be35865 100644 --- a/drivers/net/skge.c +++ b/drivers/net/skge.c | |||
@@ -2627,7 +2627,7 @@ static int skge_poll(struct net_device *dev, int *budget) | |||
2627 | unsigned int to_do = min(dev->quota, *budget); | 2627 | unsigned int to_do = min(dev->quota, *budget); |
2628 | unsigned int work_done = 0; | 2628 | unsigned int work_done = 0; |
2629 | 2629 | ||
2630 | for (e = ring->to_clean; work_done < to_do; e = e->next) { | 2630 | for (e = ring->to_clean; prefetch(e->next), work_done < to_do; e = e->next) { |
2631 | struct skge_rx_desc *rd = e->desc; | 2631 | struct skge_rx_desc *rd = e->desc; |
2632 | struct sk_buff *skb; | 2632 | struct sk_buff *skb; |
2633 | u32 control; | 2633 | u32 control; |
@@ -2660,11 +2660,11 @@ static int skge_poll(struct net_device *dev, int *budget) | |||
2660 | if (work_done >= to_do) | 2660 | if (work_done >= to_do) |
2661 | return 1; /* not done */ | 2661 | return 1; /* not done */ |
2662 | 2662 | ||
2663 | local_irq_disable(); | 2663 | netif_rx_complete(dev); |
2664 | __netif_rx_complete(dev); | ||
2665 | hw->intr_mask |= portirqmask[skge->port]; | 2664 | hw->intr_mask |= portirqmask[skge->port]; |
2666 | skge_write32(hw, B0_IMSK, hw->intr_mask); | 2665 | skge_write32(hw, B0_IMSK, hw->intr_mask); |
2667 | local_irq_enable(); | 2666 | skge_read32(hw, B0_IMSK); |
2667 | |||
2668 | return 0; | 2668 | return 0; |
2669 | } | 2669 | } |
2670 | 2670 | ||
@@ -2676,7 +2676,7 @@ static inline void skge_tx_intr(struct net_device *dev) | |||
2676 | struct skge_element *e; | 2676 | struct skge_element *e; |
2677 | 2677 | ||
2678 | spin_lock(&skge->tx_lock); | 2678 | spin_lock(&skge->tx_lock); |
2679 | for (e = ring->to_clean; e != ring->to_use; e = e->next) { | 2679 | for (e = ring->to_clean; prefetch(e->next), e != ring->to_use; e = e->next) { |
2680 | struct skge_tx_desc *td = e->desc; | 2680 | struct skge_tx_desc *td = e->desc; |
2681 | u32 control; | 2681 | u32 control; |
2682 | 2682 | ||
@@ -2829,6 +2829,14 @@ static void skge_extirq(unsigned long data) | |||
2829 | local_irq_enable(); | 2829 | local_irq_enable(); |
2830 | } | 2830 | } |
2831 | 2831 | ||
2832 | static inline void skge_wakeup(struct net_device *dev) | ||
2833 | { | ||
2834 | struct skge_port *skge = netdev_priv(dev); | ||
2835 | |||
2836 | prefetch(skge->rx_ring.to_clean); | ||
2837 | netif_rx_schedule(dev); | ||
2838 | } | ||
2839 | |||
2832 | static irqreturn_t skge_intr(int irq, void *dev_id, struct pt_regs *regs) | 2840 | static irqreturn_t skge_intr(int irq, void *dev_id, struct pt_regs *regs) |
2833 | { | 2841 | { |
2834 | struct skge_hw *hw = dev_id; | 2842 | struct skge_hw *hw = dev_id; |
@@ -2840,12 +2848,12 @@ static irqreturn_t skge_intr(int irq, void *dev_id, struct pt_regs *regs) | |||
2840 | status &= hw->intr_mask; | 2848 | status &= hw->intr_mask; |
2841 | if (status & IS_R1_F) { | 2849 | if (status & IS_R1_F) { |
2842 | hw->intr_mask &= ~IS_R1_F; | 2850 | hw->intr_mask &= ~IS_R1_F; |
2843 | netif_rx_schedule(hw->dev[0]); | 2851 | skge_wakeup(hw->dev[0]); |
2844 | } | 2852 | } |
2845 | 2853 | ||
2846 | if (status & IS_R2_F) { | 2854 | if (status & IS_R2_F) { |
2847 | hw->intr_mask &= ~IS_R2_F; | 2855 | hw->intr_mask &= ~IS_R2_F; |
2848 | netif_rx_schedule(hw->dev[1]); | 2856 | skge_wakeup(hw->dev[1]); |
2849 | } | 2857 | } |
2850 | 2858 | ||
2851 | if (status & IS_XA1_F) | 2859 | if (status & IS_XA1_F) |