diff --git a/openssl-sys/CHANGELOG.md b/openssl-sys/CHANGELOG.md index 3a1a1f1865..9166bd5aca 100644 --- a/openssl-sys/CHANGELOG.md +++ b/openssl-sys/CHANGELOG.md @@ -2,6 +2,14 @@ ## [Unreleased] +## [v0.9.92] - 2023-08-27 + +### Added + +* Added `EVP_CIPHER_CTX_copy` +* Expose `EVP_chacha20_poly1305` on LibreSSL +* Added `X509_VERIFY_PARAM_set1_email` + ## [v0.9.91] - 2023-08-06 ### Added @@ -490,7 +498,8 @@ Fixed builds against OpenSSL built with `no-cast`. * Added `X509_verify` and `X509_REQ_verify`. * Added `EVP_MD_type` and `EVP_GROUP_get_curve_name`. -[Unreleased]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.91..master +[Unreleased]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.92..master +[v0.9.92]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.91...openssl-sys-v0.9.92 [v0.9.91]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.90...openssl-sys-v0.9.91 [v0.9.90]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.89...openssl-sys-v0.9.90 [v0.9.89]: https://github.com/sfackler/rust-openssl/compare/openssl-sys-v0.9.88...openssl-sys-v0.9.89 diff --git a/openssl-sys/Cargo.toml b/openssl-sys/Cargo.toml index 3caa72fa79..98a7c793be 100644 --- a/openssl-sys/Cargo.toml +++ b/openssl-sys/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "openssl-sys" -version = "0.9.91" +version = "0.9.92" authors = [ "Alex Crichton ", "Steven Fackler ", diff --git a/openssl-sys/src/handwritten/evp.rs b/openssl-sys/src/handwritten/evp.rs index 7da92eeeb8..e8ad6aa2d7 100644 --- a/openssl-sys/src/handwritten/evp.rs +++ b/openssl-sys/src/handwritten/evp.rs @@ -271,6 +271,8 @@ const_ptr_api! { extern "C" { pub fn EVP_CIPHER_CTX_new() -> *mut EVP_CIPHER_CTX; pub fn EVP_CIPHER_CTX_free(ctx: *mut EVP_CIPHER_CTX); + pub fn EVP_CIPHER_CTX_copy(dst: *mut EVP_CIPHER_CTX, src: *const EVP_CIPHER_CTX) -> c_int; + pub fn EVP_MD_CTX_copy_ex(dst: *mut EVP_MD_CTX, src: *const EVP_MD_CTX) -> c_int; #[cfg(ossl111)] pub fn EVP_MD_CTX_reset(ctx: *mut EVP_MD_CTX) -> c_int; @@ -367,7 +369,7 @@ extern "C" { pub fn EVP_aes_256_wrap_pad() -> *const EVP_CIPHER; #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_CHACHA")))] pub fn EVP_chacha20() -> *const EVP_CIPHER; - #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_CHACHA")))] + #[cfg(all(any(ossl110, libressl360), not(osslconf = "OPENSSL_NO_CHACHA")))] pub fn EVP_chacha20_poly1305() -> *const EVP_CIPHER; #[cfg(not(osslconf = "OPENSSL_NO_SEED"))] pub fn EVP_seed_cbc() -> *const EVP_CIPHER; diff --git a/openssl-sys/src/handwritten/x509_vfy.rs b/openssl-sys/src/handwritten/x509_vfy.rs index 9adf63fa0e..a560e586d8 100644 --- a/openssl-sys/src/handwritten/x509_vfy.rs +++ b/openssl-sys/src/handwritten/x509_vfy.rs @@ -118,6 +118,12 @@ extern "C" { #[cfg(any(ossl102, libressl261))] pub fn X509_VERIFY_PARAM_set_hostflags(param: *mut X509_VERIFY_PARAM, flags: c_uint); #[cfg(any(ossl102, libressl261))] + pub fn X509_VERIFY_PARAM_set1_email( + param: *mut X509_VERIFY_PARAM, + email: *const c_char, + emaillen: size_t, + ) -> c_int; + #[cfg(any(ossl102, libressl261))] pub fn X509_VERIFY_PARAM_set1_ip( param: *mut X509_VERIFY_PARAM, ip: *const c_uchar, diff --git a/openssl-sys/src/rsa.rs b/openssl-sys/src/rsa.rs index ff30cf1e23..64107cd6b2 100644 --- a/openssl-sys/src/rsa.rs +++ b/openssl-sys/src/rsa.rs @@ -76,7 +76,7 @@ pub unsafe fn EVP_PKEY_CTX_set0_rsa_oaep_label( EVP_PKEY_OP_TYPE_CRYPT, EVP_PKEY_CTRL_RSA_OAEP_LABEL, len, - label as *mut c_void, + label, ) } diff --git a/openssl/CHANGELOG.md b/openssl/CHANGELOG.md index b6bbbb9ce7..f5409b1222 100644 --- a/openssl/CHANGELOG.md +++ b/openssl/CHANGELOG.md @@ -2,6 +2,16 @@ ## [Unreleased] +## [v0.10.57] - 2023-08-27 + +### Added +* Added `X509VerifyParam::set_email` +* `Cipher::chacha20_poly1305` is now available on LibreSSL +* Added `CipherCtx::copy` + +### Changed +* Updated `bitflags` dependecy to the 2.x series + ## [v0.10.56] - 2023-08-06 ## Added @@ -787,7 +797,8 @@ Look at the [release tags] for information about older releases. -[Unreleased]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.56...master +[Unreleased]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.57...master +[v0.10.57]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.56...openssl-v0.10.57 [v0.10.56]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.55...openssl-v0.10.56 [v0.10.55]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.54...openssl-v0.10.55 [v0.10.54]: https://github.com/sfackler/rust-openssl/compare/openssl-v0.10.53...openssl-v0.10.54 diff --git a/openssl/Cargo.toml b/openssl/Cargo.toml index 17f82ca843..ec8beaef9c 100644 --- a/openssl/Cargo.toml +++ b/openssl/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "openssl" -version = "0.10.56" +version = "0.10.57" authors = ["Steven Fackler "] license = "Apache-2.0" description = "OpenSSL bindings" @@ -23,14 +23,14 @@ unstable_boringssl = ["ffi/unstable_boringssl"] default = [] [dependencies] -bitflags = "1.0" +bitflags = "2.2.1" cfg-if = "1.0" foreign-types = "0.3.1" libc = "0.2" once_cell = "1.5.2" openssl-macros = { version = "0.1.0", path = "../openssl-macros" } -ffi = { package = "openssl-sys", version = "0.9.91", path = "../openssl-sys" } +ffi = { package = "openssl-sys", version = "0.9.92", path = "../openssl-sys" } [dev-dependencies] hex = "0.3" diff --git a/openssl/src/cipher.rs b/openssl/src/cipher.rs index f81895e513..2b89861365 100644 --- a/openssl/src/cipher.rs +++ b/openssl/src/cipher.rs @@ -435,7 +435,7 @@ impl Cipher { unsafe { CipherRef::from_ptr(ffi::EVP_chacha20() as *mut _) } } - #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_CHACHA")))] + #[cfg(all(any(ossl110, libressl360), not(osslconf = "OPENSSL_NO_CHACHA")))] pub fn chacha20_poly1305() -> &'static CipherRef { unsafe { CipherRef::from_ptr(ffi::EVP_chacha20_poly1305() as *mut _) } } diff --git a/openssl/src/cipher_ctx.rs b/openssl/src/cipher_ctx.rs index 56d0d26700..f9031d2976 100644 --- a/openssl/src/cipher_ctx.rs +++ b/openssl/src/cipher_ctx.rs @@ -105,6 +105,14 @@ impl CipherCtx { } impl CipherCtxRef { + #[corresponds(EVP_CIPHER_CTX_copy)] + pub fn copy(&mut self, src: &CipherCtxRef) -> Result<(), ErrorStack> { + unsafe { + cvt(ffi::EVP_CIPHER_CTX_copy(self.as_ptr(), src.as_ptr()))?; + Ok(()) + } + } + /// Initializes the context for encryption. /// /// Normally this is called once to set all of the cipher, key, and IV. However, this process can be split up diff --git a/openssl/src/cms.rs b/openssl/src/cms.rs index 6b6aa9fd8c..d11443b5ce 100644 --- a/openssl/src/cms.rs +++ b/openssl/src/cms.rs @@ -20,6 +20,8 @@ use crate::{cvt, cvt_p}; use openssl_macros::corresponds; bitflags! { + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct CMSOptions : c_uint { const TEXT = ffi::CMS_TEXT; const CMS_NOCERTS = ffi::CMS_NOCERTS; diff --git a/openssl/src/encrypt.rs b/openssl/src/encrypt.rs index d3db0fd414..4522146f89 100644 --- a/openssl/src/encrypt.rs +++ b/openssl/src/encrypt.rs @@ -40,7 +40,7 @@ //! assert_eq!(&*decrypted, data); //! ``` #[cfg(any(ossl102, libressl310))] -use libc::{c_int, c_void}; +use libc::c_int; use std::{marker::PhantomData, ptr}; use crate::error::ErrorStack; @@ -174,7 +174,7 @@ impl<'a> Encrypter<'a> { cvt(ffi::EVP_PKEY_CTX_set0_rsa_oaep_label( self.pctx, - p as *mut c_void, + p, label.len() as c_int, )) .map(|_| ()) @@ -378,7 +378,7 @@ impl<'a> Decrypter<'a> { cvt(ffi::EVP_PKEY_CTX_set0_rsa_oaep_label( self.pctx, - p as *mut c_void, + p, label.len() as c_int, )) .map(|_| ()) diff --git a/openssl/src/lib.rs b/openssl/src/lib.rs index c2c390cc1b..fe29d02293 100644 --- a/openssl/src/lib.rs +++ b/openssl/src/lib.rs @@ -44,7 +44,7 @@ //! $ sudo apt-get install pkg-config libssl-dev //! //! # Fedora -//! $ sudo dnf install pkg-config openssl-devel +//! $ sudo dnf install pkg-config perl-FindBin openssl-devel //! //! # Alpine Linux //! $ apk add pkgconfig openssl-dev diff --git a/openssl/src/ocsp.rs b/openssl/src/ocsp.rs index 7506d34fb3..93a5d36b7e 100644 --- a/openssl/src/ocsp.rs +++ b/openssl/src/ocsp.rs @@ -15,6 +15,8 @@ use crate::{cvt, cvt_p}; use openssl_macros::corresponds; bitflags! { + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct OcspFlag: c_ulong { const NO_CERTS = ffi::OCSP_NOCERTS; const NO_INTERN = ffi::OCSP_NOINTERN; diff --git a/openssl/src/pkcs7.rs b/openssl/src/pkcs7.rs index ae4571db85..a272c598b8 100644 --- a/openssl/src/pkcs7.rs +++ b/openssl/src/pkcs7.rs @@ -28,6 +28,8 @@ foreign_type_and_impl_send_sync! { } bitflags! { + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct Pkcs7Flags: c_int { const TEXT = ffi::PKCS7_TEXT; const NOCERTS = ffi::PKCS7_NOCERTS; @@ -111,7 +113,7 @@ impl Pkcs7 { certs.as_ptr(), input_bio.as_ptr(), cipher.as_ptr(), - flags.bits, + flags.bits(), )) .map(Pkcs7) } @@ -141,7 +143,7 @@ impl Pkcs7 { pkey.as_ptr(), certs.as_ptr(), input_bio.as_ptr(), - flags.bits, + flags.bits(), )) .map(Pkcs7) } @@ -159,7 +161,7 @@ impl Pkcs7Ref { output.as_ptr(), self.as_ptr(), input_bio.as_ptr(), - flags.bits, + flags.bits(), )) .map(|_| output.get_buf().to_owned()) } @@ -205,7 +207,7 @@ impl Pkcs7Ref { pkey.as_ptr(), cert.as_ptr(), output.as_ptr(), - flags.bits, + flags.bits(), )) .map(|_| output.get_buf().to_owned()) } @@ -241,7 +243,7 @@ impl Pkcs7Ref { store.as_ptr(), indata_bio_ptr, out_bio.as_ptr(), - flags.bits, + flags.bits(), )) .map(|_| ())? } @@ -265,7 +267,7 @@ impl Pkcs7Ref { let ptr = cvt_p(ffi::PKCS7_get0_signers( self.as_ptr(), certs.as_ptr(), - flags.bits, + flags.bits(), ))?; // The returned stack is owned by the caller, but the certs inside are not! Our stack interface can't deal diff --git a/openssl/src/ssl/callbacks.rs b/openssl/src/ssl/callbacks.rs index 091b1fb771..c6414fb517 100644 --- a/openssl/src/ssl/callbacks.rs +++ b/openssl/src/ssl/callbacks.rs @@ -86,6 +86,7 @@ where }; // Give the callback mutable slices into which it can write the identity and psk. let identity_sl = slice::from_raw_parts_mut(identity as *mut u8, max_identity_len as usize); + #[allow(clippy::unnecessary_cast)] let psk_sl = slice::from_raw_parts_mut(psk as *mut u8, max_psk_len as usize); match (*callback)(ssl, hint, identity_sl, psk_sl) { Ok(psk_len) => psk_len as u32, @@ -124,6 +125,7 @@ where Some(CStr::from_ptr(identity).to_bytes()) }; // Give the callback mutable slices into which it can write the psk. + #[allow(clippy::unnecessary_cast)] let psk_sl = slice::from_raw_parts_mut(psk as *mut u8, max_psk_len as usize); match (*callback)(ssl, identity, psk_sl) { Ok(psk_len) => psk_len as u32, @@ -194,6 +196,7 @@ where .ssl_context() .ex_data(SslContext::cached_ex_index::()) .expect("BUG: alpn callback missing") as *const F; + #[allow(clippy::unnecessary_cast)] let protos = slice::from_raw_parts(inbuf as *const u8, inlen as usize); match (*callback)(ssl, protos) { @@ -412,6 +415,7 @@ where .expect("BUG: session context missing") .ex_data(SslContext::cached_ex_index::()) .expect("BUG: get session callback missing") as *const F; + #[allow(clippy::unnecessary_cast)] let data = slice::from_raw_parts(data as *const u8, len as usize); match (*callback)(ssl, data) { @@ -455,6 +459,7 @@ where .ssl_context() .ex_data(SslContext::cached_ex_index::()) .expect("BUG: stateless cookie generate callback missing") as *const F; + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts_mut(cookie as *mut u8, ffi::SSL_COOKIE_LENGTH as usize); match (*callback)(ssl, slice) { Ok(len) => { @@ -482,6 +487,7 @@ where .ssl_context() .ex_data(SslContext::cached_ex_index::()) .expect("BUG: stateless cookie verify callback missing") as *const F; + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts(cookie as *const c_uchar as *const u8, cookie_len); (*callback)(ssl, slice) as c_int } @@ -503,6 +509,7 @@ where .expect("BUG: cookie generate callback missing") as *const F; // We subtract 1 from DTLS1_COOKIE_LENGTH as the ostensible value, 256, is erroneous but retained for // compatibility. See comments in dtls1.h. + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts_mut(cookie as *mut u8, ffi::DTLS1_COOKIE_LENGTH as usize - 1); match (*callback)(ssl, slice) { @@ -542,6 +549,7 @@ where .ssl_context() .ex_data(SslContext::cached_ex_index::()) .expect("BUG: cookie verify callback missing") as *const F; + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts(cookie as *const c_uchar as *const u8, cookie_len as usize); (*callback)(ssl, slice) as c_int @@ -654,6 +662,7 @@ where .ex_data(SslContext::cached_ex_index::()) .expect("BUG: custom ext parse callback missing") as *const F; let ectx = ExtensionContext::from_bits_truncate(context); + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts(input as *const u8, inlen); let cert = if ectx.contains(ExtensionContext::TLS1_3_CERTIFICATE) { Some((chainidx, X509Ref::from_ptr(x))) diff --git a/openssl/src/ssl/mod.rs b/openssl/src/ssl/mod.rs index 27e817f307..bdfbfc14f0 100644 --- a/openssl/src/ssl/mod.rs +++ b/openssl/src/ssl/mod.rs @@ -143,6 +143,8 @@ cfg_if! { bitflags! { /// Options controlling the behavior of an `SslContext`. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct SslOptions: SslOptionsRepr { /// Disables a countermeasure against an SSLv3/TLSv1.0 vulnerability affecting CBC ciphers. const DONT_INSERT_EMPTY_FRAGMENTS = ffi::SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS as SslOptionsRepr; @@ -281,6 +283,8 @@ bitflags! { bitflags! { /// Options controlling the behavior of an `SslContext`. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct SslMode: SslBitType { /// Enables "short writes". /// @@ -378,6 +382,8 @@ unsafe impl Send for SslMethod {} bitflags! { /// Options controlling the behavior of certificate verification. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct SslVerifyMode: i32 { /// Verifies that the peer's certificate is trusted. /// @@ -410,6 +416,8 @@ type SslTimeTy = c_long; bitflags! { /// Options controlling the behavior of session caching. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct SslSessionCacheMode: SslBitType { /// No session caching for the client or server takes place. const OFF = ffi::SSL_SESS_CACHE_OFF; @@ -447,6 +455,8 @@ bitflags! { #[cfg(ossl111)] bitflags! { /// Which messages and under which conditions an extension should be added or expected. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct ExtensionContext: c_uint { /// This extension is only allowed in TLS const TLS_ONLY = ffi::SSL_EXT_TLS_ONLY; @@ -735,7 +745,7 @@ impl SslContextBuilder { #[corresponds(SSL_CTX_set_verify)] pub fn set_verify(&mut self, mode: SslVerifyMode) { unsafe { - ffi::SSL_CTX_set_verify(self.as_ptr(), mode.bits as c_int, None); + ffi::SSL_CTX_set_verify(self.as_ptr(), mode.bits() as c_int, None); } } @@ -752,7 +762,7 @@ impl SslContextBuilder { { unsafe { self.set_ex_data(SslContext::cached_ex_index::(), verify); - ffi::SSL_CTX_set_verify(self.as_ptr(), mode.bits as c_int, Some(raw_verify::)); + ffi::SSL_CTX_set_verify(self.as_ptr(), mode.bits() as c_int, Some(raw_verify::)); } } @@ -839,7 +849,7 @@ impl SslContextBuilder { pub fn set_mode(&mut self, mode: SslMode) -> SslMode { unsafe { let bits = ffi::SSL_CTX_set_mode(self.as_ptr(), mode.bits() as MtuTy) as SslBitType; - SslMode { bits } + SslMode::from_bits_retain(bits) } } @@ -1111,14 +1121,14 @@ impl SslContextBuilder { pub fn set_options(&mut self, option: SslOptions) -> SslOptions { let bits = unsafe { ffi::SSL_CTX_set_options(self.as_ptr(), option.bits()) } as SslOptionsRepr; - SslOptions { bits } + SslOptions::from_bits_retain(bits) } /// Returns the options used by the context. #[corresponds(SSL_CTX_get_options)] pub fn options(&self) -> SslOptions { let bits = unsafe { ffi::SSL_CTX_get_options(self.as_ptr()) } as SslOptionsRepr; - SslOptions { bits } + SslOptions::from_bits_retain(bits) } /// Clears the options used by the context, returning the old set. @@ -1126,7 +1136,7 @@ impl SslContextBuilder { pub fn clear_options(&mut self, option: SslOptions) -> SslOptions { let bits = unsafe { ffi::SSL_CTX_clear_options(self.as_ptr(), option.bits()) } as SslOptionsRepr; - SslOptions { bits } + SslOptions::from_bits_retain(bits) } /// Sets the minimum supported protocol version. @@ -1475,7 +1485,7 @@ impl SslContextBuilder { pub fn set_session_cache_mode(&mut self, mode: SslSessionCacheMode) -> SslSessionCacheMode { unsafe { let bits = ffi::SSL_CTX_set_session_cache_mode(self.as_ptr(), mode.bits()); - SslSessionCacheMode { bits } + SslSessionCacheMode::from_bits_retain(bits) } } @@ -2122,6 +2132,7 @@ impl SslSessionRef { unsafe { let mut len = 0; let p = ffi::SSL_SESSION_get_id(self.as_ptr(), &mut len); + #[allow(clippy::unnecessary_cast)] slice::from_raw_parts(p as *const u8, len as usize) } } @@ -2350,7 +2361,7 @@ impl SslRef { /// [`SslContextBuilder::set_verify`]: struct.SslContextBuilder.html#method.set_verify #[corresponds(SSL_set_verify)] pub fn set_verify(&mut self, mode: SslVerifyMode) { - unsafe { ffi::SSL_set_verify(self.as_ptr(), mode.bits as c_int, None) } + unsafe { ffi::SSL_set_verify(self.as_ptr(), mode.bits() as c_int, None) } } /// Returns the verify mode that was set using `set_verify`. @@ -2371,7 +2382,11 @@ impl SslRef { unsafe { // this needs to be in an Arc since the callback can register a new callback! self.set_ex_data(Ssl::cached_ex_index(), Arc::new(verify)); - ffi::SSL_set_verify(self.as_ptr(), mode.bits as c_int, Some(ssl_raw_verify::)); + ffi::SSL_set_verify( + self.as_ptr(), + mode.bits() as c_int, + Some(ssl_raw_verify::), + ); } } @@ -3718,7 +3733,7 @@ impl SslStream { pub fn get_shutdown(&mut self) -> ShutdownState { unsafe { let bits = ffi::SSL_get_shutdown(self.ssl.as_ptr()); - ShutdownState { bits } + ShutdownState::from_bits_retain(bits) } } @@ -4051,6 +4066,8 @@ pub enum ShutdownResult { bitflags! { /// The shutdown state of a session. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct ShutdownState: c_int { /// A close notify message has been sent to the peer. const SENT = ffi::SSL_SENT_SHUTDOWN; diff --git a/openssl/src/symm.rs b/openssl/src/symm.rs index c1dbdfee7b..7ebb70338e 100644 --- a/openssl/src/symm.rs +++ b/openssl/src/symm.rs @@ -295,7 +295,7 @@ impl Cipher { } /// Requires OpenSSL 1.1.0 or newer. - #[cfg(all(ossl110, not(osslconf = "OPENSSL_NO_CHACHA")))] + #[cfg(all(any(ossl110, libressl360), not(osslconf = "OPENSSL_NO_CHACHA")))] pub fn chacha20_poly1305() -> Cipher { unsafe { Cipher(ffi::EVP_chacha20_poly1305()) } } @@ -1493,7 +1493,7 @@ mod tests { } #[test] - #[cfg(ossl110)] + #[cfg(any(ossl110, libressl360))] fn test_chacha20_poly1305() { let key = "808182838485868788898a8b8c8d8e8f909192939495969798999a9b9c9d9e9f"; let iv = "070000004041424344454647"; diff --git a/openssl/src/x509/mod.rs b/openssl/src/x509/mod.rs index 4325b132e3..24605df806 100644 --- a/openssl/src/x509/mod.rs +++ b/openssl/src/x509/mod.rs @@ -2102,6 +2102,7 @@ impl GeneralNameRef { let ptr = ASN1_STRING_get0_data(d as *mut _); let len = ffi::ASN1_STRING_length(d as *mut _); + #[allow(clippy::unnecessary_cast)] let slice = slice::from_raw_parts(ptr as *const u8, len as usize); // IA5Strings are stated to be ASCII (specifically IA5). Hopefully // OpenSSL checks that when loading a certificate but if not we'll @@ -2155,6 +2156,7 @@ impl GeneralNameRef { let ptr = ASN1_STRING_get0_data(d as *mut _); let len = ffi::ASN1_STRING_length(d as *mut _); + #[allow(clippy::unnecessary_cast)] Some(slice::from_raw_parts(ptr as *const u8, len as usize)) } } diff --git a/openssl/src/x509/verify.rs b/openssl/src/x509/verify.rs index e8481c551c..541cd82663 100644 --- a/openssl/src/x509/verify.rs +++ b/openssl/src/x509/verify.rs @@ -11,6 +11,8 @@ use openssl_macros::corresponds; bitflags! { /// Flags used to check an `X509` certificate. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct X509CheckFlags: c_uint { const ALWAYS_CHECK_SUBJECT = ffi::X509_CHECK_FLAG_ALWAYS_CHECK_SUBJECT; const NO_WILDCARDS = ffi::X509_CHECK_FLAG_NO_WILDCARDS; @@ -28,6 +30,8 @@ bitflags! { bitflags! { /// Flags used to verify an `X509` certificate chain. + #[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] + #[repr(transparent)] pub struct X509VerifyFlags: c_ulong { const CB_ISSUER_CHECK = ffi::X509_V_FLAG_CB_ISSUER_CHECK; const USE_CHECK_TIME = ffi::X509_V_FLAG_USE_CHECK_TIME; @@ -87,14 +91,20 @@ impl X509VerifyParamRef { #[corresponds(X509_VERIFY_PARAM_set_hostflags)] pub fn set_hostflags(&mut self, hostflags: X509CheckFlags) { unsafe { - ffi::X509_VERIFY_PARAM_set_hostflags(self.as_ptr(), hostflags.bits); + ffi::X509_VERIFY_PARAM_set_hostflags(self.as_ptr(), hostflags.bits()); } } /// Set verification flags. #[corresponds(X509_VERIFY_PARAM_set_flags)] pub fn set_flags(&mut self, flags: X509VerifyFlags) -> Result<(), ErrorStack> { - unsafe { cvt(ffi::X509_VERIFY_PARAM_set_flags(self.as_ptr(), flags.bits)).map(|_| ()) } + unsafe { + cvt(ffi::X509_VERIFY_PARAM_set_flags( + self.as_ptr(), + flags.bits(), + )) + .map(|_| ()) + } } /// Clear verification flags. @@ -103,7 +113,7 @@ impl X509VerifyParamRef { unsafe { cvt(ffi::X509_VERIFY_PARAM_clear_flags( self.as_ptr(), - flags.bits, + flags.bits(), )) .map(|_| ()) } @@ -113,7 +123,7 @@ impl X509VerifyParamRef { #[corresponds(X509_VERIFY_PARAM_get_flags)] pub fn flags(&mut self) -> X509VerifyFlags { let bits = unsafe { ffi::X509_VERIFY_PARAM_get_flags(self.as_ptr()) }; - X509VerifyFlags { bits } + X509VerifyFlags::from_bits_retain(bits) } /// Set the expected DNS hostname. @@ -131,6 +141,21 @@ impl X509VerifyParamRef { } } + /// Set the expected email address. + #[corresponds(X509_VERIFY_PARAM_set1_email)] + pub fn set_email(&mut self, email: &str) -> Result<(), ErrorStack> { + unsafe { + // len == 0 means "run strlen" :( + let raw_email = if email.is_empty() { "\0" } else { email }; + cvt(ffi::X509_VERIFY_PARAM_set1_email( + self.as_ptr(), + raw_email.as_ptr() as *const _, + email.len(), + )) + .map(|_| ()) + } + } + /// Set the expected IPv4 or IPv6 address. #[corresponds(X509_VERIFY_PARAM_set1_ip)] pub fn set_ip(&mut self, ip: IpAddr) -> Result<(), ErrorStack> {