lib/tpm: Walk EFI_CC_FINAL_EVENTS_TABLE on confidential computing platforms
diff --git a/common/lib/tpm.c b/common/lib/tpm.c
index 53ed40fe..ce6f8a02 100644
--- a/common/lib/tpm.c
+++ b/common/lib/tpm.c
@@ -308,4 +308,25 @@ void tpm_release_event_log(void) {
}
}
+void *tpm_get_final_events_table(void) {
+ EFI_GUID guid;
+ if (tcg2 != NULL) {
+ EFI_GUID tcg2_guid = EFI_TCG2_FINAL_EVENTS_TABLE_GUID;
+ guid = tcg2_guid;
+ } else if (cc != NULL) {
+ EFI_GUID cc_guid = EFI_CC_FINAL_EVENTS_TABLE_GUID;
+ guid = cc_guid;
+ } else {
+ return NULL;
+ }
+
+ for (UINTN i = 0; i < gST->NumberOfTableEntries; i++) {
+ if (memcmp(&gST->ConfigurationTable[i].VendorGuid,
+ &guid, sizeof(EFI_GUID)) == 0) {
+ return gST->ConfigurationTable[i].VendorTable;
+ }
+ }
+ return NULL;
+}
+
#endif
diff --git a/common/lib/tpm.h b/common/lib/tpm.h
index 91d81a81..94e5c065 100644
--- a/common/lib/tpm.h
+++ b/common/lib/tpm.h
@@ -41,6 +41,13 @@ void tpm_release_event_log(void);
// digest lists. Returns 0 on malformed input.
uint32_t tpm_calc_event_size(const void *event, const void *header);
+// Locate the firmware's final-events table for the active measurement
+// protocol (EFI_TCG2_FINAL_EVENTS_TABLE_GUID for TCG2, or
+// EFI_CC_FINAL_EVENTS_TABLE_GUID for CC). Both tables share the same
+// {Version, NumberOfEvents, Events[]} layout. Returns NULL if no TPM/CC
+// interface is active or the table isn't present.
+void *tpm_get_final_events_table(void);
+
#endif
#endif
diff --git a/common/protos/linux.c b/common/protos/linux.c
index ae1346fe..4f08b52a 100644
--- a/common/protos/linux.c
+++ b/common/protos/linux.c
@@ -34,19 +34,12 @@ void linux_install_efi_tpm_event_log(void) {
return;
}
- // Walk the firmware's EFI_TCG2_FINAL_EVENTS_TABLE so the kernel can
- // deduplicate any pre-boot events firmware migrated there.
+ // Walk the firmware's final-events table so the kernel can deduplicate
+ // any pre-boot events firmware migrated there. The table is selected
+ // by the active measurement protocol (TCG2 vs CC).
uint32_t final_events_preboot_size = 0;
if (format > EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2) {
- EFI_TCG2_FINAL_EVENTS_TABLE *final_events = NULL;
- EFI_GUID final_events_guid = EFI_TCG2_FINAL_EVENTS_TABLE_GUID;
- for (UINTN i = 0; i < gST->NumberOfTableEntries; i++) {
- if (memcmp(&gST->ConfigurationTable[i].VendorGuid,
- &final_events_guid, sizeof(EFI_GUID)) == 0) {
- final_events = gST->ConfigurationTable[i].VendorTable;
- break;
- }
- }
+ EFI_TCG2_FINAL_EVENTS_TABLE *final_events = tpm_get_final_events_table();
if (final_events != NULL && final_events->NumberOfEvents > 0) {
const uint8_t *base = final_events->Events;
uint64_t remaining = final_events->NumberOfEvents;
