rustls_platform_verifier/
lib.rs

1#![cfg_attr(docsrs, feature(doc_cfg))]
2#![doc = include_str!("../README.md")]
3#![warn(missing_docs)]
4
5use std::sync::Arc;
6
7#[cfg(feature = "dbg")]
8use rustls::crypto::CryptoProvider;
9#[cfg(feature = "dbg")]
10use rustls::pki_types::CertificateDer;
11use rustls::{client::WantsClientCert, ClientConfig, ConfigBuilder, WantsVerifier};
12
13mod verification;
14pub use verification::Verifier;
15
16// Build the Android module when generating docs so that
17// the Android-specific functions are included regardless of
18// the host.
19#[cfg(any(all(doc, docsrs), target_os = "android"))]
20#[cfg_attr(docsrs, doc(cfg(target_os = "android")))]
21pub mod android;
22
23/// Fixures and data to support testing the server
24/// certificate verifier.
25#[cfg(any(test, feature = "ffi-testing"))]
26mod tests;
27
28// Re-export any exported functions that are required for
29// tests to run in a platform-native environment.
30#[cfg(feature = "ffi-testing")]
31#[cfg_attr(feature = "ffi-testing", allow(unused_imports))]
32pub use tests::ffi::*;
33
34/// Exposed for debugging certificate issues with standalone tools.
35///
36/// This is not intended for production use, you should use [`BuilderVerifierExt`] or
37/// [`ConfigVerifierExt`] instead.
38#[cfg(feature = "dbg")]
39pub fn verifier_for_dbg(
40    root: CertificateDer<'static>,
41    crypto_provider: Arc<CryptoProvider>,
42) -> Arc<dyn rustls::client::danger::ServerCertVerifier> {
43    Arc::new(Verifier::new_with_fake_root(root, crypto_provider))
44}
45
46/// Extension trait to help configure [`ClientConfig`]s with the platform verifier.
47pub trait BuilderVerifierExt {
48    /// Configures the `ClientConfig` with the platform verifier.
49    ///
50    /// ```rust
51    /// use rustls::ClientConfig;
52    /// use rustls_platform_verifier::BuilderVerifierExt;
53    /// let config = ClientConfig::builder()
54    ///     .with_platform_verifier()
55    ///     .unwrap()
56    ///     .with_no_client_auth();
57    /// ```
58    fn with_platform_verifier(
59        self,
60    ) -> Result<ConfigBuilder<ClientConfig, WantsClientCert>, rustls::Error>;
61}
62
63impl BuilderVerifierExt for ConfigBuilder<ClientConfig, WantsVerifier> {
64    fn with_platform_verifier(
65        self,
66    ) -> Result<ConfigBuilder<ClientConfig, WantsClientCert>, rustls::Error> {
67        let verifier = Verifier::new(self.crypto_provider().clone())?;
68        Ok(self
69            .dangerous()
70            .with_custom_certificate_verifier(Arc::new(verifier)))
71    }
72}
73
74/// Extension trait to help build a [`ClientConfig`] with the platform verifier.
75pub trait ConfigVerifierExt {
76    /// Build a [`ClientConfig`] with the platform verifier and the default `CryptoProvider`.
77    ///
78    /// ```rust
79    /// use rustls::ClientConfig;
80    /// use rustls_platform_verifier::ConfigVerifierExt;
81    /// let config = ClientConfig::with_platform_verifier();
82    /// ```
83    fn with_platform_verifier() -> Result<ClientConfig, rustls::Error>;
84}
85
86impl ConfigVerifierExt for ClientConfig {
87    fn with_platform_verifier() -> Result<ClientConfig, rustls::Error> {
88        Ok(ClientConfig::builder()
89            .with_platform_verifier()?
90            .with_no_client_auth())
91    }
92}