From 4793624c65673268128fb0146cd9bd1b3cfeb6c4 Mon Sep 17 00:00:00 2001 From: Jameson Graef Rollins Date: Tue, 10 Jun 2008 17:17:51 -0400 Subject: New client/server components: - broke out all common functions to "common" file - put all client commands into "monkeysphere" script - put all server commands into "monkeysphere-server" script - moved all code into src directory to clean things up a bit - this effectively makes obsolete rhesus and howler - added proposed monkeysphere-ssh-proxycommand script that can be called to update known_hosts from ssh ProxyCommand - updated monkeysphere.conf to work as global client config - added monkeysphere-server.conf for server config --- src/monkeysphere-ssh-proxycommand | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100755 src/monkeysphere-ssh-proxycommand (limited to 'src/monkeysphere-ssh-proxycommand') diff --git a/src/monkeysphere-ssh-proxycommand b/src/monkeysphere-ssh-proxycommand new file mode 100755 index 0000000..1724966 --- /dev/null +++ b/src/monkeysphere-ssh-proxycommand @@ -0,0 +1,16 @@ +#!/bin/sh -e + +# MonkeySphere ssh ProxyCommand hook +# Proxy command script to initiate a monkeysphere known_hosts update +# before an ssh connection to host is established. +# Can be added to ~/.ssh/config as follows: +# ProxyCommand monkeysphere-ssh-proxycommand %h %p + +HOST="$1" +PORT="$2" + +# update the known_hosts file for the host +monkeysphere update-known-hosts "$HOST" + +# make a netcat connection to host for the ssh connection +exec nc "$HOST" "$PORT" -- cgit v1.2.3 From be186e427ac34812e2b2a55489ae55fe2341f6a0 Mon Sep 17 00:00:00 2001 From: Jameson Graef Rollins Date: Tue, 10 Jun 2008 18:38:46 -0400 Subject: Cleaned/fix up update-userid function. also some general cleanup. --- src/common | 40 ++++++++++++++++++++++++++++++++ src/monkeysphere | 31 +++++++++++++++---------- src/monkeysphere-server | 49 +++++++++++++++++---------------------- src/monkeysphere-ssh-proxycommand | 19 ++++++++++----- 4 files changed, 93 insertions(+), 46 deletions(-) (limited to 'src/monkeysphere-ssh-proxycommand') diff --git a/src/common b/src/common index 8643080..073b8af 100755 --- a/src/common +++ b/src/common @@ -351,3 +351,43 @@ process_authorized_ids() { process_user_id "$userID" "$cacheDir" > /dev/null done } + +# update the cache for userid, and prompt to add file to +# authorized_user_ids file if the userid is found in gpg +# and not already in file. +update_userid() { + local userID + local cacheDir + local userIDKeyCache + + userID="$1" + cacheDir="$2" + + log "processing userid: '$userID'" + userIDKeyCache=$(process_user_id "$userID" "$cacheDir") + if [ -z "$userIDKeyCache" ] ; then + return 1 + fi + if ! grep -q "^${userID}\$" "$AUTHORIZED_USER_IDS" ; then + echo "the following userid is not in the authorized_user_ids file:" + echo " $userID" + read -p "would you like to add? [Y|n]: " OK; OK=${OK:=Y} + if [ ${OK/y/Y} = 'Y' ] ; then + log -n " adding userid to authorized_user_ids file... " + echo "$userID" >> "$AUTHORIZED_USER_IDS" + echo "done." + fi + fi +} + +# retrieve key from web of trust, and set owner trust to "full" +# if key is found. +trust_key() { + # get the key from the key server + gpg --keyserver "$KEYSERVER" --recv-key "$keyID" || failure "could not retrieve key '$keyID'" + + # edit the key to change trust + # FIXME: need to figure out how to automate this, + # in a batch mode or something. + gpg --edit-key "$keyID" +} diff --git a/src/monkeysphere b/src/monkeysphere index f279d86..d652ab3 100755 --- a/src/monkeysphere +++ b/src/monkeysphere @@ -1,5 +1,13 @@ #!/bin/sh +# monkeysphere: MonkeySphere client tool +# +# The monkeysphere scripts are written by: +# Jameson Rollins +# +# They are Copyright 2008, and are all released under the GPL, version 3 +# or later. + ######################################################################## PGRM=$(basename $0) @@ -26,11 +34,11 @@ usage: $PGRM [args] Monkeysphere client tool. subcommands: - update-known-hosts (k) [HOST]... update known_hosts file - update-authorized-keys (a) update authorized_keys file - update-userid (u) [USERID]... add/update userid to - authorized_user_ids - help (h,?) this help + update-known-hosts (k) [HOST]... update known_hosts file + update-authorized-keys (a) update authorized_keys file + update-userids (u) [USERID]... add/update userid + gen-ae-subkey (g) generate an 'ae' capable subkey + help (h,?) this help EOF } @@ -129,20 +137,19 @@ case $COMMAND in log "$msAuthorizedKeys" ;; - 'update-userid'|'u') + 'update-userids'|'u') if [ -z "$1" ] ; then failure "you must specify at least one userid." fi for userID ; do - if ! grep -q "^${userID}\$" "$AUTHORIZED_USER_IDS" ; then - log "userid '$userID' not in authorized_user_ids file." - continue - fi - log "processing user id: '$userID'" - process_user_id "$userID" "$userKeysCacheDir" > /dev/null + update_userid "$userID" "$userKeysCacheDir" done ;; + 'gen-ae-subkey'|) + failure "function not implemented yet." + ;; + 'help'|'h'|'?') usage ;; diff --git a/src/monkeysphere-server b/src/monkeysphere-server index f1b4892..fd7b583 100755 --- a/src/monkeysphere-server +++ b/src/monkeysphere-server @@ -1,5 +1,13 @@ #!/bin/sh +# monkeysphere-server: MonkeySphere server admin tool +# +# The monkeysphere scripts are written by: +# Jameson Rollins +# +# They are Copyright 2008, and are all released under the GPL, version 3 +# or later. + ######################################################################## PGRM=$(basename $0) @@ -23,12 +31,12 @@ usage: $PGRM [args] Monkeysphere server admin tool. subcommands: - update-users (s) [USER]... update authorized_keys file - gen-key (g) generate gpg key for the host - publish-key (p) publish host gpg to keyserver - trust-key (t) KEYID [KEYID]... mark keyid as trusted - update-user-userid (u) USER UID [UID]... add/update userid for user - help (h,?) this help + update-users (s) [USER]... update user authorized_keys file + gen-key (g) generate gpg key for the server + publish-key (p) publish server gpg to keyserver + trust-key (t) KEYID [KEYID]... mark keyid as trusted + update-user-userids (u) USER UID [UID]... add/update userid for user + help (h,?) this help EOF } @@ -85,19 +93,6 @@ publish_key() { echo "gpg --send-keys --keyserver $KEYSERVER $keyID" } -# trust key -trust_key() { - for keyID ; do - # get the key from the key server - gpg --keyserver "$KEYSERVER" --recv-key "$keyID" || failure "could not retrieve key '$keyID'" - - # edit the key to change trust - # FIXME: need to figure out how to automate this, - # in a batch mode or something. - gpg --edit-key "$keyID" - done -} - ######################################################################## # MAIN ######################################################################## @@ -185,10 +180,12 @@ case $COMMAND in if [ -z "$1" ] ; then failure "you must specify at least one key to trust." fi - trust_key "$@" + for keyID ; do + trust_key "$keyID" + done ;; - 'update-user-userid'|'u') + 'update-user-userids'|'u') uname="$1" shift if [ -z "$uname" ] ; then @@ -197,14 +194,10 @@ case $COMMAND in if [ -z "$1" ] ; then failure "you must specify at least one userid." fi + AUTHORIZED_USER_IDS="$MS_HOME"/authorized_user_ids/"$uname" + userKeysCacheDir="$STAGING_AREA"/"$uname"/user_keys for userID ; do - AUTHORIZED_USER_IDS="$MS_HOME"/authorized_user_ids/"$uname" - if ! grep -q "^${userID}\$" "$AUTHORIZED_USER_IDS" ; then - log "userid '$userID' not in authorized_user_ids file." - continue - fi - log "processing user id: '$userID'" - process_user_id "$userID" "$userKeysCacheDir" > /dev/null + update_userid "$userID" "$userKeysCacheDir" done ;; diff --git a/src/monkeysphere-ssh-proxycommand b/src/monkeysphere-ssh-proxycommand index 1724966..417d013 100755 --- a/src/monkeysphere-ssh-proxycommand +++ b/src/monkeysphere-ssh-proxycommand @@ -1,10 +1,17 @@ #!/bin/sh -e -# MonkeySphere ssh ProxyCommand hook -# Proxy command script to initiate a monkeysphere known_hosts update -# before an ssh connection to host is established. -# Can be added to ~/.ssh/config as follows: -# ProxyCommand monkeysphere-ssh-proxycommand %h %p +# monkeysphere-ssh-proxycommand: MonkeySphere ssh ProxyCommand hook +# +# The monkeysphere scripts are written by: +# Jameson Rollins +# +# They are Copyright 2008, and are all released under the GPL, version 3 +# or later. + +# This is meant to be run as an ssh ProxyCommand to initiate a +# monkeysphere known_hosts update before an ssh connection to host is +# established. Can be added to ~/.ssh/config as follows: +# ProxyCommand monkeysphere-ssh-proxycommand %h %p HOST="$1" PORT="$2" @@ -12,5 +19,5 @@ PORT="$2" # update the known_hosts file for the host monkeysphere update-known-hosts "$HOST" -# make a netcat connection to host for the ssh connection +# exec a netcat passthrough to host for the ssh connection exec nc "$HOST" "$PORT" -- cgit v1.2.3 From bb17921883afe6edfeaa029d2113baebf10b7b92 Mon Sep 17 00:00:00 2001 From: Jameson Graef Rollins Date: Mon, 16 Jun 2008 14:07:33 -0400 Subject: Allow for specification of whether to check keyserver. Update proxy command to check keyserver if host not found in known_hosts. --- src/monkeysphere-ssh-proxycommand | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) (limited to 'src/monkeysphere-ssh-proxycommand') diff --git a/src/monkeysphere-ssh-proxycommand b/src/monkeysphere-ssh-proxycommand index 417d013..ec162ab 100755 --- a/src/monkeysphere-ssh-proxycommand +++ b/src/monkeysphere-ssh-proxycommand @@ -16,6 +16,36 @@ HOST="$1" PORT="$2" +usage() { +cat <&2 +usage: ssh -o ProxyCommand="$(basename $0) %h %p" ... +EOF +} + +log() { + echo "$@" >&2 +} + +if [ -z "$HOST" ] ; then + log "host must be specified." + usage + exit 1 +fi +if [ -z "$PORT" ] ; then + log "port must be specified." + usage + exit 1 +fi + +# check for the host key in the known_hosts file +hostKey=$(ssh-keygen -F "$HOST") + +# if the host key is not found in the known_hosts file, +# check the keyserver +if [ -z "$hostKey" ] ; then + CHECK_KEYSERVER="true" +fi + # update the known_hosts file for the host monkeysphere update-known-hosts "$HOST" -- cgit v1.2.3 From b6983d7cb86f450ebd7fafcb254011fd7099c246 Mon Sep 17 00:00:00 2001 From: Jameson Graef Rollins Date: Mon, 16 Jun 2008 14:07:33 -0400 Subject: Allow for specification of whether to check keyserver. Update proxy command to check keyserver if host not found in known_hosts. --- src/common | 40 +++++++++++++++++++++++++-------------- src/monkeysphere | 2 +- src/monkeysphere-ssh-proxycommand | 30 +++++++++++++++++++++++++++++ 3 files changed, 57 insertions(+), 15 deletions(-) (limited to 'src/monkeysphere-ssh-proxycommand') diff --git a/src/common b/src/common index 8d8e506..471e75a 100644 --- a/src/common +++ b/src/common @@ -43,12 +43,22 @@ cutline() { # FIXME: need to figure out how to retrieve all matching keys # (not just first 5) gpg_fetch_userid() { - local id - id="$1" - echo 1,2,3,4,5 | \ - gpg --quiet --batch --command-fd 0 --with-colons \ - --keyserver "$KEYSERVER" \ - --search ="$id" >/dev/null 2>&1 + local userID + + userID="$1" + + # if CHECK_KEYSERVER variable set, check the keyserver + # for the user ID + if [ "CHECK_KEYSERVER" ] ; then + echo 1,2,3,4,5 | \ + gpg --quiet --batch --command-fd 0 --with-colons \ + --keyserver "$KEYSERVER" \ + --search ="$userID" >/dev/null 2>&1 + + # otherwise just return true + else + return + fi } # check that characters are in a string (in an AND fashion). @@ -117,7 +127,7 @@ gpg2authorized_keys() { gpg --export "$keyID" | \ openpgp2ssh "$keyID" | tr -d '\n' - echo " MonkeySphere${DATE}:${userID}" + echo " MonkeySphere${DATE}: ${userID}" } # userid and key policy checking @@ -296,18 +306,23 @@ update_userid() { log "processing userid: '$userID'" + # return 1 if there is no output of the user ID processing + # ie. no key was found keyCachePath=$(process_user_id "$userID" "$cacheDir") - if [ -z "$keyCachePath" ] ; then return 1 fi + + # check if user ID is in the authorized_user_ids file if ! grep -q "^${userID}\$" "$AUTHORIZED_USER_IDS" ; then read -p "user ID not currently authorized. authorize? [Y|n]: " OK; OK=${OK:=Y} if [ ${OK/y/Y} = 'Y' ] ; then + # add if specified log -n "adding user ID to authorized_user_ids file... " echo "$userID" >> "$AUTHORIZED_USER_IDS" echo "done." else + # else do nothing log "authorized_user_ids file untouched." fi fi @@ -340,7 +355,7 @@ process_host() { host="$1" cacheDir="$2" - log "processing host: '$host'" + log "processing host: $host" keyCachePath=$(process_user_id "ssh://${host}" "$cacheDir") if [ $? = 0 ] ; then @@ -353,18 +368,15 @@ process_host() { # go through line-by-line, extract each host, and process with the # host processing function process_known_hosts() { - local knownHosts local cacheDir local hosts local host - knownHosts="$1" - cacheDir="$2" + cacheDir="$1" # take all the hosts from the known_hosts file (first field), # grep out all the hashed hosts (lines starting with '|')... - cut -d ' ' -f 1 "$knownHosts" | \ - grep -v '^|.*$' | \ + meat "$USER_KNOWN_HOSTS" | cut -d ' ' -f 1 | grep -v '^|.*$' | \ while IFS=, read -r -a hosts ; do # ...and process each host for host in ${hosts[*]} ; do diff --git a/src/monkeysphere b/src/monkeysphere index 23ebd63..79bc352 100755 --- a/src/monkeysphere +++ b/src/monkeysphere @@ -157,7 +157,7 @@ case $COMMAND in failure "known_hosts file '$USER_KNOWN_HOSTS' is empty." fi log "processing known_hosts file..." - process_known_hosts "$USER_KNOWN_HOSTS" "$hostKeysCacheDir" + process_known_hosts "$hostKeysCacheDir" fi ;; diff --git a/src/monkeysphere-ssh-proxycommand b/src/monkeysphere-ssh-proxycommand index 417d013..ec162ab 100755 --- a/src/monkeysphere-ssh-proxycommand +++ b/src/monkeysphere-ssh-proxycommand @@ -16,6 +16,36 @@ HOST="$1" PORT="$2" +usage() { +cat <&2 +usage: ssh -o ProxyCommand="$(basename $0) %h %p" ... +EOF +} + +log() { + echo "$@" >&2 +} + +if [ -z "$HOST" ] ; then + log "host must be specified." + usage + exit 1 +fi +if [ -z "$PORT" ] ; then + log "port must be specified." + usage + exit 1 +fi + +# check for the host key in the known_hosts file +hostKey=$(ssh-keygen -F "$HOST") + +# if the host key is not found in the known_hosts file, +# check the keyserver +if [ -z "$hostKey" ] ; then + CHECK_KEYSERVER="true" +fi + # update the known_hosts file for the host monkeysphere update-known-hosts "$HOST" -- cgit v1.2.3 From 62ff87e0328bc1406979656029a5e313839cac35 Mon Sep 17 00:00:00 2001 From: Jameson Graef Rollins Date: Mon, 16 Jun 2008 14:52:20 -0400 Subject: Add log output for keyserver checking. Fix bug in proxy command to export CHECK_KEYSERVER variable. --- src/common | 31 +++++++++++++++++-------------- src/monkeysphere | 1 + src/monkeysphere-ssh-proxycommand | 9 +++++---- 3 files changed, 23 insertions(+), 18 deletions(-) (limited to 'src/monkeysphere-ssh-proxycommand') diff --git a/src/common b/src/common index c0a9030..d1554a6 100644 --- a/src/common +++ b/src/common @@ -47,17 +47,17 @@ gpg_fetch_userid() { userID="$1" - # if CHECK_KEYSERVER variable set, check the keyserver - # for the user ID - if [ "CHECK_KEYSERVER" ] ; then - echo 1,2,3,4,5 | \ - gpg --quiet --batch --command-fd 0 --with-colons \ - --keyserver "$KEYSERVER" \ - --search ="$userID" >/dev/null 2>&1 - - # otherwise just return true + log "checking keyserver $KEYSERVER..." + echo 1,2,3,4,5 | \ + gpg --quiet --batch --command-fd 0 --with-colons \ + --keyserver "$KEYSERVER" \ + --search ="$userID" >/dev/null 2>&1 + if [ "$?" = 0 ] ; then + log " user ID found on keyserver." + return 0 else - return + log " user ID not found on keyserver." + return 1 fi } @@ -167,8 +167,11 @@ process_user_id() { fi requiredPubCapability=$(echo "$requiredCapability" | tr "[:lower:]" "[:upper:]") - # fetch keys from keyserver, return 1 if none found - gpg_fetch_userid "$userID" || return 1 + # if CHECK_KEYSERVER variable set, check the keyserver + # for the user ID + if [ "$CHECK_KEYSERVER" = "true" ] ; then + gpg_fetch_userid "$userID" + fi # output gpg info for (exact) userid and store gpgOut=$(gpg --fixed-list-mode --list-key --with-colons \ @@ -176,7 +179,7 @@ process_user_id() { # return 1 if there only "tru" lines are output from gpg if [ -z "$(echo "$gpgOut" | grep -v '^tru:')" ] ; then - log " key not found." + log " key not found in keychain." return 1 fi @@ -268,7 +271,7 @@ process_user_id() { # key cache file if [ "$keyOK" -a "$uidOK" -a "${keyIDs[*]}" ] ; then for keyID in ${keyIDs[@]} ; do - log " acceptable key/uid found." + log " acceptable key/userID found." if [ "$MODE" = 'known_hosts' ] ; then # export the key diff --git a/src/monkeysphere b/src/monkeysphere index a6ca62d..230de06 100755 --- a/src/monkeysphere +++ b/src/monkeysphere @@ -113,6 +113,7 @@ MS_CONF=${MS_CONF:-"${MS_HOME}/monkeysphere.conf"} AUTHORIZED_USER_IDS=${AUTHORIZED_USER_IDS:-"${MS_HOME}/authorized_user_ids"} GNUPGHOME=${GNUPGHOME:-"${HOME}/.gnupg"} KEYSERVER=${KEYSERVER:-"subkeys.pgp.net"} +CHECK_KEYSERVER=${CHECK_KEYSERVER:="true"} REQUIRED_HOST_KEY_CAPABILITY=${REQUIRED_HOST_KEY_CAPABILITY:-"e a"} REQUIRED_USER_KEY_CAPABILITY=${REQUIRED_USER_KEY_CAPABILITY:-"a"} USER_CONTROLLED_AUTHORIZED_KEYS=${USER_CONTROLLED_AUTHORIZED_KEYS:-"${HOME}/.ssh/authorized_keys"} diff --git a/src/monkeysphere-ssh-proxycommand b/src/monkeysphere-ssh-proxycommand index ec162ab..3887e48 100755 --- a/src/monkeysphere-ssh-proxycommand +++ b/src/monkeysphere-ssh-proxycommand @@ -40,11 +40,12 @@ fi # check for the host key in the known_hosts file hostKey=$(ssh-keygen -F "$HOST") -# if the host key is not found in the known_hosts file, -# check the keyserver -if [ -z "$hostKey" ] ; then - CHECK_KEYSERVER="true" +# if the host key is found in the known_hosts file, +# don't check the keyserver +if [ "$hostKey" ] ; then + CHECK_KEYSERVER="false" fi +export CHECK_KEYSERVER # update the known_hosts file for the host monkeysphere update-known-hosts "$HOST" -- cgit v1.2.3