import shim-unsigned-x64-15.4-4.el8_1
This commit is contained in:
parent
06b3e6a57f
commit
ed609fbec2
2
.gitignore
vendored
2
.gitignore
vendored
@ -1 +1 @@
|
||||
SOURCES/shim-15.tar.bz2
|
||||
SOURCES/shim-15.4.tar.bz2
|
||||
|
@ -1 +1 @@
|
||||
2dc6308584187bf3ee88bf9b119938c72c5a5088 SOURCES/shim-15.tar.bz2
|
||||
d70485792a300bfa66f551adf7ae766451dfe7c0 SOURCES/shim-15.4.tar.bz2
|
||||
|
32
SOURCES/0001-Fix-a-broken-file-header-on-ia32.patch
Normal file
32
SOURCES/0001-Fix-a-broken-file-header-on-ia32.patch
Normal file
@ -0,0 +1,32 @@
|
||||
From 1bea91ba72165d97c3b453cf769cb4bc5c07207a Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Wed, 31 Mar 2021 14:54:52 -0400
|
||||
Subject: [PATCH] Fix a broken file header on ia32
|
||||
|
||||
Commit c6281c6a195edee61185 needs to have included a ". = ALIGN(4096)"
|
||||
directive before .reloc, but fails to do so.
|
||||
|
||||
As a result, binutils, which does not care about the actual binary
|
||||
format's constraints in any way, does not enforce the section alignment,
|
||||
and it will not load.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
---
|
||||
elf_ia32_efi.lds | 1 +
|
||||
1 file changed, 1 insertion(+)
|
||||
|
||||
diff --git a/elf_ia32_efi.lds b/elf_ia32_efi.lds
|
||||
index 742e0a47a73..497a3a15265 100644
|
||||
--- a/elf_ia32_efi.lds
|
||||
+++ b/elf_ia32_efi.lds
|
||||
@@ -15,6 +15,7 @@ SECTIONS
|
||||
*(.gnu.linkonce.t.*)
|
||||
_etext = .;
|
||||
}
|
||||
+ . = ALIGN(4096);
|
||||
.reloc :
|
||||
{
|
||||
*(.reloc)
|
||||
--
|
||||
2.30.2
|
||||
|
@ -1,29 +0,0 @@
|
||||
From 1d50318f448b73b072724eb6664d311e6084a446 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Tue, 10 Apr 2018 12:36:34 -0400
|
||||
Subject: [PATCH 01/62] Make some things dprint() instead of console_print()
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: dad59f8c0f36
|
||||
---
|
||||
shim.c | 4 ++--
|
||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 00155346c12..ff0817009cd 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2087,8 +2087,8 @@ static int is_our_path(EFI_LOADED_IMAGE *li, CHAR16 *path, UINTN len)
|
||||
if (!dppath)
|
||||
return 0;
|
||||
|
||||
- console_print(L"dppath: %s\n", dppath);
|
||||
- console_print(L"path: %s\n", path);
|
||||
+ dprint(L"dppath: %s\n", dppath);
|
||||
+ dprint(L"path: %s\n", path);
|
||||
if (StrnCaseCmp(dppath, path, len))
|
||||
ret = 0;
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,131 +0,0 @@
|
||||
From 32f71225382ddb7dd1ad51f584bc3d42a7ee39d1 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 12 Apr 2018 13:24:48 -0400
|
||||
Subject: [PATCH 02/62] Makefiles: ensure -m32 gets propogated to our gcc
|
||||
parameter queries
|
||||
|
||||
'gcc -print-file-name=include' and 'gcc -print-libgcc-file-name' both
|
||||
need -m32 when we're building 32-on-64 on some distros, so ensure that
|
||||
gets propogated correctly.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 104d6e54ac7
|
||||
---
|
||||
Make.defaults | 66 ++++++++++++++++++++++++++-------------------------
|
||||
1 file changed, 34 insertions(+), 32 deletions(-)
|
||||
|
||||
diff --git a/Make.defaults b/Make.defaults
|
||||
index e11ab5a7f2c..bbfc1d7f77b 100644
|
||||
--- a/Make.defaults
|
||||
+++ b/Make.defaults
|
||||
@@ -33,66 +33,46 @@ EFI_INCLUDES = -nostdinc -I$(TOPDIR)/Cryptlib -I$(TOPDIR)/Cryptlib/Include \
|
||||
-I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol \
|
||||
-I$(TOPDIR)/include -iquote $(TOPDIR) -iquote $(shell pwd)
|
||||
|
||||
-LIB_GCC = $(shell $(CC) -print-libgcc-file-name)
|
||||
-EFI_LIBS = -lefi -lgnuefi --start-group Cryptlib/libcryptlib.a Cryptlib/OpenSSL/libopenssl.a --end-group $(LIB_GCC)
|
||||
-
|
||||
EFI_CRT_OBJS = $(EFI_PATH)/crt0-efi-$(ARCH).o
|
||||
EFI_LDS = $(TOPDIR)/elf_$(ARCH)_efi.lds
|
||||
|
||||
-CFLAGS = -ggdb -O0 -fno-stack-protector -fno-strict-aliasing -fpic \
|
||||
- -fshort-wchar -Wall -Wsign-compare -Werror -fno-builtin \
|
||||
- -Werror=sign-compare -ffreestanding -std=gnu89 \
|
||||
- -I$(shell $(CC) -print-file-name=include) \
|
||||
- "-DDEFAULT_LOADER=L\"$(DEFAULT_LOADER)\"" \
|
||||
- "-DDEFAULT_LOADER_CHAR=\"$(DEFAULT_LOADER)\"" \
|
||||
- $(EFI_INCLUDES)
|
||||
-
|
||||
CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,)
|
||||
|
||||
COMMIT_ID ?= $(shell if [ -e .git ] ; then git log -1 --pretty=format:%H ; elif [ -f commit ]; then cat commit ; else echo master; fi)
|
||||
|
||||
-ifneq ($(origin OVERRIDE_SECURITY_POLICY), undefined)
|
||||
- CFLAGS += -DOVERRIDE_SECURITY_POLICY
|
||||
-endif
|
||||
-
|
||||
-ifneq ($(origin ENABLE_HTTPBOOT), undefined)
|
||||
- CFLAGS += -DENABLE_HTTPBOOT
|
||||
-endif
|
||||
-
|
||||
-ifneq ($(origin REQUIRE_TPM), undefined)
|
||||
- CFLAGS += -DREQUIRE_TPM
|
||||
-endif
|
||||
-
|
||||
ifeq ($(ARCH),x86_64)
|
||||
- CFLAGS += -mno-mmx -mno-sse -mno-red-zone -nostdinc \
|
||||
- $(CLANG_BUGS) -m64 \
|
||||
- -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \
|
||||
- -DNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 -DPAGE_SIZE=4096
|
||||
+ ARCH_CFLAGS ?= -mno-mmx -mno-sse -mno-red-zone -nostdinc \
|
||||
+ $(CLANG_BUGS) -m64 \
|
||||
+ -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \
|
||||
+ -DNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 \
|
||||
+ -DPAGE_SIZE=4096
|
||||
LIBDIR ?= $(prefix)/lib64
|
||||
ARCH_SUFFIX ?= x64
|
||||
ARCH_SUFFIX_UPPER ?= X64
|
||||
ARCH_LDFLAGS ?=
|
||||
endif
|
||||
ifeq ($(ARCH),ia32)
|
||||
- CFLAGS += -mno-mmx -mno-sse -mno-red-zone -nostdinc \
|
||||
- $(CLANG_BUGS) -m32 \
|
||||
- -DMDE_CPU_IA32 -DPAGE_SIZE=4096
|
||||
+ ARCH_CFLAGS ?= -mno-mmx -mno-sse -mno-red-zone -nostdinc \
|
||||
+ $(CLANG_BUGS) -m32 \
|
||||
+ -DMDE_CPU_IA32 -DPAGE_SIZE=4096
|
||||
LIBDIR ?= $(prefix)/lib
|
||||
ARCH_SUFFIX ?= ia32
|
||||
ARCH_SUFFIX_UPPER ?= IA32
|
||||
ARCH_LDFLAGS ?=
|
||||
+ ARCH_CFLAGS ?= -m32
|
||||
endif
|
||||
ifeq ($(ARCH),aarch64)
|
||||
- CFLAGS += -DMDE_CPU_AARCH64 -DPAGE_SIZE=4096 -mstrict-align
|
||||
+ ARCH_CFLAGS ?= -DMDE_CPU_AARCH64 -DPAGE_SIZE=4096 -mstrict-align
|
||||
LIBDIR ?= $(prefix)/lib64
|
||||
ARCH_SUFFIX ?= aa64
|
||||
ARCH_SUFFIX_UPPER ?= AA64
|
||||
FORMAT := -O binary
|
||||
SUBSYSTEM := 0xa
|
||||
ARCH_LDFLAGS += --defsym=EFI_SUBSYSTEM=$(SUBSYSTEM)
|
||||
+ ARCH_CFLAGS ?=
|
||||
endif
|
||||
ifeq ($(ARCH),arm)
|
||||
- CFLAGS += -DMDE_CPU_ARM -DPAGE_SIZE=4096 -mstrict-align
|
||||
+ ARCH_CFLAGS ?= -DMDE_CPU_ARM -DPAGE_SIZE=4096 -mstrict-align
|
||||
LIBDIR ?= $(prefix)/lib
|
||||
ARCH_SUFFIX ?= arm
|
||||
ARCH_SUFFIX_UPPER ?= ARM
|
||||
@@ -101,6 +81,28 @@ ifeq ($(ARCH),arm)
|
||||
ARCH_LDFLAGS += --defsym=EFI_SUBSYSTEM=$(SUBSYSTEM)
|
||||
endif
|
||||
|
||||
+CFLAGS = -ggdb -O0 -fno-stack-protector -fno-strict-aliasing -fpic \
|
||||
+ -fshort-wchar -Wall -Wsign-compare -Werror -fno-builtin \
|
||||
+ -Werror=sign-compare -ffreestanding -std=gnu89 \
|
||||
+ -I$(shell $(CC) $(ARCH_CFLAGS) -print-file-name=include) \
|
||||
+ "-DDEFAULT_LOADER=L\"$(DEFAULT_LOADER)\"" \
|
||||
+ "-DDEFAULT_LOADER_CHAR=\"$(DEFAULT_LOADER)\"" \
|
||||
+ $(EFI_INCLUDES) $(ARCH_CFLAGS)
|
||||
+
|
||||
+ifneq ($(origin OVERRIDE_SECURITY_POLICY), undefined)
|
||||
+ CFLAGS += -DOVERRIDE_SECURITY_POLICY
|
||||
+endif
|
||||
+
|
||||
+ifneq ($(origin ENABLE_HTTPBOOT), undefined)
|
||||
+ CFLAGS += -DENABLE_HTTPBOOT
|
||||
+endif
|
||||
+
|
||||
+ifneq ($(origin REQUIRE_TPM), undefined)
|
||||
+ CFLAGS += -DREQUIRE_TPM
|
||||
+endif
|
||||
+
|
||||
+LIB_GCC = $(shell $(CC) $(ARCH_CFLAGS) -print-libgcc-file-name)
|
||||
+EFI_LIBS = -lefi -lgnuefi --start-group Cryptlib/libcryptlib.a Cryptlib/OpenSSL/libopenssl.a --end-group $(LIB_GCC)
|
||||
FORMAT ?= --target efi-app-$(ARCH)
|
||||
EFI_PATH ?= $(LIBDIR)/gnuefi
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,61 +0,0 @@
|
||||
From 74718677945b1ab825130b317c63f5002876e772 Mon Sep 17 00:00:00 2001
|
||||
From: Mathieu Trudel-Lapierre <mathieu.trudel-lapierre@canonical.com>
|
||||
Date: Thu, 5 Jul 2018 11:28:12 -0400
|
||||
Subject: [PATCH 03/62] Let MokManager follow a MokTimeout var for timeout
|
||||
length for the prompt
|
||||
|
||||
This timeout can have the values [-1,0..0x7fff]; where -1 means "no timeout",
|
||||
with MokManager going directly to the menu, and is capped to 0x7fff to avoid
|
||||
unecessary long timeouts. The default remains 10, which will be used whenever
|
||||
the MokTimeout variable isn't set.
|
||||
|
||||
Signed-off-by: Mathieu Trudel-Lapierre <mathieu.trudel-lapierre@canonical.com>
|
||||
Upstream-commit-id: 93708c11083
|
||||
---
|
||||
MokManager.c | 23 ++++++++++++++++++++++-
|
||||
1 file changed, 22 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index 7e40a38f1d1..0767e4a6cde 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -40,6 +40,10 @@ typedef struct {
|
||||
CHAR16 Password[SB_PASSWORD_LEN];
|
||||
} __attribute__ ((packed)) MokDBvar;
|
||||
|
||||
+typedef struct {
|
||||
+ INT32 Timeout;
|
||||
+} __attribute__ ((packed)) MokTimeoutvar;
|
||||
+
|
||||
static EFI_STATUS get_sha1sum(void *Data, int DataSize, UINT8 * hash)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
@@ -2041,7 +2045,24 @@ static int draw_countdown()
|
||||
UINTN cols, rows;
|
||||
CHAR16 *title[2];
|
||||
CHAR16 *message = L"Press any key to perform MOK management";
|
||||
- int timeout = 10, wait = 10000000;
|
||||
+ void *MokTimeout = NULL;
|
||||
+ MokTimeoutvar *var;
|
||||
+ UINTN MokTimeoutSize = 0;
|
||||
+ int timeout, wait = 10000000;
|
||||
+
|
||||
+ efi_status = get_variable(L"MokTimeout", (UINT8 **) &MokTimeout,
|
||||
+ &MokTimeoutSize, SHIM_LOCK_GUID);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ timeout = 10;
|
||||
+ } else {
|
||||
+ var = MokTimeout;
|
||||
+ timeout = (int)var->Timeout;
|
||||
+ FreePool(MokTimeout);
|
||||
+ LibDeleteVariable(L"MokTimeout", &SHIM_LOCK_GUID);
|
||||
+ }
|
||||
+
|
||||
+ if (timeout < 0)
|
||||
+ return timeout;
|
||||
|
||||
console_save_and_set_mode(&SavedMode);
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,30 +0,0 @@
|
||||
From 8a66f5571bb059d2692e804f4ba9817e978dd103 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Mon, 28 May 2018 16:05:38 +0800
|
||||
Subject: [PATCH 04/62] httpboot: return EFI_NOT_FOUND when it fails to find
|
||||
the NIC handle
|
||||
|
||||
httpboot_fetch_buffer() should return EFI_NOT_FOUND to reflect the error
|
||||
status when get_nic_handle() returns NULL.
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 2be5c7dc4b0
|
||||
---
|
||||
httpboot.c | 1 +
|
||||
1 file changed, 1 insertion(+)
|
||||
|
||||
diff --git a/httpboot.c b/httpboot.c
|
||||
index 4cfa3aab3b7..d656073c633 100644
|
||||
--- a/httpboot.c
|
||||
+++ b/httpboot.c
|
||||
@@ -715,6 +715,7 @@ httpboot_fetch_buffer (EFI_HANDLE image, VOID **buffer, UINT64 *buf_size)
|
||||
also supports the HTTP service binding protocol */
|
||||
nic = get_nic_handle(&mac_addr);
|
||||
if (!nic) {
|
||||
+ efi_status = EFI_NOT_FOUND;
|
||||
goto error;
|
||||
}
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,107 +0,0 @@
|
||||
From 0ba6c87bdf55f749a0ec1c3b0fd24ebb8200d537 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Mon, 28 May 2018 17:24:30 +0800
|
||||
Subject: [PATCH 05/62] httpboot: print more messages when it fails to set IP
|
||||
|
||||
We previously only print the return status and it may not be clear
|
||||
enough in some situations. Print the IP address and the gateway to help
|
||||
the user to identify the possible errors.
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 3abe94516c7
|
||||
---
|
||||
httpboot.c | 45 +++++++++++++++++++++++++++++++++++++++++----
|
||||
1 file changed, 41 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/httpboot.c b/httpboot.c
|
||||
index d656073c633..6f27b01bf71 100644
|
||||
--- a/httpboot.c
|
||||
+++ b/httpboot.c
|
||||
@@ -311,6 +311,20 @@ is_unspecified_addr (EFI_IPv6_ADDRESS ip6)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
+static inline void
|
||||
+print_ip6_addr(EFI_IPv6_ADDRESS ip6addr)
|
||||
+{
|
||||
+ perror(L"%x:%x:%x:%x:%x:%x:%x:%x\n",
|
||||
+ ip6addr.Addr[0] << 8 | ip6addr.Addr[1],
|
||||
+ ip6addr.Addr[2] << 8 | ip6addr.Addr[3],
|
||||
+ ip6addr.Addr[4] << 8 | ip6addr.Addr[5],
|
||||
+ ip6addr.Addr[6] << 8 | ip6addr.Addr[7],
|
||||
+ ip6addr.Addr[8] << 8 | ip6addr.Addr[9],
|
||||
+ ip6addr.Addr[10] << 8 | ip6addr.Addr[11],
|
||||
+ ip6addr.Addr[12] << 8 | ip6addr.Addr[13],
|
||||
+ ip6addr.Addr[14] << 8 | ip6addr.Addr[15]);
|
||||
+}
|
||||
+
|
||||
static EFI_STATUS
|
||||
set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node)
|
||||
{
|
||||
@@ -329,8 +343,12 @@ set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node)
|
||||
ip6.IsAnycast = FALSE;
|
||||
efi_status = ip6cfg->SetData(ip6cfg, Ip6ConfigDataTypeManualAddress,
|
||||
sizeof(ip6), &ip6);
|
||||
- if (EFI_ERROR(efi_status))
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to set IPv6 Address:\nIP: ");
|
||||
+ print_ip6_addr(ip6.Address);
|
||||
+ perror(L"Prefix Length: %u\n", ip6.PrefixLength);
|
||||
return efi_status;
|
||||
+ }
|
||||
|
||||
gateway = ip6node->GatewayIpAddress;
|
||||
if (is_unspecified_addr(gateway))
|
||||
@@ -338,12 +356,23 @@ set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node)
|
||||
|
||||
efi_status = ip6cfg->SetData(ip6cfg, Ip6ConfigDataTypeGateway,
|
||||
sizeof(gateway), &gateway);
|
||||
- if (EFI_ERROR(efi_status))
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to set IPv6 Gateway:\nIP: ");
|
||||
+ print_ip6_addr(gateway);
|
||||
return efi_status;
|
||||
+ }
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
+static inline void
|
||||
+print_ip4_addr(EFI_IPv4_ADDRESS ip4addr)
|
||||
+{
|
||||
+ perror(L"%u.%u.%u.%u\n",
|
||||
+ ip4addr.Addr[0], ip4addr.Addr[1],
|
||||
+ ip4addr.Addr[2], ip4addr.Addr[3]);
|
||||
+}
|
||||
+
|
||||
static EFI_STATUS
|
||||
set_ip4(EFI_HANDLE *nic, IPv4_DEVICE_PATH *ip4node)
|
||||
{
|
||||
@@ -361,14 +390,22 @@ set_ip4(EFI_HANDLE *nic, IPv4_DEVICE_PATH *ip4node)
|
||||
ip4.SubnetMask = ip4node->SubnetMask;
|
||||
efi_status = ip4cfg2->SetData(ip4cfg2, Ip4Config2DataTypeManualAddress,
|
||||
sizeof(ip4), &ip4);
|
||||
- if (EFI_ERROR(efi_status))
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to Set IPv4 Address:\nIP: ");
|
||||
+ print_ip4_addr(ip4.Address);
|
||||
+ perror(L"Mask: ");
|
||||
+ print_ip4_addr(ip4.SubnetMask);
|
||||
return efi_status;
|
||||
+ }
|
||||
|
||||
gateway = ip4node->GatewayIpAddress;
|
||||
efi_status = ip4cfg2->SetData(ip4cfg2, Ip4Config2DataTypeGateway,
|
||||
sizeof(gateway), &gateway);
|
||||
- if (EFI_ERROR(efi_status))
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to Set IPv4 Gateway:\nGateway: ");
|
||||
+ print_ip4_addr(gateway);
|
||||
return efi_status;
|
||||
+ }
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,68 +0,0 @@
|
||||
From 80e52895f206fcb40a60f031e7b721627bb193ca Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Mon, 28 May 2018 17:42:56 +0800
|
||||
Subject: [PATCH 06/62] httpboot: allow the IPv4 gateway to be empty
|
||||
|
||||
The gateway is not mandatory.
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 69089e9c678
|
||||
---
|
||||
httpboot.c | 20 ++++++++++++++++++--
|
||||
1 file changed, 18 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/httpboot.c b/httpboot.c
|
||||
index 6f27b01bf71..16dd6621f66 100644
|
||||
--- a/httpboot.c
|
||||
+++ b/httpboot.c
|
||||
@@ -299,7 +299,7 @@ out:
|
||||
}
|
||||
|
||||
static BOOLEAN
|
||||
-is_unspecified_addr (EFI_IPv6_ADDRESS ip6)
|
||||
+is_unspecified_ip6addr (EFI_IPv6_ADDRESS ip6)
|
||||
{
|
||||
UINT8 i;
|
||||
|
||||
@@ -351,7 +351,7 @@ set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node)
|
||||
}
|
||||
|
||||
gateway = ip6node->GatewayIpAddress;
|
||||
- if (is_unspecified_addr(gateway))
|
||||
+ if (is_unspecified_ip6addr(gateway))
|
||||
return EFI_SUCCESS;
|
||||
|
||||
efi_status = ip6cfg->SetData(ip6cfg, Ip6ConfigDataTypeGateway,
|
||||
@@ -365,6 +365,19 @@ set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node)
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
+static BOOLEAN
|
||||
+is_unspecified_ip4addr (EFI_IPv4_ADDRESS ip4)
|
||||
+{
|
||||
+ UINT8 i;
|
||||
+
|
||||
+ for (i = 0; i<4; i++) {
|
||||
+ if (ip4.Addr[i] != 0)
|
||||
+ return FALSE;
|
||||
+ }
|
||||
+
|
||||
+ return TRUE;
|
||||
+}
|
||||
+
|
||||
static inline void
|
||||
print_ip4_addr(EFI_IPv4_ADDRESS ip4addr)
|
||||
{
|
||||
@@ -399,6 +412,9 @@ set_ip4(EFI_HANDLE *nic, IPv4_DEVICE_PATH *ip4node)
|
||||
}
|
||||
|
||||
gateway = ip4node->GatewayIpAddress;
|
||||
+ if (is_unspecified_ip4addr(gateway))
|
||||
+ return EFI_SUCCESS;
|
||||
+
|
||||
efi_status = ip4cfg2->SetData(ip4cfg2, Ip4Config2DataTypeGateway,
|
||||
sizeof(gateway), &gateway);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,30 +0,0 @@
|
||||
From c2f645c7cd9872585e7b4522b01c368bb545258b Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Mon, 28 May 2018 18:03:39 +0800
|
||||
Subject: [PATCH 07/62] httpboot: show the error message for the ChildHandle
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 0fd3c7e8518
|
||||
---
|
||||
httpboot.c | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/httpboot.c b/httpboot.c
|
||||
index 16dd6621f66..3622e85867c 100644
|
||||
--- a/httpboot.c
|
||||
+++ b/httpboot.c
|
||||
@@ -696,8 +696,10 @@ http_fetch (EFI_HANDLE image, EFI_HANDLE device,
|
||||
/* Set the handle to NULL to request a new handle */
|
||||
http_handle = NULL;
|
||||
efi_status = service->CreateChild(service, &http_handle);
|
||||
- if (EFI_ERROR(efi_status))
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to create the ChildHandle\n");
|
||||
return efi_status;
|
||||
+ }
|
||||
|
||||
/* Get the http protocol */
|
||||
efi_status = gBS->HandleProtocol(http_handle, &EFI_HTTP_PROTOCOL_GUID,
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,54 +0,0 @@
|
||||
From 409b59af29b8749207a527c91dccba7eee98232b Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Wed, 23 May 2018 15:15:56 +0800
|
||||
Subject: [PATCH 08/62] Fix typo in debug path in shim.h
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: a98c20bbdbb
|
||||
---
|
||||
shim.h | 8 ++++----
|
||||
1 file changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/shim.h b/shim.h
|
||||
index a25a660df6a..2b359d821e3 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -43,7 +43,7 @@
|
||||
#define EFI_ARCH L"x64"
|
||||
#endif
|
||||
#ifndef DEBUGDIR
|
||||
-#define DEBUGDIR L"/usr/lub/debug/usr/share/shim/x64/"
|
||||
+#define DEBUGDIR L"/usr/lib/debug/usr/share/shim/x64/"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -58,7 +58,7 @@
|
||||
#define EFI_ARCH L"ia32"
|
||||
#endif
|
||||
#ifndef DEBUGDIR
|
||||
-#define DEBUGDIR L"/usr/lub/debug/usr/share/shim/ia32/"
|
||||
+#define DEBUGDIR L"/usr/lib/debug/usr/share/shim/ia32/"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -73,7 +73,7 @@
|
||||
#define EFI_ARCH L"aa64"
|
||||
#endif
|
||||
#ifndef DEBUGDIR
|
||||
-#define DEBUGDIR L"/usr/lub/debug/usr/share/shim/aa64/"
|
||||
+#define DEBUGDIR L"/usr/lib/debug/usr/share/shim/aa64/"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -88,7 +88,7 @@
|
||||
#define EFI_ARCH L"arm"
|
||||
#endif
|
||||
#ifndef DEBUGDIR
|
||||
-#define DEBUGDIR L"/usr/lub/debug/usr/share/shim/arm/"
|
||||
+#define DEBUGDIR L"/usr/lib/debug/usr/share/shim/arm/"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,43 +0,0 @@
|
||||
From 85c837d67fef9cd831a3126398ed8da1421f61c5 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Fri, 11 May 2018 16:59:03 +0800
|
||||
Subject: [PATCH 09/62] MokManager: Stop using EFI_VARIABLE_APPEND_WRITE
|
||||
|
||||
When writing MokList with EFI_VARIABLE_APPEND_WRITE, some HP laptops
|
||||
may just return EFI_SUCCESS without writing the content into the flash,
|
||||
so we have no way to detect if MokList is updated or not. Now we always
|
||||
read MokList first and write it back with the new content.
|
||||
|
||||
https://github.com/rhboot/shim/issues/105
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: f442c8424b4
|
||||
---
|
||||
MokManager.c | 11 +++--------
|
||||
1 file changed, 3 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index 0767e4a6cde..df9b6fe6912 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -880,14 +880,9 @@ static EFI_STATUS write_db(CHAR16 * db_name, void *MokNew, UINTN MokNewSize)
|
||||
UINTN old_size;
|
||||
UINTN new_size;
|
||||
|
||||
- efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID,
|
||||
- EFI_VARIABLE_NON_VOLATILE |
|
||||
- EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
- EFI_VARIABLE_APPEND_WRITE,
|
||||
- MokNewSize, MokNew);
|
||||
- if (!EFI_ERROR(efi_status) || efi_status != EFI_INVALID_PARAMETER) {
|
||||
- return efi_status;
|
||||
- }
|
||||
+ /* Do not use EFI_VARIABLE_APPEND_WRITE due to faulty firmwares.
|
||||
+ * ref: https://github.com/rhboot/shim/issues/55
|
||||
+ * https://github.com/rhboot/shim/issues/105 */
|
||||
|
||||
efi_status = get_variable_attr(db_name, (UINT8 **)&old_data, &old_size,
|
||||
SHIM_LOCK_GUID, &attributes);
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,40 +0,0 @@
|
||||
From 956717e2b375d7c7f0faafec8f12a7692708eb9a Mon Sep 17 00:00:00 2001
|
||||
From: Paul Menzel <pmenzel@molgen.mpg.de>
|
||||
Date: Wed, 23 May 2018 12:32:37 +0200
|
||||
Subject: [PATCH 10/62] shim: Extend invalid reloc size warning message
|
||||
|
||||
Knowing the value of the reloc directory size is helpful for debugging,
|
||||
cf. issue #131 [1],
|
||||
|
||||
[1]: https://github.com/rhboot/shim/issues/131
|
||||
|
||||
Signed-off-by: Paul Menzel <pmenzel@molgen.mpg.de>
|
||||
Upstream-commit-id: dd3230d07f3
|
||||
---
|
||||
shim.c | 10 ++++++++--
|
||||
1 file changed, 8 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index ff0817009cd..05fc65005d1 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -280,8 +280,14 @@ static EFI_STATUS relocate_coff (PE_COFF_LOADER_IMAGE_CONTEXT *context,
|
||||
while (RelocBase < RelocBaseEnd) {
|
||||
Reloc = (UINT16 *) ((char *) RelocBase + sizeof (EFI_IMAGE_BASE_RELOCATION));
|
||||
|
||||
- if ((RelocBase->SizeOfBlock == 0) || (RelocBase->SizeOfBlock > context->RelocDir->Size)) {
|
||||
- perror(L"Reloc %d block size %d is invalid\n", n, RelocBase->SizeOfBlock);
|
||||
+ if (RelocBase->SizeOfBlock == 0) {
|
||||
+ perror(L"Reloc %d block size 0 is invalid\n", n);
|
||||
+ return EFI_UNSUPPORTED;
|
||||
+ } else if (RelocBase->SizeOfBlock > context->RelocDir->Size) {
|
||||
+ perror(L"Reloc %d block size %d greater than reloc dir"
|
||||
+ "size %d, which is invalid\n", n,
|
||||
+ RelocBase->SizeOfBlock,
|
||||
+ context->RelocDir->Size);
|
||||
return EFI_UNSUPPORTED;
|
||||
}
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,34 +0,0 @@
|
||||
From bd97e72f0490b2be766949f448bf6ea3ec2bba1a Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Wed, 1 Aug 2018 09:58:09 -0500
|
||||
Subject: [PATCH 11/62] Add GRUB's PCR Usage to README.tpm
|
||||
|
||||
This didn't seem to get documented anywhere, and this is as good a place as any.
|
||||
Upstream-commit-id: 4fab7281a8c
|
||||
---
|
||||
README.tpm | 9 +++++++++
|
||||
1 file changed, 9 insertions(+)
|
||||
|
||||
diff --git a/README.tpm b/README.tpm
|
||||
index b7314f12d57..d9c7c53483b 100644
|
||||
--- a/README.tpm
|
||||
+++ b/README.tpm
|
||||
@@ -19,6 +19,15 @@ PCR7:
|
||||
- MokSBState will be extended into PCR7 if it is set, logged as
|
||||
"MokSBState".
|
||||
|
||||
+PCR8:
|
||||
+- If you're using the grub2 TPM patchset we cary in Fedora, the kernel command
|
||||
+ line and all grub commands (including all of grub.cfg that gets run) are
|
||||
+ measured into PCR8.
|
||||
+
|
||||
+PCR9:
|
||||
+- If you're using the grub2 TPM patchset we cary in Fedora, the kernel,
|
||||
+ initramfs, and any multiboot modules loaded are measured into PCR9.
|
||||
+
|
||||
PCR14:
|
||||
- MokList, MokListX, and MokSBState will be extended into PCR14 if they are
|
||||
set.
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,36 +0,0 @@
|
||||
From c4e3516e303daa42b3381ddd889a90641717f720 Mon Sep 17 00:00:00 2001
|
||||
From: TanMing <tanminger@TanMing-WorkPC.sh.intel.com>
|
||||
Date: Tue, 21 Aug 2018 02:25:52 -0400
|
||||
Subject: [PATCH 12/62] Fix the compile error of mkdir wrong directory.
|
||||
|
||||
In Ubuntu 14.04, the following code in old Makefile:
|
||||
mkdir -p Cryptlib/{Hash,Hmac,Cipher,Rand,Pk,Pem,SysCall}
|
||||
will create a directory named "{Hash,Hmac,Cipher,Rand,Pk,Pem,SysCall}".
|
||||
|
||||
Signed-off-by: Ming Tan <ming.tan@intel.com>
|
||||
Upstream-commit-id: 39b83455d68
|
||||
---
|
||||
Makefile | 4 ++--
|
||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/Makefile b/Makefile
|
||||
index 115e7f08c0f..3f2105595a6 100644
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -102,11 +102,11 @@ $(MMSONAME): $(MOK_OBJS) Cryptlib/libcryptlib.a Cryptlib/OpenSSL/libopenssl.a li
|
||||
$(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) lib/lib.a
|
||||
|
||||
Cryptlib/libcryptlib.a:
|
||||
- mkdir -p Cryptlib/{Hash,Hmac,Cipher,Rand,Pk,Pem,SysCall}
|
||||
+ for i in Hash Hmac Cipher Rand Pk Pem SysCall; do mkdir -p Cryptlib/$$i; done
|
||||
$(MAKE) VPATH=$(TOPDIR)/Cryptlib TOPDIR=$(TOPDIR)/Cryptlib -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile
|
||||
|
||||
Cryptlib/OpenSSL/libopenssl.a:
|
||||
- mkdir -p Cryptlib/OpenSSL/crypto/{x509v3,x509,txt_db,stack,sha,rsa,rc4,rand,pkcs7,pkcs12,pem,ocsp,objects,modes,md5,lhash,kdf,hmac,evp,err,dso,dh,conf,comp,cmac,buffer,bn,bio,async{,/arch},asn1,aes}/
|
||||
+ for i in x509v3 x509 txt_db stack sha rsa rc4 rand pkcs7 pkcs12 pem ocsp objects modes md5 lhash kdf hmac evp err dso dh conf comp cmac buffer bn bio async/arch asn1 aes; do mkdir -p Cryptlib/OpenSSL/crypto/$$i; done
|
||||
$(MAKE) VPATH=$(TOPDIR)/Cryptlib/OpenSSL TOPDIR=$(TOPDIR)/Cryptlib/OpenSSL -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile
|
||||
|
||||
lib/lib.a: | $(TOPDIR)/lib/Makefile $(wildcard $(TOPDIR)/include/*.[ch])
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,52 +0,0 @@
|
||||
From 79be2af5260b1f2e2a4680e74e14da0fdb42b570 Mon Sep 17 00:00:00 2001
|
||||
From: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Date: Fri, 7 Sep 2018 14:11:02 +0200
|
||||
Subject: [PATCH 13/62] shim: Properly generate absolute paths from relative
|
||||
image paths
|
||||
|
||||
The generate_path_from_image_path() doesn't properly handle the case when
|
||||
shim is invoked using a relative path (e.g: from the EFI shell). In that
|
||||
function, always the last component is stripped from absolute file path
|
||||
to calculate the dirname, and this is concatenated with the image path.
|
||||
|
||||
But if the path is a relative one, the function will wrongly concatenate
|
||||
the dirname with the relative image path, i.e:
|
||||
|
||||
Shell> FS0:
|
||||
FS0:\> cd EFI
|
||||
FS0:\EFI\> BOOT\BOOTX64.EFI
|
||||
Failed to open \EFI\BOOT\BOOT\BOOTX64.EFI - Not found
|
||||
Failed to load image \EFI\BOOT\BOOT\BOOTX64.EFI: Not found
|
||||
start_image() returned Not found
|
||||
|
||||
Calculate the image path basename and concatenate that with the dirname.
|
||||
|
||||
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Reviewed-by: Maran Wilson maran.wilson@oracle.com
|
||||
Tested-by: Maran Wilson maran.wilson@oracle.com
|
||||
Upstream-commit-id: a625fa5096c
|
||||
---
|
||||
shim.c | 6 ++++--
|
||||
1 file changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 05fc65005d1..5ab23d03db4 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -1610,9 +1610,11 @@ static EFI_STATUS generate_path_from_image_path(EFI_LOADED_IMAGE *li,
|
||||
bootpath[j] = '\0';
|
||||
}
|
||||
|
||||
- while (*ImagePath == '\\')
|
||||
- ImagePath++;
|
||||
+ for (i = 0, last = 0; i < StrLen(ImagePath); i++)
|
||||
+ if (ImagePath[i] == '\\')
|
||||
+ last = i + 1;
|
||||
|
||||
+ ImagePath = ImagePath + last;
|
||||
*PathName = AllocatePool(StrSize(bootpath) + StrSize(ImagePath));
|
||||
|
||||
if (!*PathName) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,77 +0,0 @@
|
||||
From 818a0dbd247f7c83d844febfa0a037b396d22701 Mon Sep 17 00:00:00 2001
|
||||
From: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Date: Fri, 7 Sep 2018 15:10:51 +0200
|
||||
Subject: [PATCH 14/62] shim: Prevent shim to set itself as a second stage
|
||||
loader
|
||||
|
||||
When shim is invoked from a relative path (e.g: from the UEFI shell), the
|
||||
Loaded Image handle LoadOptions can be set to the binary relative path.
|
||||
|
||||
But the is_our_path() function only checks if LoadOptions is set to the
|
||||
absolute path of shim to ignore it. So if a relative path is there, shim
|
||||
would set itself as the secondary loader and invoke itself in a loop.
|
||||
|
||||
To prevent that, use the path in LoadOptions to calculate the absolute
|
||||
path and compare it with the one in the Loader Image handle FilePath.
|
||||
|
||||
Resolves: bz#1622485
|
||||
|
||||
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Reviewed-by: Maran Wilson maran.wilson@oracle.com
|
||||
Tested-by: Maran Wilson maran.wilson@oracle.com
|
||||
Upstream-commit-id: e563bc3dcd1
|
||||
---
|
||||
shim.c | 17 ++++++++++++++---
|
||||
1 file changed, 14 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 5ab23d03db4..ae03da7eddf 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2086,21 +2086,32 @@ get_load_option_optional_data(UINT8 *data, UINTN data_size,
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
-static int is_our_path(EFI_LOADED_IMAGE *li, CHAR16 *path, UINTN len)
|
||||
+static int is_our_path(EFI_LOADED_IMAGE *li, CHAR16 *path)
|
||||
{
|
||||
CHAR16 *dppath = NULL;
|
||||
+ CHAR16 *PathName = NULL;
|
||||
+ EFI_STATUS efi_status;
|
||||
int ret = 1;
|
||||
|
||||
dppath = DevicePathToStr(li->FilePath);
|
||||
if (!dppath)
|
||||
return 0;
|
||||
|
||||
+ efi_status = generate_path_from_image_path(li, path, &PathName);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Unable to generate path %s: %r\n", path,
|
||||
+ efi_status);
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
dprint(L"dppath: %s\n", dppath);
|
||||
dprint(L"path: %s\n", path);
|
||||
- if (StrnCaseCmp(dppath, path, len))
|
||||
+ if (StrnCaseCmp(dppath, PathName, strlen(dppath)))
|
||||
ret = 0;
|
||||
|
||||
+done:
|
||||
FreePool(dppath);
|
||||
+ FreePool(PathName);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -2289,7 +2300,7 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle)
|
||||
|
||||
* which is just cruel... So yeah, just don't use it.
|
||||
*/
|
||||
- if (strings == 1 && is_our_path(li, start, loader_len))
|
||||
+ if (strings == 1 && is_our_path(li, start))
|
||||
return EFI_SUCCESS;
|
||||
|
||||
/*
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,121 +0,0 @@
|
||||
From 3d04aef8d80293d701f7efee6b5300f9f528ddfc Mon Sep 17 00:00:00 2001
|
||||
From: Maran Wilson <maran.wilson@oracle.com>
|
||||
Date: Tue, 7 Aug 2018 15:32:29 -0700
|
||||
Subject: [PATCH 15/62] Fix for "Section 0 has negative size" error when
|
||||
loading fbaa64.efi
|
||||
|
||||
The current code is incorrectly failing to load the fbaa64.efi image found
|
||||
in Arm servers even though the UEFI shell code is able to properly load
|
||||
and execute the same image.
|
||||
|
||||
The problem is due to the presence of a section header that has zero size
|
||||
and address and marked "discardable" in the fbaa64.efi image.
|
||||
|
||||
Although there is already a check further down in the code to look for
|
||||
the discardable bit and skip further verification checks if set, we never
|
||||
get to that point due to the "end < base" check at the start of the loop.
|
||||
|
||||
Here is a dump of the fbaa64.efi image as compiled on an Arm machine
|
||||
from the latest code in this repo:
|
||||
|
||||
% # First I used hexedit to change header byte from 'AA' to '86'
|
||||
% # so that objdump was able to correctly parse the file:
|
||||
% objdump -x -m aarch64 fbaa64.efi
|
||||
|
||||
fbaa64.efi: file format pei-x86-64
|
||||
fbaa64.efi
|
||||
architecture: i386:x86-64, flags 0x00000103:
|
||||
HAS_RELOC, EXEC_P, D_PAGED
|
||||
start address 0x0000000000000148
|
||||
|
||||
Characteristics 0x20e
|
||||
executable
|
||||
line numbers stripped
|
||||
symbols stripped
|
||||
debugging information removed
|
||||
|
||||
Time/Date Wed Dec 31 16:00:00 1969
|
||||
Magic 020b (PE32+)
|
||||
MajorLinkerVersion 2
|
||||
MinorLinkerVersion 20
|
||||
SizeOfCode 000b15d0
|
||||
SizeOfInitializedData 00000000
|
||||
SizeOfUninitializedData 00000000
|
||||
AddressOfEntryPoint 0000000000000148
|
||||
BaseOfCode 0000000000000148
|
||||
ImageBase 0000000000000000
|
||||
SectionAlignment 0000000000000020
|
||||
FileAlignment 0000000000000008
|
||||
MajorOSystemVersion 0
|
||||
MinorOSystemVersion 0
|
||||
MajorImageVersion 0
|
||||
MinorImageVersion 0
|
||||
MajorSubsystemVersion 0
|
||||
MinorSubsystemVersion 0
|
||||
Win32Version 00000000
|
||||
SizeOfImage 000b1718
|
||||
SizeOfHeaders 00000148
|
||||
CheckSum 00000000
|
||||
Subsystem 0000000a (EFI application)
|
||||
DllCharacteristics 00000000
|
||||
SizeOfStackReserve 0000000000000000
|
||||
SizeOfStackCommit 0000000000000000
|
||||
SizeOfHeapReserve 0000000000000000
|
||||
SizeOfHeapCommit 0000000000000000
|
||||
LoaderFlags 00000000
|
||||
NumberOfRvaAndSizes 00000006
|
||||
|
||||
The Data Directory
|
||||
Entry 0 0000000000000000 00000000 Export Directory [.edata (or where ever we found it)]
|
||||
Entry 1 0000000000000000 00000000 Import Directory [parts of .idata]
|
||||
Entry 2 0000000000000000 00000000 Resource Directory [.rsrc]
|
||||
Entry 3 0000000000000000 00000000 Exception Directory [.pdata]
|
||||
Entry 4 0000000000000000 00000000 Security Directory
|
||||
Entry 5 0000000000000000 00000000 Base Relocation Directory [.reloc]
|
||||
Entry 6 0000000000000000 00000000 Debug Directory
|
||||
Entry 7 0000000000000000 00000000 Description Directory
|
||||
Entry 8 0000000000000000 00000000 Special Directory
|
||||
Entry 9 0000000000000000 00000000 Thread Storage Directory [.tls]
|
||||
Entry a 0000000000000000 00000000 Load Configuration Directory
|
||||
Entry b 0000000000000000 00000000 Bound Import Directory
|
||||
Entry c 0000000000000000 00000000 Import Address Table Directory
|
||||
Entry d 0000000000000000 00000000 Delay Import Directory
|
||||
Entry e 0000000000000000 00000000 CLR Runtime Header
|
||||
Entry f 0000000000000000 00000000 Reserved
|
||||
|
||||
Sections:
|
||||
Idx Name Size VMA LMA File off Algn
|
||||
0 .reloc 00000000 0000000000000000 0000000000000000 00000000 2**0
|
||||
ALLOC, LOAD, READONLY, DATA
|
||||
1 .text 000b15d0 0000000000000148 0000000000000148 00000148 2**4
|
||||
CONTENTS, ALLOC, LOAD, CODE
|
||||
SYMBOL TABLE:
|
||||
no symbols
|
||||
|
||||
Signed-off-by: Maran Wilson <maran.wilson@oracle.com>
|
||||
Reviewed-by: Aaron Young <aaron.young@oracle.com>
|
||||
Reviewed-by: Jack Schwartz <jack.schwartz@oracle.com>
|
||||
Upstream-commit-id: 6df7a8f5609
|
||||
---
|
||||
shim.c | 5 +++++
|
||||
1 file changed, 5 insertions(+)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index ae03da7eddf..d980cadacfc 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -1347,6 +1347,11 @@ static EFI_STATUS handle_image (void *data, unsigned int datasize,
|
||||
*/
|
||||
Section = context.FirstSection;
|
||||
for (i = 0; i < context.NumberOfSections; i++, Section++) {
|
||||
+ /* Don't try to copy discardable sections with zero size */
|
||||
+ if ((Section->Characteristics & EFI_IMAGE_SCN_MEM_DISCARDABLE) &&
|
||||
+ !Section->Misc.VirtualSize)
|
||||
+ continue;
|
||||
+
|
||||
base = ImageAddress (buffer, context.ImageSize,
|
||||
Section->VirtualAddress);
|
||||
end = ImageAddress (buffer, context.ImageSize,
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,30 +0,0 @@
|
||||
From d5b72b322d5b7c6c115833c518e1aa5798076309 Mon Sep 17 00:00:00 2001
|
||||
From: dann frazier <dann.frazier@canonical.com>
|
||||
Date: Mon, 14 Jan 2019 15:25:11 -0700
|
||||
Subject: [PATCH 16/62] Fix apparent typo in ARM 32-on-64 code
|
||||
|
||||
The architecture is aarch64, not arch64.
|
||||
|
||||
Fixes: 750584c20775 ("Make 64-on-32 maybe work on x86_64.")
|
||||
Signed-off-by: dann frazier <dann.frazier@canonical.com>
|
||||
Upstream-commit-id: e9f67aaa75a
|
||||
---
|
||||
shim.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index d980cadacfc..e4d4fea226d 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -150,7 +150,7 @@ allow_32_bit(void)
|
||||
#endif
|
||||
#elif defined(__i386__) || defined(__i686__)
|
||||
return 1;
|
||||
-#elif defined(__arch64__)
|
||||
+#elif defined(__aarch64__)
|
||||
return 0;
|
||||
#else /* assuming everything else is 32-bit... */
|
||||
return 1;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,32 +0,0 @@
|
||||
From 8544018093b8aa4311b1e970f8396140c22ede0b Mon Sep 17 00:00:00 2001
|
||||
From: Luca Boccassi <bluca@debian.org>
|
||||
Date: Mon, 14 Jan 2019 19:29:34 +0000
|
||||
Subject: [PATCH 17/62] Makefile: do not run git on clean if there's no .git
|
||||
directory
|
||||
|
||||
When building in minimal chroot on build workers, like in Debian (where
|
||||
make clean is called at the beginning of the build process), git will
|
||||
not be available. Skip the git clean.
|
||||
|
||||
Signed-off-by: Luca Boccassi <bluca@debian.org>
|
||||
Upstream-commit-id: be352762a01
|
||||
---
|
||||
Makefile | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/Makefile b/Makefile
|
||||
index 3f2105595a6..fd7e83dc764 100644
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -225,7 +225,7 @@ clean-shim-objs:
|
||||
@rm -rvf $(TARGET) *.o $(SHIM_OBJS) $(MOK_OBJS) $(FALLBACK_OBJS) $(KEYS) certdb $(BOOTCSVNAME)
|
||||
@rm -vf *.debug *.so *.efi *.efi.* *.tar.* version.c buildid
|
||||
@rm -vf Cryptlib/*.[oa] Cryptlib/*/*.[oa]
|
||||
- @git clean -f -d -e 'Cryptlib/OpenSSL/*'
|
||||
+ @if [ -d .git ] ; then git clean -f -d -e 'Cryptlib/OpenSSL/*'; fi
|
||||
|
||||
clean: clean-shim-objs
|
||||
$(MAKE) -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile clean
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,40 +0,0 @@
|
||||
From 7f080b30f3c3718d6b2533f62a50f373fd2cda21 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Korsgaard <peter@korsgaard.com>
|
||||
Date: Thu, 10 Jan 2019 23:34:11 +0100
|
||||
Subject: [PATCH 18/62] Make.default: use correct flags to disable unaligned
|
||||
access for 32 bit ARM
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
The GCC flag to disable unaligned access on 32bit ARM is
|
||||
-mno-unaligned-access, not -mstrict-align (which is used on aarch64):
|
||||
|
||||
https://lkml.org/lkml/2018/8/3/294
|
||||
|
||||
Otherwise build dies with:
|
||||
arm-linux-gnueabihf-gcc: error: unrecognized command line option
|
||||
‘-mstrict-align’; did you mean ‘-Wstrict-aliasing’?
|
||||
|
||||
Signed-off-by: Peter Korsgaard <peter@korsgaard.com>
|
||||
Upstream-commit-id: 41b93358e8c
|
||||
---
|
||||
Make.defaults | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/Make.defaults b/Make.defaults
|
||||
index bbfc1d7f77b..09807bd8108 100644
|
||||
--- a/Make.defaults
|
||||
+++ b/Make.defaults
|
||||
@@ -72,7 +72,7 @@ ifeq ($(ARCH),aarch64)
|
||||
ARCH_CFLAGS ?=
|
||||
endif
|
||||
ifeq ($(ARCH),arm)
|
||||
- ARCH_CFLAGS ?= -DMDE_CPU_ARM -DPAGE_SIZE=4096 -mstrict-align
|
||||
+ ARCH_CFLAGS ?= -DMDE_CPU_ARM -DPAGE_SIZE=4096 -mno-unaligned-access
|
||||
LIBDIR ?= $(prefix)/lib
|
||||
ARCH_SUFFIX ?= arm
|
||||
ARCH_SUFFIX_UPPER ?= ARM
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,34 +0,0 @@
|
||||
From ee832f21c6706d6b3890d82f9d8bcb2bd249ee04 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Korsgaard <peter@korsgaard.com>
|
||||
Date: Fri, 11 Jan 2019 09:17:42 +0100
|
||||
Subject: [PATCH 19/62] Cryptlib: fix build on 32bit ARM
|
||||
|
||||
Pass MDE_CPU_ARM, similar to how it is done for the other supported
|
||||
architectures, otherwise the build fails in:
|
||||
|
||||
Cryptlib/Include/OpenSslSupport.h:55:2: error:
|
||||
#error Unknown target architecture
|
||||
|
||||
Signed-off-by: Peter Korsgaard <peter@korsgaard.com>
|
||||
Upstream-commit-id: cb83c14628b
|
||||
---
|
||||
Cryptlib/Makefile | 3 +++
|
||||
1 file changed, 3 insertions(+)
|
||||
|
||||
diff --git a/Cryptlib/Makefile b/Cryptlib/Makefile
|
||||
index 2aa569594a0..5c098f34cec 100644
|
||||
--- a/Cryptlib/Makefile
|
||||
+++ b/Cryptlib/Makefile
|
||||
@@ -19,6 +19,9 @@ endif
|
||||
ifeq ($(ARCH),aarch64)
|
||||
CFLAGS += -DMDE_CPU_AARCH64
|
||||
endif
|
||||
+ifeq ($(ARCH),arm)
|
||||
+ CFLAGS += -DMDE_CPU_ARM
|
||||
+endif
|
||||
LDFLAGS = -nostdlib -znocombreloc
|
||||
|
||||
TARGET = libcryptlib.a
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,61 +0,0 @@
|
||||
From ac0400b20264ef67b67891d2216edd3fe20e5571 Mon Sep 17 00:00:00 2001
|
||||
From: Patrick Uiterwijk <patrick@puiterwijk.org>
|
||||
Date: Mon, 5 Nov 2018 14:51:16 +0100
|
||||
Subject: [PATCH 20/62] Make sure that MOK variables always get mirrored
|
||||
|
||||
Without this, if a Mok variable doesn't exist in Boot Services, it will also
|
||||
not be copied to Runtime, even if we have data to be added to it (vendor cert).
|
||||
This patch makes sure that if we have extra data to append, we still mirror
|
||||
the variable.
|
||||
|
||||
Signed-off-by: Patrick Uiterwijk <patrick@puiterwijk.org>
|
||||
Upstream-commit-id: 9ab0d796bdc
|
||||
---
|
||||
mok.c | 20 ++++++++++++++++----
|
||||
1 file changed, 16 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 38675211e0e..00dd1ad3034 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -223,11 +223,26 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
UINT32 attrs = 0;
|
||||
BOOLEAN delete = FALSE, present, addend;
|
||||
|
||||
+ addend = (v->addend_source && v->addend_size &&
|
||||
+ *v->addend_source && *v->addend_size)
|
||||
+ ? TRUE : FALSE;
|
||||
+
|
||||
efi_status = get_variable_attr(v->name,
|
||||
&v->data, &v->data_size,
|
||||
*v->guid, &attrs);
|
||||
- if (efi_status == EFI_NOT_FOUND)
|
||||
+ if (efi_status == EFI_NOT_FOUND) {
|
||||
+ if (v->rtname && addend) {
|
||||
+ efi_status = mirror_one_mok_variable(v);
|
||||
+ if (EFI_ERROR(efi_status) &&
|
||||
+ ret != EFI_SECURITY_VIOLATION)
|
||||
+ ret = efi_status;
|
||||
+ }
|
||||
+ /*
|
||||
+ * after possibly adding, we can continue, no
|
||||
+ * further checks to be done.
|
||||
+ */
|
||||
continue;
|
||||
+ }
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
perror(L"Could not verify %s: %r\n", v->name,
|
||||
efi_status);
|
||||
@@ -272,9 +287,6 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
}
|
||||
|
||||
present = (v->data && v->data_size) ? TRUE : FALSE;
|
||||
- addend = (v->addend_source && v->addend_size &&
|
||||
- *v->addend_source && *v->addend_size)
|
||||
- ? TRUE : FALSE;
|
||||
|
||||
if (v->flags & MOK_VARIABLE_MEASURE && present) {
|
||||
/*
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,50 +0,0 @@
|
||||
From f748139695384fb4e09833898f0b8cb3ab85d810 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Wed, 21 Nov 2018 12:47:43 +0800
|
||||
Subject: [PATCH 21/62] mok: fix the mirroring of RT variables
|
||||
|
||||
When there is no key in MokList, import_mok_state() just skipped MokList
|
||||
even though it should always mirror the vendor cert. Besides, the faulty
|
||||
check of 'present' and 'addend' invalidates the mirroring of MokListXRT,
|
||||
MokSBStateRT, and MokIgnoreDB.
|
||||
|
||||
https://github.com/rhboot/shim/issues/154
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 4b27ae034ba
|
||||
---
|
||||
mok.c | 11 ++++-------
|
||||
1 file changed, 4 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 00dd1ad3034..41925abbb49 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -231,12 +231,8 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
&v->data, &v->data_size,
|
||||
*v->guid, &attrs);
|
||||
if (efi_status == EFI_NOT_FOUND) {
|
||||
- if (v->rtname && addend) {
|
||||
- efi_status = mirror_one_mok_variable(v);
|
||||
- if (EFI_ERROR(efi_status) &&
|
||||
- ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
+ if (addend)
|
||||
+ goto mirror_addend;
|
||||
/*
|
||||
* after possibly adding, we can continue, no
|
||||
* further checks to be done.
|
||||
@@ -316,7 +312,8 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
}
|
||||
}
|
||||
|
||||
- if (v->rtname && present && addend) {
|
||||
+mirror_addend:
|
||||
+ if (v->rtname && (present || addend)) {
|
||||
if (v->flags & MOK_MIRROR_DELETE_FIRST)
|
||||
LibDeleteVariable(v->rtname, v->guid);
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,110 +0,0 @@
|
||||
From ff6e5cda136c8fd637d3d6b8334f4f221ba2b1ee Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 31 Jan 2019 13:45:30 -0500
|
||||
Subject: [PATCH 22/62] mok: consolidate mirroring code in a helper instead of
|
||||
using goto
|
||||
|
||||
There's no reason to complicate the logic with a goto here, instead just
|
||||
pull the logic we're jumping to out to a helper function.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 29c11483101
|
||||
---
|
||||
mok.c | 42 +++++++++++++++++++++++++++++-------------
|
||||
shim.h | 2 ++
|
||||
2 files changed, 31 insertions(+), 13 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 41925abbb49..2b9d796a0e8 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -130,7 +130,8 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{ NULL, }
|
||||
};
|
||||
|
||||
-static EFI_STATUS mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
+static EFI_STATUS nonnull(1)
|
||||
+mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
{
|
||||
EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
void *FullData = NULL;
|
||||
@@ -196,6 +197,29 @@ static EFI_STATUS mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
return efi_status;
|
||||
}
|
||||
|
||||
+/*
|
||||
+ * Mirror a variable if it has an rtname, and preserve any
|
||||
+ * EFI_SECURITY_VIOLATION status at the same time.
|
||||
+ */
|
||||
+static EFI_STATUS nonnull(1)
|
||||
+maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
+{
|
||||
+ EFI_STATUS efi_status;
|
||||
+ if (v->rtname) {
|
||||
+ if (v->flags & MOK_MIRROR_DELETE_FIRST)
|
||||
+ LibDeleteVariable(v->rtname, v->guid);
|
||||
+
|
||||
+ efi_status = mirror_one_mok_variable(v);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ if (ret != EFI_SECURITY_VIOLATION)
|
||||
+ ret = efi_status;
|
||||
+ perror(L"Could not create %s: %r\n", v->rtname,
|
||||
+ efi_status);
|
||||
+ }
|
||||
+ }
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Verify our non-volatile MoK state. This checks the variables above
|
||||
* accessable and have valid attributes. If they don't, it removes
|
||||
@@ -232,7 +256,7 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
*v->guid, &attrs);
|
||||
if (efi_status == EFI_NOT_FOUND) {
|
||||
if (addend)
|
||||
- goto mirror_addend;
|
||||
+ ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
/*
|
||||
* after possibly adding, we can continue, no
|
||||
* further checks to be done.
|
||||
@@ -312,16 +336,8 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
}
|
||||
}
|
||||
|
||||
-mirror_addend:
|
||||
- if (v->rtname && (present || addend)) {
|
||||
- if (v->flags & MOK_MIRROR_DELETE_FIRST)
|
||||
- LibDeleteVariable(v->rtname, v->guid);
|
||||
-
|
||||
- efi_status = mirror_one_mok_variable(v);
|
||||
- if (EFI_ERROR(efi_status) &&
|
||||
- ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
+ if (present)
|
||||
+ ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -340,4 +356,4 @@ mirror_addend:
|
||||
return ret;
|
||||
}
|
||||
|
||||
-// vim:fenc=utf-8:tw=75
|
||||
+// vim:fenc=utf-8:tw=75:noet
|
||||
diff --git a/shim.h b/shim.h
|
||||
index 2b359d821e3..c26d5f06538 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -30,6 +30,8 @@
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
+#define nonnull(...) __attribute__((__nonnull__(__VA_ARGS__)))
|
||||
+
|
||||
#define min(a, b) ({(a) < (b) ? (a) : (b);})
|
||||
|
||||
#ifdef __x86_64__
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,82 +0,0 @@
|
||||
From 7a3638173e406ce7cbd682213606e3152244fcb2 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Wed, 19 Dec 2018 11:27:42 +0800
|
||||
Subject: [PATCH 23/62] shim: only include shim_cert.h in shim.c
|
||||
|
||||
The shim_cert array was declared as a static array, and every user of
|
||||
shim_cert.h would create a shim_cert array for its own and grow the file
|
||||
size. To remove the unnecessary duplicate shim_cert arrays, this commit
|
||||
declares shim_cert in shim.c while other users still can access the
|
||||
array through the external variables: build_cert and build_cert_size.
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: 4e2d62f0f4e
|
||||
---
|
||||
shim.c | 11 +++++++++++
|
||||
shim.h | 7 ++++---
|
||||
2 files changed, 15 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index e4d4fea226d..0a95f94b360 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -34,6 +34,9 @@
|
||||
*/
|
||||
|
||||
#include "shim.h"
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+#include "shim_cert.h"
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/bn.h>
|
||||
@@ -75,6 +78,10 @@ UINT32 vendor_cert_size;
|
||||
UINT32 vendor_dbx_size;
|
||||
UINT8 *vendor_cert;
|
||||
UINT8 *vendor_dbx;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+UINT32 build_cert_size;
|
||||
+UINT8 *build_cert;
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
|
||||
/*
|
||||
* indicator of how an image has been verified
|
||||
@@ -2562,6 +2569,10 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
vendor_dbx_size = cert_table.vendor_dbx_size;
|
||||
vendor_cert = (UINT8 *)&cert_table + cert_table.vendor_cert_offset;
|
||||
vendor_dbx = (UINT8 *)&cert_table + cert_table.vendor_dbx_offset;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ build_cert_size = sizeof(shim_cert);
|
||||
+ build_cert = shim_cert;
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
CHAR16 *msgs[] = {
|
||||
L"import_mok_state() failed\n",
|
||||
L"shim_int() failed\n",
|
||||
diff --git a/shim.h b/shim.h
|
||||
index c26d5f06538..e4d40505f09 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -122,9 +122,6 @@
|
||||
#include "include/variables.h"
|
||||
|
||||
#include "version.h"
|
||||
-#ifdef ENABLE_SHIM_CERT
|
||||
-#include "shim_cert.h"
|
||||
-#endif
|
||||
|
||||
INTERFACE_DECL(_SHIM_LOCK);
|
||||
|
||||
@@ -172,6 +169,10 @@ extern UINT32 vendor_cert_size;
|
||||
extern UINT32 vendor_dbx_size;
|
||||
extern UINT8 *vendor_cert;
|
||||
extern UINT8 *vendor_dbx;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+extern UINT32 build_cert_size;
|
||||
+extern UINT8 *build_cert;
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
|
||||
extern UINT8 user_insecure_mode;
|
||||
extern UINT8 ignore_db;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,153 +0,0 @@
|
||||
From 3d62232feb296b238ca5d7963ba40a2c346767e7 Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Wed, 19 Dec 2018 12:40:02 +0800
|
||||
Subject: [PATCH 24/62] mok: also mirror the build cert to MokListRT
|
||||
|
||||
If the build cert is enabled, we should also mirror it to MokListRT.
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: aecbe1f99b6
|
||||
---
|
||||
mok.c | 78 ++++++++++++++++++++++++++++++++++++++++++++++++++++++-----
|
||||
1 file changed, 72 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 2b9d796a0e8..6150d8c8868 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -68,6 +68,10 @@ struct mok_state_variable {
|
||||
*/
|
||||
UINT8 **addend_source;
|
||||
UINT32 *addend_size;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ UINT8 **build_cert;
|
||||
+ UINT32 *build_cert_size;
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
UINT32 yes_attr;
|
||||
UINT32 no_attr;
|
||||
UINT32 flags;
|
||||
@@ -90,6 +94,10 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
.no_attr = EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
.addend_source = &vendor_cert,
|
||||
.addend_size = &vendor_cert_size,
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ .build_cert = &build_cert,
|
||||
+ .build_cert_size = &build_cert_size,
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
.flags = MOK_MIRROR_KEYDB |
|
||||
MOK_VARIABLE_LOG,
|
||||
.pcr = 14,
|
||||
@@ -130,6 +138,22 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{ NULL, }
|
||||
};
|
||||
|
||||
+inline BOOLEAN check_vendor_cert(struct mok_state_variable *v)
|
||||
+{
|
||||
+ return (v->addend_source && v->addend_size &&
|
||||
+ *v->addend_source && *v->addend_size) ? TRUE : FALSE;
|
||||
+}
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+inline BOOLEAN check_build_cert(struct mok_state_variable *v)
|
||||
+{
|
||||
+ return (v->build_cert && v->build_cert_size &&
|
||||
+ *v->build_cert && *v->build_cert_size) ? TRUE : FALSE;
|
||||
+}
|
||||
+#define check_addend(v) (check_vendor_cert(v) || check_build_cert(v))
|
||||
+#else
|
||||
+#define check_addend(v) check_vendor_cert(v)
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
static EFI_STATUS nonnull(1)
|
||||
mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
{
|
||||
@@ -138,15 +162,27 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
UINTN FullDataSize = 0;
|
||||
uint8_t *p = NULL;
|
||||
|
||||
- if ((v->flags & MOK_MIRROR_KEYDB) &&
|
||||
- v->addend_source && *v->addend_source &&
|
||||
- v->addend_size && *v->addend_size) {
|
||||
+ if ((v->flags & MOK_MIRROR_KEYDB) && check_addend(v)) {
|
||||
EFI_SIGNATURE_LIST *CertList = NULL;
|
||||
EFI_SIGNATURE_DATA *CertData = NULL;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ FullDataSize = v->data_size;
|
||||
+ if (check_build_cert(v)) {
|
||||
+ FullDataSize += sizeof (*CertList)
|
||||
+ + sizeof (EFI_GUID)
|
||||
+ + *v->build_cert_size;
|
||||
+ }
|
||||
+ if (check_vendor_cert(v)) {
|
||||
+ FullDataSize += sizeof (*CertList)
|
||||
+ + sizeof (EFI_GUID)
|
||||
+ + *v->addend_size;
|
||||
+ }
|
||||
+#else
|
||||
FullDataSize = v->data_size
|
||||
+ sizeof (*CertList)
|
||||
+ sizeof (EFI_GUID)
|
||||
+ *v->addend_size;
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
FullData = AllocatePool(FullDataSize);
|
||||
if (!FullData) {
|
||||
perror(L"Failed to allocate space for MokListRT\n");
|
||||
@@ -158,6 +194,35 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
CopyMem(p, v->data, v->data_size);
|
||||
p += v->data_size;
|
||||
}
|
||||
+
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ if (check_build_cert(v) == FALSE)
|
||||
+ goto skip_build_cert;
|
||||
+
|
||||
+ CertList = (EFI_SIGNATURE_LIST *)p;
|
||||
+ p += sizeof (*CertList);
|
||||
+ CertData = (EFI_SIGNATURE_DATA *)p;
|
||||
+ p += sizeof (EFI_GUID);
|
||||
+
|
||||
+ CertList->SignatureType = EFI_CERT_TYPE_X509_GUID;
|
||||
+ CertList->SignatureListSize = *v->build_cert_size
|
||||
+ + sizeof (*CertList)
|
||||
+ + sizeof (*CertData)
|
||||
+ -1;
|
||||
+ CertList->SignatureHeaderSize = 0;
|
||||
+ CertList->SignatureSize = *v->build_cert_size +
|
||||
+ sizeof (EFI_GUID);
|
||||
+
|
||||
+ CertData->SignatureOwner = SHIM_LOCK_GUID;
|
||||
+ CopyMem(p, *v->build_cert, *v->build_cert_size);
|
||||
+
|
||||
+ p += *v->build_cert_size;
|
||||
+
|
||||
+ if (check_vendor_cert(v) == FALSE)
|
||||
+ goto skip_vendor_cert;
|
||||
+skip_build_cert:
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
CertList = (EFI_SIGNATURE_LIST *)p;
|
||||
p += sizeof (*CertList);
|
||||
CertData = (EFI_SIGNATURE_DATA *)p;
|
||||
@@ -174,6 +239,9 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
CertData->SignatureOwner = SHIM_LOCK_GUID;
|
||||
CopyMem(p, *v->addend_source, *v->addend_size);
|
||||
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+skip_vendor_cert:
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
if (v->data && v->data_size)
|
||||
FreePool(v->data);
|
||||
v->data = FullData;
|
||||
@@ -247,9 +315,7 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
UINT32 attrs = 0;
|
||||
BOOLEAN delete = FALSE, present, addend;
|
||||
|
||||
- addend = (v->addend_source && v->addend_size &&
|
||||
- *v->addend_source && *v->addend_size)
|
||||
- ? TRUE : FALSE;
|
||||
+ addend = check_addend(v);
|
||||
|
||||
efi_status = get_variable_attr(v->name,
|
||||
&v->data, &v->data_size,
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,37 +0,0 @@
|
||||
From ff890cf45224926574eee93b0ea1494468870bd3 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 31 Jan 2019 14:04:57 -0500
|
||||
Subject: [PATCH 25/62] mok: minor cleanups
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 617b9007668
|
||||
---
|
||||
mok.c | 7 +++++--
|
||||
1 file changed, 5 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 6150d8c8868..59630e74425 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -138,13 +138,16 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{ NULL, }
|
||||
};
|
||||
|
||||
-inline BOOLEAN check_vendor_cert(struct mok_state_variable *v)
|
||||
+static inline BOOLEAN nonnull(1)
|
||||
+check_vendor_cert(struct mok_state_variable *v)
|
||||
{
|
||||
return (v->addend_source && v->addend_size &&
|
||||
*v->addend_source && *v->addend_size) ? TRUE : FALSE;
|
||||
}
|
||||
+
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
-inline BOOLEAN check_build_cert(struct mok_state_variable *v)
|
||||
+static inline BOOLEAN nonnull(1)
|
||||
+check_build_cert(struct mok_state_variable *v)
|
||||
{
|
||||
return (v->build_cert && v->build_cert_size &&
|
||||
*v->build_cert && *v->build_cert_size) ? TRUE : FALSE;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,91 +0,0 @@
|
||||
From cf3f99c3b1e11c8c83938784975331db5efb410f Mon Sep 17 00:00:00 2001
|
||||
From: Matthew Garrett <mjg59@google.com>
|
||||
Date: Tue, 11 Dec 2018 15:25:44 -0800
|
||||
Subject: [PATCH 26/62] Remove call to TPM2 get_event_log()
|
||||
|
||||
Calling the TPM2 get_event_log causes the firmware to start logging
|
||||
events to the final events table, but implementations may also continue
|
||||
logging to the boot services event log. Any OS that wishes to
|
||||
reconstruct the full PCR state must already look at both the final
|
||||
events log and the boot services event log, so if this call is made
|
||||
anywhere other than immediately before ExitBootServices() then the OS
|
||||
must deduplicate events that occur in both, complicating things
|
||||
immensely.
|
||||
|
||||
Linux already has support for copying up the boot services event log
|
||||
across the ExitBootServices() boundary, so there's no reason to make
|
||||
this call. Remove it.
|
||||
|
||||
Signed-off-by: Matthew Garrett <mjg59@google.com>
|
||||
Upstream-commit-id: fd7c3bd920b
|
||||
---
|
||||
tpm.c | 46 ----------------------------------------------
|
||||
1 file changed, 46 deletions(-)
|
||||
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index 674e69b715f..f07362c70bb 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -70,41 +70,6 @@ static BOOLEAN tpm2_present(EFI_TCG2_BOOT_SERVICE_CAPABILITY *caps,
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
-static inline EFI_TCG2_EVENT_LOG_BITMAP
|
||||
-tpm2_get_supported_logs(efi_tpm2_protocol_t *tpm,
|
||||
- EFI_TCG2_BOOT_SERVICE_CAPABILITY *caps,
|
||||
- BOOLEAN old_caps)
|
||||
-{
|
||||
- if (old_caps)
|
||||
- return ((TREE_BOOT_SERVICE_CAPABILITY *)caps)->SupportedEventLogs;
|
||||
-
|
||||
- return caps->SupportedEventLogs;
|
||||
-}
|
||||
-
|
||||
-/*
|
||||
- * According to TCG EFI Protocol Specification for TPM 2.0 family,
|
||||
- * all events generated after the invocation of EFI_TCG2_GET_EVENT_LOG
|
||||
- * shall be stored in an instance of an EFI_CONFIGURATION_TABLE aka
|
||||
- * EFI TCG 2.0 final events table. Hence, it is necessary to trigger the
|
||||
- * internal switch through calling get_event_log() in order to allow
|
||||
- * to retrieve the logs from OS runtime.
|
||||
- */
|
||||
-static EFI_STATUS trigger_tcg2_final_events_table(efi_tpm2_protocol_t *tpm2,
|
||||
- EFI_TCG2_EVENT_LOG_BITMAP supported_logs)
|
||||
-{
|
||||
- EFI_TCG2_EVENT_LOG_FORMAT log_fmt;
|
||||
- EFI_PHYSICAL_ADDRESS start;
|
||||
- EFI_PHYSICAL_ADDRESS end;
|
||||
- BOOLEAN truncated;
|
||||
-
|
||||
- if (supported_logs & EFI_TCG2_EVENT_LOG_FORMAT_TCG_2)
|
||||
- log_fmt = EFI_TCG2_EVENT_LOG_FORMAT_TCG_2;
|
||||
- else
|
||||
- log_fmt = EFI_TCG2_EVENT_LOG_FORMAT_TCG_1_2;
|
||||
-
|
||||
- return tpm2->get_event_log(tpm2, log_fmt, &start, &end, &truncated);
|
||||
-}
|
||||
-
|
||||
static EFI_STATUS tpm_locate_protocol(efi_tpm_protocol_t **tpm,
|
||||
efi_tpm2_protocol_t **tpm2,
|
||||
BOOLEAN *old_caps_p,
|
||||
@@ -166,17 +131,6 @@ static EFI_STATUS tpm_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
#endif
|
||||
} else if (tpm2) {
|
||||
EFI_TCG2_EVENT *event;
|
||||
- EFI_TCG2_EVENT_LOG_BITMAP supported_logs;
|
||||
-
|
||||
- supported_logs = tpm2_get_supported_logs(tpm2, &caps, old_caps);
|
||||
-
|
||||
- efi_status = trigger_tcg2_final_events_table(tpm2,
|
||||
- supported_logs);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Unable to trigger tcg2 final events table: %r\n",
|
||||
- efi_status);
|
||||
- return efi_status;
|
||||
- }
|
||||
|
||||
event = AllocatePool(sizeof(*event) + logsize);
|
||||
if (!event) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,48 +0,0 @@
|
||||
From 95bd1d88003a9a7c2732472b061ad2a9c7140419 Mon Sep 17 00:00:00 2001
|
||||
From: Patrick Uiterwijk <patrick@puiterwijk.org>
|
||||
Date: Thu, 6 Dec 2018 10:08:45 +0100
|
||||
Subject: [PATCH 27/62] Make EFI variable copying fatal only on secureboot
|
||||
enabled systems
|
||||
|
||||
I have come across systems that are unwilling to reserve enough memory for
|
||||
a MokListRT big enough for big certificates.
|
||||
This seems to be the case with firmware implementations that do not support
|
||||
secureboot, which is probably the reason they went with much lower variable
|
||||
storage.
|
||||
|
||||
This patch set makes sure we can still boot on those systems, by only
|
||||
making the copy action fatal if the system has secure boot enabled, or if
|
||||
the error was anything other than EFI_INVALID_PARAMETER.
|
||||
|
||||
Signed-off-by: Patrick Uiterwijk <patrick@puiterwijk.org>
|
||||
Upstream-commit-id: 741c61abba7
|
||||
---
|
||||
shim.c | 12 +++++++++++-
|
||||
1 file changed, 11 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 0a95f94b360..d4ed332f901 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2609,7 +2609,17 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
* boot-services-only state variables are what we think they are.
|
||||
*/
|
||||
efi_status = import_mok_state(image_handle);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
+ if (!secure_mode() && efi_status == EFI_INVALID_PARAMETER) {
|
||||
+ /*
|
||||
+ * Make copy failures fatal only if secure_mode is enabled, or
|
||||
+ * the error was anything else than EFI_INVALID_PARAMETER.
|
||||
+ * There are non-secureboot firmware implementations that don't
|
||||
+ * reserve enough EFI variable memory to fit the variable.
|
||||
+ */
|
||||
+ console_print(L"Importing MOK states has failed: %s: %r\n",
|
||||
+ msgs[msg], efi_status);
|
||||
+ console_print(L"Continuing boot since secure mode is disabled");
|
||||
+ } else if (EFI_ERROR(efi_status)) {
|
||||
die:
|
||||
console_print(L"Something has gone seriously wrong: %s: %r\n",
|
||||
msgs[msg], efi_status);
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,66 +0,0 @@
|
||||
From 344a8364cb05cdaafc43231d0f73d5217c4e118c Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Tue, 12 Feb 2019 18:04:49 -0500
|
||||
Subject: [PATCH 28/62] VLogError(): Avoid NULL pointer dereferences in
|
||||
(V)Sprint calls
|
||||
|
||||
VLogError() calculates the size of format strings by using calls to
|
||||
SPrint and VSPrint with a StrSize of 0 and NULL for an output buffer.
|
||||
Unfortunately, this is an incorrect usage of (V)Sprint. A StrSize
|
||||
of "0" is special-cased to mean "there is no limit". So, we end up
|
||||
writing our string to address 0x0. This was discovered because it
|
||||
causes a crash on ARM where, unlike x86, it does not necessarily
|
||||
have memory mapped at 0x0.
|
||||
|
||||
Avoid the (V)Sprint calls altogether by using (V)PoolPrint, which
|
||||
handles the size calculation and allocation for us.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Fixes: 25f6fd08cd26 ("try to show errors more usefully.")
|
||||
[dannf: commit message ]
|
||||
Signed-off-by: dann frazier <dann.frazier@canonical.com>
|
||||
Upstream-commit-id: 20e731f423a
|
||||
---
|
||||
errlog.c | 15 +++------------
|
||||
1 file changed, 3 insertions(+), 12 deletions(-)
|
||||
|
||||
diff --git a/errlog.c b/errlog.c
|
||||
index 18be4822d53..eebb266d396 100644
|
||||
--- a/errlog.c
|
||||
+++ b/errlog.c
|
||||
@@ -14,29 +14,20 @@ EFI_STATUS
|
||||
VLogError(const char *file, int line, const char *func, CHAR16 *fmt, va_list args)
|
||||
{
|
||||
va_list args2;
|
||||
- UINTN size = 0, size2;
|
||||
CHAR16 **newerrs;
|
||||
|
||||
- size = SPrint(NULL, 0, L"%a:%d %a() ", file, line, func);
|
||||
- va_copy(args2, args);
|
||||
- size2 = VSPrint(NULL, 0, fmt, args2);
|
||||
- va_end(args2);
|
||||
-
|
||||
newerrs = ReallocatePool(errs, (nerrs + 1) * sizeof(*errs),
|
||||
(nerrs + 3) * sizeof(*errs));
|
||||
if (!newerrs)
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
|
||||
- newerrs[nerrs] = AllocatePool(size*2+2);
|
||||
+ newerrs[nerrs] = PoolPrint(L"%a:%d %a() ", file, line, func);
|
||||
if (!newerrs[nerrs])
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
- newerrs[nerrs+1] = AllocatePool(size2*2+2);
|
||||
+ va_copy(args2, args);
|
||||
+ newerrs[nerrs+1] = VPoolPrint(fmt, args2);
|
||||
if (!newerrs[nerrs+1])
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
-
|
||||
- SPrint(newerrs[nerrs], size*2+2, L"%a:%d %a() ", file, line, func);
|
||||
- va_copy(args2, args);
|
||||
- VSPrint(newerrs[nerrs+1], size2*2+2, fmt, args2);
|
||||
va_end(args2);
|
||||
|
||||
nerrs += 2;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,98 +0,0 @@
|
||||
From 10d6e3d90f1ea504a1dedaea50478c444e92951c Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Fri, 15 Mar 2019 09:52:02 -0400
|
||||
Subject: [PATCH 29/62] Once again, try even harder to get binaries without
|
||||
timestamps in them.
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
$ objdump -x /builddir/build/BUILDROOT/shim-*/usr/share/shim/*/shimx64.efi | grep 'Time/Date'
|
||||
Time/Date Thu Jan 1 00:00:08 1970
|
||||
$ _
|
||||
|
||||
"What is despair? I have known it—hear my song. Despair is when you’re
|
||||
debugging a kernel driver and you look at a memory dump and you see that
|
||||
a pointer has a value of 7."
|
||||
- http://scholar.harvard.edu/files/mickens/files/thenightwatch.pdf
|
||||
|
||||
objcopy only knows about -D for some targets.
|
||||
ld only believes in --no-insert-timestamp in some versions.
|
||||
dd takes off and nukes the site from orbit.
|
||||
|
||||
It's the only way to be sure.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: a4a1fbe728c
|
||||
---
|
||||
Make.defaults | 4 ++++
|
||||
Makefile | 6 ++++--
|
||||
2 files changed, 8 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/Make.defaults b/Make.defaults
|
||||
index 09807bd8108..f0bfa9fd573 100644
|
||||
--- a/Make.defaults
|
||||
+++ b/Make.defaults
|
||||
@@ -50,6 +50,7 @@ ifeq ($(ARCH),x86_64)
|
||||
ARCH_SUFFIX ?= x64
|
||||
ARCH_SUFFIX_UPPER ?= X64
|
||||
ARCH_LDFLAGS ?=
|
||||
+ TIMESTAMP_LOCATION := 136
|
||||
endif
|
||||
ifeq ($(ARCH),ia32)
|
||||
ARCH_CFLAGS ?= -mno-mmx -mno-sse -mno-red-zone -nostdinc \
|
||||
@@ -60,6 +61,7 @@ ifeq ($(ARCH),ia32)
|
||||
ARCH_SUFFIX_UPPER ?= IA32
|
||||
ARCH_LDFLAGS ?=
|
||||
ARCH_CFLAGS ?= -m32
|
||||
+ TIMESTAMP_LOCATION := 136
|
||||
endif
|
||||
ifeq ($(ARCH),aarch64)
|
||||
ARCH_CFLAGS ?= -DMDE_CPU_AARCH64 -DPAGE_SIZE=4096 -mstrict-align
|
||||
@@ -70,6 +72,7 @@ ifeq ($(ARCH),aarch64)
|
||||
SUBSYSTEM := 0xa
|
||||
ARCH_LDFLAGS += --defsym=EFI_SUBSYSTEM=$(SUBSYSTEM)
|
||||
ARCH_CFLAGS ?=
|
||||
+ TIMESTAMP_LOCATION := 72
|
||||
endif
|
||||
ifeq ($(ARCH),arm)
|
||||
ARCH_CFLAGS ?= -DMDE_CPU_ARM -DPAGE_SIZE=4096 -mno-unaligned-access
|
||||
@@ -79,6 +82,7 @@ ifeq ($(ARCH),arm)
|
||||
FORMAT := -O binary
|
||||
SUBSYSTEM := 0xa
|
||||
ARCH_LDFLAGS += --defsym=EFI_SUBSYSTEM=$(SUBSYSTEM)
|
||||
+ TIMESTAMP_LOCATION := 72
|
||||
endif
|
||||
|
||||
CFLAGS = -ggdb -O0 -fno-stack-protector -fno-strict-aliasing -fpic \
|
||||
diff --git a/Makefile b/Makefile
|
||||
index fd7e83dc764..49e14a26521 100644
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -189,11 +189,13 @@ endif
|
||||
ifneq ($(OBJCOPY_GTE224),1)
|
||||
$(error objcopy >= 2.24 is required)
|
||||
endif
|
||||
- $(OBJCOPY) -j .text -j .sdata -j .data -j .data.ident \
|
||||
+ $(OBJCOPY) -D -j .text -j .sdata -j .data -j .data.ident \
|
||||
-j .dynamic -j .dynsym -j .rel* \
|
||||
-j .rela* -j .reloc -j .eh_frame \
|
||||
-j .vendor_cert \
|
||||
$(FORMAT) $^ $@
|
||||
+ # I am tired of wasting my time fighting binutils timestamp code.
|
||||
+ dd conv=notrunc bs=1 count=4 seek=$(TIMESTAMP_LOCATION) if=/dev/zero of=$@
|
||||
|
||||
ifneq ($(origin ENABLE_SHIM_HASH),undefined)
|
||||
%.hash : %.efi
|
||||
@@ -204,7 +206,7 @@ endif
|
||||
ifneq ($(OBJCOPY_GTE224),1)
|
||||
$(error objcopy >= 2.24 is required)
|
||||
endif
|
||||
- $(OBJCOPY) -j .text -j .sdata -j .data \
|
||||
+ $(OBJCOPY) -D -j .text -j .sdata -j .data \
|
||||
-j .dynamic -j .dynsym -j .rel* \
|
||||
-j .rela* -j .reloc -j .eh_frame \
|
||||
-j .debug_info -j .debug_abbrev -j .debug_aranges \
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,280 +0,0 @@
|
||||
From 1b382ef850de5a6c59b192c146a0e8d898d2d961 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Tue, 23 Oct 2018 18:17:57 -0400
|
||||
Subject: [PATCH 30/62] shim: Rework pause functions and add read_counter()
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: fc6b0bca84e
|
||||
---
|
||||
shim.c | 4 +-
|
||||
include/asm.h | 59 +++++++++++++++++
|
||||
include/compiler.h | 156 +++++++++++++++++++++++++++++++++++++++++++++
|
||||
shim.h | 1 +
|
||||
4 files changed, 217 insertions(+), 3 deletions(-)
|
||||
create mode 100644 include/asm.h
|
||||
create mode 100644 include/compiler.h
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index d4ed332f901..f69e69487fc 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2543,16 +2543,14 @@ debug_hook(void)
|
||||
#if defined(__x86_64__) || defined(__i386__) || defined(__i686__)
|
||||
if (x > 4294967294ULL)
|
||||
break;
|
||||
- __asm__ __volatile__("pause");
|
||||
#elif defined(__aarch64__)
|
||||
if (x > 1000)
|
||||
break;
|
||||
- __asm__ __volatile__("wfi");
|
||||
#else
|
||||
if (x > 12000)
|
||||
break;
|
||||
- msleep(5000);
|
||||
#endif
|
||||
+ pause();
|
||||
}
|
||||
x = 1;
|
||||
}
|
||||
diff --git a/include/asm.h b/include/asm.h
|
||||
new file mode 100644
|
||||
index 00000000000..5e8f9ed9d7c
|
||||
--- /dev/null
|
||||
+++ b/include/asm.h
|
||||
@@ -0,0 +1,59 @@
|
||||
+/*
|
||||
+ * asm.h
|
||||
+ * Copyright 2018 Peter Jones <pjones@redhat.com>
|
||||
+ */
|
||||
+
|
||||
+#ifndef SHIM_ASM_H_
|
||||
+#define SHIM_ASM_H_
|
||||
+
|
||||
+#define __stringify_1(x...) #x
|
||||
+#define __stringify(x...) __stringify_1(x)
|
||||
+
|
||||
+static inline uint64_t read_counter(void)
|
||||
+{
|
||||
+ uint64_t val;
|
||||
+#if defined (__x86_64__)
|
||||
+ unsigned long low, high;
|
||||
+ __asm__ __volatile__("rdtsc" : "=a" (low), "=d" (high));
|
||||
+ val = (low) | (high) << 32;
|
||||
+#elif defined(__i386__) || defined(__i686__)
|
||||
+ __asm__ __volatile__("rdtsc" : "=A" (val));
|
||||
+#elif defined(__aarch64__)
|
||||
+ __asm__ __volatile__ ("mrs %0, pmccntr_el0" : "=r" (val));
|
||||
+#elif defined(__arm__)
|
||||
+ __asm__ __volatile__ ("mrc p15, 0, %0, c9, c13, 0" : "=r" (val));
|
||||
+#else
|
||||
+#error unsupported arch
|
||||
+#endif
|
||||
+ return val;
|
||||
+}
|
||||
+
|
||||
+#if defined(__x86_64__) || defined(__i386__) || defined(__i686__)
|
||||
+static inline void pause(void)
|
||||
+{
|
||||
+ __asm__ __volatile__("pause");
|
||||
+}
|
||||
+#elif defined(__aarch64__)
|
||||
+static inline void pause(void)
|
||||
+{
|
||||
+ __asm__ __volatile__("wfi");
|
||||
+}
|
||||
+#else
|
||||
+static inline void pause(void)
|
||||
+{
|
||||
+ uint64_t a, b;
|
||||
+ int x;
|
||||
+ extern void msleep(unsigned long msecs);
|
||||
+
|
||||
+ a = read_counter();
|
||||
+ for (x = 0; x < 1000; x++) {
|
||||
+ msleep(1000);
|
||||
+ b = read_counter();
|
||||
+ if (a != b)
|
||||
+ break;
|
||||
+ }
|
||||
+}
|
||||
+#endif
|
||||
+
|
||||
+#endif /* !SHIM_ASM_H_ */
|
||||
+// vim:fenc=utf-8:tw=75:et
|
||||
diff --git a/include/compiler.h b/include/compiler.h
|
||||
new file mode 100644
|
||||
index 00000000000..a2a0859379f
|
||||
--- /dev/null
|
||||
+++ b/include/compiler.h
|
||||
@@ -0,0 +1,156 @@
|
||||
+/*
|
||||
+ * compiler.h
|
||||
+ * Copyright 2019 Peter Jones <pjones@redhat.com>
|
||||
+ */
|
||||
+
|
||||
+#ifndef COMPILER_H_
|
||||
+#define COMPILER_H_
|
||||
+
|
||||
+#ifndef UNUSED
|
||||
+#define UNUSED __attribute__((__unused__))
|
||||
+#endif
|
||||
+#ifndef HIDDEN
|
||||
+#define HIDDEN __attribute__((__visibility__ ("hidden")))
|
||||
+#endif
|
||||
+#ifndef PUBLIC
|
||||
+#define PUBLIC __attribute__((__visibility__ ("default")))
|
||||
+#endif
|
||||
+#ifndef DESTRUCTOR
|
||||
+#define DESTRUCTOR __attribute__((destructor))
|
||||
+#endif
|
||||
+#ifndef CONSTRUCTOR
|
||||
+#define CONSTRUCTOR __attribute__((constructor))
|
||||
+#endif
|
||||
+#ifndef ALIAS
|
||||
+#define ALIAS(x) __attribute__((weak, alias (#x)))
|
||||
+#endif
|
||||
+#ifndef NONNULL
|
||||
+#endif
|
||||
+#define NONNULL(first, args...) __attribute__((__nonnull__(first, ## args)))
|
||||
+#ifndef PRINTF
|
||||
+#define PRINTF(first, args...) __attribute__((__format__(printf, first, ## args)))
|
||||
+#endif
|
||||
+#ifndef FLATTEN
|
||||
+#define FLATTEN __attribute__((__flatten__))
|
||||
+#endif
|
||||
+#ifndef PACKED
|
||||
+#define PACKED __attribute__((__packed__))
|
||||
+#endif
|
||||
+#ifndef VERSION
|
||||
+#define VERSION(sym, ver) __asm__(".symver " # sym "," # ver)
|
||||
+#endif
|
||||
+#ifndef NORETURN
|
||||
+#define NORETURN __attribute__((__noreturn__))
|
||||
+#endif
|
||||
+#ifndef ALIGNED
|
||||
+#define ALIGNED(n) __attribute__((__aligned__(n)))
|
||||
+#endif
|
||||
+#ifndef CLEANUP_FUNC
|
||||
+#define CLEANUP_FUNC(x) __attribute__((__cleanup__(x)))
|
||||
+#endif
|
||||
+#ifndef USED
|
||||
+#define USED __attribute__((__used__))
|
||||
+#endif
|
||||
+#ifndef SECTION
|
||||
+#define SECTION(x) __attribute__((__section__(x)))
|
||||
+#endif
|
||||
+#ifndef OPTIMIZE
|
||||
+#define OPTIMIZE(x) __attribute__((__optimize__(x)))
|
||||
+#endif
|
||||
+
|
||||
+#ifndef __CONCAT
|
||||
+#define __CONCAT3(a, b, c) a ## b ## c
|
||||
+#endif
|
||||
+#ifndef CAT
|
||||
+#define CAT(a, b) __CONCAT(a, b)
|
||||
+#endif
|
||||
+#ifndef CAT3
|
||||
+#define CAT3(a, b, c) __CONCAT3(a, b, c)
|
||||
+#endif
|
||||
+#ifndef STRING
|
||||
+#define STRING(x) __STRING(x)
|
||||
+#endif
|
||||
+
|
||||
+#ifndef WRITE_ONCE
|
||||
+#define WRITE_ONCE(var, val) \
|
||||
+ (*((volatile typeof(val) *)(&(var))) = (val))
|
||||
+#endif
|
||||
+
|
||||
+#ifndef READ_ONCE
|
||||
+#define READ_ONCE(var) (*((volatile typeof(var) *)(&(var))))
|
||||
+#endif
|
||||
+
|
||||
+#ifndef likely
|
||||
+#define likely(x) __builtin_expect(!!(x), 1)
|
||||
+#endif
|
||||
+
|
||||
+#ifndef unlikely
|
||||
+#define unlikely(x) __builtin_expect(!!(x), 0)
|
||||
+#endif
|
||||
+
|
||||
+/* Are two types/vars the same type (ignoring qualifiers)? */
|
||||
+#ifndef __same_type
|
||||
+#define __same_type(a, b) __builtin_types_compatible_p(typeof(a), typeof(b))
|
||||
+#endif
|
||||
+
|
||||
+/* Compile time object size, -1 for unknown */
|
||||
+#ifndef __compiletime_object_size
|
||||
+# define __compiletime_object_size(obj) -1
|
||||
+#endif
|
||||
+#ifndef __compiletime_warning
|
||||
+# define __compiletime_warning(message)
|
||||
+#endif
|
||||
+#ifndef __compiletime_error
|
||||
+# define __compiletime_error(message)
|
||||
+#endif
|
||||
+
|
||||
+#ifndef __compiletime_assert
|
||||
+#define __compiletime_assert(condition, msg, prefix, suffix) \
|
||||
+ do { \
|
||||
+ extern void prefix ## suffix(void) __compiletime_error(msg); \
|
||||
+ if (!(condition)) \
|
||||
+ prefix ## suffix(); \
|
||||
+ } while (0)
|
||||
+#endif
|
||||
+
|
||||
+#ifndef _compiletime_assert
|
||||
+#define _compiletime_assert(condition, msg, prefix, suffix) \
|
||||
+ __compiletime_assert(condition, msg, prefix, suffix)
|
||||
+#endif
|
||||
+
|
||||
+/**
|
||||
+ * compiletime_assert - break build and emit msg if condition is false
|
||||
+ * @condition: a compile-time constant condition to check
|
||||
+ * @msg: a message to emit if condition is false
|
||||
+ *
|
||||
+ * In tradition of POSIX assert, this macro will break the build if the
|
||||
+ * supplied condition is *false*, emitting the supplied error message if the
|
||||
+ * compiler has support to do so.
|
||||
+ */
|
||||
+#ifndef compiletime_assert
|
||||
+#define compiletime_assert(condition, msg) \
|
||||
+ _compiletime_assert(condition, msg, __compiletime_assert_, __LINE__)
|
||||
+#endif
|
||||
+
|
||||
+/**
|
||||
+ * BUILD_BUG_ON_MSG - break compile if a condition is true & emit supplied
|
||||
+ * error message.
|
||||
+ * @condition: the condition which the compiler should know is false.
|
||||
+ *
|
||||
+ * See BUILD_BUG_ON for description.
|
||||
+ */
|
||||
+#ifndef BUILD_BUG_ON_MSG
|
||||
+#define BUILD_BUG_ON_MSG(cond, msg) compiletime_assert(!(cond), msg)
|
||||
+#endif
|
||||
+
|
||||
+#ifndef ALIGN
|
||||
+#define __ALIGN_MASK(x, mask) (((x) + (mask)) & ~(mask))
|
||||
+#define __ALIGN(x, a) __ALIGN_MASK(x, (typeof(x))(a) - 1)
|
||||
+#define ALIGN(x, a) __ALIGN((x), (a))
|
||||
+#endif
|
||||
+#ifndef ALIGN_DOWN
|
||||
+#define ALIGN_DOWN(x, a) __ALIGN((x) - ((a) - 1), (a))
|
||||
+#endif
|
||||
+
|
||||
+#endif /* !COMPILER_H_ */
|
||||
+// vim:fenc=utf-8:tw=75:et
|
||||
diff --git a/shim.h b/shim.h
|
||||
index e4d40505f09..a0fa5a75e7e 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -97,6 +97,7 @@
|
||||
#define FALLBACK L"\\fb" EFI_ARCH L".efi"
|
||||
#define MOK_MANAGER L"\\mm" EFI_ARCH L".efi"
|
||||
|
||||
+#include "include/asm.h"
|
||||
#include "include/configtable.h"
|
||||
#include "include/console.h"
|
||||
#include "include/crypt_blowfish.h"
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,49 +0,0 @@
|
||||
From b5e10f70c7a495dc1788e3604803ee633f1e5f76 Mon Sep 17 00:00:00 2001
|
||||
From: Stuart Hayes <stuart.w.hayes@gmail.com>
|
||||
Date: Fri, 8 Feb 2019 15:48:20 -0500
|
||||
Subject: [PATCH 31/62] Hook exit when shim_lock protocol installed
|
||||
|
||||
A recent commit moved where the shim_lock protocol is loaded and
|
||||
unloaded, but did not move where exit was hooked and unhooked. Exit
|
||||
needs to be hooked when the protocol is installed, so that the protocol
|
||||
will be uninstalled on exit. Otherwise, the system can crash if, for
|
||||
example, shim loads grub, the user exits grub, shim is run again, which
|
||||
installs a second instance of the protocol, and then grub tries to use
|
||||
the shim_lock protocol that was installed by the first instance of shim.
|
||||
|
||||
Signed-off-by: Stuart Hayes <stuart.w.hayes@gmail.com>
|
||||
Upstream-commit-id: 06c92591e94
|
||||
---
|
||||
shim.c | 5 +++--
|
||||
1 file changed, 3 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index f69e69487fc..16911a37b17 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2474,9 +2474,9 @@ shim_init(void)
|
||||
loader_is_participating = 0;
|
||||
}
|
||||
|
||||
- hook_exit(systab);
|
||||
}
|
||||
|
||||
+ hook_exit(systab);
|
||||
return install_shim_protocols();
|
||||
}
|
||||
|
||||
@@ -2494,9 +2494,10 @@ shim_fini(void)
|
||||
* Remove our hooks from system services.
|
||||
*/
|
||||
unhook_system_services();
|
||||
- unhook_exit();
|
||||
}
|
||||
|
||||
+ unhook_exit();
|
||||
+
|
||||
/*
|
||||
* Free the space allocated for the alternative 2nd stage loader
|
||||
*/
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,89 +0,0 @@
|
||||
From 2cbf56b82a5102777b37c4f7f47c8cf058cea027 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Mon, 13 May 2019 16:34:35 -0400
|
||||
Subject: [PATCH 32/62] Work around stuff -Waddress-of-packed-member finds.
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
In MokManager we get a lot of these:
|
||||
|
||||
../src/MokManager.c:1063:19: error: taking address of packed member of ‘struct <anonymous>’ may result in an unaligned pointer value [-Werror=address-of-packed-member]
|
||||
1063 | if (CompareGuid(&(list[i].Type), &X509_GUID) == 0)
|
||||
| ^~~~~~~~~~~~~~~
|
||||
|
||||
The reason for this is that gnu-efi takes EFI_GUID * as its argument
|
||||
instead of VOID *, and there's nothing telling the compiler that it
|
||||
doesn't have alignment constraints on the input, so the compiler wants
|
||||
it to have 16-byte alignment.
|
||||
|
||||
Just use CompareMem() for these, as that's all CompareGuid is calling
|
||||
anyway.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 08c14376b59
|
||||
---
|
||||
MokManager.c | 12 +++++++-----
|
||||
1 file changed, 7 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index df9b6fe6912..a1bd39a68e2 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -22,6 +22,8 @@
|
||||
#define CERT_STRING L"Select an X509 certificate to enroll:\n\n"
|
||||
#define HASH_STRING L"Select a file to trust:\n\n"
|
||||
|
||||
+#define CompareMemberGuid(x, y) CompareMem(x, y, sizeof(EFI_GUID))
|
||||
+
|
||||
typedef struct {
|
||||
UINT32 MokSize;
|
||||
UINT8 *Mok;
|
||||
@@ -1077,7 +1079,7 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
continue;
|
||||
|
||||
DataSize += sizeof(EFI_SIGNATURE_LIST);
|
||||
- if (CompareGuid(&(list[i].Type), &X509_GUID) == 0)
|
||||
+ if (CompareMemberGuid(&(list[i].Type), &X509_GUID) == 0)
|
||||
DataSize += sizeof(EFI_GUID);
|
||||
DataSize += list[i].MokSize;
|
||||
}
|
||||
@@ -1099,7 +1101,7 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
CertList->SignatureType = list[i].Type;
|
||||
CertList->SignatureHeaderSize = 0;
|
||||
|
||||
- if (CompareGuid(&(list[i].Type), &X509_GUID) == 0) {
|
||||
+ if (CompareMemberGuid(&(list[i].Type), &X509_GUID) == 0) {
|
||||
CertList->SignatureListSize = list[i].MokSize +
|
||||
sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID);
|
||||
CertList->SignatureSize =
|
||||
@@ -1140,7 +1142,7 @@ static void delete_cert(void *key, UINT32 key_size,
|
||||
int i;
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if (CompareGuid(&(mok[i].Type), &X509_GUID) != 0)
|
||||
+ if (CompareMemberGuid(&(mok[i].Type), &X509_GUID) != 0)
|
||||
continue;
|
||||
|
||||
if (mok[i].MokSize == key_size &&
|
||||
@@ -1191,7 +1193,7 @@ static void delete_hash_in_list(EFI_GUID Type, UINT8 * hash, UINT32 hash_size,
|
||||
sig_size = hash_size + sizeof(EFI_GUID);
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if ((CompareGuid(&(mok[i].Type), &Type) != 0) ||
|
||||
+ if ((CompareMemberGuid(&(mok[i].Type), &Type) != 0) ||
|
||||
(mok[i].MokSize < sig_size))
|
||||
continue;
|
||||
|
||||
@@ -1355,7 +1357,7 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
|
||||
/* Search and destroy */
|
||||
for (i = 0; i < del_num; i++) {
|
||||
- if (CompareGuid(&(del_key[i].Type), &X509_GUID) == 0) {
|
||||
+ if (CompareMemberGuid(&(del_key[i].Type), &X509_GUID) == 0) {
|
||||
delete_cert(del_key[i].Mok, del_key[i].MokSize,
|
||||
mok, mok_num);
|
||||
} else if (is_sha2_hash(del_key[i].Type)) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,27 +0,0 @@
|
||||
From c372ec7a254147f70d62c1f72da5806d42df6994 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 5 Sep 2019 10:36:23 -0400
|
||||
Subject: [PATCH 33/62] Fix a use of strlen() instead of Strlen()
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 1870bae7960
|
||||
---
|
||||
shim.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 16911a37b17..a0eb19b91fe 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2118,7 +2118,7 @@ static int is_our_path(EFI_LOADED_IMAGE *li, CHAR16 *path)
|
||||
|
||||
dprint(L"dppath: %s\n", dppath);
|
||||
dprint(L"path: %s\n", path);
|
||||
- if (StrnCaseCmp(dppath, PathName, strlen(dppath)))
|
||||
+ if (StrnCaseCmp(dppath, PathName, StrLen(dppath)))
|
||||
ret = 0;
|
||||
|
||||
done:
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,72 +0,0 @@
|
||||
From 5d30a31fef4eb7e773da24c5e6c20576282a9c3a Mon Sep 17 00:00:00 2001
|
||||
From: Gary Lin <glin@suse.com>
|
||||
Date: Tue, 26 Feb 2019 11:33:53 +0800
|
||||
Subject: [PATCH 34/62] MokManager: Use CompareMem on MokListNode.Type instead
|
||||
of CompareGuid
|
||||
|
||||
Fix the errors from gcc9 '-Werror=address-of-packed-member'
|
||||
|
||||
https://github.com/rhboot/shim/issues/161
|
||||
|
||||
Signed-off-by: Gary Lin <glin@suse.com>
|
||||
Upstream-commit-id: aaa09b35e73
|
||||
---
|
||||
MokManager.c | 14 +++++++++-----
|
||||
1 file changed, 9 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index a1bd39a68e2..30192c16789 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -1079,7 +1079,8 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
continue;
|
||||
|
||||
DataSize += sizeof(EFI_SIGNATURE_LIST);
|
||||
- if (CompareMemberGuid(&(list[i].Type), &X509_GUID) == 0)
|
||||
+ if (CompareMem(&(list[i].Type), &X509_GUID,
|
||||
+ sizeof(EFI_GUID)) == 0)
|
||||
DataSize += sizeof(EFI_GUID);
|
||||
DataSize += list[i].MokSize;
|
||||
}
|
||||
@@ -1101,7 +1102,8 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
CertList->SignatureType = list[i].Type;
|
||||
CertList->SignatureHeaderSize = 0;
|
||||
|
||||
- if (CompareMemberGuid(&(list[i].Type), &X509_GUID) == 0) {
|
||||
+ if (CompareMem(&(list[i].Type), &X509_GUID,
|
||||
+ sizeof(EFI_GUID)) == 0) {
|
||||
CertList->SignatureListSize = list[i].MokSize +
|
||||
sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID);
|
||||
CertList->SignatureSize =
|
||||
@@ -1142,7 +1144,8 @@ static void delete_cert(void *key, UINT32 key_size,
|
||||
int i;
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if (CompareMemberGuid(&(mok[i].Type), &X509_GUID) != 0)
|
||||
+ if (CompareMem(&(mok[i].Type), &X509_GUID,
|
||||
+ sizeof(EFI_GUID)) != 0)
|
||||
continue;
|
||||
|
||||
if (mok[i].MokSize == key_size &&
|
||||
@@ -1193,7 +1196,7 @@ static void delete_hash_in_list(EFI_GUID Type, UINT8 * hash, UINT32 hash_size,
|
||||
sig_size = hash_size + sizeof(EFI_GUID);
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if ((CompareMemberGuid(&(mok[i].Type), &Type) != 0) ||
|
||||
+ if ((CompareMem(&(mok[i].Type), &Type, sizeof(EFI_GUID)) != 0) ||
|
||||
(mok[i].MokSize < sig_size))
|
||||
continue;
|
||||
|
||||
@@ -1357,7 +1360,8 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
|
||||
/* Search and destroy */
|
||||
for (i = 0; i < del_num; i++) {
|
||||
- if (CompareMemberGuid(&(del_key[i].Type), &X509_GUID) == 0) {
|
||||
+ if (CompareMem(&(del_key[i].Type), &X509_GUID,
|
||||
+ sizeof(EFI_GUID)) == 0) {
|
||||
delete_cert(del_key[i].Mok, del_key[i].MokSize,
|
||||
mok, mok_num);
|
||||
} else if (is_sha2_hash(del_key[i].Type)) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,32 +0,0 @@
|
||||
From 44b211bcf7ad58ff29e6495e1c3978e4660cb7d1 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Tue, 15 Jan 2019 18:04:34 -0500
|
||||
Subject: [PATCH 35/62] OpenSSL: always provide OBJ_create() with name strings.
|
||||
|
||||
Some versions of OpenSSL seem to go back and forth as to whether NULL
|
||||
for these names are okay. Don't risk it.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 46b76a01717
|
||||
---
|
||||
shim.c | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index a0eb19b91fe..d7ee2b6de6f 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -388,7 +388,9 @@ static BOOLEAN verify_eku(UINT8 *Cert, UINTN CertSize)
|
||||
EXTENDED_KEY_USAGE *eku;
|
||||
ASN1_OBJECT *module_signing;
|
||||
|
||||
- module_signing = OBJ_nid2obj(OBJ_create(OID_EKU_MODSIGN, NULL, NULL));
|
||||
+ module_signing = OBJ_nid2obj(OBJ_create(OID_EKU_MODSIGN,
|
||||
+ "modsign-eku",
|
||||
+ "modsign-eku"));
|
||||
|
||||
x509 = d2i_X509 (NULL, &Temp, (long) CertSize);
|
||||
if (x509 != NULL) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,42 +0,0 @@
|
||||
From 07de085dabab8daaea589b597e3915893cc98445 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Bj=C3=B8rn=20Forsman?= <bjorn.forsman@gmail.com>
|
||||
Date: Fri, 26 Apr 2019 11:41:02 +0200
|
||||
Subject: [PATCH 36/62] Use portable shebangs: /bin/bash -> /usr/bin/env bash
|
||||
|
||||
Upstream-commit-id: 6a73ca814af
|
||||
---
|
||||
Cryptlib/update.sh | 2 +-
|
||||
make-certs | 4 +++-
|
||||
2 files changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/Cryptlib/update.sh b/Cryptlib/update.sh
|
||||
index 31a082d4db6..7ea59831a06 100755
|
||||
--- a/Cryptlib/update.sh
|
||||
+++ b/Cryptlib/update.sh
|
||||
@@ -1,4 +1,4 @@
|
||||
-#!/bin/bash
|
||||
+#!/usr/bin/env bash
|
||||
|
||||
DIR=$1
|
||||
OPENSSL_VERSION="1.0.2k"
|
||||
diff --git a/make-certs b/make-certs
|
||||
index 3e9293b2497..6f40b234d6a 100755
|
||||
--- a/make-certs
|
||||
+++ b/make-certs
|
||||
@@ -1,10 +1,12 @@
|
||||
-#!/bin/bash -e
|
||||
+#!/usr/bin/env bash
|
||||
#
|
||||
# Generate a root CA cert for signing, and then a subject cert.
|
||||
# Usage: make-certs.sh hostname [user[@domain]] [more ...]
|
||||
# For testing only, probably still has some bugs in it.
|
||||
#
|
||||
|
||||
+set -e
|
||||
+
|
||||
DOMAIN=xn--u4h.net
|
||||
DAYS=365
|
||||
KEYTYPE=RSA
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,44 +0,0 @@
|
||||
From 6fd8db6bb3b23b9e41f109135253f77263071f46 Mon Sep 17 00:00:00 2001
|
||||
From: Chris Coulson <chris.coulson@canonical.com>
|
||||
Date: Sat, 22 Jun 2019 15:33:03 +0100
|
||||
Subject: [PATCH 37/62] tpm: Fix off-by-one error when calculating event size
|
||||
|
||||
tpm_log_event_raw() allocates a buffer for the EFI_TCG2_EVENT structure
|
||||
that is one byte larger than necessary, and sets event->Size accordingly.
|
||||
The result of this is that the event data recorded in the log differs
|
||||
from the data that is measured to the TPM (it has an extra zero byte
|
||||
at the end).
|
||||
|
||||
Upstream-commit-id: 8a27a4809a6
|
||||
---
|
||||
tpm.c | 6 ++++--
|
||||
1 file changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index f07362c70bb..516fb876caa 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -131,8 +131,10 @@ static EFI_STATUS tpm_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
#endif
|
||||
} else if (tpm2) {
|
||||
EFI_TCG2_EVENT *event;
|
||||
+ UINTN event_size = sizeof(*event) - sizeof(event->Event) +
|
||||
+ logsize;
|
||||
|
||||
- event = AllocatePool(sizeof(*event) + logsize);
|
||||
+ event = AllocatePool(event_size);
|
||||
if (!event) {
|
||||
perror(L"Unable to allocate event structure\n");
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
@@ -142,7 +144,7 @@ static EFI_STATUS tpm_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
event->Header.HeaderVersion = 1;
|
||||
event->Header.PCRIndex = pcr;
|
||||
event->Header.EventType = type;
|
||||
- event->Size = sizeof(*event) - sizeof(event->Event) + logsize + 1;
|
||||
+ event->Size = event_size;
|
||||
CopyMem(event->Event, (VOID *)log, logsize);
|
||||
if (hash) {
|
||||
/* TPM 2 systems will generate the appropriate hash
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,36 +0,0 @@
|
||||
From 9f80be9f16a854e3946568fa92edebe26eb79e78 Mon Sep 17 00:00:00 2001
|
||||
From: Chris Coulson <chris.coulson@canonical.com>
|
||||
Date: Sat, 22 Jun 2019 15:37:29 +0100
|
||||
Subject: [PATCH 38/62] tpm: Define EFI_VARIABLE_DATA_TREE as packed
|
||||
|
||||
tpm_measure_variable() calculates VarLogSize by adding the size of VarName
|
||||
and VarData to the size of EFI_VARIABLE_DATA_TREE, and then subtracting
|
||||
the size of the UnicodeName and VariableData members. This results in a
|
||||
calculation that is 5 bytes larger than necessary because it doesn't take
|
||||
in to account the padding of these members. The effect of this is that
|
||||
shim measures an additional 5 zero bytes when measuring UEFI variables
|
||||
(at least on 64-bit architectures).
|
||||
|
||||
Byte packing EFI_VARIABLE_DATA_TREE fixes this.
|
||||
|
||||
Upstream-commit-id: 7e4d3f1c8c7
|
||||
---
|
||||
tpm.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index 516fb876caa..c0617bb479e 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -233,7 +233,7 @@ typedef struct {
|
||||
UINT64 VariableDataLength;
|
||||
CHAR16 UnicodeName[1];
|
||||
INT8 VariableData[1];
|
||||
-} EFI_VARIABLE_DATA_TREE;
|
||||
+} __attribute__ ((packed)) EFI_VARIABLE_DATA_TREE;
|
||||
|
||||
static BOOLEAN tpm_data_measured(CHAR16 *VarName, EFI_GUID VendorGuid, UINTN VarSize, VOID *VarData)
|
||||
{
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,223 +0,0 @@
|
||||
From 55163bc82c5179adb109c3d8b982c2689d68b4c9 Mon Sep 17 00:00:00 2001
|
||||
From: Ivan Hu <ivan.hu@canonical.com>
|
||||
Date: Fri, 10 May 2019 17:50:12 +0800
|
||||
Subject: [PATCH 39/62] MokManager: console mode modification for hi-dpi screen
|
||||
devices
|
||||
|
||||
There are lots of hi-dpi laptops nowadays, as doing mok enrollment, the font
|
||||
is too small to see.
|
||||
https://bugs.launchpad.net/ubuntu/+source/shim/+bug/1822043
|
||||
|
||||
This patch checks if the resolution is larger than Full HD (1920x1080) and
|
||||
current console output columns and rows is in a good mode. Then swith the
|
||||
console output to a better mode.
|
||||
|
||||
Signed-off-by: Ivan Hu <ivan.hu@canonical.com>
|
||||
Upstream-commit-id: cf05af6d899
|
||||
---
|
||||
MokManager.c | 2 +
|
||||
lib/console.c | 161 +++++++++++++++++++++++++++++++++++++++++++++-
|
||||
include/console.h | 2 +
|
||||
3 files changed, 164 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index 30192c16789..78da9fd95ee 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -2560,6 +2560,8 @@ EFI_STATUS efi_main(EFI_HANDLE image_handle, EFI_SYSTEM_TABLE * systab)
|
||||
|
||||
setup_rand();
|
||||
|
||||
+ console_mode_handle();
|
||||
+
|
||||
efi_status = check_mok_request(image_handle);
|
||||
|
||||
console_fini();
|
||||
diff --git a/lib/console.c b/lib/console.c
|
||||
index 3aee41cd276..c92d27f3c86 100644
|
||||
--- a/lib/console.c
|
||||
+++ b/lib/console.c
|
||||
@@ -409,7 +409,166 @@ console_notify(CHAR16 *string)
|
||||
console_alertbox(str_arr);
|
||||
}
|
||||
|
||||
-#define ARRAY_SIZE(a) (sizeof (a) / sizeof ((a)[0]))
|
||||
+void
|
||||
+console_save_and_set_mode(SIMPLE_TEXT_OUTPUT_MODE * SavedMode)
|
||||
+{
|
||||
+ SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
|
||||
+
|
||||
+ if (!SavedMode) {
|
||||
+ console_print(L"Invalid parameter: SavedMode\n");
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ CopyMem(SavedMode, co->Mode, sizeof(SIMPLE_TEXT_OUTPUT_MODE));
|
||||
+ co->EnableCursor(co, FALSE);
|
||||
+ co->SetAttribute(co, EFI_LIGHTGRAY | EFI_BACKGROUND_BLUE);
|
||||
+}
|
||||
+
|
||||
+void
|
||||
+console_restore_mode(SIMPLE_TEXT_OUTPUT_MODE * SavedMode)
|
||||
+{
|
||||
+ SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
|
||||
+
|
||||
+ co->EnableCursor(co, SavedMode->CursorVisible);
|
||||
+ co->SetCursorPosition(co, SavedMode->CursorColumn,
|
||||
+ SavedMode->CursorRow);
|
||||
+ co->SetAttribute(co, SavedMode->Attribute);
|
||||
+}
|
||||
+
|
||||
+int
|
||||
+console_countdown(CHAR16* title, const CHAR16* message, int timeout)
|
||||
+{
|
||||
+ SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
|
||||
+ SIMPLE_INPUT_INTERFACE *ci = ST->ConIn;
|
||||
+ SIMPLE_TEXT_OUTPUT_MODE SavedMode;
|
||||
+ EFI_INPUT_KEY key;
|
||||
+ EFI_STATUS efi_status;
|
||||
+ UINTN cols, rows;
|
||||
+ CHAR16 *titles[2];
|
||||
+ int wait = 10000000;
|
||||
+
|
||||
+ console_save_and_set_mode(&SavedMode);
|
||||
+
|
||||
+ titles[0] = title;
|
||||
+ titles[1] = NULL;
|
||||
+
|
||||
+ console_print_box_at(titles, -1, 0, 0, -1, -1, 1, 1);
|
||||
+
|
||||
+ co->QueryMode(co, co->Mode->Mode, &cols, &rows);
|
||||
+
|
||||
+ console_print_at((cols - StrLen(message)) / 2, rows / 2, message);
|
||||
+ while (1) {
|
||||
+ if (timeout > 1)
|
||||
+ console_print_at(2, rows - 3,
|
||||
+ L"Booting in %d seconds ",
|
||||
+ timeout);
|
||||
+ else if (timeout)
|
||||
+ console_print_at(2, rows - 3,
|
||||
+ L"Booting in %d second ",
|
||||
+ timeout);
|
||||
+
|
||||
+ efi_status = WaitForSingleEvent(ci->WaitForKey, wait);
|
||||
+ if (efi_status != EFI_TIMEOUT) {
|
||||
+ /* Clear the key in the queue */
|
||||
+ ci->ReadKeyStroke(ci, &key);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ timeout--;
|
||||
+ if (!timeout)
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ console_restore_mode(&SavedMode);
|
||||
+
|
||||
+ return timeout;
|
||||
+}
|
||||
+
|
||||
+#define HORIZONTAL_MAX_OK 1920
|
||||
+#define VERTICAL_MAX_OK 1080
|
||||
+#define COLUMNS_MAX_OK 200
|
||||
+#define ROWS_MAX_OK 100
|
||||
+
|
||||
+void
|
||||
+console_mode_handle(VOID)
|
||||
+{
|
||||
+ SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
|
||||
+ EFI_GRAPHICS_OUTPUT_PROTOCOL *gop;
|
||||
+ EFI_GUID gop_guid = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
|
||||
+ EFI_GRAPHICS_OUTPUT_MODE_INFORMATION *Info;
|
||||
+
|
||||
+ UINTN mode_set;
|
||||
+ UINTN rows = 0, columns = 0;
|
||||
+ EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
+
|
||||
+ efi_status = gBS->LocateProtocol(&gop_guid, NULL, (void **)&gop);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ console_error(L"Locate graphic output protocol fail", efi_status);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ Info = gop->Mode->Info;
|
||||
+
|
||||
+ /*
|
||||
+ * Start verifying if we are in a resolution larger than Full HD
|
||||
+ * (1920x1080). If we're not, assume we're in a good mode and do not
|
||||
+ * try to change it.
|
||||
+ */
|
||||
+ if (Info->HorizontalResolution <= HORIZONTAL_MAX_OK &&
|
||||
+ Info->VerticalResolution <= VERTICAL_MAX_OK) {
|
||||
+ /* keep original mode and return */
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ efi_status = co->QueryMode(co, co->Mode->Mode, &columns, &rows);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ console_error(L"Console query mode fail", efi_status);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Verify current console output to check if the character columns and
|
||||
+ * rows in a good mode.
|
||||
+ */
|
||||
+ if (columns <= COLUMNS_MAX_OK && rows <= ROWS_MAX_OK) {
|
||||
+ /* keep original mode and return */
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ if (!console_text_mode)
|
||||
+ setup_console(1);
|
||||
+
|
||||
+ co->Reset(co, TRUE);
|
||||
+
|
||||
+ /*
|
||||
+ * If we reached here, then we have a high resolution screen and the
|
||||
+ * text too small. Try to switch to a better mode. Mode number 2 is
|
||||
+ * first non standard mode, which is provided by the device
|
||||
+ * manufacturer, so it should be a good mode.
|
||||
+ */
|
||||
+ if (co->Mode->MaxMode > 2)
|
||||
+ mode_set = 2;
|
||||
+ else
|
||||
+ mode_set = 0;
|
||||
+
|
||||
+ efi_status = co->SetMode(co, mode_set);
|
||||
+ if (EFI_ERROR(efi_status) && mode_set != 0) {
|
||||
+ /*
|
||||
+ * Set to 0 mode which is required that all output devices
|
||||
+ * support at least 80x25 text mode.
|
||||
+ */
|
||||
+ mode_set = 0;
|
||||
+ efi_status = co->SetMode(co, mode_set);
|
||||
+ }
|
||||
+
|
||||
+ co->ClearScreen(co);
|
||||
+
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ console_error(L"Console set mode fail", efi_status);
|
||||
+ }
|
||||
+
|
||||
+ return;
|
||||
+}
|
||||
|
||||
/* Copy of gnu-efi-3.0 with the added secure boot strings */
|
||||
static struct {
|
||||
diff --git a/include/console.h b/include/console.h
|
||||
index deb4fa3db23..9f259c71b72 100644
|
||||
--- a/include/console.h
|
||||
+++ b/include/console.h
|
||||
@@ -34,6 +34,8 @@ void
|
||||
console_notify(CHAR16 *string);
|
||||
void
|
||||
console_reset(void);
|
||||
+void
|
||||
+console_mode_handle(void);
|
||||
#define NOSEL 0x7fffffff
|
||||
|
||||
typedef struct _EFI_CONSOLE_CONTROL_PROTOCOL EFI_CONSOLE_CONTROL_PROTOCOL;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,111 +0,0 @@
|
||||
From d57e53f3bddc4bc7299b3d5efd5ba8c547e8dfa5 Mon Sep 17 00:00:00 2001
|
||||
From: Jonas Witschel <diabonas@gmx.de>
|
||||
Date: Thu, 5 Sep 2019 10:39:37 +0200
|
||||
Subject: [PATCH 40/62] MokManager: avoid -Werror=address-of-packed-member
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
When compiling with GCC 9, there are a couple of errors of the form
|
||||
|
||||
MokManager.c: In function ‘write_back_mok_list’:
|
||||
MokManager.c:1056:19: error: taking address of packed member of ‘struct <anonymous>’ may result in an unaligned pointer value [-Werror=address-of-packed-member]
|
||||
1056 | if (CompareGuid(&(list[i].Type), &X509_GUID) == 0)
|
||||
| ^~~~~~~~~~~~~~~
|
||||
|
||||
Copying the member of the packed struct to a temporary variable and
|
||||
pointing to that variable solves the problem.
|
||||
|
||||
Upstream-commit-id: 58532e12e9a
|
||||
---
|
||||
MokManager.c | 22 +++++++++++++---------
|
||||
1 file changed, 13 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index 78da9fd95ee..fa73e2fd865 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -1064,6 +1064,7 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
EFI_STATUS efi_status;
|
||||
EFI_SIGNATURE_LIST *CertList;
|
||||
EFI_SIGNATURE_DATA *CertData;
|
||||
+ EFI_GUID type;
|
||||
void *Data = NULL, *ptr;
|
||||
INTN DataSize = 0;
|
||||
int i;
|
||||
@@ -1079,8 +1080,8 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
continue;
|
||||
|
||||
DataSize += sizeof(EFI_SIGNATURE_LIST);
|
||||
- if (CompareMem(&(list[i].Type), &X509_GUID,
|
||||
- sizeof(EFI_GUID)) == 0)
|
||||
+ type = list[i].Type; /* avoid -Werror=address-of-packed-member */
|
||||
+ if (CompareGuid(&type, &X509_GUID) == 0)
|
||||
DataSize += sizeof(EFI_GUID);
|
||||
DataSize += list[i].MokSize;
|
||||
}
|
||||
@@ -1102,8 +1103,7 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
CertList->SignatureType = list[i].Type;
|
||||
CertList->SignatureHeaderSize = 0;
|
||||
|
||||
- if (CompareMem(&(list[i].Type), &X509_GUID,
|
||||
- sizeof(EFI_GUID)) == 0) {
|
||||
+ if (CompareGuid(&(CertList->SignatureType), &X509_GUID) == 0) {
|
||||
CertList->SignatureListSize = list[i].MokSize +
|
||||
sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID);
|
||||
CertList->SignatureSize =
|
||||
@@ -1141,11 +1141,12 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
static void delete_cert(void *key, UINT32 key_size,
|
||||
MokListNode * mok, INTN mok_num)
|
||||
{
|
||||
+ EFI_GUID type;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if (CompareMem(&(mok[i].Type), &X509_GUID,
|
||||
- sizeof(EFI_GUID)) != 0)
|
||||
+ type = mok[i].Type; /* avoid -Werror=address-of-packed-member */
|
||||
+ if (CompareGuid(&type, &X509_GUID) != 0)
|
||||
continue;
|
||||
|
||||
if (mok[i].MokSize == key_size &&
|
||||
@@ -1187,6 +1188,7 @@ static void mem_move(void *dest, void *src, UINTN size)
|
||||
static void delete_hash_in_list(EFI_GUID Type, UINT8 * hash, UINT32 hash_size,
|
||||
MokListNode * mok, INTN mok_num)
|
||||
{
|
||||
+ EFI_GUID type;
|
||||
UINT32 sig_size;
|
||||
UINT32 list_num;
|
||||
int i, del_ind;
|
||||
@@ -1196,7 +1198,8 @@ static void delete_hash_in_list(EFI_GUID Type, UINT8 * hash, UINT32 hash_size,
|
||||
sig_size = hash_size + sizeof(EFI_GUID);
|
||||
|
||||
for (i = 0; i < mok_num; i++) {
|
||||
- if ((CompareMem(&(mok[i].Type), &Type, sizeof(EFI_GUID)) != 0) ||
|
||||
+ type = mok[i].Type; /* avoid -Werror=address-of-packed-member */
|
||||
+ if ((CompareGuid(&type, &Type) != 0) ||
|
||||
(mok[i].MokSize < sig_size))
|
||||
continue;
|
||||
|
||||
@@ -1252,6 +1255,7 @@ static void delete_hash_list(EFI_GUID Type, void *hash_list, UINT32 list_size,
|
||||
static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
+ EFI_GUID type;
|
||||
CHAR16 *db_name;
|
||||
CHAR16 *auth_name;
|
||||
CHAR16 *err_strs[] = { NULL, NULL, NULL };
|
||||
@@ -1360,8 +1364,8 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
|
||||
/* Search and destroy */
|
||||
for (i = 0; i < del_num; i++) {
|
||||
- if (CompareMem(&(del_key[i].Type), &X509_GUID,
|
||||
- sizeof(EFI_GUID)) == 0) {
|
||||
+ type = del_key[i].Type; /* avoid -Werror=address-of-packed-member */
|
||||
+ if (CompareGuid(&type, &X509_GUID) == 0) {
|
||||
delete_cert(del_key[i].Mok, del_key[i].MokSize,
|
||||
mok, mok_num);
|
||||
} else if (is_sha2_hash(del_key[i].Type)) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,31 +0,0 @@
|
||||
From 58df8d745c6516818ba6ebfa8fe826702c1621a0 Mon Sep 17 00:00:00 2001
|
||||
From: Chris Coulson <chris.coulson@canonical.com>
|
||||
Date: Thu, 26 Sep 2019 20:01:01 +0100
|
||||
Subject: [PATCH 41/62] tpm: Don't log duplicate identical events
|
||||
|
||||
According to the comment in tpm_measure_variable ("Don't measure something that we've already measured"), shim
|
||||
shouldn't measure duplicate events if they are identical, which also aligns with section 2.3.4.8 of the TCG PC
|
||||
Client Platform Firmware Profile Specification ("If it has been measured previously, it MUST NOT be measured
|
||||
again"). This is currently broken because tpm_data_measured() uses the return value of CompareGuid() incorrectly.
|
||||
|
||||
Upstream-commit-id: 103adc89ce5
|
||||
---
|
||||
tpm.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index c0617bb479e..196b93c30f6 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -241,7 +241,7 @@ static BOOLEAN tpm_data_measured(CHAR16 *VarName, EFI_GUID VendorGuid, UINTN Var
|
||||
|
||||
for (i=0; i<measuredcount; i++) {
|
||||
if ((StrCmp (VarName, measureddata[i].VariableName) == 0) &&
|
||||
- (CompareGuid (&VendorGuid, measureddata[i].VendorGuid)) &&
|
||||
+ (CompareGuid (&VendorGuid, measureddata[i].VendorGuid) == 0) &&
|
||||
(VarSize == measureddata[i].Size) &&
|
||||
(CompareMem (VarData, measureddata[i].Data, VarSize) == 0)) {
|
||||
return TRUE;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,57 +0,0 @@
|
||||
From 5e6e0792cedb3b71cbe061ae56e96906cf710579 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Mon, 18 Nov 2019 13:59:14 -0500
|
||||
Subject: [PATCH 42/62] Slightly better debugging messages
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 173d35fe8f5
|
||||
---
|
||||
shim.c | 14 ++++++++++----
|
||||
1 file changed, 10 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index d7ee2b6de6f..2f7aba07421 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2459,6 +2459,8 @@ uninstall_shim_protocols(void)
|
||||
EFI_STATUS
|
||||
shim_init(void)
|
||||
{
|
||||
+ EFI_STATUS efi_status;
|
||||
+
|
||||
setup_verbosity();
|
||||
dprint(L"%a", shim_version);
|
||||
|
||||
@@ -2479,7 +2481,12 @@ shim_init(void)
|
||||
}
|
||||
|
||||
hook_exit(systab);
|
||||
- return install_shim_protocols();
|
||||
+
|
||||
+ efi_status = install_shim_protocols();
|
||||
+ if (EFI_ERROR(efi_status))
|
||||
+ perror(L"install_shim_protocols() failed: %r\n", efi_status);
|
||||
+
|
||||
+ return efi_status;
|
||||
}
|
||||
|
||||
void
|
||||
@@ -2575,13 +2582,12 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
build_cert = shim_cert;
|
||||
#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
CHAR16 *msgs[] = {
|
||||
- L"import_mok_state() failed\n",
|
||||
- L"shim_int() failed\n",
|
||||
+ L"import_mok_state() failed",
|
||||
+ L"shim_init() failed",
|
||||
NULL
|
||||
};
|
||||
int msg = 0;
|
||||
|
||||
-
|
||||
/*
|
||||
* Set up the shim lock protocol so that grub and MokManager can
|
||||
* call back in and use shim functions
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,69 +0,0 @@
|
||||
From 959f5e4e993a82020fef48c7e7c012a44074645c Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Mon, 18 Nov 2019 13:58:46 -0500
|
||||
Subject: [PATCH 43/62] Actually check for errors from set_second_stage()
|
||||
|
||||
This changes shim_init() to check for errors from set_second_stage().
|
||||
In order to make that work, it also does the following:
|
||||
|
||||
- correctly /always/ allocate second_stage, not sometimes allocate and
|
||||
sometimes point at .data
|
||||
- test for LoadOptionSize == 0 and return success
|
||||
- print an error message for the failure so we can see it.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 354bd9b1931
|
||||
---
|
||||
shim.c | 21 +++++++++++++++++++--
|
||||
1 file changed, 19 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 2f7aba07421..5329795c333 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2141,8 +2141,15 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle)
|
||||
CHAR16 *loader_str = NULL;
|
||||
UINTN loader_len = 0;
|
||||
unsigned int i;
|
||||
+ UINTN second_stage_len;
|
||||
|
||||
- second_stage = DEFAULT_LOADER;
|
||||
+ second_stage_len = StrLen(DEFAULT_LOADER) + 1;
|
||||
+ second_stage = AllocatePool(second_stage_len);
|
||||
+ if (!second_stage) {
|
||||
+ perror(L"Could not allocate %lu bytes\n", second_stage_len);
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+ }
|
||||
+ StrCpy(second_stage, DEFAULT_LOADER);
|
||||
load_options = NULL;
|
||||
load_options_size = 0;
|
||||
|
||||
@@ -2199,6 +2206,12 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle)
|
||||
* BDS will add that, but we ignore that here.
|
||||
*/
|
||||
|
||||
+ /*
|
||||
+ * Maybe there just aren't any options...
|
||||
+ */
|
||||
+ if (li->LoadOptionsSize == 0)
|
||||
+ return EFI_SUCCESS;
|
||||
+
|
||||
/*
|
||||
* In either case, we've got to have at least a UCS2 NUL...
|
||||
*/
|
||||
@@ -2465,7 +2478,11 @@ shim_init(void)
|
||||
dprint(L"%a", shim_version);
|
||||
|
||||
/* Set the second stage loader */
|
||||
- set_second_stage (global_image_handle);
|
||||
+ efi_status = set_second_stage(global_image_handle);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"set_second_stage() failed: %r\n", efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
|
||||
if (secure_mode()) {
|
||||
if (vendor_cert_size || vendor_dbx_size) {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,140 +0,0 @@
|
||||
From c6bedd5b83529925c3ec08f96a3bf61c81bff0ae Mon Sep 17 00:00:00 2001
|
||||
From: Laszlo Ersek <lersek@redhat.com>
|
||||
Date: Tue, 28 Jan 2020 23:33:46 +0100
|
||||
Subject: [PATCH 44/62] translate_slashes(): don't write to string literals
|
||||
|
||||
Currently, all three invocations of the translate_slashes() function may
|
||||
lead to writes to the string literal that is #defined with the
|
||||
DEFAULT_LOADER_CHAR macro. According to ISO C99 6.4.5p6, this is undefined
|
||||
behavior ("If the program attempts to modify such an array, the behavior
|
||||
is undefined").
|
||||
|
||||
This bug crashes shim on e.g. the 64-bit ArmVirtQemu platform ("Data
|
||||
abort: Permission fault"), where the platform firmware maps the .text
|
||||
section (which contains the string literal) read-only.
|
||||
|
||||
Modify translate_slashes() so that it copies and translates characters
|
||||
from an input array of "char" to an output array of "CHAR8".
|
||||
|
||||
While at it, fix another bug. Before this patch, if translate_slashes()
|
||||
ever encountered a double backslash (translating it to a single forward
|
||||
slash), then the output would end up shorter than the input. However, the
|
||||
output was not NUL-terminated in-place, therefore the original string
|
||||
length (and according trailing garbage) would be preserved. After this
|
||||
patch, the NUL-termination on contraction is automatic, as the output
|
||||
array's contents are indeterminate when entering the function, and so we
|
||||
must NUL-terminate it anyway.
|
||||
|
||||
Fixes: 8e9124227d18475d3bc634c33518963fc8db7c98
|
||||
Fixes: e62b69a5b0b87c6df7a4fc23906134945309e927
|
||||
Fixes: 3d79bcb2651b9eae809b975b3e03e2f96c067072
|
||||
Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1795654
|
||||
Signed-off-by: Laszlo Ersek <lersek@redhat.com>
|
||||
Upstream-commit-id: 9813e8bc8b3
|
||||
---
|
||||
httpboot.c | 4 ++--
|
||||
netboot.c | 16 +++++++++++-----
|
||||
include/str.h | 14 ++++++++------
|
||||
3 files changed, 21 insertions(+), 13 deletions(-)
|
||||
|
||||
diff --git a/httpboot.c b/httpboot.c
|
||||
index 3622e85867c..2d27e8ed993 100644
|
||||
--- a/httpboot.c
|
||||
+++ b/httpboot.c
|
||||
@@ -743,14 +743,14 @@ httpboot_fetch_buffer (EFI_HANDLE image, VOID **buffer, UINT64 *buf_size)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
EFI_HANDLE nic;
|
||||
- CHAR8 *next_loader = NULL;
|
||||
+ CHAR8 next_loader[sizeof DEFAULT_LOADER_CHAR];
|
||||
CHAR8 *next_uri = NULL;
|
||||
CHAR8 *hostname = NULL;
|
||||
|
||||
if (!uri)
|
||||
return EFI_NOT_READY;
|
||||
|
||||
- next_loader = translate_slashes(DEFAULT_LOADER_CHAR);
|
||||
+ translate_slashes(next_loader, DEFAULT_LOADER_CHAR);
|
||||
|
||||
/* Create the URI for the next loader based on the original URI */
|
||||
efi_status = generate_next_uri(uri, next_loader, &next_uri);
|
||||
diff --git a/netboot.c b/netboot.c
|
||||
index 58babfb4d2e..4922ef284b1 100644
|
||||
--- a/netboot.c
|
||||
+++ b/netboot.c
|
||||
@@ -189,7 +189,9 @@ static BOOLEAN extract_tftp_info(CHAR8 *url)
|
||||
CHAR8 *start, *end;
|
||||
CHAR8 ip6str[40];
|
||||
CHAR8 ip6inv[16];
|
||||
- CHAR8 *template = (CHAR8 *)translate_slashes(DEFAULT_LOADER_CHAR);
|
||||
+ CHAR8 template[sizeof DEFAULT_LOADER_CHAR];
|
||||
+
|
||||
+ translate_slashes(template, DEFAULT_LOADER_CHAR);
|
||||
|
||||
// to check against str2ip6() errors
|
||||
memset(ip6inv, 0, sizeof(ip6inv));
|
||||
@@ -254,10 +256,14 @@ static EFI_STATUS parseDhcp6()
|
||||
|
||||
static EFI_STATUS parseDhcp4()
|
||||
{
|
||||
- CHAR8 *template = (CHAR8 *)translate_slashes(DEFAULT_LOADER_CHAR);
|
||||
- INTN template_len = strlen(template) + 1;
|
||||
+ CHAR8 template[sizeof DEFAULT_LOADER_CHAR];
|
||||
+ INTN template_len;
|
||||
+ UINTN template_ofs = 0;
|
||||
EFI_PXE_BASE_CODE_DHCPV4_PACKET* pkt_v4 = (EFI_PXE_BASE_CODE_DHCPV4_PACKET *)&pxe->Mode->DhcpAck.Dhcpv4;
|
||||
|
||||
+ translate_slashes(template, DEFAULT_LOADER_CHAR);
|
||||
+ template_len = strlen(template) + 1;
|
||||
+
|
||||
if(pxe->Mode->ProxyOfferReceived) {
|
||||
/*
|
||||
* Proxy should not have precedence. Check if DhcpAck
|
||||
@@ -288,8 +294,8 @@ static EFI_STATUS parseDhcp4()
|
||||
full_path[dir_len-1] = '\0';
|
||||
}
|
||||
if (dir_len == 0 && dir[0] != '/' && template[0] == '/')
|
||||
- template++;
|
||||
- strcata(full_path, template);
|
||||
+ template_ofs++;
|
||||
+ strcata(full_path, template + template_ofs);
|
||||
memcpy(&tftp_addr.v4, pkt_v4->BootpSiAddr, 4);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
diff --git a/include/str.h b/include/str.h
|
||||
index 9a748366bd1..f73c6212cd9 100644
|
||||
--- a/include/str.h
|
||||
+++ b/include/str.h
|
||||
@@ -45,21 +45,23 @@ strcata(CHAR8 *dest, const CHAR8 *src)
|
||||
static inline
|
||||
__attribute__((unused))
|
||||
CHAR8 *
|
||||
-translate_slashes(char *str)
|
||||
+translate_slashes(CHAR8 *out, const char *str)
|
||||
{
|
||||
int i;
|
||||
int j;
|
||||
- if (str == NULL)
|
||||
- return (CHAR8 *)str;
|
||||
+ if (str == NULL || out == NULL)
|
||||
+ return NULL;
|
||||
|
||||
for (i = 0, j = 0; str[i] != '\0'; i++, j++) {
|
||||
if (str[i] == '\\') {
|
||||
- str[j] = '/';
|
||||
+ out[j] = '/';
|
||||
if (str[i+1] == '\\')
|
||||
i++;
|
||||
- }
|
||||
+ } else
|
||||
+ out[j] = str[i];
|
||||
}
|
||||
- return (CHAR8 *)str;
|
||||
+ out[j] = '\0';
|
||||
+ return out;
|
||||
}
|
||||
|
||||
#endif /* SHIM_STR_H */
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,93 +0,0 @@
|
||||
From 89d72301aa67c82f00fe7fa4f42d7f6eb6045538 Mon Sep 17 00:00:00 2001
|
||||
From: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Date: Tue, 18 Feb 2020 12:03:28 +0100
|
||||
Subject: [PATCH 45/62] shim: Update EFI_LOADED_IMAGE with the second stage
|
||||
loader file path
|
||||
|
||||
When shim loads the second stage loader (e.g: GRUB) the FilePath field of
|
||||
the EFI_LOADED_IMAGE structure isn't updated with the path of the loaded
|
||||
binary. So it still contains the file path of the shim binary.
|
||||
|
||||
This isn't a problem since the file path is currently not used. But should
|
||||
be used to set the DevicePath field of the EFI_IMAGE_LOAD_EVENT structure
|
||||
that is logged when measuring the PE/COFF binaries. In that case the TPM
|
||||
Event Log will have an incorrect file path for the measured binary, i.e:
|
||||
|
||||
$ hexdump -Cv /sys/kernel/security/tpm0/binary_bios_measurements
|
||||
...
|
||||
00000a50 00 00 00 00 00 00 04 04 34 00 5c 00 45 00 46 00 |........4.\.E.F.|
|
||||
00000a60 49 00 5c 00 72 00 65 00 64 00 68 00 61 00 74 00 |I.\.r.e.d.h.a.t.|
|
||||
00000a70 5c 00 73 00 68 00 69 00 6d 00 78 00 36 00 34 00 |\.s.h.i.m.x.6.4.|
|
||||
00000a80 2e 00 65 00 66 00 69 00 00 00 7f ff 04 00 00 00 |..e.f.i.........|
|
||||
00000a90 00 00 00 00 00 00 af 08 00 00 00 0d 00 00 00 b5 |................|
|
||||
00000aa0 cd d0 8f bb 16 31 e2 80 8b e8 58 75 c9 89 18 95 |.....1....Xu....|
|
||||
00000ab0 d2 de 15 15 00 00 00 67 72 75 62 5f 63 6d 64 20 |.......grub_cmd |
|
||||
00000ac0 73 65 74 20 70 61 67 65 72 3d 31 00 08 00 00 00 |set pager=1.....|
|
||||
...
|
||||
|
||||
So update the EFI_LOADED_IMAGE structure with the second stage loader file
|
||||
path to have the correct value in the log, i.e:
|
||||
|
||||
$ hexdump -Cv /sys/kernel/security/tpm0/binary_bios_measurements
|
||||
...
|
||||
00000a50 00 00 00 00 00 00 04 04 34 00 5c 00 45 00 46 00 |........4.\.E.F.|
|
||||
00000a60 49 00 5c 00 72 00 65 00 64 00 68 00 61 00 74 00 |I.\.r.e.d.h.a.t.|
|
||||
00000a70 5c 00 67 00 72 00 75 00 62 00 78 00 36 00 34 00 |\.g.r.u.b.x.6.4.|
|
||||
00000a80 2e 00 65 00 66 00 69 00 00 00 7f ff 04 00 00 00 |..e.f.i.........|
|
||||
00000a90 00 00 00 00 00 00 af 08 00 00 00 0d 00 00 00 b5 |................|
|
||||
00000aa0 cd d0 8f bb 16 31 e2 80 8b e8 58 75 c9 89 18 95 |.....1....Xu....|
|
||||
00000ab0 d2 de 15 15 00 00 00 67 72 75 62 5f 63 6d 64 20 |.......grub_cmd |
|
||||
00000ac0 73 65 74 20 70 61 67 65 72 3d 31 00 08 00 00 00 |set pager=1.....|
|
||||
...
|
||||
|
||||
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Upstream-commit-id: cd7d42d493d
|
||||
---
|
||||
shim.c | 17 +++++++++++++++--
|
||||
1 file changed, 15 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 5329795c333..a4f7769b38b 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -1925,6 +1925,16 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
|
||||
*/
|
||||
CopyMem(&li_bak, li, sizeof(li_bak));
|
||||
|
||||
+ /*
|
||||
+ * Update the loaded image with the second stage loader file path
|
||||
+ */
|
||||
+ li->FilePath = FileDevicePath(NULL, PathName);
|
||||
+ if (!li->FilePath) {
|
||||
+ perror(L"Unable to update loaded image file path\n");
|
||||
+ efi_status = EFI_OUT_OF_RESOURCES;
|
||||
+ goto restore;
|
||||
+ }
|
||||
+
|
||||
/*
|
||||
* Verify and, if appropriate, relocate and execute the executable
|
||||
*/
|
||||
@@ -1934,8 +1944,7 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
|
||||
perror(L"Failed to load image: %r\n", efi_status);
|
||||
PrintErrors();
|
||||
ClearErrors();
|
||||
- CopyMem(li, &li_bak, sizeof(li_bak));
|
||||
- goto done;
|
||||
+ goto restore;
|
||||
}
|
||||
|
||||
loader_is_participating = 0;
|
||||
@@ -1945,6 +1954,10 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
|
||||
*/
|
||||
efi_status = entry_point(image_handle, systab);
|
||||
|
||||
+restore:
|
||||
+ if (li->FilePath)
|
||||
+ FreePool(li->FilePath);
|
||||
+
|
||||
/*
|
||||
* Restore our original loaded image values
|
||||
*/
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,124 +0,0 @@
|
||||
From 0a8f7ade76ff3eede486027eaa638181e6bed3b8 Mon Sep 17 00:00:00 2001
|
||||
From: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Date: Tue, 18 Feb 2020 12:03:17 +0100
|
||||
Subject: [PATCH 46/62] tpm: Include information about PE/COFF images in the
|
||||
TPM Event Log
|
||||
|
||||
The "TCG PC Client Specific Platform Firmware Profile Specification" says
|
||||
that when measuring a PE/COFF image, the TCG_PCR_EVENT2 structure Event
|
||||
field MUST contain a UEFI_IMAGE_LOAD_EVENT structure.
|
||||
|
||||
Currently an empty UEFI_IMAGE_LOAD_EVENT structure is passed so users only
|
||||
have the hash of the PE/COFF image, but not information such the file path
|
||||
of the binary.
|
||||
|
||||
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Upstream-commit-id: c252b9ee94c
|
||||
---
|
||||
shim.c | 7 +++++--
|
||||
tpm.c | 46 ++++++++++++++++++++++++++++++++--------------
|
||||
include/tpm.h | 5 +++--
|
||||
3 files changed, 40 insertions(+), 18 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index a4f7769b38b..b35b0ad90cc 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -1274,7 +1274,9 @@ static EFI_STATUS handle_image (void *data, unsigned int datasize,
|
||||
#ifdef REQUIRE_TPM
|
||||
efi_status =
|
||||
#endif
|
||||
- tpm_log_pe((EFI_PHYSICAL_ADDRESS)(UINTN)data, datasize, sha1hash, 4);
|
||||
+ tpm_log_pe((EFI_PHYSICAL_ADDRESS)(UINTN)data, datasize,
|
||||
+ (EFI_PHYSICAL_ADDRESS)(UINTN)context.ImageAddress,
|
||||
+ li->FilePath, sha1hash, 4);
|
||||
#ifdef REQUIRE_TPM
|
||||
if (efi_status != EFI_SUCCESS) {
|
||||
return efi_status;
|
||||
@@ -1788,7 +1790,8 @@ EFI_STATUS shim_verify (void *buffer, UINT32 size)
|
||||
#ifdef REQUIRE_TPM
|
||||
efi_status =
|
||||
#endif
|
||||
- tpm_log_pe((EFI_PHYSICAL_ADDRESS)(UINTN)buffer, size, sha1hash, 4);
|
||||
+ tpm_log_pe((EFI_PHYSICAL_ADDRESS)(UINTN)buffer, size, 0, NULL,
|
||||
+ sha1hash, 4);
|
||||
#ifdef REQUIRE_TPM
|
||||
if (EFI_ERROR(efi_status))
|
||||
goto done;
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index 196b93c30f6..22ad148b35a 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -210,21 +210,39 @@ EFI_STATUS tpm_log_event(EFI_PHYSICAL_ADDRESS buf, UINTN size, UINT8 pcr,
|
||||
strlen(description) + 1, 0xd, NULL);
|
||||
}
|
||||
|
||||
-EFI_STATUS tpm_log_pe(EFI_PHYSICAL_ADDRESS buf, UINTN size, UINT8 *sha1hash,
|
||||
- UINT8 pcr)
|
||||
+EFI_STATUS tpm_log_pe(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
+ EFI_PHYSICAL_ADDRESS addr, EFI_DEVICE_PATH *path,
|
||||
+ UINT8 *sha1hash, UINT8 pcr)
|
||||
{
|
||||
- EFI_IMAGE_LOAD_EVENT ImageLoad;
|
||||
-
|
||||
- // All of this is informational and forces us to do more parsing before
|
||||
- // we can generate it, so let's just leave it out for now
|
||||
- ImageLoad.ImageLocationInMemory = 0;
|
||||
- ImageLoad.ImageLengthInMemory = 0;
|
||||
- ImageLoad.ImageLinkTimeAddress = 0;
|
||||
- ImageLoad.LengthOfDevicePath = 0;
|
||||
-
|
||||
- return tpm_log_event_raw(buf, size, pcr, (CHAR8 *)&ImageLoad,
|
||||
- sizeof(ImageLoad),
|
||||
- EV_EFI_BOOT_SERVICES_APPLICATION, sha1hash);
|
||||
+ EFI_IMAGE_LOAD_EVENT *ImageLoad = NULL;
|
||||
+ EFI_STATUS efi_status;
|
||||
+ UINTN path_size = 0;
|
||||
+
|
||||
+ if (path)
|
||||
+ path_size = DevicePathSize(path);
|
||||
+
|
||||
+ ImageLoad = AllocateZeroPool(sizeof(*ImageLoad) + path_size);
|
||||
+ if (!ImageLoad) {
|
||||
+ perror(L"Unable to allocate image load event structure\n");
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+ }
|
||||
+
|
||||
+ ImageLoad->ImageLocationInMemory = buf;
|
||||
+ ImageLoad->ImageLengthInMemory = size;
|
||||
+ ImageLoad->ImageLinkTimeAddress = addr;
|
||||
+
|
||||
+ if (path_size > 0) {
|
||||
+ CopyMem(ImageLoad->DevicePath, path, path_size);
|
||||
+ ImageLoad->LengthOfDevicePath = path_size;
|
||||
+ }
|
||||
+
|
||||
+ efi_status = tpm_log_event_raw(buf, size, pcr, (CHAR8 *)ImageLoad,
|
||||
+ sizeof(*ImageLoad) + path_size,
|
||||
+ EV_EFI_BOOT_SERVICES_APPLICATION,
|
||||
+ sha1hash);
|
||||
+ FreePool(ImageLoad);
|
||||
+
|
||||
+ return efi_status;
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
diff --git a/include/tpm.h b/include/tpm.h
|
||||
index 746e871ff22..a05c24949e5 100644
|
||||
--- a/include/tpm.h
|
||||
+++ b/include/tpm.h
|
||||
@@ -10,8 +10,9 @@ EFI_STATUS tpm_log_event(EFI_PHYSICAL_ADDRESS buf, UINTN size, UINT8 pcr,
|
||||
const CHAR8 *description);
|
||||
EFI_STATUS fallback_should_prefer_reset(void);
|
||||
|
||||
-EFI_STATUS tpm_log_pe(EFI_PHYSICAL_ADDRESS buf, UINTN size, UINT8 *sha1hash,
|
||||
- UINT8 pcr);
|
||||
+EFI_STATUS tpm_log_pe(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
+ EFI_PHYSICAL_ADDRESS addr, EFI_DEVICE_PATH *path,
|
||||
+ UINT8 *sha1hash, UINT8 pcr);
|
||||
|
||||
EFI_STATUS tpm_measure_variable(CHAR16 *dbname, EFI_GUID guid, UINTN size, void *data);
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,27 +0,0 @@
|
||||
From dce3659ac3d14ed338cdb37798a429751898c078 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Apr 2020 18:55:34 -0400
|
||||
Subject: [PATCH 47/62] Fix the license on our buildid extractor.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 71439f848f6
|
||||
---
|
||||
buildid.c | 2 --
|
||||
1 file changed, 2 deletions(-)
|
||||
|
||||
diff --git a/buildid.c b/buildid.c
|
||||
index f213f3bc921..6b414cdcffb 100644
|
||||
--- a/buildid.c
|
||||
+++ b/buildid.c
|
||||
@@ -1,8 +1,6 @@
|
||||
/*
|
||||
* Walk a list of input files, printing the name and buildid of any file
|
||||
* that has one.
|
||||
- *
|
||||
- * This program is licensed under the GNU Public License version 2.
|
||||
*/
|
||||
|
||||
#include <err.h>
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,27 +0,0 @@
|
||||
From 633169fe3291c832236ca1074fc679852f9caee1 Mon Sep 17 00:00:00 2001
|
||||
From: noahbliss <noah@superuser.sh>
|
||||
Date: Wed, 4 Mar 2020 19:46:28 -0500
|
||||
Subject: [PATCH 48/62] Update README.tpm
|
||||
|
||||
typo
|
||||
Upstream-commit-id: bc24c9eb1d4
|
||||
---
|
||||
README.tpm | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/README.tpm b/README.tpm
|
||||
index d9c7c53483b..c060dbe22db 100644
|
||||
--- a/README.tpm
|
||||
+++ b/README.tpm
|
||||
@@ -25,7 +25,7 @@ PCR8:
|
||||
measured into PCR8.
|
||||
|
||||
PCR9:
|
||||
-- If you're using the grub2 TPM patchset we cary in Fedora, the kernel,
|
||||
+- If you're using the grub2 TPM patchset we carry in Fedora, the kernel,
|
||||
initramfs, and any multiboot modules loaded are measured into PCR9.
|
||||
|
||||
PCR14:
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,61 +0,0 @@
|
||||
From 9a209af5d84f4015ec399e1d1fa9dab31ef4d2b7 Mon Sep 17 00:00:00 2001
|
||||
From: Thomas Frauendorfer | Miray Software <tf@miray.de>
|
||||
Date: Wed, 25 Mar 2020 09:19:19 +0100
|
||||
Subject: [PATCH 49/62] Check PxeReplyReceived as fallback in netboot
|
||||
|
||||
Some mainboards do not update the ProxyOffset dhcp information when using
|
||||
proxy dhcp and boot menus.
|
||||
This adds a fallback to check the PxeReply field if no boot information is
|
||||
found in the v4 dhcp or proxy dhcp information
|
||||
|
||||
Upstream-commit-id: cc7ebe0f9f4
|
||||
---
|
||||
netboot.c | 15 ++++++++++++---
|
||||
1 file changed, 12 insertions(+), 3 deletions(-)
|
||||
mode change 100644 => 100755 netboot.c
|
||||
|
||||
diff --git a/netboot.c b/netboot.c
|
||||
old mode 100644
|
||||
new mode 100755
|
||||
index 4922ef284b1..047dad3a760
|
||||
--- a/netboot.c
|
||||
+++ b/netboot.c
|
||||
@@ -273,7 +273,16 @@ static EFI_STATUS parseDhcp4()
|
||||
pkt_v4 = &pxe->Mode->ProxyOffer.Dhcpv4;
|
||||
}
|
||||
|
||||
- INTN dir_len = strnlena(pkt_v4->BootpBootFile, 127);
|
||||
+ if(pxe->Mode->PxeReplyReceived) {
|
||||
+ /*
|
||||
+ * If we have no bootinfo yet search for it in the PxeReply.
|
||||
+ * Some mainboards run into this when the server uses boot menus
|
||||
+ */
|
||||
+ if(pkt_v4->BootpBootFile[0] == '\0' && pxe->Mode->PxeReply.Dhcpv4.BootpBootFile[0] != '\0')
|
||||
+ pkt_v4 = &pxe->Mode->PxeReply.Dhcpv4;
|
||||
+ }
|
||||
+
|
||||
+ INTN dir_len = strnlena((CHAR8 *)pkt_v4->BootpBootFile, 127);
|
||||
INTN i;
|
||||
UINT8 *dir = pkt_v4->BootpBootFile;
|
||||
|
||||
@@ -289,7 +298,7 @@ static EFI_STATUS parseDhcp4()
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
|
||||
if (dir_len > 0) {
|
||||
- strncpya(full_path, dir, dir_len);
|
||||
+ strncpya(full_path, (CHAR8 *)dir, dir_len);
|
||||
if (full_path[dir_len-1] == '/' && template[0] == '/')
|
||||
full_path[dir_len-1] = '\0';
|
||||
}
|
||||
@@ -340,7 +349,7 @@ EFI_STATUS FetchNetbootimage(EFI_HANDLE image_handle, VOID **buffer, UINT64 *buf
|
||||
|
||||
try_again:
|
||||
efi_status = pxe->Mtftp(pxe, read, *buffer, overwrite, bufsiz, &blksz,
|
||||
- &tftp_addr, full_path, NULL, nobuffer);
|
||||
+ &tftp_addr, (UINT8 *)full_path, NULL, nobuffer);
|
||||
if (efi_status == EFI_BUFFER_TOO_SMALL) {
|
||||
/* try again, doubling buf size */
|
||||
*bufsiz *= 2;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,46 +0,0 @@
|
||||
From e8a04c1d84d2ebd0dbdf7bda26d7a22017100586 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 9 Jul 2020 00:24:57 -0400
|
||||
Subject: [PATCH 50/62] Remove a couple of incorrect license claims.
|
||||
|
||||
A certain someone's default editor template leaked in to a couple of
|
||||
source files, and claims they're GPL licensed. They're not.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream-commit-id: 476cbff1110
|
||||
---
|
||||
errlog.c | 3 ---
|
||||
mok.c | 2 --
|
||||
2 files changed, 5 deletions(-)
|
||||
|
||||
diff --git a/errlog.c b/errlog.c
|
||||
index eebb266d396..6669c800233 100644
|
||||
--- a/errlog.c
|
||||
+++ b/errlog.c
|
||||
@@ -1,10 +1,7 @@
|
||||
/*
|
||||
* errlog.c
|
||||
* Copyright 2017 Peter Jones <pjones@redhat.com>
|
||||
- *
|
||||
- * Distributed under terms of the GPLv3 license.
|
||||
*/
|
||||
-
|
||||
#include "shim.h"
|
||||
|
||||
static CHAR16 **errs = NULL;
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 59630e74425..089ea6bfc9a 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -1,8 +1,6 @@
|
||||
/*
|
||||
* mok.c
|
||||
* Copyright 2017 Peter Jones <pjones@redhat.com>
|
||||
- *
|
||||
- * Distributed under terms of the GPLv3 license.
|
||||
*/
|
||||
|
||||
#include "shim.h"
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,27 +0,0 @@
|
||||
From 7b77bee7966a1aa5f00a9b34aeb7e550bfa47be1 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Wed, 22 Jul 2020 23:53:09 -0400
|
||||
Subject: [PATCH 51/62] MokManager: fix uninitialized value
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#212
|
||||
---
|
||||
MokManager.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index fa73e2fd865..654a115033c 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -1431,7 +1431,7 @@ static CHAR16 get_password_charater(CHAR16 * prompt)
|
||||
SIMPLE_TEXT_OUTPUT_MODE SavedMode;
|
||||
EFI_STATUS efi_status;
|
||||
CHAR16 *message[2];
|
||||
- CHAR16 character;
|
||||
+ CHAR16 character = 0;
|
||||
UINTN length;
|
||||
UINT32 pw_length;
|
||||
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,41 +0,0 @@
|
||||
From d3b7dc54cdac474a57b67cf9bcdb15bcb131d06c Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 16:18:52 -0400
|
||||
Subject: [PATCH 52/62] Fix some volatile usage gcc whines about.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#212
|
||||
---
|
||||
fallback.c | 2 +-
|
||||
shim.c | 2 +-
|
||||
2 files changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/fallback.c b/fallback.c
|
||||
index c3f5583c626..5a4bfff0793 100644
|
||||
--- a/fallback.c
|
||||
+++ b/fallback.c
|
||||
@@ -983,7 +983,7 @@ debug_hook(void)
|
||||
UINT8 *data = NULL;
|
||||
UINTN dataSize = 0;
|
||||
EFI_STATUS efi_status;
|
||||
- volatile register int x = 0;
|
||||
+ register volatile int x = 0;
|
||||
extern char _etext, _edata;
|
||||
|
||||
efi_status = get_variable(L"SHIM_DEBUG", &data, &dataSize,
|
||||
diff --git a/shim.c b/shim.c
|
||||
index b35b0ad90cc..0e7e784b4c8 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2559,7 +2559,7 @@ debug_hook(void)
|
||||
UINT8 *data = NULL;
|
||||
UINTN dataSize = 0;
|
||||
EFI_STATUS efi_status;
|
||||
- volatile register UINTN x = 0;
|
||||
+ register volatile UINTN x = 0;
|
||||
extern char _text, _data;
|
||||
|
||||
if (x)
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,31 +0,0 @@
|
||||
From 6df96cdb20b84b33027d2e40bc0dbe0676d31282 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 19:01:27 -0400
|
||||
Subject: [PATCH 53/62] MokManager: fix a wrong allocation failure check.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#212
|
||||
---
|
||||
MokManager.c | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index 654a115033c..c9949e33bcf 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -1085,9 +1085,11 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
DataSize += sizeof(EFI_GUID);
|
||||
DataSize += list[i].MokSize;
|
||||
}
|
||||
+ if (DataSize == 0)
|
||||
+ return EFI_SUCCESS;
|
||||
|
||||
Data = AllocatePool(DataSize);
|
||||
- if (Data == NULL && DataSize != 0)
|
||||
+ if (Data == NULL)
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
|
||||
ptr = Data;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,33 +0,0 @@
|
||||
From c186bdddaa7b103aef9d4a164ac0a07499dba112 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Wed, 22 Jul 2020 23:55:44 -0400
|
||||
Subject: [PATCH 54/62] simple_file: fix uninitialized variable/unchecked
|
||||
return
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#212
|
||||
---
|
||||
lib/simple_file.c | 6 +++---
|
||||
1 file changed, 3 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/lib/simple_file.c b/lib/simple_file.c
|
||||
index 3bf92ed8e0f..6ad31b4dc04 100644
|
||||
--- a/lib/simple_file.c
|
||||
+++ b/lib/simple_file.c
|
||||
@@ -403,10 +403,10 @@ simple_file_selector(EFI_HANDLE * im, CHAR16 ** title, CHAR16 * name,
|
||||
filter = L"";
|
||||
if (!*im) {
|
||||
EFI_HANDLE h;
|
||||
- CHAR16 *volname;
|
||||
+ CHAR16 *volname = NULL;
|
||||
|
||||
- simple_volume_selector(title, &volname, &h);
|
||||
- if (!volname)
|
||||
+ efi_status = simple_volume_selector(title, &volname, &h);
|
||||
+ if (EFI_ERROR(efi_status) || !volname)
|
||||
return;
|
||||
FreePool(volname);
|
||||
*im = h;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,27 +0,0 @@
|
||||
From a7f9911b776f3cdc12e42bf5990ddef0b08d3701 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 20:35:56 -0400
|
||||
Subject: [PATCH 55/62] Fix a broken tpm type
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#212
|
||||
---
|
||||
tpm.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/tpm.c b/tpm.c
|
||||
index 22ad148b35a..03cf3a1f60e 100644
|
||||
--- a/tpm.c
|
||||
+++ b/tpm.c
|
||||
@@ -239,7 +239,7 @@ EFI_STATUS tpm_log_pe(EFI_PHYSICAL_ADDRESS buf, UINTN size,
|
||||
efi_status = tpm_log_event_raw(buf, size, pcr, (CHAR8 *)ImageLoad,
|
||||
sizeof(*ImageLoad) + path_size,
|
||||
EV_EFI_BOOT_SERVICES_APPLICATION,
|
||||
- sha1hash);
|
||||
+ (CHAR8 *)sha1hash);
|
||||
FreePool(ImageLoad);
|
||||
|
||||
return efi_status;
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,279 +0,0 @@
|
||||
From 7d542805ba5c48185128a2351bb315a5648fe3d7 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 00:08:30 -0400
|
||||
Subject: [PATCH 56/62] Make cert.S not impossible to read.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#206
|
||||
---
|
||||
shim.c | 47 +++++++++++++++++--------------
|
||||
shim.h | 28 +++++++++++++++---
|
||||
cert.S | 89 ++++++++++++++++++++++------------------------------------
|
||||
3 files changed, 84 insertions(+), 80 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 0e7e784b4c8..888ee6e8d7b 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -68,16 +68,18 @@ static UINT32 load_options_size;
|
||||
* The vendor certificate used for validating the second stage loader
|
||||
*/
|
||||
extern struct {
|
||||
- UINT32 vendor_cert_size;
|
||||
- UINT32 vendor_dbx_size;
|
||||
- UINT32 vendor_cert_offset;
|
||||
- UINT32 vendor_dbx_offset;
|
||||
+ UINT32 vendor_authorized_size;
|
||||
+ UINT32 vendor_deauthorized_size;
|
||||
+ UINT32 vendor_authorized_offset;
|
||||
+ UINT32 vendor_deauthorized_offset;
|
||||
} cert_table;
|
||||
|
||||
-UINT32 vendor_cert_size;
|
||||
-UINT32 vendor_dbx_size;
|
||||
-UINT8 *vendor_cert;
|
||||
-UINT8 *vendor_dbx;
|
||||
+UINT32 vendor_authorized_size = 0;
|
||||
+UINT8 *vendor_authorized = NULL;
|
||||
+
|
||||
+UINT32 vendor_deauthorized_size = 0;
|
||||
+UINT8 *vendor_deauthorized = NULL;
|
||||
+
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
UINT32 build_cert_size;
|
||||
UINT8 *build_cert;
|
||||
@@ -554,22 +556,22 @@ static CHECK_STATUS check_db_hash(CHAR16 *dbname, EFI_GUID guid, UINT8 *data,
|
||||
static EFI_STATUS check_blacklist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
UINT8 *sha256hash, UINT8 *sha1hash)
|
||||
{
|
||||
- EFI_SIGNATURE_LIST *dbx = (EFI_SIGNATURE_LIST *)vendor_dbx;
|
||||
+ EFI_SIGNATURE_LIST *dbx = (EFI_SIGNATURE_LIST *)vendor_deauthorized;
|
||||
|
||||
- if (check_db_hash_in_ram(dbx, vendor_dbx_size, sha256hash,
|
||||
+ if (check_db_hash_in_ram(dbx, vendor_deauthorized_size, sha256hash,
|
||||
SHA256_DIGEST_SIZE, EFI_CERT_SHA256_GUID, L"dbx",
|
||||
EFI_SECURE_BOOT_DB_GUID) == DATA_FOUND) {
|
||||
LogError(L"binary sha256hash found in vendor dbx\n");
|
||||
return EFI_SECURITY_VIOLATION;
|
||||
}
|
||||
- if (check_db_hash_in_ram(dbx, vendor_dbx_size, sha1hash,
|
||||
+ if (check_db_hash_in_ram(dbx, vendor_deauthorized_size, sha1hash,
|
||||
SHA1_DIGEST_SIZE, EFI_CERT_SHA1_GUID, L"dbx",
|
||||
EFI_SECURE_BOOT_DB_GUID) == DATA_FOUND) {
|
||||
LogError(L"binary sha1hash found in vendor dbx\n");
|
||||
return EFI_SECURITY_VIOLATION;
|
||||
}
|
||||
if (cert &&
|
||||
- check_db_cert_in_ram(dbx, vendor_dbx_size, cert, sha256hash, L"dbx",
|
||||
+ check_db_cert_in_ram(dbx, vendor_deauthorized_size, cert, sha256hash, L"dbx",
|
||||
EFI_SECURE_BOOT_DB_GUID) == DATA_FOUND) {
|
||||
LogError(L"cert sha256hash found in vendor dbx\n");
|
||||
return EFI_SECURITY_VIOLATION;
|
||||
@@ -1077,19 +1079,19 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
/*
|
||||
* And finally, check against shim's built-in key
|
||||
*/
|
||||
- if (vendor_cert_size &&
|
||||
+ if (vendor_authorized_size &&
|
||||
AuthenticodeVerify(cert->CertData,
|
||||
cert->Hdr.dwLength - sizeof(cert->Hdr),
|
||||
- vendor_cert, vendor_cert_size,
|
||||
+ vendor_authorized, vendor_authorized_size,
|
||||
sha256hash, SHA256_DIGEST_SIZE)) {
|
||||
update_verification_method(VERIFIED_BY_CERT);
|
||||
tpm_measure_variable(L"Shim", SHIM_LOCK_GUID,
|
||||
- vendor_cert_size, vendor_cert);
|
||||
+ vendor_authorized_size, vendor_authorized);
|
||||
efi_status = EFI_SUCCESS;
|
||||
drain_openssl_errors();
|
||||
return efi_status;
|
||||
} else {
|
||||
- LogError(L"AuthenticodeVerify(vendor_cert) failed\n");
|
||||
+ LogError(L"AuthenticodeVerify(vendor_authorized) failed\n");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2501,7 +2503,7 @@ shim_init(void)
|
||||
}
|
||||
|
||||
if (secure_mode()) {
|
||||
- if (vendor_cert_size || vendor_dbx_size) {
|
||||
+ if (vendor_authorized_size || vendor_deauthorized_size) {
|
||||
/*
|
||||
* If shim includes its own certificates then ensure
|
||||
* that anything it boots has performed some
|
||||
@@ -2606,14 +2608,17 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
|
||||
verification_method = VERIFIED_BY_NOTHING;
|
||||
|
||||
- vendor_cert_size = cert_table.vendor_cert_size;
|
||||
- vendor_dbx_size = cert_table.vendor_dbx_size;
|
||||
- vendor_cert = (UINT8 *)&cert_table + cert_table.vendor_cert_offset;
|
||||
- vendor_dbx = (UINT8 *)&cert_table + cert_table.vendor_dbx_offset;
|
||||
+ vendor_authorized_size = cert_table.vendor_authorized_size;
|
||||
+ vendor_authorized = (UINT8 *)&cert_table + cert_table.vendor_authorized_offset;
|
||||
+
|
||||
+ vendor_deauthorized_size = cert_table.vendor_deauthorized_size;
|
||||
+ vendor_deauthorized = (UINT8 *)&cert_table + cert_table.vendor_deauthorized_offset;
|
||||
+
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
build_cert_size = sizeof(shim_cert);
|
||||
build_cert = shim_cert;
|
||||
#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
CHAR16 *msgs[] = {
|
||||
L"import_mok_state() failed",
|
||||
L"shim_init() failed",
|
||||
diff --git a/shim.h b/shim.h
|
||||
index a0fa5a75e7e..555498c6673 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -97,6 +97,24 @@
|
||||
#define FALLBACK L"\\fb" EFI_ARCH L".efi"
|
||||
#define MOK_MANAGER L"\\mm" EFI_ARCH L".efi"
|
||||
|
||||
+#if defined(VENDOR_CERT_FILE)
|
||||
+# define vendor_authorized vendor_cert
|
||||
+# define vendor_authorized_size vendor_cert_size
|
||||
+# define vendor_authorized_category VENDOR_ADDEND_X509
|
||||
+#else
|
||||
+# define vendor_authorized vendor_null
|
||||
+# define vendor_authorized_size vendor_null_size
|
||||
+# define vendor_authorized_category VENDOR_ADDEND_NONE
|
||||
+#endif
|
||||
+
|
||||
+#if defined(VENDOR_DBX_FILE)
|
||||
+# define vendor_deauthorized vendor_dbx
|
||||
+# define vendor_deauthorized_size vendor_dbx_size
|
||||
+#else
|
||||
+# define vendor_deauthorized vendor_deauthorized_null
|
||||
+# define vendor_deauthorized_size vendor_deauthorized_null_size
|
||||
+#endif
|
||||
+
|
||||
#include "include/asm.h"
|
||||
#include "include/configtable.h"
|
||||
#include "include/console.h"
|
||||
@@ -166,10 +184,12 @@ extern VOID ClearErrors(VOID);
|
||||
extern EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath);
|
||||
extern EFI_STATUS import_mok_state(EFI_HANDLE image_handle);
|
||||
|
||||
-extern UINT32 vendor_cert_size;
|
||||
-extern UINT32 vendor_dbx_size;
|
||||
-extern UINT8 *vendor_cert;
|
||||
-extern UINT8 *vendor_dbx;
|
||||
+extern UINT32 vendor_authorized_size;
|
||||
+extern UINT8 *vendor_authorized;
|
||||
+
|
||||
+extern UINT32 vendor_deauthorized_size;
|
||||
+extern UINT8 *vendor_deauthorized;
|
||||
+
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
extern UINT32 build_cert_size;
|
||||
extern UINT8 *build_cert;
|
||||
diff --git a/cert.S b/cert.S
|
||||
index cfc4525b44c..520caaef3af 100644
|
||||
--- a/cert.S
|
||||
+++ b/cert.S
|
||||
@@ -1,65 +1,44 @@
|
||||
+
|
||||
+#if defined(VENDOR_CERT_FILE)
|
||||
+# define vendor_authorized vendor_cert
|
||||
+# define vendor_authorized_end vendor_cert_end
|
||||
+# define vendor_authorized_size vendor_cert_size
|
||||
+# define vendor_authorized_size_end vendor_cert_size_end
|
||||
+#endif
|
||||
+
|
||||
+#if defined(VENDOR_DBX_FILE)
|
||||
+# define vendor_deauthorized vendor_dbx
|
||||
+# define vendor_deauthorized_end vendor_dbx_end
|
||||
+# define vendor_deauthorized_size vendor_dbx_size
|
||||
+# define vendor_deauthorized_size_end vendor_dbx_size_end
|
||||
+#endif
|
||||
+
|
||||
.globl cert_table
|
||||
.type cert_table, %object
|
||||
- .size cert_table, 4
|
||||
+ .size cert_table, .Lcert_table_end - cert_table
|
||||
.section .vendor_cert, "a", %progbits
|
||||
+ .balignl 4, 0
|
||||
cert_table:
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
- .long vendor_cert_priv_end - vendor_cert_priv
|
||||
-#else
|
||||
- .long 0
|
||||
-#endif
|
||||
-#if defined(VENDOR_DBX_FILE)
|
||||
- .long vendor_dbx_priv_end - vendor_dbx_priv
|
||||
-#else
|
||||
- .long 0
|
||||
-#endif
|
||||
- .long vendor_cert_priv - cert_table
|
||||
- .long vendor_dbx_priv - cert_table
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
- .data
|
||||
- .align 1
|
||||
- .type vendor_cert_priv, %object
|
||||
- .size vendor_cert_priv, vendor_cert_priv_end-vendor_cert_priv
|
||||
+ .4byte .Lvendor_authorized_end - vendor_authorized
|
||||
+ .4byte .Lvendor_deauthorized_end - vendor_deauthorized
|
||||
+ .4byte vendor_authorized - cert_table
|
||||
+ .4byte vendor_deauthorized - cert_table
|
||||
+ .balign 1, 0
|
||||
+ .type vendor_authorized, %object
|
||||
+ .size vendor_authorized, .Lvendor_authorized_end - vendor_authorized
|
||||
.section .vendor_cert, "a", %progbits
|
||||
-vendor_cert_priv:
|
||||
+vendor_authorized:
|
||||
+#if defined(VENDOR_CERT_FILE)
|
||||
.incbin VENDOR_CERT_FILE
|
||||
-vendor_cert_priv_end:
|
||||
-#else
|
||||
- .bss
|
||||
- .type vendor_cert_priv, %object
|
||||
- .size vendor_cert_priv, 1
|
||||
- .section .vendor_cert, "a", %progbits
|
||||
-vendor_cert_priv:
|
||||
- .zero 1
|
||||
-
|
||||
- .data
|
||||
- .align 4
|
||||
- .type vendor_cert_size_priv, %object
|
||||
- .size vendor_cert_size_priv, 4
|
||||
- .section .vendor_cert, "a", %progbits
|
||||
-vendor_cert_priv_end:
|
||||
#endif
|
||||
+.Lvendor_authorized_end:
|
||||
+ .balign 1, 0
|
||||
+ .type vendor_deauthorized, %object
|
||||
+ .size vendor_deauthorized, .Lvendor_deauthorized_end - vendor_deauthorized
|
||||
+ .section .vendor_cert, "a", %progbits
|
||||
+vendor_deauthorized:
|
||||
#if defined(VENDOR_DBX_FILE)
|
||||
- .data
|
||||
- .align 1
|
||||
- .type vendor_dbx_priv, %object
|
||||
- .size vendor_dbx_priv, vendor_dbx_priv_end-vendor_dbx_priv
|
||||
- .section .vendor_cert, "a", %progbits
|
||||
-vendor_dbx_priv:
|
||||
.incbin VENDOR_DBX_FILE
|
||||
-vendor_dbx_priv_end:
|
||||
-#else
|
||||
- .bss
|
||||
- .type vendor_dbx_priv, %object
|
||||
- .size vendor_dbx_priv, 1
|
||||
- .section .vendor_cert, "a", %progbits
|
||||
-vendor_dbx_priv:
|
||||
- .zero 1
|
||||
-
|
||||
- .data
|
||||
- .align 4
|
||||
- .type vendor_dbx_size_priv, %object
|
||||
- .size vendor_dbx_size_priv, 4
|
||||
- .section .vendor_cert, "a", %progbits
|
||||
-vendor_dbx_priv_end:
|
||||
#endif
|
||||
+.Lvendor_deauthorized_end:
|
||||
+.Lcert_table_end:
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,943 +0,0 @@
|
||||
From dd3a5d71252a1f94e37f1a4c8841d253630b305a Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 12:36:56 -0400
|
||||
Subject: [PATCH 57/62] Add support for vendor_db built-in shim authorized
|
||||
list.
|
||||
|
||||
Potential new signing strategies ( for example signing grub, fwupdate
|
||||
and vmlinuz with separate certificates ) require shim to support a
|
||||
vendor provided bundle of trusted certificates and hashes, which allows
|
||||
shim to trust EFI binaries matching either certificate by signature or
|
||||
hash in the vendor_db. Functionality is similar to vendor_dbx.
|
||||
|
||||
This also improves the mirroring quite a bit.
|
||||
Upstream: pr#206
|
||||
---
|
||||
lib/variables.c | 55 +++--
|
||||
mok.c | 502 ++++++++++++++++++++++++++++++--------------
|
||||
shim.c | 27 +++
|
||||
include/console.h | 3 +-
|
||||
include/variables.h | 9 +-
|
||||
shim.h | 7 +-
|
||||
cert.S | 13 +-
|
||||
Make.defaults | 3 +
|
||||
README.tpm | 1 +
|
||||
9 files changed, 437 insertions(+), 183 deletions(-)
|
||||
|
||||
diff --git a/lib/variables.c b/lib/variables.c
|
||||
index 9c2e7d0ac2d..8123ae60fc9 100644
|
||||
--- a/lib/variables.c
|
||||
+++ b/lib/variables.c
|
||||
@@ -25,32 +25,59 @@
|
||||
#include "shim.h"
|
||||
|
||||
EFI_STATUS
|
||||
-variable_create_esl(void *cert, int cert_len, EFI_GUID *type, EFI_GUID *owner,
|
||||
- void **out, int *outlen)
|
||||
+fill_esl(const uint8_t *data, const size_t data_len,
|
||||
+ const EFI_GUID *type, const EFI_GUID *owner,
|
||||
+ uint8_t *out, size_t *outlen)
|
||||
{
|
||||
- *outlen = cert_len + sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID);
|
||||
+ EFI_SIGNATURE_LIST *sl;
|
||||
+ EFI_SIGNATURE_DATA *sd;
|
||||
+ size_t needed = 0;
|
||||
|
||||
- *out = AllocateZeroPool(*outlen);
|
||||
- if (!*out)
|
||||
- return EFI_OUT_OF_RESOURCES;
|
||||
+ if (!data || !data_len || !type || !outlen)
|
||||
+ return EFI_INVALID_PARAMETER;
|
||||
|
||||
- EFI_SIGNATURE_LIST *sl = *out;
|
||||
+ needed = sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID) + data_len;
|
||||
+ if (!out || *outlen < needed) {
|
||||
+ *outlen = needed;
|
||||
+ return EFI_BUFFER_TOO_SMALL;
|
||||
+ }
|
||||
+
|
||||
+ *outlen = needed;
|
||||
+ sl = (EFI_SIGNATURE_LIST *)out;
|
||||
|
||||
sl->SignatureHeaderSize = 0;
|
||||
sl->SignatureType = *type;
|
||||
- sl->SignatureSize = cert_len + sizeof(EFI_GUID);
|
||||
- sl->SignatureListSize = *outlen;
|
||||
-
|
||||
- EFI_SIGNATURE_DATA *sd = *out + sizeof(EFI_SIGNATURE_LIST);
|
||||
+ sl->SignatureSize = sizeof(EFI_GUID) + data_len;
|
||||
+ sl->SignatureListSize = needed;
|
||||
|
||||
+ sd = (EFI_SIGNATURE_DATA *)(out + sizeof(EFI_SIGNATURE_LIST));
|
||||
if (owner)
|
||||
sd->SignatureOwner = *owner;
|
||||
|
||||
- CopyMem(sd->SignatureData, cert, cert_len);
|
||||
+ CopyMem(sd->SignatureData, data, data_len);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
+EFI_STATUS
|
||||
+variable_create_esl(const uint8_t *data, const size_t data_len,
|
||||
+ const EFI_GUID *type, const EFI_GUID *owner,
|
||||
+ uint8_t **out, size_t *outlen)
|
||||
+{
|
||||
+ EFI_STATUS efi_status;
|
||||
+
|
||||
+ *outlen = 0;
|
||||
+ efi_status = fill_esl(data, data_len, type, owner, NULL, outlen);
|
||||
+ if (efi_status != EFI_BUFFER_TOO_SMALL)
|
||||
+ return efi_status;
|
||||
+
|
||||
+ *out = AllocateZeroPool(*outlen);
|
||||
+ if (!*out)
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+
|
||||
+ return fill_esl(data, data_len, type, owner, *out, outlen);
|
||||
+}
|
||||
+
|
||||
EFI_STATUS
|
||||
CreateTimeBasedPayload(IN OUT UINTN * DataSize, IN OUT UINT8 ** Data)
|
||||
{
|
||||
@@ -137,9 +164,9 @@ SetSecureVariable(CHAR16 *var, UINT8 *Data, UINTN len, EFI_GUID owner,
|
||||
return EFI_SECURITY_VIOLATION;
|
||||
|
||||
if (createtimebased) {
|
||||
- int ds;
|
||||
+ size_t ds;
|
||||
efi_status = variable_create_esl(Data, len, &X509_GUID, NULL,
|
||||
- (void **)&Cert, &ds);
|
||||
+ (uint8_t **)&Cert, &ds);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
console_print(L"Failed to create %s certificate %d\n",
|
||||
var, efi_status);
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 089ea6bfc9a..e69857f3c37 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -5,6 +5,8 @@
|
||||
|
||||
#include "shim.h"
|
||||
|
||||
+#include <stdint.h>
|
||||
+
|
||||
/*
|
||||
* Check if a variable exists
|
||||
*/
|
||||
@@ -47,6 +49,15 @@ static EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
+typedef enum {
|
||||
+ VENDOR_ADDEND_DB,
|
||||
+ VENDOR_ADDEND_X509,
|
||||
+ VENDOR_ADDEND_NONE,
|
||||
+} vendor_addend_category_t;
|
||||
+
|
||||
+struct mok_state_variable;
|
||||
+typedef vendor_addend_category_t (vendor_addend_categorizer_t)(struct mok_state_variable *);
|
||||
+
|
||||
/*
|
||||
* MoK variables that need to have their storage validated.
|
||||
*
|
||||
@@ -58,18 +69,20 @@ struct mok_state_variable {
|
||||
char *name8;
|
||||
CHAR16 *rtname;
|
||||
EFI_GUID *guid;
|
||||
+
|
||||
UINT8 *data;
|
||||
UINTN data_size;
|
||||
+
|
||||
/*
|
||||
- * These two are indirect pointers just to make initialization
|
||||
- * saner...
|
||||
+ * These are indirect pointers just to make initialization saner...
|
||||
*/
|
||||
- UINT8 **addend_source;
|
||||
+ vendor_addend_categorizer_t *categorize_addend;
|
||||
+ UINT8 **addend;
|
||||
UINT32 *addend_size;
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
+
|
||||
UINT8 **build_cert;
|
||||
UINT32 *build_cert_size;
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
UINT32 yes_attr;
|
||||
UINT32 no_attr;
|
||||
UINT32 flags;
|
||||
@@ -77,6 +90,28 @@ struct mok_state_variable {
|
||||
UINT8 *state;
|
||||
};
|
||||
|
||||
+static vendor_addend_category_t
|
||||
+categorize_authorized(struct mok_state_variable *v)
|
||||
+{
|
||||
+ if (!(v->addend && v->addend_size &&
|
||||
+ *v->addend && *v->addend_size)) {
|
||||
+ return VENDOR_ADDEND_NONE;
|
||||
+ }
|
||||
+
|
||||
+ return vendor_authorized_category;
|
||||
+}
|
||||
+
|
||||
+static vendor_addend_category_t
|
||||
+categorize_deauthorized(struct mok_state_variable *v)
|
||||
+{
|
||||
+ if (!(v->addend && v->addend_size &&
|
||||
+ *v->addend && *v->addend_size)) {
|
||||
+ return VENDOR_ADDEND_NONE;
|
||||
+ }
|
||||
+
|
||||
+ return VENDOR_ADDEND_DB;
|
||||
+}
|
||||
+
|
||||
#define MOK_MIRROR_KEYDB 0x01
|
||||
#define MOK_MIRROR_DELETE_FIRST 0x02
|
||||
#define MOK_VARIABLE_MEASURE 0x04
|
||||
@@ -90,8 +125,9 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
.no_attr = EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
- .addend_source = &vendor_cert,
|
||||
- .addend_size = &vendor_cert_size,
|
||||
+ .categorize_addend = categorize_authorized,
|
||||
+ .addend = &vendor_authorized,
|
||||
+ .addend_size = &vendor_authorized_size,
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
.build_cert = &build_cert,
|
||||
.build_cert_size = &build_cert_size,
|
||||
@@ -107,6 +143,9 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
.no_attr = EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
+ .categorize_addend = categorize_deauthorized,
|
||||
+ .addend = &vendor_deauthorized,
|
||||
+ .addend_size = &vendor_deauthorized_size,
|
||||
.flags = MOK_MIRROR_KEYDB |
|
||||
MOK_VARIABLE_LOG,
|
||||
.pcr = 14,
|
||||
@@ -136,123 +175,253 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{ NULL, }
|
||||
};
|
||||
|
||||
-static inline BOOLEAN nonnull(1)
|
||||
-check_vendor_cert(struct mok_state_variable *v)
|
||||
-{
|
||||
- return (v->addend_source && v->addend_size &&
|
||||
- *v->addend_source && *v->addend_size) ? TRUE : FALSE;
|
||||
-}
|
||||
+#define should_mirror_addend(v) (((v)->categorize_addend) && ((v)->categorize_addend(v) != VENDOR_ADDEND_NONE))
|
||||
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
static inline BOOLEAN nonnull(1)
|
||||
-check_build_cert(struct mok_state_variable *v)
|
||||
+should_mirror_build_cert(struct mok_state_variable *v)
|
||||
{
|
||||
return (v->build_cert && v->build_cert_size &&
|
||||
*v->build_cert && *v->build_cert_size) ? TRUE : FALSE;
|
||||
}
|
||||
-#define check_addend(v) (check_vendor_cert(v) || check_build_cert(v))
|
||||
-#else
|
||||
-#define check_addend(v) check_vendor_cert(v)
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
+static const uint8_t null_sha256[32] = { 0, };
|
||||
|
||||
static EFI_STATUS nonnull(1)
|
||||
mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
{
|
||||
EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
- void *FullData = NULL;
|
||||
- UINTN FullDataSize = 0;
|
||||
+ uint8_t *FullData = NULL;
|
||||
+ size_t FullDataSize = 0;
|
||||
+ vendor_addend_category_t addend_category = VENDOR_ADDEND_NONE;
|
||||
uint8_t *p = NULL;
|
||||
|
||||
- if ((v->flags & MOK_MIRROR_KEYDB) && check_addend(v)) {
|
||||
- EFI_SIGNATURE_LIST *CertList = NULL;
|
||||
- EFI_SIGNATURE_DATA *CertData = NULL;
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
- FullDataSize = v->data_size;
|
||||
- if (check_build_cert(v)) {
|
||||
- FullDataSize += sizeof (*CertList)
|
||||
- + sizeof (EFI_GUID)
|
||||
- + *v->build_cert_size;
|
||||
- }
|
||||
- if (check_vendor_cert(v)) {
|
||||
- FullDataSize += sizeof (*CertList)
|
||||
- + sizeof (EFI_GUID)
|
||||
- + *v->addend_size;
|
||||
- }
|
||||
-#else
|
||||
- FullDataSize = v->data_size
|
||||
- + sizeof (*CertList)
|
||||
- + sizeof (EFI_GUID)
|
||||
- + *v->addend_size;
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
- FullData = AllocatePool(FullDataSize);
|
||||
- if (!FullData) {
|
||||
- perror(L"Failed to allocate space for MokListRT\n");
|
||||
- return EFI_OUT_OF_RESOURCES;
|
||||
- }
|
||||
- p = FullData;
|
||||
+ size_t build_cert_esl_sz = 0, addend_esl_sz = 0;
|
||||
|
||||
- if (!EFI_ERROR(efi_status) && v->data_size > 0) {
|
||||
- CopyMem(p, v->data, v->data_size);
|
||||
- p += v->data_size;
|
||||
- }
|
||||
+ if (v->categorize_addend)
|
||||
+ addend_category = v->categorize_addend(v);
|
||||
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
- if (check_build_cert(v) == FALSE)
|
||||
- goto skip_build_cert;
|
||||
+ /*
|
||||
+ * we're always mirroring the original data, whether this is an efi
|
||||
+ * security database or not
|
||||
+ */
|
||||
+ dprint(L"v->data_size:%lu v->data:0x%08llx\n", v->data_size, v->data);
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n", FullDataSize, FullData);
|
||||
+ if (v->data_size) {
|
||||
+ FullDataSize = v->data_size;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ }
|
||||
|
||||
- CertList = (EFI_SIGNATURE_LIST *)p;
|
||||
- p += sizeof (*CertList);
|
||||
- CertData = (EFI_SIGNATURE_DATA *)p;
|
||||
- p += sizeof (EFI_GUID);
|
||||
+ /*
|
||||
+ * if it is, there's more data
|
||||
+ */
|
||||
+ if (v->flags & MOK_MIRROR_KEYDB) {
|
||||
|
||||
- CertList->SignatureType = EFI_CERT_TYPE_X509_GUID;
|
||||
- CertList->SignatureListSize = *v->build_cert_size
|
||||
- + sizeof (*CertList)
|
||||
- + sizeof (*CertData)
|
||||
- -1;
|
||||
- CertList->SignatureHeaderSize = 0;
|
||||
- CertList->SignatureSize = *v->build_cert_size +
|
||||
- sizeof (EFI_GUID);
|
||||
+ /*
|
||||
+ * We're mirroring (into) an efi security database, aka an
|
||||
+ * array of efi_signature_list_t. Its layout goes like:
|
||||
+ *
|
||||
+ * existing_variable_data
|
||||
+ * existing_variable_data_size
|
||||
+ * if flags & MOK_MIRROR_KEYDB
|
||||
+ * if build_cert
|
||||
+ * build_cert_esl
|
||||
+ * build_cert_header (always sz=0)
|
||||
+ * build_cert_esd[0] { owner, data }
|
||||
+ * if addend==vendor_db
|
||||
+ * for n=[1..N]
|
||||
+ * vendor_db_esl_n
|
||||
+ * vendor_db_header_n (always sz=0)
|
||||
+ * vendor_db_esd_n[m] {{ owner, data }, ... }
|
||||
+ * elif addend==vendor_cert
|
||||
+ * vendor_cert_esl
|
||||
+ * vendor_cert_header (always sz=0)
|
||||
+ * vendor_cert_esd[1] { owner, data }
|
||||
+ *
|
||||
+ * first we determine the size of the variable, then alloc
|
||||
+ * and add the data.
|
||||
+ */
|
||||
|
||||
- CertData->SignatureOwner = SHIM_LOCK_GUID;
|
||||
- CopyMem(p, *v->build_cert, *v->build_cert_size);
|
||||
+ /*
|
||||
+ * first bit is existing data, but we added that above
|
||||
+ */
|
||||
|
||||
- p += *v->build_cert_size;
|
||||
+ /*
|
||||
+ * then the build cert if it's there
|
||||
+ */
|
||||
+ if (should_mirror_build_cert(v)) {
|
||||
+ efi_status = fill_esl(*v->build_cert,
|
||||
+ *v->build_cert_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ NULL, &build_cert_esl_sz);
|
||||
+ if (efi_status != EFI_BUFFER_TOO_SMALL) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ FullDataSize += build_cert_esl_sz;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ }
|
||||
|
||||
- if (check_vendor_cert(v) == FALSE)
|
||||
- goto skip_vendor_cert;
|
||||
-skip_build_cert:
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+ /*
|
||||
+ * then the addend data
|
||||
+ */
|
||||
+ switch (addend_category) {
|
||||
+ case VENDOR_ADDEND_DB:
|
||||
+ /*
|
||||
+ * if it's an ESL already, we use it wholesale
|
||||
+ */
|
||||
+ FullDataSize += *v->addend_size;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ break;
|
||||
+ case VENDOR_ADDEND_X509:
|
||||
+ efi_status = fill_esl(*v->addend, *v->addend_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ NULL, &addend_esl_sz);
|
||||
+ if (efi_status != EFI_BUFFER_TOO_SMALL) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ FullDataSize += addend_esl_sz;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ break;
|
||||
+ default:
|
||||
+ case VENDOR_ADDEND_NONE:
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
|
||||
- CertList = (EFI_SIGNATURE_LIST *)p;
|
||||
- p += sizeof (*CertList);
|
||||
- CertData = (EFI_SIGNATURE_DATA *)p;
|
||||
- p += sizeof (EFI_GUID);
|
||||
+ /*
|
||||
+ * Now we have the full size
|
||||
+ */
|
||||
+ if (FullDataSize) {
|
||||
+ /*
|
||||
+ * allocate the buffer, or use the old one if it's just the
|
||||
+ * existing data.
|
||||
+ */
|
||||
+ if (FullDataSize != v->data_size) {
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx allocating FullData\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ FullData = AllocatePool(FullDataSize);
|
||||
+ if (!FullData) {
|
||||
+ FreePool(v->data);
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ perror(L"Failed to allocate %lu bytes for %s\n",
|
||||
+ FullDataSize, v->name);
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+ }
|
||||
+ p = FullData;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ if (v->data && v->data_size) {
|
||||
+ CopyMem(p, v->data, v->data_size);
|
||||
+ p += v->data_size;
|
||||
+ }
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ } else {
|
||||
+ FullData = v->data;
|
||||
+ FullDataSize = v->data_size;
|
||||
+ p = FullData + FullDataSize;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ }
|
||||
+ }
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
|
||||
- CertList->SignatureType = EFI_CERT_TYPE_X509_GUID;
|
||||
- CertList->SignatureListSize = *v->addend_size
|
||||
- + sizeof (*CertList)
|
||||
- + sizeof (*CertData)
|
||||
- -1;
|
||||
- CertList->SignatureHeaderSize = 0;
|
||||
- CertList->SignatureSize = *v->addend_size + sizeof (EFI_GUID);
|
||||
+ /*
|
||||
+ * Now fill it.
|
||||
+ */
|
||||
+ if (v->flags & MOK_MIRROR_KEYDB) {
|
||||
+ /*
|
||||
+ * first bit is existing data, but again, we added that above
|
||||
+ */
|
||||
|
||||
- CertData->SignatureOwner = SHIM_LOCK_GUID;
|
||||
- CopyMem(p, *v->addend_source, *v->addend_size);
|
||||
+ /*
|
||||
+ * second is the build cert
|
||||
+ */
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ if (should_mirror_build_cert(v)) {
|
||||
+ efi_status = fill_esl(*v->build_cert,
|
||||
+ *v->build_cert_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ p, &build_cert_esl_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ p += build_cert_esl_sz;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ }
|
||||
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
-skip_vendor_cert:
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
- if (v->data && v->data_size)
|
||||
- FreePool(v->data);
|
||||
- v->data = FullData;
|
||||
- v->data_size = FullDataSize;
|
||||
- } else {
|
||||
- FullDataSize = v->data_size;
|
||||
- FullData = v->data;
|
||||
+ switch (addend_category) {
|
||||
+ case VENDOR_ADDEND_DB:
|
||||
+ CopyMem(p, *v->addend, *v->addend_size);
|
||||
+ p += *v->addend_size;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ break;
|
||||
+ case VENDOR_ADDEND_X509:
|
||||
+ efi_status = fill_esl(*v->addend, *v->addend_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ p, &addend_esl_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ p += addend_esl_sz;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ break;
|
||||
+ default:
|
||||
+ case VENDOR_ADDEND_NONE:
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ /*
|
||||
+ * We always want to create our key databases, so in this case we
|
||||
+ * need a dummy entry
|
||||
+ */
|
||||
+ if ((v->flags & MOK_MIRROR_KEYDB) && FullDataSize == 0) {
|
||||
+ efi_status = variable_create_esl(
|
||||
+ null_sha256, sizeof(null_sha256),
|
||||
+ &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID,
|
||||
+ &FullData, &FullDataSize);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to allocate %lu bytes for %s\n",
|
||||
+ FullDataSize, v->name);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ p = FullData + FullDataSize;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
}
|
||||
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
if (FullDataSize) {
|
||||
+ dprint(L"Setting %s with %lu bytes of data\n",
|
||||
+ v->rtname, FullDataSize);
|
||||
efi_status = gRT->SetVariable(v->rtname, v->guid,
|
||||
EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
@@ -262,7 +431,15 @@ skip_vendor_cert:
|
||||
v->rtname, efi_status);
|
||||
}
|
||||
}
|
||||
-
|
||||
+ if (v->data && v->data_size) {
|
||||
+ FreePool(v->data);
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ }
|
||||
+ if (FullData && FullDataSize) {
|
||||
+ FreePool(FullData);
|
||||
+ }
|
||||
+ dprint(L"returning %r\n", efi_status);
|
||||
return efi_status;
|
||||
}
|
||||
|
||||
@@ -274,6 +451,8 @@ static EFI_STATUS nonnull(1)
|
||||
maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
+ BOOLEAN present = FALSE;
|
||||
+
|
||||
if (v->rtname) {
|
||||
if (v->flags & MOK_MIRROR_DELETE_FIRST)
|
||||
LibDeleteVariable(v->rtname, v->guid);
|
||||
@@ -286,6 +465,43 @@ maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
efi_status);
|
||||
}
|
||||
}
|
||||
+
|
||||
+ present = (v->data && v->data_size) ? TRUE : FALSE;
|
||||
+ if (!present)
|
||||
+ return ret;
|
||||
+
|
||||
+ if (v->data_size == sizeof(UINT8) && v->state) {
|
||||
+ *v->state = v->data[0];
|
||||
+ }
|
||||
+
|
||||
+ if (v->flags & MOK_VARIABLE_MEASURE) {
|
||||
+ /*
|
||||
+ * Measure this into PCR 7 in the Microsoft format
|
||||
+ */
|
||||
+ efi_status = tpm_measure_variable(v->name, *v->guid,
|
||||
+ v->data_size,
|
||||
+ v->data);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ if (ret != EFI_SECURITY_VIOLATION)
|
||||
+ ret = efi_status;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (v->flags & MOK_VARIABLE_LOG) {
|
||||
+ /*
|
||||
+ * Log this variable into whichever PCR the table
|
||||
+ * says.
|
||||
+ */
|
||||
+ EFI_PHYSICAL_ADDRESS datap =
|
||||
+ (EFI_PHYSICAL_ADDRESS)(UINTN)v->data,
|
||||
+ efi_status = tpm_log_event(datap, v->data_size,
|
||||
+ v->pcr, (CHAR8 *)v->name8);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ if (ret != EFI_SECURITY_VIOLATION)
|
||||
+ ret = efi_status;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -311,26 +527,20 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
user_insecure_mode = 0;
|
||||
ignore_db = 0;
|
||||
|
||||
+ dprint(L"importing mok state\n");
|
||||
for (i = 0; mok_state_variables[i].name != NULL; i++) {
|
||||
struct mok_state_variable *v = &mok_state_variables[i];
|
||||
UINT32 attrs = 0;
|
||||
- BOOLEAN delete = FALSE, present, addend;
|
||||
-
|
||||
- addend = check_addend(v);
|
||||
+ BOOLEAN delete = FALSE;
|
||||
|
||||
efi_status = get_variable_attr(v->name,
|
||||
&v->data, &v->data_size,
|
||||
*v->guid, &attrs);
|
||||
+ dprint(L"maybe mirroring %s\n", v->name);
|
||||
if (efi_status == EFI_NOT_FOUND) {
|
||||
- if (addend)
|
||||
- ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
- /*
|
||||
- * after possibly adding, we can continue, no
|
||||
- * further checks to be done.
|
||||
- */
|
||||
- continue;
|
||||
- }
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ } else if (EFI_ERROR(efi_status)) {
|
||||
perror(L"Could not verify %s: %r\n", v->name,
|
||||
efi_status);
|
||||
/*
|
||||
@@ -339,22 +549,22 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
*/
|
||||
if (ret != EFI_SECURITY_VIOLATION)
|
||||
ret = efi_status;
|
||||
- continue;
|
||||
- }
|
||||
-
|
||||
- if (!(attrs & v->yes_attr)) {
|
||||
- perror(L"Variable %s is missing attributes:\n",
|
||||
- v->name);
|
||||
- perror(L" 0x%08x should have 0x%08x set.\n",
|
||||
- attrs, v->yes_attr);
|
||||
- delete = TRUE;
|
||||
- }
|
||||
- if (attrs & v->no_attr) {
|
||||
- perror(L"Variable %s has incorrect attribute:\n",
|
||||
- v->name);
|
||||
- perror(L" 0x%08x should not have 0x%08x set.\n",
|
||||
- attrs, v->no_attr);
|
||||
delete = TRUE;
|
||||
+ } else {
|
||||
+ if (!(attrs & v->yes_attr)) {
|
||||
+ perror(L"Variable %s is missing attributes:\n",
|
||||
+ v->name);
|
||||
+ perror(L" 0x%08x should have 0x%08x set.\n",
|
||||
+ attrs, v->yes_attr);
|
||||
+ delete = TRUE;
|
||||
+ }
|
||||
+ if (attrs & v->no_attr) {
|
||||
+ perror(L"Variable %s has incorrect attribute:\n",
|
||||
+ v->name);
|
||||
+ perror(L" 0x%08x should not have 0x%08x set.\n",
|
||||
+ attrs, v->no_attr);
|
||||
+ delete = TRUE;
|
||||
+ }
|
||||
}
|
||||
if (delete == TRUE) {
|
||||
perror(L"Deleting bad variable %s\n", v->name);
|
||||
@@ -366,45 +576,9 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
FreePool(v->data);
|
||||
v->data = NULL;
|
||||
v->data_size = 0;
|
||||
- continue;
|
||||
}
|
||||
|
||||
- if (v->data && v->data_size == sizeof(UINT8) && v->state) {
|
||||
- *v->state = v->data[0];
|
||||
- }
|
||||
-
|
||||
- present = (v->data && v->data_size) ? TRUE : FALSE;
|
||||
-
|
||||
- if (v->flags & MOK_VARIABLE_MEASURE && present) {
|
||||
- /*
|
||||
- * Measure this into PCR 7 in the Microsoft format
|
||||
- */
|
||||
- efi_status = tpm_measure_variable(v->name, *v->guid,
|
||||
- v->data_size,
|
||||
- v->data);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- if (ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- if (v->flags & MOK_VARIABLE_LOG && present) {
|
||||
- /*
|
||||
- * Log this variable into whichever PCR the table
|
||||
- * says.
|
||||
- */
|
||||
- EFI_PHYSICAL_ADDRESS datap =
|
||||
- (EFI_PHYSICAL_ADDRESS)(UINTN)v->data,
|
||||
- efi_status = tpm_log_event(datap, v->data_size,
|
||||
- v->pcr, (CHAR8 *)v->name8);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- if (ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- if (present)
|
||||
- ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
+ ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -412,14 +586,16 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
* cause MokManager to demand a machine reboot, so this is safe to
|
||||
* have after the entire loop.
|
||||
*/
|
||||
+ dprint(L"checking mok request\n");
|
||||
efi_status = check_mok_request(image_handle);
|
||||
+ dprint(L"mok returned %r\n", efi_status);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
if (ret != EFI_SECURITY_VIOLATION)
|
||||
ret = efi_status;
|
||||
return ret;
|
||||
}
|
||||
|
||||
-
|
||||
+ dprint(L"returning %r\n", ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 888ee6e8d7b..ee62248ca4e 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -646,6 +646,31 @@ static EFI_STATUS check_whitelist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
}
|
||||
}
|
||||
|
||||
+#if defined(VENDOR_DB_FILE)
|
||||
+ EFI_SIGNATURE_LIST *db = (EFI_SIGNATURE_LIST *)vendor_db;
|
||||
+
|
||||
+ if (check_db_hash_in_ram(db, vendor_db_size,
|
||||
+ sha256hash, SHA256_DIGEST_SIZE,
|
||||
+ EFI_CERT_SHA256_GUID, L"vendor_db",
|
||||
+ EFI_SECURE_BOOT_DB_GUID) == DATA_FOUND) {
|
||||
+ verification_method = VERIFIED_BY_HASH;
|
||||
+ update_verification_method(VERIFIED_BY_HASH);
|
||||
+ return EFI_SUCCESS;
|
||||
+ } else {
|
||||
+ LogError(L"check_db_hash(vendor_db, sha256hash) != DATA_FOUND\n");
|
||||
+ }
|
||||
+ if (cert &&
|
||||
+ check_db_cert_in_ram(db, vendor_db_size,
|
||||
+ cert, sha256hash, L"vendor_db",
|
||||
+ EFI_SECURE_BOOT_DB_GUID) == DATA_FOUND) {
|
||||
+ verification_method = VERIFIED_BY_CERT;
|
||||
+ update_verification_method(VERIFIED_BY_CERT);
|
||||
+ return EFI_SUCCESS;
|
||||
+ } else {
|
||||
+ LogError(L"check_db_cert(vendor_db, sha256hash) != DATA_FOUND\n");
|
||||
+ }
|
||||
+#endif
|
||||
+
|
||||
if (check_db_hash(L"MokList", SHIM_LOCK_GUID, sha256hash,
|
||||
SHA256_DIGEST_SIZE, EFI_CERT_SHA256_GUID)
|
||||
== DATA_FOUND) {
|
||||
@@ -1076,6 +1101,7 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
}
|
||||
#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
|
||||
+#if defined(VENDOR_CERT_FILE)
|
||||
/*
|
||||
* And finally, check against shim's built-in key
|
||||
*/
|
||||
@@ -1093,6 +1119,7 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
} else {
|
||||
LogError(L"AuthenticodeVerify(vendor_authorized) failed\n");
|
||||
}
|
||||
+#endif /* defined(VENDOR_CERT_FILE) */
|
||||
}
|
||||
|
||||
LogError(L"Binary is not whitelisted\n");
|
||||
diff --git a/include/console.h b/include/console.h
|
||||
index 9f259c71b72..810bf13a1f1 100644
|
||||
--- a/include/console.h
|
||||
+++ b/include/console.h
|
||||
@@ -78,12 +78,13 @@ struct _EFI_CONSOLE_CONTROL_PROTOCOL {
|
||||
extern VOID console_fini(VOID);
|
||||
extern VOID setup_verbosity(VOID);
|
||||
extern UINT32 verbose;
|
||||
-#define dprint(fmt, ...) ({ \
|
||||
+#define dprint_(fmt, ...) ({ \
|
||||
UINTN __dprint_ret = 0; \
|
||||
if (verbose) \
|
||||
__dprint_ret = console_print((fmt), ##__VA_ARGS__); \
|
||||
__dprint_ret; \
|
||||
})
|
||||
+#define dprint(fmt, ...) dprint_(L"%a:%d:%a() " fmt, __FILE__, __LINE__, __func__, ##__VA_ARGS__)
|
||||
|
||||
extern EFI_STATUS print_crypto_errors(EFI_STATUS rc, char *file, const char *func, int line);
|
||||
#define crypterr(rc) print_crypto_errors((rc), __FILE__, __func__, __LINE__)
|
||||
diff --git a/include/variables.h b/include/variables.h
|
||||
index 8566a1a4746..436adb46e16 100644
|
||||
--- a/include/variables.h
|
||||
+++ b/include/variables.h
|
||||
@@ -57,7 +57,12 @@ EFI_STATUS
|
||||
variable_enroll_hash(CHAR16 *var, EFI_GUID owner,
|
||||
UINT8 hash[SHA256_DIGEST_SIZE]);
|
||||
EFI_STATUS
|
||||
-variable_create_esl(void *cert, int cert_len, EFI_GUID *type, EFI_GUID *owner,
|
||||
- void **out, int *outlen);
|
||||
+variable_create_esl(const uint8_t *cert, const size_t cert_len,
|
||||
+ const EFI_GUID *type, const EFI_GUID *owner,
|
||||
+ uint8_t **out, size_t *outlen);
|
||||
+EFI_STATUS
|
||||
+fill_esl(const uint8_t *data, const size_t data_len,
|
||||
+ const EFI_GUID *type, const EFI_GUID *owner,
|
||||
+ uint8_t *out, size_t *outlen);
|
||||
|
||||
#endif /* SHIM_VARIABLES_H */
|
||||
diff --git a/shim.h b/shim.h
|
||||
index 555498c6673..c1d7e7c7197 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -97,7 +97,11 @@
|
||||
#define FALLBACK L"\\fb" EFI_ARCH L".efi"
|
||||
#define MOK_MANAGER L"\\mm" EFI_ARCH L".efi"
|
||||
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
+#if defined(VENDOR_DB_FILE)
|
||||
+# define vendor_authorized vendor_db
|
||||
+# define vendor_authorized_size vendor_db_size
|
||||
+# define vendor_authorized_category VENDOR_ADDEND_DB
|
||||
+#elif defined(VENDOR_CERT_FILE)
|
||||
# define vendor_authorized vendor_cert
|
||||
# define vendor_authorized_size vendor_cert_size
|
||||
# define vendor_authorized_category VENDOR_ADDEND_X509
|
||||
@@ -116,6 +120,7 @@
|
||||
#endif
|
||||
|
||||
#include "include/asm.h"
|
||||
+#include "include/compiler.h"
|
||||
#include "include/configtable.h"
|
||||
#include "include/console.h"
|
||||
#include "include/crypt_blowfish.h"
|
||||
diff --git a/cert.S b/cert.S
|
||||
index 520caaef3af..e636fcbbf2d 100644
|
||||
--- a/cert.S
|
||||
+++ b/cert.S
|
||||
@@ -1,5 +1,12 @@
|
||||
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
+#if defined(VENDOR_DB_FILE) && defined(VENDOR_CERT_FILE)
|
||||
+# error both VENDOR_DB_FILE and VENDOR_CERT_FILE have been configured
|
||||
+#elif defined(VENDOR_DB_FILE)
|
||||
+# define vendor_authorized vendor_db
|
||||
+# define vendor_authorized_end vendor_db_end
|
||||
+# define vendor_authorized_size vendor_db_size
|
||||
+# define vendor_authorized_size_end vendor_db_size_end
|
||||
+#elif defined(VENDOR_CERT_FILE)
|
||||
# define vendor_authorized vendor_cert
|
||||
# define vendor_authorized_end vendor_cert_end
|
||||
# define vendor_authorized_size vendor_cert_size
|
||||
@@ -28,7 +35,9 @@ cert_table:
|
||||
.size vendor_authorized, .Lvendor_authorized_end - vendor_authorized
|
||||
.section .vendor_cert, "a", %progbits
|
||||
vendor_authorized:
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
+#if defined(VENDOR_DB_FILE)
|
||||
+.incbin VENDOR_DB_FILE
|
||||
+#elif defined(VENDOR_CERT_FILE)
|
||||
.incbin VENDOR_CERT_FILE
|
||||
#endif
|
||||
.Lvendor_authorized_end:
|
||||
diff --git a/Make.defaults b/Make.defaults
|
||||
index f0bfa9fd573..2e01646a35d 100644
|
||||
--- a/Make.defaults
|
||||
+++ b/Make.defaults
|
||||
@@ -125,6 +125,9 @@ BOOTCSVNAME ?= BOOT$(ARCH_SUFFIX_UPPER).CSV
|
||||
|
||||
CFLAGS += "-DEFI_ARCH=L\"$(ARCH_SUFFIX)\"" "-DDEBUGDIR=L\"/usr/lib/debug/usr/share/shim/$(ARCH_SUFFIX)-$(VERSION)$(DASHRELEASE)/\""
|
||||
|
||||
+ifneq ($(origin VENDOR_DB_FILE), undefined)
|
||||
+ CFLAGS += -DVENDOR_DB_FILE=\"$(VENDOR_DB_FILE)\"
|
||||
+endif
|
||||
ifneq ($(origin VENDOR_CERT_FILE), undefined)
|
||||
CFLAGS += -DVENDOR_CERT_FILE=\"$(VENDOR_CERT_FILE)\"
|
||||
endif
|
||||
diff --git a/README.tpm b/README.tpm
|
||||
index c060dbe22db..62308d5c71a 100644
|
||||
--- a/README.tpm
|
||||
+++ b/README.tpm
|
||||
@@ -13,6 +13,7 @@ PCR7:
|
||||
- MokListX - the Mok blacklist, logged as "MokListX"
|
||||
- vendor_dbx - shim's built-in vendor blacklist, logged as "dbx"
|
||||
- DB - the system whitelist, logged as "db"
|
||||
+ - vendor_db - shim's built-in vendor whitelist, logged as "db"
|
||||
- MokList the Mok whitelist, logged as "MokList"
|
||||
- vendor_cert - shim's built-in vendor whitelist, logged as "Shim"
|
||||
- shim_cert - shim's build-time generated whitelist, logged as "Shim"
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,366 +0,0 @@
|
||||
From 76c0447e204c7e4ce918c4887ce8aae0e0816271 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 16:32:05 -0400
|
||||
Subject: [PATCH 58/62] Handle binaries with multiple signatures.
|
||||
|
||||
This adds support for multiple signatures. It first tries validating
|
||||
the binary by hash, first against our dbx lists, then against our db
|
||||
lists. If it isn't allowed or rejected at that step, it continues to
|
||||
the normal routine of checking all the signatures.
|
||||
|
||||
At this point it does *not* reject a binary just because a signature is
|
||||
by a cert on a dbx list, though that will override any db list that
|
||||
certificate is listed on. If at any point any assertion about the
|
||||
binary or signature list being well-formed fails, the binary is
|
||||
immediately rejected, though we do allow skipping over signatures
|
||||
which have an unsupported sig->Hdr.wCertificateType.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#210
|
||||
---
|
||||
shim.c | 287 +++++++++++++++++++++++++++++++++++++++------------------
|
||||
1 file changed, 198 insertions(+), 89 deletions(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index ee62248ca4e..d10a1ba1cac 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -690,7 +690,7 @@ static EFI_STATUS check_whitelist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
}
|
||||
|
||||
update_verification_method(VERIFIED_BY_NOTHING);
|
||||
- return EFI_SECURITY_VIOLATION;
|
||||
+ return EFI_NOT_FOUND;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -1004,6 +1004,103 @@ done:
|
||||
return efi_status;
|
||||
}
|
||||
|
||||
+static EFI_STATUS
|
||||
+verify_one_signature(WIN_CERTIFICATE_EFI_PKCS *sig,
|
||||
+ UINT8 *sha256hash, UINT8 *sha1hash)
|
||||
+{
|
||||
+ EFI_STATUS efi_status;
|
||||
+
|
||||
+ /*
|
||||
+ * Ensure that the binary isn't blacklisted
|
||||
+ */
|
||||
+ drain_openssl_errors();
|
||||
+ efi_status = check_blacklist(sig, sha256hash, sha1hash);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Binary is blacklisted: %r\n", efi_status);
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Check whether the binary is whitelisted in any of the firmware
|
||||
+ * databases
|
||||
+ */
|
||||
+ drain_openssl_errors();
|
||||
+ efi_status = check_whitelist(sig, sha256hash, sha1hash);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ if (efi_status != EFI_NOT_FOUND) {
|
||||
+ dprint(L"check_whitelist(): %r\n", efi_status);
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(efi_status);
|
||||
+ }
|
||||
+ } else {
|
||||
+ drain_openssl_errors();
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ efi_status = EFI_NOT_FOUND;
|
||||
+#if defined(ENABLE_SHIM_CERT)
|
||||
+ /*
|
||||
+ * Check against the shim build key
|
||||
+ */
|
||||
+ drain_openssl_errors();
|
||||
+ if (build_cert && build_cert_size) {
|
||||
+ dprint("verifying against shim cert\n");
|
||||
+ }
|
||||
+ if (build_cert && build_cert_size &&
|
||||
+ AuthenticodeVerify(sig->CertData,
|
||||
+ sig->Hdr.dwLength - sizeof(sig->Hdr),
|
||||
+ build_cert, build_cert_size, sha256hash,
|
||||
+ SHA256_DIGEST_SIZE)) {
|
||||
+ dprint(L"AuthenticodeVerify(shim_cert) succeeded\n");
|
||||
+ update_verification_method(VERIFIED_BY_CERT);
|
||||
+ tpm_measure_variable(L"Shim", SHIM_LOCK_GUID,
|
||||
+ build_cert_size, build_cert);
|
||||
+ efi_status = EFI_SUCCESS;
|
||||
+ drain_openssl_errors();
|
||||
+ return efi_status;
|
||||
+ } else {
|
||||
+ dprint(L"AuthenticodeVerify(shim_cert) failed\n");
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(EFI_NOT_FOUND);
|
||||
+ }
|
||||
+#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
+
|
||||
+#if defined(VENDOR_CERT_FILE)
|
||||
+ /*
|
||||
+ * And finally, check against shim's built-in key
|
||||
+ */
|
||||
+ drain_openssl_errors();
|
||||
+ if (vendor_cert_size) {
|
||||
+ dprint("verifying against vendor_cert\n");
|
||||
+ }
|
||||
+ if (vendor_cert_size &&
|
||||
+ AuthenticodeVerify(sig->CertData,
|
||||
+ sig->Hdr.dwLength - sizeof(sig->Hdr),
|
||||
+ vendor_cert, vendor_cert_size,
|
||||
+ sha256hash, SHA256_DIGEST_SIZE)) {
|
||||
+ dprint(L"AuthenticodeVerify(vendor_cert) succeeded\n");
|
||||
+ update_verification_method(VERIFIED_BY_CERT);
|
||||
+ tpm_measure_variable(L"Shim", SHIM_LOCK_GUID,
|
||||
+ vendor_cert_size, vendor_cert);
|
||||
+ efi_status = EFI_SUCCESS;
|
||||
+ drain_openssl_errors();
|
||||
+ return efi_status;
|
||||
+ } else {
|
||||
+ dprint(L"AuthenticodeVerify(vendor_cert) failed\n");
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(EFI_NOT_FOUND);
|
||||
+ }
|
||||
+#endif /* defined(VENDOR_CERT_FILE) */
|
||||
+
|
||||
+ return efi_status;
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Check that the signature is valid and matches the binary
|
||||
*/
|
||||
@@ -1011,40 +1108,14 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
PE_COFF_LOADER_IMAGE_CONTEXT *context,
|
||||
UINT8 *sha256hash, UINT8 *sha1hash)
|
||||
{
|
||||
- EFI_STATUS efi_status = EFI_SECURITY_VIOLATION;
|
||||
- WIN_CERTIFICATE_EFI_PKCS *cert = NULL;
|
||||
- unsigned int size = datasize;
|
||||
+ EFI_STATUS ret_efi_status;
|
||||
+ size_t size = datasize;
|
||||
+ size_t offset = 0;
|
||||
+ unsigned int i = 0;
|
||||
|
||||
if (datasize < 0)
|
||||
return EFI_INVALID_PARAMETER;
|
||||
|
||||
- if (context->SecDir->Size != 0) {
|
||||
- if (context->SecDir->Size >= size) {
|
||||
- perror(L"Certificate Database size is too large\n");
|
||||
- return EFI_INVALID_PARAMETER;
|
||||
- }
|
||||
-
|
||||
- cert = ImageAddress (data, size,
|
||||
- context->SecDir->VirtualAddress);
|
||||
-
|
||||
- if (!cert) {
|
||||
- perror(L"Certificate located outside the image\n");
|
||||
- return EFI_INVALID_PARAMETER;
|
||||
- }
|
||||
-
|
||||
- if (cert->Hdr.dwLength > context->SecDir->Size) {
|
||||
- perror(L"Certificate list size is inconsistent with PE headers");
|
||||
- return EFI_INVALID_PARAMETER;
|
||||
- }
|
||||
-
|
||||
- if (cert->Hdr.wCertificateType !=
|
||||
- WIN_CERT_TYPE_PKCS_SIGNED_DATA) {
|
||||
- perror(L"Unsupported certificate type %x\n",
|
||||
- cert->Hdr.wCertificateType);
|
||||
- return EFI_UNSUPPORTED;
|
||||
- }
|
||||
- }
|
||||
-
|
||||
/*
|
||||
* Clear OpenSSL's error log, because we get some DSO unimplemented
|
||||
* errors during its intialization, and we don't want those to look
|
||||
@@ -1052,81 +1123,119 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
*/
|
||||
drain_openssl_errors();
|
||||
|
||||
- efi_status = generate_hash(data, datasize, context, sha256hash, sha1hash);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- LogError(L"generate_hash: %r\n", efi_status);
|
||||
- return efi_status;
|
||||
+ ret_efi_status = generate_hash(data, datasize, context, sha256hash, sha1hash);
|
||||
+ if (EFI_ERROR(ret_efi_status)) {
|
||||
+ dprint(L"generate_hash: %r\n", ret_efi_status);
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(ret_efi_status);
|
||||
+ return ret_efi_status;
|
||||
}
|
||||
|
||||
/*
|
||||
- * Ensure that the binary isn't blacklisted
|
||||
+ * Ensure that the binary isn't blacklisted by hash
|
||||
*/
|
||||
- efi_status = check_blacklist(cert, sha256hash, sha1hash);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
+ drain_openssl_errors();
|
||||
+ ret_efi_status = check_blacklist(NULL, sha256hash, sha1hash);
|
||||
+ if (EFI_ERROR(ret_efi_status)) {
|
||||
perror(L"Binary is blacklisted\n");
|
||||
- LogError(L"Binary is blacklisted: %r\n", efi_status);
|
||||
- return efi_status;
|
||||
+ dprint(L"Binary is blacklisted: %r\n", ret_efi_status);
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(ret_efi_status);
|
||||
+ return ret_efi_status;
|
||||
}
|
||||
|
||||
/*
|
||||
- * Check whether the binary is whitelisted in any of the firmware
|
||||
- * databases
|
||||
+ * Check whether the binary is whitelisted by hash in any of the
|
||||
+ * firmware databases
|
||||
*/
|
||||
- efi_status = check_whitelist(cert, sha256hash, sha1hash);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- LogError(L"check_whitelist(): %r\n", efi_status);
|
||||
+ drain_openssl_errors();
|
||||
+ ret_efi_status = check_whitelist(NULL, sha256hash, sha1hash);
|
||||
+ if (EFI_ERROR(ret_efi_status)) {
|
||||
+ dprint(L"check_whitelist: %r\n", ret_efi_status);
|
||||
+ if (ret_efi_status != EFI_NOT_FOUND) {
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(ret_efi_status);
|
||||
+ return ret_efi_status;
|
||||
+ }
|
||||
} else {
|
||||
drain_openssl_errors();
|
||||
- return efi_status;
|
||||
+ return ret_efi_status;
|
||||
}
|
||||
|
||||
- if (cert) {
|
||||
-#if defined(ENABLE_SHIM_CERT)
|
||||
- /*
|
||||
- * Check against the shim build key
|
||||
- */
|
||||
- if (sizeof(shim_cert) &&
|
||||
- AuthenticodeVerify(cert->CertData,
|
||||
- cert->Hdr.dwLength - sizeof(cert->Hdr),
|
||||
- shim_cert, sizeof(shim_cert), sha256hash,
|
||||
- SHA256_DIGEST_SIZE)) {
|
||||
- update_verification_method(VERIFIED_BY_CERT);
|
||||
- tpm_measure_variable(L"Shim", SHIM_LOCK_GUID,
|
||||
- sizeof(shim_cert), shim_cert);
|
||||
- efi_status = EFI_SUCCESS;
|
||||
- drain_openssl_errors();
|
||||
- return efi_status;
|
||||
- } else {
|
||||
- LogError(L"AuthenticodeVerify(shim_cert) failed\n");
|
||||
+ if (context->SecDir->Size == 0) {
|
||||
+ dprint(L"No signatures found\n");
|
||||
+ return EFI_SECURITY_VIOLATION;
|
||||
+ }
|
||||
+
|
||||
+ if (context->SecDir->Size >= size) {
|
||||
+ perror(L"Certificate Database size is too large\n");
|
||||
+ return EFI_INVALID_PARAMETER;
|
||||
+ }
|
||||
+
|
||||
+ ret_efi_status = EFI_NOT_FOUND;
|
||||
+ do {
|
||||
+ WIN_CERTIFICATE_EFI_PKCS *sig = NULL;
|
||||
+ size_t sz;
|
||||
+
|
||||
+ sig = ImageAddress(data, size,
|
||||
+ context->SecDir->VirtualAddress + offset);
|
||||
+ if (!sig)
|
||||
+ break;
|
||||
+
|
||||
+ sz = offset + offsetof(WIN_CERTIFICATE_EFI_PKCS, Hdr.dwLength)
|
||||
+ + sizeof(sig->Hdr.dwLength);
|
||||
+ if (sz > context->SecDir->Size) {
|
||||
+ perror(L"Certificate size is too large for secruity database");
|
||||
+ return EFI_INVALID_PARAMETER;
|
||||
+ }
|
||||
+
|
||||
+ sz = sig->Hdr.dwLength;
|
||||
+ if (sz > context->SecDir->Size - offset) {
|
||||
+ perror(L"Certificate size is too large for secruity database");
|
||||
+ return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
-#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
-
|
||||
-#if defined(VENDOR_CERT_FILE)
|
||||
- /*
|
||||
- * And finally, check against shim's built-in key
|
||||
- */
|
||||
- if (vendor_authorized_size &&
|
||||
- AuthenticodeVerify(cert->CertData,
|
||||
- cert->Hdr.dwLength - sizeof(cert->Hdr),
|
||||
- vendor_authorized, vendor_authorized_size,
|
||||
- sha256hash, SHA256_DIGEST_SIZE)) {
|
||||
- update_verification_method(VERIFIED_BY_CERT);
|
||||
- tpm_measure_variable(L"Shim", SHIM_LOCK_GUID,
|
||||
- vendor_authorized_size, vendor_authorized);
|
||||
- efi_status = EFI_SUCCESS;
|
||||
- drain_openssl_errors();
|
||||
- return efi_status;
|
||||
+
|
||||
+ if (sz < sizeof(sig->Hdr)) {
|
||||
+ perror(L"Certificate size is too small for certificate data");
|
||||
+ return EFI_INVALID_PARAMETER;
|
||||
+ }
|
||||
+
|
||||
+ if (sig->Hdr.wCertificateType == WIN_CERT_TYPE_PKCS_SIGNED_DATA) {
|
||||
+ EFI_STATUS efi_status;
|
||||
+
|
||||
+ dprint(L"Attempting to verify signature %d:\n", i++);
|
||||
+
|
||||
+ efi_status = verify_one_signature(sig, sha256hash, sha1hash);
|
||||
+
|
||||
+ /*
|
||||
+ * If we didn't get EFI_SECURITY_VIOLATION from
|
||||
+ * checking the hashes above, then any dbx entries are
|
||||
+ * for a certificate, not this individual binary.
|
||||
+ *
|
||||
+ * So don't clobber successes with security violation
|
||||
+ * here; that just means it isn't a success.
|
||||
+ */
|
||||
+ if (ret_efi_status != EFI_SUCCESS)
|
||||
+ ret_efi_status = efi_status;
|
||||
} else {
|
||||
- LogError(L"AuthenticodeVerify(vendor_authorized) failed\n");
|
||||
+ perror(L"Unsupported certificate type %x\n",
|
||||
+ sig->Hdr.wCertificateType);
|
||||
}
|
||||
-#endif /* defined(VENDOR_CERT_FILE) */
|
||||
- }
|
||||
+ offset = ALIGN_VALUE(offset + sz, 8);
|
||||
+ } while (offset < context->SecDir->Size);
|
||||
|
||||
- LogError(L"Binary is not whitelisted\n");
|
||||
- crypterr(EFI_SECURITY_VIOLATION);
|
||||
- PrintErrors();
|
||||
- efi_status = EFI_SECURITY_VIOLATION;
|
||||
- return efi_status;
|
||||
+ if (ret_efi_status != EFI_SUCCESS) {
|
||||
+ dprint(L"Binary is not whitelisted\n");
|
||||
+ PrintErrors();
|
||||
+ ClearErrors();
|
||||
+ crypterr(EFI_SECURITY_VIOLATION);
|
||||
+ ret_efi_status = EFI_SECURITY_VIOLATION;
|
||||
+ }
|
||||
+ drain_openssl_errors();
|
||||
+ return ret_efi_status;
|
||||
}
|
||||
|
||||
/*
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,119 +0,0 @@
|
||||
From 705d47ac2c90b8de07a4ef3e1930de6c4b8fece0 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Wed, 22 Jul 2020 19:54:58 -0400
|
||||
Subject: [PATCH 59/62] Make openssl accept the right set of KU/EKUs
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#211
|
||||
---
|
||||
Cryptlib/Pk/CryptPkcs7Verify.c | 87 ++++++++++++++++++++++++++++++++++
|
||||
1 file changed, 87 insertions(+)
|
||||
|
||||
diff --git a/Cryptlib/Pk/CryptPkcs7Verify.c b/Cryptlib/Pk/CryptPkcs7Verify.c
|
||||
index dcaba436797..09895d8c66a 100644
|
||||
--- a/Cryptlib/Pk/CryptPkcs7Verify.c
|
||||
+++ b/Cryptlib/Pk/CryptPkcs7Verify.c
|
||||
@@ -30,6 +30,91 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
|
||||
|
||||
UINT8 mOidValue[9] = { 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x07, 0x02 };
|
||||
|
||||
+#if 1
|
||||
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
|
||||
+#define X509_OBJECT_get0_X509(obj) ((obj)->data.x509)
|
||||
+#define X509_OBJECT_get_type(obj) ((obj)->type)
|
||||
+#define X509_STORE_CTX_get0_cert(ctx) ((ctx)->cert)
|
||||
+#define X509_STORE_get0_objects(certs) ((certs)->objs)
|
||||
+#define X509_get_extended_key_usage(cert) ((cert)->ex_xkusage)
|
||||
+#if OPENSSL_VERSION_NUMBER < 0x10020000L
|
||||
+#define X509_STORE_CTX_get0_store(ctx) ((ctx)->ctx)
|
||||
+#endif
|
||||
+#endif
|
||||
+
|
||||
+static int cert_in_store(X509 *cert, X509_STORE_CTX *ctx)
|
||||
+{
|
||||
+ X509_OBJECT obj;
|
||||
+ obj.type = X509_LU_X509;
|
||||
+ obj.data.x509 = cert;
|
||||
+ return X509_OBJECT_retrieve_match(ctx->ctx->objs, &obj) != NULL;
|
||||
+}
|
||||
+#else
|
||||
+/*
|
||||
+ * Later versions of openssl will need this instead.
|
||||
+ */
|
||||
+static int cert_in_store(X509 *cert, X509_STORE_CTX *ctx)
|
||||
+{
|
||||
+ STACK_OF(X509_OBJECT) *objs;
|
||||
+ X509_OBJECT *obj;
|
||||
+ int i;
|
||||
+
|
||||
+ objs = X509_STORE_get0_objects(X509_STORE_CTX_get0_store(ctx));
|
||||
+
|
||||
+ for (i = 0; i < sk_X509_OBJECT_num(objs); i++) {
|
||||
+ obj = sk_X509_OBJECT_value(objs, i);
|
||||
+
|
||||
+ if (X509_OBJECT_get_type(obj) == X509_LU_X509 &&
|
||||
+ !X509_cmp(X509_OBJECT_get0_X509(obj), cert))
|
||||
+ return 1;
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+#endif
|
||||
+
|
||||
+int
|
||||
+X509VerifyCb (
|
||||
+ IN int Status,
|
||||
+ IN X509_STORE_CTX *Context
|
||||
+ )
|
||||
+{
|
||||
+ INTN Error;
|
||||
+
|
||||
+ Error = (INTN) X509_STORE_CTX_get_error (Context);
|
||||
+
|
||||
+ /* Accept code-signing keys */
|
||||
+ if (Error == X509_V_ERR_INVALID_PURPOSE &&
|
||||
+ X509_get_extended_key_usage(X509_STORE_CTX_get0_cert(Context)) == XKU_CODE_SIGN) {
|
||||
+ Status = 1;
|
||||
+ } else if (Error == X509_V_ERR_CERT_UNTRUSTED ||
|
||||
+ Error == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT ||
|
||||
+ Error == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY ||
|
||||
+ Error == X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE) {
|
||||
+ /* all certs in our cert database are explicitly trusted */
|
||||
+
|
||||
+ if (cert_in_store(X509_STORE_CTX_get_current_cert(Context), Context))
|
||||
+ Status = 1;
|
||||
+ } else if (Error == X509_V_ERR_CERT_HAS_EXPIRED ||
|
||||
+ Error == X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD ||
|
||||
+ Error == X509_V_ERR_CERT_NOT_YET_VALID ||
|
||||
+ Error == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY ||
|
||||
+ Error == X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD) {
|
||||
+ /* UEFI explicitly allows expired certificates */
|
||||
+ Status = 1;
|
||||
+#if 0
|
||||
+ } else if (Error == X509_V_ERR_INVALID_CA) {
|
||||
+ /* Due to the historical reason, we have to relax the the x509 v3 extension
|
||||
+ * check to allow the CA certificates without the CA flag in the basic
|
||||
+ * constraints or KeyCertSign in the key usage to be loaded. In the future,
|
||||
+ * this callback should be removed to enforce the proper check. */
|
||||
+ Status = 1;
|
||||
+#endif
|
||||
+ }
|
||||
+
|
||||
+ return Status;
|
||||
+}
|
||||
+
|
||||
/**
|
||||
Check input P7Data is a wrapped ContentInfo structure or not. If not construct
|
||||
a new structure to wrap P7Data.
|
||||
@@ -844,6 +929,8 @@ Pkcs7Verify (
|
||||
goto _Exit;
|
||||
}
|
||||
|
||||
+ X509_STORE_set_verify_cb (CertStore, X509VerifyCb);
|
||||
+
|
||||
//
|
||||
// For generic PKCS#7 handling, InData may be NULL if the content is present
|
||||
// in PKCS#7 structure. So ignore NULL checking here.
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,451 +0,0 @@
|
||||
From fc4368fed53837e00d303600d8b628cb0392b629 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 20:29:52 -0400
|
||||
Subject: [PATCH 60/62] Improve debug output some
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: pr#213
|
||||
---
|
||||
errlog.c | 26 ++++++-
|
||||
shim.c | 36 ++++++++--
|
||||
include/console.h | 3 +
|
||||
include/hexdump.h | 172 ++++++++++++++++++++++++++++------------------
|
||||
shim.h | 5 +-
|
||||
5 files changed, 164 insertions(+), 78 deletions(-)
|
||||
|
||||
diff --git a/errlog.c b/errlog.c
|
||||
index 6669c800233..08f7a82a6b2 100644
|
||||
--- a/errlog.c
|
||||
+++ b/errlog.c
|
||||
@@ -3,12 +3,28 @@
|
||||
* Copyright 2017 Peter Jones <pjones@redhat.com>
|
||||
*/
|
||||
#include "shim.h"
|
||||
+#include "hexdump.h"
|
||||
|
||||
static CHAR16 **errs = NULL;
|
||||
static UINTN nerrs = 0;
|
||||
|
||||
EFI_STATUS
|
||||
-VLogError(const char *file, int line, const char *func, CHAR16 *fmt, va_list args)
|
||||
+vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, va_list args)
|
||||
+{
|
||||
+ va_list args2;
|
||||
+ EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
+
|
||||
+ if (verbose) {
|
||||
+ va_copy(args2, args);
|
||||
+ console_print(L"%a:%d:%a() ", file, line, func);
|
||||
+ efi_status = VPrint(fmt, args2);
|
||||
+ va_end(args2);
|
||||
+ }
|
||||
+ return efi_status;
|
||||
+}
|
||||
+
|
||||
+EFI_STATUS
|
||||
+VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_list args)
|
||||
{
|
||||
va_list args2;
|
||||
CHAR16 **newerrs;
|
||||
@@ -35,7 +51,7 @@ VLogError(const char *file, int line, const char *func, CHAR16 *fmt, va_list arg
|
||||
}
|
||||
|
||||
EFI_STATUS
|
||||
-LogError_(const char *file, int line, const char *func, CHAR16 *fmt, ...)
|
||||
+LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
EFI_STATUS efi_status;
|
||||
@@ -47,6 +63,12 @@ LogError_(const char *file, int line, const char *func, CHAR16 *fmt, ...)
|
||||
return efi_status;
|
||||
}
|
||||
|
||||
+VOID
|
||||
+LogHexdump_(const char *file, int line, const char *func, const void *data, size_t sz)
|
||||
+{
|
||||
+ hexdumpat(file, line, func, data, sz, 0);
|
||||
+}
|
||||
+
|
||||
VOID
|
||||
PrintErrors(VOID)
|
||||
{
|
||||
diff --git a/shim.c b/shim.c
|
||||
index d10a1ba1cac..9248642bd57 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -34,6 +34,7 @@
|
||||
*/
|
||||
|
||||
#include "shim.h"
|
||||
+#include "hexdump.h"
|
||||
#if defined(ENABLE_SHIM_CERT)
|
||||
#include "shim_cert.h"
|
||||
#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
@@ -373,12 +374,18 @@ static BOOLEAN verify_x509(UINT8 *Cert, UINTN CertSize)
|
||||
* and 64KB. For convenience, assume the number of value bytes
|
||||
* is 2, i.e. the second byte is 0x82.
|
||||
*/
|
||||
- if (Cert[0] != 0x30 || Cert[1] != 0x82)
|
||||
+ if (Cert[0] != 0x30 || Cert[1] != 0x82) {
|
||||
+ dprint(L"cert[0:1] is [%02x%02x], should be [%02x%02x]\n",
|
||||
+ Cert[0], Cert[1], 0x30, 0x82);
|
||||
return FALSE;
|
||||
+ }
|
||||
|
||||
length = Cert[2]<<8 | Cert[3];
|
||||
- if (length != (CertSize - 4))
|
||||
+ if (length != (CertSize - 4)) {
|
||||
+ dprint(L"Cert length is %ld, expecting %ld\n",
|
||||
+ length, CertSize);
|
||||
return FALSE;
|
||||
+ }
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
@@ -426,19 +433,23 @@ static CHECK_STATUS check_db_cert_in_ram(EFI_SIGNATURE_LIST *CertList,
|
||||
EFI_SIGNATURE_DATA *Cert;
|
||||
UINTN CertSize;
|
||||
BOOLEAN IsFound = FALSE;
|
||||
+ int i = 0;
|
||||
|
||||
while ((dbsize > 0) && (dbsize >= CertList->SignatureListSize)) {
|
||||
if (CompareGuid (&CertList->SignatureType, &EFI_CERT_TYPE_X509_GUID) == 0) {
|
||||
Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
|
||||
CertSize = CertList->SignatureSize - sizeof(EFI_GUID);
|
||||
+ dprint(L"trying to verify cert %d (%s)\n", i++, dbname);
|
||||
if (verify_x509(Cert->SignatureData, CertSize)) {
|
||||
if (verify_eku(Cert->SignatureData, CertSize)) {
|
||||
+ drain_openssl_errors();
|
||||
IsFound = AuthenticodeVerify (data->CertData,
|
||||
data->Hdr.dwLength - sizeof(data->Hdr),
|
||||
Cert->SignatureData,
|
||||
CertSize,
|
||||
hash, SHA256_DIGEST_SIZE);
|
||||
if (IsFound) {
|
||||
+ dprint(L"AuthenticodeVerify() succeeded: %d\n", IsFound);
|
||||
tpm_measure_variable(dbname, guid, CertSize, Cert->SignatureData);
|
||||
drain_openssl_errors();
|
||||
return DATA_FOUND;
|
||||
@@ -447,7 +458,9 @@ static CHECK_STATUS check_db_cert_in_ram(EFI_SIGNATURE_LIST *CertList,
|
||||
}
|
||||
}
|
||||
} else if (verbose) {
|
||||
- console_notify(L"Not a DER encoding x.509 Certificate");
|
||||
+ console_print(L"Not a DER encoded x.509 Certificate");
|
||||
+ dprint(L"cert:\n");
|
||||
+ dhexdumpat(Cert->SignatureData, CertSize, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -641,7 +654,7 @@ static EFI_STATUS check_whitelist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
verification_method = VERIFIED_BY_CERT;
|
||||
update_verification_method(VERIFIED_BY_CERT);
|
||||
return EFI_SUCCESS;
|
||||
- } else {
|
||||
+ } else if (cert) {
|
||||
LogError(L"check_db_cert(db, sha256hash) != DATA_FOUND\n");
|
||||
}
|
||||
}
|
||||
@@ -666,7 +679,7 @@ static EFI_STATUS check_whitelist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
verification_method = VERIFIED_BY_CERT;
|
||||
update_verification_method(VERIFIED_BY_CERT);
|
||||
return EFI_SUCCESS;
|
||||
- } else {
|
||||
+ } else if (cert) {
|
||||
LogError(L"check_db_cert(vendor_db, sha256hash) != DATA_FOUND\n");
|
||||
}
|
||||
#endif
|
||||
@@ -685,7 +698,7 @@ static EFI_STATUS check_whitelist (WIN_CERTIFICATE_EFI_PKCS *cert,
|
||||
verification_method = VERIFIED_BY_CERT;
|
||||
update_verification_method(VERIFIED_BY_CERT);
|
||||
return EFI_SUCCESS;
|
||||
- } else {
|
||||
+ } else if (cert) {
|
||||
LogError(L"check_db_cert(MokList, sha256hash) != DATA_FOUND\n");
|
||||
}
|
||||
|
||||
@@ -993,6 +1006,11 @@ static EFI_STATUS generate_hash (char *data, unsigned int datasize_in,
|
||||
goto done;
|
||||
}
|
||||
|
||||
+ dprint(L"sha1 authenticode hash:\n");
|
||||
+ dhexdumpat(sha1hash, SHA1_DIGEST_SIZE, 0);
|
||||
+ dprint(L"sha256 authenticode hash:\n");
|
||||
+ dhexdumpat(sha256hash, SHA256_DIGEST_SIZE, 0);
|
||||
+
|
||||
done:
|
||||
if (SectionHeader)
|
||||
FreePool(SectionHeader);
|
||||
@@ -1155,6 +1173,7 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
|
||||
if (EFI_ERROR(ret_efi_status)) {
|
||||
dprint(L"check_whitelist: %r\n", ret_efi_status);
|
||||
if (ret_efi_status != EFI_NOT_FOUND) {
|
||||
+ dprint(L"check_whitelist(): %r\n", ret_efi_status);
|
||||
PrintErrors();
|
||||
ClearErrors();
|
||||
crypterr(ret_efi_status);
|
||||
@@ -1803,6 +1822,7 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data,
|
||||
|
||||
device = li->DeviceHandle;
|
||||
|
||||
+ dprint(L"attempting to load %s\n", PathName);
|
||||
/*
|
||||
* Open the device
|
||||
*/
|
||||
@@ -2778,6 +2798,10 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
*/
|
||||
InitializeLib(image_handle, systab);
|
||||
|
||||
+ dprint(L"vendor_authorized:0x%08lx vendor_authorized_size:%lu\n",
|
||||
+ __FILE__, __LINE__, __func__, vendor_authorized, vendor_authorized_size);
|
||||
+ dprint(L"vendor_deauthorized:0x%08lx vendor_deauthorized_size:%lu\n",
|
||||
+ __FILE__, __LINE__, __func__, vendor_deauthorized, vendor_deauthorized_size);
|
||||
init_openssl();
|
||||
|
||||
/*
|
||||
diff --git a/include/console.h b/include/console.h
|
||||
index 810bf13a1f1..ac6fdf61d18 100644
|
||||
--- a/include/console.h
|
||||
+++ b/include/console.h
|
||||
@@ -85,6 +85,9 @@ extern UINT32 verbose;
|
||||
__dprint_ret; \
|
||||
})
|
||||
#define dprint(fmt, ...) dprint_(L"%a:%d:%a() " fmt, __FILE__, __LINE__, __func__, ##__VA_ARGS__)
|
||||
+extern EFI_STATUS
|
||||
+vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, va_list args);
|
||||
+#define vdprint(fmt, ...) vdprint_(fmt, __FILE__, __LINE__, __func__, ##__VA_ARGS__)
|
||||
|
||||
extern EFI_STATUS print_crypto_errors(EFI_STATUS rc, char *file, const char *func, int line);
|
||||
#define crypterr(rc) print_crypto_errors((rc), __FILE__, __func__, __LINE__)
|
||||
diff --git a/include/hexdump.h b/include/hexdump.h
|
||||
index d337b571d8d..f3f3ac284a3 100644
|
||||
--- a/include/hexdump.h
|
||||
+++ b/include/hexdump.h
|
||||
@@ -1,104 +1,140 @@
|
||||
#ifndef STATIC_HEXDUMP_H
|
||||
#define STATIC_HEXDUMP_H
|
||||
|
||||
-static int
|
||||
-__attribute__((__unused__))
|
||||
-isprint(char c)
|
||||
-{
|
||||
- if (c < 0x20)
|
||||
- return 0;
|
||||
- if (c > 0x7e)
|
||||
- return 0;
|
||||
- return 1;
|
||||
-}
|
||||
+#include <stdint.h>
|
||||
|
||||
-static UINTN
|
||||
-__attribute__((__unused__))
|
||||
-format_hex(UINT8 *data, UINTN size, CHAR16 *buf)
|
||||
+static inline unsigned long UNUSED
|
||||
+prepare_hex(const void *data, size_t size, char *buf, int position)
|
||||
{
|
||||
- UINTN sz = (UINTN)data % 16;
|
||||
- CHAR16 hexchars[] = L"0123456789abcdef";
|
||||
+ char hexchars[] = "0123456789abcdef";
|
||||
int offset = 0;
|
||||
- UINTN i;
|
||||
- UINTN j;
|
||||
+ unsigned long i;
|
||||
+ unsigned long j;
|
||||
+ unsigned long ret;
|
||||
|
||||
- for (i = 0; i < sz; i++) {
|
||||
- buf[offset++] = L' ';
|
||||
- buf[offset++] = L' ';
|
||||
- buf[offset++] = L' ';
|
||||
+ unsigned long before = (position % 16);
|
||||
+ unsigned long after = (before+size >= 16) ? 0 : 16 - (before+size);
|
||||
+
|
||||
+ for (i = 0; i < before; i++) {
|
||||
+ buf[offset++] = 'X';
|
||||
+ buf[offset++] = 'X';
|
||||
+ buf[offset++] = ' ';
|
||||
if (i == 7)
|
||||
- buf[offset++] = L' ';
|
||||
+ buf[offset++] = ' ';
|
||||
}
|
||||
- for (j = sz; j < 16 && j < size; j++) {
|
||||
- UINT8 d = data[j-sz];
|
||||
+ for (j = 0; j < 16 - after - before; j++) {
|
||||
+ uint8_t d = ((uint8_t *)data)[j];
|
||||
buf[offset++] = hexchars[(d & 0xf0) >> 4];
|
||||
buf[offset++] = hexchars[(d & 0x0f)];
|
||||
- if (j != 15)
|
||||
- buf[offset++] = L' ';
|
||||
- if (j == 7)
|
||||
- buf[offset++] = L' ';
|
||||
+ if (i+j != 15)
|
||||
+ buf[offset++] = ' ';
|
||||
+ if (i+j == 7)
|
||||
+ buf[offset++] = ' ';
|
||||
}
|
||||
- for (i = j; i < 16; i++) {
|
||||
- buf[offset++] = L' ';
|
||||
- buf[offset++] = L' ';
|
||||
- if (i != 15)
|
||||
- buf[offset++] = L' ';
|
||||
- if (i == 7)
|
||||
- buf[offset++] = L' ';
|
||||
+ ret = 16 - after - before;
|
||||
+ j += i;
|
||||
+ for (i = 0; i < after; i++) {
|
||||
+ buf[offset++] = 'X';
|
||||
+ buf[offset++] = 'X';
|
||||
+ if (i+j != 15)
|
||||
+ buf[offset++] = ' ';
|
||||
+ if (i+j == 7)
|
||||
+ buf[offset++] = ' ';
|
||||
}
|
||||
- buf[offset] = L'\0';
|
||||
- return j - sz;
|
||||
+ buf[offset] = '\0';
|
||||
+ return ret;
|
||||
}
|
||||
|
||||
-static void
|
||||
-__attribute__((__unused__))
|
||||
-format_text(UINT8 *data, UINTN size, CHAR16 *buf)
|
||||
+#define isprint(c) ((c) >= 0x20 && (c) <= 0x7e)
|
||||
+
|
||||
+static inline void UNUSED
|
||||
+prepare_text(const void *data, size_t size, char *buf, int position)
|
||||
{
|
||||
- UINTN sz = (UINTN)data % 16;
|
||||
int offset = 0;
|
||||
- UINTN i;
|
||||
- UINTN j;
|
||||
+ unsigned long i;
|
||||
+ unsigned long j;
|
||||
|
||||
- for (i = 0; i < sz; i++)
|
||||
- buf[offset++] = L' ';
|
||||
- buf[offset++] = L'|';
|
||||
- for (j = sz; j < 16 && j < size; j++) {
|
||||
- if (isprint(data[j-sz]))
|
||||
- buf[offset++] = data[j-sz];
|
||||
+ unsigned long before = position % 16;
|
||||
+ unsigned long after = (before+size > 16) ? 0 : 16 - (before+size);
|
||||
+
|
||||
+ if (size == 0) {
|
||||
+ buf[0] = '\0';
|
||||
+ return;
|
||||
+ }
|
||||
+ for (i = 0; i < before; i++)
|
||||
+ buf[offset++] = 'X';
|
||||
+ buf[offset++] = '|';
|
||||
+ for (j = 0; j < 16 - after - before; j++) {
|
||||
+ if (isprint(((uint8_t *)data)[j]))
|
||||
+ buf[offset++] = ((uint8_t *)data)[j];
|
||||
else
|
||||
- buf[offset++] = L'.';
|
||||
+ buf[offset++] = '.';
|
||||
}
|
||||
- buf[offset++] = L'|';
|
||||
- for (i = j; i < 16; i++)
|
||||
- buf[offset++] = L' ';
|
||||
- buf[offset] = L'\0';
|
||||
+ buf[offset++] = size > 0 ? '|' : 'X';
|
||||
+ buf[offset] = '\0';
|
||||
}
|
||||
|
||||
-static void
|
||||
-__attribute__((__unused__))
|
||||
-hexdump(UINT8 *data, UINTN size)
|
||||
+/*
|
||||
+ * variadic hexdump formatted
|
||||
+ * think of it as: printf("%s%s\n", vformat(fmt, ap), hexdump(data,size));
|
||||
+ */
|
||||
+static inline void UNUSED
|
||||
+vhexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt, const void *data, unsigned long size, size_t at, va_list ap)
|
||||
{
|
||||
- UINTN display_offset = (UINTN)data & 0xffffffff;
|
||||
- UINTN offset = 0;
|
||||
- //console_print(L"hexdump: data=0x%016x size=0x%x\n", data, size);
|
||||
+ unsigned long display_offset = at;
|
||||
+ unsigned long offset = 0;
|
||||
|
||||
while (offset < size) {
|
||||
- CHAR16 hexbuf[49];
|
||||
- CHAR16 txtbuf[19];
|
||||
- UINTN sz;
|
||||
+ char hexbuf[49];
|
||||
+ char txtbuf[19];
|
||||
+ unsigned long sz;
|
||||
|
||||
- sz = format_hex(data+offset, size-offset, hexbuf);
|
||||
+ sz = prepare_hex(data+offset, size-offset, hexbuf,
|
||||
+ (unsigned long)data+offset);
|
||||
if (sz == 0)
|
||||
return;
|
||||
- msleep(200000);
|
||||
|
||||
- format_text(data+offset, size-offset, txtbuf);
|
||||
- console_print(L"%08x %s %s\n", display_offset, hexbuf, txtbuf);
|
||||
- msleep(200000);
|
||||
+ prepare_text(data+offset, size-offset, txtbuf,
|
||||
+ (unsigned long)data+offset);
|
||||
+ if (fmt && fmt[0] != 0)
|
||||
+ vdprint_(fmt, file, line, func, ap);
|
||||
+ dprint_(L"%a:%d:%a() %08lx %a %a\n", file, line, func, display_offset, hexbuf, txtbuf);
|
||||
|
||||
display_offset += sz;
|
||||
offset += sz;
|
||||
}
|
||||
}
|
||||
|
||||
+/*
|
||||
+ * hexdump formatted
|
||||
+ * think of it as: printf("%s%s", format(fmt, ...), hexdump(data,size)[lineN]);
|
||||
+ */
|
||||
+static inline void UNUSED
|
||||
+hexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt, const void *data, unsigned long size, size_t at, ...)
|
||||
+{
|
||||
+ va_list ap;
|
||||
+
|
||||
+ va_start(ap, at);
|
||||
+ vhexdumpf(file, line, func, fmt, data, size, at, ap);
|
||||
+ va_end(ap);
|
||||
+}
|
||||
+
|
||||
+static inline void UNUSED
|
||||
+hexdump(const char *file, int line, const char *func, const void *data, unsigned long size)
|
||||
+{
|
||||
+ hexdumpf(file, line, func, L"", data, size, (intptr_t)data);
|
||||
+}
|
||||
+
|
||||
+static inline void UNUSED
|
||||
+hexdumpat(const char *file, int line, const char *func, const void *data, unsigned long size, size_t at)
|
||||
+{
|
||||
+ hexdumpf(file, line, func, L"", data, size, at);
|
||||
+}
|
||||
+
|
||||
+#define LogHexdump(data, sz) LogHexdump_(__FILE__, __LINE__, __func__, data, sz)
|
||||
+#define dhexdump(data, sz) hexdump(__FILE__, __LINE__, __func__, data, sz)
|
||||
+#define dhexdumpat(data, sz, at) hexdumpat(__FILE__, __LINE__, __func__, data, sz, at)
|
||||
+#define dhexdumpf(fmt, data, sz, at, ...) hexdumpf(__FILE__, __LINE__, __func__, fmt, data, sz, at, ##__VA_ARGS__)
|
||||
+
|
||||
#endif /* STATIC_HEXDUMP_H */
|
||||
+// vim:fenc=utf-8:tw=75:noet
|
||||
diff --git a/shim.h b/shim.h
|
||||
index c1d7e7c7197..0b3ad4f2d20 100644
|
||||
--- a/shim.h
|
||||
+++ b/shim.h
|
||||
@@ -182,8 +182,9 @@ typedef struct _SHIM_LOCK {
|
||||
|
||||
extern EFI_STATUS shim_init(void);
|
||||
extern void shim_fini(void);
|
||||
-extern EFI_STATUS LogError_(const char *file, int line, const char *func, CHAR16 *fmt, ...);
|
||||
-extern EFI_STATUS VLogError(const char *file, int line, const char *func, CHAR16 *fmt, va_list args);
|
||||
+extern EFI_STATUS LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...);
|
||||
+extern EFI_STATUS VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_list args);
|
||||
+extern VOID LogHexdump_(const char *file, int line, const char *func, const void *data, size_t sz);
|
||||
extern VOID PrintErrors(VOID);
|
||||
extern VOID ClearErrors(VOID);
|
||||
extern EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath);
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,352 +0,0 @@
|
||||
From fecc2dfb8e408526221091923d9345796b8e294e Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 23 Jul 2020 22:09:03 -0400
|
||||
Subject: [PATCH 61/62] Also use a config table to mirror mok variables.
|
||||
|
||||
Everything was going just fine until I made a vendor_db with 17kB of
|
||||
sha256 sums in it. And then the same source tree that had worked fine
|
||||
without that threw errors and failed all over the place. I wrote some
|
||||
code to diagnose the problem, and of course it was a failure in
|
||||
mirroring MokList to MokListRT.
|
||||
|
||||
As Patrick noted in 741c61abba7, some systems have obnoxiously low
|
||||
amounts of variable storage available:
|
||||
|
||||
mok.c:550:import_mok_state() BS+RT variable info:
|
||||
MaximumVariableStorageSize:0x000000000000DFE4
|
||||
RemainingVariableStorageSize:0x000000000000D21C
|
||||
MaximumVariableSize:0x0000000000001FC4
|
||||
|
||||
The most annoying part is that on at least this edk2 build,
|
||||
SetVariable() /does actually appear to set the variable/, but it returns
|
||||
EFI_INVALID_PARAMETER. I'm not planning on relying on that behavior.
|
||||
|
||||
So... yeah, the largest *volatile* (i.e. RAM only) variable this edk2
|
||||
build will let you create is less than two pages. It's only got 7.9G
|
||||
free, so I guess it's feeling like space is a little tight.
|
||||
|
||||
We're also not quite preserving that return code well enough for his
|
||||
workaround to work.
|
||||
|
||||
New plan. We try to create variables the normal way, but we don't
|
||||
consider not having enough space to be fatal. In that case, we create
|
||||
an EFI_SECURITY_LIST with one sha256sum in it, with a value of all 0,
|
||||
and try to add that so we're sure there's /something/ there that's
|
||||
innocuous. On systems where the first SetVariable() /
|
||||
QueryVariableInfo() lied to us, the correct variable should be there,
|
||||
otherwise the one with the zero-hash will be.
|
||||
|
||||
We then also build a config table to hold this info and install that.
|
||||
|
||||
The config table is a packed array of this struct:
|
||||
|
||||
struct mok_variable_config_entry {
|
||||
CHAR8 name[256];
|
||||
UINT64 data_size;
|
||||
UINT8 data[];
|
||||
};
|
||||
|
||||
There will be N+1 entries, and the last entry is all 0 for name and
|
||||
data_size. The total allocation size will always be a multiple of 4096.
|
||||
In the typical RHEL 7.9 case that means it'll be around 5 pages.
|
||||
|
||||
It's installed with this guid:
|
||||
|
||||
c451ed2b-9694-45d3-baba-ed9f8988a389
|
||||
|
||||
Anything that can go wrong will.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
Upstream: not yet, I don't want people to read this before Wednesday.
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
---
|
||||
lib/guid.c | 2 +
|
||||
mok.c | 150 ++++++++++++++++++++++++++++++++++++++++++++-----
|
||||
include/guid.h | 2 +
|
||||
3 files changed, 140 insertions(+), 14 deletions(-)
|
||||
|
||||
diff --git a/lib/guid.c b/lib/guid.c
|
||||
index 57c02fbeecd..99ff400a0ab 100644
|
||||
--- a/lib/guid.c
|
||||
+++ b/lib/guid.c
|
||||
@@ -36,4 +36,6 @@ EFI_GUID EFI_SECURE_BOOT_DB_GUID = { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc,
|
||||
EFI_GUID EFI_SIMPLE_FILE_SYSTEM_GUID = SIMPLE_FILE_SYSTEM_PROTOCOL;
|
||||
EFI_GUID SECURITY_PROTOCOL_GUID = { 0xA46423E3, 0x4617, 0x49f1, {0xB9, 0xFF, 0xD1, 0xBF, 0xA9, 0x11, 0x58, 0x39 } };
|
||||
EFI_GUID SECURITY2_PROTOCOL_GUID = { 0x94ab2f58, 0x1438, 0x4ef1, {0x91, 0x52, 0x18, 0x94, 0x1a, 0x3a, 0x0e, 0x68 } };
|
||||
+
|
||||
EFI_GUID SHIM_LOCK_GUID = {0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } };
|
||||
+EFI_GUID MOK_VARIABLE_STORE = {0xc451ed2b, 0x9694, 0x45d3, {0xba, 0xba, 0xed, 0x9f, 0x89, 0x88, 0xa3, 0x89} };
|
||||
diff --git a/mok.c b/mok.c
|
||||
index e69857f3c37..4e141fb21fc 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -68,6 +68,7 @@ struct mok_state_variable {
|
||||
CHAR16 *name;
|
||||
char *name8;
|
||||
CHAR16 *rtname;
|
||||
+ char *rtname8;
|
||||
EFI_GUID *guid;
|
||||
|
||||
UINT8 *data;
|
||||
@@ -121,6 +122,7 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{.name = L"MokList",
|
||||
.name8 = "MokList",
|
||||
.rtname = L"MokListRT",
|
||||
+ .rtname8 = "MokListRT",
|
||||
.guid = &SHIM_LOCK_GUID,
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
@@ -133,12 +135,14 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
.build_cert_size = &build_cert_size,
|
||||
#endif /* defined(ENABLE_SHIM_CERT) */
|
||||
.flags = MOK_MIRROR_KEYDB |
|
||||
+ MOK_MIRROR_DELETE_FIRST |
|
||||
MOK_VARIABLE_LOG,
|
||||
.pcr = 14,
|
||||
},
|
||||
{.name = L"MokListX",
|
||||
.name8 = "MokListX",
|
||||
.rtname = L"MokListXRT",
|
||||
+ .rtname8 = "MokListXRT",
|
||||
.guid = &SHIM_LOCK_GUID,
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
@@ -147,12 +151,14 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
.addend = &vendor_deauthorized,
|
||||
.addend_size = &vendor_deauthorized_size,
|
||||
.flags = MOK_MIRROR_KEYDB |
|
||||
+ MOK_MIRROR_DELETE_FIRST |
|
||||
MOK_VARIABLE_LOG,
|
||||
.pcr = 14,
|
||||
},
|
||||
{.name = L"MokSBState",
|
||||
.name8 = "MokSBState",
|
||||
.rtname = L"MokSBStateRT",
|
||||
+ .rtname8 = "MokSBStateRT",
|
||||
.guid = &SHIM_LOCK_GUID,
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
@@ -166,6 +172,7 @@ struct mok_state_variable mok_state_variables[] = {
|
||||
{.name = L"MokDBState",
|
||||
.name8 = "MokDBState",
|
||||
.rtname = L"MokIgnoreDB",
|
||||
+ .rtname8 = "MokIgnoreDB",
|
||||
.guid = &SHIM_LOCK_GUID,
|
||||
.yes_attr = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_NON_VOLATILE,
|
||||
@@ -204,6 +211,7 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
* we're always mirroring the original data, whether this is an efi
|
||||
* security database or not
|
||||
*/
|
||||
+ dprint(L"v->name:\"%s\" v->rtname:\"%s\"\n", v->name, v->rtname);
|
||||
dprint(L"v->data_size:%lu v->data:0x%08llx\n", v->data_size, v->data);
|
||||
dprint(L"FullDataSize:%lu FullData:0x%08llx\n", FullDataSize, FullData);
|
||||
if (v->data_size) {
|
||||
@@ -299,6 +307,7 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
}
|
||||
}
|
||||
|
||||
+
|
||||
/*
|
||||
* Now we have the full size
|
||||
*/
|
||||
@@ -417,28 +426,72 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
}
|
||||
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%016llx p:0x%016llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
if (FullDataSize) {
|
||||
- dprint(L"Setting %s with %lu bytes of data\n",
|
||||
- v->rtname, FullDataSize);
|
||||
+ uint32_t attrs = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
+ EFI_VARIABLE_RUNTIME_ACCESS;
|
||||
+ uint64_t max_storage_sz = 0;
|
||||
+ uint64_t remaining_sz = 0;
|
||||
+ uint64_t max_var_sz = 0;
|
||||
+ UINT8 *tmp = NULL;
|
||||
+ UINTN tmpsz = 0;
|
||||
+
|
||||
+ efi_status = gRT->QueryVariableInfo(attrs, &max_storage_sz,
|
||||
+ &remaining_sz, &max_var_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not get variable storage info: %r\n", efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ dprint(L"calling SetVariable(\"%s\", 0x%016llx, 0x%08lx, %lu, 0x%016llx)\n",
|
||||
+ v->rtname, v->guid,
|
||||
+ EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
+ | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
+ FullDataSize, FullData);
|
||||
efi_status = gRT->SetVariable(v->rtname, v->guid,
|
||||
- EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
- EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
+ EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
+ | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
FullDataSize, FullData);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Failed to set %s: %r\n",
|
||||
- v->rtname, efi_status);
|
||||
+ if (efi_status == EFI_INVALID_PARAMETER && max_var_sz < FullDataSize) {
|
||||
+ /*
|
||||
+ * In this case we're going to try to create a
|
||||
+ * dummy variable so that there's one there. It
|
||||
+ * may or may not work, because on some firmware
|
||||
+ * builds when the SetVariable call above fails it
|
||||
+ * does actually set the variable(!), so aside from
|
||||
+ * not using the allocation if it doesn't work, we
|
||||
+ * don't care about failures here.
|
||||
+ */
|
||||
+ console_print(L"WARNING: Maximum volatile variable size is %lu.\n", max_var_sz);
|
||||
+ console_print(L"WARNING: Cannot set %s (%lu bytes)\n", v->rtname, FullDataSize);
|
||||
+ perror(L"Failed to set %s: %r\n", v->rtname, efi_status);
|
||||
+ efi_status = variable_create_esl(
|
||||
+ null_sha256, sizeof(null_sha256),
|
||||
+ &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID,
|
||||
+ &tmp, &tmpsz);
|
||||
+ /*
|
||||
+ * from here we don't really care if it works or
|
||||
+ * doens't.
|
||||
+ */
|
||||
+ if (!EFI_ERROR(efi_status) && tmp && tmpsz) {
|
||||
+ gRT->SetVariable(v->rtname, v->guid,
|
||||
+ EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
+ | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
+ tmpsz, tmp);
|
||||
+ FreePool(tmp);
|
||||
+ }
|
||||
+ efi_status = EFI_INVALID_PARAMETER;
|
||||
+ } else if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to set %s: %r\n", v->rtname, efi_status);
|
||||
}
|
||||
}
|
||||
- if (v->data && v->data_size) {
|
||||
+ if (v->data && v->data_size && v->data != FullData) {
|
||||
FreePool(v->data);
|
||||
v->data = NULL;
|
||||
v->data_size = 0;
|
||||
}
|
||||
- if (FullData && FullDataSize) {
|
||||
- FreePool(FullData);
|
||||
- }
|
||||
+ v->data = FullData;
|
||||
+ v->data_size = FullDataSize;
|
||||
dprint(L"returning %r\n", efi_status);
|
||||
return efi_status;
|
||||
}
|
||||
@@ -454,8 +507,11 @@ maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
BOOLEAN present = FALSE;
|
||||
|
||||
if (v->rtname) {
|
||||
- if (v->flags & MOK_MIRROR_DELETE_FIRST)
|
||||
- LibDeleteVariable(v->rtname, v->guid);
|
||||
+ if (v->flags & MOK_MIRROR_DELETE_FIRST) {
|
||||
+ dprint(L"deleting \"%s\"\n", v->rtname);
|
||||
+ efi_status = LibDeleteVariable(v->rtname, v->guid);
|
||||
+ dprint(L"LibDeleteVariable(\"%s\",...) => %r\n", v->rtname, efi_status);
|
||||
+ }
|
||||
|
||||
efi_status = mirror_one_mok_variable(v);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
@@ -505,6 +561,12 @@ maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
+struct mok_variable_config_entry {
|
||||
+ CHAR8 name[256];
|
||||
+ UINT64 data_size;
|
||||
+ UINT8 data[];
|
||||
+};
|
||||
+
|
||||
/*
|
||||
* Verify our non-volatile MoK state. This checks the variables above
|
||||
* accessable and have valid attributes. If they don't, it removes
|
||||
@@ -527,6 +589,11 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
user_insecure_mode = 0;
|
||||
ignore_db = 0;
|
||||
|
||||
+ UINT64 config_sz = 0;
|
||||
+ UINT8 *config_table = NULL;
|
||||
+ size_t npages = 0;
|
||||
+ struct mok_variable_config_entry config_template;
|
||||
+
|
||||
dprint(L"importing mok state\n");
|
||||
for (i = 0; mok_state_variables[i].name != NULL; i++) {
|
||||
struct mok_state_variable *v = &mok_state_variables[i];
|
||||
@@ -579,6 +646,61 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
}
|
||||
|
||||
ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
+ if (v->data && v->data_size) {
|
||||
+ config_sz += v->data_size;
|
||||
+ config_sz += sizeof(config_template);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Alright, so we're going to copy these to a config table. The
|
||||
+ * table is a packed array of N+1 struct mok_variable_config_entry
|
||||
+ * items, with the last item having all zero's in name and
|
||||
+ * data_size.
|
||||
+ */
|
||||
+ if (config_sz) {
|
||||
+ config_sz += sizeof(config_template);
|
||||
+ npages = ALIGN_VALUE(config_sz, PAGE_SIZE) >> EFI_PAGE_SHIFT;
|
||||
+ config_table = NULL;
|
||||
+ efi_status = gBS->AllocatePages(AllocateAnyPages,
|
||||
+ EfiRuntimeServicesData,
|
||||
+ npages,
|
||||
+ (EFI_PHYSICAL_ADDRESS *)&config_table);
|
||||
+ if (EFI_ERROR(efi_status) || !config_table) {
|
||||
+ console_print(L"Allocating %lu pages for mok config table failed: %r\n",
|
||||
+ npages, efi_status);
|
||||
+ if (ret != EFI_SECURITY_VIOLATION)
|
||||
+ ret = efi_status;
|
||||
+ config_table = NULL;
|
||||
+ } else {
|
||||
+ ZeroMem(config_table, npages << EFI_PAGE_SHIFT);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ UINT8 *p = (UINT8 *)config_table;
|
||||
+ for (i = 0; p && mok_state_variables[i].name != NULL; i++) {
|
||||
+ struct mok_state_variable *v = &mok_state_variables[i];
|
||||
+
|
||||
+ ZeroMem(&config_template, sizeof(config_template));
|
||||
+ strncpya(config_template.name, (CHAR8 *)v->rtname8, 255);
|
||||
+ config_template.name[255] = '\0';
|
||||
+
|
||||
+ config_template.data_size = v->data_size;
|
||||
+
|
||||
+ CopyMem(p, &config_template, sizeof(config_template));
|
||||
+ p += sizeof(config_template);
|
||||
+ CopyMem(p, v->data, v->data_size);
|
||||
+ p += v->data_size;
|
||||
+ }
|
||||
+ if (p) {
|
||||
+ ZeroMem(&config_template, sizeof(config_template));
|
||||
+ CopyMem(p, &config_template, sizeof(config_template));
|
||||
+
|
||||
+ efi_status = gBS->InstallConfigurationTable(&MOK_VARIABLE_STORE,
|
||||
+ config_table);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ console_print(L"Couldn't install MoK configuration table\n");
|
||||
+ }
|
||||
}
|
||||
|
||||
/*
|
||||
diff --git a/include/guid.h b/include/guid.h
|
||||
index 81689d6cc1a..91b14d96146 100644
|
||||
--- a/include/guid.h
|
||||
+++ b/include/guid.h
|
||||
@@ -35,4 +35,6 @@ extern EFI_GUID SECURITY_PROTOCOL_GUID;
|
||||
extern EFI_GUID SECURITY2_PROTOCOL_GUID;
|
||||
extern EFI_GUID SHIM_LOCK_GUID;
|
||||
|
||||
+extern EFI_GUID MOK_VARIABLE_STORE;
|
||||
+
|
||||
#endif /* SHIM_GUID_H */
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,991 +0,0 @@
|
||||
From 65be350308783a8ef537246c8ad0545b4e6ad069 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Sat, 25 Jul 2020 22:13:57 -0400
|
||||
Subject: [PATCH 62/62] Implement lennysz's suggestions for MokListRT
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
---
|
||||
mok.c | 726 ++++++++++++++++++++++++++++++++--------------
|
||||
shim.c | 7 +-
|
||||
include/PeImage.h | 3 +-
|
||||
3 files changed, 515 insertions(+), 221 deletions(-)
|
||||
|
||||
diff --git a/mok.c b/mok.c
|
||||
index 4e141fb21fc..3e6c7e43025 100644
|
||||
--- a/mok.c
|
||||
+++ b/mok.c
|
||||
@@ -7,6 +7,8 @@
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
+#include "hexdump.h"
|
||||
+
|
||||
/*
|
||||
* Check if a variable exists
|
||||
*/
|
||||
@@ -25,6 +27,15 @@ static BOOLEAN check_var(CHAR16 *varname)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
+#define SetVariable(name, guid, attrs, varsz, var) ({ \
|
||||
+ EFI_STATUS efi_status_; \
|
||||
+ efi_status_ = gRT->SetVariable(name, guid, attrs, varsz, var); \
|
||||
+ dprint_(L"%a:%d:%a() SetVariable(\"%s\", ... varsz=0x%llx) = %r\n",\
|
||||
+ __FILE__, __LINE__, __func__, \
|
||||
+ name, varsz, efi_status_); \
|
||||
+ efi_status_; \
|
||||
+})
|
||||
+
|
||||
/*
|
||||
* If the OS has set any of these variables we need to drop into MOK and
|
||||
* handle them appropriately
|
||||
@@ -193,33 +204,296 @@ should_mirror_build_cert(struct mok_state_variable *v)
|
||||
|
||||
static const uint8_t null_sha256[32] = { 0, };
|
||||
|
||||
+typedef UINTN SIZE_T;
|
||||
+
|
||||
+static EFI_STATUS
|
||||
+get_max_var_sz(UINT32 attrs, SIZE_T *max_var_szp)
|
||||
+{
|
||||
+ EFI_STATUS efi_status;
|
||||
+ uint64_t max_storage_sz = 0;
|
||||
+ uint64_t remaining_sz = 0;
|
||||
+ uint64_t max_var_sz = 0;
|
||||
+
|
||||
+ *max_var_szp = 0;
|
||||
+ efi_status = gRT->QueryVariableInfo(attrs, &max_storage_sz,
|
||||
+ &remaining_sz, &max_var_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not get variable storage info: %r\n", efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * I just don't trust implementations to not be showing static data
|
||||
+ * for max_var_sz
|
||||
+ */
|
||||
+ *max_var_szp = (max_var_sz < remaining_sz) ? max_var_sz : remaining_sz;
|
||||
+ dprint("max_var_sz:%lx remaining_sz:%lx max_storage_sz:%lx\n",
|
||||
+ max_var_sz, remaining_sz, max_storage_sz);
|
||||
+ return efi_status;
|
||||
+}
|
||||
+
|
||||
+/*
|
||||
+ * If any entries fit in < maxsz, and nothing goes wrong, create a variable
|
||||
+ * of the given name and guid with as many esd entries as possible in it,
|
||||
+ * and updates *esdp with what would be the next entry (even if makes *esdp
|
||||
+ * > esl+esl->SignatureListSize), and returns whatever SetVariable()
|
||||
+ * returns
|
||||
+ *
|
||||
+ * If no entries fit (i.e. sizeof(esl) + esl->SignatureSize > maxsz),
|
||||
+ * returns EFI_BUFFER_TOO_SMALL;
|
||||
+ */
|
||||
+static EFI_STATUS
|
||||
+mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs,
|
||||
+ EFI_SIGNATURE_LIST *esl, EFI_SIGNATURE_DATA *esd,
|
||||
+ UINTN *newsz, SIZE_T maxsz)
|
||||
+{
|
||||
+ EFI_STATUS efi_status;
|
||||
+ SIZE_T howmany, varsz = 0, esdsz;
|
||||
+ UINT8 *var, *data;
|
||||
+
|
||||
+ howmany = min((maxsz - sizeof(*esl)) / esl->SignatureSize,
|
||||
+ (esl->SignatureListSize - sizeof(*esl)) / esl->SignatureSize);
|
||||
+ if (howmany < 1) {
|
||||
+ return EFI_BUFFER_TOO_SMALL;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * We always assume esl->SignatureHeaderSize is 0 (and so far,
|
||||
+ * that's true as per UEFI 2.8)
|
||||
+ */
|
||||
+ esdsz = howmany * esl->SignatureSize;
|
||||
+ data = (UINT8 *)esd;
|
||||
+ dprint(L"Trying to add %lx signatures to \"%s\" of size %lx\n",
|
||||
+ howmany, name, esl->SignatureSize);
|
||||
+
|
||||
+ /*
|
||||
+ * Because of the semantics of variable_create_esl(), the first
|
||||
+ * owner guid from the data is not part of esdsz, or the data.
|
||||
+ *
|
||||
+ * Compensate here.
|
||||
+ */
|
||||
+ efi_status = variable_create_esl(data + sizeof(EFI_GUID),
|
||||
+ esdsz - sizeof(EFI_GUID),
|
||||
+ &esl->SignatureType,
|
||||
+ &esd->SignatureOwner,
|
||||
+ &var, &varsz);
|
||||
+ if (EFI_ERROR(efi_status) || !var || !varsz) {
|
||||
+ LogError(L"Couldn't allocate %lu bytes for mok variable \"%s\": %r\n",
|
||||
+ varsz, var, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ dprint(L"new esl:\n");
|
||||
+ dhexdumpat(var, varsz, 0);
|
||||
+
|
||||
+ efi_status = SetVariable(name, guid, attrs, varsz, var);
|
||||
+ FreePool(var);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ LogError(L"Couldn't create mok variable \"%s\": %r\n",
|
||||
+ varsz, var, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ *newsz = esdsz;
|
||||
+
|
||||
+ return efi_status;
|
||||
+}
|
||||
+
|
||||
+static EFI_STATUS
|
||||
+mirror_mok_db(CHAR16 *name, CHAR8 *name8, EFI_GUID *guid, UINT32 attrs,
|
||||
+ UINT8 *FullData, SIZE_T FullDataSize, BOOLEAN only_first)
|
||||
+{
|
||||
+ EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
+ SIZE_T max_var_sz;
|
||||
+
|
||||
+ if (only_first) {
|
||||
+ efi_status = get_max_var_sz(attrs, &max_var_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ LogError(L"Could not get maximum variable size: %r",
|
||||
+ efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ if (FullDataSize <= max_var_sz) {
|
||||
+ efi_status = SetVariable(name, guid, attrs,
|
||||
+ FullDataSize, FullData);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ CHAR16 *namen;
|
||||
+ CHAR8 *namen8;
|
||||
+ UINTN namelen, namesz;
|
||||
+
|
||||
+ namelen = StrLen(name);
|
||||
+ namesz = namelen * 2;
|
||||
+ if (only_first) {
|
||||
+ namen = name;
|
||||
+ namen8 = name8;
|
||||
+ } else {
|
||||
+ namelen += 18;
|
||||
+ namesz += 34;
|
||||
+ namen = AllocateZeroPool(namesz);
|
||||
+ if (!namen) {
|
||||
+ LogError(L"Could not allocate %lu bytes", namesz);
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+ }
|
||||
+ namen8 = AllocateZeroPool(namelen);
|
||||
+ if (!namen8) {
|
||||
+ FreePool(namen);
|
||||
+ LogError(L"Could not allocate %lu bytes", namelen);
|
||||
+ return EFI_OUT_OF_RESOURCES;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ UINTN pos, i;
|
||||
+ const SIZE_T minsz = sizeof(EFI_SIGNATURE_LIST)
|
||||
+ + sizeof(EFI_SIGNATURE_DATA)
|
||||
+ + SHA1_DIGEST_SIZE;
|
||||
+ BOOLEAN did_one = FALSE;
|
||||
+
|
||||
+ /*
|
||||
+ * Create any entries that can fit.
|
||||
+ */
|
||||
+ if (!only_first) {
|
||||
+ dprint(L"full data for \"%s\":\n", name);
|
||||
+ dhexdumpat(FullData, FullDataSize, 0);
|
||||
+ }
|
||||
+ EFI_SIGNATURE_LIST *esl = NULL;
|
||||
+ UINTN esl_end_pos = 0;
|
||||
+ for (i = 0, pos = 0; FullDataSize - pos >= minsz && FullData; ) {
|
||||
+ EFI_SIGNATURE_DATA *esd = NULL;
|
||||
+
|
||||
+ dprint(L"pos:0x%llx FullDataSize:0x%llx\n", pos, FullDataSize);
|
||||
+ if (esl == NULL || pos >= esl_end_pos) {
|
||||
+ UINT8 *nesl = FullData + pos;
|
||||
+ dprint(L"esl:0x%llx->0x%llx\n", esl, nesl);
|
||||
+ esl = (EFI_SIGNATURE_LIST *)nesl;
|
||||
+ esl_end_pos = pos + esl->SignatureListSize;
|
||||
+ dprint(L"pos:0x%llx->0x%llx\n", pos, pos + sizeof(*esl));
|
||||
+ pos += sizeof(*esl);
|
||||
+ }
|
||||
+ esd = (EFI_SIGNATURE_DATA *)(FullData + pos);
|
||||
+ if (pos >= FullDataSize)
|
||||
+ break;
|
||||
+ if (esl->SignatureListSize == 0 || esl->SignatureSize == 0)
|
||||
+ break;
|
||||
+
|
||||
+ dprint(L"esl[%lu] 0x%llx = {sls=0x%lx, ss=0x%lx} esd:0x%llx\n",
|
||||
+ i, esl, esl->SignatureListSize, esl->SignatureSize, esd);
|
||||
+
|
||||
+ if (!only_first) {
|
||||
+ SPrint(namen, namelen, L"%s%lu", name, i);
|
||||
+ namen[namelen-1] = 0;
|
||||
+ /* uggggh */
|
||||
+ UINTN j;
|
||||
+ for (j = 0; j < namelen; j++)
|
||||
+ namen8[j] = (CHAR8)(namen[j] & 0xff);
|
||||
+ namen8[namelen - 1] = 0;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * In case max_var_sz is computed dynamically, refresh the
|
||||
+ * value here.
|
||||
+ */
|
||||
+ efi_status = get_max_var_sz(attrs, &max_var_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ LogError(L"Could not get maximum variable size: %r",
|
||||
+ efi_status);
|
||||
+ if (!only_first) {
|
||||
+ FreePool(namen);
|
||||
+ FreePool(namen8);
|
||||
+ }
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+
|
||||
+ SIZE_T howmany;
|
||||
+ UINTN adj = 0;
|
||||
+ howmany = min((max_var_sz - sizeof(*esl)) / esl->SignatureSize,
|
||||
+ (esl->SignatureListSize - sizeof(*esl)) / esl->SignatureSize);
|
||||
+ if (!only_first && i == 0 && howmany >= 1) {
|
||||
+ adj = howmany * esl->SignatureSize;
|
||||
+ dprint(L"pos:0x%llx->0x%llx\n", pos, pos + adj);
|
||||
+ pos += adj;
|
||||
+ i++;
|
||||
+ continue;
|
||||
+
|
||||
+ }
|
||||
+
|
||||
+ efi_status = mirror_one_esl(namen, guid, attrs,
|
||||
+ esl, esd, &adj, max_var_sz);
|
||||
+ dprint(L"esd:0x%llx adj:0x%llx\n", esd, adj);
|
||||
+ if (EFI_ERROR(efi_status) && efi_status != EFI_BUFFER_TOO_SMALL) {
|
||||
+ LogError(L"Could not mirror mok variable \"%s\": %r\n",
|
||||
+ namen, efi_status);
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ if (!EFI_ERROR(efi_status)) {
|
||||
+ did_one = TRUE;
|
||||
+ if (only_first)
|
||||
+ break;
|
||||
+ dprint(L"pos:0x%llx->0x%llx\n", pos, pos + adj);
|
||||
+ pos += adj;
|
||||
+ i++;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (only_first && !did_one) {
|
||||
+ /*
|
||||
+ * In this case we're going to try to create a
|
||||
+ * dummy variable so that there's one there. It
|
||||
+ * may or may not work, because on some firmware
|
||||
+ * builds when the SetVariable call above fails it
|
||||
+ * does actually set the variable(!), so aside from
|
||||
+ * not using the allocation if it doesn't work, we
|
||||
+ * don't care about failures here.
|
||||
+ */
|
||||
+ UINT8 *var;
|
||||
+ UINTN varsz;
|
||||
+
|
||||
+ efi_status = variable_create_esl(
|
||||
+ null_sha256, sizeof(null_sha256),
|
||||
+ &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID,
|
||||
+ &var, &varsz);
|
||||
+ /*
|
||||
+ * from here we don't really care if it works or
|
||||
+ * doesn't.
|
||||
+ */
|
||||
+ if (!EFI_ERROR(efi_status) && var && varsz) {
|
||||
+ SetVariable(name, guid,
|
||||
+ EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
+ | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
+ varsz, var);
|
||||
+ FreePool(var);
|
||||
+ }
|
||||
+ efi_status = EFI_INVALID_PARAMETER;
|
||||
+ } else if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to set %s: %r\n", name, efi_status);
|
||||
+ }
|
||||
+ return efi_status;
|
||||
+}
|
||||
+
|
||||
+
|
||||
static EFI_STATUS nonnull(1)
|
||||
-mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
+mirror_one_mok_variable(struct mok_state_variable *v,
|
||||
+ BOOLEAN only_first)
|
||||
{
|
||||
EFI_STATUS efi_status = EFI_SUCCESS;
|
||||
uint8_t *FullData = NULL;
|
||||
size_t FullDataSize = 0;
|
||||
vendor_addend_category_t addend_category = VENDOR_ADDEND_NONE;
|
||||
uint8_t *p = NULL;
|
||||
-
|
||||
+ uint32_t attrs = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
+ EFI_VARIABLE_RUNTIME_ACCESS;
|
||||
+ BOOLEAN measure = v->flags & MOK_VARIABLE_MEASURE;
|
||||
+ BOOLEAN log = v->flags & MOK_VARIABLE_LOG;
|
||||
size_t build_cert_esl_sz = 0, addend_esl_sz = 0;
|
||||
+ bool reuse = FALSE;
|
||||
|
||||
if (v->categorize_addend)
|
||||
addend_category = v->categorize_addend(v);
|
||||
|
||||
- /*
|
||||
- * we're always mirroring the original data, whether this is an efi
|
||||
- * security database or not
|
||||
- */
|
||||
- dprint(L"v->name:\"%s\" v->rtname:\"%s\"\n", v->name, v->rtname);
|
||||
- dprint(L"v->data_size:%lu v->data:0x%08llx\n", v->data_size, v->data);
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n", FullDataSize, FullData);
|
||||
- if (v->data_size) {
|
||||
- FullDataSize = v->data_size;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
- FullDataSize, FullData);
|
||||
- }
|
||||
-
|
||||
/*
|
||||
* if it is, there's more data
|
||||
*/
|
||||
@@ -227,7 +501,7 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
|
||||
/*
|
||||
* We're mirroring (into) an efi security database, aka an
|
||||
- * array of efi_signature_list_t. Its layout goes like:
|
||||
+ * array of EFI_SIGNATURE_LIST. Its layout goes like:
|
||||
*
|
||||
* existing_variable_data
|
||||
* existing_variable_data_size
|
||||
@@ -251,30 +525,7 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
*/
|
||||
|
||||
/*
|
||||
- * first bit is existing data, but we added that above
|
||||
- */
|
||||
-
|
||||
- /*
|
||||
- * then the build cert if it's there
|
||||
- */
|
||||
- if (should_mirror_build_cert(v)) {
|
||||
- efi_status = fill_esl(*v->build_cert,
|
||||
- *v->build_cert_size,
|
||||
- &EFI_CERT_TYPE_X509_GUID,
|
||||
- &SHIM_LOCK_GUID,
|
||||
- NULL, &build_cert_esl_sz);
|
||||
- if (efi_status != EFI_BUFFER_TOO_SMALL) {
|
||||
- perror(L"Could not add built-in cert to %s: %r\n",
|
||||
- v->name, efi_status);
|
||||
- return efi_status;
|
||||
- }
|
||||
- FullDataSize += build_cert_esl_sz;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
- FullDataSize, FullData);
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
- * then the addend data
|
||||
+ * *first* vendor_db or vendor_cert
|
||||
*/
|
||||
switch (addend_category) {
|
||||
case VENDOR_ADDEND_DB:
|
||||
@@ -282,7 +533,7 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
* if it's an ESL already, we use it wholesale
|
||||
*/
|
||||
FullDataSize += *v->addend_size;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx\n",
|
||||
FullDataSize, FullData);
|
||||
break;
|
||||
case VENDOR_ADDEND_X509:
|
||||
@@ -296,17 +547,51 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
return efi_status;
|
||||
}
|
||||
FullDataSize += addend_esl_sz;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx\n",
|
||||
FullDataSize, FullData);
|
||||
break;
|
||||
default:
|
||||
case VENDOR_ADDEND_NONE:
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx\n",
|
||||
FullDataSize, FullData);
|
||||
break;
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * then the build cert if it's there
|
||||
+ */
|
||||
+ if (should_mirror_build_cert(v)) {
|
||||
+ efi_status = fill_esl(*v->build_cert,
|
||||
+ *v->build_cert_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ NULL, &build_cert_esl_sz);
|
||||
+ if (efi_status != EFI_BUFFER_TOO_SMALL) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ FullDataSize += build_cert_esl_sz;
|
||||
+ dprint(L"FullDataSize:0x%lx FullData:0x%llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ }
|
||||
+
|
||||
}
|
||||
|
||||
+ /*
|
||||
+ * we're always mirroring the original data, whether this is an efi
|
||||
+ * security database or not
|
||||
+ */
|
||||
+ dprint(L"v->name:\"%s\" v->rtname:\"%s\"\n", v->name, v->rtname);
|
||||
+ dprint(L"v->data_size:%lu v->data:0x%llx\n", v->data_size, v->data);
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx\n", FullDataSize, FullData);
|
||||
+ if (v->data_size) {
|
||||
+ FullDataSize += v->data_size;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx\n",
|
||||
+ FullDataSize, FullData);
|
||||
+ }
|
||||
+ if (v->data_size == FullDataSize)
|
||||
+ reuse = TRUE;
|
||||
|
||||
/*
|
||||
* Now we have the full size
|
||||
@@ -316,38 +601,33 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
* allocate the buffer, or use the old one if it's just the
|
||||
* existing data.
|
||||
*/
|
||||
- if (FullDataSize != v->data_size) {
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx allocating FullData\n",
|
||||
+ if (FullDataSize == v->data_size) {
|
||||
+ FullData = v->data;
|
||||
+ FullDataSize = v->data_size;
|
||||
+ p = FullData + FullDataSize;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ } else {
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx allocating FullData\n",
|
||||
FullDataSize, FullData);
|
||||
- FullData = AllocatePool(FullDataSize);
|
||||
+ /*
|
||||
+ * make sure we've got some zeroes at the end, just
|
||||
+ * in case.
|
||||
+ */
|
||||
+ UINTN allocsz = FullDataSize + sizeof(EFI_SIGNATURE_LIST);
|
||||
+ allocsz = ALIGN_VALUE(allocsz, 4096);
|
||||
+ FullData = AllocateZeroPool(FullDataSize);
|
||||
if (!FullData) {
|
||||
- FreePool(v->data);
|
||||
- v->data = NULL;
|
||||
- v->data_size = 0;
|
||||
perror(L"Failed to allocate %lu bytes for %s\n",
|
||||
FullDataSize, v->name);
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
p = FullData;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
- FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- if (v->data && v->data_size) {
|
||||
- CopyMem(p, v->data, v->data_size);
|
||||
- p += v->data_size;
|
||||
- }
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
- FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- } else {
|
||||
- FullData = v->data;
|
||||
- FullDataSize = v->data_size;
|
||||
- p = FullData + FullDataSize;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
- FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- v->data = NULL;
|
||||
- v->data_size = 0;
|
||||
}
|
||||
}
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
|
||||
/*
|
||||
@@ -355,35 +635,13 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
*/
|
||||
if (v->flags & MOK_MIRROR_KEYDB) {
|
||||
/*
|
||||
- * first bit is existing data, but again, we added that above
|
||||
+ * first vendor_cert or vendor_db
|
||||
*/
|
||||
-
|
||||
- /*
|
||||
- * second is the build cert
|
||||
- */
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
- FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- if (should_mirror_build_cert(v)) {
|
||||
- efi_status = fill_esl(*v->build_cert,
|
||||
- *v->build_cert_size,
|
||||
- &EFI_CERT_TYPE_X509_GUID,
|
||||
- &SHIM_LOCK_GUID,
|
||||
- p, &build_cert_esl_sz);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Could not add built-in cert to %s: %r\n",
|
||||
- v->name, efi_status);
|
||||
- return efi_status;
|
||||
- }
|
||||
- p += build_cert_esl_sz;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
- FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- }
|
||||
-
|
||||
switch (addend_category) {
|
||||
case VENDOR_ADDEND_DB:
|
||||
CopyMem(p, *v->addend, *v->addend_size);
|
||||
p += *v->addend_size;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
break;
|
||||
case VENDOR_ADDEND_X509:
|
||||
@@ -397,16 +655,53 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
return efi_status;
|
||||
}
|
||||
p += addend_esl_sz;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
break;
|
||||
default:
|
||||
case VENDOR_ADDEND_NONE:
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
break;
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * then is the build cert
|
||||
+ */
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ if (should_mirror_build_cert(v)) {
|
||||
+ efi_status = fill_esl(*v->build_cert,
|
||||
+ *v->build_cert_size,
|
||||
+ &EFI_CERT_TYPE_X509_GUID,
|
||||
+ &SHIM_LOCK_GUID,
|
||||
+ p, &build_cert_esl_sz);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not add built-in cert to %s: %r\n",
|
||||
+ v->name, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ p += build_cert_esl_sz;
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ }
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * last bit is existing data, unless it's the only thing,
|
||||
+ * in which case it's already there.
|
||||
+ */
|
||||
+ if (!reuse) {
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ if (v->data && v->data_size) {
|
||||
+ CopyMem(p, v->data, v->data_size);
|
||||
+ p += v->data_size;
|
||||
+ }
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
+ FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
+ }
|
||||
+
|
||||
/*
|
||||
* We always want to create our key databases, so in this case we
|
||||
* need a dummy entry
|
||||
@@ -422,68 +717,55 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
return efi_status;
|
||||
}
|
||||
p = FullData + FullDataSize;
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%08llx p:0x%08llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
}
|
||||
|
||||
- dprint(L"FullDataSize:%lu FullData:0x%016llx p:0x%016llx pos:%lld\n",
|
||||
+ dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n",
|
||||
FullDataSize, FullData, p, p-(uintptr_t)FullData);
|
||||
- if (FullDataSize) {
|
||||
- uint32_t attrs = EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
- EFI_VARIABLE_RUNTIME_ACCESS;
|
||||
- uint64_t max_storage_sz = 0;
|
||||
- uint64_t remaining_sz = 0;
|
||||
- uint64_t max_var_sz = 0;
|
||||
- UINT8 *tmp = NULL;
|
||||
- UINTN tmpsz = 0;
|
||||
-
|
||||
- efi_status = gRT->QueryVariableInfo(attrs, &max_storage_sz,
|
||||
- &remaining_sz, &max_var_sz);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Could not get variable storage info: %r\n", efi_status);
|
||||
- return efi_status;
|
||||
- }
|
||||
- dprint(L"calling SetVariable(\"%s\", 0x%016llx, 0x%08lx, %lu, 0x%016llx)\n",
|
||||
- v->rtname, v->guid,
|
||||
- EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
- | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
- FullDataSize, FullData);
|
||||
- efi_status = gRT->SetVariable(v->rtname, v->guid,
|
||||
- EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
- | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
- FullDataSize, FullData);
|
||||
- if (efi_status == EFI_INVALID_PARAMETER && max_var_sz < FullDataSize) {
|
||||
+ if (FullDataSize && v->flags & MOK_MIRROR_KEYDB) {
|
||||
+ dprint(L"calling mirror_mok_db(\"%s\", datasz=%lu)\n",
|
||||
+ v->rtname, FullDataSize);
|
||||
+ efi_status = mirror_mok_db(v->rtname, (CHAR8 *)v->rtname8, v->guid,
|
||||
+ attrs, FullData, FullDataSize,
|
||||
+ only_first);
|
||||
+ dprint(L"mirror_mok_db(\"%s\", datasz=%lu) returned %r\n",
|
||||
+ v->rtname, FullDataSize, efi_status);
|
||||
+ } else if (FullDataSize && only_first) {
|
||||
+ efi_status = SetVariable(v->rtname, v->guid, attrs,
|
||||
+ FullDataSize, FullData);
|
||||
+ }
|
||||
+ if (FullDataSize && only_first) {
|
||||
+ if (measure) {
|
||||
/*
|
||||
- * In this case we're going to try to create a
|
||||
- * dummy variable so that there's one there. It
|
||||
- * may or may not work, because on some firmware
|
||||
- * builds when the SetVariable call above fails it
|
||||
- * does actually set the variable(!), so aside from
|
||||
- * not using the allocation if it doesn't work, we
|
||||
- * don't care about failures here.
|
||||
+ * Measure this into PCR 7 in the Microsoft format
|
||||
*/
|
||||
- console_print(L"WARNING: Maximum volatile variable size is %lu.\n", max_var_sz);
|
||||
- console_print(L"WARNING: Cannot set %s (%lu bytes)\n", v->rtname, FullDataSize);
|
||||
- perror(L"Failed to set %s: %r\n", v->rtname, efi_status);
|
||||
- efi_status = variable_create_esl(
|
||||
- null_sha256, sizeof(null_sha256),
|
||||
- &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID,
|
||||
- &tmp, &tmpsz);
|
||||
+ efi_status = tpm_measure_variable(v->name, *v->guid,
|
||||
+ FullDataSize, FullData);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ dprint(L"tpm_measure_variable(\"%s\",%lu,0x%llx)->%r\n",
|
||||
+ v->name, FullDataSize, FullData, efi_status);
|
||||
+ return efi_status;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (log) {
|
||||
/*
|
||||
- * from here we don't really care if it works or
|
||||
- * doens't.
|
||||
+ * Log this variable into whichever PCR the table
|
||||
+ * says.
|
||||
*/
|
||||
- if (!EFI_ERROR(efi_status) && tmp && tmpsz) {
|
||||
- gRT->SetVariable(v->rtname, v->guid,
|
||||
- EFI_VARIABLE_BOOTSERVICE_ACCESS
|
||||
- | EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
- tmpsz, tmp);
|
||||
- FreePool(tmp);
|
||||
+ EFI_PHYSICAL_ADDRESS datap =
|
||||
+ (EFI_PHYSICAL_ADDRESS)(UINTN)FullData,
|
||||
+ efi_status = tpm_log_event(datap, FullDataSize,
|
||||
+ v->pcr, (CHAR8 *)v->name8);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ dprint(L"tpm_log_event(0x%llx, %lu, %lu, \"%s\")->%r\n",
|
||||
+ FullData, FullDataSize, v->pcr, v->name,
|
||||
+ efi_status);
|
||||
+ return efi_status;
|
||||
}
|
||||
- efi_status = EFI_INVALID_PARAMETER;
|
||||
- } else if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Failed to set %s: %r\n", v->rtname, efi_status);
|
||||
}
|
||||
+
|
||||
}
|
||||
if (v->data && v->data_size && v->data != FullData) {
|
||||
FreePool(v->data);
|
||||
@@ -501,19 +783,20 @@ mirror_one_mok_variable(struct mok_state_variable *v)
|
||||
* EFI_SECURITY_VIOLATION status at the same time.
|
||||
*/
|
||||
static EFI_STATUS nonnull(1)
|
||||
-maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
+maybe_mirror_one_mok_variable(struct mok_state_variable *v,
|
||||
+ EFI_STATUS ret, BOOLEAN only_first)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
BOOLEAN present = FALSE;
|
||||
|
||||
if (v->rtname) {
|
||||
- if (v->flags & MOK_MIRROR_DELETE_FIRST) {
|
||||
+ if (!only_first && (v->flags & MOK_MIRROR_DELETE_FIRST)) {
|
||||
dprint(L"deleting \"%s\"\n", v->rtname);
|
||||
efi_status = LibDeleteVariable(v->rtname, v->guid);
|
||||
dprint(L"LibDeleteVariable(\"%s\",...) => %r\n", v->rtname, efi_status);
|
||||
}
|
||||
|
||||
- efi_status = mirror_one_mok_variable(v);
|
||||
+ efi_status = mirror_one_mok_variable(v, only_first);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
if (ret != EFI_SECURITY_VIOLATION)
|
||||
ret = efi_status;
|
||||
@@ -530,34 +813,6 @@ maybe_mirror_one_mok_variable(struct mok_state_variable *v, EFI_STATUS ret)
|
||||
*v->state = v->data[0];
|
||||
}
|
||||
|
||||
- if (v->flags & MOK_VARIABLE_MEASURE) {
|
||||
- /*
|
||||
- * Measure this into PCR 7 in the Microsoft format
|
||||
- */
|
||||
- efi_status = tpm_measure_variable(v->name, *v->guid,
|
||||
- v->data_size,
|
||||
- v->data);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- if (ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- if (v->flags & MOK_VARIABLE_LOG) {
|
||||
- /*
|
||||
- * Log this variable into whichever PCR the table
|
||||
- * says.
|
||||
- */
|
||||
- EFI_PHYSICAL_ADDRESS datap =
|
||||
- (EFI_PHYSICAL_ADDRESS)(UINTN)v->data,
|
||||
- efi_status = tpm_log_event(datap, v->data_size,
|
||||
- v->pcr, (CHAR8 *)v->name8);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- if (ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
- }
|
||||
- }
|
||||
-
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -567,6 +822,66 @@ struct mok_variable_config_entry {
|
||||
UINT8 data[];
|
||||
};
|
||||
|
||||
+EFI_STATUS import_one_mok_state(struct mok_state_variable *v,
|
||||
+ BOOLEAN only_first)
|
||||
+{
|
||||
+ EFI_STATUS ret = EFI_SUCCESS;
|
||||
+ EFI_STATUS efi_status;
|
||||
+
|
||||
+ user_insecure_mode = 0;
|
||||
+ ignore_db = 0;
|
||||
+
|
||||
+ UINT32 attrs = 0;
|
||||
+ BOOLEAN delete = FALSE;
|
||||
+
|
||||
+ dprint(L"importing mok state for \"%s\"\n", v->name);
|
||||
+
|
||||
+ efi_status = get_variable_attr(v->name,
|
||||
+ &v->data, &v->data_size,
|
||||
+ *v->guid, &attrs);
|
||||
+ if (efi_status == EFI_NOT_FOUND) {
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ } else if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Could not verify %s: %r\n", v->name,
|
||||
+ efi_status);
|
||||
+ delete = TRUE;
|
||||
+ } else {
|
||||
+ if (!(attrs & v->yes_attr)) {
|
||||
+ perror(L"Variable %s is missing attributes:\n",
|
||||
+ v->name);
|
||||
+ perror(L" 0x%08x should have 0x%08x set.\n",
|
||||
+ attrs, v->yes_attr);
|
||||
+ delete = TRUE;
|
||||
+ }
|
||||
+ if (attrs & v->no_attr) {
|
||||
+ perror(L"Variable %s has incorrect attribute:\n",
|
||||
+ v->name);
|
||||
+ perror(L" 0x%08x should not have 0x%08x set.\n",
|
||||
+ attrs, v->no_attr);
|
||||
+ delete = TRUE;
|
||||
+ }
|
||||
+ }
|
||||
+ if (delete == TRUE) {
|
||||
+ perror(L"Deleting bad variable %s\n", v->name);
|
||||
+ efi_status = LibDeleteVariable(v->name, v->guid);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ perror(L"Failed to erase %s\n", v->name);
|
||||
+ ret = EFI_SECURITY_VIOLATION;
|
||||
+ }
|
||||
+ FreePool(v->data);
|
||||
+ v->data = NULL;
|
||||
+ v->data_size = 0;
|
||||
+ }
|
||||
+
|
||||
+ dprint(L"maybe mirroring \"%s\". original data:\n", v->name);
|
||||
+ dhexdumpat(v->data, v->data_size, 0);
|
||||
+
|
||||
+ ret = maybe_mirror_one_mok_variable(v, ret, only_first);
|
||||
+ dprint(L"returning %r\n", ret);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Verify our non-volatile MoK state. This checks the variables above
|
||||
* accessable and have valid attributes. If they don't, it removes
|
||||
@@ -594,58 +909,22 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
size_t npages = 0;
|
||||
struct mok_variable_config_entry config_template;
|
||||
|
||||
- dprint(L"importing mok state\n");
|
||||
+ dprint(L"importing minimal mok state variables\n");
|
||||
for (i = 0; mok_state_variables[i].name != NULL; i++) {
|
||||
struct mok_state_variable *v = &mok_state_variables[i];
|
||||
- UINT32 attrs = 0;
|
||||
- BOOLEAN delete = FALSE;
|
||||
|
||||
- efi_status = get_variable_attr(v->name,
|
||||
- &v->data, &v->data_size,
|
||||
- *v->guid, &attrs);
|
||||
- dprint(L"maybe mirroring %s\n", v->name);
|
||||
- if (efi_status == EFI_NOT_FOUND) {
|
||||
- v->data = NULL;
|
||||
- v->data_size = 0;
|
||||
- } else if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Could not verify %s: %r\n", v->name,
|
||||
- efi_status);
|
||||
+ efi_status = import_one_mok_state(v, TRUE);
|
||||
+ if (EFI_ERROR(efi_status)) {
|
||||
+ dprint(L"import_one_mok_state(ih, \"%s\", TRUE): %r\n",
|
||||
+ v->rtname);
|
||||
/*
|
||||
* don't clobber EFI_SECURITY_VIOLATION from some
|
||||
* other variable in the list.
|
||||
*/
|
||||
if (ret != EFI_SECURITY_VIOLATION)
|
||||
ret = efi_status;
|
||||
- delete = TRUE;
|
||||
- } else {
|
||||
- if (!(attrs & v->yes_attr)) {
|
||||
- perror(L"Variable %s is missing attributes:\n",
|
||||
- v->name);
|
||||
- perror(L" 0x%08x should have 0x%08x set.\n",
|
||||
- attrs, v->yes_attr);
|
||||
- delete = TRUE;
|
||||
- }
|
||||
- if (attrs & v->no_attr) {
|
||||
- perror(L"Variable %s has incorrect attribute:\n",
|
||||
- v->name);
|
||||
- perror(L" 0x%08x should not have 0x%08x set.\n",
|
||||
- attrs, v->no_attr);
|
||||
- delete = TRUE;
|
||||
- }
|
||||
- }
|
||||
- if (delete == TRUE) {
|
||||
- perror(L"Deleting bad variable %s\n", v->name);
|
||||
- efi_status = LibDeleteVariable(v->name, v->guid);
|
||||
- if (EFI_ERROR(efi_status)) {
|
||||
- perror(L"Failed to erase %s\n", v->name);
|
||||
- ret = EFI_SECURITY_VIOLATION;
|
||||
- }
|
||||
- FreePool(v->data);
|
||||
- v->data = NULL;
|
||||
- v->data_size = 0;
|
||||
}
|
||||
|
||||
- ret = maybe_mirror_one_mok_variable(v, ret);
|
||||
if (v->data && v->data_size) {
|
||||
config_sz += v->data_size;
|
||||
config_sz += sizeof(config_template);
|
||||
@@ -669,8 +948,6 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
if (EFI_ERROR(efi_status) || !config_table) {
|
||||
console_print(L"Allocating %lu pages for mok config table failed: %r\n",
|
||||
npages, efi_status);
|
||||
- if (ret != EFI_SECURITY_VIOLATION)
|
||||
- ret = efi_status;
|
||||
config_table = NULL;
|
||||
} else {
|
||||
ZeroMem(config_table, npages << EFI_PAGE_SHIFT);
|
||||
@@ -703,6 +980,16 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
}
|
||||
}
|
||||
|
||||
+ /*
|
||||
+ * This is really just to make it easy for userland.
|
||||
+ */
|
||||
+ dprint(L"importing full mok state variables\n");
|
||||
+ for (i = 0; mok_state_variables[i].name != NULL; i++) {
|
||||
+ struct mok_state_variable *v = &mok_state_variables[i];
|
||||
+
|
||||
+ import_one_mok_state(v, FALSE);
|
||||
+ }
|
||||
+
|
||||
/*
|
||||
* Enter MokManager if necessary. Any actual *changes* here will
|
||||
* cause MokManager to demand a machine reboot, so this is safe to
|
||||
@@ -712,6 +999,9 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle)
|
||||
efi_status = check_mok_request(image_handle);
|
||||
dprint(L"mok returned %r\n", efi_status);
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
+ /*
|
||||
+ * don't clobber EFI_SECURITY_VIOLATION
|
||||
+ */
|
||||
if (ret != EFI_SECURITY_VIOLATION)
|
||||
ret = efi_status;
|
||||
return ret;
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 9248642bd57..1a4d7bb9ded 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -1445,7 +1445,10 @@ static EFI_STATUS handle_image (void *data, unsigned int datasize,
|
||||
sha256hash, sha1hash);
|
||||
|
||||
if (EFI_ERROR(efi_status)) {
|
||||
- console_error(L"Verification failed", efi_status);
|
||||
+ if (verbose)
|
||||
+ console_print(L"Verification failed: %r\n", efi_status);
|
||||
+ else
|
||||
+ console_error(L"Verification failed", efi_status);
|
||||
return efi_status;
|
||||
} else {
|
||||
if (verbose)
|
||||
@@ -2648,7 +2651,6 @@ shim_init(void)
|
||||
{
|
||||
EFI_STATUS efi_status;
|
||||
|
||||
- setup_verbosity();
|
||||
dprint(L"%a", shim_version);
|
||||
|
||||
/* Set the second stage loader */
|
||||
@@ -2797,6 +2799,7 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab)
|
||||
* Ensure that gnu-efi functions are available
|
||||
*/
|
||||
InitializeLib(image_handle, systab);
|
||||
+ setup_verbosity();
|
||||
|
||||
dprint(L"vendor_authorized:0x%08lx vendor_authorized_size:%lu\n",
|
||||
__FILE__, __LINE__, __func__, vendor_authorized, vendor_authorized_size);
|
||||
diff --git a/include/PeImage.h b/include/PeImage.h
|
||||
index a606e8b2a9f..209b96fb8ff 100644
|
||||
--- a/include/PeImage.h
|
||||
+++ b/include/PeImage.h
|
||||
@@ -768,7 +768,8 @@ typedef struct {
|
||||
UINT8 CertData[1];
|
||||
} WIN_CERTIFICATE_EFI_PKCS;
|
||||
|
||||
-#define SHA256_DIGEST_SIZE 32
|
||||
+#define SHA1_DIGEST_SIZE 20
|
||||
+#define SHA256_DIGEST_SIZE 32
|
||||
#define WIN_CERT_TYPE_PKCS_SIGNED_DATA 0x0002
|
||||
|
||||
typedef struct {
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,77 +0,0 @@
|
||||
From 9313a515432ba938e66f2edc1e22d548fed1eb5c Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Thu, 30 Jul 2020 14:34:22 -0400
|
||||
Subject: [PATCH] hexdump.h: fix arithmetic error.
|
||||
|
||||
When I modified the hexdumper to help debug MokListRT mirroring not
|
||||
working because of PcdMaxVolatileVariableSize being tiny, I
|
||||
inadvertently added something that is effectively:
|
||||
|
||||
hexdump(..., char *buf, ..., int position)
|
||||
{
|
||||
unsigned long begin = (position % 16);
|
||||
unsigned long i;
|
||||
...
|
||||
for (i = 0; i < begin; i++) {
|
||||
...
|
||||
}
|
||||
...
|
||||
}
|
||||
|
||||
Unfortunately, in c if 0x8 is set in position, that means begin is
|
||||
0xfffffffffffff8, because signed integer math is horrifying:
|
||||
|
||||
include/hexdump.h:99:vhexdumpf() &data[offset]:0x9E77E6BC size-offset:0x14
|
||||
include/hexdump.h:15:prepare_hex() position:0x9E77E6BC
|
||||
include/hexdump.h:17:prepare_hex() before:0xFFFFFFFFFFFFFFFC size:0x14
|
||||
include/hexdump.h:19:prepare_hex() before:0xFFFFFFFFFFFFFFFC after:0x0
|
||||
include/hexdump.h:21:prepare_hex() buf:0x000000009E77E2BC offset:0 &buf[offset]:0x000000009E77E2BC
|
||||
|
||||
Woops.
|
||||
|
||||
This could further have been prevented in /some/ cases by simply not
|
||||
preparing the hexdump buffer when "verbose" is disabled.
|
||||
|
||||
This patch makes "pos" be unsigned in all cases, and also checks for
|
||||
verbose in vhexdumpf() and simply returns if it is 0.
|
||||
|
||||
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||||
---
|
||||
include/hexdump.h | 7 +++++--
|
||||
1 file changed, 5 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/include/hexdump.h b/include/hexdump.h
|
||||
index f3f3ac284a3..b2968cd4f85 100644
|
||||
--- a/include/hexdump.h
|
||||
+++ b/include/hexdump.h
|
||||
@@ -4,7 +4,7 @@
|
||||
#include <stdint.h>
|
||||
|
||||
static inline unsigned long UNUSED
|
||||
-prepare_hex(const void *data, size_t size, char *buf, int position)
|
||||
+prepare_hex(const void *data, size_t size, char *buf, unsigned int position)
|
||||
{
|
||||
char hexchars[] = "0123456789abcdef";
|
||||
int offset = 0;
|
||||
@@ -48,7 +48,7 @@ prepare_hex(const void *data, size_t size, char *buf, int position)
|
||||
#define isprint(c) ((c) >= 0x20 && (c) <= 0x7e)
|
||||
|
||||
static inline void UNUSED
|
||||
-prepare_text(const void *data, size_t size, char *buf, int position)
|
||||
+prepare_text(const void *data, size_t size, char *buf, unsigned int position)
|
||||
{
|
||||
int offset = 0;
|
||||
unsigned long i;
|
||||
@@ -84,6 +84,9 @@ vhexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt
|
||||
unsigned long display_offset = at;
|
||||
unsigned long offset = 0;
|
||||
|
||||
+ if (verbose == 0)
|
||||
+ return;
|
||||
+
|
||||
while (offset < size) {
|
||||
char hexbuf[49];
|
||||
char txtbuf[19];
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,122 +0,0 @@
|
||||
From 18843127dc0eace16d43d479bd091e221e8785c4 Mon Sep 17 00:00:00 2001
|
||||
From: Peter Jones <pjones@redhat.com>
|
||||
Date: Mon, 17 Aug 2020 15:47:19 -0400
|
||||
Subject: [PATCH] Fix some mokmanager deletion paths
|
||||
|
||||
This fixes several codepaths where MokList and MokListX are supposed to
|
||||
be deleted, but are not. It also adds debug logging to much of the
|
||||
deletion codepath.
|
||||
|
||||
---
|
||||
MokManager.c | 24 +++++++++++++++++++++++-
|
||||
Makefile | 2 +-
|
||||
2 files changed, 24 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/MokManager.c b/MokManager.c
|
||||
index c9949e33bcf..9bae3414fe7 100644
|
||||
--- a/MokManager.c
|
||||
+++ b/MokManager.c
|
||||
@@ -9,6 +9,8 @@
|
||||
|
||||
#include "shim.h"
|
||||
|
||||
+#include "hexdump.h"
|
||||
+
|
||||
#define PASSWORD_MAX 256
|
||||
#define PASSWORD_MIN 1
|
||||
#define SB_PASSWORD_LEN 16
|
||||
@@ -1050,9 +1052,11 @@ static EFI_STATUS mok_reset_prompt(BOOLEAN MokX)
|
||||
if (MokX) {
|
||||
LibDeleteVariable(L"MokXNew", &SHIM_LOCK_GUID);
|
||||
LibDeleteVariable(L"MokXAuth", &SHIM_LOCK_GUID);
|
||||
+ LibDeleteVariable(L"MokListX", &SHIM_LOCK_GUID);
|
||||
} else {
|
||||
LibDeleteVariable(L"MokNew", &SHIM_LOCK_GUID);
|
||||
LibDeleteVariable(L"MokAuth", &SHIM_LOCK_GUID);
|
||||
+ LibDeleteVariable(L"MokList", &SHIM_LOCK_GUID);
|
||||
}
|
||||
|
||||
return EFI_SUCCESS;
|
||||
@@ -1075,6 +1079,7 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
else
|
||||
db_name = L"MokList";
|
||||
|
||||
+ dprint(L"Writing back %s (%d entries)\n", db_name, key_num);
|
||||
for (i = 0; i < key_num; i++) {
|
||||
if (list[i].Mok == NULL)
|
||||
continue;
|
||||
@@ -1085,8 +1090,15 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num,
|
||||
DataSize += sizeof(EFI_GUID);
|
||||
DataSize += list[i].MokSize;
|
||||
}
|
||||
- if (DataSize == 0)
|
||||
+ if (DataSize == 0) {
|
||||
+ dprint(L"DataSize = 0; deleting variable %s\n", db_name);
|
||||
+ efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID,
|
||||
+ EFI_VARIABLE_NON_VOLATILE |
|
||||
+ EFI_VARIABLE_BOOTSERVICE_ACCESS,
|
||||
+ DataSize, Data);
|
||||
+ dprint(L"efi_status:%llu\n", efi_status);
|
||||
return EFI_SUCCESS;
|
||||
+ }
|
||||
|
||||
Data = AllocatePool(DataSize);
|
||||
if (Data == NULL)
|
||||
@@ -1291,11 +1303,15 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
}
|
||||
|
||||
if (auth_size == PASSWORD_CRYPT_SIZE) {
|
||||
+ dprint(L"matching password with CRYPT");
|
||||
efi_status = match_password((PASSWORD_CRYPT *) auth, NULL, 0,
|
||||
NULL, NULL);
|
||||
+ dprint(L"match_password(0x%llx, NULL, 0, NULL, NULL) = %lu\n", auth, efi_status);
|
||||
} else {
|
||||
+ dprint(L"matching password as sha256sum");
|
||||
efi_status =
|
||||
match_password(NULL, MokDel, MokDelSize, auth, NULL);
|
||||
+ dprint(L"match_password(NULL, 0x%llx, %llu, 0x%llx, NULL) = %lu\n", MokDel, MokDelSize, auth, efi_status);
|
||||
}
|
||||
if (EFI_ERROR(efi_status))
|
||||
return EFI_ACCESS_DENIED;
|
||||
@@ -1365,12 +1381,17 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
|
||||
}
|
||||
|
||||
/* Search and destroy */
|
||||
+ dprint(L"deleting certs from %a\n", MokX ? "MokListX" : "MokList");
|
||||
for (i = 0; i < del_num; i++) {
|
||||
type = del_key[i].Type; /* avoid -Werror=address-of-packed-member */
|
||||
if (CompareGuid(&type, &X509_GUID) == 0) {
|
||||
+ dprint(L"deleting key %d (total %d):\n", i, mok_num);
|
||||
+ dhexdumpat(del_key[i].Mok, del_key[i].MokSize, 0);
|
||||
delete_cert(del_key[i].Mok, del_key[i].MokSize,
|
||||
mok, mok_num);
|
||||
} else if (is_sha2_hash(del_key[i].Type)) {
|
||||
+ dprint(L"deleting hash %d (total %d):\n", i, mok_num);
|
||||
+ dhexdumpat(del_key[i].Mok, del_key[i].MokSize, 0);
|
||||
delete_hash_list(del_key[i].Type, del_key[i].Mok,
|
||||
del_key[i].MokSize, mok, mok_num);
|
||||
}
|
||||
@@ -2564,6 +2585,7 @@ EFI_STATUS efi_main(EFI_HANDLE image_handle, EFI_SYSTEM_TABLE * systab)
|
||||
|
||||
InitializeLib(image_handle, systab);
|
||||
|
||||
+ setup_verbosity();
|
||||
setup_rand();
|
||||
|
||||
console_mode_handle();
|
||||
diff --git a/Makefile b/Makefile
|
||||
index 49e14a26521..a17fa2bef14 100644
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -36,7 +36,7 @@ endif
|
||||
OBJS = shim.o mok.o netboot.o cert.o replacements.o tpm.o version.o errlog.o
|
||||
KEYS = shim_cert.h ocsp.* ca.* shim.crt shim.csr shim.p12 shim.pem shim.key shim.cer
|
||||
ORIG_SOURCES = shim.c mok.c netboot.c replacements.c tpm.c errlog.c shim.h version.h $(wildcard include/*.h)
|
||||
-MOK_OBJS = MokManager.o PasswordCrypt.o crypt_blowfish.o
|
||||
+MOK_OBJS = MokManager.o PasswordCrypt.o crypt_blowfish.o errlog.o
|
||||
ORIG_MOK_SOURCES = MokManager.c PasswordCrypt.c crypt_blowfish.c shim.h $(wildcard include/*.h)
|
||||
FALLBACK_OBJS = fallback.o tpm.o errlog.o
|
||||
ORIG_FALLBACK_SRCS = fallback.c
|
||||
--
|
||||
2.26.2
|
||||
|
@ -1,37 +0,0 @@
|
||||
From ac610fe45491deccaab2c4ee689cbbdac117930a Mon Sep 17 00:00:00 2001
|
||||
From: Javier Martinez Canillas <javierm@redhat.com>
|
||||
Date: Tue, 8 Sep 2020 12:26:45 +0200
|
||||
Subject: [PATCH] Fix buffer overrun due DEFAULT_LOADER length miscalculation
|
||||
|
||||
The DEFAULT_LOADER is a UCS-2 string and the StrLen() function returns the
|
||||
number of UCS-2 encoded characters in the string. But the allocated memory
|
||||
is in bytes, so only half of the needed memory to store it is allocated.
|
||||
|
||||
This leads to a buffer overrun when the StrCpy() function attempts to copy
|
||||
the DEFAULT_LOADER to the allocated buffer.
|
||||
|
||||
Fixes: 354bd9b1931 ("Actually check for errors from set_second_stage()")
|
||||
Reported-by: Stuart Hayes <stuart_hayes@dell.com>
|
||||
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
|
||||
---
|
||||
shim.c | 3 ++-
|
||||
1 file changed, 2 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/shim.c b/shim.c
|
||||
index 34dce25c330..82913c934f6 100644
|
||||
--- a/shim.c
|
||||
+++ b/shim.c
|
||||
@@ -2096,8 +2096,9 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle)
|
||||
unsigned int i;
|
||||
UINTN second_stage_len;
|
||||
|
||||
- second_stage_len = StrLen(DEFAULT_LOADER) + 1;
|
||||
+ second_stage_len = (StrLen(DEFAULT_LOADER) + 1) * sizeof(CHAR16);
|
||||
second_stage = AllocatePool(second_stage_len);
|
||||
+
|
||||
if (!second_stage) {
|
||||
perror(L"Could not allocate %lu bytes\n", second_stage_len);
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
--
|
||||
2.28.0
|
||||
|
1
SOURCES/sbat.redhat.csv
Normal file
1
SOURCES/sbat.redhat.csv
Normal file
@ -0,0 +1 @@
|
||||
shim.redhat,1,Red Hat,shim,15.4-4,secalert@redhat.com
|
|
@ -20,9 +20,9 @@ fi
|
||||
findsource()
|
||||
{
|
||||
(
|
||||
cd ${RPM_BUILD_ROOT}
|
||||
find usr/src/debug/ -type d | sed "s,^,%dir /,"
|
||||
find usr/src/debug/ -type f | sed "s,^,/,"
|
||||
cd "${RPM_BUILD_ROOT}"
|
||||
find usr/src/debug/ -type d | sed -e "s,^,%dir /," | sort -u | tac
|
||||
find usr/src/debug/ -type f | sed -e "s,^,/," | sort -u | tac
|
||||
)
|
||||
}
|
||||
|
||||
@ -32,9 +32,12 @@ finddebug()
|
||||
declare -a dirs=()
|
||||
declare -a files=()
|
||||
declare -a excludes=()
|
||||
declare -a tmp=()
|
||||
|
||||
pushd ${RPM_BUILD_ROOT} >/dev/null 2>&1
|
||||
for x in $(find usr/lib/debug/ -type f -iname *.efi.debug); do
|
||||
pushd "${RPM_BUILD_ROOT}" >/dev/null 2>&1
|
||||
|
||||
mapfile -t tmp < <(find usr/lib/debug/ -type f -iname "*.efi.debug")
|
||||
for x in "${tmp[@]}" ; do
|
||||
if ! [ -e "${x}" ]; then
|
||||
break
|
||||
fi
|
||||
@ -57,8 +60,10 @@ finddebug()
|
||||
excludes[${#excludes[@]}]=${x%%.debug}
|
||||
fi
|
||||
done
|
||||
for x in ${files[@]} ; do
|
||||
declare name=$(dirname /${x})
|
||||
for x in "${files[@]}" ; do
|
||||
declare name
|
||||
|
||||
name=$(dirname "/${x}")
|
||||
while [ "${name}" != "/" ]; do
|
||||
case "${name}" in
|
||||
"/usr/lib/debug"|"/usr/lib"|"/usr")
|
||||
@ -67,24 +72,24 @@ finddebug()
|
||||
dirs[${#dirs[@]}]=${name}
|
||||
;;
|
||||
esac
|
||||
name=$(dirname ${name})
|
||||
name=$(dirname "${name}")
|
||||
done
|
||||
done
|
||||
|
||||
popd >/dev/null 2>&1
|
||||
for x in ${dirs[@]} ; do
|
||||
for x in "${dirs[@]}" ; do
|
||||
echo "%dir ${x}"
|
||||
done | sort | uniq
|
||||
for x in ${files[@]} ; do
|
||||
for x in "${files[@]}" ; do
|
||||
echo "/${x}"
|
||||
done | sort | uniq
|
||||
for x in ${excludes[@]} ; do
|
||||
for x in "${excludes[@]}" ; do
|
||||
echo "%exclude /${x}"
|
||||
done
|
||||
}
|
||||
|
||||
findsource > build-${mainarch}/debugsource.list
|
||||
finddebug ${mainarch} > build-${mainarch}/debugfiles.list
|
||||
findsource > "build-${mainarch}/debugsource.list"
|
||||
finddebug "${mainarch}" > "build-${mainarch}/debugfiles.list"
|
||||
if [ -v altarch ]; then
|
||||
finddebug ${altarch} > build-${altarch}/debugfiles.list
|
||||
finddebug "${altarch}" > "build-${altarch}/debugfiles.list"
|
||||
fi
|
||||
|
@ -1,13 +1,6 @@
|
||||
%global pesign_vre 0.106-1
|
||||
%global gnuefi_vre 1:3.0.5-6
|
||||
%global openssl_vre 1.0.2j
|
||||
|
||||
%global debug_package %{nil}
|
||||
%global __debug_package 1
|
||||
%global _binaries_in_noarch_packages_terminate_build 0
|
||||
%global __debug_install_post %{SOURCE100} x64 ia32
|
||||
%undefine _debuginfo_subpackages
|
||||
|
||||
%global efidir %(eval echo $(grep ^ID= /etc/os-release | sed -e 's/^ID=//' -e 's/rhel/redhat/'))
|
||||
%global shimrootdir %{_datadir}/shim/
|
||||
%global shimversiondir %{shimrootdir}/%{version}-%{release}
|
||||
@ -16,92 +9,38 @@
|
||||
%global efialtarch ia32
|
||||
%global shimaltdir %{shimversiondir}/%{efialtarch}
|
||||
|
||||
%global debug_package %{nil}
|
||||
%global __debug_package 1
|
||||
%global _binaries_in_noarch_packages_terminate_build 0
|
||||
%global __debug_install_post %{SOURCE100} %{efiarch} %{efialtarch}
|
||||
%undefine _debuginfo_subpackages
|
||||
|
||||
# currently here's what's in our dbx: nothing
|
||||
%global dbxfile %{nil}
|
||||
|
||||
Name: shim-unsigned-%{efiarch}
|
||||
Version: 15
|
||||
Release: 9.el8
|
||||
Version: 15.4
|
||||
Release: 4%{?dist}
|
||||
Summary: First-stage UEFI bootloader
|
||||
ExclusiveArch: x86_64
|
||||
License: BSD
|
||||
URL: https://github.com/rhboot/shim
|
||||
Source0: https://github.com/rhboot/shim/releases/download/%{version}/shim-%{version}.tar.bz2
|
||||
Source1: redhatsecurebootca5.cer
|
||||
# currently here's what's in our dbx:
|
||||
# nothing.
|
||||
Source2: dbx.esl
|
||||
%if 0%{?dbxfile}
|
||||
Source2: %{dbxfile}
|
||||
%endif
|
||||
Source3: sbat.redhat.csv
|
||||
|
||||
Source100: shim-find-debuginfo.sh
|
||||
|
||||
Patch0001: 0001-Make-some-things-dprint-instead-of-console_print.patch
|
||||
Patch0002: 0002-Makefiles-ensure-m32-gets-propogated-to-our-gcc-para.patch
|
||||
Patch0003: 0003-Let-MokManager-follow-a-MokTimeout-var-for-timeout-l.patch
|
||||
Patch0004: 0004-httpboot-return-EFI_NOT_FOUND-when-it-fails-to-find-.patch
|
||||
Patch0005: 0005-httpboot-print-more-messages-when-it-fails-to-set-IP.patch
|
||||
Patch0006: 0006-httpboot-allow-the-IPv4-gateway-to-be-empty.patch
|
||||
Patch0007: 0007-httpboot-show-the-error-message-for-the-ChildHandle.patch
|
||||
Patch0008: 0008-Fix-typo-in-debug-path-in-shim.h.patch
|
||||
Patch0009: 0009-MokManager-Stop-using-EFI_VARIABLE_APPEND_WRITE.patch
|
||||
Patch0010: 0010-shim-Extend-invalid-reloc-size-warning-message.patch
|
||||
Patch0011: 0011-Add-GRUB-s-PCR-Usage-to-README.tpm.patch
|
||||
Patch0012: 0012-Fix-the-compile-error-of-mkdir-wrong-directory.patch
|
||||
Patch0013: 0013-shim-Properly-generate-absolute-paths-from-relative-.patch
|
||||
Patch0014: 0014-shim-Prevent-shim-to-set-itself-as-a-second-stage-lo.patch
|
||||
Patch0015: 0015-Fix-for-Section-0-has-negative-size-error-when-loadi.patch
|
||||
Patch0016: 0016-Fix-apparent-typo-in-ARM-32-on-64-code.patch
|
||||
Patch0017: 0017-Makefile-do-not-run-git-on-clean-if-there-s-no-.git-.patch
|
||||
Patch0018: 0018-Make.default-use-correct-flags-to-disable-unaligned-.patch
|
||||
Patch0019: 0019-Cryptlib-fix-build-on-32bit-ARM.patch
|
||||
Patch0020: 0020-Make-sure-that-MOK-variables-always-get-mirrored.patch
|
||||
Patch0021: 0021-mok-fix-the-mirroring-of-RT-variables.patch
|
||||
Patch0022: 0022-mok-consolidate-mirroring-code-in-a-helper-instead-o.patch
|
||||
Patch0023: 0023-shim-only-include-shim_cert.h-in-shim.c.patch
|
||||
Patch0024: 0024-mok-also-mirror-the-build-cert-to-MokListRT.patch
|
||||
Patch0025: 0025-mok-minor-cleanups.patch
|
||||
Patch0026: 0026-Remove-call-to-TPM2-get_event_log.patch
|
||||
Patch0027: 0027-Make-EFI-variable-copying-fatal-only-on-secureboot-e.patch
|
||||
Patch0028: 0028-VLogError-Avoid-NULL-pointer-dereferences-in-V-Sprin.patch
|
||||
Patch0029: 0029-Once-again-try-even-harder-to-get-binaries-without-t.patch
|
||||
Patch0030: 0030-shim-Rework-pause-functions-and-add-read_counter.patch
|
||||
Patch0031: 0031-Hook-exit-when-shim_lock-protocol-installed.patch
|
||||
Patch0032: 0032-Work-around-stuff-Waddress-of-packed-member-finds.patch
|
||||
Patch0033: 0033-Fix-a-use-of-strlen-instead-of-Strlen.patch
|
||||
Patch0034: 0034-MokManager-Use-CompareMem-on-MokListNode.Type-instea.patch
|
||||
Patch0035: 0035-OpenSSL-always-provide-OBJ_create-with-name-strings.patch
|
||||
Patch0036: 0036-Use-portable-shebangs-bin-bash-usr-bin-env-bash.patch
|
||||
Patch0037: 0037-tpm-Fix-off-by-one-error-when-calculating-event-size.patch
|
||||
Patch0038: 0038-tpm-Define-EFI_VARIABLE_DATA_TREE-as-packed.patch
|
||||
Patch0039: 0039-MokManager-console-mode-modification-for-hi-dpi-scre.patch
|
||||
Patch0040: 0040-MokManager-avoid-Werror-address-of-packed-member.patch
|
||||
Patch0041: 0041-tpm-Don-t-log-duplicate-identical-events.patch
|
||||
Patch0042: 0042-Slightly-better-debugging-messages.patch
|
||||
Patch0043: 0043-Actually-check-for-errors-from-set_second_stage.patch
|
||||
Patch0044: 0044-translate_slashes-don-t-write-to-string-literals.patch
|
||||
Patch0045: 0045-shim-Update-EFI_LOADED_IMAGE-with-the-second-stage-l.patch
|
||||
Patch0046: 0046-tpm-Include-information-about-PE-COFF-images-in-the-.patch
|
||||
Patch0047: 0047-Fix-the-license-on-our-buildid-extractor.patch
|
||||
Patch0048: 0048-Update-README.tpm.patch
|
||||
Patch0049: 0049-Check-PxeReplyReceived-as-fallback-in-netboot.patch
|
||||
Patch0050: 0050-Remove-a-couple-of-incorrect-license-claims.patch
|
||||
Patch0051: 0051-MokManager-fix-uninitialized-value.patch
|
||||
Patch0052: 0052-Fix-some-volatile-usage-gcc-whines-about.patch
|
||||
Patch0053: 0053-MokManager-fix-a-wrong-allocation-failure-check.patch
|
||||
Patch0054: 0054-simple_file-fix-uninitialized-variable-unchecked-ret.patch
|
||||
Patch0055: 0055-Fix-a-broken-tpm-type.patch
|
||||
Patch0056: 0056-Make-cert.S-not-impossible-to-read.patch
|
||||
Patch0057: 0057-Add-support-for-vendor_db-built-in-shim-authorized-l.patch
|
||||
Patch0058: 0058-Handle-binaries-with-multiple-signatures.patch
|
||||
Patch0059: 0059-Make-openssl-accept-the-right-set-of-KU-EKUs.patch
|
||||
Patch0060: 0060-Improve-debug-output-some.patch
|
||||
Patch0061: 0061-Also-use-a-config-table-to-mirror-mok-variables.patch
|
||||
Patch0062: 0062-Implement-lennysz-s-suggestions-for-MokListRT.patch
|
||||
Patch0063: 0063-hexdump.h-fix-arithmetic-error.patch
|
||||
Patch0064: 0064-Fix-some-mokmanager-deletion-paths.patch
|
||||
Patch0065: 0065-Fix-buffer-overrun-due-DEFAULT_LOADER-length-miscalc.patch
|
||||
Patch0001: 0001-Fix-a-broken-file-header-on-ia32.patch
|
||||
|
||||
BuildRequires: gcc make
|
||||
BuildRequires: elfutils-libelf-devel
|
||||
BuildRequires: git openssl-devel openssl
|
||||
BuildRequires: pesign >= %{pesign_vre}
|
||||
BuildRequires: gnu-efi >= %{gnuefi_vre}
|
||||
BuildRequires: gnu-efi-devel >= %{gnuefi_vre}
|
||||
BuildRequires: dos2unix findutils
|
||||
|
||||
# Shim uses OpenSSL, but cannot use the system copy as the UEFI ABI is not
|
||||
# compatible with SysV (there's no red zone under UEFI) and there isn't a
|
||||
@ -129,7 +68,6 @@ Provides: bundled(openssl) = %{openssl_vre}
|
||||
|
||||
%package debuginfo
|
||||
Summary: Debug information for shim-unsigned-%{efiarch}
|
||||
Requires: %{name}-debugsource = %{version}-%{release}
|
||||
Group: Development/Debug
|
||||
AutoReqProv: 0
|
||||
BuildArch: noarch
|
||||
@ -140,7 +78,6 @@ BuildArch: noarch
|
||||
%package -n shim-unsigned-%{efialtarch}-debuginfo
|
||||
Summary: Debug information for shim-unsigned-%{efialtarch}
|
||||
Group: Development/Debug
|
||||
Requires: %{name}-debugsource = %{version}-%{release}
|
||||
AutoReqProv: 0
|
||||
BuildArch: noarch
|
||||
|
||||
@ -162,39 +99,49 @@ git config --unset user.email
|
||||
git config --unset user.name
|
||||
mkdir build-%{efiarch}
|
||||
mkdir build-%{efialtarch}
|
||||
cp %{SOURCE3} data/
|
||||
|
||||
%build
|
||||
COMMITID=$(cat commit)
|
||||
MAKEFLAGS="TOPDIR=.. -f ../Makefile COMMITID=${COMMITID} "
|
||||
MAKEFLAGS+="EFIDIR=%{efidir} PKGNAME=shim RELEASE=%{release} "
|
||||
MAKEFLAGS+="ENABLE_HTTPBOOT=true ENABLE_SHIM_HASH=true "
|
||||
MAKEFLAGS+="ENABLE_SHIM_HASH=true "
|
||||
MAKEFLAGS+="%{_smp_mflags}"
|
||||
if [ -s "%{SOURCE1}" ]; then
|
||||
if [ -f "%{SOURCE1}" ]; then
|
||||
MAKEFLAGS="$MAKEFLAGS VENDOR_CERT_FILE=%{SOURCE1}"
|
||||
fi
|
||||
if [ -s "%{SOURCE2}" ]; then
|
||||
%if 0%{?dbxfile}
|
||||
if [ -f "%{SOURCE2}" ]; then
|
||||
MAKEFLAGS="$MAKEFLAGS VENDOR_DBX_FILE=%{SOURCE2}"
|
||||
fi
|
||||
%endif
|
||||
|
||||
cd build-%{efiarch}
|
||||
make ${MAKEFLAGS} DEFAULT_LOADER='\\\\grub%{efiarch}.efi' all
|
||||
make ${MAKEFLAGS} \
|
||||
DEFAULT_LOADER='\\\\grub%{efiarch}.efi' \
|
||||
all
|
||||
cd ..
|
||||
|
||||
cd build-%{efialtarch}
|
||||
setarch linux32 -B make ${MAKEFLAGS} ARCH=%{efialtarch} DEFAULT_LOADER='\\\\grub%{efialtarch}.efi' all
|
||||
setarch linux32 -B make ${MAKEFLAGS} \
|
||||
ARCH=%{efialtarch} \
|
||||
DEFAULT_LOADER='\\\\grub%{efialtarch}.efi' \
|
||||
all
|
||||
cd ..
|
||||
|
||||
%install
|
||||
COMMITID=$(cat commit)
|
||||
MAKEFLAGS="TOPDIR=.. -f ../Makefile COMMITID=${COMMITID} "
|
||||
MAKEFLAGS+="EFIDIR=%{efidir} PKGNAME=shim RELEASE=%{release} "
|
||||
MAKEFLAGS+="ENABLE_HTTPBOOT=true ENABLE_SHIM_HASH=true "
|
||||
if [ -s "%{SOURCE1}" ]; then
|
||||
MAKEFLAGS+="ENABLE_SHIM_HASH=true "
|
||||
if [ -f "%{SOURCE1}" ]; then
|
||||
MAKEFLAGS="$MAKEFLAGS VENDOR_CERT_FILE=%{SOURCE1}"
|
||||
fi
|
||||
if [ -s "%{SOURCE2}" ]; then
|
||||
%if 0%{?dbxfile}
|
||||
if [ -f "%{SOURCE2}" ]; then
|
||||
MAKEFLAGS="$MAKEFLAGS VENDOR_DBX_FILE=%{SOURCE2}"
|
||||
fi
|
||||
%endif
|
||||
|
||||
cd build-%{efiarch}
|
||||
make ${MAKEFLAGS} \
|
||||
@ -204,7 +151,8 @@ make ${MAKEFLAGS} \
|
||||
cd ..
|
||||
|
||||
cd build-%{efialtarch}
|
||||
setarch linux32 make ${MAKEFLAGS} ARCH=%{efialtarch} \
|
||||
setarch linux32 make ${MAKEFLAGS} \
|
||||
ARCH=%{efialtarch} \
|
||||
DEFAULT_LOADER='\\\\grub%{efialtarch}.efi' \
|
||||
DESTDIR=${RPM_BUILD_ROOT} \
|
||||
install-as-data install-debuginfo install-debugsource
|
||||
@ -217,6 +165,7 @@ cd ..
|
||||
%dir %{shimdir}
|
||||
%{shimdir}/*.efi
|
||||
%{shimdir}/*.hash
|
||||
%{shimdir}/*.CSV
|
||||
|
||||
%files -n shim-unsigned-%{efialtarch}
|
||||
%license COPYRIGHT
|
||||
@ -225,6 +174,7 @@ cd ..
|
||||
%dir %{shimaltdir}
|
||||
%{shimaltdir}/*.efi
|
||||
%{shimaltdir}/*.hash
|
||||
%{shimaltdir}/*.CSV
|
||||
|
||||
%files debuginfo -f build-%{efiarch}/debugfiles.list
|
||||
|
||||
@ -233,45 +183,63 @@ cd ..
|
||||
%files debugsource -f build-%{efiarch}/debugsource.list
|
||||
|
||||
%changelog
|
||||
* Thu Sep 17 2020 Peter Jones <pjones@redhat.com> - 15-9.el8
|
||||
- Fix an incorrect allocation size.
|
||||
Related: rhbz#1877253
|
||||
* Thu Apr 01 2021 Peter Jones <pjones@redhat.com> - 15.4-4
|
||||
- Fix the sbat data to actually match /this/ product.
|
||||
Resolves: CVE-2020-14372
|
||||
Resolves: CVE-2020-25632
|
||||
Resolves: CVE-2020-25647
|
||||
Resolves: CVE-2020-27749
|
||||
Resolves: CVE-2020-27779
|
||||
Resolves: CVE-2021-20225
|
||||
Resolves: CVE-2021-20233
|
||||
|
||||
* Thu Jul 30 2020 Peter Jones <pjones@redhat.com> - 15-8
|
||||
- Fix a load-address-dependent forever loop.
|
||||
Resolves: rhbz#1861977
|
||||
Related: CVE-2020-10713
|
||||
Related: CVE-2020-14308
|
||||
Related: CVE-2020-14309
|
||||
Related: CVE-2020-14310
|
||||
Related: CVE-2020-14311
|
||||
Related: CVE-2020-15705
|
||||
Related: CVE-2020-15706
|
||||
Related: CVE-2020-15707
|
||||
* Wed Mar 31 2021 Peter Jones <pjones@redhat.com> - 15.4-3
|
||||
- Build with the correct certificate trust list for this OS.
|
||||
Resolves: CVE-2020-14372
|
||||
Resolves: CVE-2020-25632
|
||||
Resolves: CVE-2020-25647
|
||||
Resolves: CVE-2020-27749
|
||||
Resolves: CVE-2020-27779
|
||||
Resolves: CVE-2021-20225
|
||||
Resolves: CVE-2021-20233
|
||||
|
||||
* Sat Jul 25 2020 Peter Jones <pjones@redhat.com> - 15-7
|
||||
- Implement Lenny's workaround
|
||||
Related: CVE-2020-10713
|
||||
Related: CVE-2020-14308
|
||||
Related: CVE-2020-14309
|
||||
Related: CVE-2020-14310
|
||||
Related: CVE-2020-14311
|
||||
* Wed Mar 31 2021 Peter Jones <pjones@redhat.com> - 15.4-2
|
||||
- Fix the ia32 build.
|
||||
Resolves: CVE-2020-14372
|
||||
Resolves: CVE-2020-25632
|
||||
Resolves: CVE-2020-25647
|
||||
Resolves: CVE-2020-27749
|
||||
Resolves: CVE-2020-27779
|
||||
Resolves: CVE-2021-20225
|
||||
Resolves: CVE-2021-20233
|
||||
|
||||
* Fri Jul 24 2020 Peter Jones <pjones@redhat.com> - 15-5
|
||||
- Once more with the MokListRT config table patch added.
|
||||
Related: CVE-2020-10713
|
||||
Related: CVE-2020-14308
|
||||
Related: CVE-2020-14309
|
||||
Related: CVE-2020-14310
|
||||
Related: CVE-2020-14311
|
||||
* Tue Mar 30 2021 Peter Jones <pjones@redhat.com> - 15.4-1
|
||||
- Update to shim 15.4
|
||||
- Support for revocations via the ".sbat" section and SBAT EFI variable
|
||||
- A new unit test framework and a bunch of unit tests
|
||||
- No external gnu-efi dependency
|
||||
- Better CI
|
||||
Resolves: CVE-2020-14372
|
||||
Resolves: CVE-2020-25632
|
||||
Resolves: CVE-2020-25647
|
||||
Resolves: CVE-2020-27749
|
||||
Resolves: CVE-2020-27779
|
||||
Resolves: CVE-2021-20225
|
||||
Resolves: CVE-2021-20233
|
||||
|
||||
* Thu Jul 23 2020 Peter Jones <pjones@redhat.com> - 15-4
|
||||
- Rebuild for bug fixes and new signing keys
|
||||
Related: CVE-2020-10713
|
||||
Related: CVE-2020-14308
|
||||
Related: CVE-2020-14309
|
||||
Related: CVE-2020-14310
|
||||
Related: CVE-2020-14311
|
||||
* Wed Mar 24 2021 Peter Jones <pjones@redhat.com> - 15.3-0~1
|
||||
- Update to shim 15.3
|
||||
- Support for revocations via the ".sbat" section and SBAT EFI variable
|
||||
- A new unit test framework and a bunch of unit tests
|
||||
- No external gnu-efi dependency
|
||||
- Better CI
|
||||
Resolves: CVE-2020-14372
|
||||
Resolves: CVE-2020-25632
|
||||
Resolves: CVE-2020-25647
|
||||
Resolves: CVE-2020-27749
|
||||
Resolves: CVE-2020-27779
|
||||
Resolves: CVE-2021-20225
|
||||
Resolves: CVE-2021-20233
|
||||
|
||||
* Wed Jun 05 2019 Javier Martinez Canillas <javierm@redhat.com> - 15-3
|
||||
- Make EFI variable copying fatal only on secureboot enabled systems
|
||||
|
Loading…
Reference in New Issue
Block a user