djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 1 | # $OpenBSD: keygen-knownhosts.sh,v 1.4 2018/06/01 03:52:37 djm Exp $ |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 2 | # Placed in the Public Domain. |
| 3 | |
| 4 | tid="ssh-keygen known_hosts" |
| 5 | |
| 6 | rm -f $OBJ/kh.* |
| 7 | |
| 8 | # Generate some keys for testing (just ed25519 for speed) and make a hosts file. |
| 9 | for x in host-a host-b host-c host-d host-e host-f host-a2 host-b2; do |
| 10 | ${SSHKEYGEN} -qt ed25519 -f $OBJ/kh.$x -C "$x" -N "" || \ |
| 11 | fatal "ssh-keygen failed" |
| 12 | # Add a comment that we expect should be preserved. |
| 13 | echo "# $x" >> $OBJ/kh.hosts |
| 14 | ( |
| 15 | case "$x" in |
djm@openbsd.org | e56aa87 | 2015-01-27 12:01:36 +0000 | [diff] [blame] | 16 | host-a|host-b) printf "$x " ;; |
| 17 | host-c) printf "@cert-authority $x " ;; |
| 18 | host-d) printf "@revoked $x " ;; |
| 19 | host-e) printf "host-e* " ;; |
| 20 | host-f) printf "host-f,host-g,host-h " ;; |
| 21 | host-a2) printf "host-a " ;; |
| 22 | host-b2) printf "host-b " ;; |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 23 | esac |
| 24 | cat $OBJ/kh.${x}.pub |
| 25 | # Blank line should be preserved. |
| 26 | echo "" >> $OBJ/kh.hosts |
| 27 | ) >> $OBJ/kh.hosts |
| 28 | done |
| 29 | |
| 30 | # Generate a variant with an invalid line. We'll use this for most tests, |
| 31 | # because keygen should be able to cope and it should be preserved in any |
| 32 | # output file. |
| 33 | cat $OBJ/kh.hosts >> $OBJ/kh.invalid |
| 34 | echo "host-i " >> $OBJ/kh.invalid |
| 35 | |
| 36 | cp $OBJ/kh.invalid $OBJ/kh.invalid.orig |
| 37 | cp $OBJ/kh.hosts $OBJ/kh.hosts.orig |
| 38 | |
| 39 | expect_key() { |
| 40 | _host=$1 |
| 41 | _hosts=$2 |
| 42 | _key=$3 |
| 43 | _line=$4 |
| 44 | _mark=$5 |
| 45 | _marker="" |
| 46 | test "x$_mark" = "xCA" && _marker="@cert-authority " |
| 47 | test "x$_mark" = "xREVOKED" && _marker="@revoked " |
| 48 | test "x$_line" != "x" && |
| 49 | echo "# Host $_host found: line $_line $_mark" >> $OBJ/kh.expect |
djm@openbsd.org | e56aa87 | 2015-01-27 12:01:36 +0000 | [diff] [blame] | 50 | printf "${_marker}$_hosts " >> $OBJ/kh.expect |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 51 | cat $OBJ/kh.${_key}.pub >> $OBJ/kh.expect || |
| 52 | fatal "${_key}.pub missing" |
| 53 | } |
| 54 | |
| 55 | check_find() { |
| 56 | _host=$1 |
| 57 | _name=$2 |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 58 | shift; shift |
| 59 | ${SSHKEYGEN} "$@" -f $OBJ/kh.invalid -F $_host > $OBJ/kh.result |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 60 | if ! diff -w $OBJ/kh.expect $OBJ/kh.result ; then |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 61 | fail "didn't find $_name" |
| 62 | fi |
| 63 | } |
| 64 | |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 65 | check_find_exit_code() { |
| 66 | _host=$1 |
| 67 | _name=$2 |
| 68 | _keygenopt=$3 |
| 69 | _exp_exit_code=$4 |
| 70 | ${SSHKEYGEN} $_keygenopt -f $OBJ/kh.invalid -F $_host > /dev/null |
| 71 | if [ "$?" != "$_exp_exit_code" ] ; then |
| 72 | fail "Unexpected exit code $_name" |
| 73 | fi |
| 74 | } |
| 75 | |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 76 | # Find key |
| 77 | rm -f $OBJ/kh.expect |
| 78 | expect_key host-a host-a host-a 2 |
| 79 | expect_key host-a host-a host-a2 20 |
| 80 | check_find host-a "simple find" |
| 81 | |
| 82 | # find CA key |
| 83 | rm -f $OBJ/kh.expect |
| 84 | expect_key host-c host-c host-c 8 CA |
| 85 | check_find host-c "find CA key" |
| 86 | |
| 87 | # find revoked key |
| 88 | rm -f $OBJ/kh.expect |
| 89 | expect_key host-d host-d host-d 11 REVOKED |
| 90 | check_find host-d "find revoked key" |
| 91 | |
| 92 | # find key with wildcard |
| 93 | rm -f $OBJ/kh.expect |
| 94 | expect_key host-e.somedomain "host-e*" host-e 14 |
| 95 | check_find host-e.somedomain "find wildcard key" |
| 96 | |
| 97 | # find key among multiple hosts |
| 98 | rm -f $OBJ/kh.expect |
| 99 | expect_key host-h "host-f,host-g,host-h " host-f 17 |
| 100 | check_find host-h "find multiple hosts" |
| 101 | |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 102 | # Check exit code, known host |
| 103 | check_find_exit_code host-a "known host" "-q" "0" |
| 104 | |
| 105 | # Check exit code, unknown host |
| 106 | check_find_exit_code host-aa "unknown host" "-q" "1" |
| 107 | |
| 108 | # Check exit code, the hash mode, known host |
| 109 | check_find_exit_code host-a "known host" "-q -H" "0" |
| 110 | |
| 111 | # Check exit code, the hash mode, unknown host |
| 112 | check_find_exit_code host-aa "unknown host" "-q -H" "1" |
| 113 | |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 114 | check_hashed_find() { |
| 115 | _host=$1 |
| 116 | _name=$2 |
| 117 | _file=$3 |
| 118 | test "x$_file" = "x" && _file=$OBJ/kh.invalid |
| 119 | ${SSHKEYGEN} -f $_file -HF $_host | grep '|1|' | \ |
| 120 | sed "s/^[^ ]*/$_host/" > $OBJ/kh.result |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 121 | if ! diff -w $OBJ/kh.expect $OBJ/kh.result ; then |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 122 | fail "didn't find $_name" |
| 123 | fi |
| 124 | } |
| 125 | |
| 126 | # Find key and hash |
| 127 | rm -f $OBJ/kh.expect |
| 128 | expect_key host-a host-a host-a |
| 129 | expect_key host-a host-a host-a2 |
| 130 | check_hashed_find host-a "find simple and hash" |
| 131 | |
| 132 | # Find CA key and hash |
| 133 | rm -f $OBJ/kh.expect |
| 134 | expect_key host-c host-c host-c "" CA |
| 135 | # CA key output is not hashed. |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 136 | check_find host-c "find simple and hash" -Hq |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 137 | |
| 138 | # Find revoked key and hash |
| 139 | rm -f $OBJ/kh.expect |
| 140 | expect_key host-d host-d host-d "" REVOKED |
| 141 | # Revoked key output is not hashed. |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 142 | check_find host-d "find simple and hash" -Hq |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 143 | |
| 144 | # find key with wildcard and hash |
| 145 | rm -f $OBJ/kh.expect |
| 146 | expect_key host-e "host-e*" host-e "" |
| 147 | # Key with wildcard hostname should not be hashed. |
djm@openbsd.org | a1dcafc | 2018-06-01 03:52:37 +0000 | [diff] [blame] | 148 | check_find host-e "find wildcard key" -Hq |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 149 | |
| 150 | # find key among multiple hosts |
| 151 | rm -f $OBJ/kh.expect |
| 152 | # Comma-separated hostnames should be expanded and hashed. |
| 153 | expect_key host-f "host-h " host-f |
| 154 | expect_key host-g "host-h " host-f |
| 155 | expect_key host-h "host-h " host-f |
| 156 | check_hashed_find host-h "find multiple hosts" |
| 157 | |
| 158 | # Attempt remove key on invalid file. |
| 159 | cp $OBJ/kh.invalid.orig $OBJ/kh.invalid |
| 160 | ${SSHKEYGEN} -qf $OBJ/kh.invalid -R host-a 2>/dev/null |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 161 | diff $OBJ/kh.invalid $OBJ/kh.invalid.orig || fail "remove on invalid succeeded" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 162 | |
| 163 | # Remove key |
| 164 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 165 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -R host-a 2>/dev/null |
| 166 | grep -v "^host-a " $OBJ/kh.hosts.orig > $OBJ/kh.expect |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 167 | diff $OBJ/kh.hosts $OBJ/kh.expect || fail "remove simple" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 168 | |
| 169 | # Remove CA key |
| 170 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 171 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -R host-c 2>/dev/null |
| 172 | # CA key should not be removed. |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 173 | diff $OBJ/kh.hosts $OBJ/kh.hosts.orig || fail "remove CA" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 174 | |
| 175 | # Remove revoked key |
| 176 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 177 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -R host-d 2>/dev/null |
| 178 | # revoked key should not be removed. |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 179 | diff $OBJ/kh.hosts $OBJ/kh.hosts.orig || fail "remove revoked" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 180 | |
| 181 | # Remove wildcard |
| 182 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 183 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -R host-e.blahblah 2>/dev/null |
| 184 | grep -v "^host-e[*] " $OBJ/kh.hosts.orig > $OBJ/kh.expect |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 185 | diff $OBJ/kh.hosts $OBJ/kh.expect || fail "remove wildcard" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 186 | |
| 187 | # Remove multiple |
| 188 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 189 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -R host-h 2>/dev/null |
| 190 | grep -v "^host-f," $OBJ/kh.hosts.orig > $OBJ/kh.expect |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 191 | diff $OBJ/kh.hosts $OBJ/kh.expect || fail "remove wildcard" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 192 | |
| 193 | # Attempt hash on invalid file |
| 194 | cp $OBJ/kh.invalid.orig $OBJ/kh.invalid |
| 195 | ${SSHKEYGEN} -qf $OBJ/kh.invalid -H 2>/dev/null && fail "hash invalid succeeded" |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 196 | diff $OBJ/kh.invalid $OBJ/kh.invalid.orig || fail "invalid file modified" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 197 | |
| 198 | # Hash valid file |
| 199 | cp $OBJ/kh.hosts.orig $OBJ/kh.hosts |
| 200 | ${SSHKEYGEN} -qf $OBJ/kh.hosts -H 2>/dev/null || fail "hash failed" |
djm@openbsd.org | cd7324d | 2015-07-17 03:34:27 +0000 | [diff] [blame] | 201 | diff $OBJ/kh.hosts.old $OBJ/kh.hosts.orig || fail "backup differs" |
djm@openbsd.org | 7947810 | 2015-01-18 22:00:18 +0000 | [diff] [blame] | 202 | grep "^host-[abfgh]" $OBJ/kh.hosts && fail "original hostnames persist" |
| 203 | |
| 204 | cp $OBJ/kh.hosts $OBJ/kh.hashed.orig |
| 205 | |
| 206 | # Test lookup |
| 207 | rm -f $OBJ/kh.expect |
| 208 | expect_key host-a host-a host-a |
| 209 | expect_key host-a host-a host-a2 |
| 210 | check_hashed_find host-a "find simple in hashed" $OBJ/kh.hosts |
| 211 | |
| 212 | # Test multiple expanded |
| 213 | rm -f $OBJ/kh.expect |
| 214 | expect_key host-h host-h host-f |
| 215 | check_hashed_find host-h "find simple in hashed" $OBJ/kh.hosts |
| 216 | |
| 217 | # Test remove |
| 218 | cp $OBJ/kh.hashed.orig $OBJ/kh.hashed |
| 219 | ${SSHKEYGEN} -qf $OBJ/kh.hashed -R host-a 2>/dev/null |
| 220 | ${SSHKEYGEN} -qf $OBJ/kh.hashed -F host-a && fail "found key after hashed remove" |