Fix keyboard-interactive authentication for ssh1. The problem was twofold:

- The PAM kbdint device sometimes doesn't know authentication succeeded
   until you re-query it.  The ssh1 kbdint code would never re-query the
   device, so authentication would always fail.  This patch has been
   submitted to the OpenSSH developers.

 - The monitor code for PAM sometimes forgot to tell the monitor that
   authentication had succeeded.  This caused the monitor to veto the
   privsep child's decision to allow the connection.

These patches have been tested with OpenSSH clients on -STABLE, NetBSD and
Linux, and with ssh.com's ssh1 on Solaris.

Sponsored by:	DARPA, NAI Labs
This commit is contained in:
Dag-Erling Smørgrav 2003-01-31 11:08:07 +00:00
parent f6f38550e6
commit 07fd326c9c
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=110138
2 changed files with 21 additions and 0 deletions

View File

@ -24,6 +24,7 @@
#include "includes.h"
RCSID("$OpenBSD: auth-chall.c,v 1.8 2001/05/18 14:13:28 markus Exp $");
RCSID("$FreeBSD$");
#include "auth.h"
#include "log.h"
@ -76,6 +77,24 @@ verify_response(Authctxt *authctxt, const char *response)
return 0;
resp[0] = (char *)response;
res = device->respond(authctxt->kbdintctxt, 1, resp);
if (res == 1) {
/* postponed - send a null query just in case */
char *name, *info, **prompts;
u_int i, numprompts, *echo_on;
res = device->query(authctxt->kbdintctxt, &name, &info,
&numprompts, &prompts, &echo_on);
if (res == 0) {
for (i = 0; i < numprompts; i++)
xfree(prompts[i]);
xfree(prompts);
xfree(name);
xfree(echo_on);
xfree(info);
}
/* if we received more prompts, we're screwed */
res = (numprompts != 0);
}
device->free_ctx(authctxt->kbdintctxt);
authctxt->kbdintctxt = NULL;
return res ? 0 : 1;

View File

@ -797,6 +797,8 @@ mm_answer_pam_query(int socket, Buffer *m)
debug3("%s", __func__);
pam_authok = NULL;
ret = (pam_device.query)(pam_ctxt, &name, &info, &num, &prompts, &echo_on);
if (ret == 0 && num == 0)
pam_authok = pam_ctxt;
if (num > 1 || name == NULL || info == NULL)
ret = -1;
buffer_clear(m);