New upstream version 18.02
[deb_dpdk.git] / drivers / net / ixgbe / base / ixgbe_common.c
index 1c5cb91..e7e9256 100644 (file)
@@ -113,6 +113,7 @@ s32 ixgbe_init_ops_generic(struct ixgbe_hw *hw)
        mac->ops.led_off = ixgbe_led_off_generic;
        mac->ops.blink_led_start = ixgbe_blink_led_start_generic;
        mac->ops.blink_led_stop = ixgbe_blink_led_stop_generic;
+       mac->ops.init_led_link_act = ixgbe_init_led_link_act_generic;
 
        /* RAR, Multicast, VLAN */
        mac->ops.set_rar = ixgbe_set_rar_generic;
@@ -166,18 +167,33 @@ bool ixgbe_device_supports_autoneg_fc(struct ixgbe_hw *hw)
        DEBUGFUNC("ixgbe_device_supports_autoneg_fc");
 
        switch (hw->phy.media_type) {
+       case ixgbe_media_type_fiber_fixed:
        case ixgbe_media_type_fiber_qsfp:
        case ixgbe_media_type_fiber:
-               hw->mac.ops.check_link(hw, &speed, &link_up, false);
-               /* if link is down, assume supported */
-               if (link_up)
-                       supported = speed == IXGBE_LINK_SPEED_1GB_FULL ?
+               /* flow control autoneg black list */
+               switch (hw->device_id) {
+               case IXGBE_DEV_ID_X550EM_A_SFP:
+               case IXGBE_DEV_ID_X550EM_A_SFP_N:
+               case IXGBE_DEV_ID_X550EM_A_QSFP:
+               case IXGBE_DEV_ID_X550EM_A_QSFP_N:
+                       supported = false;
+                       break;
+               default:
+                       hw->mac.ops.check_link(hw, &speed, &link_up, false);
+                       /* if link is down, assume supported */
+                       if (link_up)
+                               supported = speed == IXGBE_LINK_SPEED_1GB_FULL ?
                                true : false;
-               else
-                       supported = true;
+                       else
+                               supported = true;
+               }
+
                break;
        case ixgbe_media_type_backplane:
-               supported = true;
+               if (hw->device_id == IXGBE_DEV_ID_X550EM_X_XFI)
+                       supported = false;
+               else
+                       supported = true;
                break;
        case ixgbe_media_type_copper:
                /* only some copper devices support flow control autoneg */
@@ -185,9 +201,13 @@ bool ixgbe_device_supports_autoneg_fc(struct ixgbe_hw *hw)
                case IXGBE_DEV_ID_82599_T3_LOM:
                case IXGBE_DEV_ID_X540T:
                case IXGBE_DEV_ID_X540T1:
+               case IXGBE_DEV_ID_X540_BYPASS:
                case IXGBE_DEV_ID_X550T:
                case IXGBE_DEV_ID_X550T1:
                case IXGBE_DEV_ID_X550EM_X_10G_T:
+               case IXGBE_DEV_ID_X550EM_A_10G_T:
+               case IXGBE_DEV_ID_X550EM_A_1G_T:
+               case IXGBE_DEV_ID_X550EM_A_1G_T_L:
                        supported = true;
                        break;
                default:
@@ -197,9 +217,10 @@ bool ixgbe_device_supports_autoneg_fc(struct ixgbe_hw *hw)
                break;
        }
 
-       ERROR_REPORT2(IXGBE_ERROR_UNSUPPORTED,
-                     "Device %x does not support flow control autoneg",
-                     hw->device_id);
+       if (!supported)
+               ERROR_REPORT2(IXGBE_ERROR_UNSUPPORTED,
+                             "Device %x does not support flow control autoneg",
+                             hw->device_id);
        return supported;
 }
 
@@ -245,7 +266,8 @@ s32 ixgbe_setup_fc_generic(struct ixgbe_hw *hw)
                if (ret_val != IXGBE_SUCCESS)
                        goto out;
 
-               /* only backplane uses autoc so fall though */
+               /* fall through - only backplane uses autoc */
+       case ixgbe_media_type_fiber_fixed:
        case ixgbe_media_type_fiber_qsfp:
        case ixgbe_media_type_fiber:
                reg = IXGBE_READ_REG(hw, IXGBE_PCS1GANA);
@@ -371,6 +393,7 @@ s32 ixgbe_start_hw_generic(struct ixgbe_hw *hw)
 {
        s32 ret_val;
        u32 ctrl_ext;
+       u16 device_caps;
 
        DEBUGFUNC("ixgbe_start_hw_generic");
 
@@ -393,14 +416,31 @@ s32 ixgbe_start_hw_generic(struct ixgbe_hw *hw)
 
        /* Setup flow control */
        ret_val = ixgbe_setup_fc(hw);
-       if (ret_val != IXGBE_SUCCESS)
-               goto out;
+       if (ret_val != IXGBE_SUCCESS && ret_val != IXGBE_NOT_IMPLEMENTED) {
+               DEBUGOUT1("Flow control setup failed, returning %d\n", ret_val);
+               return ret_val;
+       }
+
+       /* Cache bit indicating need for crosstalk fix */
+       switch (hw->mac.type) {
+       case ixgbe_mac_82599EB:
+       case ixgbe_mac_X550EM_x:
+       case ixgbe_mac_X550EM_a:
+               hw->mac.ops.get_device_caps(hw, &device_caps);
+               if (device_caps & IXGBE_DEVICE_CAPS_NO_CROSSTALK_WR)
+                       hw->need_crosstalk_fix = false;
+               else
+                       hw->need_crosstalk_fix = true;
+               break;
+       default:
+               hw->need_crosstalk_fix = false;
+               break;
+       }
 
        /* Clear adapter stopped flag */
        hw->adapter_stopped = false;
 
-out:
-       return ret_val;
+       return IXGBE_SUCCESS;
 }
 
 /**
@@ -461,11 +501,18 @@ s32 ixgbe_init_hw_generic(struct ixgbe_hw *hw)
        /* Reset the hardware */
        status = hw->mac.ops.reset_hw(hw);
 
-       if (status == IXGBE_SUCCESS) {
+       if (status == IXGBE_SUCCESS || status == IXGBE_ERR_SFP_NOT_PRESENT) {
                /* Start the HW */
                status = hw->mac.ops.start_hw(hw);
        }
 
+       /* Initialize the LED link active for LED blink support */
+       if (hw->mac.ops.init_led_link_act)
+               hw->mac.ops.init_led_link_act(hw);
+
+       if (status != IXGBE_SUCCESS)
+               DEBUGOUT1("Failed to initialize HW, STATUS = %d\n", status);
+
        return status;
 }
 
@@ -1046,7 +1093,7 @@ void ixgbe_set_lan_id_multi_port_pcie(struct ixgbe_hw *hw)
        if (hw->device_id == IXGBE_DEV_ID_X550EM_A_SFP) {
                hw->eeprom.ops.read(hw, IXGBE_EEPROM_CTRL_4, &ee_ctrl_4);
                bus->instance_id = (ee_ctrl_4 & IXGBE_EE_CTRL_4_INST_ID) >>
-                       IXGBE_EE_CTRL_4_INST_ID_SHIFT;
+                                  IXGBE_EE_CTRL_4_INST_ID_SHIFT;
        }
 }
 
@@ -1104,6 +1151,47 @@ s32 ixgbe_stop_adapter_generic(struct ixgbe_hw *hw)
        return ixgbe_disable_pcie_master(hw);
 }
 
+/**
+ *  ixgbe_init_led_link_act_generic - Store the LED index link/activity.
+ *  @hw: pointer to hardware structure
+ *
+ *  Store the index for the link active LED. This will be used to support
+ *  blinking the LED.
+ **/
+s32 ixgbe_init_led_link_act_generic(struct ixgbe_hw *hw)
+{
+       struct ixgbe_mac_info *mac = &hw->mac;
+       u32 led_reg, led_mode;
+       u8 i;
+
+       led_reg = IXGBE_READ_REG(hw, IXGBE_LEDCTL);
+
+       /* Get LED link active from the LEDCTL register */
+       for (i = 0; i < 4; i++) {
+               led_mode = led_reg >> IXGBE_LED_MODE_SHIFT(i);
+
+               if ((led_mode & IXGBE_LED_MODE_MASK_BASE) ==
+                    IXGBE_LED_LINK_ACTIVE) {
+                       mac->led_link_act = i;
+                       return IXGBE_SUCCESS;
+               }
+       }
+
+       /*
+        * If LEDCTL register does not have the LED link active set, then use
+        * known MAC defaults.
+        */
+       switch (hw->mac.type) {
+       case ixgbe_mac_X550EM_a:
+       case ixgbe_mac_X550EM_x:
+               mac->led_link_act = 1;
+               break;
+       default:
+               mac->led_link_act = 2;
+       }
+       return IXGBE_SUCCESS;
+}
+
 /**
  *  ixgbe_led_on_generic - Turns on the software controllable LEDs.
  *  @hw: pointer to hardware structure
@@ -1115,6 +1203,9 @@ s32 ixgbe_led_on_generic(struct ixgbe_hw *hw, u32 index)
 
        DEBUGFUNC("ixgbe_led_on_generic");
 
+       if (index > 3)
+               return IXGBE_ERR_PARAM;
+
        /* To turn on the LED, set mode to ON. */
        led_reg &= ~IXGBE_LED_MODE_MASK(index);
        led_reg |= IXGBE_LED_ON << IXGBE_LED_MODE_SHIFT(index);
@@ -1135,6 +1226,9 @@ s32 ixgbe_led_off_generic(struct ixgbe_hw *hw, u32 index)
 
        DEBUGFUNC("ixgbe_led_off_generic");
 
+       if (index > 3)
+               return IXGBE_ERR_PARAM;
+
        /* To turn off the LED, set mode to OFF. */
        led_reg &= ~IXGBE_LED_MODE_MASK(index);
        led_reg |= IXGBE_LED_OFF << IXGBE_LED_MODE_SHIFT(index);
@@ -2002,6 +2096,7 @@ STATIC void ixgbe_shift_out_eeprom_bits(struct ixgbe_hw *hw, u16 data,
 /**
  *  ixgbe_shift_in_eeprom_bits - Shift data bits in from the EEPROM
  *  @hw: pointer to hardware structure
+ *  @count: number of bits to shift
  **/
 STATIC u16 ixgbe_shift_in_eeprom_bits(struct ixgbe_hw *hw, u16 count)
 {
@@ -2060,7 +2155,7 @@ STATIC void ixgbe_raise_eeprom_clk(struct ixgbe_hw *hw, u32 *eec)
 /**
  *  ixgbe_lower_eeprom_clk - Lowers the EEPROM's clock input.
  *  @hw: pointer to hardware structure
- *  @eecd: EECD's current value
+ *  @eec: EEC's current value
  **/
 STATIC void ixgbe_lower_eeprom_clk(struct ixgbe_hw *hw, u32 *eec)
 {
@@ -2440,6 +2535,7 @@ s32 ixgbe_init_rx_addrs_generic(struct ixgbe_hw *hw)
  *  ixgbe_add_uc_addr - Adds a secondary unicast address.
  *  @hw: pointer to hardware structure
  *  @addr: new address
+ *  @vmdq: VMDq "set" or "pool" index
  *
  *  Adds it to unused receive address register or goes into promiscuous mode.
  **/
@@ -2584,7 +2680,7 @@ STATIC s32 ixgbe_mta_vector(struct ixgbe_hw *hw, u8 *mc_addr)
 /**
  *  ixgbe_set_mta - Set bit-vector in multicast table
  *  @hw: pointer to hardware structure
- *  @hash_value: Multicast address hash value
+ *  @mc_addr: Multicast address
  *
  *  Sets the bit-vector in the multicast table.
  **/
@@ -2851,7 +2947,7 @@ out:
  *  advertised settings
  **/
 s32 ixgbe_negotiate_fc(struct ixgbe_hw *hw, u32 adv_reg, u32 lp_reg,
-                             u32 adv_sym, u32 adv_asm, u32 lp_sym, u32 lp_asm)
+                      u32 adv_sym, u32 adv_asm, u32 lp_sym, u32 lp_asm)
 {
        if ((!(adv_reg)) ||  (!(lp_reg))) {
                ERROR_REPORT3(IXGBE_ERROR_UNSUPPORTED,
@@ -3031,6 +3127,7 @@ void ixgbe_fc_autoneg(struct ixgbe_hw *hw)
 
        switch (hw->phy.media_type) {
        /* Autoneg flow control on fiber adapters */
+       case ixgbe_media_type_fiber_fixed:
        case ixgbe_media_type_fiber_qsfp:
        case ixgbe_media_type_fiber:
                if (speed == IXGBE_LINK_SPEED_1GB_FULL)
@@ -3256,7 +3353,7 @@ void ixgbe_release_swfw_sync(struct ixgbe_hw *hw, u32 mask)
  **/
 s32 ixgbe_disable_sec_rx_path_generic(struct ixgbe_hw *hw)
 {
-#define IXGBE_MAX_SECRX_POLL 40
+#define IXGBE_MAX_SECRX_POLL 4000
 
        int i;
        int secrxreg;
@@ -3273,7 +3370,7 @@ s32 ixgbe_disable_sec_rx_path_generic(struct ixgbe_hw *hw)
                        break;
                else
                        /* Use interrupt-safe sleep just in case */
-                       usec_delay(1000);
+                       usec_delay(10);
        }
 
        /* For informational purposes only */
@@ -3287,6 +3384,7 @@ s32 ixgbe_disable_sec_rx_path_generic(struct ixgbe_hw *hw)
 /**
  *  prot_autoc_read_generic - Hides MAC differences needed for AUTOC read
  *  @hw: pointer to hardware structure
+ *  @locked: bool to indicate whether the SW/FW lock was taken
  *  @reg_val: Value we read from AUTOC
  *
  *  The default case requires no protection so just to the register read.
@@ -3323,7 +3421,7 @@ s32 prot_autoc_write_generic(struct ixgbe_hw *hw, u32 reg_val, bool locked)
  **/
 s32 ixgbe_enable_sec_rx_path_generic(struct ixgbe_hw *hw)
 {
-       int secrxreg;
+       u32 secrxreg;
 
        DEBUGFUNC("ixgbe_enable_sec_rx_path_generic");
 
@@ -3370,6 +3468,9 @@ s32 ixgbe_blink_led_start_generic(struct ixgbe_hw *hw, u32 index)
 
        DEBUGFUNC("ixgbe_blink_led_start_generic");
 
+       if (index > 3)
+               return IXGBE_ERR_PARAM;
+
        /*
         * Link must be up to auto-blink the LEDs;
         * Force it if link is down.
@@ -3415,6 +3516,10 @@ s32 ixgbe_blink_led_stop_generic(struct ixgbe_hw *hw, u32 index)
 
        DEBUGFUNC("ixgbe_blink_led_stop_generic");
 
+       if (index > 3)
+               return IXGBE_ERR_PARAM;
+
+
        ret_val = hw->mac.ops.prot_autoc_read(hw, &locked, &autoc_reg);
        if (ret_val != IXGBE_SUCCESS)
                goto out;
@@ -3720,7 +3825,8 @@ s32 ixgbe_clear_vmdq_generic(struct ixgbe_hw *hw, u32 rar, u32 vmdq)
        }
 
        /* was that the last pool using this rar? */
-       if (mpsar_lo == 0 && mpsar_hi == 0 && rar != 0)
+       if (mpsar_lo == 0 && mpsar_hi == 0 &&
+           rar != 0 && rar != hw->mac.san_mac_rar_index)
                hw->mac.ops.clear_rar(hw, rar);
 done:
        return IXGBE_SUCCESS;
@@ -3806,6 +3912,9 @@ s32 ixgbe_init_uta_tables_generic(struct ixgbe_hw *hw)
  *  ixgbe_find_vlvf_slot - find the vlanid or the first empty slot
  *  @hw: pointer to hardware structure
  *  @vlan: VLAN id to write to VLAN filter
+ *  @vlvf_bypass: true to find vlanid only, false returns first empty slot if
+ *               vlanid not found
+ *
  *
  *  return the VLVF index where this VLAN id should be placed
  *
@@ -3887,7 +3996,8 @@ s32 ixgbe_set_vfta_generic(struct ixgbe_hw *hw, u32 vlan, u32 vind,
        vfta_delta = 1 << (vlan % 32);
        vfta = IXGBE_READ_REG(hw, IXGBE_VFTA(regidx));
 
-       /* vfta_delta represents the difference between the current value
+       /*
+        * vfta_delta represents the difference between the current value
         * of vfta and the value we want in the register.  Since the diff
         * is an XOR mask we can just update the vfta using an XOR
         */
@@ -3920,7 +4030,7 @@ vfta_update:
  *  @vind: VMDq output index that maps queue to VLAN id in VLVFB
  *  @vlan_on: boolean flag to turn on/off VLAN in VLVF
  *  @vfta_delta: pointer to the difference between the current value of VFTA
- * and the desired value
+ *              and the desired value
  *  @vfta: the desired value of the VFTA
  *  @vlvf_bypass: boolean flag indicating updating default pool is okay
  *
@@ -3947,6 +4057,7 @@ s32 ixgbe_set_vlvf_generic(struct ixgbe_hw *hw, u32 vlan, u32 vind,
         */
        if (!(IXGBE_READ_REG(hw, IXGBE_VT_CTL) & IXGBE_VT_CTL_VT_ENABLE))
                return IXGBE_SUCCESS;
+
        vlvf_index = ixgbe_find_vlvf_slot(hw, vlan, vlvf_bypass);
        if (vlvf_index < 0)
                return vlvf_index;
@@ -3976,6 +4087,7 @@ s32 ixgbe_set_vlvf_generic(struct ixgbe_hw *hw, u32 vlan, u32 vind,
 
                return IXGBE_SUCCESS;
        }
+
        /* If there are still bits set in the VLVFB registers
         * for the VLAN ID indicated we need to see if the
         * caller is requesting that we clear the VFTA entry bit.
@@ -4024,6 +4136,32 @@ s32 ixgbe_clear_vfta_generic(struct ixgbe_hw *hw)
        return IXGBE_SUCCESS;
 }
 
+/**
+ *  ixgbe_need_crosstalk_fix - Determine if we need to do cross talk fix
+ *  @hw: pointer to hardware structure
+ *
+ *  Contains the logic to identify if we need to verify link for the
+ *  crosstalk fix
+ **/
+static bool ixgbe_need_crosstalk_fix(struct ixgbe_hw *hw)
+{
+
+       /* Does FW say we need the fix */
+       if (!hw->need_crosstalk_fix)
+               return false;
+
+       /* Only consider SFP+ PHYs i.e. media type fiber */
+       switch (hw->mac.ops.get_media_type(hw)) {
+       case ixgbe_media_type_fiber:
+       case ixgbe_media_type_fiber_qsfp:
+               break;
+       default:
+               return false;
+       }
+
+       return true;
+}
+
 /**
  *  ixgbe_check_mac_link_generic - Determine link and speed status
  *  @hw: pointer to hardware structure
@@ -4041,6 +4179,35 @@ s32 ixgbe_check_mac_link_generic(struct ixgbe_hw *hw, ixgbe_link_speed *speed,
 
        DEBUGFUNC("ixgbe_check_mac_link_generic");
 
+       /* If Crosstalk fix enabled do the sanity check of making sure
+        * the SFP+ cage is full.
+        */
+       if (ixgbe_need_crosstalk_fix(hw)) {
+               u32 sfp_cage_full;
+
+               switch (hw->mac.type) {
+               case ixgbe_mac_82599EB:
+                       sfp_cage_full = IXGBE_READ_REG(hw, IXGBE_ESDP) &
+                                       IXGBE_ESDP_SDP2;
+                       break;
+               case ixgbe_mac_X550EM_x:
+               case ixgbe_mac_X550EM_a:
+                       sfp_cage_full = IXGBE_READ_REG(hw, IXGBE_ESDP) &
+                                       IXGBE_ESDP_SDP0;
+                       break;
+               default:
+                       /* sanity check - No SFP+ devices here */
+                       sfp_cage_full = false;
+                       break;
+               }
+
+               if (!sfp_cage_full) {
+                       *link_up = false;
+                       *speed = IXGBE_LINK_SPEED_UNKNOWN;
+                       return IXGBE_SUCCESS;
+               }
+       }
+
        /* clear the old state */
        links_orig = IXGBE_READ_REG(hw, IXGBE_LINKS);
 
@@ -4082,11 +4249,25 @@ s32 ixgbe_check_mac_link_generic(struct ixgbe_hw *hw, ixgbe_link_speed *speed,
                break;
        case IXGBE_LINKS_SPEED_100_82599:
                *speed = IXGBE_LINK_SPEED_100_FULL;
-               if (hw->mac.type >= ixgbe_mac_X550) {
+               if (hw->mac.type == ixgbe_mac_X550) {
                        if (links_reg & IXGBE_LINKS_SPEED_NON_STD)
                                *speed = IXGBE_LINK_SPEED_5GB_FULL;
                }
                break;
+       case IXGBE_LINKS_SPEED_10_X550EM_A:
+               *speed = IXGBE_LINK_SPEED_UNKNOWN;
+#ifdef PREBOOT_SUPPORT
+               if (hw->device_id == IXGBE_DEV_ID_X550EM_A_1G_T ||
+                   hw->device_id == IXGBE_DEV_ID_X550EM_A_1G_T_L ||
+                   hw->device_id == IXGBE_DEV_ID_X550EM_A_SGMII ||
+                   hw->device_id == IXGBE_DEV_ID_X550EM_A_SGMII_L)
+                       *speed = IXGBE_LINK_SPEED_10_FULL;
+#else
+               if (hw->device_id == IXGBE_DEV_ID_X550EM_A_1G_T ||
+                   hw->device_id == IXGBE_DEV_ID_X550EM_A_1G_T_L)
+                       *speed = IXGBE_LINK_SPEED_10_FULL;
+#endif /* PREBOOT_SUPPORT */
+               break;
        default:
                *speed = IXGBE_LINK_SPEED_UNKNOWN;
        }
@@ -4413,10 +4594,11 @@ s32 ixgbe_host_interface_command(struct ixgbe_hw *hw, u32 *buffer,
                                 u32 length, u32 timeout, bool return_data)
 {
        u32 hdr_size = sizeof(struct ixgbe_hic_hdr);
-       u16 dword_len;
+       struct ixgbe_hic_hdr *resp = (struct ixgbe_hic_hdr *)buffer;
        u16 buf_len;
        s32 status;
        u32 bi;
+       u32 dword_len;
 
        DEBUGFUNC("ixgbe_host_interface_command");
 
@@ -4443,11 +4625,26 @@ s32 ixgbe_host_interface_command(struct ixgbe_hw *hw, u32 *buffer,
        /* first pull in the header so we know the buffer length */
        for (bi = 0; bi < dword_len; bi++) {
                buffer[bi] = IXGBE_READ_REG_ARRAY(hw, IXGBE_FLEX_MNG, bi);
-               IXGBE_LE32_TO_CPUS(&buffer[bi]);
+               IXGBE_LE32_TO_CPUS((uintptr_t)&buffer[bi]);
        }
 
-       /* If there is any thing in data position pull it in */
-       buf_len = ((struct ixgbe_hic_hdr *)buffer)->buf_len;
+       /*
+        * If there is any thing in data position pull it in
+        * Read Flash command requires reading buffer length from
+        * two byes instead of one byte
+        */
+       if (resp->cmd == 0x30) {
+               for (; bi < dword_len + 2; bi++) {
+                       buffer[bi] = IXGBE_READ_REG_ARRAY(hw, IXGBE_FLEX_MNG,
+                                                         bi);
+                       IXGBE_LE32_TO_CPUS(&buffer[bi]);
+               }
+               buf_len = (((u16)(resp->cmd_or_resp.ret_status) << 3)
+                                 & 0xF00) | resp->buf_len;
+               hdr_size += (2 << 2);
+       } else {
+               buf_len = resp->buf_len;
+       }
        if (!buf_len)
                goto rel_out;
 
@@ -4463,7 +4660,7 @@ s32 ixgbe_host_interface_command(struct ixgbe_hw *hw, u32 *buffer,
        /* Pull in the rest of the buffer (bi is where we left off) */
        for (; bi <= dword_len; bi++) {
                buffer[bi] = IXGBE_READ_REG_ARRAY(hw, IXGBE_FLEX_MNG, bi);
-               IXGBE_LE32_TO_CPUS(&buffer[bi]);
+               IXGBE_LE32_TO_CPUS((uintptr_t)&buffer[bi]);
        }
 
 rel_out:
@@ -4479,6 +4676,8 @@ rel_out:
  *  @min: driver version minor number
  *  @build: driver version build number
  *  @sub: driver version sub build number
+ *  @len: unused
+ *  @driver_ver: unused
  *
  *  Sends driver version number to firmware through the manageability
  *  block.  On success return IXGBE_SUCCESS
@@ -4486,13 +4685,15 @@ rel_out:
  *  semaphore or IXGBE_ERR_HOST_INTERFACE_COMMAND when command fails.
  **/
 s32 ixgbe_set_fw_drv_ver_generic(struct ixgbe_hw *hw, u8 maj, u8 min,
-                                u8 build, u8 sub)
+                                u8 build, u8 sub, u16 len,
+                                const char *driver_ver)
 {
        struct ixgbe_hic_drv_info fw_cmd;
        int i;
        s32 ret_val = IXGBE_SUCCESS;
 
        DEBUGFUNC("ixgbe_set_fw_drv_ver_generic");
+       UNREFERENCED_2PARAMETER(len, driver_ver);
 
        fw_cmd.hdr.cmd = FW_CEM_CMD_DRIVER_INFO;
        fw_cmd.hdr.buf_len = FW_CEM_CMD_DRIVER_INFO_LEN;
@@ -4503,10 +4704,10 @@ s32 ixgbe_set_fw_drv_ver_generic(struct ixgbe_hw *hw, u8 maj, u8 min,
        fw_cmd.ver_build = build;
        fw_cmd.ver_sub = sub;
        fw_cmd.hdr.checksum = 0;
-       fw_cmd.hdr.checksum = ixgbe_calculate_checksum((u8 *)&fw_cmd,
-                               (FW_CEM_HDR_LEN + fw_cmd.hdr.buf_len));
        fw_cmd.pad = 0;
        fw_cmd.pad2 = 0;
+       fw_cmd.hdr.checksum = ixgbe_calculate_checksum((u8 *)&fw_cmd,
+                               (FW_CEM_HDR_LEN + fw_cmd.hdr.buf_len));
 
        for (i = 0; i <= FW_CEM_MAX_RETRIES; i++) {
                ret_val = ixgbe_host_interface_command(hw, (u32 *)&fw_cmd,
@@ -4561,7 +4762,7 @@ void ixgbe_set_rxpba_generic(struct ixgbe_hw *hw, int num_pb, u32 headroom,
                rxpktsize <<= IXGBE_RXPBSIZE_SHIFT;
                for (; i < (num_pb / 2); i++)
                        IXGBE_WRITE_REG(hw, IXGBE_RXPBSIZE(i), rxpktsize);
-               /* Fall through to configure remaining packet buffers */
+               /* fall through - configure remaining packet buffers */
        case PBA_STRATEGY_EQUAL:
                rxpktsize = (pbsize / (num_pb - i)) << IXGBE_RXPBSIZE_SHIFT;
                for (; i < num_pb; i++)
@@ -4664,7 +4865,6 @@ STATIC const u8 ixgbe_emc_therm_limit[4] = {
 /**
  *  ixgbe_get_thermal_sensor_data - Gathers thermal sensor data
  *  @hw: pointer to hardware structure
- *  @data: pointer to the thermal sensor data structure
  *
  *  Returns the thermal sensor data structure
  **/
@@ -4817,6 +5017,117 @@ eeprom_err:
        return IXGBE_NOT_IMPLEMENTED;
 }
 
+/**
+ *  ixgbe_get_orom_version - Return option ROM from EEPROM
+ *
+ *  @hw: pointer to hardware structure
+ *  @nvm_ver: pointer to output structure
+ *
+ *  if valid option ROM version, nvm_ver->or_valid set to true
+ *  else nvm_ver->or_valid is false.
+ **/
+void ixgbe_get_orom_version(struct ixgbe_hw *hw,
+                           struct ixgbe_nvm_version *nvm_ver)
+{
+       u16 offset, eeprom_cfg_blkh, eeprom_cfg_blkl;
+
+       nvm_ver->or_valid = false;
+       /* Option Rom may or may not be present.  Start with pointer */
+       hw->eeprom.ops.read(hw, NVM_OROM_OFFSET, &offset);
+
+       /* make sure offset is valid */
+       if ((offset == 0x0) || (offset == NVM_INVALID_PTR))
+               return;
+
+       hw->eeprom.ops.read(hw, offset + NVM_OROM_BLK_HI, &eeprom_cfg_blkh);
+       hw->eeprom.ops.read(hw, offset + NVM_OROM_BLK_LOW, &eeprom_cfg_blkl);
+
+       /* option rom exists and is valid */
+       if ((eeprom_cfg_blkl | eeprom_cfg_blkh) == 0x0 ||
+           eeprom_cfg_blkl == NVM_VER_INVALID ||
+           eeprom_cfg_blkh == NVM_VER_INVALID)
+               return;
+
+       nvm_ver->or_valid = true;
+       nvm_ver->or_major = eeprom_cfg_blkl >> NVM_OROM_SHIFT;
+       nvm_ver->or_build = (eeprom_cfg_blkl << NVM_OROM_SHIFT) |
+                           (eeprom_cfg_blkh >> NVM_OROM_SHIFT);
+       nvm_ver->or_patch = eeprom_cfg_blkh & NVM_OROM_PATCH_MASK;
+}
+
+/**
+ *  ixgbe_get_oem_prod_version - Return OEM Product version
+ *
+ *  @hw: pointer to hardware structure
+ *  @nvm_ver: pointer to output structure
+ *
+ *  if valid OEM product version, nvm_ver->oem_valid set to true
+ *  else nvm_ver->oem_valid is false.
+ **/
+void ixgbe_get_oem_prod_version(struct ixgbe_hw *hw,
+                               struct ixgbe_nvm_version *nvm_ver)
+{
+       u16 rel_num, prod_ver, mod_len, cap, offset;
+
+       nvm_ver->oem_valid = false;
+       hw->eeprom.ops.read(hw, NVM_OEM_PROD_VER_PTR, &offset);
+
+       /* Return is offset to OEM Product Version block is invalid */
+       if (offset == 0x0 && offset == NVM_INVALID_PTR)
+               return;
+
+       /* Read product version block */
+       hw->eeprom.ops.read(hw, offset, &mod_len);
+       hw->eeprom.ops.read(hw, offset + NVM_OEM_PROD_VER_CAP_OFF, &cap);
+
+       /* Return if OEM product version block is invalid */
+       if (mod_len != NVM_OEM_PROD_VER_MOD_LEN ||
+           (cap & NVM_OEM_PROD_VER_CAP_MASK) != 0x0)
+               return;
+
+       hw->eeprom.ops.read(hw, offset + NVM_OEM_PROD_VER_OFF_L, &prod_ver);
+       hw->eeprom.ops.read(hw, offset + NVM_OEM_PROD_VER_OFF_H, &rel_num);
+
+       /* Return if version is invalid */
+       if ((rel_num | prod_ver) == 0x0 ||
+           rel_num == NVM_VER_INVALID || prod_ver == NVM_VER_INVALID)
+               return;
+
+       nvm_ver->oem_major = prod_ver >> NVM_VER_SHIFT;
+       nvm_ver->oem_minor = prod_ver & NVM_VER_MASK;
+       nvm_ver->oem_release = rel_num;
+       nvm_ver->oem_valid = true;
+}
+
+/**
+ *  ixgbe_get_etk_id - Return Etrack ID from EEPROM
+ *
+ *  @hw: pointer to hardware structure
+ *  @nvm_ver: pointer to output structure
+ *
+ *  word read errors will return 0xFFFF
+ **/
+void ixgbe_get_etk_id(struct ixgbe_hw *hw, struct ixgbe_nvm_version *nvm_ver)
+{
+       u16 etk_id_l, etk_id_h;
+
+       if (hw->eeprom.ops.read(hw, NVM_ETK_OFF_LOW, &etk_id_l))
+               etk_id_l = NVM_VER_INVALID;
+       if (hw->eeprom.ops.read(hw, NVM_ETK_OFF_HI, &etk_id_h))
+               etk_id_h = NVM_VER_INVALID;
+
+       /* The word order for the version format is determined by high order
+        * word bit 15.
+        */
+       if ((etk_id_h & NVM_ETK_VALID) == 0) {
+               nvm_ver->etk_id = etk_id_h;
+               nvm_ver->etk_id |= (etk_id_l << NVM_ETK_SHIFT);
+       } else {
+               nvm_ver->etk_id = etk_id_l;
+               nvm_ver->etk_id |= (etk_id_h << NVM_ETK_SHIFT);
+       }
+}
+
 
 /**
  * ixgbe_dcb_get_rtrup2tc_generic - read rtrup2tc reg
@@ -4888,8 +5199,8 @@ bool ixgbe_mng_present(struct ixgbe_hw *hw)
                return false;
 
        fwsm = IXGBE_READ_REG(hw, IXGBE_FWSM_BY_MAC(hw));
-       fwsm &= IXGBE_FWSM_MODE_MASK;
-       return fwsm == IXGBE_FWSM_FW_MODE_PT;
+
+       return !!(fwsm & IXGBE_FWSM_FW_MODE_PT);
 }
 
 /**
@@ -4956,6 +5267,7 @@ s32 ixgbe_setup_mac_link_multispeed_fiber(struct ixgbe_hw *hw,
 
                /* Set the module link speed */
                switch (hw->phy.media_type) {
+               case ixgbe_media_type_fiber_fixed:
                case ixgbe_media_type_fiber:
                        ixgbe_set_rate_select_speed(hw,
                                                    IXGBE_LINK_SPEED_10GB_FULL);
@@ -5006,6 +5318,7 @@ s32 ixgbe_setup_mac_link_multispeed_fiber(struct ixgbe_hw *hw,
 
                /* Set the module link speed */
                switch (hw->phy.media_type) {
+               case ixgbe_media_type_fiber_fixed:
                case ixgbe_media_type_fiber:
                        ixgbe_set_rate_select_speed(hw,
                                                    IXGBE_LINK_SPEED_1GB_FULL);