diff mbox series

[v4,11/11] tpm: Allow disabling platform hierarchy with TPM2

Message ID 20210206142327.v4.11.I151cb828b53c98409ab85c3ea82c774fc6cb88f7@changeid
State Accepted
Commit 63af92e837f3d7c21ab5fc4a96ffcbf202efaf90
Delegated to: Tom Rini
Headers show
Series tpm: Support using TPM1 and TPM2 from a single API | expand

Commit Message

Simon Glass Feb. 6, 2021, 9:23 p.m. UTC
With TPM2 we don't actually lock the TPM once verified boot is finished.
Instead we disable the platform hierarchy which serves the same purpose.
Add an implementation of this so we can safely boot into the kernel.

Signed-off-by: Simon Glass <sjg@chromium.org>
Acked-by: Ilias Apalodimas <ilias.apalodimas@linaro.org>
---

(no changes since v2)

Changes in v2:
- Add definition of TPM2_RC_NV_DEFINED return code

 include/tpm-v2.h | 13 +++++++++++++
 lib/tpm-v2.c     | 35 +++++++++++++++++++++++++++++++++++
 2 files changed, 48 insertions(+)

Comments

Tom Rini March 3, 2021, 7:11 p.m. UTC | #1
On Sat, Feb 06, 2021 at 02:23:42PM -0700, Simon Glass wrote:

> With TPM2 we don't actually lock the TPM once verified boot is finished.
> Instead we disable the platform hierarchy which serves the same purpose.
> Add an implementation of this so we can safely boot into the kernel.
> 
> Signed-off-by: Simon Glass <sjg@chromium.org>
> Acked-by: Ilias Apalodimas <ilias.apalodimas@linaro.org>

Applied to u-boot/next, thanks!
diff mbox series

Patch

diff --git a/include/tpm-v2.h b/include/tpm-v2.h
index 1ca1e7e2011..e18c8b1ccca 100644
--- a/include/tpm-v2.h
+++ b/include/tpm-v2.h
@@ -235,6 +235,7 @@  enum tpm2_handles {
 enum tpm2_command_codes {
 	TPM2_CC_STARTUP		= 0x0144,
 	TPM2_CC_SELF_TEST	= 0x0143,
+	TPM2_CC_HIER_CONTROL	= 0x0121,
 	TPM2_CC_CLEAR		= 0x0126,
 	TPM2_CC_CLEARCONTROL	= 0x0127,
 	TPM2_CC_HIERCHANGEAUTH	= 0x0129,
@@ -272,6 +273,7 @@  enum tpm2_return_codes {
 	TPM2_RC_COMMAND_CODE	= TPM2_RC_VER1 + 0x0043,
 	TPM2_RC_AUTHSIZE	= TPM2_RC_VER1 + 0x0044,
 	TPM2_RC_AUTH_CONTEXT	= TPM2_RC_VER1 + 0x0045,
+	TPM2_RC_NV_DEFINED	= TPM2_RC_VER1 + 0x004c,
 	TPM2_RC_NEEDS_TEST	= TPM2_RC_VER1 + 0x0053,
 	TPM2_RC_WARN		= 0x0900,
 	TPM2_RC_TESTING		= TPM2_RC_WARN + 0x000A,
@@ -582,4 +584,15 @@  u32 tpm2_get_random(struct udevice *dev, void *data, u32 count);
  */
 u32 tpm2_write_lock(struct udevice *dev, u32 index);
 
+/**
+ * Disable access to any platform data
+ *
+ * This can be called to close off access to the firmware data in the data,
+ * before calling the kernel.
+ *
+ * @dev		TPM device
+ * @return code of the operation
+ */
+u32 tpm2_disable_platform_hierarchy(struct udevice *dev);
+
 #endif /* __TPM_V2_H */
diff --git a/lib/tpm-v2.c b/lib/tpm-v2.c
index b796004930e..235f8c20d43 100644
--- a/lib/tpm-v2.c
+++ b/lib/tpm-v2.c
@@ -624,3 +624,38 @@  u32 tpm2_write_lock(struct udevice *dev, u32 index)
 
 	return tpm_sendrecv_command(dev, command_v2, NULL, NULL);
 }
+
+u32 tpm2_disable_platform_hierarchy(struct udevice *dev)
+{
+	struct tpm_chip_priv *priv = dev_get_uclass_priv(dev);
+	u8 command_v2[COMMAND_BUFFER_SIZE] = {
+		/* header 10 bytes */
+		tpm_u16(TPM2_ST_SESSIONS),	/* TAG */
+		tpm_u32(10 + 4 + 13 + 5),	/* Length */
+		tpm_u32(TPM2_CC_HIER_CONTROL),	/* Command code */
+
+		/* 4 bytes */
+		tpm_u32(TPM2_RH_PLATFORM),	/* Primary platform seed */
+
+		/* session header 9 bytes */
+		tpm_u32(9),			/* Header size */
+		tpm_u32(TPM2_RS_PW),		/* Password authorisation */
+		tpm_u16(0),			/* nonce_size */
+		0,				/* session_attrs */
+		tpm_u16(0),			/* auth_size */
+
+		/* payload 5 bytes */
+		tpm_u32(TPM2_RH_PLATFORM),	/* Hierarchy to disable */
+		0,				/* 0=disable */
+	};
+	int ret;
+
+	ret = tpm_sendrecv_command(dev, command_v2, NULL, NULL);
+	log_info("ret=%s, %x\n", dev->name, ret);
+	if (ret)
+		return ret;
+
+	priv->plat_hier_disabled = true;
+
+	return 0;
+}