These changes are the raw update to linux-4.4.6-rt14. Kernel sources
[kvmfornfv.git] / kernel / drivers / net / ethernet / intel / igb / e1000_82575.c
index 0f69ef8..7a73510 100644 (file)
@@ -1,5 +1,5 @@
 /* Intel(R) Gigabit Ethernet Linux driver
- * Copyright(c) 2007-2014 Intel Corporation.
+ * Copyright(c) 2007-2015 Intel Corporation.
  *
  * This program is free software; you can redistribute it and/or modify it
  * under the terms and conditions of the GNU General Public License,
@@ -139,10 +139,6 @@ static s32 igb_check_for_link_media_swap(struct e1000_hw *hw)
        if (ret_val)
                return ret_val;
 
-       /* reset page to 0 */
-       ret_val = phy->ops.write_reg(hw, E1000_M88E1112_PAGE_ADDR, 0);
-       if (ret_val)
-               return ret_val;
 
        if (data & E1000_M88E1112_STATUS_LINK)
                port = E1000_MEDIA_PORT_OTHER;
@@ -151,8 +147,20 @@ static s32 igb_check_for_link_media_swap(struct e1000_hw *hw)
        if (port && (hw->dev_spec._82575.media_port != port)) {
                hw->dev_spec._82575.media_port = port;
                hw->dev_spec._82575.media_changed = true;
+       }
+
+       if (port == E1000_MEDIA_PORT_COPPER) {
+               /* reset page to 0 */
+               ret_val = phy->ops.write_reg(hw, E1000_M88E1112_PAGE_ADDR, 0);
+               if (ret_val)
+                       return ret_val;
+               igb_check_for_link_82575(hw);
        } else {
-               ret_val = igb_check_for_link_82575(hw);
+               igb_check_for_link_82575(hw);
+               /* reset page to 0 */
+               ret_val = phy->ops.write_reg(hw, E1000_M88E1112_PAGE_ADDR, 0);
+               if (ret_val)
+                       return ret_val;
        }
 
        return 0;
@@ -223,6 +231,7 @@ static s32 igb_init_phy_params_82575(struct e1000_hw *hw)
        /* Verify phy id and set remaining function pointers */
        switch (phy->id) {
        case M88E1543_E_PHY_ID:
+       case M88E1512_E_PHY_ID:
        case I347AT4_E_PHY_ID:
        case M88E1112_E_PHY_ID:
        case M88E1111_I_PHY_ID:
@@ -235,7 +244,7 @@ static s32 igb_init_phy_params_82575(struct e1000_hw *hw)
                else
                        phy->ops.get_cable_length = igb_get_cable_length_m88;
                phy->ops.force_speed_duplex = igb_phy_force_speed_duplex_m88;
-               /* Check if this PHY is confgured for media swap. */
+               /* Check if this PHY is configured for media swap. */
                if (phy->id == M88E1112_E_PHY_ID) {
                        u16 data;
 
@@ -258,6 +267,11 @@ static s32 igb_init_phy_params_82575(struct e1000_hw *hw)
                                hw->mac.ops.check_for_link =
                                                igb_check_for_link_media_swap;
                }
+               if (phy->id == M88E1512_E_PHY_ID) {
+                       ret_val = igb_initialize_M88E1512_phy(hw);
+                       if (ret_val)
+                               goto out;
+               }
                break;
        case IGP03E1000_E_PHY_ID:
                phy->type = e1000_phy_igp_3;
@@ -889,6 +903,7 @@ out:
  **/
 static s32 igb_phy_hw_reset_sgmii_82575(struct e1000_hw *hw)
 {
+       struct e1000_phy_info *phy = &hw->phy;
        s32 ret_val;
 
        /* This isn't a true "hard" reset, but is the only reset
@@ -905,7 +920,11 @@ static s32 igb_phy_hw_reset_sgmii_82575(struct e1000_hw *hw)
                goto out;
 
        ret_val = igb_phy_sw_reset(hw);
+       if (ret_val)
+               goto out;
 
+       if (phy->id == M88E1512_E_PHY_ID)
+               ret_val = igb_initialize_M88E1512_phy(hw);
 out:
        return ret_val;
 }
@@ -1579,6 +1598,7 @@ static s32 igb_setup_copper_link_82575(struct e1000_hw *hw)
                case I347AT4_E_PHY_ID:
                case M88E1112_E_PHY_ID:
                case M88E1543_E_PHY_ID:
+               case M88E1512_E_PHY_ID:
                case I210_I_PHY_ID:
                        ret_val = igb_copper_link_setup_m88_gen2(hw);
                        break;
@@ -1900,8 +1920,8 @@ static void igb_clear_hw_cntrs_82575(struct e1000_hw *hw)
  *  igb_rx_fifo_flush_82575 - Clean rx fifo after RX enable
  *  @hw: pointer to the HW structure
  *
- *  After rx enable if managability is enabled then there is likely some
- *  bad data at the start of the fifo and possibly in the DMA fifo.  This
+ *  After rx enable if manageability is enabled then there is likely some
+ *  bad data at the start of the fifo and possibly in the DMA fifo. This
  *  function clears the fifos and flushes any packets that came in as rx was
  *  being enabled.
  **/
@@ -1910,6 +1930,11 @@ void igb_rx_fifo_flush_82575(struct e1000_hw *hw)
        u32 rctl, rlpml, rxdctl[4], rfctl, temp_rctl, rx_enabled;
        int i, ms_wait;
 
+       /* disable IPv6 options as per hardware errata */
+       rfctl = rd32(E1000_RFCTL);
+       rfctl |= E1000_RFCTL_IPV6_EX_DIS;
+       wr32(E1000_RFCTL, rfctl);
+
        if (hw->mac.type != e1000_82575 ||
            !(rd32(E1000_MANC) & E1000_MANC_RCV_TCO_EN))
                return;
@@ -1937,7 +1962,6 @@ void igb_rx_fifo_flush_82575(struct e1000_hw *hw)
         * incoming packets are rejected.  Set enable and wait 2ms so that
         * any packet that was coming in as RCTL.EN was set is flushed
         */
-       rfctl = rd32(E1000_RFCTL);
        wr32(E1000_RFCTL, rfctl & ~E1000_RFCTL_LEF);
 
        rlpml = rd32(E1000_RLPML);
@@ -2617,7 +2641,8 @@ s32 igb_set_eee_i354(struct e1000_hw *hw, bool adv1G, bool adv100M)
        u16 phy_data;
 
        if ((hw->phy.media_type != e1000_media_type_copper) ||
-           (phy->id != M88E1543_E_PHY_ID))
+           ((phy->id != M88E1543_E_PHY_ID) &&
+            (phy->id != M88E1512_E_PHY_ID)))
                goto out;
 
        if (!hw->dev_spec._82575.eee_disable) {
@@ -2697,7 +2722,8 @@ s32 igb_get_eee_status_i354(struct e1000_hw *hw, bool *status)
 
        /* Check if EEE is supported on this device. */
        if ((hw->phy.media_type != e1000_media_type_copper) ||
-           (phy->id != M88E1543_E_PHY_ID))
+           ((phy->id != M88E1543_E_PHY_ID) &&
+            (phy->id != M88E1512_E_PHY_ID)))
                goto out;
 
        ret_val = igb_read_xmdio_reg(hw, E1000_PCS_STATUS_ADDR_I354,