From c9352b79137fbe21dcb37188fc1fb37388d92d17 Mon Sep 17 00:00:00 2001 From: Michael Boquard Date: Fri, 20 Dec 2024 12:47:35 -0500 Subject: [PATCH] tls/ossl: Added new error codes to TLS api Added a number of error codes to report different connection error conditions encountered with OpenSSL: * ERROR_WRONG_VERSION_NUMBER - this error is reported when an invalid version number is encountered (this is distinctive to an unsupported version number). This error routinely occurs when attempting to connect to a TLS enabled endpoint using a non-TLS connection * ERROR_HTTP_REQUEST - Similar to ERROR_WRONG_VERSION_NUMBER, however this will be reported if the start of the packet begins with an HTTP verb such as GET or POST * ERROR_HTTPS_PROXY_REQUEST - Similar to the above but the verb encountered starts with 'CONNE' Added method that can be used to override the OpenSSL message with one that may be more helpful to users. Signed-off-by: Michael Boquard --- include/seastar/net/tls.hh | 3 +++ src/net/ossl.cc | 54 ++++++++++++++++++++++++++++++-------- src/net/tls.cc | 3 +++ 3 files changed, 49 insertions(+), 11 deletions(-) diff --git a/include/seastar/net/tls.hh b/include/seastar/net/tls.hh index 8d4b90d687..df7fb90e44 100644 --- a/include/seastar/net/tls.hh +++ b/include/seastar/net/tls.hh @@ -641,6 +641,9 @@ namespace tls { extern const int ERROR_NO_CIPHER_SUITES; extern const int ERROR_DECRYPTION_FAILED; extern const int ERROR_MAC_VERIFY_FAILED; + extern const int ERROR_WRONG_VERSION_NUMBER; + extern const int ERROR_HTTP_REQUEST; + extern const int ERROR_HTTPS_PROXY_REQUEST; } } diff --git a/src/net/ossl.cc b/src/net/ossl.cc index 5b75b13a4b..d159e6a11c 100644 --- a/src/net/ossl.cc +++ b/src/net/ossl.cc @@ -84,17 +84,16 @@ struct is_error_code_enum : true_type {}; } template<> -struct fmt::formatter : public fmt::formatter { - auto format(seastar::ossl_errc error, fmt::format_context& ctx) const -> decltype(ctx.out()) { - constexpr size_t error_buf_size = 256; - // Buffer passed to ERR_error_string must be at least 256 bytes large - // https://www.openssl.org/docs/man3.0/man3/ERR_error_string_n.html - std::array buf{}; - ERR_error_string_n( - static_cast(error), buf.data(), buf.size()); - // ERR_error_string_n does include the terminating null character - return fmt::format_to(ctx.out(), "{}", buf.data()); - } +struct fmt::formatter : + public fmt::formatter { + /** + * Some OpenSSL errors are hard to parse. This method can be used to provide + * an alternative, more readable, error message. + */ + static std::optional + alternate_message(seastar::ossl_errc error); + + auto format(seastar::ossl_errc error, fmt::format_context& ctx) const -> decltype(ctx.out()); }; namespace seastar { @@ -2077,3 +2076,36 @@ const int seastar::tls::ERROR_DECRYPTION_FAILED = ERR_PACK( ERR_LIB_SSL, 0, SSL_R_DECRYPTION_FAILED); const int seastar::tls::ERROR_MAC_VERIFY_FAILED = ERR_PACK( ERR_LIB_SSL, 0, SSL_R_DECRYPTION_FAILED_OR_BAD_RECORD_MAC); +const int seastar::tls::ERROR_WRONG_VERSION_NUMBER = ERR_PACK( + ERR_LIB_SSL, 0, SSL_R_WRONG_VERSION_NUMBER); +const int seastar::tls::ERROR_HTTP_REQUEST = ERR_PACK( + ERR_LIB_SSL, 0, SSL_R_HTTP_REQUEST); +const int seastar::tls::ERROR_HTTPS_PROXY_REQUEST = ERR_PACK( + ERR_LIB_SSL, 0, SSL_R_HTTPS_PROXY_REQUEST); + +std::optional fmt::formatter::alternate_message(seastar::ossl_errc error) { + switch(static_cast(error)) { + case seastar::tls::ERROR_WRONG_VERSION_NUMBER: + return "Wrong SSL Version number: ensure client is configured to use TLS"; + case seastar::tls::ERROR_HTTP_REQUEST: + return "Received HTTP request on HTTPS server"; + case seastar::tls::ERROR_HTTPS_PROXY_REQUEST: + return "Received HTTPS proxy request"; + } + + return std::nullopt; +} + +auto fmt::formatter::format(seastar::ossl_errc error, fmt::format_context& ctx) const -> decltype(ctx.out()) { + if (auto alternate = alternate_message(error); alternate.has_value()) { + return fmt::format_to(ctx.out(), "{}", alternate.value()); + } + constexpr size_t error_buf_size = 256; + // Buffer passed to ERR_error_string must be at least 256 bytes large + // https://www.openssl.org/docs/man3.0/man3/ERR_error_string_n.html + std::array buf{}; + ERR_error_string_n( + static_cast(error), buf.data(), buf.size()); + // ERR_error_string_n does include the terminating null character + return fmt::format_to(ctx.out(), "{}", buf.data()); +} diff --git a/src/net/tls.cc b/src/net/tls.cc index 72452021ac..ed29e25115 100644 --- a/src/net/tls.cc +++ b/src/net/tls.cc @@ -1397,3 +1397,6 @@ const int seastar::tls::ERROR_UNSUPPORTED_VERSION = GNUTLS_E_UNSUPPORTED_VERSION const int seastar::tls::ERROR_NO_CIPHER_SUITES = GNUTLS_E_NO_CIPHER_SUITES; const int seastar::tls::ERROR_DECRYPTION_FAILED = GNUTLS_E_DECRYPTION_FAILED; const int seastar::tls::ERROR_MAC_VERIFY_FAILED = GNUTLS_E_MAC_VERIFY_FAILED; +const int seastar::tls::ERROR_WRONG_VERSION_NUMBER = GNUTLS_E_UNEXPECTED_PACKET; +const int seastar::tls::ERROR_HTTP_REQUEST = GNUTLS_E_UNEXPECTED_PACKET; +const int seastar::tls::ERROR_HTTPS_PROXY_REQUEST = GNUTLS_E_UNEXPECTED_PACKET;