From 444a2c8dd35394d22aba66ce36b87041a5ebbb9c Mon Sep 17 00:00:00 2001 From: chn Date: Tue, 7 Oct 2025 14:35:10 +0800 Subject: [PATCH] modules.system.network: explicit set implementation --- devices/cross/tinc/default.nix | 2 +- devices/nas/default.nix | 2 +- devices/r2s/default.nix | 1 - devices/srv1/node0/default.nix | 2 +- devices/srv1/node1/default.nix | 2 +- devices/srv1/node2/default.nix | 2 +- devices/srv2/node0/default.nix | 2 +- devices/srv2/node1/default.nix | 2 +- devices/vps4/default.nix | 1 - devices/vps6/default.nix | 1 - modules/services/nginx/transparentProxy.nix | 4 +- modules/services/xray/client.nix | 4 +- modules/system/initrd.nix | 2 +- modules/system/network.nix | 262 +++++++++++--------- 14 files changed, 151 insertions(+), 138 deletions(-) diff --git a/devices/cross/tinc/default.nix b/devices/cross/tinc/default.nix index c03ba89b..ab5ce9e4 100644 --- a/devices/cross/tinc/default.nix +++ b/devices/cross/tinc/default.nix @@ -76,7 +76,7 @@ in nixos.system = { sops.secrets."tinc".owner = "tinc-tinc0"; - network = inputs.lib.mkIf (configs.${inputs.config.nixos.model.hostname}.useNetworkd) + network.settings = inputs.lib.mkIf (configs.${inputs.config.nixos.model.hostname}.useNetworkd) { static."tinc0" = { ip = configs.${inputs.config.nixos.model.hostname}.address; mask = 24; }; }; diff --git a/devices/nas/default.nix b/devices/nas/default.nix index 582bbdca..a352eac3 100644 --- a/devices/nas/default.nix +++ b/devices/nas/default.nix @@ -25,7 +25,7 @@ inputs: }; initrd.sshd = {}; nixpkgs.march = "alderlake"; - network = + network.settings = { bridge.nixvirt.interfaces = [ "enp3s0" ]; static.nixvirt = { ip = "192.168.1.2"; mask = 24; gateway = "192.168.1.1"; dns = "192.168.1.1"; }; diff --git a/devices/r2s/default.nix b/devices/r2s/default.nix index dfbb2d2e..4398da05 100644 --- a/devices/r2s/default.nix +++ b/devices/r2s/default.nix @@ -12,7 +12,6 @@ inputs: mount.btrfs."/dev/disk/by-partlabel/r2s-root" = { "/nix" = "/nix"; "/nix/rootfs/current" = "/"; }; swap = [ "/nix/swap/swap" ]; }; - network = {}; # uboot 起始位置 0x8000 字节,这个地方还在分区表内部;除此以外还需要预留一些空间,预留32M足够。 uboot.buildArgs = { diff --git a/devices/srv1/node0/default.nix b/devices/srv1/node0/default.nix index b9040749..b4dfadf0 100644 --- a/devices/srv1/node0/default.nix +++ b/devices/srv1/node0/default.nix @@ -8,7 +8,7 @@ inputs: system = { nixpkgs.march = "cascadelake"; - network = + network.settings = { static = { diff --git a/devices/srv1/node1/default.nix b/devices/srv1/node1/default.nix index efd56872..11939478 100644 --- a/devices/srv1/node1/default.nix +++ b/devices/srv1/node1/default.nix @@ -7,7 +7,7 @@ inputs: system = { nixpkgs.march = "broadwell"; - network = + network.settings = { static.eno2 = { ip = "192.168.178.2"; mask = 24; gateway = "192.168.178.1"; dns = "192.168.178.1"; }; diff --git a/devices/srv1/node2/default.nix b/devices/srv1/node2/default.nix index b8423521..1291614c 100644 --- a/devices/srv1/node2/default.nix +++ b/devices/srv1/node2/default.nix @@ -7,7 +7,7 @@ inputs: system = { nixpkgs.march = "broadwell"; - network = + network.settings = { static = { diff --git a/devices/srv2/node0/default.nix b/devices/srv2/node0/default.nix index 5159b2d0..e6bdecbd 100644 --- a/devices/srv2/node0/default.nix +++ b/devices/srv2/node0/default.nix @@ -8,7 +8,7 @@ inputs: system = { nixpkgs.march = "skylake"; - network = + network.settings = { static.eno2 = { ip = "192.168.178.1"; mask = 24; }; masquerade = [ "eno2" ]; diff --git a/devices/srv2/node1/default.nix b/devices/srv2/node1/default.nix index d7bcbc44..26c4a4e4 100644 --- a/devices/srv2/node1/default.nix +++ b/devices/srv2/node1/default.nix @@ -7,7 +7,7 @@ inputs: system = { nixpkgs.march = "znver3"; - network = + network.settings = { static.enp58s0 = { ip = "192.168.178.2"; mask = 24; gateway = "192.168.178.1"; dns = "192.168.178.1"; }; diff --git a/devices/vps4/default.nix b/devices/vps4/default.nix index fd1d0429..48a530ba 100644 --- a/devices/vps4/default.nix +++ b/devices/vps4/default.nix @@ -21,7 +21,6 @@ inputs: grub.installDevice = "/dev/disk/by-path/pci-0000:00:04.0"; nixpkgs.march = "znver2"; initrd.sshd = {}; - network = {}; }; services = { diff --git a/devices/vps6/default.nix b/devices/vps6/default.nix index 97f270d8..5feb284b 100644 --- a/devices/vps6/default.nix +++ b/devices/vps6/default.nix @@ -21,7 +21,6 @@ inputs: grub.installDevice = "/dev/disk/by-path/pci-0000:00:05.0-scsi-0:0:0:0"; nixpkgs.march = "znver2"; initrd.sshd = {}; - network = {}; }; services = { diff --git a/modules/services/nginx/transparentProxy.nix b/modules/services/nginx/transparentProxy.nix index 119722ca..774968cc 100644 --- a/modules/services/nginx/transparentProxy.nix +++ b/modules/services/nginx/transparentProxy.nix @@ -40,7 +40,7 @@ inputs: ''; systemd = { - services = inputs.lib.mkIf (inputs.config.nixos.system.network == null) + services = inputs.lib.mkIf (inputs.config.nixos.system.network.implementation == "networkmanager") { nginx-proxy = let @@ -70,7 +70,7 @@ inputs: wantedBy= [ "multi-user.target" ]; }; }; - network.networks = inputs.lib.mkIf (inputs.config.nixos.system.network != null) + network.networks = inputs.lib.mkIf (inputs.config.nixos.system.network.implementation == "systemd-networkd") { "10-custom" = { diff --git a/modules/services/xray/client.nix b/modules/services/xray/client.nix index 9d92c16d..787e3f24 100644 --- a/modules/services/xray/client.nix +++ b/modules/services/xray/client.nix @@ -198,7 +198,7 @@ inputs: restartTriggers = [ inputs.config.nixos.system.sops.templates."xray-client.json".file ]; }; } - (inputs.lib.mkIf (inputs.config.nixos.system.network == null) + (inputs.lib.mkIf (inputs.config.nixos.system.network.implementation == "networkmanager") { v2ray-forwarder = { @@ -223,7 +223,7 @@ inputs: }; }) ]; - network.networks = inputs.lib.mkIf (inputs.config.nixos.system.network != null) + network.networks = inputs.lib.mkIf (inputs.config.nixos.system.network.implementation == "systemd-networkd") { "10-custom" = { diff --git a/modules/system/initrd.nix b/modules/system/initrd.nix index 023e44e9..e44794ee 100644 --- a/modules/system/initrd.nix +++ b/modules/system/initrd.nix @@ -46,7 +46,7 @@ inputs: # resolved does not work in initrd, causing network.target to fail services.resolved.enable = false; systemd.network = - let inherit (inputs.config.nixos.system.network) dhcp static bridge; in + let inherit (inputs.config.nixos.system.network.settings) dhcp static bridge; in let networks = inputs.lib.unique ( diff --git a/modules/system/network.nix b/modules/system/network.nix index 77199b2d..e054038c 100644 --- a/modules/system/network.nix +++ b/modules/system/network.nix @@ -1,45 +1,57 @@ inputs: { - options.nixos.system.network = let inherit (inputs.lib) mkOption types; in mkOption + options.nixos.system.network = let inherit (inputs.lib) mkOption types; in { - # null: use network-manager; otherwise use networkd - type = types.nullOr (types.submodule { options = + settings = mkOption { - dhcp = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; - static = mkOption + type = types.nullOr (types.submodule { options = { - type = types.attrsOf (types.submodule { options = + dhcp = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; + static = mkOption { - ip = mkOption { type = types.nonEmptyStr; }; - mask = mkOption { type = types.ints.unsigned; }; - gateway = mkOption { type = types.nullOr types.nonEmptyStr; default = null; }; - dns = mkOption { type = types.nullOr types.nonEmptyStr; default = null; }; - };}); - default = {}; - }; - bridge = mkOption - { - type = types.attrsOf (types.submodule { options = + type = types.attrsOf (types.submodule { options = + { + ip = mkOption { type = types.nonEmptyStr; }; + mask = mkOption { type = types.ints.unsigned; }; + gateway = mkOption { type = types.nullOr types.nonEmptyStr; default = null; }; + dns = mkOption { type = types.nullOr types.nonEmptyStr; default = null; }; + };}); + default = {}; + }; + bridge = mkOption { - interfaces = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; - };}); - default = {}; - }; - wireless = - { - # wpa_passphrase SSID(wifi name) PSK(password) - networks = mkOption { type = types.nullOr (types.listOf types.nonEmptyStr); default = null; }; - fourAddr = mkOption { type = types.bool; default = false; }; - }; - trust = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; - masquerade = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; - };}); - default = null; + type = types.attrsOf (types.submodule { options = + { + interfaces = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; + };}); + default = {}; + }; + wireless = + { + # wpa_passphrase SSID(wifi name) PSK(password) + networks = mkOption { type = types.nullOr (types.listOf types.nonEmptyStr); default = null; }; + fourAddr = mkOption { type = types.bool; default = false; }; + }; + trust = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; + masquerade = mkOption { type = types.listOf types.nonEmptyStr; default = []; }; + };}); + default = null; + }; + implementation = mkOption + { + type = types.enum [ "systemd-networkd" "networkmanager" ]; + default = if inputs.config.nixos.model.type == "desktop" then "networkmanager" else "systemd-networkd"; + }; }; config = let inherit (inputs.config.nixos.system) network; in inputs.lib.mkMerge [ # general config { + assertions = + [{ + assertion = network.implementation == "networkmanager" -> network.settings == null; + message = "only systemd-networkd is supported when network settings is set"; + }]; boot.kernel.sysctl = { "net.core.rmem_max" = 67108864; @@ -65,110 +77,114 @@ inputs: }; networking.nftables = { enable = true; flushRuleset = false; }; } - (inputs.localLib.mkConditional (network == null) + (inputs.lib.mkIf (network.implementation == "networkmanager") + { + networking.networkmanager = { - networking.networkmanager = - { - enable = true; - settings.device.keep-configuration = "no"; - }; - environment.persistence."/nix/persistent".directories = - [{ directory = "/etc/NetworkManager/system-connections"; mode = "0700"; }]; - } + enable = true; + settings.device.keep-configuration = "no"; + }; + environment.persistence."/nix/persistent".directories = + [{ directory = "/etc/NetworkManager/system-connections"; mode = "0700"; }]; + }) + (inputs.lib.mkIf (network.implementation == "systemd-networkd") + { + systemd.network.enable = true; + networking.useNetworkd = true; + # dnsable dns fallback, use provided dns servers or no dns + services.resolved.fallbackDns = []; + }) + (inputs.lib.mkIf (network.implementation == "systemd-networkd" && network.settings != null) + { + systemd.network = { - systemd.network = - { - enable = true; - networks = inputs.lib.mkMerge - [ - (builtins.listToAttrs (builtins.map + networks = inputs.lib.mkMerge + [ + (builtins.listToAttrs (builtins.map + (network: + { + name = "10-${network}"; + value = + { + matchConfig.Name = network; + networkConfig = { DHCP = "yes"; IPv6AcceptRA = true; }; + linkConfig.RequiredForOnline = "routable"; + }; + }) + network.settings.dhcp)) + (builtins.listToAttrs (builtins.map + (network: + { + name = "10-${network.name}"; + value = + { + matchConfig.Name = network.name; + address = [ "${network.value.ip}/${builtins.toString network.value.mask}" ]; + routes = inputs.lib.mkIf (network.value.gateway != null) + [{ Gateway = network.value.gateway; Destination = "0.0.0.0/0"; }]; + linkConfig.RequiredForOnline = "routable"; + dns = inputs.lib.mkIf (network.value.dns != null) [ network.value.dns ]; + }; + }) + (inputs.localLib.attrsToList network.settings.static))) + (builtins.listToAttrs (builtins.map + (network: + { + name = "10-${network.name}"; + value = + { + matchConfig.Name = network.name; + bridgeConfig = {}; + linkConfig.RequiredForOnline = "routable"; + }; + }) + (inputs.localLib.attrsToList network.settings.bridge))) + (builtins.listToAttrs (builtins.concatLists (builtins.map + (bridge: builtins.map (network: { name = "10-${network}"; value = { matchConfig.Name = network; - networkConfig = { DHCP = "yes"; IPv6AcceptRA = true; }; - linkConfig.RequiredForOnline = "routable"; + networkConfig.Bridge = bridge.name; + linkConfig.RequiredForOnline = "enslaved"; }; - }) - network.dhcp)) - (builtins.listToAttrs (builtins.map - (network: - { - name = "10-${network.name}"; - value = - { - matchConfig.Name = network.name; - address = [ "${network.value.ip}/${builtins.toString network.value.mask}" ]; - routes = inputs.lib.mkIf (network.value.gateway != null) - [{ Gateway = network.value.gateway; Destination = "0.0.0.0/0"; }]; - linkConfig.RequiredForOnline = "routable"; - dns = inputs.lib.mkIf (network.value.dns != null) [ network.value.dns ]; - }; - }) - (inputs.localLib.attrsToList network.static))) - (builtins.listToAttrs (builtins.map - (network: - { - name = "10-${network.name}"; - value = - { - matchConfig.Name = network.name; - bridgeConfig = {}; - linkConfig.RequiredForOnline = "routable"; - }; - }) - (inputs.localLib.attrsToList network.bridge))) - (builtins.listToAttrs (builtins.concatLists (builtins.map - (bridge: builtins.map - (network: - { - name = "10-${network}"; - value = - { - matchConfig.Name = network; - networkConfig.Bridge = bridge.name; - linkConfig.RequiredForOnline = "enslaved"; - }; - }) bridge.value.interfaces) - (inputs.localLib.attrsToList network.bridge)))) - (builtins.listToAttrs (builtins.map - (network: { name = "10-${network}"; value.networkConfig.IPMasquerade = "both"; }) - network.masquerade)) - ]; - netdevs = builtins.listToAttrs (builtins.map - (network: { name = "10-${network}"; value.netdevConfig = { Name = network; Kind = "bridge"; }; }) - (builtins.attrNames network.bridge)); - }; - networking = + }) bridge.value.interfaces) + (inputs.localLib.attrsToList network.settings.bridge)))) + (builtins.listToAttrs (builtins.map + (network: { name = "10-${network}"; value.networkConfig.IPMasquerade = "both"; }) + network.settings.masquerade)) + ]; + netdevs = builtins.listToAttrs (builtins.map + (network: { name = "10-${network}"; value.netdevConfig = { Name = network; Kind = "bridge"; }; }) + (builtins.attrNames network.settings.bridge)); + }; + networking = + { + wireless = inputs.lib.mkIf (network.settings.wireless.networks != null) { - useNetworkd = true; - wireless = inputs.lib.mkIf (network.wireless.networks != null) - { - enable = true; - # wpa_passphrase SSID password - networks = builtins.listToAttrs (builtins.map - (network: { name = network; value.pskRaw = "ext:${network}"; }) network.wireless.networks); - secretsFile = inputs.config.nixos.system.sops.templates."wireless.env".path; - }; - firewall.trustedInterfaces = network.trust; + enable = true; + # wpa_passphrase SSID password + networks = builtins.listToAttrs (builtins.map + (network: { name = network; value.pskRaw = "ext:${network}"; }) network.settings.wireless.networks); + secretsFile = inputs.config.nixos.system.sops.templates."wireless.env".path; }; - # dnsable dns fallback, use provided dns servers or no dns - services.resolved.fallbackDns = []; - nixos.system.sops = inputs.lib.mkIf (network.wireless.networks != null) - { - templates."wireless.env".content = builtins.concatStringsSep "\n" (builtins.map - (network: "${network}=${inputs.config.nixos.system.sops.placeholder."wireless/${network}"}") - network.wireless.networks); - secrets = builtins.listToAttrs (builtins.map - (network: inputs.lib.nameValuePair "wireless/${network}" {}) - network.wireless.networks); - }; - services.udev.extraRules = inputs.lib.mkIf (network.wireless.fourAddr) - '' - ACTION=="add", SUBSYSTEM=="net", ENV{INTERFACE}=="wlp*", RUN+="${inputs.pkgs.iw}/bin/iw dev %k set 4addr on" - ''; + firewall.trustedInterfaces = network.settings.trust; + }; + nixos.system.sops = inputs.lib.mkIf (network.settings.wireless.networks != null) + { + templates."wireless.env".content = builtins.concatStringsSep "\n" (builtins.map + (network: "${network}=${inputs.config.nixos.system.sops.placeholder."wireless/${network}"}") + network.settings.wireless.networks); + secrets = builtins.listToAttrs (builtins.map + (network: inputs.lib.nameValuePair "wireless/${network}" {}) + network.settings.wireless.networks); + }; + services.udev.extraRules = inputs.lib.mkIf (network.settings.wireless.fourAddr) + '' + ACTION=="add", SUBSYSTEM=="net", ENV{INTERFACE}=="wlp*", RUN+="${inputs.pkgs.iw}/bin/iw dev %k set 4addr on" + ''; }) ]; }