aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorFelix Fietkau <nbd@openwrt.org>2009-01-08 21:39:57 -0500
committerDavid S. Miller <davem@davemloft.net>2009-01-11 03:04:12 -0500
commit4ca857958c129781b46870ec1d2d13c50aafb8c5 (patch)
tree4046e0a5a973ec383935ae07d577bd237e40f909 /drivers
parent9498c05820580afbf03a317b0b5bdb0ca0e27e40 (diff)
b44: fix misalignment and wasted space in rx handling
Broadcom 4400 puts a header of configurable size (apparently needs to be at least 28 bytes) in front of received packets. When handling this, the previous code accidentally added the offset 30 *twice* for the software and once for the hardware, thereby cancelling out the IP alignment effect of the 30 byte padding and wasting an additional 30 bytes of memory per packet. This patch fixes this problem and improves routing throughput by about 30% on MIPS, where unaligned access is expensive. Signed-off-by: Felix Fietkau <nbd@openwrt.org> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/b44.c13
1 files changed, 6 insertions, 7 deletions
diff --git a/drivers/net/b44.c b/drivers/net/b44.c
index 6926ebedfdc9..5ae131c147f9 100644
--- a/drivers/net/b44.c
+++ b/drivers/net/b44.c
@@ -73,8 +73,8 @@
73 (BP)->tx_cons - (BP)->tx_prod - TX_RING_GAP(BP)) 73 (BP)->tx_cons - (BP)->tx_prod - TX_RING_GAP(BP))
74#define NEXT_TX(N) (((N) + 1) & (B44_TX_RING_SIZE - 1)) 74#define NEXT_TX(N) (((N) + 1) & (B44_TX_RING_SIZE - 1))
75 75
76#define RX_PKT_OFFSET 30 76#define RX_PKT_OFFSET (RX_HEADER_LEN + 2)
77#define RX_PKT_BUF_SZ (1536 + RX_PKT_OFFSET + 64) 77#define RX_PKT_BUF_SZ (1536 + RX_PKT_OFFSET)
78 78
79/* minimum number of free TX descriptors required to wake up TX process */ 79/* minimum number of free TX descriptors required to wake up TX process */
80#define B44_TX_WAKEUP_THRESH (B44_TX_RING_SIZE / 4) 80#define B44_TX_WAKEUP_THRESH (B44_TX_RING_SIZE / 4)
@@ -682,7 +682,6 @@ static int b44_alloc_rx_skb(struct b44 *bp, int src_idx, u32 dest_idx_unmasked)
682 } 682 }
683 683
684 rh = (struct rx_header *) skb->data; 684 rh = (struct rx_header *) skb->data;
685 skb_reserve(skb, RX_PKT_OFFSET);
686 685
687 rh->len = 0; 686 rh->len = 0;
688 rh->flags = 0; 687 rh->flags = 0;
@@ -693,13 +692,13 @@ static int b44_alloc_rx_skb(struct b44 *bp, int src_idx, u32 dest_idx_unmasked)
693 if (src_map != NULL) 692 if (src_map != NULL)
694 src_map->skb = NULL; 693 src_map->skb = NULL;
695 694
696 ctrl = (DESC_CTRL_LEN & (RX_PKT_BUF_SZ - RX_PKT_OFFSET)); 695 ctrl = (DESC_CTRL_LEN & RX_PKT_BUF_SZ);
697 if (dest_idx == (B44_RX_RING_SIZE - 1)) 696 if (dest_idx == (B44_RX_RING_SIZE - 1))
698 ctrl |= DESC_CTRL_EOT; 697 ctrl |= DESC_CTRL_EOT;
699 698
700 dp = &bp->rx_ring[dest_idx]; 699 dp = &bp->rx_ring[dest_idx];
701 dp->ctrl = cpu_to_le32(ctrl); 700 dp->ctrl = cpu_to_le32(ctrl);
702 dp->addr = cpu_to_le32((u32) mapping + RX_PKT_OFFSET + bp->dma_offset); 701 dp->addr = cpu_to_le32((u32) mapping + bp->dma_offset);
703 702
704 if (bp->flags & B44_FLAG_RX_RING_HACK) 703 if (bp->flags & B44_FLAG_RX_RING_HACK)
705 b44_sync_dma_desc_for_device(bp->sdev, bp->rx_ring_dma, 704 b44_sync_dma_desc_for_device(bp->sdev, bp->rx_ring_dma,
@@ -809,8 +808,8 @@ static int b44_rx(struct b44 *bp, int budget)
809 ssb_dma_unmap_single(bp->sdev, map, 808 ssb_dma_unmap_single(bp->sdev, map,
810 skb_size, DMA_FROM_DEVICE); 809 skb_size, DMA_FROM_DEVICE);
811 /* Leave out rx_header */ 810 /* Leave out rx_header */
812 skb_put(skb, len + RX_PKT_OFFSET); 811 skb_put(skb, len + RX_PKT_OFFSET);
813 skb_pull(skb, RX_PKT_OFFSET); 812 skb_pull(skb, RX_PKT_OFFSET);
814 } else { 813 } else {
815 struct sk_buff *copy_skb; 814 struct sk_buff *copy_skb;
816 815