15#ifndef OPENVPN_OPENSSL_SSL_SSLCTX_H
16#define OPENVPN_OPENSSL_SSL_SSLCTX_H
26#include <openssl/crypto.h>
27#include <openssl/ssl.h>
28#include <openssl/x509v3.h>
29#include <openssl/rsa.h>
30#include <openssl/dsa.h>
31#include <openssl/ec.h>
32#include <openssl/bn.h>
33#include <openssl/rand.h>
34#include <openssl/evp.h>
35#if OPENSSL_VERSION_NUMBER >= 0x30000000L
36#include <openssl/provider.h>
65#if ENABLE_EXTERNAL_PKI
66#if OPENSSL_VERSION_NUMBER >= 0x30000000L
93#if OPENSSL_VERSION_NUMBER < 0x30000000L
134#if OPENSSL_VERSION_NUMBER >= 0x30000000L
139 using TlsLibCtxType = std::remove_pointer<SSLLib::Ctx>::type;
141 using SSLProviderUPtr = std::unique_ptr<OSSL_PROVIDER,
decltype(&::OSSL_PROVIDER_unload)>;
161 LibContext(
unsigned short config)
167 if (
config & LIB_CTX_LEGACY_PROVIDER)
169 SSLProviderUPtr legacy_provider{OSSL_PROVIDER_load(ctx_.get(),
"legacy"), &::OSSL_PROVIDER_unload};
171 if (!legacy_provider)
174 SSLProviderUPtr default_provider{OSSL_PROVIDER_load(ctx_.get(),
"default"), &::OSSL_PROVIDER_unload};
176 if (!default_provider)
179 providers_.emplace_back(std::move(legacy_provider));
180 providers_.emplace_back(std::move(default_provider));
192 std::vector<SSLProviderUPtr> providers_;
280 void load_ca(
const std::string &ca_txt,
bool strict)
override
298 if (!extra_certs_txt.empty())
307 void load_dh(
const std::string &dh_txt)
override
329 std::vector<std::string>
ret;
416 if (!
override.empty())
422 if (!
override.empty())
485 && opt.
exists(
"client-cert-not-required"))
490 const std::string name = opt.
get_optional(
"sni", 1, 256);
497 std::string ca_txt = opt.
cat(
"ca");
499 ca_txt += opt.
cat(
"relay-extra-ca");
505 const std::string crl_txt = opt.
cat(
"crl-verify");
506 if (!crl_txt.empty())
516 const std::string ec_txt = opt.
cat(
"extra-certs");
536 std::string relay_prefix;
538 relay_prefix =
"relay-";
566 if (opt.
exists(
"tls-cipher"))
569 if (opt.
exists(
"tls-ciphersuites"))
572 if (opt.
exists(
"tls-groups"))
580#ifdef OPENVPN_JSON_INTERNAL
582 SSLConfigAPI::Ptr json_override(
const Json::Value &root,
const bool load_cert_key)
const override
584 static const char title[] =
"json_override";
597 const std::string &ca_txt = json::get_string_ref(root,
"ca", title);
598 ret->load_ca(ca_txt,
true);
604 if (!crl_txt.empty())
605 ret->load_crl(crl_txt);
611 bool loaded_cert =
false;
632 const std::string &key_txt = json::get_string_ref(root,
"key", title);
633 if (!key_txt.empty())
634 ret->load_private_key(key_txt);
682#if OPENSSL_VERSION_NUMBER >= 0x30000000L
684 return lib_ctx->ctx();
693#if OPENSSL_VERSION_NUMBER >= 0x30000000L
694 std::lock_guard guard{lib_ctx_mutex};
701 if (it != lib_ctx_map.end())
703 auto cached_ctx = it->second.lock();
707 lib_ctx = std::move(cached_ctx);
723#if defined(SSL_OP_NO_TLSv1_3)
725#elif defined(SSL_OP_NO_TLSv1_2)
727#elif defined(SSL_OP_NO_TLSv1_1)
734#if OPENSSL_VERSION_NUMBER >= 0x30000000L
746 static inline std::map<unsigned short, std::weak_ptr<LibContext>> lib_ctx_map;
747 mutable std::shared_ptr<LibContext> lib_ctx;
748 static inline std::mutex lib_ctx_mutex;
767 std::vector<unsigned int>
ku;
794 SSL_do_handshake(
ssl);
799 const int status = BIO_write(
ssl_bio, data, numeric_cast<int>(size));
802 if (status == -1 && BIO_should_retry(
ssl_bio))
818 const int status = BIO_read(
ssl_bio, data, numeric_cast<int>(capacity));
821 if ((status == 0 || status == -1) && BIO_should_retry(
ssl_bio))
833 throw ssl_ciphertext_in_overflow();
854 in->
write(data, size);
876 return SSL_get_session(
ssl) && SSL_export_keying_material(
ssl, dest, size, label.c_str(), label.size(),
nullptr, 0, 0) == 1;
889 return !SSL_session_reused(
ssl);
914#if OPENSSL_VERSION_NUMBER < 0x30000010L && !defined(OPENSSL_NO_EC) && defined(ENABLE_EXTERNAL_PKI)
919 ssl_data_index = SSL_get_ex_new_index(0, (
char *)
"OpenSSLContext::SSL",
nullptr,
nullptr,
nullptr);
920 context_data_index = SSL_get_ex_new_index(0, (
char *)
"OpenSSLContext",
nullptr,
nullptr,
nullptr);
930 ssl = SSL_new(
ctx.ctx.get());
935 SSL_set_mode(
ssl, SSL_MODE_RELEASE_BUFFERS);
940 X509_VERIFY_PARAM *param = SSL_get0_param(
ssl);
941 X509_VERIFY_PARAM_set_hostflags(param, 0);
942 X509_VERIFY_PARAM_set1_host(param, hostname->c_str(), 0);
946 ssl_bio = BIO_new(BIO_f_ssl());
953 if (
ctx.config->mode.is_server())
955 SSL_set_accept_state(
ssl);
957 if (!
ctx.config->x509_track_config.empty())
960 else if (
ctx.config->mode.is_client())
962 if (cache_key &&
ctx.sess_cache)
965 ctx.sess_cache->extract(*cache_key, [
this](SSL_SESSION *sess)
967 if (!SSL_set_session(
ssl, sess))
973 SSL_set_connect_state(
ssl);
976 if (!
ctx.config->sni_name.empty())
978 if (SSL_set_tlsext_host_name(
ssl,
ctx.config->sni_name.c_str()) != 1)
979 throw OpenSSLException(
"OpenSSLContext::SSL: SSL_set_tlsext_host_name failed (sni_name)");
983 if (SSL_set_tlsext_host_name(
ssl, hostname->c_str()) != 1)
984 throw OpenSSLException(
"OpenSSLContext::SSL: SSL_set_tlsext_host_name failed (hostname)");
988 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext::SSL: unknown client/server mode");
996 throw ssl_context_error(
"OpenSSLContext::SSL: ssl_data_index is uninitialized");
1010 throw ssl_context_error(
"OpenSSLContext::SSL: context_data_index is uninitialized");
1016 ::X509 *cert = SSL_get_peer_certificate(
ssl);
1045 std::array<char, 1024> gname{};
1046 size_t gname_sz = gname.size();
1048 const char *group = gname.data();
1051 group =
"Error getting group name";
1059 std::ostringstream
os;
1061 ::X509 *cert = SSL_get_peer_certificate(
ssl);
1066 if (cert !=
nullptr)
1068 EVP_PKEY *pkey = X509_get_pubkey(cert);
1069 if (pkey !=
nullptr)
1071#ifndef OPENSSL_NO_EC
1072 if ((EVP_PKEY_id(pkey) == EVP_PKEY_EC))
1077#if OPENSSL_VERSION_NUMBER < 0x30000000L
1078 int pkeyId = EVP_PKEY_id(pkey);
1079 const char *pkeySN = OBJ_nid2sn(pkeyId);
1081 pkeySN =
"(error getting public key type)";
1084 if (pkeyId == EVP_PKEY_RSA)
1086 else if (pkeyId == EVP_PKEY_DSA)
1089 const char *pkeySN = EVP_PKEY_get0_type_name(pkey);
1092 pkeySN =
"(error getting public key type)";
1096 os <<
", " << EVP_PKEY_bits(pkey) <<
" bit " << pkeySN;
1098 EVP_PKEY_free(pkey);
1103 const SSL_CIPHER *ciph = SSL_get_current_cipher(
ssl);
1106 char *desc = SSL_CIPHER_description(ciph,
nullptr, 0);
1109 os <<
", cipher: Error getting TLS cipher description from SSL_CIPHER_description";
1113 std::string cipher_str(desc);
1116 os <<
", cipher: " << cipher_str;
1121 if (SSL_session_reused(
ssl))
1124#if OPENSSL_VERSION_NUMBER >= 0x30000000L
1125 const char *key_agreement = SSL_get0_group_name(
ssl);
1128 key_agreement =
"(error fetching key-agreeement)";
1130 os <<
", key-agreement: " << key_agreement;
1161 SSL_set_shutdown(
ssl, SSL_SENT_SHUTDOWN | SSL_RECEIVED_SHUTDOWN);
1173 throw OpenSSLException(
"OpenSSLContext::SSL: BIO_new failed on bmq_stream");
1200 std::stringstream cipher_list_ss(cipherlist);
1201 std::string ciphersuite;
1203 std::stringstream result;
1206 while (std::getline(cipher_list_ss, ciphersuite,
':'))
1210 if (!result.str().empty())
1217 OVPN_LOG_INFO(
"OpenSSLContext: Deprecated cipher suite name '"
1225 result << ciphersuite;
1229 return result.str();
1236 if (!SSL_CTX_set_session_id_context(
ctx.get(), (
unsigned char *)sess_id_context.c_str(), numeric_cast<unsigned int>(sess_id_context.length())))
1237 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_set_session_id_context failed");
1239#if OPENSSL_VERSION_NUMBER < 0x30000000L
1241 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_set_tlsext_ticket_key_cb failed");
1245 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_set_tlsext_ticket_evp_cb failed");
1257 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_new_ex failed for server method");
1262#if OPENSSL_VERSION_NUMBER >= 0x30000000L
1263 if (!SSL_CTX_set0_tmp_dh_pkey(
ctx.get(),
config->
dh.obj_release()))
1271 SSL_CTX_set_purpose(
ctx.get(), X509_PURPOSE_SSL_SERVER);
1283 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_new_ex failed for client method");
1286 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: unknown config->mode");
1291 int vf = SSL_VERIFY_PEER;
1293 vf |= SSL_VERIFY_FAIL_IF_NO_PEER_CERT;
1294 SSL_CTX_set_verify(
ctx.get(),
1299 SSL_CTX_set_verify_depth(
ctx.get(), 16);
1303 long sslopt = SSL_OP_SINGLE_DH_USE | SSL_OP_SINGLE_ECDH_USE | SSL_OP_NO_COMPRESSION | SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3;
1305#ifdef SSL_OP_NO_RENEGOTIATION
1306 sslopt |= SSL_OP_NO_RENEGOTIATION;
1311 SSL_CTX_set_session_cache_mode(
ctx.get(), SSL_SESS_CACHE_OFF);
1317 sslopt |= SSL_OP_NO_TICKET;
1324 if (SSL_CTX_add_client_CA(
ctx.get(), e.obj()) != 1)
1333 SSL_CTX_set_session_cache_mode(
ctx.get(), SSL_SESS_CACHE_CLIENT);
1338 SSL_CTX_set_session_cache_mode(
ctx.get(), SSL_SESS_CACHE_OFF);
1339 sslopt |= SSL_OP_NO_TICKET;
1342#if OPENSSL_VERSION_NUMBER >= 0x10100000L
1349 sslopt |= SSL_OP_NO_TLSv1;
1350#ifdef SSL_OP_NO_TLSv1_1
1352 sslopt |= SSL_OP_NO_TLSv1_1;
1354#ifdef SSL_OP_NO_TLSv1_2
1356 sslopt |= SSL_OP_NO_TLSv1_2;
1358#ifdef SSL_OP_NO_TLSv1_3
1360 sslopt |= SSL_OP_NO_TLSv1_3;
1363#if OPENSSL_VERSION_NUMBER >= 0x10100000L
1370 sslopt |= SSL_OP_NO_TLSv1;
1371#ifdef SSL_OP_NO_TLSv1_1
1373 sslopt |= SSL_OP_NO_TLSv1_1;
1375#ifdef SSL_OP_NO_TLSv1_2
1377 sslopt |= SSL_OP_NO_TLSv1_2;
1379#ifdef SSL_OP_NO_TLSv1_3
1381 sslopt |= SSL_OP_NO_TLSv1_3;
1384 SSL_CTX_set_options(
ctx.get(), sslopt);
1390#if defined(TLS1_3_VERSION)
1394 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: SSL_CTX_set_ciphersuites_list failed");
1397 std::string tls_cipher_list =
1401 ":!EXP:!LOW:!MEDIUM"
1419 tls_cipher_list +=
":!SHA1";
1422 std::string translated_cipherlist;
1429 if (!SSL_CTX_set_cipher_list(
ctx.get(), tls_cipher_list.c_str()))
1430 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: SSL_CTX_set_cipher_list failed");
1431#if OPENSSL_VERSION_NUMBER >= 0x10002000L && OPENSSL_VERSION_NUMBER < 0x10100000L
1432 SSL_CTX_set_ecdh_auto(
ctx.get(), 1);
1435#if OPENSSL_VERSION_NUMBER >= 0x10100000L
1440 "OpenSSLContext: undefined tls-cert-profile");
1442#ifdef OPENVPN_ALLOW_INSECURE_CERTPROFILE
1443 case TLSCertProfile::INSECURE:
1444 SSL_CTX_set_security_level(
ctx.get(), 0);
1448 SSL_CTX_set_security_level(
ctx.get(), 1);
1451 SSL_CTX_set_security_level(
ctx.get(), 2);
1454 SSL_CTX_set_security_level(
ctx.get(), 3);
1458 "OpenSSLContext: unexpected tls-cert-profile value");
1466 "OpenSSLContext: tls-cert-profile not supported by this OpenSSL build. Use 'legacy' instead");
1474 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: cert not defined");
1481#ifdef ENABLE_EXTERNAL_PKI
1482#if OPENSSL_VERSION_NUMBER >= 0x30000010L
1486 auto certType = EVP_PKEY_id(X509_get0_pubkey(
config->
cert.
obj()));
1487 if (certType == EVP_PKEY_RSA)
1491#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(OPENSSL_NO_EC)
1492 else if (certType == EVP_PKEY_EC)
1499 throw OpenSSLException(
"OpenSSLContext: pkey is neither RSA nor EC. Unsupported with external pki");
1503 throw OpenSSLException(
"OpenSSLContext: External PKI is not enabled in this build. ");
1509 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: private key not defined");
1514 if (!SSL_CTX_check_private_key(
ctx.get()))
1515 throw OpenSSLException(
"OpenSSLContext: private key does not match the certificate");
1524 if (SSL_CTX_add_extra_chain_cert(
ctx.get(), e.obj_dup()) != 1)
1525 throw OpenSSLException(
"OpenSSLContext: SSL_CTX_add_extra_chain_cert failed");
1534 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: CA not defined");
1545 return SSL::Ptr(
new SSL(*
this,
nullptr,
nullptr));
1551 return SSL::Ptr(
new SSL(*
this, hostname, cache_key));
1557#if OPENSSL_VERSION_NUMBER >= 0x30000000L
1559 throw OpenSSLException(
"OpenSSLContext: library context is not initialised");
1568 SSL_CTX_set_cert_store(
ctx.get(), store.
release());
1584 static void load_cert_info_into_authcert(
AuthCert &authcert,
const std::string &
cert_txt)
1591 X509_digest(cert.obj(), EVP_sha1(), authcert.
issuer_fp, &md_len);
1615 return X509_check_purpose(cert, X509_PURPOSE_SSL_SERVER, 0);
1617 return X509_check_purpose(cert, X509_PURPOSE_SSL_CLIENT, 0);
1625 auto num_groups = std::count(tls_groups.begin(), tls_groups.end(),
':') + 1;
1627 std::unique_ptr<int[]> glist(
new int[num_groups]);
1629 std::stringstream groups_ss(tls_groups);
1633 while (std::getline(groups_ss, group,
':'))
1638 if (group ==
"secp256r1")
1640 group =
"prime256v1";
1643 int nid = OBJ_sn2nid(group.c_str());
1646 glist[glistlen] = nid;
1652 << group <<
"' in tls-groups");
1656 if (!SSL_CTX_set1_groups(
ctx.get(), glist.get(), glistlen))
1657 OPENVPN_THROW(ssl_context_error,
"OpenSSLContext: SSL_CTX_set1_groups failed");
1670 ASN1_BIT_STRING *ku = (ASN1_BIT_STRING *)X509_get_ext_d2i(cert, NID_key_usage,
nullptr,
nullptr);
1675 unsigned int nku = 0;
1677 for (
int i = 0; i < 8; i++)
1679 if (ASN1_BIT_STRING_get_bit(ku, i))
1680 nku |= 1 << (7 - i);
1685 if ((nku & 0xff) == 0)
1690 for (std::vector<unsigned int>::const_iterator i =
config->
ku.begin(); i !=
config->
ku.end(); ++i)
1700 ASN1_BIT_STRING_free(ku);
1715 EXTENDED_KEY_USAGE *eku = (EXTENDED_KEY_USAGE *)X509_get_ext_d2i(cert, NID_ext_key_usage,
nullptr,
nullptr);
1720 for (
int i = 0; !found && i < sk_ASN1_OBJECT_num(eku); i++)
1722 ASN1_OBJECT *oid = sk_ASN1_OBJECT_value(eku, i);
1725 if (!found && OBJ_obj2txt(oid_str,
sizeof(oid_str), oid, 0) != -1)
1732 if (!found && OBJ_obj2txt(oid_str,
sizeof(oid_str), oid, 1) != -1)
1740 sk_ASN1_OBJECT_pop_free(eku, ASN1_OBJECT_free);
1763 if (c.depth_match(depth))
1770 if (!serial.empty())
1783 unsigned char buf[EVP_MAX_MD_SIZE];
1784 unsigned int len = EVP_MAX_MD_SIZE;
1785 X509_digest(cert, EVP_sha1(), buf, &len);
1821 const ASN1_INTEGER *ai = X509_get_serialNumber(cert);
1824 if (ai->type == V_ASN1_NEG_INTEGER)
1826 if (!is_safe_conversion<int>(authcert.
serial.
size()))
1828 BIGNUM *bn = ASN1_INTEGER_to_BN(ai, NULL);
1839 const std::string &signature,
1840 const std::string &subject)
1852 if (!subject.empty())
1855 ret +=
"NO_SUBJECT";
1856 ret +=
", signature: " + signature;
1860 ret += X509_verify_cert_error_string(err);
1869 switch (openssl_err)
1871 case X509_V_ERR_CERT_HAS_EXPIRED:
1881 int nid = X509_get_signature_nid(cert);
1885 case NID_ecdsa_with_SHA1:
1886 case NID_dsaWithSHA:
1887 case NID_dsaWithSHA1:
1888 case NID_sha1WithRSAEncryption:
1890 case NID_md5WithRSA:
1891 case NID_md5WithRSAEncryption:
1901 ::SSL *
ssl = (::SSL *)X509_STORE_CTX_get_ex_data(
ctx, SSL_get_ex_data_X509_STORE_CTX_idx());
1910 const int depth = X509_STORE_CTX_get_error_depth(
ctx);
1913 X509 *current_cert = X509_STORE_CTX_get_current_cert(
ctx);
1920 int err = X509_STORE_CTX_get_error(
ctx);
1922 || err != X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT
1938 return preverify_ok;
1950 OVPN_LOG_INFO(
"VERIFY FAIL -- bad peer-fingerprint in leaf certificate");
1957 OVPN_LOG_INFO(
"VERIFY FAIL -- bad ns-cert-type in leaf certificate");
1958 preverify_ok =
false;
1964 OVPN_LOG_INFO(
"VERIFY FAIL -- bad X509 key usage in leaf certificate");
1965 preverify_ok =
false;
1971 OVPN_LOG_INFO(
"VERIFY FAIL -- bad X509 extended key usage in leaf certificate");
1972 preverify_ok =
false;
1985 if (!verify_x509.
verify(name))
1988 preverify_ok =
false;
2001 preverify_ok =
false;
2005 return preverify_ok;
2011 ::SSL *
ssl = (::SSL *)X509_STORE_CTX_get_ex_data(
ctx, SSL_get_ex_data_X509_STORE_CTX_idx());
2020 const int err = X509_STORE_CTX_get_error(
ctx);
2023 const int depth = X509_STORE_CTX_get_error_depth(
ctx);
2026 X509 *current_cert = X509_STORE_CTX_get_current_cert(
ctx);
2032 int err = X509_STORE_CTX_get_error(
ctx);
2034 || err != X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT
2044 if (!preverify_ok && self_ssl->
authcert)
2047 X509_verify_cert_error_string(err));
2059 if (!X509_digest(current_cert, EVP_sha1(), self_ssl->
authcert->
issuer_fp, &digest_len))
2060 preverify_ok =
false;
2063 else if (depth == 0)
2069 OVPN_LOG_INFO(
"VERIFY FAIL -- bad peer-fingerprint in leaf certificate");
2073 "bad peer-fingerprint in leaf certificate");
2074 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE);
2075 preverify_ok =
false;
2081 OVPN_LOG_INFO(
"VERIFY FAIL -- bad ns-cert-type in leaf certificate");
2085 "bad ns-cert-type in leaf certificate");
2086 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_INVALID_PURPOSE);
2087 preverify_ok =
false;
2093 OVPN_LOG_INFO(
"VERIFY FAIL -- bad X509 key usage in leaf certificate");
2097 "bad X509 key usage in leaf certificate");
2098 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_INVALID_PURPOSE);
2099 preverify_ok =
false;
2105 OVPN_LOG_INFO(
"VERIFY FAIL -- bad X509 extended key usage in leaf certificate");
2109 "bad X509 extended key usage in leaf certificate");
2110 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_INVALID_PURPOSE);
2111 preverify_ok =
false;
2124 OVPN_LOG_INFO(
"VERIFY FAIL -- early rejection of leaf cert Common Name");
2125 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_CERT_REJECTED);
2126 preverify_ok =
false;
2129 catch (
const std::exception &e)
2131 OVPN_LOG_INFO(
"VERIFY FAIL -- early rejection of leaf cert Common Name due to handler exception: " << e.what());
2132 X509_STORE_CTX_set_error(
ctx, X509_V_ERR_CERT_REJECTED);
2133 preverify_ok =
false;
2162 if (where & SSL_CB_LOOP)
2165 << ((where & SSL_ST_CONNECT)
2167 : (where & SSL_ST_ACCEPT
2170 <<
"): " << SSL_state_string_long(s));
2172 if (where & SSL_CB_ALERT)
2175 << (where & SSL_CB_READ ?
"read" :
"write") <<
"): "
2176 << SSL_alert_type_string_long(
ret) <<
": "
2177 << SSL_alert_desc_string_long(
ret));
2182 unsigned char key_name[16],
2183 unsigned char iv[EVP_MAX_IV_LENGTH],
2184 ::EVP_CIPHER_CTX *
ctx,
2210 if (!RAND_bytes(iv, EVP_MAX_IV_LENGTH))
2253 unsigned char iv[EVP_MAX_IV_LENGTH],
2254 ::EVP_CIPHER_CTX *
ctx,
2259 if (!EVP_CipherInit_ex(
ctx, EVP_aes_256_cbc(),
nullptr, key.
cipher_value_, iv, enc))
2261#if OPENSSL_VERSION_NUMBER >= 0x30000000L
2262 OSSL_PARAM params[]{
2265 OSSL_PARAM_construct_utf8_string(
"digest", (
char *)
"sha256", 0),
2266 OSSL_PARAM_construct_end()};
2291 std::string sni_name;
2305 if (!sni_name.empty())
2323 catch (
const std::exception &e)
2326 return sni_error(e.what(), SSL_AD_INTERNAL_ERROR, self, self_ssl, al);
2329 return sni_error(
"SNI name not found", SSL_AD_UNRECOGNIZED_NAME, self, self_ssl, al);
2334 throw Exception(
"sni_handler returned wrong kind of SSLFactoryAPI");
2337 if (fapi.
get() != self)
2339 SSL_set_SSL_CTX(s, self_ssl->
sni_ctx->
ctx.get());
2344 return SSL_CLIENT_HELLO_SUCCESS;
2346 catch (
const std::exception &e)
2348 OPENVPN_LOG(
"SNI exception in OpenSSLContext, SNI=" << sni_name <<
" : " << e.what());
2349 *al = SSL_AD_INTERNAL_ERROR;
2350 return SSL_CLIENT_HELLO_ERROR;
2355 const int ssl_ad_error,
2363 return SSL_CLIENT_HELLO_SUCCESS;
2365 return SSL_CLIENT_HELLO_ERROR;
2377 const unsigned char *p;
2379 if (!SSL_client_hello_get0_ext(s, TLSEXT_TYPE_server_name, &p, &remaining))
2380 return std::string();
2390 if (len != buf.
size())
2395 if (buf.
pop_front() != TLSEXT_NAMETYPE_host_name)
2396 throw Exception(
"expecting TLSEXT_NAMETYPE_host_name");
2401 if (len > buf.
size())
2405 return std::string((
const char *)buf.
c_data(), len);
2418 &&
ssl.authcert->is_fail();
2426 std::shared_ptr<ExternalPKIImpl>
epki =
nullptr;
2435 return OpenSSL_version(OPENSSL_VERSION);
const std::uint8_t * number() const
static constexpr size_t size()
SNI::Metadata::UPtr sni_metadata
std::uint8_t issuer_fp[20]
std::unique_ptr< X509Track::Set > x509_track
void add_fail(const size_t depth, const Fail::Type new_code, std::string reason)
std::string render_pem() const
void parse_pem(const std::string &content, const std::string &title)
static void from_string(const std::string &content, const std::string &title, OpenSSLPKI::X509List *cert_list, OpenSSLPKI::CRLList *crl_list=nullptr)
virtual bool reject(const std::string &cn)=0
const T * c_data() const
Returns a const pointer to the start of the buffer.
size_t size() const
Returns the size of the buffer in T objects.
T pop_front()
Removes and returns the first element from the buffer.
static void init_static()
void write_buf(const BufferPtr &bp)
void set_frame(const Frame::Ptr &frame)
void write(const unsigned char *data, size_t size)
std::string validate_cert_list(const std::string &certs_txt) const override
std::vector< unsigned int > ku
ExternalPKIBase * external_pki
std::string extract_ca() const override
void load(const OptionList &opt, const unsigned int lflags) override
void enable_legacy_algorithms(const bool v) override
OpenSSLPKI::X509List extra_certs
virtual void set_tls_cipher_list(const std::string &override)
void initialise_lib_context() const
For OpenSSL 3.x, set up a library context if one is not already set up.
void set_tls_remote(const std::string &tls_remote_arg) override
VerifyX509Name verify_x509_name
void set_tls_version_min_override(const std::string &override) override
std::string extract_crl() const override
void load_private_key(const std::string &key_txt) override
TLSSessionTicketBase * session_ticket_handler
void set_tls_version_min(const TLSVersion::Type tvm) override
const Mode & get_mode() const override
virtual void set_tls_groups(const std::string &groups)
void set_rng(const StrongRandomAPI::Ptr &rng_arg) override
X509Track::ConfigSet x509_track_config
TLSCertProfile::Type tls_cert_profile
void set_remote_cert_tls(const KUParse::TLSWebType wt) override
void set_tls_cert_profile_override(const std::string &override) override
std::string tls_ciphersuite_list
void set_x509_track(X509Track::ConfigSet x509_track_config_arg) override
NSCert::Type ns_cert_type
void load_cert(const std::string &cert_txt, const std::string &extra_certs_txt) override
bool client_session_tickets
static constexpr unsigned short LIB_CTX_NO_PROVIDERS
void set_frame(const Frame::Ptr &frame_arg) override
unsigned short lib_ctx_provider_config
SNI::HandlerBase * sni_handler
size_t private_key_length() const override
std::string extract_private_key() const override
std::string tls_cipher_list
void load_ca(const std::string &ca_txt, bool strict) override
PKType::Type private_key_type() const override
void set_tls_version_max(const TLSVersion::Type tvm) override
TLSVersion::Type tls_version_max
void set_flags(const unsigned int flags_arg) override
void set_session_ticket_handler(TLSSessionTicketBase *session_ticket_handler_arg) override
std::string external_pki_alias
TLSVersion::Type tls_version_min
void set_sni_handler(SNI::HandlerBase *sni_handler_arg) override
static TLSVersion::Type maxver()
std::string extract_dh() const override
void set_cn_reject_handler(CommonNameReject *cn_reject_handler_arg) override
void load_cert(const std::string &cert_txt) override
friend class OpenSSLContext
std::string extract_cert() const override
std::string validate_private_key(const std::string &key_txt) const override
std::string validate_cert(const std::string &cert_txt) const override
SSLFactoryAPI::Ptr new_factory() override
Return a pointer-like object that refers to a ssl factory.
void set_local_cert_enabled(const bool v) override
void set_client_session_tickets(const bool v) override
void set_sni_name(const std::string &sni_name_arg) override
std::string validate_dh(const std::string &dh_txt) const override
CommonNameReject * cn_reject_handler
void set_tls_cert_profile(const TLSCertProfile::Type type) override
void set_mode(const Mode &mode_arg) override
void load_dh(const std::string &dh_txt) override
PeerFingerprints peer_fingerprints
std::vector< std::string > extract_extra_certs() const override
void set_debug_level(const int debug_level) override
virtual void set_tls_ciphersuite_list(const std::string &override)
void load_crl(const std::string &crl_txt) override
void set_external_pki_callback(ExternalPKIBase *external_pki_arg, const std::string &alias) override
void set_ns_cert_type(const NSCert::Type ns_cert_type_arg) override
void set_private_key_password(const std::string &pwd) override
static constexpr unsigned short LIB_CTX_LEGACY_PROVIDER
std::string validate_crl(const std::string &crl_txt) const override
static void init_static()
const AuthCert::Ptr & auth_cert() const override
ssize_t write_cleartext_unbuffered(const void *data, const size_t size) override
static int context_data_index
static int ssl_data_index
bool export_keying_material(const std::string &label, unsigned char *dest, size_t size) override
void start_handshake() override
OpenSSLContext::Ptr sni_ctx
BufferPtr read_ciphertext() override
bool read_cleartext_ready() const override
static int ssl_pending_override(const ::SSL *)
void write_ciphertext(const BufferPtr &buf) override
static std::string ssl_handshake_details(::SSL *ssl)
bool did_full_handshake() override
Returns the cached/reused status of the session.
std::string ssl_handshake_details() const override
void set_parent(const OpenSSLContext *ctx)
bool read_ciphertext_ready() const override
OpenSSLSessionCache::Key::UPtr sess_cache_key
ssize_t read_cleartext(void *data, const size_t capacity) override
void rebuild_authcert() const
void write_ciphertext_unbuffered(const unsigned char *data, const size_t size) override
void mark_no_cache() override
static BIO * mem_bio(const Frame::Ptr &frame)
SSL(const OpenSSLContext &ctx, const std::string *hostname, const std::string *cache_key)
bool called_did_full_handshake
static void print_ec_key_details(EVP_PKEY *pkey, std::ostream &os)
static void info_callback(const ::SSL *s, int where, int ret)
static bool tls_ticket_init_cipher_hmac(const TLSSessionTicketBase::Key &key, unsigned char iv[EVP_MAX_IV_LENGTH], ::EVP_CIPHER_CTX *ctx, ssl_mac_ctx *mctx, const int enc)
static std::string translate_cipher_list(std::string cipherlist)
static constexpr bool support_key_material_export()
static void load_serial_number_into_authcert(AuthCert &authcert, ::X509 *cert)
CertCRLListTemplate< OpenSSLPKI::X509List, OpenSSLPKI::CRLList > CertCRLList
static int verify_callback_client(int preverify_ok, X509_STORE_CTX *ctx)
bool ns_cert_type_defined() const
std::shared_ptr< ExternalPKIImpl > epki
void setup_server_ticket_callback() const
static std::string client_hello_get_sni(::SSL *s)
static int check_cert_warnings(const X509 *cert)
static std::string cert_status_line(int preverify_ok, int depth, int err, const std::string &signature, const std::string &subject)
bool x509_cert_ku_defined() const
SSLAPI::Ptr ssl() override
static int client_hello_callback(::SSL *s, int *al, void *)
static void x509_track_extract_nid(const X509Track::Type xt_type, const int nid, ::X509 *cert, const int depth, X509Track::Set &xts)
const Mode & mode() const override
void set_openssl_tls_groups(const std::string &tls_groups)
~OpenSSLContext()=default
static int sni_error(std::string err, const int ssl_ad_error, OpenSSLContext *self, SSL *self_ssl, int *al)
OpenSSLSessionCache::Ptr sess_cache
static size_t sni_get_len(ConstBuffer &buf)
static int tls_ticket_key_callback(::SSL *ssl, unsigned char key_name[16], unsigned char iv[EVP_MAX_IV_LENGTH], ::EVP_CIPHER_CTX *ctx, ssl_mac_ctx *hctx, int enc)
static void x509_track_extract_from_cert(::X509 *cert, const int depth, const X509Track::ConfigSet &cs, X509Track::Set &xts)
static AuthCert::Fail::Type cert_fail_code(const int openssl_err)
bool verify_x509_cert_eku(::X509 *cert) const
void update_trust(const CertCRLList &cc)
bool verify_x509_cert_ku(::X509 *cert) const
SSLAPI::Ptr ssl(const std::string *hostname, const std::string *cache_key) override
bool x509_cert_eku_defined() const
OpenSSLContext(Config *config_arg)
bool verify_ns_cert_type(::X509 *cert) const
std::unique_ptr<::SSL_CTX, decltype(&::SSL_CTX_free)> SSL_CTX_unique_ptr
SSLLib::Ctx libctx() override
static int verify_callback_server(int preverify_ok, X509_STORE_CTX *ctx)
bool deferred_cert_verify_failsafe(const SSL &ssl) const
RCPtr< OpenSSLContext > Ptr
static bool randomize_name_key(TLSSessionTicketBase::Name &name, TLSSessionTicketBase::Key &key)
std::string render_pem() const
std::string render_pem() const
void parse_pem(const std::string &dh_txt)
std::string render_pem() const
size_t key_length() const
void set_private_key_password(const std::string &pwd)
void parse_pem(const std::string &pkey_txt, const std::string &title, SSLLib::Ctx libctx)
PKType::Type key_type() const
std::string render_pem() const
std::string render_pem() const
void parse_pem(const std::string &cert_txt, const std::string &title)
std::string render_pem() const
std::unique_ptr< Key > UPtr
std::string get_optional(const std::string &name, size_t index, const size_t max_len) const
std::string cat(const std::string &name) const
const Option & get(const std::string &name) const
bool exists(const std::string &name) const
void reset() noexcept
Points this RCPtr<T> to nullptr safely.
RCPtr< U > dynamic_pointer_cast() const noexcept
Returns a "RCPtr<U>" that points to our T object.
T * get() const noexcept
Returns the raw pointer to the object T, or nullptr.
virtual SSLFactoryAPI::Ptr sni_hello(const std::string &sni_name, SNI::Metadata::UPtr &sni_metadata, SSLConfigAPI::Ptr default_factory) const =0
@ LF_ALLOW_CLIENT_CERT_NOT_REQUIRED
RCPtr< SSLFactoryAPI > Ptr
unsigned char hmac_value_[HMAC_KEY_SIZE]
unsigned char cipher_value_[CIPHER_KEY_SIZE]
static constexpr size_t CIPHER_KEY_SIZE
static constexpr size_t HMAC_KEY_SIZE
static constexpr size_t SIZE
virtual std::string session_id_context() const =0
virtual Status create_session_ticket_key(Name &name, Key &key) const =0
virtual Status lookup_session_ticket_key(const Name &name, Key &key) const =0
void init(const OptionList &opt, const std::string &relay_prefix)
bool verify(const std::string &value) const
static std::shared_ptr< XKeyExternalPKIImpl > create(SSL_CTX *ssl_ctx, ::X509 *cert, ExternalPKIBase *external_pki, std::string alias)
int log_level() const
return the current logging level for all logging
static logging::Logger< DEFAULT_LOG_LEVEL, MAX_LEVEL > log_
static void set_log_level(int level)
set the log level for all loggigng
static SSL_CTX * SSL_CTX_new_ex(void *libctx, const char *propq, const SSL_METHOD *meth)
#define EVP_PKEY_get_bits
static void OSSL_LIB_CTX_free(void *libctx)
static int EVP_PKEY_get_group_name(EVP_PKEY *pkey, char *gname, size_t gname_sz, size_t *gname_len)
#define OPENVPN_THROW(exc, stuff)
#define OPENVPN_LOG(args)
#define OVPN_LOG_TRACE(args)
#define OVPN_LOG_INFO(args)
void remote_cert_ku(const OptionList &opt, const std::string &relay_prefix, std::vector< unsigned int > &ku)
void remote_cert_tls(const TLSWebType wt, std::vector< unsigned int > &ku, std::string &eku)
void remote_cert_eku(const OptionList &opt, const std::string &relay_prefix, std::string &eku)
Type ns_cert_type(const std::string &ct)
static std::size_t x509_fingerprint_size()
static std::string x509_get_serial_hex(::X509 *cert)
static std::string x509_get_field(::X509 *cert, const int nid)
static std::string X509_get_pem_encoding(::X509 *cert)
static std::string x509_get_serial(::X509 *cert)
static std::vector< uint8_t > x509_get_fingerprint(const ::X509 *cert)
static std::string x509_get_subject(::X509 *cert, bool new_format=false)
static std::string x509_get_signature_algorithm(const ::X509 *cert)
@ VERIFY_PEER_FINGERPRINT
void apply_override(Type &type, const std::string &override)
Type default_if_undef(const Type type)
Type parse_tls_cert_profile(const std::string &profile_name)
std::string sanitize_x509_name(const std::string &str)
bool test(const std::string &tls_remote, const std::string &subject, const std::string &common_name)
std::string sanitize_common_name(const std::string &str)
void log(const std::string &tls_remote, const std::string &subject, const std::string &common_name)
int toTLSVersion(const Type version)
void apply_override(Type &tvm, const std::string &override)
Type parse_tls_version_min(const std::string &ver, const bool or_highest, const Type max_version)
bool is_valid_utf8_uchar_buf(const unsigned char *source, size_t size, const size_t max_len_flags=0)
BIO_METHOD * BIO_s_memq(void)
MemQ * memq_from_bio(BIO *b)
std::string get_string_optional(const Json::Value &root, const NAME &name, const std::string &default_value, const TITLE &title)
constexpr int LOG_LEVEL_INFO
void trim(std::string &str)
void openssl_clear_error_stack()
std::string to_string(const T &t)
Convert a value to a string.
const tls_cipher_name_pair * tls_get_cipher_name_pair(const std::string &ciphername)
std::string render_hex_sep(const unsigned char *data, size_t size, const char sep, const bool caps=false)
const std::string get_ssl_library_version()
bool match(const PeerFingerprint &fp) const
const char * openssl_name
const std::string cert_txt
static const char config[]