#include <Library/PerformanceLib.h>\r
#include <Library/MemoryAllocationLib.h>\r
#include <Library/ReportStatusCodeLib.h>\r
+#include <Library/ResetSystemLib.h>\r
#include <Library/Tcg2PhysicalPresenceLib.h>\r
\r
#define PERF_ID_TCG2_PEI 0x3080\r
}\r
\r
/**\r
- Set Tpm2HashMask PCD value according to TPM2 PCR bank.\r
+ Make sure that the current PCR allocations, the TPM supported PCRs,\r
+ and the PcdTpm2HashMask are all in agreement.\r
**/\r
VOID\r
-SetTpm2HashMask (\r
+SyncPcrAllocationsAndPcrMask (\r
VOID\r
)\r
{\r
- EFI_STATUS Status;\r
- UINT32 ActivePcrBanks;\r
- TPML_PCR_SELECTION Pcrs;\r
- UINTN Index;\r
+ EFI_STATUS Status;\r
+ EFI_TCG2_EVENT_ALGORITHM_BITMAP TpmHashAlgorithmBitmap;\r
+ UINT32 TpmActivePcrBanks;\r
+ UINT32 NewTpmActivePcrBanks;\r
+ UINT32 Tpm2PcrMask;\r
+ UINT32 NewTpm2PcrMask;\r
\r
- DEBUG ((EFI_D_ERROR, "SetTpm2HashMask!\n"));\r
+ DEBUG ((EFI_D_ERROR, "SyncPcrAllocationsAndPcrMask!\n"));\r
\r
- Status = Tpm2GetCapabilityPcrs (&Pcrs);\r
- if (EFI_ERROR (Status)) {\r
- DEBUG ((EFI_D_ERROR, "Tpm2GetCapabilityPcrs fail!\n"));\r
- ActivePcrBanks = EFI_TCG2_BOOT_HASH_ALG_SHA1;\r
- } else {\r
- DEBUG ((EFI_D_INFO, "Tpm2GetCapabilityPcrs Count - %08x\n", Pcrs.count));\r
- ActivePcrBanks = 0;\r
- for (Index = 0; Index < Pcrs.count; Index++) {\r
- DEBUG ((EFI_D_INFO, "hash - %x\n", Pcrs.pcrSelections[Index].hash));\r
- switch (Pcrs.pcrSelections[Index].hash) {\r
- case TPM_ALG_SHA1:\r
- if (!IsZeroBuffer (Pcrs.pcrSelections[Index].pcrSelect, Pcrs.pcrSelections[Index].sizeofSelect)) {\r
- ActivePcrBanks |= EFI_TCG2_BOOT_HASH_ALG_SHA1;\r
- } \r
- break;\r
- case TPM_ALG_SHA256:\r
- if (!IsZeroBuffer (Pcrs.pcrSelections[Index].pcrSelect, Pcrs.pcrSelections[Index].sizeofSelect)) {\r
- ActivePcrBanks |= EFI_TCG2_BOOT_HASH_ALG_SHA256;\r
- }\r
- break;\r
- case TPM_ALG_SHA384:\r
- if (!IsZeroBuffer (Pcrs.pcrSelections[Index].pcrSelect, Pcrs.pcrSelections[Index].sizeofSelect)) {\r
- ActivePcrBanks |= EFI_TCG2_BOOT_HASH_ALG_SHA384;\r
- }\r
- break;\r
- case TPM_ALG_SHA512:\r
- if (!IsZeroBuffer (Pcrs.pcrSelections[Index].pcrSelect, Pcrs.pcrSelections[Index].sizeofSelect)) {\r
- ActivePcrBanks |= EFI_TCG2_BOOT_HASH_ALG_SHA512;\r
- }\r
- break;\r
- case TPM_ALG_SM3_256:\r
- if (!IsZeroBuffer (Pcrs.pcrSelections[Index].pcrSelect, Pcrs.pcrSelections[Index].sizeofSelect)) {\r
- ActivePcrBanks |= EFI_TCG2_BOOT_HASH_ALG_SM3_256;\r
- }\r
- break;\r
+ //\r
+ // Determine the current TPM support and the Platform PCR mask.\r
+ //\r
+ Status = Tpm2GetCapabilitySupportedAndActivePcrs (&TpmHashAlgorithmBitmap, &TpmActivePcrBanks);\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ Tpm2PcrMask = PcdGet32 (PcdTpm2HashMask);\r
+\r
+ //\r
+ // Find the intersection of Pcd support and TPM support.\r
+ // If banks are missing from the TPM support that are in the PCD, update the PCD.\r
+ // If banks are missing from the PCD that are active in the TPM, reallocate the banks and reboot.\r
+ //\r
+\r
+ //\r
+ // If there are active PCR banks that are not supported by the Platform mask,\r
+ // update the TPM allocations and reboot the machine.\r
+ //\r
+ if ((TpmActivePcrBanks & Tpm2PcrMask) != TpmActivePcrBanks) {\r
+ NewTpmActivePcrBanks = TpmActivePcrBanks & Tpm2PcrMask;\r
+\r
+ DEBUG ((EFI_D_INFO, __FUNCTION__" - Reallocating PCR banks from 0x%X to 0x%X.\n", TpmActivePcrBanks, NewTpmActivePcrBanks ));\r
+ if (NewTpmActivePcrBanks == 0) {\r
+ DEBUG ((EFI_D_ERROR, __FUNCTION__" - No viable PCRs active! Please set a less restrictive value for PcdTpm2HashMask!\n"));\r
+ ASSERT (FALSE);\r
+ } else {\r
+ Status = Tpm2PcrAllocateBanks (NULL, (UINT32)TpmHashAlgorithmBitmap, NewTpmActivePcrBanks);\r
+ if (EFI_ERROR (Status)) {\r
+ //\r
+ // We can't do much here, but we hope that this doesn't happen.\r
+ //\r
+ DEBUG ((EFI_D_ERROR, __FUNCTION__" - Failed to reallocate PCRs!\n"));\r
+ ASSERT_EFI_ERROR (Status);\r
}\r
+ //\r
+ // Need reset system, since we just called Tpm2PcrAllocateBanks().\r
+ //\r
+ ResetCold();\r
}\r
}\r
- Status = PcdSet32S (PcdTpm2HashMask, ActivePcrBanks);\r
- ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // If there are any PCRs that claim support in the Platform mask that are\r
+ // not supported by the TPM, update the mask.\r
+ //\r
+ if ((Tpm2PcrMask & TpmHashAlgorithmBitmap) != Tpm2PcrMask) {\r
+ NewTpm2PcrMask = Tpm2PcrMask & TpmHashAlgorithmBitmap;\r
+\r
+ DEBUG ((EFI_D_INFO, __FUNCTION__" - Updating PcdTpm2HashMask from 0x%X to 0x%X.\n", Tpm2PcrMask, NewTpm2PcrMask ));\r
+ if (NewTpm2PcrMask == 0) {\r
+ DEBUG ((EFI_D_ERROR, __FUNCTION__" - No viable PCRs supported! Please set a less restrictive value for PcdTpm2HashMask!\n"));\r
+ ASSERT (FALSE);\r
+ }\r
+\r
+ Status = PcdSet32S (PcdTpm2HashMask, NewTpm2PcrMask);\r
+ ASSERT_EFI_ERROR (Status);\r
+ }\r
}\r
\r
/**\r
//\r
// Update Tpm2HashMask according to PCR bank.\r
//\r
- SetTpm2HashMask ();\r
+ SyncPcrAllocationsAndPcrMask ();\r
\r
if (S3ErrorReport) {\r
//\r