diff --git a/flake.nix b/flake.nix index 8789aa95..d0c283f0 100644 --- a/flake.nix +++ b/flake.nix @@ -8,9 +8,23 @@ outputs = { self, nixpkgs, hydra }: { - nixosConfigurations.server7 = nixpkgs.lib.nixosSystem { - modules = [ ./hosts/server7 hydra.nixosModules.hydra ]; - system = "x86_64-linux"; + nixosConfigurations = { + + server7 = nixpkgs.lib.nixosSystem { + modules = [ ./hosts/server7 hydra.nixosModules.hydra ]; + system = "x86_64-linux"; + }; + + hydra = nixpkgs.lib.nixosSystem { + modules = [ ./hosts/hydra/configuration.nix ]; + system = "x86_64-linux"; + }; + + pulsebert = nixpkgs.lib.nixosSystem { + modules = [ ./hosts/pulsebert/configuration.nix ]; + system = "x86_64-linux"; + }; + }; nixosModules.c3d2 = import ./lib; diff --git a/hosts/hydra/configuration.nix b/hosts/hydra/configuration.nix index 457851c6..b76dab2e 100644 --- a/hosts/hydra/configuration.nix +++ b/hosts/hydra/configuration.nix @@ -2,12 +2,9 @@ { imports = [ - ./hydra.nix ./cache.nix ../../lib - ../../lib/hq.nix - ../../lib/yggdrasil.nix ]; c3d2 = { @@ -18,23 +15,10 @@ isInHq = true; mapHqHosts = true; hq.interface = "eth0"; + hq.yggdrasil.enableGateway = true; }; networking.interfaces.eth0.preferTempAddress = false; - systemd.services.yggdrasil.preStart = '' - mkdir -p /dev/net - mknod /dev/net/tun c 10 200 || true - chmod 0666 /dev/net/tun - ''; - services.yggdrasil = { - configFile = "/var/lib/yggdrasil/keys"; - config.Peers = [ - "tcp://[2a03:3b40:fe:ab::1]:46370" # Praha - "tcp://ygg.thingylabs.io:443" # Nürnberg - "tcp://176.223.130.120:22632" # Wrocław - "tcp://[2a05:9403::8b]:7743" # Praha - ]; - }; nixpkgs.config.allowUnfree = true; diff --git a/hosts/pulsebert/configuration.nix b/hosts/pulsebert/configuration.nix index 497ca89c..ff33c871 100644 --- a/hosts/pulsebert/configuration.nix +++ b/hosts/pulsebert/configuration.nix @@ -13,7 +13,6 @@ in { ../../lib ../../lib/admins.nix ../../lib/hq.nix - ../../lib/yggdrasil.nix ./mpdConsole.nix ]; @@ -27,6 +26,7 @@ in { hq = { interface = "eno1"; enableMpdProxy = true; + yggdrasi.enableGateway = true; }; enableHail = true; }; diff --git a/hosts/server7/containers/adc/default.nix b/hosts/server7/containers/adc/default.nix index b0e3a04c..365f3b37 100644 --- a/hosts/server7/containers/adc/default.nix +++ b/hosts/server7/containers/adc/default.nix @@ -2,7 +2,16 @@ name: (import ../outer-defaults.nix name) // { config = { config, pkgs, lib, ... }: { - imports = [ ../inner-defaults.nix ../../../../lib/yggdrasil-hq.nix ]; + imports = [ ../inner-defaults.nix ]; + + c3d2.hq.yggdrasil.enableGateway = true; + + networking.firewall.allowedTCPPorts = [ config.services.uhub.port ]; + + networking.interfaces.eth0.ipv6.addresses = [{ + address = "310:5217:69c0:9afc:0:576d:1184:c3d2"; + prefixLength = 64; + }]; # Old address used by some clients services.uhub = { enable = true; @@ -18,8 +27,6 @@ name: }; }; - networking.firewall.allowedTCPPorts = [ config.services.uhub.port ]; - hq.yggdrasil.enable = true; }; } diff --git a/hosts/server7/containers/hydra7/default.nix b/hosts/server7/containers/hydra7/default.nix index 10837599..5ad2522b 100644 --- a/hosts/server7/containers/hydra7/default.nix +++ b/hosts/server7/containers/hydra7/default.nix @@ -1,30 +1,32 @@ name: -let port = 3000; -in (import ../outer-defaults.nix name) // { - - bindMounts."/srv/c3d2" = { - hostPath = "/srv/ceph/c3d2"; - isReadOnly = false; - }; +(import ../outer-defaults.nix name) // { ephemeral = true; - forwardPorts = [{ - containerPort = port; - hostPort = port; - protocol = "tcp"; - }]; - config = { config, pkgs, lib, ... }: { imports = [ ../inner-defaults.nix ]; + c3d2.hq.yggdrasil.enableGateway = true; networking.firewall.enable = false; + networking.interfaces.eth0.useDHCP = true; + security.acme = { + acceptTerms = true; + email = "mail@c3d2.de"; + }; services.nginx = { enable = true; + recommendedGzipSettings = true; + recommendedProxySettings = true; virtualHosts = { + "hydra7.hq.c3d2.de" = { + forceSSL = true; + enableACME = true; + locations."/".proxyPass = "http://172.22.99.245:3000"; + }; "hydra7.y.c3d2.de" = { default = true; - locations."/".proxyPass = "http://127.0.0.1:${toString port}"; + addSSL = false; + locations."/".proxyPass = "http://172.22.99.245:3000"; }; }; }; diff --git a/hosts/server7/containers/ncdc/default.nix b/hosts/server7/containers/ncdc/default.nix index d169ece4..4fdd3bdf 100644 --- a/hosts/server7/containers/ncdc/default.nix +++ b/hosts/server7/containers/ncdc/default.nix @@ -10,11 +10,12 @@ name: config = { config, pkgs, lib, ... }: let ncdcPort = 1512; in { - imports = [ ../inner-defaults.nix ../../../../lib/yggdrasil-hq.nix ]; + imports = [ ../inner-defaults.nix ]; c3d2 = { users.k-ot = true; hq.statistics.enable = true; + hq.yggdrasil.enableGateway = true; }; services.openssh.enable = true; @@ -23,7 +24,6 @@ name: environment.systemPackages = with pkgs; [ tmux ncdc ]; networking.firewall.enable = false; - hq.yggdrasil.enable = true; }; } diff --git a/hosts/server7/containers/outer-defaults.nix b/hosts/server7/containers/outer-defaults.nix index 9b849ea1..680bec38 100644 --- a/hosts/server7/containers/outer-defaults.nix +++ b/hosts/server7/containers/outer-defaults.nix @@ -7,13 +7,4 @@ in { autoStart = true; privateNetwork = true; hostBridge = "br0"; - - localAddress6 = with builtins; - let - hash = hashString "sha256" name; - hextet0 = substring 0 4 hash; - hextet1 = substring 4 4 hash; - in "${yggaddr.prefix}:${hextet0}:${hextet1}:c3d2/64"; - # Generate a deterministic IPv6 address for the container. - # This address is accessible within HQ and Yggdrasil but not from ARPANET. } diff --git a/hosts/server7/containers/storage/default.nix b/hosts/server7/containers/storage/default.nix index be8631c9..d36cc141 100644 --- a/hosts/server7/containers/storage/default.nix +++ b/hosts/server7/containers/storage/default.nix @@ -13,6 +13,7 @@ name: c3d2 = { users.k-ot = true; hq.statistics.enable = true; + hq.yggdrasil.enableGateway = true; }; services.openssh = { diff --git a/hosts/server7/default.nix b/hosts/server7/default.nix index f741d4fd..bbe60f46 100644 --- a/hosts/server7/default.nix +++ b/hosts/server7/default.nix @@ -45,15 +45,6 @@ in { ]; }; - - services.nginx = { - enable = true; - recommendedGzipSettings = true; - recommendedProxySettings = true; - recommendedTlsSettings = true; - statusPage = true; - }; - # Route IPv6 boot.kernel.sysctl."net.ipv6.conf.all.forwarding" = 1; # Obtain global IPv6 despite being a router myself @@ -98,6 +89,7 @@ in { networking = { firewall.enable = false; + firewall.trustedInterfaces = [ "br0" ]; hostName = "server7"; hostId = "454fe12c"; useDHCP = false; @@ -111,7 +103,7 @@ in { prefixLength = 24; }]; ipv6.addresses = [{ - address = yggaddr.prefix + ":1"; + address = yggaddr.prefix64 + "::1"; prefixLength = 64; }]; }; diff --git a/hosts/server7/hydra.nix b/hosts/server7/hydra.nix index 872bfde9..f0b68f5a 100644 --- a/hosts/server7/hydra.nix +++ b/hosts/server7/hydra.nix @@ -1,13 +1,22 @@ { config, pkgs, ... }: { - services.hydra-dev = { enable = true; + debugServer = true; + extraEnv.HYDRA_DEBUG = "1"; hydraURL = "https://server7.hq.c3d2.de"; logo = ./hydra.svg; notificationSender = "hydra@spam.works"; - listenHost = "127.0.0.1"; + # package = pkgs.hydra-unstable; + listenHost = "172.22.99.245"; + # listenHost = "*"; + extraConfig = '' + + username = emery + password = 36\#KAVMD + + ''; }; nix.trustedUsers = [ "hydra" ]; @@ -19,18 +28,4 @@ maxJobs = 8; }]; - services.nginx = { - enable = true; - virtualHosts = { - "server7.hq.c3d2.de" = { - default = true; - addSSL = true; - enableACME = true; - locations."/".proxyPass = - "http://127.0.0.1:${toString config.services.hydra-dev.port}"; - }; - }; - }; - - networking.firewall.allowedTCPPorts = [ 80 443 ]; } diff --git a/hosts/server7/yggaddr.nix b/hosts/server7/yggaddr.nix index f5086928..22be5469 100644 --- a/hosts/server7/yggaddr.nix +++ b/hosts/server7/yggaddr.nix @@ -1,4 +1,4 @@ { address = "210:5217:69c0:9afc:1b95:b9f:8718:c3d2"; - prefix = "310:5217:69c0:9afc:"; + prefix64 = "310:5217:69c0:9afc"; } diff --git a/lib/default.nix b/lib/default.nix index ab2e6254..505a6ab1 100644 --- a/lib/default.nix +++ b/lib/default.nix @@ -8,6 +8,8 @@ let hqPrefix64 = "fd23:42:c3d2:523"; # TODO: Is this stable? Is there a better place to specifiy this? + server7Ygg = import ../hosts/server7/yggaddr.nix; + # Generate a deterministic IPv6 address for a 64 bit prefix # and seed string. Prefix must not contain trailing ':'. toIpv6Address = prefix64: seed: @@ -21,14 +23,9 @@ let # for the HQ networking using a seed string. toHqPrivateAddress = toIpv6Address hqPrefix64; - /* # Generate a deterministic public IPv6 addresses - # for the HQ networking using a seed string. - toHqPublicAddress = toIpv6Address publicPrefix64; + toServer7Address = toIpv6Address server7Ygg.prefix64; - # Generate a deterministic public IPv6 addresses - # for the HQ networking using a seed string. - toserver7YggdrasilAddress = toIpv6Address server7YggrasilPrefix64; - */ + # toHqPublicAddress = toIpv6Address publicPrefix64; cfg = config.c3d2; @@ -106,6 +103,8 @@ in { description = "Whether to proxy the local MPD database"; }; + yggdrasil.enableGateway = mkEnableOption + "Whether to join the host to the Yggdrasil network via a gateway"; }; }; @@ -118,7 +117,8 @@ in { # Configuration specific to this machine assertions = [ - { assertion = cfg.isInHq -> (config.users.users.root.password == null); + { + assertion = cfg.isInHq -> (config.users.users.root.password == null); message = "Root passwords not allowed in HQ"; } { @@ -166,10 +166,16 @@ in { host.ip6 else toHqPrivateAddress hostName; - in [{ - name = ip6; - value = [ "${hostName}.hq" hostName ]; - }] ++ lib.optional (hasAttr "ip4" host) { + in [ + { + name = ip6; + value = [ "${hostName}.hq" hostName ]; + } + { + name = toServer7Address hostName; + value = [ "${hostName}.y.c3d2.de" "${hostName}.y" ]; + } + ] ++ lib.optional (hasAttr "ip4" host) { name = host.ip4; value = [ "${hostName}.hq" hostName ]; }; @@ -196,7 +202,16 @@ in { ipv6.addresses = [{ address = toHqPrivateAddress config.networking.hostName; prefixLength = 64; - }]; + }] ++ lib.optional (cfg.hq.yggdrasil.enableGateway) { + address = toServer7Address config.networking.hostName; + prefixLength = 64; + }; + ipv6.routes = lib.optional (cfg.hq.yggdrasil.enableGateway) { + address = "200::"; + options.pref = "low"; + prefixLength = 7; + via = server7Ygg.prefix64 + "::1"; + }; }; }); diff --git a/lib/hq.nix b/lib/hq.nix deleted file mode 100644 index 4ecc258c..00000000 --- a/lib/hq.nix +++ /dev/null @@ -1,7 +0,0 @@ -{ config, lib, ... }: - -{ - # Please import only things that are configurable and OFF BY DEFAULT! - imports = [ ./yggdrasil-hq.nix ]; - -} diff --git a/lib/yggdrasil-hq.nix b/lib/yggdrasil-hq.nix deleted file mode 100644 index 21d026b3..00000000 --- a/lib/yggdrasil-hq.nix +++ /dev/null @@ -1,40 +0,0 @@ -{ config, lib, ... }: -with lib; - -let - cfg = config.hq.yggdrasil; - hostNameHash = builtins.hashString "sha256" config.networking.hostName; - hextets = map (i: substring (4 * i) 4 hostNameHash) [ 0 1 2 3 ]; - hostAddr = concatStringsSep ":" hextets; -in { - options = with types; { - hq.yggdrasil = { - enable = - mkEnableOption "Configure Yggdrasil access via the Yggdrasil router"; - - interface = mkOption { - type = nullOr str; - default = "eth0"; - description = "Network interface to the C3D2 HQ ethernet"; - }; - }; - }; - - config = mkIf cfg.enable { - networking.interfaces = { - "${cfg.interface}" = { - "ipv6" = { - addresses = [{ - address = "310:5217:69c0:9afc:${hostAddr}"; - prefixLength = 64; - }]; - routes = [{ - address = "200::"; - prefixLength = 7; - via = "310:5217:69c0:9afc::1"; - }]; - }; - }; - }; - }; -} diff --git a/lib/yggdrasil-service.nix b/lib/yggdrasil-service.nix deleted file mode 100644 index 33d1f093..00000000 --- a/lib/yggdrasil-service.nix +++ /dev/null @@ -1,185 +0,0 @@ -{ config, lib, pkgs, ... }: -with lib; -let - cfg = config.services.yggdrasil; - configProvided = (cfg.config != { }); - configAsFile = (if configProvided then - toString (pkgs.writeTextFile { - name = "yggdrasil-conf"; - text = builtins.toJSON cfg.config; - }) - else - null); - configFileProvided = (cfg.configFile != null); - generateConfig = (if configProvided && configFileProvided then - "${pkgs.jq}/bin/jq -s add ${configAsFile} ${cfg.configFile}" - else if configProvided then - "cat ${configAsFile}" - else if configFileProvided then - "cat ${cfg.configFile}" - else - "${cfg.package}/bin/yggdrasil -genconf"); - -in { - options = with types; { - services.yggdrasil = { - enable = mkEnableOption "the yggdrasil system service"; - - configFile = mkOption { - type = nullOr str; - default = null; - example = "/run/keys/yggdrasil.conf"; - description = '' - A file which contains JSON configuration for yggdrasil. - - You do not have to supply a complete configuration, as - yggdrasil will use default values for anything which is - omitted. If the encryption and signing keys are omitted, - yggdrasil will generate new ones each time the service is - started, resulting in a random IPv6 address on the yggdrasil - network each time. - - If both this option and are - supplied, they will be combined, with values from - taking precedence. - - You can use the command nix-shell -p yggdrasil --run - "yggdrasil -genconf -json" to generate a default - JSON configuration. - ''; - }; - - config = mkOption { - type = attrs; - default = { }; - example = { - Peers = [ - "tcp://aa.bb.cc.dd:eeeee" - "tcp://[aaaa:bbbb:cccc:dddd::eeee]:fffff" - ]; - Listen = [ "tcp://0.0.0.0:xxxxx" ]; - }; - description = '' - Configuration for yggdrasil, as a Nix attribute set. - - Warning: this is stored in the WORLD-READABLE Nix store! - Therefore, it is not appropriate for private keys. If you - do not specify the keys, yggdrasil will generate a new set - each time the service is started, creating a random IPv6 - address on the yggdrasil network each time. - - If you wish to specify the keys, use - . If both - and are - supplied, they will be combined, with values from - taking precedence. - - You can use the command nix-shell -p yggdrasil --run - "yggdrasil -genconf" to generate default - configuration values with documentation. - ''; - }; - - openMulticastPort = mkOption { - type = bool; - default = false; - description = '' - Whether to open the UDP port used for multicast peer - discovery. The NixOS firewall blocks link-local - communication, so in order to make local peering work you - will also need to set LinkLocalTCPPort in your - yggdrasil configuration ( or - ) to a port number other than 0, - and then add that port to - . - ''; - }; - - denyDhcpcdInterfaces = mkOption { - type = listOf str; - default = [ ]; - example = [ "tap*" ]; - description = '' - Disable the DHCP client for any interface whose name matches - any of the shell glob patterns in this list. Use this - option to prevent the DHCP client from broadcasting requests - on the yggdrasil network. It is only necessary to do so - when yggdrasil is running in TAP mode, because TUN - interfaces do not support broadcasting. - ''; - }; - - package = mkOption { - type = package; - default = pkgs.yggdrasil; - defaultText = "pkgs.yggdrasil"; - description = "Yggdrasil package to use."; - }; - }; - }; - - config = mkIf cfg.enable { - assertions = [{ - assertion = config.networking.enableIPv6; - message = "networking.enableIPv6 must be true for yggdrasil to work"; - }]; - - systemd.services.yggdrasil = { - description = "Yggdrasil Network Service"; - path = [ cfg.package ] - ++ optional (configProvided && configFileProvided) pkgs.jq; - bindsTo = [ "network-online.target" ]; - after = [ "network-online.target" ]; - wantedBy = [ "multi-user.target" ]; - - preStart = '' - ${generateConfig} | yggdrasil -normaliseconf -useconf > /run/yggdrasil/yggdrasil.conf - ''; - - serviceConfig = { - ExecStart = - "${cfg.package}/bin/yggdrasil -useconffile /run/yggdrasil/yggdrasil.conf"; - ExecReload = "${pkgs.coreutils}/bin/kill -HUP $MAINPID"; - Restart = "always"; - - RuntimeDirectory = "yggdrasil"; - RuntimeDirectoryMode = "0700"; - BindReadOnlyPaths = mkIf configFileProvided [ "${cfg.configFile}" ]; - - # TODO: as of yggdrasil 0.3.8 and systemd 243, yggdrasil fails - # to set up the network adapter when DynamicUser is set. See - # github.com/yggdrasil-network/yggdrasil-go/issues/557. The - # following options are implied by DynamicUser according to - # the systemd.exec documentation, and can be removed if the - # upstream issue is fixed and DynamicUser is set to true: - PrivateTmp = true; - RemoveIPC = true; - NoNewPrivileges = true; - ProtectSystem = "strict"; - RestrictSUIDSGID = true; - # End of list of options implied by DynamicUser. - - AmbientCapabilities = "CAP_NET_ADMIN"; - CapabilityBoundingSet = "CAP_NET_ADMIN"; - MemoryDenyWriteExecute = true; - ProtectControlGroups = true; - ProtectHome = "tmpfs"; - ProtectKernelModules = true; - ProtectKernelTunables = true; - RestrictAddressFamilies = "AF_UNIX AF_INET AF_INET6 AF_NETLINK"; - RestrictNamespaces = true; - RestrictRealtime = true; - SystemCallArchitectures = "native"; - SystemCallFilter = - "~@clock @cpu-emulation @debug @keyring @module @mount @obsolete @raw-io @resources"; - }; - }; - - networking.dhcpcd.denyInterfaces = cfg.denyDhcpcdInterfaces; - networking.firewall.allowedUDPPorts = mkIf cfg.openMulticastPort [ 9001 ]; - - # Make yggdrasilctl available on the command line. - environment.systemPackages = [ cfg.package ]; - }; - meta.maintainers = with lib.maintainers; [ gazally ]; -} diff --git a/lib/yggdrasil.nix b/lib/yggdrasil.nix deleted file mode 100644 index f497dc6e..00000000 --- a/lib/yggdrasil.nix +++ /dev/null @@ -1,13 +0,0 @@ -{ config, ... }: { - imports = [ ./yggdrasil-service.nix ]; - - services.yggdrasil = { - enable = true; - package = (import { }).yggdrasil; - openMulticastPort = true; - config.NodeInfo = { - name = config.networking.hostName + ".c3d2"; - location = "Dresden"; - }; - }; -}