SHA256
1
0
forked from pool/shim

Accepting request 244530 from home:jsegitz:UEFI:openSUSE:Factory

- updated shim to new version (OpenSSL 0.9.8za) and requested a new
  certificate from Microsoft. Removed
  * shim-allow-fallback-use-system-loadimage.patch
  * shim-bnc872503-check-key-encoding.patch
  * shim-bnc877003-fetch-from-the-same-device.patch
  * shim-correct-user_insecure-usage.patch
  * shim-fallback-avoid-duplicate-bootorder.patch
  * shim-fallback-improve-entries-creation.patch
  * shim-fix-dhcpv4-path-generation.patch
  * shim-fix-uninitialized-variable.patch
  * shim-fix-verify-mok.patch
  * shim-get-variable-check.patch
  * shim-improve-error-messages.patch
  * shim-mokmanager-delete-bs-var-right.patch
  * shim-mokmanager-handle-keystroke-error.patch
  * shim-remove-unused-variables.patch
  since they're included in upstream and rebased the remaining onces.
  Added shim-signed-unsigned-compares.patch to fix some compiler
  warnings

OBS-URL: https://build.opensuse.org/request/show/244530
OBS-URL: https://build.opensuse.org/package/show/devel:openSUSE:Factory/shim?expand=0&rev=81
This commit is contained in:
Gary Ching-Pang Lin 2014-08-13 10:07:21 +00:00 committed by Git OBS Bridge
parent 23e59eef11
commit b8cbae7e99
25 changed files with 970 additions and 3469 deletions

View File

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:161cdfa33c1221b9d86241d7b9803240c91d939251a5d6b5c8d8626b8d93cf7f
size 1012687

View File

@ -1,3 +0,0 @@
version https://git-lfs.github.com/spec/v1
oid sha256:b85cabcdedfcf256e357dc2a8a0131a32f3b4619155a174465db47326c8102b7
size 988071

View File

@ -1,240 +0,0 @@
From 06495f692fa748a553ffbde8bfae2974d8c791c0 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 14 Feb 2014 15:38:25 -0500
Subject: [PATCH] Allow fallback to use the system's LoadImage/StartImage .
Track use of the system's LoadImage(), and when the next StartImage()
call is for an image the system verified, allow that to count as
participating, since it has been verified by the system's db.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
replacements.c | 68 ++++++++++++++++++++++++++++++++++++++++++++-
replacements.h | 3 ++
shim.c | 85 ++++++++++++++++++++++++++++++++++-----------------------
3 files changed, 121 insertions(+), 35 deletions(-)
--- a/replacements.c
+++ b/replacements.c
@@ -60,26 +60,82 @@
static EFI_SYSTEM_TABLE *systab;
+static typeof(systab->BootServices->LoadImage) system_load_image;
static typeof(systab->BootServices->StartImage) system_start_image;
static typeof(systab->BootServices->Exit) system_exit;
static typeof(systab->BootServices->ExitBootServices) system_exit_boot_services;
+static EFI_HANDLE last_loaded_image;
+
void
unhook_system_services(void)
{
systab->BootServices->Exit = system_exit;
+ systab->BootServices->LoadImage = system_load_image;
systab->BootServices->StartImage = system_start_image;
systab->BootServices->ExitBootServices = system_exit_boot_services;
}
static EFI_STATUS EFIAPI
+load_image(BOOLEAN BootPolicy, EFI_HANDLE ParentImageHandle,
+ EFI_DEVICE_PATH *DevicePath, VOID *SourceBuffer,
+ UINTN SourceSize, EFI_HANDLE *ImageHandle)
+{
+ EFI_STATUS status;
+ unhook_system_services();
+
+ status = systab->BootServices->LoadImage(BootPolicy,
+ ParentImageHandle, DevicePath,
+ SourceBuffer, SourceSize, ImageHandle);
+ hook_system_services(systab);
+ if (EFI_ERROR(status))
+ last_loaded_image = NULL;
+ else
+ last_loaded_image = *ImageHandle;
+ return status;
+}
+
+static EFI_STATUS EFIAPI
start_image(EFI_HANDLE image_handle, UINTN *exit_data_size, CHAR16 **exit_data)
{
EFI_STATUS status;
unhook_system_services();
+
+ /* We have to uninstall shim's protocol here, because if we're
+ * On the fallback.efi path, then our call pathway is:
+ *
+ * shim->fallback->shim->grub
+ * ^ ^ ^
+ * | | \- gets protocol #0
+ * | \- installs its protocol (#1)
+ * \- installs its protocol (#0)
+ * and if we haven't removed this, then grub will get the *first*
+ * shim's protocol, but it'll get the second shim's systab
+ * replacements. So even though it will participate and verify
+ * the kernel, the systab never finds out.
+ */
+ if (image_handle == last_loaded_image) {
+ loader_is_participating = 1;
+ uninstall_shim_protocols();
+ }
status = systab->BootServices->StartImage(image_handle, exit_data_size, exit_data);
- if (EFI_ERROR(status))
+ if (EFI_ERROR(status)) {
+ if (image_handle == last_loaded_image) {
+ EFI_STATUS status2 = install_shim_protocols();
+
+ if (EFI_ERROR(status2)) {
+ Print(L"Something has gone seriously wrong: %d\n",
+ status2);
+ Print(L"shim cannot continue, sorry.\n");
+ systab->BootServices->Stall(5000000);
+ systab->RuntimeServices->ResetSystem(
+ EfiResetShutdown,
+ EFI_SECURITY_VIOLATION, 0, NULL);
+ }
+ }
hook_system_services(systab);
+ loader_is_participating = 0;
+ }
return status;
}
@@ -123,6 +179,16 @@ hook_system_services(EFI_SYSTEM_TABLE *l
/* We need to hook various calls to make this work... */
+ /* We need LoadImage() hooked so that fallback.c can load shim
+ * without having to fake LoadImage as well. This allows it
+ * to call the system LoadImage(), and have us track the output
+ * and mark loader_is_participating in start_image. This means
+ * anything added by fallback has to be verified by the system db,
+ * which we want to preserve anyway, since that's all launching
+ * through BDS gives us. */
+ system_load_image = systab->BootServices->LoadImage;
+ systab->BootServices->LoadImage = load_image;
+
/* we need StartImage() so that we can allow chain booting to an
* image trusted by the firmware */
system_start_image = systab->BootServices->StartImage;
--- a/replacements.h
+++ b/replacements.h
@@ -41,4 +41,7 @@ extern int loader_is_participating;
extern void hook_system_services(EFI_SYSTEM_TABLE *local_systab);
extern void unhook_system_services(void);
+extern EFI_STATUS install_shim_protocols(void);
+extern void uninstall_shim_protocols(void);
+
#endif /* SHIM_REPLACEMENTS_H */
--- a/shim.c
+++ b/shim.c
@@ -1719,11 +1719,56 @@ EFI_STATUS set_second_stage (EFI_HANDLE
return EFI_SUCCESS;
}
-EFI_STATUS efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *passed_systab)
+static SHIM_LOCK shim_lock_interface;
+static EFI_HANDLE shim_lock_handle;
+
+EFI_STATUS
+install_shim_protocols(void)
+{
+ EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
+ EFI_STATUS efi_status;
+ /*
+ * Install the protocol
+ */
+ efi_status = uefi_call_wrapper(BS->InstallProtocolInterface, 4,
+ &shim_lock_handle, &shim_lock_guid,
+ EFI_NATIVE_INTERFACE, &shim_lock_interface);
+ if (EFI_ERROR(efi_status)) {
+ console_error(L"Could not install security protocol",
+ efi_status);
+ return efi_status;
+ }
+
+#if defined(OVERRIDE_SECURITY_POLICY)
+ /*
+ * Install the security protocol hook
+ */
+ security_policy_install(shim_verify);
+#endif
+
+ return EFI_SUCCESS;
+}
+
+void
+uninstall_shim_protocols(void)
{
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
- static SHIM_LOCK shim_lock_interface;
- EFI_HANDLE handle = NULL;
+#if defined(OVERRIDE_SECURITY_POLICY)
+ /*
+ * Clean up the security protocol hook
+ */
+ security_policy_uninstall();
+#endif
+
+ /*
+ * If we're back here then clean everything up before exiting
+ */
+ uefi_call_wrapper(BS->UninstallProtocolInterface, 3, shim_lock_handle,
+ &shim_lock_guid, &shim_lock_interface);
+}
+
+EFI_STATUS efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *passed_systab)
+{
EFI_STATUS efi_status;
verification_method = VERIFIED_BY_NOTHING;
@@ -1776,24 +1821,9 @@ EFI_STATUS efi_main (EFI_HANDLE image_ha
loader_is_participating = 0;
}
- /*
- * Install the protocol
- */
- efi_status = uefi_call_wrapper(BS->InstallProtocolInterface, 4,
- &handle, &shim_lock_guid, EFI_NATIVE_INTERFACE,
- &shim_lock_interface);
- if (EFI_ERROR(efi_status)) {
- console_error(L"Could not install security protocol",
- efi_status);
+ efi_status = install_shim_protocols();
+ if (EFI_ERROR(efi_status))
return efi_status;
- }
-
-#if defined(OVERRIDE_SECURITY_POLICY)
- /*
- * Install the security protocol hook
- */
- security_policy_install(shim_verify);
-#endif
/*
* Enter MokManager if necessary
@@ -1820,20 +1850,7 @@ EFI_STATUS efi_main (EFI_HANDLE image_ha
efi_status = init_grub(image_handle);
-#if defined(OVERRIDE_SECURITY_POLICY)
- /*
- * Clean up the security protocol hook
- */
- security_policy_uninstall();
-#endif
-
- /*
- * If we're back here then clean everything up before exiting
- */
- uefi_call_wrapper(BS->UninstallProtocolInterface, 3, handle,
- &shim_lock_guid, &shim_lock_interface);
-
-
+ uninstall_shim_protocols();
/*
* Remove our hooks from system services.
*/

View File

@ -11,11 +11,11 @@ Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
MokManager.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/MokManager.c b/MokManager.c
index e79a8e0..e0cc143 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -934,7 +934,9 @@ static EFI_STATUS write_back_mok_list (MokListNode *list, INTN key_num,
Index: shim-0.7/MokManager.c
===================================================================
--- shim-0.7.orig/MokManager.c
+++ shim-0.7/MokManager.c
@@ -940,7 +940,9 @@ static EFI_STATUS write_back_mok_list (M
if (list[i].Mok == NULL)
continue;
@ -26,30 +26,7 @@ index e79a8e0..e0cc143 100644
DataSize += list[i].MokSize;
}
--
1.8.4.5
From 6b70c15cd8a83e0e62088bc4f2f8e84e818d2b73 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Mon, 17 Feb 2014 17:49:55 +0800
Subject: [PATCH 2/2] MokManager: fix the hash list counting in delete
match_hash() requests the number of keys in a list and it was
mistakenly replaced with the size of the Mok node. This would
made MokManager to remove the whole Mok node instead of one
hash.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 8 ++++++--
1 file changed, 6 insertions(+), 2 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index e0cc143..5af5ce6 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -1042,6 +1042,7 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
@@ -1046,6 +1048,7 @@ static void delete_hash_in_list (UINT8 *
{
EFI_GUID HashType = EFI_CERT_SHA256_GUID;
UINT32 sig_size;
@ -57,7 +34,7 @@ index e0cc143..5af5ce6 100644
int i, del_ind;
void *start, *end;
UINT32 remain;
@@ -1053,8 +1054,10 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
@@ -1057,8 +1060,10 @@ static void delete_hash_in_list (UINT8 *
(mok[i].MokSize < sig_size))
continue;
@ -69,7 +46,7 @@ index e0cc143..5af5ce6 100644
while (del_ind >= 0) {
/* Remove the hash */
if (sig_size == mok[i].MokSize) {
@@ -1069,9 +1072,10 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
@@ -1073,9 +1078,10 @@ static void delete_hash_in_list (UINT8 *
mem_move(start, end, remain);
mok[i].MokSize -= sig_size;
@ -81,6 +58,3 @@ index e0cc143..5af5ce6 100644
}
}
}
--
1.8.4.5

View File

@ -1,140 +0,0 @@
From a7246827074c6c17fa15c696ad48ff1ff1a2b4d2 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Tue, 27 May 2014 17:42:00 +0800
Subject: [PATCH] Check the first 4 bytes of the certificate
A non-DER encoding x509 certificate may be mistakenly enrolled into
db or MokList. This commit checks the first 4 bytes of the certificate
to ensure that it's DER encoding.
This commit also removes the iteration of the x509 signature list.
Per UEFI SPEC, each x509 signature list contains only one x509 certificate.
Besides, the size of certificate is incorrect. The size of the header must
be substracted from the signature size.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 23 +++++++++++++++++++++--
shim.c | 45 +++++++++++++++++++++++++++++++--------------
2 files changed, 52 insertions(+), 16 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index 3da61f4..c9fbbac 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -1306,11 +1306,30 @@ static INTN mok_pw_prompt (void *MokPW, UINTN MokPWSize) {
return -1;
}
-static BOOLEAN verify_certificate(void *cert, UINTN size)
+static BOOLEAN verify_certificate(UINT8 *cert, UINTN size)
{
X509 *X509Cert;
- if (!cert || size == 0)
+ UINTN length;
+ if (!cert || size < 0)
+ return FALSE;
+
+ /*
+ * A DER encoding x509 certificate starts with SEQUENCE(0x30),
+ * the number of length bytes, and the number of value bytes.
+ * The size of a x509 certificate is usually between 127 bytes
+ * 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) {
+ console_notify(L"Not a DER encoding X509 certificate");
return FALSE;
+ }
+
+ length = (cert[2]<<8 | cert[3]);
+ if (length != (size - 4)) {
+ console_notify(L"Invalid X509 certificate: Inconsistent size");
+ return FALSE;
+ }
if (!(X509ConstructCertificate(cert, size, (UINT8 **) &X509Cert)) ||
X509Cert == NULL) {
diff --git a/shim.c b/shim.c
index 48a6f2f..e674079 100644
--- a/shim.c
+++ b/shim.c
@@ -226,44 +226,61 @@ static EFI_STATUS relocate_coff (PE_COFF_LOADER_IMAGE_CONTEXT *context,
return EFI_SUCCESS;
}
+static BOOLEAN verify_x509(UINT8 *Cert, UINTN CertSize)
+{
+ UINTN length;
+
+ if (!Cert || CertSize < 4)
+ return FALSE;
+
+ /*
+ * A DER encoding x509 certificate starts with SEQUENCE(0x30),
+ * the number of length bytes, and the number of value bytes.
+ * The size of a x509 certificate is usually between 127 bytes
+ * 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)
+ return FALSE;
+
+ length = Cert[2]<<8 | Cert[3];
+ if (length != (CertSize - 4))
+ return FALSE;
+
+ return TRUE;
+}
+
static CHECK_STATUS check_db_cert_in_ram(EFI_SIGNATURE_LIST *CertList,
UINTN dbsize,
WIN_CERTIFICATE_EFI_PKCS *data,
UINT8 *hash)
{
EFI_SIGNATURE_DATA *Cert;
- UINTN CertCount, Index;
+ UINTN CertSize;
BOOLEAN IsFound = FALSE;
EFI_GUID CertType = X509_GUID;
while ((dbsize > 0) && (dbsize >= CertList->SignatureListSize)) {
if (CompareGuid (&CertList->SignatureType, &CertType) == 0) {
- CertCount = (CertList->SignatureListSize - sizeof (EFI_SIGNATURE_LIST) - CertList->SignatureHeaderSize) / CertList->SignatureSize;
Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) CertList + sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
- for (Index = 0; Index < CertCount; Index++) {
+ CertSize = CertList->SignatureSize - sizeof(EFI_GUID);
+ if (verify_x509(Cert->SignatureData, CertSize)) {
IsFound = AuthenticodeVerify (data->CertData,
data->Hdr.dwLength - sizeof(data->Hdr),
Cert->SignatureData,
- CertList->SignatureSize,
+ CertSize,
hash, SHA256_DIGEST_SIZE);
if (IsFound)
- break;
-
- Cert = (EFI_SIGNATURE_DATA *) ((UINT8 *) Cert + CertList->SignatureSize);
+ return DATA_FOUND;
+ } else if (verbose) {
+ console_notify(L"Not a DER encoding x.509 Certificate");
}
-
}
- if (IsFound)
- break;
-
dbsize -= CertList->SignatureListSize;
CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList + CertList->SignatureListSize);
}
- if (IsFound)
- return DATA_FOUND;
-
return DATA_NOT_FOUND;
}
--
1.8.4.5

View File

@ -1,144 +0,0 @@
From cd92dd17fa990856d7d94f1fbb9cf08a4640915f Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Tue, 27 May 2014 14:12:32 +0800
Subject: [PATCH] Fetch the netboot image from the same device
The previous strategy is to locate the first available PXE_BASE_CODE
protocol and to fetch the second stage image from it, and this may
cause shim to fetch the wrong second stage image, i.e. grub.efi.
Consider the machine with the following boot order:
1. PXE Boot
2. Hard Drive
Assume that the EFI image, e.g. bootx64.efi, in the PXE server is
broken, then "PXE Boot" will fail and fallback to "Hard Drive". While
shim.efi in "Hard Drive" is loaded, it will find the PXE protocol is
available and fetch grub.efi from the PXE server, not grub.efi in the
disk.
This commit checks the DeviceHandle from Loaded Image. If the device
supports PXE, then shim fetches grub.efi with the PXE protocol. Otherwise,
shim loads grub.efi from the disk.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
netboot.c | 77 +++++++++++++--------------------------------------------------
shim.c | 2 +-
2 files changed, 17 insertions(+), 62 deletions(-)
diff --git a/netboot.c b/netboot.c
index 07e2773..5ef53f7 100644
--- a/netboot.c
+++ b/netboot.c
@@ -85,78 +85,33 @@ translate_slashes(char *str)
* Returns TRUE if we identify a protocol that is enabled and Providing us with
* the needed information to fetch a grubx64.efi image
*/
-BOOLEAN findNetboot(EFI_HANDLE image_handle)
+BOOLEAN findNetboot(EFI_HANDLE device)
{
- UINTN bs = sizeof(EFI_HANDLE);
- EFI_GUID pxe_base_code_protocol = EFI_PXE_BASE_CODE_PROTOCOL;
- EFI_HANDLE *hbuf;
- BOOLEAN rc = FALSE;
- void *buffer = AllocatePool(bs);
- UINTN errcnt = 0;
- UINTN i;
EFI_STATUS status;
- if (!buffer)
+ status = uefi_call_wrapper(BS->HandleProtocol, 3, device,
+ &PxeBaseCodeProtocol, (VOID **)&pxe);
+ if (status != EFI_SUCCESS) {
+ pxe = NULL;
return FALSE;
-
-try_again:
- status = uefi_call_wrapper(BS->LocateHandle,5, ByProtocol,
- &pxe_base_code_protocol, NULL, &bs,
- buffer);
-
- if (status == EFI_BUFFER_TOO_SMALL) {
- errcnt++;
- FreePool(buffer);
- if (errcnt > 1)
- return FALSE;
- buffer = AllocatePool(bs);
- if (!buffer)
- return FALSE;
- goto try_again;
}
- if (status == EFI_NOT_FOUND) {
- FreePool(buffer);
+ if (!pxe || !pxe->Mode) {
+ pxe = NULL;
return FALSE;
}
- /*
- * We have a list of pxe supporting protocols, lets see if any are
- * active
- */
- hbuf = buffer;
- pxe = NULL;
- for (i=0; i < (bs / sizeof(EFI_HANDLE)); i++) {
- status = uefi_call_wrapper(BS->OpenProtocol, 6, hbuf[i],
- &pxe_base_code_protocol,
- (void **)&pxe, image_handle, NULL,
- EFI_OPEN_PROTOCOL_GET_PROTOCOL);
-
- if (status != EFI_SUCCESS) {
- pxe = NULL;
- continue;
- }
-
- if (!pxe || !pxe->Mode) {
- pxe = NULL;
- continue;
- }
-
- if (pxe->Mode->Started && pxe->Mode->DhcpAckReceived) {
- /*
- * We've located a pxe protocol handle thats been
- * started and has received an ACK, meaning its
- * something we'll be able to get tftp server info
- * out of
- */
- rc = TRUE;
- break;
- }
-
+ if (!pxe->Mode->Started || !pxe->Mode->DhcpAckReceived) {
+ pxe = NULL;
+ return FALSE;
}
- FreePool(buffer);
- return rc;
+ /*
+ * We've located a pxe protocol handle thats been started and has
+ * received an ACK, meaning its something we'll be able to get
+ * tftp server info out of
+ */
+ return TRUE;
}
static CHAR8 *get_v6_bootfile_url(EFI_PXE_BASE_CODE_DHCPV6_PACKET *pkt)
diff --git a/shim.c b/shim.c
index 48a6f2f..d8699f9 100644
--- a/shim.c
+++ b/shim.c
@@ -1373,7 +1373,7 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
goto done;
}
- if (findNetboot(image_handle)) {
+ if (findNetboot(li->DeviceHandle)) {
efi_status = parseNetbootinfo(image_handle);
if (efi_status != EFI_SUCCESS) {
Print(L"Netboot parsing failed: %r\n", efi_status);
--
1.8.4.5

View File

@ -1,93 +0,0 @@
commit d95b24bd02cf41cca9adebd95f10609d6424d2b3
Author: Matthew Garrett <matthew.garrett@nebula.com>
Date: Tue Nov 19 10:09:13 2013 -0500
Clarify meaning of insecure_mode
insecure_mode was intended to indicate that the user had explicity disabled
checks with mokutil, which means it wasn't the opposite of secure_mode().
Change the names to clarify this and don't show the insecure mode message
unless the user has explicitly enabled that mode.
Signed-off-by: Matthew Garrett <matthew.garrett@nebula.com>
diff --git a/replacements.c b/replacements.c
index bac5e5d..5ea5c32 100644
--- a/replacements.c
+++ b/replacements.c
@@ -64,13 +64,9 @@ static typeof(systab->BootServices->StartImage) system_start_image;
static typeof(systab->BootServices->Exit) system_exit;
static typeof(systab->BootServices->ExitBootServices) system_exit_boot_services;
-extern UINT8 insecure_mode;
-
void
unhook_system_services(void)
{
- if (insecure_mode)
- return;
systab->BootServices->Exit = system_exit;
systab->BootServices->StartImage = system_start_image;
systab->BootServices->ExitBootServices = system_exit_boot_services;
@@ -123,8 +119,6 @@ exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus,
void
hook_system_services(EFI_SYSTEM_TABLE *local_systab)
{
- if (insecure_mode)
- return;
systab = local_systab;
/* We need to hook various calls to make this work... */
diff --git a/shim.c b/shim.c
index 9ae1936..524f5fc 100644
--- a/shim.c
+++ b/shim.c
@@ -85,7 +85,7 @@ int loader_is_participating;
#define EFI_IMAGE_SECURITY_DATABASE_GUID { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc, 0xda, 0xd0, 0x0e, 0x67, 0x65, 0x6f }}
-UINT8 insecure_mode;
+UINT8 user_insecure_mode;
UINT8 ignore_db;
typedef enum {
@@ -456,7 +456,7 @@ static BOOLEAN secure_mode (void)
UINT8 *Data;
UINT8 sb, setupmode;
- if (insecure_mode)
+ if (user_insecure_mode)
return FALSE;
status = get_variable(L"SecureBoot", &Data, &len, global_var);
@@ -1534,7 +1534,7 @@ static EFI_STATUS check_mok_sb (void)
UINTN MokSBStateSize = 0;
UINT32 attributes;
- insecure_mode = 0;
+ user_insecure_mode = 0;
ignore_db = 0;
status = get_variable_attr(L"MokSBState", &MokSBState, &MokSBStateSize,
@@ -1555,7 +1555,7 @@ static EFI_STATUS check_mok_sb (void)
status = EFI_ACCESS_DENIED;
} else {
if (*(UINT8 *)MokSBState == 1) {
- insecure_mode = 1;
+ user_insecure_mode = 1;
}
}
@@ -1753,10 +1753,10 @@ EFI_STATUS efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *passed_systab)
/*
* Tell the user that we're in insecure mode if necessary
*/
- if (!secure_mode()) {
+ if (user_insecure_mode) {
Print(L"Booting in insecure mode\n");
uefi_call_wrapper(BS->Stall, 1, 2000000);
- } else {
+ } else if (secure_mode()) {
/*
* Install our hooks for ExitBootServices() and StartImage()
*/

View File

@ -1,177 +0,0 @@
From 99858938a08dbdd892cc5438ec49b4262077017d Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 6 Mar 2014 11:58:36 +0800
Subject: [PATCH 1/3] [fallback] Avoid duplicate old BootOrder
set_boot_order() already copies the old BootOrder to the variable,
bootorder. Besides, we can adjust BootOrder when adding the newly
generated boot option. So, we don't have to copy the old one again
in update_boot_order(). This avoid the duplicate entries in BootOrder.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
fallback.c | 39 +++++++++++++--------------------------
1 file changed, 13 insertions(+), 26 deletions(-)
diff --git a/fallback.c b/fallback.c
index 44638ec..8aee618 100644
--- a/fallback.c
+++ b/fallback.c
@@ -204,12 +204,12 @@ add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp,
return EFI_OUT_OF_RESOURCES;
int j = 0;
+ newbootorder[0] = i & 0xffff;
if (nbootorder) {
- for (j = 0; j < nbootorder; j++)
- newbootorder[j] = bootorder[j];
+ for (j = 1; j < nbootorder + 1; j++)
+ newbootorder[j] = bootorder[j-1];
FreePool(bootorder);
}
- newbootorder[j] = i & 0xffff;
bootorder = newbootorder;
nbootorder += 1;
#ifdef DEBUG_FALLBACK
@@ -307,28 +307,17 @@ set_boot_order(void)
EFI_STATUS
update_boot_order(void)
{
- CHAR16 *oldbootorder;
UINTN size;
+ UINTN len = 0;
EFI_GUID global = EFI_GLOBAL_VARIABLE;
CHAR16 *newbootorder = NULL;
+ EFI_STATUS rc;
- oldbootorder = LibGetVariableAndSize(L"BootOrder", &global, &size);
- if (oldbootorder) {
- int n = size / sizeof (CHAR16) + nbootorder;
-
- newbootorder = AllocateZeroPool(n * sizeof (CHAR16));
- if (!newbootorder)
- return EFI_OUT_OF_RESOURCES;
- CopyMem(newbootorder, bootorder, nbootorder * sizeof (CHAR16));
- CopyMem(newbootorder + nbootorder, oldbootorder, size);
- size = n * sizeof (CHAR16);
- } else {
- size = nbootorder * sizeof(CHAR16);
- newbootorder = AllocateZeroPool(size);
- if (!newbootorder)
- return EFI_OUT_OF_RESOURCES;
- CopyMem(newbootorder, bootorder, size);
- }
+ size = nbootorder * sizeof(CHAR16);
+ newbootorder = AllocateZeroPool(size);
+ if (!newbootorder)
+ return EFI_OUT_OF_RESOURCES;
+ CopyMem(newbootorder, bootorder, size);
#ifdef DEBUG_FALLBACK
Print(L"nbootorder: %d\nBootOrder: ", size / sizeof (CHAR16));
@@ -337,13 +326,11 @@ update_boot_order(void)
Print(L"%04x ", newbootorder[j]);
Print(L"\n");
#endif
-
- if (oldbootorder) {
+ rc = uefi_call_wrapper(RT->GetVariable, 5, L"BootOrder", &global,
+ NULL, &len, NULL);
+ if (rc == EFI_BUFFER_TOO_SMALL)
LibDeleteVariable(L"BootOrder", &global);
- FreePool(oldbootorder);
- }
- EFI_STATUS rc;
rc = uefi_call_wrapper(RT->SetVariable, 5, L"BootOrder", &global,
EFI_VARIABLE_NON_VOLATILE |
EFI_VARIABLE_BOOTSERVICE_ACCESS |
--
1.8.4.5
From 80c15a7e90d8f51b09211994895a64ec5e4f5c1e Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 6 Mar 2014 10:57:02 +0800
Subject: [PATCH 2/3] [fallback] Fix the data size for boot option comparison
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
fallback.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/fallback.c b/fallback.c
index 8aee618..156115f 100644
--- a/fallback.c
+++ b/fallback.c
@@ -231,7 +231,7 @@ find_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label,
{
int size = sizeof(UINT32) + sizeof (UINT16) +
StrLen(label)*2 + 2 + DevicePathSize(dp) +
- StrLen(arguments) * 2 + 2;
+ StrLen(arguments) * 2;
CHAR8 *data = AllocateZeroPool(size);
if (!data)
--
1.8.4.5
From 70ffe93b85380a9866ebf3a99b35dde0b332cd65 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Wed, 5 Mar 2014 18:14:09 +0800
Subject: [PATCH 3/3] [fallback] Try to boot the first boot option anyway
Some UEFI implementations never care the boot options, so the
restored boot options could be just ignored and this results in
endless reboot.
To avoid this situation, this commit makes fallback.efi to
load the first matched boot option even if there is not boot
option to be restored.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
fallback.c | 13 ++++++++++---
1 file changed, 10 insertions(+), 3 deletions(-)
diff --git a/fallback.c b/fallback.c
index 156115f..777e708 100644
--- a/fallback.c
+++ b/fallback.c
@@ -226,8 +226,9 @@ add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp,
}
EFI_STATUS
-find_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label,
- CHAR16 *arguments, UINT16 *optnum)
+find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp,
+ CHAR16 *filename, CHAR16 *label, CHAR16 *arguments,
+ UINT16 *optnum)
{
int size = sizeof(UINT32) + sizeof (UINT16) +
StrLen(label)*2 + 2 + DevicePathSize(dp) +
@@ -278,6 +279,12 @@ find_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label,
continue;
/* at this point, we have duplicate data. */
+ if (!first_new_option) {
+ first_new_option = DuplicateDevicePath(fulldp);
+ first_new_option_args = arguments;
+ first_new_option_size = StrLen(arguments) * sizeof (CHAR16);
+ }
+
*optnum = i;
FreePool(candidate);
FreePool(data);
@@ -403,7 +410,7 @@ add_to_boot_list(EFI_FILE_HANDLE fh, CHAR16 *dirname, CHAR16 *filename, CHAR16 *
#endif
UINT16 option;
- rc = find_boot_option(dp, fullpath, label, arguments, &option);
+ rc = find_boot_option(dp, full_device_path, fullpath, label, arguments, &option);
if (EFI_ERROR(rc)) {
add_boot_option(dp, full_device_path, fullpath, label, arguments);
} else if (option != 0) {
--
1.8.4.5

View File

@ -1,365 +0,0 @@
From 9ba08c4e8e7cf9b001497a0752652e0ece0b2b84 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 31 Jan 2014 10:30:24 -0500
Subject: [PATCH 1/2] For HD() device paths, use just the media node and later.
UEFI 2.x section 3.1.2 provides for "short-form device path", where the
first element specified is a "hard drive media device path", so that you
can move a disk around on different buses without invalidating your
device path. Fallback has not been using this option, though in most
cases efibootmgr has.
Note that we still keep the full device path, because LoadImage()
isn't necessarily the layer where HD() works - one some systems BDS is
responsible for resolving the full path and passes that to LoadImage()
instead. So we have to do LoadImage() with the full path.
---
fallback.c | 103 ++++++++++++++++++++++++++++++++++++++++++++++---------------
1 file changed, 78 insertions(+), 25 deletions(-)
diff --git a/fallback.c b/fallback.c
index 82ddbf2..7f4201e 100644
--- a/fallback.c
+++ b/fallback.c
@@ -15,6 +15,27 @@
EFI_LOADED_IMAGE *this_image = NULL;
static EFI_STATUS
+FindSubDevicePath(EFI_DEVICE_PATH *In, UINT8 Type, UINT8 SubType,
+ EFI_DEVICE_PATH **Out)
+{
+ EFI_DEVICE_PATH *dp = In;
+ if (!In || !Out)
+ return EFI_INVALID_PARAMETER;
+
+ for (dp = In; !IsDevicePathEnd(dp); dp = NextDevicePathNode(dp)) {
+ if (DevicePathType(dp) == Type &&
+ DevicePathSubType(dp) == SubType) {
+ *Out = DuplicateDevicePath(dp);
+ if (!*Out)
+ return EFI_OUT_OF_RESOURCES;
+ return EFI_SUCCESS;
+ }
+ }
+ *Out = NULL;
+ return EFI_NOT_FOUND;
+}
+
+static EFI_STATUS
get_file_size(EFI_FILE_HANDLE fh, UINT64 *retsize)
{
EFI_STATUS rc;
@@ -93,7 +114,9 @@ make_full_path(CHAR16 *dirname, CHAR16 *filename, CHAR16 **out, UINT64 *outlen)
{
UINT64 len;
- len = StrLen(dirname) + StrLen(filename) + StrLen(L"\\EFI\\\\") + 2;
+ len = StrLen(L"\\EFI\\") + StrLen(dirname)
+ + StrLen(L"\\") + StrLen(filename)
+ + 2;
CHAR16 *fullpath = AllocateZeroPool(len*sizeof(CHAR16));
if (!fullpath) {
@@ -119,7 +142,8 @@ VOID *first_new_option_args = NULL;
UINTN first_new_option_size = 0;
EFI_STATUS
-add_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label, CHAR16 *arguments)
+add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp,
+ CHAR16 *filename, CHAR16 *label, CHAR16 *arguments)
{
static int i = 0;
CHAR16 varname[] = L"Boot0000";
@@ -136,24 +160,31 @@ add_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label, CHAR16 *ar
void *var = LibGetVariable(varname, &global);
if (!var) {
int size = sizeof(UINT32) + sizeof (UINT16) +
- StrLen(label)*2 + 2 + DevicePathSize(dp) +
- StrLen(arguments) * 2 + 2;
+ StrLen(label)*2 + 2 + DevicePathSize(hddp) +
+ StrLen(arguments) * 2;
CHAR8 *data = AllocateZeroPool(size);
CHAR8 *cursor = data;
*(UINT32 *)cursor = LOAD_OPTION_ACTIVE;
cursor += sizeof (UINT32);
- *(UINT16 *)cursor = DevicePathSize(dp);
+ *(UINT16 *)cursor = DevicePathSize(hddp);
cursor += sizeof (UINT16);
StrCpy((CHAR16 *)cursor, label);
cursor += StrLen(label)*2 + 2;
- CopyMem(cursor, dp, DevicePathSize(dp));
- cursor += DevicePathSize(dp);
+ CopyMem(cursor, hddp, DevicePathSize(hddp));
+ cursor += DevicePathSize(hddp);
StrCpy((CHAR16 *)cursor, arguments);
Print(L"Creating boot entry \"%s\" with label \"%s\" "
L"for file \"%s\"\n",
varname, label, filename);
+
+ if (!first_new_option) {
+ first_new_option = DuplicateDevicePath(fulldp);
+ first_new_option_args = arguments;
+ first_new_option_size = StrLen(arguments) * sizeof (CHAR16);
+ }
+
rc = uefi_call_wrapper(RT->SetVariable, 5, varname,
&global, EFI_VARIABLE_NON_VOLATILE |
EFI_VARIABLE_BOOTSERVICE_ACCESS |
@@ -254,7 +285,10 @@ add_to_boot_list(EFI_FILE_HANDLE fh, CHAR16 *dirname, CHAR16 *filename, CHAR16 *
if (EFI_ERROR(rc))
return rc;
- EFI_DEVICE_PATH *dph = NULL, *dpf = NULL, *dp = NULL;
+ EFI_DEVICE_PATH *dph = NULL;
+ EFI_DEVICE_PATH *file = NULL;
+ EFI_DEVICE_PATH *full_device_path = NULL;
+ EFI_DEVICE_PATH *dp = NULL;
dph = DevicePathFromHandle(this_image->DeviceHandle);
if (!dph) {
@@ -262,19 +296,31 @@ add_to_boot_list(EFI_FILE_HANDLE fh, CHAR16 *dirname, CHAR16 *filename, CHAR16 *
goto err;
}
- dpf = FileDevicePath(fh, fullpath);
- if (!dpf) {
+ file = FileDevicePath(fh, fullpath);
+ if (!file) {
rc = EFI_OUT_OF_RESOURCES;
goto err;
}
- dp = AppendDevicePath(dph, dpf);
- if (!dp) {
+ full_device_path = AppendDevicePath(dph, file);
+ if (!full_device_path) {
rc = EFI_OUT_OF_RESOURCES;
goto err;
}
+ rc = FindSubDevicePath(full_device_path,
+ MEDIA_DEVICE_PATH, MEDIA_HARDDRIVE_DP, &dp);
+ if (EFI_ERROR(rc)) {
+ if (rc == EFI_NOT_FOUND) {
+ dp = full_device_path;
+ } else {
+ rc = EFI_OUT_OF_RESOURCES;
+ goto err;
+ }
+ }
+
#ifdef DEBUG_FALLBACK
+ {
UINTN s = DevicePathSize(dp);
int i;
UINT8 *dpv = (void *)dp;
@@ -287,20 +333,16 @@ add_to_boot_list(EFI_FILE_HANDLE fh, CHAR16 *dirname, CHAR16 *filename, CHAR16 *
CHAR16 *dps = DevicePathToStr(dp);
Print(L"device path: \"%s\"\n", dps);
-#endif
- if (!first_new_option) {
- CHAR16 *dps = DevicePathToStr(dp);
- Print(L"device path: \"%s\"\n", dps);
- first_new_option = DuplicateDevicePath(dp);
- first_new_option_args = arguments;
- first_new_option_size = StrLen(arguments) * sizeof (CHAR16);
}
+#endif
- add_boot_option(dp, fullpath, label, arguments);
+ add_boot_option(dp, full_device_path, fullpath, label, arguments);
err:
- if (dpf)
- FreePool(dpf);
+ if (file)
+ FreePool(file);
+ if (full_device_path)
+ FreePool(full_device_path);
if (dp)
FreePool(dp);
if (fullpath)
@@ -622,8 +664,19 @@ try_start_first_option(EFI_HANDLE parent_image_handle)
first_new_option, NULL, 0,
&image_handle);
if (EFI_ERROR(rc)) {
- Print(L"LoadImage failed: %d\n", rc);
- uefi_call_wrapper(BS->Stall, 1, 2000000);
+ CHAR16 *dps = DevicePathToStr(first_new_option);
+ UINTN s = DevicePathSize(first_new_option);
+ int i;
+ UINT8 *dpv = (void *)first_new_option;
+ Print(L"LoadImage failed: %d\nDevice path: \"%s\"\n", rc, dps);
+ for (i = 0; i < s; i++) {
+ if (i > 0 && i % 16 == 0)
+ Print(L"\n");
+ Print(L"%02x ", dpv[i]);
+ }
+ Print(L"\n");
+
+ uefi_call_wrapper(BS->Stall, 1, 500000000);
return rc;
}
@@ -637,7 +690,7 @@ try_start_first_option(EFI_HANDLE parent_image_handle)
rc = uefi_call_wrapper(BS->StartImage, 3, image_handle, NULL, NULL);
if (EFI_ERROR(rc)) {
Print(L"StartImage failed: %d\n", rc);
- uefi_call_wrapper(BS->Stall, 1, 2000000);
+ uefi_call_wrapper(BS->Stall, 1, 500000000);
}
return rc;
}
--
1.8.4.5
From 23ed6291df5dd34789829607a97b3605b739a629 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 31 Jan 2014 10:31:10 -0500
Subject: [PATCH 2/2] Attempt to re-use existing entries when possible.
Some firmwares seem to ignore our boot entries and put their fallback
entries back on top. Right now that results in a lot of boot entries
for our stuff, a la https://bugzilla.redhat.com/show_bug.cgi?id=995834 .
Instead of that happening, if we simply find existing entries that match
the entry we would create and move them to the top of the boot order,
the machine will continue to operate in failure mode (which we can't
avoid), but at least we won't create thousands of extra entries.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
fallback.c | 99 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-
1 file changed, 98 insertions(+), 1 deletion(-)
diff --git a/fallback.c b/fallback.c
index 7f4201e..044e4ba 100644
--- a/fallback.c
+++ b/fallback.c
@@ -226,6 +226,85 @@ add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp,
}
EFI_STATUS
+find_boot_option(EFI_DEVICE_PATH *dp, CHAR16 *filename, CHAR16 *label,
+ CHAR16 *arguments, UINT16 *optnum)
+{
+ int size = sizeof(UINT32) + sizeof (UINT16) +
+ StrLen(label)*2 + 2 + DevicePathSize(dp) +
+ StrLen(arguments) * 2 + 2;
+
+ CHAR8 *data = AllocateZeroPool(size);
+ if (!data)
+ return EFI_OUT_OF_RESOURCES;
+ CHAR8 *cursor = data;
+ *(UINT32 *)cursor = LOAD_OPTION_ACTIVE;
+ cursor += sizeof (UINT32);
+ *(UINT16 *)cursor = DevicePathSize(dp);
+ cursor += sizeof (UINT16);
+ StrCpy((CHAR16 *)cursor, label);
+ cursor += StrLen(label)*2 + 2;
+ CopyMem(cursor, dp, DevicePathSize(dp));
+ cursor += DevicePathSize(dp);
+ StrCpy((CHAR16 *)cursor, arguments);
+
+ int i = 0;
+ CHAR16 varname[] = L"Boot0000";
+ CHAR16 hexmap[] = L"0123456789ABCDEF";
+ EFI_GUID global = EFI_GLOBAL_VARIABLE;
+ EFI_STATUS rc;
+
+ CHAR8 *candidate = AllocateZeroPool(size);
+ if (!candidate) {
+ FreePool(data);
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ for(i = 0; i < nbootorder && i < 0x10000; i++) {
+ varname[4] = hexmap[(bootorder[i] & 0xf000) >> 12];
+ varname[5] = hexmap[(bootorder[i] & 0x0f00) >> 8];
+ varname[6] = hexmap[(bootorder[i] & 0x00f0) >> 4];
+ varname[7] = hexmap[(bootorder[i] & 0x000f) >> 0];
+
+ UINTN candidate_size = size;
+ rc = uefi_call_wrapper(RT->GetVariable, 5, varname, &global,
+ NULL, &candidate_size, candidate);
+ if (EFI_ERROR(rc))
+ continue;
+
+ if (candidate_size != size)
+ continue;
+
+ if (CompareMem(candidate, data, size))
+ continue;
+
+ /* at this point, we have duplicate data. */
+ *optnum = i;
+ FreePool(candidate);
+ FreePool(data);
+ return EFI_SUCCESS;
+ }
+ FreePool(candidate);
+ FreePool(data);
+ return EFI_NOT_FOUND;
+}
+
+EFI_STATUS
+set_boot_order(void)
+{
+ CHAR16 *oldbootorder;
+ UINTN size;
+ EFI_GUID global = EFI_GLOBAL_VARIABLE;
+
+ oldbootorder = LibGetVariableAndSize(L"BootOrder", &global, &size);
+ if (oldbootorder) {
+ nbootorder = size / sizeof (CHAR16);
+ bootorder = oldbootorder;
+ }
+ return EFI_SUCCESS;
+
+}
+
+EFI_STATUS
update_boot_order(void)
{
CHAR16 *oldbootorder;
@@ -336,7 +415,23 @@ add_to_boot_list(EFI_FILE_HANDLE fh, CHAR16 *dirname, CHAR16 *filename, CHAR16 *
}
#endif
- add_boot_option(dp, full_device_path, fullpath, label, arguments);
+ UINT16 option;
+ rc = find_boot_option(dp, fullpath, label, arguments, &option);
+ if (EFI_ERROR(rc)) {
+ add_boot_option(dp, full_device_path, fullpath, label, arguments);
+ } else if (option != 0) {
+ CHAR16 *newbootorder;
+ newbootorder = AllocateZeroPool(sizeof (CHAR16) * nbootorder);
+ if (!newbootorder)
+ return EFI_OUT_OF_RESOURCES;
+
+ newbootorder[0] = bootorder[option];
+ CopyMem(newbootorder + 1, bootorder, sizeof (CHAR16) * option);
+ CopyMem(newbootorder + option + 1, bootorder + option + 1,
+ sizeof (CHAR16) * (nbootorder - option - 1));
+ FreePool(bootorder);
+ bootorder = newbootorder;
+ }
err:
if (file)
@@ -710,6 +805,8 @@ efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *systab)
Print(L"System BootOrder not found. Initializing defaults.\n");
+ set_boot_order();
+
rc = find_boot_options(this_image->DeviceHandle);
if (EFI_ERROR(rc)) {
Print(L"Error: could not find boot options: %d\n", rc);
--
1.8.4.5

View File

@ -1,165 +0,0 @@
From e62b69a5b0b87c6df7a4fc23906134945309e927 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Wed, 20 Nov 2013 12:20:23 -0500
Subject: [PATCH 1/2] Fix path generation for Dhcpv4 bootloader.
Right now we always look for e.g. "\grubx64.efi", which is completely
wrong. This makes it look for the path shim was loaded from and modify
that to end in a sanitized version of our default loader name.
Resolves: rhbz#1032583
Signed-off-by: Peter Jones <pjones@redhat.com>
---
include/str.h | 45 +++++++++++++++++++++++++++++++++++++++++++++
netboot.c | 28 +++++++++++++++++++++-------
2 files changed, 66 insertions(+), 7 deletions(-)
create mode 100644 include/str.h
diff --git a/include/str.h b/include/str.h
new file mode 100644
index 0000000..0f3e003
--- /dev/null
+++ b/include/str.h
@@ -0,0 +1,45 @@
+#ifndef SHIM_STR_H
+#define SHIM_STR_H
+
+static inline
+__attribute__((unused))
+unsigned long strnlena(const CHAR8 *s, unsigned long n)
+{
+ unsigned long i;
+ for (i = 0; i <= n; i++)
+ if (s[i] == '\0')
+ break;
+ return i;
+}
+
+static inline
+__attribute__((unused))
+CHAR8 *
+strncpya(CHAR8 *dest, const CHAR8 *src, unsigned long n)
+{
+ unsigned long i;
+
+ for (i = 0; i < n && src[i] != '\0'; i++)
+ dest[i] = src[i];
+ for (; i < n; i++)
+ dest[i] = '\0';
+
+ return dest;
+}
+
+static inline
+__attribute__((unused))
+CHAR8 *
+strcata(CHAR8 *dest, const CHAR8 *src)
+{
+ unsigned long dest_len = strlena(dest);
+ unsigned long i;
+
+ for (i = 0; src[i] != '\0'; i++)
+ dest[dest_len + i] = src[i];
+ dest[dest_len + i] = '\0';
+
+ return dest;
+}
+
+#endif /* SHIM_STR_H */
diff --git a/netboot.c b/netboot.c
index a83c82a..1732dc7 100644
--- a/netboot.c
+++ b/netboot.c
@@ -38,6 +38,7 @@
#include <string.h>
#include "shim.h"
#include "netboot.h"
+#include "str.h"
static inline unsigned short int __swap16(unsigned short int x)
{
@@ -305,19 +306,32 @@ static EFI_STATUS parseDhcp6()
static EFI_STATUS parseDhcp4()
{
- CHAR8 *template = (CHAR8 *)DEFAULT_LOADER_CHAR;
- full_path = AllocateZeroPool(strlen(template)+1);
+ CHAR8 *template = (CHAR8 *)translate_slashes(DEFAULT_LOADER_CHAR);
+ UINTN template_len = strlen(template) + 1;
+
+ UINTN dir_len = strnlena(pxe->Mode->DhcpAck.Dhcpv4.BootpBootFile, 127);
+ UINTN i;
+ UINT8 *dir = pxe->Mode->DhcpAck.Dhcpv4.BootpBootFile;
+
+ for (i = dir_len; i >= 0; i--) {
+ if (dir[i] == '/')
+ break;
+ }
+ dir_len = (i >= 0) ? i + 1 : 0;
+
+ full_path = AllocateZeroPool(dir_len + template_len);
if (!full_path)
return EFI_OUT_OF_RESOURCES;
+ if (dir_len > 0) {
+ strncpya(full_path, dir, dir_len);
+ if (full_path[dir_len-1] == '/' && template[0] == '/')
+ full_path[dir_len-1] = '\0';
+ }
+ strcata(full_path, template);
memcpy(&tftp_addr.v4, pxe->Mode->DhcpAck.Dhcpv4.BootpSiAddr, 4);
- memcpy(full_path, template, strlen(template));
-
- /* Note we don't capture the filename option here because we know its shim.efi
- * We instead assume the filename at the end of the path is going to be grubx64.efi
- */
return EFI_SUCCESS;
}
--
1.8.1.4
From 27129a5a05d1947e6f7479766e8281d50d6031f6 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Thu, 21 Nov 2013 11:26:08 -0500
Subject: [PATCH 2/2] Lengths that might be -1 can't be unsigned, Peter.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
netboot.c | 8 +++++---
1 file changed, 5 insertions(+), 3 deletions(-)
diff --git a/netboot.c b/netboot.c
index 1732dc7..07e2773 100644
--- a/netboot.c
+++ b/netboot.c
@@ -307,10 +307,10 @@ static EFI_STATUS parseDhcp6()
static EFI_STATUS parseDhcp4()
{
CHAR8 *template = (CHAR8 *)translate_slashes(DEFAULT_LOADER_CHAR);
- UINTN template_len = strlen(template) + 1;
+ INTN template_len = strlen(template) + 1;
- UINTN dir_len = strnlena(pxe->Mode->DhcpAck.Dhcpv4.BootpBootFile, 127);
- UINTN i;
+ INTN dir_len = strnlena(pxe->Mode->DhcpAck.Dhcpv4.BootpBootFile, 127);
+ INTN i;
UINT8 *dir = pxe->Mode->DhcpAck.Dhcpv4.BootpBootFile;
for (i = dir_len; i >= 0; i--) {
@@ -329,6 +329,8 @@ static EFI_STATUS parseDhcp4()
if (full_path[dir_len-1] == '/' && template[0] == '/')
full_path[dir_len-1] = '\0';
}
+ if (dir_len == 0 && dir[0] != '/' && template[0] == '/')
+ template++;
strcata(full_path, template);
memcpy(&tftp_addr.v4, pxe->Mode->DhcpAck.Dhcpv4.BootpSiAddr, 4);
--
1.8.1.4

View File

@ -1,60 +0,0 @@
From ccf21ef9a8868aacf9084400a15d73fcc24a6d39 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 15 Nov 2013 09:21:53 -0500
Subject: [PATCH 1/2] Fix wrong sizeof().
CHAR16* vs CHAR16**, so the result is the same on all platforms.
Detected by coverity.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
lib/shell.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/lib/shell.c b/lib/shell.c
index 51de4e0..7337834 100644
--- a/lib/shell.c
+++ b/lib/shell.c
@@ -35,7 +35,7 @@ argsplit(EFI_HANDLE image, int *argc, CHAR16*** ARGV)
(*argc)++; /* we counted spaces, so add one for initial */
- *ARGV = AllocatePool(*argc * sizeof(*ARGV));
+ *ARGV = AllocatePool(*argc * sizeof(**ARGV));
if (!*ARGV) {
return EFI_OUT_OF_RESOURCES;
}
--
1.8.4.5
From c4277cf343555646dbf0c17679108983af1e8887 Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 15 Nov 2013 09:24:01 -0500
Subject: [PATCH 2/2] Initialize entries before we pass it to another function.
Coverity scan noticed that entries is uninitialized when we pass its
location to another function.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
lib/simple_file.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/lib/simple_file.c b/lib/simple_file.c
index 3af0ec8..d345d87 100644
--- a/lib/simple_file.c
+++ b/lib/simple_file.c
@@ -415,7 +415,7 @@ simple_file_selector(EFI_HANDLE *im, CHAR16 **title, CHAR16 *name,
CHAR16 *filter, CHAR16 **result)
{
EFI_STATUS status;
- CHAR16 **entries;
+ CHAR16 **entries = NULL;
EFI_FILE_INFO *dmp;
int count, select, len;
CHAR16 *newname, *selected;
--
1.8.4.5

View File

@ -1,49 +0,0 @@
commit 11495d4019d44dce1487939f91f7d751ffbb9730
Author: Andrew Boie <andrew.p.boie@intel.com>
Date: Mon Apr 15 14:11:17 2013 -0700
fix verify_mok()
() Fix the return value semantics. If the MokList doesn't
exist, we are OK. If the MokList was compromised but we
were able to erase it, that is OK too. Only if the list
can't be nuked do we return an error.
() Fix use of potentially uninitialized attribute variable
() Actually use the return value when called from verify_buffer.
Change-Id: If16df21d79c52a1726928df96d133390cde4cb7e
Signed-off-by: Andrew Boie <andrew.p.boie@intel.com>
diff --git a/shim.c b/shim.c
index 23dd0ee..dcb36d0 100644
--- a/shim.c
+++ b/shim.c
@@ -670,13 +670,12 @@ static EFI_STATUS verify_mok (void) {
status = get_variable_attr(L"MokList", &MokListData, &MokListDataSize,
shim_lock_guid, &attributes);
- if (attributes & EFI_VARIABLE_RUNTIME_ACCESS) {
+ if (!EFI_ERROR(status) && attributes & EFI_VARIABLE_RUNTIME_ACCESS) {
Print(L"MokList is compromised!\nErase all keys in MokList!\n");
if (LibDeleteVariable(L"MokList", &shim_lock_guid) != EFI_SUCCESS) {
Print(L"Failed to erase MokList\n");
+ return EFI_ACCESS_DENIED;
}
- status = EFI_ACCESS_DENIED;
- return status;
}
if (MokListData)
@@ -722,7 +721,9 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
/*
* Check that the MOK database hasn't been modified
*/
- verify_mok();
+ status = verify_mok();
+ if (status != EFI_SUCCESS)
+ return status;
/*
* Ensure that the binary isn't blacklisted

View File

@ -1,27 +0,0 @@
From 293f28d1fe3921c5348c60948b4dedcef5042d5b Mon Sep 17 00:00:00 2001
From: Peter Jones <pjones@redhat.com>
Date: Fri, 15 Nov 2013 10:55:37 -0500
Subject: [PATCH] Error check the right thing in get_variable_attr() when
allocating.
Signed-off-by: Peter Jones <pjones@redhat.com>
---
lib/variables.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/lib/variables.c b/lib/variables.c
index 81bd34d..3a9735e 100644
--- a/lib/variables.c
+++ b/lib/variables.c
@@ -224,7 +224,7 @@ get_variable_attr(CHAR16 *var, UINT8 **data, UINTN *len, EFI_GUID owner,
return efi_status;
*data = AllocateZeroPool(*len);
- if (!data)
+ if (!*data)
return EFI_OUT_OF_RESOURCES;
efi_status = uefi_call_wrapper(RT->GetVariable, 5, var, &owner,
--
1.8.4.5

View File

@ -1,181 +0,0 @@
commit 2f09d0ab290d9b0d8aa14c3243f1d85a20bc34e6
Author: Andrew Boie <andrew.p.boie@intel.com>
Date: Mon Nov 11 17:29:06 2013 -0800
shim: improve error messages
%r when used in Print() will show a string representation of
an EFI_STATUS code.
Change-Id: I6db47f5213454603bd66177aca378ad01e9f0bd4
Signed-off-by: Andrew Boie <andrew.p.boie@intel.com>
diff --git a/shim.c b/shim.c
index a043779..9ae1936 100644
--- a/shim.c
+++ b/shim.c
@@ -914,7 +914,7 @@ static EFI_STATUS handle_image (void *data, unsigned int datasize,
*/
efi_status = read_header(data, datasize, &context);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to read header\n");
+ Print(L"Failed to read header: %r\n", efi_status);
return efi_status;
}
@@ -981,7 +981,7 @@ static EFI_STATUS handle_image (void *data, unsigned int datasize,
efi_status = relocate_coff(&context, buffer);
if (efi_status != EFI_SUCCESS) {
- Print(L"Relocation failed\n");
+ Print(L"Relocation failed: %r\n", efi_status);
FreePool(buffer);
return efi_status;
}
@@ -1022,7 +1022,7 @@ should_use_fallback(EFI_HANDLE image_handle)
rc = uefi_call_wrapper(BS->HandleProtocol, 3, image_handle,
&loaded_image_protocol, (void **)&li);
if (EFI_ERROR(rc)) {
- Print(L"Could not get image for bootx64.efi: %d\n", rc);
+ Print(L"Could not get image for bootx64.efi: %r\n", rc);
return 0;
}
@@ -1044,13 +1044,13 @@ should_use_fallback(EFI_HANDLE image_handle)
rc = uefi_call_wrapper(BS->HandleProtocol, 3, li->DeviceHandle,
&FileSystemProtocol, (void **)&fio);
if (EFI_ERROR(rc)) {
- Print(L"Could not get fio for li->DeviceHandle: %d\n", rc);
+ Print(L"Could not get fio for li->DeviceHandle: %r\n", rc);
return 0;
}
rc = uefi_call_wrapper(fio->OpenVolume, 2, fio, &vh);
if (EFI_ERROR(rc)) {
- Print(L"Could not open fio volume: %d\n", rc);
+ Print(L"Could not open fio volume: %r\n", rc);
return 0;
}
@@ -1172,14 +1172,14 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data,
(void **)&drive);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to find fs\n");
+ Print(L"Failed to find fs: %r\n", efi_status);
goto error;
}
efi_status = uefi_call_wrapper(drive->OpenVolume, 2, drive, &root);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to open fs\n");
+ Print(L"Failed to open fs: %r\n", efi_status);
goto error;
}
@@ -1190,7 +1190,7 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data,
EFI_FILE_MODE_READ, 0);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to open %s - %lx\n", PathName, efi_status);
+ Print(L"Failed to open %s - %r\n", PathName, efi_status);
goto error;
}
@@ -1223,7 +1223,7 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data,
}
if (efi_status != EFI_SUCCESS) {
- Print(L"Unable to get file info\n");
+ Print(L"Unable to get file info: %r\n", efi_status);
goto error;
}
@@ -1251,7 +1251,7 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data,
}
if (efi_status != EFI_SUCCESS) {
- Print(L"Unexpected return from initial read: %x, buffersize %x\n", efi_status, buffersize);
+ Print(L"Unexpected return from initial read: %r, buffersize %x\n", efi_status, buffersize);
goto error;
}
@@ -1328,20 +1328,20 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
efi_status = generate_path(li, ImagePath, &path, &PathName);
if (efi_status != EFI_SUCCESS) {
- Print(L"Unable to generate path: %s\n", ImagePath);
+ Print(L"Unable to generate path %s: %r\n", ImagePath, efi_status);
goto done;
}
if (findNetboot(image_handle)) {
efi_status = parseNetbootinfo(image_handle);
if (efi_status != EFI_SUCCESS) {
- Print(L"Netboot parsing failed: %d\n", efi_status);
+ Print(L"Netboot parsing failed: %r\n", efi_status);
return EFI_PROTOCOL_ERROR;
}
efi_status = FetchNetbootimage(image_handle, &sourcebuffer,
&sourcesize);
if (efi_status != EFI_SUCCESS) {
- Print(L"Unable to fetch TFTP image\n");
+ Print(L"Unable to fetch TFTP image: %r\n", efi_status);
return efi_status;
}
data = sourcebuffer;
@@ -1353,7 +1353,7 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
efi_status = load_image(li, &data, &datasize, PathName);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to load image\n");
+ Print(L"Failed to load image %s: %r\n", PathName, efi_status);
goto done;
}
}
@@ -1370,7 +1370,7 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
efi_status = handle_image(data, datasize, li);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to load image\n");
+ Print(L"Failed to load image: %r\n", efi_status);
CopyMem(li, &li_bak, sizeof(li_bak));
goto done;
}
@@ -1473,7 +1473,7 @@ EFI_STATUS mirror_mok_list()
| EFI_VARIABLE_RUNTIME_ACCESS,
FullDataSize, FullData);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to set MokListRT %d\n", efi_status);
+ Print(L"Failed to set MokListRT: %r\n", efi_status);
}
return efi_status;
@@ -1514,7 +1514,7 @@ EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
efi_status = start_image(image_handle, MOK_MANAGER);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to start MokManager\n");
+ Print(L"Failed to start MokManager: %r\n", efi_status);
return efi_status;
}
}
@@ -1621,7 +1621,7 @@ static EFI_STATUS mok_ignore_db()
| EFI_VARIABLE_RUNTIME_ACCESS,
DataSize, (void *)&Data);
if (efi_status != EFI_SUCCESS) {
- Print(L"Failed to set MokIgnoreDB %d\n", efi_status);
+ Print(L"Failed to set MokIgnoreDB: %r\n", efi_status);
}
}
@@ -1648,7 +1648,7 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle)
status = uefi_call_wrapper(BS->HandleProtocol, 3, image_handle,
&LoadedImageProtocol, (void **) &li);
if (status != EFI_SUCCESS) {
- Print (L"Failed to get load options\n");
+ Print (L"Failed to get load options: %r\n", status);
return status;
}

View File

@ -1,69 +0,0 @@
From 3c545d630917d76d91a8491f8759927f512e56f2 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Fri, 7 Mar 2014 16:56:14 +0800
Subject: [PATCH] MokManager: delete the BS+NV variables the right way
LibDeleteVariable assumes that the variable is RT+NV and it
won't work on a BS+NV variable.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 28 +++++++++++++++++++++++++---
1 file changed, 25 insertions(+), 3 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index f5ed379..4ea28ef 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -1112,7 +1112,16 @@ static INTN mok_sb_prompt (void *MokSB, UINTN MokSBSize) {
return -1;
}
} else {
- LibDeleteVariable(L"MokSBState", &shim_lock_guid);
+ efi_status = uefi_call_wrapper(RT->SetVariable,
+ 5, L"MokSBState",
+ &shim_lock_guid,
+ EFI_VARIABLE_NON_VOLATILE |
+ EFI_VARIABLE_BOOTSERVICE_ACCESS,
+ 0, NULL);
+ if (efi_status != EFI_SUCCESS) {
+ console_notify(L"Failed to delete Secure Boot state");
+ return -1;
+ }
}
console_notify(L"The system must now be rebooted");
@@ -1224,7 +1233,16 @@ static INTN mok_db_prompt (void *MokDB, UINTN MokDBSize) {
return -1;
}
} else {
- LibDeleteVariable(L"MokDBState", &shim_lock_guid);
+ efi_status = uefi_call_wrapper(RT->SetVariable, 5,
+ L"MokDBState",
+ &shim_lock_guid,
+ EFI_VARIABLE_NON_VOLATILE |
+ EFI_VARIABLE_BOOTSERVICE_ACCESS,
+ 0, NULL);
+ if (efi_status != EFI_SUCCESS) {
+ console_notify(L"Failed to delete DB state");
+ return -1;
+ }
}
console_notify(L"The system must now be rebooted");
@@ -1261,7 +1279,11 @@ static INTN mok_pw_prompt (void *MokPW, UINTN MokPWSize) {
if (console_yes_no((CHAR16 *[]){L"Clear MOK password?", NULL}) == 0)
return 0;
- LibDeleteVariable(L"MokPWStore", &shim_lock_guid);
+ uefi_call_wrapper(RT->SetVariable, 5, L"MokPWStore",
+ &shim_lock_guid,
+ EFI_VARIABLE_NON_VOLATILE
+ | EFI_VARIABLE_BOOTSERVICE_ACCESS,
+ 0, NULL);
LibDeleteVariable(L"MokPW", &shim_lock_guid);
console_notify(L"The system must now be rebooted");
uefi_call_wrapper(RT->ResetSystem, 4, EfiResetWarm, EFI_SUCCESS, 0,
--
1.8.4.5

View File

@ -1,157 +0,0 @@
From 7edfcaa6e03c8aa1ce39e8eb193d2064f4119342 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Tue, 3 Dec 2013 15:52:02 +0800
Subject: [PATCH] MokManager: handle the error status from ReadKeyStroke
On some machines, even though the key event was signaled, ReadKeyStroke
still got EFI_NOT_READY. This commit handles the error status to avoid
console_get_keystroke from returning unexpected keys.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 17 +++++++++++++----
include/console.h | 4 ++--
lib/console.c | 26 ++++++++++++++++++--------
3 files changed, 33 insertions(+), 14 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index f5ed379..d700fa8 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -488,13 +488,19 @@ static EFI_STATUS list_keys (void *KeyList, UINTN KeyListSize, CHAR16 *title)
return EFI_SUCCESS;
}
-static UINT8 get_line (UINT32 *length, CHAR16 *line, UINT32 line_max, UINT8 show)
+static EFI_STATUS get_line (UINT32 *length, CHAR16 *line, UINT32 line_max, UINT8 show)
{
EFI_INPUT_KEY key;
+ EFI_STATUS status;
int count = 0;
do {
- key = console_get_keystroke();
+ status = console_get_keystroke(&key);
+ if (EFI_ERROR (status)) {
+ console_error(L"Failed to read the keystroke", status);
+ *length = 0;
+ return status;
+ }
if ((count >= line_max &&
key.UnicodeChar != CHAR_BACKSPACE) ||
@@ -525,7 +531,7 @@ static UINT8 get_line (UINT32 *length, CHAR16 *line, UINT32 line_max, UINT8 show
*length = count;
- return 1;
+ return EFI_SUCCESS;
}
static EFI_STATUS compute_pw_hash (void *Data, UINTN DataSize, UINT8 *password,
@@ -989,6 +995,7 @@ static INTN mok_deletion_prompt (void *MokDel, UINTN MokDelSize)
static CHAR16 get_password_charater (CHAR16 *prompt)
{
SIMPLE_TEXT_OUTPUT_MODE SavedMode;
+ EFI_STATUS status;
CHAR16 *message[2];
CHAR16 character;
UINTN length;
@@ -1003,7 +1010,9 @@ static CHAR16 get_password_charater (CHAR16 *prompt)
message[1] = NULL;
length = StrLen(message[0]);
console_print_box_at(message, -1, -length-4, -5, length+4, 3, 0, 1);
- get_line(&pw_length, &character, 1, 0);
+ status = get_line(&pw_length, &character, 1, 0);
+ if (EFI_ERROR(status))
+ character = 0;
console_restore_mode(&SavedMode);
diff --git a/include/console.h b/include/console.h
index e6c2818..9c793ea 100644
--- a/include/console.h
+++ b/include/console.h
@@ -1,8 +1,8 @@
#ifndef _SHIM_LIB_CONSOLE_H
#define _SHIM_LIB_CONSOLE_H 1
-EFI_INPUT_KEY
-console_get_keystroke(void);
+EFI_STATUS
+console_get_keystroke(EFI_INPUT_KEY *key);
void
console_print_box_at(CHAR16 *str_arr[], int highlight, int start_col, int start_row, int size_cols, int size_rows, int offset, int lines);
void
diff --git a/lib/console.c b/lib/console.c
index 2fc8db3..41ed83a 100644
--- a/lib/console.c
+++ b/lib/console.c
@@ -40,16 +40,18 @@ SetMem16(CHAR16 *dst, UINT32 n, CHAR16 c)
}
}
-EFI_INPUT_KEY
-console_get_keystroke(void)
+EFI_STATUS
+console_get_keystroke(EFI_INPUT_KEY *key)
{
- EFI_INPUT_KEY key;
UINTN EventIndex;
+ EFI_STATUS status;
- uefi_call_wrapper(BS->WaitForEvent, 3, 1, &ST->ConIn->WaitForKey, &EventIndex);
- uefi_call_wrapper(ST->ConIn->ReadKeyStroke, 2, ST->ConIn, &key);
+ do {
+ uefi_call_wrapper(BS->WaitForEvent, 3, 1, &ST->ConIn->WaitForKey, &EventIndex);
+ status = uefi_call_wrapper(ST->ConIn->ReadKeyStroke, 2, ST->ConIn, key);
+ } while (status == EFI_NOT_READY);
- return key;
+ return status;
}
void
@@ -162,6 +164,8 @@ console_print_box(CHAR16 *str_arr[], int highlight)
{
SIMPLE_TEXT_OUTPUT_MODE SavedConsoleMode;
SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
+ EFI_INPUT_KEY key;
+
CopyMem(&SavedConsoleMode, co->Mode, sizeof(SavedConsoleMode));
uefi_call_wrapper(co->EnableCursor, 2, co, FALSE);
uefi_call_wrapper(co->SetAttribute, 2, co, EFI_LIGHTGRAY | EFI_BACKGROUND_BLUE);
@@ -169,7 +173,7 @@ console_print_box(CHAR16 *str_arr[], int highlight)
console_print_box_at(str_arr, highlight, 0, 0, -1, -1, 0,
count_lines(str_arr));
- console_get_keystroke();
+ console_get_keystroke(&key);
uefi_call_wrapper(co->EnableCursor, 2, co, SavedConsoleMode.CursorVisible);
@@ -184,6 +188,7 @@ console_select(CHAR16 *title[], CHAR16* selectors[], int start)
SIMPLE_TEXT_OUTPUT_MODE SavedConsoleMode;
SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut;
EFI_INPUT_KEY k;
+ EFI_STATUS status;
int selector;
int selector_lines = count_lines(selectors);
int selector_max_cols = 0;
@@ -237,7 +242,12 @@ console_select(CHAR16 *title[], CHAR16* selectors[], int start)
size_cols, size_rows, 0, lines);
do {
- k = console_get_keystroke();
+ status = console_get_keystroke(&k);
+ if (EFI_ERROR (status)) {
+ Print(L"Failed to read the keystroke: %r", status);
+ selector = -1;
+ break;
+ }
if (k.ScanCode == SCAN_ESC) {
selector = -1;
--
1.8.4

View File

@ -9,23 +9,42 @@ other SHA digests.
MokManager.c | 121 ++++++++++++++++++++++++++++++++++++-----------------------
1 file changed, 75 insertions(+), 46 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index 5af5ce6..7cf31c1 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -93,27 +93,58 @@ done:
Index: shim-0.7/MokManager.c
===================================================================
--- shim-0.7.orig/MokManager.c
+++ shim-0.7/MokManager.c
@@ -25,6 +25,9 @@
#define EFI_VARIABLE_APPEND_WRITE 0x00000040
EFI_GUID SHIM_LOCK_GUID = { 0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23} };
+EFI_GUID EFI_CERT_SHA224_GUID = { 0xb6e5233, 0xa65c, 0x44c9, {0x94, 0x7, 0xd9, 0xab, 0x83, 0xbf, 0xc8, 0xbd} };
+EFI_GUID EFI_CERT_SHA384_GUID = { 0xff3e5307, 0x9fd0, 0x48c9, {0x85, 0xf1, 0x8a, 0xd5, 0x6c, 0x70, 0x1e, 0x1} };
+EFI_GUID EFI_CERT_SHA512_GUID = { 0x93e0fae, 0xa6c4, 0x4f50, {0x9f, 0x1b, 0xd4, 0x1e, 0x2b, 0x89, 0xc1, 0x9a} };
#define CERT_STRING L"Select an X509 certificate to enroll:\n\n"
#define HASH_STRING L"Select a file to trust:\n\n"
@@ -93,31 +96,84 @@ done:
return status;
}
+static BOOLEAN is_sha_hash (EFI_GUID Type)
+{
+ EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
+ EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
+
+ if (CompareGuid(&Type, &Sha1) == 0)
+ return TRUE;
+ else if (CompareGuid(&Type, &Sha224) == 0)
+ return TRUE;
+ else if (CompareGuid(&Type, &Sha256) == 0)
+ return TRUE;
+ else if (CompareGuid(&Type, &Sha384) == 0)
+ return TRUE;
+ else if (CompareGuid(&Type, &Sha512) == 0)
+ return TRUE;
+
+ return FALSE;
+}
@ -33,12 +52,21 @@ index 5af5ce6..7cf31c1 100644
+static UINT32 sha_size (EFI_GUID Type)
+{
+ EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
+ EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
+
+ if (CompareGuid(&Type, &Sha1) == 0)
+ return SHA1_DIGEST_SIZE;
+ else if (CompareGuid(&Type, &Sha224) == 0)
+ return SHA224_DIGEST_LENGTH;
+ else if (CompareGuid(&Type, &Sha256) == 0)
+ return SHA256_DIGEST_SIZE;
+ else if (CompareGuid(&Type, &Sha384) == 0)
+ return SHA384_DIGEST_LENGTH;
+ else if (CompareGuid(&Type, &Sha512) == 0)
+ return SHA512_DIGEST_LENGTH;
+
+ return 0;
+}
@ -77,16 +105,26 @@ index 5af5ce6..7cf31c1 100644
- CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList +
- CertList->SignatureListSize);
- continue;
- }
-
+ if (CertList->SignatureListSize == 0 ||
+ CertList->SignatureListSize <= CertList->SignatureSize) {
+ console_errorbox(L"Corrupted signature list");
+ return 0;
}
- if ((CompareGuid (&CertList->SignatureType, &CertType) != 0) &&
- (CertList->SignatureSize != 48)) {
- console_notify(L"Doesn't look like a valid hash");
- dbsize -= CertList->SignatureListSize;
- CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList +
- CertList->SignatureListSize);
- continue;
+ if (!is_valid_siglist(CertList->SignatureType, CertList->SignatureSize)) {
dbsize -= CertList->SignatureListSize;
CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList +
CertList->SignatureListSize);
@@ -134,7 +165,6 @@ static MokListNode *build_mok_list(UINT32 num, void *Data, UINTN DataSize) {
+ console_errorbox(L"Invalid signature list found");
+ return 0;
}
MokNum++;
@@ -134,7 +190,6 @@ static MokListNode *build_mok_list(UINT3
EFI_SIGNATURE_LIST *CertList = Data;
EFI_SIGNATURE_DATA *Cert;
EFI_GUID CertType = X509_GUID;
@ -94,7 +132,7 @@ index 5af5ce6..7cf31c1 100644
UINTN dbsize = DataSize;
UINTN count = 0;
@@ -146,16 +176,7 @@ static MokListNode *build_mok_list(UINT32 num, void *Data, UINTN DataSize) {
@@ -146,21 +201,8 @@ static MokListNode *build_mok_list(UINT3
}
while ((dbsize > 0) && (dbsize >= CertList->SignatureListSize)) {
@ -108,11 +146,17 @@ index 5af5ce6..7cf31c1 100644
-
- if ((CompareGuid (&CertList->SignatureType, &HashType) == 0) &&
- (CertList->SignatureSize != 48)) {
+ if (!is_valid_siglist(CertList->SignatureType, CertList->SignatureSize)) {
dbsize -= CertList->SignatureListSize;
CertList = (EFI_SIGNATURE_LIST *)((UINT8 *) CertList +
CertList->SignatureListSize);
@@ -380,22 +401,34 @@ static void show_x509_info (X509 *X509Cert, UINT8 *hash)
- dbsize -= CertList->SignatureListSize;
- CertList = (EFI_SIGNATURE_LIST *)((UINT8 *) CertList +
- CertList->SignatureListSize);
- continue;
- }
+ /* Omit the signature check here since we already did it
+ in count_keys() */
Cert = (EFI_SIGNATURE_DATA *) (((UINT8 *) CertList) +
sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
@@ -380,22 +422,46 @@ static void show_x509_info (X509 *X509Ce
FreePool(text);
}
@ -120,7 +164,10 @@ index 5af5ce6..7cf31c1 100644
+static void show_sha_digest (EFI_GUID Type, UINT8 *hash)
{
+ EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
+ EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
CHAR16 *text[5];
POOL_PRINT hash_string1;
POOL_PRINT hash_string2;
@ -130,9 +177,18 @@ index 5af5ce6..7cf31c1 100644
+ if (CompareGuid(&Type, &Sha1) == 0) {
+ length = SHA1_DIGEST_SIZE;
+ text[0] = L"SHA1 hash";
+ } else if (CompareGuid(&Type, &Sha224) == 0) {
+ length = SHA224_DIGEST_LENGTH;
+ text[0] = L"SHA224 hash";
+ } else if (CompareGuid(&Type, &Sha256) == 0) {
+ length = SHA256_DIGEST_SIZE;
+ text[0] = L"SHA256 hash";
+ } else if (CompareGuid(&Type, &Sha384) == 0) {
+ length = SHA384_DIGEST_LENGTH;
+ text[0] = L"SHA384 hash";
+ } else if (CompareGuid(&Type, &Sha512) == 0) {
+ length = SHA512_DIGEST_LENGTH;
+ text[0] = L"SHA512 hash";
+ } else {
+ return;
+ }
@ -151,7 +207,7 @@ index 5af5ce6..7cf31c1 100644
CatPrint(&hash_string2, L"%02x ", hash[i]);
text[2] = hash_string1.str;
@@ -411,7 +444,7 @@ static void show_sha256_digest (UINT8 *hash)
@@ -411,7 +477,7 @@ static void show_sha256_digest (UINT8 *h
FreePool(hash_string2.str);
}
@ -160,7 +216,7 @@ index 5af5ce6..7cf31c1 100644
{
UINTN sig_size;
UINTN hash_num;
@@ -420,7 +453,7 @@ static void show_efi_hash (void *Mok, UINTN MokSize)
@@ -420,7 +486,7 @@ static void show_efi_hash (void *Mok, UI
int key_num = 0;
int i;
@ -169,7 +225,7 @@ index 5af5ce6..7cf31c1 100644
if ((MokSize % sig_size) != 0) {
console_errorbox(L"Corrupted Hash List");
return;
@@ -429,7 +462,7 @@ static void show_efi_hash (void *Mok, UINTN MokSize)
@@ -429,7 +495,7 @@ static void show_efi_hash (void *Mok, UI
if (hash_num == 1) {
hash = (UINT8 *)Mok + sizeof(EFI_GUID);
@ -178,7 +234,7 @@ index 5af5ce6..7cf31c1 100644
return;
}
@@ -452,7 +485,7 @@ static void show_efi_hash (void *Mok, UINTN MokSize)
@@ -452,7 +518,7 @@ static void show_efi_hash (void *Mok, UI
break;
hash = (UINT8 *)Mok + sig_size*key_num + sizeof(EFI_GUID);
@ -187,7 +243,7 @@ index 5af5ce6..7cf31c1 100644
}
for (i=0; menu_strings[i] != NULL; i++)
@@ -467,7 +500,6 @@ static void show_mok_info (EFI_GUID Type, void *Mok, UINTN MokSize)
@@ -467,7 +533,6 @@ static void show_mok_info (EFI_GUID Type
UINT8 hash[SHA1_DIGEST_SIZE];
X509 *X509Cert;
EFI_GUID CertType = X509_GUID;
@ -195,7 +251,7 @@ index 5af5ce6..7cf31c1 100644
if (!Mok || MokSize == 0)
return;
@@ -488,8 +520,8 @@ static void show_mok_info (EFI_GUID Type, void *Mok, UINTN MokSize)
@@ -488,8 +553,8 @@ static void show_mok_info (EFI_GUID Type
console_notify(L"Not a valid X509 certificate");
return;
}
@ -206,94 +262,7 @@ index 5af5ce6..7cf31c1 100644
}
}
@@ -968,7 +1000,7 @@ static EFI_STATUS write_back_mok_list (MokListNode *list, INTN key_num,
} else {
CertList->SignatureListSize = list[i].MokSize +
sizeof(EFI_SIGNATURE_LIST);
- CertList->SignatureSize = SHA256_DIGEST_SIZE + sizeof(EFI_GUID);
+ CertList->SignatureSize = sha_size(list[i].Type) + sizeof(EFI_GUID);
CopyMem(CertData, list[i].Mok, list[i].MokSize);
}
@@ -1040,7 +1072,6 @@ static void mem_move (void *dest, void *src, UINTN size)
static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
MokListNode *mok, INTN mok_num)
{
- EFI_GUID HashType = EFI_CERT_SHA256_GUID;
UINT32 sig_size;
UINT32 list_num;
int i, del_ind;
@@ -1050,8 +1081,7 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
sig_size = hash_size + sizeof(EFI_GUID);
for (i = 0; i < mok_num; i++) {
- if ((CompareGuid(&(mok[i].Type), &HashType) != 0) ||
- (mok[i].MokSize < sig_size))
+ if (!is_sha_hash(mok[i].Type) || (mok[i].MokSize < sig_size))
continue;
list_num = mok[i].MokSize / sig_size;
@@ -1080,7 +1110,7 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
}
}
-static void delete_hash_list (void *hash_list, UINT32 list_size,
+static void delete_hash_list (EFI_GUID Type, void *hash_list, UINT32 list_size,
MokListNode *mok, INTN mok_num)
{
UINT32 hash_size;
@@ -1089,7 +1119,7 @@ static void delete_hash_list (void *hash_list, UINT32 list_size,
UINT8 *hash;
int i;
- hash_size = SHA256_DIGEST_SIZE;
+ hash_size = sha_size (Type);
sig_size = hash_size + sizeof(EFI_GUID);
if (list_size < sig_size)
return;
@@ -1108,7 +1138,6 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
{
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
EFI_GUID CertType = X509_GUID;
- EFI_GUID HashType = EFI_CERT_SHA256_GUID;
EFI_STATUS efi_status;
CHAR16 *db_name;
CHAR16 *auth_name;
@@ -1183,9 +1212,9 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
if (CompareGuid(&(del_key[i].Type), &CertType) == 0) {
delete_cert(del_key[i].Mok, del_key[i].MokSize,
mok, mok_num);
- } else if (CompareGuid(&(del_key[i].Type), &HashType) == 0) {
- delete_hash_list(del_key[i].Mok, del_key[i].MokSize,
- mok, mok_num);
+ } else if (is_sha_hash(del_key[i].Type)) {
+ delete_hash_list(del_key[i].Type, del_key[i].Mok,
+ del_key[i].MokSize, mok, mok_num);
}
}
--
1.8.4.5
From 9a0aaf045859be5ba3abdaaf06683cb9ab0b6c57 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Wed, 9 Apr 2014 16:49:25 +0800
Subject: [PATCH 2/5] MokManager: fix the return value and type
There are some functions that the return value and the type
didn't match.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index 7cf31c1..b09f5b8 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -536,7 +536,7 @@ static EFI_STATUS list_keys (void *KeyList, UINTN KeyListSize, CHAR16 *title)
@@ -504,15 +569,18 @@ static EFI_STATUS list_keys (void *KeyLi
if (KeyListSize < (sizeof(EFI_SIGNATURE_LIST) +
sizeof(EFI_SIGNATURE_DATA))) {
console_notify(L"No MOK keys found");
@ -301,59 +270,6 @@ index 7cf31c1..b09f5b8 100644
+ return EFI_NOT_FOUND;
}
MokNum = count_keys(KeyList, KeyListSize);
@@ -544,7 +544,7 @@ static EFI_STATUS list_keys (void *KeyList, UINTN KeyListSize, CHAR16 *title)
if (!keys) {
console_notify(L"Failed to construct key list");
- return 0;
+ return EFI_ABORTED;
}
menu_strings = AllocateZeroPool(sizeof(CHAR16 *) * (MokNum + 2));
@@ -863,7 +863,7 @@ static EFI_STATUS store_keys (void *MokNew, UINTN MokNewSize, int authenticate,
return EFI_SUCCESS;
}
-static UINTN mok_enrollment_prompt (void *MokNew, UINTN MokNewSize, int auth,
+static INTN mok_enrollment_prompt (void *MokNew, UINTN MokNewSize, int auth,
BOOLEAN MokX)
{
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
--
1.8.4.5
From 790eb376dbe692d4702d807f24c1be7a492a5717 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 10 Apr 2014 14:39:43 +0800
Subject: [PATCH 3/5] MokManager: Add more key list safe checks
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++----
1 file changed, 56 insertions(+), 4 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index b09f5b8..c5501f3 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -144,6 +144,12 @@ static UINT32 count_keys(void *Data, UINTN DataSize)
UINT32 MokNum = 0;
while ((dbsize > 0) && (dbsize >= CertList->SignatureListSize)) {
+ if (CertList->SignatureListSize == 0 ||
+ CertList->SignatureListSize <= CertList->SignatureSize) {
+ console_errorbox(L"Corrupted signature list");
+ return 0;
+ }
+
if (!is_valid_siglist(CertList->SignatureType, CertList->SignatureSize)) {
dbsize -= CertList->SignatureListSize;
CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList +
@@ -540,10 +546,13 @@ static EFI_STATUS list_keys (void *KeyList, UINTN KeyListSize, CHAR16 *title)
}
MokNum = count_keys(KeyList, KeyListSize);
+ if (MokNum == 0) {
+ console_errorbox(L"Invalid key list");
@ -363,11 +279,87 @@ index b09f5b8..c5501f3 100644
-
if (!keys) {
- console_notify(L"Failed to construct key list");
- return 0;
+ console_errorbox(L"Failed to construct key list");
return EFI_ABORTED;
+ return EFI_ABORTED;
}
@@ -1184,7 +1193,13 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
menu_strings = AllocateZeroPool(sizeof(CHAR16 *) * (MokNum + 2));
@@ -837,7 +905,7 @@ static EFI_STATUS store_keys (void *MokN
return EFI_SUCCESS;
}
-static UINTN mok_enrollment_prompt (void *MokNew, UINTN MokNewSize, int auth,
+static INTN mok_enrollment_prompt (void *MokNew, UINTN MokNewSize, int auth,
BOOLEAN MokX)
{
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
@@ -974,7 +1042,7 @@ static EFI_STATUS write_back_mok_list (M
} else {
CertList->SignatureListSize = list[i].MokSize +
sizeof(EFI_SIGNATURE_LIST);
- CertList->SignatureSize = SHA256_DIGEST_SIZE + sizeof(EFI_GUID);
+ CertList->SignatureSize = sha_size(list[i].Type) + sizeof(EFI_GUID);
CopyMem(CertData, list[i].Mok, list[i].MokSize);
}
@@ -1043,10 +1111,9 @@ static void mem_move (void *dest, void *
d[i] = s[i];
}
-static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
+static void delete_hash_in_list (EFI_GUID Type, UINT8 *hash, UINT32 hash_size,
MokListNode *mok, INTN mok_num)
{
- EFI_GUID HashType = EFI_CERT_SHA256_GUID;
UINT32 sig_size;
UINT32 list_num;
int i, del_ind;
@@ -1056,7 +1123,7 @@ static void delete_hash_in_list (UINT8 *
sig_size = hash_size + sizeof(EFI_GUID);
for (i = 0; i < mok_num; i++) {
- if ((CompareGuid(&(mok[i].Type), &HashType) != 0) ||
+ if ((CompareGuid(&(mok[i].Type), &Type) != 0) ||
(mok[i].MokSize < sig_size))
continue;
@@ -1086,7 +1153,7 @@ static void delete_hash_in_list (UINT8 *
}
}
-static void delete_hash_list (void *hash_list, UINT32 list_size,
+static void delete_hash_list (EFI_GUID Type, void *hash_list, UINT32 list_size,
MokListNode *mok, INTN mok_num)
{
UINT32 hash_size;
@@ -1095,7 +1162,7 @@ static void delete_hash_list (void *hash
UINT8 *hash;
int i;
- hash_size = SHA256_DIGEST_SIZE;
+ hash_size = sha_size (Type);
sig_size = hash_size + sizeof(EFI_GUID);
if (list_size < sig_size)
return;
@@ -1105,7 +1172,7 @@ static void delete_hash_list (void *hash
hash = hash_list + sizeof(EFI_GUID);
for (i = 0; i < hash_num; i++) {
- delete_hash_in_list (hash, hash_size, mok, mok_num);
+ delete_hash_in_list (Type, hash, hash_size, mok, mok_num);
hash += sig_size;
}
}
@@ -1114,7 +1181,6 @@ static EFI_STATUS delete_keys (void *Mok
{
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
EFI_GUID CertType = X509_GUID;
- EFI_GUID HashType = EFI_CERT_SHA256_GUID;
EFI_STATUS efi_status;
CHAR16 *db_name;
CHAR16 *auth_name;
@@ -1161,7 +1227,13 @@ static EFI_STATUS delete_keys (void *Mok
efi_status = get_variable_attr (db_name, &MokListData, &MokListDataSize,
shim_lock_guid, &attributes);
@ -382,7 +374,7 @@ index b09f5b8..c5501f3 100644
if (MokX) {
err_str1 = L"MokListX is compromised!";
err_str2 = L"Erase all keys in MokListX!";
@@ -1193,7 +1208,11 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
@@ -1170,7 +1242,11 @@ static EFI_STATUS delete_keys (void *Mok
err_str2 = L"Erase all keys in MokList!";
}
console_alertbox((CHAR16 *[]){err_str1, err_str2, NULL});
@ -395,7 +387,7 @@ index b09f5b8..c5501f3 100644
return EFI_ACCESS_DENIED;
}
@@ -1203,9 +1222,41 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
@@ -1180,23 +1256,56 @@ static EFI_STATUS delete_keys (void *Mok
/* Construct lists */
mok_num = count_keys(MokListData, MokListDataSize);
@ -437,7 +429,17 @@ index b09f5b8..c5501f3 100644
/* Search and destroy */
for (i = 0; i < del_num; i++) {
@@ -1220,6 +1271,7 @@ static EFI_STATUS delete_keys (void *MokDel, UINTN MokDelSize, BOOLEAN MokX)
if (CompareGuid(&(del_key[i].Type), &CertType) == 0) {
delete_cert(del_key[i].Mok, del_key[i].MokSize,
mok, mok_num);
- } else if (CompareGuid(&(del_key[i].Type), &HashType) == 0) {
- delete_hash_list(del_key[i].Mok, del_key[i].MokSize,
- mok, mok_num);
+ } else if (is_sha_hash(del_key[i].Type)) {
+ delete_hash_list(del_key[i].Type, del_key[i].Mok,
+ del_key[i].MokSize, mok, mok_num);
}
}
efi_status = write_back_mok_list(mok, mok_num, MokX);
@ -445,183 +447,3 @@ index b09f5b8..c5501f3 100644
if (MokListData)
FreePool(MokListData);
if (mok)
--
1.8.4.5
From a2879e575439b019d1eff5b32ca8b59d1e2e1503 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 10 Apr 2014 15:29:14 +0800
Subject: [PATCH 4/5] MokManager: Support SHA224, SHA384, and SHA512
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 40 +++++++++++++++++++++++++++++++++++++---
1 file changed, 37 insertions(+), 3 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index c5501f3..117cf9b 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -25,6 +25,9 @@
#define EFI_VARIABLE_APPEND_WRITE 0x00000040
EFI_GUID SHIM_LOCK_GUID = { 0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23} };
+EFI_GUID EFI_CERT_SHA224_GUID = { 0xb6e5233, 0xa65c, 0x44c9, {0x94, 0x7, 0xd9, 0xab, 0x83, 0xbf, 0xc8, 0xbd} };
+EFI_GUID EFI_CERT_SHA384_GUID = { 0xff3e5307, 0x9fd0, 0x48c9, {0x85, 0xf1, 0x8a, 0xd5, 0x6c, 0x70, 0x1e, 0x1} };
+EFI_GUID EFI_CERT_SHA512_GUID = { 0x93e0fae, 0xa6c4, 0x4f50, {0x9f, 0x1b, 0xd4, 0x1e, 0x2b, 0x89, 0xc1, 0x9a} };
#define CERT_STRING L"Select an X509 certificate to enroll:\n\n"
#define HASH_STRING L"Select a file to trust:\n\n"
@@ -96,12 +99,21 @@ done:
static BOOLEAN is_sha_hash (EFI_GUID Type)
{
EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
if (CompareGuid(&Type, &Sha1) == 0)
return TRUE;
+ else if (CompareGuid(&Type, &Sha224) == 0)
+ return TRUE;
else if (CompareGuid(&Type, &Sha256) == 0)
return TRUE;
+ else if (CompareGuid(&Type, &Sha384) == 0)
+ return TRUE;
+ else if (CompareGuid(&Type, &Sha512) == 0)
+ return TRUE;
return FALSE;
}
@@ -109,12 +121,21 @@ static BOOLEAN is_sha_hash (EFI_GUID Type)
static UINT32 sha_size (EFI_GUID Type)
{
EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
if (CompareGuid(&Type, &Sha1) == 0)
return SHA1_DIGEST_SIZE;
+ else if (CompareGuid(&Type, &Sha224) == 0)
+ return SHA224_DIGEST_LENGTH;
else if (CompareGuid(&Type, &Sha256) == 0)
return SHA256_DIGEST_SIZE;
+ else if (CompareGuid(&Type, &Sha384) == 0)
+ return SHA384_DIGEST_LENGTH;
+ else if (CompareGuid(&Type, &Sha512) == 0)
+ return SHA512_DIGEST_LENGTH;
return 0;
}
@@ -410,7 +431,10 @@ static void show_x509_info (X509 *X509Cert, UINT8 *hash)
static void show_sha_digest (EFI_GUID Type, UINT8 *hash)
{
EFI_GUID Sha1 = EFI_CERT_SHA1_GUID;
+ EFI_GUID Sha224 = EFI_CERT_SHA224_GUID;
EFI_GUID Sha256 = EFI_CERT_SHA256_GUID;
+ EFI_GUID Sha384 = EFI_CERT_SHA384_GUID;
+ EFI_GUID Sha512 = EFI_CERT_SHA512_GUID;
CHAR16 *text[5];
POOL_PRINT hash_string1;
POOL_PRINT hash_string2;
@@ -420,9 +444,18 @@ static void show_sha_digest (EFI_GUID Type, UINT8 *hash)
if (CompareGuid(&Type, &Sha1) == 0) {
length = SHA1_DIGEST_SIZE;
text[0] = L"SHA1 hash";
+ } else if (CompareGuid(&Type, &Sha224) == 0) {
+ length = SHA224_DIGEST_LENGTH;
+ text[0] = L"SHA224 hash";
} else if (CompareGuid(&Type, &Sha256) == 0) {
length = SHA256_DIGEST_SIZE;
text[0] = L"SHA256 hash";
+ } else if (CompareGuid(&Type, &Sha384) == 0) {
+ length = SHA384_DIGEST_LENGTH;
+ text[0] = L"SHA384 hash";
+ } else if (CompareGuid(&Type, &Sha512) == 0) {
+ length = SHA512_DIGEST_LENGTH;
+ text[0] = L"SHA512 hash";
} else {
return;
}
@@ -1078,7 +1111,7 @@ static void mem_move (void *dest, void *src, UINTN size)
d[i] = s[i];
}
-static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
+static void delete_hash_in_list (EFI_GUID Type, UINT8 *hash, UINT32 hash_size,
MokListNode *mok, INTN mok_num)
{
UINT32 sig_size;
@@ -1090,7 +1123,8 @@ static void delete_hash_in_list (UINT8 *hash, UINT32 hash_size,
sig_size = hash_size + sizeof(EFI_GUID);
for (i = 0; i < mok_num; i++) {
- if (!is_sha_hash(mok[i].Type) || (mok[i].MokSize < sig_size))
+ if ((CompareGuid(&(mok[i].Type), &Type) != 0) ||
+ (mok[i].MokSize < sig_size))
continue;
list_num = mok[i].MokSize / sig_size;
@@ -1138,7 +1172,7 @@ static void delete_hash_list (EFI_GUID Type, void *hash_list, UINT32 list_size,
hash = hash_list + sizeof(EFI_GUID);
for (i = 0; i < hash_num; i++) {
- delete_hash_in_list (hash, hash_size, mok, mok_num);
+ delete_hash_in_list (Type, hash, hash_size, mok, mok_num);
hash += sig_size;
}
}
--
1.8.4.5
From 04955238a98734aac8df7ad46a732e130681acfd Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 10 Apr 2014 15:55:35 +0800
Subject: [PATCH 5/5] MokManager: Discard the list contains an invalid
signature
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
MokManager.c | 14 ++++----------
1 file changed, 4 insertions(+), 10 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index 117cf9b..b896836 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -172,10 +172,8 @@ static UINT32 count_keys(void *Data, UINTN DataSize)
}
if (!is_valid_siglist(CertList->SignatureType, CertList->SignatureSize)) {
- dbsize -= CertList->SignatureListSize;
- CertList = (EFI_SIGNATURE_LIST *) ((UINT8 *) CertList +
- CertList->SignatureListSize);
- continue;
+ console_errorbox(L"Invalid signature list found");
+ return 0;
}
MokNum++;
@@ -203,12 +201,8 @@ static MokListNode *build_mok_list(UINT32 num, void *Data, UINTN DataSize) {
}
while ((dbsize > 0) && (dbsize >= CertList->SignatureListSize)) {
- if (!is_valid_siglist(CertList->SignatureType, CertList->SignatureSize)) {
- dbsize -= CertList->SignatureListSize;
- CertList = (EFI_SIGNATURE_LIST *)((UINT8 *) CertList +
- CertList->SignatureListSize);
- continue;
- }
+ /* Omit the signature check here since we already did it
+ in count_keys() */
Cert = (EFI_SIGNATURE_DATA *) (((UINT8 *) CertList) +
sizeof (EFI_SIGNATURE_LIST) + CertList->SignatureHeaderSize);
--
1.8.4.5

File diff suppressed because it is too large Load Diff

View File

@ -1,8 +1,8 @@
diff --git a/Makefile b/Makefile
index 91e6bcd..6ed5ba7 100644
--- a/Makefile
+++ b/Makefile
@@ -63,7 +63,7 @@ shim_cert.h: shim.cer
Index: shim-0.7/Makefile
===================================================================
--- shim-0.7.orig/Makefile
+++ shim-0.7/Makefile
@@ -67,7 +67,7 @@ shim_cert.h: shim.cer
version.c : version.c.in
sed -e "s,@@VERSION@@,$(VERSION)," \

View File

@ -20,11 +20,11 @@ The state will store in use_openSUSE_cert, a volatile RT variable.
shim.c | 116 ++++++++++++++++++++++++++++++++++++++++++++++++++++++-----------
1 file changed, 97 insertions(+), 19 deletions(-)
diff --git a/shim.c b/shim.c
index 3921028..1335d61 100644
--- a/shim.c
+++ b/shim.c
@@ -82,6 +82,7 @@ UINT8 *vendor_dbx;
Index: shim-0.7/shim.c
===================================================================
--- shim-0.7.orig/shim.c
+++ shim-0.7/shim.c
@@ -90,6 +90,7 @@ UINT8 *vendor_dbx;
*/
verification_method_t verification_method;
int loader_is_participating;
@ -32,7 +32,7 @@ index 3921028..1335d61 100644
#define EFI_IMAGE_SECURITY_DATABASE_GUID { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc, 0xda, 0xd0, 0x0e, 0x67, 0x65, 0x6f }}
@@ -769,7 +770,7 @@ static EFI_STATUS verify_buffer (char *data, int datasize,
@@ -817,7 +818,7 @@ static EFI_STATUS verify_buffer (char *d
if (status == EFI_SUCCESS)
return status;
@ -41,7 +41,7 @@ index 3921028..1335d61 100644
/*
* Check against the shim build key
*/
@@ -1430,11 +1431,14 @@ EFI_STATUS mirror_mok_list()
@@ -1523,11 +1524,14 @@ EFI_STATUS mirror_mok_list()
if (efi_status != EFI_SUCCESS)
DataSize = 0;
@ -60,8 +60,8 @@ index 3921028..1335d61 100644
+ }
FullData = AllocatePool(FullDataSize);
if (!FullData) {
Print(L"Failed to allocate space for MokListRT\n");
@@ -1446,21 +1450,24 @@ EFI_STATUS mirror_mok_list()
perror(L"Failed to allocate space for MokListRT\n");
@@ -1539,21 +1543,24 @@ EFI_STATUS mirror_mok_list()
CopyMem(p, Data, DataSize);
p += DataSize;
}
@ -69,7 +69,7 @@ index 3921028..1335d61 100644
- p += sizeof (*CertList);
- CertData = (EFI_SIGNATURE_DATA *)p;
- p += sizeof (EFI_GUID);
-
- CertList->SignatureType = EFI_CERT_X509_GUID;
- CertList->SignatureListSize = vendor_cert_size
- + sizeof (*CertList)
@ -77,14 +77,15 @@ index 3921028..1335d61 100644
- -1;
- CertList->SignatureHeaderSize = 0;
- CertList->SignatureSize = vendor_cert_size + sizeof (EFI_GUID);
- CertData->SignatureOwner = SHIM_LOCK_GUID;
- CopyMem(p, vendor_cert, vendor_cert_size);
+ if (use_builtin_cert) {
+ CertList = (EFI_SIGNATURE_LIST *)p;
+ p += sizeof (*CertList);
+ CertData = (EFI_SIGNATURE_DATA *)p;
+ p += sizeof (EFI_GUID);
- CertData->SignatureOwner = SHIM_LOCK_GUID;
- CopyMem(p, vendor_cert, vendor_cert_size);
+
+ CertList->SignatureType = EFI_CERT_X509_GUID;
+ CertList->SignatureListSize = vendor_cert_size
+ + sizeof (*CertList)
@ -99,7 +100,16 @@ index 3921028..1335d61 100644
efi_status = uefi_call_wrapper(RT->SetVariable, 5, L"MokListRT",
&shim_lock_guid,
@@ -1779,6 +1786,75 @@ uninstall_shim_protocols(void)
@@ -1600,7 +1607,7 @@ EFI_STATUS check_mok_request(EFI_HANDLE
check_var(L"MokPW") || check_var(L"MokAuth") ||
check_var(L"MokDel") || check_var(L"MokDB") ||
check_var(L"MokXNew") || check_var(L"MokXDel") ||
- check_var(L"MokXAuth")) {
+ check_var(L"MokXAuth") || check_var(L"ClearVerify")) {
efi_status = start_image(image_handle, MOK_MANAGER);
if (efi_status != EFI_SUCCESS) {
@@ -1840,6 +1847,75 @@ uninstall_shim_protocols(void)
&shim_lock_guid, &shim_lock_interface);
}
@ -175,39 +185,20 @@ index 3921028..1335d61 100644
EFI_STATUS efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *passed_systab)
{
EFI_STATUS efi_status;
@@ -1831,6 +1907,8 @@ EFI_STATUS efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *passed_systab)
@@ -1895,6 +1971,8 @@ EFI_STATUS efi_main (EFI_HANDLE image_ha
*/
hook_system_services(systab);
loader_is_participating = 0;
+ if (builtin_cert_prompt() != 0)
+ return EFI_ABORTED;
}
}
efi_status = install_shim_protocols();
--
1.8.4.5
From 6a53209ece97f3e1ca34b73473b5bc57284bd669 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Thu, 20 Feb 2014 16:57:08 +0800
Subject: [PATCH 2/3] Support revoking the openSUSE cert
This is an openSUSE-only patch.
To revoke the openSUSE cert, create ClearVerify, a NV RT variable,
and store the password hash in the variable, and then MokManager
will show up with an additional option to clear openSUSE_Verify
---
MokManager.c | 61 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++--
shim.c | 2 +-
2 files changed, 60 insertions(+), 3 deletions(-)
diff --git a/MokManager.c b/MokManager.c
index dbfb67a..c6589e9 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -1701,6 +1701,33 @@ static INTN mok_pw_prompt (void *MokPW, UINTN MokPWSize) {
Index: shim-0.7/MokManager.c
===================================================================
--- shim-0.7.orig/MokManager.c
+++ shim-0.7/MokManager.c
@@ -1701,6 +1701,36 @@ static INTN mok_pw_prompt (void *MokPW,
return -1;
}
@ -225,7 +216,10 @@ index dbfb67a..c6589e9 100644
+ if (status != EFI_SUCCESS)
+ return -1;
+
+ status = LibDeleteVariable(L"openSUSE_Verify", &shim_lock_guid);
+ status = uefi_call_wrapper(RT->SetVariable, 5,
+ L"openSUSE_Verify", &shim_lock_guid,
+ EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
+ 0, NULL);
+ if (status != EFI_SUCCESS) {
+ console_error(L"Failed to delete openSUSE_Verify", status);
+ return -1;
@ -241,7 +235,7 @@ index dbfb67a..c6589e9 100644
static BOOLEAN verify_certificate(UINT8 *cert, UINTN size)
{
X509 *X509Cert;
@@ -2053,6 +2080,7 @@ typedef enum {
@@ -2053,6 +2083,7 @@ typedef enum {
MOK_CHANGE_SB,
MOK_SET_PW,
MOK_CHANGE_DB,
@ -249,7 +243,7 @@ index dbfb67a..c6589e9 100644
MOK_KEY_ENROLL,
MOK_HASH_ENROLL
} mok_menu_item;
@@ -2064,7 +2092,8 @@ static EFI_STATUS enter_mok_menu(EFI_HANDLE image_handle,
@@ -2064,7 +2095,8 @@ static EFI_STATUS enter_mok_menu(EFI_HAN
void *MokPW, UINTN MokPWSize,
void *MokDB, UINTN MokDBSize,
void *MokXNew, UINTN MokXNewSize,
@ -259,7 +253,7 @@ index dbfb67a..c6589e9 100644
{
CHAR16 **menu_strings;
mok_menu_item *menu_item;
@@ -2138,6 +2167,9 @@ static EFI_STATUS enter_mok_menu(EFI_HANDLE image_handle,
@@ -2138,6 +2170,9 @@ static EFI_STATUS enter_mok_menu(EFI_HAN
if (MokDB)
menucount++;
@ -269,7 +263,7 @@ index dbfb67a..c6589e9 100644
menu_strings = AllocateZeroPool(sizeof(CHAR16 *) * (menucount + 1));
if (!menu_strings)
@@ -2207,6 +2239,12 @@ static EFI_STATUS enter_mok_menu(EFI_HANDLE image_handle,
@@ -2207,6 +2242,12 @@ static EFI_STATUS enter_mok_menu(EFI_HAN
i++;
}
@ -282,7 +276,7 @@ index dbfb67a..c6589e9 100644
menu_strings[i] = L"Enroll key from disk";
menu_item[i] = MOK_KEY_ENROLL;
i++;
@@ -2257,6 +2295,9 @@ static EFI_STATUS enter_mok_menu(EFI_HANDLE image_handle,
@@ -2257,6 +2298,9 @@ static EFI_STATUS enter_mok_menu(EFI_HAN
case MOK_CHANGE_DB:
mok_db_prompt(MokDB, MokDBSize);
break;
@ -292,7 +286,7 @@ index dbfb67a..c6589e9 100644
case MOK_KEY_ENROLL:
mok_key_enroll();
break;
@@ -2282,6 +2323,7 @@ static EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
@@ -2282,6 +2326,7 @@ static EFI_STATUS check_mok_request(EFI_
EFI_GUID shim_lock_guid = SHIM_LOCK_GUID;
UINTN MokNewSize = 0, MokDelSize = 0, MokSBSize = 0, MokPWSize = 0;
UINTN MokDBSize = 0, MokXNewSize = 0, MokXDelSize = 0;
@ -300,7 +294,7 @@ index dbfb67a..c6589e9 100644
void *MokNew = NULL;
void *MokDel = NULL;
void *MokSB = NULL;
@@ -2289,6 +2331,7 @@ static EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
@@ -2289,6 +2334,7 @@ static EFI_STATUS check_mok_request(EFI_
void *MokDB = NULL;
void *MokXNew = NULL;
void *MokXDel = NULL;
@ -308,7 +302,7 @@ index dbfb67a..c6589e9 100644
EFI_STATUS status;
status = get_variable(L"MokNew", (UINT8 **)&MokNew, &MokNewSize,
@@ -2361,9 +2404,20 @@ static EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
@@ -2361,9 +2407,20 @@ static EFI_STATUS check_mok_request(EFI_
console_error(L"Could not retrieve MokXDel", status);
}
@ -330,7 +324,7 @@ index dbfb67a..c6589e9 100644
if (MokNew)
FreePool (MokNew);
@@ -2386,6 +2440,9 @@ static EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
@@ -2386,6 +2443,9 @@ static EFI_STATUS check_mok_request(EFI_
if (MokXDel)
FreePool (MokXDel);
@ -340,51 +334,3 @@ index dbfb67a..c6589e9 100644
LibDeleteVariable(L"MokAuth", &shim_lock_guid);
LibDeleteVariable(L"MokDelAuth", &shim_lock_guid);
LibDeleteVariable(L"MokXAuth", &shim_lock_guid);
diff --git a/shim.c b/shim.c
index 1335d61..3c7cbe8 100644
--- a/shim.c
+++ b/shim.c
@@ -1541,7 +1541,7 @@ EFI_STATUS check_mok_request(EFI_HANDLE image_handle)
check_var(L"MokPW") || check_var(L"MokAuth") ||
check_var(L"MokDel") || check_var(L"MokDB") ||
check_var(L"MokXNew") || check_var(L"MokXDel") ||
- check_var(L"MokXAuth")) {
+ check_var(L"MokXAuth") || check_var(L"ClearVerify")) {
efi_status = start_image(image_handle, MOK_MANAGER);
if (efi_status != EFI_SUCCESS) {
--
1.8.4.5
From 437fb0feb6fd0dd321bd4e4cdbbf0095bda5f715 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Fri, 7 Mar 2014 16:17:20 +0800
Subject: [PATCH 3/3] Delete openSUSE_Verify the right way
This is an openSUSE-only patch.
LibDeleteVariable only works on the runtime variables.
---
MokManager.c | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/MokManager.c b/MokManager.c
index c6589e9..a08385a 100644
--- a/MokManager.c
+++ b/MokManager.c
@@ -1715,7 +1715,10 @@ static INTN mok_clear_verify_prompt(void *ClearVerify, UINTN ClearVerifySize) {
if (status != EFI_SUCCESS)
return -1;
- status = LibDeleteVariable(L"openSUSE_Verify", &shim_lock_guid);
+ status = uefi_call_wrapper(RT->SetVariable, 5,
+ L"openSUSE_Verify", &shim_lock_guid,
+ EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON_VOLATILE,
+ 0, NULL);
if (status != EFI_SUCCESS) {
console_error(L"Failed to delete openSUSE_Verify", status);
return -1;
--
1.8.4.5

View File

@ -1,63 +0,0 @@
From c5d0105fb66be43c0f5f96778e750e9cf7a2cdce Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <glin@suse.com>
Date: Mon, 26 May 2014 16:49:10 +0800
Subject: [PATCH] Remove grubpath in generate_path()
The variable is not used anymore.
Signed-off-by: Gary Ching-Pang Lin <glin@suse.com>
---
shim.c | 9 ++-------
1 file changed, 2 insertions(+), 7 deletions(-)
diff --git a/shim.c b/shim.c
index 0b20191..7966cbd 100644
--- a/shim.c
+++ b/shim.c
@@ -1060,16 +1060,14 @@ should_use_fallback(EFI_HANDLE image_handle)
* of the executable
*/
static EFI_STATUS generate_path(EFI_LOADED_IMAGE *li, CHAR16 *ImagePath,
- EFI_DEVICE_PATH **grubpath, CHAR16 **PathName)
+ CHAR16 **PathName)
{
EFI_DEVICE_PATH *devpath;
- EFI_HANDLE device;
int i, j, last = -1;
unsigned int pathlen = 0;
EFI_STATUS efi_status = EFI_SUCCESS;
CHAR16 *bootpath;
- device = li->DeviceHandle;
devpath = li->FilePath;
bootpath = DevicePathToStr(devpath);
@@ -1122,8 +1120,6 @@ static EFI_STATUS generate_path(EFI_LOADED_IMAGE *li, CHAR16 *ImagePath,
StrCat(*PathName, bootpath);
StrCat(*PathName, ImagePath);
- *grubpath = FileDevicePath(device, *PathName);
-
error:
FreePool(bootpath);
@@ -1286,7 +1282,6 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
EFI_GUID loaded_image_protocol = LOADED_IMAGE_PROTOCOL;
EFI_STATUS efi_status;
EFI_LOADED_IMAGE *li, li_bak;
- EFI_DEVICE_PATH *path;
CHAR16 *PathName = NULL;
void *sourcebuffer = NULL;
UINT64 sourcesize = 0;
@@ -1308,7 +1303,7 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath)
/*
* Build a new path from the existing one plus the executable name
*/
- efi_status = generate_path(li, ImagePath, &path, &PathName);
+ efi_status = generate_path(li, ImagePath, &PathName);
if (efi_status != EFI_SUCCESS) {
Print(L"Unable to generate path %s: %r\n", ImagePath, efi_status);
--
1.8.4.5

View File

@ -0,0 +1,51 @@
Index: shim-0.7/MokManager.c
===================================================================
--- shim-0.7.orig/MokManager.c
+++ shim-0.7/MokManager.c
@@ -483,8 +483,8 @@ static void show_efi_hash (EFI_GUID Type
UINTN hash_num;
UINT8 *hash;
CHAR16 **menu_strings;
- int key_num = 0;
- int i;
+ UINTN key_num = 0;
+ UINTN i;
sig_size = sha_size(Type) + sizeof(EFI_GUID);
if ((MokSize % sig_size) != 0) {
@@ -562,7 +562,7 @@ static EFI_STATUS list_keys (void *KeyLi
{
UINT32 MokNum = 0;
MokListNode *keys = NULL;
- int key_num = 0;
+ UINT32 key_num = 0;
CHAR16 **menu_strings;
unsigned int i;
@@ -1088,7 +1088,7 @@ static int match_hash (UINT8 *hash, UINT
void *hash_list, UINT32 list_num)
{
UINT8 *ptr;
- int i;
+ UINTN i;
ptr = hash_list + sizeof(EFI_GUID);
for (i = start; i < list_num; i++) {
@@ -1103,7 +1103,7 @@ static int match_hash (UINT8 *hash, UINT
static void mem_move (void *dest, void *src, UINTN size)
{
UINT8 *d, *s;
- int i;
+ UINTN i;
d = (UINT8 *)dest;
s = (UINT8 *)src;
@@ -1160,7 +1160,7 @@ static void delete_hash_list (EFI_GUID T
UINT32 hash_num;
UINT32 sig_size;
UINT8 *hash;
- int i;
+ UINT32 i;
hash_size = sha_size (Type);
sig_size = hash_size + sizeof(EFI_GUID);

View File

@ -1,3 +1,26 @@
-------------------------------------------------------------------
Tue Aug 12 14:19:36 UTC 2014 - jsegitz@suse.com
- updated shim to new version (OpenSSL 0.9.8za) and requested a new
certificate from Microsoft. Removed
* shim-allow-fallback-use-system-loadimage.patch
* shim-bnc872503-check-key-encoding.patch
* shim-bnc877003-fetch-from-the-same-device.patch
* shim-correct-user_insecure-usage.patch
* shim-fallback-avoid-duplicate-bootorder.patch
* shim-fallback-improve-entries-creation.patch
* shim-fix-dhcpv4-path-generation.patch
* shim-fix-uninitialized-variable.patch
* shim-fix-verify-mok.patch
* shim-get-variable-check.patch
* shim-improve-error-messages.patch
* shim-mokmanager-delete-bs-var-right.patch
* shim-mokmanager-handle-keystroke-error.patch
* shim-remove-unused-variables.patch
since they're included in upstream and rebased the remaining onces.
Added shim-signed-unsigned-compares.patch to fix some compiler
warnings
-------------------------------------------------------------------
Tue Aug 12 09:18:42 UTC 2014 - glin@suse.com

View File

@ -17,9 +17,13 @@
# needssslcertforbuild
%define commit 81ee561dde0213bc487aa1b701799f6d2faeaf31
%define shortcommit 81ee561d
Name: shim
Version: 0.7
# to ensure newer versions of the git export are always higher numbers the output of
# git rev-list master|wc -l is added before the git commit hash
Version: 0.7.318.%{shortcommit}
Release: 0
Summary: UEFI shim loader
License: BSD-2-Clause
@ -40,42 +44,16 @@ Source9: openSUSE-UEFI-CA-Certificate-4096.crt
Source10: timestamp.pl
Source11: strip_signature.sh
Source12: signature-sles.asc
# PATCH-FIX-UPSTREAM shim-fix-verify-mok.patch glin@suse.com -- Fix the error handling in verify_mok()
Patch1: shim-fix-verify-mok.patch
# PATCH-FIX-UPSTREAM shim-improve-error-messages.patch glin@suse.com -- Improve the error messages
Patch2: shim-improve-error-messages.patch
# PATCH-FIX-UPSTREAM shim-correct-user_insecure-usage.patch glin@suse.com -- Correct the usage of the user insecure mode variable
Patch3: shim-correct-user_insecure-usage.patch
# PATCH-FIX-UPSTREAM shim-fix-dhcpv4-path-generation.patch glin@suse.com -- Fix path generation for DHCPv4 bootloader
Patch4: shim-fix-dhcpv4-path-generation.patch
# PATCH-FIX-UPSTREAM shim-mokx-support.patch glin@suse.com -- Support MOK blacklist
Patch5: shim-mokx-support.patch
# PATCH-FIX-UPSTREAM shim-mokmanager-handle-keystroke-error.patch glin@suse.com -- Handle the error status from ReadKeyStroke to avoid the unexpected keys
Patch6: shim-mokmanager-handle-keystroke-error.patch
Patch1: shim-mokx-support.patch
# PATCH-FIX-SUSE shim-only-os-name.patch glin@suse.com -- Only include the OS name in version.c
Patch7: shim-only-os-name.patch
# PATCH-FIX-UPSTREAM shim-get-variable-check.patch glin@suse.com -- Fix the variable checking in get_variable_attr
Patch8: shim-get-variable-check.patch
# PATCH-FIX-UPSTREAM shim-fallback-improve--entries-creation.patch glin@suse.com -- Improve the boot entry pathes and avoid generating the boot entries that are already there
Patch9: shim-fallback-improve-entries-creation.patch
Patch2: shim-only-os-name.patch
# PATCH-FIX-UPSTREAM shim-bnc863205-mokmanager-fix-hash-delete.patch bnc#863205 glin@suse.com -- Fix the hash deletion operation to avoid ruining the whole list
Patch10: shim-bnc863205-mokmanager-fix-hash-delete.patch
# PATCH-FIX-UPSTREAM shim-fallback-avoid-duplicate-bootorder.patch glin@suse.com -- Fix the duplicate BootOrder entries generated by fallback.efi
Patch11: shim-fallback-avoid-duplicate-bootorder.patch
# PATCH-FIX-UPSTREAM shim-allow-fallback-use-system-loadimage.patch glin@suse.com -- Handle the shim protocol properly to keep only one protocol entity
Patch12: shim-allow-fallback-use-system-loadimage.patch
# PATCH-FIX-UPSTREAM shim-mokmanager-delete-bs-var-right.patch glin@suse.com -- Delete BootService non-volatile variables the right way
Patch13: shim-mokmanager-delete-bs-var-right.patch
# PATCH-FIX-UPSTREAM shim-fix-uninitialized-variable.patch glin@suse.com -- Initialize the variable in lib properly
Patch14: shim-fix-uninitialized-variable.patch
Patch3: shim-bnc863205-mokmanager-fix-hash-delete.patch
# PATCH-FIX-UPSTREAM shim-mokmanager-support-sha-family.patch glin@suse.com -- Support SHA hashes in MOK
Patch15: shim-mokmanager-support-sha-family.patch
# PATCH-FIX-UPSTREAM shim-remove-unused-variables.patch glin@suse.com -- Remove unused variables
Patch16: shim-remove-unused-variables.patch
# PATCH-FIX-UPSTREAM shim-bnc872503-check-key-encoding.patch bnc#872503 glin@suse.com -- Check the key encoding before using it
Patch17: shim-bnc872503-check-key-encoding.patch
# PATCH-FIX-UPSTREAM shim-bnc877003-fetch-from-the-same-device.patch bnc#877003 glin@suse.com -- Fetch the netboot image from the same device
Patch18: shim-bnc877003-fetch-from-the-same-device.patch
Patch4: shim-mokmanager-support-sha-family.patch
# PATCH-FIX-OPENSUSE shim-signed-unsigned-compares.patch jsegitz@suse.com -- Fixed some signed - unsigned comparisons
Patch5: shim-signed-unsigned-compares.patch
# PATCH-FIX-OPENSUSE shim-opensuse-cert-prompt.patch glin@suse.com -- Show the prompt to ask whether the user trusts openSUSE certificate or not
Patch100: shim-opensuse-cert-prompt.patch
BuildRequires: gnu-efi >= 3.0t
@ -106,19 +84,6 @@ Authors:
%patch3 -p1
%patch4 -p1
%patch5 -p1
%patch6 -p1
%patch7 -p1
%patch8 -p1
%patch9 -p1
%patch10 -p1
%patch11 -p1
%patch12 -p1
%patch13 -p1
%patch14 -p1
%patch15 -p1
%patch16 -p1
%patch17 -p1
%patch18 -p1
%patch100 -p1
%build

View File

@ -1,11 +1,11 @@
hash: 97a8c5ba11d61fefbb5d6a05da4e15ba472dc4c6cd4972fc1a035de321342fe4
# 2013-10-01 08:29:53
timestamp: 524a8801
checksum: d364
hash: bdd01126e9d85710d3fe75af1cc1702a29f081b4f6fdf6a2b2135c0297a9cec5
# 2069-04-10 06:07:54
timestamp: babababa
checksum: ff45
-----BEGIN AUTHENTICODE SIGNATURE-----
MIIh8QYJKoZIhvcNAQcCoIIh4jCCId4CAQExDzANBglghkgBZQMEAgEFADBcBgor
MIIh3AYJKoZIhvcNAQcCoIIhzTCCIckCAQExDzANBglghkgBZQMEAgEFADBcBgor
BgEEAYI3AgEEoE4wTDAXBgorBgEEAYI3AgEPMAkDAQCgBKICgAAwMTANBglghkgB
ZQMEAgEFAAQgl6jFuhHWH++7XWoF2k4VukctxMbNSXL8GgNd4yE0L+Sgggs8MIIF
ZQMEAgEFAAQgvdARJunYVxDT/nWvHMFwKinwgbT2/faishNcApepzsWgggs8MIIF
JDCCBAygAwIBAgITMwAAAApmQvP0n7c3lgABAAAACjANBgkqhkiG9w0BAQsFADCB
gTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1Jl
ZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjErMCkGA1UEAxMi
@ -65,124 +65,123 @@ HYw9Rw5EpuSwmzQ1sfq2U6gsgeykBXHInbi66BtEZuRHVA6OVn+znxaYsobQaD6Q
I7UvXo9QhY3GjYJfQaH0Lg3gmdJsdeS2abUhhvoH0fbiTdHarSx3Ux4lMjfHbFJy
lYaw8TVhahn1sjuBUFamMi3+oon5QoYnGFWhgspam/gwmFQUpkeWJS/IJuRBlBpc
Aj/lluOFWzw+P7tHFnJV4iUisdl75wMGKqP3HpBGwwAN1hmJ4w41J2IDcRWm79An
oKBZN2D4OJS44Hhw+LpMhoeU9uCuAkXuZcK2o35pFnUHkpv1prxZg1gxghYoMIIW
JAIBATCBmTCBgTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAO
oKBZN2D4OJS44Hhw+LpMhoeU9uCuAkXuZcK2o35pFnUHkpv1prxZg1gxghYTMIIW
DwIBATCBmTCBgTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAO
BgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEr
MCkGA1UEAxMiTWljcm9zb2Z0IENvcnBvcmF0aW9uIFVFRkkgQ0EgMjAxMQITMwAA
AApmQvP0n7c3lgABAAAACjANBglghkgBZQMEAgEFAKCCAREwGQYJKoZIhvcNAQkD
MQwGCisGAQQBgjcCAQQwHAYKKwYBBAGCNwIBCzEOMAwGCisGAQQBgjcCARUwLwYJ
KoZIhvcNAQkEMSIEIOBR1lXJ0yMtGJm8ETD6MEFIJCyjBPLlLe2aF6PcGN1xMIGk
KoZIhvcNAQkEMSIEIKOfDrPjsHj5IpbLDH/emIN2ujjTNjWxi+JiBMeM1lejMIGk
BgorBgEEAYI3AgEMMYGVMIGSoF6AXABoAHQAdABwADoALwAvAHcAdwB3AC4AbQBp
AGMAcgBvAHMAbwBmAHQALgBjAG8AbQAvAHcAaABkAGMALwBoAGMAbAAvAGQAZQBm
AGEAdQBsAHQALgBtAHMAcAB4oTCALmh0dHA6Ly93d3cubWljcm9zb2Z0LmNvbS93
aGRjL2hjbC9kZWZhdWx0Lm1zcHgwDQYJKoZIhvcNAQEBBQAEggEAVajbL42oQSy1
NUS6HAoCq0L01hhN9fHn8acFrSpXK+GjijNspEcxVWSmJCWUWj4oVgBU7hgB2cFr
YBm7M6VLl0h45tCI0jyHURNs4bYeKhBlywIAKQ1B3sxBi84vrNmVv7tZqtV8eAte
tmX/8X6mOObVtD1YfYRVc2/EAEqv/Dee3BKb2/3MJ8TlUDuPZ1yAjAq4MViGs0J3
m4T63cugiWPuoaZEGJ6eaPiVXPcEKiDDOboCMm6MY1CLADE0moMrQ86dtbmycXIu
N44ImKRkPSSCnRbmNDl/OkITHAicitORyvpet6uciDQtXQEq8xuRHJ7tOrwTmuLs
r+BEVn7BR6GCE0owghNGBgorBgEEAYI3AwMBMYITNjCCEzIGCSqGSIb3DQEHAqCC
EyMwghMfAgEDMQ8wDQYJYIZIAWUDBAIBBQAwggE9BgsqhkiG9w0BCRABBKCCASwE
ggEoMIIBJAIBAQYKKwYBBAGEWQoDATAxMA0GCWCGSAFlAwQCAQUABCBfmL3wsdu9
3kovdSnRVAah9huZNZbgGFJ05HSVLqfy9gIGUmk4IyjpGBMyMDEzMTAzMDE5MTY0
My42ODZaMAcCAQGAAgH0oIG5pIG2MIGzMQswCQYDVQQGEwJVUzETMBEGA1UECBMK
V2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0
IENvcnBvcmF0aW9uMQ0wCwYDVQQLEwRNT1BSMScwJQYDVQQLEx5uQ2lwaGVyIERT
RSBFU046QzBGNC0zMDg2LURFRjgxJTAjBgNVBAMTHE1pY3Jvc29mdCBUaW1lLVN0
YW1wIFNlcnZpY2Wggg7NMIIGcTCCBFmgAwIBAgIKYQmBKgAAAAAAAjANBgkqhkiG
9w0BAQsFADCBiDELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAO
BgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEy
MDAGA1UEAxMpTWljcm9zb2Z0IFJvb3QgQ2VydGlmaWNhdGUgQXV0aG9yaXR5IDIw
MTAwHhcNMTAwNzAxMjEzNjU1WhcNMjUwNzAxMjE0NjU1WjB8MQswCQYDVQQGEwJV
UzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9uZDEeMBwGA1UE
ChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSYwJAYDVQQDEx1NaWNyb3NvZnQgVGlt
ZS1TdGFtcCBQQ0EgMjAxMDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB
AKkdDbx3EYo6IOz8E5f1+n9plGt0VBDVpQoAgoX77XxoSyxfxcPlYcJ2tz5mK1vw
FVMnBDEfQRsalR3OCROOfGEwWbEwRA/xYIiEVEMM1024OAizQt2TrNZzMFcmgqNF
DdDq9UeBzb8kYDJYYEbyWEeGMoQedGFnkV+BVLHPk0ySwcSmXdFhE24oxhr5hoC7
32H8RsEnHSRnEnIaIYqvS2SJUGKxXf13Hz3wV3WsvYpCTUBR0Q+cBj5nf/VmwAOW
RH7v0Ev9buWayrGo8noqCjHw2k4GkbaICDXoeByw6ZnNPOcvRLqn9NxkvaQBwSAJ
k3jN/LzAyURdXhacAQVPIk0CAwEAAaOCAeYwggHiMBAGCSsGAQQBgjcVAQQDAgEA
MB0GA1UdDgQWBBTVYzpcijGQ80N7fEYbxTNoWoVtVTAZBgkrBgEEAYI3FAIEDB4K
AFMAdQBiAEMAQTALBgNVHQ8EBAMCAYYwDwYDVR0TAQH/BAUwAwEB/zAfBgNVHSME
GDAWgBTV9lbLj+iiXGJo0T2UkFvXzpoYxDBWBgNVHR8ETzBNMEugSaBHhkVodHRw
Oi8vY3JsLm1pY3Jvc29mdC5jb20vcGtpL2NybC9wcm9kdWN0cy9NaWNSb29DZXJB
dXRfMjAxMC0wNi0yMy5jcmwwWgYIKwYBBQUHAQEETjBMMEoGCCsGAQUFBzAChj5o
dHRwOi8vd3d3Lm1pY3Jvc29mdC5jb20vcGtpL2NlcnRzL01pY1Jvb0NlckF1dF8y
MDEwLTA2LTIzLmNydDCBoAYDVR0gAQH/BIGVMIGSMIGPBgkrBgEEAYI3LgMwgYEw
PQYIKwYBBQUHAgEWMWh0dHA6Ly93d3cubWljcm9zb2Z0LmNvbS9QS0kvZG9jcy9D
UFMvZGVmYXVsdC5odG0wQAYIKwYBBQUHAgIwNB4yIB0ATABlAGcAYQBsAF8AUABv
AGwAaQBjAHkAXwBTAHQAYQB0AGUAbQBlAG4AdAAuIB0wDQYJKoZIhvcNAQELBQAD
ggIBAAfmiFEN4sbgmD+BcQM9naOhIW+z66bM9TG+zwXiqf76V20ZMLPCxWbJat/1
5/B4vceoniXj+bzta1RXCCtRgkQS+7lTjMz0YBKKdsxAQEGb3FwX/1z5Xhc1mCRW
S3TvQhDIr79/xn/yN31aPxzymXlKkVIArzgPF/UveYFl2am1a+THzvbKegBvSzBE
JCI8z+0DpZaPWSm8tv0E4XCfMkon/VWvL/625Y4zu2JfmttXQOnxzplmkIz/amJ/
3cVKC5Em4jnsGUpxY517IW3DnKOiPPp/fZZqkHimbdLhnPkd/DjYlPTGpQqWhqS9
nhquBEKDuLWAmyI4ILUl5WTs9/S/fmNZJQ96LjlXdqJxqgaKD4kWumGnEcua2A5H
moDF0M2n0O99g/DhO3EJ3110mCIIYdqwUB5vvfHhAN/nMQekkzr3ZUd46PioSKv3
3nJ+YWtvd6mBy6cJrDm77MbL2IK0cs0d9LiFAR6A+xuJKlQ5slvayA1VmXqHczsI
5pgt6o3gMy4SKfXAL1QnIffIrE7aKLixqduWsqdCosnPGUFN4Ib5KpqjEWYw07t0
MkvfY3v1mYovG8chr1m1rtxEPJdQcdeh0sVV42neV8HR3jDA/czmTfsNv11P6Z0e
GTgvvM9YBS7vDaBQNdrvCScc1bN+NR4Iuto229Nfj950iEkSMIIE2jCCA8KgAwIB
AgITMwAAACiQZ7kEsDxuZgAAAAAAKDANBgkqhkiG9w0BAQsFADB8MQswCQYDVQQG
EwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHUmVkbW9uZDEeMBwG
A1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMSYwJAYDVQQDEx1NaWNyb3NvZnQg
VGltZS1TdGFtcCBQQ0EgMjAxMDAeFw0xMzAzMjcyMDEzMTNaFw0xNDA2MjcyMDEz
MTNaMIGzMQswCQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UE
BxMHUmVkbW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMQ0wCwYD
VQQLEwRNT1BSMScwJQYDVQQLEx5uQ2lwaGVyIERTRSBFU046QzBGNC0zMDg2LURF
RjgxJTAjBgNVBAMTHE1pY3Jvc29mdCBUaW1lLVN0YW1wIFNlcnZpY2UwggEiMA0G
CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDdpUi/akidSiGckmve4C3c5GP4zLmJ
xMcbvee10/vtrs8x/vNmsEQD2plnCFq/dQYiEYnQZ1LM+s+SN0Xo+vG9M9PMc+O4
IaSgFX3LL8QDBdo/lnPTWeWYTQtWhi+dR9HWX52R6ceE2ZVrMky0awBS4EHTPGl0
qM7MfWidUlXmcH8UB6KeZ7CGRPMzP3Ndxij4F19SAS1EL9bteAi45TsvwLnDS8O3
Oy/TprWcsUhK3TIJVqEbS1rTqiYnDBJDYMVq19pADWCYiUG7k3Pdv/7EjFvO+lUn
yk1Nmm99EWyxRyOwTHxsfwahdIIfUngY6QYaFlCawzrdgYH3mydyIX91AgMBAAGj
ggEbMIIBFzAdBgNVHQ4EFgQU3JgInXnRBLKLR8Nx0Izns+awU50wHwYDVR0jBBgw
FoAU1WM6XIoxkPNDe3xGG8UzaFqFbVUwVgYDVR0fBE8wTTBLoEmgR4ZFaHR0cDov
L2NybC5taWNyb3NvZnQuY29tL3BraS9jcmwvcHJvZHVjdHMvTWljVGltU3RhUENB
XzIwMTAtMDctMDEuY3JsMFoGCCsGAQUFBwEBBE4wTDBKBggrBgEFBQcwAoY+aHR0
cDovL3d3dy5taWNyb3NvZnQuY29tL3BraS9jZXJ0cy9NaWNUaW1TdGFQQ0FfMjAx
MC0wNy0wMS5jcnQwDAYDVR0TAQH/BAIwADATBgNVHSUEDDAKBggrBgEFBQcDCDAN
BgkqhkiG9w0BAQsFAAOCAQEAgiLztz1kfhJL/Cb84OS30MQUTgn+q1aa0VqYpr6M
QR6UtDK+hLS3RXbj72AYJIeoz+m00VQpvMrkyxJ7wPHUDp8xMxsRP3o73d0CqhjK
yjz6luNsu6+7yYQ+x9gMhctyCwEbpPUxERAMRaVaSJl+2r5Fhte6TeSB/9NYCnZl
Blkv9sJCzwTJqxv6YZ3185hJcLFJ0GTEIejuYBdTfusC2miVi/UKPAHbo7WYFFF0
nlPp2nKYZqBfKc+Prx+CnNPr5vFMG1T46DLcwRXDrCpudAUWg+NEmJ/L7+gweX+v
UqU6H99lx43+J9hHGZIItIs0jmknNxoC9pGzlSL/CEgq/qGCA3YwggJeAgEBMIHj
oYG5pIG2MIGzMQswCQYDVQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4G
A1UEBxMHUmVkbW9uZDEeMBwGA1UEChMVTWljcm9zb2Z0IENvcnBvcmF0aW9uMQ0w
CwYDVQQLEwRNT1BSMScwJQYDVQQLEx5uQ2lwaGVyIERTRSBFU046QzBGNC0zMDg2
LURFRjgxJTAjBgNVBAMTHE1pY3Jvc29mdCBUaW1lLVN0YW1wIFNlcnZpY2WiJQoB
ATAJBgUrDgMCGgUAAxUA8120HsdfO2ZOZQ7emART9hWnH0SggcIwgb+kgbwwgbkx
CzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRt
b25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xDTALBgNVBAsTBE1P
UFIxJzAlBgNVBAsTHm5DaXBoZXIgTlRTIEVTTjpCMDI3LUM2RjgtMUQ4ODErMCkG
A1UEAxMiTWljcm9zb2Z0IFRpbWUgU291cmNlIE1hc3RlciBDbG9jazANBgkqhkiG
9w0BAQUFAAIFANYbbXkwIhgPMjAxMzEwMzAxMTM1MjFaGA8yMDEzMTAzMTExMzUy
MVowdDA6BgorBgEEAYRZCgQBMSwwKjAKAgUA1htteQIBADAHAgEAAgIQxzAHAgEA
AgIYcDAKAgUA1hy++QIBADA2BgorBgEEAYRZCgQCMSgwJjAMBgorBgEEAYRZCgMB
oAowCAIBAAIDFuNgoQowCAIBAAIDB6EgMA0GCSqGSIb3DQEBBQUAA4IBAQAxxOL5
p8WZx+WQXwsf9YpPA4dWCU2xk7l1MY2R653keklyM7ks9Md5/7JbBzMPQXMPJ0Ts
SllTUWF+wCUwW84ZAJCG4IUS5MrfbC5yXPkCjYEW6pll2A77OgwC+UG7X5VN67nm
XfRbw+3lyAAcCjpreeEOiMRTNP1UW3Th2x5Lmbgc4AW/6p+6VEj/7QJEuj7oMXVe
KQNp/I+lJn1rBGU42wqteobjNmUI55+i5PN+Wa5uGh7IhkqpDRPIkBM9wqVDQoHb
d727DRVQMwzTAGYdSaOPJjLYti078h71WDJYyM1waA435nrkukJ6ObWdMTNjJqsy
/Tz7rYZPgMPKLjtfMYIC9TCCAvECAQEwgZMwfDELMAkGA1UEBhMCVVMxEzARBgNV
aGRjL2hjbC9kZWZhdWx0Lm1zcHgwDQYJKoZIhvcNAQEBBQAEggEAThlP7UGIWeaL
wSgeXtn8Whnj2NuB/+fBohdlEmuU4oOJsKt07jxVrzXWHO0/znARfCMhsqGnwQq6
IU45DSbqHiBsPS2bucCmygVJZjS+lYUY0o1OSiAOgkcOb3byqbOhFx+yU4jyi1I6
vZsetJf0VIB/50CUDWw/jgC29MS5uLKPbljn6Gav6BmWkbzR7g7e44QInagtQsEm
kxI4FaHRkaKnkTtrJZ2htMCGJUEm83iyEaFB1jfwE+eSVilltwZeUiM8cm5jSIeZ
CWyF2+bOgaOyIk47XVZWI0683wwf43yftlRMsuySQuD7Vk4sKsRM87Nl1SszQSqI
murrQX0OHqGCEzUwghMxBgorBgEEAYI3AwMBMYITITCCEx0GCSqGSIb3DQEHAqCC
Ew4wghMKAgEDMQ8wDQYJYIZIAWUDBAIBBQAwggE1BgsqhkiG9w0BCRABBKCCASQE
ggEgMIIBHAIBAQYKKwYBBAGEWQoDATAxMA0GCWCGSAFlAwQCAQUABCBhVxDrnAE1
Odf8YYCrsCpxqlspu1YwtY7Xj0HNqt+MlgIGU8faFW37GBMyMDE0MDgwMjAwMjcx
My4yMzVaMAcCAQGAAgH0oIGxpIGuMIGrMQswCQYDVQQGEwJVUzELMAkGA1UECBMC
V0ExEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3Jh
dGlvbjENMAsGA1UECxMETU9QUjEnMCUGA1UECxMebkNpcGhlciBEU0UgRVNOOjMx
QzUtMzBCQS03QzkxMSUwIwYDVQQDExxNaWNyb3NvZnQgVGltZS1TdGFtcCBTZXJ2
aWNloIIOwDCCBnEwggRZoAMCAQICCmEJgSoAAAAAAAIwDQYJKoZIhvcNAQELBQAw
gYgxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdS
ZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xMjAwBgNVBAMT
KU1pY3Jvc29mdCBSb290IENlcnRpZmljYXRlIEF1dGhvcml0eSAyMDEwMB4XDTEw
MDcwMTIxMzY1NVoXDTI1MDcwMTIxNDY1NVowfDELMAkGA1UEBhMCVVMxEzARBgNV
BAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jv
c29mdCBDb3Jwb3JhdGlvbjEmMCQGA1UEAxMdTWljcm9zb2Z0IFRpbWUtU3RhbXAg
UENBIDIwMTACEzMAAAAokGe5BLA8bmYAAAAAACgwDQYJYIZIAWUDBAIBBQCgggEy
MBoGCSqGSIb3DQEJAzENBgsqhkiG9w0BCRABBDAvBgkqhkiG9w0BCQQxIgQgqtHU
/PG7RLWN/Y5UsjD6+lFX/RpWbpbjNV/x7SF3lQwwgeIGCyqGSIb3DQEJEAIMMYHS
MIHPMIHMMIGxBBTzXbQex187Zk5lDt6YBFP2FacfRDCBmDCBgKR+MHwxCzAJBgNV
BAYTAlVTMRMwEQYDVQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4w
HAYDVQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xJjAkBgNVBAMTHU1pY3Jvc29m
dCBUaW1lLVN0YW1wIFBDQSAyMDEwAhMzAAAAKJBnuQSwPG5mAAAAAAAoMBYEFLWf
+tQPMIlyzZih4uVtvwa31BWHMA0GCSqGSIb3DQEBCwUABIIBAEJSSeyhVFmVBArn
o02R+f9PxUVjdMsHRqTWdnfA6F4uFU2GGGB2NoGTPHVeHrTTejo2bzXf5Di0jO5r
nIM1KVSUIDmM6xgvcIgxMuo2oM8MxHnYSh9QdWTCnJsqcR+PzIhsdrxaQOLRXNiS
uEyj0MgaJuYATAmhM2oM4BFNmbFavr0Sar3fj54zoZ9/p7ZhROSVm40OKt8tzSDu
7KrU8rr6VikJV2svuvLsmBKP7H6A+ZBWgrSlraQhdOxgjdPci6rhoZ9GG3WzNIcg
c+4KZEXs0hxinuZA2+Z9QhyXcTeLXm1UbKtN+P6hEv6ABEaghtj238dcrBtwijpX
BkfJeJoAAAA=
UENBIDIwMTAwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCpHQ28dxGK
OiDs/BOX9fp/aZRrdFQQ1aUKAIKF++18aEssX8XD5WHCdrc+Zitb8BVTJwQxH0Eb
GpUdzgkTjnxhMFmxMEQP8WCIhFRDDNdNuDgIs0Ldk6zWczBXJoKjRQ3Q6vVHgc2/
JGAyWGBG8lhHhjKEHnRhZ5FfgVSxz5NMksHEpl3RYRNuKMYa+YaAu99h/EbBJx0k
ZxJyGiGKr0tkiVBisV39dx898Fd1rL2KQk1AUdEPnAY+Z3/1ZsADlkR+79BL/W7l
msqxqPJ6Kgox8NpOBpG2iAg16HgcsOmZzTznL0S6p/TcZL2kAcEgCZN4zfy8wMlE
XV4WnAEFTyJNAgMBAAGjggHmMIIB4jAQBgkrBgEEAYI3FQEEAwIBADAdBgNVHQ4E
FgQU1WM6XIoxkPNDe3xGG8UzaFqFbVUwGQYJKwYBBAGCNxQCBAweCgBTAHUAYgBD
AEEwCwYDVR0PBAQDAgGGMA8GA1UdEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAU1fZW
y4/oolxiaNE9lJBb186aGMQwVgYDVR0fBE8wTTBLoEmgR4ZFaHR0cDovL2NybC5t
aWNyb3NvZnQuY29tL3BraS9jcmwvcHJvZHVjdHMvTWljUm9vQ2VyQXV0XzIwMTAt
MDYtMjMuY3JsMFoGCCsGAQUFBwEBBE4wTDBKBggrBgEFBQcwAoY+aHR0cDovL3d3
dy5taWNyb3NvZnQuY29tL3BraS9jZXJ0cy9NaWNSb29DZXJBdXRfMjAxMC0wNi0y
My5jcnQwgaAGA1UdIAEB/wSBlTCBkjCBjwYJKwYBBAGCNy4DMIGBMD0GCCsGAQUF
BwIBFjFodHRwOi8vd3d3Lm1pY3Jvc29mdC5jb20vUEtJL2RvY3MvQ1BTL2RlZmF1
bHQuaHRtMEAGCCsGAQUFBwICMDQeMiAdAEwAZQBnAGEAbABfAFAAbwBsAGkAYwB5
AF8AUwB0AGEAdABlAG0AZQBuAHQALiAdMA0GCSqGSIb3DQEBCwUAA4ICAQAH5ohR
DeLG4Jg/gXEDPZ2joSFvs+umzPUxvs8F4qn++ldtGTCzwsVmyWrf9efweL3HqJ4l
4/m87WtUVwgrUYJEEvu5U4zM9GASinbMQEBBm9xcF/9c+V4XNZgkVkt070IQyK+/
f8Z/8jd9Wj8c8pl5SpFSAK84Dxf1L3mBZdmptWvkx872ynoAb0swRCQiPM/tA6WW
j1kpvLb9BOFwnzJKJ/1Vry/+tuWOM7tiX5rbV0Dp8c6ZZpCM/2pif93FSguRJuI5
7BlKcWOdeyFtw5yjojz6f32WapB4pm3S4Zz5Hfw42JT0xqUKloakvZ4argRCg7i1
gJsiOCC1JeVk7Pf0v35jWSUPei45V3aicaoGig+JFrphpxHLmtgOR5qAxdDNp9Dv
fYPw4TtxCd9ddJgiCGHasFAeb73x4QDf5zEHpJM692VHeOj4qEir995yfmFrb3ep
gcunCaw5u+zGy9iCtHLNHfS4hQEegPsbiSpUObJb2sgNVZl6h3M7COaYLeqN4DMu
Ein1wC9UJyH3yKxO2ii4sanblrKnQqLJzxlBTeCG+SqaoxFmMNO7dDJL32N79ZmK
LxvHIa9Zta7cRDyXUHHXodLFVeNp3lfB0d4wwP3M5k37Db9dT+mdHhk4L7zPWAUu
7w2gUDXa7wknHNWzfjUeCLraNtvTX4/edIhJEjCCBNIwggO6oAMCAQICEzMAAABP
rehUlVAolGcAAAAAAE8wDQYJKoZIhvcNAQELBQAwfDELMAkGA1UEBhMCVVMxEzAR
BgNVBAgTCldhc2hpbmd0b24xEDAOBgNVBAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1p
Y3Jvc29mdCBDb3Jwb3JhdGlvbjEmMCQGA1UEAxMdTWljcm9zb2Z0IFRpbWUtU3Rh
bXAgUENBIDIwMTAwHhcNMTQwNTIzMTcyMDA4WhcNMTUwODIzMTcyMDA4WjCBqzEL
MAkGA1UEBhMCVVMxCzAJBgNVBAgTAldBMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYD
VQQKExVNaWNyb3NvZnQgQ29ycG9yYXRpb24xDTALBgNVBAsTBE1PUFIxJzAlBgNV
BAsTHm5DaXBoZXIgRFNFIEVTTjozMUM1LTMwQkEtN0M5MTElMCMGA1UEAxMcTWlj
cm9zb2Z0IFRpbWUtU3RhbXAgU2VydmljZTCCASIwDQYJKoZIhvcNAQEBBQADggEP
ADCCAQoCggEBAKFVkneQwi1RLhVhgJoMVZY6JIU3jigasjbuZClciQzP0d0z9Ev8
mxS2T2+fdfVkWZWKQXeYmD5mejixNPhFpoQR0zWhpfNQe4XA7x4l8a48+P483uz3
7sMyBlYtYaQEnfBPmCqG/Wbr9cdH9QVx94F4NKVZFnSa/eEq3hDRLfqqiDmkRTN4
t+w8d3Yx41CVzx6TBgh6bE2km58m5YS/+54xLirgm44nHlmQCut58IGTZ6CArg/1
g1cqGrFbMUZC/mhSgCA4uFNSRctPc56zSTBbsM5vP6PqOW6J8VWJICxREyBqg2gV
Qp7JhZmczo+DtG+W3QyjPO8Thwx+mo3iFnkCAwEAAaOCARswggEXMB0GA1UdDgQW
BBQrpekQU9AS8xkbQCwKTRfMxEXJLjAfBgNVHSMEGDAWgBTVYzpcijGQ80N7fEYb
xTNoWoVtVTBWBgNVHR8ETzBNMEugSaBHhkVodHRwOi8vY3JsLm1pY3Jvc29mdC5j
b20vcGtpL2NybC9wcm9kdWN0cy9NaWNUaW1TdGFQQ0FfMjAxMC0wNy0wMS5jcmww
WgYIKwYBBQUHAQEETjBMMEoGCCsGAQUFBzAChj5odHRwOi8vd3d3Lm1pY3Jvc29m
dC5jb20vcGtpL2NlcnRzL01pY1RpbVN0YVBDQV8yMDEwLTA3LTAxLmNydDAMBgNV
HRMBAf8EAjAAMBMGA1UdJQQMMAoGCCsGAQUFBwMIMA0GCSqGSIb3DQEBCwUAA4IB
AQBhbgv5FjD4pzjfVhGhfk23Gom8Ip4kfRTobqi7up1JHBTWidiUVKwoszU9TPi+
PTuCNBDJgWuMIXNGcpXRTLTENDW9Maln6yp7zFUEtYGulWSFT9EGMLfjBTLoBl4M
GxU8IDviiM6GuCy7vV0QbsNfeBZpo761j42sHJccu7LPTk8VD24W1diIEaCjePJW
FRBKidTcAQRHki0xDK4xYbN9GFncfhXaMlQn4TN/mRx6YBTELjiP1RH3rdW9I/NX
0kXfCGth/BbVctp6rGRkK8NQaHkq9rXqt+C75sVwASx/JxMkXS1q+Rnwbilso9Rq
LsiE9SszQjNKzc+rebhHpUELoYIDcTCCAlkCAQEwgduhgbGkga4wgasxCzAJBgNV
BAYTAlVTMQswCQYDVQQIEwJXQTEQMA4GA1UEBxMHUmVkbW9uZDEeMBwGA1UEChMV
TWljcm9zb2Z0IENvcnBvcmF0aW9uMQ0wCwYDVQQLEwRNT1BSMScwJQYDVQQLEx5u
Q2lwaGVyIERTRSBFU046MzFDNS0zMEJBLTdDOTExJTAjBgNVBAMTHE1pY3Jvc29m
dCBUaW1lLVN0YW1wIFNlcnZpY2WiJQoBATAJBgUrDgMCGgUAAxUAKLyR2kF+5obQ
k1yVhHi3u5xWWaqggcIwgb+kgbwwgbkxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpX
YXNoaW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQg
Q29ycG9yYXRpb24xDTALBgNVBAsTBE1PUFIxJzAlBgNVBAsTHm5DaXBoZXIgTlRT
IEVTTjpCMDI3LUM2RjgtMUQ4ODErMCkGA1UEAxMiTWljcm9zb2Z0IFRpbWUgU291
cmNlIE1hc3RlciBDbG9jazANBgkqhkiG9w0BAQUFAAIFANeGrl0wIhgPMjAxNDA4
MDIwMDI1MDFaGA8yMDE0MDgwMzAwMjUwMVowdzA9BgorBgEEAYRZCgQBMS8wLTAK
AgUA14auXQIBADAKAgEAAgIJAAIB/zAHAgEAAgIYWjAKAgUA14f/3QIBADA2Bgor
BgEEAYRZCgQCMSgwJjAMBgorBgEEAYRZCgMBoAowCAIBAAIDFuNgoQowCAIBAAID
B6EgMA0GCSqGSIb3DQEBBQUAA4IBAQCFCxo0b2hLnmf+xoh21SzjNvFsZm6WfCFc
PlGAEgOqq1Dlp9KNsYik0tjif3xLKmMjM1sBE8JJ85c2iYDMm/y5PUyyM16zlojk
q4zwcJEiPzEzBPzKqtgGRvJElVY37BuowRCgbRv5gi6eKGiHObCFf0ElAwGNJydf
DDxy7BmNS5/kPk926NxynXs1kdqPdUmyZmh/3wtm0w9S6+NIzfCXLp0kxCP3kPVv
kEHTiPUj/ogu4DVvkbECmJyZwtjhlsEcr+VxT2PYNdQX+89UdreCR0deUXY7Y6WS
M1Zr7cVhFJAWjLPB8ciqG8WDmijJviFDp8e+7lrBCxZdRwXilBKiMYIC9TCCAvEC
AQEwgZMwfDELMAkGA1UEBhMCVVMxEzARBgNVBAgTCldhc2hpbmd0b24xEDAOBgNV
BAcTB1JlZG1vbmQxHjAcBgNVBAoTFU1pY3Jvc29mdCBDb3Jwb3JhdGlvbjEmMCQG
A1UEAxMdTWljcm9zb2Z0IFRpbWUtU3RhbXAgUENBIDIwMTACEzMAAABPrehUlVAo
lGcAAAAAAE8wDQYJYIZIAWUDBAIBBQCgggEyMBoGCSqGSIb3DQEJAzENBgsqhkiG
9w0BCRABBDAvBgkqhkiG9w0BCQQxIgQg2Fdy/47bukVF9tAPO8fA4meI/cXYbmn7
z135MrP1QSowgeIGCyqGSIb3DQEJEAIMMYHSMIHPMIHMMIGxBBQovJHaQX7mhtCT
XJWEeLe7nFZZqjCBmDCBgKR+MHwxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpXYXNo
aW5ndG9uMRAwDgYDVQQHEwdSZWRtb25kMR4wHAYDVQQKExVNaWNyb3NvZnQgQ29y
cG9yYXRpb24xJjAkBgNVBAMTHU1pY3Jvc29mdCBUaW1lLVN0YW1wIFBDQSAyMDEw
AhMzAAAAT63oVJVQKJRnAAAAAABPMBYEFCYplGRrdF2iEXIxRDr2Yo/nmNd0MA0G
CSqGSIb3DQEBCwUABIIBAIUNbJ8A82Vn/zft6B33oO5uQqRZcSD6zqqM3z7a/Tb2
VLnhWYmDjxsLesS8kXcSZKv5MBVBA01FQQaL6jEwkjRx/qYM8ly6qthXGsgN0WoE
vXKnOPjJ40Iz03g/AlMHzs2lI9hYWw/iaArpzdiCgD0qeOt12K+HANTEm3azsDWr
d7F/rUlHOQJxbCkxuMhpN8kFcV8qtgiVJ5jYna6AlOEDOL0E7Z15Tesid2ZjJn/5
/hrND9ZCeYcgROjy154VnT0a0zEWaiN6Rp8xqYYGSnLiXZAZPMtHNkXAIRUy34ut
XgbI8J3rkmRK1vZYNa4dHD7X/7cohNa9/XZZi4Usn8k=
-----END AUTHENTICODE SIGNATURE-----