From d170d0d4d448987dcd74ce919f76fc834acd399c Mon Sep 17 00:00:00 2001 From: "Eric S. Raymond" Date: Tue, 20 Feb 2001 05:15:42 +0000 Subject: More authentication types. svn path=/trunk/; revision=3130 --- NEWS | 2 ++ conf.c | 4 +++ fetchmail.h | 14 ++++++---- fetchmail.man | 28 ++++++++++--------- pop3.c | 89 ++++++++++++++++++++++++++++------------------------------- 5 files changed, 71 insertions(+), 66 deletions(-) diff --git a/NEWS b/NEWS index 97e97453..6e1a40ab 100644 --- a/NEWS +++ b/NEWS @@ -5,6 +5,8 @@ * `preauth' option changed back to `auth' * IMAP code now bails out if the server forces the mailbox read-only. * Fixed a core dump in Dave Zarzycki's new plugin code. +* POP3 latency optimization: only do CAPA and set authentication capabilities + from it once at start of run. fetchmail-5.6.7 (Mon Feb 19 12:31:03 EST 2001), 20082 lines: diff --git a/conf.c b/conf.c index 3f6e7af1..4b43b674 100644 --- a/conf.c +++ b/conf.c @@ -275,6 +275,10 @@ void dump_config(struct runctl *runp, struct query *querylist) stringdump("auth", "any"); else if (ctl->server.authenticate == A_PASSWORD) stringdump("auth", "password"); + else if (ctl->server.authenticate == A_OTP) + stringdump("auth", "otp"); + else if (ctl->server.authenticate == A_CRAM_MD5) + stringdump("auth", "cram-md5"); else if (ctl->server.authenticate == A_GSSAPI) stringdump("auth", "gssapi"); else if (ctl->server.authenticate == A_KERBEROS_V4) diff --git a/fetchmail.h b/fetchmail.h index e78e2121..3c7d4b9b 100644 --- a/fetchmail.h +++ b/fetchmail.h @@ -39,14 +39,16 @@ /* authentication types */ #define A_ANY 0 /* use the first method that works */ -#define A_PASSWORD 1 /* password or inline authentication */ -#define A_KERBEROS_V4 2 /* authenticate w/ Kerberos V4 */ -#define A_KERBEROS_V5 3 /* authenticate w/ Kerberos V5 */ -#define A_GSSAPI 4 /* authenticate with GSSAPI */ -#define A_SSH 5 /* authentication at session level */ +#define A_PASSWORD 1 /* password authentication */ +#define A_CRAM_MD5 2 /* CRAM-MD5 shrouding (RFC2195) */ +#define A_OTP 3 /* One-time password (RFC1508) */ +#define A_KERBEROS_V4 4 /* authenticate w/ Kerberos V4 */ +#define A_KERBEROS_V5 5 /* authenticate w/ Kerberos V5 */ +#define A_GSSAPI 6 /* authenticate with GSSAPI */ +#define A_SSH 7 /* authentication at session level */ /* some protocols (KERBEROS, GSSAPI, SSH) don't require a password */ -#define NO_PASSWORD(ctl) ((ctl)->server.authenticate > A_PASSWORD || !MAILBOX_PROTOCOL(ctl)) +#define NO_PASSWORD(ctl) ((ctl)->server.authenticate > A_OTP || !MAILBOX_PROTOCOL(ctl)) /* * Definitions for buffer sizes. We get little help on setting maxima diff --git a/fetchmail.man b/fetchmail.man index 5342b8a5..9de9e9c9 100644 --- a/fetchmail.man +++ b/fetchmail.man @@ -502,19 +502,21 @@ when interface data is being collected. This option permits you to specify an authentication type (see USER AUTHENTICATION below for details). The possible values are \fBany\fR, \&`\fBpassword\fR', `\fBkerberos_v5\fR' and `\fBkerberos\fR' (or, for -excruciating exactness, `\fBkerberos_v4\fR'), \fRgssapi\fR, and -\fBssh\fR. When \fBany\fR (the default) is specified, fetchmail tries -first methods that don't require a password (GSSAPI, KERBEROS_IV); -then it looks for methods that mask your password (CRAM-MD5, X-OTP); -and only if it the server doesn't support any of those will it ship -your password en clair. Other values may be used to force various -authentication methods (\fBssh\fR suppresses authentication). Any -value other than "password" suppresses fetchmail's normal inquiry for -a password. Specify \fBssh\fR when you are using an end-to-end secure -connection such as an ssh tunnel; specify \fRgssapi\fR or -\fBkerberos_v4\fR if you are using a protocol variant that employs -GSSAPI or K4. Choosing KPOP protocol automatically selects Kerberos -authentication. This option does not work with ETRN or ODMR. +excruciating exactness, `\fBkerberos_v4\fR'), \fRgssapi\fR, +\fIcram-md5\fR, \fIotp\fR, and \fBssh\fR. When \fBany\fR (the +default) is specified, fetchmail tries first methods that don't +require a password (GSSAPI, KERBEROS_IV); then it looks for methods +that mask your password (CRAM-MD5, X-OTP); and only if the server +doesn't support any of those will it ship your password en clair. +Other values may be used to force various authentication methods +(\fBssh\fR suppresses authentication). Any value other than +\fIpassword\fR, \fIcram-md5\fR or \fIotp\fR suppresses fetchmail's +normal inquiry for a password. Specify \fBssh\fR when you are using +an end-to-end secure connection such as an ssh tunnel; specify +\fRgssapi\fR or \fBkerberos_v4\fR if you are using a protocol variant +that employs GSSAPI or K4. Choosing KPOP protocol automatically +selects Kerberos authentication. This option does not work with ETRN +or ODMR. .SS Miscellaneous Options .TP .B \-f , --fetchmailrc diff --git a/pop3.c b/pop3.c index 7684b1a1..c5b6d58c 100644 --- a/pop3.c +++ b/pop3.c @@ -167,35 +167,12 @@ int pop3_getauth(int sock, struct query *ctl, char *greeting) } #endif /* RPA_ENABLE */ -#if OPIE_ENABLE - /* see RFC1938: A One-Time Password System */ - if (challenge = strstr(lastok, "otp-")) { - char response[OPIE_RESPONSE_MAX+1]; - int i; - - i = opiegenerator(challenge, !strcmp(ctl->password, "opie") ? "" : ctl->password, response); - if ((i == -2) && !run.poll_interval) { - char secret[OPIE_SECRET_MAX+1]; - fprintf(stderr, _("Secret pass phrase: ")); - if (opiereadpass(secret, sizeof(secret), 0)) - i = opiegenerator(challenge, secret, response); - memset(secret, 0, sizeof(secret)); - }; - - if (i) { - ok = PS_ERROR; - break; - }; - - ok = gen_transact(sock, "PASS %s", response); - break; - } -#endif /* OPIE_ENABLE */ - /* - * CAPA command may return a list of available mechanisms. - * if it doesn't, no harm done, we just fall back to a - * plain login. + * CAPA command may return a list including available + * authentication mechanisms. if it doesn't, no harm done, we + * just fall back to a plain login. Note that this code + * latches the server's authentication type, so that in daemon mode + * the CAPA check only needs to be done once at start of run. * * APOP was introduced in RFC 1450, and CAPA not until * RFC2449. So the < check is an easy way to prevent CAPA from @@ -204,7 +181,7 @@ int pop3_getauth(int sock, struct query *ctl, char *greeting) * it. This certainly catches IMAP-2000's POP3 gateway. * * These authentication methods are blessed by RFC1734, - * describing the POP3 AUTHentication command. + * describing the POP3 AUTHentication command. */ if (ctl->server.authenticate == A_ANY && strchr(greeting, '<') @@ -235,35 +212,53 @@ int pop3_getauth(int sock, struct query *ctl, char *greeting) if (strstr(buffer, "KERBEROS_V4")) has_kerberos = TRUE; #endif /* defined(KERBEROS_V4) || defined(KERBEROS_V5) */ - if (strstr(buffer, "CRAM-MD5")) - has_cram = TRUE; #ifdef OPIE_ENABLE if (strstr(buffer, "X-OTP")) - has_opie = TRUE; + has_otp = TRUE; #endif /* OPIE_ENABLE */ + if (strstr(buffer, "CRAM-MD5")) + has_cram = TRUE; } + /* + * Here's where we set priorities. Note that we must do tests + * in *reverse* order of desirability. + */ + if (has_cram) + ctl->server.authenticate = A_CRAM_MD5; +#ifdef OPIE_ENABLE + if (has_opie) + ctl->server.authenticate = A_OTP; +#endif /* OPIE_ENABLE */ #if defined(GSSAPI) - if ((ctl->server.authenticate == A_ANY - || ctl->server.authenticate==A_GSSAPI) - && has_gssapi) - return(do_gssauth(sock, "AUTH", - ctl->server.truename, ctl->remotename)); + if (has_gssapi) + ctl->server.authenticate = A_GSSAPI; #endif /* defined(GSSAPI) */ #if defined(KERBEROS_V4) || defined(KERBEROS_V5) - if ((ctl->server.authenticate == A_ANY - || ctl->server.authenticate==A_KERBEROS_V4 - || ctl->server.authenticate==A_KERBEROS_V5) - && has_kerberos) - return(do_rfc1731(sock, "AUTH", ctl->server.truename)); + if (has_kerberos) + ctl->server.authenticate = A_KERBEROS_V4; #endif /* defined(KERBEROS_V4) || defined(KERBEROS_V5) */ - if (has_cram) - return(do_cram_md5(sock, "AUTH", ctl)); + } + + /* + * OK, we have an authentication type now. + */ +#if defined(KERBEROS_V4) || defined(KERBEROS_V5) + if (ctl->server.authenticate == A_KERBEROS_V4 + || ctl->server.authenticate == A_KERBEROS_V5) + return(do_rfc1731(sock, "AUTH", ctl->server.truename)); +#endif /* defined(KERBEROS_V4) || defined(KERBEROS_V5) */ +#if defined(GSSAPI) + if (ctl->server.authenticate==A_GSSAPI)) + return(do_gssauth(sock, "AUTH", + ctl->server.truename, ctl->remotename)); +#endif /* defined(GSSAPI) */ #ifdef OPIE_ENABLE - if (has_opie) - do_otp(sock, "AUTH", ctl) + if (ctl->server.authenticate == A_OTP) + do_otp(sock, "AUTH", ctl) #endif /* OPIE_ENABLE */ - } + if (ctl->server.authenticate == A_CRAM_MD5) + return(do_cram_md5(sock, "AUTH", ctl)); /* ordinary validation, no one-time password or RPA */ gen_transact(sock, "USER %s", ctl->remotename); -- cgit v1.2.3