示例#1
0
static EFI_STATUS EFIAPI
start_image(EFI_HANDLE image_handle, UINTN *exit_data_size, CHAR16 **exit_data)
{
	EFI_STATUS status;
	unhook_system_services();
	status = systab->BootServices->StartImage(image_handle, exit_data_size, exit_data);
	if (EFI_ERROR(status))
		hook_system_services(systab);
	return status;
}
示例#2
0
static EFI_STATUS EFIAPI
efi_exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus,
     UINTN ExitDataSize, CHAR16 *ExitData)
{
	EFI_STATUS status;
	unhook_system_services();

	status = systab->BootServices->Exit(ImageHandle, ExitStatus, ExitDataSize, ExitData);
	if (EFI_ERROR(status))
		hook_system_services(systab);
	return status;
}
示例#3
0
static EFI_STATUS EFIAPI
exit_boot_services(EFI_HANDLE image_key, UINTN map_key)
{
	if (loader_is_participating || verification_method == VERIFIED_BY_HASH) {
		unhook_system_services();
		EFI_STATUS status;
		status = systab->BootServices->ExitBootServices(image_key, map_key);
		if (status != EFI_SUCCESS)
			hook_system_services(systab);
		return status;
	}

	Print(L"Bootloader has not verified loaded image.\n");
	Print(L"System is compromised.  halting.\n");
	systab->BootServices->Stall(5000000);
	systab->RuntimeServices->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL);
	return EFI_SECURITY_VIOLATION;
}
示例#4
0
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;
}
示例#5
0
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 (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;
}