}
}
-void libssl_setup_context_no_sni(std::unique_ptr<SSL_CTX, decltype(&SSL_CTX_free)>& ctx, const TLSCertKeyPair& pair, std::vector<int>& keyTypes)
+void libssl_setup_context_no_sni(SSL_CTX* ctx, const TLSCertKeyPair& pair, std::vector<int>& keyTypes)
{
if (!pair.d_key) {
#if defined(HAVE_SSL_CTX_USE_CERT_AND_KEY)
auto cert = std::unique_ptr<X509, void(*)(X509*)>(certptr, X509_free);
auto ca = std::unique_ptr<STACK_OF(X509), void(*)(STACK_OF(X509)*)>(captr, [](STACK_OF(X509)* st){ sk_X509_free(st); });
- if (SSL_CTX_use_cert_and_key(ctx.get(), cert.get(), key.get(), ca.get(), 1) != 1) {
+ if (SSL_CTX_use_cert_and_key(ctx, cert.get(), key.get(), ca.get(), 1) != 1) {
ERR_print_errors_fp(stderr);
throw std::runtime_error("An error occurred while trying to load the TLS certificate and key from PKCS12 file " + pair.d_cert);
}
throw std::runtime_error("PKCS12 files are not supported by your openssl version");
#endif /* HAVE_SSL_CTX_USE_CERT_AND_KEY */
} else {
- if (SSL_CTX_use_certificate_chain_file(ctx.get(), pair.d_cert.c_str()) != 1) {
+ if (SSL_CTX_use_certificate_chain_file(ctx, pair.d_cert.c_str()) != 1) {
ERR_print_errors_fp(stderr);
throw std::runtime_error("An error occurred while trying to load the TLS server certificate file: " + pair.d_cert);
}
- if (SSL_CTX_use_PrivateKey_file(ctx.get(), pair.d_key->c_str(), SSL_FILETYPE_PEM) != 1) {
+ if (SSL_CTX_use_PrivateKey_file(ctx, pair.d_key->c_str(), SSL_FILETYPE_PEM) != 1) {
ERR_print_errors_fp(stderr);
throw std::runtime_error("An error occurred while trying to load the TLS server private key file: " + pair.d_key.value());
}
}
- if (SSL_CTX_check_private_key(ctx.get()) != 1) {
+ if (SSL_CTX_check_private_key(ctx) != 1) {
ERR_print_errors_fp(stderr);
throw std::runtime_error("The key from '" + pair.d_key.value() + "' does not match the certificate from '" + pair.d_cert + "'");
}
std::vector<int> keyTypes;
/* load certificate and private key */
for (const auto& pair : config.d_certKeyPairs) {
- libssl_setup_context_no_sni(ctx, pair, keyTypes);
+ libssl_setup_context_no_sni(ctx.get(), pair, keyTypes);
}
#ifndef DISABLE_OCSP_STAPLING
}
/* add a keypair to an SSL context */
-void libssl_setup_context_no_sni(std::unique_ptr<SSL_CTX, decltype(&SSL_CTX_free)>& ctx, const TLSCertKeyPair& pair, std::vector<int>& keyTypes);
+void libssl_setup_context_no_sni(SSL_CTX* ctx, const TLSCertKeyPair& pair, std::vector<int>& keyTypes);
/* return the created context, and a list of warning messages for issues not severe enough
to trigger raising an exception, like failing to load an OCSP response file */
ciphers: String,
#[serde(default, skip_serializing_if = "crate::is_default")]
ciphers_tls_13: String,
+ #[serde(default, skip_serializing_if = "crate::is_default")]
+ // Fields below added in 5.5.0
+ client_certificate: String,
+ #[serde(default, skip_serializing_if = "crate::is_default")]
+ client_certificate_key: String,
+ #[serde(default, skip_serializing_if = "crate::is_default")]
+ client_certificate_password: String,
}
#[derive(Deserialize, Serialize, Clone, Debug, PartialEq)]
inserts(&mut map, "subject_name", &self.subject_name);
inserts(&mut map, "subject_address", &self.subject_address);
inserts(&mut map, "ciphers", &self.ciphers);
- inserts(&mut map, "ciphers_tls", &self.ciphers_tls_13);
+ inserts(&mut map, "ciphers_tls_13", &self.ciphers_tls_13);
+
+ inserts(&mut map, "client_certificate", &self.client_certificate);
+ inserts(&mut map, "client_certificate_key", &self.client_certificate_key);
+ inserts(&mut map, "client_certificate_password", &self.client_certificate_password);
+
serde_yaml::Value::Mapping(map)
}
verboseLogging = config->verbose_logging;
tlsParams.d_ciphers = std::string(config->ciphers);
tlsParams.d_ciphers13 = std::string(config->ciphers_tls_13);
+
+ tlsParams.d_client_certificate = std::string(config->client_certificate);
+ tlsParams.d_client_certificate_key = std::string(config->client_certificate_key);
+ tlsParams.d_client_certificate_password = std::string(config->client_certificate_password);
}
}
return ::getTLSContext(tlsParams);
libssl_set_alpn_protos(d_tlsCtx.get(), getALPNVector(params.d_alpn, true));
+ if (!params.d_client_certificate.empty()) {
+ std::optional<std::string> key = std::nullopt;
+ if (!params.d_client_certificate_key.empty()) {
+ key = params.d_client_certificate_key;
+ }
+ std::optional<std::string> password = std::nullopt;
+ if (!params.d_client_certificate_password.empty()) {
+ password = params.d_client_certificate_password;
+ }
+ TLSCertKeyPair pair{params.d_client_certificate, key, password};
+ std::vector<int> keyTypes;
+ libssl_setup_context_no_sni(d_tlsCtx.get(), pair, keyTypes);
+ }
+
#ifdef SSL_MODE_RELEASE_BUFFERS
if (params.d_releaseBuffers) {
SSL_CTX_set_mode(d_tlsCtx.get(), SSL_MODE_RELEASE_BUFFERS);
std::string d_ciphers13;
std::string d_caStore;
std::string d_keyLogFile;
+ std::string d_client_certificate;
+ std::string d_client_certificate_key;
+ std::string d_client_certificate_password;
TLSFrontend::ALPN d_alpn{TLSFrontend::ALPN::Unset};
bool d_validateCertificates{true};
bool d_releaseBuffers{true};