From d08af73883e57d354aa601be51e15b7c205eb1ce Mon Sep 17 00:00:00 2001 From: turuslan Date: Thu, 21 Dec 2023 11:02:51 +0300 Subject: [PATCH 1/2] ssl config Signed-off-by: turuslan --- CMakeLists.txt | 4 ++++ cmake/functions.cmake | 3 --- core/offchain/impl/http_request.cpp | 31 ++++--------------------- core/offchain/impl/http_request.hpp | 3 ++- core/telemetry/impl/connection_impl.cpp | 6 +++-- core/telemetry/impl/connection_impl.hpp | 3 ++- core/utils/asio_ssl_context_client.hpp | 25 ++++++++++++++++++++ 7 files changed, 42 insertions(+), 33 deletions(-) create mode 100644 core/utils/asio_ssl_context_client.hpp diff --git a/CMakeLists.txt b/CMakeLists.txt index d6ce6e35a9..8bb26c5b07 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -6,6 +6,10 @@ cmake_minimum_required(VERSION 3.12) +if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.27") + cmake_policy(SET CMP0144 NEW) +endif() + find_program(CCACHE_FOUND ccache) if(CCACHE_FOUND) set_property(GLOBAL PROPERTY RULE_LAUNCH_COMPILE ccache) diff --git a/cmake/functions.cmake b/cmake/functions.cmake index e44cf8f8bf..b031fec310 100644 --- a/cmake/functions.cmake +++ b/cmake/functions.cmake @@ -32,9 +32,6 @@ function(addtest_part test_name) target_sources(${test_name} PUBLIC ${ARGN} ) - target_link_libraries(${test_name} - GTest::gtest - ) endfunction() # conditionally applies flag. If flag is supported by current compiler, it will be added to compile options. diff --git a/core/offchain/impl/http_request.cpp b/core/offchain/impl/http_request.cpp index 5a0d5290ba..6c68ab798d 100644 --- a/core/offchain/impl/http_request.cpp +++ b/core/offchain/impl/http_request.cpp @@ -23,27 +23,9 @@ namespace kagome::offchain { HttpRequest::HttpRequest(RequestId id) : id_(id), resolver_(io_context_), - ssl_ctx_(boost::asio::ssl::context::sslv23), deadline_timer_(io_context_), log_(log::createLogger("HttpRequest#" + std::to_string(id_), - "offchain")) { - ssl_ctx_.set_default_verify_paths(); - ssl_ctx_.set_verify_mode(boost::asio::ssl::verify_peer); - ssl_ctx_.set_verify_callback( - [log = log_, wp = weak_from_this()]( - bool preverified, boost::asio::ssl::verify_context &ctx) { - // We will simply print the certificate's subject name here - char subject_name[256]; - X509 *cert = X509_STORE_CTX_get_current_cert(ctx.native_handle()); - X509_NAME_oneline(X509_get_subject_name(cert), subject_name, 256); - SL_WARN(log, - "Verifying [{}] was {}", - subject_name, - preverified ? "Successful" : "Failed"); - - return preverified; - }); - } + "offchain")) {} bool HttpRequest::init(HttpMethod method, std::string_view uri_arg, @@ -85,7 +67,10 @@ namespace kagome::offchain { if (uri_.Schema == "https") { secure_ = true; - stream_ = std::make_unique(io_context_, ssl_ctx_); + if (not ssl_ctx_) { + ssl_ctx_.emplace(uri_.Host); + } + stream_ = std::make_unique(io_context_, *ssl_ctx_); } else if (uri_.Schema == "http") { secure_ = false; stream_ = std::make_unique(io_context_); @@ -329,16 +314,10 @@ namespace kagome::offchain { if (secure_) { auto &stream = *boost::relaxed_get(stream_); - boost::system::error_code ec; - boost::beast::get_lowest_layer(stream).socket().shutdown( - boost::asio::ip::tcp::socket::shutdown_send, ec); boost::beast::http::async_read( stream, buffer_, parser_, std::move(read_handler)); } else { auto &stream = *boost::relaxed_get(stream_); - boost::system::error_code ec; - boost::beast::get_lowest_layer(stream).socket().shutdown( - boost::asio::ip::tcp::socket::shutdown_send, ec); boost::beast::http::async_read( stream, buffer_, parser_, std::move(read_handler)); } diff --git a/core/offchain/impl/http_request.hpp b/core/offchain/impl/http_request.hpp index b51235e503..4de0854992 100644 --- a/core/offchain/impl/http_request.hpp +++ b/core/offchain/impl/http_request.hpp @@ -18,6 +18,7 @@ #include "common/uri.hpp" #include "log/logger.hpp" #include "offchain/types.hpp" +#include "utils/asio_ssl_context_client.hpp" namespace kagome::offchain { @@ -63,7 +64,7 @@ namespace kagome::offchain { int16_t id_; boost::asio::ip::tcp::resolver resolver_; - boost::asio::ssl::context ssl_ctx_; + std::optional ssl_ctx_; using TcpStream = boost::beast::tcp_stream; using SslStream = boost::beast::ssl_stream; diff --git a/core/telemetry/impl/connection_impl.cpp b/core/telemetry/impl/connection_impl.cpp index 4c7156fe78..30e73b1545 100644 --- a/core/telemetry/impl/connection_impl.cpp +++ b/core/telemetry/impl/connection_impl.cpp @@ -25,7 +25,6 @@ namespace kagome::telemetry { callback_{std::move(callback)}, message_pool_{std::move(message_pool)}, scheduler_{std::move(scheduler)}, - ssl_ctx_{boost::asio::ssl::context::sslv23}, resolver_{boost::asio::make_strand(*io_context_)} { BOOST_ASSERT(io_context_); BOOST_ASSERT(message_pool_); @@ -86,8 +85,11 @@ namespace kagome::telemetry { path_ = path.empty() ? "/" : path; if (secure_) { + if (not ssl_ctx_) { + ssl_ctx_.emplace(endpoint_.uri().Host); + } ws_ = std::make_unique( - boost::asio::make_strand(*io_context_), ssl_ctx_); + boost::asio::make_strand(*io_context_), *ssl_ctx_); } else { ws_ = std::make_unique(boost::asio::make_strand(*io_context_)); diff --git a/core/telemetry/impl/connection_impl.hpp b/core/telemetry/impl/connection_impl.hpp index 77184f842d..4fab55a9f6 100644 --- a/core/telemetry/impl/connection_impl.hpp +++ b/core/telemetry/impl/connection_impl.hpp @@ -24,6 +24,7 @@ #include #include "log/logger.hpp" #include "telemetry/impl/message_pool.hpp" +#include "utils/asio_ssl_context_client.hpp" namespace kagome::telemetry { @@ -135,7 +136,7 @@ namespace kagome::telemetry { std::string path_; std::string ws_handshake_hostname_; - boost::asio::ssl::context ssl_ctx_; + std::optional ssl_ctx_; boost::asio::ip::tcp::resolver resolver_; boost::variant ws_; diff --git a/core/utils/asio_ssl_context_client.hpp b/core/utils/asio_ssl_context_client.hpp new file mode 100644 index 0000000000..7a340e78d1 --- /dev/null +++ b/core/utils/asio_ssl_context_client.hpp @@ -0,0 +1,25 @@ +/** + * Copyright Quadrivium LLC + * All Rights Reserved + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once + +#include +#include + +namespace kagome { + // TODO(turuslan): move to qtils, reuse for libp2p "/wss" + struct AsioSslContextClient : boost::asio::ssl::context { + AsioSslContextClient(const std::string &host) + : context{context::tlsv13_client} { + set_options(context::default_workarounds | context::no_sslv2 + | context::no_sslv3 | context::no_tlsv1 | context::no_tlsv1_1 + | context::no_tlsv1_2 | context::single_dh_use); + set_default_verify_paths(); + set_verify_mode(boost::asio::ssl::verify_peer); + set_verify_callback(boost::asio::ssl::rfc2818_verification{host}); + } + }; +} // namespace kagome From 137e47270bafe0ab8531c437e584396127baa15a Mon Sep 17 00:00:00 2001 From: turuslan Date: Thu, 21 Dec 2023 15:44:29 +0300 Subject: [PATCH 2/2] system cert Signed-off-by: turuslan --- core/utils/asio_ssl_context_client.hpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/core/utils/asio_ssl_context_client.hpp b/core/utils/asio_ssl_context_client.hpp index 7a340e78d1..ef1316a1e0 100644 --- a/core/utils/asio_ssl_context_client.hpp +++ b/core/utils/asio_ssl_context_client.hpp @@ -8,12 +8,25 @@ #include #include +#include namespace kagome { // TODO(turuslan): move to qtils, reuse for libp2p "/wss" struct AsioSslContextClient : boost::asio::ssl::context { AsioSslContextClient(const std::string &host) : context{context::tlsv13_client} { + // X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT + // X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY + [[maybe_unused]] static bool find_system_certificates = [] { + constexpr auto extra = "/etc/ssl/cert.pem"; + if (getenv(X509_get_default_cert_file_env()) == nullptr + and getenv(X509_get_default_cert_dir_env()) == nullptr + and std::string_view{X509_get_default_cert_file()} != extra + and std::filesystem::exists(extra)) { + setenv(X509_get_default_cert_file_env(), extra, true); + } + return true; + }(); set_options(context::default_workarounds | context::no_sslv2 | context::no_sslv3 | context::no_tlsv1 | context::no_tlsv1_1 | context::no_tlsv1_2 | context::single_dh_use);