aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/libs/curl/lib/vtls/openssl.c
diff options
context:
space:
mode:
authorshadchin <shadchin@yandex-team.ru>2022-04-09 00:41:32 +0300
committershadchin <shadchin@yandex-team.ru>2022-04-09 00:41:32 +0300
commit3bbb3d7e7e261716b0a83c1a35022e5d36f7875f (patch)
tree96955fafe753aad4486b22280aafe9050c508954 /contrib/libs/curl/lib/vtls/openssl.c
parentbeae089571d44f32f0edd323496377d3abe1bce6 (diff)
downloadydb-3bbb3d7e7e261716b0a83c1a35022e5d36f7875f.tar.gz
CONTRIB-2513 Update contrib/libs/curl to 7.77.0
ref:88dc545867909534adecc7502c44301cabf1a899
Diffstat (limited to 'contrib/libs/curl/lib/vtls/openssl.c')
-rw-r--r--contrib/libs/curl/lib/vtls/openssl.c361
1 files changed, 227 insertions, 134 deletions
diff --git a/contrib/libs/curl/lib/vtls/openssl.c b/contrib/libs/curl/lib/vtls/openssl.c
index 6583300b3c..ebd7abc3b4 100644
--- a/contrib/libs/curl/lib/vtls/openssl.c
+++ b/contrib/libs/curl/lib/vtls/openssl.c
@@ -122,12 +122,6 @@
#define HAVE_ERR_REMOVE_THREAD_STATE 1
#endif
-#if !defined(HAVE_SSLV2_CLIENT_METHOD) || \
- OPENSSL_VERSION_NUMBER >= 0x10100000L /* 1.1.0+ has no SSLv2 */
-#undef OPENSSL_NO_SSL2 /* undef first to avoid compiler warnings */
-#define OPENSSL_NO_SSL2
-#endif
-
#if (OPENSSL_VERSION_NUMBER >= 0x10100000L) && /* OpenSSL 1.1.0+ */ \
!(defined(LIBRESSL_VERSION_NUMBER) && \
LIBRESSL_VERSION_NUMBER < 0x20700000L)
@@ -246,6 +240,10 @@ struct ssl_backend_data {
#endif
};
+static void ossl_associate_connection(struct Curl_easy *data,
+ struct connectdata *conn,
+ int sockindex);
+
/*
* Number of bytes to read from the random number seed file. This must be
* a finite value (because some entropy "files" like /dev/urandom have
@@ -625,7 +623,7 @@ SSL_CTX_use_certificate_blob(SSL_CTX *ctx, const struct curl_blob *blob,
goto end;
}
- if(x == NULL) {
+ if(!x) {
ret = 0;
goto end;
}
@@ -656,7 +654,7 @@ SSL_CTX_use_PrivateKey_blob(SSL_CTX *ctx, const struct curl_blob *blob,
ret = 0;
goto end;
}
- if(pkey == NULL) {
+ if(!pkey) {
ret = 0;
goto end;
}
@@ -669,7 +667,7 @@ SSL_CTX_use_PrivateKey_blob(SSL_CTX *ctx, const struct curl_blob *blob,
static int
SSL_CTX_use_certificate_chain_blob(SSL_CTX *ctx, const struct curl_blob *blob,
- const char *key_passwd)
+ const char *key_passwd)
{
/* SSL_CTX_add1_chain_cert introduced in OpenSSL 1.0.2 */
#if (OPENSSL_VERSION_NUMBER >= 0x1000200fL) && /* OpenSSL 1.0.2 or later */ \
@@ -687,7 +685,7 @@ SSL_CTX_use_certificate_chain_blob(SSL_CTX *ctx, const struct curl_blob *blob,
x = PEM_read_bio_X509_AUX(in, NULL,
passwd_callback, (void *)key_passwd);
- if(x == NULL) {
+ if(!x) {
ret = 0;
goto end;
}
@@ -731,7 +729,7 @@ SSL_CTX_use_certificate_chain_blob(SSL_CTX *ctx, const struct curl_blob *blob,
return ret;
#else
(void)ctx; /* unused */
- (void)in; /* unused */
+ (void)blob; /* unused */
(void)key_passwd; /* unused */
return 0;
#endif
@@ -875,7 +873,7 @@ int cert_stuff(struct Curl_easy *data,
STACK_OF(X509) *ca = NULL;
if(cert_blob) {
cert_bio = BIO_new_mem_buf(cert_blob->data, (int)(cert_blob->len));
- if(cert_bio == NULL) {
+ if(!cert_bio) {
failf(data,
"BIO_new_mem_buf NULL, " OSSL_PACKAGE
" error %s",
@@ -886,7 +884,7 @@ int cert_stuff(struct Curl_easy *data,
}
else {
cert_bio = BIO_new(BIO_s_file());
- if(cert_bio == NULL) {
+ if(!cert_bio) {
failf(data,
"BIO_new return NULL, " OSSL_PACKAGE
" error %s",
@@ -2262,12 +2260,10 @@ select_next_proto_cb(SSL *ssl,
struct connectdata *conn = data->conn;
(void)ssl;
-#ifdef USE_NGHTTP2
+#ifdef USE_HTTP2
if(data->state.httpwant >= CURL_HTTP_VERSION_2 &&
- !select_next_protocol(out, outlen, in, inlen, NGHTTP2_PROTO_VERSION_ID,
- NGHTTP2_PROTO_VERSION_ID_LEN)) {
- infof(data, "NPN, negotiated HTTP2 (%s)\n",
- NGHTTP2_PROTO_VERSION_ID);
+ !select_next_protocol(out, outlen, in, inlen, ALPN_H2, ALPN_H2_LENGTH)) {
+ infof(data, "NPN, negotiated HTTP2 (%s)\n", ALPN_H2);
conn->negnpn = CURL_HTTP_VERSION_2;
return SSL_TLSEXT_ERR_OK;
}
@@ -2518,6 +2514,67 @@ static int ossl_new_session_cb(SSL *ssl, SSL_SESSION *ssl_sessionid)
return res;
}
+static CURLcode load_cacert_from_memory(SSL_CTX *ctx,
+ const struct curl_blob *ca_info_blob)
+{
+ /* these need freed at the end */
+ BIO *cbio = NULL;
+ STACK_OF(X509_INFO) *inf = NULL;
+
+ /* everything else is just a reference */
+ int i, count = 0;
+ X509_STORE *cts = NULL;
+ X509_INFO *itmp = NULL;
+
+ if(ca_info_blob->len > (size_t)INT_MAX)
+ return CURLE_SSL_CACERT_BADFILE;
+
+ cts = SSL_CTX_get_cert_store(ctx);
+ if(!cts)
+ return CURLE_OUT_OF_MEMORY;
+
+ cbio = BIO_new_mem_buf(ca_info_blob->data, (int)ca_info_blob->len);
+ if(!cbio)
+ return CURLE_OUT_OF_MEMORY;
+
+ inf = PEM_X509_INFO_read_bio(cbio, NULL, NULL, NULL);
+ if(!inf) {
+ BIO_free(cbio);
+ return CURLE_SSL_CACERT_BADFILE;
+ }
+
+ /* add each entry from PEM file to x509_store */
+ for(i = 0; i < (int)sk_X509_INFO_num(inf); ++i) {
+ itmp = sk_X509_INFO_value(inf, i);
+ if(itmp->x509) {
+ if(X509_STORE_add_cert(cts, itmp->x509)) {
+ ++count;
+ }
+ else {
+ /* set count to 0 to return an error */
+ count = 0;
+ break;
+ }
+ }
+ if(itmp->crl) {
+ if(X509_STORE_add_crl(cts, itmp->crl)) {
+ ++count;
+ }
+ else {
+ /* set count to 0 to return an error */
+ count = 0;
+ break;
+ }
+ }
+ }
+
+ sk_X509_INFO_pop_free(inf, X509_INFO_free);
+ BIO_free(cbio);
+
+ /* if we didn't end up importing anything, treat that as an error */
+ return (count > 0 ? CURLE_OK : CURLE_SSL_CACERT_BADFILE);
+}
+
static CURLcode ossl_connect_step1(struct Curl_easy *data,
struct connectdata *conn, int sockindex)
{
@@ -2528,6 +2585,7 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
curl_socket_t sockfd = conn->sock[sockindex];
struct ssl_connect_data *connssl = &conn->ssl[sockindex];
ctx_option_t ctx_options = 0;
+ void *ssl_sessionid = NULL;
#ifdef SSL_CTRL_SET_TLSEXT_HOSTNAME
bool sni;
@@ -2545,8 +2603,11 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
#endif
char * const ssl_cert = SSL_SET_OPTION(primary.clientcert);
const struct curl_blob *ssl_cert_blob = SSL_SET_OPTION(primary.cert_blob);
+ const struct curl_blob *ca_info_blob = SSL_CONN_CONFIG(ca_info_blob);
const char * const ssl_cert_type = SSL_SET_OPTION(cert_type);
- const char * const ssl_cafile = SSL_CONN_CONFIG(CAfile);
+ const char * const ssl_cafile =
+ /* CURLOPT_CAINFO_BLOB overrides CURLOPT_CAINFO */
+ (ca_info_blob ? NULL : SSL_CONN_CONFIG(CAfile));
const char * const ssl_capath = SSL_CONN_CONFIG(CApath);
const bool verifypeer = SSL_CONN_CONFIG(verifypeer);
const char * const ssl_crlfile = SSL_SET_OPTION(CRLfile);
@@ -2581,31 +2642,11 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
use_sni(TRUE);
break;
case CURL_SSLVERSION_SSLv2:
-#ifdef OPENSSL_NO_SSL2
- failf(data, OSSL_PACKAGE " was built without SSLv2 support");
+ failf(data, "No SSLv2 support");
return CURLE_NOT_BUILT_IN;
-#else
-#ifdef USE_OPENSSL_SRP
- if(ssl_authtype == CURL_TLSAUTH_SRP)
- return CURLE_SSL_CONNECT_ERROR;
-#endif
- req_method = SSLv2_client_method();
- use_sni(FALSE);
- break;
-#endif
case CURL_SSLVERSION_SSLv3:
-#ifdef OPENSSL_NO_SSL3_METHOD
- failf(data, OSSL_PACKAGE " was built without SSLv3 support");
+ failf(data, "No SSLv3 support");
return CURLE_NOT_BUILT_IN;
-#else
-#ifdef USE_OPENSSL_SRP
- if(ssl_authtype == CURL_TLSAUTH_SRP)
- return CURLE_SSL_CONNECT_ERROR;
-#endif
- req_method = SSLv3_client_method();
- use_sni(FALSE);
- break;
-#endif
default:
failf(data, "Unrecognized parameter passed via CURLOPT_SSLVERSION");
return CURLE_SSL_CONNECT_ERROR;
@@ -2693,41 +2734,9 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
#endif
switch(ssl_version) {
- /* "--sslv2" option means SSLv2 only, disable all others */
case CURL_SSLVERSION_SSLv2:
-#if OPENSSL_VERSION_NUMBER >= 0x10100000L /* 1.1.0 */
- SSL_CTX_set_min_proto_version(backend->ctx, SSL2_VERSION);
- SSL_CTX_set_max_proto_version(backend->ctx, SSL2_VERSION);
-#else
- ctx_options |= SSL_OP_NO_SSLv3;
- ctx_options |= SSL_OP_NO_TLSv1;
-# if OPENSSL_VERSION_NUMBER >= 0x1000100FL
- ctx_options |= SSL_OP_NO_TLSv1_1;
- ctx_options |= SSL_OP_NO_TLSv1_2;
-# ifdef TLS1_3_VERSION
- ctx_options |= SSL_OP_NO_TLSv1_3;
-# endif
-# endif
-#endif
- break;
-
- /* "--sslv3" option means SSLv3 only, disable all others */
case CURL_SSLVERSION_SSLv3:
-#if OPENSSL_VERSION_NUMBER >= 0x10100000L /* 1.1.0 */
- SSL_CTX_set_min_proto_version(backend->ctx, SSL3_VERSION);
- SSL_CTX_set_max_proto_version(backend->ctx, SSL3_VERSION);
-#else
- ctx_options |= SSL_OP_NO_SSLv2;
- ctx_options |= SSL_OP_NO_TLSv1;
-# if OPENSSL_VERSION_NUMBER >= 0x1000100FL
- ctx_options |= SSL_OP_NO_TLSv1_1;
- ctx_options |= SSL_OP_NO_TLSv1_2;
-# ifdef TLS1_3_VERSION
- ctx_options |= SSL_OP_NO_TLSv1_3;
-# endif
-# endif
-#endif
- break;
+ return CURLE_NOT_BUILT_IN;
/* "--tlsv<x.y>" options mean TLS >= version <x.y> */
case CURL_SSLVERSION_DEFAULT:
@@ -2768,18 +2777,17 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
int cur = 0;
unsigned char protocols[128];
-#ifdef USE_NGHTTP2
+#ifdef USE_HTTP2
if(data->state.httpwant >= CURL_HTTP_VERSION_2
#ifndef CURL_DISABLE_PROXY
&& (!SSL_IS_PROXY() || !conn->bits.tunnel_proxy)
#endif
) {
- protocols[cur++] = NGHTTP2_PROTO_VERSION_ID_LEN;
+ protocols[cur++] = ALPN_H2_LENGTH;
- memcpy(&protocols[cur], NGHTTP2_PROTO_VERSION_ID,
- NGHTTP2_PROTO_VERSION_ID_LEN);
- cur += NGHTTP2_PROTO_VERSION_ID_LEN;
- infof(data, "ALPN, offering %s\n", NGHTTP2_PROTO_VERSION_ID);
+ memcpy(&protocols[cur], ALPN_H2, ALPN_H2_LENGTH);
+ cur += ALPN_H2_LENGTH;
+ infof(data, "ALPN, offering %s\n", ALPN_H2);
}
#endif
@@ -2885,8 +2893,7 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
if((SSL_CONN_CONFIG(verifypeer) || SSL_CONN_CONFIG(verifyhost)) &&
(SSL_SET_OPTION(native_ca_store))) {
X509_STORE *store = SSL_CTX_get_cert_store(backend->ctx);
- HCERTSTORE hStore = CertOpenSystemStore((HCRYPTPROV_LEGACY)NULL,
- TEXT("ROOT"));
+ HCERTSTORE hStore = CertOpenSystemStore(0, TEXT("ROOT"));
if(hStore) {
PCCERT_CONTEXT pContext = NULL;
@@ -3023,6 +3030,19 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
}
#endif
+ if(ca_info_blob) {
+ result = load_cacert_from_memory(backend->ctx, ca_info_blob);
+ if(result) {
+ if(result == CURLE_OUT_OF_MEMORY ||
+ (verifypeer && !imported_native_ca)) {
+ failf(data, "error importing CA certificate blob");
+ return result;
+ }
+ /* Only warning if no certificate verification is required. */
+ infof(data, "error importing CA certificate blob, continuing anyway\n");
+ }
+ }
+
#if defined(OPENSSL_VERSION_MAJOR) && (OPENSSL_VERSION_MAJOR >= 3)
/* OpenSSL 3.0.0 has deprecated SSL_CTX_load_verify_locations */
{
@@ -3079,7 +3099,8 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
#endif
#ifdef CURL_CA_FALLBACK
- if(verifypeer && !ssl_cafile && !ssl_capath && !imported_native_ca) {
+ if(verifypeer &&
+ !ca_info_blob && !ssl_cafile && !ssl_capath && !imported_native_ca) {
/* verifying the peer without any CA certificates won't
work so use openssl's built in default as fallback */
SSL_CTX_set_default_verify_paths(backend->ctx);
@@ -3209,46 +3230,23 @@ static CURLcode ossl_connect_step1(struct Curl_easy *data,
}
#endif
- /* Check if there's a cached ID we can/should use here! */
- if(SSL_SET_OPTION(primary.sessionid)) {
- void *ssl_sessionid = NULL;
- int data_idx = ossl_get_ssl_data_index();
- int connectdata_idx = ossl_get_ssl_conn_index();
- int sockindex_idx = ossl_get_ssl_sockindex_index();
- int proxy_idx = ossl_get_proxy_index();
+ ossl_associate_connection(data, conn, sockindex);
- if(data_idx >= 0 && connectdata_idx >= 0 && sockindex_idx >= 0 &&
- proxy_idx >= 0) {
- /* Store the data needed for the "new session" callback.
- * The sockindex is stored as a pointer to an array element. */
- SSL_set_ex_data(backend->handle, data_idx, data);
- SSL_set_ex_data(backend->handle, connectdata_idx, conn);
- SSL_set_ex_data(backend->handle, sockindex_idx, conn->sock + sockindex);
-#ifndef CURL_DISABLE_PROXY
- SSL_set_ex_data(backend->handle, proxy_idx, SSL_IS_PROXY() ? (void *) 1:
- NULL);
-#else
- SSL_set_ex_data(backend->handle, proxy_idx, NULL);
-#endif
-
- }
-
- Curl_ssl_sessionid_lock(data);
- if(!Curl_ssl_getsessionid(data, conn, SSL_IS_PROXY() ? TRUE : FALSE,
- &ssl_sessionid, NULL, sockindex)) {
- /* we got a session id, use it! */
- if(!SSL_set_session(backend->handle, ssl_sessionid)) {
- Curl_ssl_sessionid_unlock(data);
- failf(data, "SSL: SSL_set_session failed: %s",
- ossl_strerror(ERR_get_error(), error_buffer,
- sizeof(error_buffer)));
- return CURLE_SSL_CONNECT_ERROR;
- }
- /* Informational message */
- infof(data, "SSL re-using session ID\n");
+ Curl_ssl_sessionid_lock(data);
+ if(!Curl_ssl_getsessionid(data, conn, SSL_IS_PROXY() ? TRUE : FALSE,
+ &ssl_sessionid, NULL, sockindex)) {
+ /* we got a session id, use it! */
+ if(!SSL_set_session(backend->handle, ssl_sessionid)) {
+ Curl_ssl_sessionid_unlock(data);
+ failf(data, "SSL: SSL_set_session failed: %s",
+ ossl_strerror(ERR_get_error(), error_buffer,
+ sizeof(error_buffer)));
+ return CURLE_SSL_CONNECT_ERROR;
}
- Curl_ssl_sessionid_unlock(data);
+ /* Informational message */
+ infof(data, "SSL re-using session ID\n");
}
+ Curl_ssl_sessionid_unlock(data);
#ifndef CURL_DISABLE_PROXY
if(conn->proxy_ssl[sockindex].use) {
@@ -3353,6 +3351,19 @@ static CURLcode ossl_connect_step2(struct Curl_easy *data,
error_buffer */
strcpy(error_buffer, "SSL certificate verification failed");
}
+#if (OPENSSL_VERSION_NUMBER >= 0x10101000L && \
+ !defined(LIBRESSL_VERSION_NUMBER) && \
+ !defined(OPENSSL_IS_BORINGSSL))
+ /* SSL_R_TLSV13_ALERT_CERTIFICATE_REQUIRED is only available on
+ OpenSSL version above v1.1.1, not Libre SSL nor BoringSSL */
+ else if((lib == ERR_LIB_SSL) &&
+ (reason == SSL_R_TLSV13_ALERT_CERTIFICATE_REQUIRED)) {
+ /* If client certificate is required, communicate the
+ error to client */
+ result = CURLE_SSL_CLIENTCERT;
+ ossl_strerror(errdetail, error_buffer, sizeof(error_buffer));
+ }
+#endif
else {
result = CURLE_SSL_CONNECT_ERROR;
ossl_strerror(errdetail, error_buffer, sizeof(error_buffer));
@@ -3366,11 +3377,7 @@ static CURLcode ossl_connect_step2(struct Curl_easy *data,
*/
if(CURLE_SSL_CONNECT_ERROR == result && errdetail == 0) {
const char * const hostname = SSL_HOST_NAME();
-#ifndef CURL_DISABLE_PROXY
- const long int port = SSL_IS_PROXY() ? conn->port : conn->remote_port;
-#else
- const long int port = conn->remote_port;
-#endif
+ const long int port = SSL_HOST_PORT();
char extramsg[80]="";
int sockerr = SOCKERRNO;
if(sockerr && detail == SSL_ERROR_SYSCALL)
@@ -3404,12 +3411,12 @@ static CURLcode ossl_connect_step2(struct Curl_easy *data,
const unsigned char *neg_protocol;
unsigned int len;
SSL_get0_alpn_selected(backend->handle, &neg_protocol, &len);
- if(len != 0) {
+ if(len) {
infof(data, "ALPN, server accepted to use %.*s\n", len, neg_protocol);
-#ifdef USE_NGHTTP2
- if(len == NGHTTP2_PROTO_VERSION_ID_LEN &&
- !memcmp(NGHTTP2_PROTO_VERSION_ID, neg_protocol, len)) {
+#ifdef USE_HTTP2
+ if(len == ALPN_H2_LENGTH &&
+ !memcmp(ALPN_H2, neg_protocol, len)) {
conn->negnpn = CURL_HTTP_VERSION_2;
}
else
@@ -3896,7 +3903,7 @@ static CURLcode servercert(struct Curl_easy *data,
(int)SSL_SET_OPTION(issuercert_blob)->len);
else {
fp = BIO_new(BIO_s_file());
- if(fp == NULL) {
+ if(!fp) {
failf(data,
"BIO_new return NULL, " OSSL_PACKAGE
" error %s",
@@ -3983,8 +3990,7 @@ static CURLcode servercert(struct Curl_easy *data,
/* when not strict, we don't bother about the verify cert problems */
result = CURLE_OK;
- ptr = SSL_IS_PROXY() ? data->set.str[STRING_SSL_PINNEDPUBLICKEY_PROXY] :
- data->set.str[STRING_SSL_PINNEDPUBLICKEY];
+ ptr = SSL_PINNED_PUB_KEY();
if(!result && ptr) {
result = pkp_pin_peer_pubkey(data, backend->server_cert, ptr);
if(result)
@@ -4474,10 +4480,95 @@ static void *ossl_get_internals(struct ssl_connect_data *connssl,
(void *)backend->ctx : (void *)backend->handle;
}
+static void ossl_associate_connection(struct Curl_easy *data,
+ struct connectdata *conn,
+ int sockindex)
+{
+ struct ssl_connect_data *connssl = &conn->ssl[sockindex];
+ struct ssl_backend_data *backend = connssl->backend;
+
+ /* If we don't have SSL context, do nothing. */
+ if(!backend->handle)
+ return;
+
+ if(SSL_SET_OPTION(primary.sessionid)) {
+ int data_idx = ossl_get_ssl_data_index();
+ int connectdata_idx = ossl_get_ssl_conn_index();
+ int sockindex_idx = ossl_get_ssl_sockindex_index();
+ int proxy_idx = ossl_get_proxy_index();
+
+ if(data_idx >= 0 && connectdata_idx >= 0 && sockindex_idx >= 0 &&
+ proxy_idx >= 0) {
+ /* Store the data needed for the "new session" callback.
+ * The sockindex is stored as a pointer to an array element. */
+ SSL_set_ex_data(backend->handle, data_idx, data);
+ SSL_set_ex_data(backend->handle, connectdata_idx, conn);
+ SSL_set_ex_data(backend->handle, sockindex_idx, conn->sock + sockindex);
+#ifndef CURL_DISABLE_PROXY
+ SSL_set_ex_data(backend->handle, proxy_idx, SSL_IS_PROXY() ? (void *) 1:
+ NULL);
+#else
+ SSL_set_ex_data(backend->handle, proxy_idx, NULL);
+#endif
+ }
+ }
+}
+
+/*
+ * Starting with TLS 1.3, the ossl_new_session_cb callback gets called after
+ * the handshake. If the transfer that sets up the callback gets killed before
+ * this callback arrives, we must make sure to properly clear the data to
+ * avoid UAF problems. A future optimization could be to instead store another
+ * transfer that might still be using the same connection.
+ */
+
+static void ossl_disassociate_connection(struct Curl_easy *data,
+ int sockindex)
+{
+ struct connectdata *conn = data->conn;
+ struct ssl_connect_data *connssl = &conn->ssl[sockindex];
+ struct ssl_backend_data *backend = connssl->backend;
+
+ /* If we don't have SSL context, do nothing. */
+ if(!backend->handle)
+ return;
+
+ if(SSL_SET_OPTION(primary.sessionid)) {
+ bool isproxy = FALSE;
+ bool incache;
+ void *old_ssl_sessionid = NULL;
+ int data_idx = ossl_get_ssl_data_index();
+ int connectdata_idx = ossl_get_ssl_conn_index();
+ int sockindex_idx = ossl_get_ssl_sockindex_index();
+ int proxy_idx = ossl_get_proxy_index();
+
+ if(data_idx >= 0 && connectdata_idx >= 0 && sockindex_idx >= 0 &&
+ proxy_idx >= 0) {
+ /* Invalidate the session cache entry, if any */
+ isproxy = SSL_get_ex_data(backend->handle, proxy_idx) ? TRUE : FALSE;
+
+ /* Disable references to data in "new session" callback to avoid
+ * accessing a stale pointer. */
+ SSL_set_ex_data(backend->handle, data_idx, NULL);
+ SSL_set_ex_data(backend->handle, connectdata_idx, NULL);
+ SSL_set_ex_data(backend->handle, sockindex_idx, NULL);
+ SSL_set_ex_data(backend->handle, proxy_idx, NULL);
+ }
+
+ Curl_ssl_sessionid_lock(data);
+ incache = !(Curl_ssl_getsessionid(data, conn, isproxy,
+ &old_ssl_sessionid, NULL, sockindex));
+ if(incache)
+ Curl_ssl_delsessionid(data, old_ssl_sessionid);
+ Curl_ssl_sessionid_unlock(data);
+ }
+}
+
const struct Curl_ssl Curl_ssl_openssl = {
{ CURLSSLBACKEND_OPENSSL, "openssl" }, /* info */
SSLSUPP_CA_PATH |
+ SSLSUPP_CAINFO_BLOB |
SSLSUPP_CERTINFO |
SSLSUPP_PINNEDPUBKEY |
SSLSUPP_SSL_CTX |
@@ -4508,10 +4599,12 @@ const struct Curl_ssl Curl_ssl_openssl = {
ossl_engines_list, /* engines_list */
Curl_none_false_start, /* false_start */
#if (OPENSSL_VERSION_NUMBER >= 0x0090800fL) && !defined(OPENSSL_NO_SHA256)
- ossl_sha256sum /* sha256sum */
+ ossl_sha256sum, /* sha256sum */
#else
- NULL /* sha256sum */
+ NULL, /* sha256sum */
#endif
+ ossl_associate_connection, /* associate_connection */
+ ossl_disassociate_connection /* disassociate_connection */
};
#endif /* USE_OPENSSL */