added iOS source code
[wl-app.git] / iOS / Pods / Realm / include / core / realm / util / network_ssl.hpp
1 /*************************************************************************
2  *
3  * REALM CONFIDENTIAL
4  * __________________
5  *
6  *  [2011] - [2015] Realm Inc
7  *  All Rights Reserved.
8  *
9  * NOTICE:  All information contained herein is, and remains
10  * the property of Realm Incorporated and its suppliers,
11  * if any.  The intellectual and technical concepts contained
12  * herein are proprietary to Realm Incorporated
13  * and its suppliers and may be covered by U.S. and Foreign Patents,
14  * patents in process, and are protected by trade secret or copyright law.
15  * Dissemination of this information or reproduction of this material
16  * is strictly forbidden unless prior written permission is obtained
17  * from Realm Incorporated.
18  *
19  **************************************************************************/
20 #ifndef REALM_UTIL_NETWORK_SSL_HPP
21 #define REALM_UTIL_NETWORK_SSL_HPP
22
23 #include <cstddef>
24 #include <limits>
25 #include <memory>
26 #include <string>
27 #include <exception>
28 #include <system_error>
29
30 #include <realm/util/features.h>
31 #include <realm/util/assert.hpp>
32 #include <realm/util/misc_errors.hpp>
33 #include <realm/util/network.hpp>
34 #include <realm/util/optional.hpp>
35
36 #if REALM_HAVE_OPENSSL
37 #  include <openssl/ssl.h>
38 #  include <openssl/err.h>
39 #elif REALM_HAVE_SECURE_TRANSPORT
40 #  include <realm/util/cf_ptr.hpp>
41 #  include <Security/Security.h>
42 #  include <Security/SecureTransport.h>
43
44 #define REALM_HAVE_KEYCHAIN_APIS (TARGET_OS_MAC && !TARGET_OS_IPHONE)
45
46 #endif
47
48 // FIXME: Add necessary support for customizing the SSL server and client
49 // configurations.
50
51 // FIXME: Currently, the synchronous SSL operations (handshake, read, write,
52 // shutdown) do not automatically retry if the underlying SSL function returns
53 // with SSL_ERROR_WANT_READ or SSL_ERROR_WANT_WRITE. This normally never
54 // happens, but it can happen according to the man pages, but in the case of
55 // SSL_write(), only when a renegotiation has to take place. It is likely that
56 // the solution is to to wrap the SSL calls inside a loop, such that they keep
57 // retrying until they succeed, however, such a simple scheme will fail if the
58 // synchronous operations were to be used with an underlying TCP socket in
59 // nonblocking mode. Currently, the underlying TCP socket is always in blocking
60 // mode when performing synchronous operations, but that may continue to be the
61 // case in teh future.
62
63
64 namespace realm {
65 namespace util {
66 namespace network {
67 namespace ssl {
68
69 enum class Error {
70     certificate_rejected = 1,
71 };
72
73 const std::error_category& ssl_error_category();
74
75 std::error_condition make_error_condition(Error value);
76
77 } // namespace ssl
78 } // namespace network
79 } // namespace util
80 } // namespace realm
81
82 namespace std {
83
84 template <>
85 struct is_error_condition_enum<realm::util::network::ssl::Error>: public true_type {};
86
87 } // namespace std
88
89 namespace realm {
90 namespace util {
91 namespace network {
92 namespace ssl {
93
94 #if REALM_HAVE_OPENSSL
95
96 const std::error_category& openssl_error_category();
97
98 #elif REALM_HAVE_SECURE_TRANSPORT
99
100 const std::error_category& secure_transport_error_category();
101
102 #endif
103
104
105 class ProtocolNotSupported;
106
107
108 /// `VerifyMode::none` corresponds to OpenSSL's `SSL_VERIFY_NONE`, and
109 /// `VerifyMode::peer` to `SSL_VERIFY_PEER`.
110 enum class VerifyMode { none, peer };
111
112
113 class Context {
114 public:
115     Context();
116     ~Context() noexcept;
117
118     /// File must be in PEM format. Corresponds to OpenSSL's
119     /// `SSL_CTX_use_certificate_chain_file()`.
120     void use_certificate_chain_file(const std::string& path);
121
122     /// File must be in PEM format. Corresponds to OpenSSL's
123     /// `SSL_CTX_use_PrivateKey_file()`.
124     void use_private_key_file(const std::string& path);
125
126     /// Calling use_default_verify() will make a client use the
127     /// device default certificates for server verification.
128     /// For OpenSSL, use_default_verify() corresponds to
129     /// SSL_CTX_set_default_verify_paths(SSL_CTX*);
130     void use_default_verify();
131
132     /// The verify file is a PEM file containing trust
133     /// certificates that the client will use to
134     /// verify the server crtificate. If use_verify_file()
135     /// is not called, the default device trust store will
136     /// be used.
137     /// Corresponds roughly to OpenSSL's
138     /// SSL_CTX_load_verify_locations().
139     void use_verify_file(const std::string& path);
140
141 private:
142     void ssl_init();
143     void ssl_destroy() noexcept;
144     void ssl_use_certificate_chain_file(const std::string& path, std::error_code&);
145     void ssl_use_private_key_file(const std::string& path, std::error_code&);
146     void ssl_use_default_verify(std::error_code&);
147     void ssl_use_verify_file(const std::string& path, std::error_code&);
148
149 #if REALM_HAVE_OPENSSL
150     SSL_CTX* m_ssl_ctx = nullptr;
151
152 #elif REALM_HAVE_SECURE_TRANSPORT
153
154 #if REALM_HAVE_KEYCHAIN_APIS
155     static util::CFPtr<CFArrayRef> load_pem_file(const std::string& path, SecKeychainRef, std::error_code&);
156
157     std::error_code open_temporary_keychain_if_needed();
158     std::error_code update_identity_if_needed();
159
160     util::CFPtr<SecKeychainRef> m_keychain;
161     std::string m_keychain_path;
162
163     util::CFPtr<SecCertificateRef> m_certificate;
164     util::CFPtr<SecKeyRef> m_private_key;
165     util::CFPtr<SecIdentityRef> m_identity;
166
167     util::CFPtr<CFArrayRef> m_certificate_chain;
168
169     util::CFPtr<CFArrayRef> m_trust_anchors;
170 #endif // REALM_HAVE_KEYCHAIN_APIS
171
172 #endif
173
174     friend class Stream;
175 };
176
177
178 /// Switching between synchronous and asynchronous operations is allowed, but
179 /// only in a nonoverlapping fashion. That is, a synchronous operation is not
180 /// allowed to run concurrently with an asynchronous one on the same
181 /// stream. Note that an asynchronous operation is considered to be running
182 /// until its completion handler starts executing.
183 class Stream {
184 public:
185     using port_type = util::network::Endpoint::port_type;
186     using SSLVerifyCallback = bool(const std::string& server_address,
187                                    port_type server_port,
188                                    const char* pem_data,
189                                    size_t pem_size,
190                                    int preverify_ok,
191                                    int depth);
192
193     enum HandshakeType { client, server };
194
195     Stream(Socket&, Context&, HandshakeType);
196     ~Stream() noexcept;
197
198     /// \brief Set the certificate verification mode for this SSL stream.
199     ///
200     /// Corresponds to OpenSSL's `SSL_set_verify()` with null passed as
201     /// `verify_callback`.
202     ///
203     /// Clients should always set it to `VerifyMode::peer`, such that the client
204     /// verifies the servers certificate. Servers should only set it to
205     /// `VerifyMode::peer` if they want to request a certificate from the
206     /// client. When testing with self-signed certificates, it is necessary to
207     /// set it to `VerifyMode::none` for clients too.
208     ///
209     /// It is an error if this function is called after the handshake operation
210     /// is initiated.
211     ///
212     /// The default verify mode is `VerifyMode::none`.
213     void set_verify_mode(VerifyMode);
214
215     /// \brief Check the certificate against a host_name.
216     ///
217     /// set_check_host() includes a host name check in the
218     /// certificate verification. It is typically used by clients
219     /// to secure that the received certificate has a common name
220     /// or subject alternative name that matches \param host_name.
221     ///
222     /// set_check_host() is only useful if verify_mode is
223     /// set to VerifyMode::peer.
224     void set_check_host(std::string host_name);
225     const std::string& get_host_name();
226
227     /// get_server_port() and set_server_port() are getter and setter for
228     /// the server port. They are only used by the verify callback function
229     /// below.
230     port_type get_server_port();
231     void set_server_port(port_type server_port);
232
233     /// If use_verify_callback() is called, the SSL certificate chain of
234     /// the server is presented to callback, one certificate at a time.
235     /// The SSL connection is accepted if and only if callback returns true
236     /// for all certificates.
237     /// The signature of \param callback is
238     ///
239     /// bool(const std::string& server_address,
240     ///      port_type server_port,
241     ///      const char* pem_data,
242     ///      size_t pem_size,
243     ///      int preverify_ok,
244     ///      int depth);
245     //
246     /// server address and server_port is the address and port of the server
247     /// that a SSL connection is being established to.
248     /// pem_data is the certificate of length pem_size in
249     /// the PEM format. preverify_ok is OpenSSL's preverification of the
250     /// certificate. preverify_ok is either 0, or 1. If preverify_ok is 1,
251     /// OpenSSL has accepted the certificate and it will generally be safe
252     /// to trust that certificate. depth represents the position of the
253     /// certificate in the certificate chain sent by the server. depth = 0
254     /// represents the actual server certificate that should contain the
255     /// host name(server address) of the server. The highest depth is the
256     /// root certificate.
257     /// The callback function will receive the certificates starting from
258     /// the root certificate and moving down the chain until it reaches the
259     /// server's own certificate with a host name. The depth of the last
260     /// certificate is 0. The depth of the first certificate is chain
261     /// length - 1.
262     ///
263     /// The return value of the callback function decides whether the
264     /// client accepts the certificate. If the return value is false, the
265     /// processing of the certificate chain is interrupted and the SSL
266     /// connection is rejected. If the return value is true, the verification
267     /// process continues. If the callback function returns true for all
268     /// presented certificates including the depth == 0 certificate, the
269     /// SSL connection is accepted.
270     ///
271     /// A recommended way of using the callback function is to return true
272     /// if preverify_ok = 1 and depth > 0,
273     /// always check the host name if depth = 0,
274     /// and use an independent verification step if preverify_ok = 0.
275     ///
276     /// Another possible way of using the callback is to collect all the
277     /// certificates until depth = 0, and present the entire chain for
278     /// independent verification.
279     void use_verify_callback(const std::function<SSLVerifyCallback>& callback);
280
281     /// @{
282     ///
283     /// Read and write operations behave the same way as they do on \ref
284     /// network::Socket, except that after cancellation of asynchronous
285     /// operations (`lowest_layer().cancel()`), the stream may be left in a bad
286     /// state (see below).
287     ///
288     /// The handshake operation must complete successfully before any read,
289     /// write, or shutdown operations are performed.
290     ///
291     /// The shutdown operation sends the shutdown alert to the peer, and
292     /// returns/completes as soon as the alert message has been written to the
293     /// underlying socket. It is an error if the shutdown operation is initiated
294     /// while there are read or write operations in progress. No read or write
295     /// operations are allowed to be initiated after the shutdown operation has
296     /// been initiated. When the shutdown operation has completed, it is safe to
297     /// close the underlying socket (`lowest_layer().close()`).
298     ///
299     /// If a write operation is executing while, or is initiated after a close
300     /// notify alert is received from the remote peer, the write operation will
301     /// fail with error::broken_pipe.
302     ///
303     /// Callback functions for async read and write operations must take two
304     /// arguments, an std::error_code(), and an integer of a type std::size_t
305     /// indicating the number of transferred bytes (other types are allowed as
306     /// long as implicit conversion can take place).
307     ///
308     /// Callback functions for async handshake and shutdown operations must take
309     /// a single argument of type std::error_code() (other types are allowed as
310     /// long as implicit conversion can take place).
311     ///
312     /// Resumption of stream operation after cancellation of asynchronous
313     /// operations is not supported (does not work). Since the shutdown
314     /// operation involves network communication, that operation is also not
315     /// allowed after cancellation. The only thing that is allowed, is to
316     /// destroy the stream object. Other stream objects are not affected.
317
318     void handshake();
319     std::error_code handshake(std::error_code&);
320
321     std::size_t read(char* buffer, std::size_t size);
322     std::size_t read(char* buffer, std::size_t size, std::error_code& ec);
323     std::size_t read(char* buffer, std::size_t size, ReadAheadBuffer&);
324     std::size_t read(char* buffer, std::size_t size, ReadAheadBuffer&, std::error_code& ec);
325     std::size_t read_until(char* buffer, std::size_t size, char delim, ReadAheadBuffer&);
326     std::size_t read_until(char* buffer, std::size_t size, char delim, ReadAheadBuffer&,
327                            std::error_code& ec);
328
329     std::size_t write(const char* data, std::size_t size);
330     std::size_t write(const char* data, std::size_t size, std::error_code& ec);
331
332     std::size_t read_some(char* buffer, std::size_t size);
333     std::size_t read_some(char* buffer, std::size_t size, std::error_code&);
334
335     std::size_t write_some(const char* data, std::size_t size);
336     std::size_t write_some(const char* data, std::size_t size, std::error_code&);
337
338     void shutdown();
339     std::error_code shutdown(std::error_code&);
340
341     template<class H> void async_handshake(H handler);
342
343     template<class H> void async_read(char* buffer, std::size_t size, H handler);
344     template<class H> void async_read(char* buffer, std::size_t size, ReadAheadBuffer&, H handler);
345     template<class H> void async_read_until(char* buffer, std::size_t size, char delim,
346                                             ReadAheadBuffer&, H handler);
347
348     template<class H> void async_write(const char* data, std::size_t size, H handler);
349
350     template<class H> void async_read_some(char* buffer, std::size_t size, H handler);
351
352     template<class H> void async_write_some(const char* data, std::size_t size, H handler);
353
354     template<class H> void async_shutdown(H handler);
355
356     /// @}
357
358     /// Returns a reference to the underlying socket.
359     Socket& lowest_layer() noexcept;
360
361 private:
362     using Want = Service::Want;
363     using StreamOps = Service::BasicStreamOps<Stream>;
364
365     class HandshakeOperBase;
366     template<class H> class HandshakeOper;
367     class ShutdownOperBase;
368     template<class H> class ShutdownOper;
369
370     using LendersHandshakeOperPtr = std::unique_ptr<HandshakeOperBase, Service::LendersOperDeleter>;
371     using LendersShutdownOperPtr  = std::unique_ptr<ShutdownOperBase,  Service::LendersOperDeleter>;
372
373     Socket& m_tcp_socket;
374     Context& m_ssl_context;
375     const HandshakeType m_handshake_type;
376
377     // The host name that the certificate should be checked against.
378     // The host name is called server address in the certificate verify
379     // callback function.
380     std::string m_host_name;
381
382     // The port of the server which is used in the certificate verify
383     // callback function.
384     port_type m_server_port;
385
386     // The callback for certificate verification and an
387     // opaque argument that will be supplied to the callback.
388     const std::function<SSLVerifyCallback>* m_ssl_verify_callback = nullptr;
389
390     // See Service::BasicStreamOps for details on these these 6 functions.
391     void do_init_read_async(std::error_code&, Want&) noexcept;
392     void do_init_write_async(std::error_code&, Want&) noexcept;
393     std::size_t do_read_some_sync(char* buffer, std::size_t size,
394                                   std::error_code&) noexcept;
395     std::size_t do_write_some_sync(const char* data, std::size_t size,
396                                    std::error_code&) noexcept;
397     std::size_t do_read_some_async(char* buffer, std::size_t size,
398                                    std::error_code&, Want&) noexcept;
399     std::size_t do_write_some_async(const char* data, std::size_t size,
400                                     std::error_code&, Want&) noexcept;
401
402     // The meaning of the arguments and return values of ssl_read() and
403     // ssl_write() are identical to do_read_some_async() and
404     // do_write_some_async() respectively, except that when the return value is
405     // nonzero, `want` is always `Want::nothing`, meaning that after bytes have
406     // been transferred, ssl_read() and ssl_write() must be called again to
407     // figure out whether it is necessary to wait for read or write readiness.
408     //
409     // The first invocation of ssl_shutdown() must send the shutdown alert to
410     // the peer. In blocking mode it must wait until the alert has been sent. In
411     // nonblocking mode, it must keep setting `want` to something other than
412     // `Want::nothing` until the alert has been sent. When the shutdown alert
413     // has been sent, it is safe to shut down the sending side of the underlying
414     // socket. On failure, ssl_shutdown() must set `ec` to something different
415     // than `std::error_code()` and return false. On success, it must set `ec`
416     // to `std::error_code()`, and return true if a shutdown alert from the peer
417     // has already been received, otherwise it must return false. When it sets
418     // `want` to something other than `Want::nothing`, it must set `ec` to
419     // `std::error_code()` and return false.
420     //
421     // The second invocation of ssl_shutdown() (after the first invocation
422     // completed) must wait for reception on the peers shutdown alert.
423     //
424     // Note: The semantics around the second invocation of shutdown is currently
425     // unused by the higher level API, because of a requirement of compatibility
426     // with Apple's Secure Transport API.
427     void ssl_init();
428     void ssl_destroy() noexcept;
429     void ssl_set_verify_mode(VerifyMode, std::error_code&);
430     void ssl_set_check_host(std::string, std::error_code&);
431     void ssl_use_verify_callback(const std::function<SSLVerifyCallback>&, std::error_code&);
432
433     void ssl_handshake(std::error_code&, Want& want) noexcept;
434     bool ssl_shutdown(std::error_code& ec, Want& want) noexcept;
435     std::size_t ssl_read(char* buffer, std::size_t size,
436                          std::error_code&, Want& want) noexcept;
437     std::size_t ssl_write(const char* data, std::size_t size,
438                           std::error_code&, Want& want) noexcept;
439
440 #if REALM_HAVE_OPENSSL
441     class BioMethod;
442     static BioMethod s_bio_method;
443     SSL* m_ssl = nullptr;
444     std::error_code m_bio_error_code;
445
446     int m_ssl_index = -1;
447
448     template<class Oper>
449     std::size_t ssl_perform(Oper oper, std::error_code& ec, Want& want) noexcept;
450
451     int do_ssl_accept() noexcept;
452     int do_ssl_connect() noexcept;
453     int do_ssl_shutdown() noexcept;
454     int do_ssl_read(char* buffer, std::size_t size) noexcept;
455     int do_ssl_write(const char* data, std::size_t size) noexcept;
456
457     static int bio_write(BIO*, const char*, int) noexcept;
458     static int bio_read(BIO*, char*, int) noexcept;
459     static int bio_puts(BIO*, const char*) noexcept;
460     static long bio_ctrl(BIO*, int, long, void*) noexcept;
461     static int bio_create(BIO*) noexcept;
462     static int bio_destroy(BIO*) noexcept;
463
464     // verify_callback_using_hostname is used as an argument to OpenSSL's SSL_set_verify function.
465     // verify_callback_using_hostname verifies that the certificate is valid and contains
466     // m_host_name as a Common Name or Subject Alternative Name.
467     static int verify_callback_using_hostname(int preverify_ok, X509_STORE_CTX *ctx) noexcept;
468
469     // verify_callback_using_delegate() is also used as an argument to OpenSSL's set_verify_function.
470     // verify_callback_using_delegate() calls out to the user supplied verify callback.
471     static int verify_callback_using_delegate(int preverify_ok, X509_STORE_CTX *ctx) noexcept;
472 #elif REALM_HAVE_SECURE_TRANSPORT
473     util::CFPtr<SSLContextRef> m_ssl;
474     VerifyMode m_verify_mode = VerifyMode::none;
475
476     enum class BlockingOperation {
477         read,
478         write,
479     };
480     util::Optional<BlockingOperation> m_last_operation;
481
482     // Details of the underlying I/O error that lead to errSecIO being returned
483     // from a SecureTransport function.
484     std::error_code m_last_error;
485
486     // The number of bytes accepted by SSWrite() but not yet confirmed to be
487     // written to the underlying socket.
488     std::size_t m_num_partially_written_bytes = 0;
489
490     template<class Oper>
491     std::size_t ssl_perform(Oper oper, std::error_code& ec, Want& want) noexcept;
492
493     std::pair<OSStatus, std::size_t> do_ssl_handshake() noexcept;
494     std::pair<OSStatus, std::size_t> do_ssl_shutdown() noexcept;
495     std::pair<OSStatus, std::size_t> do_ssl_read(char* buffer, std::size_t size) noexcept;
496     std::pair<OSStatus, std::size_t> do_ssl_write(const char* data, std::size_t size) noexcept;
497
498     static OSStatus tcp_read(SSLConnectionRef, void*, std::size_t* length) noexcept;
499     static OSStatus tcp_write(SSLConnectionRef, const void*, std::size_t* length) noexcept;
500
501     OSStatus tcp_read(void*, std::size_t* length) noexcept;
502     OSStatus tcp_write(const void*, std::size_t* length) noexcept;
503
504     OSStatus verify_peer() noexcept;
505 #endif
506
507     friend class Service::BasicStreamOps<Stream>;
508     friend class network::ReadAheadBuffer;
509 };
510
511
512 // Implementation
513
514 class ProtocolNotSupported: public std::exception {
515 public:
516     const char* what() const noexcept override final;
517 };
518
519 inline Context::Context()
520 {
521     ssl_init(); // Throws
522 }
523
524 inline Context::~Context() noexcept
525 {
526     ssl_destroy();
527 }
528
529 inline void Context::use_certificate_chain_file(const std::string& path)
530 {
531     std::error_code ec;
532     ssl_use_certificate_chain_file(path, ec); // Throws
533     if (ec)
534         throw std::system_error(ec);
535 }
536
537 inline void Context::use_private_key_file(const std::string& path)
538 {
539     std::error_code ec;
540     ssl_use_private_key_file(path, ec); // Throws
541     if (ec)
542         throw std::system_error(ec);
543 }
544
545 inline void Context::use_default_verify()
546 {
547     std::error_code ec;
548     ssl_use_default_verify(ec);
549     if (ec)
550         throw std::system_error(ec);
551 }
552
553 inline void Context::use_verify_file(const std::string& path)
554 {
555     std::error_code ec;
556     ssl_use_verify_file(path, ec);
557     if (ec)
558         throw std::system_error(ec);
559 }
560
561 class Stream::HandshakeOperBase: public Service::IoOper {
562 public:
563     HandshakeOperBase(std::size_t size, Stream& stream):
564         IoOper{size},
565         m_stream{&stream}
566     {
567     }
568     Want initiate()
569     {
570         REALM_ASSERT(this == m_stream->m_tcp_socket.m_read_oper.get());
571         REALM_ASSERT(!is_complete());
572         m_stream->m_tcp_socket.m_desc.ensure_nonblocking_mode(); // Throws
573         return advance();
574     }
575     Want advance() noexcept override final
576     {
577         REALM_ASSERT(!is_complete());
578         REALM_ASSERT(!is_canceled());
579         REALM_ASSERT(!m_error_code);
580         Want want = Want::nothing;
581         m_stream->ssl_handshake(m_error_code, want);
582         set_is_complete(want == Want::nothing);
583         return want;
584     }
585     void recycle() noexcept override final
586     {
587         bool orphaned = !m_stream;
588         REALM_ASSERT(orphaned);
589         // Note: do_recycle() commits suicide.
590         do_recycle(orphaned);
591     }
592     void orphan() noexcept override final
593     {
594         m_stream = nullptr;
595     }
596     Service::Descriptor& descriptor() noexcept override final
597     {
598         return m_stream->lowest_layer().m_desc;
599     }
600 protected:
601     Stream* m_stream;
602     std::error_code m_error_code;
603 };
604
605 template<class H> class Stream::HandshakeOper: public HandshakeOperBase {
606 public:
607     HandshakeOper(std::size_t size, Stream& stream, H handler):
608         HandshakeOperBase{size, stream},
609         m_handler{std::move(handler)}
610     {
611     }
612     void recycle_and_execute() override final
613     {
614         REALM_ASSERT(is_complete() || is_canceled());
615         bool orphaned = !m_stream;
616         std::error_code ec = m_error_code;
617         if (is_canceled())
618             ec = error::operation_aborted;
619         // Note: do_recycle_and_execute() commits suicide.
620         do_recycle_and_execute<H>(orphaned, m_handler, ec); // Throws
621     }
622 private:
623     H m_handler;
624 };
625
626 class Stream::ShutdownOperBase: public Service::IoOper {
627 public:
628     ShutdownOperBase(std::size_t size, Stream& stream):
629         IoOper{size},
630         m_stream{&stream}
631     {
632     }
633     Want initiate()
634     {
635         REALM_ASSERT(this == m_stream->m_tcp_socket.m_write_oper.get());
636         REALM_ASSERT(!is_complete());
637         m_stream->m_tcp_socket.m_desc.ensure_nonblocking_mode(); // Throws
638         return advance();
639     }
640     Want advance() noexcept override final
641     {
642         REALM_ASSERT(!is_complete());
643         REALM_ASSERT(!is_canceled());
644         REALM_ASSERT(!m_error_code);
645         Want want = Want::nothing;
646         m_stream->ssl_shutdown(m_error_code, want);
647         if (want == Want::nothing)
648             set_is_complete(true);
649         return want;
650     }
651     void recycle() noexcept override final
652     {
653         bool orphaned = !m_stream;
654         REALM_ASSERT(orphaned);
655         // Note: do_recycle() commits suicide.
656         do_recycle(orphaned);
657     }
658     void orphan() noexcept override final
659     {
660         m_stream = nullptr;
661     }
662     Service::Descriptor& descriptor() noexcept override final
663     {
664         return m_stream->lowest_layer().m_desc;
665     }
666 protected:
667     Stream* m_stream;
668     std::error_code m_error_code;
669 };
670
671 template<class H> class Stream::ShutdownOper: public ShutdownOperBase {
672 public:
673     ShutdownOper(std::size_t size, Stream& stream, H handler):
674         ShutdownOperBase{size, stream},
675         m_handler{std::move(handler)}
676     {
677     }
678     void recycle_and_execute() override final
679     {
680         REALM_ASSERT(is_complete() || is_canceled());
681         bool orphaned = !m_stream;
682         std::error_code ec = m_error_code;
683         if (is_canceled())
684             ec = error::operation_aborted;
685         // Note: do_recycle_and_execute() commits suicide.
686         do_recycle_and_execute<H>(orphaned, m_handler, ec); // Throws
687     }
688 private:
689     H m_handler;
690 };
691
692 inline Stream::Stream(Socket& socket, Context& context, HandshakeType type):
693     m_tcp_socket{socket},
694     m_ssl_context{context},
695     m_handshake_type{type}
696 {
697     ssl_init(); // Throws
698 }
699
700 inline Stream::~Stream() noexcept
701 {
702     m_tcp_socket.cancel();
703     ssl_destroy();
704 }
705
706 inline void Stream::set_verify_mode(VerifyMode mode)
707 {
708     std::error_code ec;
709     ssl_set_verify_mode(mode, ec); // Throws
710     if (ec)
711         throw std::system_error(ec);
712 }
713
714 inline void Stream::set_check_host(std::string host_name)
715 {
716     m_host_name = host_name;
717     std::error_code ec;
718     ssl_set_check_host(host_name, ec);
719     if (ec)
720         throw std::system_error(ec);
721 }
722
723 inline const std::string& Stream::get_host_name()
724 {
725     return m_host_name;
726 }
727
728 inline Stream::port_type Stream::get_server_port()
729 {
730     return m_server_port;
731 }
732
733 inline void Stream::set_server_port(port_type server_port)
734 {
735     m_server_port = server_port;
736 }
737
738 inline void Stream::use_verify_callback(const std::function<SSLVerifyCallback>& callback)
739 {
740     std::error_code ec;
741     ssl_use_verify_callback(callback, ec); // Throws
742     if (ec)
743         throw std::system_error(ec);
744 }
745 inline void Stream::handshake()
746 {
747     std::error_code ec;
748     if (handshake(ec)) // Throws
749         throw std::system_error(ec);
750 }
751
752 inline std::size_t Stream::read(char* buffer, std::size_t size)
753 {
754     std::error_code ec;
755     read(buffer, size, ec); // Throws
756     if (ec)
757         throw std::system_error(ec);
758     return size;
759 }
760
761 inline std::size_t Stream::read(char* buffer, std::size_t size, std::error_code& ec)
762 {
763     return StreamOps::read(*this, buffer, size, ec); // Throws
764 }
765
766 inline std::size_t Stream::read(char* buffer, std::size_t size, ReadAheadBuffer& rab)
767 {
768     std::error_code ec;
769     read(buffer, size, rab, ec); // Throws
770     if (ec)
771         throw std::system_error(ec);
772     return size;
773 }
774
775 inline std::size_t Stream::read(char* buffer, std::size_t size, ReadAheadBuffer& rab,
776                                 std::error_code& ec)
777 {
778     int delim = std::char_traits<char>::eof();
779     return StreamOps::buffered_read(*this, buffer, size, delim, rab, ec); // Throws
780 }
781
782 inline std::size_t Stream::read_until(char* buffer, std::size_t size, char delim,
783                                       ReadAheadBuffer& rab)
784 {
785     std::error_code ec;
786     std::size_t n = read_until(buffer, size, delim, rab, ec); // Throws
787     if (ec)
788         throw std::system_error(ec);
789     return n;
790 }
791
792 inline std::size_t Stream::read_until(char* buffer, std::size_t size, char delim,
793                                       ReadAheadBuffer& rab, std::error_code& ec)
794 {
795     int delim_2 = std::char_traits<char>::to_int_type(delim);
796     return StreamOps::buffered_read(*this, buffer, size, delim_2, rab, ec); // Throws
797 }
798
799 inline std::size_t Stream::write(const char* data, std::size_t size)
800 {
801     std::error_code ec;
802     write(data, size, ec); // Throws
803     if (ec)
804         throw std::system_error(ec);
805     return size;
806 }
807
808 inline std::size_t Stream::write(const char* data, std::size_t size, std::error_code& ec)
809 {
810     return StreamOps::write(*this, data, size, ec); // Throws
811 }
812
813 inline std::size_t Stream::read_some(char* buffer, std::size_t size)
814 {
815     std::error_code ec;
816     std::size_t n = read_some(buffer, size, ec); // Throws
817     if (ec)
818         throw std::system_error(ec);
819     return n;
820 }
821
822 inline std::size_t Stream::read_some(char* buffer, std::size_t size, std::error_code& ec)
823 {
824     return StreamOps::read_some(*this, buffer, size, ec); // Throws
825 }
826
827 inline std::size_t Stream::write_some(const char* data, std::size_t size)
828 {
829     std::error_code ec;
830     std::size_t n = write_some(data, size, ec); // Throws
831     if (ec)
832         throw std::system_error(ec);
833     return n;
834 }
835
836 inline std::size_t Stream::write_some(const char* data, std::size_t size, std::error_code& ec)
837 {
838     return StreamOps::write_some(*this, data, size, ec); // Throws
839 }
840
841 inline void Stream::shutdown()
842 {
843     std::error_code ec;
844     if (shutdown(ec)) // Throws
845         throw std::system_error(ec);
846 }
847
848 template<class H> inline void Stream::async_handshake(H handler)
849 {
850     LendersHandshakeOperPtr op =
851         Service::alloc<HandshakeOper<H>>(m_tcp_socket.m_read_oper, *this,
852                                          std::move(handler)); // Throws
853     m_tcp_socket.m_desc.initiate_oper(std::move(op)); // Throws
854 }
855
856 template<class H> inline void Stream::async_read(char* buffer, std::size_t size, H handler)
857 {
858     bool is_read_some = false;
859     StreamOps::async_read(*this, buffer, size, is_read_some, std::move(handler)); // Throws
860 }
861
862 template<class H>
863 inline void Stream::async_read(char* buffer, std::size_t size, ReadAheadBuffer& rab, H handler)
864 {
865     int delim = std::char_traits<char>::eof();
866     StreamOps::async_buffered_read(*this, buffer, size, delim, rab, std::move(handler)); // Throws
867 }
868
869 template<class H>
870 inline void Stream::async_read_until(char* buffer, std::size_t size, char delim,
871                                      ReadAheadBuffer& rab, H handler)
872 {
873     int delim_2 = std::char_traits<char>::to_int_type(delim);
874     StreamOps::async_buffered_read(*this, buffer, size, delim_2, rab, std::move(handler)); // Throws
875 }
876
877 template<class H> inline void Stream::async_write(const char* data, std::size_t size, H handler)
878 {
879     bool is_write_some = false;
880     StreamOps::async_write(*this, data, size, is_write_some, std::move(handler)); // Throws
881 }
882
883 template<class H> inline void Stream::async_read_some(char* buffer, std::size_t size, H handler)
884 {
885     bool is_read_some = true;
886     StreamOps::async_read(*this, buffer, size, is_read_some, std::move(handler)); // Throws
887 }
888
889 template<class H> inline void Stream::async_write_some(const char* data, std::size_t size, H handler)
890 {
891     bool is_write_some = true;
892     StreamOps::async_write(*this, data, size, is_write_some, std::move(handler)); // Throws
893 }
894
895 template<class H> inline void Stream::async_shutdown(H handler)
896 {
897     LendersShutdownOperPtr op =
898         Service::alloc<ShutdownOper<H>>(m_tcp_socket.m_write_oper, *this,
899                                         std::move(handler)); // Throws
900     m_tcp_socket.m_desc.initiate_oper(std::move(op)); // Throws
901 }
902
903 inline void Stream::do_init_read_async(std::error_code&, Want& want) noexcept
904 {
905     want = Want::nothing; // Proceed immediately unless there is an error
906 }
907
908 inline void Stream::do_init_write_async(std::error_code&, Want& want) noexcept
909 {
910     want = Want::nothing; // Proceed immediately unless there is an error
911 }
912
913 inline std::size_t Stream::do_read_some_sync(char* buffer, std::size_t size,
914                                              std::error_code& ec) noexcept
915 {
916     Want want = Want::nothing;
917     std::size_t n = do_read_some_async(buffer, size, ec, want);
918     if (n == 0 && want != Want::nothing)
919         ec = error::resource_unavailable_try_again;
920     return n;
921 }
922
923 inline std::size_t Stream::do_write_some_sync(const char* data, std::size_t size,
924                                               std::error_code& ec) noexcept
925 {
926     Want want = Want::nothing;
927     std::size_t n = do_write_some_async(data, size, ec, want);
928     if (n == 0 && want != Want::nothing)
929         ec = error::resource_unavailable_try_again;
930     return n;
931 }
932
933 inline std::size_t Stream::do_read_some_async(char* buffer, std::size_t size,
934                                               std::error_code& ec, Want& want) noexcept
935 {
936     return ssl_read(buffer, size, ec, want);
937 }
938
939 inline std::size_t Stream::do_write_some_async(const char* data, std::size_t size,
940                                                std::error_code& ec, Want& want) noexcept
941 {
942     return ssl_write(data, size, ec, want);
943 }
944
945 inline Socket& Stream::lowest_layer() noexcept
946 {
947     return m_tcp_socket;
948 }
949
950
951 #if REALM_HAVE_OPENSSL
952
953 inline void Stream::ssl_handshake(std::error_code& ec, Want& want) noexcept
954 {
955     auto perform = [this]() noexcept {
956         switch (m_handshake_type) {
957             case client:
958                 return do_ssl_connect();
959             case server:
960                 return do_ssl_accept();
961         }
962         REALM_ASSERT(false);
963         return 0;
964     };
965     std::size_t n = ssl_perform(std::move(perform), ec, want);
966     REALM_ASSERT(n == 0 || n == 1);
967     if (want == Want::nothing && n == 0 && !ec) {
968         // End of input on TCP socket
969         ec = network::premature_end_of_input;
970     }
971 }
972
973 inline std::size_t Stream::ssl_read(char* buffer, std::size_t size,
974                                     std::error_code& ec, Want& want) noexcept
975 {
976     auto perform = [this, buffer, size]() noexcept {
977         return do_ssl_read(buffer, size);
978     };
979     std::size_t n = ssl_perform(std::move(perform), ec, want);
980     if (want == Want::nothing && n == 0 && !ec) {
981         // End of input on TCP socket
982         if (SSL_get_shutdown(m_ssl) & SSL_RECEIVED_SHUTDOWN) {
983             ec = network::end_of_input;
984         }
985         else {
986             ec = network::premature_end_of_input;
987         }
988     }
989     return n;
990 }
991
992 inline std::size_t Stream::ssl_write(const char* data, std::size_t size,
993                                      std::error_code& ec, Want& want) noexcept
994 {
995     // While OpenSSL is able to continue writing after we have received the
996     // close notify alert fro the remote peer, Apple's Secure Transport API is
997     // not, so to achieve common behaviour, we make sure that any such attempt
998     // will result in an `error::broken_pipe` error.
999     if ((SSL_get_shutdown(m_ssl) & SSL_RECEIVED_SHUTDOWN) != 0) {
1000         ec = error::broken_pipe;
1001         want = Want::nothing;
1002         return 0;
1003     }
1004     auto perform = [this, data, size]() noexcept {
1005         return do_ssl_write(data, size);
1006     };
1007     std::size_t n = ssl_perform(std::move(perform), ec, want);
1008     if (want == Want::nothing && n == 0 && !ec) {
1009         // End of input on TCP socket
1010         ec = network::premature_end_of_input;
1011     }
1012     return n;
1013 }
1014
1015 inline bool Stream::ssl_shutdown(std::error_code& ec, Want& want) noexcept
1016 {
1017     auto perform = [this]() noexcept {
1018         return do_ssl_shutdown();
1019     };
1020     std::size_t n = ssl_perform(std::move(perform), ec, want);
1021     REALM_ASSERT(n == 0 || n == 1);
1022     if (want == Want::nothing && n == 0 && !ec) {
1023         // The first invocation of SSL_shutdown() does not signal completion
1024         // until the shutdown alert has been sent to the peer, or an error
1025         // occurred (does not wait for acknowledgment).
1026         //
1027         // The second invocation (after a completed first invocation) does not
1028         // signal completion until the peers shutdown alert has been received,
1029         // or an error occurred.
1030         //
1031         // It is believed that:
1032         //
1033         // If this is the first time SSL_shutdown() is called, and
1034         // `SSL_get_shutdown() & SSL_SENT_SHUTDOWN` evaluates to nonzero, then a
1035         // zero return value means "partial success" (shutdown alert was sent,
1036         // but the peers shutdown alert was not yet received), and 1 means "full
1037         // success" (peers shutdown alert has already been received).
1038         //
1039         // If this is the first time SSL_shutdown() is called, and
1040         // `SSL_get_shutdown() & SSL_SENT_SHUTDOWN` valuates to zero, then a
1041         // zero return value means "premature end of input", and 1 is supposedly
1042         // not a possibility.
1043         //
1044         // If this is the second time SSL_shutdown() is called (after the first
1045         // call has returned zero), then a zero return value means "premature
1046         // end of input", and 1 means "full success" (peers shutdown alert has
1047         // now been received).
1048         if ((SSL_get_shutdown(m_ssl) & SSL_SENT_SHUTDOWN) == 0)
1049             ec = network::premature_end_of_input;
1050     }
1051     return (n > 0);
1052 }
1053
1054 // Provides a homogeneous, and mostly quirks-free interface across the OpenSSL
1055 // operations (handshake, read, write, shutdown).
1056 //
1057 // First of all, if the operation remains incomplete (neither successfully
1058 // completed, nor failed), ssl_perform() will set `ec` to `std::system_error()`,
1059 // `want` to something other than `Want::nothing`, and return zero. Note that
1060 // read and write operations are partial in the sense that they do not need to
1061 // read or write everything before completing successfully. They only need to
1062 // read or write at least one byte to complete successfully.
1063 //
1064 // Such a situation will normally only happen when the underlying TCP socket is
1065 // in nonblocking mode, and the read/write requirements of the operation could
1066 // not be immediately accommodated. However, as is noted in the SSL_write() man
1067 // page, it can also happen in blocking mode (at least while writing).
1068 //
1069 // If an error occurred, ssl_perform() will set `ec` to something other than
1070 // `std::system_error()`, `want` to `Want::nothing`, and return 0.
1071 //
1072 // If no error occurred, and the operation completed (`!ec && want ==
1073 // Want::nothing`), then the return value indicates the outcome of the
1074 // operation.
1075 //
1076 // In general, a nonzero value means "full" success, and a zero value means
1077 // "partial" success, however, a zero result can also generally mean "premature
1078 // end of input" / "unclean protocol termination".
1079 //
1080 // Assuming there is no premature end of input, then for reads and writes, the
1081 // returned value is the number of transferred bytes. Zero for read on end of
1082 // input. Never zero for write. For handshake it is always 1. For shutdown it is
1083 // 1 if the peer shutdown alert was already received, otherwise it is zero.
1084 //
1085 // ssl_read() should use `SSL_get_shutdown() & SSL_RECEIVED_SHUTDOWN` to
1086 // distinguish between the two possible meanings of zero.
1087 //
1088 // ssl_shutdown() should use `SSL_get_shutdown() & SSL_SENT_SHUTDOWN` to
1089 // distinguish between the two possible meanings of zero.
1090 template<class Oper>
1091 std::size_t Stream::ssl_perform(Oper oper, std::error_code& ec, Want& want) noexcept
1092 {
1093     ERR_clear_error();
1094     m_bio_error_code = std::error_code(); // Success
1095     int ret = oper();
1096     int ssl_error = SSL_get_error(m_ssl, ret);
1097     int sys_error = int(ERR_get_error());
1098
1099     // Guaranteed by the documentation of SSL_get_error()
1100     REALM_ASSERT((ret > 0) == (ssl_error == SSL_ERROR_NONE));
1101
1102     REALM_ASSERT(!m_bio_error_code || ssl_error == SSL_ERROR_SYSCALL);
1103
1104     // Judging from various comments in the man pages, and from experience with
1105     // the API, it seems that,
1106     //
1107     //   ret=0, ssl_error=SSL_ERROR_SYSCALL, sys_error=0
1108     //
1109     // is supposed to be an indicator of "premature end of input" / "unclean
1110     // protocol termination", while
1111     //
1112     //   ret=0, ssl_error=SSL_ERROR_ZERO_RETURN
1113     //
1114     // is supposed to be an indicator of the following success conditions:
1115     //
1116     //   - Mature end of input / clean protocol termination.
1117     //
1118     //   - Successful transmission of the shutdown alert, but no prior reception
1119     //     of shutdown alert from peer.
1120     //
1121     // Unfortunately, as is also remarked in various places in the man pages,
1122     // those two success conditions may actually result in `ret=0,
1123     // ssl_error=SSL_ERROR_SYSCALL, sys_error=0` too, and it seems that they
1124     // almost always do.
1125     //
1126     // This means that we cannot properly discriminate between these conditions
1127     // in ssl_perform(), and will have to defer to the caller to interpret the
1128     // situation. Since thay cannot be properly told apart, we report all
1129     // `ret=0, ssl_error=SSL_ERROR_SYSCALL, sys_error=0` and `ret=0,
1130     // ssl_error=SSL_ERROR_ZERO_RETURN` cases as the latter.
1131     switch (ssl_error) {
1132         case SSL_ERROR_NONE:
1133             ec = std::error_code(); // Success
1134             want = Want::nothing;
1135             return std::size_t(ret); // ret > 0
1136         case SSL_ERROR_ZERO_RETURN:
1137             ec = std::error_code(); // Success
1138             want = Want::nothing;
1139             return 0;
1140         case SSL_ERROR_WANT_READ:
1141             ec = std::error_code(); // Success
1142             want = Want::read;
1143             return 0;
1144         case SSL_ERROR_WANT_WRITE:
1145             ec = std::error_code(); // Success
1146             want = Want::write;
1147             return 0;
1148         case SSL_ERROR_SYSCALL:
1149             if (REALM_UNLIKELY(sys_error != 0)) {
1150                 ec = make_basic_system_error_code(sys_error);
1151             }
1152             else if (REALM_UNLIKELY(m_bio_error_code)) {
1153                 ec = m_bio_error_code;
1154             }
1155             else if (ret == 0) {
1156                 // ret = 0, ssl_eror = SSL_ERROR_SYSCALL, sys_error = 0
1157                 //
1158                 // See remarks above!
1159                 ec = std::error_code(); // Success
1160             }
1161             else {
1162                 // ret = -1, ssl_eror = SSL_ERROR_SYSCALL, sys_error = 0
1163                 //
1164                 // This situation arises in OpenSSL version >= 1.1.
1165                 // It has been observed in the SSL_connect call if the
1166                 // other endpoint terminates the connection during
1167                 // SSL_connect. The OpenSSL documentation states
1168                 // that ret = -1 implies an underlying BIO error and
1169                 // that errno should be consulted. However,
1170                 // errno = 0(Undefined error) in the observed case.
1171                 // At the moment. we will report
1172                 // premature_end_of_input.
1173                 // If we see this error case occurring in other situations in
1174                 // the future, we will have to update this case.
1175                 ec = network::premature_end_of_input;
1176             }
1177             want = Want::nothing;
1178             return 0;
1179         case SSL_ERROR_SSL:
1180             ec = std::error_code(sys_error, openssl_error_category());
1181             want = Want::nothing;
1182             return 0;
1183         default:
1184             break;
1185     }
1186     // We are not supposed to ever get here
1187     REALM_ASSERT(false);
1188     return 0;
1189 }
1190
1191 inline int Stream::do_ssl_accept() noexcept
1192 {
1193     int ret = SSL_accept(m_ssl);
1194     return ret;
1195 }
1196
1197 inline int Stream::do_ssl_connect() noexcept
1198 {
1199     int ret = SSL_connect(m_ssl);
1200     return ret;
1201 }
1202
1203 inline int Stream::do_ssl_read(char* buffer, std::size_t size) noexcept
1204 {
1205     int size_2 = int(size);
1206     if (size > unsigned(std::numeric_limits<int>::max()))
1207         size_2 = std::size_t(std::numeric_limits<int>::max());
1208     int ret = SSL_read(m_ssl, buffer, size_2);
1209     return ret;
1210 }
1211
1212 inline int Stream::do_ssl_write(const char* data, std::size_t size) noexcept
1213 {
1214     int size_2 = int(size);
1215     if (size > unsigned(std::numeric_limits<int>::max()))
1216         size_2 = std::size_t(std::numeric_limits<int>::max());
1217     int ret = SSL_write(m_ssl, data, size_2);
1218     return ret;
1219 }
1220
1221 inline int Stream::do_ssl_shutdown() noexcept
1222 {
1223     int ret = SSL_shutdown(m_ssl);
1224     return ret;
1225 }
1226
1227 #elif REALM_HAVE_SECURE_TRANSPORT
1228
1229 // Provides a homogeneous, and mostly quirks-free interface across the SecureTransport
1230 // operations (handshake, read, write, shutdown).
1231 //
1232 // First of all, if the operation remains incomplete (neither successfully
1233 // completed, nor failed), ssl_perform() will set `ec` to `std::system_error()`,
1234 // `want` to something other than `Want::nothing`, and return zero.
1235 //
1236 // If an error occurred, ssl_perform() will set `ec` to something other than
1237 // `std::system_error()`, `want` to `Want::nothing`, and return 0.
1238 //
1239 // If no error occurred, and the operation completed (`!ec && want ==
1240 // Want::nothing`), then the return value indicates the outcome of the
1241 // operation.
1242 //
1243 // In general, a nonzero value means "full" success, and a zero value means
1244 // "partial" success, however, a zero result can also generally mean "premature
1245 // end of input" / "unclean protocol termination".
1246 //
1247 // Assuming there is no premature end of input, then for reads and writes, the
1248 // returned value is the number of transferred bytes. Zero for read on end of
1249 // input. Never zero for write. For handshake it is always 1. For shutdown it is
1250 // 1 if the peer shutdown alert was already received, otherwise it is zero.
1251 template<class Oper>
1252 std::size_t Stream::ssl_perform(Oper oper, std::error_code& ec, Want& want) noexcept
1253 {
1254     OSStatus result;
1255     std::size_t n;
1256     std::tie(result, n) = oper();
1257
1258     if (result == noErr) {
1259         ec = std::error_code();
1260         want = Want::nothing;
1261         return n;
1262     }
1263
1264     if (result == errSSLWouldBlock) {
1265         REALM_ASSERT(m_last_operation);
1266         ec = std::error_code();
1267         want = m_last_operation == BlockingOperation::read ? Want::read : Want::write;
1268         m_last_operation = {};
1269         return n;
1270     }
1271
1272     if (result == errSSLClosedGraceful) {
1273         ec = network::end_of_input;
1274         want = Want::nothing;
1275         return n;
1276     }
1277
1278     if (result == errSSLClosedAbort || result == errSSLClosedNoNotify) {
1279         ec = network::premature_end_of_input;
1280         want = Want::nothing;
1281         return n;
1282     }
1283
1284     if (result == errSecIO) {
1285         // A generic I/O error means something went wrong at a lower level. Use the error
1286         // code we smuggled out of our lower-level functions to provide a more specific error.
1287         REALM_ASSERT(m_last_error);
1288         ec = m_last_error;
1289         want = Want::nothing;
1290         return n;
1291     }
1292
1293     ec = std::error_code(result, secure_transport_error_category());
1294     want = Want::nothing;
1295     return 0;
1296 }
1297 #endif // REALM_HAVE_OPENSSL / REALM_HAVE_SECURE_TRANSPORT
1298
1299 } // namespace ssl
1300 } // namespace network
1301 } // namespace util
1302 } // namespace realm
1303
1304 #endif // REALM_UTIL_NETWORK_SSL_HPP