diff options
author | Eduardo Chappa <chappa@washington.edu> | 2013-10-06 23:58:51 -0600 |
---|---|---|
committer | Eduardo Chappa <chappa@washington.edu> | 2013-10-06 23:58:51 -0600 |
commit | 30a979ab1460a57d466a6a5cc6adb96eac452ce4 (patch) | |
tree | 1aec0ebb21be40922bc5a708c7780fb0db602202 /imap/src | |
parent | c5bb25b1320af6cda4cc62ea9e15fbb03ee92026 (diff) | |
download | alpine-30a979ab1460a57d466a6a5cc6adb96eac452ce4.tar.xz |
* new version 2.11.8
* Fix in configure script for recognition of SSL files in Ubuntu 12.04
* Alpine does not attempt to automatically reopen a collection that
was not opened due to cancellation by the user. Instead, the user
must try to open it explicitly.
* few improvements on new /tls1, /tls1_1, etc. options.
Diffstat (limited to 'imap/src')
-rw-r--r-- | imap/src/c-client/imap4r1.c | 15 | ||||
-rw-r--r-- | imap/src/c-client/mail.c | 29 | ||||
-rw-r--r-- | imap/src/c-client/mail.h | 18 | ||||
-rw-r--r-- | imap/src/c-client/nntp.c | 14 | ||||
-rw-r--r-- | imap/src/c-client/pop3.c | 6 | ||||
-rw-r--r-- | imap/src/c-client/smtp.c | 2 | ||||
-rw-r--r-- | imap/src/mtest/mtest.c | 36 | ||||
-rw-r--r-- | imap/src/osdep/unix/ssl_unix.c | 30 |
8 files changed, 105 insertions, 45 deletions
diff --git a/imap/src/c-client/imap4r1.c b/imap/src/c-client/imap4r1.c index 8c1d326a..48017cab 100644 --- a/imap/src/c-client/imap4r1.c +++ b/imap/src/c-client/imap4r1.c @@ -81,6 +81,10 @@ typedef struct imap_local { unsigned int tlssslv23 : 1; /* TLS using SSLv23 client method */ unsigned int notlsflag : 1; /* TLS not used in session */ unsigned int sslflag : 1; /* SSL session */ + unsigned int tls1 : 1; /* using TLSv1 over SSL */ + unsigned int tls1_1 : 1; /* using TLSv1_1 over SSL */ + unsigned int tls1_2 : 1; /* using TLSv1_2 over SSL */ + unsigned int dtls1 : 1; /* using DTLSv1 over SSL */ unsigned int novalidate : 1; /* certificate not validated */ unsigned int filter : 1; /* filter SEARCH/SORT/THREAD results */ unsigned int loser : 1; /* server is a loser */ @@ -885,7 +889,7 @@ MAILSTREAM *imap_open (MAILSTREAM *stream) LOCAL->netstream->dtb = ssld; if (!(LOCAL->netstream->stream = (*stls) (LOCAL->netstream->stream,mb.host, - SSL_METHOD(mb) | (mb.novalidate ? NET_NOVALIDATECERT : NIL)))) { + SSL_MTHD(mb) | (mb.novalidate ? NET_NOVALIDATECERT : NIL)))) { /* drat, drop this connection */ if (LOCAL->netstream) net_close (LOCAL->netstream); LOCAL->netstream = NIL; @@ -911,6 +915,7 @@ MAILSTREAM *imap_open (MAILSTREAM *stream) (LOCAL->cap.auth ? imap_auth (stream,&mb,tmp,usr) : imap_login (stream,&mb,tmp,usr)))) { /* failed, is there a referral? */ + if (mb.tlsflag) LOCAL->tlsflag = T; if (ir && LOCAL->referral && (s = (*ir) (stream,LOCAL->referral,REFAUTHFAILED))) { imap_close (stream,NIL); @@ -935,6 +940,10 @@ MAILSTREAM *imap_open (MAILSTREAM *stream) if (LOCAL->netstream && !LOCAL->gotcapability) imap_capability (stream); /* save state for future recycling */ if (mb.tlsflag) LOCAL->tlsflag = T; + if (mb.tls1) LOCAL->tls1 = T; + if (mb.dtls1) LOCAL->dtls1 = T; + if (mb.tls1_1) LOCAL->tls1_1 = T; + if (mb.tls1_2) LOCAL->tls1_2 = T; if (mb.tlssslv23) LOCAL->tlssslv23 = T; if (mb.notlsflag) LOCAL->notlsflag = T; if (mb.sslflag) LOCAL->sslflag = T; @@ -953,6 +962,10 @@ MAILSTREAM *imap_open (MAILSTREAM *stream) sprintf (tmp + strlen (tmp),":%lu",i); strcat (tmp,"/imap"); if (LOCAL->tlsflag) strcat (tmp,"/tls"); + if (LOCAL->tls1) strcat (tmp,"/tls1"); + if (LOCAL->tls1_1) strcat (tmp,"/tls1_1"); + if (LOCAL->tls1_2) strcat (tmp,"/tls1_2"); + if (LOCAL->dtls1) strcat (tmp,"/dtls"); if (LOCAL->tlssslv23) strcat (tmp,"/tls-sslv23"); if (LOCAL->notlsflag) strcat (tmp,"/notls"); if (LOCAL->sslflag) strcat (tmp,"/ssl"); diff --git a/imap/src/c-client/mail.c b/imap/src/c-client/mail.c index 9b5526b4..0b479a1c 100644 --- a/imap/src/c-client/mail.c +++ b/imap/src/c-client/mail.c @@ -815,17 +815,19 @@ long mail_valid_net_parse_work (char *name,NETMBX *mb,char *service) else if (mailssldriver && !compare_cstring (s,"ssl") && !mb->tlsflag) mb->sslflag = mb->notlsflag = T; else if (!compare_cstring(s, "tls1") - && !mb->tls1_1flag && !mb->tls1_2flag && !mb->dtls1flag) - mb->sslflag = mb->notlsflag = mb->tls1_1flag = T; + && !mb->tls1_1 && !mb->tls1_2 && !mb->dtls1) + mb->sslflag = mb->notlsflag = mb->tls1 = T; +#ifdef TLSV1_2 else if (!compare_cstring(s, "tls1_1") - && !mb->tls1flag && !mb->tls1_2flag && !mb->dtls1flag) - mb->sslflag = mb->notlsflag = mb->tls1_1flag = T; + && !mb->tls1 && !mb->tls1_2 && !mb->dtls1) + mb->sslflag = mb->notlsflag = mb->tls1_1 = T; else if (!compare_cstring(s, "tls1_2") - && !mb->tls1flag && !mb->tls1_1flag && !mb->dtls1flag) - mb->sslflag = mb->notlsflag = mb->tls1_2flag = T; + && !mb->tls1 && !mb->tls1_1 && !mb->dtls1) + mb->sslflag = mb->notlsflag = mb->tls1_2 = T; +#endif else if (!compare_cstring(s, "dtls1") - && !mb->tls1flag && !mb->tls1_1flag && !mb->tls1_2flag) - mb->sslflag = mb->notlsflag = mb->dtls1flag = T; + && !mb->tls1 && !mb->tls1_1 && !mb->tls1_2) + mb->sslflag = mb->notlsflag = mb->dtls1 = T; else if (mailssldriver && !compare_cstring (s,"novalidate-cert")) mb->novalidate = T; /* hack for compatibility with the past */ @@ -1234,9 +1236,10 @@ MAILSTREAM *mail_open (MAILSTREAM *stream,char *name,long options) if (mb.tlsflag) strcat (tmp,"/tls"); if (mb.notlsflag) strcat (tmp,"/notls"); if (mb.sslflag) strcat (tmp,"/ssl"); - if (mb.tls1_1flag) strcat (tmp,"/tls1_1"); - if (mb.tls1_2flag) strcat (tmp,"/tls1_2"); - if (mb.dtls1flag) strcat (tmp,"/dtls1"); + if (mb.tls1) strcat (tmp,"/tls1"); + if (mb.tls1_1) strcat (tmp,"/tls1_1"); + if (mb.tls1_2) strcat (tmp,"/tls1_2"); + if (mb.dtls1) strcat (tmp,"/dtls1"); if (mb.trysslflag) strcat (tmp,"/tryssl"); if (mb.novalidate) strcat (tmp,"/novalidate-cert"); strcat (tmp,"/pop3/loser}"); @@ -6170,6 +6173,10 @@ NETSTREAM *net_open (NETMBX *mb,NETDRIVER *dv,unsigned long port, NETSTREAM *stream = NIL; char tmp[MAILTMPLEN]; unsigned long flags = mb->novalidate ? NET_NOVALIDATECERT : 0; + flags |= mb->tls1 || mb->tlsflag ? NET_TRYTLS1 : 0; + flags |= mb->tls1_1 ? NET_TRYTLS1_1 : 0; + flags |= mb->tls1_2 ? NET_TRYTLS1_2 : 0; + flags |= mb->dtls1 ? NET_TRYDTLS1 : 0; if (strlen (mb->host) >= NETMAXHOST) { sprintf (tmp,"Invalid host name: %.80s",mb->host); MM_LOG (tmp,ERROR); diff --git a/imap/src/c-client/mail.h b/imap/src/c-client/mail.h index 2c3f92d2..ad63fa2d 100644 --- a/imap/src/c-client/mail.h +++ b/imap/src/c-client/mail.h @@ -662,10 +662,10 @@ typedef struct net_mailbox { unsigned int dbgflag : 1; /* debug flag */ unsigned int secflag : 1; /* secure flag */ unsigned int sslflag : 1; /* SSL driver flag */ - unsigned int tls1flag : 1; /* Use TLSv1 */ - unsigned int tls1_1flag : 1; /* Use TLSv1.1 */ - unsigned int tls1_2flag : 1; /* Use TLSV1.2 */ - unsigned int dtls1flag : 1; /* Use DTLSv1 */ + unsigned int tls1 : 1; /* Use TLSv1 */ + unsigned int tls1_1 : 1; /* Use TLSv1.1 */ + unsigned int tls1_2 : 1; /* Use TLSV1.2 */ + unsigned int dtls1 : 1; /* Use DTLSv1 */ unsigned int trysslflag : 1; /* try SSL driver first flag */ unsigned int novalidate : 1; /* don't validate certificates */ unsigned int tlsflag : 1; /* TLS flag */ @@ -676,11 +676,11 @@ typedef struct net_mailbox { unsigned int tlssslv23 : 1; /* force SSLv23 client method over TLS */ } NETMBX; -#define SSL_METHOD(M) ((M).tlssslv23 ? NIL \ - : (M).tls1flag ? NET_TRYTLS1 \ - : (M).tls1_1flag ? NET_TRYTLS1_1 \ - : (M).tls1_2flag ? NET_TRYTLS1_2 \ - : (M).dtls1flag ? NET_TRYDTLS1 \ +#define SSL_MTHD(M) ((M).tlssslv23 ? NIL \ + : (M).tls1 ? NET_TRYTLS1 \ + : (M).tls1_1 ? NET_TRYTLS1_1 \ + : (M).tls1_2 ? NET_TRYTLS1_2 \ + : (M).dtls1 ? NET_TRYDTLS1 \ : NET_TLSCLIENT) diff --git a/imap/src/c-client/nntp.c b/imap/src/c-client/nntp.c index 8a9d00a8..5a805e86 100644 --- a/imap/src/c-client/nntp.c +++ b/imap/src/c-client/nntp.c @@ -71,6 +71,10 @@ typedef struct nntp_local { unsigned int tlssslv23 : 1; /* TLS using SSLv23 client method */ unsigned int notlsflag : 1; /* TLS not used in session */ unsigned int sslflag : 1; /* SSL session */ + unsigned int tls1 : 1; /* TLSv1 on SSL port */ + unsigned int dtls1 : 1; /* DTLSv1 on SSL port */ + unsigned int tls1_1 : 1; /* TLSv1_1 on SSL port */ + unsigned int tls1_2 : 1; /* TLSv1_2 on SSL port */ unsigned int novalidate : 1; /* certificate not validated */ unsigned int xover : 1; /* supports XOVER */ unsigned int xhdr : 1; /* supports XHDR */ @@ -663,6 +667,10 @@ MAILSTREAM *nntp_mopen (MAILSTREAM *stream) if (LOCAL->tlssslv23) mb.tlssslv23 = T; if (LOCAL->notlsflag) mb.notlsflag = T; if (LOCAL->sslflag) mb.sslflag = T; + if (LOCAL->tls1) mb.tls1 = T; + if (LOCAL->dtls1) mb.dtls1 = T; + if (LOCAL->tls1_1) mb.tls1_1 = T; + if (LOCAL->tls1_2) mb.tls1_2 = T; if (LOCAL->novalidate) mb.novalidate = T; if (LOCAL->nntpstream->loser) mb.loser = T; if (stream->secure) mb.secflag = T; @@ -684,6 +692,10 @@ MAILSTREAM *nntp_mopen (MAILSTREAM *stream) if (mb.tlssslv23) strcat (tmp,"/tls-sslv23"); if (mb.notlsflag) strcat (tmp,"/notls"); if (mb.sslflag) strcat (tmp,"/ssl"); + if (mb.tls1) strcat (tmp,"/tls1"); + if (mb.tls1_1) strcat (tmp,"/tls1_1"); + if (mb.tls1_2) strcat (tmp,"/tls1_2"); + if (mb.dtls1) strcat (tmp,"/dtls1"); if (mb.novalidate) strcat (tmp,"/novalidate-cert"); if (mb.loser) strcat (tmp,"/loser"); if (mb.secflag) strcat (tmp,"/secure"); @@ -1719,7 +1731,7 @@ SENDSTREAM *nntp_open_full (NETDRIVER *dv,char **hostlist,char *service, /* negotiate TLS */ if (stream->netstream->stream = (*stls) (stream->netstream->stream,mb.host, - SSL_METHOD(mb) | (mb.novalidate ? NET_NOVALIDATECERT:NIL))) + SSL_MTHD(mb) | (mb.novalidate ? NET_NOVALIDATECERT:NIL))) extok = nntp_extensions (stream,(mb.secflag ? AU_SECURE : NIL) | (mb.authuser[0] ? AU_AUTHUSER : NIL)); else { diff --git a/imap/src/c-client/pop3.c b/imap/src/c-client/pop3.c index 5065fed2..123abd9d 100644 --- a/imap/src/c-client/pop3.c +++ b/imap/src/c-client/pop3.c @@ -423,6 +423,10 @@ MAILSTREAM *pop3_open (MAILSTREAM *stream) net_port (LOCAL->netstream)); if (mb.tlsflag) strcat (tmp,"/tls"); if (mb.tlssslv23) strcat (tmp,"/tls-sslv23"); + if (mb.tls1) strcat (tmp,"/tls1"); + if (mb.tls1_1) strcat (tmp,"/tls1_1"); + if (mb.tls1_2) strcat (tmp,"/tls1_1"); + if (mb.dtls1) strcat (tmp,"/dtls1"); if (mb.notlsflag) strcat (tmp,"/notls"); if (mb.sslflag) strcat (tmp,"/ssl"); if (mb.novalidate) strcat (tmp,"/novalidate-cert"); @@ -567,7 +571,7 @@ long pop3_auth (MAILSTREAM *stream,NETMBX *mb,char *pwd,char *usr) LOCAL->netstream->dtb = ssld; if (!(LOCAL->netstream->stream = (*stls) (LOCAL->netstream->stream,mb->host, - SSL_METHOD(*mb) | (mb->novalidate ? NET_NOVALIDATECERT : NIL)))) { + SSL_MTHD(*mb) | (mb->novalidate ? NET_NOVALIDATECERT : NIL)))) { /* drat, drop this connection */ if (LOCAL->netstream) net_close (LOCAL->netstream); LOCAL->netstream= NIL; diff --git a/imap/src/c-client/smtp.c b/imap/src/c-client/smtp.c index 1cba3357..fe38cad0 100644 --- a/imap/src/c-client/smtp.c +++ b/imap/src/c-client/smtp.c @@ -210,7 +210,7 @@ SENDSTREAM *smtp_open_full (NETDRIVER *dv,char **hostlist,char *service, /* TLS started, negotiate it */ if (!(stream->netstream->stream = (*stls) (stream->netstream->stream,mb.host, - SSL_METHOD(mb) | (mb.novalidate ? NET_NOVALIDATECERT:NIL)))){ + SSL_MTHD(mb) | (mb.novalidate ? NET_NOVALIDATECERT:NIL)))){ /* TLS negotiation failed after STARTTLS */ sprintf (tmp,"Unable to negotiate TLS with this server: %.80s", mb.host); diff --git a/imap/src/mtest/mtest.c b/imap/src/mtest/mtest.c index 69af568b..12a05e33 100644 --- a/imap/src/mtest/mtest.c +++ b/imap/src/mtest/mtest.c @@ -81,7 +81,7 @@ void overview_header (MAILSTREAM *stream,unsigned long uid,OVERVIEW *ov, void header (MAILSTREAM *stream,long msgno); void display_body (BODY *body,char *pfx,long i); void status (MAILSTREAM *stream); -void prompt (char *msg,char *txt); +void prompt (char *msg,char *txt, int buflen); void smtptest (long debug); /* Main program - initialization */ @@ -118,13 +118,13 @@ int main () #endif curhst = cpystr (mylocalhost ()); puts ("MTest -- C client test program"); - if (!*personalname) prompt ("Personal name: ",personalname); + if (!*personalname) prompt ("Personal name: ",personalname, sizeof(personalname)); /* user wants protocol telemetry? */ - prompt ("Debug protocol (y/n)?",tmp); + prompt ("Debug protocol (y/n)?",tmp, sizeof(tmp)); ucase (tmp); debug = (tmp[0] == 'Y') ? T : NIL; do { - prompt ("Mailbox ('?' for help): ",tmp); + prompt ("Mailbox ('?' for help): ",tmp, sizeof(tmp)); if (!strcmp (tmp,"?")) { puts ("Enter INBOX, mailbox name, or IMAP mailbox as {host}mailbox"); puts ("Known local mailboxes:"); @@ -154,13 +154,13 @@ void mm (MAILSTREAM *stream,long debug) { void *sdb = NIL; char cmd[MAILTMPLEN]; - char *s,*arg; + char *s, *arg; unsigned long i; unsigned long last = 0; BODY *body; status (stream); /* first report message status */ while (stream) { - prompt ("MTest>",cmd); /* prompt user, get command */ + prompt ("MTest> ",cmd, sizeof(cmd)); /* prompt user, get command */ /* get argument */ if (arg = strchr (cmd,' ')) *arg++ = '\0'; switch (*ucase (cmd)) { /* dispatch based on command */ @@ -255,7 +255,7 @@ void mm (MAILSTREAM *stream,long debug) } /* get the new mailbox */ while (!(stream = mail_open (stream,arg,debug))) { - prompt ("Mailbox: ",arg); + prompt ("Mailbox: ",arg, sizeof(arg)); if (!arg[0]) break; } last = 0; @@ -592,10 +592,14 @@ void status (MAILSTREAM *stream) * pointer to input buffer */ -void prompt (char *msg,char *txt) +void prompt (char *msg,char *txt, int buflen) { printf ("%s",msg); - gets (txt); + fgets (txt, buflen-1, stdin); + if(txt[strlen(txt)-1] == '\012') + txt[strlen(txt)-1] = '\0'; + if(txt[strlen(txt)-1] == '\015') + txt[strlen(txt)-1] = '\0'; } /* Interfaces to C-client */ @@ -758,14 +762,14 @@ void smtptest (long debug) msg->return_path = mail_newaddr (); msg->return_path->mailbox = cpystr (curusr); msg->return_path->host = cpystr (curhst); - prompt ("To: ",line); + prompt ("To: ",line, sizeof(line)); rfc822_parse_adrlist (&msg->to,line,curhst); if (msg->to) { - prompt ("cc: ",line); + prompt ("cc: ",line, sizeof(line)); rfc822_parse_adrlist (&msg->cc,line,curhst); } else { - prompt ("Newsgroups: ",line); + prompt ("Newsgroups: ",line, sizeof(line)); if (*line) msg->newsgroups = cpystr (line); else { mail_free_body (&body); @@ -774,12 +778,16 @@ void smtptest (long debug) return; } } - prompt ("Subject: ",line); + prompt ("Subject: ",line, sizeof(line)); msg->subject = cpystr (line); puts (" Msg (end with a line with only a '.'):"); body->type = TYPETEXT; *text = '\0'; - while (gets (line)) { + while (fgets(line, sizeof(line)-1, stdin)){ + if(line[strlen(line)-1] == '\012') + line[strlen(line)-1] = '\0'; + if(line[strlen(line)-1] == '\015') + line[strlen(line)-1] = '\0'; if (line[0] == '.') { if (line[1] == '\0') break; else strcat (text,"."); diff --git a/imap/src/osdep/unix/ssl_unix.c b/imap/src/osdep/unix/ssl_unix.c index 5a7d0bc0..3f6bcce9 100644 --- a/imap/src/osdep/unix/ssl_unix.c +++ b/imap/src/osdep/unix/ssl_unix.c @@ -55,7 +55,7 @@ typedef struct ssl_stream { #include "sslio.h" /* Function prototypes */ - +const SSL_METHOD *ssl_connect_mthd(int flag); static SSLSTREAM *ssl_start(TCPSTREAM *tstream,char *host,unsigned long flags); static char *ssl_start_work (SSLSTREAM *stream,char *host,unsigned long flags); static int ssl_open_verify (int ok,X509_STORE_CTX *ctx); @@ -98,8 +98,8 @@ void ssl_onceonlyinit (void) struct stat sbuf; /* if system doesn't have /dev/urandom */ if (stat ("/dev/urandom",&sbuf)) { - while ((fd = open (tmpnam (tmp),O_WRONLY|O_CREAT|O_EXCL,0600)) < 0) - sleep (1); + strcpy(tmp, "SSLXXXXXX"); + while ((fd = mkstemp(tmp)) < 0) sleep (1); unlink (tmp); /* don't need the file */ fstat (fd,&sbuf); /* get information about the file */ close (fd); /* flush descriptor */ @@ -143,7 +143,25 @@ SSLSTREAM *ssl_aopen (NETMBX *mb,char *service,char *usrbuf) { return NIL; /* don't use this mechanism with SSL */ } - + +/* ssl_connect_mthd: returns a context pointer to the connection to + * a ssl server + */ +const SSL_METHOD *ssl_connect_mthd(int flag) +{ + if(flag & NET_TRYTLS1) + return TLSv1_client_method(); +#ifdef TLSV1_2 + else if(flag & NET_TRYTLS1_1) + return TLSv1_1_client_method(); + else if(flag & NET_TRYTLS1_2) + return TLSv1_2_client_method(); +#endif + else if(flag & NET_TRYDTLS1) + return DTLSv1_client_method(); + else return SSLv23_client_method(); +} + /* Start SSL/TLS negotiations * Accepts: open TCP stream of session * user's host name @@ -219,9 +237,7 @@ static char *ssl_start_work (SSLSTREAM *stream,char *host,unsigned long flags) (sslclientkey_t) mail_parameters (NIL,GET_SSLCLIENTKEY,NIL); if (ssl_last_error) fs_give ((void **) &ssl_last_error); ssl_last_host = host; - if (!(stream->context = SSL_CTX_new ((flags & NET_TLSCLIENT) ? - TLSv1_client_method () : - SSLv23_client_method ()))) + if (!(stream->context = SSL_CTX_new (ssl_connect_mthd(flags)))) return "SSL context failed"; SSL_CTX_set_options (stream->context,0); /* disable certificate validation? */ |