nixos/initrd-network: flush interfaces before stage 2
Depending on the network management backend being used, if the interface configuration in stage 1 is not cleared, there might still be some old addresses or routes from stage 1 present in stage 2 after network configuration has finished.
This commit is contained in:
parent
44e289f93b
commit
ea7d02406b
|
@ -6,7 +6,11 @@ let
|
||||||
|
|
||||||
cfg = config.boot.initrd.network;
|
cfg = config.boot.initrd.network;
|
||||||
|
|
||||||
dhcpinterfaces = lib.attrNames (lib.filterAttrs (iface: v: v.useDHCP == true) (config.networking.interfaces or {}));
|
dhcpInterfaces = lib.attrNames (lib.filterAttrs (iface: v: v.useDHCP == true) (config.networking.interfaces or {}));
|
||||||
|
doDhcp = config.networking.useDHCP || dhcpInterfaces != [];
|
||||||
|
dhcpIfShellExpr = if config.networking.useDHCP
|
||||||
|
then "$(ls /sys/class/net/ | grep -v ^lo$)"
|
||||||
|
else lib.concatMapStringsSep " " lib.escapeShellArg dhcpInterfaces;
|
||||||
|
|
||||||
udhcpcScript = pkgs.writeScript "udhcp-script"
|
udhcpcScript = pkgs.writeScript "udhcp-script"
|
||||||
''
|
''
|
||||||
|
@ -62,6 +66,16 @@ in
|
||||||
'';
|
'';
|
||||||
};
|
};
|
||||||
|
|
||||||
|
boot.initrd.network.flushBeforeStage2 = mkOption {
|
||||||
|
type = types.bool;
|
||||||
|
default = true;
|
||||||
|
description = ''
|
||||||
|
Whether to clear the configuration of the interfaces that were set up in
|
||||||
|
the initrd right before stage 2 takes over. Stage 2 will do the regular network
|
||||||
|
configuration based on the NixOS networking options.
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
|
||||||
boot.initrd.network.udhcpc.extraArgs = mkOption {
|
boot.initrd.network.udhcpc.extraArgs = mkOption {
|
||||||
default = [];
|
default = [];
|
||||||
type = types.listOf types.str;
|
type = types.listOf types.str;
|
||||||
|
@ -95,31 +109,29 @@ in
|
||||||
boot.initrd.preLVMCommands = mkBefore (
|
boot.initrd.preLVMCommands = mkBefore (
|
||||||
# Search for interface definitions in command line.
|
# Search for interface definitions in command line.
|
||||||
''
|
''
|
||||||
|
ifaces=""
|
||||||
for o in $(cat /proc/cmdline); do
|
for o in $(cat /proc/cmdline); do
|
||||||
case $o in
|
case $o in
|
||||||
ip=*)
|
ip=*)
|
||||||
ipconfig $o && hasNetwork=1
|
ipconfig $o && hasNetwork=1 \
|
||||||
|
&& ifaces="$ifaces $(echo $o | cut -d: -f6)"
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
done
|
done
|
||||||
''
|
''
|
||||||
|
|
||||||
# Otherwise, use DHCP.
|
# Otherwise, use DHCP.
|
||||||
+ optionalString (config.networking.useDHCP || dhcpinterfaces != []) ''
|
+ optionalString doDhcp ''
|
||||||
if [ -z "$hasNetwork" ]; then
|
if [ -z "$hasNetwork" ]; then
|
||||||
|
|
||||||
# Bring up all interfaces.
|
# Bring up all interfaces.
|
||||||
for iface in $(ls /sys/class/net/); do
|
for iface in ${dhcpIfShellExpr}; do
|
||||||
echo "bringing up network interface $iface..."
|
echo "bringing up network interface $iface..."
|
||||||
ip link set "$iface" up
|
ip link set "$iface" up && ifaces="$ifaces $iface"
|
||||||
done
|
done
|
||||||
|
|
||||||
# Acquire DHCP leases.
|
# Acquire DHCP leases.
|
||||||
for iface in ${ if config.networking.useDHCP then
|
for iface in ${dhcpIfShellExpr}; do
|
||||||
"$(ls /sys/class/net/ | grep -v ^lo$)"
|
|
||||||
else
|
|
||||||
lib.concatMapStringsSep " " lib.escapeShellArg dhcpinterfaces
|
|
||||||
}; do
|
|
||||||
echo "acquiring IP address via DHCP on $iface..."
|
echo "acquiring IP address via DHCP on $iface..."
|
||||||
udhcpc --quit --now -i $iface -O staticroutes --script ${udhcpcScript} ${udhcpcArgs} && hasNetwork=1
|
udhcpc --quit --now -i $iface -O staticroutes --script ${udhcpcScript} ${udhcpcArgs} && hasNetwork=1
|
||||||
done
|
done
|
||||||
|
@ -133,6 +145,13 @@ in
|
||||||
fi
|
fi
|
||||||
'');
|
'');
|
||||||
|
|
||||||
|
boot.initrd.postMountCommands = mkIf cfg.flushBeforeStage2 ''
|
||||||
|
for iface in $ifaces; do
|
||||||
|
ip address flush "$iface"
|
||||||
|
ip link down "$iface"
|
||||||
|
done
|
||||||
|
'';
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import ./make-test-python.nix ({ pkgs, ...} : {
|
import ./make-test-python.nix ({ pkgs, lib, ...} : {
|
||||||
name = "initrd-network";
|
name = "initrd-network";
|
||||||
|
|
||||||
meta.maintainers = [ pkgs.stdenv.lib.maintainers.eelco ];
|
meta.maintainers = [ pkgs.stdenv.lib.maintainers.eelco ];
|
||||||
|
@ -8,15 +8,26 @@ import ./make-test-python.nix ({ pkgs, ...} : {
|
||||||
boot.initrd.network.enable = true;
|
boot.initrd.network.enable = true;
|
||||||
boot.initrd.network.postCommands =
|
boot.initrd.network.postCommands =
|
||||||
''
|
''
|
||||||
|
ip addr show
|
||||||
|
ip route show
|
||||||
ip addr | grep 10.0.2.15 || exit 1
|
ip addr | grep 10.0.2.15 || exit 1
|
||||||
ping -c1 10.0.2.2 || exit 1
|
ping -c1 10.0.2.2 || exit 1
|
||||||
'';
|
'';
|
||||||
|
# Check if cleanup was done correctly
|
||||||
|
boot.initrd.postMountCommands = lib.mkAfter
|
||||||
|
''
|
||||||
|
ip addr show
|
||||||
|
ip route show
|
||||||
|
ip addr | grep 10.0.2.15 && exit 1
|
||||||
|
ping -c1 10.0.2.2 && exit 1
|
||||||
|
'';
|
||||||
};
|
};
|
||||||
|
|
||||||
testScript =
|
testScript =
|
||||||
''
|
''
|
||||||
start_all()
|
start_all()
|
||||||
machine.wait_for_unit("multi-user.target")
|
machine.wait_for_unit("multi-user.target")
|
||||||
machine.succeed("ip link >&2")
|
machine.succeed("ip addr show >&2")
|
||||||
|
machine.succeed("ip route show >&2")
|
||||||
'';
|
'';
|
||||||
})
|
})
|
||||||
|
|
Loading…
Reference in New Issue