ixgbe: Refactor overtemp event handling
[ Upstream commit 6c1b4af8c1b20c70dde01e58381685d6a4a1d2c8 ] Currently ixgbe driver is notified of overheating events via internal IXGBE_ERR_OVERTEMP error code. Change the approach for handle_lasi() to use freshly introduced is_overtemp function parameter which set when such event occurs. Change check_overtemp() to bool and return true if overtemp event occurs. Reviewed-by: Przemek Kitszel <przemyslaw.kitszel@intel.com> Signed-off-by: Jedrzej Jagielski <jedrzej.jagielski@intel.com> Reviewed-by: Jacob Keller <jacob.e.keller@intel.com> Reviewed-by: Simon Horman <horms@kernel.org> Tested-by: Sunitha Mekala <sunithax.d.mekala@intel.com> (A Contingent worker at Intel) Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com> Signed-off-by: Sasha Levin <sashal@kernel.org>
This commit is contained in:
Родитель
52ec65d4d4
Коммит
c7f47912f7
|
@ -2758,7 +2758,6 @@ static void ixgbe_check_overtemp_subtask(struct ixgbe_adapter *adapter)
|
|||
{
|
||||
struct ixgbe_hw *hw = &adapter->hw;
|
||||
u32 eicr = adapter->interrupt_event;
|
||||
s32 rc;
|
||||
|
||||
if (test_bit(__IXGBE_DOWN, &adapter->state))
|
||||
return;
|
||||
|
@ -2792,14 +2791,13 @@ static void ixgbe_check_overtemp_subtask(struct ixgbe_adapter *adapter)
|
|||
}
|
||||
|
||||
/* Check if this is not due to overtemp */
|
||||
if (hw->phy.ops.check_overtemp(hw) != IXGBE_ERR_OVERTEMP)
|
||||
if (!hw->phy.ops.check_overtemp(hw))
|
||||
return;
|
||||
|
||||
break;
|
||||
case IXGBE_DEV_ID_X550EM_A_1G_T:
|
||||
case IXGBE_DEV_ID_X550EM_A_1G_T_L:
|
||||
rc = hw->phy.ops.check_overtemp(hw);
|
||||
if (rc != IXGBE_ERR_OVERTEMP)
|
||||
if (!hw->phy.ops.check_overtemp(hw))
|
||||
return;
|
||||
break;
|
||||
default:
|
||||
|
@ -7845,7 +7843,7 @@ static void ixgbe_service_timer(struct timer_list *t)
|
|||
static void ixgbe_phy_interrupt_subtask(struct ixgbe_adapter *adapter)
|
||||
{
|
||||
struct ixgbe_hw *hw = &adapter->hw;
|
||||
u32 status;
|
||||
bool overtemp;
|
||||
|
||||
if (!(adapter->flags2 & IXGBE_FLAG2_PHY_INTERRUPT))
|
||||
return;
|
||||
|
@ -7855,10 +7853,8 @@ static void ixgbe_phy_interrupt_subtask(struct ixgbe_adapter *adapter)
|
|||
if (!hw->phy.ops.handle_lasi)
|
||||
return;
|
||||
|
||||
status = hw->phy.ops.handle_lasi(&adapter->hw);
|
||||
if (status != IXGBE_ERR_OVERTEMP)
|
||||
return;
|
||||
|
||||
hw->phy.ops.handle_lasi(&adapter->hw, &overtemp);
|
||||
if (overtemp)
|
||||
e_crit(drv, "%s\n", ixgbe_overheat_msg);
|
||||
}
|
||||
|
||||
|
|
|
@ -408,8 +408,7 @@ s32 ixgbe_reset_phy_generic(struct ixgbe_hw *hw)
|
|||
return status;
|
||||
|
||||
/* Don't reset PHY if it's shut down due to overtemp. */
|
||||
if (!hw->phy.reset_if_overtemp &&
|
||||
(IXGBE_ERR_OVERTEMP == hw->phy.ops.check_overtemp(hw)))
|
||||
if (!hw->phy.reset_if_overtemp && hw->phy.ops.check_overtemp(hw))
|
||||
return 0;
|
||||
|
||||
/* Blocked by MNG FW so bail */
|
||||
|
@ -2621,22 +2620,24 @@ static void ixgbe_i2c_bus_clear(struct ixgbe_hw *hw)
|
|||
* @hw: pointer to hardware structure
|
||||
*
|
||||
* Checks if the LASI temp alarm status was triggered due to overtemp
|
||||
*
|
||||
* Return true when an overtemp event detected, otherwise false.
|
||||
**/
|
||||
s32 ixgbe_tn_check_overtemp(struct ixgbe_hw *hw)
|
||||
bool ixgbe_tn_check_overtemp(struct ixgbe_hw *hw)
|
||||
{
|
||||
u16 phy_data = 0;
|
||||
u32 status;
|
||||
|
||||
if (hw->device_id != IXGBE_DEV_ID_82599_T3_LOM)
|
||||
return 0;
|
||||
return false;
|
||||
|
||||
/* Check that the LASI temp alarm status was triggered */
|
||||
hw->phy.ops.read_reg(hw, IXGBE_TN_LASI_STATUS_REG,
|
||||
status = hw->phy.ops.read_reg(hw, IXGBE_TN_LASI_STATUS_REG,
|
||||
MDIO_MMD_PMAPMD, &phy_data);
|
||||
if (status)
|
||||
return false;
|
||||
|
||||
if (!(phy_data & IXGBE_TN_LASI_STATUS_TEMP_ALARM))
|
||||
return 0;
|
||||
|
||||
return IXGBE_ERR_OVERTEMP;
|
||||
return !!(phy_data & IXGBE_TN_LASI_STATUS_TEMP_ALARM);
|
||||
}
|
||||
|
||||
/** ixgbe_set_copper_phy_power - Control power for copper phy
|
||||
|
|
|
@ -155,7 +155,7 @@ s32 ixgbe_identify_sfp_module_generic(struct ixgbe_hw *hw);
|
|||
s32 ixgbe_get_sfp_init_sequence_offsets(struct ixgbe_hw *hw,
|
||||
u16 *list_offset,
|
||||
u16 *data_offset);
|
||||
s32 ixgbe_tn_check_overtemp(struct ixgbe_hw *hw);
|
||||
bool ixgbe_tn_check_overtemp(struct ixgbe_hw *hw);
|
||||
s32 ixgbe_read_i2c_byte_generic(struct ixgbe_hw *hw, u8 byte_offset,
|
||||
u8 dev_addr, u8 *data);
|
||||
s32 ixgbe_read_i2c_byte_generic_unlocked(struct ixgbe_hw *hw, u8 byte_offset,
|
||||
|
|
|
@ -3502,10 +3502,10 @@ struct ixgbe_phy_operations {
|
|||
s32 (*read_i2c_sff8472)(struct ixgbe_hw *, u8 , u8 *);
|
||||
s32 (*read_i2c_eeprom)(struct ixgbe_hw *, u8 , u8 *);
|
||||
s32 (*write_i2c_eeprom)(struct ixgbe_hw *, u8, u8);
|
||||
s32 (*check_overtemp)(struct ixgbe_hw *);
|
||||
bool (*check_overtemp)(struct ixgbe_hw *);
|
||||
s32 (*set_phy_power)(struct ixgbe_hw *, bool on);
|
||||
s32 (*enter_lplu)(struct ixgbe_hw *);
|
||||
s32 (*handle_lasi)(struct ixgbe_hw *hw);
|
||||
s32 (*handle_lasi)(struct ixgbe_hw *hw, bool *);
|
||||
s32 (*read_i2c_byte_unlocked)(struct ixgbe_hw *, u8 offset, u8 addr,
|
||||
u8 *value);
|
||||
s32 (*write_i2c_byte_unlocked)(struct ixgbe_hw *, u8 offset, u8 addr,
|
||||
|
|
|
@ -600,8 +600,10 @@ static s32 ixgbe_setup_fw_link(struct ixgbe_hw *hw)
|
|||
rc = ixgbe_fw_phy_activity(hw, FW_PHY_ACT_SETUP_LINK, &setup);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
if (setup[0] == FW_PHY_ACT_SETUP_LINK_RSP_DOWN)
|
||||
return IXGBE_ERR_OVERTEMP;
|
||||
return -EIO;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -2319,18 +2321,18 @@ static s32 ixgbe_get_link_capabilities_X550em(struct ixgbe_hw *hw,
|
|||
* @hw: pointer to hardware structure
|
||||
* @lsc: pointer to boolean flag which indicates whether external Base T
|
||||
* PHY interrupt is lsc
|
||||
* @is_overtemp: indicate whether an overtemp event encountered
|
||||
*
|
||||
* Determime if external Base T PHY interrupt cause is high temperature
|
||||
* failure alarm or link status change.
|
||||
*
|
||||
* Return IXGBE_ERR_OVERTEMP if interrupt is high temperature
|
||||
* failure alarm, else return PHY access status.
|
||||
**/
|
||||
static s32 ixgbe_get_lasi_ext_t_x550em(struct ixgbe_hw *hw, bool *lsc)
|
||||
static s32 ixgbe_get_lasi_ext_t_x550em(struct ixgbe_hw *hw, bool *lsc,
|
||||
bool *is_overtemp)
|
||||
{
|
||||
u32 status;
|
||||
u16 reg;
|
||||
|
||||
*is_overtemp = false;
|
||||
*lsc = false;
|
||||
|
||||
/* Vendor alarm triggered */
|
||||
|
@ -2362,7 +2364,8 @@ static s32 ixgbe_get_lasi_ext_t_x550em(struct ixgbe_hw *hw, bool *lsc)
|
|||
if (reg & IXGBE_MDIO_GLOBAL_ALM_1_HI_TMP_FAIL) {
|
||||
/* power down the PHY in case the PHY FW didn't already */
|
||||
ixgbe_set_copper_phy_power(hw, false);
|
||||
return IXGBE_ERR_OVERTEMP;
|
||||
*is_overtemp = true;
|
||||
return -EIO;
|
||||
}
|
||||
if (reg & IXGBE_MDIO_GLOBAL_ALM_1_DEV_FAULT) {
|
||||
/* device fault alarm triggered */
|
||||
|
@ -2376,7 +2379,8 @@ static s32 ixgbe_get_lasi_ext_t_x550em(struct ixgbe_hw *hw, bool *lsc)
|
|||
if (reg == IXGBE_MDIO_GLOBAL_FAULT_MSG_HI_TMP) {
|
||||
/* power down the PHY in case the PHY FW didn't */
|
||||
ixgbe_set_copper_phy_power(hw, false);
|
||||
return IXGBE_ERR_OVERTEMP;
|
||||
*is_overtemp = true;
|
||||
return -EIO;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2412,12 +2416,12 @@ static s32 ixgbe_get_lasi_ext_t_x550em(struct ixgbe_hw *hw, bool *lsc)
|
|||
**/
|
||||
static s32 ixgbe_enable_lasi_ext_t_x550em(struct ixgbe_hw *hw)
|
||||
{
|
||||
bool lsc, overtemp;
|
||||
u32 status;
|
||||
u16 reg;
|
||||
bool lsc;
|
||||
|
||||
/* Clear interrupt flags */
|
||||
status = ixgbe_get_lasi_ext_t_x550em(hw, &lsc);
|
||||
status = ixgbe_get_lasi_ext_t_x550em(hw, &lsc, &overtemp);
|
||||
|
||||
/* Enable link status change alarm */
|
||||
|
||||
|
@ -2496,21 +2500,20 @@ static s32 ixgbe_enable_lasi_ext_t_x550em(struct ixgbe_hw *hw)
|
|||
/**
|
||||
* ixgbe_handle_lasi_ext_t_x550em - Handle external Base T PHY interrupt
|
||||
* @hw: pointer to hardware structure
|
||||
* @is_overtemp: indicate whether an overtemp event encountered
|
||||
*
|
||||
* Handle external Base T PHY interrupt. If high temperature
|
||||
* failure alarm then return error, else if link status change
|
||||
* then setup internal/external PHY link
|
||||
*
|
||||
* Return IXGBE_ERR_OVERTEMP if interrupt is high temperature
|
||||
* failure alarm, else return PHY access status.
|
||||
**/
|
||||
static s32 ixgbe_handle_lasi_ext_t_x550em(struct ixgbe_hw *hw)
|
||||
static s32 ixgbe_handle_lasi_ext_t_x550em(struct ixgbe_hw *hw,
|
||||
bool *is_overtemp)
|
||||
{
|
||||
struct ixgbe_phy_info *phy = &hw->phy;
|
||||
bool lsc;
|
||||
u32 status;
|
||||
|
||||
status = ixgbe_get_lasi_ext_t_x550em(hw, &lsc);
|
||||
status = ixgbe_get_lasi_ext_t_x550em(hw, &lsc, is_overtemp);
|
||||
if (status)
|
||||
return status;
|
||||
|
||||
|
@ -3138,21 +3141,23 @@ static s32 ixgbe_reset_phy_fw(struct ixgbe_hw *hw)
|
|||
/**
|
||||
* ixgbe_check_overtemp_fw - Check firmware-controlled PHYs for overtemp
|
||||
* @hw: pointer to hardware structure
|
||||
*
|
||||
* Return true when an overtemp event detected, otherwise false.
|
||||
*/
|
||||
static s32 ixgbe_check_overtemp_fw(struct ixgbe_hw *hw)
|
||||
static bool ixgbe_check_overtemp_fw(struct ixgbe_hw *hw)
|
||||
{
|
||||
u32 store[FW_PHY_ACT_DATA_COUNT] = { 0 };
|
||||
s32 rc;
|
||||
|
||||
rc = ixgbe_fw_phy_activity(hw, FW_PHY_ACT_GET_LINK_INFO, &store);
|
||||
if (rc)
|
||||
return rc;
|
||||
return false;
|
||||
|
||||
if (store[0] & FW_PHY_ACT_GET_LINK_INFO_TEMP) {
|
||||
ixgbe_shutdown_fw_phy(hw);
|
||||
return IXGBE_ERR_OVERTEMP;
|
||||
return true;
|
||||
}
|
||||
return 0;
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
Загрузка…
Ссылка в новой задаче