From 97f4f518fef39cb1c02c77b26f81b8afb0a319be Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Tue, 12 Nov 2024 12:58:29 +0200 Subject: [PATCH 1/8] added certificate chains for http tls connection --- core/include/userver/engine/io/tls_wrapper.hpp | 1 + core/src/engine/io/tls_wrapper.cpp | 13 +++++++++++++ core/src/server/component.cpp | 3 +++ core/src/server/net/listener_config.cpp | 7 +++++++ core/src/server/net/listener_config.hpp | 1 + core/src/server/net/listener_impl.cpp | 1 + 6 files changed, 26 insertions(+) diff --git a/core/include/userver/engine/io/tls_wrapper.hpp b/core/include/userver/engine/io/tls_wrapper.hpp index 3e114f788700..17bb2a1e1d49 100644 --- a/core/include/userver/engine/io/tls_wrapper.hpp +++ b/core/include/userver/engine/io/tls_wrapper.hpp @@ -42,6 +42,7 @@ class [[nodiscard]] TlsWrapper final : public RwBase { static TlsWrapper StartTlsServer( Socket&& socket, const crypto::Certificate& cert, const crypto::PrivateKey& key, Deadline deadline, + const std::string& certificate_chain_path = "", const std::vector& extra_cert_authorities = {}); ~TlsWrapper() override; diff --git a/core/src/engine/io/tls_wrapper.cpp b/core/src/engine/io/tls_wrapper.cpp index 1452b2d8f0e1..1989de495edc 100644 --- a/core/src/engine/io/tls_wrapper.cpp +++ b/core/src/engine/io/tls_wrapper.cpp @@ -527,6 +527,7 @@ TlsWrapper TlsWrapper::StartTlsClient( TlsWrapper TlsWrapper::StartTlsServer( Socket&& socket, const crypto::Certificate& cert, const crypto::PrivateKey& key, Deadline deadline, + const std::string& certificate_chain_path, const std::vector& extra_cert_authorities) { auto ssl_ctx = MakeSslCtx(); @@ -540,6 +541,18 @@ TlsWrapper TlsWrapper::StartTlsServer( LOG_INFO() << "Client SSL cert will not be verified"; } + if(!certificate_chain_path.empty()) { + if(1 !=SSL_CTX_use_certificate_chain_file(ssl_ctx.get(), certificate_chain_path.c_str())) + { + throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate_chain_file")); + } + } + else { + if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert.GetNative())) { + throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); + } + } + if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert.GetNative())) { throw TlsException(crypto::FormatSslError( "Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); diff --git a/core/src/server/component.cpp b/core/src/server/component.cpp index a054f12618bd..e44742c4ba26 100644 --- a/core/src/server/component.cpp +++ b/core/src/server/component.cpp @@ -128,6 +128,9 @@ additionalProperties: false cert: type: string description: path to TLS certificate + cert-chain-path: + type: string + description: path to TLS certificates chain private-key: type: string description: path to TLS certificate private key diff --git a/core/src/server/net/listener_config.cpp b/core/src/server/net/listener_config.cpp index b8e85a985ed8..58a2aa7e8865 100644 --- a/core/src/server/net/listener_config.cpp +++ b/core/src/server/net/listener_config.cpp @@ -38,6 +38,7 @@ ListenerConfig Parse(const yaml_config::YamlConfig& value, throw std::runtime_error("Invalid backlog value in " + value.GetPath()); } + auto cert_chain_path = value["tls"]["cert-chain-path"].As({}); auto cert_path = value["tls"]["cert"].As({}); auto pkey_path = value["tls"]["private-key"].As({}); auto pkey_pass_name = @@ -51,6 +52,12 @@ ListenerConfig Parse(const yaml_config::YamlConfig& value, config.tls_cert = crypto::Certificate::LoadFromString(contents); config.tls = true; } + + if (!cert_chain_path.empty()) { + config.tls_certificate_chain_path = cert_chain_path; + config.tls = true; + } + if (!pkey_path.empty()) { config.tls_private_key_path = pkey_path; } diff --git a/core/src/server/net/listener_config.hpp b/core/src/server/net/listener_config.hpp index afc557eef824..330ecbddcd0a 100644 --- a/core/src/server/net/listener_config.hpp +++ b/core/src/server/net/listener_config.hpp @@ -27,6 +27,7 @@ struct ListenerConfig { bool tls{false}; crypto::Certificate tls_cert; + std::string tls_certificate_chain_path; std::string tls_private_key_path; std::string tls_private_key_passphrase_name; crypto::PrivateKey tls_private_key; diff --git a/core/src/server/net/listener_impl.cpp b/core/src/server/net/listener_impl.cpp index 58d82090adb4..6d044ed82438 100644 --- a/core/src/server/net/listener_impl.cpp +++ b/core/src/server/net/listener_impl.cpp @@ -105,6 +105,7 @@ void ListenerImpl::ProcessConnection(engine::io::Socket peer_socket) { socket = std::make_unique( engine::io::TlsWrapper::StartTlsServer( std::move(peer_socket), config.tls_cert, config.tls_private_key, {}, + config.tls_certificate_chain_path, config.tls_certificate_authorities)); } else { socket = std::make_unique(std::move(peer_socket)); From 2d71aac7ed25314b89dd07af8cda71a2658c2db1 Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Tue, 12 Nov 2024 13:03:46 +0200 Subject: [PATCH 2/8] fix naming --- core/src/server/component.cpp | 2 +- core/src/server/net/listener_config.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/core/src/server/component.cpp b/core/src/server/component.cpp index e44742c4ba26..a1f45952525f 100644 --- a/core/src/server/component.cpp +++ b/core/src/server/component.cpp @@ -128,7 +128,7 @@ additionalProperties: false cert: type: string description: path to TLS certificate - cert-chain-path: + cert-chain: type: string description: path to TLS certificates chain private-key: diff --git a/core/src/server/net/listener_config.cpp b/core/src/server/net/listener_config.cpp index 58a2aa7e8865..9f44c8af4d69 100644 --- a/core/src/server/net/listener_config.cpp +++ b/core/src/server/net/listener_config.cpp @@ -38,7 +38,7 @@ ListenerConfig Parse(const yaml_config::YamlConfig& value, throw std::runtime_error("Invalid backlog value in " + value.GetPath()); } - auto cert_chain_path = value["tls"]["cert-chain-path"].As({}); + auto cert_chain_path = value["tls"]["cert-chain"].As({}); auto cert_path = value["tls"]["cert"].As({}); auto pkey_path = value["tls"]["private-key"].As({}); auto pkey_pass_name = From 32ef6708ddcfa16c8e28ffad3560420b9b8c8205 Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Wed, 13 Nov 2024 09:11:10 +0200 Subject: [PATCH 3/8] [Tb-926] http cert chains cleanup --- core/include/userver/server/component.hpp | 1 + core/src/engine/io/tls_wrapper.cpp | 5 ----- core/src/server/component.cpp | 1 + 3 files changed, 2 insertions(+), 5 deletions(-) diff --git a/core/include/userver/server/component.hpp b/core/include/userver/server/component.hpp index 66a2fde295fe..48597d529967 100644 --- a/core/include/userver/server/component.hpp +++ b/core/include/userver/server/component.hpp @@ -63,6 +63,7 @@ namespace components { /// task_processor | task processor to process incoming requests | - /// backlog | max count of new connections pending acceptance | 1024 /// tls.ca | paths to TLS CAs for client authentication | - +/// tls.cert-chain | path to TLS server certificate chain | - /// tls.cert | path to TLS server certificate | - /// tls.private-key | path to TLS server certificate private key | - /// tls.private-key-passphrase-name | passphrase name located in secdist's "passphrases" section | - diff --git a/core/src/engine/io/tls_wrapper.cpp b/core/src/engine/io/tls_wrapper.cpp index 1989de495edc..11e0d11ea3a5 100644 --- a/core/src/engine/io/tls_wrapper.cpp +++ b/core/src/engine/io/tls_wrapper.cpp @@ -553,11 +553,6 @@ TlsWrapper TlsWrapper::StartTlsServer( } } - if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert.GetNative())) { - throw TlsException(crypto::FormatSslError( - "Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); - } - if (1 != SSL_CTX_use_PrivateKey(ssl_ctx.get(), key.GetNative())) { throw TlsException(crypto::FormatSslError( "Failed to set up server TLS wrapper: SSL_CTX_use_PrivateKey")); diff --git a/core/src/server/component.cpp b/core/src/server/component.cpp index a1f45952525f..81d252f7e9cd 100644 --- a/core/src/server/component.cpp +++ b/core/src/server/component.cpp @@ -131,6 +131,7 @@ additionalProperties: false cert-chain: type: string description: path to TLS certificates chain + defaultDescription: empty string private-key: type: string description: path to TLS certificate private key From f2925042cc36910b4e7b753b058294e4809c1f7e Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Sun, 5 Jan 2025 11:33:57 +0200 Subject: [PATCH 4/8] use common logic for tls cert chain --- .../include/userver/engine/io/tls_wrapper.hpp | 3 +- core/src/clients/http/client_crl_test.cpp | 2 +- core/src/engine/io/tls_wrapper.cpp | 22 +-- core/src/engine/io/tls_wrapper_benchmark.cpp | 2 +- core/src/engine/io/tls_wrapper_test.cpp | 131 +++++++++++++++--- core/src/server/net/listener_config.cpp | 12 +- core/src/server/net/listener_config.hpp | 3 +- core/src/server/net/listener_impl.cpp | 3 +- .../include/userver/crypto/certificate.hpp | 10 ++ universal/src/crypto/certificate.cpp | 23 +++ 10 files changed, 168 insertions(+), 43 deletions(-) diff --git a/core/include/userver/engine/io/tls_wrapper.hpp b/core/include/userver/engine/io/tls_wrapper.hpp index 17bb2a1e1d49..aa9950bb8ba5 100644 --- a/core/include/userver/engine/io/tls_wrapper.hpp +++ b/core/include/userver/engine/io/tls_wrapper.hpp @@ -40,9 +40,8 @@ class [[nodiscard]] TlsWrapper final : public RwBase { /// Starts a TLS server on an opened socket static TlsWrapper StartTlsServer( - Socket&& socket, const crypto::Certificate& cert, + Socket&& socket, const crypto::CertificatesChain& cert_chain, const crypto::PrivateKey& key, Deadline deadline, - const std::string& certificate_chain_path = "", const std::vector& extra_cert_authorities = {}); ~TlsWrapper() override; diff --git a/core/src/clients/http/client_crl_test.cpp b/core/src/clients/http/client_crl_test.cpp index 63dd7b8b8e77..713cefeebad3 100644 --- a/core/src/clients/http/client_crl_test.cpp +++ b/core/src/clients/http/client_crl_test.cpp @@ -317,7 +317,7 @@ struct TlsServer { auto tls_server = engine::io::TlsWrapper::StartTlsServer( std::move(socket), - crypto::Certificate::LoadFromString(kServerCertificate), + crypto::LoadCertficatesChainFromString(kServerCertificate), crypto::PrivateKey::LoadFromString(kRevokedServerPrivateKey), deadline, cas); diff --git a/core/src/engine/io/tls_wrapper.cpp b/core/src/engine/io/tls_wrapper.cpp index 11e0d11ea3a5..9f8fdb0067c8 100644 --- a/core/src/engine/io/tls_wrapper.cpp +++ b/core/src/engine/io/tls_wrapper.cpp @@ -3,6 +3,7 @@ #include #include #include +#include #include #include @@ -525,9 +526,8 @@ TlsWrapper TlsWrapper::StartTlsClient( } TlsWrapper TlsWrapper::StartTlsServer( - Socket&& socket, const crypto::Certificate& cert, + Socket&& socket, const crypto::CertificatesChain& cert_chain, const crypto::PrivateKey& key, Deadline deadline, - const std::string& certificate_chain_path, const std::vector& extra_cert_authorities) { auto ssl_ctx = MakeSslCtx(); @@ -541,15 +541,17 @@ TlsWrapper TlsWrapper::StartTlsServer( LOG_INFO() << "Client SSL cert will not be verified"; } - if(!certificate_chain_path.empty()) { - if(1 !=SSL_CTX_use_certificate_chain_file(ssl_ctx.get(), certificate_chain_path.c_str())) - { - throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate_chain_file")); - } + UASSERT_MSG(!cert_chain.empty(), "No certificate chain provided"); + + if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert_chain.begin()->GetNative())) { + throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); } - else { - if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert.GetNative())) { - throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); + + if(cert_chain.size() > 1) { + for(const auto& cert : cert_chain | std::ranges::views::drop(1)) { + if (SSL_CTX_add_extra_chain_cert(ssl_ctx.get(), cert.GetNative()) <= 0) { + throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_add_extra_chain_cert")); + } } } diff --git a/core/src/engine/io/tls_wrapper_benchmark.cpp b/core/src/engine/io/tls_wrapper_benchmark.cpp index b436b822952e..8f66cc61fe9f 100644 --- a/core/src/engine/io/tls_wrapper_benchmark.cpp +++ b/core/src/engine/io/tls_wrapper_benchmark.cpp @@ -97,7 +97,7 @@ constexpr auto kDeadlineMaxTime = std::chrono::seconds{60}; [&reading, deadline](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), deadline); std::array buf{}; diff --git a/core/src/engine/io/tls_wrapper_test.cpp b/core/src/engine/io/tls_wrapper_test.cpp index b86b697da23f..8fdb6bb22c5a 100644 --- a/core/src/engine/io/tls_wrapper_test.cpp +++ b/core/src/engine/io/tls_wrapper_test.cpp @@ -135,6 +135,105 @@ Z49kghXJ5KAS4jOB6SxClxbR5Tpc1E3khduX6aGau1VOkgPJxfdqHHqsyUc1RH/Z v2R63aFo/UfQSQ4dhC0o2Vy74DyLwnO3pH8wudfBJ8/LX/Uz/A== -----END CERTIFICATE-----)"; +// Certificates for testing were generated via the following command: +// openssl req -x509 -sha256 -nodes -newkey rsa:2048 +// -days 3650 -subj '/CN=tlswrapper_test_other' +// -keyout testing_priv.key -out testing_cert.crt +// +// NOTE: Ubuntu 20.04 requires RSA of at least 2048 length + +constexpr auto chain_private_key = R"(-----BEGIN PRIVATE KEY----- +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCtQd5O3Zow01ZC +vbuUv9s7jm48KwSmVje+k887w/h5fNR+lah44owNw6P/7RQ4uMmgGPxtIxdkZNvI +p5TjBcqMWK3OP4ReG3c/Ak+A1b6NOC5KborngfO0K9uzV/9Pa53UfcWoqSyqcc91 +G7zzDGuYHOs3FKk53fTNaRUYd5UMX8zZkTdTPpOJWDWZHIOYr6sgt7Py+NtVp70D +zS4/qIHD68oTjTYwp8DCQ3qljoTvSoYudKC+Xnm9lXnc2INJXmxYUFZBkq5vMczY +0mNFw4PNyEQyfyEOseaPFrAF/AWIiQWmYfe6M4gitc9Ct4cu7+VdLqDN3/D2bsbG +ceKzCbZzAgMBAAECggEAO56m+UyYeqS+0kin/A/pSR1CIcJL31Fb7WC/tzlAj828 +8bJePvr2ZuYj0TWr97je6RCwDH4+1nU+jFXejiC4CoOZi5ef3SJmbnBFG3hyEfZ7 +N3HCqte1HRLaj2SAnrvRnAWLtvZAQIbZdNsOsjRb8gRBjLq3YQpX6zd14u2DhLYB +vQxVfONtOGeUx/UUiss2MpJfrqoUoGVb+/onG1yAEbtWOs0Ig/dljopvcgkeCz9J +mB2MD5yv5a7sLBOcgyTpvE6ODgXzs+ZtS3TybGS+ld2rFrDlcInY1zXSP5iaW6Z5 +lSUeolx5w1lVjRcc9WdybEOYpkV76EqX4v9XbGIxAQKBgQDUUX36l3YQDkBgZOvb +FnQaGUUAUiRenJedW5FMKWxBh2tXNUIa3aw7GtPhf4/8JLCaFrYF4WLkDfb0CfSY +wbunEjqa1Fa/CFmuagBHg6ClIiGX2/p9t2iQEEMZA+qjeAeFgfYy86e4t1oRn6iA +EED7j/7szqZvWrHtcv4Z9HP0YwKBgQDQ5xY0i+ouWJ7nGWEZ2A2arixL6KSAPIlm +NAPoYZGTWYXl259vCrJmnqCRpqtCLkCwhtFbDewPtf1PTWYLJUUWcjdljpuKfPpu +sIseA3CSRIfggW1X3A/txtscWZQhctie+jU9BFqiSaG/Mto+GdH4BFT4oUFKmfA/ +J2rEKVyqsQKBgDoTCEhxAWQm4cj8Ed9dZuh0nQEXdsdCQd5S241fjzLlXaD++lPq +6l9IWUhG4hVv27ZqG+PD4I7Mmw3pYzQdWby7KbiL+CZMnGsup2DoShqhGVs2Wm/k +qP8u04uWHKoV/Mix4avSJcBKtqI3b5mH2J52pp4TcEbpId33JDXpPYZNAoGBAMif +5jd41+LCwXj4asTDNe2DsI8GUlXFzb8V3VrjuUdmBq4GCkw+Xa8oUNUQ2BCrEv11 +vMJR0JAWG7x5fLLfjEZOUt154+9Qr8J2UmT0sLwIjOYT5ssmUTXucKf9b8Hf5iJn +8ZE0CUcqp+hUEjzp1zj2EBTn6SiYRp6gYG0bvB9BAoGBANLAq1ZJw7JsZ6rCvduA +GgdtFZePPol1/iQX7YXgP0jP1i3gqRKa7M621u8Hunl5BAqQ/1fu/7qAExzDcmkn +OmJhJDUFdNcQ6+4LCpj5JVed/J1Tnh8vUaRbYV+9l0y5WolcuAY+hfJuB4K0mUXL +11/L+DCO5OYM9ud/kl+ttDWj +-----END PRIVATE KEY-----)"; + +constexpr auto chain_primary_cert = R"(-----BEGIN CERTIFICATE----- +MIIDFTCCAf2gAwIBAgIUXOIkjRBGF8HhB43My6tlrFcOoJcwDQYJKoZIhvcNAQEL +BQAwGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MB4XDTI1MDEwNDExMTMxMVoX +DTM1MDEwMjExMTMxMVowGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MIIBIjAN +BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArUHeTt2aMNNWQr27lL/bO45uPCsE +plY3vpPPO8P4eXzUfpWoeOKMDcOj/+0UOLjJoBj8bSMXZGTbyKeU4wXKjFitzj+E +Xht3PwJPgNW+jTguSm6K54HztCvbs1f/T2ud1H3FqKksqnHPdRu88wxrmBzrNxSp +Od30zWkVGHeVDF/M2ZE3Uz6TiVg1mRyDmK+rILez8vjbVae9A80uP6iBw+vKE402 +MKfAwkN6pY6E70qGLnSgvl55vZV53NiDSV5sWFBWQZKubzHM2NJjRcODzchEMn8h +DrHmjxawBfwFiIkFpmH3ujOIIrXPQreHLu/lXS6gzd/w9m7GxnHiswm2cwIDAQAB +o1MwUTAdBgNVHQ4EFgQUAatvjk2xqeE77VlZGHuC31sm0/owHwYDVR0jBBgwFoAU +Aatvjk2xqeE77VlZGHuC31sm0/owDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0B +AQsFAAOCAQEAOs+WfsO7k2zZS3CMAOHwxZzXy9PvdCzZFzJfjkKRh22zjZ1dmf8f +dlMGPqAENae3zuUd4ErFztNg6bGKW66j5JCQvfdqrj2XUUpTuJJWVcsvtxamDFz8 +2h2+ky35xop4GLv3E9BPZvXSZ4wwiFbehI79tPwz3Qn4rsaowxM+bhMIgf+Wt4hS +nyLZGLR3MYH5wY6kCErZobxlXukvxS/+RTobvyo/9wbKjx1qaOXfuMKsFK3hpYzq +uwddqXEoNvE0VFCib7dsBnBUEeKhnVioD0vpDfvrCLNTm8VOg3xVz902WNnpgSdu +ud5lWYZNZ6ygIOvwFz1VST30jT4Lj3Bmrg== +-----END CERTIFICATE-----)"; + +// intermediate certificate for other_key and other_cert was generated by +// openssl x509 -req -in <(openssl req -new -key testing_priv.key -subj "/CN=intermediate_test") -CA testing_cert.crt -CAkey testing_priv.key -CAcreateserial -out intermediate_cert.crt -days 1825 -sha256 +// full chain generated by +// cat intermediate_cert.crt testing_cert.crt > fullchain.crt + +constexpr auto cert_chain = R"(-----BEGIN CERTIFICATE----- +MIIC5TCCAc2gAwIBAgIUEAEQSbPfQymprdTsER15SJz+eaowDQYJKoZIhvcNAQEL +BQAwGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MB4XDTI1MDEwNDExMjgzMFoX +DTMwMDEwMzExMjgzMFowHDEaMBgGA1UEAwwRaW50ZXJtZWRpYXRlX3Rlc3QwggEi +MA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCtQd5O3Zow01ZCvbuUv9s7jm48 +KwSmVje+k887w/h5fNR+lah44owNw6P/7RQ4uMmgGPxtIxdkZNvIp5TjBcqMWK3O +P4ReG3c/Ak+A1b6NOC5KborngfO0K9uzV/9Pa53UfcWoqSyqcc91G7zzDGuYHOs3 +FKk53fTNaRUYd5UMX8zZkTdTPpOJWDWZHIOYr6sgt7Py+NtVp70DzS4/qIHD68oT +jTYwp8DCQ3qljoTvSoYudKC+Xnm9lXnc2INJXmxYUFZBkq5vMczY0mNFw4PNyEQy +fyEOseaPFrAF/AWIiQWmYfe6M4gitc9Ct4cu7+VdLqDN3/D2bsbGceKzCbZzAgMB +AAGjITAfMB0GA1UdDgQWBBQBq2+OTbGp4TvtWVkYe4LfWybT+jANBgkqhkiG9w0B +AQsFAAOCAQEAYaebsazdrABtiJF+FmLwmX9RJkLBxf4cxuSHzhieNeOSyVecCAmF +eJ1/4VKSWpDKfIk6pG8CWFO3EUCkytCof/idlbTqoYZ/WckzsYGrzxPTGSLw1Oen +/vnDFEE6cnIqJEB6v3LzfQrLBXr57+I7/SvpSGin9DuxfTQplNAt8lxDuiwJZz0+ +IrzRwLB9HzXo8xvG9v88L35SW8SwWds6R5hjpZ928qOP5JbosI6ccQ6fgu8hSy5D +H9ZIE4FyGrLTbA1reSjT43yBYBzX0H4JsQnzGjbraGk5HYLFETVKbCYurYo+4Rl5 +sYDUeR5wwfcKZCH43JERoG4DVI7yIKIzZQ== +-----END CERTIFICATE----- +-----BEGIN CERTIFICATE----- +MIIDFTCCAf2gAwIBAgIUXOIkjRBGF8HhB43My6tlrFcOoJcwDQYJKoZIhvcNAQEL +BQAwGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MB4XDTI1MDEwNDExMTMxMVoX +DTM1MDEwMjExMTMxMVowGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MIIBIjAN +BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArUHeTt2aMNNWQr27lL/bO45uPCsE +plY3vpPPO8P4eXzUfpWoeOKMDcOj/+0UOLjJoBj8bSMXZGTbyKeU4wXKjFitzj+E +Xht3PwJPgNW+jTguSm6K54HztCvbs1f/T2ud1H3FqKksqnHPdRu88wxrmBzrNxSp +Od30zWkVGHeVDF/M2ZE3Uz6TiVg1mRyDmK+rILez8vjbVae9A80uP6iBw+vKE402 +MKfAwkN6pY6E70qGLnSgvl55vZV53NiDSV5sWFBWQZKubzHM2NJjRcODzchEMn8h +DrHmjxawBfwFiIkFpmH3ujOIIrXPQreHLu/lXS6gzd/w9m7GxnHiswm2cwIDAQAB +o1MwUTAdBgNVHQ4EFgQUAatvjk2xqeE77VlZGHuC31sm0/owHwYDVR0jBBgwFoAU +Aatvjk2xqeE77VlZGHuC31sm0/owDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0B +AQsFAAOCAQEAOs+WfsO7k2zZS3CMAOHwxZzXy9PvdCzZFzJfjkKRh22zjZ1dmf8f +dlMGPqAENae3zuUd4ErFztNg6bGKW66j5JCQvfdqrj2XUUpTuJJWVcsvtxamDFz8 +2h2+ky35xop4GLv3E9BPZvXSZ4wwiFbehI79tPwz3Qn4rsaowxM+bhMIgf+Wt4hS +nyLZGLR3MYH5wY6kCErZobxlXukvxS/+RTobvyo/9wbKjx1qaOXfuMKsFK3hpYzq +uwddqXEoNvE0VFCib7dsBnBUEeKhnVioD0vpDfvrCLNTm8VOg3xVz902WNnpgSdu +ud5lWYZNZ6ygIOvwFz1VST30jT4Lj3Bmrg== +-----END CERTIFICATE-----)"; + constexpr auto kShortTimeout = std::chrono::milliseconds{10}; } // namespace @@ -158,7 +257,7 @@ UTEST(TlsWrapper, InitListSmall) { [deadline, kDataA, kDataB, kDataC, kDataD](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), deadline); if (tls_server.WriteAll({kDataA, kDataB, kDataC, kDataD}, deadline) != kDataA.len + kDataB.len + kDataC.len + kDataD.len) { @@ -197,7 +296,7 @@ UTEST(TlsWrapper, InitListLarge) { [deadline, kDataA, kDataB, kDataC, kDataD](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), deadline); if (tls_server.WriteAll({kDataA, kDataB, kDataC, kDataD}, deadline) != kDataA.len + kDataB.len + kDataC.len + kDataD.len) { @@ -232,7 +331,7 @@ UTEST(TlsWrapper, InitListSmallThenLarge) { [deadline, kDataSmall, kDataLarge](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), deadline); if (tls_server.WriteAll( {kDataSmall, kDataSmall, kDataSmall, kDataSmall, kDataLarge}, @@ -264,7 +363,7 @@ UTEST_MT(TlsWrapper, Smoke, 2) { try { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); EXPECT_EQ(1, tls_server.SendAll("1", 1, test_deadline)); char c = 0; @@ -309,7 +408,7 @@ UTEST_MT(TlsWrapper, DocTest, 2) { [deadline](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), deadline); if (tls_server.SendAll(kData.data(), kData.size(), deadline) != kData.size()) { @@ -341,7 +440,7 @@ UTEST(TlsWrapper, Move) { try { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); engine::AsyncNoSpan( [test_deadline](auto&& tls_server) { @@ -385,7 +484,7 @@ UTEST(TlsWrapper, ConnectTimeout) { std::move(client), {}, Deadline::FromDuration(kShortTimeout))), io::IoTimeout); EXPECT_THROW(static_cast(io::TlsWrapper::StartTlsServer( - std::move(server), crypto::Certificate::LoadFromString(cert), + std::move(server), crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), Deadline::FromDuration(kShortTimeout))), io::IoException); @@ -402,7 +501,7 @@ UTEST_MT(TlsWrapper, IoTimeout, 2) { [test_deadline, &timeout_happened](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); char c = 0; UEXPECT_THROW(static_cast(tls_server.RecvSome( @@ -437,7 +536,7 @@ UTEST(TlsWrapper, Cancel) { [test_deadline](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); char c = 0; UEXPECT_THROW( @@ -464,7 +563,7 @@ UTEST_MT(TlsWrapper, CertKeyMismatch, 2) { UEXPECT_THROW( static_cast(io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(other_key), test_deadline)), io::TlsException); }, @@ -487,7 +586,7 @@ UTEST_MT(TlsWrapper, NonTlsClient, 2) { UEXPECT_THROW( static_cast(io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(other_key), test_deadline)), io::TlsException); }, @@ -527,7 +626,7 @@ UTEST_MT(TlsWrapper, DoubleSmoke, 4) { [test_deadline](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); EXPECT_EQ(1, tls_server.SendAll("1", 1, test_deadline)); char c = 0; @@ -545,7 +644,7 @@ UTEST_MT(TlsWrapper, DoubleSmoke, 4) { [test_deadline](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(other_cert), + crypto::LoadCertficatesChainFromString(other_cert), crypto::PrivateKey::LoadFromString(other_key), test_deadline); EXPECT_EQ(1, tls_server.SendAll("5", 1, test_deadline)); char c = 0; @@ -597,7 +696,7 @@ UTEST(TlsWrapper, InvalidSocket) { static_cast(io::TlsWrapper::StartTlsClient({}, {}, test_deadline)), io::TlsException); UEXPECT_THROW(static_cast(io::TlsWrapper::StartTlsServer( - {}, crypto::Certificate::LoadFromString(cert), + {}, crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline)), io::TlsException); } @@ -613,7 +712,7 @@ UTEST(TlsWrapper, PeerShutdown) { try { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); char c = 0; // Get a non-fatal error on the channel @@ -653,7 +752,7 @@ UTEST(TlsWrapper, PeerDisconnect) { try { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::Certificate::LoadFromString(cert), + crypto::LoadCertficatesChainFromString(cert), crypto::PrivateKey::LoadFromString(key), test_deadline); char c = 0; // Get a non-fatal error on the channel diff --git a/core/src/server/net/listener_config.cpp b/core/src/server/net/listener_config.cpp index 9f44c8af4d69..ab20074281c6 100644 --- a/core/src/server/net/listener_config.cpp +++ b/core/src/server/net/listener_config.cpp @@ -47,17 +47,11 @@ ListenerConfig Parse(const yaml_config::YamlConfig& value, throw std::runtime_error( "Either set both tls.cert and tls.private-key options or none of them"); } - if (!cert_path.empty()) { - auto contents = fs::blocking::ReadFileContents(cert_path); - config.tls_cert = crypto::Certificate::LoadFromString(contents); - config.tls = true; - } - - if (!cert_chain_path.empty()) { - config.tls_certificate_chain_path = cert_chain_path; + if(!cert_path.empty()) { + auto contents = fs::blocking::ReadFileContents(cert_path); + config.tls_cert_chain = crypto::LoadCertficatesChainFromString(contents); config.tls = true; } - if (!pkey_path.empty()) { config.tls_private_key_path = pkey_path; } diff --git a/core/src/server/net/listener_config.hpp b/core/src/server/net/listener_config.hpp index 330ecbddcd0a..39e510811ea8 100644 --- a/core/src/server/net/listener_config.hpp +++ b/core/src/server/net/listener_config.hpp @@ -26,8 +26,7 @@ struct ListenerConfig { std::string task_processor; bool tls{false}; - crypto::Certificate tls_cert; - std::string tls_certificate_chain_path; + crypto::CertificatesChain tls_cert_chain; std::string tls_private_key_path; std::string tls_private_key_passphrase_name; crypto::PrivateKey tls_private_key; diff --git a/core/src/server/net/listener_impl.cpp b/core/src/server/net/listener_impl.cpp index 6d044ed82438..84364fe08242 100644 --- a/core/src/server/net/listener_impl.cpp +++ b/core/src/server/net/listener_impl.cpp @@ -104,8 +104,7 @@ void ListenerImpl::ProcessConnection(engine::io::Socket peer_socket) { const auto& config = endpoint_info_->listener_config; socket = std::make_unique( engine::io::TlsWrapper::StartTlsServer( - std::move(peer_socket), config.tls_cert, config.tls_private_key, {}, - config.tls_certificate_chain_path, + std::move(peer_socket), config.tls_cert_chain, config.tls_private_key, {}, config.tls_certificate_authorities)); } else { socket = std::make_unique(std::move(peer_socket)); diff --git a/universal/include/userver/crypto/certificate.hpp b/universal/include/userver/crypto/certificate.hpp index 65da12b5ef63..7d692f733cc7 100644 --- a/universal/include/userver/crypto/certificate.hpp +++ b/universal/include/userver/crypto/certificate.hpp @@ -7,6 +7,7 @@ #include #include #include +#include #include @@ -45,6 +46,15 @@ class Certificate { std::shared_ptr cert_; }; +using CertificatesChain = std::list; + +/// Accepts a string that contains a chain of certificates (primary and intermediate), checks that +/// it's correct, loads it into OpenSSL structures and returns as a +/// list of 'Certificate's. +/// +/// @throw crypto::KeyParseError if failed to load the certificate. +CertificatesChain LoadCertficatesChainFromString(std::string_view certificatesChain); + } // namespace crypto USERVER_NAMESPACE_END diff --git a/universal/src/crypto/certificate.cpp b/universal/src/crypto/certificate.cpp index a231a4cf61a6..99b331d94599 100644 --- a/universal/src/crypto/certificate.cpp +++ b/universal/src/crypto/certificate.cpp @@ -61,6 +61,29 @@ Certificate Certificate::LoadFromString(std::string_view certificate) { return Certificate{std::move(cert)}; } +CertificatesChain LoadCertficatesChainFromString(std::string_view chain) +{ + CertificatesChain certificates; + const std::string beginMarker = "-----BEGIN CERTIFICATE-----"; + const std::string endMarker = "-----END CERTIFICATE-----"; + + size_t start = 0; + while ((start = chain.find(beginMarker, start)) != std::string::npos) { + size_t end = chain.find(endMarker, start); + if (end == std::string::npos) { + break; // No matching end marker found + } + end += endMarker.length(); + certificates.push_back(Certificate::LoadFromString(chain.substr(start, end - start))); + start = end; // Move past the current certificate + } + if(certificates.empty()) { + throw KeyParseError(FormatSslError("There is no certificates in chain")); + } + + return certificates; +} + } // namespace crypto USERVER_NAMESPACE_END From 0b6e98c0a195926b346ade58ea0b5d75b3bf0bac Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Sun, 5 Jan 2025 12:06:12 +0200 Subject: [PATCH 5/8] cleanup --- core/include/userver/server/component.hpp | 3 +-- core/src/engine/io/tls_wrapper.cpp | 11 +++++------ core/src/server/component.cpp | 6 +----- 3 files changed, 7 insertions(+), 13 deletions(-) diff --git a/core/include/userver/server/component.hpp b/core/include/userver/server/component.hpp index 4dff0b4314da..4501670a5d7b 100644 --- a/core/include/userver/server/component.hpp +++ b/core/include/userver/server/component.hpp @@ -63,8 +63,7 @@ namespace components { /// task_processor | task processor to process incoming requests | - /// backlog | max count of new connections pending acceptance | 1024 /// tls.ca | paths to TLS CAs for client authentication | - -/// tls.cert-chain | path to TLS server certificate chain | - -/// tls.cert | path to TLS server certificate | - +/// tls.cert | path to TLS server certificate chain | - /// tls.private-key | path to TLS server certificate private key | - /// tls.private-key-passphrase-name | passphrase name located in secdist's "passphrases" section | - /// handler-defaults.max_url_size | max path/URL size or empty to not limit | 8192 diff --git a/core/src/engine/io/tls_wrapper.cpp b/core/src/engine/io/tls_wrapper.cpp index 344475001416..ac91a66e369c 100644 --- a/core/src/engine/io/tls_wrapper.cpp +++ b/core/src/engine/io/tls_wrapper.cpp @@ -3,7 +3,6 @@ #include #include #include -#include #include #include @@ -514,18 +513,18 @@ TlsWrapper TlsWrapper::StartTlsServer( LOG_INFO() << "Client SSL cert will not be verified"; } - if(cert_chain.empty()) - { + if(cert_chain.empty()) { throw TlsException(crypto::FormatSslError("Empty certificate chain provided")); - } + } if (1 != SSL_CTX_use_certificate(ssl_ctx.get(), cert_chain.begin()->GetNative())) { throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_use_certificate")); } if(cert_chain.size() > 1) { - for(const auto& cert : cert_chain | std::ranges::views::drop(1)) { - if (SSL_CTX_add_extra_chain_cert(ssl_ctx.get(), cert.GetNative()) <= 0) { + auto certIt = std::next(cert_chain.begin()); + for (; certIt != cert_chain.end(); ++certIt) { + if (SSL_CTX_add_extra_chain_cert(ssl_ctx.get(), certIt->GetNative()) <= 0) { throw TlsException(crypto::FormatSslError("Failed to set up server TLS wrapper: SSL_CTX_add_extra_chain_cert")); } } diff --git a/core/src/server/component.cpp b/core/src/server/component.cpp index 2017aa0fdd06..98ac8fad9651 100644 --- a/core/src/server/component.cpp +++ b/core/src/server/component.cpp @@ -125,11 +125,7 @@ additionalProperties: false description: path to TLS CA cert: type: string - description: path to TLS certificate - cert-chain: - type: string - description: path to TLS certificates chain - defaultDescription: empty string + description: path to TLS certificate chain private-key: type: string description: path to TLS certificate private key From 751ac667c1242b6c519c1417c02d0f9e65bf5ca1 Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Sun, 5 Jan 2025 13:17:30 +0200 Subject: [PATCH 6/8] fix compile --- core/src/engine/io/tls_wrapper.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core/src/engine/io/tls_wrapper.cpp b/core/src/engine/io/tls_wrapper.cpp index ac91a66e369c..6377f61f6afd 100644 --- a/core/src/engine/io/tls_wrapper.cpp +++ b/core/src/engine/io/tls_wrapper.cpp @@ -498,7 +498,7 @@ TlsWrapper TlsWrapper::StartTlsClient( TlsWrapper TlsWrapper::StartTlsServer( Socket&& socket, - const crypto::Certificate& cert, + const crypto::CertificatesChain& cert_chain, const crypto::PrivateKey& key, Deadline deadline, const std::vector& extra_cert_authorities From d472f2f107dce49ab7573bfbb25e1475c1f79e20 Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Sun, 5 Jan 2025 15:38:59 +0200 Subject: [PATCH 7/8] test chains --- core/src/engine/io/tls_wrapper_test.cpp | 34 +++++-------------------- 1 file changed, 6 insertions(+), 28 deletions(-) diff --git a/core/src/engine/io/tls_wrapper_test.cpp b/core/src/engine/io/tls_wrapper_test.cpp index 770ced89690d..a1c4c3315d07 100644 --- a/core/src/engine/io/tls_wrapper_test.cpp +++ b/core/src/engine/io/tls_wrapper_test.cpp @@ -140,6 +140,10 @@ v2R63aFo/UfQSQ4dhC0o2Vy74DyLwnO3pH8wudfBJ8/LX/Uz/A== // -days 3650 -subj '/CN=tlswrapper_test_other' // -keyout testing_priv.key -out testing_cert.crt // +// intermediate certificate was generated by +// openssl x509 -req -in <(openssl req -new -key testing_priv.key -subj "/CN=intermediate_test") -CA testing_cert.crt -CAkey testing_priv.key -CAcreateserial -out intermediate_cert.crt -days 1825 -sha256 +// full chain generated by +// cat intermediate_cert.crt testing_cert.crt > fullchain.crt // NOTE: Ubuntu 20.04 requires RSA of at least 2048 length constexpr auto chain_private_key = R"(-----BEGIN PRIVATE KEY----- @@ -171,31 +175,6 @@ OmJhJDUFdNcQ6+4LCpj5JVed/J1Tnh8vUaRbYV+9l0y5WolcuAY+hfJuB4K0mUXL 11/L+DCO5OYM9ud/kl+ttDWj -----END PRIVATE KEY-----)"; -constexpr auto chain_primary_cert = R"(-----BEGIN CERTIFICATE----- -MIIDFTCCAf2gAwIBAgIUXOIkjRBGF8HhB43My6tlrFcOoJcwDQYJKoZIhvcNAQEL -BQAwGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MB4XDTI1MDEwNDExMTMxMVoX -DTM1MDEwMjExMTMxMVowGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MIIBIjAN -BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArUHeTt2aMNNWQr27lL/bO45uPCsE -plY3vpPPO8P4eXzUfpWoeOKMDcOj/+0UOLjJoBj8bSMXZGTbyKeU4wXKjFitzj+E -Xht3PwJPgNW+jTguSm6K54HztCvbs1f/T2ud1H3FqKksqnHPdRu88wxrmBzrNxSp -Od30zWkVGHeVDF/M2ZE3Uz6TiVg1mRyDmK+rILez8vjbVae9A80uP6iBw+vKE402 -MKfAwkN6pY6E70qGLnSgvl55vZV53NiDSV5sWFBWQZKubzHM2NJjRcODzchEMn8h -DrHmjxawBfwFiIkFpmH3ujOIIrXPQreHLu/lXS6gzd/w9m7GxnHiswm2cwIDAQAB -o1MwUTAdBgNVHQ4EFgQUAatvjk2xqeE77VlZGHuC31sm0/owHwYDVR0jBBgwFoAU -Aatvjk2xqeE77VlZGHuC31sm0/owDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0B -AQsFAAOCAQEAOs+WfsO7k2zZS3CMAOHwxZzXy9PvdCzZFzJfjkKRh22zjZ1dmf8f -dlMGPqAENae3zuUd4ErFztNg6bGKW66j5JCQvfdqrj2XUUpTuJJWVcsvtxamDFz8 -2h2+ky35xop4GLv3E9BPZvXSZ4wwiFbehI79tPwz3Qn4rsaowxM+bhMIgf+Wt4hS -nyLZGLR3MYH5wY6kCErZobxlXukvxS/+RTobvyo/9wbKjx1qaOXfuMKsFK3hpYzq -uwddqXEoNvE0VFCib7dsBnBUEeKhnVioD0vpDfvrCLNTm8VOg3xVz902WNnpgSdu -ud5lWYZNZ6ygIOvwFz1VST30jT4Lj3Bmrg== ------END CERTIFICATE-----)"; - -// intermediate certificate for other_key and other_cert was generated by -// openssl x509 -req -in <(openssl req -new -key testing_priv.key -subj "/CN=intermediate_test") -CA testing_cert.crt -CAkey testing_priv.key -CAcreateserial -out intermediate_cert.crt -days 1825 -sha256 -// full chain generated by -// cat intermediate_cert.crt testing_cert.crt > fullchain.crt - constexpr auto cert_chain = R"(-----BEGIN CERTIFICATE----- MIIC5TCCAc2gAwIBAgIUEAEQSbPfQymprdTsER15SJz+eaowDQYJKoZIhvcNAQEL BQAwGjEYMBYGA1UEAwwPdGxzd3JhcHBlcl90ZXN0MB4XDTI1MDEwNDExMjgzMFoX @@ -233,7 +212,6 @@ nyLZGLR3MYH5wY6kCErZobxlXukvxS/+RTobvyo/9wbKjx1qaOXfuMKsFK3hpYzq uwddqXEoNvE0VFCib7dsBnBUEeKhnVioD0vpDfvrCLNTm8VOg3xVz902WNnpgSdu ud5lWYZNZ6ygIOvwFz1VST30jT4Lj3Bmrg== -----END CERTIFICATE-----)"; - constexpr auto kShortTimeout = std::chrono::milliseconds{10}; } // namespace @@ -257,8 +235,8 @@ UTEST(TlsWrapper, InitListSmall) { [deadline, kDataA, kDataB, kDataC, kDataD](auto&& server) { auto tls_server = io::TlsWrapper::StartTlsServer( std::forward(server), - crypto::LoadCertficatesChainFromString(cert), - crypto::PrivateKey::LoadFromString(key), + crypto::LoadCertficatesChainFromString(cert_chain), + crypto::PrivateKey::LoadFromString(chain_private_key), deadline ); if (tls_server.WriteAll({kDataA, kDataB, kDataC, kDataD}, deadline) != From 99f96fb6b81a417aecf51c4b778a5b877c34c236 Mon Sep 17 00:00:00 2001 From: "alexander.klyuchev" Date: Wed, 8 Jan 2025 09:27:32 +0200 Subject: [PATCH 8/8] review comments --- core/include/userver/server/component.hpp | 2 +- universal/include/userver/crypto/certificate.hpp | 2 +- universal/src/crypto/certificate.cpp | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/core/include/userver/server/component.hpp b/core/include/userver/server/component.hpp index 4501670a5d7b..2539dc358d69 100644 --- a/core/include/userver/server/component.hpp +++ b/core/include/userver/server/component.hpp @@ -63,7 +63,7 @@ namespace components { /// task_processor | task processor to process incoming requests | - /// backlog | max count of new connections pending acceptance | 1024 /// tls.ca | paths to TLS CAs for client authentication | - -/// tls.cert | path to TLS server certificate chain | - +/// tls.cert | path to TLS server certificate or certificate chain | - /// tls.private-key | path to TLS server certificate private key | - /// tls.private-key-passphrase-name | passphrase name located in secdist's "passphrases" section | - /// handler-defaults.max_url_size | max path/URL size or empty to not limit | 8192 diff --git a/universal/include/userver/crypto/certificate.hpp b/universal/include/userver/crypto/certificate.hpp index bbcd12065320..ea2cf2f49e94 100644 --- a/universal/include/userver/crypto/certificate.hpp +++ b/universal/include/userver/crypto/certificate.hpp @@ -52,7 +52,7 @@ using CertificatesChain = std::list; /// list of 'Certificate's. /// /// @throw crypto::KeyParseError if failed to load the certificate. -CertificatesChain LoadCertficatesChainFromString(std::string_view certificatesChain); +CertificatesChain LoadCertficatesChainFromString(std::string_view chain); } // namespace crypto diff --git a/universal/src/crypto/certificate.cpp b/universal/src/crypto/certificate.cpp index 163b27fc65d4..1ae220d33c0c 100644 --- a/universal/src/crypto/certificate.cpp +++ b/universal/src/crypto/certificate.cpp @@ -58,8 +58,8 @@ Certificate Certificate::LoadFromString(std::string_view certificate) { CertificatesChain LoadCertficatesChainFromString(std::string_view chain) { CertificatesChain certificates; - const std::string beginMarker = "-----BEGIN CERTIFICATE-----"; - const std::string endMarker = "-----END CERTIFICATE-----"; + constexpr std::string_view beginMarker = "-----BEGIN CERTIFICATE-----"; + constexpr std::string_view endMarker = "-----END CERTIFICATE-----"; size_t start = 0; while ((start = chain.find(beginMarker, start)) != std::string::npos) {