Line data Source code
1 : #pragma once 2 : 3 : #include <sys/types.h> 4 : 5 : #include <cstdint> 6 : 7 : #include "envoy/network/connection.h" 8 : #include "envoy/network/transport_socket.h" 9 : #include "envoy/secret/secret_callbacks.h" 10 : #include "envoy/server/options.h" 11 : #include "envoy/ssl/handshaker.h" 12 : #include "envoy/ssl/private_key/private_key_callbacks.h" 13 : #include "envoy/ssl/ssl_socket_extended_info.h" 14 : #include "envoy/ssl/ssl_socket_state.h" 15 : #include "envoy/stats/scope.h" 16 : #include "envoy/stats/stats_macros.h" 17 : 18 : #include "source/common/common/logger.h" 19 : #include "source/extensions/transport_sockets/tls/connection_info_impl_base.h" 20 : #include "source/extensions/transport_sockets/tls/utility.h" 21 : 22 : #include "absl/container/node_hash_map.h" 23 : #include "absl/synchronization/mutex.h" 24 : #include "absl/types/optional.h" 25 : #include "openssl/ssl.h" 26 : 27 : namespace Envoy { 28 : namespace Extensions { 29 : namespace TransportSockets { 30 : namespace Tls { 31 : 32 : class SslHandshakerImpl; 33 : class SslExtendedSocketInfoImpl; 34 : 35 : class ValidateResultCallbackImpl : public Ssl::ValidateResultCallback { 36 : public: 37 : ValidateResultCallbackImpl(Event::Dispatcher& dispatcher, 38 : SslExtendedSocketInfoImpl& extended_socket_info) 39 0 : : dispatcher_(dispatcher), extended_socket_info_(extended_socket_info) {} 40 : 41 0 : Event::Dispatcher& dispatcher() override { return dispatcher_; } 42 : 43 : void onCertValidationResult(bool succeeded, Ssl::ClientValidationStatus detailed_status, 44 : const std::string& error_details, uint8_t tls_alert) override; 45 : 46 : void onSslHandshakeCancelled(); 47 : 48 : private: 49 : Event::Dispatcher& dispatcher_; 50 : OptRef<SslExtendedSocketInfoImpl> extended_socket_info_; 51 : }; 52 : 53 : class SslExtendedSocketInfoImpl : public Envoy::Ssl::SslExtendedSocketInfo { 54 : public: 55 0 : explicit SslExtendedSocketInfoImpl(SslHandshakerImpl& handshaker) : ssl_handshaker_(handshaker) {} 56 : // Overridden to notify cert_validate_result_callback_ that the handshake has been cancelled. 57 : ~SslExtendedSocketInfoImpl() override; 58 : 59 : void setCertificateValidationStatus(Envoy::Ssl::ClientValidationStatus validated) override; 60 : Envoy::Ssl::ClientValidationStatus certificateValidationStatus() const override; 61 : Ssl::ValidateResultCallbackPtr createValidateResultCallback() override; 62 : void onCertificateValidationCompleted(bool succeeded, bool async) override; 63 0 : Ssl::ValidateStatus certificateValidationResult() const override { 64 0 : return cert_validation_result_; 65 0 : } 66 0 : uint8_t certificateValidationAlert() const override { return cert_validation_alert_; } 67 : 68 0 : void setCertificateValidationAlert(uint8_t alert) { cert_validation_alert_ = alert; } 69 : 70 : private: 71 : Envoy::Ssl::ClientValidationStatus certificate_validation_status_{ 72 : Envoy::Ssl::ClientValidationStatus::NotValidated}; 73 : SslHandshakerImpl& ssl_handshaker_; 74 : // Latch the in-flight async cert validation callback. 75 : // nullopt if there is none. 76 : OptRef<ValidateResultCallbackImpl> cert_validate_result_callback_; 77 : // Stores the TLS alert. 78 : uint8_t cert_validation_alert_{SSL_AD_CERTIFICATE_UNKNOWN}; 79 : // Stores the validation result if there is any. 80 : // nullopt if no validation has ever been kicked off. 81 : Ssl::ValidateStatus cert_validation_result_{Ssl::ValidateStatus::NotStarted}; 82 : }; 83 : 84 : class SslHandshakerImpl : public ConnectionInfoImplBase, 85 : public Ssl::Handshaker, 86 : protected Logger::Loggable<Logger::Id::connection> { 87 : public: 88 : SslHandshakerImpl(bssl::UniquePtr<SSL> ssl, int ssl_extended_socket_info_index, 89 : Ssl::HandshakeCallbacks* handshake_callbacks); 90 : 91 : // Ssl::ConnectionInfo 92 : bool peerCertificateValidated() const override; 93 : 94 : // ConnectionInfoImplBase 95 0 : SSL* ssl() const override { return ssl_.get(); } 96 : 97 : // Ssl::Handshaker 98 : Network::PostIoAction doHandshake() override; 99 : 100 0 : Ssl::SocketState state() const { return state_; } 101 0 : void setState(Ssl::SocketState state) { state_ = state; } 102 0 : Ssl::HandshakeCallbacks* handshakeCallbacks() { return handshake_callbacks_; } 103 : 104 : bssl::UniquePtr<SSL> ssl_; 105 : 106 : private: 107 : Ssl::HandshakeCallbacks* handshake_callbacks_; 108 : 109 : Ssl::SocketState state_{Ssl::SocketState::PreHandshake}; 110 : mutable SslExtendedSocketInfoImpl extended_socket_info_; 111 : }; 112 : 113 : using SslHandshakerImplSharedPtr = std::shared_ptr<SslHandshakerImpl>; 114 : 115 : class HandshakerFactoryContextImpl : public Ssl::HandshakerFactoryContext { 116 : public: 117 : HandshakerFactoryContextImpl(Api::Api& api, const Server::Options& options, 118 : absl::string_view alpn_protocols, 119 : Singleton::Manager& singleton_manager) 120 : : api_(api), options_(options), alpn_protocols_(alpn_protocols), 121 0 : singleton_manager_(singleton_manager) {} 122 : 123 : // HandshakerFactoryContext 124 0 : Api::Api& api() override { return api_; } 125 0 : const Server::Options& options() const override { return options_; } 126 0 : absl::string_view alpnProtocols() const override { return alpn_protocols_; } 127 0 : Singleton::Manager& singletonManager() override { return singleton_manager_; } 128 : 129 : private: 130 : Api::Api& api_; 131 : const Server::Options& options_; 132 : const std::string alpn_protocols_; 133 : Singleton::Manager& singleton_manager_; 134 : }; 135 : 136 : class HandshakerFactoryImpl : public Ssl::HandshakerFactory { 137 : public: 138 0 : std::string name() const override { return "envoy.default_tls_handshaker"; } 139 : 140 0 : ProtobufTypes::MessagePtr createEmptyConfigProto() override { 141 0 : return ProtobufTypes::MessagePtr{new Envoy::ProtobufWkt::Struct()}; 142 0 : } 143 : 144 : Ssl::HandshakerFactoryCb createHandshakerCb(const Protobuf::Message&, 145 : Ssl::HandshakerFactoryContext&, 146 0 : ProtobufMessage::ValidationVisitor&) override { 147 : // The default HandshakerImpl doesn't take a config or use the HandshakerFactoryContext. 148 0 : return [](bssl::UniquePtr<SSL> ssl, int ssl_extended_socket_info_index, 149 0 : Ssl::HandshakeCallbacks* handshake_callbacks) { 150 0 : return std::make_shared<SslHandshakerImpl>(std::move(ssl), ssl_extended_socket_info_index, 151 0 : handshake_callbacks); 152 0 : }; 153 0 : } 154 : 155 0 : Ssl::HandshakerCapabilities capabilities() const override { 156 : // The default handshaker impl requires Envoy to handle all enumerated behaviors. 157 0 : return Ssl::HandshakerCapabilities{}; 158 0 : } 159 : 160 0 : Ssl::SslCtxCb sslctxCb(Ssl::HandshakerFactoryContext&) const override { 161 : // The default handshaker impl doesn't additionally modify SSL_CTX. 162 0 : return nullptr; 163 0 : } 164 : 165 0 : static HandshakerFactory* getDefaultHandshakerFactory() { 166 0 : static HandshakerFactoryImpl default_handshaker_factory; 167 0 : return &default_handshaker_factory; 168 0 : } 169 : }; 170 : 171 : } // namespace Tls 172 : } // namespace TransportSockets 173 : } // namespace Extensions 174 : } // namespace Envoy