From 9f8008020a8293074a65f5f23ec1f40ac97d6beb Mon Sep 17 00:00:00 2001 From: Russell King Date: Mon, 31 Mar 2014 14:47:06 +0100 Subject: net:fec: even larger rings Signed-off-by: Russell King --- drivers/net/ethernet/freescale/fec_main.c | 68 +++++++++++++++++++------------ 1 file changed, 42 insertions(+), 26 deletions(-) diff --git a/drivers/net/ethernet/freescale/fec_main.c b/drivers/net/ethernet/freescale/fec_main.c index 95a9fbd70f4e..95fad9862ef5 100644 --- a/drivers/net/ethernet/freescale/fec_main.c +++ b/drivers/net/ethernet/freescale/fec_main.c @@ -872,7 +872,7 @@ fec_enet_hwtstamp(struct fec_enet_private *fep, unsigned ts, hwtstamps->hwtstamp = ns_to_ktime(ns); } -static void +static void noinline fec_enet_tx(struct net_device *ndev) { struct fec_enet_private *fep = netdev_priv(ndev); @@ -2041,6 +2041,7 @@ static void fec_enet_free_buffers(struct net_device *ndev) unsigned int i; struct sk_buff *skb; union bufdesc_u *bdp; + int rx_cbd_size, tx_cbd_size; for (i = 0; i < fep->rx_ring_size; i++) { bdp = fec_enet_rx_get(i, fep); @@ -2066,7 +2067,18 @@ static void fec_enet_free_buffers(struct net_device *ndev) dev_kfree_skb(skb); } - dma_free_coherent(NULL, PAGE_SIZE, fep->rx_bd_base, fep->rx_bd_dma); + rx_cbd_size = fep->rx_ring_size; + tx_cbd_size = fep->tx_ring_size; + if (fep->flags & FEC_FLAG_BUFDESC_EX) { + rx_cbd_size *= sizeof(struct bufdesc_ex); + tx_cbd_size *= sizeof(struct bufdesc_ex); + } else { + rx_cbd_size *= sizeof(struct bufdesc); + tx_cbd_size *= sizeof(struct bufdesc); + } + + dma_free_coherent(NULL, rx_cbd_size, fep->rx_bd_base, fep->rx_bd_dma); + dma_free_coherent(NULL, tx_cbd_size, fep->tx_bd_base, fep->tx_bd_dma); } static int fec_enet_alloc_buffers(struct net_device *ndev) @@ -2074,38 +2086,42 @@ static int fec_enet_alloc_buffers(struct net_device *ndev) struct fec_enet_private *fep = netdev_priv(ndev); unsigned int i; struct sk_buff *skb; + union bufdesc_u *rx_cbd_cpu, *tx_cbd_cpu; + dma_addr_t rx_cbd_dma, tx_cbd_dma; union bufdesc_u *bdp; - union bufdesc_u *cbd_base; - dma_addr_t cbd_dma; - int bd_size; + int rx_cbd_size, tx_cbd_size; - bd_size = fep->tx_ring_size + fep->rx_ring_size; - if (fep->flags & FEC_FLAG_BUFDESC_EX) - bd_size *= sizeof(struct bufdesc_ex); - else - bd_size *= sizeof(struct bufdesc); + rx_cbd_size = fep->rx_ring_size; + tx_cbd_size = fep->tx_ring_size; + if (fep->flags & FEC_FLAG_BUFDESC_EX) { + rx_cbd_size *= sizeof(struct bufdesc_ex); + tx_cbd_size *= sizeof(struct bufdesc_ex); + } else { + rx_cbd_size *= sizeof(struct bufdesc); + tx_cbd_size *= sizeof(struct bufdesc); + } /* Allocate memory for buffer descriptors. */ - cbd_base = dma_alloc_coherent(NULL, bd_size, &cbd_dma, GFP_KERNEL); - if (!cbd_base) + rx_cbd_cpu = dma_alloc_coherent(NULL, rx_cbd_size, &rx_cbd_dma, + GFP_KERNEL); + tx_cbd_cpu = dma_alloc_coherent(NULL, tx_cbd_size, &tx_cbd_dma, + GFP_KERNEL); + if (!rx_cbd_cpu || !tx_cbd_cpu) { + if (rx_cbd_cpu) + dma_free_coherent(NULL, rx_cbd_size, rx_cbd_cpu, rx_cbd_dma); + if (tx_cbd_cpu) + dma_free_coherent(NULL, tx_cbd_size, tx_cbd_cpu, tx_cbd_dma); return -ENOMEM; + } - memset(cbd_base, 0, PAGE_SIZE); + memset(rx_cbd_cpu, 0, PAGE_SIZE); + memset(tx_cbd_cpu, 0, PAGE_SIZE); /* Set receive and transmit descriptor base. */ - fep->rx_bd_base = cbd_base; - fep->rx_bd_dma = cbd_dma; - if (fep->flags & FEC_FLAG_BUFDESC_EX) { - fep->tx_bd_base = (union bufdesc_u *) - (&cbd_base->ebd + fep->rx_ring_size); - fep->tx_bd_dma = cbd_dma + sizeof(struct bufdesc_ex) * - fep->rx_ring_size; - } else { - fep->tx_bd_base = (union bufdesc_u *) - (&cbd_base->bd + fep->rx_ring_size); - fep->tx_bd_dma = cbd_dma + sizeof(struct bufdesc) * - fep->rx_ring_size; - } + fep->rx_bd_base = rx_cbd_cpu; + fep->rx_bd_dma = rx_cbd_dma; + fep->tx_bd_base = tx_cbd_cpu; + fep->tx_bd_dma = tx_cbd_dma; for (i = 0; i < fep->rx_ring_size; i++) { dma_addr_t addr; -- cgit