You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@trafficserver.apache.org by jp...@apache.org on 2016/05/02 00:54:25 UTC

[trafficserver] 02/04: TS-4373: Move SSL_CTX setup out of ssl_store_ssl_context.

This is an automated email from the ASF dual-hosted git repository.

jpeach pushed a commit to branch master
in repository https://git-dual.apache.org/repos/asf/trafficserver.git

commit c15a957addee610b2b8314108a2e83c02b483fef
Author: David Calavera <da...@gmail.com>
AuthorDate: Thu Apr 21 09:59:19 2016 -0700

    TS-4373: Move SSL_CTX setup out of ssl_store_ssl_context.
    
    Refactor ssl_store_ssl_context method to separate context initialization
    and configuration from inserting the context into the SSLCertLookup.
    
    (cherry picked from commit 8b248f4493c0e6e53c4fbc8cbdf618fabc0e818f)
    
    Signed-off-by: David Calavera <da...@gmail.com>
     Please enter the commit message for your changes. Lines starting
---
 iocore/net/SSLUtils.cc | 301 +++++++++++++++++++++++--------------------------
 proxy/InkAPI.cc        |   2 +-
 proxy/api/ts/ts.h      |   1 -
 3 files changed, 144 insertions(+), 160 deletions(-)

diff --git a/iocore/net/SSLUtils.cc b/iocore/net/SSLUtils.cc
index ed80cf4..30e4466 100644
--- a/iocore/net/SSLUtils.cc
+++ b/iocore/net/SSLUtils.cc
@@ -1281,6 +1281,129 @@ SSLCheckServerCertNow(X509 *cert, const char *certname)
 
 } /* CheckServerCertNow() */
 
+static char *
+asn1_strdup(ASN1_STRING *s)
+{
+  // Make sure we have an 8-bit encoding.
+  ink_assert(ASN1_STRING_type(s) == V_ASN1_IA5STRING || ASN1_STRING_type(s) == V_ASN1_UTF8STRING ||
+             ASN1_STRING_type(s) == V_ASN1_PRINTABLESTRING || ASN1_STRING_type(s) == V_ASN1_T61STRING);
+
+  return ats_strndup((const char *)ASN1_STRING_data(s), ASN1_STRING_length(s));
+}
+
+// Given a certificate and it's corresponding SSL_CTX context, insert hash
+// table aliases for subject CN and subjectAltNames DNS without wildcard,
+// insert trie aliases for those with wildcard.
+static bool
+ssl_index_certificate(SSLCertLookup *lookup, SSLCertContext const &cc, X509 *cert, const char *certname)
+{
+  X509_NAME *subject = NULL;
+  bool inserted = false;
+
+  if (NULL == cert) {
+    Error("Failed to load certificate %s", certname);
+    lookup->is_valid = false;
+    return false;
+  }
+
+  // Insert a key for the subject CN.
+  subject = X509_get_subject_name(cert);
+  ats_scoped_str subj_name;
+  if (subject) {
+    int pos = -1;
+    for (;;) {
+      pos = X509_NAME_get_index_by_NID(subject, NID_commonName, pos);
+      if (pos == -1) {
+        break;
+      }
+
+      X509_NAME_ENTRY *e = X509_NAME_get_entry(subject, pos);
+      ASN1_STRING *cn = X509_NAME_ENTRY_get_data(e);
+      subj_name = asn1_strdup(cn);
+
+      Debug("ssl", "mapping '%s' to certificate %s", (const char *)subj_name, certname);
+      if (lookup->insert(subj_name, cc) >= 0)
+        inserted = true;
+    }
+  }
+
+#if HAVE_OPENSSL_TS_H
+  // Traverse the subjectAltNames (if any) and insert additional keys for the SSL context.
+  GENERAL_NAMES *names = (GENERAL_NAMES *)X509_get_ext_d2i(cert, NID_subject_alt_name, NULL, NULL);
+  if (names) {
+    unsigned count = sk_GENERAL_NAME_num(names);
+    for (unsigned i = 0; i < count; ++i) {
+      GENERAL_NAME *name;
+
+      name = sk_GENERAL_NAME_value(names, i);
+      if (name->type == GEN_DNS) {
+        ats_scoped_str dns(asn1_strdup(name->d.dNSName));
+        // only try to insert if the alternate name is not the main name
+        if (strcmp(dns, subj_name) != 0) {
+          Debug("ssl", "mapping '%s' to certificates %s", (const char *)dns, certname);
+          if (lookup->insert(dns, cc) >= 0)
+            inserted = true;
+        }
+      }
+    }
+
+    GENERAL_NAMES_free(names);
+  }
+#endif // HAVE_OPENSSL_TS_H
+  return inserted;
+}
+
+// This callback function is executed while OpenSSL processes the SSL
+// handshake and does SSL record layer stuff.  It's used to trap
+// client-initiated renegotiations and update cipher stats
+static void
+ssl_callback_info(const SSL *ssl, int where, int ret)
+{
+  Debug("ssl", "ssl_callback_info ssl: %p where: %d ret: %d", ssl, where, ret);
+  SSLNetVConnection *netvc = (SSLNetVConnection *)SSL_get_app_data(ssl);
+
+  if ((where & SSL_CB_ACCEPT_LOOP) && netvc->getSSLHandShakeComplete() == true &&
+      SSLConfigParams::ssl_allow_client_renegotiation == false) {
+    int state = SSL_get_state(ssl);
+
+// TODO: ifdef can be removed in the future
+// Support for SSL23 only if we have it
+#ifdef SSL23_ST_SR_CLNT_HELLO_A
+    if (state == SSL3_ST_SR_CLNT_HELLO_A || state == SSL23_ST_SR_CLNT_HELLO_A) {
+#else
+    if (state == SSL3_ST_SR_CLNT_HELLO_A) {
+#endif
+      netvc->setSSLClientRenegotiationAbort(true);
+      Debug("ssl", "ssl_callback_info trying to renegotiate from the client");
+    }
+  }
+  if (where & SSL_CB_HANDSHAKE_DONE) {
+    // handshake is complete
+    const SSL_CIPHER *cipher = SSL_get_current_cipher(ssl);
+    if (cipher) {
+      const char *cipherName = SSL_CIPHER_get_name(cipher);
+      // lookup index of stat by name and incr count
+      InkHashTableValue data;
+      if (ink_hash_table_lookup(ssl_cipher_name_table, cipherName, &data)) {
+        SSL_INCREMENT_DYN_STAT((intptr_t)data);
+      }
+    }
+  }
+}
+
+static void
+ssl_set_handshake_callbacks(SSL_CTX *ctx)
+{
+#if TS_USE_TLS_SNI
+// Make sure the callbacks are set
+#if TS_USE_CERT_CB
+  SSL_CTX_set_cert_cb(ctx, ssl_cert_callback, NULL);
+#else
+  SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_callback);
+#endif
+#endif
+}
+
 SSL_CTX *
 SSLInitServerContext(const SSLConfigParams *params, const ssl_user_config &sslMultCertSettings, Vec<X509 *> &certList)
 {
@@ -1550,149 +1673,9 @@ SSLInitServerContext(const SSLConfigParams *params, const ssl_user_config &sslMu
   if (!ssl_context_enable_dhe(params->dhparamsFile, ctx)) {
     goto fail;
   }
-  return ssl_context_enable_ecdh(ctx);
-
-fail:
-  SSL_CLEAR_PW_REFERENCES(ud, ctx)
-  SSLReleaseContext(ctx);
-  for (unsigned int i = 0; i < certList.length(); i++) {
-    X509_free(certList[i]);
-  }
-
-  return NULL;
-}
-
-static char *
-asn1_strdup(ASN1_STRING *s)
-{
-  // Make sure we have an 8-bit encoding.
-  ink_assert(ASN1_STRING_type(s) == V_ASN1_IA5STRING || ASN1_STRING_type(s) == V_ASN1_UTF8STRING ||
-             ASN1_STRING_type(s) == V_ASN1_PRINTABLESTRING || ASN1_STRING_type(s) == V_ASN1_T61STRING);
-
-  return ats_strndup((const char *)ASN1_STRING_data(s), ASN1_STRING_length(s));
-}
-
-// Given a certificate and it's corresponding SSL_CTX context, insert hash
-// table aliases for subject CN and subjectAltNames DNS without wildcard,
-// insert trie aliases for those with wildcard.
-static bool
-ssl_index_certificate(SSLCertLookup *lookup, SSLCertContext const &cc, X509 *cert, const char *certname)
-{
-  X509_NAME *subject = NULL;
-  bool inserted = false;
-
-  if (NULL == cert) {
-    Error("Failed to load certificate %s", certname);
-    lookup->is_valid = false;
-    return false;
-  }
 
-  // Insert a key for the subject CN.
-  subject = X509_get_subject_name(cert);
-  ats_scoped_str subj_name;
-  if (subject) {
-    int pos = -1;
-    for (;;) {
-      pos = X509_NAME_get_index_by_NID(subject, NID_commonName, pos);
-      if (pos == -1) {
-        break;
-      }
-
-      X509_NAME_ENTRY *e = X509_NAME_get_entry(subject, pos);
-      ASN1_STRING *cn = X509_NAME_ENTRY_get_data(e);
-      subj_name = asn1_strdup(cn);
-
-      Debug("ssl", "mapping '%s' to certificate %s", (const char *)subj_name, certname);
-      if (lookup->insert(subj_name, cc) >= 0)
-        inserted = true;
-    }
-  }
+  ssl_context_enable_ecdh(ctx);
 
-#if HAVE_OPENSSL_TS_H
-  // Traverse the subjectAltNames (if any) and insert additional keys for the SSL context.
-  GENERAL_NAMES *names = (GENERAL_NAMES *)X509_get_ext_d2i(cert, NID_subject_alt_name, NULL, NULL);
-  if (names) {
-    unsigned count = sk_GENERAL_NAME_num(names);
-    for (unsigned i = 0; i < count; ++i) {
-      GENERAL_NAME *name;
-
-      name = sk_GENERAL_NAME_value(names, i);
-      if (name->type == GEN_DNS) {
-        ats_scoped_str dns(asn1_strdup(name->d.dNSName));
-        // only try to insert if the alternate name is not the main name
-        if (strcmp(dns, subj_name) != 0) {
-          Debug("ssl", "mapping '%s' to certificates %s", (const char *)dns, certname);
-          if (lookup->insert(dns, cc) >= 0)
-            inserted = true;
-        }
-      }
-    }
-
-    GENERAL_NAMES_free(names);
-  }
-#endif // HAVE_OPENSSL_TS_H
-  return inserted;
-}
-
-// This callback function is executed while OpenSSL processes the SSL
-// handshake and does SSL record layer stuff.  It's used to trap
-// client-initiated renegotiations and update cipher stats
-static void
-ssl_callback_info(const SSL *ssl, int where, int ret)
-{
-  Debug("ssl", "ssl_callback_info ssl: %p where: %d ret: %d", ssl, where, ret);
-  SSLNetVConnection *netvc = (SSLNetVConnection *)SSL_get_app_data(ssl);
-
-  if ((where & SSL_CB_ACCEPT_LOOP) && netvc->getSSLHandShakeComplete() == true &&
-      SSLConfigParams::ssl_allow_client_renegotiation == false) {
-    int state = SSL_get_state(ssl);
-
-// TODO: ifdef can be removed in the future
-// Support for SSL23 only if we have it
-#ifdef SSL23_ST_SR_CLNT_HELLO_A
-    if (state == SSL3_ST_SR_CLNT_HELLO_A || state == SSL23_ST_SR_CLNT_HELLO_A) {
-#else
-    if (state == SSL3_ST_SR_CLNT_HELLO_A) {
-#endif
-      netvc->setSSLClientRenegotiationAbort(true);
-      Debug("ssl", "ssl_callback_info trying to renegotiate from the client");
-    }
-  }
-  if (where & SSL_CB_HANDSHAKE_DONE) {
-    // handshake is complete
-    const SSL_CIPHER *cipher = SSL_get_current_cipher(ssl);
-    if (cipher) {
-      const char *cipherName = SSL_CIPHER_get_name(cipher);
-      // lookup index of stat by name and incr count
-      InkHashTableValue data;
-      if (ink_hash_table_lookup(ssl_cipher_name_table, cipherName, &data)) {
-        SSL_INCREMENT_DYN_STAT((intptr_t)data);
-      }
-    }
-  }
-}
-
-static void
-ssl_set_handshake_callbacks(SSL_CTX *ctx)
-{
-#if TS_USE_TLS_SNI
-// Make sure the callbacks are set
-#if TS_USE_CERT_CB
-  SSL_CTX_set_cert_cb(ctx, ssl_cert_callback, NULL);
-#else
-  SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_callback);
-#endif
-#endif
-}
-
-SSL_CTX *
-SSLCreateServerContext(const SSLConfigParams *params) {
-  Vec<X509 *> cert_list;
-  const ssl_user_config sslMultCertSettings;
-  SSL_CTX *ctx = SSLInitServerContext(params, sslMultCertSettings, cert_list);
-
-  // The certificate callbacks are set by the caller only
-  // for the default certificate
   SSL_CTX_set_info_callback(ctx, ssl_callback_info);
 
 #if TS_USE_TLS_NPN
@@ -1703,9 +1686,6 @@ SSLCreateServerContext(const SSLConfigParams *params) {
   SSL_CTX_set_alpn_select_cb(ctx, SSLNetVConnection::select_next_protocol, NULL);
 #endif /* TS_USE_TLS_ALPN */
 
-  // TODO: Allow control over tickets and ticket path when using SSLCreateServerContext
-  ssl_context_enable_tickets(ctx, NULL);
-
 #ifdef HAVE_OPENSSL_OCSP_STAPLING
   if (SSLConfigParams::ssl_ocsp_enabled) {
     Debug("ssl", "ssl ocsp stapling is enabled");
@@ -1719,11 +1699,29 @@ SSLCreateServerContext(const SSLConfigParams *params) {
   }
 #endif /* HAVE_OPENSSL_OCSP_STAPLING */
 
-
   if (SSLConfigParams::init_ssl_ctx_cb) {
     SSLConfigParams::init_ssl_ctx_cb(ctx, true);
   }
   return ctx;
+
+fail:
+  SSL_CLEAR_PW_REFERENCES(ud, ctx)
+  SSLReleaseContext(ctx);
+  for (unsigned int i = 0; i < certList.length(); i++) {
+    X509_free(certList[i]);
+  }
+
+  return NULL;
+}
+
+SSL_CTX *
+SSLCreateServerContext(const SSLConfigParams *params)
+{
+  const ssl_user_config sslMultCertSettings;
+  Vec<X509 *> cert_list;
+  SSL_CTX *ctx = SSLInitServerContext(params, sslMultCertSettings, cert_list);
+  ink_assert(cert_list.length() == 0);
+  return ctx;
 }
 
 static SSL_CTX *
@@ -1739,19 +1737,6 @@ ssl_store_ssl_context(const SSLConfigParams *params, SSLCertLookup *lookup, cons
     return ctx;
   }
 
-  // The certificate callbacks are set by the caller only
-  // for the default certificate
-
-  SSL_CTX_set_info_callback(ctx, ssl_callback_info);
-
-#if TS_USE_TLS_NPN
-  SSL_CTX_set_next_protos_advertised_cb(ctx, SSLNetVConnection::advertise_next_protocol, NULL);
-#endif /* TS_USE_TLS_NPN */
-
-#if TS_USE_TLS_ALPN
-  SSL_CTX_set_alpn_select_cb(ctx, SSLNetVConnection::select_next_protocol, NULL);
-#endif /* TS_USE_TLS_ALPN */
-
   const char *certname = sslMultCertSettings.cert.get();
   for (unsigned i = 0; i < cert_list.length(); ++i) {
     if (0 > SSLCheckServerCertNow(cert_list[i], certname)) {
diff --git a/proxy/InkAPI.cc b/proxy/InkAPI.cc
index dd7f649..6b2bce2 100644
--- a/proxy/InkAPI.cc
+++ b/proxy/InkAPI.cc
@@ -8860,7 +8860,7 @@ TSSslServerContextCreate()
 tsapi void
 TSSslContextDestroy(TSSslContext ctx)
 {
-  SSLReleaseContext(reinterpret_cast<SSL_CTX*>(ctx));
+  SSLReleaseContext(reinterpret_cast<SSL_CTX *>(ctx));
 }
 
 tsapi int
diff --git a/proxy/api/ts/ts.h b/proxy/api/ts/ts.h
index 7fb07de..1aaaa5d 100644
--- a/proxy/api/ts/ts.h
+++ b/proxy/api/ts/ts.h
@@ -1231,7 +1231,6 @@ tsapi void TSSslContextDestroy(TSSslContext ctx);
 // Returns 1 if the sslp argument refers to a SSL connection
 tsapi int TSVConnIsSsl(TSVConn sslp);
 
-
 /* --------------------------------------------------------------------------
    HTTP transactions */
 tsapi void TSHttpTxnHookAdd(TSHttpTxn txnp, TSHttpHookID id, TSCont contp);

-- 
To stop receiving notification emails like this one, please contact
"commits@trafficserver.apache.org" <co...@trafficserver.apache.org>.