Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/dev/pci/ixgbe Add recovery code for unsupported SFP+.
details: https://anonhg.NetBSD.org/src/rev/de0f4d568a24
branches: trunk
changeset: 967812:de0f4d568a24
user: msaitoh <msaitoh%NetBSD.org@localhost>
date: Mon Dec 23 09:36:17 2019 +0000
description:
Add recovery code for unsupported SFP+.
Before this commit:
If an unsuppored SFP module is inserted before booting, the driver attach
failed and there was no way to recover form it without rebooting or
detaching/reattaching drvier (drvctl -d && drvctl -r pciN).
After this commit:
We can automatically recover any time by replacing it with a supported
module.
diffstat:
sys/dev/pci/ixgbe/ixgbe.c | 85 +++++++++++++++++++++++++---------------
sys/dev/pci/ixgbe/ixgbe_82598.c | 7 +-
sys/dev/pci/ixgbe/ixgbe_82599.c | 23 ++++++----
sys/dev/pci/ixgbe/ixgbe_phy.c | 6 ++-
sys/dev/pci/ixgbe/ixgbe_type.h | 3 +-
sys/dev/pci/ixgbe/ixgbe_x550.c | 22 ++++++----
6 files changed, 89 insertions(+), 57 deletions(-)
diffs (truncated from 359 to 300 lines):
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe.c
--- a/sys/dev/pci/ixgbe/ixgbe.c Mon Dec 23 09:19:40 2019 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe.c Mon Dec 23 09:36:17 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe.c,v 1.218 2019/12/23 09:19:40 msaitoh Exp $ */
+/* $NetBSD: ixgbe.c,v 1.219 2019/12/23 09:36:17 msaitoh Exp $ */
/******************************************************************************
@@ -776,6 +776,7 @@
pcireg_t id, subid;
const ixgbe_vendor_info_t *ent;
struct pci_attach_args *pa = aux;
+ bool unsupported_sfp = false;
const char *str;
char buf[256];
@@ -954,8 +955,8 @@
error = IXGBE_SUCCESS;
} else if (error == IXGBE_ERR_SFP_NOT_SUPPORTED) {
aprint_error_dev(dev, "Unsupported SFP+ module detected!\n");
- error = EIO;
- goto err_late;
+ unsupported_sfp = true;
+ error = IXGBE_SUCCESS;
} else if (error) {
aprint_error_dev(dev, "Hardware initialization failed\n");
error = EIO;
@@ -1126,13 +1127,6 @@
"please contact your Intel or hardware representative "
"who provided you with this hardware.\n");
break;
- case IXGBE_ERR_SFP_NOT_SUPPORTED:
- aprint_error_dev(dev, "Unsupported SFP+ Module\n");
- error = EIO;
- goto err_late;
- case IXGBE_ERR_SFP_NOT_PRESENT:
- aprint_error_dev(dev, "No SFP+ Module found\n");
- /* falls thru */
default:
break;
}
@@ -1165,16 +1159,22 @@
oui, model, rev);
}
- /* Enable the optics for 82599 SFP+ fiber */
- ixgbe_enable_tx_laser(hw);
-
/* Enable EEE power saving */
if (adapter->feat_cap & IXGBE_FEATURE_EEE)
hw->mac.ops.setup_eee(hw,
adapter->feat_en & IXGBE_FEATURE_EEE);
/* Enable power to the phy. */
- ixgbe_set_phy_power(hw, TRUE);
+ if (!unsupported_sfp) {
+ /* Enable the optics for 82599 SFP+ fiber */
+ ixgbe_enable_tx_laser(hw);
+
+ /*
+ * XXX Currently, ixgbe_set_phy_power() supports only copper
+ * PHY, so it's not required to test with !unsupported_sfp.
+ */
+ ixgbe_set_phy_power(hw, TRUE);
+ }
/* Initialize statistics */
ixgbe_update_stats_counters(adapter);
@@ -3901,6 +3901,7 @@
u32 txdctl, mhadd;
u32 rxdctl, rxctrl;
u32 ctrl_ext;
+ bool unsupported_sfp = false;
int i, j, err;
/* XXX check IFF_UP and IFF_RUNNING, power-saving state! */
@@ -3908,6 +3909,7 @@
KASSERT(mutex_owned(&adapter->core_mtx));
INIT_DEBUGOUT("ixgbe_init_locked: begin");
+ hw->need_unsupported_sfp_recovery = false;
hw->adapter_stopped = FALSE;
ixgbe_stop_adapter(hw);
callout_stop(&adapter->timer);
@@ -4081,12 +4083,14 @@
*/
if (hw->phy.type == ixgbe_phy_none) {
err = hw->phy.ops.identify(hw);
- if (err == IXGBE_ERR_SFP_NOT_SUPPORTED) {
- device_printf(dev,
- "Unsupported SFP+ module type was detected.\n");
- return;
- }
- }
+ if (err == IXGBE_ERR_SFP_NOT_SUPPORTED)
+ unsupported_sfp = true;
+ } else if (hw->phy.type == ixgbe_phy_sfp_unsupported)
+ unsupported_sfp = true;
+
+ if (unsupported_sfp)
+ device_printf(dev,
+ "Unsupported SFP+ module type was detected.\n");
/* Set moderation on the Link interrupt */
ixgbe_eitr_write(adapter, adapter->vector, IXGBE_LINK_ITR);
@@ -4097,10 +4101,12 @@
adapter->feat_en & IXGBE_FEATURE_EEE);
/* Enable power to the phy. */
- ixgbe_set_phy_power(hw, TRUE);
-
- /* Config/Enable Link */
- ixgbe_config_link(adapter);
+ if (!unsupported_sfp) {
+ ixgbe_set_phy_power(hw, TRUE);
+
+ /* Config/Enable Link */
+ ixgbe_config_link(adapter);
+ }
/* Hardware Packet Buffer & Flow Control setup */
ixgbe_config_delay_values(adapter);
@@ -4636,15 +4642,28 @@
goto out;
}
- if (hw->mac.type == ixgbe_mac_82598EB)
- err = hw->phy.ops.reset(hw);
- else
- err = hw->mac.ops.setup_sfp(hw);
-
- if (err == IXGBE_ERR_SFP_NOT_SUPPORTED) {
- device_printf(dev,
- "Setup failure - unsupported SFP+ module type.\n");
- goto out;
+ if (hw->need_unsupported_sfp_recovery) {
+ device_printf(dev, "Recovering from unsupported SFP\n");
+ /*
+ * We could recover the status by calling setup_sfp(),
+ * setup_link() and some others. It's complex and might not
+ * work correctly on some unknown cases. To avoid such type of
+ * problem, call ixgbe_init_locked(). It's simple and safe
+ * approach.
+ */
+ ixgbe_init_locked(adapter);
+ } else {
+ if (hw->mac.type == ixgbe_mac_82598EB)
+ err = hw->phy.ops.reset(hw);
+ else {
+ err = hw->mac.ops.setup_sfp(hw);
+ hw->phy.sfp_setup_needed = FALSE;
+ }
+ if (err == IXGBE_ERR_SFP_NOT_SUPPORTED) {
+ device_printf(dev,
+ "Setup failure - unsupported SFP+ module type.\n");
+ goto out;
+ }
}
softint_schedule(adapter->msf_si);
out:
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe_82598.c
--- a/sys/dev/pci/ixgbe/ixgbe_82598.c Mon Dec 23 09:19:40 2019 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_82598.c Mon Dec 23 09:36:17 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_82598.c,v 1.12 2018/04/04 08:59:22 msaitoh Exp $ */
+/* $NetBSD: ixgbe_82598.c,v 1.13 2019/12/23 09:36:17 msaitoh Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -866,9 +866,8 @@
/* Init PHY and function pointers, perform SFP setup */
phy_status = hw->phy.ops.init(hw);
- if (phy_status == IXGBE_ERR_SFP_NOT_SUPPORTED)
- goto reset_hw_out;
- if (phy_status == IXGBE_ERR_SFP_NOT_PRESENT)
+ if ((phy_status == IXGBE_ERR_SFP_NOT_SUPPORTED) ||
+ (phy_status == IXGBE_ERR_SFP_NOT_PRESENT))
goto mac_reset_top;
hw->phy.ops.reset(hw);
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe_82599.c
--- a/sys/dev/pci/ixgbe/ixgbe_82599.c Mon Dec 23 09:19:40 2019 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_82599.c Mon Dec 23 09:36:17 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_82599.c,v 1.21 2018/12/06 13:25:02 msaitoh Exp $ */
+/* $NetBSD: ixgbe_82599.c,v 1.22 2019/12/23 09:36:17 msaitoh Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -1041,6 +1041,7 @@
{
ixgbe_link_speed link_speed;
s32 status;
+ s32 phy_status = IXGBE_SUCCESS;
u32 ctrl = 0;
u32 i, autoc, autoc2;
u32 curr_lms;
@@ -1059,28 +1060,29 @@
/* PHY ops must be identified and initialized prior to reset */
/* Identify PHY and related function pointers */
- status = hw->phy.ops.init(hw);
+ phy_status = hw->phy.ops.init(hw);
- if (status == IXGBE_ERR_SFP_NOT_SUPPORTED)
- goto reset_hw_out;
+ if (phy_status == IXGBE_ERR_SFP_NOT_SUPPORTED)
+ goto mac_reset_top;
/* Setup SFP module if there is one present. */
if (hw->phy.sfp_setup_needed) {
- status = hw->mac.ops.setup_sfp(hw);
+ phy_status = hw->mac.ops.setup_sfp(hw);
hw->phy.sfp_setup_needed = FALSE;
}
- if (status == IXGBE_ERR_SFP_NOT_SUPPORTED)
- goto reset_hw_out;
+ if (phy_status == IXGBE_ERR_SFP_NOT_SUPPORTED)
+ goto mac_reset_top;
/* Reset PHY */
if (hw->phy.reset_disable == FALSE && hw->phy.ops.reset != NULL)
hw->phy.ops.reset(hw);
+mac_reset_top:
/* remember AUTOC from before we reset */
curr_lms = IXGBE_READ_REG(hw, IXGBE_AUTOC) & IXGBE_AUTOC_LMS_MASK;
-mac_reset_top:
+mac_reset_retry:
/*
* Issue global reset to the MAC. Needs to be SW reset if link is up.
* If link reset is used when link is up, it might reset the PHY when
@@ -1120,7 +1122,7 @@
*/
if (hw->mac.flags & IXGBE_FLAGS_DOUBLE_RESET_REQUIRED) {
hw->mac.flags &= ~IXGBE_FLAGS_DOUBLE_RESET_REQUIRED;
- goto mac_reset_top;
+ goto mac_reset_retry;
}
/*
@@ -1208,6 +1210,9 @@
&hw->mac.wwpn_prefix);
reset_hw_out:
+ if (phy_status != IXGBE_SUCCESS)
+ status = phy_status;
+
return status;
}
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe_phy.c
--- a/sys/dev/pci/ixgbe/ixgbe_phy.c Mon Dec 23 09:19:40 2019 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_phy.c Mon Dec 23 09:36:17 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_phy.c,v 1.19 2019/12/16 02:50:54 msaitoh Exp $ */
+/* $NetBSD: ixgbe_phy.c,v 1.20 2019/12/23 09:36:18 msaitoh Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -1585,6 +1585,8 @@
}
out:
+ if (hw->phy.type == ixgbe_phy_sfp_unsupported)
+ hw->need_unsupported_sfp_recovery = true;
return status;
err_read_i2c_eeprom:
@@ -1838,6 +1840,8 @@
}
out:
+ if (hw->phy.type == ixgbe_phy_sfp_unsupported)
+ hw->need_unsupported_sfp_recovery = true;
return status;
err_read_i2c_eeprom:
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe_type.h
--- a/sys/dev/pci/ixgbe/ixgbe_type.h Mon Dec 23 09:19:40 2019 +0000
+++ b/sys/dev/pci/ixgbe/ixgbe_type.h Mon Dec 23 09:36:17 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: ixgbe_type.h,v 1.43 2019/09/20 09:28:37 msaitoh Exp $ */
+/* $NetBSD: ixgbe_type.h,v 1.44 2019/12/23 09:36:18 msaitoh Exp $ */
/******************************************************************************
SPDX-License-Identifier: BSD-3-Clause
@@ -4263,6 +4263,7 @@
bool allow_unsupported_sfp;
bool wol_enabled;
bool need_crosstalk_fix;
+ bool need_unsupported_sfp_recovery;
};
#define ixgbe_call_func(hw, func, params, error) \
diff -r 636f1a0dcf0f -r de0f4d568a24 sys/dev/pci/ixgbe/ixgbe_x550.c
Home |
Main Index |
Thread Index |
Old Index