[RFC PATCH 4/4] pam-ssh-agent: Add authenticating the SSH agent

[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]

 



The two key sets, agent and auth, are compared. The matching keys are
used to challenge the agent in signing some random data. The first
positive proof immediately ends the verification with a success.

Tests verify the correct behavior with different auth files. A full
round with all the supported key types is also performed.

Signed-off-by: Domenico Andreoli <domenico.andreoli@xxxxxxxxx>

---
 pam-ssh-agent.c          |   33 ++++++++++++++++++++++++++++++++-
 regress/pam-ssh-agent.sh |   23 +++++++++++++++++++++++
 2 files changed, 55 insertions(+), 1 deletion(-)

Index: b/pam-ssh-agent.c
===================================================================
--- a/pam-ssh-agent.c
+++ b/pam-ssh-agent.c
@@ -38,6 +38,7 @@
 #include "authfile.h"
 #include "authfd.h"
 #include "ssherr.h"
+#include "sshkey.h"
 #include "ssh.h"
 
 static int pam_debug;
@@ -95,6 +96,36 @@ out:
 	return r;
 }
 
+static int
+challenge_agent(int agent_fd, const struct sshkey *agent_key, const struct sshkey *auth_key)
+{
+	u_char *sig = NULL;
+	size_t slen = 0;
+	char data[1024];
+	int ret;
+
+	arc4random_buf(data, sizeof(data));
+	ret = ssh_agent_sign(agent_fd, agent_key, &sig, &slen, data, sizeof(data), NULL, 0) ||
+	      sshkey_verify(auth_key, sig, slen, data, sizeof(data), NULL, 0, NULL);
+
+	if (sig != NULL)
+		free(sig);
+	return !ret;
+}
+
+static int
+authenticate_agent(int agent_fd, const struct ssh_identitylist *agent_ids,
+	const struct ssh_identitylist *auth_ids)
+{
+	unsigned i, j;
+	for (i=0; i!=agent_ids->nkeys; i++)
+		for (j=0; j!=auth_ids->nkeys; j++)
+			if (sshkey_equal(agent_ids->keys[i], auth_ids->keys[j]))
+				if (challenge_agent(agent_fd, agent_ids->keys[i], auth_ids->keys[j]))
+					return PAM_SUCCESS;
+	return PAM_AUTH_ERR;
+}
+
 int
 pam_sm_authenticate(pam_handle_t *pamh, int flags, int argc, const char **argv)
 {
@@ -161,7 +192,7 @@ pam_sm_authenticate(pam_handle_t *pamh,
 			syslog(LOG_DEBUG, "  %d) %s", i, agent_ids->comments[i]);
 	}
 
-	ret = PAM_SUCCESS;
+	ret = authenticate_agent(agent_fd, agent_ids, auth_ids);
 
 out:
 	if (agent_fd != -1)
Index: b/regress/pam-ssh-agent.sh
===================================================================
--- a/regress/pam-ssh-agent.sh
+++ b/regress/pam-ssh-agent.sh
@@ -20,7 +20,9 @@ PAM_AUTHINFO_UNAVAIL=9
 . $OBJ/keytype_gen.sh
 
 first_kt=`echo $ktypes | cut -d" " -f1`
+second_kt=`echo $ktypes | cut -d" " -f2`
 AUTH_FILE=$OBJ/key.$first_kt.pub
+AUTH_FILE2=$OBJ/key.$second_kt.pub
 
 pam_agent_test()
 {
@@ -73,6 +75,27 @@ expect=$PAM_SUCCESS           pam_agent_
 trace "authenticate agent (non-debug)"
 expect=$PAM_SUCCESS           pam_agent_test file=$AUTH_FILE
 
+trace "change of auth file (debug)"
+expect=$PAM_AUTH_ERR          pam_agent_test file=$AUTH_FILE2 debug
+
+trace "change of auth file (non-debug)"
+expect=$PAM_AUTH_ERR          pam_agent_test file=$AUTH_FILE2
+
+for kt in $ktypes; do
+	trace "load key $kt into the agent"
+	${SSHADD} -q $OBJ/key.$kt
+	r=$?
+	if [ $r -ne 0 ]; then
+		fatal "could not add the key: exit code $r"
+	fi
+
+	trace "authenticate agent with $kt (debug)"
+	expect=$PAM_SUCCESS       pam_agent_test file=$OBJ/key.$kt.pub debug
+
+	trace "authenticate agent with $kt (non-debug)"
+	expect=$PAM_SUCCESS       pam_agent_test file=$OBJ/key.$kt.pub
+done
+
 trace "kill agent"
 ${SSHAGENT} -k > /dev/null
 

_______________________________________________
openssh-unix-dev mailing list
openssh-unix-dev@xxxxxxxxxxx
https://lists.mindrot.org/mailman/listinfo/openssh-unix-dev



[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]

[Index of Archives]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux]     [Linux OMAP]     [Linux MIPS]     [ECOS]     [Asterisk Internet PBX]     [Linux API]

  Powered by Linux