aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/sky2.c
diff options
context:
space:
mode:
authorshemminger@osdl.org <shemminger@osdl.org>2005-11-30 14:45:19 -0500
committerJeff Garzik <jgarzik@pobox.com>2005-12-01 02:20:20 -0500
commit2224795d7e4c7f7e44fe21f0fa067d62539308fb (patch)
tree6414d3d4307daa181b6fc2b19762bd75f2d19ba7 /drivers/net/sky2.c
parent018d1c667ef4dce5299dd79d38447840789c97d6 (diff)
[PATCH] sky2: dual port tx completion
Sometimes on dual port cards, one tx complete may cover both ports. To handle that rearrange poll routine to lookup at end. Signed-off-by: Stephen Hemminger <shemminger@osdl.org> Signed-off-by: Jeff Garzik <jgarzik@pobox.com>
Diffstat (limited to 'drivers/net/sky2.c')
-rw-r--r--drivers/net/sky2.c26
1 files changed, 16 insertions, 10 deletions
diff --git a/drivers/net/sky2.c b/drivers/net/sky2.c
index 1d5c3039f53a..52c7b1886314 100644
--- a/drivers/net/sky2.c
+++ b/drivers/net/sky2.c
@@ -1242,6 +1242,9 @@ static void sky2_tx_complete(struct sky2_port *sky2, u16 done)
1242 struct net_device *dev = sky2->netdev; 1242 struct net_device *dev = sky2->netdev;
1243 unsigned i; 1243 unsigned i;
1244 1244
1245 if (done == sky2->tx_cons)
1246 return;
1247
1245 if (unlikely(netif_msg_tx_done(sky2))) 1248 if (unlikely(netif_msg_tx_done(sky2)))
1246 printk(KERN_DEBUG "%s: tx done, up to %u\n", 1249 printk(KERN_DEBUG "%s: tx done, up to %u\n",
1247 dev->name, done); 1250 dev->name, done);
@@ -1711,16 +1714,18 @@ error:
1711 goto resubmit; 1714 goto resubmit;
1712} 1715}
1713 1716
1714/* Transmit ring index in reported status block is encoded as: 1717/*
1715 * 1718 * Check for transmit complete
1716 * | TXS2 | TXA2 | TXS1 | TXA1
1717 */ 1719 */
1718static inline u16 tx_index(u8 port, u32 status, u16 len) 1720static inline void sky2_tx_check(struct sky2_hw *hw, int port)
1719{ 1721{
1720 if (port == 0) 1722 struct net_device *dev = hw->dev[port];
1721 return status & 0xfff; 1723
1722 else 1724 if (dev && netif_running(dev)) {
1723 return ((status >> 24) & 0xff) | (len & 0xf) << 8; 1725 sky2_tx_complete(netdev_priv(dev),
1726 sky2_read16(hw, port == 0
1727 ? STAT_TXA1_RIDX : STAT_TXA2_RIDX));
1728 }
1724} 1729}
1725 1730
1726/* 1731/*
@@ -1803,8 +1808,7 @@ static int sky2_poll(struct net_device *dev0, int *budget)
1803 break; 1808 break;
1804 1809
1805 case OP_TXINDEXLE: 1810 case OP_TXINDEXLE:
1806 sky2_tx_complete(sky2, 1811 /* pick up transmit status later */
1807 tx_index(sky2->port, status, length));
1808 break; 1812 break;
1809 1813
1810 default: 1814 default:
@@ -1816,6 +1820,8 @@ static int sky2_poll(struct net_device *dev0, int *budget)
1816 } 1820 }
1817 1821
1818exit_loop: 1822exit_loop:
1823 sky2_tx_check(hw, 0);
1824 sky2_tx_check(hw, 1);
1819 1825
1820 mmiowb(); 1826 mmiowb();
1821 1827