From f43b4ea962c7cccd74b04a60041f0a087cbe444d Mon Sep 17 00:00:00 2001
From: Felix Fietkau <nbd@openwrt.org>
Date: Mon, 12 Aug 2013 17:26:00 +0000
Subject: [PATCH] ar71xx: ethernet: cache skb->len in the tx function to avoid
 accessing it again in completion

Improves ethernet performance, especially during bridging

Signed-off-by: Felix Fietkau <nbd@openwrt.org>

SVN-Revision: 37761
---
 .../files/drivers/net/ethernet/atheros/ag71xx/ag71xx.h    | 7 +++++--
 .../drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c     | 8 +++++---
 2 files changed, 10 insertions(+), 5 deletions(-)

diff --git a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx.h b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx.h
index b9d95adaf6..6d51e722b0 100644
--- a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx.h
+++ b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx.h
@@ -91,8 +91,11 @@ struct ag71xx_buf {
 		void		*rx_buf;
 	};
 	struct ag71xx_desc	*desc;
-	dma_addr_t		dma_addr;
-	unsigned long		timestamp;
+	union {
+		dma_addr_t	dma_addr;
+		unsigned long	timestamp;
+	};
+	unsigned int		len;
 };
 
 struct ag71xx_ring {
diff --git a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
index 93071690e8..fc6be0e001 100644
--- a/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
+++ b/target/linux/ar71xx/files/drivers/net/ethernet/atheros/ag71xx/ag71xx_main.c
@@ -145,7 +145,7 @@ static void ag71xx_ring_tx_clean(struct ag71xx *ag)
 		}
 
 		if (ring->buf[i].skb) {
-			bytes_compl += ring->buf[i].skb->len;
+			bytes_compl += ring->buf[i].len;
 			pkts_compl++;
 			dev_kfree_skb_any(ring->buf[i].skb);
 		}
@@ -684,6 +684,7 @@ static netdev_tx_t ag71xx_hard_start_xmit(struct sk_buff *skb,
 				  DMA_TO_DEVICE);
 
 	netdev_sent_queue(dev, skb->len);
+	ring->buf[i].len = skb->len;
 	ring->buf[i].skb = skb;
 	ring->buf[i].timestamp = jiffies;
 
@@ -824,6 +825,7 @@ static int ag71xx_tx_packets(struct ag71xx *ag)
 		unsigned int i = ring->dirty % ring->size;
 		struct ag71xx_desc *desc = ring->buf[i].desc;
 		struct sk_buff *skb = ring->buf[i].skb;
+		int len = ring->buf[i].len;
 
 		if (!ag71xx_desc_empty(desc)) {
 			if (pdata->is_ar7240 &&
@@ -834,8 +836,8 @@ static int ag71xx_tx_packets(struct ag71xx *ag)
 
 		ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_PS);
 
-		bytes_compl += skb->len;
-		ag->dev->stats.tx_bytes += skb->len;
+		bytes_compl += len;
+		ag->dev->stats.tx_bytes += len;
 		ag->dev->stats.tx_packets++;
 
 		dev_kfree_skb_any(skb);
-- 
GitLab