Blame SOURCES/0574-Enable-TDX-measurement-to-RTMR-register.patch

235a57
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
235a57
From: Lu Ken <ken.lu@intel.com>
235a57
Date: Sat, 3 Jul 2021 10:50:37 -0400
235a57
Subject: [PATCH] Enable TDX measurement to RTMR register
235a57
235a57
Intel Trust Domain Extensions(Intel TDX) refers to an Intel technology
235a57
that extends Virtual Machine Extensions(VMX) and Multi-Key Total Memory
235a57
Encryption(MK-TME) with a new kind of virtual machine guest called a
235a57
Trust Domain(TD)[1]. A TD runs in a CPU mode that protects the confidentiality
235a57
of its memory contents and its CPU state from any other software, including
235a57
the hosting Virtual Machine Monitor (VMM).
235a57
235a57
Trust Domain Virtual Firmware (TDVF) is required to provide TD services to
235a57
the TD guest OS.[2] Its reference code is available at https://github.com/tianocore/edk2-staging/tree/TDVF.
235a57
235a57
To support TD measurement/attestation, TDs provide 4 RTMR registers like
235a57
TPM/TPM2 PCR as below:
235a57
- RTMR[0] is for TDVF configuration
235a57
- RTMR[1] is for the TD OS loader and kernel
235a57
- RTMR[2] is for the OS application
235a57
- RTMR[3] is reserved for special usage only
235a57
235a57
This patch adds TD Measurement protocol support along with TPM/TPM2 protocol.
235a57
235a57
References:
235a57
[1] https://software.intel.com/content/dam/develop/external/us/en/documents/tdx-whitepaper-v4.pdf
235a57
[2] https://software.intel.com/content/dam/develop/external/us/en/documents/tdx-virtual-firmware-design-guide-rev-1.pdf
235a57
235a57
Signed-off-by: Lu Ken <ken.lu@intel.com>
235a57
(cherry picked from commit 841a0977397cf12a5498d439b8aaf8bf28ff8544)
235a57
---
235a57
 grub-core/Makefile.core.def |  1 +
235a57
 grub-core/kern/efi/tdx.c    | 70 +++++++++++++++++++++++++++++++++++++++++++++
235a57
 grub-core/kern/tpm.c        |  4 +++
235a57
 include/grub/efi/tdx.h      | 26 +++++++++++++++++
235a57
 include/grub/tdx.h          | 36 +++++++++++++++++++++++
235a57
 5 files changed, 137 insertions(+)
235a57
 create mode 100644 grub-core/kern/efi/tdx.c
235a57
 create mode 100644 include/grub/efi/tdx.h
235a57
 create mode 100644 include/grub/tdx.h
235a57
235a57
diff --git a/grub-core/Makefile.core.def b/grub-core/Makefile.core.def
235a57
index 637d7203e3..2787d59c52 100644
235a57
--- a/grub-core/Makefile.core.def
235a57
+++ b/grub-core/Makefile.core.def
235a57
@@ -200,6 +200,7 @@ kernel = {
235a57
   efi = kern/efi/acpi.c;
235a57
   efi = kern/lockdown.c;
235a57
   efi = lib/envblk.c;
235a57
+  efi = kern/efi/tdx.c;
235a57
   efi = kern/efi/tpm.c;
235a57
   i386_coreboot = kern/i386/pc/acpi.c;
235a57
   i386_multiboot = kern/i386/pc/acpi.c;
235a57
diff --git a/grub-core/kern/efi/tdx.c b/grub-core/kern/efi/tdx.c
235a57
new file mode 100644
235a57
index 0000000000..3a49f8d117
235a57
--- /dev/null
235a57
+++ b/grub-core/kern/efi/tdx.c
235a57
@@ -0,0 +1,70 @@
235a57
+#include <grub/err.h>
235a57
+#include <grub/i18n.h>
235a57
+#include <grub/efi/api.h>
235a57
+#include <grub/efi/efi.h>
235a57
+#include <grub/efi/tpm.h>
235a57
+#include <grub/efi/tdx.h>
235a57
+#include <grub/mm.h>
235a57
+#include <grub/tpm.h>
235a57
+#include <grub/tdx.h>
235a57
+
235a57
+static grub_efi_guid_t tdx_guid = EFI_TDX_GUID;
235a57
+
235a57
+static inline grub_err_t grub_tdx_dprintf(grub_efi_status_t status)
235a57
+{
235a57
+  switch (status) {
235a57
+  case GRUB_EFI_SUCCESS:
235a57
+    return 0;
235a57
+  case GRUB_EFI_DEVICE_ERROR:
235a57
+    grub_dprintf ("tdx", "Command failed: 0x%"PRIxGRUB_EFI_STATUS"\n",
235a57
+                  status);
235a57
+    return GRUB_ERR_IO;
235a57
+  case GRUB_EFI_INVALID_PARAMETER:
235a57
+    grub_dprintf ("tdx", "Invalid parameter: 0x%"PRIxGRUB_EFI_STATUS"\n",
235a57
+                  status);
235a57
+    return GRUB_ERR_BAD_ARGUMENT;
235a57
+  case GRUB_EFI_VOLUME_FULL:
235a57
+    grub_dprintf ("tdx", "Volume is full: 0x%"PRIxGRUB_EFI_STATUS"\n",
235a57
+                  status);
235a57
+    return GRUB_ERR_BAD_ARGUMENT;
235a57
+  case GRUB_EFI_UNSUPPORTED:
235a57
+    grub_dprintf ("tdx", "TDX unavailable: 0x%"PRIxGRUB_EFI_STATUS"\n",
235a57
+                  status);
235a57
+    return GRUB_ERR_UNKNOWN_DEVICE;
235a57
+  default:
235a57
+    grub_dprintf ("tdx", "Unknown TDX error: 0x%"PRIxGRUB_EFI_STATUS"\n",
235a57
+                  status);
235a57
+    return GRUB_ERR_UNKNOWN_DEVICE;
235a57
+  }
235a57
+}
235a57
+
235a57
+grub_err_t
235a57
+grub_tdx_log_event(unsigned char *buf, grub_size_t size, grub_uint8_t pcr,
235a57
+		   const char *description)
235a57
+{
235a57
+  EFI_TCG2_EVENT *event;
235a57
+  grub_efi_status_t status;
235a57
+  grub_efi_tdx_protocol_t *tdx;
235a57
+
235a57
+  tdx = grub_efi_locate_protocol (&tdx_guid, NULL);
235a57
+
235a57
+  if (!tdx)
235a57
+    return 0;
235a57
+
235a57
+  event = grub_zalloc(sizeof (EFI_TCG2_EVENT) + grub_strlen(description) + 1);
235a57
+  if (!event)
235a57
+    return grub_error (GRUB_ERR_OUT_OF_MEMORY,
235a57
+		       N_("cannot allocate TCG2 event buffer"));
235a57
+
235a57
+  event->Header.HeaderSize = sizeof(EFI_TCG2_EVENT_HEADER);
235a57
+  event->Header.HeaderVersion = 1;
235a57
+  event->Header.PCRIndex = pcr;
235a57
+  event->Header.EventType = EV_IPL;
235a57
+  event->Size = sizeof(*event) - sizeof(event->Event) + grub_strlen(description) + 1;
235a57
+  grub_memcpy(event->Event, description, grub_strlen(description) + 1);
235a57
+
235a57
+  status = efi_call_5 (tdx->hash_log_extend_event, tdx, 0, (unsigned long) buf,
235a57
+		       (grub_uint64_t) size, event);
235a57
+
235a57
+  return grub_tdx_dprintf(status);
235a57
+}
235a57
\ No newline at end of file
235a57
diff --git a/grub-core/kern/tpm.c b/grub-core/kern/tpm.c
235a57
index e5e8fced62..71cc4252c1 100644
235a57
--- a/grub-core/kern/tpm.c
235a57
+++ b/grub-core/kern/tpm.c
235a57
@@ -4,6 +4,7 @@
235a57
 #include <grub/mm.h>
235a57
 #include <grub/tpm.h>
235a57
 #include <grub/term.h>
235a57
+#include <grub/tdx.h>
235a57
 
235a57
 grub_err_t
235a57
 grub_tpm_measure (unsigned char *buf, grub_size_t size, grub_uint8_t pcr,
235a57
@@ -13,6 +14,9 @@ grub_tpm_measure (unsigned char *buf, grub_size_t size, grub_uint8_t pcr,
235a57
   char *desc = grub_xasprintf("%s %s", kind, description);
235a57
   if (!desc)
235a57
     return GRUB_ERR_OUT_OF_MEMORY;
235a57
+
235a57
+  grub_tdx_log_event(buf, size, pcr, desc);
235a57
+
235a57
   ret = grub_tpm_log_event(buf, size, pcr, desc);
235a57
   grub_free(desc);
235a57
   return ret;
235a57
diff --git a/include/grub/efi/tdx.h b/include/grub/efi/tdx.h
235a57
new file mode 100644
235a57
index 0000000000..9bdac2a275
235a57
--- /dev/null
235a57
+++ b/include/grub/efi/tdx.h
235a57
@@ -0,0 +1,26 @@
235a57
+/*
235a57
+ *  GRUB  --  GRand Unified Bootloader
235a57
+ *  Copyright (C) 2015  Free Software Foundation, Inc.
235a57
+ *
235a57
+ *  GRUB is free software: you can redistribute it and/or modify
235a57
+ *  it under the terms of the GNU General Public License as published by
235a57
+ *  the Free Software Foundation, either version 3 of the License, or
235a57
+ *  (at your option) any later version.
235a57
+ *
235a57
+ *  GRUB is distributed in the hope that it will be useful,
235a57
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
235a57
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
235a57
+ *  GNU General Public License for more details.
235a57
+ *
235a57
+ *  You should have received a copy of the GNU General Public License
235a57
+ *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
235a57
+ */
235a57
+
235a57
+#ifndef GRUB_EFI_TDX_HEADER
235a57
+#define GRUB_EFI_TDX_HEADER 1
235a57
+
235a57
+#define EFI_TDX_GUID {0x96751a3d, 0x72f4, 0x41a6, {0xa7, 0x94, 0xed, 0x5d, 0x0e, 0x67, 0xae, 0x6b}};
235a57
+
235a57
+typedef grub_efi_tpm2_protocol_t grub_efi_tdx_protocol_t;
235a57
+
235a57
+#endif
235a57
\ No newline at end of file
235a57
diff --git a/include/grub/tdx.h b/include/grub/tdx.h
235a57
new file mode 100644
235a57
index 0000000000..4a98008e39
235a57
--- /dev/null
235a57
+++ b/include/grub/tdx.h
235a57
@@ -0,0 +1,36 @@
235a57
+/*
235a57
+ *  GRUB  --  GRand Unified Bootloader
235a57
+ *  Copyright (C) 2015  Free Software Foundation, Inc.
235a57
+ *
235a57
+ *  GRUB is free software: you can redistribute it and/or modify
235a57
+ *  it under the terms of the GNU General Public License as published by
235a57
+ *  the Free Software Foundation, either version 3 of the License, or
235a57
+ *  (at your option) any later version.
235a57
+ *
235a57
+ *  GRUB is distributed in the hope that it will be useful,
235a57
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
235a57
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
235a57
+ *  GNU General Public License for more details.
235a57
+ *
235a57
+ *  You should have received a copy of the GNU General Public License
235a57
+ *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
235a57
+ */
235a57
+
235a57
+#ifndef GRUB_TDX_HEADER
235a57
+#define GRUB_TDX_HEADER 1
235a57
+
235a57
+#if defined (GRUB_MACHINE_EFI)
235a57
+grub_err_t grub_tdx_log_event(unsigned char *buf, grub_size_t size,
235a57
+			      grub_uint8_t pcr, const char *description);
235a57
+#else
235a57
+static inline grub_err_t grub_tdx_log_event(
235a57
+	unsigned char *buf __attribute__ ((unused)),
235a57
+	grub_size_t size __attribute__ ((unused)),
235a57
+	grub_uint8_t pcr __attribute__ ((unused)),
235a57
+	const char *description __attribute__ ((unused)))
235a57
+{
235a57
+	return 0;
235a57
+};
235a57
+#endif
235a57
+
235a57
+#endif