sky2: Create buffer alloc and free helpers
authorMike McCormack <mikem@ring3k.org>
Tue, 1 Sep 2009 03:21:35 +0000 (03:21 +0000)
committerDavid S. Miller <davem@davemloft.net>
Wed, 2 Sep 2009 00:40:42 +0000 (17:40 -0700)
Refactor similar two sections of code that free buffers into one.
Only call tx_init if all buffer allocations succeed.

Signed-off-by: Mike McCormack <mikem@ring3k.org>
Acked-by: Stephen Hemminger <shemminger@vyatta.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/net/sky2.c

index ba5180a2326456d8731fdd33e47494bf7323ef99..7108b1292b92e921e84bab8b64adb180d345ccd1 100644 (file)
@@ -1405,6 +1405,61 @@ nomem:
        return -ENOMEM;
 }
 
+static int sky2_alloc_buffers(struct sky2_port *sky2)
+{
+       struct sky2_hw *hw = sky2->hw;
+
+       /* must be power of 2 */
+       sky2->tx_le = pci_alloc_consistent(hw->pdev,
+                                          sky2->tx_ring_size *
+                                          sizeof(struct sky2_tx_le),
+                                          &sky2->tx_le_map);
+       if (!sky2->tx_le)
+               goto nomem;
+
+       sky2->tx_ring = kcalloc(sky2->tx_ring_size, sizeof(struct tx_ring_info),
+                               GFP_KERNEL);
+       if (!sky2->tx_ring)
+               goto nomem;
+
+       sky2->rx_le = pci_alloc_consistent(hw->pdev, RX_LE_BYTES,
+                                          &sky2->rx_le_map);
+       if (!sky2->rx_le)
+               goto nomem;
+       memset(sky2->rx_le, 0, RX_LE_BYTES);
+
+       sky2->rx_ring = kcalloc(sky2->rx_pending, sizeof(struct rx_ring_info),
+                               GFP_KERNEL);
+       if (!sky2->rx_ring)
+               goto nomem;
+
+       return 0;
+nomem:
+       return -ENOMEM;
+}
+
+static void sky2_free_buffers(struct sky2_port *sky2)
+{
+       struct sky2_hw *hw = sky2->hw;
+
+       if (sky2->rx_le) {
+               pci_free_consistent(hw->pdev, RX_LE_BYTES,
+                                   sky2->rx_le, sky2->rx_le_map);
+               sky2->rx_le = NULL;
+       }
+       if (sky2->tx_le) {
+               pci_free_consistent(hw->pdev,
+                                   sky2->tx_ring_size * sizeof(struct sky2_tx_le),
+                                   sky2->tx_le, sky2->tx_le_map);
+               sky2->tx_le = NULL;
+       }
+       kfree(sky2->tx_ring);
+       kfree(sky2->rx_ring);
+
+       sky2->tx_ring = NULL;
+       sky2->rx_ring = NULL;
+}
+
 /* Bring up network interface. */
 static int sky2_up(struct net_device *dev)
 {
@@ -1412,7 +1467,7 @@ static int sky2_up(struct net_device *dev)
        struct sky2_hw *hw = sky2->hw;
        unsigned port = sky2->port;
        u32 imask, ramsize;
-       int cap, err = -ENOMEM;
+       int cap, err;
        struct net_device *otherdev = hw->dev[sky2->port^1];
 
        /*
@@ -1431,32 +1486,12 @@ static int sky2_up(struct net_device *dev)
 
        netif_carrier_off(dev);
 
-       /* must be power of 2 */
-       sky2->tx_le = pci_alloc_consistent(hw->pdev,
-                                          sky2->tx_ring_size *
-                                          sizeof(struct sky2_tx_le),
-                                          &sky2->tx_le_map);
-       if (!sky2->tx_le)
-               goto err_out;
-
-       sky2->tx_ring = kcalloc(sky2->tx_ring_size, sizeof(struct tx_ring_info),
-                               GFP_KERNEL);
-       if (!sky2->tx_ring)
+       err = sky2_alloc_buffers(sky2);
+       if (err)
                goto err_out;
 
        tx_init(sky2);
 
-       sky2->rx_le = pci_alloc_consistent(hw->pdev, RX_LE_BYTES,
-                                          &sky2->rx_le_map);
-       if (!sky2->rx_le)
-               goto err_out;
-       memset(sky2->rx_le, 0, RX_LE_BYTES);
-
-       sky2->rx_ring = kcalloc(sky2->rx_pending, sizeof(struct rx_ring_info),
-                               GFP_KERNEL);
-       if (!sky2->rx_ring)
-               goto err_out;
-
        sky2_mac_init(hw, port);
 
        /* Register is number of 4K blocks on internal RAM buffer. */
@@ -1513,22 +1548,7 @@ static int sky2_up(struct net_device *dev)
        return 0;
 
 err_out:
-       if (sky2->rx_le) {
-               pci_free_consistent(hw->pdev, RX_LE_BYTES,
-                                   sky2->rx_le, sky2->rx_le_map);
-               sky2->rx_le = NULL;
-       }
-       if (sky2->tx_le) {
-               pci_free_consistent(hw->pdev,
-                                   sky2->tx_ring_size * sizeof(struct sky2_tx_le),
-                                   sky2->tx_le, sky2->tx_le_map);
-               sky2->tx_le = NULL;
-       }
-       kfree(sky2->tx_ring);
-       kfree(sky2->rx_ring);
-
-       sky2->tx_ring = NULL;
-       sky2->rx_ring = NULL;
+       sky2_free_buffers(sky2);
        return err;
 }
 
@@ -1880,20 +1900,7 @@ static int sky2_down(struct net_device *dev)
 
        sky2_rx_clean(sky2);
 
-       pci_free_consistent(hw->pdev, RX_LE_BYTES,
-                           sky2->rx_le, sky2->rx_le_map);
-       kfree(sky2->rx_ring);
-
-       pci_free_consistent(hw->pdev,
-                           sky2->tx_ring_size * sizeof(struct sky2_tx_le),
-                           sky2->tx_le, sky2->tx_le_map);
-       kfree(sky2->tx_ring);
-
-       sky2->tx_le = NULL;
-       sky2->rx_le = NULL;
-
-       sky2->rx_ring = NULL;
-       sky2->tx_ring = NULL;
+       sky2_free_buffers(sky2);
 
        return 0;
 }