az_snp_vtpm/lib.rs
1// Copyright (c) Microsoft Corporation.
2// Licensed under the MIT License.
3
4//! This library enables guest attestation flows for [SEV-SNP CVMs on Azure](https://learn.microsoft.com/en-us/azure/confidential-computing/confidential-vm-overview). Please refer to the documentation in [this repository](https://github.com/Azure/confidential-computing-cvm-guest-attestation) for details on the attestation procedure.
5//!
6//! # SNP Report Validation
7//!
8//! The following code will retrieve an SNP report from the vTPM device, parse it, and validate it against the AMD certificate chain. Finally it will verify that a hash of a raw HCL report's Variable Data is equal to the `report_data` field in an embedded [Attestation Report](sev::firmware::guest::AttestationReport) structure.
9//!
10//! #
11//! ```no_run
12//! use az_snp_vtpm::{amd_kds, hcl, vtpm};
13//! use az_snp_vtpm::report::{AttestationReport, Validateable};
14//! use std::error::Error;
15//!
16//! fn main() -> Result<(), Box<dyn Error>> {
17//! let bytes = vtpm::get_report()?;
18//! let hcl_report = hcl::HclReport::new(bytes)?;
19//! let var_data_hash = hcl_report.var_data_sha256();
20//! let snp_report: AttestationReport = hcl_report.try_into()?;
21//!
22//! let vcek = amd_kds::get_vcek(&snp_report)?;
23//! let cert_chain = amd_kds::get_cert_chain()?;
24//!
25//! cert_chain.validate()?;
26//! vcek.validate(&cert_chain)?;
27//! snp_report.validate(&vcek)?;
28//!
29//! if var_data_hash != snp_report.report_data[..32] {
30//! return Err("var_data_hash mismatch".into());
31//! }
32//!
33//! Ok(())
34//! }
35//! ```
36
37pub use az_cvm_vtpm::{hcl, vtpm};
38use thiserror::Error;
39
40#[derive(Error, Debug)]
41pub enum HttpError {
42 #[error("HTTP error")]
43 Http(#[from] Box<ureq::Error>),
44 #[error("failed to read HTTP response")]
45 Io(#[from] std::io::Error),
46}
47
48/// Determines if the current VM is an SEV-SNP CVM.
49/// Returns `Ok(true)` if the VM is an SEV-SNP CVM, `Ok(false)` if it is not,
50/// and `Err` if an error occurs.
51pub fn is_snp_cvm() -> Result<bool, vtpm::ReportError> {
52 let bytes = vtpm::get_report()?;
53 let Ok(hcl_report) = hcl::HclReport::new(bytes) else {
54 return Ok(false);
55 };
56 let is_snp = hcl_report.report_type() == hcl::ReportType::Snp;
57 Ok(is_snp)
58}
59
60#[cfg(feature = "verifier")]
61pub mod amd_kds;
62#[cfg(feature = "verifier")]
63pub mod certs;
64#[cfg(feature = "attester")]
65pub mod imds;
66pub mod report;