Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
76 changes: 0 additions & 76 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6,839 changes: 1,751 additions & 5,088 deletions LICENSE-3rdparty.yml

Large diffs are not rendered by default.

32 changes: 13 additions & 19 deletions libdd-common/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,9 @@ regex = "1.5"
# Use hickory-dns instead of the default system DNS resolver to avoid fork safety issues.
# The default resolver can hold locks or other global state that can cause deadlocks
# or corruption when the process forks (e.g., in PHP-FPM or other forking environments).
reqwest = { version = "0.13.2", features = ["rustls", "hickory-dns"], default-features = false, optional = true }
# Use rustls-no-provider instead of rustls to avoid reqwest forcing aws-lc-rs as the crypto
# backend. We install the ring provider explicitly in connector/mod.rs instead.
reqwest = { version = "0.13.2", features = ["rustls-no-provider", "hickory-dns"], default-features = false, optional = true }
rustls-native-certs = { version = "0.8.1", optional = true }
thiserror = "1.0"
tokio = { version = "1.23", features = ["rt", "macros", "net", "io-util", "fs"] }
Expand All @@ -48,6 +50,16 @@ static_assertions = "1.1.0"
libc = "0.2"
const_format = "0.2.34"
nix = { version = "0.29", features = ["process"] }
# Use ring as the default crypto provider for non-FIPS builds on all platforms.
# FIPS builds activate aws-lc-rs via the hyper-rustls/fips feature instead.
rustls = { version = "0.23.37", default-features = false, optional = true, features = ["ring"] }
hyper-rustls = { version = "0.27.7", default-features = false, features = [
"native-tokio",
"http1",
"tls12",
"ring",
], optional = true }

[target.'cfg(windows)'.dependencies.windows-sys]
version = "0.52"
features = [
Expand All @@ -57,24 +69,6 @@ features = [
"Win32_System_Threading",
]

[target.'cfg(unix)'.dependencies]
rustls = { version = "0.23.37", default-features = false, optional = true, features = ["aws-lc-rs"] }
hyper-rustls = { version = "0.27.7", default-features = false, features = [
"native-tokio",
"http1",
"tls12",
"aws-lc-rs",
], optional = true }

[target.'cfg(not(unix))'.dependencies]
rustls = { version = "0.23.37", default-features = false, optional = true, features = ["ring"] }
hyper-rustls = { version = "0.27.7", default-features = false, features = [
"native-tokio",
"http1",
"tls12",
"ring",
], optional = true }

[dev-dependencies]
httparse = "1.9"
indexmap = "2.11"
Expand Down
14 changes: 4 additions & 10 deletions libdd-common/src/connector/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -88,27 +88,21 @@ mod https {

use rustls::ClientConfig;

/// When using aws-lc-rs, rustls needs to be initialized with the default CryptoProvider;
/// sometimes this is done as a side-effect of other operations, but we need to ensure it
/// happens here. On non-unix platforms, ddcommon uses `ring` instead, which handles this
/// at rustls initialization.
/// In fips mode we expect someone to have done this already.
/// Ensures the rustls default CryptoProvider is installed (ring for non-FIPS).
/// In FIPS mode, the caller must install the FIPS provider before any TLS use.
#[cfg(any(not(feature = "fips"), coverage))]
fn ensure_crypto_provider_initialized() {
use std::sync::Once;

static INIT_CRYPTO_PROVIDER: Once = Once::new();

INIT_CRYPTO_PROVIDER.call_once(|| {
#[cfg(unix)]
let _ = rustls::crypto::aws_lc_rs::default_provider().install_default();
#[cfg(not(unix))]
let _ = rustls::crypto::ring::default_provider().install_default();
});
}

// This actually needs to be done by the user somewhere in their own main. This will only
// be active on Unix platforms
/// In FIPS mode, the caller must install the FIPS-compliant crypto provider
/// (e.g., aws-lc-rs FIPS) before any TLS connections are established.
#[cfg(all(feature = "fips", not(coverage)))]
fn ensure_crypto_provider_initialized() {}

Expand Down
9 changes: 9 additions & 0 deletions libdd-common/tests/reqwest_builder_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,12 @@ mod tests {
};
use libdd_common::Endpoint;

/// With rustls-no-provider, reqwest does not auto-install a crypto provider.
/// Tests that build a reqwest client must ensure one is installed first.
fn ensure_crypto_provider() {
let _ = rustls::crypto::ring::default_provider().install_default();
}

/// Helper to send a simple HTTP request and return the response
async fn send_request(
client: reqwest::Client,
Expand All @@ -26,6 +32,7 @@ mod tests {
#[tokio::test]
#[cfg_attr(miri, ignore)]
async fn test_file_dump_captures_http_request() {
ensure_crypto_provider();
let file_path = create_temp_file_path("libdd_common_test", "http");

// Create endpoint with file:// scheme
Expand Down Expand Up @@ -89,6 +96,7 @@ mod tests {
#[test]
#[cfg_attr(miri, ignore)]
fn test_both_resolver_configs_build_client() {
ensure_crypto_provider();
let url = "http://example.com/";
for use_system_resolver in [false, true] {
let endpoint = Endpoint::from_slice(url).with_system_resolver(use_system_resolver);
Expand Down Expand Up @@ -150,6 +158,7 @@ mod tests {
/// alive, drop client, drop runtime, then count threads after drop. Returns (threads_alive,
/// threads_after_drop).
fn run_resolver_phase(url_slice: &str, use_system_resolver: bool) -> (usize, usize) {
ensure_crypto_provider();
let rt = tokio::runtime::Builder::new_current_thread()
.enable_all()
.build()
Expand Down
14 changes: 6 additions & 8 deletions libdd-profiling/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,13 @@ parking_lot = { version = "0.12", default-features = false }
prost = "0.14.1"
rand = "0.8"
# Use rustls to align with the rest of the workspace (libdd-common, libdd-telemetry, etc.)
# This uses the same TLS stack (rustls + aws-lc-rs/ring) as other crates
# Non-FIPS builds use ring as the crypto provider; FIPS builds use aws-lc-rs.
# Use hickory-dns instead of the default system DNS resolver to avoid fork safety issues.
# The default resolver can hold locks or other global state that can cause deadlocks
# or corruption when the process forks (e.g., in PHP-FPM or other forking environments).
reqwest = { version = "0.13.2", features = ["multipart", "rustls", "hickory-dns"], default-features = false}
# Use rustls-no-provider instead of rustls to avoid reqwest forcing aws-lc-rs as the crypto
# backend. We install the ring provider explicitly via tls.rs / libdd-common instead.
reqwest = { version = "0.13.2", features = ["multipart", "rustls-no-provider", "hickory-dns"], default-features = false}
rustls-platform-verifier = "0.6"
rustc-hash = { version = "1.1", default-features = false }
serde = {version = "1.0", features = ["derive"]}
Expand All @@ -63,12 +65,8 @@ thiserror = "2"
tokio = {version = "1.23", features = ["rt", "macros", "net", "io-util", "fs"]}
tokio-util = { version = "0.7.1", default-features = false }
zstd = { version = "0.13", default-features = false }

# aws-lc-rs is preferred on Unix; ring is used on Windows where aws-lc-rs has build issues.
[target.'cfg(unix)'.dependencies]
rustls = { version = "0.23.37", default-features = false, features = ["aws-lc-rs"] }

[target.'cfg(not(unix))'.dependencies]
# ring is the crypto provider for non-FIPS builds on all platforms.
# FIPS builds activate aws-lc-rs via the rustls/fips feature instead.
rustls = { version = "0.23.37", default-features = false, features = ["ring"] }

[dev-dependencies]
Expand Down
20 changes: 6 additions & 14 deletions libdd-profiling/src/exporter/tls.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,9 +39,8 @@ impl TlsConfig {

// Use an explicit CryptoProvider rather than relying on
// `CryptoProvider::get_default_or_install_from_crate_features()`.
// Feature unification can enable both `aws-lc-rs` and `ring` in the
// same build (reqwest enables aws-lc-rs while libdd-common enables
// ring on Windows), which causes the automatic detection to panic.
// Feature unification may enable multiple crypto backends in the same
// build, which causes the automatic detection to panic.
let provider = rustls::crypto::CryptoProvider::get_default()
.cloned()
.unwrap_or_else(|| std::sync::Arc::new(Self::default_crypto_provider()));
Expand All @@ -53,19 +52,12 @@ impl TlsConfig {
Ok(Self(config))
}

/// Returns the platform-appropriate default crypto provider.
/// Returns the default crypto provider (ring for non-FIPS builds).
///
/// Matches the convention used by `libdd-common`: `aws-lc-rs` on Unix,
/// `ring` on Windows (where `aws-lc-rs` has issues).
/// Matches the convention used by `libdd-common`: ring on all platforms
/// for non-FIPS. FIPS builds install the aws-lc-rs FIPS provider externally.
fn default_crypto_provider() -> rustls::crypto::CryptoProvider {
#[cfg(unix)]
{
rustls::crypto::aws_lc_rs::default_provider()
}
#[cfg(not(unix))]
{
rustls::crypto::ring::default_provider()
}
rustls::crypto::ring::default_provider()
}
}

Expand Down
Loading