]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - drivers/net/igb/igb_main.c
Merge branch 'avr32-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/hskinnemo...
[linux-2.6-omap-h63xx.git] / drivers / net / igb / igb_main.c
index d4eb8e2d87202b681cff99ff6cd8ec1eec1f3664..aaee02e9e3f03c4bc0da116942964996fe061fda 100644 (file)
@@ -31,7 +31,6 @@
 #include <linux/vmalloc.h>
 #include <linux/pagemap.h>
 #include <linux/netdevice.h>
-#include <linux/tcp.h>
 #include <linux/ipv6.h>
 #include <net/checksum.h>
 #include <net/ip6_checksum.h>
@@ -439,7 +438,7 @@ static int igb_request_irq(struct igb_adapter *adapter)
                err = igb_request_msix(adapter);
                if (!err) {
                        /* enable IAM, auto-mask,
-                        * DO NOT USE EIAME or IAME in legacy mode */
+                        * DO NOT USE EIAM or IAM in legacy mode */
                        wr32(E1000_IAM, IMS_ENABLE_MASK);
                        goto request_done;
                }
@@ -465,14 +464,9 @@ static int igb_request_irq(struct igb_adapter *adapter)
        err = request_irq(adapter->pdev->irq, &igb_intr, IRQF_SHARED,
                          netdev->name, netdev);
 
-       if (err) {
+       if (err)
                dev_err(&adapter->pdev->dev, "Error %d getting interrupt\n",
                        err);
-               goto request_done;
-       }
-
-       /* enable IAM, auto-mask */
-       wr32(E1000_IAM, IMS_ENABLE_MASK);
 
 request_done:
        return err;
@@ -606,9 +600,6 @@ static void igb_init_manageability(struct igb_adapter *adapter)
                u32 manc2h = rd32(E1000_MANC2H);
                u32 manc = rd32(E1000_MANC);
 
-               /* disable hardware interception of ARP */
-               manc &= ~(E1000_MANC_ARP_EN);
-
                /* enable receiving management packets to the host */
                /* this will probably generate destination unreachable messages
                 * from the host OS, but the packets will be handled on SMBUS */
@@ -623,25 +614,6 @@ static void igb_init_manageability(struct igb_adapter *adapter)
        }
 }
 
-static void igb_release_manageability(struct igb_adapter *adapter)
-{
-       struct e1000_hw *hw = &adapter->hw;
-
-       if (adapter->en_mng_pt) {
-               u32 manc = rd32(E1000_MANC);
-
-               /* re-enable hardware interception of ARP */
-               manc |= E1000_MANC_ARP_EN;
-               manc &= ~E1000_MANC_EN_MNG2HOST;
-
-               /* don't explicitly have to mess with MANC2H since
-                * MANC has an enable disable that gates MANC2H */
-
-               /* XXX stop the hardware watchdog ? */
-               wr32(E1000_MANC, manc);
-       }
-}
-
 /**
  * igb_configure - configure the hardware for RX and TX
  * @adapter: private board structure
@@ -843,8 +815,8 @@ void igb_reset(struct igb_adapter *adapter)
        wr32(E1000_VET, ETHERNET_IEEE_VLAN_TYPE);
 
        igb_reset_adaptive(&adapter->hw);
-       adapter->hw.phy.ops.get_phy_info(&adapter->hw);
-       igb_release_manageability(adapter);
+       if (adapter->hw.phy.ops.get_phy_info)
+               adapter->hw.phy.ops.get_phy_info(&adapter->hw);
 }
 
 /**
@@ -1178,9 +1150,6 @@ static void __devexit igb_remove(struct pci_dev *pdev)
 
        flush_scheduled_work();
 
-
-       igb_release_manageability(adapter);
-
        /* Release control of h/w to f/w.  If f/w is AMT enabled, this
         * would have already happened in close and is redundant. */
        igb_release_hw_control(adapter);
@@ -2083,7 +2052,8 @@ static void igb_set_multi(struct net_device *netdev)
 static void igb_update_phy_info(unsigned long data)
 {
        struct igb_adapter *adapter = (struct igb_adapter *) data;
-       adapter->hw.phy.ops.get_phy_info(&adapter->hw);
+       if (adapter->hw.phy.ops.get_phy_info)
+               adapter->hw.phy.ops.get_phy_info(&adapter->hw);
 }
 
 /**
@@ -2513,10 +2483,24 @@ static inline bool igb_tx_csum_adv(struct igb_adapter *adapter,
                tu_cmd |= (E1000_TXD_CMD_DEXT | E1000_ADVTXD_DTYP_CTXT);
 
                if (skb->ip_summed == CHECKSUM_PARTIAL) {
-                       if (skb->protocol == htons(ETH_P_IP))
+                       switch (skb->protocol) {
+                       case __constant_htons(ETH_P_IP):
                                tu_cmd |= E1000_ADVTXD_TUCMD_IPV4;
-                       if (skb->sk && (skb->sk->sk_protocol == IPPROTO_TCP))
-                               tu_cmd |= E1000_ADVTXD_TUCMD_L4T_TCP;
+                               if (ip_hdr(skb)->protocol == IPPROTO_TCP)
+                                       tu_cmd |= E1000_ADVTXD_TUCMD_L4T_TCP;
+                               break;
+                       case __constant_htons(ETH_P_IPV6):
+                               /* XXX what about other V6 headers?? */
+                               if (ipv6_hdr(skb)->nexthdr == IPPROTO_TCP)
+                                       tu_cmd |= E1000_ADVTXD_TUCMD_L4T_TCP;
+                               break;
+                       default:
+                               if (unlikely(net_ratelimit()))
+                                       dev_warn(&adapter->pdev->dev,
+                                           "partial checksum but proto=%x!\n",
+                                           skb->protocol);
+                               break;
+                       }
                }
 
                context_desc->type_tucmd_mlhl = cpu_to_le32(tu_cmd);
@@ -3270,6 +3254,13 @@ quit_polling:
 
        return 1;
 }
+
+static inline u32 get_head(struct igb_ring *tx_ring)
+{
+       void *end = (struct e1000_tx_desc *)tx_ring->desc + tx_ring->count;
+       return le32_to_cpu(*(volatile __le32 *)end);
+}
+
 /**
  * igb_clean_tx_irq - Reclaim resources after transmit completes
  * @adapter: board private structure
@@ -3291,9 +3282,7 @@ static bool igb_clean_tx_irq(struct igb_adapter *adapter,
        unsigned int total_bytes = 0, total_packets = 0;
 
        rmb();
-       head = *(volatile u32 *)((struct e1000_tx_desc *)tx_ring->desc
-                                + tx_ring->count);
-       head = le32_to_cpu(head);
+       head = get_head(tx_ring);
        i = tx_ring->next_to_clean;
        while (1) {
                while (i != head) {
@@ -3328,9 +3317,7 @@ static bool igb_clean_tx_irq(struct igb_adapter *adapter,
                }
                oldhead = head;
                rmb();
-               head = *(volatile u32 *)((struct e1000_tx_desc *)tx_ring->desc
-                                        + tx_ring->count);
-               head = le32_to_cpu(head);
+               head = get_head(tx_ring);
                if (head == oldhead)
                        goto done_cleaning;
        }  /* while (1) */
@@ -3404,7 +3391,7 @@ done_cleaning:
  * @vlan: descriptor vlan field as written by hardware (no le/be conversion)
  * @skb: pointer to sk_buff to be indicated to stack
  **/
-static void igb_receive_skb(struct igb_adapter *adapter, u8 status, u16 vlan,
+static void igb_receive_skb(struct igb_adapter *adapter, u8 status, __le16 vlan,
                            struct sk_buff *skb)
 {
        if (adapter->vlgrp && (status & E1000_RXD_STAT_VP))
@@ -3468,8 +3455,8 @@ static bool igb_clean_rx_irq_adv(struct igb_adapter *adapter,
                 * that case, it fills the header buffer and spills the rest
                 * into the page.
                 */
-               hlen = le16_to_cpu((rx_desc->wb.lower.lo_dword.hdr_info &
-                 E1000_RXDADV_HDRBUFLEN_MASK) >> E1000_RXDADV_HDRBUFLEN_SHIFT);
+               hlen = (le16_to_cpu(rx_desc->wb.lower.lo_dword.hdr_info) &
+                 E1000_RXDADV_HDRBUFLEN_MASK) >> E1000_RXDADV_HDRBUFLEN_SHIFT;
                if (hlen > adapter->rx_ps_hdr_size)
                        hlen = adapter->rx_ps_hdr_size;
 
@@ -3955,8 +3942,6 @@ static int igb_suspend(struct pci_dev *pdev, pm_message_t state)
                pci_enable_wake(pdev, PCI_D3cold, 0);
        }
 
-       igb_release_manageability(adapter);
-
        /* make sure adapter isn't asleep if manageability is enabled */
        if (adapter->en_mng_pt) {
                pci_enable_wake(pdev, PCI_D3hot, 1);