include/boost/corosio/tls_context.hpp

87.5% Lines (14/0/16) 92.3% List of functions (12/0/13)
tls_context.hpp
f(x) Functions (13)
Function Calls Lines Blocks
boost::corosio::verify_context::certificate() const :186 0 0.0% 0.0% boost::corosio::tls_context::tls_context(boost::corosio::tls_context const&) :269 2x 100.0% 100.0% boost::corosio::tls_context::operator=(boost::corosio::tls_context const&) :280 1x 100.0% 100.0% boost::corosio::tls_context::tls_context(boost::corosio::tls_context&&) :289 2x 100.0% 100.0% boost::corosio::tls_context::operator=(boost::corosio::tls_context&&) :301 1x 100.0% 100.0% boost::corosio::tls_context::~tls_context() :309 55x 100.0% 100.0% void boost::corosio::tls_context::set_servername_callback<boost::corosio::tls_context_test::testServernameCallback()::{lambda(std::basic_string_view<char, std::char_traits<char> >)#1}>(boost::corosio::tls_context_test::testServernameCallback()::{lambda(std::basic_string_view<char, std::char_traits<char> >)#1}) :932 1x 100.0% 75.0% void boost::corosio::tls_context::set_password_callback<(anonymous namespace)::password_callback(boost::corosio::tls_context&)::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}>((anonymous namespace)::password_callback(boost::corosio::tls_context&)::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}) :939 1x 100.0% 75.0% void boost::corosio::tls_context::set_password_callback<(anonymous namespace)::password_env(boost::corosio::tls_context&)::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}>((anonymous namespace)::password_env(boost::corosio::tls_context&)::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}) :939 1x 100.0% 75.0% void boost::corosio::tls_context::set_password_callback<(anonymous namespace)::tls_test::testPasswordCallback()::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}>((anonymous namespace)::tls_test::testPasswordCallback()::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}) :939 1x 100.0% 75.0% void boost::corosio::tls_context::set_password_callback<boost::corosio::tls_context_test::testPasswordCallback()::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}>(boost::corosio::tls_context_test::testPasswordCallback()::{lambda(unsigned long, boost::corosio::tls_password_purpose)#1}) :939 1x 100.0% 75.0% void boost::corosio::tls_context::set_verify_callback<(anonymous namespace)::tls_test::testVerifyCallback()::{lambda(bool, boost::corosio::verify_context&)#1}>((anonymous namespace)::tls_test::testVerifyCallback()::{lambda(bool, boost::corosio::verify_context&)#1}) :946 1x 100.0% 75.0% void boost::corosio::tls_context::set_verify_callback<(anonymous namespace)::verify_callback(boost::corosio::tls_context&)::{lambda(bool, boost::corosio::verify_context&)#1}>((anonymous namespace)::verify_callback(boost::corosio::tls_context&)::{lambda(bool, boost::corosio::verify_context&)#1}) :946 1x 100.0% 75.0%
Line TLA Hits Source Code
1 //
2 // Copyright (c) 2025 Vinnie Falco (vinnie.falco@gmail.com)
3 // Copyright (c) 2026 Michael Vandeberg
4 //
5 // Distributed under the Boost Software License, Version 1.0. (See accompanying
6 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7 //
8 // Official repository: https://github.com/cppalliance/corosio
9 //
10
11 #ifndef BOOST_COROSIO_TLS_CONTEXT_HPP
12 #define BOOST_COROSIO_TLS_CONTEXT_HPP
13
14 #include <boost/corosio/detail/config.hpp>
15
16 #include <cstddef>
17 #include <functional>
18 #include <span>
19 #include <system_error>
20 #include <memory>
21 #include <string_view>
22
23 namespace boost::corosio {
24
25 //
26 // Enumerations
27 //
28
29 /** TLS protocol version.
30
31 Specifies the minimum or maximum TLS protocol version to use
32 for connections. Only modern, secure versions are supported.
33
34 @see tls_context::set_min_protocol_version
35 @see tls_context::set_max_protocol_version
36 */
37 enum class tls_version
38 {
39 /// TLS 1.2 (RFC 5246).
40 tls_1_2,
41
42 /// TLS 1.3 (RFC 8446).
43 tls_1_3
44 };
45
46 /** Certificate and key file format.
47
48 Specifies the encoding format for certificate and key data.
49
50 @see tls_context::use_certificate
51 @see tls_context::use_private_key
52 */
53 enum class tls_file_format
54 {
55 /// PEM format (Base64-encoded with header/footer lines).
56 pem,
57
58 /// DER format (raw ASN.1 binary encoding).
59 der
60 };
61
62 /** Peer certificate verification mode.
63
64 Controls how the TLS implementation verifies the peer's
65 certificate during the handshake.
66
67 @see tls_context::set_verify_mode
68 */
69 enum class tls_verify_mode
70 {
71 /// Do not request or verify the peer certificate.
72 none,
73
74 /// Request and verify the peer certificate if presented.
75 peer,
76
77 /// Require and verify the peer certificate (fail if not presented).
78 require_peer
79 };
80
81 /** Certificate revocation checking policy.
82
83 Controls how certificate revocation status is checked during
84 verification.
85
86 @see tls_context::set_revocation_policy
87 */
88 enum class tls_revocation_policy
89 {
90 /// Do not check revocation status.
91 disabled,
92
93 /// Check revocation but allow connection if status is unknown.
94 soft_fail,
95
96 /// Require successful revocation check (fail if status is unknown).
97 hard_fail
98 };
99
100 /** Purpose for password callback invocation.
101
102 Indicates whether the password is needed for reading (decrypting)
103 or writing (encrypting) key material.
104
105 @see tls_context::set_password_callback
106 */
107 enum class tls_password_purpose
108 {
109 /// Password needed to decrypt/read protected key material.
110 for_reading,
111
112 /// Password needed to encrypt/write protected key material.
113 for_writing
114 };
115
116 class tls_context;
117
118 /** A non-owning view of certificate verification state.
119
120 An instance is passed to the callback installed via
121 tls_context::set_verify_callback during the TLS handshake. It
122 exposes the backend's native verification handle so the callback
123 can inspect the certificate and chain currently being verified.
124
125 The value returned by native_handle() is, for the OpenSSL and
126 WolfSSL backends, an `X509_STORE_CTX*`. For portable inspection that
127 works across backends (for example certificate pinning), prefer
128 certificate(), which returns the DER encoding of the certificate
129 currently being verified.
130
131 @par Lifetime
132
133 The wrapped handle and the certificate() bytes are owned by the TLS
134 backend and are valid only for the duration of a single callback
135 invocation. Do not retain them beyond the call.
136
137 @see tls_context::set_verify_callback
138 */
139 class verify_context
140 {
141 void* handle_;
142 unsigned char const* der_;
143 std::size_t der_len_;
144
145 public:
146 /** Construct from a native handle and the current certificate.
147
148 @param handle The backend verification handle (for OpenSSL and
149 WolfSSL, an `X509_STORE_CTX*`).
150 @param der Pointer to the DER encoding of the certificate under
151 verification, or `nullptr` if unavailable.
152 @param der_len Length of the DER encoding in bytes.
153 */
154 verify_context(
155 void* handle, unsigned char const* der, std::size_t der_len) noexcept
156 : handle_(handle)
157 , der_(der)
158 , der_len_(der_len)
159 {
160 }
161
162 /** Return the native verification handle.
163
164 Cast the result to the backend's verification context type
165 (e.g. `X509_STORE_CTX*`) to inspect the certificate chain using
166 backend-specific APIs.
167
168 @return The native handle, or `nullptr` if none is available.
169 */
170 void* native_handle() const noexcept
171 {
172 return handle_;
173 }
174
175 /** Return the DER encoding of the certificate being verified.
176
177 This is the portable way to inspect the peer certificate from a
178 verification callback: it works identically on every backend,
179 without depending on backend-specific build options. A DER
180 certificate is an ASN.1 `SEQUENCE`, so the first byte is `0x30`.
181
182 @return A view of the certificate's DER bytes, valid only for the
183 duration of the callback. Empty if the certificate is not
184 available.
185 */
186 std::span<unsigned char const> certificate() const noexcept
187 {
188 return {der_, der_len_};
189 }
190 };
191
192 namespace detail {
193 struct tls_context_data;
194 tls_context_data const& get_tls_context_data(tls_context const&) noexcept;
195 } // namespace detail
196
197 #ifdef _MSC_VER
198 #pragma warning(push)
199 #pragma warning(disable : 4251) // shared_ptr needs dll-interface
200 #endif
201
202 /** A portable TLS context for certificate and settings storage.
203
204 The `tls_context` class provides a backend-agnostic interface for
205 configuring TLS connections. It stores credentials (certificates and
206 private keys), trust anchors, protocol settings, and verification
207 options that are used when establishing TLS connections.
208
209 This class is a shared handle to an opaque implementation. Copies
210 share the same underlying state. This allows contexts to be passed
211 by value and shared across multiple TLS streams.
212
213 This class abstracts the configuration phase of TLS across multiple
214 backend implementations (OpenSSL, WolfSSL, mbedTLS, Schannel, etc.),
215 allowing portable code that works regardless of which TLS library
216 is linked.
217
218 @par Modification After Stream Creation
219
220 Modifying a context after a TLS stream has been created from it
221 results in undefined behavior. The context's configuration is
222 captured when the first stream is constructed, and subsequent
223 modifications are not reflected in existing or new streams
224 sharing the context.
225
226 If different configurations are needed, create separate context
227 objects.
228
229 @par Thread Safety
230
231 Distinct objects: Safe.
232
233 Shared objects: Unsafe. A context must not be modified while
234 any thread is creating streams from it.
235
236 @par Example
237 @par !example tls_context
238
239 @see tls_role
240 */
241 class BOOST_COROSIO_DECL tls_context
242 {
243 struct implementation;
244 std::shared_ptr<implementation> impl_;
245
246 friend detail::tls_context_data const&
247 detail::get_tls_context_data(tls_context const&) noexcept;
248
249 public:
250 /** Construct a default TLS context.
251
252 Creates a context with default settings suitable for TLS 1.2
253 and TLS 1.3 connections. No certificates or trust anchors are
254 loaded; call the appropriate methods to configure credentials
255 and verification.
256
257 @par Example
258 @par !example tls_context
259 */
260 tls_context();
261
262 /** Copy constructor.
263
264 Creates a new handle that shares ownership of the underlying
265 TLS context state with `other`.
266
267 @param other The context to copy from.
268 */
269 2x tls_context(tls_context const& other) = default;
270
271 /** Copy assignment operator.
272
273 Releases the current context's shared ownership and acquires
274 shared ownership of `other`'s underlying state.
275
276 @param other The context to copy from.
277
278 @return Reference to this context.
279 */
280 1x tls_context& operator=(tls_context const& other) = default;
281
282 /** Move constructor.
283
284 Transfers ownership of the TLS context from another instance.
285 After the move, `other` is in a valid but empty state.
286
287 @param other The context to move from.
288 */
289 2x tls_context(tls_context&& other) noexcept = default;
290
291 /** Move assignment operator.
292
293 Releases the current context's shared ownership and transfers
294 ownership from another instance. After the move, `other` is
295 in a valid but empty state.
296
297 @param other The context to move from.
298
299 @return Reference to this context.
300 */
301 1x tls_context& operator=(tls_context&& other) noexcept = default;
302
303 /** Destructor.
304
305 Releases this handle's shared ownership of the underlying
306 context. The context state is destroyed when the last handle
307 is released.
308 */
309 55x ~tls_context() = default;
310
311 //
312 // Credential Loading
313 //
314
315 /** Load the entity certificate from a memory buffer.
316
317 Sets the certificate that identifies this endpoint to the peer.
318 For servers, this is the server certificate. For clients using
319 mutual TLS, this is the client certificate.
320
321 The certificate must match the private key loaded via
322 `use_private_key()` or `use_private_key_file()`.
323
324 @param certificate The certificate data.
325
326 @param format The encoding format of the certificate data.
327
328 @return Success. The certificate is recorded and decoded when the
329 native context is first built; a malformed certificate surfaces
330 as a handshake failure.
331
332 @see use_certificate_file
333 @see use_private_key
334 */
335 [[nodiscard]] std::error_code
336 use_certificate(std::string_view certificate, tls_file_format format);
337
338 /** Load the entity certificate from a file.
339
340 Sets the certificate that identifies this endpoint to the peer.
341 For servers, this is the server certificate. For clients using
342 mutual TLS, this is the client certificate.
343
344 @param filename Path to the certificate file.
345
346 @param format The encoding format of the file.
347
348 @return Success, or an error if the file could not be read. The
349 certificate is decoded when the native context is first built;
350 a malformed certificate surfaces as a handshake failure.
351
352 @par Example
353 @par !example use_certificate_file
354
355 @see use_certificate
356 @see use_private_key_file
357 */
358 [[nodiscard]] std::error_code
359 use_certificate_file(std::string_view filename, tls_file_format format);
360
361 /** Load a certificate chain from a memory buffer.
362
363 Loads the entity certificate followed by intermediate CA certificates.
364 The chain should be ordered from leaf to root (excluding the root).
365 This is the typical format for PEM certificate bundles.
366
367 @param chain The certificate chain data in PEM format (concatenated
368 certificates).
369
370 @return Success. The chain is recorded and decoded when the native
371 context is first built; a malformed chain surfaces as a
372 handshake failure.
373
374 @see use_certificate_chain_file
375 */
376 [[nodiscard]] std::error_code use_certificate_chain(std::string_view chain);
377
378 /** Load a certificate chain from a file.
379
380 Loads the entity certificate followed by intermediate CA certificates
381 from a PEM file. The file should contain concatenated PEM certificates
382 ordered from leaf to root (excluding the root).
383
384 @param filename Path to the certificate chain file.
385
386 @return Success, or an error if the file could not be read. The
387 chain is decoded when the native context is first built; a
388 malformed chain surfaces as a handshake failure.
389
390 @par Example
391 @par !example use_certificate_chain_file
392
393 @see use_certificate_chain
394 */
395 [[nodiscard]] std::error_code
396 use_certificate_chain_file(std::string_view filename);
397
398 /** Load the private key from a memory buffer.
399
400 Sets the private key corresponding to the entity certificate.
401 The key must match the certificate loaded via `use_certificate()`
402 or `use_certificate_chain()`.
403
404 If the key is encrypted, set a password callback via
405 `set_password_callback()` before calling this function.
406
407 @param private_key The private key data.
408
409 @param format The encoding format of the key data.
410
411 @return Success. The key is recorded and decoded when the native
412 context is first built; a malformed key, a missing password
413 callback for an encrypted key, or a certificate mismatch
414 surfaces as a handshake failure.
415
416 @see use_private_key_file
417 @see set_password_callback
418 */
419 [[nodiscard]] std::error_code
420 use_private_key(std::string_view private_key, tls_file_format format);
421
422 /** Load the private key from a file.
423
424 Sets the private key corresponding to the entity certificate.
425 The key must match the certificate loaded via `use_certificate_file()`
426 or `use_certificate_chain_file()`.
427
428 If the key file is encrypted, set a password callback via
429 `set_password_callback()` before calling this function.
430
431 @param filename Path to the private key file.
432
433 @param format The encoding format of the file.
434
435 @return Success, or an error if the file could not be read. The
436 key is decoded when the native context is first built; a
437 malformed key or a certificate mismatch surfaces as a
438 handshake failure.
439
440 @par Example
441 @par !example use_private_key_file
442
443 @see use_private_key
444 @see set_password_callback
445 */
446 [[nodiscard]] std::error_code
447 use_private_key_file(std::string_view filename, tls_file_format format);
448
449 /** Load credentials from a PKCS#12 bundle in memory.
450
451 PKCS#12 (also known as PFX) is a binary format that bundles a
452 certificate, private key, and optionally intermediate certificates
453 into a single password-protected file.
454
455 @param data The PKCS#12 bundle data.
456
457 @param passphrase The password protecting the bundle.
458
459 @return Success. The bundle is recorded and decoded into the
460 certificate, private key, and chain when the native context is
461 first built; a malformed bundle or wrong passphrase surfaces as
462 a handshake failure.
463
464 @note Intermediate certificates inside the bundle are loaded and
465 sent during the handshake on both backends.
466
467 @see use_pkcs12_file
468 */
469 [[nodiscard]] std::error_code
470 use_pkcs12(std::string_view data, std::string_view passphrase);
471
472 /** Load credentials from a PKCS#12 file.
473
474 PKCS#12 (also known as PFX) is a binary format that bundles a
475 certificate, private key, and optionally intermediate certificates
476 into a single password-protected file. This is common on Windows
477 and for certificates exported from browsers.
478
479 @param filename Path to the PKCS#12 file.
480
481 @param passphrase The password protecting the file.
482
483 @return Success, or an error if the file could not be read. The
484 bundle is decoded when the native context is first built; a
485 malformed bundle or wrong passphrase surfaces as a handshake
486 failure.
487
488 @note Intermediate certificates inside the bundle are loaded and
489 sent during the handshake on both backends.
490
491 @par Example
492 @par !example use_pkcs12_file
493
494 @see use_pkcs12
495 */
496 [[nodiscard]] std::error_code
497 use_pkcs12_file(std::string_view filename, std::string_view passphrase);
498
499 //
500 // Trust Anchors
501 //
502
503 /** Add a certificate authority for peer verification.
504
505 Adds a single CA certificate to the trust store used for verifying
506 peer certificates. Call this multiple times to add multiple CAs,
507 or use `load_verify_file()` for a bundle.
508
509 @param ca The CA certificate data in PEM format.
510
511 @return Success. The certificate is recorded and decoded when the
512 native context is first built; a malformed certificate
513 surfaces as a handshake failure.
514
515 @see load_verify_file
516 @see set_default_verify_paths
517 */
518 [[nodiscard]] std::error_code
519 add_certificate_authority(std::string_view ca);
520
521 /** Load CA certificates from a file.
522
523 Loads one or more CA certificates from a PEM file. The file may
524 contain multiple concatenated PEM certificates.
525
526 @param filename Path to a PEM file containing CA certificates.
527
528 @return Success, or an error if the file could not be read. The
529 certificates are decoded when the native context is first
530 built; malformed certificates surface as a handshake failure.
531
532 @par Example
533 @par !example load_verify_file
534
535 @see add_certificate_authority
536 @see add_verify_path
537 */
538 [[nodiscard]] std::error_code load_verify_file(std::string_view filename);
539
540 /** Add a directory of CA certificates for verification.
541
542 Adds a directory of CA certificates to the trust store. The
543 directory is applied when the native context is first built from
544 this context.
545
546 The expected directory layout depends on the backend. OpenSSL
547 performs on-demand lookups and requires each certificate file to
548 be named by its subject-name hash (as generated by
549 `openssl rehash` or `c_rehash`); WolfSSL loads every certificate
550 file in the directory.
551
552 @param path Path to the directory of CA certificates.
553
554 @return Success. The path is recorded and applied when the native
555 context is built; a directory that cannot be read at that time
556 is skipped rather than reported here.
557
558 @par Example
559 @par !example add_verify_path
560
561 @see load_verify_file
562 @see set_default_verify_paths
563 */
564 [[nodiscard]] std::error_code add_verify_path(std::string_view path);
565
566 /** Use the system default CA certificate store.
567
568 Configures the context to use the operating system's default
569 trust store for peer certificate verification. This is the
570 recommended approach for HTTPS clients connecting to public
571 servers.
572
573 The system store is loaded when the native context is first built
574 from this context. For a verified-safe client, combine this with
575 `set_verify_mode( tls_verify_mode::peer )` and, when connecting by
576 name, `tls_stream::set_hostname()`.
577
578 @return Success. The request is recorded and applied when the
579 native context is built; if the system store cannot be loaded
580 at that time it is skipped rather than reported here, so a
581 context that must reject unverified peers should also use
582 `set_verify_mode( tls_verify_mode::peer )`.
583
584 @note The OpenSSL backend honors the `SSL_CERT_FILE` and
585 `SSL_CERT_DIR` environment variables. The WolfSSL backend
586 requires a build with `WOLFSSL_SYS_CA_CERTS`; without it the
587 system store is unavailable and this call has no effect.
588
589 @par Example
590 @par !example set_default_verify_paths
591
592 @see load_verify_file
593 @see add_verify_path
594 @see set_verify_mode
595 */
596 [[nodiscard]] std::error_code set_default_verify_paths();
597
598 //
599 // Protocol Configuration
600 //
601
602 /** Set the minimum TLS protocol version.
603
604 Connections will reject protocol versions older than this.
605 The default allows TLS 1.2 and newer.
606
607 @param v The minimum protocol version to accept.
608
609 @return Success. The version is recorded and applied when the
610 native context is first built.
611
612 @par Example
613 @par !example set_min_protocol_version
614
615 @see set_max_protocol_version
616 */
617 [[nodiscard]] std::error_code set_min_protocol_version(tls_version v);
618
619 /** Set the maximum TLS protocol version.
620
621 Connections will not negotiate protocol versions newer than this.
622 The default allows the newest supported version.
623
624 @param v The maximum protocol version to accept.
625
626 @return Success. The version is recorded and applied when the
627 native context is first built.
628
629 @note On WolfSSL the ceiling is applied by selecting a
630 version-specific method (no native set-max API exists); an
631 invalid window where the minimum exceeds the maximum yields a
632 context that fails the handshake.
633
634 @see set_min_protocol_version
635 */
636 [[nodiscard]] std::error_code set_max_protocol_version(tls_version v);
637
638 /** Set the allowed cipher suites.
639
640 Configures which cipher suites may be used for connections.
641 The format is backend-specific but typically follows OpenSSL
642 cipher list syntax.
643
644 @param ciphers The cipher suite specification string.
645
646 @return Success. The string is recorded and applied when the
647 native context is first built; an invalid cipher string
648 surfaces as a handshake failure.
649
650 @par Example
651 @par !example set_ciphersuites
652
653 @note This configures cipher suites for TLS 1.2 and below. For
654 TLS 1.3, use @ref set_ciphersuites_tls13.
655 */
656 [[nodiscard]] std::error_code set_ciphersuites(std::string_view ciphers);
657
658 /** Set the allowed TLS 1.3 cipher suites.
659
660 TLS 1.3 uses a distinct, fixed set of cipher suites configured
661 separately from earlier versions. The format is a colon-separated
662 list of TLS 1.3 suite names.
663
664 @param ciphers The TLS 1.3 cipher suite list.
665
666 @return Success. The string is recorded and applied when the
667 native context is first built; an invalid cipher string
668 surfaces as a handshake failure.
669
670 @par Example
671 @par !example set_ciphersuites_tls13
672
673 @note On the WolfSSL backend, TLS 1.2 and TLS 1.3 suites share a
674 single cipher list; this call and @ref set_ciphersuites are
675 merged into one list.
676
677 @see set_ciphersuites
678 */
679 [[nodiscard]] std::error_code
680 set_ciphersuites_tls13(std::string_view ciphers);
681
682 /** Set the ALPN protocol list.
683
684 Configures Application-Layer Protocol Negotiation (ALPN) for
685 the connection. ALPN is used to negotiate which application
686 protocol to use over the TLS connection (e.g., "h2" for HTTP/2,
687 "http/1.1" for HTTP/1.1).
688
689 The protocols are tried in preference order (first = highest).
690
691 @param protocols Ordered list of protocol identifiers.
692
693 @return Success, or an error if ALPN configuration fails.
694
695 @note Read the negotiated protocol after the handshake via
696 @ref tls_stream::alpn_protocol. On WolfSSL, ALPN requires a
697 build with `HAVE_ALPN`; without it, offering protocols fails
698 the handshake with `std::errc::function_not_supported` rather
699 than negotiate nothing silently.
700
701 @par Example
702 @par !example set_alpn
703 */
704 [[nodiscard]] std::error_code
705 set_alpn(std::initializer_list<std::string_view> protocols);
706
707 //
708 // Certificate Verification
709 //
710
711 /** Set the peer certificate verification mode.
712
713 Controls whether and how peer certificates are verified during
714 the TLS handshake.
715
716 @param mode The verification mode to use.
717
718 @return Success. The mode is recorded and applied when the native
719 context is first built.
720
721 @par Example
722 @par !example set_verify_mode
723
724 @see tls_verify_mode
725 */
726 [[nodiscard]] std::error_code set_verify_mode(tls_verify_mode mode);
727
728 /** Set the maximum certificate chain verification depth.
729
730 Limits how many intermediate certificates can appear between
731 the peer certificate and a trusted root. The default is
732 typically 100, which is sufficient for most certificate chains.
733
734 @param depth Maximum number of intermediate certificates allowed.
735
736 @return Success. The depth is recorded and applied when the native
737 context is first built.
738 */
739 [[nodiscard]] std::error_code set_verify_depth(int depth);
740
741 /** Set a custom certificate verification callback.
742
743 Installs a callback that is invoked during certificate chain
744 verification. The callback can perform additional validation
745 beyond the standard checks and can override verification
746 results.
747
748 The callback receives the built-in verification result so far and
749 a verify_context describing the certificate being verified. Return
750 `true` to accept the certificate, `false` to reject. Inspect the
751 certificate portably via `verify_context::certificate()` (its DER
752 encoding) — for example to pin a specific certificate.
753
754 @par Backend Support
755
756 The exact set of certificates the callback sees differs by backend:
757
758 - OpenSSL: the callback runs once per certificate in the chain,
759 including certificates that passed the built-in checks. It can
760 therefore both relax verification (return `true` for a
761 certificate the library rejected) and tighten it (return `false`
762 for a certificate the library accepted, e.g. pinning).
763 - WolfSSL built with `WOLFSSL_ALWAYS_VERIFY_CB` (implied by
764 `--enable-opensslextra`): same as OpenSSL.
765 - WolfSSL without that option: the library invokes the callback
766 only on verification *failure*, so it cannot be honored on a
767 successful handshake. To avoid silently ignoring a
768 verification-tightening callback (which would fail open), a
769 context that carries a callback instead **fails the handshake**
770 with `std::errc::function_not_supported` on such a build. Rebuild
771 WolfSSL with `WOLFSSL_ALWAYS_VERIFY_CB`, or omit the callback.
772
773 @tparam Callback A callable with signature
774 `bool( bool preverified, verify_context& ctx )`.
775
776 @param callback The verification callback. Recorded here and
777 applied during the handshake; on a WolfSSL build that
778 cannot honor it, the handshake fails with
779 `std::errc::function_not_supported` (see Backend Support).
780
781 @par Example
782 @par !example set_verify_callback
783
784 @see verify_context
785 @see set_verify_mode
786 */
787 template<typename Callback>
788 void set_verify_callback(Callback callback);
789
790 /** Set a callback for Server Name Indication (SNI).
791
792 For server connections, this callback is invoked during the TLS
793 handshake when a client sends an SNI extension. The callback
794 receives the requested hostname and can accept or reject the
795 connection.
796
797 @tparam Callback A callable with signature
798 `bool( std::string_view hostname )`.
799
800 @param callback The SNI callback. Return `true` to accept the
801 connection or `false` to reject it with an alert.
802
803 @par Example
804 @par !example set_servername_callback
805
806 @note For virtual hosting with different certificates per hostname,
807 create separate contexts and select the appropriate one before
808 creating the TLS stream.
809
810 @see tls_stream::set_hostname
811 */
812 template<typename Callback>
813 void set_servername_callback(Callback callback);
814
815 private:
816 void set_servername_callback_impl(
817 std::function<bool(std::string_view)> callback);
818
819 void set_password_callback_impl(
820 std::function<std::string(std::size_t, tls_password_purpose)> callback);
821
822 void set_verify_callback_impl(
823 std::function<bool(bool, verify_context&)> callback);
824
825 public:
826 //
827 // Revocation Checking
828 //
829
830 /** Add a Certificate Revocation List from memory.
831
832 Adds a CRL to the verification store for checking whether
833 certificates have been revoked. CRLs are typically fetched
834 from the URLs in a certificate's CRL Distribution Points
835 extension.
836
837 @param crl The CRL data in DER or PEM format.
838
839 @return Success. The CRL is recorded and decoded when the native
840 context is first built; a malformed CRL surfaces as a
841 handshake failure.
842
843 @note CRLs are consulted only when a revocation policy is set via
844 @ref set_revocation_policy. On WolfSSL, CRL checking requires a
845 build with `HAVE_CRL`; without it, supplying a CRL or a
846 revocation policy fails the handshake with
847 `std::errc::function_not_supported`.
848
849 @see add_crl_file
850 @see set_revocation_policy
851 */
852 [[nodiscard]] std::error_code add_crl(std::string_view crl);
853
854 /** Add a Certificate Revocation List from a file.
855
856 Adds a CRL to the verification store for checking whether
857 certificates have been revoked.
858
859 @param filename Path to a CRL file (DER or PEM format).
860
861 @return Success, or an error if the file could not be read. The
862 CRL is decoded when the native context is first built; a
863 malformed CRL surfaces as a handshake failure.
864
865 @note CRLs are consulted only when a revocation policy is set via
866 @ref set_revocation_policy (WolfSSL requires a `HAVE_CRL`
867 build).
868
869 @par Example
870 @par !example add_crl_file
871
872 @see add_crl
873 @see set_revocation_policy
874 */
875 [[nodiscard]] std::error_code add_crl_file(std::string_view filename);
876
877 /** Set the certificate revocation checking policy.
878
879 Controls how certificate revocation status is checked during
880 verification via CRLs.
881
882 @param policy The revocation checking policy.
883
884 @par Example
885 @par !example set_revocation_policy
886
887 @note Revocation is checked via CRLs supplied with @ref add_crl /
888 @ref add_crl_file. `soft_fail` accepts a certificate whose
889 status cannot be determined (missing/expired CRL) but rejects
890 one that is actually revoked; `hard_fail` also rejects unknown
891 status. OCSP-based revocation is not available (see the TLS
892 guide). On WolfSSL a non-disabled policy requires a `HAVE_CRL`
893 build, else the handshake fails with
894 `std::errc::function_not_supported`.
895
896 @see tls_revocation_policy
897 @see add_crl
898 */
899 void set_revocation_policy(tls_revocation_policy policy);
900
901 //
902 // Password Handling
903 //
904
905 /** Set the password callback for encrypted keys.
906
907 Installs a callback that provides passwords for encrypted
908 private keys and PKCS#12 files. The callback is invoked when
909 loading encrypted key material.
910
911 @tparam Callback A callable with signature
912 `std::string( std::size_t max_length, password_purpose purpose )`.
913
914 @param callback The password callback. It receives the maximum
915 password length and the purpose (reading or writing), and
916 returns the password string.
917
918 @par Example
919 @par !example set_password_callback
920
921 @see tls_password_purpose
922 */
923 template<typename Callback>
924 void set_password_callback(Callback callback);
925 };
926 #ifdef _MSC_VER
927 #pragma warning(pop)
928 #endif
929
930 template<typename Callback>
931 void
932 1x tls_context::set_servername_callback(Callback callback)
933 {
934 1x set_servername_callback_impl(std::move(callback));
935 1x }
936
937 template<typename Callback>
938 void
939 4x tls_context::set_password_callback(Callback callback)
940 {
941 4x set_password_callback_impl(std::move(callback));
942 4x }
943
944 template<typename Callback>
945 void
946 2x tls_context::set_verify_callback(Callback callback)
947 {
948 2x set_verify_callback_impl(std::move(callback));
949 2x }
950
951 } // namespace boost::corosio
952
953 #endif
954