b4ad0648c647497a980f4b229e9c0f9a3e2dd4b5
[monkeysphere.git] / tests / basic
1 #!/usr/bin/env bash
2
3 # Tests to ensure that the monkeysphere is working
4 #
5 # unset MONKEYSPHERE_TEST_NO_EXAMINE to examine
6
7 # Authors: 
8 #   Daniel Kahn Gillmor <dkg@fifthhorseman.net>
9 #   Jameson Rollins <jrollins@fifthhorseman.net>
10 #   Micah Anderson <micah@riseup.net> 
11 #
12 # Copyright: 2008-2009
13 # License: GPL v3 or later
14
15 # these tests should all be able to run as a non-privileged user.
16
17 # put all the test output to stdout
18 exec 2>&1
19 # all subcommands in this script should complete without failure:
20 set -e
21 # piped commands should return the code of the first non-zero return
22 set -o pipefail
23
24 # make sure the TESTDIR is an absolute path, not a relative one.
25 export TESTDIR=$(cd $(dirname "$0") && pwd)
26
27 source "$TESTDIR"/common
28
29 ## make sure that the right tools are installed to run the test.  the
30 ## test has *more* requirements than plain ol' monkeysphere:
31 [ -f /usr/sbin/sshd ] || { echo "You must have sshd installed to run this test." ; exit 1; }
32 which socat >/dev/null || { echo "You must have socat installed to run this test." ; exit 1; }
33
34 perl -MCrypt::OpenSSL::RSA -e 1 2>/dev/null || { echo "You must have the perl module Crypt::OpenSSL::RSA installed to run this test.  
35 On debian-derived systems, you can set this up with:
36   apt-get install libcrypt-openssl-rsa-perl" ; exit 1; }
37
38 perl -MDigest::SHA -e 1 2>/dev/null || { echo "You must have the perl module Digest::SHA installed to run this test.  
39 On debian-derived systems, you can set this up with:
40   apt-get install libdigest-sha-perl" ; exit 1; }
41
42 ## FIXME: other checks?
43
44 ######################################################################
45 ### FUNCTIONS
46
47 # gpg command for test admin user
48 gpgadmin() {
49     chmod 0700 "$TEMPDIR"/admin
50     GNUPGHOME="$TEMPDIR"/admin/.gnupg gpg --no-tty "$@"
51 }
52
53 # test ssh connection
54 # first argument is expected return code from ssh connection
55 ssh_test() {
56     local RETURN=0
57
58     umask 0077
59
60     CODE=${1:-0}
61
62     # start the ssh daemon on the socket
63     echo "##### starting ssh server..."
64     socat EXEC:"/usr/sbin/sshd -f ${SSHD_CONFIG} -i -D -e" "UNIX-LISTEN:${SOCKET}" 2> "$TEMPDIR"/sshd.log &
65     SSHD_PID="$!"
66
67     # wait until the socket is created before continuing
68     while [ ! -S "$SOCKET" ] ; do
69         sleep 2
70     done
71
72     # make a client connection to the socket
73     echo "##### starting ssh client..."
74     ssh-agent bash -c \
75         "monkeysphere subkey-to-ssh-agent && ssh -F $TEMPDIR/testuser/.ssh/config testhost true" \
76         || RETURN="$?"
77
78     # kill the sshd process if it's still running
79     kill "$SSHD_PID"
80     SSHD_PID=
81
82     if [ "$RETURN" = "$CODE" ] ; then
83         echo "##### ssh connection test PASSED. returned: $RETURN"
84         return 0
85     else
86         echo "##### ssh connection test FAILED. returned: $RETURN, expected: $CODE"
87         return 1
88     fi
89 }
90
91 SSHD_PID=
92
93 ## setup trap
94 trap failed_cleanup EXIT
95
96
97 ######################################################################
98 ### SETUP VARIABLES
99
100 ## set up some variables to ensure that we're operating strictly in
101 ## the tests, not system-wide:
102
103 # set up temp dir
104
105 # NOTE: /tmp can not be used as the temp dir here, since the
106 # permissions on /tmp are usually such that they will not pass the
107 # monkeysphere/ssh path permission checking.  If you need to use a
108 # different location than the current source, please set $TMPDIR
109 # somewhere with tighter permissions.
110
111 mkdir -p "$TESTDIR"/tmp
112 TEMPDIR=$(mktemp -d "${TMPDIR:-$TESTDIR/tmp}/monkeyspheretest.XXXXXXX")
113
114 # Use the local copy of executables first, instead of system ones.
115 # This should help us test without installing.
116 export PATH="$TESTDIR"/../src:"$PATH"
117
118 export MONKEYSPHERE_SYSDATADIR="$TEMPDIR"
119 export MONKEYSPHERE_SYSCONFIGDIR="$TEMPDIR"
120 export MONKEYSPHERE_SYSSHAREDIR="$TESTDIR"/../src/share
121 export MONKEYSPHERE_MONKEYSPHERE_USER=$(whoami)
122
123 export MONKEYSPHERE_CHECK_KEYSERVER=false
124 # example.org does not respond to the HKP port, so this should cause
125 # any keyserver connection attempts that do happen (they shouldn't!)
126 # to hang, so we'll notice them:
127 export MONKEYSPHERE_KEYSERVER=example.org
128
129 export MONKEYSPHERE_LOG_LEVEL=DEBUG
130 export MONKEYSPHERE_CORE_KEYLENGTH=1024
131 export MONKEYSPHERE_PROMPT=false
132
133 # unset SUBKEYS_FOR_AGENT variable which, if set, would confuse the
134 # into trying to use the user's key, instead of the testuser's key
135 unset MONKEYSPHERE_SUBKEYS_FOR_AGENT
136
137 export SSHD_CONFIG="$TEMPDIR"/sshd_config
138 export SOCKET="$TEMPDIR"/ssh-socket
139
140 # Make sure $DISPLAY is set to convince ssh and monkeysphere to fall
141 # back on $SSH_ASKPASS.  Make sure it's not set to the current actual
142 # $DISPLAY (if one exists) because this test suite should not be doing
143 # *anything* with any running X11 session.
144 export DISPLAY=monkeys
145
146
147 ######################################################################
148 ### CONFIGURE ENVIRONMENTS
149
150 # copy in admin and testuser home to tmp
151 echo
152 echo "##################################################"
153 echo "### configuring testuser home..."
154 (cd "$TESTDIR"/home && find testuser | cpio -pdu "$TEMPDIR")
155
156 # set up environment for testuser
157 export TESTHOME="$TEMPDIR"/testuser
158 export GNUPGHOME="$TESTHOME"/.gnupg
159 chmod 0700 "$GNUPGHOME"
160 export SSH_ASKPASS="$TESTHOME"/.ssh/askpass
161 export MONKEYSPHERE_HOME="$TESTHOME"/.monkeysphere
162 cat <<EOF >> "$TESTHOME"/.ssh/config
163 UserKnownHostsFile $TESTHOME/.ssh/known_hosts
164 IdentityFile $TESTHOME/.ssh/no-such-identity
165 ProxyCommand $TESTHOME/.ssh/proxy-command %h %p $SOCKET
166 EOF
167 cat <<EOF >> "$MONKEYSPHERE_HOME"/monkeysphere.conf
168 KNOWN_HOSTS=$TESTHOME/.ssh/known_hosts
169 EOF
170 get_gpg_prng_arg >> "$GNUPGHOME"/gpg.conf
171
172 echo
173 echo "##################################################"
174 echo "### configuring admin home..."
175 (cd "$TESTDIR"/home && find admin | cpio -pdu "$TEMPDIR")
176
177 # set up sshd
178 echo
179 echo "##################################################"
180 echo "### configuring sshd..."
181 cp "$TESTDIR"/etc/ssh/sshd_config "$SSHD_CONFIG"
182 # write the sshd_config
183 cat <<EOF >> "$SSHD_CONFIG"
184 HostKey ${MONKEYSPHERE_SYSDATADIR}/ssh_host_rsa_key
185 AuthorizedKeysFile ${MONKEYSPHERE_SYSDATADIR}/authorized_keys/%u
186 EOF
187
188
189 ######################################################################
190 ### SERVER HOST SETUP
191
192 # import host key
193 echo
194 echo "##################################################"
195 echo "### import host key..."
196 ssh-keygen -b 1024 -t rsa -N '' -f "$TEMPDIR"/ssh_host_rsa_key
197 monkeysphere-host import-key "$TEMPDIR"/ssh_host_rsa_key testhost
198
199 echo
200 echo "##################################################"
201 echo "### getting host key fingerprint..."
202 HOSTKEYID=$( monkeysphere-host show-key | grep '^OpenPGP fingerprint: ' | cut -f3 -d\  )
203 echo "$HOSTKEYID"
204
205 # change host key expiration
206 echo
207 echo "##################################################"
208 echo "### setting host key expiration..."
209 monkeysphere-host set-expire 1
210 # FIXME: how do we check that the expiration has really been set?
211
212 # certify host key with the "Admin's Key".
213 # (this would normally be done via keyservers)
214 echo
215 echo "##################################################"
216 echo "### certifying server host key..."
217 < "$MONKEYSPHERE_SYSCONFIGDIR"/ssh_host_rsa_key.pub.gpg gpgadmin --import
218 echo y | gpgadmin --command-fd 0 --sign-key "$HOSTKEYID"
219
220 # FIXME: add revoker?
221
222 # FIXME: how can we test publish-key without flooding junk into the
223 # keyservers?
224
225 # FIXME: should we run "diagnostics" here to test setup?
226
227
228 ######################################################################
229 ### SERVER AUTHENTICATION SETUP
230
231 # set up monkeysphere authentication
232 echo
233 echo "##################################################"
234 echo "### setup monkeysphere authentication..."
235 cp "$TESTDIR"/etc/monkeysphere/monkeysphere-authentication.conf "$TEMPDIR"/
236 cat <<EOF >> "$TEMPDIR"/monkeysphere-authentication.conf
237 AUTHORIZED_USER_IDS="$MONKEYSPHERE_HOME/authorized_user_ids"
238 EOF
239 monkeysphere-authentication setup
240 get_gpg_prng_arg >> "$MONKEYSPHERE_SYSDATADIR"/authentication/sphere/gpg.conf
241
242 # add admin as identity certifier for testhost
243 echo
244 echo "##################################################"
245 echo "### adding admin as certifier..."
246 monkeysphere-authentication add-id-certifier "$TEMPDIR"/admin/.gnupg/pubkey.gpg
247
248 echo
249 echo "##################################################"
250 echo "### list certifiers..."
251 monkeysphere-authentication list-certifiers
252
253 # FIXME: should we run "diagnostics" here to test setup?
254
255 ######################################################################
256 ### TESTUSER SETUP
257
258 # generate an auth subkey for the test user that expires in 2 days
259 echo
260 echo "##################################################"
261 echo "### generating key for testuser..."
262 monkeysphere gen-subkey
263
264 # add server key to testuser keychain
265 echo
266 echo "##################################################"
267 echo "### export server key to testuser..."
268 gpgadmin --armor --export "$HOSTKEYID" | gpg --import
269
270 # teach the "server" about the testuser's key
271 echo
272 echo "##################################################"
273 echo "### export testuser key to server..."
274 gpg --export testuser | monkeysphere-authentication gpg-cmd --import
275
276 # update authorized_keys for user
277 echo
278 echo "##################################################"
279 echo "### update server authorized_keys file for this testuser..."
280 monkeysphere-authentication update-users $(whoami)
281 # FIXME: this is maybe not failing properly for:
282 # ms: improper group or other writability on path '/tmp'.
283
284 ######################################################################
285 ### TESTS
286
287 # connect to test sshd, using monkeysphere ssh-proxycommand to verify
288 # the identity before connection.  This should work in both directions!
289 echo
290 echo "##################################################"
291 echo "### ssh connection test for success..."
292 ssh_test
293
294 # remove the testuser's authorized_user_ids file, update, and make
295 # sure that the ssh authentication FAILS
296 echo
297 echo "##################################################"
298 echo "### removing testuser authorized_user_ids and updating..."
299 mv "$TESTHOME"/.monkeysphere/authorized_user_ids{,.bak}
300 monkeysphere-authentication update-users $(whoami)
301 echo
302 echo "##################################################"
303 echo "### ssh connection test for failure..."
304 ssh_test 255
305 mv "$TESTHOME"/.monkeysphere/authorized_user_ids{.bak,}
306
307 # put improper permissions on authorized_user_ids file, update, and
308 # make sure ssh authentication FAILS
309 echo
310 echo "##################################################"
311 echo "### setting group writability on authorized_user_ids and updating..."
312 chmod g+w "$TESTHOME"/.monkeysphere/authorized_user_ids
313 monkeysphere-authentication update-users $(whoami)
314 echo
315 echo "##################################################"
316 echo "### ssh connection test for failure..."
317 ssh_test 255
318 chmod g-w "$TESTHOME"/.monkeysphere/authorized_user_ids
319 echo
320 echo "##################################################"
321 echo "### setting other writability on authorized_user_ids and updating..."
322 chmod o+w "$TESTHOME"/.monkeysphere/authorized_user_ids
323 monkeysphere-authentication update-users $(whoami)
324 echo
325 echo "##################################################"
326 echo "### ssh connection test for failure..."
327 ssh_test 255
328 chmod o-w "$TESTHOME"/.monkeysphere/authorized_user_ids
329 monkeysphere-authentication update-users $(whoami)
330
331 # test symlinks
332 echo
333 echo "##################################################"
334 echo "### setup for symlink tests..."
335 cp -a "$TESTHOME"/.monkeysphere{,.linktest}
336
337 echo
338 echo "##################################################"
339 echo "### make authorized_user_ids an absolute symlink and updating..."
340 mv "$TESTHOME"/.monkeysphere/authorized_user_ids{,.bak}
341 ln -s "$TESTHOME"/.monkeysphere{.linktest,}/authorized_user_ids
342 monkeysphere-authentication update-users $(whoami)
343 echo
344 echo "##################################################"
345 echo "### ssh connection test for success..."
346 ssh_test
347 echo
348 echo "##################################################"
349 echo "### create bad permissions on link dir and updating..."
350 chmod o+w "$TESTHOME"/.monkeysphere.linktest
351 monkeysphere-authentication update-users $(whoami)
352 echo
353 echo "##################################################"
354 echo "### ssh connection test for failure..."
355 ssh_test 255
356 chmod o-w "$TESTHOME"/.monkeysphere.linktest
357 echo
358 echo "##################################################"
359 echo "### make authorized_user_ids a relative symlink and updating..."
360 ln -sf ../.monkeysphere.linktest/authorized_user_ids "$TESTHOME"/.monkeysphere/authorized_user_ids
361 monkeysphere-authentication update-users $(whoami)
362 echo
363 echo "##################################################"
364 echo "### ssh connection test for success..."
365 ssh_test
366 echo
367 echo "##################################################"
368 echo "### create bad permissions on link dir updating..."
369 chmod o+w "$TESTHOME"/.monkeysphere.linktest
370 monkeysphere-authentication update-users $(whoami)
371 echo
372 echo "##################################################"
373 echo "### ssh connection test for failure..."
374 ssh_test 255
375 chmod o-w "$TESTHOME"/.monkeysphere.linktest
376 # FIXME: implement check of link path, and uncomment this test
377 # echo
378 # echo "##################################################"
379 # echo "### create bad permissions on link dir and updating..."
380 # chmod o+w "$TESTHOME"/.monkeysphere
381 # monkeysphere-authentication update-users $(whoami)
382 # echo
383 # echo "##################################################"
384 # echo "### ssh connection test for failure..."
385 # ssh_test 255
386 # chmod o-w "$TESTHOME"/.monkeysphere
387 rm "$TESTHOME"/.monkeysphere/authorized_user_ids
388 mv "$TESTHOME"/.monkeysphere/authorized_user_ids{.bak,}
389
390 echo
391 echo "##################################################"
392 echo "### make .monkeysphere directory an absolute symlink and updating..."
393 mv "$TESTHOME"/.monkeysphere{,.bak}
394 ln -s "$TESTHOME"/.monkeysphere{.linktest,}
395 monkeysphere-authentication update-users $(whoami)
396 echo
397 echo "##################################################"
398 echo "### ssh connection test for success..."
399 ssh_test
400 echo
401 echo "##################################################"
402 echo "### create bad permissions on link dir and updating..."
403 chmod o+w "$TESTHOME"/.monkeysphere.linktest
404 monkeysphere-authentication update-users $(whoami)
405 echo
406 echo "##################################################"
407 echo "### ssh connection test for failure..."
408 ssh_test 255
409 chmod o-w "$TESTHOME"/.monkeysphere.linktest
410 echo
411 echo "##################################################"
412 echo "### make .monkeysphere directory a relative symlink and updating..."
413 ln -sfn .monkeysphere{.linktest,}
414 monkeysphere-authentication update-users $(whoami)
415 echo
416 echo "##################################################"
417 echo "### ssh connection test for success..."
418 ssh_test
419 echo
420 echo "##################################################"
421 echo "### create bad permissions on link dir updating..."
422 chmod o+w "$TESTHOME"/.monkeysphere.linktest
423 monkeysphere-authentication update-users $(whoami)
424 echo
425 echo "##################################################"
426 echo "### ssh connection test for failure..."
427 ssh_test 255
428 chmod o-w "$TESTHOME"/.monkeysphere.linktest
429 rm "$TESTHOME"/.monkeysphere
430 mv "$TESTHOME"/.monkeysphere{.bak,}
431
432 # FIXME: addtest: remove admin as id-certifier and check ssh failure
433
434 # FIXME: addtest: add hostname on host key
435 # FIXME: addtest: revoke hostname on host key and check ssh failure
436
437 # addtest: revoke the host key and check ssh failure
438
439 # test to make sure things are OK after the previous tests:
440 echo
441 echo "##################################################"
442 echo "### settings reset, updating..."
443 monkeysphere-authentication update-users $(whoami)
444 echo
445 echo "##################################################"
446 echo "### ssh connection test for success..."
447 ssh_test
448
449 echo
450 echo "##################################################"
451 echo "### revoking host key..."
452 # generate the revocation certificate and feed it directly to the test
453 # user's keyring (we're not publishing to the keyservers)
454 monkeysphere-host revoke-key | gpg --import
455 echo
456 echo "##################################################"
457 echo "### ssh connection test for failure..."
458 ssh_test 255
459
460
461 ######################################################################
462
463 trap - EXIT
464
465 echo
466 echo "##################################################"
467 echo " Monkeysphere basic tests completed successfully!"
468 echo "##################################################"
469
470 cleanup