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