git: 41a0f7a0a447 - main - e1000: Propagate hardware initialization failures
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sun, 16 Aug 2026 10:20:32 UTC
The branch main has been updated by kbowling:
URL: https://cgit.FreeBSD.org/src/commit/?id=41a0f7a0a447ef2092faadb35f6d4c3f80c088bf
commit 41a0f7a0a447ef2092faadb35f6d4c3f80c088bf
Author: Kevin Bowling <kbowling@FreeBSD.org>
AuthorDate: 2026-08-16 07:55:37 +0000
Commit: Kevin Bowling <kbowling@FreeBSD.org>
CommitDate: 2026-08-16 10:20:17 +0000
e1000: Propagate hardware initialization failures
The reset helper discards reset_hw and init_hw errors. Runtime
initialization then continues programming rings and filters, and iflib
publishes the interface as running even though the controller did not
reach a usable state. Initial attach similarly continues into NVM and
MAC setup after a failed reset.
Return errors from the reset helper. Fail attach when the controller
cannot be reset or initialized, and report runtime failures through
iflib_init_failed() so iflib leaves the interface stopped. Also stop
register accesses and report the error when a stop-path reset fails.
MFC after: 2 weeks
Sponsored by: BBOX.io
---
sys/dev/e1000/if_em.c | 46 ++++++++++++++++++++++++++++++++++------------
1 file changed, 34 insertions(+), 12 deletions(-)
diff --git a/sys/dev/e1000/if_em.c b/sys/dev/e1000/if_em.c
index 1622468bd2a0..6574b2d0e7d7 100644
--- a/sys/dev/e1000/if_em.c
+++ b/sys/dev/e1000/if_em.c
@@ -440,7 +440,7 @@ static bool em_if_needs_restart(if_ctx_t, enum iflib_restart_event);
static void em_identify_hardware(if_ctx_t);
static int em_allocate_pci_resources(if_ctx_t);
static void em_free_pci_resources(if_ctx_t);
-static void em_reset(if_ctx_t);
+static int em_reset(if_ctx_t);
static int em_setup_interface(if_ctx_t);
static int em_setup_msix(if_ctx_t);
@@ -1571,6 +1571,10 @@ em_if_attach_pre(if_ctx_t ctx)
error == E1000_SUCCESS);
if (error != E1000_SUCCESS)
igbv_log_reset_failure(sc, error, true);
+ } else if (error != E1000_SUCCESS) {
+ device_printf(dev, "Hardware reset failed: %d\n", error);
+ error = EIO;
+ goto err_late;
}
/* Make sure a PF has a good EEPROM before we read from it. */
@@ -1656,10 +1660,12 @@ em_if_attach_post(if_ctx_t ctx)
goto err_late;
}
- if (sc->vf_ifp)
+ if (sc->vf_ifp) {
(void)igbv_reset(ctx);
- else
- em_reset(ctx);
+ } else if (em_reset(ctx) != E1000_SUCCESS) {
+ error = EIO;
+ goto err_late;
+ }
/* Initialize statistics */
if (sc->vf_ifp)
@@ -1870,8 +1876,9 @@ em_if_init(if_ctx_t ctx)
if (sc->vf_ifp) {
(void)igbv_reset(ctx);
em_rebase_vf_stats(sc);
- } else {
- em_reset(ctx);
+ } else if (em_reset(ctx) != E1000_SUCCESS) {
+ iflib_init_failed(ctx);
+ return;
}
if (sc->vf_ifp && !sc->vf_queues_sanitized) {
/*
@@ -3461,6 +3468,7 @@ static void
em_if_stop(if_ctx_t ctx)
{
struct e1000_softc *sc = iflib_get_softc(ctx);
+ s32 error;
INIT_DEBUGOUT("em_if_stop: begin");
@@ -3478,7 +3486,12 @@ em_if_stop(if_ctx_t ctx)
(atomic_load_acq_32(&sc->vf_mbx_ready) != 0 &&
(if_getflags(iflib_get_ifp(ctx)) & IFF_UP) == 0)) {
em_prepare_fatal_error_reset(sc);
- e1000_reset_hw(&sc->hw);
+ error = e1000_reset_hw(&sc->hw);
+ if (!sc->vf_ifp && error != E1000_SUCCESS) {
+ device_printf(sc->dev, "Hardware reset failed while "
+ "stopping: %d\n", error);
+ return;
+ }
}
if (sc->vf_ifp)
atomic_store_rel_32(&sc->vf_mbx_ready, 0);
@@ -4225,7 +4238,7 @@ em_flush_desc_rings(struct e1000_softc *sc)
* sc structure.
*
**********************************************************************/
-static void
+static int
em_reset(if_ctx_t ctx)
{
device_t dev = iflib_get_dev(ctx);
@@ -4234,6 +4247,7 @@ em_reset(if_ctx_t ctx)
struct e1000_hw *hw = &sc->hw;
u32 rx_buffer_size;
u32 pba;
+ s32 error;
INIT_DEBUGOUT("em_reset: begin");
KASSERT(!sc->vf_ifp, ("%s called for a VF", __func__));
@@ -4463,7 +4477,11 @@ em_reset(if_ctx_t ctx)
/* Issue a global reset */
em_prepare_fatal_error_reset(sc);
- e1000_reset_hw(hw);
+ error = e1000_reset_hw(hw);
+ if (error != E1000_SUCCESS) {
+ device_printf(dev, "Hardware reset failed: %d\n", error);
+ return (error);
+ }
if (hw->mac.type >= igb_mac_min) {
E1000_WRITE_REG(hw, E1000_WUC, 0);
} else {
@@ -4476,9 +4494,11 @@ em_reset(if_ctx_t ctx)
sc->flags &= ~IGB_MEDIA_RESET;
}
/* and a re-init */
- if (e1000_init_hw(hw) < 0) {
- device_printf(dev, "Hardware Initialization Failed\n");
- return;
+ error = e1000_init_hw(hw);
+ if (error != E1000_SUCCESS) {
+ device_printf(dev, "Hardware initialization failed: %d\n",
+ error);
+ return (error);
}
em_configure_82576_memory_errors(sc);
em_finish_fatal_error_reset(sc);
@@ -4491,6 +4511,8 @@ em_reset(if_ctx_t ctx)
E1000_WRITE_REG(hw, E1000_VET, ETHERTYPE_VLAN);
e1000_get_phy_info(hw);
e1000_check_for_link(hw);
+
+ return (E1000_SUCCESS);
}
/*