Example #1
0
/**
  Initialize the platform default console variables when the console variable is empty.

  @param PlatformConsole  Predfined platform default console device array.
**/
VOID
InitializeConsoleVariables (
  IN BDS_CONSOLE_CONNECT_ENTRY   *PlatformConsole
  )
{
  UINTN                     Index;
  EFI_DEVICE_PATH_PROTOCOL  *VarConOut;
  EFI_DEVICE_PATH_PROTOCOL  *VarConIn;
  EFI_BOOT_MODE             BootMode;

  BootMode = GetBootModeHob ();

  VarConOut = GetEfiGlobalVariable (L"ConOut");   if (VarConOut != NULL) { FreePool (VarConOut); }
  VarConIn  = GetEfiGlobalVariable (L"ConIn");    if (VarConIn  != NULL) { FreePool (VarConIn);  }
  if (VarConOut == NULL || VarConIn == NULL) {
    //
    // Only fill ConIn/ConOut when ConIn/ConOut is empty because we may drop to Full Configuration boot mode in non-first boot
    //
    for (Index = 0; PlatformConsole[Index].DevicePath != NULL; Index++) {
      //
      // Update the console variable with the connect type
      //
      if ((PlatformConsole[Index].ConnectType & CONSOLE_IN) == CONSOLE_IN) {
        EfiBootManagerUpdateConsoleVariable (ConIn, PlatformConsole[Index].DevicePath, NULL);
      }
      if ((PlatformConsole[Index].ConnectType & CONSOLE_OUT) == CONSOLE_OUT) {
        EfiBootManagerUpdateConsoleVariable (ConOut, PlatformConsole[Index].DevicePath, NULL);
      }
      if ((PlatformConsole[Index].ConnectType & STD_ERROR) == STD_ERROR) {
        EfiBootManagerUpdateConsoleVariable (ErrOut, PlatformConsole[Index].DevicePath, NULL);
      }
    }
  }
}
Example #2
0
/**
  This CALLBACK_FUNCTION retrieves the EFI_DEVICE_PATH_PROTOCOL from the
  handle, and adds it to ConOut and ErrOut.
**/
STATIC
VOID
EFIAPI
AddOutput (
  IN EFI_HANDLE   Handle,
  IN CONST CHAR16 *ReportText
  )
{
  EFI_STATUS               Status;
  EFI_DEVICE_PATH_PROTOCOL *DevicePath;

  DevicePath = DevicePathFromHandle (Handle);
  if (DevicePath == NULL) {
    DEBUG ((EFI_D_ERROR, "%a: %s: handle %p: device path not found\n",
      __FUNCTION__, ReportText, Handle));
    return;
  }

  Status = EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
  if (EFI_ERROR (Status)) {
    DEBUG ((EFI_D_ERROR, "%a: %s: adding to ConOut: %r\n", __FUNCTION__,
      ReportText, Status));
    return;
  }

  Status = EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
  if (EFI_ERROR (Status)) {
    DEBUG ((EFI_D_ERROR, "%a: %s: adding to ErrOut: %r\n", __FUNCTION__,
      ReportText, Status));
    return;
  }

  DEBUG ((EFI_D_VERBOSE, "%a: %s: added to ConOut and ErrOut\n", __FUNCTION__,
    ReportText));
}
Example #3
0
/**
  Do the platform init, can be customized by OEM/IBV
  Possible things that can be done in PlatformBootManagerBeforeConsole:
  > Update console variable: 1. include hot-plug devices;
  >                          2. Clear ConIn and add SOL for AMT
  > Register new Driver#### or Boot####
  > Register new Key####: e.g.: F12
  > Signal ReadyToLock event
  > Authentication action: 1. connect Auth devices;
  >                        2. Identify auto logon user.
**/
VOID
EFIAPI
PlatformBootManagerBeforeConsole (
  VOID
  )
{
  //
  // Signal EndOfDxe PI Event
  //
  EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);

  //
  // Locate the PCI root bridges and make the PCI bus driver connect each,
  // non-recursively. This will produce a number of child handles with PciIo on
  // them.
  //
  FilterAndProcess (&gEfiPciRootBridgeIoProtocolGuid, NULL, Connect);

  //
  // Find all display class PCI devices (using the handles from the previous
  // step), and connect them non-recursively. This should produce a number of
  // child handles with GOPs on them.
  //
  FilterAndProcess (&gEfiPciIoProtocolGuid, IsPciDisplay, Connect);

  //
  // Now add the device path of all handles with GOP on them to ConOut and
  // ErrOut.
  //
  FilterAndProcess (&gEfiGraphicsOutputProtocolGuid, NULL, AddOutput);

  //
  // Add the hardcoded short-form USB keyboard device path to ConIn.
  //
  EfiBootManagerUpdateConsoleVariable (ConIn,
    (EFI_DEVICE_PATH_PROTOCOL *)&mUsbKeyboard, NULL);

  //
  // Add the hardcoded serial console device path to ConIn, ConOut, ErrOut.
  //
  ASSERT (FixedPcdGet8 (PcdDefaultTerminalType) == 4);
  CopyGuid (&mSerialConsole.TermType.Guid, &gEfiTtyTermGuid);

  EfiBootManagerUpdateConsoleVariable (ConIn,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
  EfiBootManagerUpdateConsoleVariable (ConOut,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
  EfiBootManagerUpdateConsoleVariable (ErrOut,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);

  //
  // Register platform-specific boot options and keyboard shortcuts.
  //
  PlatformRegisterOptionsAndKeys ();
}
/**
  Do the platform specific action before the console is connected.

  Such as:
    Update console variable;
    Register new Driver#### or Boot####;
    Signal ReadyToLock event.
**/
VOID
EFIAPI
PlatformBootManagerBeforeConsole (
  VOID
  )
{
  UINTN                        Index;
  EFI_STATUS                   Status;
  WIN_NT_SYSTEM_CONFIGURATION  *Configuration;

  GetVariable2 (L"Setup", &gEfiWinNtSystemConfigGuid, (VOID **) &Configuration, NULL);
  if (Configuration != NULL) {
    //
    // SetupVariable is corrupt
    //
    Configuration->ConOutRow = PcdGet32 (PcdConOutColumn);
    Configuration->ConOutColumn = PcdGet32 (PcdConOutRow);

    Status = gRT->SetVariable (
                    L"Setup",
                    &gEfiWinNtSystemConfigGuid,
                    EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS,
                    sizeof (WIN_NT_SYSTEM_CONFIGURATION),
                    Configuration
                    );
    if (EFI_ERROR (Status)) {
      DEBUG ((EFI_D_ERROR, "Failed to save Setup Variable to non-volatile storage, Status = %r\n", Status));
    }
    FreePool (Configuration);
  }

  //
  // Update the ocnsole variables.
  //
  for (Index = 0; gPlatformConsole[Index].DevicePath != NULL; Index++) {
    if ((gPlatformConsole[Index].ConnectType & CONSOLE_IN) == CONSOLE_IN) {
      EfiBootManagerUpdateConsoleVariable (ConIn, gPlatformConsole[Index].DevicePath, NULL);
    }

    if ((gPlatformConsole[Index].ConnectType & CONSOLE_OUT) == CONSOLE_OUT) {
      EfiBootManagerUpdateConsoleVariable (ConOut, gPlatformConsole[Index].DevicePath, NULL);
    }

    if ((gPlatformConsole[Index].ConnectType & STD_ERROR) == STD_ERROR) {
      EfiBootManagerUpdateConsoleVariable (ErrOut, gPlatformConsole[Index].DevicePath, NULL);
    }
  }

  //
  // From PI spec vol2:
  // Prior to invoking any UEFI drivers, applications, or connecting consoles, 
  // the platform should signal the event EFI_END_OF_DXE_EVENT_GUID
  //
  EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);
}
Example #5
0
/**
  Do the platform specific action before the console is connected.

  Such as:
    Update console variable;
    Register new Driver#### or Boot####;
    Signal ReadyToLock event.
**/
VOID
EFIAPI
PlatformBootManagerBeforeConsole (
  VOID
  )
{
  UINTN                        Index;
  EFI_STATUS                   Status;
  WIN_NT_SYSTEM_CONFIGURATION  *Configuration;
  EFI_INPUT_KEY                Enter;
  EFI_INPUT_KEY                F2;
  EFI_BOOT_MANAGER_LOAD_OPTION BootOption;

  //
  // Update the ocnsole variables.
  //
  for (Index = 0; gPlatformConsole[Index].DevicePath != NULL; Index++) {
    if ((gPlatformConsole[Index].ConnectType & CONSOLE_IN) == CONSOLE_IN) {
      EfiBootManagerUpdateConsoleVariable (ConIn, gPlatformConsole[Index].DevicePath, NULL);
    }

    if ((gPlatformConsole[Index].ConnectType & CONSOLE_OUT) == CONSOLE_OUT) {
      EfiBootManagerUpdateConsoleVariable (ConOut, gPlatformConsole[Index].DevicePath, NULL);
    }

    if ((gPlatformConsole[Index].ConnectType & STD_ERROR) == STD_ERROR) {
      EfiBootManagerUpdateConsoleVariable (ErrOut, gPlatformConsole[Index].DevicePath, NULL);
    }
  }

  //
  // Register ENTER as CONTINUE key
  //
  Enter.ScanCode    = SCAN_NULL;
  Enter.UnicodeChar = CHAR_CARRIAGE_RETURN;
  EfiBootManagerRegisterContinueKeyOption (0, &Enter, NULL);
  //
  // Map F2 to Boot Manager Menu
  //
  F2.ScanCode    = SCAN_F2;
  F2.UnicodeChar = CHAR_NULL;
  EfiBootManagerGetBootManagerMenu (&BootOption);
  EfiBootManagerAddKeyOptionVariable (NULL, (UINT16) BootOption.OptionNumber, 0, &F2, NULL);
  //
  // Register UEFI Shell
  //
  PlatformRegisterFvBootOption (&mUefiShellFileGuid, L"UEFI Shell", LOAD_OPTION_ACTIVE);
}
Example #6
0
/**
  Find the platform active active video controller and connect it.

  @retval EFI_NOT_FOUND There is no active video controller.
  @retval EFI_SUCCESS   The video controller is connected.
**/
EFI_STATUS
ConnectVideoController (
  VOID
  )
{
  EFI_HANDLE                 VideoController;
  EFI_DEVICE_PATH_PROTOCOL   *Gop;
  
  //
  // Get the platform vga device
  //
  VideoController = GetVideoController ();
  
  if (VideoController == NULL) {
    return EFI_NOT_FOUND;
  }

  //
  // Try to connect the PCI device path, so that GOP dirver could start on this 
  // device and create child handles with GraphicsOutput Protocol installed
  // on them, then we get device paths of these child handles and select 
  // them as possible console device.
  //
  gBS->ConnectController (VideoController, NULL, NULL, FALSE);

  Gop = EfiBootManagerGetGopDevicePath (VideoController);
  if (Gop == NULL) {
    //
    // Last chance - just try VGA controller
    // Don't assume all VGA controller support GOP operation
    //
    DEBUG ((EFI_D_ERROR, "[Bds] GOP not found, try VGA device path!\n"));
    Gop = DuplicateDevicePath (DevicePathFromHandle (VideoController));
    if (Gop == NULL) {
      return EFI_NOT_FOUND;
    }
  }

  EfiBootManagerUpdateConsoleVariable (ConOut, Gop, NULL);
  FreePool (Gop);

  //
  // Necessary for ConPlatform and ConSplitter driver to start up again after ConOut is updated.
  //
  return gBS->ConnectController (VideoController, NULL, NULL, TRUE);
}
Example #7
0
/**
  Connect the platform active active video controller.

  @param VideoController       PCI handle of video controller.

  @retval EFI_NOT_FOUND There is no active video controller.
  @retval EFI_SUCCESS   The video controller is connected.
**/
EFI_STATUS
EFIAPI
EfiBootManagerConnectVideoController (
  EFI_HANDLE                 VideoController  OPTIONAL
  )
{
  EFI_DEVICE_PATH_PROTOCOL   *Gop;
  
  if (VideoController == NULL) {
    //
    // Get the platform vga device
    //
    VideoController = BmGetVideoController ();
  }
 
  if (VideoController == NULL) {
    return EFI_NOT_FOUND;
  }

  //
  // Try to connect the PCI device path, so that GOP dirver could start on this 
  // device and create child handles with GraphicsOutput Protocol installed
  // on them, then we get device paths of these child handles and select 
  // them as possible console device.
  //
  gBS->ConnectController (VideoController, NULL, NULL, FALSE);

  Gop = EfiBootManagerGetGopDevicePath (VideoController);
  if (Gop == NULL) {
    return EFI_NOT_FOUND;
  }

  EfiBootManagerUpdateConsoleVariable (ConOut, Gop, NULL);
  FreePool (Gop);

  //
  // Necessary for ConPlatform and ConSplitter driver to start up again after ConOut is updated.
  //
  return gBS->ConnectController (VideoController, NULL, NULL, TRUE);
}
Example #8
0
//
// BDS Platform Functions
//
VOID
EFIAPI
PlatformBootManagerBeforeConsole (
  VOID
  )
{
  EFI_HANDLE                Handle;
  EFI_STATUS                Status;
  EFI_ACPI_S3_SAVE_PROTOCOL *AcpiS3Save;
  BOOLEAN                   SecureBootSupportEnabled;
  BOOLEAN                   SecureBootEnabled;

  SecureBootSupportEnabled = FALSE;
  SecureBootEnabled = FALSE;

  if (FeaturePcdGet (PcdSupportSecureBoot)) {

    //
    // Auto provision UEFI Secure boot.
    //
    SecureBootSupportEnabled = TRUE;
    SecureBootEnabled = PlatformAutoProvisionSecureBoot ();

    //
    // UEFI Secure boot not supported / validated for this firmware release.
    //
    ASSERT (FALSE);

  }

  if (FeaturePcdGet (PcdEnableSecureLock)) {
    if (!SecureBootEnabled) {
      PcdSetBool (PcdConInConnectOnDemand, TRUE);
    }

    DEBUG (
      (EFI_D_INFO, "Secure Lock ENABLED Secure Boot Support %s Secure Boot %s\n",
      SecureBootSupportEnabled ? L"ENABLED" : L"DISABLED",
      SecureBootEnabled ? L"ENABLED" : L"DISABLED"
      ));
  } else {
    DEBUG (
      (EFI_D_INFO, "Secure Lock DISABLED Secure Boot Support %s Secure Boot %s\n",
      SecureBootSupportEnabled ? L"ENABLED" : L"DISABLED",
      SecureBootEnabled ? L"ENABLED" : L"DISABLED"
      ));
  }

  //
  // Add platform string package
  //
  InitializeStringSupport ();

  InitializeConsoleVariables (gPlatformConsole);
  UpdateConOut ();
  
  RegisterLoadOptions ();


  Status = gBS->LocateProtocol (&gEfiAcpiS3SaveProtocolGuid, NULL, (VOID **)&AcpiS3Save);
  if (!EFI_ERROR (Status)) {
    AcpiS3Save->S3Save (AcpiS3Save, NULL);
  }

  //
  // Inform the SMM infrastructure that we're entering BDS and may run 3rd party code hereafter 
  //
  Handle = NULL;
  Status = gBS->InstallProtocolInterface (
                  &Handle,
                  &gExitPmAuthProtocolGuid,
                  EFI_NATIVE_INTERFACE,
                  NULL
                  );
  ASSERT_EFI_ERROR (Status);
  
  //
  // Append Usb Keyboard short form DevicePath into "ConInDev" 
  //
  EfiBootManagerUpdateConsoleVariable (
    ConInDev,
    (EFI_DEVICE_PATH_PROTOCOL *) &gUsbClassKeyboardDevicePath,
    NULL
    );
    
  //
  // Before user authentication, the user identification devices need be connected 
  // from the platform customized device paths
  //
  ConnectAuthDevice ();

  //
  // As console is not ready, the auto logon user will be identified.
  //
  UserIdentify (&mCurrentUser);
}
Example #9
0
VOID
UpdateConOut (
  VOID
  )
{
  EFI_HANDLE                 VideoController;
  EFI_DEVICE_PATH_PROTOCOL   *Gop;
  EFI_HANDLE                 OnboardVideoController = NULL;
  EFI_HANDLE                 AddinVideoController = NULL;
  UINTN                      VideoSelect;

  //
  // Get the platform vga device
  //
  VideoController = PlatformGetVideoController (&OnboardVideoController, &AddinVideoController);
  
  if (VideoController == NULL) {
    return ;
  }
  

  // Force to Auto
  VideoSelect = 0;

  // If device selected by SystemConfig is not present, force to Auto
  if (VideoSelect == 1 && OnboardVideoController == NULL) {
    VideoSelect = 0;
  }
  if (VideoSelect == 2 && AddinVideoController == NULL) {
    VideoSelect = 0;
  }

  switch(VideoSelect) {
  case 1: 
    // Onboard selected
    VideoController = OnboardVideoController;
    DEBUG((EFI_D_INFO, "Video select: Onboard\n"));
    break;
  case 2:
    // Add-in selected
    VideoController = AddinVideoController;
    DEBUG((EFI_D_INFO, "Video select: Add-in\n"));
    break;
  case 0:
  default:
    // Use first VideoController found, which is what GetVideoController returns as VideoController
    DEBUG((EFI_D_INFO, "Video select: Auto\n"));
    break;
  }

  //
  // Try to connect the PCI device path, so that GOP dirver could start on this 
  // device and create child handles with GraphicsOutput Protocol installed
  // on them, then we get device paths of these child handles and select 
  // them as possible console device.
  //
  gBS->ConnectController (VideoController, NULL, NULL, FALSE);

  Gop = EfiBootManagerGetGopDevicePath (VideoController);
  if (Gop == NULL) {
    return ;
  }

  //
  // Update ConOut variable to remove device path of on-board/add-in video controller
  // and add the device path of the specified video controller
  //
  EfiBootManagerUpdateConsoleVariable (ConOut, NULL, DevicePathFromHandle (OnboardVideoController));
  EfiBootManagerUpdateConsoleVariable (ConOut, Gop, DevicePathFromHandle (AddinVideoController));
  FreePool (Gop);

}
Example #10
0
/**
  This function will search every input/output device in current system,
  and make every input/output device as potential console device.
**/
VOID
EFIAPI
EfiBootManagerConnectAllConsoles (
  VOID
  )
{
  UINTN                     Index;
  EFI_DEVICE_PATH_PROTOCOL  *ConDevicePath;
  UINTN                     HandleCount;
  EFI_HANDLE                *HandleBuffer;

  Index         = 0;
  HandleCount   = 0;
  HandleBuffer  = NULL;
  ConDevicePath = NULL;

  //
  // Update all the console variables
  //
  gBS->LocateHandleBuffer (
          ByProtocol,
          &gEfiSimpleTextInProtocolGuid,
          NULL,
          &HandleCount,
          &HandleBuffer
          );

  for (Index = 0; Index < HandleCount; Index++) {
    gBS->HandleProtocol (
            HandleBuffer[Index],
            &gEfiDevicePathProtocolGuid,
            (VOID **) &ConDevicePath
            );
    EfiBootManagerUpdateConsoleVariable (ConIn, ConDevicePath, NULL);
  }

  if (HandleBuffer != NULL) {
    FreePool(HandleBuffer);
    HandleBuffer = NULL;
  }

  gBS->LocateHandleBuffer (
          ByProtocol,
          &gEfiSimpleTextOutProtocolGuid,
          NULL,
          &HandleCount,
          &HandleBuffer
          );
  for (Index = 0; Index < HandleCount; Index++) {
    gBS->HandleProtocol (
            HandleBuffer[Index],
            &gEfiDevicePathProtocolGuid,
            (VOID **) &ConDevicePath
            );
    EfiBootManagerUpdateConsoleVariable (ConOut, ConDevicePath, NULL);
    EfiBootManagerUpdateConsoleVariable (ErrOut, ConDevicePath, NULL);
  }

  if (HandleBuffer != NULL) {
    FreePool(HandleBuffer);
  }

  //
  // Connect all console variables
  //
  EfiBootManagerConnectAllDefaultConsoles ();
}
Example #11
0
/**
  Connect the console device base on the variable ConsoleType.

  @param  ConsoleType              ConIn, ConOut or ErrOut.

  @retval EFI_NOT_FOUND            There is not any console devices connected
                                   success
  @retval EFI_SUCCESS              Success connect any one instance of the console
                                   device path base on the variable ConVarName.

**/
EFI_STATUS
EFIAPI
EfiBootManagerConnectConsoleVariable (
  IN  CONSOLE_TYPE              ConsoleType
  )
{
  EFI_STATUS                Status;
  EFI_DEVICE_PATH_PROTOCOL  *StartDevicePath;
  EFI_DEVICE_PATH_PROTOCOL  *Instance;
  EFI_DEVICE_PATH_PROTOCOL  *Next;
  EFI_DEVICE_PATH_PROTOCOL  *CopyOfDevicePath;
  UINTN                     Size;
  BOOLEAN                   DeviceExist;
  EFI_HANDLE                Handle;

  if ((ConsoleType != ConIn) && (ConsoleType != ConOut) && (ConsoleType != ErrOut)) {
    return EFI_INVALID_PARAMETER;
  }

  Status      = EFI_SUCCESS;
  DeviceExist = FALSE;
  Handle      = NULL;

  //
  // Check if the console variable exist
  //
  GetEfiGlobalVariable2 (mConVarName[ConsoleType], (VOID **) &StartDevicePath, NULL);
  if (StartDevicePath == NULL) {
    return EFI_UNSUPPORTED;
  }

  CopyOfDevicePath = StartDevicePath;
  do {
    //
    // Check every instance of the console variable
    //
    Instance  = GetNextDevicePathInstance (&CopyOfDevicePath, &Size);
    if (Instance == NULL) {
      FreePool (StartDevicePath);
      return EFI_UNSUPPORTED;
    }
    
    Next      = Instance;
    while (!IsDevicePathEndType (Next)) {
      Next = NextDevicePathNode (Next);
    }

    SetDevicePathEndNode (Next);
    //
    // Connect the USB console
    // USB console device path is a short-form device path that 
    //  starts with the first element being a USB WWID
    //  or a USB Class device path
    //
    if ((DevicePathType (Instance) == MESSAGING_DEVICE_PATH) &&
        ((DevicePathSubType (Instance) == MSG_USB_CLASS_DP) || (DevicePathSubType (Instance) == MSG_USB_WWID_DP))
       ) {
      Status = BmConnectUsbShortFormDevicePath (Instance);
      if (!EFI_ERROR (Status)) {
        DeviceExist = TRUE;
      }
    } else {
      for (Next = Instance; !IsDevicePathEnd (Next); Next = NextDevicePathNode (Next)) {
        if (DevicePathType (Next) == ACPI_DEVICE_PATH && DevicePathSubType (Next) == ACPI_ADR_DP) {
          break;
        } else if (DevicePathType (Next) == HARDWARE_DEVICE_PATH && 
                   DevicePathSubType (Next) == HW_CONTROLLER_DP &&
                   DevicePathType (NextDevicePathNode (Next)) == ACPI_DEVICE_PATH &&
                   DevicePathSubType (NextDevicePathNode (Next)) == ACPI_ADR_DP
                   ) {
          break;
        }
      }
      if (!IsDevicePathEnd (Next)) {
        //
        // For GOP device path, start the video driver with NULL remaining device path
        //
        SetDevicePathEndNode (Next);
        Status = EfiBootManagerConnectDevicePath (Instance, &Handle);
        if (!EFI_ERROR (Status)) {
          gBS->ConnectController (Handle, NULL, NULL, TRUE);
        }
      } else {
        Status = EfiBootManagerConnectDevicePath (Instance, NULL);
      }
      if (EFI_ERROR (Status)) {
        //
        // Delete the instance from the console varialbe
        //
        EfiBootManagerUpdateConsoleVariable (ConsoleType, NULL, Instance);
      } else {
        DeviceExist = TRUE;
      }
    }
    FreePool(Instance);
  } while (CopyOfDevicePath != NULL);

  FreePool (StartDevicePath);

  if (!DeviceExist) {
    return EFI_NOT_FOUND;
  }

  return EFI_SUCCESS;
}
Example #12
0
/**
  Do the platform init, can be customized by OEM/IBV
  Possible things that can be done in PlatformBootManagerBeforeConsole:
  > Update console variable: 1. include hot-plug devices;
  >                          2. Clear ConIn and add SOL for AMT
  > Register new Driver#### or Boot####
  > Register new Key####: e.g.: F12
  > Signal ReadyToLock event
  > Authentication action: 1. connect Auth devices;
  >                        2. Identify auto logon user.
**/
VOID
EFIAPI
PlatformBootManagerBeforeConsole (
  VOID
  )
{
  //
  // Signal EndOfDxe PI Event
  //
  EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);

  //
  // Locate the PCI root bridges and make the PCI bus driver connect each,
  // non-recursively. This will produce a number of child handles with PciIo on
  // them.
  //
  FilterAndProcess (&gEfiPciRootBridgeIoProtocolGuid, NULL, Connect);

  //
  // Signal the ACPI platform driver that it can download QEMU ACPI tables.
  //
  EfiEventGroupSignal (&gRootBridgesConnectedEventGroupGuid);

  //
  // Find all display class PCI devices (using the handles from the previous
  // step), and connect them non-recursively. This should produce a number of
  // child handles with GOPs on them.
  //
  FilterAndProcess (&gEfiPciIoProtocolGuid, IsPciDisplay, Connect);

  //
  // Now add the device path of all handles with GOP on them to ConOut and
  // ErrOut.
  //
  FilterAndProcess (&gEfiGraphicsOutputProtocolGuid, NULL, AddOutput);

  //
  // Add the hardcoded short-form USB keyboard device path to ConIn.
  //
  EfiBootManagerUpdateConsoleVariable (ConIn,
    (EFI_DEVICE_PATH_PROTOCOL *)&mUsbKeyboard, NULL);

  //
  // Add the hardcoded serial console device path to ConIn, ConOut, ErrOut.
  //
  CopyGuid (&mSerialConsole.TermType.Guid,
    PcdGetPtr (PcdTerminalTypeGuidBuffer));
  EfiBootManagerUpdateConsoleVariable (ConIn,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
  EfiBootManagerUpdateConsoleVariable (ConOut,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);
  EfiBootManagerUpdateConsoleVariable (ErrOut,
    (EFI_DEVICE_PATH_PROTOCOL *)&mSerialConsole, NULL);

  //
  // Set the front page timeout from the QEMU configuration.
  //
  PcdSet16 (PcdPlatformBootTimeOut, GetFrontPageTimeoutFromQemu ());

  //
  // Register platform-specific boot options and keyboard shortcuts.
  //
  PlatformRegisterOptionsAndKeys ();
}
Example #13
0
/**
  Connect the console device base on the variable ConsoleType.

  @param  ConsoleType              ConIn, ConOut or ErrOut.
  @param  NeedDispatch             Whether need to dispatch.

  @retval EFI_NOT_FOUND            There is not any console devices connected
                                   success
  @retval EFI_SUCCESS              Success connect any one instance of the console
                                   device path base on the variable ConVarName.

**/
EFI_STATUS
EFIAPI
EfiBootManagerConnectConsoleVariable (
  IN  CONSOLE_TYPE              ConsoleType,
  IN  BOOLEAN                   NeedDispatch
  )
{
  EFI_STATUS                Status;
  EFI_DEVICE_PATH_PROTOCOL  *StartDevicePath;
  UINTN                     VariableSize;
  EFI_DEVICE_PATH_PROTOCOL  *Instance;
  EFI_DEVICE_PATH_PROTOCOL  *Next;
  EFI_DEVICE_PATH_PROTOCOL  *CopyOfDevicePath;
  UINTN                     Size;
  BOOLEAN                   DeviceExist;
  EFI_HANDLE                Handle;

  if ((ConsoleType != ConIn) && (ConsoleType != ConOut) && (ConsoleType != ErrOut)) {
    return EFI_INVALID_PARAMETER;
  }

  Status      = EFI_SUCCESS;
  DeviceExist = FALSE;

  //
  // Check if the console variable exist
  //
  StartDevicePath = EfiBootManagerGetVariableAndSize (
                      mConVarName[ConsoleType],
                      &gEfiGlobalVariableGuid,
                      &VariableSize
                      );
  if (StartDevicePath == NULL) {
    return EFI_UNSUPPORTED;
  }

  CopyOfDevicePath = StartDevicePath;
  do {
    //
    // Check every instance of the console variable
    //
    Instance  = GetNextDevicePathInstance (&CopyOfDevicePath, &Size);
    if (Instance == NULL) {
      FreePool (StartDevicePath);
      return EFI_UNSUPPORTED;
    }
    
    Next      = Instance;
    while (!IsDevicePathEndType (Next)) {
      Next = NextDevicePathNode (Next);
    }

    SetDevicePathEndNode (Next);
    //
    // Connect the USB console
    // USB console device path is a short-form device path that 
    //  starts with the first element being a USB WWID
    //  or a USB Class device path
    //
    if (FeaturePcdGet (PcdShortformBootSupport) &&
        (DevicePathType (Instance) == MESSAGING_DEVICE_PATH) &&
        ((DevicePathSubType (Instance) == MSG_USB_CLASS_DP) || (DevicePathSubType (Instance) == MSG_USB_WWID_DP))
       ) {
      Status = EfiBootManagerConnectUsbShortFormDevicePath (Instance);
      if (!EFI_ERROR (Status)) {
        DeviceExist = TRUE;
      }
    } else {
      //
      // Connect the instance device path
      //
      Status = ConnectDevicePath (Instance, NeedDispatch, NULL);
      if (EFI_ERROR (Status)) {
        //
        // Do not delete the instance from the console variable if the device path is of GOP type
        // and the parent controller exists in the system
        // This is to support the monitor hotplug in a headless boot
        //
        for (Next = Instance; !IsDevicePathEnd (Next); Next = NextDevicePathNode (Next)) {
          if (DevicePathType (Next) == ACPI_DEVICE_PATH && DevicePathSubType (Next) == ACPI_ADR_DP) {
            break;
          }
        }
        if (!IsDevicePathEnd (Next)) {
          Next = Instance;
          Status = gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &Next, &Handle);
          if (!EFI_ERROR (Status) && (DevicePathType (Next) != ACPI_DEVICE_PATH || DevicePathSubType (Next) != ACPI_ADR_DP)) {
            //
            // We found the parent controller but it's not the direct parent of the ADR device path instance
            // which indicates the video controller doesn't exist.
            // If this happens, we need to delete the invalid device path from ConOut
            //
            Status = EFI_NOT_FOUND;
          }
        }
      } else {
        DeviceExist = TRUE;
      }

      if (EFI_ERROR (Status)) {
        //
        // Delete the instance from the console variable
        //
        EfiBootManagerUpdateConsoleVariable (ConsoleType, NULL, Instance);
      }
    }
    FreePool(Instance);
  } while (CopyOfDevicePath != NULL);

  FreePool (StartDevicePath);

  if ((ConsoleType == ConOut) && FeaturePcdGet (PcdBdsFindDisplay) && !HasLocalDisplay ()) {
    //
    // Force to connect local video controller
    // Backward compatible to old platforms which don't insert the GOP device path to ConOut
    //
    DEBUG ((EFI_D_ERROR, "[Bds] Local display isn't found, find & connect it automatically\n"));
    Status = ConnectVideoController ();
    if (!EFI_ERROR (Status)) {
      DeviceExist = TRUE;
    }
  }

  if (!DeviceExist) {
    return EFI_NOT_FOUND;
  }

  return EFI_SUCCESS;
}