diff --git a/net/proxy/http/BUILD b/net/proxy/http/BUILD index 3d316a9..4ac972e 100644 --- a/net/proxy/http/BUILD +++ b/net/proxy/http/BUILD @@ -14,3 +14,15 @@ cc_library( "@org_iceboy_trunk//util:strings", ], ) + +cc_library( + name = "tls-stream", + srcs = ["tls-stream.cc"], + hdrs = ["tls-stream.h"], + deps = [ + "//net/proxy:interface", + "//net/proxy/util:stream-wrapper", + "@boringssl//:ssl", + "@com_google_absl//absl/container:fixed_array", + ], +) diff --git a/net/proxy/http/tls-stream.cc b/net/proxy/http/tls-stream.cc new file mode 100644 index 0000000..54e560f --- /dev/null +++ b/net/proxy/http/tls-stream.cc @@ -0,0 +1,52 @@ +#include "net/proxy/http/tls-stream.h" + +#include + +#include "absl/container/fixed_array.h" + +namespace net { +namespace proxy { +namespace http { + +TlsStream::TlsStream( + const any_io_executor &executor, + Stream &base_stream, + boost::asio::ssl::context &ssl_context) + : base_stream_wrapper_(base_stream, executor), + ssl_stream_(base_stream_wrapper_, ssl_context) { + // TODO: SSL_set_tlsext_host_name if not numeric host +} + +void TlsStream::handshake( + absl::AnyInvocable callback) { + ssl_stream_.async_handshake( + boost::asio::ssl::stream_base::client, + std::move(callback)); +} + +void TlsStream::read( + absl::Span buffers, + absl::AnyInvocable callback) { + ssl_stream_.async_read_some( + absl::FixedArray(buffers.begin(), buffers.end()), + std::move(callback)); +} + +void TlsStream::write( + absl::Span buffers, + absl::AnyInvocable callback) { + ssl_stream_.async_write_some( + absl::FixedArray(buffers.begin(), buffers.end()), + std::move(callback)); +} + +std::string_view TlsStream::alpn_selected() { + const unsigned char *data; + unsigned int len; + SSL_get0_alpn_selected(ssl_stream_.native_handle(), &data, &len); + return std::string_view(reinterpret_cast(data), len); +} + +} // namespace http +} // namespace proxy +} // namespace net diff --git a/net/proxy/http/tls-stream.h b/net/proxy/http/tls-stream.h new file mode 100644 index 0000000..2d69019 --- /dev/null +++ b/net/proxy/http/tls-stream.h @@ -0,0 +1,42 @@ +#ifndef _NET_PROXY_HTTP_TLS_STREAM_H +#define _NET_PROXY_HTTP_TLS_STREAM_H + +#include "boost/asio/ssl.hpp" +#include "net/proxy/stream.h" +#include "net/proxy/util/stream-wrapper.h" + +namespace net { +namespace proxy { +namespace http { + +class TlsStream : public Stream { +public: + TlsStream( + const any_io_executor &executor, + Stream &base_stream, + boost::asio::ssl::context &ssl_context); + + void handshake(absl::AnyInvocable callback); + + void read( + absl::Span buffers, + absl::AnyInvocable callback) override; + + void write( + absl::Span buffers, + absl::AnyInvocable callback) override; + + void close() override { base_stream_wrapper_.stream().close(); } + + std::string_view alpn_selected(); + +private: + StreamWrapper base_stream_wrapper_; + boost::asio::ssl::stream ssl_stream_; +}; + +} // namespace http +} // namespace proxy +} // namespace net + +#endif // _NET_PROXY_HTTP_TLS_STREAM_H