From 2c670b5bd794ef93c81bf8797b7d6393c8453fc6 Mon Sep 17 00:00:00 2001 From: Carolyn Wyborny Date: Tue, 24 May 2011 06:52:51 +0000 Subject: [PATCH] igb: Add support of SerDes Forced mode for certain hardware This patch changes the serdes link code to support a forced mode for some hardware, based on bit set in EEPROM. Signed-off-by: Carolyn Wyborny Tested-by: Jeff Pieper Signed-off-by: Jeff Kirsher --- drivers/net/igb/e1000_82575.c | 19 +++++++++++++++++-- drivers/net/igb/e1000_82575.h | 2 ++ drivers/net/igb/e1000_defines.h | 5 +++-- 3 files changed, 22 insertions(+), 4 deletions(-) diff --git a/drivers/net/igb/e1000_82575.c b/drivers/net/igb/e1000_82575.c index 7b7e1571fa5e..c0857bdfb03a 100644 --- a/drivers/net/igb/e1000_82575.c +++ b/drivers/net/igb/e1000_82575.c @@ -1156,10 +1156,13 @@ static s32 igb_setup_serdes_link_82575(struct e1000_hw *hw) { u32 ctrl_ext, ctrl_reg, reg; bool pcs_autoneg; + s32 ret_val = E1000_SUCCESS; + u16 data; if ((hw->phy.media_type != e1000_media_type_internal_serdes) && !igb_sgmii_active_82575(hw)) - return 0; + return ret_val; + /* * On the 82575, SerDes loopback mode persists until it is @@ -1203,6 +1206,18 @@ static s32 igb_setup_serdes_link_82575(struct e1000_hw *hw) /* disable PCS autoneg and support parallel detect only */ pcs_autoneg = false; default: + if (hw->mac.type == e1000_82575 || + hw->mac.type == e1000_82576) { + ret_val = hw->nvm.ops.read(hw, NVM_COMPAT, 1, &data); + if (ret_val) { + printk(KERN_DEBUG "NVM Read Error\n\n"); + return ret_val; + } + + if (data & E1000_EEPROM_PCS_AUTONEG_DISABLE_BIT) + pcs_autoneg = false; + } + /* * non-SGMII modes only supports a speed of 1000/Full for the * link so it is best to just force the MAC and let the pcs @@ -1250,7 +1265,7 @@ static s32 igb_setup_serdes_link_82575(struct e1000_hw *hw) if (!igb_sgmii_active_82575(hw)) igb_force_mac_fc(hw); - return 0; + return ret_val; } /** diff --git a/drivers/net/igb/e1000_82575.h b/drivers/net/igb/e1000_82575.h index fd28d62470e1..786e110011a3 100644 --- a/drivers/net/igb/e1000_82575.h +++ b/drivers/net/igb/e1000_82575.h @@ -243,6 +243,8 @@ struct e1000_adv_tx_context_desc { #define E1000_DTXCTL_MDP_EN 0x0020 #define E1000_DTXCTL_SPOOF_INT 0x0040 +#define E1000_EEPROM_PCS_AUTONEG_DISABLE_BIT (1 << 14) + #define ALL_QUEUES 0xFFFF /* RX packet buffer size defines */ diff --git a/drivers/net/igb/e1000_defines.h b/drivers/net/igb/e1000_defines.h index 446eb5cb25e1..2cd4082c86ca 100644 --- a/drivers/net/igb/e1000_defines.h +++ b/drivers/net/igb/e1000_defines.h @@ -437,6 +437,7 @@ #define E1000_RAH_POOL_1 0x00040000 /* Error Codes */ +#define E1000_SUCCESS 0 #define E1000_ERR_NVM 1 #define E1000_ERR_PHY 2 #define E1000_ERR_CONFIG 3 @@ -587,8 +588,8 @@ #define E1000_NVM_POLL_READ 0 /* Flag for polling for read complete */ /* NVM Word Offsets */ -#define NVM_ID_LED_SETTINGS 0x0004 -/* For SERDES output amplitude adjustment. */ +#define NVM_COMPAT 0x0003 +#define NVM_ID_LED_SETTINGS 0x0004 /* SERDES output amplitude */ #define NVM_INIT_CONTROL2_REG 0x000F #define NVM_INIT_CONTROL3_PORT_B 0x0014 #define NVM_INIT_CONTROL3_PORT_A 0x0024