[edk2-devel] [PATCH v3 2/6] OvmfPkg: add 'initrd' shell command to expose Linux initrd via device path

Laszlo Ersek lersek at redhat.com
Thu Feb 27 10:59:00 UTC 2020


On 02/26/20 20:43, Ard Biesheuvel wrote:
> Add a new 'initrd' command to the UEFI Shell that allows any file that is
> accessible to the shell to be registered as the initrd that is returned
> when Linux's EFI stub loader invokes the LoadFile2 protocol on its special
> vendor media device path.
> 
> Signed-off-by: Ard Biesheuvel <ard.biesheuvel at linaro.org>
> ---
>  OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.c   | 429 ++++++++++++++++++++
>  OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.inf |  53 +++
>  OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.uni |  49 +++
>  3 files changed, 531 insertions(+)
> 
> diff --git a/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.c b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.c
> new file mode 100644
> index 000000000000..7ddeba0df624
> --- /dev/null
> +++ b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.c
> @@ -0,0 +1,429 @@
> +/** @file
> +  Provides 'initrd' dynamic UEFI shell command to load a Linux initrd
> +  via its GUIDed vendor media path
> +
> +  Copyright (c) 2020, Arm, Ltd. All rights reserved.<BR>
> +
> +  SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Uefi.h>
> +
> +#include <Library/DebugLib.h>
> +#include <Library/DevicePathLib.h>
> +#include <Library/HiiLib.h>
> +#include <Library/MemoryAllocationLib.h>
> +#include <Library/ShellLib.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +#include <Library/UefiHiiServicesLib.h>
> +
> +#include <Guid/LinuxEfiInitrdMedia.h>
> +
> +#include <Protocol/DevicePath.h>
> +#include <Protocol/HiiPackageList.h>
> +#include <Protocol/LoadFile2.h>
> +#include <Protocol/ShellDynamicCommand.h>
> +
> +#pragma pack (1)
> +typedef struct {
> +  VENDOR_DEVICE_PATH          VenMediaNode;
> +  EFI_DEVICE_PATH_PROTOCOL    EndNode;
> +} SINGLE_NODE_VENDOR_MEDIA_DEVPATH;
> +#pragma pack ()
> +
> +STATIC EFI_HII_HANDLE         mLinuxInitrdShellCommandHiiHandle;
> +STATIC EFI_PHYSICAL_ADDRESS   mInitrdFileAddress;
> +STATIC UINTN                  mInitrdFileSize;
> +STATIC EFI_HANDLE             mInitrdLoadFile2Handle;
> +
> +STATIC CONST SHELL_PARAM_ITEM ParamList[] = {
> +  {L"-u", TypeFlag},
> +  {NULL, TypeMax}
> +  };
> +
> +STATIC CONST SINGLE_NODE_VENDOR_MEDIA_DEVPATH mInitrdDevicePath = {
> +  {
> +    {
> +      MEDIA_DEVICE_PATH, MEDIA_VENDOR_DP, { sizeof (VENDOR_DEVICE_PATH) }
> +    },
> +    LINUX_EFI_INITRD_MEDIA_GUID
> +  }, {
> +    END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE,
> +    { sizeof (EFI_DEVICE_PATH_PROTOCOL) }
> +  }
> +};
> +
> +STATIC
> +EFI_STATUS
> +EFIAPI
> +InitrdLoadFile2 (
> +  IN  EFI_LOAD_FILE2_PROTOCOL           *This,
> +  IN  EFI_DEVICE_PATH_PROTOCOL          *FilePath,
> +  IN  BOOLEAN                           BootPolicy,
> +  IN  OUT UINTN                         *BufferSize,
> +  OUT VOID                              *Buffer OPTIONAL

"BufferSize" is IN OUT, so if we wanted to align those annotations
nicely, we'd do

  IN     EFI_LOAD_FILE2_PROTOCOL  *This,
  IN     EFI_DEVICE_PATH_PROTOCOL *FilePath,
  IN     BOOLEAN                  BootPolicy,
  IN OUT UINTN                    *BufferSize,
  OUT    VOID                     *Buffer OPTIONAL

But I'm fine with the current columns too.

One request below:

> +  )
> +{
> +  if (BootPolicy) {
> +    return EFI_UNSUPPORTED;
> +  }
> +
> +  if (BufferSize == NULL || !IsDevicePathValid (FilePath, 0)) {
> +    return EFI_INVALID_PARAMETER;
> +  }
> +
> +  if (FilePath->Type != END_DEVICE_PATH_TYPE ||
> +      FilePath->SubType != END_ENTIRE_DEVICE_PATH_SUBTYPE ||
> +      mInitrdFileSize == 0) {
> +    return EFI_NOT_FOUND;
> +  }
> +
> +  if (Buffer == NULL || *BufferSize < mInitrdFileSize) {
> +    *BufferSize = mInitrdFileSize;
> +    return EFI_BUFFER_TOO_SMALL;
> +  }
> +
> +  ASSERT (mInitrdFileAddress != 0);
> +
> +  gBS->CopyMem (Buffer, (VOID *)(UINTN)mInitrdFileAddress, mInitrdFileSize);
> +  *BufferSize = mInitrdFileSize;
> +  return EFI_SUCCESS;
> +}
> +
> +STATIC CONST EFI_LOAD_FILE2_PROTOCOL     mInitrdLoadFile2 = {
> +  InitrdLoadFile2,
> +};
> +
> +STATIC
> +EFI_STATUS
> +UninstallLoadFile2Protocol (
> +  VOID
> +  )
> +{
> +  EFI_STATUS    Status;
> +
> +  if (mInitrdLoadFile2Handle != NULL) {
> +    Status = gBS->UninstallMultipleProtocolInterfaces (mInitrdLoadFile2Handle,
> +                    &gEfiDevicePathProtocolGuid,    &mInitrdDevicePath,
> +                    &gEfiLoadFile2ProtocolGuid,     &mInitrdLoadFile2,
> +                    NULL);
> +    if (!EFI_ERROR (Status)) {
> +      mInitrdLoadFile2Handle = NULL;
> +    }
> +  }
> +  return Status;
> +}
> +
> +STATIC
> +VOID
> +FreeInitrdFile (
> +  VOID
> +  )
> +{
> +  if (mInitrdFileSize != 0) {
> +    gBS->FreePages (mInitrdFileAddress, EFI_SIZE_TO_PAGES (mInitrdFileSize));
> +    mInitrdFileSize = 0;
> +  }
> +}
> +
> +STATIC
> +EFI_STATUS
> +CacheInitrdFile (
> +  IN  SHELL_FILE_HANDLE   FileHandle
> +  )
> +{
> +  EFI_STATUS              Status;
> +  UINT64                  FileSize;
> +  UINTN                   ReadSize;
> +
> +  Status = gEfiShellProtocol->GetFileSize (FileHandle, &FileSize);
> +  if (EFI_ERROR (Status)) {
> +    return Status;
> +  }
> +
> +  if (FileSize == 0 || FileSize > MAX_UINTN) {
> +    return EFI_UNSUPPORTED;
> +  }
> +
> +  Status = gBS->AllocatePages (AllocateAnyPages, EfiLoaderData,
> +                  EFI_SIZE_TO_PAGES ((UINTN)FileSize), &mInitrdFileAddress);
> +  if (EFI_ERROR (Status)) {
> +    return Status;
> +  }
> +
> +  ReadSize = (UINTN)FileSize;
> +  Status = gEfiShellProtocol->ReadFile (FileHandle, &ReadSize,
> +                                (VOID *)(UINTN)mInitrdFileAddress);
> +  if (EFI_ERROR (Status) || ReadSize < FileSize) {
> +    DEBUG ((DEBUG_WARN, "%a: failed to read initrd file - %r 0x%lx 0x%lx\n",
> +      __FUNCTION__, Status, (UINT64)ReadSize, FileSize));
> +    goto FreeMemory;
> +  }
> +
> +  if (mInitrdLoadFile2Handle == NULL) {
> +    Status = gBS->InstallMultipleProtocolInterfaces (&mInitrdLoadFile2Handle,
> +                    &gEfiDevicePathProtocolGuid,  &mInitrdDevicePath,
> +                    &gEfiLoadFile2ProtocolGuid,   &mInitrdLoadFile2,
> +                    NULL);
> +    ASSERT_EFI_ERROR (Status);
> +  }
> +
> +  mInitrdFileSize = FileSize;
> +  return EFI_SUCCESS;
> +
> +FreeMemory:
> +  gBS->FreePages (mInitrdFileAddress, EFI_SIZE_TO_PAGES ((UINTN)FileSize));
> +  return Status;
> +}
> +
> +/**
> +  Function for 'initrd' command.
> +
> +  @param[in] ImageHandle  Handle to the Image (NULL if Internal).
> +  @param[in] SystemTable  Pointer to the System Table (NULL if Internal).
> +**/
> +STATIC
> +SHELL_STATUS
> +EFIAPI
> +RunInitrd (
> +  IN EFI_HANDLE        ImageHandle,
> +  IN EFI_SYSTEM_TABLE  *SystemTable
> +  )
> +{
> +  EFI_STATUS            Status;
> +  LIST_ENTRY            *Package;
> +  CHAR16                *ProblemParam;
> +  CONST CHAR16          *Param;
> +  CONST CHAR16          *Filename;
> +  SHELL_STATUS          ShellStatus;
> +  SHELL_FILE_HANDLE     FileHandle;
> +
> +  ProblemParam        = NULL;
> +  ShellStatus         = SHELL_SUCCESS;
> +
> +  Status = ShellInitialize ();
> +  ASSERT_EFI_ERROR (Status);
> +
> +  //
> +  // parse the command line
> +  //
> +  Status = ShellCommandLineParse (ParamList, &Package, &ProblemParam, TRUE);
> +  if (EFI_ERROR (Status)) {
> +    if (Status == EFI_VOLUME_CORRUPTED && ProblemParam != NULL) {
> +      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM),
> +        mLinuxInitrdShellCommandHiiHandle, L"initrd", ProblemParam);
> +      FreePool (ProblemParam);
> +      ShellStatus = SHELL_INVALID_PARAMETER;
> +    } else {
> +      ASSERT(FALSE);
> +    }
> +  } else {
> +    if (ShellCommandLineGetCount (Package) > 2) {
> +      ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_MANY),
> +        mLinuxInitrdShellCommandHiiHandle, L"initrd");
> +      ShellStatus = SHELL_INVALID_PARAMETER;
> +    } else if (ShellCommandLineGetCount (Package) < 2) {
> +      if (ShellCommandLineGetFlag (Package, L"-u")) {
> +        FreeInitrdFile ();
> +        UninstallLoadFile2Protocol ();
> +      } else {
> +        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW),
> +          mLinuxInitrdShellCommandHiiHandle, L"initrd");
> +        ShellStatus = SHELL_INVALID_PARAMETER;
> +      }
> +    } else {
> +      Param = ShellCommandLineGetRawValue (Package, 1);
> +      ASSERT (Param != NULL);
> +
> +      Filename = ShellFindFilePath (Param);
> +      if (Filename == NULL) {
> +        ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_FIND_FAIL),
> +          mLinuxInitrdShellCommandHiiHandle, L"initrd", Param);
> +        ShellStatus = SHELL_NOT_FOUND;
> +      } else {
> +        Status = ShellOpenFileByName (Filename, &FileHandle,
> +                   EFI_FILE_MODE_READ, 0);
> +        if (!EFI_ERROR (Status)) {
> +          FreeInitrdFile ();
> +          Status = CacheInitrdFile (FileHandle);
> +          ShellCloseFile (&FileHandle);
> +        }
> +        if (EFI_ERROR (Status)) {
> +          ShellPrintHiiEx (-1, -1, NULL, STRING_TOKEN (STR_GEN_FILE_OPEN_FAIL),
> +            mLinuxInitrdShellCommandHiiHandle, L"initrd", Param);
> +          ShellStatus = SHELL_NOT_FOUND;
> +        }
> +      }
> +      FreePool (Filename);

(1) This FreePool() is in the wrong spot; FreePool() can't deal with
NULL (unlike free() in standard C) in general. Please move FreePool()
just one line higher up (and two spaces to the right); i.e., to the end
of the "else" branch of the (Filename == NULL) check.

With (1) addressed (no need to repost):

Reviewed-by: Laszlo Ersek <lersek at redhat.com>

Thanks!
Laszlo



> +    }
> +  }
> +  return ShellStatus;
> +}
> +
> +
> +/**
> +  This is the shell command handler function pointer callback type.  This
> +  function handles the command when it is invoked in the shell.
> +
> +  @param[in] This                   The instance of the
> +                                    EFI_SHELL_DYNAMIC_COMMAND_PROTOCOL.
> +  @param[in] SystemTable            The pointer to the system table.
> +  @param[in] ShellParameters        The parameters associated with the command.
> +  @param[in] Shell                  The instance of the shell protocol used in
> +                                    the context of processing this command.
> +
> +  @return EFI_SUCCESS               the operation was successful
> +  @return other                     the operation failed.
> +**/
> +SHELL_STATUS
> +EFIAPI
> +LinuxInitrdCommandHandler (
> +  IN EFI_SHELL_DYNAMIC_COMMAND_PROTOCOL    *This,
> +  IN EFI_SYSTEM_TABLE                      *SystemTable,
> +  IN EFI_SHELL_PARAMETERS_PROTOCOL         *ShellParameters,
> +  IN EFI_SHELL_PROTOCOL                    *Shell
> +  )
> +{
> +  gEfiShellParametersProtocol = ShellParameters;
> +  gEfiShellProtocol           = Shell;
> +
> +  return RunInitrd (gImageHandle, SystemTable);
> +}
> +
> +/**
> +  This is the command help handler function pointer callback type.  This
> +  function is responsible for displaying help information for the associated
> +  command.
> +
> +  @param[in] This                   The instance of the
> +                                    EFI_SHELL_DYNAMIC_COMMAND_PROTOCOL.
> +  @param[in] Language               The pointer to the language string to use.
> +
> +  @return string                    Pool allocated help string, must be freed
> +                                    by caller
> +**/
> +STATIC
> +CHAR16 *
> +EFIAPI
> +LinuxInitrdGetHelp (
> +  IN EFI_SHELL_DYNAMIC_COMMAND_PROTOCOL    *This,
> +  IN CONST CHAR8                           *Language
> +  )
> +{
> +  return HiiGetString (mLinuxInitrdShellCommandHiiHandle,
> +           STRING_TOKEN (STR_GET_HELP_INITRD), Language);
> +}
> +
> +STATIC EFI_SHELL_DYNAMIC_COMMAND_PROTOCOL mLinuxInitrdDynamicCommand = {
> +  L"initrd",
> +  LinuxInitrdCommandHandler,
> +  LinuxInitrdGetHelp
> +};
> +
> +/**
> +  Retrieve HII package list from ImageHandle and publish to HII database.
> +
> +  @param ImageHandle            The image handle of the process.
> +
> +  @return HII handle.
> +**/
> +STATIC
> +EFI_HII_HANDLE
> +InitializeHiiPackage (
> +  EFI_HANDLE                  ImageHandle
> +  )
> +{
> +  EFI_STATUS                  Status;
> +  EFI_HII_PACKAGE_LIST_HEADER *PackageList;
> +  EFI_HII_HANDLE              HiiHandle;
> +
> +  //
> +  // Retrieve HII package list from ImageHandle
> +  //
> +  Status = gBS->OpenProtocol (ImageHandle, &gEfiHiiPackageListProtocolGuid,
> +                  (VOID **)&PackageList, ImageHandle, NULL,
> +                  EFI_OPEN_PROTOCOL_GET_PROTOCOL);
> +  ASSERT_EFI_ERROR (Status);
> +  if (EFI_ERROR (Status)) {
> +    return NULL;
> +  }
> +
> +  //
> +  // Publish HII package list to HII Database.
> +  //
> +  Status = gHiiDatabase->NewPackageList (gHiiDatabase, PackageList, NULL,
> +                           &HiiHandle);
> +  ASSERT_EFI_ERROR (Status);
> +  if (EFI_ERROR (Status)) {
> +    return NULL;
> +  }
> +  return HiiHandle;
> +}
> +
> +/**
> +  Entry point of Linux Initrd dynamic UEFI Shell command.
> +
> +  Produce the DynamicCommand protocol to handle "initrd" command.
> +
> +  @param ImageHandle            The image handle of the process.
> +  @param SystemTable            The EFI System Table pointer.
> +
> +  @retval EFI_SUCCESS           Initrd command is executed successfully.
> +  @retval EFI_ABORTED           HII package was failed to initialize.
> +  @retval others                Other errors when executing Initrd command.
> +**/
> +EFI_STATUS
> +EFIAPI
> +LinuxInitrdDynamicShellCommandEntryPoint (
> +  IN EFI_HANDLE               ImageHandle,
> +  IN EFI_SYSTEM_TABLE         *SystemTable
> +  )
> +{
> +  EFI_STATUS                  Status;
> +
> +  mLinuxInitrdShellCommandHiiHandle = InitializeHiiPackage (ImageHandle);
> +  if (mLinuxInitrdShellCommandHiiHandle == NULL) {
> +    return EFI_ABORTED;
> +  }
> +
> +  Status = gBS->InstallProtocolInterface (&ImageHandle,
> +                  &gEfiShellDynamicCommandProtocolGuid,
> +                  EFI_NATIVE_INTERFACE,
> +                  &mLinuxInitrdDynamicCommand);
> +  ASSERT_EFI_ERROR (Status);
> +  return Status;
> +}
> +
> +/**
> +  Unload the dynamic UEFI Shell command.
> +
> +  @param ImageHandle            The image handle of the process.
> +
> +  @retval EFI_SUCCESS           The image is unloaded.
> +  @retval Others                Failed to unload the image.
> +**/
> +EFI_STATUS
> +EFIAPI
> +LinuxInitrdDynamicShellCommandUnload (
> +  IN EFI_HANDLE               ImageHandle
> +)
> +{
> +  EFI_STATUS                  Status;
> +
> +  FreeInitrdFile ();
> +
> +  Status = UninstallLoadFile2Protocol ();
> +  if (EFI_ERROR (Status)) {
> +    return Status;
> +  }
> +
> +  Status = gBS->UninstallProtocolInterface (ImageHandle,
> +                  &gEfiShellDynamicCommandProtocolGuid,
> +                  &mLinuxInitrdDynamicCommand);
> +  if (EFI_ERROR (Status)) {
> +    return Status;
> +  }
> +
> +  HiiRemovePackages (mLinuxInitrdShellCommandHiiHandle);
> +  return EFI_SUCCESS;
> +}
> diff --git a/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.inf b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.inf
> new file mode 100644
> index 000000000000..6da6ef6d7818
> --- /dev/null
> +++ b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.inf
> @@ -0,0 +1,53 @@
> +##  @file
> +# Provides 'initrd' dynamic UEFI shell command to load a Linux initrd
> +# via its GUIDed vendor media path
> +#
> +# Copyright (c) 2020, Arm, Ltd. All rights reserved.<BR>
> +#
> +#  SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +#
> +##
> +
> +[Defines]
> +  INF_VERSION                    = 1.27
> +  BASE_NAME                      = LinuxInitrdDynamicShellCommand
> +  FILE_GUID                      = 2f30da26-f51b-4b6f-85c4-31873c281bca
> +  MODULE_TYPE                    = DXE_DRIVER
> +  VERSION_STRING                 = 1.0
> +  ENTRY_POINT                    = LinuxInitrdDynamicShellCommandEntryPoint
> +  UNLOAD_IMAGE                   = LinuxInitrdDynamicShellCommandUnload
> +  UEFI_HII_RESOURCE_SECTION      = TRUE
> +
> +#
> +#  VALID_ARCHITECTURES           = IA32 X64 ARM AARCH64 EBC
> +#
> +
> +[Sources.common]
> +  LinuxInitrdDynamicShellCommand.c
> +  LinuxInitrdDynamicShellCommand.uni
> +
> +[Packages]
> +  MdePkg/MdePkg.dec
> +  ShellPkg/ShellPkg.dec
> +  MdeModulePkg/MdeModulePkg.dec
> +  OvmfPkg/OvmfPkg.dec
> +
> +[LibraryClasses]
> +  DebugLib
> +  DevicePathLib
> +  HiiLib
> +  MemoryAllocationLib
> +  ShellLib
> +  UefiBootServicesTableLib
> +  UefiDriverEntryPoint
> +  UefiHiiServicesLib
> +
> +[Protocols]
> +  gEfiDevicePathProtocolGuid                      ## SOMETIMES_PRODUCES
> +  gEfiHiiPackageListProtocolGuid                  ## CONSUMES
> +  gEfiLoadFile2ProtocolGuid                       ## SOMETIMES_PRODUCES
> +  gEfiShellDynamicCommandProtocolGuid             ## PRODUCES
> +
> +[DEPEX]
> +  TRUE
> diff --git a/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.uni b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.uni
> new file mode 100644
> index 000000000000..a88fa6e3641b
> --- /dev/null
> +++ b/OvmfPkg/LinuxInitrdDynamicShellCommand/LinuxInitrdDynamicShellCommand.uni
> @@ -0,0 +1,49 @@
> +// /**
> +//
> +// Copyright (c) 2020, Arm, Ltd. All rights reserved.<BR>
> +// SPDX-License-Identifier: BSD-2-Clause-Patent
> +//
> +// Module Name:
> +//
> +// LinuxInitrdDynamicShellCommand.uni
> +//
> +// Abstract:
> +//
> +// String definitions for 'initrd' UEFI Shell command
> +//
> +// **/
> +
> +/=#
> +
> +#langdef   en-US "english"
> +
> +#string STR_GEN_PROBLEM           #language en-US "%H%s%N: Unknown flag - '%H%s%N'\r\n"
> +#string STR_GEN_TOO_MANY          #language en-US "%H%s%N: Too many arguments.\r\n"
> +#string STR_GEN_TOO_FEW           #language en-US "%H%s%N: Too few arguments.\r\n"
> +#string STR_GEN_FIND_FAIL         #language en-US "%H%s%N: File not found - '%H%s%N'\r\n"
> +#string STR_GEN_FILE_OPEN_FAIL    #language en-US "%H%s%N: Cannot open file - '%H%s%N'\r\n"
> +
> +#string STR_GET_HELP_INITRD       #language en-US ""
> +".TH initrd 0 "Registers or unregisters a file as Linux initrd."\r\n"
> +".SH NAME\r\n"
> +"Registers or unregisters a file as Linux initrd.\r\n"
> +".SH SYNOPSIS\r\n"
> +" \r\n"
> +"initrd <FileName>\r\n"
> +"initrd -u\r\n"
> +".SH OPTIONS\r\n"
> +" \r\n"
> +"  FileName    - Specifies a file to register as initrd.\r\n"
> +"  -u          - Unregisters any previously registered initrd files.\r\n"
> +".SH DESCRIPTION\r\n"
> +" \r\n"
> +"NOTES:\r\n"
> +"  1. Only a single file can be loaded as initrd at any given time. Using the\r\n"
> +"     command twice with a <FileName> option will result in the first file to\r\n"
> +"     be unloaded again, regardless of whether the second invocation succeeded\r\n"
> +"     or not.\r\n"
> +"  2. The initrd is not unloaded when the shell exits, and will remain active\r\n"
> +"     until it is unloaded again by a different invocation of the shell.\r\n"
> +"     Consumers of the LoadFile2 protocol on the LINUX_EFI_INITRD_MEDIA_GUID\r\n"
> +"     device path that are started via means other than the shell will be able\r\n"
> +"     to locate the protocol and invoke it.\r\n"
> 


-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.

View/Reply Online (#54994): https://edk2.groups.io/g/devel/message/54994
Mute This Topic: https://groups.io/mt/71572292/1813853
Group Owner: devel+owner at edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub  [edk2-devel-archive at redhat.com]
-=-=-=-=-=-=-=-=-=-=-=-





More information about the edk2-devel-archive mailing list