Skip to content

Commit

Permalink
[update] Add MLDSA key revocation to the verifier (#1869)
Browse files Browse the repository at this point in the history
This change adds the MLDSA key revocation logic to the verifier.
  • Loading branch information
mhatrevi authored Jan 3, 2025
1 parent f2a6bf5 commit 7ce9cc4
Show file tree
Hide file tree
Showing 7 changed files with 44 additions and 23 deletions.
5 changes: 5 additions & 0 deletions common/src/verifier.rs
Original file line number Diff line number Diff line change
Expand Up @@ -137,6 +137,11 @@ impl<'a, 'b> ImageVerificationEnv for &mut FirmwareImageVerificationEnv<'a, 'b>
self.soc_ifc.fuse_bank().vendor_lms_pub_key_revocation()
}

/// Retrieve Vendor MLDSA Public Key Revocation Bitmask
fn vendor_mldsa_pub_key_revocation(&self) -> u32 {
self.soc_ifc.fuse_bank().vendor_mldsa_pub_key_revocation()
}

/// Retrieve Owner Public Key Digest from fuses
fn owner_pub_key_digest_fuses(&self) -> ImageDigest384 {
self.soc_ifc.fuse_bank().owner_pub_key_hash().into()
Expand Down
4 changes: 2 additions & 2 deletions error/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,7 @@ impl CaliptraError {
CaliptraError::new_const(0x000b0030);
pub const IMAGE_VERIFIER_ERR_VENDOR_LMS_VERIFY_FAILURE: CaliptraError =
CaliptraError::new_const(0x000b0031);
pub const IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_INDEX_OUT_OF_BOUNDS: CaliptraError =
pub const IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_INDEX_OUT_OF_BOUNDS: CaliptraError =
CaliptraError::new_const(0x000b0032);
pub const IMAGE_VERIFIER_ERR_VENDOR_LMS_SIGNATURE_INVALID: CaliptraError =
CaliptraError::new_const(0x000b0033);
Expand All @@ -250,7 +250,7 @@ impl CaliptraError {
CaliptraError::new_const(0x000b0036);
pub const IMAGE_VERIFIER_ERR_OWNER_LMS_SIGNATURE_INVALID: CaliptraError =
CaliptraError::new_const(0x000b0038);
pub const IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_REVOKED: CaliptraError =
pub const IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_REVOKED: CaliptraError =
CaliptraError::new_const(0x000b0003a);
pub const IMAGE_VERIFIER_ERR_FMC_SIZE_ZERO: CaliptraError =
CaliptraError::new_const(0x000b003b);
Expand Down
3 changes: 3 additions & 0 deletions image/verify/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,9 @@ pub trait ImageVerificationEnv {
/// Get Vendor LMS Public Key Revocation list
fn vendor_lms_pub_key_revocation(&self) -> u32;

/// Get Vendor MLDSA Public Key Revocation list
fn vendor_mldsa_pub_key_revocation(&self) -> u32;

/// Get Owner Public Key Digest from fuses
fn owner_pub_key_digest_fuses(&self) -> ImageDigest384;

Expand Down
40 changes: 24 additions & 16 deletions image/verify/src/verifier.rs
Original file line number Diff line number Diff line change
Expand Up @@ -240,13 +240,14 @@ impl<Env: ImageVerificationEnv> ImageVerifier<Env> {
vendor_pqc_info = PqcKeyInfo::Lms(lms_pub_key, lms_sig);

// Verify the vendor LMS public key index and revocation status
let (vendor_pqc_pub_key_idx, vendor_lms_pub_key_revocation) =
self.verify_vendor_lms_pk_idx(preamble, reason)?;
let key_revocation = self.env.vendor_lms_pub_key_revocation();
let vendor_pqc_pub_key_idx =
self.verify_vendor_pqc_pk_idx(preamble, reason, key_revocation)?;

// Return the public key index information
PubKeyIndexInfo {
key_idx: vendor_pqc_pub_key_idx,
key_revocation: vendor_lms_pub_key_revocation,
key_revocation,
}
}
FwVerificationPqcKeyType::MLDSA => {
Expand All @@ -261,12 +262,15 @@ impl<Env: ImageVerificationEnv> ImageVerifier<Env> {

vendor_pqc_info = PqcKeyInfo::Mldsa(mldsa_pub_key, mldsa_sig);

// [TODO][CAP2] Verify the vendor MLDSA public key index and revocation status
// Verify the vendor MLDSA public key index and revocation status
let key_revocation = self.env.vendor_mldsa_pub_key_revocation();
let vendor_pqc_pub_key_idx =
self.verify_vendor_pqc_pk_idx(preamble, reason, key_revocation)?;

// Return the public key index information
PubKeyIndexInfo {
key_idx: 0,
key_revocation: 0,
key_idx: vendor_pqc_pub_key_idx,
key_revocation,
}
}
};
Expand Down Expand Up @@ -367,14 +371,14 @@ impl<Env: ImageVerificationEnv> ImageVerifier<Env> {
Ok((key_idx, revocation))
}

/// Verify Vendor LMS Public Key Index
fn verify_vendor_lms_pk_idx(
/// Verify Vendor PQC (LMS or MLDSA) Public Key Index
fn verify_vendor_pqc_pk_idx(
&mut self,
preamble: &ImagePreamble,
reason: ResetReason,
) -> CaliptraResult<(u32, u32)> {
revocation: u32,
) -> CaliptraResult<u32> {
let key_idx = preamble.vendor_pqc_pub_key_idx;
let revocation = self.env.vendor_lms_pub_key_revocation();
let key_hash_count = preamble
.vendor_pub_key_info
.pqc_key_descriptor
Expand All @@ -383,14 +387,14 @@ impl<Env: ImageVerificationEnv> ImageVerifier<Env> {

// Check if the key index is within bounds.
if key_idx > last_key_idx {
Err(CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_INDEX_OUT_OF_BOUNDS)?;
Err(CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_INDEX_OUT_OF_BOUNDS)?;
}

// Check if key idx is the last key index. Last key index is never revoked.
if key_idx == last_key_idx {
cfi_assert_eq(cfi_launder(key_idx), last_key_idx);
} else if (cfi_launder(revocation) & (0x01u32 << key_idx)) != 0 {
Err(CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_REVOKED)?;
Err(CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_REVOKED)?;
} else {
cfi_assert_eq(revocation & (0x01u32 << key_idx), 0);
}
Expand All @@ -408,7 +412,7 @@ impl<Env: ImageVerificationEnv> ImageVerifier<Env> {
cfi_assert_ne(reason, ResetReason::UpdateReset);
}

Ok((key_idx, revocation))
Ok(key_idx)
}

/// Verify vendor public key info digest
Expand Down Expand Up @@ -2217,7 +2221,7 @@ mod tests {
verify_pqc_result: bool,
vendor_pub_key_digest: ImageDigest384,
vendor_ecc_pub_key_revocation: VendorPubKeyRevocation,
vendor_lms_pub_key_revocation: u32,
vendor_pqc_pub_key_revocation: u32,
owner_pub_key_digest: ImageDigest384,
lifecycle: Lifecycle,
}
Expand All @@ -2232,7 +2236,7 @@ mod tests {
verify_pqc_result: false,
vendor_pub_key_digest: ImageDigest384::default(),
vendor_ecc_pub_key_revocation: VendorPubKeyRevocation::default(),
vendor_lms_pub_key_revocation: 0,
vendor_pqc_pub_key_revocation: 0,
owner_pub_key_digest: ImageDigest384::default(),
lifecycle: Lifecycle::Unprovisioned,
}
Expand Down Expand Up @@ -2296,7 +2300,11 @@ mod tests {
}

fn vendor_lms_pub_key_revocation(&self) -> u32 {
self.vendor_lms_pub_key_revocation
self.vendor_pqc_pub_key_revocation
}

fn vendor_mldsa_pub_key_revocation(&self) -> u32 {
self.vendor_pqc_pub_key_revocation
}

fn owner_pub_key_digest_fuses(&self) -> ImageDigest384 {
Expand Down
5 changes: 5 additions & 0 deletions rom/dev/src/flow/fake.rs
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,11 @@ impl<'a, 'b> ImageVerificationEnv for &mut FakeRomImageVerificationEnv<'a, 'b> {
self.soc_ifc.fuse_bank().vendor_lms_pub_key_revocation()
}

/// Retrieve Vendor MLDSA Public Key Revocation Bitmask
fn vendor_mldsa_pub_key_revocation(&self) -> u32 {
self.soc_ifc.fuse_bank().vendor_mldsa_pub_key_revocation()
}

/// Retrieve Owner Public Key Digest from fuses
fn owner_pub_key_digest_fuses(&self) -> ImageDigest384 {
self.soc_ifc.fuse_bank().owner_pub_key_hash().into()
Expand Down
6 changes: 3 additions & 3 deletions rom/dev/tests/rom_integration_tests/test_image_validation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -291,7 +291,7 @@ fn test_preamble_vendor_lms_pubkey_revocation() {
} else {
assert_eq!(
ModelError::MailboxCmdFailed(
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_REVOKED.into()
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_REVOKED.into()
),
hw.upload_firmware(&image_bundle.to_bytes().unwrap())
.unwrap_err()
Expand Down Expand Up @@ -331,7 +331,7 @@ fn test_preamble_vendor_lms_pubkey_out_of_bounds() {

assert_eq!(
ModelError::MailboxCmdFailed(
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_INDEX_OUT_OF_BOUNDS.into()
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_INDEX_OUT_OF_BOUNDS.into()
),
hw.upload_firmware(&image_bundle.to_bytes().unwrap())
.unwrap_err()
Expand Down Expand Up @@ -2488,7 +2488,7 @@ fn test_preamble_vendor_mldsa_pubkey_out_of_bounds() {
hw.upload_firmware(&image_bundle.to_bytes().unwrap())
.unwrap_err(),
ModelError::MailboxCmdFailed(
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_INDEX_OUT_OF_BOUNDS.into()
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_INDEX_OUT_OF_BOUNDS.into()
)
);
}
4 changes: 2 additions & 2 deletions test/tests/fips_test_suite/fw_load.rs
Original file line number Diff line number Diff line change
Expand Up @@ -990,7 +990,7 @@ fn fw_load_error_vendor_lms_pub_key_index_out_of_bounds() {
fw_load_error_flow(
Some(fw_image),
Some(fuses),
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_INDEX_OUT_OF_BOUNDS.into(),
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_INDEX_OUT_OF_BOUNDS.into(),
);
}

Expand Down Expand Up @@ -1109,7 +1109,7 @@ fn fw_load_error_vendor_lms_pub_key_revoked() {
fw_load_error_flow(
Some(fw_image),
Some(fuses),
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_LMS_PUB_KEY_REVOKED.into(),
CaliptraError::IMAGE_VERIFIER_ERR_VENDOR_PQC_PUB_KEY_REVOKED.into(),
);
}

Expand Down

0 comments on commit 7ce9cc4

Please sign in to comment.