Signed-off-by: Jinhua Cao <caojinhua1@huawei.com> Signed-off-by: yezengruan <yezengruan@huawei.com>
379 lines
11 KiB
Diff
379 lines
11 KiB
Diff
From 6642e762e1cedae30a08e28c456de2372bda7766 Mon Sep 17 00:00:00 2001
|
|
From: Stefan Berger <stefanb@linux.vnet.ibm.com>
|
|
Date: Mon, 13 Sep 2021 22:20:57 +0800
|
|
Subject: [PATCH 1/8] SecurityPkg/TPM: Import PeiDxeTpmPlatformHierarchyLib.c
|
|
from edk2-platforms
|
|
|
|
Import PeiDxeTpmPlatformHierarchyLib from edk2-platforms without any
|
|
modifications.
|
|
|
|
Signed-off-by: Stefan Berger <stefanb@linux.ibm.com>
|
|
---
|
|
.../Include/Library/TpmPlatformHierarchyLib.h | 27 ++
|
|
.../PeiDxeTpmPlatformHierarchyLib.c | 266 ++++++++++++++++++
|
|
.../PeiDxeTpmPlatformHierarchyLib.inf | 45 +++
|
|
3 files changed, 338 insertions(+)
|
|
create mode 100644 SecurityPkg/Include/Library/TpmPlatformHierarchyLib.h
|
|
create mode 100644 SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.c
|
|
create mode 100644 SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.inf
|
|
|
|
diff --git a/SecurityPkg/Include/Library/TpmPlatformHierarchyLib.h b/SecurityPkg/Include/Library/TpmPlatformHierarchyLib.h
|
|
new file mode 100644
|
|
index 0000000000..a872fa09dc
|
|
--- /dev/null
|
|
+++ b/SecurityPkg/Include/Library/TpmPlatformHierarchyLib.h
|
|
@@ -0,0 +1,27 @@
|
|
+/** @file
|
|
+ TPM Platform Hierarchy configuration library.
|
|
+
|
|
+ This library provides functions for customizing the TPM's Platform Hierarchy
|
|
+ Authorization Value (platformAuth) and Platform Hierarchy Authorization
|
|
+ Policy (platformPolicy) can be defined through this function.
|
|
+
|
|
+Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
|
|
+Copyright (c) Microsoft Corporation.<BR>
|
|
+SPDX-License-Identifier: BSD-2-Clause-Patent
|
|
+
|
|
+**/
|
|
+
|
|
+#ifndef _TPM_PLATFORM_HIERARCHY_LIB_H_
|
|
+#define _TPM_PLATFORM_HIERARCHY_LIB_H_
|
|
+
|
|
+/**
|
|
+ This service will perform the TPM Platform Hierarchy configuration at the SmmReadyToLock event.
|
|
+
|
|
+**/
|
|
+VOID
|
|
+EFIAPI
|
|
+ConfigureTpmPlatformHierarchy (
|
|
+ VOID
|
|
+ );
|
|
+
|
|
+#endif
|
|
diff --git a/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.c b/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.c
|
|
new file mode 100644
|
|
index 0000000000..9812ab99ab
|
|
--- /dev/null
|
|
+++ b/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.c
|
|
@@ -0,0 +1,266 @@
|
|
+/** @file
|
|
+ TPM Platform Hierarchy configuration library.
|
|
+
|
|
+ This library provides functions for customizing the TPM's Platform Hierarchy
|
|
+ Authorization Value (platformAuth) and Platform Hierarchy Authorization
|
|
+ Policy (platformPolicy) can be defined through this function.
|
|
+
|
|
+ Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
|
|
+ Copyright (c) Microsoft Corporation.<BR>
|
|
+ SPDX-License-Identifier: BSD-2-Clause-Patent
|
|
+
|
|
+ @par Specification Reference:
|
|
+ https://trustedcomputinggroup.org/resource/tcg-tpm-v2-0-provisioning-guidance/
|
|
+**/
|
|
+
|
|
+#include <Uefi.h>
|
|
+
|
|
+#include <Library/BaseMemoryLib.h>
|
|
+#include <Library/DebugLib.h>
|
|
+#include <Library/MemoryAllocationLib.h>
|
|
+#include <Library/PcdLib.h>
|
|
+#include <Library/RngLib.h>
|
|
+#include <Library/Tpm2CommandLib.h>
|
|
+#include <Library/Tpm2DeviceLib.h>
|
|
+
|
|
+//
|
|
+// The authorization value may be no larger than the digest produced by the hash
|
|
+// algorithm used for context integrity.
|
|
+//
|
|
+#define MAX_NEW_AUTHORIZATION_SIZE SHA512_DIGEST_SIZE
|
|
+
|
|
+UINT16 mAuthSize;
|
|
+
|
|
+/**
|
|
+ Generate high-quality entropy source through RDRAND.
|
|
+
|
|
+ @param[in] Length Size of the buffer, in bytes, to fill with.
|
|
+ @param[out] Entropy Pointer to the buffer to store the entropy data.
|
|
+
|
|
+ @retval EFI_SUCCESS Entropy generation succeeded.
|
|
+ @retval EFI_NOT_READY Failed to request random data.
|
|
+
|
|
+**/
|
|
+EFI_STATUS
|
|
+EFIAPI
|
|
+RdRandGenerateEntropy (
|
|
+ IN UINTN Length,
|
|
+ OUT UINT8 *Entropy
|
|
+ )
|
|
+{
|
|
+ EFI_STATUS Status;
|
|
+ UINTN BlockCount;
|
|
+ UINT64 Seed[2];
|
|
+ UINT8 *Ptr;
|
|
+
|
|
+ Status = EFI_NOT_READY;
|
|
+ BlockCount = Length / 64;
|
|
+ Ptr = (UINT8 *)Entropy;
|
|
+
|
|
+ //
|
|
+ // Generate high-quality seed for DRBG Entropy
|
|
+ //
|
|
+ while (BlockCount > 0) {
|
|
+ Status = GetRandomNumber128 (Seed);
|
|
+ if (EFI_ERROR (Status)) {
|
|
+ return Status;
|
|
+ }
|
|
+ CopyMem (Ptr, Seed, 64);
|
|
+
|
|
+ BlockCount--;
|
|
+ Ptr = Ptr + 64;
|
|
+ }
|
|
+
|
|
+ //
|
|
+ // Populate the remained data as request.
|
|
+ //
|
|
+ Status = GetRandomNumber128 (Seed);
|
|
+ if (EFI_ERROR (Status)) {
|
|
+ return Status;
|
|
+ }
|
|
+ CopyMem (Ptr, Seed, (Length % 64));
|
|
+
|
|
+ return Status;
|
|
+}
|
|
+
|
|
+/**
|
|
+ This function returns the maximum size of TPM2B_AUTH; this structure is used for an authorization value
|
|
+ and limits an authValue to being no larger than the largest digest produced by a TPM.
|
|
+
|
|
+ @param[out] AuthSize Tpm2 Auth size
|
|
+
|
|
+ @retval EFI_SUCCESS Auth size returned.
|
|
+ @retval EFI_DEVICE_ERROR Can not return platform auth due to device error.
|
|
+
|
|
+**/
|
|
+EFI_STATUS
|
|
+EFIAPI
|
|
+GetAuthSize (
|
|
+ OUT UINT16 *AuthSize
|
|
+ )
|
|
+{
|
|
+ EFI_STATUS Status;
|
|
+ TPML_PCR_SELECTION Pcrs;
|
|
+ UINTN Index;
|
|
+ UINT16 DigestSize;
|
|
+
|
|
+ Status = EFI_SUCCESS;
|
|
+
|
|
+ while (mAuthSize == 0) {
|
|
+
|
|
+ mAuthSize = SHA1_DIGEST_SIZE;
|
|
+ ZeroMem (&Pcrs, sizeof (TPML_PCR_SELECTION));
|
|
+ Status = Tpm2GetCapabilityPcrs (&Pcrs);
|
|
+
|
|
+ if (EFI_ERROR (Status)) {
|
|
+ DEBUG ((DEBUG_ERROR, "Tpm2GetCapabilityPcrs fail!\n"));
|
|
+ break;
|
|
+ }
|
|
+
|
|
+ DEBUG ((DEBUG_ERROR, "Tpm2GetCapabilityPcrs - %08x\n", Pcrs.count));
|
|
+
|
|
+ for (Index = 0; Index < Pcrs.count; Index++) {
|
|
+ DEBUG ((DEBUG_ERROR, "alg - %x\n", Pcrs.pcrSelections[Index].hash));
|
|
+
|
|
+ switch (Pcrs.pcrSelections[Index].hash) {
|
|
+ case TPM_ALG_SHA1:
|
|
+ DigestSize = SHA1_DIGEST_SIZE;
|
|
+ break;
|
|
+ case TPM_ALG_SHA256:
|
|
+ DigestSize = SHA256_DIGEST_SIZE;
|
|
+ break;
|
|
+ case TPM_ALG_SHA384:
|
|
+ DigestSize = SHA384_DIGEST_SIZE;
|
|
+ break;
|
|
+ case TPM_ALG_SHA512:
|
|
+ DigestSize = SHA512_DIGEST_SIZE;
|
|
+ break;
|
|
+ case TPM_ALG_SM3_256:
|
|
+ DigestSize = SM3_256_DIGEST_SIZE;
|
|
+ break;
|
|
+ default:
|
|
+ DigestSize = SHA1_DIGEST_SIZE;
|
|
+ break;
|
|
+ }
|
|
+
|
|
+ if (DigestSize > mAuthSize) {
|
|
+ mAuthSize = DigestSize;
|
|
+ }
|
|
+ }
|
|
+ break;
|
|
+ }
|
|
+
|
|
+ *AuthSize = mAuthSize;
|
|
+ return Status;
|
|
+}
|
|
+
|
|
+/**
|
|
+ Set PlatformAuth to random value.
|
|
+**/
|
|
+VOID
|
|
+RandomizePlatformAuth (
|
|
+ VOID
|
|
+ )
|
|
+{
|
|
+ EFI_STATUS Status;
|
|
+ UINT16 AuthSize;
|
|
+ UINT8 *Rand;
|
|
+ UINTN RandSize;
|
|
+ TPM2B_AUTH NewPlatformAuth;
|
|
+
|
|
+ //
|
|
+ // Send Tpm2HierarchyChange Auth with random value to avoid PlatformAuth being null
|
|
+ //
|
|
+
|
|
+ GetAuthSize (&AuthSize);
|
|
+
|
|
+ ZeroMem (NewPlatformAuth.buffer, AuthSize);
|
|
+ NewPlatformAuth.size = AuthSize;
|
|
+
|
|
+ //
|
|
+ // Allocate one buffer to store random data.
|
|
+ //
|
|
+ RandSize = MAX_NEW_AUTHORIZATION_SIZE;
|
|
+ Rand = AllocatePool (RandSize);
|
|
+
|
|
+ RdRandGenerateEntropy (RandSize, Rand);
|
|
+ CopyMem (NewPlatformAuth.buffer, Rand, AuthSize);
|
|
+
|
|
+ FreePool (Rand);
|
|
+
|
|
+ //
|
|
+ // Send Tpm2HierarchyChangeAuth command with the new Auth value
|
|
+ //
|
|
+ Status = Tpm2HierarchyChangeAuth (TPM_RH_PLATFORM, NULL, &NewPlatformAuth);
|
|
+ DEBUG ((DEBUG_INFO, "Tpm2HierarchyChangeAuth Result: - %r\n", Status));
|
|
+ ZeroMem (NewPlatformAuth.buffer, AuthSize);
|
|
+ ZeroMem (Rand, RandSize);
|
|
+}
|
|
+
|
|
+/**
|
|
+ Disable the TPM platform hierarchy.
|
|
+
|
|
+ @retval EFI_SUCCESS The TPM was disabled successfully.
|
|
+ @retval Others An error occurred attempting to disable the TPM platform hierarchy.
|
|
+
|
|
+**/
|
|
+EFI_STATUS
|
|
+DisableTpmPlatformHierarchy (
|
|
+ VOID
|
|
+ )
|
|
+{
|
|
+ EFI_STATUS Status;
|
|
+
|
|
+ // Make sure that we have use of the TPM.
|
|
+ Status = Tpm2RequestUseTpm ();
|
|
+ if (EFI_ERROR (Status)) {
|
|
+ DEBUG ((DEBUG_ERROR, "%a:%a() - Tpm2RequestUseTpm Failed! %r\n", gEfiCallerBaseName, __FUNCTION__, Status));
|
|
+ ASSERT_EFI_ERROR (Status);
|
|
+ return Status;
|
|
+ }
|
|
+
|
|
+ // Let's do what we can to shut down the hierarchies.
|
|
+
|
|
+ // Disable the PH NV.
|
|
+ // IMPORTANT NOTE: We *should* be able to disable the PH NV here, but TPM parts have
|
|
+ // been known to store the EK cert in the PH NV. If we disable it, the
|
|
+ // EK cert will be unreadable.
|
|
+
|
|
+ // Disable the PH.
|
|
+ Status = Tpm2HierarchyControl (
|
|
+ TPM_RH_PLATFORM, // AuthHandle
|
|
+ NULL, // AuthSession
|
|
+ TPM_RH_PLATFORM, // Hierarchy
|
|
+ NO // State
|
|
+ );
|
|
+ DEBUG ((DEBUG_VERBOSE, "%a:%a() - Disable PH = %r\n", gEfiCallerBaseName, __FUNCTION__, Status));
|
|
+ if (EFI_ERROR (Status)) {
|
|
+ DEBUG ((DEBUG_ERROR, "%a:%a() - Disable PH Failed! %r\n", gEfiCallerBaseName, __FUNCTION__, Status));
|
|
+ ASSERT_EFI_ERROR (Status);
|
|
+ }
|
|
+
|
|
+ return Status;
|
|
+}
|
|
+
|
|
+/**
|
|
+ This service defines the configuration of the Platform Hierarchy Authorization Value (platformAuth)
|
|
+ and Platform Hierarchy Authorization Policy (platformPolicy)
|
|
+
|
|
+**/
|
|
+VOID
|
|
+EFIAPI
|
|
+ConfigureTpmPlatformHierarchy (
|
|
+ )
|
|
+{
|
|
+ if (PcdGetBool (PcdRandomizePlatformHierarchy)) {
|
|
+ //
|
|
+ // Send Tpm2HierarchyChange Auth with random value to avoid PlatformAuth being null
|
|
+ //
|
|
+ RandomizePlatformAuth ();
|
|
+ } else {
|
|
+ //
|
|
+ // Disable the hierarchy entirely (do not randomize it)
|
|
+ //
|
|
+ DisableTpmPlatformHierarchy ();
|
|
+ }
|
|
+}
|
|
diff --git a/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.inf b/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.inf
|
|
new file mode 100644
|
|
index 0000000000..b7a7fb0a08
|
|
--- /dev/null
|
|
+++ b/SecurityPkg/Library/PeiDxeTpmPlatformHierarchyLib/PeiDxeTpmPlatformHierarchyLib.inf
|
|
@@ -0,0 +1,45 @@
|
|
+### @file
|
|
+#
|
|
+# TPM Platform Hierarchy configuration library.
|
|
+#
|
|
+# This library provides functions for customizing the TPM's Platform Hierarchy
|
|
+# Authorization Value (platformAuth) and Platform Hierarchy Authorization
|
|
+# Policy (platformPolicy) can be defined through this function.
|
|
+#
|
|
+# Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
|
|
+# Copyright (c) Microsoft Corporation.<BR>
|
|
+#
|
|
+# SPDX-License-Identifier: BSD-2-Clause-Patent
|
|
+#
|
|
+###
|
|
+
|
|
+[Defines]
|
|
+ INF_VERSION = 0x00010005
|
|
+ BASE_NAME = PeiDxeTpmPlatformHierarchyLib
|
|
+ FILE_GUID = 7794F92C-4E8E-4E57-9E4A-49A0764C7D73
|
|
+ MODULE_TYPE = PEIM
|
|
+ VERSION_STRING = 1.0
|
|
+ LIBRARY_CLASS = TpmPlatformHierarchyLib|PEIM DXE_DRIVER
|
|
+
|
|
+[LibraryClasses]
|
|
+ BaseLib
|
|
+ BaseMemoryLib
|
|
+ DebugLib
|
|
+ MemoryAllocationLib
|
|
+ PcdLib
|
|
+ RngLib
|
|
+ Tpm2CommandLib
|
|
+ Tpm2DeviceLib
|
|
+
|
|
+[Packages]
|
|
+ MdePkg/MdePkg.dec
|
|
+ MdeModulePkg/MdeModulePkg.dec
|
|
+ SecurityPkg/SecurityPkg.dec
|
|
+ CryptoPkg/CryptoPkg.dec
|
|
+ MinPlatformPkg/MinPlatformPkg.dec
|
|
+
|
|
+[Sources]
|
|
+ PeiDxeTpmPlatformHierarchyLib.c
|
|
+
|
|
+[Pcd]
|
|
+ gMinPlatformPkgTokenSpaceGuid.PcdRandomizePlatformHierarchy
|
|
--
|
|
2.27.0
|
|
|