]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - drivers/net/e1000e/netdev.c
Merge branch 'x86/cpu' into x86/core
[linux-2.6-omap-h63xx.git] / drivers / net / e1000e / netdev.c
index d1367789976740f829083d63ed787b788e854e01..d266510c8a94683ae4d21516cf6c18491dc3eb3a 100644 (file)
@@ -484,8 +484,8 @@ static bool e1000_clean_rx_irq(struct e1000_adapter *adapter,
                 * packet, also make sure the frame isn't just CRC only */
                if (!(status & E1000_RXD_STAT_EOP) || (length <= 4)) {
                        /* All receives must fit into a single buffer */
-                       ndev_dbg(netdev, "%s: Receive packet consumed "
-                                "multiple buffers\n", netdev->name);
+                       e_dbg("%s: Receive packet consumed multiple buffers\n",
+                             netdev->name);
                        /* recycle */
                        buffer_info->skb = skb;
                        goto next_desc;
@@ -510,9 +510,12 @@ static bool e1000_clean_rx_irq(struct e1000_adapter *adapter,
                            netdev_alloc_skb(netdev, length + NET_IP_ALIGN);
                        if (new_skb) {
                                skb_reserve(new_skb, NET_IP_ALIGN);
-                               memcpy(new_skb->data - NET_IP_ALIGN,
-                                      skb->data - NET_IP_ALIGN,
-                                      length + NET_IP_ALIGN);
+                               skb_copy_to_linear_data_offset(new_skb,
+                                                              -NET_IP_ALIGN,
+                                                              (skb->data -
+                                                               NET_IP_ALIGN),
+                                                              (length +
+                                                               NET_IP_ALIGN));
                                /* save the skb in buffer_info as good */
                                buffer_info->skb = skb;
                                skb = new_skb;
@@ -576,28 +579,26 @@ static void e1000_print_tx_hang(struct e1000_adapter *adapter)
        unsigned int i = tx_ring->next_to_clean;
        unsigned int eop = tx_ring->buffer_info[i].next_to_watch;
        struct e1000_tx_desc *eop_desc = E1000_TX_DESC(*tx_ring, eop);
-       struct net_device *netdev = adapter->netdev;
 
        /* detected Tx unit hang */
-       ndev_err(netdev,
-                "Detected Tx Unit Hang:\n"
-                "  TDH                  <%x>\n"
-                "  TDT                  <%x>\n"
-                "  next_to_use          <%x>\n"
-                "  next_to_clean        <%x>\n"
-                "buffer_info[next_to_clean]:\n"
-                "  time_stamp           <%lx>\n"
-                "  next_to_watch        <%x>\n"
-                "  jiffies              <%lx>\n"
-                "  next_to_watch.status <%x>\n",
-                readl(adapter->hw.hw_addr + tx_ring->head),
-                readl(adapter->hw.hw_addr + tx_ring->tail),
-                tx_ring->next_to_use,
-                tx_ring->next_to_clean,
-                tx_ring->buffer_info[eop].time_stamp,
-                eop,
-                jiffies,
-                eop_desc->upper.fields.status);
+       e_err("Detected Tx Unit Hang:\n"
+             "  TDH                  <%x>\n"
+             "  TDT                  <%x>\n"
+             "  next_to_use          <%x>\n"
+             "  next_to_clean        <%x>\n"
+             "buffer_info[next_to_clean]:\n"
+             "  time_stamp           <%lx>\n"
+             "  next_to_watch        <%x>\n"
+             "  jiffies              <%lx>\n"
+             "  next_to_watch.status <%x>\n",
+             readl(adapter->hw.hw_addr + tx_ring->head),
+             readl(adapter->hw.hw_addr + tx_ring->tail),
+             tx_ring->next_to_use,
+             tx_ring->next_to_clean,
+             tx_ring->buffer_info[eop].time_stamp,
+             eop,
+             jiffies,
+             eop_desc->upper.fields.status);
 }
 
 /**
@@ -747,8 +748,8 @@ static bool e1000_clean_rx_irq_ps(struct e1000_adapter *adapter,
                buffer_info->dma = 0;
 
                if (!(staterr & E1000_RXD_STAT_EOP)) {
-                       ndev_dbg(netdev, "%s: Packet Split buffers didn't pick "
-                                "up the full packet\n", netdev->name);
+                       e_dbg("%s: Packet Split buffers didn't pick up the "
+                             "full packet\n", netdev->name);
                        dev_kfree_skb_irq(skb);
                        goto next_desc;
                }
@@ -761,8 +762,8 @@ static bool e1000_clean_rx_irq_ps(struct e1000_adapter *adapter,
                length = le16_to_cpu(rx_desc->wb.middle.length0);
 
                if (!length) {
-                       ndev_dbg(netdev, "%s: Last part of the packet spanning"
-                                " multiple descriptors\n", netdev->name);
+                       e_dbg("%s: Last part of the packet spanning multiple "
+                             "descriptors\n", netdev->name);
                        dev_kfree_skb_irq(skb);
                        goto next_desc;
                }
@@ -1011,7 +1012,7 @@ static bool e1000_clean_jumbo_rx_irq(struct e1000_adapter *adapter,
 
                /* eth type trans needs skb->data to point to something */
                if (!pskb_may_pull(skb, ETH_HLEN)) {
-                       ndev_err(netdev, "pskb_may_pull failed.\n");
+                       e_err("pskb_may_pull failed.\n");
                        dev_kfree_skb(skb);
                        goto next_desc;
                }
@@ -1235,28 +1236,36 @@ static irqreturn_t e1000_intr(int irq, void *data)
        return IRQ_HANDLED;
 }
 
+/**
+ * e1000_request_irq - initialize interrupts
+ *
+ * Attempts to configure interrupts using the best available
+ * capabilities of the hardware and kernel.
+ **/
 static int e1000_request_irq(struct e1000_adapter *adapter)
 {
        struct net_device *netdev = adapter->netdev;
-       irq_handler_t handler = e1000_intr;
        int irq_flags = IRQF_SHARED;
        int err;
 
-       if (!pci_enable_msi(adapter->pdev)) {
-               adapter->flags |= FLAG_MSI_ENABLED;
-               handler = e1000_intr_msi;
-               irq_flags = 0;
+       if (!(adapter->flags & FLAG_MSI_TEST_FAILED)) {
+               err = pci_enable_msi(adapter->pdev);
+               if (!err) {
+                       adapter->flags |= FLAG_MSI_ENABLED;
+                       irq_flags = 0;
+               }
        }
 
-       err = request_irq(adapter->pdev->irq, handler, irq_flags, netdev->name,
-                         netdev);
+       err = request_irq(adapter->pdev->irq,
+                         ((adapter->flags & FLAG_MSI_ENABLED) ?
+                               &e1000_intr_msi : &e1000_intr),
+                         irq_flags, netdev->name, netdev);
        if (err) {
-               ndev_err(netdev,
-                      "Unable to allocate %s interrupt (return: %d)\n",
-                       adapter->flags & FLAG_MSI_ENABLED ? "MSI":"INTx",
-                       err);
-               if (adapter->flags & FLAG_MSI_ENABLED)
+               if (adapter->flags & FLAG_MSI_ENABLED) {
                        pci_disable_msi(adapter->pdev);
+                       adapter->flags &= ~FLAG_MSI_ENABLED;
+               }
+               e_err("Unable to allocate interrupt, Error: %d\n", err);
        }
 
        return err;
@@ -1395,8 +1404,7 @@ int e1000e_setup_tx_resources(struct e1000_adapter *adapter)
        return 0;
 err:
        vfree(tx_ring->buffer_info);
-       ndev_err(adapter->netdev,
-       "Unable to allocate memory for the transmit descriptor ring\n");
+       e_err("Unable to allocate memory for the transmit descriptor ring\n");
        return err;
 }
 
@@ -1450,8 +1458,7 @@ err_pages:
        }
 err:
        vfree(rx_ring->buffer_info);
-       ndev_err(adapter->netdev,
-       "Unable to allocate memory for the transmit descriptor ring\n");
+       e_err("Unable to allocate memory for the transmit descriptor ring\n");
        return err;
 }
 
@@ -2450,13 +2457,13 @@ void e1000e_reset(struct e1000_adapter *adapter)
         * For parts with AMT enabled, let the firmware know
         * that the network interface is in control
         */
-       if ((adapter->flags & FLAG_HAS_AMT) && e1000e_check_mng_mode(hw))
+       if (adapter->flags & FLAG_HAS_AMT)
                e1000_get_hw_control(adapter);
 
        ew32(WUC, 0);
 
        if (mac->ops.init_hw(hw))
-               ndev_err(adapter->netdev, "Hardware Error\n");
+               e_err("Hardware Error\n");
 
        e1000_update_mng_vlan(adapter);
 
@@ -2591,12 +2598,141 @@ static int __devinit e1000_sw_init(struct e1000_adapter *adapter)
        return 0;
 
 err:
-       ndev_err(netdev, "Unable to allocate memory for queues\n");
+       e_err("Unable to allocate memory for queues\n");
        kfree(adapter->rx_ring);
        kfree(adapter->tx_ring);
        return -ENOMEM;
 }
 
+/**
+ * e1000_intr_msi_test - Interrupt Handler
+ * @irq: interrupt number
+ * @data: pointer to a network interface device structure
+ **/
+static irqreturn_t e1000_intr_msi_test(int irq, void *data)
+{
+       struct net_device *netdev = data;
+       struct e1000_adapter *adapter = netdev_priv(netdev);
+       struct e1000_hw *hw = &adapter->hw;
+       u32 icr = er32(ICR);
+
+       e_dbg("%s: icr is %08X\n", netdev->name, icr);
+       if (icr & E1000_ICR_RXSEQ) {
+               adapter->flags &= ~FLAG_MSI_TEST_FAILED;
+               wmb();
+       }
+
+       return IRQ_HANDLED;
+}
+
+/**
+ * e1000_test_msi_interrupt - Returns 0 for successful test
+ * @adapter: board private struct
+ *
+ * code flow taken from tg3.c
+ **/
+static int e1000_test_msi_interrupt(struct e1000_adapter *adapter)
+{
+       struct net_device *netdev = adapter->netdev;
+       struct e1000_hw *hw = &adapter->hw;
+       int err;
+
+       /* poll_enable hasn't been called yet, so don't need disable */
+       /* clear any pending events */
+       er32(ICR);
+
+       /* free the real vector and request a test handler */
+       e1000_free_irq(adapter);
+
+       /* Assume that the test fails, if it succeeds then the test
+        * MSI irq handler will unset this flag */
+       adapter->flags |= FLAG_MSI_TEST_FAILED;
+
+       err = pci_enable_msi(adapter->pdev);
+       if (err)
+               goto msi_test_failed;
+
+       err = request_irq(adapter->pdev->irq, &e1000_intr_msi_test, 0,
+                         netdev->name, netdev);
+       if (err) {
+               pci_disable_msi(adapter->pdev);
+               goto msi_test_failed;
+       }
+
+       wmb();
+
+       e1000_irq_enable(adapter);
+
+       /* fire an unusual interrupt on the test handler */
+       ew32(ICS, E1000_ICS_RXSEQ);
+       e1e_flush();
+       msleep(50);
+
+       e1000_irq_disable(adapter);
+
+       rmb();
+
+       if (adapter->flags & FLAG_MSI_TEST_FAILED) {
+               err = -EIO;
+               e_info("MSI interrupt test failed!\n");
+       }
+
+       free_irq(adapter->pdev->irq, netdev);
+       pci_disable_msi(adapter->pdev);
+
+       if (err == -EIO)
+               goto msi_test_failed;
+
+       /* okay so the test worked, restore settings */
+       e_dbg("%s: MSI interrupt test succeeded!\n", netdev->name);
+msi_test_failed:
+       /* restore the original vector, even if it failed */
+       e1000_request_irq(adapter);
+       return err;
+}
+
+/**
+ * e1000_test_msi - Returns 0 if MSI test succeeds or INTx mode is restored
+ * @adapter: board private struct
+ *
+ * code flow taken from tg3.c, called with e1000 interrupts disabled.
+ **/
+static int e1000_test_msi(struct e1000_adapter *adapter)
+{
+       int err;
+       u16 pci_cmd;
+
+       if (!(adapter->flags & FLAG_MSI_ENABLED))
+               return 0;
+
+       /* disable SERR in case the MSI write causes a master abort */
+       pci_read_config_word(adapter->pdev, PCI_COMMAND, &pci_cmd);
+       pci_write_config_word(adapter->pdev, PCI_COMMAND,
+                             pci_cmd & ~PCI_COMMAND_SERR);
+
+       err = e1000_test_msi_interrupt(adapter);
+
+       /* restore previous setting of command word */
+       pci_write_config_word(adapter->pdev, PCI_COMMAND, pci_cmd);
+
+       /* success ! */
+       if (!err)
+               return 0;
+
+       /* EIO means MSI test failed */
+       if (err != -EIO)
+               return err;
+
+       /* back to INTx mode */
+       e_warn("MSI interrupt test failed, using legacy interrupt.\n");
+
+       e1000_free_irq(adapter);
+
+       err = e1000_request_irq(adapter);
+
+       return err;
+}
+
 /**
  * e1000_open - Called when a network interface is made active
  * @netdev: network interface device structure
@@ -2640,8 +2776,7 @@ static int e1000_open(struct net_device *netdev)
         * If AMT is enabled, let the firmware know that the network
         * interface is now open
         */
-       if ((adapter->flags & FLAG_HAS_AMT) &&
-           e1000e_check_mng_mode(&adapter->hw))
+       if (adapter->flags & FLAG_HAS_AMT)
                e1000_get_hw_control(adapter);
 
        /*
@@ -2656,6 +2791,19 @@ static int e1000_open(struct net_device *netdev)
        if (err)
                goto err_req_irq;
 
+       /*
+        * Work around PCIe errata with MSI interrupts causing some chipsets to
+        * ignore e1000e MSI messages, which means we need to test our MSI
+        * interrupt now
+        */
+       {
+               err = e1000_test_msi(adapter);
+               if (err) {
+                       e_err("Interrupt allocation failed\n");
+                       goto err_req_irq;
+               }
+       }
+
        /* From here on the code is the same as e1000e_up() */
        clear_bit(__E1000_DOWN, &adapter->state);
 
@@ -2719,8 +2867,7 @@ static int e1000_close(struct net_device *netdev)
         * If AMT is enabled, let the firmware know that the network
         * interface is now closed
         */
-       if ((adapter->flags & FLAG_HAS_AMT) &&
-           e1000e_check_mng_mode(&adapter->hw))
+       if (adapter->flags & FLAG_HAS_AMT)
                e1000_release_hw_control(adapter);
 
        return 0;
@@ -2917,8 +3064,7 @@ static void e1000_phy_read_status(struct e1000_adapter *adapter)
                ret_val |= e1e_rphy(hw, PHY_1000T_STATUS, &phy->stat1000);
                ret_val |= e1e_rphy(hw, PHY_EXT_STATUS, &phy->estatus);
                if (ret_val)
-                       ndev_warn(adapter->netdev,
-                                 "Error reading PHY register\n");
+                       e_warn("Error reading PHY register\n");
        } else {
                /*
                 * Do not read PHY registers if link is not up
@@ -2943,18 +3089,16 @@ static void e1000_phy_read_status(struct e1000_adapter *adapter)
 static void e1000_print_link_info(struct e1000_adapter *adapter)
 {
        struct e1000_hw *hw = &adapter->hw;
-       struct net_device *netdev = adapter->netdev;
        u32 ctrl = er32(CTRL);
 
-       ndev_info(netdev,
-               "Link is Up %d Mbps %s, Flow Control: %s\n",
-               adapter->link_speed,
-               (adapter->link_duplex == FULL_DUPLEX) ?
-                               "Full Duplex" : "Half Duplex",
-               ((ctrl & E1000_CTRL_TFCE) && (ctrl & E1000_CTRL_RFCE)) ?
-                               "RX/TX" :
-               ((ctrl & E1000_CTRL_RFCE) ? "RX" :
-               ((ctrl & E1000_CTRL_TFCE) ? "TX" : "None" )));
+       e_info("Link is Up %d Mbps %s, Flow Control: %s\n",
+              adapter->link_speed,
+              (adapter->link_duplex == FULL_DUPLEX) ?
+                               "Full Duplex" : "Half Duplex",
+              ((ctrl & E1000_CTRL_TFCE) && (ctrl & E1000_CTRL_RFCE)) ?
+                               "RX/TX" :
+              ((ctrl & E1000_CTRL_RFCE) ? "RX" :
+              ((ctrl & E1000_CTRL_TFCE) ? "TX" : "None" )));
 }
 
 static bool e1000_has_link(struct e1000_adapter *adapter)
@@ -2994,8 +3138,7 @@ static bool e1000_has_link(struct e1000_adapter *adapter)
        if ((ret_val == E1000_ERR_PHY) && (hw->phy.type == e1000_phy_igp_3) &&
            (er32(CTRL) & E1000_PHY_CTRL_GBE_DISABLE)) {
                /* See e1000_kmrn_lock_loss_workaround_ich8lan() */
-               ndev_info(adapter->netdev,
-                         "Gigabit has been disabled, downgrading speed\n");
+               e_info("Gigabit has been disabled, downgrading speed\n");
        }
 
        return link_active;
@@ -3067,7 +3210,7 @@ static void e1000_watchdog_task(struct work_struct *work)
                        case SPEED_10:
                                txb2b = 0;
                                netdev->tx_queue_len = 10;
-                               adapter->tx_timeout_factor = 14;
+                               adapter->tx_timeout_factor = 16;
                                break;
                        case SPEED_100:
                                txb2b = 0;
@@ -3096,8 +3239,7 @@ static void e1000_watchdog_task(struct work_struct *work)
                                switch (adapter->link_speed) {
                                case SPEED_10:
                                case SPEED_100:
-                                       ndev_info(netdev,
-                                       "10/100 speed: disabling TSO\n");
+                                       e_info("10/100 speed: disabling TSO\n");
                                        netdev->features &= ~NETIF_F_TSO;
                                        netdev->features &= ~NETIF_F_TSO6;
                                        break;
@@ -3130,7 +3272,7 @@ static void e1000_watchdog_task(struct work_struct *work)
                if (netif_carrier_ok(netdev)) {
                        adapter->link_speed = 0;
                        adapter->link_duplex = 0;
-                       ndev_info(netdev, "Link is Down\n");
+                       e_info("Link is Down\n");
                        netif_carrier_off(netdev);
                        netif_tx_stop_all_queues(netdev);
                        if (!test_bit(__E1000_DOWN, &adapter->state))
@@ -3604,8 +3746,7 @@ static int e1000_xmit_frame(struct sk_buff *skb, struct net_device *netdev)
 
                        pull_size = min((unsigned int)4, skb->data_len);
                        if (!__pskb_pull_tail(skb, pull_size)) {
-                               ndev_err(netdev,
-                                        "__pskb_pull_tail failed.\n");
+                               e_err("__pskb_pull_tail failed.\n");
                                dev_kfree_skb_any(skb);
                                return NETDEV_TX_OK;
                        }
@@ -3735,27 +3876,27 @@ static int e1000_change_mtu(struct net_device *netdev, int new_mtu)
        struct e1000_adapter *adapter = netdev_priv(netdev);
        int max_frame = new_mtu + ETH_HLEN + ETH_FCS_LEN;
 
-       if ((max_frame < ETH_ZLEN + ETH_FCS_LEN) ||
+       if ((new_mtu < ETH_ZLEN + ETH_FCS_LEN + VLAN_HLEN) ||
            (max_frame > MAX_JUMBO_FRAME_SIZE)) {
-               ndev_err(netdev, "Invalid MTU setting\n");
+               e_err("Invalid MTU setting\n");
                return -EINVAL;
        }
 
        /* Jumbo frame size limits */
        if (max_frame > ETH_FRAME_LEN + ETH_FCS_LEN) {
                if (!(adapter->flags & FLAG_HAS_JUMBO_FRAMES)) {
-                       ndev_err(netdev, "Jumbo Frames not supported.\n");
+                       e_err("Jumbo Frames not supported.\n");
                        return -EINVAL;
                }
                if (adapter->hw.phy.type == e1000_phy_ife) {
-                       ndev_err(netdev, "Jumbo Frames not supported.\n");
+                       e_err("Jumbo Frames not supported.\n");
                        return -EINVAL;
                }
        }
 
 #define MAX_STD_JUMBO_FRAME_SIZE 9234
        if (max_frame > MAX_STD_JUMBO_FRAME_SIZE) {
-               ndev_err(netdev, "MTU > 9216 not supported.\n");
+               e_err("MTU > 9216 not supported.\n");
                return -EINVAL;
        }
 
@@ -3792,8 +3933,7 @@ static int e1000_change_mtu(struct net_device *netdev, int new_mtu)
                adapter->rx_buffer_len = ETH_FRAME_LEN + VLAN_HLEN
                                         + ETH_FCS_LEN;
 
-       ndev_info(netdev, "changing MTU from %d to %d\n",
-               netdev->mtu, new_mtu);
+       e_info("changing MTU from %d to %d\n", netdev->mtu, new_mtu);
        netdev->mtu = new_mtu;
 
        if (netif_running(netdev))
@@ -4006,10 +4146,7 @@ static int e1000_resume(struct pci_dev *pdev)
        pci_restore_state(pdev);
        e1000e_disable_l1aspm(pdev);
 
-       if (adapter->need_ioport)
-               err = pci_enable_device(pdev);
-       else
-               err = pci_enable_device_mem(pdev);
+       err = pci_enable_device_mem(pdev);
        if (err) {
                dev_err(&pdev->dev,
                        "Cannot enable PCI device from suspend\n");
@@ -4043,7 +4180,7 @@ static int e1000_resume(struct pci_dev *pdev)
         * is up.  For all other cases, let the f/w know that the h/w is now
         * under the control of the driver.
         */
-       if (!(adapter->flags & FLAG_HAS_AMT) || !e1000e_check_mng_mode(&adapter->hw))
+       if (!(adapter->flags & FLAG_HAS_AMT))
                e1000_get_hw_control(adapter);
 
        return 0;
@@ -4111,10 +4248,7 @@ static pci_ers_result_t e1000_io_slot_reset(struct pci_dev *pdev)
        int err;
 
        e1000e_disable_l1aspm(pdev);
-       if (adapter->need_ioport)
-               err = pci_enable_device(pdev);
-       else
-               err = pci_enable_device_mem(pdev);
+       err = pci_enable_device_mem(pdev);
        if (err) {
                dev_err(&pdev->dev,
                        "Cannot re-enable PCI device after reset.\n");
@@ -4162,8 +4296,7 @@ static void e1000_io_resume(struct pci_dev *pdev)
         * is up.  For all other cases, let the f/w know that the h/w is now
         * under the control of the driver.
         */
-       if (!(adapter->flags & FLAG_HAS_AMT) ||
-           !e1000e_check_mng_mode(&adapter->hw))
+       if (!(adapter->flags & FLAG_HAS_AMT))
                e1000_get_hw_control(adapter);
 
 }
@@ -4175,36 +4308,40 @@ static void e1000_print_device_info(struct e1000_adapter *adapter)
        u32 pba_num;
 
        /* print bus type/speed/width info */
-       ndev_info(netdev, "(PCI Express:2.5GB/s:%s) "
-                 "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                 /* bus width */
-                ((hw->bus.width == e1000_bus_width_pcie_x4) ? "Width x4" :
-                 "Width x1"),
-                 /* MAC address */
-                 netdev->dev_addr[0], netdev->dev_addr[1],
-                 netdev->dev_addr[2], netdev->dev_addr[3],
-                 netdev->dev_addr[4], netdev->dev_addr[5]);
-       ndev_info(netdev, "Intel(R) PRO/%s Network Connection\n",
-                 (hw->phy.type == e1000_phy_ife)
-                  ? "10/100" : "1000");
+       e_info("(PCI Express:2.5GB/s:%s) %02x:%02x:%02x:%02x:%02x:%02x\n",
+              /* bus width */
+              ((hw->bus.width == e1000_bus_width_pcie_x4) ? "Width x4" :
+               "Width x1"),
+              /* MAC address */
+              netdev->dev_addr[0], netdev->dev_addr[1],
+              netdev->dev_addr[2], netdev->dev_addr[3],
+              netdev->dev_addr[4], netdev->dev_addr[5]);
+       e_info("Intel(R) PRO/%s Network Connection\n",
+              (hw->phy.type == e1000_phy_ife) ? "10/100" : "1000");
        e1000e_read_pba_num(hw, &pba_num);
-       ndev_info(netdev, "MAC: %d, PHY: %d, PBA No: %06x-%03x\n",
-                 hw->mac.type, hw->phy.type,
-                 (pba_num >> 8), (pba_num & 0xff));
+       e_info("MAC: %d, PHY: %d, PBA No: %06x-%03x\n",
+              hw->mac.type, hw->phy.type, (pba_num >> 8), (pba_num & 0xff));
 }
 
-/**
- * e1000e_is_need_ioport - determine if an adapter needs ioport resources or not
- * @pdev: PCI device information struct
- *
- * Returns true if an adapters needs ioport resources
- **/
-static int e1000e_is_need_ioport(struct pci_dev *pdev)
+static void e1000_eeprom_checks(struct e1000_adapter *adapter)
 {
-       switch (pdev->device) {
-       /* Currently there are no adapters that need ioport resources */
-       default:
-               return false;
+       struct e1000_hw *hw = &adapter->hw;
+       int ret_val;
+       u16 buf = 0;
+
+       if (hw->mac.type != e1000_82573)
+               return;
+
+       ret_val = e1000_read_nvm(hw, NVM_INIT_CONTROL2_REG, 1, &buf);
+       if (!(le16_to_cpu(buf) & (1 << 0))) {
+               /* Deep Smart Power Down (DSPD) */
+               e_warn("Warning: detected DSPD enabled in EEPROM\n");
+       }
+
+       ret_val = e1000_read_nvm(hw, NVM_INIT_3GIO_3, 1, &buf);
+       if (le16_to_cpu(buf) & (3 << 2)) {
+               /* ASPM enable */
+               e_warn("Warning: detected ASPM enabled in EEPROM\n");
        }
 }
 
@@ -4233,19 +4370,10 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
        int i, err, pci_using_dac;
        u16 eeprom_data = 0;
        u16 eeprom_apme_mask = E1000_EEPROM_APME;
-       int bars, need_ioport;
 
        e1000e_disable_l1aspm(pdev);
 
-       /* do not allocate ioport bars when not needed */
-       need_ioport = e1000e_is_need_ioport(pdev);
-       if (need_ioport) {
-               bars = pci_select_bars(pdev, IORESOURCE_MEM | IORESOURCE_IO);
-               err = pci_enable_device(pdev);
-       } else {
-               bars = pci_select_bars(pdev, IORESOURCE_MEM);
-               err = pci_enable_device_mem(pdev);
-       }
+       err = pci_enable_device_mem(pdev);
        if (err)
                return err;
 
@@ -4268,7 +4396,9 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
                }
        }
 
-       err = pci_request_selected_regions(pdev, bars, e1000e_driver_name);
+       err = pci_request_selected_regions(pdev,
+                                         pci_select_bars(pdev, IORESOURCE_MEM),
+                                         e1000e_driver_name);
        if (err)
                goto err_pci_reg;
 
@@ -4293,8 +4423,6 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
        adapter->hw.adapter = adapter;
        adapter->hw.mac.type = ei->mac;
        adapter->msg_enable = (1 << NETIF_MSG_DRV | NETIF_MSG_PROBE) - 1;
-       adapter->bars = bars;
-       adapter->need_ioport = need_ioport;
 
        mmio_start = pci_resource_start(pdev, 0);
        mmio_len = pci_resource_len(pdev, 0);
@@ -4366,8 +4494,7 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
        }
 
        if (e1000_check_reset_block(&adapter->hw))
-               ndev_info(netdev,
-                         "PHY reset is blocked due to SOL/IDER session.\n");
+               e_info("PHY reset is blocked due to SOL/IDER session.\n");
 
        netdev->features = NETIF_F_SG |
                           NETIF_F_HW_CSUM |
@@ -4411,25 +4538,26 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
                if (e1000_validate_nvm_checksum(&adapter->hw) >= 0)
                        break;
                if (i == 2) {
-                       ndev_err(netdev, "The NVM Checksum Is Not Valid\n");
+                       e_err("The NVM Checksum Is Not Valid\n");
                        err = -EIO;
                        goto err_eeprom;
                }
        }
 
+       e1000_eeprom_checks(adapter);
+
        /* copy the MAC address out of the NVM */
        if (e1000e_read_mac_addr(&adapter->hw))
-               ndev_err(netdev, "NVM Read Error while reading MAC address\n");
+               e_err("NVM Read Error while reading MAC address\n");
 
        memcpy(netdev->dev_addr, adapter->hw.mac.addr, netdev->addr_len);
        memcpy(netdev->perm_addr, adapter->hw.mac.addr, netdev->addr_len);
 
        if (!is_valid_ether_addr(netdev->perm_addr)) {
-               ndev_err(netdev, "Invalid MAC Address: "
-                        "%02x:%02x:%02x:%02x:%02x:%02x\n",
-                        netdev->perm_addr[0], netdev->perm_addr[1],
-                        netdev->perm_addr[2], netdev->perm_addr[3],
-                        netdev->perm_addr[4], netdev->perm_addr[5]);
+               e_err("Invalid MAC Address: %02x:%02x:%02x:%02x:%02x:%02x\n",
+                     netdev->perm_addr[0], netdev->perm_addr[1],
+                     netdev->perm_addr[2], netdev->perm_addr[3],
+                     netdev->perm_addr[4], netdev->perm_addr[5]);
                err = -EIO;
                goto err_eeprom;
        }
@@ -4499,8 +4627,7 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
         * is up.  For all other cases, let the f/w know that the h/w is now
         * under the control of the driver.
         */
-       if (!(adapter->flags & FLAG_HAS_AMT) ||
-           !e1000e_check_mng_mode(&adapter->hw))
+       if (!(adapter->flags & FLAG_HAS_AMT))
                e1000_get_hw_control(adapter);
 
        /* tell the stack to leave us alone until e1000_open() is called */
@@ -4517,24 +4644,25 @@ static int __devinit e1000_probe(struct pci_dev *pdev,
        return 0;
 
 err_register:
-err_hw_init:
-       e1000_release_hw_control(adapter);
+       if (!(adapter->flags & FLAG_HAS_AMT))
+               e1000_release_hw_control(adapter);
 err_eeprom:
        if (!e1000_check_reset_block(&adapter->hw))
                e1000_phy_hw_reset(&adapter->hw);
+err_hw_init:
 
-       if (adapter->hw.flash_address)
-               iounmap(adapter->hw.flash_address);
-
-err_flashmap:
        kfree(adapter->tx_ring);
        kfree(adapter->rx_ring);
 err_sw_init:
+       if (adapter->hw.flash_address)
+               iounmap(adapter->hw.flash_address);
+err_flashmap:
        iounmap(adapter->hw.hw_addr);
 err_ioremap:
        free_netdev(netdev);
 err_alloc_etherdev:
-       pci_release_selected_regions(pdev, bars);
+       pci_release_selected_regions(pdev,
+                                    pci_select_bars(pdev, IORESOURCE_MEM));
 err_pci_reg:
 err_dma:
        pci_disable_device(pdev);
@@ -4582,7 +4710,8 @@ static void __devexit e1000_remove(struct pci_dev *pdev)
        iounmap(adapter->hw.hw_addr);
        if (adapter->hw.flash_address)
                iounmap(adapter->hw.flash_address);
-       pci_release_selected_regions(pdev, adapter->bars);
+       pci_release_selected_regions(pdev,
+                                    pci_select_bars(pdev, IORESOURCE_MEM));
 
        free_netdev(netdev);