Files
s390-tools/rust/pv/openssl_extensions/src/akid.rs
Steffen Eiden 02dded11a5 rust/pv: Replace libc wherever possible
Replace all libc references to rust-std references if available.
This eliminates the need to include libc in the pv crate.
However, pv_base still refers to libc::ioctl and libc::ENOTTY.

Reviewed-by: Marc Hartmayer <mhartmay@linux.ibm.com>
Signed-off-by: Steffen Eiden <seiden@linux.ibm.com>
Signed-off-by: Jan Höppner <hoeppner@linux.ibm.com>
2024-02-02 16:11:21 +01:00

121 lines
3.0 KiB
Rust

// SPDX-License-Identifier: MIT
//
// Copyright IBM Corp. 2023
use std::fmt;
use foreign_types::{foreign_type, ForeignType, ForeignTypeRef};
use openssl::x509::{X509CrlRef, X509Ref};
use std::ffi::c_int;
mod ffi {
extern "C" {
pub fn X509_check_akid(
issuer: *const openssl_sys::X509,
akid: *const openssl_sys::AUTHORITY_KEYID,
) -> super::c_int;
}
}
foreign_type! {
type CType = openssl_sys::AUTHORITY_KEYID;
fn drop = openssl_sys::AUTHORITY_KEYID_free;
/// An `Authority Key Identifier`.
pub struct Akid;
/// Reference to `Akid`
pub struct AkidRef;
}
#[derive(Copy, Clone, PartialEq, Eq)]
pub struct AkidCheckResult(c_int);
impl fmt::Debug for AkidCheckResult {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt.debug_struct("AkidCheckResult")
.field("code", &self.0)
.finish()
}
}
impl AkidCheckResult {
/// Creates an `AkidCheckResult` from a raw error number.
unsafe fn from_raw(err: c_int) -> AkidCheckResult {
AkidCheckResult(err)
}
pub const OK: AkidCheckResult = AkidCheckResult(openssl_sys::X509_V_OK);
pub const ERR_AKID_ISSUER_SERIAL_MISMATCH: AkidCheckResult =
AkidCheckResult(openssl_sys::X509_V_ERR_AKID_ISSUER_SERIAL_MISMATCH);
pub const ERR_AKID_SKID_MISMATCH: AkidCheckResult =
AkidCheckResult(openssl_sys::X509_V_ERR_AKID_SKID_MISMATCH);
}
impl AkidRef {
///Check if the `Akid` matches the issuer
///
pub fn check(&self, issuer: &X509Ref) -> AkidCheckResult {
unsafe {
let res = ffi::X509_check_akid(issuer.as_ptr(), self.as_ptr());
AkidCheckResult::from_raw(res)
}
}
}
pub trait AkidExtension {
fn akid(&self) -> Option<Akid>;
}
impl AkidExtension for X509Ref {
fn akid(&self) -> Option<Akid> {
unsafe {
let ptr = openssl_sys::X509_get_ext_d2i(
self.as_ptr(),
openssl_sys::NID_authority_key_identifier,
std::ptr::null_mut(),
std::ptr::null_mut(),
);
if ptr.is_null() {
None
} else {
Some(Akid::from_ptr(ptr as *mut _))
}
}
}
}
impl AkidExtension for X509CrlRef {
fn akid(&self) -> Option<Akid> {
unsafe {
let ptr = openssl_sys::X509_CRL_get_ext_d2i(
self.as_ptr(),
openssl_sys::NID_authority_key_identifier,
std::ptr::null_mut(),
std::ptr::null_mut(),
);
if ptr.is_null() {
None
} else {
Some(Akid::from_ptr(ptr as *mut _))
}
}
}
}
#[cfg(test)]
mod test {
use crate::test_utils::load_gen_cert;
use super::*;
#[test]
fn akid() {
let cert = load_gen_cert("ibm.crt");
let ca = load_gen_cert("root_ca.crt");
let akid = cert.akid().unwrap();
let res = akid.check(&ca);
assert_eq!(res, AkidCheckResult::OK);
}
}