Network Manager refactor

This commit is contained in:
Audiobuzz
2026-06-17 13:40:28 +00:00
parent 4b0e0135b3
commit 55aa517976
10 changed files with 198 additions and 62 deletions
+20 -2
View File
@@ -107,8 +107,26 @@ info "dot1x-macsec: port authorized, macsec0 up after ${i}s"
# --- 4. address the secure interface; netroot rides on macsec0 --------------
ip link set macsec0 up
# Hand macsec0 to dracut's network stack for DHCP + netroot resolution
ifup macsec0
# DHCP on macsec0 via NetworkManager (NOT the old network-legacy `ifup`): NM owns
# macsec0, so it RENEWS the lease in the running system after switch-root — the
# whole point of the network-manager port. macsec0 was created externally by
# wpa_supplicant; ask NM to manage+activate it with a default DHCP profile. The
# physical NIC stays unmanaged (nm-unmanaged.sh cmdline drop-in), so
# wpa_supplicant keeps EAPOL/MKA on it. -w 0 returns immediately; we poll below.
nmcli device set macsec0 managed yes 2>/dev/null || true
nmcli -w 0 device connect macsec0 2>/dev/null || true
# Wait for the DHCP lease (IPv4 on macsec0) before netroot/NVMe connect.
i=0
while [ "$i" -lt "$TIMEOUT" ]; do
ip -4 addr show macsec0 2>/dev/null | grep -q 'inet ' && break
sleep 1; i=$((i + 1))
done
if [ "$i" -ge "$TIMEOUT" ]; then
warn "dot1x-macsec: no DHCP lease on macsec0 after ${TIMEOUT}s"
exit 1
fi
info "dot1x-macsec: macsec0 addressed via NetworkManager (DHCP)"
# --- 5. derive per-host NVMe identity from the TPM certificate --------------
# Keeps the image fleet-generic: the host NQN is a function of the machine
+14 -2
View File
@@ -11,7 +11,10 @@ check() {
}
depends() {
echo "network-legacy bash"
# network-manager (not network-legacy): NM renews the DHCP lease in the real
# root after switch-root (the legacy one-shot lease was never renewed). The
# secure path drives DHCP on macsec0 via nmcli instead of the old `ifup`.
echo "network-manager bash"
return 0
}
@@ -29,7 +32,9 @@ install() {
# distro's dracut nvmf module populates discovery.conf but never registers
# an initqueue/online autoconnect hook). The nvmf module installs nvme too,
# but list it here so the hook's dependency is explicit and load-order-safe.
inst_multiple wpa_supplicant wpa_cli tpm2_nvread openssl ip setsid \
# nmcli: the secure path brings macsec0 up via NetworkManager (DHCP+renewal)
# instead of the old network-legacy `ifup`.
inst_multiple wpa_supplicant wpa_cli tpm2_nvread openssl ip setsid nmcli \
grep sed cut tr sha256sum sleep mkdir nvme
# TSS libraries that tpm2_nvread dlopens
@@ -39,6 +44,13 @@ install() {
inst_simple /etc/dot1x/wpa_supplicant-dot1x.conf /etc/dot1x/wpa_supplicant-dot1x.conf
inst_simple /etc/dot1x/radius-ca.pem /etc/dot1x/radius-ca.pem
# cmdline-stage hook (runs BEFORE NetworkManager starts): in secure mode it
# drops /run/NetworkManager/conf.d/10-dot1x-unmanaged.conf so NM never grabs
# the physical EAPOL NIC (wpa_supplicant owns it). No-op in rd.dot1x=0 test
# mode, so NM manages+renews the boot NIC. Replaces the old static
# 99-dot1x-unmanaged.conf, which couldn't be mode-aware.
inst_hook cmdline 10 "$moddir/nm-unmanaged.sh"
# Hook: runs from the initqueue once the NIC exists, before netroot
inst_hook initqueue/settled 30 "$moddir/dot1x-macsec-up.sh"
@@ -0,0 +1,37 @@
#!/bin/bash
# nm-unmanaged.sh — dracut cmdline-stage hook (runs BEFORE NetworkManager starts).
#
# In the SECURE path (802.1X/MACsec), wpa_supplicant owns the physical NIC: it
# runs EAPOL and the MACsec key agreement (MKA) on it, and that link carries the
# root filesystem. NetworkManager must NOT touch that NIC — a competing NM
# supplicant would drop MKA and kill netroot. So drop an NM config that marks the
# physical NIC unmanaged. IP is carried by macsec0, which is left MANAGED so NM
# does DHCP *and renews the lease* on it.
#
# In the TEST path (rd.dot1x=0) there is no macsec0; IP rides on the physical NIC
# directly and we WANT NM to manage+renew it — so write nothing.
#
# Why /run (not /etc) and why the cmdline stage: /run/NetworkManager/conf.d is
# read by NM and the tmpfs survives switch-root, so the same rule applies in both
# the initramfs and the real root. Writing here at the cmdline stage guarantees
# the file exists before NM is started, so NM never transiently manages the EAPOL
# NIC. This replaces the old static /etc/.../99-dot1x-unmanaged.conf, which could
# not be mode-aware (it wrongly unmanaged en* in test mode too, blocking renewal).
type getarg >/dev/null 2>&1 || . /lib/dracut-lib.sh
# Test mode: leave the boot NIC managed so NM renews its lease.
[ "$(getarg rd.dot1x=)" = "0" ] && return 0
_dir=/run/NetworkManager/conf.d
_conf="$_dir/10-dot1x-unmanaged.conf"
[ -e "$_conf" ] && return 0 # idempotent (cmdline hooks may re-run)
mkdir -p "$_dir"
# interface-name:en* matches the predictable physical NIC names (eno/ens/enp);
# macsec0 is deliberately NOT listed, so NM manages it for DHCP/renewal.
{
echo "[keyfile]"
echo "unmanaged-devices=interface-name:en*"
} > "$_conf"
info "dot1x-macsec: NM unmanaged drop-in written ($_conf) — physical NIC reserved for wpa_supplicant"