From 262447705c48d0c7dd3746b6a6c872ab8bd33007 Mon Sep 17 00:00:00 2001 From: Alyssa Ross Date: Sun, 21 Nov 2021 17:25:03 +0000 Subject: [PATCH] nixos/ssh: add programs.ssh.knownHostsFiles option The programs.ssh.knownHosts.*.publicKeyFile is broken, because it's scoped to a set of host names, but to insert those host names on each line of the file we'd have to parse out blank lines and comments, so only the first line works. It would be much easier all round if users just provided known hosts files in the normal format, and we pointed ssh directly to them. This way, it would be possible to have multiple keys for a single host (which is extremely common due to multiple algorithms being commonplace). We add an option for this instead of relying on extraConfig, because we need to make sure /etc/ssh/ssh_known_hosts is always included to ensure programs.ssh.knownHosts keeps working. /etc/ssh/ssh_known_hosts2 is another OpenSSH default that seems a bit weird, but there's no real reason to change that so we'll leave it. --- nixos/modules/programs/ssh.nix | 30 +++++++++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/nixos/modules/programs/ssh.nix b/nixos/modules/programs/ssh.nix index c680063a47c3..35380f864208 100644 --- a/nixos/modules/programs/ssh.nix +++ b/nixos/modules/programs/ssh.nix @@ -25,6 +25,9 @@ let + (if h.publicKey != null then h.publicKey else readFile h.publicKeyFile) )) + "\n"; + knownHostsFiles = [ "/etc/ssh/ssh_known_hosts" "/etc/ssh/ssh_known_hosts2" ] + ++ map pkgs.copyPathToStore cfg.knownHostsFiles; + in { ###### interface @@ -177,7 +180,9 @@ in You can fetch a public key file from a running SSH server with the ssh-keyscan command. The content of the file should follow the same format as described for - the publicKey option. + the publicKey option. Only a single key + is supported. If a host has multiple keys, use + instead. ''; }; }; @@ -202,6 +207,28 @@ in ''; }; + knownHostsFiles = mkOption { + default = []; + type = with types; listOf path; + description = '' + Files containing SSH host keys to set as global known hosts. + /etc/ssh/ssh_known_hosts (which is + generated by ) and + /etc/ssh/ssh_known_hosts2 are always + included. + ''; + example = literalExpression '' + [ + ./known_hosts + (writeText "github.keys" ''' + github.com ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ== + github.com ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBEmKSENjQEezOmxkZMy7opKgwFB9nkt5YRrYMjNuG5N87uRgg6CLrbo5wAdT/y6v0mKV0U2w0WZ2YB/++Tpockg= + github.com ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOMqqnkVzrm0SdG6UOoqKLsabgH5C9okWi0dh2l9GKJl + ''') + ] + ''; + }; + kexAlgorithms = mkOption { type = types.nullOr (types.listOf types.str); default = null; @@ -258,6 +285,7 @@ in # Generated options from other settings Host * AddressFamily ${if config.networking.enableIPv6 then "any" else "inet"} + GlobalKnownHostsFile ${concatStringsSep " " knownHostsFiles} ${optionalString cfg.setXAuthLocation '' XAuthLocation ${pkgs.xorg.xauth}/bin/xauth