fixup! systemd-creds: move to creds-{setup,encrypt,decrypt}.sh
[julm/julm-nix.git] / nixos / profiles / wireguard / wg-intra.nix
index 2cbd61f3c1c9c475ff2084bf7f0367d79fc39488..36c961052b9e25fbb11d66a2c4470631d426b9c0 100644 (file)
@@ -1,16 +1,19 @@
-{ pkgs, lib, config, hostName, private, ... }:
+{ inputs, pkgs, lib, config, hostName, ... }:
 let
-  iface = "wg-intra";
+  wgIface = "wg-intra";
   peers = import wg-intra/peers.nix;
-  wg = config.networking.wireguard.interfaces.${iface};
+  wg = config.networking.wireguard.interfaces.${wgIface};
 in
 {
-options.networking.wireguard.${iface}.peers =
+# Each peer select the other peers allowed to connect to it
+options.networking.wireguard.${wgIface}.peers =
   lib.genAttrs (lib.attrNames peers) (peerName: {
     enable = lib.mkEnableOption "this peer";
   });
 config = {
-networking.wireguard.interfaces.${iface} = lib.recursiveUpdate
+systemd.services."wireguard-${wgIface}".serviceConfig.LoadCredentialEncrypted =
+  "privateKey:" + inputs.self.outPath + "/hosts/${hostName}/wireguard/${wgIface}/privateKey.cred";
+networking.wireguard.interfaces.${wgIface} = lib.recursiveUpdate
   (removeAttrs peers.${hostName} ["ipv4" "persistentKeepalive" "peer"])
   {
     peers =
@@ -24,31 +27,90 @@ networking.wireguard.interfaces.${iface} = lib.recursiveUpdate
           }
           peer.peer)
         (removeAttrs
-          (lib.filterAttrs (peerName: _: config.networking.wireguard.${iface}.peers.${peerName}.enable) peers)
+          (lib.filterAttrs (peerName: _: config.networking.wireguard.${wgIface}.peers.${peerName}.enable) peers)
           [hostName]);
-    privateKeyFile = lib.mkDefault "${private}/${hostName}/wireguard/${iface}/privateKey";
+    privateKeyFile = "$CREDENTIALS_DIRECTORY/privateKey";
 
     # Set the MTU to a minimum
     # (IPv4 requires at least 68 but it's 1280 for IPv6).
     # This prevents connections to stall on huge packets,
     # or delaying their initializing due to TCP PMTU probing.
     postSetup = ''
-      ip link set dev ${iface} mtu 1280
+      ip link set dev ${wgIface} mtu 1280
     '';
   };
 networking.hosts = lib.mkMerge [
   (lib.mapAttrs' (hostName: host:
     lib.nameValuePair host.ipv4 [ "${hostName}.wg" ]) peers)
-  { "${peers.losurdo.ipv4}" = [
-    "nix-extracache.losurdo.wg"
-    "nix-localcache.losurdo.wg"
-  ]; }
+  {
+    "${peers.losurdo.ipv4}" = [
+      "nix-extracache.losurdo.wg"
+      "nix-localcache.losurdo.wg"
+      "sftp.losurdo.wg"
+    ];
+  }
 ];
 networking.firewall.extraCommands = lib.optionalString (wg.listenPort != null) ''
   ip46tables -A nixos-fw -i any -p udp -m udp --dport ${toString wg.listenPort} -j ACCEPT
 '';
+
+networking.nftables.ruleset = lib.optionalString (wg.listenPort != null) ''
+  table inet filter {
+    chain input-lan {
+      udp dport ${toString wg.listenPort} counter accept \
+        comment "Wireguard ${wgIface} input from peers"
+    }
+    chain input-net {
+      udp dport ${toString wg.listenPort} counter accept \
+        comment "Wireguard ${wgIface} input from peers"
+    }
+    chain input-intra {
+      ${lib.optionalString (peers.${hostName}.peer.endpointsUpdater.enable or false) ''
+        tcp dport ${toString peers.${hostName}.listenPort} ip daddr ${peers.${hostName}.ipv4} counter accept comment "Wireguard ${wgIface} from peers to endpointUpdater"
+        ''
+      }
+    }
+    chain input {
+      iifname ${wgIface} jump input-intra
+      iifname ${wgIface} log level warn prefix "input-intra: " counter drop
+    }
+
+    chain output-lan {
+      udp sport ${toString wg.listenPort} counter accept \
+        comment "Wireguard ${wgIface} output to peers"
+    }
+    chain output-net {
+      udp sport ${toString wg.listenPort} counter accept \
+        comment "Wireguard ${wgIface} output to peers"
+    }
+    chain output-intra {
+      ${lib.concatStringsSep "\n"
+          (lib.mapAttrsToList (peerName: peer: ''
+            ip daddr ${peer.ipv4} \
+              tcp dport ${toString peer.listenPort} \
+              counter accept \
+              comment "Wireguard ${wgIface} to endpointUpdater ${peerName}"
+            '')
+            (lib.filterAttrs (peerName: peer:
+              config.networking.wireguard.${wgIface}.peers.${peerName}.enable &&
+              (peers.${peerName}.peer.endpointsUpdater.enable or false))
+              peers))
+      }
+    }
+    chain output {
+      oifname ${wgIface} jump output-intra
+      oifname ${wgIface} log level warn prefix "output-intra: " counter drop
+    }
+  }
+'';
+
 services.fail2ban.ignoreIP = lib.concatMap
   (host: host.peer.allowedIPs)
   (lib.attrValues peers);
+networking.networkmanager.unmanaged = [ wgIface ];
+systemd.services.sshd.after = ["wireguard-${wgIface}.service"];
+services.openssh.listenAddresses = [
+  { addr = peers.${hostName}.ipv4; port = 22; }
+];
 };
 }