Merge pull request #871 from sfackler/tweaks

Tweak verify_cert's signature
This commit is contained in:
Steven Fackler 2018-03-11 14:15:21 -07:00 committed by GitHub
commit f2575138eb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 40 additions and 36 deletions

View File

@ -122,22 +122,33 @@ impl X509StoreContextRef {
/// ///
/// [`X509_STORE_CTX_init`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_STORE_CTX_init.html /// [`X509_STORE_CTX_init`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_STORE_CTX_init.html
/// [`X509_STORE_CTX_cleanup`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_STORE_CTX_cleanup.html /// [`X509_STORE_CTX_cleanup`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_STORE_CTX_cleanup.html
pub fn init<F, T>(&mut self, trust: &store::X509StoreRef, cert: &X509Ref, pub fn init<F, T>(
cert_chain: &StackRef<X509>, with_context: F) -> Result<T, ErrorStack> &mut self,
trust: &store::X509StoreRef,
cert: &X509Ref,
cert_chain: &StackRef<X509>,
with_context: F,
) -> Result<T, ErrorStack>
where where
F: FnOnce(&mut X509StoreContextRef) -> Result<T, ErrorStack> F: FnOnce(&mut X509StoreContextRef) -> Result<T, ErrorStack>,
{ {
struct Cleanup<'a>(&'a mut X509StoreContextRef); struct Cleanup<'a>(&'a mut X509StoreContextRef);
impl<'a> Drop for Cleanup<'a> { impl<'a> Drop for Cleanup<'a> {
fn drop(&mut self) { fn drop(&mut self) {
self.0.cleanup(); unsafe {
ffi::X509_STORE_CTX_cleanup(self.0.as_ptr());
}
} }
} }
unsafe { unsafe {
cvt(ffi::X509_STORE_CTX_init(self.as_ptr(), trust.as_ptr(), cvt(ffi::X509_STORE_CTX_init(
cert.as_ptr(), cert_chain.as_ptr()))?; self.as_ptr(),
trust.as_ptr(),
cert.as_ptr(),
cert_chain.as_ptr(),
))?;
let cleanup = Cleanup(self); let cleanup = Cleanup(self);
with_context(cleanup.0) with_context(cleanup.0)
@ -145,30 +156,17 @@ impl X509StoreContextRef {
} }
/// Verifies the stored certificate. /// Verifies the stored certificate.
/// It is required to call `init` in beforehand, to initialize the required values. ///
/// Returns `true` if verification succeeds. The `error` method will return the specific
/// validation error if the certificate was not valid.
///
/// This will only work inside of a call to `init`.
/// ///
/// This corresponds to [`X509_verify_cert`]. /// This corresponds to [`X509_verify_cert`].
/// ///
/// [`X509_verify_cert`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_verify_cert.html /// [`X509_verify_cert`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_verify_cert.html
/// pub fn verify_cert(&mut self) -> Result<bool, ErrorStack> {
/// # Result unsafe { cvt_n(ffi::X509_verify_cert(self.as_ptr())).map(|n| n != 0) }
///
/// The Result must be `Ok(())` to be a valid certificate, otherwise the cert is not valid.
pub fn verify_cert(&mut self) -> Result<(), ErrorStack> {
unsafe {
cvt(ffi::X509_verify_cert(self.as_ptr())).map(|_| ())
}
}
/// Cleans-up the context.
///
/// This corresponds to [`X509_STORE_CTX_cleanup`].
///
/// [`X509_STORE_CTX_cleanup`]: https://www.openssl.org/docs/man1.0.2/crypto/X509_STORE_CTX_cleanup.html
fn cleanup(&mut self) {
unsafe {
ffi::X509_STORE_CTX_cleanup(self.as_ptr());
}
} }
/// Set the error code of the context. /// Set the error code of the context.

View File

@ -7,7 +7,7 @@ use nid::Nid;
use pkey::{PKey, Private}; use pkey::{PKey, Private};
use rsa::Rsa; use rsa::Rsa;
use stack::Stack; use stack::Stack;
use x509::{X509, X509Name, X509Req, X509VerifyResult, X509StoreContext}; use x509::{X509, X509Name, X509Req, X509StoreContext, X509VerifyResult};
use x509::extension::{AuthorityKeyIdentifier, BasicConstraints, ExtendedKeyUsage, KeyUsage, use x509::extension::{AuthorityKeyIdentifier, BasicConstraints, ExtendedKeyUsage, KeyUsage,
SubjectAlternativeName, SubjectKeyIdentifier}; SubjectAlternativeName, SubjectKeyIdentifier};
use x509::store::X509StoreBuilder; use x509::store::X509StoreBuilder;
@ -242,15 +242,11 @@ fn test_stack_from_pem() {
assert_eq!(certs.len(), 2); assert_eq!(certs.len(), 2);
assert_eq!( assert_eq!(
hex::encode(certs[0] hex::encode(certs[0].fingerprint(MessageDigest::sha1()).unwrap()),
.fingerprint(MessageDigest::sha1())
.unwrap()),
"59172d9313e84459bcff27f967e79e6e9217e584" "59172d9313e84459bcff27f967e79e6e9217e584"
); );
assert_eq!( assert_eq!(
hex::encode(certs[1] hex::encode(certs[1].fingerprint(MessageDigest::sha1()).unwrap()),
.fingerprint(MessageDigest::sha1())
.unwrap()),
"c0cbdf7cdd03c9773e5468e1f6d2da7d5cbb1875" "c0cbdf7cdd03c9773e5468e1f6d2da7d5cbb1875"
); );
} }
@ -306,8 +302,16 @@ fn test_verify_cert() {
let store = store_bldr.build(); let store = store_bldr.build();
let mut context = X509StoreContext::new().unwrap(); let mut context = X509StoreContext::new().unwrap();
assert!(context.init(&store, &cert, &chain, |c| c.verify_cert()).is_ok()); assert!(
assert!(context.init(&store, &cert, &chain, |c| c.verify_cert()).is_ok()); context
.init(&store, &cert, &chain, |c| c.verify_cert())
.unwrap()
);
assert!(
context
.init(&store, &cert, &chain, |c| c.verify_cert())
.unwrap()
);
} }
#[test] #[test]
@ -323,5 +327,7 @@ fn test_verify_fails() {
let store = store_bldr.build(); let store = store_bldr.build();
let mut context = X509StoreContext::new().unwrap(); let mut context = X509StoreContext::new().unwrap();
assert!(context.init(&store, &cert, &chain, |c| c.verify_cert()).is_err()); assert!(!context
.init(&store, &cert, &chain, |c| c.verify_cert())
.unwrap());
} }