git: 198908895f18 - stable/14 - e1000: restrict conventional PCI DMA to 32 bits
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sat, 08 Aug 2026 00:43:56 UTC
The branch stable/14 has been updated by kbowling:
URL: https://cgit.FreeBSD.org/src/commit/?id=198908895f18c81d4e645199b5992d6e65922c2f
commit 198908895f18c81d4e645199b5992d6e65922c2f
Author: Kevin Bowling <kbowling@FreeBSD.org>
AuthorDate: 2026-07-31 07:02:22 +0000
Commit: Kevin Bowling <kbowling@FreeBSD.org>
CommitDate: 2026-08-08 00:39:45 +0000
e1000: restrict conventional PCI DMA to 32 bits
Some conventional PCI e1000 configurations hang when given DMA
addresses above 4 GB, particularly on systems using AMD
HyperTransport-to-PCI bridges. Linux has restricted e1000 to DMA32 in
PCI mode since 2011 for the same failure class in commit
e508be174ad36b0cf9b324cd04978c2b13c21502.
Set iflib's DMA width after determining the negotiated bus type. This
covers descriptor and packet-buffer mappings while preserving 64-bit
DMA for PCI-X and PCIe devices and providing a conditional tunable.
PR: 297064
Reported by: Alexander Leidinger <netchild@FreeBSD.org>
Tested by: Alexander Leidinger <netchild@FreeBSD.org>
(cherry picked from commit 41759495769dff87cd4ebbb257d4054128ea5b42)
---
sys/dev/e1000/if_em.c | 21 +++++++++++++++++++++
sys/dev/e1000/if_em.h | 1 +
2 files changed, 22 insertions(+)
diff --git a/sys/dev/e1000/if_em.c b/sys/dev/e1000/if_em.c
index 98c2a5c640a7..867f5cc0cd69 100644
--- a/sys/dev/e1000/if_em.c
+++ b/sys/dev/e1000/if_em.c
@@ -1224,6 +1224,27 @@ em_if_attach_pre(if_ctx_t ctx)
em_setup_msix(ctx);
e1000_get_bus_info(hw);
+ /*
+ * Some conventional PCI systems hang when e1000 devices use
+ * DMA addresses above 4 GB. Keep PCI-mode DMA below that boundary
+ * by default; PCI-X and PCIe retain 64-bit DMA.
+ */
+ if (hw->bus.type == e1000_bus_type_pci) {
+ SYSCTL_ADD_BOOL(ctx_list, child, OID_AUTO, "allow_64bit_dma",
+ CTLFLAG_RDTUN, &sc->allow_64bit_dma, 0,
+ "Allow 64-bit DMA in conventional PCI mode");
+ if (sc->allow_64bit_dma)
+ device_printf(dev, "64-bit DMA in conventional PCI mode. "
+ "Some chipsets are unstable.\n");
+ else {
+ scctx->isc_dma_width = 32;
+ device_printf(dev, "32-bit DMA in conventional PCI mode. "
+ "Set dev.%s.%d.allow_64bit_dma=1 at boot to enable "
+ "64-bit DMA if the chipset is stable with it.\n",
+ device_get_name(dev), device_get_unit(dev));
+ }
+ }
+
/* Set up some sysctls for the tunable interrupt delays */
if (hw->mac.type < igb_mac_min) {
em_add_int_delay_sysctl(sc, "rx_int_delay",
diff --git a/sys/dev/e1000/if_em.h b/sys/dev/e1000/if_em.h
index 16da6684c30d..272bb5a7ba3f 100644
--- a/sys/dev/e1000/if_em.h
+++ b/sys/dev/e1000/if_em.h
@@ -543,6 +543,7 @@ struct e1000_softc {
int if_flags;
int em_insert_vlan_header;
u32 ims;
+ bool allow_64bit_dma;
bool in_detach;
u32 flags;