2 This module implements Tcg2 Protocol.
4 Copyright (c) 2015 - 2017, Intel Corporation. All rights reserved.<BR>
5 (C) Copyright 2016 Hewlett Packard Enterprise Development LP<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
17 #include <IndustryStandard/Acpi.h>
18 #include <IndustryStandard/PeImage.h>
19 #include <IndustryStandard/TcpaAcpi.h>
21 #include <Guid/GlobalVariable.h>
22 #include <Guid/HobList.h>
23 #include <Guid/TcgEventHob.h>
24 #include <Guid/EventGroup.h>
25 #include <Guid/EventExitBootServiceFailed.h>
26 #include <Guid/ImageAuthentication.h>
27 #include <Guid/TpmInstance.h>
29 #include <Protocol/DevicePath.h>
30 #include <Protocol/MpService.h>
31 #include <Protocol/VariableWrite.h>
32 #include <Protocol/Tcg2Protocol.h>
33 #include <Protocol/TrEEProtocol.h>
35 #include <Library/DebugLib.h>
36 #include <Library/BaseMemoryLib.h>
37 #include <Library/UefiRuntimeServicesTableLib.h>
38 #include <Library/UefiDriverEntryPoint.h>
39 #include <Library/HobLib.h>
40 #include <Library/UefiBootServicesTableLib.h>
41 #include <Library/BaseLib.h>
42 #include <Library/MemoryAllocationLib.h>
43 #include <Library/PrintLib.h>
44 #include <Library/Tpm2CommandLib.h>
45 #include <Library/PcdLib.h>
46 #include <Library/UefiLib.h>
47 #include <Library/Tpm2DeviceLib.h>
48 #include <Library/HashLib.h>
49 #include <Library/PerformanceLib.h>
50 #include <Library/ReportStatusCodeLib.h>
51 #include <Library/Tcg2PhysicalPresenceLib.h>
53 #define PERF_ID_TCG2_DXE 0x3120
60 #define TCG2_DEFAULT_MAX_COMMAND_SIZE 0x1000
61 #define TCG2_DEFAULT_MAX_RESPONSE_SIZE 0x1000
65 EFI_TCG2_EVENT_LOG_FORMAT LogFormat
;
66 } TCG2_EVENT_INFO_STRUCT
;
68 TCG2_EVENT_INFO_STRUCT mTcg2EventInfo
[] = {
69 {&gTcgEventEntryHobGuid
, EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
},
70 {&gTcgEvent2EntryHobGuid
, EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
},
73 #define TCG_EVENT_LOG_AREA_COUNT_MAX 2
76 EFI_TCG2_EVENT_LOG_FORMAT EventLogFormat
;
77 EFI_PHYSICAL_ADDRESS Lasa
;
81 BOOLEAN EventLogStarted
;
82 BOOLEAN EventLogTruncated
;
83 } TCG_EVENT_LOG_AREA_STRUCT
;
85 typedef struct _TCG_DXE_DATA
{
86 EFI_TCG2_BOOT_SERVICE_CAPABILITY BsCap
;
87 TCG_EVENT_LOG_AREA_STRUCT EventLogAreaStruct
[TCG_EVENT_LOG_AREA_COUNT_MAX
];
88 BOOLEAN GetEventLogCalled
[TCG_EVENT_LOG_AREA_COUNT_MAX
];
89 TCG_EVENT_LOG_AREA_STRUCT FinalEventLogAreaStruct
[TCG_EVENT_LOG_AREA_COUNT_MAX
];
90 EFI_TCG2_FINAL_EVENTS_TABLE
*FinalEventsTable
[TCG_EVENT_LOG_AREA_COUNT_MAX
];
93 TCG_DXE_DATA mTcgDxeData
= {
95 sizeof (EFI_TCG2_BOOT_SERVICE_CAPABILITY
), // Size
96 { 1, 1 }, // StructureVersion
97 { 1, 1 }, // ProtocolVersion
98 EFI_TCG2_BOOT_HASH_ALG_SHA1
, // HashAlgorithmBitmap
99 EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
, // SupportedEventLogs
100 TRUE
, // TPMPresentFlag
101 TCG2_DEFAULT_MAX_COMMAND_SIZE
, // MaxCommandSize
102 TCG2_DEFAULT_MAX_RESPONSE_SIZE
, // MaxResponseSize
104 0, // NumberOfPCRBanks
109 UINTN mBootAttempts
= 0;
110 CHAR16 mBootVarName
[] = L
"BootOrder";
112 VARIABLE_TYPE mVariableType
[] = {
113 {EFI_SECURE_BOOT_MODE_NAME
, &gEfiGlobalVariableGuid
},
114 {EFI_PLATFORM_KEY_NAME
, &gEfiGlobalVariableGuid
},
115 {EFI_KEY_EXCHANGE_KEY_NAME
, &gEfiGlobalVariableGuid
},
116 {EFI_IMAGE_SECURITY_DATABASE
, &gEfiImageSecurityDatabaseGuid
},
117 {EFI_IMAGE_SECURITY_DATABASE1
, &gEfiImageSecurityDatabaseGuid
},
120 EFI_HANDLE mImageHandle
;
123 Measure PE image into TPM log based on the authenticode image hashing in
124 PE/COFF Specification 8.0 Appendix A.
126 Caution: This function may receive untrusted input.
127 PE/COFF image is external input, so this function will validate its data structure
128 within this image buffer before use.
130 Notes: PE/COFF image is checked by BasePeCoffLib PeCoffLoaderGetImageInfo().
132 @param[in] PCRIndex TPM PCR index
133 @param[in] ImageAddress Start address of image buffer.
134 @param[in] ImageSize Image size
135 @param[out] DigestList Digeest list of this image.
137 @retval EFI_SUCCESS Successfully measure image.
138 @retval EFI_OUT_OF_RESOURCES No enough resource to measure image.
139 @retval other error value
142 MeasurePeImageAndExtend (
144 IN EFI_PHYSICAL_ADDRESS ImageAddress
,
146 OUT TPML_DIGEST_VALUES
*DigestList
151 This function dump raw data.
154 @param Size raw data size
164 for (Index
= 0; Index
< Size
; Index
++) {
165 DEBUG ((EFI_D_INFO
, "%02x", (UINTN
)Data
[Index
]));
171 This function initialize TCG_PCR_EVENT2_HDR for EV_NO_ACTION Event Type other than EFI Specification ID event
172 The behavior is defined by TCG PC Client PFP Spec. Section 9.3.4 EV_NO_ACTION Event Types
174 @param[in, out] NoActionEvent Event Header of EV_NO_ACTION Event
175 @param[in] EventSize Event Size of the EV_NO_ACTION Event
180 IN OUT TCG_PCR_EVENT2_HDR
*NoActionEvent
,
184 UINT32 DigestListCount
;
185 TPMI_ALG_HASH HashAlgId
;
188 DigestBuffer
= (UINT8
*)NoActionEvent
->Digests
.digests
;
191 NoActionEvent
->PCRIndex
= 0;
192 NoActionEvent
->EventType
= EV_NO_ACTION
;
195 // Set Hash count & hashAlg accordingly, while Digest.digests[n].digest to all 0
197 ZeroMem (&NoActionEvent
->Digests
, sizeof(NoActionEvent
->Digests
));
199 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA1
) != 0) {
200 HashAlgId
= TPM_ALG_SHA1
;
201 CopyMem (DigestBuffer
, &HashAlgId
, sizeof(TPMI_ALG_HASH
));
202 DigestBuffer
+= sizeof(TPMI_ALG_HASH
) + GetHashSizeFromAlgo (HashAlgId
);
206 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA256
) != 0) {
207 HashAlgId
= TPM_ALG_SHA256
;
208 CopyMem (DigestBuffer
, &HashAlgId
, sizeof(TPMI_ALG_HASH
));
209 DigestBuffer
+= sizeof(TPMI_ALG_HASH
) + GetHashSizeFromAlgo (HashAlgId
);
213 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA384
) != 0) {
214 HashAlgId
= TPM_ALG_SHA384
;
215 CopyMem (DigestBuffer
, &HashAlgId
, sizeof(TPMI_ALG_HASH
));
216 DigestBuffer
+= sizeof(TPMI_ALG_HASH
) + GetHashSizeFromAlgo (HashAlgId
);
220 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA512
) != 0) {
221 HashAlgId
= TPM_ALG_SHA512
;
222 CopyMem (DigestBuffer
, &HashAlgId
, sizeof(TPMI_ALG_HASH
));
223 DigestBuffer
+= sizeof(TPMI_ALG_HASH
) + GetHashSizeFromAlgo (HashAlgId
);
227 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SM3_256
) != 0) {
228 HashAlgId
= TPM_ALG_SM3_256
;
229 CopyMem (DigestBuffer
, &HashAlgId
, sizeof(TPMI_ALG_HASH
));
230 DigestBuffer
+= sizeof(TPMI_ALG_HASH
) + GetHashSizeFromAlgo (HashAlgId
);
237 WriteUnaligned32 ((UINT32
*)&NoActionEvent
->Digests
.count
, DigestListCount
);
242 WriteUnaligned32((UINT32
*)DigestBuffer
, EventSize
);
247 This function dump raw data with colume format.
250 @param Size raw data size
263 #define COLUME_SIZE (16 * 2)
265 Count
= Size
/ COLUME_SIZE
;
266 Left
= Size
% COLUME_SIZE
;
267 for (Index
= 0; Index
< Count
; Index
++) {
268 DEBUG ((EFI_D_INFO
, "%04x: ", Index
* COLUME_SIZE
));
269 InternalDumpData (Data
+ Index
* COLUME_SIZE
, COLUME_SIZE
);
270 DEBUG ((EFI_D_INFO
, "\n"));
274 DEBUG ((EFI_D_INFO
, "%04x: ", Index
* COLUME_SIZE
));
275 InternalDumpData (Data
+ Index
* COLUME_SIZE
, Left
);
276 DEBUG ((EFI_D_INFO
, "\n"));
281 Get All processors EFI_CPU_LOCATION in system. LocationBuf is allocated inside the function
282 Caller is responsible to free LocationBuf.
284 @param[out] LocationBuf Returns Processor Location Buffer.
285 @param[out] Num Returns processor number.
287 @retval EFI_SUCCESS Operation completed successfully.
288 @retval EFI_UNSUPPORTED MpService protocol not found.
292 GetProcessorsCpuLocation (
293 OUT EFI_CPU_PHYSICAL_LOCATION
**LocationBuf
,
298 EFI_MP_SERVICES_PROTOCOL
*MpProtocol
;
300 UINTN EnabledProcessorNum
;
301 EFI_PROCESSOR_INFORMATION ProcessorInfo
;
302 EFI_CPU_PHYSICAL_LOCATION
*ProcessorLocBuf
;
305 Status
= gBS
->LocateProtocol (&gEfiMpServiceProtocolGuid
, NULL
, (VOID
**) &MpProtocol
);
306 if (EFI_ERROR (Status
)) {
308 // MP protocol is not installed
310 return EFI_UNSUPPORTED
;
313 Status
= MpProtocol
->GetNumberOfProcessors(
318 if (EFI_ERROR(Status
)){
322 Status
= gBS
->AllocatePool(
324 sizeof(EFI_CPU_PHYSICAL_LOCATION
) * ProcessorNum
,
325 (VOID
**) &ProcessorLocBuf
327 if (EFI_ERROR(Status
)){
332 // Get each processor Location info
334 for (Index
= 0; Index
< ProcessorNum
; Index
++) {
335 Status
= MpProtocol
->GetProcessorInfo(
340 if (EFI_ERROR(Status
)){
341 FreePool(ProcessorLocBuf
);
346 // Get all Processor Location info & measure
349 &ProcessorLocBuf
[Index
],
350 &ProcessorInfo
.Location
,
351 sizeof(EFI_CPU_PHYSICAL_LOCATION
)
355 *LocationBuf
= ProcessorLocBuf
;
362 The EFI_TCG2_PROTOCOL GetCapability function call provides protocol
363 capability information and state information.
365 @param[in] This Indicates the calling context
366 @param[in, out] ProtocolCapability The caller allocates memory for a EFI_TCG2_BOOT_SERVICE_CAPABILITY
367 structure and sets the size field to the size of the structure allocated.
368 The callee fills in the fields with the EFI protocol capability information
369 and the current EFI TCG2 state information up to the number of fields which
370 fit within the size of the structure passed in.
372 @retval EFI_SUCCESS Operation completed successfully.
373 @retval EFI_DEVICE_ERROR The command was unsuccessful.
374 The ProtocolCapability variable will not be populated.
375 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
376 The ProtocolCapability variable will not be populated.
377 @retval EFI_BUFFER_TOO_SMALL The ProtocolCapability variable is too small to hold the full response.
378 It will be partially populated (required Size field will be set).
383 IN EFI_TCG2_PROTOCOL
*This
,
384 IN OUT EFI_TCG2_BOOT_SERVICE_CAPABILITY
*ProtocolCapability
387 DEBUG ((DEBUG_VERBOSE
, "Tcg2GetCapability ...\n"));
389 if ((This
== NULL
) || (ProtocolCapability
== NULL
)) {
390 return EFI_INVALID_PARAMETER
;
393 DEBUG ((DEBUG_VERBOSE
, "Size - 0x%x\n", ProtocolCapability
->Size
));
394 DEBUG ((DEBUG_VERBOSE
, " 1.1 - 0x%x, 1.0 - 0x%x\n", sizeof(EFI_TCG2_BOOT_SERVICE_CAPABILITY
), sizeof(TREE_BOOT_SERVICE_CAPABILITY_1_0
)));
396 if (ProtocolCapability
->Size
< mTcgDxeData
.BsCap
.Size
) {
398 // Handle the case that firmware support 1.1 but OS only support 1.0.
400 if ((mTcgDxeData
.BsCap
.ProtocolVersion
.Major
> 0x01) ||
401 ((mTcgDxeData
.BsCap
.ProtocolVersion
.Major
== 0x01) && ((mTcgDxeData
.BsCap
.ProtocolVersion
.Minor
> 0x00)))) {
402 if (ProtocolCapability
->Size
>= sizeof(TREE_BOOT_SERVICE_CAPABILITY_1_0
)) {
403 CopyMem (ProtocolCapability
, &mTcgDxeData
.BsCap
, sizeof(TREE_BOOT_SERVICE_CAPABILITY_1_0
));
404 ProtocolCapability
->Size
= sizeof(TREE_BOOT_SERVICE_CAPABILITY_1_0
);
405 ProtocolCapability
->StructureVersion
.Major
= 1;
406 ProtocolCapability
->StructureVersion
.Minor
= 0;
407 ProtocolCapability
->ProtocolVersion
.Major
= 1;
408 ProtocolCapability
->ProtocolVersion
.Minor
= 0;
409 DEBUG ((EFI_D_ERROR
, "TreeGetCapability (Compatible) - %r\n", EFI_SUCCESS
));
413 ProtocolCapability
->Size
= mTcgDxeData
.BsCap
.Size
;
414 return EFI_BUFFER_TOO_SMALL
;
417 CopyMem (ProtocolCapability
, &mTcgDxeData
.BsCap
, mTcgDxeData
.BsCap
.Size
);
418 DEBUG ((DEBUG_VERBOSE
, "Tcg2GetCapability - %r\n", EFI_SUCCESS
));
423 This function dump PCR event.
425 @param[in] EventHdr TCG PCR event structure.
429 IN TCG_PCR_EVENT_HDR
*EventHdr
434 DEBUG ((EFI_D_INFO
, " Event:\n"));
435 DEBUG ((EFI_D_INFO
, " PCRIndex - %d\n", EventHdr
->PCRIndex
));
436 DEBUG ((EFI_D_INFO
, " EventType - 0x%08x\n", EventHdr
->EventType
));
437 DEBUG ((EFI_D_INFO
, " Digest - "));
438 for (Index
= 0; Index
< sizeof(TCG_DIGEST
); Index
++) {
439 DEBUG ((EFI_D_INFO
, "%02x ", EventHdr
->Digest
.digest
[Index
]));
441 DEBUG ((EFI_D_INFO
, "\n"));
442 DEBUG ((EFI_D_INFO
, " EventSize - 0x%08x\n", EventHdr
->EventSize
));
443 InternalDumpHex ((UINT8
*)(EventHdr
+ 1), EventHdr
->EventSize
);
447 This function dump TCG_EfiSpecIDEventStruct.
449 @param[in] TcgEfiSpecIdEventStruct A pointer to TCG_EfiSpecIDEventStruct.
452 DumpTcgEfiSpecIdEventStruct (
453 IN TCG_EfiSpecIDEventStruct
*TcgEfiSpecIdEventStruct
456 TCG_EfiSpecIdEventAlgorithmSize
*DigestSize
;
458 UINT8
*VendorInfoSize
;
460 UINT32 NumberOfAlgorithms
;
462 DEBUG ((EFI_D_INFO
, " TCG_EfiSpecIDEventStruct:\n"));
463 DEBUG ((EFI_D_INFO
, " signature - '"));
464 for (Index
= 0; Index
< sizeof(TcgEfiSpecIdEventStruct
->signature
); Index
++) {
465 DEBUG ((EFI_D_INFO
, "%c", TcgEfiSpecIdEventStruct
->signature
[Index
]));
467 DEBUG ((EFI_D_INFO
, "'\n"));
468 DEBUG ((EFI_D_INFO
, " platformClass - 0x%08x\n", TcgEfiSpecIdEventStruct
->platformClass
));
469 DEBUG ((EFI_D_INFO
, " specVersion - %d.%d%d\n", TcgEfiSpecIdEventStruct
->specVersionMajor
, TcgEfiSpecIdEventStruct
->specVersionMinor
, TcgEfiSpecIdEventStruct
->specErrata
));
470 DEBUG ((EFI_D_INFO
, " uintnSize - 0x%02x\n", TcgEfiSpecIdEventStruct
->uintnSize
));
472 CopyMem (&NumberOfAlgorithms
, TcgEfiSpecIdEventStruct
+ 1, sizeof(NumberOfAlgorithms
));
473 DEBUG ((EFI_D_INFO
, " NumberOfAlgorithms - 0x%08x\n", NumberOfAlgorithms
));
475 DigestSize
= (TCG_EfiSpecIdEventAlgorithmSize
*)((UINT8
*)TcgEfiSpecIdEventStruct
+ sizeof(*TcgEfiSpecIdEventStruct
) + sizeof(NumberOfAlgorithms
));
476 for (Index
= 0; Index
< NumberOfAlgorithms
; Index
++) {
477 DEBUG ((EFI_D_INFO
, " digest(%d)\n", Index
));
478 DEBUG ((EFI_D_INFO
, " algorithmId - 0x%04x\n", DigestSize
[Index
].algorithmId
));
479 DEBUG ((EFI_D_INFO
, " digestSize - 0x%04x\n", DigestSize
[Index
].digestSize
));
481 VendorInfoSize
= (UINT8
*)&DigestSize
[NumberOfAlgorithms
];
482 DEBUG ((EFI_D_INFO
, " VendorInfoSize - 0x%02x\n", *VendorInfoSize
));
483 VendorInfo
= VendorInfoSize
+ 1;
484 DEBUG ((EFI_D_INFO
, " VendorInfo - "));
485 for (Index
= 0; Index
< *VendorInfoSize
; Index
++) {
486 DEBUG ((EFI_D_INFO
, "%02x ", VendorInfo
[Index
]));
488 DEBUG ((EFI_D_INFO
, "\n"));
492 This function get size of TCG_EfiSpecIDEventStruct.
494 @param[in] TcgEfiSpecIdEventStruct A pointer to TCG_EfiSpecIDEventStruct.
497 GetTcgEfiSpecIdEventStructSize (
498 IN TCG_EfiSpecIDEventStruct
*TcgEfiSpecIdEventStruct
501 TCG_EfiSpecIdEventAlgorithmSize
*DigestSize
;
502 UINT8
*VendorInfoSize
;
503 UINT32 NumberOfAlgorithms
;
505 CopyMem (&NumberOfAlgorithms
, TcgEfiSpecIdEventStruct
+ 1, sizeof(NumberOfAlgorithms
));
507 DigestSize
= (TCG_EfiSpecIdEventAlgorithmSize
*)((UINT8
*)TcgEfiSpecIdEventStruct
+ sizeof(*TcgEfiSpecIdEventStruct
) + sizeof(NumberOfAlgorithms
));
508 VendorInfoSize
= (UINT8
*)&DigestSize
[NumberOfAlgorithms
];
509 return sizeof(TCG_EfiSpecIDEventStruct
) + sizeof(UINT32
) + (NumberOfAlgorithms
* sizeof(TCG_EfiSpecIdEventAlgorithmSize
)) + sizeof(UINT8
) + (*VendorInfoSize
);
513 This function dump PCR event 2.
515 @param[in] TcgPcrEvent2 TCG PCR event 2 structure.
519 IN TCG_PCR_EVENT2
*TcgPcrEvent2
525 TPMI_ALG_HASH HashAlgo
;
531 DEBUG ((EFI_D_INFO
, " Event:\n"));
532 DEBUG ((EFI_D_INFO
, " PCRIndex - %d\n", TcgPcrEvent2
->PCRIndex
));
533 DEBUG ((EFI_D_INFO
, " EventType - 0x%08x\n", TcgPcrEvent2
->EventType
));
535 DEBUG ((EFI_D_INFO
, " DigestCount: 0x%08x\n", TcgPcrEvent2
->Digest
.count
));
537 DigestCount
= TcgPcrEvent2
->Digest
.count
;
538 HashAlgo
= TcgPcrEvent2
->Digest
.digests
[0].hashAlg
;
539 DigestBuffer
= (UINT8
*)&TcgPcrEvent2
->Digest
.digests
[0].digest
;
540 for (DigestIndex
= 0; DigestIndex
< DigestCount
; DigestIndex
++) {
541 DEBUG ((EFI_D_INFO
, " HashAlgo : 0x%04x\n", HashAlgo
));
542 DEBUG ((EFI_D_INFO
, " Digest(%d): ", DigestIndex
));
543 DigestSize
= GetHashSizeFromAlgo (HashAlgo
);
544 for (Index
= 0; Index
< DigestSize
; Index
++) {
545 DEBUG ((EFI_D_INFO
, "%02x ", DigestBuffer
[Index
]));
547 DEBUG ((EFI_D_INFO
, "\n"));
551 CopyMem (&HashAlgo
, DigestBuffer
+ DigestSize
, sizeof(TPMI_ALG_HASH
));
552 DigestBuffer
= DigestBuffer
+ DigestSize
+ sizeof(TPMI_ALG_HASH
);
554 DEBUG ((EFI_D_INFO
, "\n"));
555 DigestBuffer
= DigestBuffer
- sizeof(TPMI_ALG_HASH
);
557 CopyMem (&EventSize
, DigestBuffer
, sizeof(TcgPcrEvent2
->EventSize
));
558 DEBUG ((EFI_D_INFO
, " EventSize - 0x%08x\n", EventSize
));
559 EventBuffer
= DigestBuffer
+ sizeof(TcgPcrEvent2
->EventSize
);
560 InternalDumpHex (EventBuffer
, EventSize
);
564 This function returns size of TCG PCR event 2.
566 @param[in] TcgPcrEvent2 TCG PCR event 2 structure.
568 @return size of TCG PCR event 2.
572 IN TCG_PCR_EVENT2
*TcgPcrEvent2
577 TPMI_ALG_HASH HashAlgo
;
583 DigestCount
= TcgPcrEvent2
->Digest
.count
;
584 HashAlgo
= TcgPcrEvent2
->Digest
.digests
[0].hashAlg
;
585 DigestBuffer
= (UINT8
*)&TcgPcrEvent2
->Digest
.digests
[0].digest
;
586 for (DigestIndex
= 0; DigestIndex
< DigestCount
; DigestIndex
++) {
587 DigestSize
= GetHashSizeFromAlgo (HashAlgo
);
591 CopyMem (&HashAlgo
, DigestBuffer
+ DigestSize
, sizeof(TPMI_ALG_HASH
));
592 DigestBuffer
= DigestBuffer
+ DigestSize
+ sizeof(TPMI_ALG_HASH
);
594 DigestBuffer
= DigestBuffer
- sizeof(TPMI_ALG_HASH
);
596 CopyMem (&EventSize
, DigestBuffer
, sizeof(TcgPcrEvent2
->EventSize
));
597 EventBuffer
= DigestBuffer
+ sizeof(TcgPcrEvent2
->EventSize
);
599 return (UINTN
)EventBuffer
+ EventSize
- (UINTN
)TcgPcrEvent2
;
603 This function dump event log.
605 @param[in] EventLogFormat The type of the event log for which the information is requested.
606 @param[in] EventLogLocation A pointer to the memory address of the event log.
607 @param[in] EventLogLastEntry If the Event Log contains more than one entry, this is a pointer to the
608 address of the start of the last entry in the event log in memory.
609 @param[in] FinalEventsTable A pointer to the memory address of the final event table.
613 IN EFI_TCG2_EVENT_LOG_FORMAT EventLogFormat
,
614 IN EFI_PHYSICAL_ADDRESS EventLogLocation
,
615 IN EFI_PHYSICAL_ADDRESS EventLogLastEntry
,
616 IN EFI_TCG2_FINAL_EVENTS_TABLE
*FinalEventsTable
619 TCG_PCR_EVENT_HDR
*EventHdr
;
620 TCG_PCR_EVENT2
*TcgPcrEvent2
;
621 TCG_EfiSpecIDEventStruct
*TcgEfiSpecIdEventStruct
;
622 UINTN NumberOfEvents
;
624 DEBUG ((EFI_D_INFO
, "EventLogFormat: (0x%x)\n", EventLogFormat
));
626 switch (EventLogFormat
) {
627 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
:
628 EventHdr
= (TCG_PCR_EVENT_HDR
*)(UINTN
)EventLogLocation
;
629 while ((UINTN
)EventHdr
<= EventLogLastEntry
) {
630 DumpEvent (EventHdr
);
631 EventHdr
= (TCG_PCR_EVENT_HDR
*)((UINTN
)EventHdr
+ sizeof(TCG_PCR_EVENT_HDR
) + EventHdr
->EventSize
);
633 if (FinalEventsTable
== NULL
) {
634 DEBUG ((EFI_D_INFO
, "FinalEventsTable: NOT FOUND\n"));
636 DEBUG ((EFI_D_INFO
, "FinalEventsTable: (0x%x)\n", FinalEventsTable
));
637 DEBUG ((EFI_D_INFO
, " Version: (0x%x)\n", FinalEventsTable
->Version
));
638 DEBUG ((EFI_D_INFO
, " NumberOfEvents: (0x%x)\n", FinalEventsTable
->NumberOfEvents
));
640 EventHdr
= (TCG_PCR_EVENT_HDR
*)(UINTN
)(FinalEventsTable
+ 1);
641 for (NumberOfEvents
= 0; NumberOfEvents
< FinalEventsTable
->NumberOfEvents
; NumberOfEvents
++) {
642 DumpEvent (EventHdr
);
643 EventHdr
= (TCG_PCR_EVENT_HDR
*)((UINTN
)EventHdr
+ sizeof(TCG_PCR_EVENT_HDR
) + EventHdr
->EventSize
);
647 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
:
651 EventHdr
= (TCG_PCR_EVENT_HDR
*)(UINTN
)EventLogLocation
;
652 DumpEvent (EventHdr
);
654 TcgEfiSpecIdEventStruct
= (TCG_EfiSpecIDEventStruct
*)(EventHdr
+ 1);
655 DumpTcgEfiSpecIdEventStruct (TcgEfiSpecIdEventStruct
);
657 TcgPcrEvent2
= (TCG_PCR_EVENT2
*)((UINTN
)TcgEfiSpecIdEventStruct
+ GetTcgEfiSpecIdEventStructSize (TcgEfiSpecIdEventStruct
));
658 while ((UINTN
)TcgPcrEvent2
<= EventLogLastEntry
) {
659 DumpEvent2 (TcgPcrEvent2
);
660 TcgPcrEvent2
= (TCG_PCR_EVENT2
*)((UINTN
)TcgPcrEvent2
+ GetPcrEvent2Size (TcgPcrEvent2
));
663 if (FinalEventsTable
== NULL
) {
664 DEBUG ((EFI_D_INFO
, "FinalEventsTable: NOT FOUND\n"));
666 DEBUG ((EFI_D_INFO
, "FinalEventsTable: (0x%x)\n", FinalEventsTable
));
667 DEBUG ((EFI_D_INFO
, " Version: (0x%x)\n", FinalEventsTable
->Version
));
668 DEBUG ((EFI_D_INFO
, " NumberOfEvents: (0x%x)\n", FinalEventsTable
->NumberOfEvents
));
670 TcgPcrEvent2
= (TCG_PCR_EVENT2
*)(UINTN
)(FinalEventsTable
+ 1);
671 for (NumberOfEvents
= 0; NumberOfEvents
< FinalEventsTable
->NumberOfEvents
; NumberOfEvents
++) {
672 DumpEvent2 (TcgPcrEvent2
);
673 TcgPcrEvent2
= (TCG_PCR_EVENT2
*)((UINTN
)TcgPcrEvent2
+ GetPcrEvent2Size (TcgPcrEvent2
));
683 The EFI_TCG2_PROTOCOL Get Event Log function call allows a caller to
684 retrieve the address of a given event log and its last entry.
686 @param[in] This Indicates the calling context
687 @param[in] EventLogFormat The type of the event log for which the information is requested.
688 @param[out] EventLogLocation A pointer to the memory address of the event log.
689 @param[out] EventLogLastEntry If the Event Log contains more than one entry, this is a pointer to the
690 address of the start of the last entry in the event log in memory.
691 @param[out] EventLogTruncated If the Event Log is missing at least one entry because an event would
692 have exceeded the area allocated for events, this value is set to TRUE.
693 Otherwise, the value will be FALSE and the Event Log will be complete.
695 @retval EFI_SUCCESS Operation completed successfully.
696 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect
697 (e.g. asking for an event log whose format is not supported).
702 IN EFI_TCG2_PROTOCOL
*This
,
703 IN EFI_TCG2_EVENT_LOG_FORMAT EventLogFormat
,
704 OUT EFI_PHYSICAL_ADDRESS
*EventLogLocation
,
705 OUT EFI_PHYSICAL_ADDRESS
*EventLogLastEntry
,
706 OUT BOOLEAN
*EventLogTruncated
711 DEBUG ((EFI_D_INFO
, "Tcg2GetEventLog ... (0x%x)\n", EventLogFormat
));
714 return EFI_INVALID_PARAMETER
;
717 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
718 if (EventLogFormat
== mTcg2EventInfo
[Index
].LogFormat
) {
723 if (Index
== sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0])) {
724 return EFI_INVALID_PARAMETER
;
727 if ((mTcg2EventInfo
[Index
].LogFormat
& mTcgDxeData
.BsCap
.SupportedEventLogs
) == 0) {
728 return EFI_INVALID_PARAMETER
;
731 if (!mTcgDxeData
.BsCap
.TPMPresentFlag
) {
732 if (EventLogLocation
!= NULL
) {
733 *EventLogLocation
= 0;
735 if (EventLogLastEntry
!= NULL
) {
736 *EventLogLastEntry
= 0;
738 if (EventLogTruncated
!= NULL
) {
739 *EventLogTruncated
= FALSE
;
744 if (EventLogLocation
!= NULL
) {
745 *EventLogLocation
= mTcgDxeData
.EventLogAreaStruct
[Index
].Lasa
;
746 DEBUG ((EFI_D_INFO
, "Tcg2GetEventLog (EventLogLocation - %x)\n", *EventLogLocation
));
749 if (EventLogLastEntry
!= NULL
) {
750 if (!mTcgDxeData
.EventLogAreaStruct
[Index
].EventLogStarted
) {
751 *EventLogLastEntry
= (EFI_PHYSICAL_ADDRESS
)(UINTN
)0;
753 *EventLogLastEntry
= (EFI_PHYSICAL_ADDRESS
)(UINTN
)mTcgDxeData
.EventLogAreaStruct
[Index
].LastEvent
;
755 DEBUG ((EFI_D_INFO
, "Tcg2GetEventLog (EventLogLastEntry - %x)\n", *EventLogLastEntry
));
758 if (EventLogTruncated
!= NULL
) {
759 *EventLogTruncated
= mTcgDxeData
.EventLogAreaStruct
[Index
].EventLogTruncated
;
760 DEBUG ((EFI_D_INFO
, "Tcg2GetEventLog (EventLogTruncated - %x)\n", *EventLogTruncated
));
763 DEBUG ((EFI_D_INFO
, "Tcg2GetEventLog - %r\n", EFI_SUCCESS
));
765 // Dump Event Log for debug purpose
766 if ((EventLogLocation
!= NULL
) && (EventLogLastEntry
!= NULL
)) {
767 DumpEventLog (EventLogFormat
, *EventLogLocation
, *EventLogLastEntry
, mTcgDxeData
.FinalEventsTable
[Index
]);
771 // All events generated after the invocation of EFI_TCG2_GET_EVENT_LOG SHALL be stored
772 // in an instance of an EFI_CONFIGURATION_TABLE named by the VendorGuid of EFI_TCG2_FINAL_EVENTS_TABLE_GUID.
774 mTcgDxeData
.GetEventLogCalled
[Index
] = TRUE
;
780 Add a new entry to the Event Log.
782 @param[in, out] EventLogPtr Pointer to the Event Log data.
783 @param[in, out] LogSize Size of the Event Log.
784 @param[in] MaxSize Maximum size of the Event Log.
785 @param[in] NewEventHdr Pointer to a TCG_PCR_EVENT_HDR/TCG_PCR_EVENT_EX data structure.
786 @param[in] NewEventHdrSize New event header size.
787 @param[in] NewEventData Pointer to the new event data.
788 @param[in] NewEventSize New event data size.
790 @retval EFI_SUCCESS The new event log entry was added.
791 @retval EFI_OUT_OF_RESOURCES No enough memory to log the new event.
796 IN OUT UINT8
**EventLogPtr
,
797 IN OUT UINTN
*LogSize
,
799 IN VOID
*NewEventHdr
,
800 IN UINT32 NewEventHdrSize
,
801 IN UINT8
*NewEventData
,
802 IN UINT32 NewEventSize
807 if (NewEventSize
> MAX_ADDRESS
- NewEventHdrSize
) {
808 return EFI_OUT_OF_RESOURCES
;
811 NewLogSize
= NewEventHdrSize
+ NewEventSize
;
813 if (NewLogSize
> MAX_ADDRESS
- *LogSize
) {
814 return EFI_OUT_OF_RESOURCES
;
817 if (NewLogSize
+ *LogSize
> MaxSize
) {
818 DEBUG ((EFI_D_INFO
, " MaxSize - 0x%x\n", MaxSize
));
819 DEBUG ((EFI_D_INFO
, " NewLogSize - 0x%x\n", NewLogSize
));
820 DEBUG ((EFI_D_INFO
, " LogSize - 0x%x\n", *LogSize
));
821 DEBUG ((EFI_D_INFO
, "TcgCommLogEvent - %r\n", EFI_OUT_OF_RESOURCES
));
822 return EFI_OUT_OF_RESOURCES
;
825 *EventLogPtr
+= *LogSize
;
826 *LogSize
+= NewLogSize
;
827 CopyMem (*EventLogPtr
, NewEventHdr
, NewEventHdrSize
);
829 *EventLogPtr
+ NewEventHdrSize
,
837 Add a new entry to the Event Log.
839 @param[in] EventLogFormat The type of the event log for which the information is requested.
840 @param[in] NewEventHdr Pointer to a TCG_PCR_EVENT_HDR/TCG_PCR_EVENT_EX data structure.
841 @param[in] NewEventHdrSize New event header size.
842 @param[in] NewEventData Pointer to the new event data.
843 @param[in] NewEventSize New event data size.
845 @retval EFI_SUCCESS The new event log entry was added.
846 @retval EFI_OUT_OF_RESOURCES No enough memory to log the new event.
851 IN EFI_TCG2_EVENT_LOG_FORMAT EventLogFormat
,
852 IN VOID
*NewEventHdr
,
853 IN UINT32 NewEventHdrSize
,
854 IN UINT8
*NewEventData
,
855 IN UINT32 NewEventSize
860 TCG_EVENT_LOG_AREA_STRUCT
*EventLogAreaStruct
;
862 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
863 if (EventLogFormat
== mTcg2EventInfo
[Index
].LogFormat
) {
868 if (Index
== sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0])) {
869 return EFI_INVALID_PARAMETER
;
873 // Record to normal event log
875 EventLogAreaStruct
= &mTcgDxeData
.EventLogAreaStruct
[Index
];
877 if (EventLogAreaStruct
->EventLogTruncated
) {
878 return EFI_VOLUME_FULL
;
881 EventLogAreaStruct
->LastEvent
= (UINT8
*)(UINTN
)EventLogAreaStruct
->Lasa
;
882 Status
= TcgCommLogEvent (
883 &EventLogAreaStruct
->LastEvent
,
884 &EventLogAreaStruct
->EventLogSize
,
885 (UINTN
)EventLogAreaStruct
->Laml
,
892 if (Status
== EFI_OUT_OF_RESOURCES
) {
893 EventLogAreaStruct
->EventLogTruncated
= TRUE
;
894 return EFI_VOLUME_FULL
;
895 } else if (Status
== EFI_SUCCESS
) {
896 EventLogAreaStruct
->EventLogStarted
= TRUE
;
900 // If GetEventLog is called, record to FinalEventsTable, too.
902 if (mTcgDxeData
.GetEventLogCalled
[Index
]) {
903 if (mTcgDxeData
.FinalEventsTable
[Index
] == NULL
) {
905 // no need for FinalEventsTable
909 EventLogAreaStruct
= &mTcgDxeData
.FinalEventLogAreaStruct
[Index
];
911 if (EventLogAreaStruct
->EventLogTruncated
) {
912 return EFI_VOLUME_FULL
;
915 EventLogAreaStruct
->LastEvent
= (UINT8
*)(UINTN
)EventLogAreaStruct
->Lasa
;
916 Status
= TcgCommLogEvent (
917 &EventLogAreaStruct
->LastEvent
,
918 &EventLogAreaStruct
->EventLogSize
,
919 (UINTN
)EventLogAreaStruct
->Laml
,
925 if (Status
== EFI_OUT_OF_RESOURCES
) {
926 EventLogAreaStruct
->EventLogTruncated
= TRUE
;
927 return EFI_VOLUME_FULL
;
928 } else if (Status
== EFI_SUCCESS
) {
929 EventLogAreaStruct
->EventLogStarted
= TRUE
;
931 // Increase the NumberOfEvents in FinalEventsTable
933 (mTcgDxeData
.FinalEventsTable
[Index
])->NumberOfEvents
++;
934 DEBUG ((EFI_D_INFO
, "FinalEventsTable->NumberOfEvents - 0x%x\n", (mTcgDxeData
.FinalEventsTable
[Index
])->NumberOfEvents
));
935 DEBUG ((EFI_D_INFO
, " Size - 0x%x\n", (UINTN
)EventLogAreaStruct
->EventLogSize
));
943 Get TPML_DIGEST_VALUES compact binary buffer size.
945 @param[in] DigestListBin TPML_DIGEST_VALUES compact binary buffer.
947 @return TPML_DIGEST_VALUES compact binary buffer size.
950 GetDigestListBinSize (
951 IN VOID
*DigestListBin
958 TPMI_ALG_HASH HashAlg
;
960 Count
= ReadUnaligned32 (DigestListBin
);
961 TotalSize
= sizeof(Count
);
962 DigestListBin
= (UINT8
*)DigestListBin
+ sizeof(Count
);
963 for (Index
= 0; Index
< Count
; Index
++) {
964 HashAlg
= ReadUnaligned16 (DigestListBin
);
965 TotalSize
+= sizeof(HashAlg
);
966 DigestListBin
= (UINT8
*)DigestListBin
+ sizeof(HashAlg
);
968 DigestSize
= GetHashSizeFromAlgo (HashAlg
);
969 TotalSize
+= DigestSize
;
970 DigestListBin
= (UINT8
*)DigestListBin
+ DigestSize
;
977 Copy TPML_DIGEST_VALUES compact binary into a buffer
979 @param[in,out] Buffer Buffer to hold copied TPML_DIGEST_VALUES compact binary.
980 @param[in] DigestListBin TPML_DIGEST_VALUES compact binary buffer.
981 @param[in] HashAlgorithmMask HASH bits corresponding to the desired digests to copy.
982 @param[out] HashAlgorithmMaskCopied Pointer to HASH bits corresponding to the digests copied.
984 @return The end of buffer to hold TPML_DIGEST_VALUES compact binary.
987 CopyDigestListBinToBuffer (
989 IN VOID
*DigestListBin
,
990 IN UINT32 HashAlgorithmMask
,
991 OUT UINT32
*HashAlgorithmMaskCopied
997 TPMI_ALG_HASH HashAlg
;
998 UINT32 DigestListCount
;
999 UINT32
*DigestListCountPtr
;
1001 DigestListCountPtr
= (UINT32
*) Buffer
;
1002 DigestListCount
= 0;
1003 (*HashAlgorithmMaskCopied
) = 0;
1005 Count
= ReadUnaligned32 (DigestListBin
);
1006 Buffer
= (UINT8
*)Buffer
+ sizeof(Count
);
1007 DigestListBin
= (UINT8
*)DigestListBin
+ sizeof(Count
);
1008 for (Index
= 0; Index
< Count
; Index
++) {
1009 HashAlg
= ReadUnaligned16 (DigestListBin
);
1010 DigestListBin
= (UINT8
*)DigestListBin
+ sizeof(HashAlg
);
1011 DigestSize
= GetHashSizeFromAlgo (HashAlg
);
1013 if (IsHashAlgSupportedInHashAlgorithmMask(HashAlg
, HashAlgorithmMask
)) {
1014 CopyMem (Buffer
, &HashAlg
, sizeof(HashAlg
));
1015 Buffer
= (UINT8
*)Buffer
+ sizeof(HashAlg
);
1016 CopyMem (Buffer
, DigestListBin
, DigestSize
);
1017 Buffer
= (UINT8
*)Buffer
+ DigestSize
;
1019 (*HashAlgorithmMaskCopied
) |= GetHashMaskFromAlgo (HashAlg
);
1021 DEBUG ((DEBUG_ERROR
, "WARNING: CopyDigestListBinToBuffer Event log has HashAlg unsupported by PCR bank (0x%x)\n", HashAlg
));
1023 DigestListBin
= (UINT8
*)DigestListBin
+ DigestSize
;
1025 WriteUnaligned32 (DigestListCountPtr
, DigestListCount
);
1031 Add a new entry to the Event Log.
1033 @param[in] DigestList A list of digest.
1034 @param[in,out] NewEventHdr Pointer to a TCG_PCR_EVENT_HDR data structure.
1035 @param[in] NewEventData Pointer to the new event data.
1037 @retval EFI_SUCCESS The new event log entry was added.
1038 @retval EFI_OUT_OF_RESOURCES No enough memory to log the new event.
1041 TcgDxeLogHashEvent (
1042 IN TPML_DIGEST_VALUES
*DigestList
,
1043 IN OUT TCG_PCR_EVENT_HDR
*NewEventHdr
,
1044 IN UINT8
*NewEventData
1050 EFI_STATUS RetStatus
;
1051 TCG_PCR_EVENT2 TcgPcrEvent2
;
1052 UINT8
*DigestBuffer
;
1053 UINT32
*EventSizePtr
;
1055 DEBUG ((EFI_D_INFO
, "SupportedEventLogs - 0x%08x\n", mTcgDxeData
.BsCap
.SupportedEventLogs
));
1057 RetStatus
= EFI_SUCCESS
;
1058 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
1059 if ((mTcgDxeData
.BsCap
.SupportedEventLogs
& mTcg2EventInfo
[Index
].LogFormat
) != 0) {
1060 DEBUG ((EFI_D_INFO
, " LogFormat - 0x%08x\n", mTcg2EventInfo
[Index
].LogFormat
));
1061 switch (mTcg2EventInfo
[Index
].LogFormat
) {
1062 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
:
1063 Status
= GetDigestFromDigestList (TPM_ALG_SHA1
, DigestList
, &NewEventHdr
->Digest
);
1064 if (!EFI_ERROR (Status
)) {
1066 // Enter critical region
1068 OldTpl
= gBS
->RaiseTPL (TPL_HIGH_LEVEL
);
1069 Status
= TcgDxeLogEvent (
1070 mTcg2EventInfo
[Index
].LogFormat
,
1072 sizeof(TCG_PCR_EVENT_HDR
),
1074 NewEventHdr
->EventSize
1076 if (Status
!= EFI_SUCCESS
) {
1079 gBS
->RestoreTPL (OldTpl
);
1081 // Exit critical region
1085 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
:
1086 ZeroMem (&TcgPcrEvent2
, sizeof(TcgPcrEvent2
));
1087 TcgPcrEvent2
.PCRIndex
= NewEventHdr
->PCRIndex
;
1088 TcgPcrEvent2
.EventType
= NewEventHdr
->EventType
;
1089 DigestBuffer
= (UINT8
*)&TcgPcrEvent2
.Digest
;
1090 EventSizePtr
= CopyDigestListToBuffer (DigestBuffer
, DigestList
, mTcgDxeData
.BsCap
.ActivePcrBanks
);
1091 CopyMem (EventSizePtr
, &NewEventHdr
->EventSize
, sizeof(NewEventHdr
->EventSize
));
1094 // Enter critical region
1096 OldTpl
= gBS
->RaiseTPL (TPL_HIGH_LEVEL
);
1097 Status
= TcgDxeLogEvent (
1098 mTcg2EventInfo
[Index
].LogFormat
,
1100 sizeof(TcgPcrEvent2
.PCRIndex
) + sizeof(TcgPcrEvent2
.EventType
) + GetDigestListBinSize (DigestBuffer
) + sizeof(TcgPcrEvent2
.EventSize
),
1102 NewEventHdr
->EventSize
1104 if (Status
!= EFI_SUCCESS
) {
1107 gBS
->RestoreTPL (OldTpl
);
1109 // Exit critical region
1120 Do a hash operation on a data buffer, extend a specific TPM PCR with the hash result,
1121 and add an entry to the Event Log.
1123 @param[in] Flags Bitmap providing additional information.
1124 @param[in] HashData Physical address of the start of the data buffer
1125 to be hashed, extended, and logged.
1126 @param[in] HashDataLen The length, in bytes, of the buffer referenced by HashData
1127 @param[in, out] NewEventHdr Pointer to a TCG_PCR_EVENT_HDR data structure.
1128 @param[in] NewEventData Pointer to the new event data.
1130 @retval EFI_SUCCESS Operation completed successfully.
1131 @retval EFI_OUT_OF_RESOURCES No enough memory to log the new event.
1132 @retval EFI_DEVICE_ERROR The command was unsuccessful.
1136 TcgDxeHashLogExtendEvent (
1139 IN UINT64 HashDataLen
,
1140 IN OUT TCG_PCR_EVENT_HDR
*NewEventHdr
,
1141 IN UINT8
*NewEventData
1145 TPML_DIGEST_VALUES DigestList
;
1147 if (!mTcgDxeData
.BsCap
.TPMPresentFlag
) {
1148 return EFI_DEVICE_ERROR
;
1151 Status
= HashAndExtend (
1152 NewEventHdr
->PCRIndex
,
1157 if (!EFI_ERROR (Status
)) {
1158 if ((Flags
& EFI_TCG2_EXTEND_ONLY
) == 0) {
1159 Status
= TcgDxeLogHashEvent (&DigestList
, NewEventHdr
, NewEventData
);
1163 if (Status
== EFI_DEVICE_ERROR
) {
1164 DEBUG ((EFI_D_ERROR
, "TcgDxeHashLogExtendEvent - %r. Disable TPM.\n", Status
));
1165 mTcgDxeData
.BsCap
.TPMPresentFlag
= FALSE
;
1166 REPORT_STATUS_CODE (
1167 EFI_ERROR_CODE
| EFI_ERROR_MINOR
,
1168 (PcdGet32 (PcdStatusCodeSubClassTpmDevice
) | EFI_P_EC_INTERFACE_ERROR
)
1176 The EFI_TCG2_PROTOCOL HashLogExtendEvent function call provides callers with
1177 an opportunity to extend and optionally log events without requiring
1178 knowledge of actual TPM commands.
1179 The extend operation will occur even if this function cannot create an event
1180 log entry (e.g. due to the event log being full).
1182 @param[in] This Indicates the calling context
1183 @param[in] Flags Bitmap providing additional information.
1184 @param[in] DataToHash Physical address of the start of the data buffer to be hashed.
1185 @param[in] DataToHashLen The length in bytes of the buffer referenced by DataToHash.
1186 @param[in] Event Pointer to data buffer containing information about the event.
1188 @retval EFI_SUCCESS Operation completed successfully.
1189 @retval EFI_DEVICE_ERROR The command was unsuccessful.
1190 @retval EFI_VOLUME_FULL The extend operation occurred, but the event could not be written to one or more event logs.
1191 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
1192 @retval EFI_UNSUPPORTED The PE/COFF image type is not supported.
1196 Tcg2HashLogExtendEvent (
1197 IN EFI_TCG2_PROTOCOL
*This
,
1199 IN EFI_PHYSICAL_ADDRESS DataToHash
,
1200 IN UINT64 DataToHashLen
,
1201 IN EFI_TCG2_EVENT
*Event
1205 TCG_PCR_EVENT_HDR NewEventHdr
;
1206 TPML_DIGEST_VALUES DigestList
;
1208 DEBUG ((DEBUG_VERBOSE
, "Tcg2HashLogExtendEvent ...\n"));
1210 if ((This
== NULL
) || (DataToHash
== 0) || (Event
== NULL
)) {
1211 return EFI_INVALID_PARAMETER
;
1214 if (!mTcgDxeData
.BsCap
.TPMPresentFlag
) {
1215 return EFI_DEVICE_ERROR
;
1218 if (Event
->Size
< Event
->Header
.HeaderSize
+ sizeof(UINT32
)) {
1219 return EFI_INVALID_PARAMETER
;
1222 if (Event
->Header
.PCRIndex
> MAX_PCR_INDEX
) {
1223 return EFI_INVALID_PARAMETER
;
1226 NewEventHdr
.PCRIndex
= Event
->Header
.PCRIndex
;
1227 NewEventHdr
.EventType
= Event
->Header
.EventType
;
1228 NewEventHdr
.EventSize
= Event
->Size
- sizeof(UINT32
) - Event
->Header
.HeaderSize
;
1229 if ((Flags
& PE_COFF_IMAGE
) != 0) {
1230 Status
= MeasurePeImageAndExtend (
1231 NewEventHdr
.PCRIndex
,
1233 (UINTN
)DataToHashLen
,
1236 if (!EFI_ERROR (Status
)) {
1237 if ((Flags
& EFI_TCG2_EXTEND_ONLY
) == 0) {
1238 Status
= TcgDxeLogHashEvent (&DigestList
, &NewEventHdr
, Event
->Event
);
1241 if (Status
== EFI_DEVICE_ERROR
) {
1242 DEBUG ((EFI_D_ERROR
, "MeasurePeImageAndExtend - %r. Disable TPM.\n", Status
));
1243 mTcgDxeData
.BsCap
.TPMPresentFlag
= FALSE
;
1244 REPORT_STATUS_CODE (
1245 EFI_ERROR_CODE
| EFI_ERROR_MINOR
,
1246 (PcdGet32 (PcdStatusCodeSubClassTpmDevice
) | EFI_P_EC_INTERFACE_ERROR
)
1250 Status
= TcgDxeHashLogExtendEvent (
1252 (UINT8
*) (UINTN
) DataToHash
,
1258 DEBUG ((DEBUG_VERBOSE
, "Tcg2HashLogExtendEvent - %r\n", Status
));
1263 This service enables the sending of commands to the TPM.
1265 @param[in] This Indicates the calling context
1266 @param[in] InputParameterBlockSize Size of the TPM input parameter block.
1267 @param[in] InputParameterBlock Pointer to the TPM input parameter block.
1268 @param[in] OutputParameterBlockSize Size of the TPM output parameter block.
1269 @param[in] OutputParameterBlock Pointer to the TPM output parameter block.
1271 @retval EFI_SUCCESS The command byte stream was successfully sent to the device and a response was successfully received.
1272 @retval EFI_DEVICE_ERROR The command was not successfully sent to the device or a response was not successfully received from the device.
1273 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
1274 @retval EFI_BUFFER_TOO_SMALL The output parameter block is too small.
1279 IN EFI_TCG2_PROTOCOL
*This
,
1280 IN UINT32 InputParameterBlockSize
,
1281 IN UINT8
*InputParameterBlock
,
1282 IN UINT32 OutputParameterBlockSize
,
1283 IN UINT8
*OutputParameterBlock
1288 DEBUG ((EFI_D_INFO
, "Tcg2SubmitCommand ...\n"));
1290 if ((This
== NULL
) ||
1291 (InputParameterBlockSize
== 0) || (InputParameterBlock
== NULL
) ||
1292 (OutputParameterBlockSize
== 0) || (OutputParameterBlock
== NULL
)) {
1293 return EFI_INVALID_PARAMETER
;
1296 if (!mTcgDxeData
.BsCap
.TPMPresentFlag
) {
1297 return EFI_DEVICE_ERROR
;
1300 if (InputParameterBlockSize
> mTcgDxeData
.BsCap
.MaxCommandSize
) {
1301 return EFI_INVALID_PARAMETER
;
1303 if (OutputParameterBlockSize
> mTcgDxeData
.BsCap
.MaxResponseSize
) {
1304 return EFI_INVALID_PARAMETER
;
1307 Status
= Tpm2SubmitCommand (
1308 InputParameterBlockSize
,
1309 InputParameterBlock
,
1310 &OutputParameterBlockSize
,
1311 OutputParameterBlock
1313 DEBUG ((EFI_D_INFO
, "Tcg2SubmitCommand - %r\n", Status
));
1318 This service returns the currently active PCR banks.
1320 @param[in] This Indicates the calling context
1321 @param[out] ActivePcrBanks Pointer to the variable receiving the bitmap of currently active PCR banks.
1323 @retval EFI_SUCCESS The bitmap of active PCR banks was stored in the ActivePcrBanks parameter.
1324 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
1328 Tcg2GetActivePCRBanks (
1329 IN EFI_TCG2_PROTOCOL
*This
,
1330 OUT UINT32
*ActivePcrBanks
1333 if (ActivePcrBanks
== NULL
) {
1334 return EFI_INVALID_PARAMETER
;
1336 *ActivePcrBanks
= mTcgDxeData
.BsCap
.ActivePcrBanks
;
1341 This service sets the currently active PCR banks.
1343 @param[in] This Indicates the calling context
1344 @param[in] ActivePcrBanks Bitmap of the requested active PCR banks. At least one bit SHALL be set.
1346 @retval EFI_SUCCESS The bitmap in ActivePcrBank parameter is already active.
1347 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
1351 Tcg2SetActivePCRBanks (
1352 IN EFI_TCG2_PROTOCOL
*This
,
1353 IN UINT32 ActivePcrBanks
1359 DEBUG ((EFI_D_INFO
, "Tcg2SetActivePCRBanks ... (0x%x)\n", ActivePcrBanks
));
1361 if (ActivePcrBanks
== 0) {
1362 return EFI_INVALID_PARAMETER
;
1364 if ((ActivePcrBanks
& (~mTcgDxeData
.BsCap
.HashAlgorithmBitmap
)) != 0) {
1365 return EFI_INVALID_PARAMETER
;
1367 if (ActivePcrBanks
== mTcgDxeData
.BsCap
.ActivePcrBanks
) {
1369 // Need clear previous SET_PCR_BANKS setting
1371 ReturnCode
= Tcg2PhysicalPresenceLibSubmitRequestToPreOSFunction (TCG2_PHYSICAL_PRESENCE_NO_ACTION
, 0);
1373 ReturnCode
= Tcg2PhysicalPresenceLibSubmitRequestToPreOSFunction (TCG2_PHYSICAL_PRESENCE_SET_PCR_BANKS
, ActivePcrBanks
);
1376 if (ReturnCode
== TCG_PP_SUBMIT_REQUEST_TO_PREOS_SUCCESS
) {
1377 Status
= EFI_SUCCESS
;
1378 } else if (ReturnCode
== TCG_PP_SUBMIT_REQUEST_TO_PREOS_GENERAL_FAILURE
) {
1379 Status
= EFI_OUT_OF_RESOURCES
;
1380 } else if (ReturnCode
== TCG_PP_SUBMIT_REQUEST_TO_PREOS_NOT_IMPLEMENTED
) {
1381 Status
= EFI_UNSUPPORTED
;
1383 Status
= EFI_DEVICE_ERROR
;
1386 DEBUG ((EFI_D_INFO
, "Tcg2SetActivePCRBanks - %r\n", Status
));
1392 This service retrieves the result of a previous invocation of SetActivePcrBanks.
1394 @param[in] This Indicates the calling context
1395 @param[out] OperationPresent Non-zero value to indicate a SetActivePcrBank operation was invoked during the last boot.
1396 @param[out] Response The response from the SetActivePcrBank request.
1398 @retval EFI_SUCCESS The result value could be returned.
1399 @retval EFI_INVALID_PARAMETER One or more of the parameters are incorrect.
1403 Tcg2GetResultOfSetActivePcrBanks (
1404 IN EFI_TCG2_PROTOCOL
*This
,
1405 OUT UINT32
*OperationPresent
,
1406 OUT UINT32
*Response
1411 if ((OperationPresent
== NULL
) || (Response
== NULL
)) {
1412 return EFI_INVALID_PARAMETER
;
1415 ReturnCode
= Tcg2PhysicalPresenceLibReturnOperationResponseToOsFunction (OperationPresent
, Response
);
1416 if (ReturnCode
== TCG_PP_RETURN_TPM_OPERATION_RESPONSE_SUCCESS
) {
1419 return EFI_UNSUPPORTED
;
1423 EFI_TCG2_PROTOCOL mTcg2Protocol
= {
1426 Tcg2HashLogExtendEvent
,
1428 Tcg2GetActivePCRBanks
,
1429 Tcg2SetActivePCRBanks
,
1430 Tcg2GetResultOfSetActivePcrBanks
,
1434 Initialize the Event Log and log events passed from the PEI phase.
1436 @retval EFI_SUCCESS Operation completed successfully.
1437 @retval EFI_OUT_OF_RESOURCES Out of memory.
1447 EFI_PEI_HOB_POINTERS GuidHob
;
1448 EFI_PHYSICAL_ADDRESS Lasa
;
1450 VOID
*DigestListBin
;
1451 TPML_DIGEST_VALUES TempDigestListBin
;
1452 UINT32 DigestListBinSize
;
1455 UINT32
*EventSizePtr
;
1456 UINT32 HashAlgorithmMaskCopied
;
1457 TCG_EfiSpecIDEventStruct
*TcgEfiSpecIdEventStruct
;
1458 UINT8 TempBuf
[sizeof(TCG_EfiSpecIDEventStruct
) + sizeof(UINT32
) + (HASH_COUNT
* sizeof(TCG_EfiSpecIdEventAlgorithmSize
)) + sizeof(UINT8
)];
1459 TCG_PCR_EVENT_HDR SpecIdEvent
;
1460 TCG_PCR_EVENT2_HDR NoActionEvent
;
1461 TCG_EfiSpecIdEventAlgorithmSize
*DigestSize
;
1462 TCG_EfiSpecIdEventAlgorithmSize
*TempDigestSize
;
1463 UINT8
*VendorInfoSize
;
1464 UINT32 NumberOfAlgorithms
;
1465 TCG_EfiStartupLocalityEvent StartupLocalityEvent
;
1467 DEBUG ((EFI_D_INFO
, "SetupEventLog\n"));
1470 // 1. Create Log Area
1472 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
1473 if ((mTcgDxeData
.BsCap
.SupportedEventLogs
& mTcg2EventInfo
[Index
].LogFormat
) != 0) {
1474 mTcgDxeData
.EventLogAreaStruct
[Index
].EventLogFormat
= mTcg2EventInfo
[Index
].LogFormat
;
1475 Status
= gBS
->AllocatePages (
1477 EfiBootServicesData
,
1478 EFI_SIZE_TO_PAGES (PcdGet32 (PcdTcgLogAreaMinLen
)),
1481 if (EFI_ERROR (Status
)) {
1484 mTcgDxeData
.EventLogAreaStruct
[Index
].Lasa
= Lasa
;
1485 mTcgDxeData
.EventLogAreaStruct
[Index
].Laml
= PcdGet32 (PcdTcgLogAreaMinLen
);
1487 // To initialize them as 0xFF is recommended
1488 // because the OS can know the last entry for that.
1490 SetMem ((VOID
*)(UINTN
)Lasa
, PcdGet32 (PcdTcgLogAreaMinLen
), 0xFF);
1492 // Create first entry for Log Header Entry Data
1494 if (mTcg2EventInfo
[Index
].LogFormat
!= EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
) {
1496 // TcgEfiSpecIdEventStruct
1498 TcgEfiSpecIdEventStruct
= (TCG_EfiSpecIDEventStruct
*)TempBuf
;
1499 CopyMem (TcgEfiSpecIdEventStruct
->signature
, TCG_EfiSpecIDEventStruct_SIGNATURE_03
, sizeof(TcgEfiSpecIdEventStruct
->signature
));
1500 TcgEfiSpecIdEventStruct
->platformClass
= PcdGet8 (PcdTpmPlatformClass
);
1501 TcgEfiSpecIdEventStruct
->specVersionMajor
= TCG_EfiSpecIDEventStruct_SPEC_VERSION_MAJOR_TPM2
;
1502 TcgEfiSpecIdEventStruct
->specVersionMinor
= TCG_EfiSpecIDEventStruct_SPEC_VERSION_MINOR_TPM2
;
1503 TcgEfiSpecIdEventStruct
->specErrata
= TCG_EfiSpecIDEventStruct_SPEC_ERRATA_TPM2
;
1504 TcgEfiSpecIdEventStruct
->uintnSize
= sizeof(UINTN
)/sizeof(UINT32
);
1505 NumberOfAlgorithms
= 0;
1506 DigestSize
= (TCG_EfiSpecIdEventAlgorithmSize
*)((UINT8
*)TcgEfiSpecIdEventStruct
+ sizeof(*TcgEfiSpecIdEventStruct
) + sizeof(NumberOfAlgorithms
));
1507 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA1
) != 0) {
1508 TempDigestSize
= DigestSize
;
1509 TempDigestSize
+= NumberOfAlgorithms
;
1510 TempDigestSize
->algorithmId
= TPM_ALG_SHA1
;
1511 TempDigestSize
->digestSize
= SHA1_DIGEST_SIZE
;
1512 NumberOfAlgorithms
++;
1514 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA256
) != 0) {
1515 TempDigestSize
= DigestSize
;
1516 TempDigestSize
+= NumberOfAlgorithms
;
1517 TempDigestSize
->algorithmId
= TPM_ALG_SHA256
;
1518 TempDigestSize
->digestSize
= SHA256_DIGEST_SIZE
;
1519 NumberOfAlgorithms
++;
1521 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA384
) != 0) {
1522 TempDigestSize
= DigestSize
;
1523 TempDigestSize
+= NumberOfAlgorithms
;
1524 TempDigestSize
->algorithmId
= TPM_ALG_SHA384
;
1525 TempDigestSize
->digestSize
= SHA384_DIGEST_SIZE
;
1526 NumberOfAlgorithms
++;
1528 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA512
) != 0) {
1529 TempDigestSize
= DigestSize
;
1530 TempDigestSize
+= NumberOfAlgorithms
;
1531 TempDigestSize
->algorithmId
= TPM_ALG_SHA512
;
1532 TempDigestSize
->digestSize
= SHA512_DIGEST_SIZE
;
1533 NumberOfAlgorithms
++;
1535 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SM3_256
) != 0) {
1536 TempDigestSize
= DigestSize
;
1537 TempDigestSize
+= NumberOfAlgorithms
;
1538 TempDigestSize
->algorithmId
= TPM_ALG_SM3_256
;
1539 TempDigestSize
->digestSize
= SM3_256_DIGEST_SIZE
;
1540 NumberOfAlgorithms
++;
1542 CopyMem (TcgEfiSpecIdEventStruct
+ 1, &NumberOfAlgorithms
, sizeof(NumberOfAlgorithms
));
1543 TempDigestSize
= DigestSize
;
1544 TempDigestSize
+= NumberOfAlgorithms
;
1545 VendorInfoSize
= (UINT8
*)TempDigestSize
;
1546 *VendorInfoSize
= 0;
1548 SpecIdEvent
.PCRIndex
= 0;
1549 SpecIdEvent
.EventType
= EV_NO_ACTION
;
1550 ZeroMem (&SpecIdEvent
.Digest
, sizeof(SpecIdEvent
.Digest
));
1551 SpecIdEvent
.EventSize
= (UINT32
)GetTcgEfiSpecIdEventStructSize (TcgEfiSpecIdEventStruct
);
1554 // Log TcgEfiSpecIdEventStruct as the first Event. Event format is TCG_PCR_EVENT.
1555 // TCG EFI Protocol Spec. Section 5.3 Event Log Header
1556 // TCG PC Client PFP spec. Section 9.2 Measurement Event Entries and Log
1558 Status
= TcgDxeLogEvent (
1559 mTcg2EventInfo
[Index
].LogFormat
,
1561 sizeof(SpecIdEvent
),
1562 (UINT8
*)TcgEfiSpecIdEventStruct
,
1563 SpecIdEvent
.EventSize
1567 // EfiStartupLocalityEvent. Event format is TCG_PCR_EVENT2
1569 GuidHob
.Guid
= GetFirstGuidHob (&gTpm2StartupLocalityHobGuid
);
1570 if (GuidHob
.Guid
!= NULL
) {
1572 // Get Locality Indicator from StartupLocality HOB
1574 StartupLocalityEvent
.StartupLocality
= *(UINT8
*)(GET_GUID_HOB_DATA (GuidHob
.Guid
));
1575 CopyMem (StartupLocalityEvent
.Signature
, TCG_EfiStartupLocalityEvent_SIGNATURE
, sizeof(StartupLocalityEvent
.Signature
));
1576 DEBUG ((DEBUG_INFO
, "SetupEventLog: Set Locality from HOB into StartupLocalityEvent 0x%02x\n", StartupLocalityEvent
.StartupLocality
));
1579 // Initialize StartupLocalityEvent
1581 InitNoActionEvent(&NoActionEvent
, sizeof(StartupLocalityEvent
));
1584 // Log EfiStartupLocalityEvent as the second Event
1585 // TCG PC Client PFP spec. Section 9.3.4.3 Startup Locality Event
1587 Status
= TcgDxeLogEvent (
1588 mTcg2EventInfo
[Index
].LogFormat
,
1590 sizeof(NoActionEvent
.PCRIndex
) + sizeof(NoActionEvent
.EventType
) + GetDigestListBinSize (&NoActionEvent
.Digests
) + sizeof(NoActionEvent
.EventSize
),
1591 (UINT8
*)&StartupLocalityEvent
,
1592 sizeof(StartupLocalityEvent
)
1601 // 2. Create Final Log Area
1603 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
1604 if ((mTcgDxeData
.BsCap
.SupportedEventLogs
& mTcg2EventInfo
[Index
].LogFormat
) != 0) {
1605 if (mTcg2EventInfo
[Index
].LogFormat
== EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
) {
1606 Status
= gBS
->AllocatePages (
1609 EFI_SIZE_TO_PAGES (PcdGet32 (PcdTcg2FinalLogAreaLen
)),
1612 if (EFI_ERROR (Status
)) {
1615 SetMem ((VOID
*)(UINTN
)Lasa
, PcdGet32 (PcdTcg2FinalLogAreaLen
), 0xFF);
1620 mTcgDxeData
.FinalEventsTable
[Index
] = (VOID
*)(UINTN
)Lasa
;
1621 (mTcgDxeData
.FinalEventsTable
[Index
])->Version
= EFI_TCG2_FINAL_EVENTS_TABLE_VERSION
;
1622 (mTcgDxeData
.FinalEventsTable
[Index
])->NumberOfEvents
= 0;
1624 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogFormat
= mTcg2EventInfo
[Index
].LogFormat
;
1625 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].Lasa
= Lasa
+ sizeof(EFI_TCG2_FINAL_EVENTS_TABLE
);
1626 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].Laml
= PcdGet32 (PcdTcg2FinalLogAreaLen
) - sizeof(EFI_TCG2_FINAL_EVENTS_TABLE
);
1627 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogSize
= 0;
1628 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].LastEvent
= (VOID
*)(UINTN
)mTcgDxeData
.FinalEventLogAreaStruct
[Index
].Lasa
;
1629 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogStarted
= FALSE
;
1630 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogTruncated
= FALSE
;
1633 // Install to configuration table for EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
1635 Status
= gBS
->InstallConfigurationTable (&gEfiTcg2FinalEventsTableGuid
, (VOID
*)mTcgDxeData
.FinalEventsTable
[Index
]);
1636 if (EFI_ERROR (Status
)) {
1641 // No need to handle EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
1643 mTcgDxeData
.FinalEventsTable
[Index
] = NULL
;
1644 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogFormat
= mTcg2EventInfo
[Index
].LogFormat
;
1645 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].Lasa
= 0;
1646 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].Laml
= 0;
1647 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogSize
= 0;
1648 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].LastEvent
= 0;
1649 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogStarted
= FALSE
;
1650 mTcgDxeData
.FinalEventLogAreaStruct
[Index
].EventLogTruncated
= FALSE
;
1656 // 3. Sync data from PEI to DXE
1658 Status
= EFI_SUCCESS
;
1659 for (Index
= 0; Index
< sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]); Index
++) {
1660 if ((mTcgDxeData
.BsCap
.SupportedEventLogs
& mTcg2EventInfo
[Index
].LogFormat
) != 0) {
1661 GuidHob
.Raw
= GetHobList ();
1662 Status
= EFI_SUCCESS
;
1663 while (!EFI_ERROR (Status
) &&
1664 (GuidHob
.Raw
= GetNextGuidHob (mTcg2EventInfo
[Index
].EventGuid
, GuidHob
.Raw
)) != NULL
) {
1665 TcgEvent
= AllocateCopyPool (GET_GUID_HOB_DATA_SIZE (GuidHob
.Guid
), GET_GUID_HOB_DATA (GuidHob
.Guid
));
1666 ASSERT (TcgEvent
!= NULL
);
1667 GuidHob
.Raw
= GET_NEXT_HOB (GuidHob
);
1668 switch (mTcg2EventInfo
[Index
].LogFormat
) {
1669 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
:
1670 Status
= TcgDxeLogEvent (
1671 mTcg2EventInfo
[Index
].LogFormat
,
1673 sizeof(TCG_PCR_EVENT_HDR
),
1674 ((TCG_PCR_EVENT
*)TcgEvent
)->Event
,
1675 ((TCG_PCR_EVENT_HDR
*)TcgEvent
)->EventSize
1678 case EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
:
1679 DigestListBin
= (UINT8
*)TcgEvent
+ sizeof(TCG_PCRINDEX
) + sizeof(TCG_EVENTTYPE
);
1680 DigestListBinSize
= GetDigestListBinSize (DigestListBin
);
1684 CopyMem (&EventSize
, (UINT8
*)DigestListBin
+ DigestListBinSize
, sizeof(UINT32
));
1685 Event
= (UINT8
*)DigestListBin
+ DigestListBinSize
+ sizeof(UINT32
);
1687 // Filter inactive digest in the event2 log from PEI HOB.
1689 CopyMem (&TempDigestListBin
, DigestListBin
, GetDigestListBinSize (DigestListBin
));
1690 EventSizePtr
= CopyDigestListBinToBuffer (
1693 mTcgDxeData
.BsCap
.ActivePcrBanks
,
1694 &HashAlgorithmMaskCopied
1696 if (HashAlgorithmMaskCopied
!= mTcgDxeData
.BsCap
.ActivePcrBanks
) {
1699 "ERROR: The event2 log includes digest hash mask 0x%x, but required digest hash mask is 0x%x\n",
1700 HashAlgorithmMaskCopied
,
1701 mTcgDxeData
.BsCap
.ActivePcrBanks
1705 // Restore event size.
1707 CopyMem (EventSizePtr
, &EventSize
, sizeof(UINT32
));
1708 DigestListBinSize
= GetDigestListBinSize (DigestListBin
);
1710 Status
= TcgDxeLogEvent (
1711 mTcg2EventInfo
[Index
].LogFormat
,
1713 sizeof(TCG_PCRINDEX
) + sizeof(TCG_EVENTTYPE
) + DigestListBinSize
+ sizeof(UINT32
),
1719 FreePool (TcgEvent
);
1728 Measure and log an action string, and extend the measurement result into PCR[PCRIndex].
1730 @param[in] PCRIndex PCRIndex to extend
1731 @param[in] String A specific string that indicates an Action event.
1733 @retval EFI_SUCCESS Operation completed successfully.
1734 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1739 IN TPM_PCRINDEX PCRIndex
,
1743 TCG_PCR_EVENT_HDR TcgEvent
;
1745 TcgEvent
.PCRIndex
= PCRIndex
;
1746 TcgEvent
.EventType
= EV_EFI_ACTION
;
1747 TcgEvent
.EventSize
= (UINT32
)AsciiStrLen (String
);
1748 return TcgDxeHashLogExtendEvent (
1758 Measure and log EFI handoff tables, and extend the measurement result into PCR[1].
1760 @retval EFI_SUCCESS Operation completed successfully.
1761 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1765 MeasureHandoffTables (
1770 TCG_PCR_EVENT_HDR TcgEvent
;
1771 EFI_HANDOFF_TABLE_POINTERS HandoffTables
;
1773 EFI_CPU_PHYSICAL_LOCATION
*ProcessorLocBuf
;
1775 ProcessorLocBuf
= NULL
;
1776 Status
= EFI_SUCCESS
;
1778 if (PcdGet8 (PcdTpmPlatformClass
) == TCG_PLATFORM_TYPE_SERVER
) {
1781 // Measure each processor EFI_CPU_PHYSICAL_LOCATION with EV_TABLE_OF_DEVICES to PCR[1]
1783 Status
= GetProcessorsCpuLocation(&ProcessorLocBuf
, &ProcessorNum
);
1785 if (!EFI_ERROR(Status
)){
1786 TcgEvent
.PCRIndex
= 1;
1787 TcgEvent
.EventType
= EV_TABLE_OF_DEVICES
;
1788 TcgEvent
.EventSize
= sizeof (HandoffTables
);
1790 HandoffTables
.NumberOfTables
= 1;
1791 HandoffTables
.TableEntry
[0].VendorGuid
= gEfiMpServiceProtocolGuid
;
1792 HandoffTables
.TableEntry
[0].VendorTable
= ProcessorLocBuf
;
1794 Status
= TcgDxeHashLogExtendEvent (
1796 (UINT8
*)(UINTN
)ProcessorLocBuf
,
1797 sizeof(EFI_CPU_PHYSICAL_LOCATION
) * ProcessorNum
,
1799 (UINT8
*)&HandoffTables
1802 FreePool(ProcessorLocBuf
);
1810 Measure and log Separator event, and extend the measurement result into a specific PCR.
1812 @param[in] PCRIndex PCR index.
1814 @retval EFI_SUCCESS Operation completed successfully.
1815 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1819 MeasureSeparatorEvent (
1820 IN TPM_PCRINDEX PCRIndex
1823 TCG_PCR_EVENT_HDR TcgEvent
;
1826 DEBUG ((EFI_D_INFO
, "MeasureSeparatorEvent Pcr - %x\n", PCRIndex
));
1829 TcgEvent
.PCRIndex
= PCRIndex
;
1830 TcgEvent
.EventType
= EV_SEPARATOR
;
1831 TcgEvent
.EventSize
= (UINT32
)sizeof (EventData
);
1832 return TcgDxeHashLogExtendEvent (
1834 (UINT8
*)&EventData
,
1842 Measure and log an EFI variable, and extend the measurement result into a specific PCR.
1844 @param[in] PCRIndex PCR Index.
1845 @param[in] EventType Event type.
1846 @param[in] VarName A Null-terminated string that is the name of the vendor's variable.
1847 @param[in] VendorGuid A unique identifier for the vendor.
1848 @param[in] VarData The content of the variable data.
1849 @param[in] VarSize The size of the variable data.
1851 @retval EFI_SUCCESS Operation completed successfully.
1852 @retval EFI_OUT_OF_RESOURCES Out of memory.
1853 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1858 IN TPM_PCRINDEX PCRIndex
,
1859 IN TCG_EVENTTYPE EventType
,
1861 IN EFI_GUID
*VendorGuid
,
1867 TCG_PCR_EVENT_HDR TcgEvent
;
1868 UINTN VarNameLength
;
1869 UEFI_VARIABLE_DATA
*VarLog
;
1871 DEBUG ((EFI_D_INFO
, "Tcg2Dxe: MeasureVariable (Pcr - %x, EventType - %x, ", (UINTN
)PCRIndex
, (UINTN
)EventType
));
1872 DEBUG ((EFI_D_INFO
, "VariableName - %s, VendorGuid - %g)\n", VarName
, VendorGuid
));
1874 VarNameLength
= StrLen (VarName
);
1875 TcgEvent
.PCRIndex
= PCRIndex
;
1876 TcgEvent
.EventType
= EventType
;
1878 TcgEvent
.EventSize
= (UINT32
)(sizeof (*VarLog
) + VarNameLength
* sizeof (*VarName
) + VarSize
1879 - sizeof (VarLog
->UnicodeName
) - sizeof (VarLog
->VariableData
));
1881 VarLog
= (UEFI_VARIABLE_DATA
*)AllocatePool (TcgEvent
.EventSize
);
1882 if (VarLog
== NULL
) {
1883 return EFI_OUT_OF_RESOURCES
;
1886 VarLog
->VariableName
= *VendorGuid
;
1887 VarLog
->UnicodeNameLength
= VarNameLength
;
1888 VarLog
->VariableDataLength
= VarSize
;
1890 VarLog
->UnicodeName
,
1892 VarNameLength
* sizeof (*VarName
)
1894 if (VarSize
!= 0 && VarData
!= NULL
) {
1896 (CHAR16
*)VarLog
->UnicodeName
+ VarNameLength
,
1902 if (EventType
== EV_EFI_VARIABLE_DRIVER_CONFIG
) {
1904 // Digest is the event data (UEFI_VARIABLE_DATA)
1906 Status
= TcgDxeHashLogExtendEvent (
1914 ASSERT (VarData
!= NULL
);
1915 Status
= TcgDxeHashLogExtendEvent (
1928 Read then Measure and log an EFI variable, and extend the measurement result into a specific PCR.
1930 @param[in] PCRIndex PCR Index.
1931 @param[in] EventType Event type.
1932 @param[in] VarName A Null-terminated string that is the name of the vendor's variable.
1933 @param[in] VendorGuid A unique identifier for the vendor.
1934 @param[out] VarSize The size of the variable data.
1935 @param[out] VarData Pointer to the content of the variable.
1937 @retval EFI_SUCCESS Operation completed successfully.
1938 @retval EFI_OUT_OF_RESOURCES Out of memory.
1939 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1943 ReadAndMeasureVariable (
1944 IN TPM_PCRINDEX PCRIndex
,
1945 IN TCG_EVENTTYPE EventType
,
1947 IN EFI_GUID
*VendorGuid
,
1954 Status
= GetVariable2 (VarName
, VendorGuid
, VarData
, VarSize
);
1955 if (EventType
== EV_EFI_VARIABLE_DRIVER_CONFIG
) {
1956 if (EFI_ERROR (Status
)) {
1958 // It is valid case, so we need handle it.
1965 // if status error, VarData is freed and set NULL by GetVariable2
1967 if (EFI_ERROR (Status
)) {
1968 return EFI_NOT_FOUND
;
1972 Status
= MeasureVariable (
1984 Read then Measure and log an EFI boot variable, and extend the measurement result into PCR[1].
1985 according to TCG PC Client PFP spec 0021 Section 2.4.4.2
1987 @param[in] VarName A Null-terminated string that is the name of the vendor's variable.
1988 @param[in] VendorGuid A unique identifier for the vendor.
1989 @param[out] VarSize The size of the variable data.
1990 @param[out] VarData Pointer to the content of the variable.
1992 @retval EFI_SUCCESS Operation completed successfully.
1993 @retval EFI_OUT_OF_RESOURCES Out of memory.
1994 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
1998 ReadAndMeasureBootVariable (
2000 IN EFI_GUID
*VendorGuid
,
2005 return ReadAndMeasureVariable (
2007 EV_EFI_VARIABLE_BOOT
,
2016 Read then Measure and log an EFI Secure variable, and extend the measurement result into PCR[7].
2018 @param[in] VarName A Null-terminated string that is the name of the vendor's variable.
2019 @param[in] VendorGuid A unique identifier for the vendor.
2020 @param[out] VarSize The size of the variable data.
2021 @param[out] VarData Pointer to the content of the variable.
2023 @retval EFI_SUCCESS Operation completed successfully.
2024 @retval EFI_OUT_OF_RESOURCES Out of memory.
2025 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
2029 ReadAndMeasureSecureVariable (
2031 IN EFI_GUID
*VendorGuid
,
2036 return ReadAndMeasureVariable (
2038 EV_EFI_VARIABLE_DRIVER_CONFIG
,
2047 Measure and log all EFI boot variables, and extend the measurement result into a specific PCR.
2049 The EFI boot variables are BootOrder and Boot#### variables.
2051 @retval EFI_SUCCESS Operation completed successfully.
2052 @retval EFI_OUT_OF_RESOURCES Out of memory.
2053 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
2057 MeasureAllBootVariables (
2068 Status
= ReadAndMeasureBootVariable (
2070 &gEfiGlobalVariableGuid
,
2072 (VOID
**) &BootOrder
2074 if (Status
== EFI_NOT_FOUND
|| BootOrder
== NULL
) {
2078 if (EFI_ERROR (Status
)) {
2080 // BootOrder can't be NULL if status is not EFI_NOT_FOUND
2082 FreePool (BootOrder
);
2086 BootCount
/= sizeof (*BootOrder
);
2087 for (Index
= 0; Index
< BootCount
; Index
++) {
2088 UnicodeSPrint (mBootVarName
, sizeof (mBootVarName
), L
"Boot%04x", BootOrder
[Index
]);
2089 Status
= ReadAndMeasureBootVariable (
2091 &gEfiGlobalVariableGuid
,
2095 if (!EFI_ERROR (Status
)) {
2096 FreePool (BootVarData
);
2100 FreePool (BootOrder
);
2105 Measure and log all EFI Secure variables, and extend the measurement result into a specific PCR.
2107 The EFI boot variables are BootOrder and Boot#### variables.
2109 @retval EFI_SUCCESS Operation completed successfully.
2110 @retval EFI_OUT_OF_RESOURCES Out of memory.
2111 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
2115 MeasureAllSecureVariables (
2124 Status
= EFI_NOT_FOUND
;
2125 for (Index
= 0; Index
< sizeof(mVariableType
)/sizeof(mVariableType
[0]); Index
++) {
2126 Status
= ReadAndMeasureSecureVariable (
2127 mVariableType
[Index
].VariableName
,
2128 mVariableType
[Index
].VendorGuid
,
2132 if (!EFI_ERROR (Status
)) {
2140 // Measure DBT if present and not empty
2142 Status
= GetVariable2 (EFI_IMAGE_SECURITY_DATABASE2
, &gEfiImageSecurityDatabaseGuid
, &Data
, &DataSize
);
2143 if (!EFI_ERROR(Status
)) {
2144 Status
= MeasureVariable (
2146 EV_EFI_VARIABLE_DRIVER_CONFIG
,
2147 EFI_IMAGE_SECURITY_DATABASE2
,
2148 &gEfiImageSecurityDatabaseGuid
,
2154 DEBUG((DEBUG_INFO
, "Skip measuring variable %s since it's deleted\n", EFI_IMAGE_SECURITY_DATABASE2
));
2161 Measure and log launch of FirmwareDebugger, and extend the measurement result into a specific PCR.
2163 @retval EFI_SUCCESS Operation completed successfully.
2164 @retval EFI_OUT_OF_RESOURCES Out of memory.
2165 @retval EFI_DEVICE_ERROR The operation was unsuccessful.
2169 MeasureLaunchOfFirmwareDebugger (
2173 TCG_PCR_EVENT_HDR TcgEvent
;
2175 TcgEvent
.PCRIndex
= 7;
2176 TcgEvent
.EventType
= EV_EFI_ACTION
;
2177 TcgEvent
.EventSize
= sizeof(FIRMWARE_DEBUGGER_EVENT_STRING
) - 1;
2178 return TcgDxeHashLogExtendEvent (
2180 (UINT8
*)FIRMWARE_DEBUGGER_EVENT_STRING
,
2181 sizeof(FIRMWARE_DEBUGGER_EVENT_STRING
) - 1,
2183 (UINT8
*)FIRMWARE_DEBUGGER_EVENT_STRING
2188 Measure and log all Secure Boot Policy, and extend the measurement result into a specific PCR.
2190 Platform firmware adhering to the policy must therefore measure the following values into PCR[7]: (in order listed)
2191 - The contents of the SecureBoot variable
2192 - The contents of the PK variable
2193 - The contents of the KEK variable
2194 - The contents of the EFI_IMAGE_SECURITY_DATABASE variable
2195 - The contents of the EFI_IMAGE_SECURITY_DATABASE1 variable
2197 - Entries in the EFI_IMAGE_SECURITY_DATABASE that are used to validate EFI Drivers or EFI Boot Applications in the boot path
2199 NOTE: Because of the above, UEFI variables PK, KEK, EFI_IMAGE_SECURITY_DATABASE,
2200 EFI_IMAGE_SECURITY_DATABASE1 and SecureBoot SHALL NOT be measured into PCR[3].
2202 @param[in] Event Event whose notification function is being invoked
2203 @param[in] Context Pointer to the notification function's context
2207 MeasureSecureBootPolicy (
2215 Status
= gBS
->LocateProtocol (&gEfiVariableWriteArchProtocolGuid
, NULL
, (VOID
**)&Protocol
);
2216 if (EFI_ERROR (Status
)) {
2220 if (PcdGetBool (PcdFirmwareDebuggerInitialized
)) {
2221 Status
= MeasureLaunchOfFirmwareDebugger ();
2222 DEBUG ((EFI_D_INFO
, "MeasureLaunchOfFirmwareDebugger - %r\n", Status
));
2225 Status
= MeasureAllSecureVariables ();
2226 DEBUG ((EFI_D_INFO
, "MeasureAllSecureVariables - %r\n", Status
));
2229 // We need measure Separator(7) here, because this event must be between SecureBootPolicy (Configure)
2230 // and ImageVerification (Authority)
2231 // There might be a case that we need measure UEFI image from DriverOrder, besides BootOrder. So
2232 // the Authority measurement happen before ReadToBoot event.
2234 Status
= MeasureSeparatorEvent (7);
2235 DEBUG ((EFI_D_INFO
, "MeasureSeparatorEvent - %r\n", Status
));
2240 Ready to Boot Event notification handler.
2242 Sequence of OS boot events is measured in this event notification handler.
2244 @param[in] Event Event whose notification function is being invoked
2245 @param[in] Context Pointer to the notification function's context
2256 TPM_PCRINDEX PcrIndex
;
2258 PERF_START_EX (mImageHandle
, "EventRec", "Tcg2Dxe", 0, PERF_ID_TCG2_DXE
);
2259 if (mBootAttempts
== 0) {
2262 // Measure handoff tables.
2264 Status
= MeasureHandoffTables ();
2265 if (EFI_ERROR (Status
)) {
2266 DEBUG ((EFI_D_ERROR
, "HOBs not Measured. Error!\n"));
2270 // Measure BootOrder & Boot#### variables.
2272 Status
= MeasureAllBootVariables ();
2273 if (EFI_ERROR (Status
)) {
2274 DEBUG ((EFI_D_ERROR
, "Boot Variables not Measured. Error!\n"));
2278 // 1. This is the first boot attempt.
2280 Status
= TcgMeasureAction (
2282 EFI_CALLING_EFI_APPLICATION
2284 if (EFI_ERROR (Status
)) {
2285 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_CALLING_EFI_APPLICATION
));
2289 // 2. Draw a line between pre-boot env and entering post-boot env.
2290 // PCR[7] is already done.
2292 for (PcrIndex
= 0; PcrIndex
< 7; PcrIndex
++) {
2293 Status
= MeasureSeparatorEvent (PcrIndex
);
2294 if (EFI_ERROR (Status
)) {
2295 DEBUG ((DEBUG_ERROR
, "Separator Event not Measured. Error!\n"));
2300 // 3. Measure GPT. It would be done in SAP driver.
2304 // 4. Measure PE/COFF OS loader. It would be done in SAP driver.
2308 // 5. Read & Measure variable. BootOrder already measured.
2312 // 6. Not first attempt, meaning a return from last attempt
2314 Status
= TcgMeasureAction (
2316 EFI_RETURNING_FROM_EFI_APPLICATOIN
2318 if (EFI_ERROR (Status
)) {
2319 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_RETURNING_FROM_EFI_APPLICATOIN
));
2323 // 7. Next boot attempt, measure "Calling EFI Application from Boot Option" again
2324 // TCG PC Client PFP spec Section 2.4.4.5 Step 4
2326 Status
= TcgMeasureAction (
2328 EFI_CALLING_EFI_APPLICATION
2330 if (EFI_ERROR (Status
)) {
2331 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_CALLING_EFI_APPLICATION
));
2335 DEBUG ((EFI_D_INFO
, "TPM2 Tcg2Dxe Measure Data when ReadyToBoot\n"));
2337 // Increase boot attempt counter.
2340 PERF_END_EX (mImageHandle
, "EventRec", "Tcg2Dxe", 0, PERF_ID_TCG2_DXE
+ 1);
2344 Exit Boot Services Event notification handler.
2346 Measure invocation and success of ExitBootServices.
2348 @param[in] Event Event whose notification function is being invoked
2349 @param[in] Context Pointer to the notification function's context
2354 OnExitBootServices (
2362 // Measure invocation of ExitBootServices,
2364 Status
= TcgMeasureAction (
2366 EFI_EXIT_BOOT_SERVICES_INVOCATION
2368 if (EFI_ERROR (Status
)) {
2369 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_EXIT_BOOT_SERVICES_INVOCATION
));
2373 // Measure success of ExitBootServices
2375 Status
= TcgMeasureAction (
2377 EFI_EXIT_BOOT_SERVICES_SUCCEEDED
2379 if (EFI_ERROR (Status
)) {
2380 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_EXIT_BOOT_SERVICES_SUCCEEDED
));
2385 Exit Boot Services Failed Event notification handler.
2387 Measure Failure of ExitBootServices.
2389 @param[in] Event Event whose notification function is being invoked
2390 @param[in] Context Pointer to the notification function's context
2395 OnExitBootServicesFailed (
2403 // Measure Failure of ExitBootServices,
2405 Status
= TcgMeasureAction (
2407 EFI_EXIT_BOOT_SERVICES_FAILED
2409 if (EFI_ERROR (Status
)) {
2410 DEBUG ((EFI_D_ERROR
, "%a not Measured. Error!\n", EFI_EXIT_BOOT_SERVICES_FAILED
));
2416 The function install Tcg2 protocol.
2418 @retval EFI_SUCCESS Tcg2 protocol is installed.
2419 @retval other Some error occurs.
2430 Status
= gBS
->InstallMultipleProtocolInterfaces (
2432 &gEfiTcg2ProtocolGuid
,
2440 The driver's entry point. It publishes EFI Tcg2 Protocol.
2442 @param[in] ImageHandle The firmware allocated handle for the EFI image.
2443 @param[in] SystemTable A pointer to the EFI System Table.
2445 @retval EFI_SUCCESS The entry point is executed successfully.
2446 @retval other Some error occurs when executing this entry point.
2451 IN EFI_HANDLE ImageHandle
,
2452 IN EFI_SYSTEM_TABLE
*SystemTable
2458 UINT32 MaxCommandSize
;
2459 UINT32 MaxResponseSize
;
2461 EFI_TCG2_EVENT_ALGORITHM_BITMAP TpmHashAlgorithmBitmap
;
2462 UINT32 ActivePCRBanks
;
2463 UINT32 NumberOfPCRBanks
;
2465 mImageHandle
= ImageHandle
;
2467 if (CompareGuid (PcdGetPtr(PcdTpmInstanceGuid
), &gEfiTpmDeviceInstanceNoneGuid
) ||
2468 CompareGuid (PcdGetPtr(PcdTpmInstanceGuid
), &gEfiTpmDeviceInstanceTpm12Guid
)){
2469 DEBUG ((EFI_D_ERROR
, "No TPM2 instance required!\n"));
2470 return EFI_UNSUPPORTED
;
2473 if (GetFirstGuidHob (&gTpmErrorHobGuid
) != NULL
) {
2474 DEBUG ((EFI_D_ERROR
, "TPM2 error!\n"));
2475 return EFI_DEVICE_ERROR
;
2478 Status
= Tpm2RequestUseTpm ();
2479 if (EFI_ERROR (Status
)) {
2480 DEBUG ((EFI_D_ERROR
, "TPM2 not detected!\n"));
2487 ASSERT (TCG_EVENT_LOG_AREA_COUNT_MAX
== sizeof(mTcg2EventInfo
)/sizeof(mTcg2EventInfo
[0]));
2489 mTcgDxeData
.BsCap
.Size
= sizeof(EFI_TCG2_BOOT_SERVICE_CAPABILITY
);
2490 mTcgDxeData
.BsCap
.ProtocolVersion
.Major
= 1;
2491 mTcgDxeData
.BsCap
.ProtocolVersion
.Minor
= 1;
2492 mTcgDxeData
.BsCap
.StructureVersion
.Major
= 1;
2493 mTcgDxeData
.BsCap
.StructureVersion
.Minor
= 1;
2495 DEBUG ((EFI_D_INFO
, "Tcg2.ProtocolVersion - %02x.%02x\n", mTcgDxeData
.BsCap
.ProtocolVersion
.Major
, mTcgDxeData
.BsCap
.ProtocolVersion
.Minor
));
2496 DEBUG ((EFI_D_INFO
, "Tcg2.StructureVersion - %02x.%02x\n", mTcgDxeData
.BsCap
.StructureVersion
.Major
, mTcgDxeData
.BsCap
.StructureVersion
.Minor
));
2498 Status
= Tpm2GetCapabilityManufactureID (&mTcgDxeData
.BsCap
.ManufacturerID
);
2499 if (EFI_ERROR (Status
)) {
2500 DEBUG ((EFI_D_ERROR
, "Tpm2GetCapabilityManufactureID fail!\n"));
2502 DEBUG ((EFI_D_INFO
, "Tpm2GetCapabilityManufactureID - %08x\n", mTcgDxeData
.BsCap
.ManufacturerID
));
2506 UINT32 FirmwareVersion1
;
2507 UINT32 FirmwareVersion2
;
2509 Status
= Tpm2GetCapabilityFirmwareVersion (&FirmwareVersion1
, &FirmwareVersion2
);
2510 if (EFI_ERROR (Status
)) {
2511 DEBUG ((EFI_D_ERROR
, "Tpm2GetCapabilityFirmwareVersion fail!\n"));
2513 DEBUG ((EFI_D_INFO
, "Tpm2GetCapabilityFirmwareVersion - %08x %08x\n", FirmwareVersion1
, FirmwareVersion2
));
2517 Status
= Tpm2GetCapabilityMaxCommandResponseSize (&MaxCommandSize
, &MaxResponseSize
);
2518 if (EFI_ERROR (Status
)) {
2519 DEBUG ((EFI_D_ERROR
, "Tpm2GetCapabilityMaxCommandResponseSize fail!\n"));
2521 mTcgDxeData
.BsCap
.MaxCommandSize
= (UINT16
)MaxCommandSize
;
2522 mTcgDxeData
.BsCap
.MaxResponseSize
= (UINT16
)MaxResponseSize
;
2523 DEBUG ((EFI_D_INFO
, "Tpm2GetCapabilityMaxCommandResponseSize - %08x, %08x\n", MaxCommandSize
, MaxResponseSize
));
2527 // Get supported PCR and current Active PCRs
2529 Status
= Tpm2GetCapabilitySupportedAndActivePcrs (&TpmHashAlgorithmBitmap
, &ActivePCRBanks
);
2530 ASSERT_EFI_ERROR (Status
);
2532 mTcgDxeData
.BsCap
.HashAlgorithmBitmap
= TpmHashAlgorithmBitmap
& PcdGet32 (PcdTcg2HashAlgorithmBitmap
);
2533 mTcgDxeData
.BsCap
.ActivePcrBanks
= ActivePCRBanks
& PcdGet32 (PcdTcg2HashAlgorithmBitmap
);
2536 // Need calculate NumberOfPCRBanks here, because HashAlgorithmBitmap might be removed by PCD.
2538 NumberOfPCRBanks
= 0;
2539 for (Index
= 0; Index
< 32; Index
++) {
2540 if ((mTcgDxeData
.BsCap
.HashAlgorithmBitmap
& (1u << Index
)) != 0) {
2545 if (PcdGet32 (PcdTcg2NumberOfPCRBanks
) == 0) {
2546 mTcgDxeData
.BsCap
.NumberOfPCRBanks
= NumberOfPCRBanks
;
2548 mTcgDxeData
.BsCap
.NumberOfPCRBanks
= PcdGet32 (PcdTcg2NumberOfPCRBanks
);
2549 if (PcdGet32 (PcdTcg2NumberOfPCRBanks
) > NumberOfPCRBanks
) {
2550 DEBUG ((EFI_D_ERROR
, "ERROR: PcdTcg2NumberOfPCRBanks(0x%x) > NumberOfPCRBanks(0x%x)\n", PcdGet32 (PcdTcg2NumberOfPCRBanks
), NumberOfPCRBanks
));
2551 mTcgDxeData
.BsCap
.NumberOfPCRBanks
= NumberOfPCRBanks
;
2555 mTcgDxeData
.BsCap
.SupportedEventLogs
= EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
| EFI_TCG2_EVENT_LOG_FORMAT_TCG_2
;
2556 if ((mTcgDxeData
.BsCap
.ActivePcrBanks
& EFI_TCG2_BOOT_HASH_ALG_SHA1
) == 0) {
2558 // No need to expose TCG1.2 event log if SHA1 bank does not exist.
2560 mTcgDxeData
.BsCap
.SupportedEventLogs
&= ~EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2
;
2563 DEBUG ((EFI_D_INFO
, "Tcg2.SupportedEventLogs - 0x%08x\n", mTcgDxeData
.BsCap
.SupportedEventLogs
));
2564 DEBUG ((EFI_D_INFO
, "Tcg2.HashAlgorithmBitmap - 0x%08x\n", mTcgDxeData
.BsCap
.HashAlgorithmBitmap
));
2565 DEBUG ((EFI_D_INFO
, "Tcg2.NumberOfPCRBanks - 0x%08x\n", mTcgDxeData
.BsCap
.NumberOfPCRBanks
));
2566 DEBUG ((EFI_D_INFO
, "Tcg2.ActivePcrBanks - 0x%08x\n", mTcgDxeData
.BsCap
.ActivePcrBanks
));
2568 if (mTcgDxeData
.BsCap
.TPMPresentFlag
) {
2570 // Setup the log area and copy event log from hob list to it
2572 Status
= SetupEventLog ();
2573 ASSERT_EFI_ERROR (Status
);
2576 // Measure handoff tables, Boot#### variables etc.
2578 Status
= EfiCreateEventReadyToBootEx (
2585 Status
= gBS
->CreateEventEx (
2590 &gEfiEventExitBootServicesGuid
,
2595 // Measure Exit Boot Service failed
2597 Status
= gBS
->CreateEventEx (
2600 OnExitBootServicesFailed
,
2602 &gEventExitBootServicesFailedGuid
,
2607 // Create event callback, because we need access variable on SecureBootPolicyVariable
2608 // We should use VariableWriteArch instead of VariableArch, because Variable driver
2609 // may update SecureBoot value based on last setting.
2611 EfiCreateProtocolNotifyEvent (&gEfiVariableWriteArchProtocolGuid
, TPL_CALLBACK
, MeasureSecureBootPolicy
, NULL
, &Registration
);
2615 // Install Tcg2Protocol
2617 Status
= InstallTcg2 ();
2618 DEBUG ((EFI_D_INFO
, "InstallTcg2 - %r\n", Status
));