From nobody Sat Aug 8 00:43:58 2026 X-Original-To: dev-commits-src-branches@mlmmj.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mlmmj.nyi.freebsd.org (Postfix) with ESMTP id 4hH2MM4Vjvz6mZDT for ; Sat, 08 Aug 2026 00:43:59 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "YR1" (not verified)) by mx1.freebsd.org (Postfix) with ESMTPS id 4hH2MM1B81z3wSw for ; Sat, 08 Aug 2026 00:43:59 +0000 (UTC) (envelope-from git@FreeBSD.org) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1786149839; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=WHP9l/5jU6VB22GNw9i3IKe5/yDS9bkFBqkZFZYTry8=; b=uW5dzX7CUfVDWcjB5CTJN2Cu4DmhV7yuzy5W2zBcxMkPT5/HFLpH/5Sa6uWHWpNCY3/Vp9 JKRaS+pj185I50xRjWoXz548X+GZV68dsLS35IjrgwkPX3HveAfYOetO3TH+ZBec6UXep7 y/CAKU+lBcERsVfB6GSYnNzaXA5AVRsM7FYZwIA2ev1UuBR8i1eE6izq6IlPuEUCKSBE5P Fi1Dc7/88ys8OxTiwe2p26jdtoVvQszh15ZqUCvgVryWxwbZBoQl9At/8V+mWHvNf6w3RT y2eigr/P+3Gy6XZN0CtxSP+mFMN+hZBpF0MdTvQ4fcw8PIFOjYwL5rPkOIjFzw== ARC-Seal: i=1; s=dkim; d=freebsd.org; t=1786149839; a=rsa-sha256; cv=none; b=rCWynbAyqrFWgrSL9SfiJGqm5TD5RrTOTqQrfiTrgxb9j+Vbr1SK53RdhkYP2nDRGtm8mr 1gF8fcl97YozohiMMCteEyZoiULnkpy6RgHEgUEmK+/+kViMJjcBVxvtE96z3SCFhC+uG+ 5RX57DbSjjRNQEG6woyhRMAfzxcmAl9jRGzs1RPBXdlBCdRlffLgrqSKiKovzD0fsyOynL plYSPQ9tO2q9kUOGKbGv9FWt8oyTmq+tIWxfopZKxdorpe5D4PUuX9nj846Fx//NPml2Kg +aBUwhtSfCQCphfB44vQpIq0zDoOuLlBnt8ddtelY5aOaftIJErUyq38z5utgg== ARC-Authentication-Results: i=1; mx1.freebsd.org; none ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1786149839; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=WHP9l/5jU6VB22GNw9i3IKe5/yDS9bkFBqkZFZYTry8=; b=oZqS4Hzu0ex2ShRTMeKJdcmLGcr+9ENcSYvnBCaEQ/Gu2mvB4+KR9OJ1B/vUiJAfCAAvTj 9GSe6h13GOg0Yp0+0VOojFsRhmSjMW5rgiG0BHDPPlto6BDREDWx5MCuNHzTrAnLemMNap jsy0uzQgKeqiMfD1EvwkFyXL2et6V/qMJYoJ3lvMf7nvgdvjtC7gil/aBeRUnpgBwIIDb1 qG44CdTxfP702qUMjwwqqG8nUZWdau2rBsSHFCe6yFRyiWafQHW19SYzjylj6LQqhNwZ3F iShosQaJ+xxz30jg/FHyRY8kq4gcFqIC2KO+EHonAsDMtdTYIh702VxknUCjww== Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) by mxrelay.nyi.freebsd.org (Postfix) with ESMTP id 4hH2ML738QzlM for ; Sat, 08 Aug 2026 00:43:58 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from git (uid 1279) (envelope-from git@FreeBSD.org) id 3eb58 by gitrepo.freebsd.org (DragonFly Mail Agent v0.13+ on gitrepo.freebsd.org); Sat, 08 Aug 2026 00:43:58 +0000 To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-branches@FreeBSD.org Cc: Michael Adler From: Kevin Bowling Subject: git: c1a574ef9a35 - stable/14 - igc: Disable ASPM L1.2 on I226 to prevent RX stalls List-Id: Commits to the stable branches of the FreeBSD src repository List-Archive: https://lists.freebsd.org/archives/dev-commits-src-branches List-Help: List-Post: List-Subscribe: List-Unsubscribe: X-BeenThere: dev-commits-src-branches@freebsd.org Sender: owner-dev-commits-src-branches@FreeBSD.org List-Id: List-Post: List-Help: List-Subscribe: List-Unsubscribe: List-Owner: Precedence: list MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: kbowling X-Git-Repository: src X-Git-Refname: refs/heads/stable/14 X-Git-Reftype: branch X-Git-Commit: c1a574ef9a35cf277ae3ecc5238586ca7763d4f5 Auto-Submitted: auto-generated Date: Sat, 08 Aug 2026 00:43:58 +0000 Message-Id: <6a767bce.3eb58.174243a7@gitrepo.freebsd.org> The branch stable/14 has been updated by kbowling: URL: https://cgit.FreeBSD.org/src/commit/?id=c1a574ef9a35cf277ae3ecc5238586ca7763d4f5 commit c1a574ef9a35cf277ae3ecc5238586ca7763d4f5 Author: Michael Adler AuthorDate: 2026-07-09 17:02:37 +0000 Commit: Kevin Bowling CommitDate: 2026-08-08 00:40:07 +0000 igc: Disable ASPM L1.2 on I226 to prevent RX stalls I226 parts advertise support for the PCIe L1.2 link substate, but a hardware erratum makes the exit latency from that low-power state longer than the packet buffer can absorb under load. This stalls the inbound packet stream. Disabling ASPM system-wide (BIOS or OS ASPM policy) does not fix it. The L1.2 enable bit must be cleared directly in the device's own PCIe L1 PM extended capability. Add igc_is_device_id_i226() to identify affected parts and igc_disable_broken_aspm_l1_2() to clear the ASPM L1.2 enable bit on attach and after resume, since PCIe config space can be reset across a suspend/resume cycle. Adapted from the Linux igc driver: 0325143b59c6 igc: disable L1.2 PCI-E link substate to avoid performance issue 1468c1f97cf3 igc: fix disabling L1.2 PCI-E link substate on I226 on init Signed-off-by: Michael Adler PR: 279245 Reviewed by: Jim Thompson Pull-Request: https://github.com/freebsd/freebsd-src/pull/2318 (cherry picked from commit 9d30fd353dd3eacb095ce98cb9c91ec015b9af64) --- sys/dev/igc/if_igc.c | 44 ++++++++++++++++++++++++++++++++++++++++++++ sys/dev/igc/igc_base.c | 21 +++++++++++++++++++++ sys/dev/igc/igc_base.h | 1 + 3 files changed, 66 insertions(+) diff --git a/sys/dev/igc/if_igc.c b/sys/dev/igc/if_igc.c index df82d5a4e073..c015bf1f3c52 100644 --- a/sys/dev/igc/if_igc.c +++ b/sys/dev/igc/if_igc.c @@ -115,6 +115,7 @@ static bool igc_if_needs_restart(if_ctx_t, enum iflib_restart_event); static void igc_identify_hardware(if_ctx_t); static int igc_allocate_pci_resources(if_ctx_t); static void igc_free_pci_resources(if_ctx_t); +static void igc_disable_broken_aspm_l1_2(if_ctx_t); static void igc_reset(if_ctx_t); static int igc_setup_interface(if_ctx_t); static int igc_setup_msix(if_ctx_t); @@ -555,6 +556,14 @@ igc_if_attach_pre(if_ctx_t ctx) /* Determine hardware and mac info */ igc_identify_hardware(ctx); + /* + * I226 parts have an erratum where the PCIe ASPM L1.2 exit + * latency can exceed what the packet buffer can absorb under + * load, stalling the inbound packet stream. Disable ASPM L1.2 + * on the device to work around it. + */ + igc_disable_broken_aspm_l1_2(ctx); + scctx->isc_tx_nsegments = IGC_MAX_SCATTER; scctx->isc_nrxqsets_max = scctx->isc_ntxqsets_max = igc_set_num_queues(ctx); @@ -797,6 +806,12 @@ igc_if_suspend(if_ctx_t ctx) static int igc_if_resume(if_ctx_t ctx) { + /* + * PCIe config space, and with it ASPM L1.2, may have been reset + * across the suspend/resume cycle. + */ + igc_disable_broken_aspm_l1_2(ctx); + igc_if_init(ctx); return(0); @@ -1498,6 +1513,35 @@ igc_identify_hardware(if_ctx_t ctx) } } +/********************************************************************* + * + * I226 devices advertise support for the PCIe L1.2 link substate, but + * due to a hardware erratum the exit latency from that low-power state + * can exceed what the packet buffer can tolerate under load, which + * stalls the inbound packet stream. Disabling ASPM L1.2 on the device + * itself (as opposed to disabling ASPM/power management in the BIOS or + * at the OS level) works around the issue. + * + **********************************************************************/ +static void +igc_disable_broken_aspm_l1_2(if_ctx_t ctx) +{ + device_t dev = iflib_get_dev(ctx); + struct igc_softc *sc = iflib_get_softc(ctx); + int cap; + uint32_t ctl1; + + if (!igc_is_device_id_i226(&sc->hw)) + return; + + if (pci_find_extcap(dev, PCIZ_L1PM, &cap) != 0) + return; + + ctl1 = pci_read_config(dev, cap + PCIR_L1PM_CTL1, 4); + ctl1 &= ~PCIM_L1PM_CTL1_ASPM_L1_2; + pci_write_config(dev, cap + PCIR_L1PM_CTL1, ctl1, 4); +} + static int igc_allocate_pci_resources(if_ctx_t ctx) { diff --git a/sys/dev/igc/igc_base.c b/sys/dev/igc/igc_base.c index de48303a9c7c..181fd7025ba3 100644 --- a/sys/dev/igc/igc_base.c +++ b/sys/dev/igc/igc_base.c @@ -184,3 +184,24 @@ void igc_rx_fifo_flush_base(struct igc_hw *hw) IGC_READ_REG(hw, IGC_RNBC); IGC_READ_REG(hw, IGC_MPC); } + +/** + * igc_is_device_id_i226 - Check whether the device is I226 silicon + * @hw: pointer to the HW structure + * + * I225 and I226 share the same mac.type, so this checks the PCI + * device ID directly to distinguish I226 parts, e.g. for erratum + * workarounds that apply only to that silicon. + **/ +bool igc_is_device_id_i226(struct igc_hw *hw) +{ + switch (hw->device_id) { + case IGC_DEV_ID_I226_LM: + case IGC_DEV_ID_I226_V: + case IGC_DEV_ID_I226_K: + case IGC_DEV_ID_I226_IT: + return true; + default: + return false; + } +} diff --git a/sys/dev/igc/igc_base.h b/sys/dev/igc/igc_base.h index c986ecc840e3..91cb602f809d 100644 --- a/sys/dev/igc/igc_base.h +++ b/sys/dev/igc/igc_base.h @@ -13,6 +13,7 @@ void igc_power_down_phy_copper_base(struct igc_hw *hw); extern void igc_rx_fifo_flush_base(struct igc_hw *hw); s32 igc_acquire_phy_base(struct igc_hw *hw); void igc_release_phy_base(struct igc_hw *hw); +bool igc_is_device_id_i226(struct igc_hw *hw); /* Transmit Descriptor - Advanced */ union igc_adv_tx_desc {