From 68fe08e7d14c0112a673b16340a01d76cb70908f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Carlos=20L=C3=B3pez?= Date: Tue, 7 Jul 2026 12:49:39 +0200 Subject: [PATCH] verify: sev: ensure report signing key is VCEK MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A report can be signed with a number of keys, typically the VCEK. This is encoded in the attestation report itself. Since currently only VCEK is supported, check that the report is in fact signed with the VCEK. Signed-off-by: Carlos López --- src/sev.rs | 30 +++++++++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/src/sev.rs b/src/sev.rs index d52294c..5ccdcd0 100644 --- a/src/sev.rs +++ b/src/sev.rs @@ -1,7 +1,7 @@ // SPDX-License-Identifier: AGPL-3.0-or-later use crate::VerifyOptions; -use anyhow::{Context, Result}; +use anyhow::{Context, Result, bail}; use asn1_rs::{Oid, oid}; use openssl::{ecdsa::EcdsaSig, sha::Sha384}; use sev::certs::snp::{Certificate, Verifiable}; @@ -37,11 +37,39 @@ pub fn parse_report(bytes: &[u8]) -> Result { .map_err(|e| anyhow::anyhow!("Failed to parse SEV report: {:?}", e)) } +#[derive(Clone, Copy, Debug)] +enum SigningKey { + Vcek, + Vlek, + None, + Unknown(u32), +} + +impl From for SigningKey { + fn from(value: u32) -> Self { + match value { + 0 => Self::Vcek, + 1 => Self::Vlek, + 7 => Self::None, + _ => Self::Unknown(value), + } + } +} + pub fn verify_report( report: &AttestationReport, certs_dir: &Path, opts: &VerifyOptions, ) -> Result<()> { + match SigningKey::from(report.key_info.signing_key()) { + SigningKey::Vcek => (), + SigningKey::Vlek => bail!("Cannot verify signature: VLEK is not supported yet"), + SigningKey::None => bail!("Cannot verify signature: report is not signed"), + SigningKey::Unknown(k) => { + bail!("Cannot verify signature: report is signed with unknown key ({k})") + } + } + let ark_path = find_cert_in_dir(certs_dir, "ark")?; let ask_path = find_cert_in_dir(certs_dir, "ask")?; let vcek_path = find_cert_in_dir(certs_dir, "vcek")?;