changeset: 6974:7cefa378ab7e
user:      Kevin McCarthy <ke...@8t8.us>
date:      Mon Mar 20 10:16:03 2017 -0700
link:      http://dev.mutt.org/hg/mutt/rev/7cefa378ab7e

Fix setenv overwriting to not truncate the envlist. (see #3922)

The refactor in 2b9c40f13e13 exposed a bug I hadn't noticed.  The
match loop performed a FREE() on the slot.  Then, below, it was
checking if (*envp) to see whether it was overwriting or creating a
new slot.  However, FREE() nulls out *envp.  This would end up
truncating the envlist just after the set slot!

Move the free down, using a mutt_str_replace(), when overwriting the
slot.

changeset: 6975:c875e6f4785d
user:      Kevin McCarthy <ke...@8t8.us>
date:      Mon Mar 20 10:18:57 2017 -0700
link:      http://dev.mutt.org/hg/mutt/rev/c875e6f4785d

merge stable

diffs (truncated from 963 to 950 lines):

diff -r 2b9c40f13e13 -r c875e6f4785d browser.c
--- a/browser.c Sat Mar 18 14:39:12 2017 -0700
+++ b/browser.c Mon Mar 20 10:18:57 2017 -0700
@@ -492,17 +492,20 @@
       tmp->msg_unread = Context->unread;
     }
 
+    strfcpy (buffer, NONULL (tmp->path), sizeof (buffer));
+    mutt_pretty_mailbox (buffer, sizeof (buffer));
+
 #ifdef USE_IMAP
     if (mx_is_imap (tmp->path))
     {
-      add_folder (menu, state, tmp->path, NULL, tmp);
+      add_folder (menu, state, buffer, NULL, tmp);
       continue;
     }
 #endif
 #ifdef USE_POP
     if (mx_is_pop (tmp->path))
     {
-      add_folder (menu, state, tmp->path, NULL, tmp);
+      add_folder (menu, state, buffer, NULL, tmp);
       continue;
     }
 #endif
@@ -528,9 +531,6 @@
        s.st_mtime = st2.st_mtime;
     }
 
-    strfcpy (buffer, NONULL(tmp->path), sizeof (buffer));
-    mutt_pretty_mailbox (buffer, sizeof (buffer));
-
     add_folder (menu, state, buffer, &s, tmp);
   }
   while ((tmp = tmp->next));
diff -r 2b9c40f13e13 -r c875e6f4785d configure.ac
--- a/configure.ac      Sat Mar 18 14:39:12 2017 -0700
+++ b/configure.ac      Mon Mar 20 10:18:57 2017 -0700
@@ -710,6 +710,11 @@
             AC_CHECK_DECLS([SSL_set_mode, SSL_MODE_AUTO_RETRY],,
               AC_MSG_ERROR([Unable to find decent SSL header]), [[#include 
<openssl/ssl.h>]])
 
+            AC_CHECK_DECL([X509_V_FLAG_PARTIAL_CHAIN],
+              AC_DEFINE(HAVE_SSL_PARTIAL_CHAIN,1,[ Define if OpenSSL supports 
partial chains. ]),
+              ,
+              [[#include <openssl/x509_vfy.h>]])
+
             AC_DEFINE(USE_SSL,1,[ Define if you want support for SSL. ])
             AC_DEFINE(USE_SSL_OPENSSL,1,[ Define if you want support for SSL 
via OpenSSL. ])
             LIBS="$saved_LIBS"
diff -r 2b9c40f13e13 -r c875e6f4785d doc/makedoc-defs.h
--- a/doc/makedoc-defs.h        Sat Mar 18 14:39:12 2017 -0700
+++ b/doc/makedoc-defs.h        Mon Mar 20 10:18:57 2017 -0700
@@ -19,6 +19,9 @@
 # ifndef USE_SSL_OPENSSL
 #  define USE_SSL_OPENSSL
 # endif
+# ifndef HAVE_SSL_PARTIAL_CHAIN
+#  define HAVE_SSL_PARTIAL_CHAIN
+# endif
 # ifndef USE_SSL_GNUTLS
 #  define USE_SSL_GNUTLS
 # endif
diff -r 2b9c40f13e13 -r c875e6f4785d init.c
--- a/init.c    Sat Mar 18 14:39:12 2017 -0700
+++ b/init.c    Mon Mar 20 10:18:57 2017 -0700
@@ -1867,10 +1867,7 @@
   while (envp && *envp)
   {
     if (!mutt_strncmp (name, *envp, len) && (*envp)[len] == '=')
-    {
-      FREE (envp);     /* __FREE_CHECKED__ */
       break;
-    }
     envp++;
     count++;
   }
@@ -1880,7 +1877,7 @@
 
   /* If slot found, overwrite */
   if (envp && *envp)
-    *envp = safe_strdup (work);
+    mutt_str_replace (envp, work);
 
   /* If not found, add new slot */
   else
diff -r 2b9c40f13e13 -r c875e6f4785d init.h
--- a/init.h    Sat Mar 18 14:39:12 2017 -0700
+++ b/init.h    Mon Mar 20 10:18:57 2017 -0700
@@ -78,7 +78,6 @@
 };
 
 #define UL (unsigned long)
-
 #endif /* _MAKEDOC */
 
 #ifndef ISPELL
@@ -3377,6 +3376,24 @@
   ** URL. You should only unset this for particular known hosts, using
   ** the \fC$<account-hook>\fP function.
   */
+# ifdef USE_SSL_OPENSSL
+#  ifdef HAVE_SSL_PARTIAL_CHAIN
+  { "ssl_verify_partial_chains", DT_BOOL, R_NONE, OPTSSLVERIFYPARTIAL, 0 },
+  /*
+  ** .pp
+  ** This option should not be changed from the default unless you understand
+  ** what you are doing.
+  ** .pp
+  ** Setting this variable to \fIyes\fP will permit verifying partial
+  ** certification chains, i. e. a certificate chain where not the root,
+  ** but an intermediate certificate CA, or the host certificate, are
+  ** marked trusted (in $$certificate_file), without marking the root
+  ** signing CA as trusted.
+  ** .pp
+  ** (OpenSSL 1.0.2b and newer only).
+  */
+#  endif /* defined HAVE_SSL_PARTIAL_CHAIN */
+# endif /* defined USE_SSL_OPENSSL */
   { "ssl_ciphers", DT_STR, R_NONE, UL &SslCiphers, UL 0 },
   /*
   ** .pp
diff -r 2b9c40f13e13 -r c875e6f4785d main.c
--- a/main.c    Sat Mar 18 14:39:12 2017 -0700
+++ b/main.c    Mon Mar 20 10:18:57 2017 -0700
@@ -163,9 +163,9 @@
   exit (0);
 }
 
-extern const char cc_version[];
-extern const char cc_cflags[];
-extern const char configure_options[];
+extern unsigned char cc_version[];
+extern unsigned char cc_cflags[];
+extern unsigned char configure_options[];
 
 static char *
 rstrip_in_place(char *s)
@@ -222,13 +222,13 @@
 
   puts ("\n\nCompiler:");
   rstrip_in_place((char *)cc_version);
-  puts (cc_version);
+  puts ((char *)cc_version);
 
   rstrip_in_place((char *)configure_options);
-  printf ("\nConfigure options: %s\n", configure_options);
+  printf ("\nConfigure options: %s\n", (char *)configure_options);
 
   rstrip_in_place((char *)cc_cflags);
-  printf ("\nCompilation CFLAGS: %s\n", cc_cflags);
+  printf ("\nCompilation CFLAGS: %s\n", (char *)cc_cflags);
 
   puts (_("\nCompile options:"));
 
diff -r 2b9c40f13e13 -r c875e6f4785d mutt.h
--- a/mutt.h    Sat Mar 18 14:39:12 2017 -0700
+++ b/mutt.h    Mon Mar 20 10:18:57 2017 -0700
@@ -396,6 +396,9 @@
   OPTSSLFORCETLS,
   OPTSSLVERIFYDATES,
   OPTSSLVERIFYHOST,
+# if defined(USE_SSL_OPENSSL) && defined(HAVE_SSL_PARTIAL_CHAIN)
+  OPTSSLVERIFYPARTIAL,
+# endif /* USE_SSL_OPENSSL */
 #endif /* defined(USE_SSL) */
   OPTIMPLICITAUTOVIEW,
   OPTINCLUDEONLYFIRST,
diff -r 2b9c40f13e13 -r c875e6f4785d mutt_ssl.c
--- a/mutt_ssl.c        Sat Mar 18 14:39:12 2017 -0700
+++ b/mutt_ssl.c        Mon Mar 20 10:18:57 2017 -0700
@@ -23,6 +23,7 @@
 #include <openssl/ssl.h>
 #include <openssl/x509.h>
 #include <openssl/x509v3.h>
+#include <openssl/x509_vfy.h>
 #include <openssl/err.h>
 #include <openssl/rand.h>
 #include <openssl/evp.h>
@@ -57,6 +58,12 @@
 
 /* index for storing hostname as application specific data in SSL structure */
 static int HostExDataIndex = -1;
+
+/* Index for storing the "skip mode" state in SSL structure.  When the
+ * user skips a certificate in the chain, the stored value will be
+ * non-null. */
+static int SkipModeExDataIndex = -1;
+
 /* keep a handle on accepted certificates in case we want to
  * open up another connection to the same server in this session */
 static STACK_OF(X509) *SslSessionCerts = NULL;
@@ -82,7 +89,7 @@
 static void ssl_dprint_err_stack (void);
 static int ssl_cache_trusted_cert (X509 *cert);
 static int ssl_verify_callback (int preverify_ok, X509_STORE_CTX *ctx);
-static int interactive_check_cert (X509 *cert, int idx, int len);
+static int interactive_check_cert (X509 *cert, int idx, int len, SSL *ssl, int 
allow_always);
 static void ssl_get_client_cert(sslsockdata *ssldata, CONNECTION *conn);
 static int ssl_passwd_cb(char *buf, int size, int rwflag, void *userdata);
 static int ssl_negotiate (CONNECTION *conn, sslsockdata*);
@@ -136,6 +143,35 @@
   return rv;
 }
 
+static int ssl_set_verify_partial (SSL_CTX *ctx)
+{
+  int rv = 0;
+#ifdef HAVE_SSL_PARTIAL_CHAIN
+  X509_VERIFY_PARAM *param;
+
+  if (option (OPTSSLVERIFYPARTIAL))
+  {
+    param = X509_VERIFY_PARAM_new();
+    if (param)
+    {
+      X509_VERIFY_PARAM_set_flags(param, X509_V_FLAG_PARTIAL_CHAIN);
+      if (0 == SSL_CTX_set1_param(ctx, param))
+      {
+        dprint (2, (debugfile, "ssl_set_verify_partial: SSL_CTX_set1_param() 
failed."));
+        rv = -1;
+      }
+      X509_VERIFY_PARAM_free(param);
+    }
+    else
+    {
+      dprint (2, (debugfile, "ssl_set_verify_partial: X509_VERIFY_PARAM_new() 
failed."));
+      rv = -1;
+    }
+  }
+#endif
+  return rv;
+}
+
 /* mutt_ssl_starttls: Negotiate TLS over an already opened connection.
  *   TODO: Merge this code better with ssl_socket_open. */
 int mutt_ssl_starttls (CONNECTION* conn)
@@ -206,6 +242,12 @@
     }
   }
 
+  if (ssl_set_verify_partial (ssldata->ctx))
+  {
+    mutt_error (_("Warning: error enabling ssl_verify_partial_chains"));
+    mutt_sleep (2);
+  }
+
   if (! (ssldata->ssl = SSL_new (ssldata->ctx)))
   {
     dprint (1, (debugfile, "mutt_ssl_starttls: Error allocating SSL\n"));
@@ -453,6 +495,12 @@
     SSL_CTX_set_cipher_list (data->ctx, SslCiphers);
   }
 
+  if (ssl_set_verify_partial (data->ctx))
+  {
+    mutt_error (_("Warning: error enabling ssl_verify_partial_chains"));
+    mutt_sleep (2);
+  }
+
   data->ssl = SSL_new (data->ctx);
   SSL_set_fd (data->ssl, conn->fd);
 
@@ -489,8 +537,30 @@
     return -1;
   }
 
+  if ((SkipModeExDataIndex = SSL_get_ex_new_index (0, "skip", NULL, NULL, 
NULL)) == -1)
+  {
+    dprint (1, (debugfile, "failed to get index for application specific 
data\n"));
+    return -1;
+  }
+
+  if (! SSL_set_ex_data (ssldata->ssl, SkipModeExDataIndex, NULL))
+  {
+    dprint (1, (debugfile, "failed to save skip mode in SSL structure\n"));
+    return -1;
+  }
+
   SSL_set_verify (ssldata->ssl, SSL_VERIFY_PEER, ssl_verify_callback);
   SSL_set_mode (ssldata->ssl, SSL_MODE_AUTO_RETRY);
+
+  if (!SSL_set_tlsext_host_name (ssldata->ssl, conn->account.host))
+  {
+    /* L10N: This is a warning when trying to set the host name for
+     * TLS Server Name Indication (SNI).  This allows the server to present
+     * the correct certificate if it supports multiple hosts. */
+    mutt_error _("Warning: unable to set TLS SNI host name");
+    mutt_sleep (1);
+  }
+
   ERR_clear_error ();
 
   if ((err = SSL_connect (ssldata->ssl)) != 1)
@@ -701,7 +771,7 @@
       X509_issuer_name_cmp (cert, peercert) != 0)
     return -1;
 
-  if (!X509_digest (cert, EVP_sha1(), md, &mdlen) || peermdlen != mdlen)
+  if (!X509_digest (cert, EVP_sha256(), md, &mdlen) || peermdlen != mdlen)
     return -1;
 
   if (memcmp(peermd, md, mdlen) != 0)
@@ -717,7 +787,7 @@
   X509 *cert;
   int i;
 
-  if (!X509_digest (peercert, EVP_sha1(), peermd, &peermdlen)
+  if (!X509_digest (peercert, EVP_sha256(), peermd, &peermdlen)
       || !SslSessionCerts)
   {
     return 0;
@@ -735,7 +805,36 @@
   return 0;
 }
 
-static int check_certificate_by_digest (X509 *peercert)
+static int check_certificate_expiration (X509 *peercert, int silent)
+{
+  if (option (OPTSSLVERIFYDATES) != MUTT_NO)
+  {
+    if (X509_cmp_current_time (X509_get_notBefore (peercert)) >= 0)
+    {
+      if (!silent)
+      {
+        dprint (2, (debugfile, "Server certificate is not yet valid\n"));
+        mutt_error (_("Server certificate is not yet valid"));
+        mutt_sleep (2);
+      }
+      return 0;
+    }
+    if (X509_cmp_current_time (X509_get_notAfter (peercert)) <= 0)
+    {
+      if (!silent)
+      {
+        dprint (2, (debugfile, "Server certificate has expired\n"));
+        mutt_error (_("Server certificate has expired"));
+        mutt_sleep (2);
+      }
+      return 0;
+    }
+  }
+
+  return 1;
+}
+
+static int check_certificate_file (X509 *peercert)
 {
   unsigned char peermd[EVP_MAX_MD_SIZE];
   unsigned int peermdlen;
@@ -743,29 +842,13 @@
   int pass = 0;
   FILE *fp;
 
-  /* expiration check */
-  if (option (OPTSSLVERIFYDATES) != MUTT_NO)
-  {
-    if (X509_cmp_current_time (X509_get_notBefore (peercert)) >= 0)
-    {
-      dprint (2, (debugfile, "Server certificate is not yet valid\n"));
-      mutt_error (_("Server certificate is not yet valid"));
-      mutt_sleep (2);
-      return 0;
-    }
-    if (X509_cmp_current_time (X509_get_notAfter (peercert)) <= 0)
-    {
-      dprint (2, (debugfile, "Server certificate has expired\n"));
-      mutt_error (_("Server certificate has expired"));
-      mutt_sleep (2);
-      return 0;
-    }
-  }
+  if (!SslCertFile)
+    return 0;
 
   if ((fp = fopen (SslCertFile, "rt")) == NULL)
     return 0;
 
-  if (!X509_digest (peercert, EVP_sha1(), peermd, &peermdlen))
+  if (!X509_digest (peercert, EVP_sha256(), peermd, &peermdlen))
   {
     safe_fclose (&fp);
     return 0;
@@ -773,10 +856,12 @@
 
   while (PEM_read_X509 (fp, &cert, NULL, NULL) != NULL)
   {
-    pass = compare_certificates (cert, peercert, peermd, peermdlen) ? 0 : 1;
-
-    if (pass)
+    if ((compare_certificates (cert, peercert, peermd, peermdlen) == 0) &&
+        check_certificate_expiration (cert, 1))
+    {
+      pass = 1;
       break;
+    }
   }
   /* PEM_read_X509 sets an error on eof */
   if (!pass)
@@ -787,6 +872,12 @@
   return pass;
 }
 
+static int check_certificate_by_digest (X509 *peercert)
+{
+  return check_certificate_expiration (peercert, 0) &&
+    check_certificate_file (peercert);
+}
+
 /* port to mutt from msmtp's tls.c */
 static int hostname_match (const char *hostname, const char *certname)
 {
@@ -947,6 +1038,13 @@
   int len, pos;
   X509 *cert;
   SSL *ssl;
+  int skip_mode;
+#ifdef HAVE_SSL_PARTIAL_CHAIN
+  static int last_pos = 0;
+  static X509 *last_cert = NULL;
+  unsigned char last_cert_md[EVP_MAX_MD_SIZE];
+  unsigned int last_cert_mdlen;
+#endif
 
   if (! (ssl = X509_STORE_CTX_get_ex_data (ctx, 
SSL_get_ex_data_X509_STORE_CTX_idx ())))
   {
@@ -959,18 +1057,53 @@
     return 0;
   }
 
+  /* This is true when a previous entry in the certificate chain did
+   * not verify and the user manually chose to skip it via the
+   * $ssl_verify_partial_chains option.
+   * In this case, all following certificates need to be treated as 
non-verified
+   * until one is actually verified.
+   */
+  skip_mode = (SSL_get_ex_data (ssl, SkipModeExDataIndex) != NULL);
+
   cert = X509_STORE_CTX_get_current_cert (ctx);
   pos = X509_STORE_CTX_get_error_depth (ctx);
   len = sk_X509_num (X509_STORE_CTX_get_chain (ctx));
 
-  dprint (1, (debugfile, "ssl_verify_callback: checking cert chain entry %s 
(preverify: %d)\n",
-              X509_NAME_oneline (X509_get_subject_name (cert),
-                                 buf, sizeof (buf)), preverify_ok));
+  dprint (1, (debugfile,
+              "ssl_verify_callback: checking cert chain entry %s (preverify: 
%d skipmode: %d)\n",
+              X509_NAME_oneline (X509_get_subject_name (cert), buf, sizeof 
(buf)),
+              preverify_ok, skip_mode));
+
+#ifdef HAVE_SSL_PARTIAL_CHAIN
+  /* Sometimes, when a certificate is (s)kipped, OpenSSL will pass it
+   * a second time with preverify_ok = 1.  Don't show it or the user
+   * will think their "s" key is broken.
+   */
+  if (option (OPTSSLVERIFYPARTIAL))
+  {
+    if (skip_mode && preverify_ok && (pos == last_pos) && last_cert)
+    {
+      if (X509_digest (last_cert, EVP_sha256(), last_cert_md, 
&last_cert_mdlen) &&
+          !compare_certificates (cert, last_cert, last_cert_md, 
last_cert_mdlen))
+      {
+        dprint (2, (debugfile,
+                    "ssl_verify_callback: ignoring duplicate skipped 
certificate.\n"));
+        return 1;
+      }
+    }
+
+    last_pos = pos;
+    if (last_cert)
+      X509_free (last_cert);
+    last_cert = X509_dup (cert);
+  }
+#endif
 
   /* check session cache first */
   if (check_certificate_cache (cert))
   {
     dprint (2, (debugfile, "ssl_verify_callback: using cached certificate\n"));
+    SSL_set_ex_data (ssl, SkipModeExDataIndex, NULL);
     return 1;
   }
 
@@ -982,17 +1115,20 @@
     {
       mutt_error (_("Certificate host check failed: %s"), buf);
       mutt_sleep (2);
-      return interactive_check_cert (cert, pos, len);
+      /* we disallow (a)ccept always in the prompt, because it will have no 
effect
+       * for hostname mismatches. */
+      return interactive_check_cert (cert, pos, len, ssl, 0);
     }
     dprint (2, (debugfile, "ssl_verify_callback: hostname check passed\n"));
   }
 
-  if (!preverify_ok)
+  if (!preverify_ok || skip_mode)
   {
     /* automatic check from user's database */
     if (SslCertFile && check_certificate_by_digest (cert))
     {
       dprint (2, (debugfile, "ssl_verify_callback: digest check passed\n"));
+      SSL_set_ex_data (ssl, SkipModeExDataIndex, NULL);
       return 1;
     }
 
@@ -1006,14 +1142,14 @@
     }
 #endif
 
-    /* prompt user */
-    return interactive_check_cert (cert, pos, len);
+   /* prompt user */
+    return interactive_check_cert (cert, pos, len, ssl, 1);
   }
 
   return 1;
 }
 
-static int interactive_check_cert (X509 *cert, int idx, int len)
+static int interactive_check_cert (X509 *cert, int idx, int len, SSL *ssl, int 
allow_always)
 {
   static const int part[] =
     { NID_commonName,             /* CN */
@@ -1032,6 +1168,7 @@
   int done, row, i;
   unsigned u;
   FILE *fp;
+  int allow_skip = 0;
 
   menu->max = mutt_array_size (part) * 2 + 10;
   menu->dialog = (char **) safe_calloc (1, menu->max * sizeof (char *));
@@ -1073,18 +1210,43 @@
            _("SSL Certificate check (certificate %d of %d in chain)"),
            len - idx, len);
   menu->title = title;
-  if (SslCertFile
-      && (option (OPTSSLVERIFYDATES) == MUTT_NO
-         || (X509_cmp_current_time (X509_get_notAfter (cert)) >= 0
-             && X509_cmp_current_time (X509_get_notBefore (cert)) < 0)))
+
+  /* The leaf/host certificate can't be skipped. */
+#ifdef HAVE_SSL_PARTIAL_CHAIN
+  if ((idx != 0) &&
+      (option (OPTSSLVERIFYPARTIAL)))
+    allow_skip = 1;
+#endif
+
+  /* Inside ssl_verify_callback(), this function is guarded by a call to
+   * check_certificate_by_digest().  This means if 
check_certificate_expiration() is
+   * true, then check_certificate_file() must be false.  Therefore we don't 
need
+   * to also scan the certificate file here.
+   */
+  allow_always = allow_always &&
+                 SslCertFile &&
+                 check_certificate_expiration (cert, 1);
+
+  /* L10N:
+   * These four letters correspond to the choices in the next four strings:
+   * (r)eject, accept (o)nce, (a)ccept always, (s)kip.
+   * These prompts are the interactive certificate confirmation prompts for
+   * an OpenSSL connection.
+   */
+  menu->keys = _("roas");
+  if (allow_always)
   {
-    menu->prompt = _("(r)eject, accept (o)nce, (a)ccept always");
-    menu->keys = _("roa");
+    if (allow_skip)
+      menu->prompt = _("(r)eject, accept (o)nce, (a)ccept always, (s)kip");
+    else
+      menu->prompt = _("(r)eject, accept (o)nce, (a)ccept always");
   }
   else
   {
-    menu->prompt = _("(r)eject, accept (o)nce");
-    menu->keys = _("ro");
+    if (allow_skip)
+      menu->prompt = _("(r)eject, accept (o)nce, (s)kip");
+    else
+      menu->prompt = _("(r)eject, accept (o)nce");
   }
 
   helpstr[0] = '\0';
@@ -1106,6 +1268,8 @@
         done = 1;
         break;
       case OP_MAX + 3:         /* accept always */
+        if (!allow_always)
+          break;
         done = 0;
         if ((fp = fopen (SslCertFile, "a")))
        {
@@ -1126,8 +1290,15 @@
         /* fall through */
       case OP_MAX + 2:         /* accept once */
         done = 2;
+        SSL_set_ex_data (ssl, SkipModeExDataIndex, NULL);
        ssl_cache_trusted_cert (cert);
         break;
+      case OP_MAX + 4:          /* skip */
+        if (!allow_skip)
+          break;
+        done = 2;
+        SSL_set_ex_data (ssl, SkipModeExDataIndex, &SkipModeExDataIndex);
+        break;
     }
   }
   unset_option(OPTIGNOREMACROEVENTS);
diff -r 2b9c40f13e13 -r c875e6f4785d mutt_ssl_gnutls.c
--- a/mutt_ssl_gnutls.c Sat Mar 18 14:39:12 2017 -0700
+++ b/mutt_ssl_gnutls.c Mon Mar 20 10:18:57 2017 -0700
@@ -417,6 +417,13 @@
   /* set socket */
   gnutls_transport_set_ptr (data->state, 
(gnutls_transport_ptr_t)(long)conn->fd);
 
+  if (gnutls_server_name_set (data->state, GNUTLS_NAME_DNS, conn->account.host,
+                              mutt_strlen (conn->account.host)))
+  {
+    mutt_error _("Warning: unable to set TLS SNI host name");
+    mutt_sleep (1);
+  }
+
   if (tls_set_priority(data) < 0) {
     goto fail;
   }
diff -r 2b9c40f13e13 -r c875e6f4785d po/fr.po
--- a/po/fr.po  Sat Mar 18 14:39:12 2017 -0700
+++ b/po/fr.po  Mon Mar 20 10:18:57 2017 -0700
@@ -1,6 +1,6 @@
 # French messages for Mutt.
-# Copyright (C) 1998-2016 Marc Baudoin <baba...@babafou.eu.org>, Vincent 
Lefevre <vinc...@vinc17.net>
-# Marc Baudoin <baba...@babafou.eu.org>, Vincent Lefevre <vinc...@vinc17.net>, 
1998-2016
+# Copyright (C) 1998-2017 Marc Baudoin <baba...@babafou.eu.org>, Vincent 
Lefevre <vinc...@vinc17.net>
+# Marc Baudoin <baba...@babafou.eu.org>, Vincent Lefevre <vinc...@vinc17.net>, 
1998-2017
 #
 # Note [VL]. In case you need it, you may find the latest temporary version
 #            at this URL:   https://www.vinc17.net/mutt/fr.po
@@ -19,10 +19,10 @@
 # , fuzzy
 msgid ""
 msgstr ""
-"Project-Id-Version: Mutt 1.7.1\n"
+"Project-Id-Version: Mutt 1.8.0\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-02-24 10:48-0800\n"
-"PO-Revision-Date: 2017-02-10 12:46+0100\n"
+"POT-Creation-Date: 2017-03-13 01:22+0100\n"
+"PO-Revision-Date: 2017-03-13 01:36+0100\n"
 "Last-Translator: Vincent Lefevre <vinc...@vinc17.net>\n"
 "Language-Team: Vincent Lefevre <vinc...@vinc17.net>\n"
 "Language: fr\n"
@@ -59,7 +59,7 @@
 msgstr "Sélectionner"
 
 #: addrbook.c:41 browser.c:49 compose.c:96 crypt-gpgme.c:4026 curs_main.c:493
-#: mutt_ssl.c:1082 mutt_ssl_gnutls.c:1003 pager.c:1663 pgpkey.c:522
+#: mutt_ssl.c:1255 mutt_ssl_gnutls.c:1010 pager.c:1663 pgpkey.c:522
 #: postpone.c:44 query.c:53 recvattach.c:57 smime.c:440
 msgid "Help"
 msgstr "Aide"
@@ -1361,7 +1361,7 @@
 msgid "All matching keys are marked expired/revoked."
 msgstr "Toutes les clés correspondantes sont marquées expirées/révoquées."
 
-#: crypt-gpgme.c:4018 mutt_ssl.c:1080 mutt_ssl_gnutls.c:1001 pgpkey.c:515
+#: crypt-gpgme.c:4018 mutt_ssl.c:1253 mutt_ssl_gnutls.c:1008 pgpkey.c:515
 #: smime.c:435
 msgid "Exit  "
 msgstr "Quitter  "
@@ -1664,7 +1664,7 @@
 msgid "Exit Mutt?"
 msgstr "Quitter Mutt ?"
 
-#: curs_lib.c:676 mutt_socket.c:577 mutt_ssl.c:500
+#: curs_lib.c:676 mutt_socket.c:577 mutt_ssl.c:577
 msgid "unknown error"
 msgstr "erreur inconnue"
 
@@ -3336,21 +3336,25 @@
 msgid "Could not connect to %s (%s)."
 msgstr "Impossible de se connecter à %s (%s)."
 
-#: mutt_ssl.c:278
+#: mutt_ssl.c:247 mutt_ssl.c:500
+msgid "Warning: error enabling ssl_verify_partial_chains"
+msgstr "Attention : erreur lors de l'activation de ssl_verify_partial_chains"
+
+#: mutt_ssl.c:326
 msgid "Failed to find enough entropy on your system"
 msgstr "Impossible de trouver assez d'entropie sur votre système"
 
-#: mutt_ssl.c:302
+#: mutt_ssl.c:350
 #, c-format
 msgid "Filling entropy pool: %s...\n"
 msgstr "Remplissage du tas d'entropie : %s...\n"
 
-#: mutt_ssl.c:310
+#: mutt_ssl.c:358
 #, c-format
 msgid "%s has insecure permissions!"
 msgstr "%s a des droits d'accès peu sûrs !"
 
-#: mutt_ssl.c:329
+#: mutt_ssl.c:377
 msgid "SSL disabled due to the lack of entropy"
 msgstr "SSL désactivé par manque d'entropie"
 
@@ -3358,15 +3362,22 @@
 #. *       function SSL_CTX_new().  In this case it returned NULL: an
 #. *       error condition.
 #.
-#: mutt_ssl.c:396
+#: mutt_ssl.c:444
 msgid "Unable to create SSL context"
 msgstr "Impossible de créer le contexte SSL"
 
-#: mutt_ssl.c:494
+#. L10N: This is a warning when trying to set the host name for
+#. * TLS Server Name Indication (SNI).  This allows the server to present
+#. * the correct certificate if it supports multiple hosts.
+#: mutt_ssl.c:560 mutt_ssl_gnutls.c:423
+msgid "Warning: unable to set TLS SNI host name"
+msgstr "Attention : impossible de fixer le nom d'hôte TLS SNI"
+
+#: mutt_ssl.c:571
 msgid "I/O error"
 msgstr "erreur d'E/S"
 
-#: mutt_ssl.c:503
+#: mutt_ssl.c:580
 #, c-format
 msgid "SSL failed: %s"
 msgstr "SSL a échoué : %s"
@@ -3376,111 +3387,121 @@
 #. %1$s is version (e.g. "TLSv1.2")
 #. %2$s is cipher_version (e.g. "TLSv1/SSLv3")
 #. %3$s is cipher_name (e.g. "ECDHE-RSA-AES128-GCM-SHA256")
-#: mutt_ssl.c:513
+#: mutt_ssl.c:590
 #, c-format
 msgid "%s connection using %s (%s)"
 msgstr "Connexion %s utilisant %s (%s)"
 
-#: mutt_ssl.c:640
+#: mutt_ssl.c:717
 msgid "Unknown"
 msgstr "Inconnu"
 
 # , c-format
-#: mutt_ssl.c:653 mutt_ssl_gnutls.c:598
+#: mutt_ssl.c:730 mutt_ssl_gnutls.c:605
 #, c-format
 msgid "[unable to calculate]"
 msgstr "[impossible de calculer]"
 
 # , c-format
-#: mutt_ssl.c:671 mutt_ssl_gnutls.c:621
+#: mutt_ssl.c:748 mutt_ssl_gnutls.c:628
 msgid "[invalid date]"
 msgstr "[date invalide]"
 
-#: mutt_ssl.c:745
+#: mutt_ssl.c:817
 msgid "Server certificate is not yet valid"
 msgstr "Le certificat du serveur n'est pas encore valide"
 
-#: mutt_ssl.c:752
+#: mutt_ssl.c:827
 msgid "Server certificate has expired"
 msgstr "Le certificat du serveur a expiré"
 
-#: mutt_ssl.c:874
+#: mutt_ssl.c:976
 msgid "cannot get certificate subject"
 msgstr "impossible d'obtenir le détenteur du certificat (subject)"
 
-#: mutt_ssl.c:884 mutt_ssl.c:893
+#: mutt_ssl.c:986 mutt_ssl.c:995
 msgid "cannot get certificate common name"
 msgstr "impossible d'obtenir le nom du détenteur du certificat (CN)"
 
-#: mutt_ssl.c:907
+#: mutt_ssl.c:1009
 #, c-format
 msgid "certificate owner does not match hostname %s"
 msgstr "le propriétaire du certificat ne correspond pas au nom %s"
 
-#: mutt_ssl.c:972
+#: mutt_ssl.c:1116
 #, c-format
 msgid "Certificate host check failed: %s"
 msgstr "Échec de vérification de machine : %s"
 
-#: mutt_ssl.c:1031 mutt_ssl_gnutls.c:860
+#: mutt_ssl.c:1179 mutt_ssl_gnutls.c:867
 msgid "This certificate belongs to:"
 msgstr "Ce certificat appartient à :"
 
-#: mutt_ssl.c:1039 mutt_ssl_gnutls.c:899
+#: mutt_ssl.c:1187 mutt_ssl_gnutls.c:906
 msgid "This certificate was issued by:"
 msgstr "Ce certificat a été émis par :"
 
-#: mutt_ssl.c:1047 mutt_ssl_gnutls.c:938
+#: mutt_ssl.c:1195 mutt_ssl_gnutls.c:945
 #, c-format
 msgid "This certificate is valid"
 msgstr "Ce certificat est valide"
 
-#: mutt_ssl.c:1048 mutt_ssl_gnutls.c:941
+#: mutt_ssl.c:1196 mutt_ssl_gnutls.c:948
 #, c-format
 msgid "   from %s"
 msgstr "     de %s"
 
-#: mutt_ssl.c:1050 mutt_ssl_gnutls.c:945
+#: mutt_ssl.c:1198 mutt_ssl_gnutls.c:952
 #, c-format
 msgid "     to %s"
 msgstr "      à %s"
 
-#: mutt_ssl.c:1056 mutt_ssl_gnutls.c:950
+#: mutt_ssl.c:1204 mutt_ssl_gnutls.c:957
 #, c-format
 msgid "SHA1 Fingerprint: %s"
 msgstr "Empreinte SHA1 : %s"
 
-#: mutt_ssl.c:1059 mutt_ssl_gnutls.c:953
+#: mutt_ssl.c:1207 mutt_ssl_gnutls.c:960
 #, c-format
 msgid "MD5 Fingerprint: %s"
 msgstr "Empreinte MD5 : %s"
 
-#: mutt_ssl.c:1062 mutt_ssl_gnutls.c:982
+#: mutt_ssl.c:1210 mutt_ssl_gnutls.c:989
 #, c-format
 msgid "SSL Certificate check (certificate %d of %d in chain)"
 msgstr "Vérification du certificat SSL (certificat %d sur %d dans la chaîne)"
 
-#: mutt_ssl.c:1070 mutt_ssl_gnutls.c:991
+#. L10N:
+#. * These four letters correspond to the choices in the next four strings:
+#. * (r)eject, accept (o)nce, (a)ccept always, (s)kip.
+#. * These prompts are the interactive certificate confirmation prompts for
+#. * an OpenSSL connection.
+#.
+#: mutt_ssl.c:1236
+msgid "roas"
+msgstr "ruas"
+
+#: mutt_ssl.c:1240
+msgid "(r)eject, accept (o)nce, (a)ccept always, (s)kip"
+msgstr "(r)ejeter, accepter (u)ne fois, (a)ccepter toujours, (s)auter"
+
+#: mutt_ssl.c:1242 mutt_ssl_gnutls.c:998
 msgid "(r)eject, accept (o)nce, (a)ccept always"
 msgstr "(r)ejeter, accepter (u)ne fois, (a)ccepter toujours"
 
-#: mutt_ssl.c:1071 mutt_ssl_gnutls.c:992
-msgid "roa"
-msgstr "rua"
-
-#: mutt_ssl.c:1075 mutt_ssl_gnutls.c:996
+#: mutt_ssl.c:1247
+msgid "(r)eject, accept (o)nce, (s)kip"
+msgstr "(r)ejeter, accepter (u)ne fois, (s)auter"
+
+#: mutt_ssl.c:1249 mutt_ssl_gnutls.c:1003
 msgid "(r)eject, accept (o)nce"
 msgstr "(r)ejeter, accepter (u)ne fois"
 
-#: mutt_ssl.c:1076 mutt_ssl_gnutls.c:997
-msgid "ro"
-msgstr "ru"
-
-#: mutt_ssl.c:1107 mutt_ssl_gnutls.c:1046
+#: mutt_ssl.c:1282 mutt_ssl_gnutls.c:1053
 msgid "Warning: Couldn't save certificate"
 msgstr "Attention : le certificat n'a pas pu être sauvé"
 
-#: mutt_ssl.c:1112 mutt_ssl_gnutls.c:1051
+#: mutt_ssl.c:1287 mutt_ssl_gnutls.c:1058
 msgid "Certificate saved"
 msgstr "Certificat sauvé"
 
@@ -3499,54 +3520,62 @@
 "Sélection de suite cryptographique explicite via $ssl_ciphers non supportée"
 
 # , c-format
-#: mutt_ssl_gnutls.c:465
+#: mutt_ssl_gnutls.c:472
 #, c-format
 msgid "SSL/TLS connection using %s (%s/%s/%s)"
 msgstr "Connexion SSL/TLS utilisant %s (%s/%s/%s)"
 
-#: mutt_ssl_gnutls.c:688 mutt_ssl_gnutls.c:840
+#: mutt_ssl_gnutls.c:695 mutt_ssl_gnutls.c:847
 msgid "Error initialising gnutls certificate data"
 msgstr "Erreur d'initialisation des données du certificat gnutls"
 
-#: mutt_ssl_gnutls.c:695 mutt_ssl_gnutls.c:847
+#: mutt_ssl_gnutls.c:702 mutt_ssl_gnutls.c:854
 msgid "Error processing certificate data"
 msgstr "Erreur de traitement des données du certificat"
 
-#: mutt_ssl_gnutls.c:831
+#: mutt_ssl_gnutls.c:838
 msgid "Warning: Server certificate was signed using an insecure algorithm"
 msgstr ""
 "Attention : le certificat du serveur a été signé avec un algorithme peu sûr"
 
-#: mutt_ssl_gnutls.c:958
+#: mutt_ssl_gnutls.c:965
 msgid "WARNING: Server certificate is not yet valid"
 msgstr "ATTENTION ! Le certificat du serveur n'est pas encore valide"
 
-#: mutt_ssl_gnutls.c:963
+#: mutt_ssl_gnutls.c:970
 msgid "WARNING: Server certificate has expired"
 msgstr "ATTENTION ! Le certificat du serveur a expiré"
 
-#: mutt_ssl_gnutls.c:968
+#: mutt_ssl_gnutls.c:975
 msgid "WARNING: Server certificate has been revoked"
 msgstr "ATTENTION ! Le certificat du serveur a été révoqué"
 
-#: mutt_ssl_gnutls.c:973
+#: mutt_ssl_gnutls.c:980
 msgid "WARNING: Server hostname does not match certificate"
 msgstr "ATTENTION ! Le nom du serveur ne correspond pas au certificat"
 
-#: mutt_ssl_gnutls.c:978
+#: mutt_ssl_gnutls.c:985
 msgid "WARNING: Signer of server certificate is not a CA"
 msgstr "ATTENTION ! Le signataire du certificat du serveur n'est pas un CA"
 
-#: mutt_ssl_gnutls.c:1079 mutt_ssl_gnutls.c:1114 mutt_ssl_gnutls.c:1124
+#: mutt_ssl_gnutls.c:999
+msgid "roa"
+msgstr "rua"
+
+#: mutt_ssl_gnutls.c:1004
+msgid "ro"
+msgstr "ru"
+
+#: mutt_ssl_gnutls.c:1086 mutt_ssl_gnutls.c:1121 mutt_ssl_gnutls.c:1131
 msgid "Unable to get certificate from peer"

Reply via email to