diff --git a/ChangeLog b/ChangeLog index 3e9e55e39..d902bd62f 100644 --- a/ChangeLog +++ b/ChangeLog @@ -7,6 +7,7 @@ [deattack.c] so that large packets do not wrap "n"; from netbsd - (bal) rijndel.c - fix up RCSID to match OpenBSD tree + - (bal) auth2-skey.c - Checked in. Missing from portable tree 20001029 - (stevesk) Fix typo in auth.c: USE_PAM not PAM diff --git a/Makefile.in b/Makefile.in index 03c745914..c55352635 100644 --- a/Makefile.in +++ b/Makefile.in @@ -41,7 +41,7 @@ LIBOPENBSD_COMPAT_OBJS=bsd-arc4random.o bsd-base64.o bsd-bindresvport.o bsd-daem SSHOBJS= ssh.o sshconnect.o sshconnect1.o sshconnect2.o log-client.o readconf.o clientloop.o -SSHDOBJS= sshd.o auth.o auth1.o auth2.o auth-rhosts.o auth-options.o auth-krb4.o auth-pam.o auth-passwd.o auth-rsa.o auth-rh-rsa.o dh.o pty.o log-server.o login.o loginrec.o servconf.o serverloop.o md5crypt.o session.o +SSHDOBJS= sshd.o auth.o auth1.o auth2.o auth2-skey.o auth-rhosts.o auth-options.o auth-krb4.o auth-pam.o auth-passwd.o auth-rsa.o auth-rh-rsa.o dh.o pty.o log-server.o login.o loginrec.o servconf.o serverloop.o md5crypt.o session.o TROFFMAN = scp.1 ssh-add.1 ssh-agent.1 ssh-keygen.1 ssh.1 sshd.8 sftp-server.8 CATMAN = scp.0 ssh-add.0 ssh-agent.0 ssh-keygen.0 ssh.0 sshd.0 sftp-server.0 diff --git a/auth2-skey.c b/auth2-skey.c new file mode 100644 index 000000000..e29205d4b --- /dev/null +++ b/auth2-skey.c @@ -0,0 +1,107 @@ +#include "includes.h" +RCSID("$OpenBSD: auth2-skey.c,v 1.1 2000/10/11 20:14:38 markus Exp $"); + +#ifdef SKEY +#include "ssh.h" +#include "ssh2.h" +#include "auth.h" +#include "packet.h" +#include "xmalloc.h" +#include "dispatch.h" + +void send_userauth_into_request(Authctxt *authctxt, int echo); +void input_userauth_info_response(int type, int plen, void *ctxt); + +/* + * try skey authentication, always return -1 (= postponed) since we have to + * wait for the s/key response. + */ +int +auth2_skey(Authctxt *authctxt) +{ + send_userauth_into_request(authctxt, 0); + dispatch_set(SSH2_MSG_USERAUTH_INFO_RESPONSE, &input_userauth_info_response); + return -1; +} + +void +send_userauth_into_request(Authctxt *authctxt, int echo) +{ + int retval = -1; + struct skey skey; + char challenge[SKEY_MAX_CHALLENGE]; + char *fake; + + if (authctxt->user == NULL) + fatal("send_userauth_into_request: internal error: no user"); + + /* get skey challenge */ + if (authctxt->valid) + retval = skeychallenge(&skey, authctxt->user, challenge); + + if (retval == -1) { + fake = skey_fake_keyinfo(authctxt->user); + strlcpy(challenge, fake, sizeof challenge); + } + /* send our info request */ + packet_start(SSH2_MSG_USERAUTH_INFO_REQUEST); + packet_put_cstring("S/Key Authentication"); /* Name */ + packet_put_cstring(challenge); /* Instruction */ + packet_put_cstring(""); /* Language */ + packet_put_int(1); /* Number of prompts */ + packet_put_cstring(echo ? + "Response [Echo]: ": "Response: "); /* Prompt */ + packet_put_char(echo); /* Echo */ + packet_send(); + packet_write_wait(); + memset(challenge, 'c', sizeof challenge); +} + +void +input_userauth_info_response(int type, int plen, void *ctxt) +{ + Authctxt *authctxt = ctxt; + int authenticated = 0; + unsigned int nresp, rlen; + char *resp, *method; + + if (authctxt == NULL) + fatal("input_userauth_info_response: no authentication context"); + + if (authctxt->attempt++ >= AUTH_FAIL_MAX) + packet_disconnect("too many failed userauth_requests"); + + nresp = packet_get_int(); + if (nresp == 1) { + /* we only support s/key and assume s/key for nresp == 1 */ + method = "s/key"; + resp = packet_get_string(&rlen); + packet_done(); + if (strlen(resp) == 0) { + /* + * if we received a null response, resend prompt with + * echo enabled + */ + authenticated = -1; + userauth_log(authctxt, authenticated, method); + send_userauth_into_request(authctxt, 1); + } else { + /* verify skey response */ + if (authctxt->valid && + skey_haskey(authctxt->pw->pw_name) == 0 && + skey_passcheck(authctxt->pw->pw_name, resp) != -1) { + authenticated = 1; + } else { + authenticated = 0; + } + memset(resp, 'r', rlen); + /* unregister callback */ + dispatch_set(SSH2_MSG_USERAUTH_INFO_RESPONSE, NULL); + userauth_log(authctxt, authenticated, method); + userauth_reply(authctxt, authenticated); + } + xfree(resp); + } +} + +#endif /* SKEY */