From 90f6336d97e954b5e39213425648c1b1e165eea9 Mon Sep 17 00:00:00 2001 From: tottoto Date: Mon, 11 Sep 2023 23:43:38 +0900 Subject: [PATCH] chore(tls): Update to rustls 0.22.0 --- Cargo.toml | 3 + tonic/Cargo.toml | 12 +-- tonic/src/transport/service/tls.rs | 148 ++++++----------------------- 3 files changed, 37 insertions(+), 126 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 117ab4de4..609381b6a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -29,3 +29,6 @@ members = [ ] resolver = "2" +[patch.crates-io] +rustls = { git = "https://github.com/rustls/rustls", package ="rustls", rev = "b57204daab48e46b216d2505d9007cbdde0a6460" } +rustls-pemfile = { git = "https://github.com/rustls/pemfile", rev = "c72614681cd0335463fb6c49ee10cd1c25912e5a" } diff --git a/tonic/Cargo.toml b/tonic/Cargo.toml index 8063764e7..1d106cabe 100644 --- a/tonic/Cargo.toml +++ b/tonic/Cargo.toml @@ -27,7 +27,7 @@ codegen = ["dep:async-trait"] gzip = ["dep:flate2"] default = ["transport", "codegen", "prost"] prost = ["dep:prost"] -tls = ["dep:rustls-pemfile", "transport", "dep:tokio-rustls", "dep:rustls", "tokio/rt", "tokio/macros"] +tls = ["dep:rustls-pki-types", "dep:rustls-pemfile", "transport", "dep:tokio-rustls", "tokio/rt", "tokio/macros"] tls-roots = ["tls-roots-common", "dep:rustls-native-certs"] tls-roots-common = ["tls"] tls-webpki-roots = ["tls-roots-common", "dep:webpki-roots"] @@ -77,11 +77,11 @@ axum = {version = "0.6.9", default_features = false, optional = true} # rustls async-stream = { version = "0.3", optional = true } -rustls-pemfile = { version = "1.0", optional = true } -rustls-native-certs = { version = "0.6.3", optional = true } -tokio-rustls = { version = "0.24.1", optional = true } -rustls = { version = "0.21.7", optional = true } -webpki-roots = { version = "0.25.0", optional = true } +rustls-pki-types = { version = "0.2", optional = true } +rustls-pemfile = { version = "2.0.0-alpha.1", optional = true } +rustls-native-certs = { git = "https://github.com/rustls/rustls-native-certs", optional = true } +tokio-rustls = { git = "https://github.com/rustls/tokio-rustls", optional = true } +webpki-roots = { version = "0.26.0-alpha.1", optional = true } # compression flate2 = {version = "1.0", optional = true} diff --git a/tonic/src/transport/service/tls.rs b/tonic/src/transport/service/tls.rs index f956132fb..206b341ad 100644 --- a/tonic/src/transport/service/tls.rs +++ b/tonic/src/transport/service/tls.rs @@ -6,7 +6,10 @@ use crate::transport::{ use std::{fmt, sync::Arc}; use tokio::io::{AsyncRead, AsyncWrite}; use tokio_rustls::{ - rustls::{ClientConfig, RootCertStore, ServerConfig, ServerName}, + rustls::{ + crypto::ring::Ring, server::WebPkiClientVerifier, ClientConfig, RootCertStore, + ServerConfig, ServerName, + }, TlsAcceptor as RustlsAcceptor, TlsConnector as RustlsConnector, }; @@ -22,7 +25,7 @@ enum TlsError { #[derive(Clone)] pub(crate) struct TlsConnector { - config: Arc, + config: Arc>, domain: Arc, } @@ -36,16 +39,10 @@ impl TlsConnector { let mut roots = RootCertStore::empty(); #[cfg(feature = "tls-roots")] - roots.add_parsable_certificates(&rustls_native_certs::load_native_certs()?); + roots.add_parsable_certificates(rustls_native_certs::load_native_certs()?); #[cfg(feature = "tls-webpki-roots")] - roots.add_trust_anchors(webpki_roots::TLS_SERVER_ROOTS.iter().map(|ta| { - tokio_rustls::rustls::OwnedTrustAnchor::from_subject_spki_name_constraints( - ta.subject, - ta.spki, - ta.name_constraints, - ) - })); + roots.extend(webpki_roots::TLS_SERVER_ROOTS.iter().cloned()); if let Some(cert) = ca_cert { rustls_keys::add_certs_from_pem(std::io::Cursor::new(cert.as_ref()), &mut roots)?; @@ -98,7 +95,7 @@ impl fmt::Debug for TlsConnector { #[derive(Clone)] pub(crate) struct TlsAcceptor { - inner: Arc, + inner: Arc>, } impl TlsAcceptor { @@ -112,18 +109,19 @@ impl TlsAcceptor { let builder = match (client_ca_root, client_auth_optional) { (None, _) => builder.with_no_client_auth(), (Some(cert), true) => { - use tokio_rustls::rustls::server::AllowAnyAnonymousOrAuthenticatedClient; let mut roots = RootCertStore::empty(); rustls_keys::add_certs_from_pem(std::io::Cursor::new(cert.as_ref()), &mut roots)?; builder.with_client_cert_verifier( - AllowAnyAnonymousOrAuthenticatedClient::new(roots).boxed(), + WebPkiClientVerifier::builder(roots.into()) + .allow_unauthenticated() + .build()?, ) } (Some(cert), false) => { - use tokio_rustls::rustls::server::AllowAnyAuthenticatedClient; let mut roots = RootCertStore::empty(); rustls_keys::add_certs_from_pem(std::io::Cursor::new(cert.as_ref()), &mut roots)?; - builder.with_client_cert_verifier(AllowAnyAuthenticatedClient::new(roots).boxed()) + builder + .with_client_cert_verifier(WebPkiClientVerifier::builder(roots.into()).build()?) } }; @@ -169,134 +167,44 @@ impl std::error::Error for TlsError {} mod rustls_keys { use std::io::Cursor; - use tokio_rustls::rustls::{Certificate, PrivateKey, RootCertStore}; + use rustls_pki_types::{CertificateDer, PrivateKeyDer}; + use tokio_rustls::rustls::RootCertStore; use crate::transport::service::tls::TlsError; use crate::transport::Identity; - pub(super) fn load_rustls_private_key( - mut cursor: std::io::Cursor<&[u8]>, - ) -> Result { - while let Ok(Some(item)) = rustls_pemfile::read_one(&mut cursor) { - match item { - rustls_pemfile::Item::RSAKey(key) - | rustls_pemfile::Item::PKCS8Key(key) - | rustls_pemfile::Item::ECKey(key) => return Ok(PrivateKey(key)), - _ => continue, - } - } - - // Otherwise we have a Private Key parsing problem - Err(Box::new(TlsError::PrivateKeyParseError)) - } - pub(crate) fn load_identity( identity: Identity, - ) -> Result<(Vec, PrivateKey), crate::Error> { - let cert = { - let mut cert = std::io::Cursor::new(identity.cert.as_ref()); - match rustls_pemfile::certs(&mut cert) { - Ok(certs) => certs.into_iter().map(Certificate).collect(), + ) -> Result<(Vec>, PrivateKeyDer<'static>), crate::Error> { + let certs = { + let mut cert = std::io::Cursor::new(&identity.cert); + match rustls_pemfile::certs(&mut cert).collect::, _>>() { + Ok(certs) => certs, Err(_) => return Err(Box::new(TlsError::CertificateParseError)), } }; let key = { - let key = std::io::Cursor::new(identity.key.as_ref()); - match load_rustls_private_key(key) { - Ok(key) => key, - Err(e) => { - return Err(e); - } + let mut key = std::io::Cursor::new(&identity.key); + match rustls_pemfile::private_key(&mut key) { + Ok(Some(key)) => key, + _ => return Err(Box::new(TlsError::PrivateKeyParseError)), } }; - Ok((cert, key)) + Ok((certs, key)) } pub(crate) fn add_certs_from_pem( mut certs: Cursor<&[u8]>, roots: &mut RootCertStore, ) -> Result<(), crate::Error> { - let (_, ignored) = roots.add_parsable_certificates(&rustls_pemfile::certs(&mut certs)?); + let (_, ignored) = roots.add_parsable_certificates( + rustls_pemfile::certs(&mut certs).collect::, _>>()?, + ); match ignored == 0 { true => Ok(()), false => Err(Box::new(TlsError::CertificateParseError)), } } } - -#[cfg(test)] -mod tests { - use std::io::Cursor; - - // generated by: openssl ecparam -keygen -name 'prime256v1' - const SIMPLE_EC_KEY: &str = r#"-----BEGIN EC PARAMETERS----- -BggqhkjOPQMBBw== ------END EC PARAMETERS----- ------BEGIN EC PRIVATE KEY----- -MHcCAQEEICIDyh40kMVWGDAYr1gXnMfeMeO3zXYigOaWrg5SNB+zoAoGCCqGSM49 -AwEHoUQDQgAEacJyVg299dkPTzUaMbOmACUfF67yp+ZrDhXVjn/5WxBAgjcmFBHg -Tw8dfwpMzaJPXX5lWYzP276fcmbRO25CXw== ------END EC PRIVATE KEY-----"#; - - // generated by: openssl genpkey -algorithm rsa - const SIMPLE_PKCS8_KEY: &str = r#"-----BEGIN PRIVATE KEY----- -MIICdwIBADANBgkqhkiG9w0BAQEFAASCAmEwggJdAgEAAoGBAKHkX1YIvqOIAllD -5fKcIxu2kYjIxxAAQrOBRTloGZUKdPFQY1RANB4t/LEaI5/NJ6NK4915pTn35QAQ -zHJl+X4rNFMgVt+o/nY40PgrQxyyv5A0/URp+iS8Yn3GKt3q6p4zguiO9uNXhiiD -b+VKIFRDm4bHR2yM7pNJ0kMdoattAgMBAAECgYAMpw6UaMaNfVnBpD7agT11MwWY -zShRpdOQt++zFuG49kJBgejhcssf+LQhG0vhd2U7q+S3MISrTSaGpMl1v2aKR/nV -G7X4Bb6X8vrVSMrfze2loT0aNri9jKDZkD/muy6+9JkhRa03NOdhDdseokmcqF3L -xsU4BUOOFYb23ycoeQJBANOGxbZu/3BqsPJMQmXWo1CXuaviZ83lTczPtrz9mJVl -Zs/KmGnJ8I2Azu/dlYXsHRvbIbqA93l1M3GnsWl5IxsCQQDD7hKvOY6qzUNyj+R4 -vul/3xaqjiTj59f3jN7Fh6+9AY+WfvEkWfyUUAXY74z43wBgtORfMXnZnjFO96tJ -sswXAkBDYDtb19E/cox4MTg5DfwpMJrwmAYufCqi4Uq4uiI++/SanVKc57jaqbvA -hZkZ9lJzTAJbULcDFgTT3/FPwkkfAkEAqbSDMIzdGuox2n/x9/f8jcpweogmQdUl -xgCZUGSnfkFk2ojXW5Ip6Viqx+0toL6fOCRWjnFvRmPz958kGPCqPwJBAID4y7XV -peOO6Yadu0YbSmFNluRebia6410p5jR21LhG1ty2h22xVhlBWjOC+TyDuKwhmiYT -ed50S3LR1PWt4zE= ------END PRIVATE KEY-----"#; - - // generated by: openssl genrsa - const SIMPLE_RSA_KEY: &str = r#"-----BEGIN RSA PRIVATE KEY----- -MIIEogIBAAKCAQEAoEILGds1/RGBHT7jM4R+EL24sQ6Bsn14GgTHc7WoZ7lainEH -H/n+DtHCYUXYyJnN5AMIi3pkigCP1hdXXBQga3zs3lXoi/mAMkT6vjuqQ7Xg5/95 -ABx5Ztyy25mZNaXm77glyAzSscKHxWYooXVJYG4C3SGuBJJ1zVjxen6Rkzse5Lpr -yZOUUeqeV3M6KbJ/dkR37HFQVwmlctQukFnb4kozFBQDDnkXi9jT/PH00g6JpW3z -YMzdMq2RMadJ0dzYv62OtdtqmQpVz0dRu/yODV4DkhrWwgPRj2uY4DnYthzILESB -x41gxHj+jqo6NW+C+0fr6uh2CXtD0p+ZVANtBQIDAQABAoIBAE7IaOCrLV1dr5WL -BvKancbpHdSdBxGSMOrJkqvFkCZ9ro8EhbYolcb/Q4nCZpInWlpPS3IWFzroj811 -6BJyKoXtAh1DKnE1lNohowrGFiv3S7uBkiCF3wC8Wokud20yQ9dxNdGkzCdrNIfM -cwj8ubfYHTxMhFnnDlaG9R98/V/dFy0FLxL37eMP/heMbcwKKm9P/G2FqvuCn8a4 -FoPbAfvaR64IGCybjoiTjUD7xMHIV4Gr5K07br2TzG2zVlFTacoqXyGBbVVy+ibt -QMh0sn+rMkAy+cFse+yCYZeAFa4FzwGz43sdFviU7uvLG7yXpvZ+uDACFzxlxUVg -v57r1cECgYEA1MMJEe6IunDUyuzRaFNTfQX16QcAv/xLN/1TtVB3HUX5p2bIZKDr -XEl0NCVOrCoz5RsYqbtGmp8B4Yxl3DeX+WeWeD9/f2ZTVGWyBx1N6dZ5hRsyfzG/ -xVBUqYxkChjXQ20cNtf8u7JKdnVjOJen9M92nXhFRTwgH83Id4gPp70CgYEAwNN8 -lvVJnd05ekyf1qIKOSyKiSGnGa5288PpqsjYMZisXy12y4n8cK2pX5Z5PICHeJVu -K99WdTtO7Q4ghCXRB1jR5pTd4/3/3089SQyDnWz9jlA3pGWcSLDTB1dBJXpMQ6yG -cR2dX5hPDNIdKsc+9Bl/OF5PScvGVUYv4SLF6ukCgYAVhh2WyNDgO6XrWYXdzgA2 -N7Im/uReh8F8So57W0aRmZCmFMnVFEp7LZsp41RQKnzRgqo+EYoU/l0MWk27t4wS -WR5pz9KwKsPnV9poydgl/eKRSq0THQ9PgM7v0BoWw2iTk6g1DCivPFw4G6wL/5uo -MozHZXFsjaaaUREktokO6QKBgC3Dg7RILtqaoIOYH+9OseJz4cU+CWyc7XpZKuHv -nO/YbkCAh8syyojrjmEzUz66umwx+t3KubhFBSxZx/nVB9EYkWiKOEdeBxY2tjLa -F3qLXXojK7GGtBrEbLE3UizU47jD/3xlLO59NXWzgFygwR4p1vnH2EWJaV7fs4lZ -OWPRAoGAL0nX0vZ0N9qPETiQan1uHjKYuuFiSP+cwRXVSUYIQM9qDRlKG9zjugwO -az+B6uiR4TrgbwG+faCQwcGk9B8QbcoIb8IigwrWe3XpVaEtcsqFORX0r+tJNDoY -I0O2DOQVPKSK2N5AZzXY4IkybWTV4Yxc7rdXEO3dOOpHGKbpwFQ= ------END RSA PRIVATE KEY-----"#; - - #[test] - fn test_parse_ec_key() { - for (n, key) in [SIMPLE_EC_KEY, SIMPLE_PKCS8_KEY, SIMPLE_RSA_KEY] - .iter() - .enumerate() - { - let c = Cursor::new(key.as_bytes()); - let key = super::rustls_keys::load_rustls_private_key(c); - - assert!(key.is_ok(), "at the {}-th case", n); - } - } -}