igb: add 88E1543 initialization code
authorTodd Fujinaka <todd.fujinaka@intel.com>
Wed, 2 Sep 2015 23:54:20 +0000 (16:54 -0700)
committerJeff Kirsher <jeffrey.t.kirsher@intel.com>
Sun, 13 Dec 2015 07:09:43 +0000 (23:09 -0800)
Initialize the 88E1543 PHY.

Signed-off-by: Todd Fujinaka <todd.fujinaka@intel.com>
Tested-by: Aaron Brown <aaron.f.brown@intel.com>
Signed-off-by: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
drivers/net/ethernet/intel/igb/e1000_82575.c
drivers/net/ethernet/intel/igb/e1000_defines.h
drivers/net/ethernet/intel/igb/e1000_phy.c
drivers/net/ethernet/intel/igb/e1000_phy.h

index 7a73510e547cd49f38629b4d60fbab8b8dce945a..d9664c47fe3a331b9299aa744a1f16dea353d495 100644 (file)
@@ -272,6 +272,11 @@ static s32 igb_init_phy_params_82575(struct e1000_hw *hw)
                        if (ret_val)
                                goto out;
                }
+               if (phy->id == M88E1543_E_PHY_ID) {
+                       ret_val = igb_initialize_M88E1543_phy(hw);
+                       if (ret_val)
+                               goto out;
+               }
                break;
        case IGP03E1000_E_PHY_ID:
                phy->type = e1000_phy_igp_3;
@@ -925,6 +930,8 @@ static s32 igb_phy_hw_reset_sgmii_82575(struct e1000_hw *hw)
 
        if (phy->id == M88E1512_E_PHY_ID)
                ret_val = igb_initialize_M88E1512_phy(hw);
+       if (phy->id == M88E1543_E_PHY_ID)
+               ret_val = igb_initialize_M88E1543_phy(hw);
 out:
        return ret_val;
 }
index b1915043bc0cfefbe416b6bf5ca59658a8f47278..a61ee9462dd48583129d839c79a9628d8480d780 100644 (file)
 #define E1000_M88E1543_PAGE_ADDR       0x16       /* Page Offset Register */
 #define E1000_M88E1543_EEE_CTRL_1      0x0
 #define E1000_M88E1543_EEE_CTRL_1_MS   0x0001     /* EEE Master/Slave */
+#define E1000_M88E1543_FIBER_CTRL      0x0
 #define E1000_EEE_ADV_DEV_I354         7
 #define E1000_EEE_ADV_ADDR_I354                60
 #define E1000_EEE_ADV_100_SUPPORTED    (1 << 1)   /* 100BaseTx EEE Supported */
index 23ec28f43f6d3d354094655c7c696c5f7e3bfb1b..c0df40f2b29585fc52d2edc23ec10b4ed192e262 100644 (file)
@@ -2277,6 +2277,100 @@ out:
        return ret_val;
 }
 
+/**
+ *  igb_initialize_M88E1543_phy - Initialize M88E1512 PHY
+ *  @hw: pointer to the HW structure
+ *
+ *  Initialize Marvell 1543 to work correctly with Avoton.
+ **/
+s32 igb_initialize_M88E1543_phy(struct e1000_hw *hw)
+{
+       struct e1000_phy_info *phy = &hw->phy;
+       s32 ret_val = 0;
+
+       /* Switch to PHY page 0xFF. */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_PAGE_ADDR, 0x00FF);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_2, 0x214B);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_1, 0x2144);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_2, 0x0C28);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_1, 0x2146);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_2, 0xB233);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_1, 0x214D);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_2, 0xDC0C);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_1, 0x2159);
+       if (ret_val)
+               goto out;
+
+       /* Switch to PHY page 0xFB. */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_PAGE_ADDR, 0x00FB);
+       if (ret_val)
+               goto out;
+
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_CFG_REG_3, 0x0C0D);
+       if (ret_val)
+               goto out;
+
+       /* Switch to PHY page 0x12. */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_PAGE_ADDR, 0x12);
+       if (ret_val)
+               goto out;
+
+       /* Change mode to SGMII-to-Copper */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1512_MODE, 0x8001);
+       if (ret_val)
+               goto out;
+
+       /* Switch to PHY page 1. */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_PAGE_ADDR, 0x1);
+       if (ret_val)
+               goto out;
+
+       /* Change mode to 1000BASE-X/SGMII and autoneg enable */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_FIBER_CTRL, 0x9140);
+       if (ret_val)
+               goto out;
+
+       /* Return the PHY to page 0. */
+       ret_val = phy->ops.write_reg(hw, E1000_M88E1543_PAGE_ADDR, 0);
+       if (ret_val)
+               goto out;
+
+       ret_val = igb_phy_sw_reset(hw);
+       if (ret_val) {
+               hw_dbg("Error committing the PHY changes\n");
+               return ret_val;
+       }
+
+       /* msec_delay(1000); */
+       usleep_range(1000, 2000);
+out:
+       return ret_val;
+}
+
 /**
  * igb_power_up_phy_copper - Restore copper link in case of PHY power down
  * @hw: pointer to the HW structure
index 24d55edbb0e3a8b58290f94e2c34f3708d8c0111..aa1ae61a61d86378273d21f4b072df8e210652c8 100644 (file)
@@ -62,6 +62,7 @@ void igb_power_up_phy_copper(struct e1000_hw *hw);
 void igb_power_down_phy_copper(struct e1000_hw *hw);
 s32  igb_phy_init_script_igp3(struct e1000_hw *hw);
 s32  igb_initialize_M88E1512_phy(struct e1000_hw *hw);
+s32  igb_initialize_M88E1543_phy(struct e1000_hw *hw);
 s32  igb_read_phy_reg_mdic(struct e1000_hw *hw, u32 offset, u16 *data);
 s32  igb_write_phy_reg_mdic(struct e1000_hw *hw, u32 offset, u16 data);
 s32  igb_read_phy_reg_i2c(struct e1000_hw *hw, u32 offset, u16 *data);