dcavalca / rpms / grub2

Forked from rpms/grub2 3 years ago
Clone

Blame SOURCES/0313-linuxefi-fail-kernel-validation-without-shim-protoco.patch

a4d572
From 2ba58823b68d5fbf8d625ed6d7e18b09bc556860 Mon Sep 17 00:00:00 2001
a4d572
From: Dimitri John Ledkov <xnox@ubuntu.com>
a4d572
Date: Wed, 22 Jul 2020 11:31:43 +0100
a4d572
Subject: [PATCH 313/314] linuxefi: fail kernel validation without shim
a4d572
 protocol.
a4d572
a4d572
If certificates that signed grub are installed into db, grub can be
a4d572
booted directly. It will then boot any kernel without signature
a4d572
validation. The booted kernel will think it was booted in secureboot
a4d572
mode and will implement lockdown, yet it could have been tampered.
a4d572
a4d572
This version of the patch skips calling verification, when booted
a4d572
without secureboot. And is indented with gnu ident.
a4d572
a4d572
CVE-2020-15705
a4d572
a4d572
Reported-by: Mathieu Trudel-Lapierre <cyphermox@ubuntu.com>
a4d572
Signed-off-by: Dimitri John Ledkov <xnox@ubuntu.com>
a4d572
---
a4d572
 grub-core/loader/arm64/linux.c     | 12 ++++++++----
a4d572
 grub-core/loader/efi/chainloader.c |  1 +
a4d572
 grub-core/loader/efi/linux.c       |  1 +
a4d572
 grub-core/loader/i386/efi/linux.c  | 13 ++++++++-----
a4d572
 4 files changed, 18 insertions(+), 9 deletions(-)
a4d572
a4d572
diff --git a/grub-core/loader/arm64/linux.c b/grub-core/loader/arm64/linux.c
a4d572
index e1110749eb9..7a076c13171 100644
a4d572
--- a/grub-core/loader/arm64/linux.c
a4d572
+++ b/grub-core/loader/arm64/linux.c
a4d572
@@ -381,11 +381,15 @@ grub_cmd_linux (grub_command_t cmd __attribute__ ((unused)),
a4d572
 
a4d572
   grub_dprintf ("linux", "kernel @ %p\n", kernel_addr);
a4d572
 
a4d572
-  rc = grub_linuxefi_secure_validate (kernel_addr, kernel_size);
a4d572
-  if (rc < 0)
a4d572
+  if (grub_efi_secure_boot ())
a4d572
     {
a4d572
-      grub_error (GRUB_ERR_INVALID_COMMAND, N_("%s has invalid signature"), argv[0]);
a4d572
-      goto fail;
a4d572
+      rc = grub_linuxefi_secure_validate (kernel_addr, kernel_size);
a4d572
+      if (rc <= 0)
a4d572
+	{
a4d572
+	  grub_error (GRUB_ERR_INVALID_COMMAND,
a4d572
+		      N_("%s has invalid signature"), argv[0]);
a4d572
+	  goto fail;
a4d572
+	}
a4d572
     }
a4d572
 
a4d572
   pe = (void *)((unsigned long)kernel_addr + lh.hdr_offset);
a4d572
diff --git a/grub-core/loader/efi/chainloader.c b/grub-core/loader/efi/chainloader.c
a4d572
index 8b99cf23e9d..a93edc975cd 100644
a4d572
--- a/grub-core/loader/efi/chainloader.c
a4d572
+++ b/grub-core/loader/efi/chainloader.c
a4d572
@@ -1079,6 +1079,7 @@ grub_cmd_chainloader (grub_command_t cmd __attribute__ ((unused)),
a4d572
 
a4d572
       return 0;
a4d572
     }
a4d572
+  // -1 fall-through to fail
a4d572
 
a4d572
 fail:
a4d572
   if (dev)
a4d572
diff --git a/grub-core/loader/efi/linux.c b/grub-core/loader/efi/linux.c
a4d572
index e09f824862b..927d89a90d7 100644
a4d572
--- a/grub-core/loader/efi/linux.c
a4d572
+++ b/grub-core/loader/efi/linux.c
a4d572
@@ -33,6 +33,7 @@ struct grub_efi_shim_lock
a4d572
 };
a4d572
 typedef struct grub_efi_shim_lock grub_efi_shim_lock_t;
a4d572
 
a4d572
+// Returns 1 on success, -1 on error, 0 when not available
a4d572
 int
a4d572
 grub_linuxefi_secure_validate (void *data, grub_uint32_t size)
a4d572
 {
a4d572
diff --git a/grub-core/loader/i386/efi/linux.c b/grub-core/loader/i386/efi/linux.c
a4d572
index ade7ab8f573..361e503cb52 100644
a4d572
--- a/grub-core/loader/i386/efi/linux.c
a4d572
+++ b/grub-core/loader/i386/efi/linux.c
a4d572
@@ -206,12 +206,15 @@ grub_cmd_linux (grub_command_t cmd __attribute__ ((unused)),
a4d572
   grub_tpm_measure (kernel, filelen, GRUB_BINARY_PCR, "grub_linuxefi", "Kernel");
a4d572
   grub_print_error();
a4d572
 
a4d572
-  rc = grub_linuxefi_secure_validate (kernel, filelen);
a4d572
-  if (rc < 0)
a4d572
+  if (grub_efi_secure_boot ())
a4d572
     {
a4d572
-      grub_error (GRUB_ERR_INVALID_COMMAND, N_("%s has invalid signature"),
a4d572
-		  argv[0]);
a4d572
-      goto fail;
a4d572
+      rc = grub_linuxefi_secure_validate (kernel, filelen);
a4d572
+      if (rc <= 0)
a4d572
+	{
a4d572
+	  grub_error (GRUB_ERR_INVALID_COMMAND,
a4d572
+		      N_("%s has invalid signature"), argv[0]);
a4d572
+	  goto fail;
a4d572
+	}
a4d572
     }
a4d572
 
a4d572
   params = grub_efi_allocate_pages_max (0x3fffffff,
a4d572
-- 
a4d572
2.26.2
a4d572