• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 use anyhow::Result;
2 use openssl::x509::X509;
3 use std::{collections::HashMap, fmt};
4 
5 use crate::dice::ChainForm;
6 
7 #[derive(Clone, Eq, PartialEq)]
8 pub struct ProtectedData {
9     mac_key: Vec<u8>,
10     dice_chain: ChainForm,
11     uds_certs: Option<UdsCerts>,
12 }
13 
14 #[derive(Clone, Debug, Default, Eq, PartialEq)]
15 pub struct UdsCerts(pub(crate) HashMap<String, UdsCertsEntry>);
16 
17 /// Represent entries in the UDS certs mapping as an enum to support special cases in the future
18 /// where the input is not actually x.509 certs.
19 #[derive(Clone, Eq, PartialEq)]
20 pub enum UdsCertsEntry {
21     /// A chain of X.509 certificates that certify the UDS
22     X509Chain(Vec<Vec<u8>>),
23 }
24 
25 impl ProtectedData {
new(mac_key: Vec<u8>, dice_chain: ChainForm, uds_certs: Option<UdsCerts>) -> Self26     pub fn new(mac_key: Vec<u8>, dice_chain: ChainForm, uds_certs: Option<UdsCerts>) -> Self {
27         Self { mac_key, dice_chain, uds_certs }
28     }
29 }
30 
31 impl UdsCerts {
new() -> Self32     pub fn new() -> Self {
33         Self(HashMap::new())
34     }
35 }
36 
37 impl UdsCertsEntry {
new_x509_chain(der_encoded_chain: Vec<Vec<u8>>) -> Result<Self>38     pub(crate) fn new_x509_chain(der_encoded_chain: Vec<Vec<u8>>) -> Result<Self> {
39         Ok(Self::X509Chain(der_encoded_chain))
40     }
41 }
42 
43 impl fmt::Debug for ProtectedData {
fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result44     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
45         fmt.debug_struct("ProtectedData")
46             .field("mac_key", &hex::encode(&self.mac_key))
47             .field("dice_chain", &self.dice_chain)
48             .field("uds_certs", &self.uds_certs)
49             .finish()
50     }
51 }
52 
53 impl fmt::Debug for UdsCertsEntry {
fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result54     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
55         match self {
56             Self::X509Chain(v) => format_x509_chain(fmt, v),
57         }
58     }
59 }
60 
format_x509_chain(fmt: &mut fmt::Formatter, chain: &Vec<Vec<u8>>) -> fmt::Result61 fn format_x509_chain(fmt: &mut fmt::Formatter, chain: &Vec<Vec<u8>>) -> fmt::Result {
62     for c in chain {
63         fmt.write_str(&x509_der_to_pem(c).unwrap_or("[INVALID CERTIFICATE]".to_string()))?;
64     }
65     Ok(())
66 }
67 
x509_der_to_pem(der: &[u8]) -> Result<String>68 fn x509_der_to_pem(der: &[u8]) -> Result<String> {
69     let utf8 = X509::from_der(der)?.to_pem()?;
70     Ok(std::str::from_utf8(&utf8)?.to_string())
71 }
72