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

masaori pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/trafficserver.git


The following commit(s) were added to refs/heads/master by this push:
     new b8d546c  Cleanup: Separate TLS SessionTicket from SSLUtils
b8d546c is described below

commit b8d546c131495bde56dfc1ff7449604c6d3385da
Author: Masaori Koshiba <[email protected]>
AuthorDate: Mon Feb 25 11:03:16 2019 +0900

    Cleanup: Separate TLS SessionTicket from SSLUtils
---
 iocore/net/Makefile.am         |   5 +-
 iocore/net/SSLCertLookup.cc    |  26 ++++-----
 iocore/net/SSLConfig.cc        |  14 ++---
 iocore/net/SSLSessionTicket.cc | 117 +++++++++++++++++++++++++++++++++++++++++
 iocore/net/SSLSessionTicket.h  |  42 +++++++++++++++
 iocore/net/SSLUtils.cc         | 107 ++++---------------------------------
 6 files changed, 186 insertions(+), 125 deletions(-)

diff --git a/iocore/net/Makefile.am b/iocore/net/Makefile.am
index 0971d5f..7e27fe5 100644
--- a/iocore/net/Makefile.am
+++ b/iocore/net/Makefile.am
@@ -134,7 +134,7 @@ libinknet_a_SOURCES = \
        ProxyProtocol.cc \
        Socks.cc \
        SSLCertLookup.cc \
-       SSLSessionCache.cc \
+       SSLClientUtils.cc \
        SSLConfig.cc \
        SSLDiags.cc \
        SSLInternal.cc \
@@ -145,8 +145,9 @@ libinknet_a_SOURCES = \
        SSLNextProtocolSet.cc \
        SSLSNIConfig.cc \
        SSLStats.cc \
+       SSLSessionCache.cc \
+       SSLSessionTicket.cc \
        SSLUtils.cc \
-       SSLClientUtils.cc \
        OCSPStapling.cc \
        Socks.cc \
        UDPIOEvent.cc \
diff --git a/iocore/net/SSLCertLookup.cc b/iocore/net/SSLCertLookup.cc
index f94f515..2b6e91d 100644
--- a/iocore/net/SSLCertLookup.cc
+++ b/iocore/net/SSLCertLookup.cc
@@ -21,12 +21,9 @@
   limitations under the License.
  */
 
-#include "tscore/ink_config.h"
-
 #include "P_SSLCertLookup.h"
-#include "P_SSLUtils.h"
-#include "P_SSLConfig.h"
-#include "I_EventSystem.h"
+
+#include "tscore/ink_config.h"
 #include "tscore/I_Layout.h"
 #include "tscore/MatcherUtils.h"
 #include "tscore/Regex.h"
@@ -35,17 +32,16 @@
 #include "tscore/bwf_std_format.h"
 #include "tscore/TestBox.h"
 
+#include "I_EventSystem.h"
+
+#include "P_SSLUtils.h"
+#include "P_SSLConfig.h"
+#include "SSLSessionTicket.h"
+
 #include <unordered_map>
 #include <vector>
 #include <algorithm>
 
-// Check if the ticket_key callback #define is available, and if so, enable 
session tickets.
-#ifdef SSL_CTX_set_tlsext_ticket_key_cb
-
-#define HAVE_OPENSSL_SESSION_TICKETS 1
-
-#endif /* SSL_CTX_set_tlsext_ticket_key_cb */
-
 struct SSLAddressLookupKey {
   explicit SSLAddressLookupKey(const IpEndpoint &ip)
   {
@@ -201,7 +197,7 @@ fail:
 ssl_ticket_key_block *
 ssl_create_ticket_keyblock(const char *ticket_key_path)
 {
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
   ats_scoped_str ticket_key_data;
   int ticket_key_len;
   ssl_ticket_key_block *keyblock = nullptr;
@@ -226,10 +222,10 @@ fail:
   ticket_block_free(keyblock);
   return nullptr;
 
-#else  /* !HAVE_OPENSSL_SESSION_TICKETS */
+#else  /* !TS_HAVE_OPENSSL_SESSION_TICKETS */
   (void)ticket_key_path;
   return nullptr;
-#endif /* HAVE_OPENSSL_SESSION_TICKETS */
+#endif /* TS_HAVE_OPENSSL_SESSION_TICKETS */
 }
 void
 SSLCertContext::release()
diff --git a/iocore/net/SSLConfig.cc b/iocore/net/SSLConfig.cc
index 26a65a4..d822ce4 100644
--- a/iocore/net/SSLConfig.cc
+++ b/iocore/net/SSLConfig.cc
@@ -43,8 +43,9 @@
 #include "P_Net.h"
 #include "P_SSLUtils.h"
 #include "P_SSLCertLookup.h"
-#include "SSLSessionCache.h"
 #include "SSLDiags.h"
+#include "SSLSessionCache.h"
+#include "SSLSessionTicket.h"
 #include "YamlSNIConfig.h"
 
 int SSLConfig::configid                                     = 0;
@@ -71,13 +72,6 @@ static 
std::unique_ptr<ConfigUpdateHandler<SSLCertificateConfig>> sslCertUpdate;
 static std::unique_ptr<ConfigUpdateHandler<SSLConfig>> sslConfigUpdate;
 static std::unique_ptr<ConfigUpdateHandler<SSLTicketKeyConfig>> sslTicketKey;
 
-// Check if the ticket_key callback #define is available, and if so, enable 
session tickets.
-#ifdef SSL_CTX_set_tlsext_ticket_key_cb
-
-#define HAVE_OPENSSL_SESSION_TICKETS 1
-
-#endif /* SSL_CTX_set_tlsext_ticket_key_cb */
-
 SSLConfigParams::SSLConfigParams()
 {
   ink_mutex_init(&ctxMapLock);
@@ -563,7 +557,7 @@ SSLTicketParams::LoadTicket()
 {
   cleanup();
 
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
   ssl_ticket_key_block *keyblock = nullptr;
 
   SSLConfig::scoped_config params;
@@ -611,7 +605,7 @@ void
 SSLTicketParams::LoadTicketData(char *ticket_data, int ticket_data_len)
 {
   cleanup();
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
   if (ticket_data != nullptr && ticket_data_len > 0) {
     default_global_keyblock = ticket_block_create(ticket_data, 
ticket_data_len);
   } else {
diff --git a/iocore/net/SSLSessionTicket.cc b/iocore/net/SSLSessionTicket.cc
new file mode 100644
index 0000000..151c64a
--- /dev/null
+++ b/iocore/net/SSLSessionTicket.cc
@@ -0,0 +1,117 @@
+/** @file
+
+  SessionTicket TLS Extension
+
+  @section license License
+
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+ */
+
+#include "SSLSessionTicket.h"
+
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
+
+#include "tscore/MatcherUtils.h"
+
+#include "P_Net.h"
+#include "SSLStats.h"
+#include "P_SSLConfig.h"
+
+// Remvoe this when drop OpenSSL 1.0.2 support
+#ifndef evp_md_func
+#ifdef OPENSSL_NO_SHA256
+#define evp_md_func EVP_sha1()
+#else
+#define evp_md_func EVP_sha256()
+#endif
+#endif
+
+void
+ssl_session_ticket_free(void * /*parent*/, void *ptr, CRYPTO_EX_DATA * /*ad*/, 
int /*idx*/, long /*argl*/, void * /*argp*/)
+{
+  ticket_block_free((struct ssl_ticket_key_block *)ptr);
+}
+
+/*
+ * RFC 5077. Create session ticket to resume SSL session without requiring 
session-specific state at the TLS server.
+ * Specifically, it distributes the encrypted session-state information to the 
client in the form of a ticket and
+ * a mechanism to present the ticket back to the server.
+ * */
+int
+ssl_callback_session_ticket(SSL *ssl, unsigned char *keyname, unsigned char 
*iv, EVP_CIPHER_CTX *cipher_ctx, HMAC_CTX *hctx,
+                            int enc)
+{
+  SSLCertificateConfig::scoped_config lookup;
+  SSLTicketKeyConfig::scoped_config params;
+  SSLNetVConnection *netvc = SSLNetVCAccess(ssl);
+
+  // Get the IP address to look up the keyblock
+  IpEndpoint ip;
+  int namelen        = sizeof(ip);
+  SSLCertContext *cc = nullptr;
+  if (0 == safe_getsockname(netvc->get_socket(), &ip.sa, &namelen)) {
+    cc = lookup->find(ip);
+  }
+  ssl_ticket_key_block *keyblock = nullptr;
+  if (cc == nullptr || cc->keyblock == nullptr) {
+    // Try the default
+    keyblock = params->default_global_keyblock;
+  } else {
+    keyblock = cc->keyblock;
+  }
+  ink_release_assert(keyblock != nullptr && keyblock->num_keys > 0);
+
+  if (enc == 1) {
+    const ssl_ticket_key_t &most_recent_key = keyblock->keys[0];
+    memcpy(keyname, most_recent_key.key_name, 
sizeof(most_recent_key.key_name));
+    RAND_bytes(iv, EVP_MAX_IV_LENGTH);
+    EVP_EncryptInit_ex(cipher_ctx, EVP_aes_128_cbc(), nullptr, 
most_recent_key.aes_key, iv);
+    HMAC_Init_ex(hctx, most_recent_key.hmac_secret, 
sizeof(most_recent_key.hmac_secret), evp_md_func, nullptr);
+
+    Debug("ssl", "create ticket for a new session.");
+    SSL_INCREMENT_DYN_STAT(ssl_total_tickets_created_stat);
+    return 1;
+  } else if (enc == 0) {
+    for (unsigned i = 0; i < keyblock->num_keys; ++i) {
+      if (memcmp(keyname, keyblock->keys[i].key_name, 
sizeof(keyblock->keys[i].key_name)) == 0) {
+        EVP_DecryptInit_ex(cipher_ctx, EVP_aes_128_cbc(), nullptr, 
keyblock->keys[i].aes_key, iv);
+        HMAC_Init_ex(hctx, keyblock->keys[i].hmac_secret, 
sizeof(keyblock->keys[i].hmac_secret), evp_md_func, nullptr);
+
+        Debug("ssl", "verify the ticket for an existing session.");
+        // Increase the total number of decrypted tickets.
+        SSL_INCREMENT_DYN_STAT(ssl_total_tickets_verified_stat);
+
+        if (i != 0) { // The number of tickets decrypted with "older" keys.
+          SSL_INCREMENT_DYN_STAT(ssl_total_tickets_verified_old_key_stat);
+        }
+
+        SSLNetVConnection *netvc = SSLNetVCAccess(ssl);
+        netvc->setSSLSessionCacheHit(true);
+        // When we decrypt with an "older" key, encrypt the ticket again with 
the most recent key.
+        return (i == 0) ? 1 : 2;
+      }
+    }
+
+    Debug("ssl", "keyname is not consistent.");
+    SSL_INCREMENT_DYN_STAT(ssl_total_tickets_not_found_stat);
+    return 0;
+  }
+
+  return -1;
+}
+
+#endif /* TS_HAVE_OPENSSL_SESSION_TICKETS */
diff --git a/iocore/net/SSLSessionTicket.h b/iocore/net/SSLSessionTicket.h
new file mode 100644
index 0000000..be520cb
--- /dev/null
+++ b/iocore/net/SSLSessionTicket.h
@@ -0,0 +1,42 @@
+/** @file
+
+  SessionTicket TLS Extension
+
+  @section license License
+
+  Licensed to the Apache Software Foundation (ASF) under one
+  or more contributor license agreements.  See the NOTICE file
+  distributed with this work for additional information
+  regarding copyright ownership.  The ASF licenses this file
+  to you under the Apache License, Version 2.0 (the
+  "License"); you may not use this file except in compliance
+  with the License.  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+ */
+
+#pragma once
+
+#include <openssl/safestack.h>
+#include <openssl/tls1.h>
+
+// Check if the ticket_key callback #define is available, and if so, enable 
session tickets.
+#ifdef SSL_CTX_set_tlsext_ticket_key_cb
+#define TS_HAVE_OPENSSL_SESSION_TICKETS 1
+#endif
+
+#ifdef TS_HAVE_OPENSSL_SESSION_TICKETS
+
+#include <openssl/crypto.h>
+#include <openssl/hmac.h>
+
+void ssl_session_ticket_free(void *, void *, CRYPTO_EX_DATA *, int, long, void 
*);
+int ssl_callback_session_ticket(SSL *, unsigned char *, unsigned char *, 
EVP_CIPHER_CTX *, HMAC_CTX *, int);
+
+#endif /* TS_HAVE_OPENSSL_SESSION_TICKETS */
diff --git a/iocore/net/SSLUtils.cc b/iocore/net/SSLUtils.cc
index c2e7061..1e48bf2 100644
--- a/iocore/net/SSLUtils.cc
+++ b/iocore/net/SSLUtils.cc
@@ -36,6 +36,7 @@
 #include "P_SSLSNI.h"
 #include "P_SSLConfig.h"
 #include "SSLSessionCache.h"
+#include "SSLSessionTicket.h"
 #include "SSLDynlock.h"
 #include "SSLDiags.h"
 #include "SSLStats.h"
@@ -59,10 +60,6 @@
 #include <openssl/evp.h>
 #endif
 
-#if HAVE_OPENSSL_HMAC_H
-#include <openssl/hmac.h>
-#endif
-
 #if HAVE_OPENSSL_TS_H
 #include <openssl/ts.h>
 #endif
@@ -130,16 +127,7 @@ struct ssl_user_config {
 
 SSLSessionCache *session_cache; // declared extern in P_SSLConfig.h
 
-// Check if the ticket_key callback #define is available, and if so, enable 
session tickets.
-#ifdef SSL_CTX_set_tlsext_ticket_key_cb
-
-#define HAVE_OPENSSL_SESSION_TICKETS 1
-
-static void session_ticket_free(void *, void *, CRYPTO_EX_DATA *, int, long, 
void *);
-static int ssl_callback_session_ticket(SSL *, unsigned char *, unsigned char 
*, EVP_CIPHER_CTX *, HMAC_CTX *, int);
-#endif /* SSL_CTX_set_tlsext_ticket_key_cb */
-
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
 static int ssl_session_ticket_index = -1;
 #endif
 
@@ -376,7 +364,7 @@ set_context_cert(SSL *ssl)
 
   if (ctx != nullptr) {
     SSL_set_SSL_CTX(ssl, ctx);
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
     // Reset the ticket callback if needed
     SSL_CTX_set_tlsext_ticket_key_cb(ctx, ssl_callback_session_ticket);
 #endif
@@ -714,7 +702,7 @@ ssl_context_enable_ecdh(SSL_CTX *ctx)
 static ssl_ticket_key_block *
 ssl_context_enable_tickets(SSL_CTX *ctx, const char *ticket_key_path)
 {
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
   ssl_ticket_key_block *keyblock = nullptr;
 
   keyblock = ssl_create_ticket_keyblock(ticket_key_path);
@@ -736,10 +724,10 @@ ssl_context_enable_tickets(SSL_CTX *ctx, const char 
*ticket_key_path)
   SSL_CTX_clear_options(ctx, SSL_OP_NO_TICKET);
   return keyblock;
 
-#else  /* !HAVE_OPENSSL_SESSION_TICKETS */
+#else  /* !TS_HAVE_OPENSSL_SESSION_TICKETS */
   (void)ticket_key_path;
   return nullptr;
-#endif /* HAVE_OPENSSL_SESSION_TICKETS */
+#endif /* TS_HAVE_OPENSSL_SESSION_TICKETS */
 }
 
 struct passphrase_cb_userdata {
@@ -1015,8 +1003,8 @@ SSLInitializeLibrary()
     CRYPTO_set_dynlock_destroy_callback(ssl_dyn_destroy_callback);
   }
 
-#ifdef SSL_CTX_set_tlsext_ticket_key_cb
-  ssl_session_ticket_index = SSL_CTX_get_ex_new_index(0, nullptr, nullptr, 
nullptr, session_ticket_free);
+#ifdef TS_HAVE_OPENSSL_SESSION_TICKETS
+  ssl_session_ticket_index = SSL_CTX_get_ex_new_index(0, nullptr, nullptr, 
nullptr, ssl_session_ticket_free);
   if (ssl_session_ticket_index == -1) {
     SSLError("failed to create session ticket index");
   }
@@ -1705,7 +1693,7 @@ ssl_store_ssl_context(const SSLConfigParams *params, 
SSLCertLookup *lookup, cons
     }
   }
   if (!inserted) {
-#if HAVE_OPENSSL_SESSION_TICKETS
+#if TS_HAVE_OPENSSL_SESSION_TICKETS
     if (keyblock != nullptr) {
       ticket_block_free(keyblock);
     }
@@ -1879,83 +1867,6 @@ SSLParseCertificateConfiguration(const SSLConfigParams 
*params, SSLCertLookup *l
   return true;
 }
 
-#if HAVE_OPENSSL_SESSION_TICKETS
-
-static void
-session_ticket_free(void * /*parent*/, void *ptr, CRYPTO_EX_DATA * /*ad*/, int 
/*idx*/, long /*argl*/, void * /*argp*/)
-{
-  ticket_block_free((struct ssl_ticket_key_block *)ptr);
-}
-
-/*
- * RFC 5077. Create session ticket to resume SSL session without requiring 
session-specific state at the TLS server.
- * Specifically, it distributes the encrypted session-state information to the 
client in the form of a ticket and
- * a mechanism to present the ticket back to the server.
- * */
-static int
-ssl_callback_session_ticket(SSL *ssl, unsigned char *keyname, unsigned char 
*iv, EVP_CIPHER_CTX *cipher_ctx, HMAC_CTX *hctx,
-                            int enc)
-{
-  SSLCertificateConfig::scoped_config lookup;
-  SSLTicketKeyConfig::scoped_config params;
-  SSLNetVConnection *netvc = SSLNetVCAccess(ssl);
-
-  // Get the IP address to look up the keyblock
-  IpEndpoint ip;
-  int namelen        = sizeof(ip);
-  SSLCertContext *cc = nullptr;
-  if (0 == safe_getsockname(netvc->get_socket(), &ip.sa, &namelen)) {
-    cc = lookup->find(ip);
-  }
-  ssl_ticket_key_block *keyblock = nullptr;
-  if (cc == nullptr || cc->keyblock == nullptr) {
-    // Try the default
-    keyblock = params->default_global_keyblock;
-  } else {
-    keyblock = cc->keyblock;
-  }
-  ink_release_assert(keyblock != nullptr && keyblock->num_keys > 0);
-
-  if (enc == 1) {
-    const ssl_ticket_key_t &most_recent_key = keyblock->keys[0];
-    memcpy(keyname, most_recent_key.key_name, 
sizeof(most_recent_key.key_name));
-    RAND_bytes(iv, EVP_MAX_IV_LENGTH);
-    EVP_EncryptInit_ex(cipher_ctx, EVP_aes_128_cbc(), nullptr, 
most_recent_key.aes_key, iv);
-    HMAC_Init_ex(hctx, most_recent_key.hmac_secret, 
sizeof(most_recent_key.hmac_secret), evp_md_func, nullptr);
-
-    Debug("ssl", "create ticket for a new session.");
-    SSL_INCREMENT_DYN_STAT(ssl_total_tickets_created_stat);
-    return 1;
-  } else if (enc == 0) {
-    for (unsigned i = 0; i < keyblock->num_keys; ++i) {
-      if (memcmp(keyname, keyblock->keys[i].key_name, 
sizeof(keyblock->keys[i].key_name)) == 0) {
-        EVP_DecryptInit_ex(cipher_ctx, EVP_aes_128_cbc(), nullptr, 
keyblock->keys[i].aes_key, iv);
-        HMAC_Init_ex(hctx, keyblock->keys[i].hmac_secret, 
sizeof(keyblock->keys[i].hmac_secret), evp_md_func, nullptr);
-
-        Debug("ssl", "verify the ticket for an existing session.");
-        // Increase the total number of decrypted tickets.
-        SSL_INCREMENT_DYN_STAT(ssl_total_tickets_verified_stat);
-
-        if (i != 0) { // The number of tickets decrypted with "older" keys.
-          SSL_INCREMENT_DYN_STAT(ssl_total_tickets_verified_old_key_stat);
-        }
-
-        SSLNetVConnection *netvc = SSLNetVCAccess(ssl);
-        netvc->setSSLSessionCacheHit(true);
-        // When we decrypt with an "older" key, encrypt the ticket again with 
the most recent key.
-        return (i == 0) ? 1 : 2;
-      }
-    }
-
-    Debug("ssl", "keyname is not consistent.");
-    SSL_INCREMENT_DYN_STAT(ssl_total_tickets_not_found_stat);
-    return 0;
-  }
-
-  return -1;
-}
-#endif /* HAVE_OPENSSL_SESSION_TICKETS */
-
 // Release SSL_CTX and the associated data. This works for both
 // client and server contexts and gracefully accepts nullptr.
 void

Reply via email to