stalwartlabs/stalwart · critical

Failed to build the TLS client configuration

Error message

Failed to build the TLS client configuration

What it means

This .expect() fires when ClientConfig::builder_with_provider(...).with_safe_default_protocol_versions() returns an error while building the STRICT rustls client config in crates/utils/src/http.rs:75-77. With a functional aws_lc_rs provider this step is effectively infallible, so an Err means the crypto provider supports none of the default protocol versions. The panic occurs when the SHARED_TLS_CONFIGS LazyLock is first forced.

Source

Thrown at crates/utils/src/http.rs:77

        _dss: &DigitallySignedStruct,
    ) -> Result<HandshakeSignatureValid, TlsError> {
        Ok(HandshakeSignatureValid::assertion())
    }

    fn supported_verify_schemes(&self) -> Vec<SignatureScheme> {
        self.0.signature_verification_algorithms.supported_schemes()
    }
}

static SHARED_TLS_CONFIGS: LazyLock<SharedTlsConfigs> = LazyLock::new(|| {
    let provider = Arc::new(aws_lc_rs::default_provider());

    let verifier = rustls_platform_verifier::Verifier::new(provider.clone())
        .expect("Failed to load the platform certificate verifier");

    let mut strict = ClientConfig::builder_with_provider(provider.clone())
        .with_safe_default_protocol_versions()
        .expect("Failed to build the TLS client configuration")
        .dangerous()
        .with_custom_certificate_verifier(Arc::new(verifier))
        .with_no_client_auth();
    strict.alpn_protocols = vec![b"h2".to_vec(), b"http/1.1".to_vec()];

    let mut insecure = ClientConfig::builder_with_provider(provider.clone())
        .with_safe_default_protocol_versions()
        .expect("Failed to build the TLS client configuration")
        .dangerous()
        .with_custom_certificate_verifier(Arc::new(NoCertificateVerification(provider)))
        .with_no_client_auth();
    insecure.alpn_protocols = vec![b"h2".to_vec(), b"http/1.1".to_vec()];

    let mut strict_http1 = strict.clone();
    strict_http1.alpn_protocols = vec![b"http/1.1".to_vec()];

    let mut insecure_http1 = insecure.clone();
    insecure_http1.alpn_protocols = vec![b"http/1.1".to_vec()];

View on GitHub (pinned to e962003857)

Solutions

  1. Run cargo update / inspect Cargo.lock so rustls, rustls-pki-types and aws-lc-rs versions are mutually compatible (cargo tree -i rustls)
  2. Ensure aws-lc-rs builds correctly (working cc, cmake, perl/bindgen/go toolchain as required) and the aws_lc_rs feature of rustls is enabled
  3. If using a custom provider, make sure it registers TLS 1.2/1.3 support before builder_with_provider
  4. Call init_shared_tls_configs() early in main so the panic surfaces at startup rather than on first network use

Example fix

// before (mismatched dependency graph)
// rustls 0.23.x mixed with an old aws-lc-rs
// after (Cargo.toml, keep in sync)
// rustls = { version = "0.23", features = ["aws_lc_rs"] }
// aws-lc-rs = "1"
// then: cargo update -p aws-lc-rs && cargo build
Defensive patterns

Strategy: try-catch

Validate before calling

fn provider_supports_defaults() -> bool {
    !aws_lc_rs::default_provider().cipher_suites.is_empty()
}
// plus keep rustls/aws-lc-rs versions aligned: cargo tree -i rustls

Try / catch

// the code uses .expect(), so guard by forcing init early and failing fast:
fn main() {
    crate::utils::http::init_shared_tls_configs(); // panics here with clear context if broken
    // ... rest of app
}

Prevention

When it happens

Trigger: First call to init_shared_tls_configs() or shared_tls_config() when the aws_lc_rs default provider reports no supported protocol versions for with_safe_default_protocol_versions() - typically a broken or version-mismatched aws-lc-rs build, or a substituted provider without TLS 1.2/1.3 support.

Common situations: Mixing incompatible rustls / rustls-pki-types / aws-lc-rs versions after cargo update; aws-lc-rs built without a working C compiler/cmake/bindgen; custom crypto providers registered without TLS 1.2/1.3 suites.

Understand the failure class

Related errors


AI-assisted analysis of stalwartlabs/stalwart@e962003857 (2026-09-06). Data as JSON: /api/errors/956a32562cb77567. Report an issue: GitHub.