Skip to main content

ntex_tls/x509/
mod.rs

1//! X.509 certificate handling: parsing, thumbprints, trust verification and identity loading.
2//!
3//! # Backends
4//!
5//! Windows always uses native APIs. Elsewhere `rustls` takes precedence over `openssl`.
6//! Both TLS transports remain available when both features are enabled. Verification
7//! failures are never retried with another backend.
8//!
9//! | Configuration | Thumbprints | Trust | PKCS#12 |
10//! |---------------|-------------|-------|---------|
11//! | Windows | CNG (`BCrypt`) | Crypt32 | Native |
12//! | rustls | SHA-1/SHA-256 crates | `WebPKI` | OpenSSL feature required on Unix |
13//! | OpenSSL only | OpenSSL | OpenSSL (`PARTIAL_CHAIN`) | OpenSSL on Unix |
14//!
15//! Client identities ([`identity::ClientIdentity`]) keep the private key in CNG on Windows and
16//! sign in place (`NCryptSignHash`).
17//!
18//! Certificate parsing uses `x509-parser` on all targets. Rustls-only builds do not depend
19//! on OpenSSL. Install a rustls crypto provider before loading keys or verifying chains,
20//! or enable `rustls-ring` to use ring when no provider is installed. Thumbprint hashing
21//! does not require an installed provider.
22
23pub mod auth;
24pub mod cert;
25#[cfg(windows)]
26mod cng;
27mod crypto;
28pub mod digest;
29mod error;
30pub mod identity;
31pub mod key;
32pub mod peer;
33#[cfg(any(test, feature = "testgen"))]
34pub mod testgen;
35#[cfg(all(
36    feature = "testgen",
37    not(test),
38    not(any(windows, all(unix, feature = "openssl"), feature = "testgen-rcgen"))
39))]
40compile_error!("`testgen` requires Windows, `openssl` on Unix, or the `testgen-rcgen` feature");
41pub mod trust;
42
43pub use self::cert::{Certificate, KeyType, SanIp, SubjectAltNames, pem_encode};
44pub use self::error::Error;
45pub use self::identity::{ClientIdentity, Identity, IdentitySource};
46pub use self::key::{HashAlg, PrivateKey, SignScheme};
47pub use self::peer::PeerCerts;
48pub use self::trust::{CaCerts, TrustError};
49
50#[cfg(any(
51    target_arch = "x86_64",
52    all(target_arch = "aarch64", target_feature = "neon")
53))]
54static BASE64: std::sync::LazyLock<base64::engine::Simd> = std::sync::LazyLock::new(|| {
55    base64::engine::Simd::standard(base64::engine::general_purpose::PAD)
56});
57
58#[cfg(not(any(
59    target_arch = "x86_64",
60    all(target_arch = "aarch64", target_feature = "neon")
61)))]
62use base64::engine::general_purpose::STANDARD as BASE64;
63
64/// Installs a provider only in unit-test processes; production never installs one implicitly.
65#[cfg(test)]
66pub(crate) fn test_provider() {
67    #[cfg(all(not(windows), feature = "rustls", not(feature = "rustls-ring")))]
68    let _ = tls_rustls::crypto::ring::default_provider().install_default();
69}