[PATCH] AMD Au1xx0: fix Ethernet TX stats
authorSergei Shtylylov <sshtylyov@ru.mvista.com>
Wed, 22 Mar 2006 06:53:52 +0000 (22:53 -0800)
committerJeff Garzik <jeff@garzik.org>
Thu, 23 Mar 2006 01:29:29 +0000 (20:29 -0500)
With Au1xx0 Ethernet driver, TX bytes/packets always remain zero.  The
problem seems to be that when packet has been transmitted, the length word
in DMA buffer is zero.

The patch updates the TX stats when a buffer is fed to DMA.  The initial
2.4 patch was posted to linux-mips@linux-mips.org by Thomas Lange 21 Jan
2005.

Signed-off-by: Thomas Lange <thomas@corelatus.se>
Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com>
Cc: Jordan Crouse <jordan.crouse@amd.com>
Cc: Jeff Garzik <jgarzik@pobox.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
drivers/net/au1000_eth.c

index cd0b1dccfb6102119334a357762b1c93502fec72..1363083b4d83e5262646d3af5713e6a4d96a7a6d 100644 (file)
@@ -90,8 +90,6 @@ static void au1000_tx_timeout(struct net_device *);
 static int au1000_set_config(struct net_device *dev, struct ifmap *map);
 static void set_rx_mode(struct net_device *);
 static struct net_device_stats *au1000_get_stats(struct net_device *);
-static inline void update_tx_stats(struct net_device *, u32, u32);
-static inline void update_rx_stats(struct net_device *, u32);
 static void au1000_timer(unsigned long);
 static int au1000_ioctl(struct net_device *, struct ifreq *, int);
 static int mdio_read(struct net_device *, int, int);
@@ -1825,16 +1823,11 @@ static void __exit au1000_cleanup_module(void)
        }
 }
 
-
-static inline void 
-update_tx_stats(struct net_device *dev, u32 status, u32 pkt_len)
+static void update_tx_stats(struct net_device *dev, u32 status)
 {
        struct au1000_private *aup = (struct au1000_private *) dev->priv;
        struct net_device_stats *ps = &aup->stats;
 
-       ps->tx_packets++;
-       ps->tx_bytes += pkt_len;
-
        if (status & TX_FRAME_ABORTED) {
                if (dev->if_port == IF_PORT_100BASEFX) {
                        if (status & (TX_JAB_TIMEOUT | TX_UNDERRUN)) {
@@ -1867,7 +1860,7 @@ static void au1000_tx_ack(struct net_device *dev)
        ptxd = aup->tx_dma_ring[aup->tx_tail];
 
        while (ptxd->buff_stat & TX_T_DONE) {
-               update_tx_stats(dev, ptxd->status, ptxd->len & 0x3ff);
+               update_tx_stats(dev, ptxd->status);
                ptxd->buff_stat &= ~TX_T_DONE;
                ptxd->len = 0;
                au_sync();
@@ -1889,6 +1882,7 @@ static void au1000_tx_ack(struct net_device *dev)
 static int au1000_tx(struct sk_buff *skb, struct net_device *dev)
 {
        struct au1000_private *aup = (struct au1000_private *) dev->priv;
+       struct net_device_stats *ps = &aup->stats;
        volatile tx_dma_t *ptxd;
        u32 buff_stat;
        db_dest_t *pDB;
@@ -1908,7 +1902,7 @@ static int au1000_tx(struct sk_buff *skb, struct net_device *dev)
                return 1;
        }
        else if (buff_stat & TX_T_DONE) {
-               update_tx_stats(dev, ptxd->status, ptxd->len & 0x3ff);
+               update_tx_stats(dev, ptxd->status);
                ptxd->len = 0;
        }
 
@@ -1928,6 +1922,9 @@ static int au1000_tx(struct sk_buff *skb, struct net_device *dev)
        else
                ptxd->len = skb->len;
 
+       ps->tx_packets++;
+       ps->tx_bytes += ptxd->len;
+
        ptxd->buff_stat = pDB->dma_addr | TX_DMA_ENABLE;
        au_sync();
        dev_kfree_skb(skb);
@@ -1936,7 +1933,6 @@ static int au1000_tx(struct sk_buff *skb, struct net_device *dev)
        return 0;
 }
 
-
 static inline void update_rx_stats(struct net_device *dev, u32 status)
 {
        struct au1000_private *aup = (struct au1000_private *) dev->priv;