From 023daf0ebd64c7645a25101c37915796303a9d2e Mon Sep 17 00:00:00 2001 From: Florian Klink Date: Mon, 3 Nov 2025 15:40:06 +0200 Subject: [PATCH] PsqClient: configure with system CA chain quiche doesn't automatically configure a set of CA certificates to use when enabling verification (as it doesn't enable verification by default either), so it was never possible to connect to an endpoint with a valid certificate, as the set of trusted root was empty. Fix this, by calling `qconfig.load_verify_locations_from_{directory_file}` with the results of a `openssl_probe::probe()` call - the same that rustls-native-certs uses in the Linux case. It uses SSL_CERT_FILE / SSL_CERT_DIR env vars, with sane defaults. I opted against using rustls-native-certs. It also supports reading from the system certificate store / keychain on Windows and MacOS, but as quiche only allows specifying a directory/file where it reads these on its own, and not from memory, and writing this kind of stuff to a temporary file before reading it back in sounds like a nightmare. With this, I'm able to point psq-client to my server with a LE certificate, without having to specify `--ignore-cert`. --- Cargo.toml | 1 + src/client/mod.rs | 19 +++++++++++++++++++ 2 files changed, 20 insertions(+) diff --git a/Cargo.toml b/Cargo.toml index d1b9abb..f2ef063 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -26,6 +26,7 @@ log = "0.4" octets = "0.3" quiche = { version = "0.24", features = ["qlog"] } ring = "0.17" +openssl-probe = "0.1.6" serde = { version = "1.0", features = ["derive"] } serde_json = "1.0" thiserror = "2.0" diff --git a/src/client/mod.rs b/src/client/mod.rs index 52c2497..dcd7e76 100644 --- a/src/client/mod.rs +++ b/src/client/mod.rs @@ -64,6 +64,25 @@ impl PsqClient { qconfig.verify_peer(!ignore_cert); + // Probe for the CA certificate location and configure qconfig with it. + if !ignore_cert { + let probe_result = openssl_probe::probe(); + if let Some(cert_dir) = probe_result.cert_dir { + qconfig + .load_verify_locations_from_directory( + cert_dir.as_path().to_str().expect("valid cert dir"), + ) + .expect("loading cert dir"); + } + if let Some(cert_file) = probe_result.cert_file { + qconfig + .load_verify_locations_from_file( + cert_file.as_path().to_str().expect("valid cert file"), + ) + .expect("loading cert file"); + } + } + qconfig .set_application_protos(quiche::h3::APPLICATION_PROTOCOL) .unwrap();