diff --git a/Cargo.lock b/Cargo.lock index 39ce785a4e..a8e400524e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -167,45 +167,6 @@ version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7c02d123df017efcdfbd739ef81735b36c5ba83ec3c59c80a9d7ecc718f92e50" -[[package]] -name = "asn1-rs" -version = "0.6.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5493c3bedbacf7fd7382c6346bbd66687d12bbaad3a89a2d2c303ee6cf20b048" -dependencies = [ - "asn1-rs-derive", - "asn1-rs-impl", - "displaydoc", - "nom", - "num-traits", - "rusticata-macros", - "thiserror 1.0.69", - "time", -] - -[[package]] -name = "asn1-rs-derive" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "965c2d33e53cb6b267e148a4cb0760bc01f4904c1cd4bb4002a085bb016d1490" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.100", - "synstructure", -] - -[[package]] -name = "asn1-rs-impl" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7b18050c2cd6fe86c3a76584ef5e0baf286d038cda203eb6223df2cc413565f7" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.100", -] - [[package]] name = "assert-json-diff" version = "2.0.2" @@ -1813,20 +1774,6 @@ dependencies = [ "zeroize", ] -[[package]] -name = "der-parser" -version = "9.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5cd0a5c643689626bec213c4d8bd4d96acc8ffdb4ad4bb6bc16abf27d5f4b553" -dependencies = [ - "asn1-rs", - "displaydoc", - "nom", - "num-bigint", - "num-traits", - "rusticata-macros", -] - [[package]] name = "der_derive" version = "0.7.3" @@ -4044,15 +3991,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "oid-registry" -version = "0.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8d8034d9489cdaf79228eb9f6a3b8d7bb32ba00d6645ebd48eef4077ceb5bd9" -dependencies = [ - "asn1-rs", -] - [[package]] name = "once_cell" version = "1.20.2" @@ -5227,7 +5165,7 @@ dependencies = [ "uuid", "walkdir", "workspace_hack", - "x509-parser", + "x509-cert", "zerocopy", ] @@ -5848,15 +5786,6 @@ dependencies = [ "semver", ] -[[package]] -name = "rusticata-macros" -version = "4.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "faf0c4a6ece9950b9abdb62b1cfcf2a68b3b67a10ba445b3bb85be2a293d0632" -dependencies = [ - "nom", -] - [[package]] name = "rustix" version = "0.38.41" @@ -8440,7 +8369,6 @@ dependencies = [ "der 0.7.8", "deranged", "digest", - "displaydoc", "ecdsa 0.16.9", "either", "elliptic-curve 0.13.8", @@ -8568,23 +8496,6 @@ dependencies = [ "zeroize", ] -[[package]] -name = "x509-parser" -version = "0.16.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fcbc162f30700d6f3f82a24bf7cc62ffe7caea42c0b2cba8bf7f3ae50cf51f69" -dependencies = [ - "asn1-rs", - "data-encoding", - "der-parser", - "lazy_static", - "nom", - "oid-registry", - "rusticata-macros", - "thiserror 1.0.69", - "time", -] - [[package]] name = "xattr" version = "1.0.0" diff --git a/Cargo.toml b/Cargo.toml index f2a94d2371..9bbc5a1a38 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -215,10 +215,10 @@ urlencoding = "2.1" uuid = { version = "1.6.1", features = ["v4", "v7", "serde"] } walkdir = "2.3.2" rustls-native-certs = "0.8" -x509-parser = "0.16" whoami = "1.5.1" zerocopy = { version = "0.7", features = ["derive"] } json-structural-diff = { version = "0.2.0" } +x509-cert = { version = "0.2.5" } ## TODO replace this with tracing env_logger = "0.11" diff --git a/compute_tools/Cargo.toml b/compute_tools/Cargo.toml index 90951e7ddb..d80ec41d34 100644 --- a/compute_tools/Cargo.toml +++ b/compute_tools/Cargo.toml @@ -61,7 +61,7 @@ thiserror.workspace = true url.workspace = true uuid.workspace = true walkdir.workspace = true -x509-cert = { version = "0.2.5" } +x509-cert.workspace = true postgres_initdb.workspace = true compute_api.workspace = true diff --git a/compute_tools/src/tls.rs b/compute_tools/src/tls.rs index 5a310d8ac4..8f465c7300 100644 --- a/compute_tools/src/tls.rs +++ b/compute_tools/src/tls.rs @@ -3,7 +3,6 @@ use std::{io::Write, os::unix::fs::OpenOptionsExt, path::Path, time::Duration}; use anyhow::{Context, Result, bail}; use compute_api::responses::TlsConfig; use ring::digest; -use spki::ObjectIdentifier; use spki::der::{Decode, PemReader}; use x509_cert::Certificate; @@ -91,13 +90,13 @@ fn try_update_key_path_blocking(pg_data: &Path, tls_config: &TlsConfig) -> Resul } fn verify_key_cert(key: &str, cert: &str) -> Result<()> { - const ECDSA_WITH_SHA256: ObjectIdentifier = ObjectIdentifier::new_unwrap("1.2.840.10045.4.3.2"); + use x509_cert::der::oid::db::rfc5912::ECDSA_WITH_SHA_256; let cert = Certificate::decode(&mut PemReader::new(cert.as_bytes()).context("pem reader")?) .context("decode cert")?; match cert.signature_algorithm.oid { - ECDSA_WITH_SHA256 => { + ECDSA_WITH_SHA_256 => { let key = p256::SecretKey::from_sec1_pem(key).context("parse key")?; let a = key.public_key().to_sec1_bytes(); diff --git a/proxy/Cargo.toml b/proxy/Cargo.toml index b6e3f03a81..2cec510d82 100644 --- a/proxy/Cargo.toml +++ b/proxy/Cargo.toml @@ -70,8 +70,9 @@ reqwest-middleware = { workspace = true, features = ["json"] } reqwest-retry.workspace = true reqwest-tracing.workspace = true rustc-hash.workspace = true -rustls-pemfile.workspace = true rustls.workspace = true +rustls-native-certs.workspace = true +rustls-pemfile.workspace = true scopeguard.workspace = true serde.workspace = true serde_json.workspace = true @@ -99,8 +100,7 @@ url.workspace = true urlencoding.workspace = true utils.workspace = true uuid.workspace = true -rustls-native-certs.workspace = true -x509-parser.workspace = true +x509-cert.workspace = true redis.workspace = true zerocopy.workspace = true diff --git a/proxy/src/tls/mod.rs b/proxy/src/tls/mod.rs index d6ce6bd9fc..7fe71abf48 100644 --- a/proxy/src/tls/mod.rs +++ b/proxy/src/tls/mod.rs @@ -6,7 +6,7 @@ use anyhow::Context; use rustls::pki_types::CertificateDer; use sha2::{Digest, Sha256}; use tracing::{error, info}; -use x509_parser::oid_registry; +use x509_cert::der::{Reader, SliceReader, oid}; /// pub const PG_ALPN_PROTOCOL: &[u8] = b"postgresql"; @@ -41,27 +41,27 @@ pub enum TlsServerEndPoint { impl TlsServerEndPoint { pub fn new(cert: &CertificateDer<'_>) -> anyhow::Result { - let sha256_oids = [ + const SHA256_OIDS: &[oid::ObjectIdentifier] = &[ // I'm explicitly not adding MD5 or SHA1 here... They're bad. - oid_registry::OID_SIG_ECDSA_WITH_SHA256, - oid_registry::OID_PKCS1_SHA256WITHRSA, + oid::db::rfc5912::ECDSA_WITH_SHA_256, + oid::db::rfc5912::SHA_256_WITH_RSA_ENCRYPTION, ]; - let pem = x509_parser::parse_x509_certificate(cert) - .context("Failed to parse PEM object from cerficiate")? - .1; + let certificate = SliceReader::new(cert) + .context("Failed to parse cerficiate")? + .decode::() + .context("Failed to parse cerficiate")?; - info!(subject = %pem.subject, "parsing TLS certificate"); + let subject = certificate.tbs_certificate.subject; + info!(%subject, "parsing TLS certificate"); - let reg = oid_registry::OidRegistry::default().with_all_crypto(); - let oid = pem.signature_algorithm.oid(); - let alg = reg.get(oid); - if sha256_oids.contains(oid) { + let oid = certificate.signature_algorithm.oid; + if SHA256_OIDS.contains(&oid) { let tls_server_end_point: [u8; 32] = Sha256::new().chain_update(cert).finalize().into(); - info!(subject = %pem.subject, signature_algorithm = alg.map(|a| a.description()), tls_server_end_point = %base64::encode(tls_server_end_point), "determined channel binding"); + info!(%subject, tls_server_end_point = %base64::encode(tls_server_end_point), "determined channel binding"); Ok(Self::Sha256(tls_server_end_point)) } else { - error!(subject = %pem.subject, signature_algorithm = alg.map(|a| a.description()), "unknown channel binding"); + error!(%subject, "unknown channel binding"); Ok(Self::Undefined) } } diff --git a/proxy/src/tls/server_config.rs b/proxy/src/tls/server_config.rs index 4cbd0474c2..eab9940e7d 100644 --- a/proxy/src/tls/server_config.rs +++ b/proxy/src/tls/server_config.rs @@ -5,6 +5,7 @@ use anyhow::{Context, bail}; use itertools::Itertools; use rustls::crypto::ring::{self, sign}; use rustls::pki_types::{CertificateDer, PrivateKeyDer}; +use x509_cert::der::{Reader, SliceReader}; use super::{PG_ALPN_PROTOCOL, TlsServerEndPoint}; @@ -131,11 +132,13 @@ impl CertResolver { let first_cert = &cert_chain[0]; let tls_server_end_point = TlsServerEndPoint::new(first_cert)?; - let pem = x509_parser::parse_x509_certificate(first_cert) - .context("Failed to parse PEM object from cerficiate")? - .1; - let common_name = pem.subject().to_string(); + let certificate = SliceReader::new(first_cert) + .context("Failed to parse cerficiate")? + .decode::() + .context("Failed to parse cerficiate")?; + + let common_name = certificate.tbs_certificate.subject.to_string(); // We need to get the canonical name for this certificate so we can match them against any domain names // seen within the proxy codebase. diff --git a/workspace_hack/Cargo.toml b/workspace_hack/Cargo.toml index 6a726f0585..e9eaf4b35e 100644 --- a/workspace_hack/Cargo.toml +++ b/workspace_hack/Cargo.toml @@ -61,7 +61,7 @@ memchr = { version = "2" } nix = { version = "0.26" } nom = { version = "7" } num = { version = "0.4" } -num-bigint = { version = "0.4" } +num-bigint = { version = "0.4", default-features = false, features = ["std"] } num-complex = { version = "0.4", default-features = false, features = ["std"] } num-integer = { version = "0.1", features = ["i128"] } num-iter = { version = "0.1", default-features = false, features = ["i128", "std"] } @@ -115,7 +115,6 @@ anyhow = { version = "1", features = ["backtrace"] } bytes = { version = "1", features = ["serde"] } cc = { version = "1", default-features = false, features = ["parallel"] } chrono = { version = "0.4", default-features = false, features = ["clock", "serde", "wasmbind"] } -displaydoc = { version = "0.2" } either = { version = "1" } getrandom = { version = "0.2", default-features = false, features = ["std"] } half = { version = "2", default-features = false, features = ["num-traits"] } @@ -128,7 +127,7 @@ log = { version = "0.4", default-features = false, features = ["std"] } memchr = { version = "2" } nom = { version = "7" } num = { version = "0.4" } -num-bigint = { version = "0.4" } +num-bigint = { version = "0.4", default-features = false, features = ["std"] } num-complex = { version = "0.4", default-features = false, features = ["std"] } num-integer = { version = "0.1", features = ["i128"] } num-iter = { version = "0.1", default-features = false, features = ["i128", "std"] }