From nobody Mon Apr 29 05:47:15 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; spf=none (zoho.com: 198.145.21.10 is neither permitted nor denied by domain of lists.01.org) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail(p=none dis=none) header.from=intel.com Return-Path: Received: from ml01.01.org (ml01.01.org [198.145.21.10]) by mx.zohomail.com with SMTPS id 15276580514070.25462792627706676; Tue, 29 May 2018 22:27:31 -0700 (PDT) Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id 3551620D7B273; Tue, 29 May 2018 22:27:30 -0700 (PDT) Received: from mga04.intel.com (mga04.intel.com [192.55.52.120]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id 55E7520D7B253 for ; Tue, 29 May 2018 22:27:29 -0700 (PDT) Received: from fmsmga002.fm.intel.com ([10.253.24.26]) by fmsmga104.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 29 May 2018 22:27:28 -0700 Received: from fmsmsx105.amr.corp.intel.com ([10.18.124.203]) by fmsmga002.fm.intel.com with ESMTP; 29 May 2018 22:27:28 -0700 Received: from fmsmsx101.amr.corp.intel.com (10.18.124.199) by FMSMSX105.amr.corp.intel.com (10.18.124.203) with Microsoft SMTP Server (TLS) id 14.3.319.2; Tue, 29 May 2018 22:27:28 -0700 Received: from shsmsx101.ccr.corp.intel.com (10.239.4.153) by fmsmsx101.amr.corp.intel.com (10.18.124.199) with Microsoft SMTP Server (TLS) id 14.3.319.2; Tue, 29 May 2018 22:27:27 -0700 Received: from shsmsx103.ccr.corp.intel.com ([169.254.4.51]) by SHSMSX101.ccr.corp.intel.com ([169.254.1.82]) with mapi id 14.03.0319.002; Wed, 30 May 2018 13:27:25 +0800 X-Original-To: edk2-devel@lists.01.org Received-SPF: none (zoho.com: 198.145.21.10 is neither permitted nor denied by domain of lists.01.org) client-ip=198.145.21.10; envelope-from=edk2-devel-bounces@lists.01.org; helo=ml01.01.org; Received-SPF: Pass (sender SPF authorized) identity=mailfrom; client-ip=192.55.52.120; helo=mga04.intel.com; envelope-from=mang.guo@intel.com; receiver=edk2-devel@lists.01.org X-Amp-Result: UNKNOWN X-Amp-Original-Verdict: FILE UNKNOWN X-Amp-File-Uploaded: False X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.49,459,1520924400"; d="dat'59?scan'59,208,59";a="51728048" From: "Guo, Mang" To: "edk2-devel@lists.01.org" Thread-Topic: [Patch][edk2-platforms/devel-MinnowBoardMax-UDK2017] Add PlatformBootManagerLib Thread-Index: AdP31uRN2rTvTUi0R0aHk7Sjkaye0A== Date: Wed, 30 May 2018 05:27:25 +0000 Message-ID: <22D2C85ED001C54AA20BFE3B0E4751D15268C332@SHSMSX103.ccr.corp.intel.com> Accept-Language: en-US Content-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: <22D2C85ED001C54AA20BFE3B0E4751D15268C332@SHSMSX103.ccr.corp.intel.com> x-originating-ip: [10.239.127.40] MIME-Version: 1.0 X-Content-Filtered-By: Mailman/MimeDel 2.1.26 Subject: [edk2] [Patch][edk2-platforms/devel-MinnowBoardMax-UDK2017] Add PlatformBootManagerLib X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.26 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Wei, David" Content-Transfer-Encoding: quoted-printable Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" X-ZohoMail: RSF_4 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Contributed-under: TianoCore Contribution Agreement 1.1 Signed-off-by: Guo Mang --- .../Include/Guid/PttPTPInstanceGuid.h | 25 + Vlv2TbltDevicePkg/Include/Protocol/ExitPmAuth.h | 25 + .../PlatformBootManagerLib/PlatformBootManager.c | 1070 ++++++++++++++++= ++++ .../PlatformBootManagerLib/PlatformBootManager.h | 226 +++++ .../PlatformBootManagerLib.inf | 110 ++ .../PlatformBootManagerLib/PlatformBootOption.c | 738 ++++++++++++++ .../Library/PlatformBootManagerLib/PlatformData.c | 179 ++++ 7 files changed, 2373 insertions(+) create mode 100644 Vlv2TbltDevicePkg/Include/Guid/PttPTPInstanceGuid.h create mode 100644 Vlv2TbltDevicePkg/Include/Protocol/ExitPmAuth.h create mode 100644 Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/Platfo= rmBootManager.c create mode 100644 Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/Platfo= rmBootManager.h create mode 100644 Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/Platfo= rmBootManagerLib.inf create mode 100644 Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/Platfo= rmBootOption.c create mode 100644 Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/Platfo= rmData.c diff --git a/Vlv2TbltDevicePkg/Include/Guid/PttPTPInstanceGuid.h b/Vlv2Tblt= DevicePkg/Include/Guid/PttPTPInstanceGuid.h new file mode 100644 index 0000000..277e7f2 --- /dev/null +++ b/Vlv2TbltDevicePkg/Include/Guid/PttPTPInstanceGuid.h @@ -0,0 +1,25 @@ +/** @file + GUID definition for the PTT device instance. + + Copyright (c) 2012 - 2016, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#ifndef __PTT_PTP_INSTANCE_GUID_H__ +#define __PTT_PTP_INSTANCE_GUID_H__ + +#define TPM_DEVICE_INTERFACE_TPM20_PTT_PTP \ +{ 0x93d66f66, 0x55da, 0x4f03, { 0x9b, 0x5f, 0x32, 0xcf, 0x9e, 0x54, 0x3b, = 0x3a } } + +extern EFI_GUID gTpmDeviceInstanceTpm20PttPtpGuid; + +#endif + diff --git a/Vlv2TbltDevicePkg/Include/Protocol/ExitPmAuth.h b/Vlv2TbltDevi= cePkg/Include/Protocol/ExitPmAuth.h new file mode 100644 index 0000000..c9677da --- /dev/null +++ b/Vlv2TbltDevicePkg/Include/Protocol/ExitPmAuth.h @@ -0,0 +1,25 @@ +/** @file + Defines the ExitPmAuth protocol. + + Copyright (c) 2010 - 2016, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#ifndef _EXIT_PM_AUTH_PROTOCOL_H_ +#define _EXIT_PM_AUTH_PROTOCOL_H_ + +#define EXIT_PM_AUTH_PROTOCOL_GUID \ + { 0xd088a413, 0xa70, 0x4217, { 0xba, 0x55, 0x9a, 0x3c, 0xb6, 0x5c, 0x41,= 0xb3 }} + +extern EFI_GUID gExitPmAuthProtocolGuid; + +#endif // #ifndef _EXIT_PM_AUTH_PROTOCOL_H_ + diff --git a/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootM= anager.c b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootMan= ager.c new file mode 100644 index 0000000..6715d90 --- /dev/null +++ b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootManager.c @@ -0,0 +1,1070 @@ +/** @file + This file include all platform action at BDS stage which can be customiz= ed by IBV/OEM. + + Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#include "PlatformBootManager.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + + +#define TIMEOUT_COMMAND 100000 +#define BIOS_COLOR_CODING_BAR_HEIGHT 40 + +GLOBAL_REMOVE_IF_UNREFERENCED EFI_HII_HANDLE gPlatformBdsLi= bStringPackHandle; +GLOBAL_REMOVE_IF_UNREFERENCED EFI_BOOT_MODE mBootMode; + +GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID *mLibTerminalType[] =3D { + &gEfiPcAnsiGuid, + &gEfiVT100Guid, + &gEfiVT100PlusGuid, + &gEfiVTUTF8Guid +}; + +// +// Internal shell mode +// +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mShellModeColumn; +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mShellModeRow; +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mShellHorizontalResolution; +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mShellVerticalResolution; + +CHAR16 *mConsoleVar[] =3D {L"ConIn", L"ConOut"}; + +extern USB_CLASS_FORMAT_DEVICE_PATH mUsbClassKeyboardDevicePath; +extern BOOLEAN mAnyKeypressed; + +/** + The handle on the path we get might be not the display device. + We must check it. + + @todo fix the parameters + + @retval TRUE PCI class type is VGA. + @retval FALSE PCI class type isn't VGA. +**/ +BOOLEAN +IsVgaHandle ( + IN EFI_HANDLE Handle +) +{ + EFI_PCI_IO_PROTOCOL *PciIo; + PCI_TYPE00 Pci; + EFI_STATUS Status; + + Status =3D gBS->HandleProtocol ( + Handle, + &gEfiPciIoProtocolGuid, + (VOID **)&PciIo); + + if (!EFI_ERROR (Status)) { + Status =3D PciIo->Pci.Read ( + PciIo, + EfiPciIoWidthUint32, + 0, + sizeof (Pci) / sizeof (UINT32), + &Pci); + + if (!EFI_ERROR (Status)) { + DEBUG ((DEBUG_ERROR, " PCI CLASS CODE =3D 0x%x\n", Pci.Hdr.Class= Code [2])); + DEBUG ((DEBUG_ERROR, " PCI SUBCLASS CODE =3D 0x%x\n", Pci.Hdr.Class= Code [1])); + + if (IS_PCI_VGA (&Pci) || IS_PCI_OLD_VGA (&Pci)) { + DEBUG ((DEBUG_ERROR, " \nPCI VGA Device Found\n")); + return TRUE; + } + } + } + return FALSE; +} + +/** + This function converts an input device structure to a Unicode string. + + @param DevPath A pointer to the device path structure. + + @return A new allocated Unicode string that represents the device path. +**/ +CHAR16 * +DevicePathToStr ( + IN EFI_DEVICE_PATH_PROTOCOL *DevPath + ) +{ + EFI_STATUS Status; + CHAR16 *ToText; + EFI_DEVICE_PATH_TO_TEXT_PROTOCOL *DevPathToText; + + if (DevPath =3D=3D NULL) { + return NULL; + } + + Status =3D gBS->LocateProtocol ( + &gEfiDevicePathToTextProtocolGuid, + NULL, + (VOID **) &DevPathToText + ); + ASSERT_EFI_ERROR (Status); + ToText =3D DevPathToText->ConvertDevicePathToText ( + DevPath, + FALSE, + TRUE + ); + ASSERT (ToText !=3D NULL); + return ToText; +} + +/** + An empty function to pass error checking of CreateEventEx (). + + This empty function ensures that EVT_NOTIFY_SIGNAL_ALL is error + checked correctly since it is now mapped into CreateEventEx() in UEFI 2.= 0. + + @param Event Event whose notification function is being= invoked. + @param Context The pointer to the notification function's= context, + which is implementation-dependent. +**/ +VOID +EFIAPI +InternalBdsEmptyCallbackFuntion ( + IN EFI_EVENT Event, + IN VOID *Context + ) +{ + return; +} + +VOID +ExitPmAuth ( + VOID + ) +{ + EFI_HANDLE Handle; + EFI_STATUS Status; + EFI_ACPI_S3_SAVE_PROTOCOL *AcpiS3Save; + EFI_EVENT EndOfDxeEvent; + + DEBUG((DEBUG_INFO,"ExitPmAuth ()- Start\n")); + + // + // Inform the SMM infrastructure that we're entering BDS and may run 3rd= party code hereafter + // We can NOT put it to PlatformBdsInit, because many boot script touch = PCI BAR. + // We have to connect PCI root bridge, allocate resource, then ExitPmAut= h(). + // + Handle =3D NULL; + Status =3D gBS->InstallProtocolInterface ( + &Handle, + &gExitPmAuthProtocolGuid, + EFI_NATIVE_INTERFACE, + NULL + ); + ASSERT_EFI_ERROR (Status); + + // + // Since PI1.2.1, we need signal EndOfDxe as ExitPmAuth. + // + Status =3D gBS->CreateEventEx ( + EVT_NOTIFY_SIGNAL, + TPL_CALLBACK, + InternalBdsEmptyCallbackFuntion, + NULL, + &gEfiEndOfDxeEventGroupGuid, + &EndOfDxeEvent + ); + ASSERT_EFI_ERROR (Status); + gBS->SignalEvent (EndOfDxeEvent); + gBS->CloseEvent (EndOfDxeEvent); + DEBUG((DEBUG_INFO,"All EndOfDxe callbacks have returned successfully\n")= ); + + // + // Prepare S3 information, this MUST be done before ExitPmAuth/EndOfDxe. + // + Status =3D gBS->LocateProtocol (&gEfiAcpiS3SaveProtocolGuid, NULL, (VOID= **)&AcpiS3Save); + if (!EFI_ERROR (Status)) { + AcpiS3Save->S3Save (AcpiS3Save, NULL); + } + + // + // NOTE: We need install DxeSmmReadyToLock directly here because many bo= ot script is added via ExitPmAuth/EndOfDxe callback. + // If we install them at same callback, these boot script will be reject= ed because BootScript Driver runs first to lock them done. + // So we seperate them to be 2 different events, ExitPmAuth is last chan= ce to let platform add boot script. DxeSmmReadyToLock will + // make boot script save driver lock down the interface. + // + Handle =3D NULL; + Status =3D gBS->InstallProtocolInterface ( + &Handle, + &gEfiDxeSmmReadyToLockProtocolGuid, + EFI_NATIVE_INTERFACE, + NULL + ); + ASSERT_EFI_ERROR (Status); + DEBUG((DEBUG_INFO,"ExitPmAuth ()- End\n")); +} + +VOID +ConnectRootBridge ( + BOOLEAN Recursive + ) +{ + UINTN RootBridgeHandleCount; + EFI_HANDLE *RootBridgeHandleBuffer; + UINTN RootBridgeIndex; + + RootBridgeHandleCount =3D 0; + gBS->LocateHandleBuffer ( + ByProtocol, + &gEfiPciRootBridgeIoProtocolGuid, + NULL, + &RootBridgeHandleCount, + &RootBridgeHandleBuffer + ); + for (RootBridgeIndex =3D 0; RootBridgeIndex < RootBridgeHandleCount; Roo= tBridgeIndex++) { + gBS->ConnectController (RootBridgeHandleBuffer[RootBridgeIndex], NULL,= NULL, Recursive); + } +} + + +BOOLEAN +IsGopDevicePath ( + EFI_DEVICE_PATH_PROTOCOL *DevicePath + ) +{ + while (!IsDevicePathEndType (DevicePath)) { + if (DevicePathType (DevicePath) =3D=3D ACPI_DEVICE_PATH && + DevicePathSubType (DevicePath) =3D=3D ACPI_ADR_DP) { + return TRUE; + } + DevicePath =3D NextDevicePathNode (DevicePath); + } + return FALSE; +} + +/** + Connect the USB short form device path. + + @param DevicePath USB short form device path. + + @retval EFI_SUCCESS Successfully connected the USB device. + @retval EFI_NOT_FOUND Cannot connect the USB device. + @retval EFI_INVALID_PARAMETER The device path is invalid. +**/ +EFI_STATUS +ConnectUsbShortFormDevicePath ( + IN EFI_DEVICE_PATH_PROTOCOL *DevicePath + ) +{ + EFI_STATUS Status; + EFI_HANDLE *Handles; + UINTN HandleCount; + UINTN Index; + EFI_PCI_IO_PROTOCOL *PciIo; + UINT8 Class[3]; + BOOLEAN AtLeastOneConnected; + + // + // Check the passed in parameters. + // + if (DevicePath =3D=3D NULL) { + return EFI_INVALID_PARAMETER; + } + + if ((DevicePathType (DevicePath) !=3D MESSAGING_DEVICE_PATH) || + ((DevicePathSubType (DevicePath) !=3D MSG_USB_CLASS_DP) && (DevicePa= thSubType (DevicePath) !=3D MSG_USB_WWID_DP)) + ) { + return EFI_INVALID_PARAMETER; + } + + // + // Find the usb host controller firstly, then connect with the remaining= device path. + // + =20 + AtLeastOneConnected =3D FALSE; + Status =3D gBS->LocateHandleBuffer ( + ByProtocol, + &gEfiPciIoProtocolGuid, + NULL, + &HandleCount, + &Handles + ); + =20 + for (Index =3D 0; Index < HandleCount; Index++) { + Status =3D gBS->HandleProtocol ( + Handles[Index], + &gEfiPciIoProtocolGuid, + (VOID **) &PciIo + ); + if (!EFI_ERROR (Status)) { + // + // Check whether the Pci device is the wanted usb host controller. + // + Status =3D PciIo->Pci.Read (PciIo, EfiPciIoWidthUint8, 0x09, 3, &Cla= ss); + if (!EFI_ERROR (Status) && + ((PCI_CLASS_SERIAL =3D=3D Class[2]) && (PCI_CLASS_SERIAL_USB =3D= =3D Class[1])) + ) { + Status =3D gBS->ConnectController ( + Handles[Index], + NULL, + DevicePath, + FALSE + ); + if (!EFI_ERROR(Status)) { + AtLeastOneConnected =3D TRUE; + } + } + } + } + + return AtLeastOneConnected ? EFI_SUCCESS : EFI_NOT_FOUND; +} + +/** + Update the ConIn variable if Ps2 keyboard is connected. +**/ +VOID +EnumPs2Keyboard ( + VOID + ) +{ + UINTN DevicePathSize; + EFI_DEVICE_PATH_PROTOCOL *VarConIn; + EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance; + EFI_DEVICE_PATH_PROTOCOL *Next; + BOOLEAN Ps2Keyboard; + + Ps2Keyboard =3D FALSE; + GetEfiGlobalVariable2 (L"ConIn", (VOID **) &VarConIn, NULL); + + // + // If ConIn variable is empty, need to enumerate PS/2 keyboard device pa= th. + // + do { + DevicePathInstance =3D GetNextDevicePathInstance ( + &VarConIn, + &DevicePathSize + ); + + if (DevicePathInstance =3D=3D NULL) { + // + // The instance is NULL, it means the VarConIn is null, escape the D= O loop, + // and need to add PS/2 keyboard dev path. + // + break; + } + + Next =3D DevicePathInstance; + while (!IsDevicePathEndType(Next)) { + // + // Checking the device path to see the PS/2 keyboard existance. + // + if ((Next->Type =3D=3D ACPI_DEVICE_PATH) && + (Next->SubType =3D=3D ACPI_DP ) && + (((ACPI_HID_DEVICE_PATH *) Next)->HID =3D=3D EISA_PNP_ID (0x0303= ))) { + // + // PS/2 keyboard already exists. + // + DEBUG ((DEBUG_INFO, "[EnumPs2Keyboard] PS2 keyboard path exists\n"= )); + Ps2Keyboard =3D TRUE; + break; + } + Next =3D NextDevicePathNode (Next); + } + + if (DevicePathInstance !=3D NULL) { + FreePool (DevicePathInstance); + } + } while (VarConIn !=3D NULL); + + // + // PS/2 keyboard device path does not exist, so try detecting ps2 keyboa= rd + // and add-in its device path. + // + if (!Ps2Keyboard) { + DEBUG ((DEBUG_INFO, "[EnumPs2Keyboard] Adding detected PS2 keyboard to= ConIn.\n")); + } + + if (VarConIn !=3D NULL) { + FreePool (VarConIn); + } +} + +/** + Update the ConIn variable with USB Keyboard device path,if its not alrea= dy exists in ConIn. +**/ +VOID +EnumUsbKeyboard ( + VOID + ) +{ + UINTN DevicePathSize; + EFI_DEVICE_PATH_PROTOCOL *VarConIn; + EFI_DEVICE_PATH_PROTOCOL *DevicePathInstance; + EFI_DEVICE_PATH_PROTOCOL *Next; + BOOLEAN UsbKeyboard; + + UsbKeyboard =3D FALSE; + GetEfiGlobalVariable2 (L"ConIn", (VOID **)&VarConIn, NULL); + + // + // If ConIn variable is empty, need to enumerate USB keyboard device pat= h. + // + do { + DevicePathInstance =3D GetNextDevicePathInstance ( + &VarConIn, + &DevicePathSize + ); + + if (DevicePathInstance =3D=3D NULL) { + // + // The instance is NULL, it means the VarConIn is null, escape the D= O loop, + // and need to add USB keyboard dev path. + // + break; + } + + Next =3D DevicePathInstance; + while (!IsDevicePathEndType(Next)) { + // + // Checking the device path to see the USB keyboard existance. + // + if ((Next->Type =3D=3D MESSAGING_DEVICE_PATH) && + (Next->SubType =3D=3D MSG_USB_CLASS_DP) && + (((USB_CLASS_DEVICE_PATH *) Next)->DeviceClass =3D=3D CLASS_HID)= && + (((USB_CLASS_DEVICE_PATH *) Next)->DeviceSubClass =3D=3D SUBCLAS= S_BOOT) && + (((USB_CLASS_DEVICE_PATH *) Next)->DeviceProtocol =3D=3D PROTOCO= L_KEYBOARD)) { + =09 + DEBUG ((DEBUG_INFO, "[EnumUsbKeyboard] USB keyboard path exists\n"= )); + UsbKeyboard =3D TRUE; + + break; + } + Next =3D NextDevicePathNode (Next); + } + + if (DevicePathInstance !=3D NULL) { + FreePool (DevicePathInstance); + } + } while (VarConIn !=3D NULL); + + // + // USB keyboard device path does not exist, So add it to the ConIn. + // + if (!UsbKeyboard) { + DEBUG ((DEBUG_INFO, "[EnumUsbKeyboard] Adding USB keyboard device path= to ConIn.\n")); + EfiBootManagerUpdateConsoleVariable (ConIn, (EFI_DEVICE_PATH_PROTOCO= L *) &mUsbClassKeyboardDevicePath, NULL); + } + + if (VarConIn !=3D NULL) { + FreePool (VarConIn); + } +} + +/** + Return whether the device is trusted console. + + @param Device The device to be tested. + + @retval TRUE The device can be trusted. + @retval FALSE The device cannot be trusted. +**/ +BOOLEAN +IsTrustedConsole ( + EFI_DEVICE_PATH_PROTOCOL *Device + ) +{ + if (IsGopDevicePath (Device)) { + return TRUE; + } + + if (CompareMem (Device, &mKeyboardDevicePath, GetDevicePathSize ((EFI_DE= VICE_PATH_PROTOCOL *) &mKeyboardDevicePath) - END_DEVICE_PATH_LENGTH) =3D= =3D 0) { + return TRUE; + } + + if (CompareMem (Device, &mUsbClassKeyboardDevicePath, GetDevicePathSize = ((EFI_DEVICE_PATH_PROTOCOL *) &mUsbClassKeyboardDevicePath) - END_DEVICE_PA= TH_LENGTH) =3D=3D 0) { + return TRUE; + } + + return FALSE; +} + +VOID +ProcessTcgPp ( + VOID + ) +{ + EFI_STATUS Status; + UINTN Tcg2PpDataSize; + EFI_TCG2_PHYSICAL_PRESENCE Tcg2PpData; + EFI_PHYSICAL_PRESENCE TcgPpData; + UINTN TcgPpDataSize; + =20 + // + // Initialize physical presence variable. + // + if (CompareGuid (PcdGetPtr (PcdTpmInstanceGuid), &gEfiTpmDeviceInstanceT= pm20DtpmGuid) || + CompareGuid (PcdGetPtr (PcdTpmInstanceGuid), &gTpmDeviceInstanceTpm20P= ttPtpGuid)) { + Tcg2PpDataSize =3D sizeof (EFI_TCG2_PHYSICAL_PRESENCE); + Status =3D gRT->GetVariable ( + TCG2_PHYSICAL_PRESENCE_VARIABLE, + &gEfiTcg2PhysicalPresenceGuid, + NULL, + &Tcg2PpDataSize, + &Tcg2PpData + ); + + if (EFI_ERROR (Status)) { + ZeroMem ((VOID *) &Tcg2PpData, sizeof (Tcg2PpData)); + Tcg2PpDataSize =3D sizeof (EFI_TCG2_PHYSICAL_PRESENCE); + Status =3D gRT->SetVariable ( + TCG2_PHYSICAL_PRESENCE_VARIABLE, + &gEfiTcg2PhysicalPresenceGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE= _ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, + Tcg2PpDataSize, + &Tcg2PpData + ); + } + } else if (CompareGuid (PcdGetPtr(PcdTpmInstanceGuid), &gEfiTpmDeviceIns= tanceTpm12Guid)) { + TcgPpDataSize =3D sizeof (EFI_PHYSICAL_PRESENCE); + Status =3D gRT->GetVariable ( + PHYSICAL_PRESENCE_VARIABLE, + &gEfiPhysicalPresenceGuid, + NULL, + &TcgPpDataSize, + &TcgPpData + ); + + if (EFI_ERROR (Status)) { + ZeroMem ((VOID *) &TcgPpData, sizeof (TcgPpData)); + TcgPpDataSize =3D sizeof (EFI_PHYSICAL_PRESENCE); + Status =3D gRT->SetVariable ( + PHYSICAL_PRESENCE_VARIABLE, + &gEfiPhysicalPresenceGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE= _ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, + TcgPpDataSize, + &TcgPpData + ); + } + } + + if (!EFI_ERROR (Status) && ((Tcg2PpData.PPRequest !=3D TCG2_PHYSICAL_PRE= SENCE_NO_ACTION) || (TcgPpData.PPRequest !=3D TCG_PHYSICAL_PRESENCE_NO_ACTI= ON))) { + // + // If it requests any action on TCG, need to connect console to display = information. + // + EfiBootManagerConnectAllDefaultConsoles(); + } + + if (CompareGuid (PcdGetPtr (PcdTpmInstanceGuid), &gEfiTpmDeviceInstanceT= pm20DtpmGuid) || + CompareGuid (PcdGetPtr (PcdTpmInstanceGuid), &gTpmDeviceInstanceTpm20P= ttPtpGuid)) { + Tcg2PhysicalPresenceLibProcessRequest (NULL); + } else if (CompareGuid (PcdGetPtr (PcdTpmInstanceGuid), &gEfiTpmDeviceIn= stanceTpm12Guid)) { + TcgPhysicalPresenceLibProcessRequest (); + } +} + +/** + Remove all GOP device path instance from DevicePath and add the Gop to t= he DevicePath. +**/ +EFI_DEVICE_PATH_PROTOCOL * +UpdateDevicePath ( + EFI_DEVICE_PATH_PROTOCOL *DevicePath, + EFI_DEVICE_PATH_PROTOCOL *Gop + ) +{ + UINTN Size; + UINTN GopSize; + EFI_DEVICE_PATH_PROTOCOL *Temp; + EFI_DEVICE_PATH_PROTOCOL *Return; + EFI_DEVICE_PATH_PROTOCOL *Instance; + BOOLEAN Exist; + + Exist =3D FALSE; + Return =3D NULL; + GopSize =3D GetDevicePathSize (Gop); + do { + Instance =3D GetNextDevicePathInstance (&DevicePath, &Size); + if (Instance =3D=3D NULL) { + break; + } + if (!IsGopDevicePath (Instance) || + (Size =3D=3D GopSize && CompareMem (Instance, Gop, GopSize) =3D=3D= 0) + ) { + if (Size =3D=3D GopSize && CompareMem (Instance, Gop, GopSize) =3D= =3D 0) { + Exist =3D TRUE; + } + Temp =3D Return; + Return =3D AppendDevicePathInstance (Return, Instance); + if (Temp !=3D NULL) { + FreePool (Temp); + } + } + FreePool (Instance); + } while (DevicePath !=3D NULL); + + if (!Exist) { + Temp =3D Return; + Return =3D AppendDevicePathInstance (Return, Gop); + gBS->FreePool (Temp); + } + return Return; +} + +/** + Check if current BootCurrent variable is internal shell boot option. + + @retval TRUE BootCurrent is internal shell. + @retval FALSE BootCurrent is not internal shell. +**/ +BOOLEAN +BootCurrentIsInternalShell ( + VOID +) +{ + UINTN VarSize; + UINT16 BootCurrent; + CHAR16 BootOptionName[16]; + UINT8 *BootOption; + UINT8 *Ptr; + EFI_DEVICE_PATH_PROTOCOL *BootDevicePath; + BOOLEAN Result; + EFI_STATUS Status; + EFI_DEVICE_PATH_PROTOCOL *TempDevicePath; + EFI_DEVICE_PATH_PROTOCOL *LastDeviceNode; + EFI_GUID *GuidPoint; + + BootOption =3D NULL; + BootDevicePath =3D NULL; + Result =3D FALSE; + + // + // Get BootCurrent variable + // + VarSize =3D sizeof (UINT16); + Status =3D gRT->GetVariable ( + L"BootCurrent", + &gEfiGlobalVariableGuid, + NULL, + &VarSize, + &BootCurrent + ); + if (EFI_ERROR (Status)) { + return FALSE; + } + + // + // Create boot option Bootxxxx from BootCurrent. + // + UnicodeSPrint (BootOptionName, sizeof(BootOptionName), L"Boot%04x", Boot= Current); + + GetEfiGlobalVariable2 (BootOptionName, (VOID **) &BootOption, &VarSize); + if (BootOption =3D=3D NULL || VarSize =3D=3D 0) { + return FALSE; + } + + Ptr =3D BootOption; + Ptr +=3D sizeof (UINT32); + Ptr +=3D sizeof (UINT16); + Ptr +=3D StrSize ((CHAR16 *) Ptr); + TempDevicePath =3D (EFI_DEVICE_PATH_PROTOCOL *) Ptr; + LastDeviceNode =3D TempDevicePath; + while (!IsDevicePathEnd (TempDevicePath)) { + LastDeviceNode =3D TempDevicePath; + TempDevicePath =3D NextDevicePathNode (TempDevicePath); + } + GuidPoint =3D EfiGetNameGuidFromFwVolDevicePathNode ( + (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *) LastDeviceNode + ); + if ((GuidPoint !=3D NULL) && + (CompareGuid (GuidPoint, &gUefiShellFileGuid)) + ) { + // + // If this option is internal shell, return TRUE. + // + Result =3D TRUE; + } + + if (BootOption !=3D NULL) { + FreePool (BootOption); + BootOption =3D NULL; + } + + return Result; +} + +/** + ReadyToBoot callback to set video and text mode for internal shell boot. + That will not connect USB controller while CSM and FastBoot are disabled= , we need to connect them + before booting to Shell for showing USB devices in Shell. + + When FastBoot is enabled and Windows Console is the chosen Console behav= ior, input devices will not be connected + by default. Hence, when booting to EFI shell, connecting input consoles = are required. + + @param Event Pointer to this event + @param Context Event hanlder private data + + @retval None. +**/ +VOID +EFIAPI +OnReadyToBootCallBack ( + IN EFI_EVENT Event, + IN VOID *Context + ) +{ + DEBUG ((EFI_D_INFO, "OnReadyToBootCallBack\n")); + + if (BootCurrentIsInternalShell ()) { + + } +} + +/** + Platform Bds init. Incude the platform firmware vendor, revision + and so crc check. +**/ +VOID +EFIAPI +PlatformBootManagerBeforeConsole ( + VOID + ) +{ + EFI_STATUS Status; + UINTN Index; + EFI_DEVICE_PATH_PROTOCOL *VarConOut; + EFI_DEVICE_PATH_PROTOCOL *VarConIn; + EFI_DEVICE_PATH_PROTOCOL *TempDevicePath; + EFI_DEVICE_PATH_PROTOCOL *ConsoleOut; + EFI_DEVICE_PATH_PROTOCOL *Temp; + EFI_DEVICE_PATH_PROTOCOL *Instance; + EFI_DEVICE_PATH_PROTOCOL *Next; + EFI_HANDLE Handle; + EFI_EVENT Event; + EFI_GUID *TerminalGuid; + UINT8 TerminalType; + UINTN InstanceSize; + =20 + DEBUG ((EFI_D_INFO, "PlatformBootManagerBeforeConsole\n")); + + Status =3D EFI_SUCCESS; + + // + // Append Usb Keyboard short form DevicePath into "ConInDev". + // + EfiBootManagerUpdateConsoleVariable ( + ConInDev, + (EFI_DEVICE_PATH_PROTOCOL *) &mUsbClassKeyboardDevicePath, + NULL + ); + + // + // Get user defined text mode for internal shell only once. + // + mShellHorizontalResolution =3D PcdGet32 (PcdSetupVideoHorizontalResoluti= on); + mShellVerticalResolution =3D PcdGet32 (PcdSetupVideoVerticalResolution= ); + mShellModeColumn =3D PcdGet32 (PcdSetupConOutColumn); + mShellModeRow =3D PcdGet32 (PcdSetupConOutRow); + + // + // Create event to set proper video resolution and text mode for interna= l shell. + // + Status =3D EfiCreateEventReadyToBootEx ( + TPL_CALLBACK, + OnReadyToBootCallBack, + NULL, + &Event + ); + ASSERT_EFI_ERROR (Status); + + // + // Connect Root Bridge to make PCI BAR resource allocated and all PciIo = created. + // + ConnectRootBridge (FALSE); + + // + // Update ConOut variable accordign to the PrimaryDisplay setting. + // + GetEfiGlobalVariable2 (L"ConOut", (VOID **)&ConsoleOut, NULL); + + // + // Add IGD to ConOut. + // + Handle =3D NULL; + TempDevicePath =3D (EFI_DEVICE_PATH_PROTOCOL *) &mPlatformIGDDevice; + Status =3D gBS->LocateDevicePath (&gEfiPciIoProtocolGuid, &TempDevicePat= h, &Handle); + if (!EFI_ERROR (Status) && + IsDevicePathEnd (TempDevicePath) && + IsVgaHandle (Handle)) { + } + DEBUG ((EFI_D_INFO, "GOP Device Handle - 0x%x\n", Handle)); + + if (Handle !=3D NULL) { + // + // Connect the GOP driver. + // + gBS->ConnectController (Handle, NULL, NULL, TRUE); + + // + // Get the GOP device path. + // NOTE: We may get a device path that contains Controller node in it. + // + TempDevicePath =3D EfiBootManagerGetGopDevicePath (Handle); + DEBUG ((EFI_D_INFO, "GOP device path - 0x%x\n", TempDevicePath)); + if (TempDevicePath !=3D NULL) { + DEBUG ((EFI_D_INFO, "GOP device string - %S\n", DevicePathToStr ((EF= I_DEVICE_PATH_PROTOCOL*)TempDevicePath) )); + Temp =3D ConsoleOut; + ConsoleOut =3D UpdateDevicePath (ConsoleOut, TempDevicePath); + if (Temp !=3D NULL) { + FreePool (Temp); + } + FreePool (TempDevicePath); + Status =3D gRT->SetVariable ( + L"ConOut", + &gEfiGlobalVariableGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACC= ESS | EFI_VARIABLE_BOOTSERVICE_ACCESS, + GetDevicePathSize (ConsoleOut), + ConsoleOut + ); + } + } + + gBS->FreePool (ConsoleOut); + + // + // Fill ConIn/ConOut in Full Configuration boot mode. + // + DEBUG ((DEBUG_ERROR, "PlatformBootManagerInit - %x\n", mBootMode)); + if (mBootMode =3D=3D BOOT_WITH_FULL_CONFIGURATION || + mBootMode =3D=3D BOOT_WITH_DEFAULT_SETTINGS || + mBootMode =3D=3D BOOT_WITH_FULL_CONFIGURATION_PLUS_DIAGNOSTICS || + mBootMode =3D=3D BOOT_IN_RECOVERY_MODE) { + + GetEfiGlobalVariable2 (L"ConOut", (VOID **)&VarConOut, NULL); if (Va= rConOut !=3D NULL) { FreePool (VarConOut); } + GetEfiGlobalVariable2 (L"ConIn", (VOID **)&VarConIn, NULL); if (Var= ConIn !=3D NULL) { FreePool (VarConIn); } + + if (VarConOut =3D=3D NULL || VarConIn =3D=3D NULL) { + // + // Only fill ConIn/ConOut when ConIn/ConOut is empty because we may = drop to Full Configuration boot mode in non-first boot. + // Update ConOutDevicePath (just in case it is wrong at build phase). + // To be enabled later. + // + for (Index =3D 0; mPlatformConsole[Index].DevicePath !=3D NULL; Inde= x++) { + // + // Update the console variable with the connect type. + // + if ((mPlatformConsole[Index].ConnectType & CONSOLE_IN) =3D=3D CONS= OLE_IN) { + EfiBootManagerUpdateConsoleVariable (ConIn, mPlatformConsole[Ind= ex].DevicePath, NULL); + } + if ((mPlatformConsole[Index].ConnectType & CONSOLE_OUT) =3D=3D CON= SOLE_OUT) { + EfiBootManagerUpdateConsoleVariable (ConOut, mPlatformConsole[In= dex].DevicePath, NULL); + } + if ((mPlatformConsole[Index].ConnectType & STD_ERROR) =3D=3D STD_E= RROR) { + EfiBootManagerUpdateConsoleVariable (ErrOut, mPlatformConsole[In= dex].DevicePath, NULL); + } + } + } else { + if (mBootMode =3D=3D BOOT_WITH_DEFAULT_SETTINGS) { + // + // Get default Terminal Type. + // + TerminalGuid =3D &gEfiPcAnsiGuid; + TerminalType =3D PcdGet8 (PcdDefaultTerminalType); + if (TerminalType < 4) { + TerminalGuid =3D mLibTerminalType[TerminalType]; + } + + GetEfiGlobalVariable2 (L"ConIn", (VOID **)&VarConIn, NULL); + Instance =3D GetNextDevicePathInstance (&VarConIn, &InstanceS= ize); + InstanceSize -=3D END_DEVICE_PATH_LENGTH; + + while (Instance !=3D NULL) { + Next =3D Instance; + while (!IsDevicePathEndType (Next)) { + Next =3D NextDevicePathNode (Next); + if (DevicePathType (Next) =3D=3D MESSAGING_DEVICE_PATH && Devi= cePathSubType (Next) =3D=3D MSG_VENDOR_DP) { + // + // Restoring default serial device path. + // + EfiBootManagerUpdateConsoleVariable (ConIn, NULL, Instance); + EfiBootManagerUpdateConsoleVariable (ConOut, NULL, Instance); + } + } + FreePool(Instance); + Instance =3D GetNextDevicePathInstance (&VarConIn, &Instanc= eSize); + InstanceSize -=3D END_DEVICE_PATH_LENGTH; + } + } + } + } + + EnumPs2Keyboard (); + EnumUsbKeyboard (); + + // + // Dynamically register hot key: F2/F7/Enter. + // + RegisterDefaultBootOption (); + RegisterStaticHotkey (); + + // + // Connect Root Bridge to make PCI BAR resource allocated. + // Then exit PM auth before Legacy OPROM run. + // + ConnectRootBridge (FALSE); + =20 + ProcessTcgPp (); + + ExitPmAuth (); +} + +/** + Connect with predeined platform connect sequence, + the OEM/IBV can customize with their own connect sequence. + + @param[in] BootMode Boot mode of this boot. +**/ +VOID +ConnectSequence ( + IN EFI_BOOT_MODE BootMode + ) +{ + EfiBootManagerConnectAll (); +} + +/** + The function is to consider the boot order which is not in our expectati= on. + In the case that we need to re-sort the boot option. + + @retval TRUE Need to sort Boot Option. + @retval FALSE Don't need to sort Boot Option. +**/ +BOOLEAN +IsNeedSortBootOption ( + VOID + ) +{ + EFI_BOOT_MANAGER_LOAD_OPTION *BootOptions; + UINTN BootOptionCount; + + BootOptions =3D EfiBootManagerGetLoadOptions (&BootOptionCount, LoadOpti= onTypeBoot); + + // + // If setup is the first priority in boot option, we need to sort boot o= ption. + // + if ((BootOptionCount > 1) && + (((StrnCmp (BootOptions->Description, L"Enter Setup", StrLen (L"Ente= r Setup"))) =3D=3D 0) || + ((StrnCmp (BootOptions->Description, L"BootManagerMenuApp", StrLen = (L"BootManagerMenuApp"))) =3D=3D 0))) { + return TRUE; + } + + return FALSE; +} + +/** + The function will excute with as the platform policy, current policy + is driven by boot mode. IBV/OEM can customize this code for their specif= ic + policy action. + + @param DriverOptionList - The header of the driver option link list + @param BootOptionList - The header of the boot option link list + @param ProcessCapsules - A pointer to ProcessCapsules() + @param BaseMemoryTest - A pointer to BaseMemoryTest() +**/ +VOID +EFIAPI +PlatformBootManagerAfterConsole ( + VOID + ) +{ + EFI_STATUS Status; + EFI_BOOT_MODE LocalBootMode; + BOOLEAN RequireSoftECCInit; + EFI_GENERIC_MEMORY_TEST_PROTOCOL *GenMemoryTest; + =20 + DEBUG ((EFI_D_INFO, "PlatformBootManagerAfterConsole\n")); + + // + // Run memory test code at this point. + // + Status =3D gBS->LocateProtocol ( + &gEfiGenericMemTestProtocolGuid, + NULL, + (VOID **) &GenMemoryTest + ); + + if (!EFI_ERROR (Status)) { + Status =3D GenMemoryTest->MemoryTestInit ( + GenMemoryTest, + IGNORE, + &RequireSoftECCInit + ); + }=20 + + // + // Get current Boot Mode. + // + LocalBootMode =3D mBootMode; + DEBUG ((DEBUG_ERROR, "Current local bootmode - %x\n", LocalBootMode)); + + // + // Go the different platform policy with different boot mode. + // Notes: this part code can be change with the table policy. + // + switch (LocalBootMode) { + + case BOOT_ASSUMING_NO_CONFIGURATION_CHANGES: + case BOOT_WITH_MINIMAL_CONFIGURATION: + case BOOT_ON_S4_RESUME: + // + // Perform some platform specific connect sequence. + // + ConnectSequence (LocalBootMode); + =20 + break; + =20 + case BOOT_WITH_FULL_CONFIGURATION: + case BOOT_WITH_FULL_CONFIGURATION_PLUS_DIAGNOSTICS: + case BOOT_WITH_DEFAULT_SETTINGS: + default: + // + // Perform some platform specific connect sequence. + // + ConnectSequence (LocalBootMode); + =20 + // + // Only in Full Configuration boot mode we do the enumeration of boo= t device. + // + EfiBootManagerRefreshAllBootOption (); + =20 + break; + } + =20 + if (IsNeedSortBootOption()) { + EfiBootManagerSortLoadOptionVariable (LoadOptionTypeBoot, (SORT_COMPAR= E)CompareBootOption); + } +} diff --git a/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootM= anager.h b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootMan= ager.h new file mode 100644 index 0000000..5ed9a4b --- /dev/null +++ b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootManager.h @@ -0,0 +1,226 @@ +/** @file + Header file of Platform Boot Manager Lib. + + Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#ifndef _BDS_PLATFORM_H +#define _BDS_PLATFORM_H + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define CONSOLE_OUT 0x00000001 +#define STD_ERROR 0x00000002 +#define CONSOLE_IN 0x00000004 +#define CONSOLE_ALL (CONSOLE_OUT | CONSOLE_IN | STD_ERROR) +#define CLASS_HID 3 +#define SUBCLASS_BOOT 1 +#define PROTOCOL_KEYBOARD 1 + +#define mPciRootBridge \ + { \ + ACPI_DEVICE_PATH, ACPI_DP, (UINT8) (sizeof (ACPI_HID_DEVICE_PATH)), (U= INT8) \ + ((sizeof (ACPI_HID_DEVICE_PATH)) >> 8), EISA_PNP_ID (0x0A03), 0 \ + } + +#define mEndEntire \ + { \ + END_DEVICE_PATH_TYPE, END_ENTIRE_DEVICE_PATH_SUBTYPE, END_DEVICE_PATH_= LENGTH, 0 \ + } + +typedef struct { + EFI_DEVICE_PATH_PROTOCOL *DevicePath; + UINTN ConnectType; +} BDS_CONSOLE_CONNECT_ENTRY; + +// +// Platform Root Bridge. +// +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_ROOT_BRIDGE_DEVICE_PATH; + +// +// Below is the platform console device path. +// +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + PCI_DEVICE_PATH IsaBridge; + ACPI_HID_DEVICE_PATH Keyboard; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_KEYBOARD_DEVICE_PATH; + +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + PCI_DEVICE_PATH IsaBridge; + ACPI_HID_DEVICE_PATH IsaSerial; + UART_DEVICE_PATH Uart; + VENDOR_DEVICE_PATH TerminalType; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_ISA_SERIAL_DEVICE_PATH; + +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + PCI_DEVICE_PATH PciDevice; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_ONBOARD_CONTROLLER_DEVICE_PATH; + +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + PCI_DEVICE_PATH Pci0Device; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_PEG_ROOT_CONTROLLER_DEVICE_PATH; + +typedef struct { + ACPI_HID_DEVICE_PATH PciRootBridge; + PCI_DEVICE_PATH PciBridge; + PCI_DEVICE_PATH PciDevice; + EFI_DEVICE_PATH_PROTOCOL End; +} PLATFORM_PCI_CONTROLLER_DEVICE_PATH; + +typedef struct { + USB_CLASS_DEVICE_PATH UsbClass; + EFI_DEVICE_PATH_PROTOCOL End; +} USB_CLASS_FORMAT_DEVICE_PATH; + +typedef +VOID +(*PROCESS_VARIABLE) ( + VOID **Variable, + UINTN *VariableSize + ); + +/** + Generic function to update the console variable. + Please refer to FastBootSupport.c for how to use it. + + @param VariableName - The name of the variable to be updated + @param AgentGuid - The Agent GUID + @param ProcessVariable - The function pointer to update the variable + NULL means to restore to the original value +**/ +VOID +UpdateEfiGlobalVariable ( + CHAR16 *VariableName, + EFI_GUID *AgentGuid, + PROCESS_VARIABLE ProcessVariable + ); + +VOID +ConnectSequence ( + IN EFI_BOOT_MODE BootMode + ); + +INTN +EFIAPI +CompareBootOption ( + CONST EFI_BOOT_MANAGER_LOAD_OPTION *Left, + CONST EFI_BOOT_MANAGER_LOAD_OPTION *Right + ); + +VOID=20 +PrintBootPrompt ( + VOID + ); + +VOID +RegisterStaticHotkey ( + VOID + ); + +VOID +RegisterDynamicHotkey ( + VOID + ); + +VOID +RegisterDefaultBootOption ( + VOID + ); + +VOID +BootUi ( + VOID + ); + +EFI_STATUS +AutomaticFirmwareUpdateHandler ( + CHAR16 *FileName + ); + +EFI_STATUS +EFIAPI +EfiPlatformBootManagerProcessCapsules ( + VOID + ); + +VOID +PlatformBootManagerAttemptUsbBoot ( + VOID + ); + +EFI_STATUS +SetMorControl ( + VOID + ); + =20 +extern PLATFORM_ISA_SERIAL_DEVICE_PATH mSerialDevicePath; +extern EFI_DEVICE_PATH_PROTOCOL *mPlatformRootBridges[]; +extern BDS_CONSOLE_CONNECT_ENTRY mPlatformConsole[]; +extern PLATFORM_ONBOARD_CONTROLLER_DEVICE_PATH mPlatformIGDDevice; +extern PLATFORM_KEYBOARD_DEVICE_PATH mKeyboardDevicePath; +extern USB_CLASS_FORMAT_DEVICE_PATH mUsbClassKeyboardDevicePa= th; +extern USB_CLASS_FORMAT_DEVICE_PATH gUsbClassMassStorageDevic= e; +extern EFI_GUID gUefiShellFileGuid; +extern EFI_HII_HANDLE mPlatformBdsLibStringPack= Handle; +extern BDS_CONSOLE_CONNECT_ENTRY mPlatformConsole []; +extern EFI_BOOT_MODE mBootMode; + +#endif diff --git a/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootM= anagerLib.inf b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBo= otManagerLib.inf new file mode 100644 index 0000000..9be8a9e --- /dev/null +++ b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootManagerL= ib.inf @@ -0,0 +1,110 @@ +## @file +# Component INF for module PlatformBootManagerLib. +# +# Copyright (c) 2008 - 2018, Intel Corporation. All rights reserved.
+# +# This program and the accompanying materials +# are licensed and made available under the terms and conditions of the B= SD License +# which accompanies this distribution. The full text of the license may b= e found at +# http://opensource.org/licenses/bsd-license.php. +# +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IM= PLIED. +# +## + + +[Defines] + INF_VERSION =3D 0x00010017 + BASE_NAME =3D DxePlatformBootManagerLib + FILE_GUID =3D A6BC385D-59E5-4b77-87D7-200ABAA83C15 + VERSION_STRING =3D 1.0 + MODULE_TYPE =3D DXE_DRIVER + UEFI_SPECIFICATION_VERSION =3D 2.10 + LIBRARY_CLASS =3D PlatformBootManagerLib|DXE_DRIVER + # + # The following information is for reference only and not required by th= e build tools. + # + # VALID_ARCHITECTURES =3D IA32 X64 EBC + # + =20 +[Sources] + PlatformBootManager.c + PlatformData.c + PlatformBootOption.c + =20 +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + SecurityPkg/SecurityPkg.dec + MdeModulePkg/MdeModulePkg.dec + IntelFrameworkPkg/IntelFrameworkPkg.dec + Vlv2TbltDevicePkg/PlatformPkg.dec + Vlv2DeviceRefCodePkg/Vlv2DeviceRefCodePkg.dec + =20 +[Pcd] + gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut + gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution + gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution + gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow + gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn + gEfiMdeModulePkgTokenSpaceGuid.PcdSetupConOutColumn + gEfiMdeModulePkgTokenSpaceGuid.PcdSetupConOutRow + gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution + gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution + gEfiMdeModulePkgTokenSpaceGuid.PcdConInConnectOnDemand + gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType + gEfiSecurityPkgTokenSpaceGuid.PcdTpmInstanceGuid =20 + =20 + [LibraryClasses] + BaseLib + MemoryAllocationLib + UefiBootServicesTableLib + UefiRuntimeServicesTableLib + BaseMemoryLib + DebugLib + PcdLib + PrintLib + DevicePathLib + UefiLib + HobLib + DxeServicesLib + DxeServicesTableLib + HiiLib + UefiBootManagerLib + PerformanceLib + TimerLib + PciLib + Tcg2PhysicalPresenceLib + TcgPhysicalPresenceLib + =20 +[Protocols] + gEfiPciRootBridgeIoProtocolGuid + gEfiPciIoProtocolGuid + gEfiCpuIo2ProtocolGuid + gEfiDxeSmmReadyToLockProtocolGuid + gEfiGenericMemTestProtocolGuid + gEfiDiskInfoProtocolGuid + gEfiAcpiS3SaveProtocolGuid + gEfiDevicePathToTextProtocolGuid + gEfiSimpleTextInputExProtocolGuid + gEfiFirmwareVolume2ProtocolGuid + gEfiFormBrowser2ProtocolGuid + gExitPmAuthProtocolGuid + gEfiGraphicsOutputProtocolGuid + gEfiGenericMemTestProtocolGuid + =20 +[Guids] + gEfiGlobalVariableGuid + gEfiEndOfDxeEventGroupGuid + gEfiVTUTF8Guid + gEfiVT100Guid + gEfiVT100PlusGuid + gEfiPcAnsiGuid + gEfiTpmDeviceInstanceTpm20DtpmGuid + gTpmDeviceInstanceTpm20PttPtpGuid + gEfiTcg2PhysicalPresenceGuid + gEfiTpmDeviceInstanceTpm12Guid + =20 +[Depex.common.DXE_DRIVER] + gEfiVariableArchProtocolGuid diff --git a/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootO= ption.c b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootOpti= on.c new file mode 100644 index 0000000..c77b20f --- /dev/null +++ b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformBootOption.c @@ -0,0 +1,738 @@ +/** @file + This file include all platform action which can be customized by IBV/OEM. + + Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#include "PlatformBootManager.h" + +BOOLEAN mContinueBoot =3D FALSE; +BOOLEAN mUiAppBoot =3D FALSE; +BOOLEAN mPxeBoot =3D FALSE; +BOOLEAN mAnyKeypressed =3D FALSE; +BOOLEAN mHotKeypressed =3D FALSE; +EFI_EVENT HotKeyEvent =3D NULL; +UINTN mUiAppOptionNumber; +CHAR16 *TmpStr =3D L"Press [F2] key to enter BIOS Setup"; + +EFI_GRAPHICS_OUTPUT_BLT_PIXEL mForeground; +EFI_GRAPHICS_OUTPUT_BLT_PIXEL mBackground; +EFI_GRAPHICS_OUTPUT_BLT_PIXEL mColor; + +EFI_GUID mUiFile =3D { 0x462CAA21, 0x7614, 0x4503, { 0x83, 0x6E, 0x8A, 0xB= 6, 0xF4, 0x66, 0x23, 0x31 } }; +EFI_GUID mBootMenuFile =3D { 0xEEC25BDC, 0x67F2, 0x4D95, { 0xB1, 0xD5, 0xF= 8, 0x1B, 0x20, 0x39, 0xD1, 0x1D }}; +EFI_GUID gUefiShellFileGuid =3D { 0x7C04A583, 0x9E3E, 0x4f1c, 0xAD, 0x65, = 0xE0, 0x52, 0x68, 0xD0, 0xB4, 0xD1 }; + +#define INTERNAL_UEFI_SHELL_NAME L"Internal UEFI Shell 2.0" +#define UEFI_HARD_DRIVE_NAME L"UEFI Hard Drive" +#define UEFI_NVME_DRIVE_NAME L"UEFI NVMe Storage" + +/** + Show progress bar with title above it. It only works in Graphics mode. + + @param TitleForeground Foreground color for Title. + @param TitleBackground Background color for Title. + @param Title Title above progress bar. + @param ProgressColor Progress bar color. + @param Progress Progress (0-100) + @param PreviousValue The previous value of the progress. + + @retval EFI_STATUS Success update the progress bar. + +**/ +EFI_STATUS +PlatformBdsShowProgress ( + IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleForeground, + IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleBackground, + IN CHAR16 *Title, + IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL ProgressColor, + IN UINTN Progress, + IN UINTN PreviousValue + ) +{ + EFI_STATUS Status; + EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput; + UINT32 SizeOfX; + UINT32 SizeOfY; + EFI_GRAPHICS_OUTPUT_BLT_PIXEL Color; + UINTN BlockHeight; + UINTN BlockWidth; + UINTN BlockNum; + UINTN PosX; + UINTN PosY; + UINTN Index; + + if (Progress > 100) { + return EFI_INVALID_PARAMETER; + } + + Status =3D gBS->HandleProtocol ( + gST->ConsoleOutHandle, + &gEfiGraphicsOutputProtocolGuid, + (VOID **) &GraphicsOutput + ); + if (EFI_ERROR (Status)) { + return EFI_UNSUPPORTED; + } + + SizeOfX =3D 0; + SizeOfY =3D 0; + if (GraphicsOutput !=3D NULL) { + SizeOfX =3D GraphicsOutput->Mode->Info->HorizontalResolution; + SizeOfY =3D GraphicsOutput->Mode->Info->VerticalResolution; + } else { + return EFI_UNSUPPORTED; + } + + BlockWidth =3D SizeOfX / 100; + BlockHeight =3D SizeOfY / 50; + + BlockNum =3D Progress; + + PosX =3D 0; + PosY =3D SizeOfY * 48 / 50; + + if (BlockNum =3D=3D 0) { + // + // Clear progress area + // + SetMem (&Color, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL), 0x0); + + if (GraphicsOutput !=3D NULL) { + Status =3D GraphicsOutput->Blt ( + GraphicsOutput, + &Color, + EfiBltVideoFill, + 0, + 0, + 0, + PosY - EFI_GLYPH_HEIGHT - 1, + SizeOfX, + SizeOfY - (PosY - EFI_GLYPH_HEIGHT - 1), + SizeOfX * sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL) + ); + } else { + return EFI_UNSUPPORTED; + } + } + // + // Show progress by drawing blocks. + // + for (Index =3D PreviousValue; Index < BlockNum; Index++) { + PosX =3D Index * BlockWidth; + if (GraphicsOutput !=3D NULL) { + Status =3D GraphicsOutput->Blt ( + GraphicsOutput, + &ProgressColor, + EfiBltVideoFill, + 0, + 0, + PosX, + PosY, + BlockWidth - 1, + BlockHeight, + (BlockWidth) * sizeof (EFI_GRAPHICS_OUTPUT_BLT_P= IXEL) + ); + } else { + return EFI_UNSUPPORTED; + } + } + + PrintXY ( + (SizeOfX - StrLen (Title) * EFI_GLYPH_WIDTH) / 2, + PosY - EFI_GLYPH_HEIGHT - 1, + &TitleForeground, + &TitleBackground, + Title + ); + + return EFI_SUCCESS; +} + +/*++ + +This function will create a SHELL BootOption to boot. + + @param void + + @retval EFI_STATUS + +--*/ +EFI_DEVICE_PATH_PROTOCOL * +BdsCreateShellDevicePath ( + VOID + ) + +{ + UINTN FvHandleCount; + EFI_HANDLE *FvHandleBuffer; + UINTN Index; + EFI_STATUS Status; + EFI_FIRMWARE_VOLUME2_PROTOCOL *Fv; + UINTN Size; + UINT32 AuthenticationStatus; + EFI_DEVICE_PATH_PROTOCOL *DevicePath; + VOID *Buffer; + + DevicePath =3D NULL; + Status =3D EFI_SUCCESS; + + DEBUG ((DEBUG_ERROR, "[FVMAIN2] BdsCreateShellDevicePath\n")); + gBS->LocateHandleBuffer ( + ByProtocol, + &gEfiFirmwareVolume2ProtocolGuid, + NULL, + &FvHandleCount, + &FvHandleBuffer + ); + + for (Index =3D 0; Index < FvHandleCount; Index++) { + gBS->HandleProtocol ( + FvHandleBuffer[Index], + &gEfiFirmwareVolume2ProtocolGuid, + (VOID **) &Fv + ); + + Buffer =3D NULL; + Size =3D 0; + Status =3D Fv->ReadSection ( + Fv, + &gUefiShellFileGuid, + EFI_SECTION_PE32, + 0, + &Buffer, + &Size, + &AuthenticationStatus + ); + if (EFI_ERROR (Status)) { + // + // Skip if no shell file in the FV. + // + continue; + } else { + // + // Found the shell. + // + break; + } + } + + if (EFI_ERROR (Status)) { + // + // No shell present. + // + if (FvHandleCount) { + FreePool (FvHandleBuffer); + } + return NULL; + } + // + // Build the shell boot option. + // + DevicePath =3D DevicePathFromHandle (FvHandleBuffer[Index]); + + if (FvHandleCount) { + FreePool (FvHandleBuffer); + } + + return DevicePath; +} + +EFI_STATUS +CreateFvBootOption ( + EFI_GUID *FileGuid, + CHAR16 *Description, + EFI_BOOT_MANAGER_LOAD_OPTION *BootOption, + UINT32 Attributes, + UINT8 *OptionalData, OPTIONAL + UINT32 OptionalDataSize + ) +{ + EFI_STATUS Status; + EFI_DEVICE_PATH_PROTOCOL *DevicePath; + EFI_LOADED_IMAGE_PROTOCOL *LoadedImage; + MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode; + EFI_FIRMWARE_VOLUME2_PROTOCOL *Fv; + UINT32 AuthenticationStatus; + VOID *Buffer; + UINTN Size; + + if ((BootOption =3D=3D NULL) || (FileGuid =3D=3D NULL) || (Description = =3D=3D NULL)) { + return EFI_INVALID_PARAMETER; + } + + EfiInitializeFwVolDevicepathNode (&FileNode, FileGuid); + + if (!CompareGuid (&gUefiShellFileGuid, FileGuid)) { + Status =3D gBS->HandleProtocol ( + gImageHandle, + &gEfiLoadedImageProtocolGuid, + (VOID **) &LoadedImage + ); + if (!EFI_ERROR (Status)) { + Status =3D gBS->HandleProtocol ( + LoadedImage->DeviceHandle, + &gEfiFirmwareVolume2ProtocolGuid, + (VOID **) &Fv + ); + if (!EFI_ERROR (Status)) { + Buffer =3D NULL; + Size =3D 0; + Status =3D Fv->ReadSection ( + Fv, + FileGuid, + EFI_SECTION_PE32, + 0, + &Buffer, + &Size, + &AuthenticationStatus + ); + if (Buffer !=3D NULL) { + FreePool (Buffer); + } + } + } + if (EFI_ERROR (Status)) { + return EFI_NOT_FOUND; + } + + DevicePath =3D AppendDevicePathNode ( + DevicePathFromHandle (LoadedImage->DeviceHandle), + (EFI_DEVICE_PATH_PROTOCOL *) &FileNode + ); + } else { + DevicePath =3D AppendDevicePathNode ( + BdsCreateShellDevicePath (), + (EFI_DEVICE_PATH_PROTOCOL *) &FileNode + ); + } + + Status =3D EfiBootManagerInitializeLoadOption ( + BootOption, + LoadOptionNumberUnassigned, + LoadOptionTypeBoot, + Attributes, + Description, + DevicePath, + OptionalData, + OptionalDataSize + ); + FreePool (DevicePath); + return Status; +} + +/** + Return the index of the load option in the load option array. + + The function consider two load options are equal when the=20 + OptionType, Attributes, Description, FilePath and OptionalData are equal. + + @param Key Pointer to the load option to be found. + @param Array Pointer to the array of load options to be found. + @param Count Number of entries in the Array. + + @retval -1 Key wasn't found in the Array. + @retval 0 ~ Count-1 The index of the Key in the Array. +**/ +INTN +PlatformFindLoadOption ( + IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Key, + IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Array, + IN UINTN Count + ) +{ + UINTN Index; + + for (Index =3D 0; Index < Count; Index++) { + if ((Key->OptionType =3D=3D Array[Index].OptionType) && + (Key->Attributes =3D=3D Array[Index].Attributes) && + (StrCmp (Key->Description, Array[Index].Description) =3D=3D 0) && + (CompareMem (Key->FilePath, Array[Index].FilePath, GetDevicePathSi= ze (Key->FilePath)) =3D=3D 0) && + (Key->OptionalDataSize =3D=3D Array[Index].OptionalDataSize) && + (CompareMem (Key->OptionalData, Array[Index].OptionalData, Key->Op= tionalDataSize) =3D=3D 0)) { + return (INTN) Index; + } + } + + return -1; +} + +UINTN +RegisterFvBootOption ( + EFI_GUID *FileGuid, + CHAR16 *Description, + UINTN Position, + UINT32 Attributes, + UINT8 *OptionalData, OPTIONAL + UINT32 OptionalDataSize + ) +{ + EFI_STATUS Status; + UINTN OptionIndex; + EFI_BOOT_MANAGER_LOAD_OPTION NewOption; + EFI_BOOT_MANAGER_LOAD_OPTION *BootOptions; + UINTN BootOptionCount; + + NewOption.OptionNumber =3D LoadOptionNumberUnassigned; + Status =3D CreateFvBootOption (FileGuid, Description, &NewOption, Attrib= utes, OptionalData, OptionalDataSize); + if (!EFI_ERROR (Status)) { + BootOptions =3D EfiBootManagerGetLoadOptions (&BootOptionCount, LoadOp= tionTypeBoot); + + OptionIndex =3D PlatformFindLoadOption (&NewOption, BootOptions, BootO= ptionCount); + + if (OptionIndex =3D=3D -1) { + Status =3D EfiBootManagerAddLoadOptionVariable (&NewOption, Position= ); + ASSERT_EFI_ERROR (Status); + } else { + NewOption.OptionNumber =3D BootOptions[OptionIndex].OptionNumber; + } + EfiBootManagerFreeLoadOption (&NewOption); + EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount); + } + + return NewOption.OptionNumber; +} + + +VOID +BootUi ( + VOID + ) +{ + EFI_STATUS Status; + EFI_BOOT_MANAGER_LOAD_OPTION BootOption; + + Status =3D EfiBootManagerGetBootManagerMenu (&BootOption); + if (!EFI_ERROR (Status)) { + EfiBootManagerBoot (&BootOption); + EfiBootManagerFreeLoadOption (&BootOption); + } +} + +VOID +EFIAPI +PlatformBootManagerWaitCallback ( + UINT16 TimeoutRemain + ) +{ + UINT16 TimeoutDefault; + EFI_STATUS Status; + EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *TxtInEx; + EFI_KEY_DATA KeyData; + BOOLEAN PausePressed; + + TimeoutDefault =3D PcdGet16 (PcdPlatformBootTimeOut); + if (TimeoutDefault =3D=3D TimeoutRemain) { + SetMem (&mForeground, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL), 0xff); + SetMem (&mBackground, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL), 0x0); + SetMem (&mColor, sizeof (EFI_GRAPHICS_OUTPUT_BLT_PIXEL), 0xff); + } + + PlatformBdsShowProgress ( + mForeground, + mBackground, + TmpStr, + mColor, + ((TimeoutDefault - TimeoutRemain) * 100 / TimeoutDefault), + 0 + ); + =20 + // + // Pause on PAUSE key. + // + Status =3D gBS->HandleProtocol (gST->ConsoleInHandle, &gEfiSimpleTextInp= utExProtocolGuid, (VOID **) &TxtInEx); + ASSERT_EFI_ERROR (Status); + + PausePressed =3D FALSE; + + while (TRUE) { + Status =3D TxtInEx->ReadKeyStrokeEx (TxtInEx, &KeyData); + if (EFI_ERROR (Status)) { + break; + } + + if (KeyData.Key.ScanCode =3D=3D SCAN_PAUSE) { + PausePressed =3D TRUE; + break; + } + } + + // + // Loop until non-PAUSE key pressed. + // + while (PausePressed) { + Status =3D TxtInEx->ReadKeyStrokeEx (TxtInEx, &KeyData); + if (!EFI_ERROR (Status)) { + DEBUG (( + DEBUG_INFO, "[PauseCallback] %x/%x %x/%x\n", + KeyData.Key.ScanCode, KeyData.Key.UnicodeChar, + KeyData.KeyState.KeyShiftState, KeyData.KeyState.KeyToggleState + )); + PausePressed =3D (BOOLEAN) (KeyData.Key.ScanCode =3D=3D SCAN_PAUSE); + } + } +} + +/** + Check if the boot option is a EFI network boot option. + + @param Option The boot option need to be processed. + + @retval TRUE It is a EFI network boot option. + @retval FALSE It is not a EFI network boot option. + +**/ +BOOLEAN +IsEfiNetWorkBootOption ( + IN EFI_BOOT_MANAGER_LOAD_OPTION *Option + ) +{ + EFI_DEVICE_PATH_PROTOCOL *Node; + + for (Node =3D Option->FilePath; !IsDevicePathEndType (Node); Node =3D Ne= xtDevicePathNode (Node)) { + if (DevicePathType (Node) =3D=3D MESSAGING_DEVICE_PATH) { + switch (DevicePathSubType (Node)) { + case MSG_MAC_ADDR_DP: + case MSG_VLAN_DP: + case MSG_IPv4_DP: + case MSG_IPv6_DP: + return TRUE; + } + } + } + return FALSE; +} + +VOID +RegisterDefaultBootOption ( + VOID + ) +{ + EFI_DEVICE_PATH_PROTOCOL *DevicePath; + EFI_LOADED_IMAGE_PROTOCOL *LoadedImage; + MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode; + UINT16 *ShellData; + UINT32 ShellDataSize;=20 + + // + // Shell. + // + if (1) { + ShellData =3D NULL; + ShellDataSize =3D 0; + RegisterFvBootOption (&gUefiShellFileGuid, INTERNAL_UEFI_SHELL_NAME, = (UINTN) -1, LOAD_OPTION_ACTIVE, (UINT8 *)ShellData, ShellDataSize); + } + =20 + // + // UiApp. + // + mUiAppOptionNumber =3D RegisterFvBootOption (&mUiFile, L"Enter Setup", = (UINTN) -1, (LOAD_OPTION_CATEGORY_APP | LOAD_OPTION_ACTIVE | LOAD_OPTION_H= IDDEN), NULL, 0); + =20 + if (mUiAppOptionNumber =3D=3D LoadOptionNumberUnassigned) { + DEBUG ((DEBUG_ERROR, "UiAppOptionNumber (%d) should not be same to Loa= dOptionNumberUnassigned(%d).\n", mUiAppOptionNumber, LoadOptionNumberUnassi= gned)); + } +=20 + // + // Boot Manager Menu. + // + EfiInitializeFwVolDevicepathNode (&FileNode, &mBootMenuFile); + + gBS->HandleProtocol ( + gImageHandle, + &gEfiLoadedImageProtocolGuid, + (VOID **) &LoadedImage + ); + DevicePath =3D AppendDevicePathNode (DevicePathFromHandle (LoadedImage->= DeviceHandle), (EFI_DEVICE_PATH_PROTOCOL *) &FileNode); + +} + +VOID +RegisterBootOptionHotkey ( + UINT16 OptionNumber, + EFI_INPUT_KEY *Key, + BOOLEAN Add + ) +{ + EFI_STATUS Status; + + if (!Add) { + // + // No enter hotkey when force to setup or there is no boot option. + // + Status =3D EfiBootManagerDeleteKeyOptionVariable (NULL, 0, Key, NULL); + ASSERT (Status =3D=3D EFI_SUCCESS || Status =3D=3D EFI_NOT_FOUND); + } else { + // + // Register enter hotkey for the first boot option. + // + Status =3D EfiBootManagerAddKeyOptionVariable (NULL, OptionNumber, 0, = Key,NULL); + ASSERT (Status =3D=3D EFI_SUCCESS || Status =3D=3D EFI_ALREADY_STARTED= ); + } +} + +EFI_STATUS +EFIAPI +DetectKeypressCallback ( + IN EFI_KEY_DATA *KeyData +) +{ + mHotKeypressed =3D TRUE; + + if (HotKeyEvent !=3D NULL) { + gBS->SignalEvent(HotKeyEvent); + } + + return EFI_SUCCESS; +} + +/** + This function is called after all the boot options are enumerated and or= dered properly. +**/ +VOID +RegisterStaticHotkey ( + VOID + ) +{ + + EFI_INPUT_KEY Enter; + EFI_KEY_DATA F2; + EFI_KEY_DATA F7; + BOOLEAN EnterSetup; + EFI_STATUS Status; + EFI_BOOT_MANAGER_LOAD_OPTION BootOption; + + EnterSetup =3D FALSE; + + // + // [Enter] + // + mContinueBoot =3D !EnterSetup; + if (mContinueBoot) { + Enter.ScanCode =3D SCAN_NULL; + Enter.UnicodeChar =3D CHAR_CARRIAGE_RETURN; + EfiBootManagerRegisterContinueKeyOption (0, &Enter, NULL); + } + + // + // [F2]/[F7]. + // + =20 + F7.Key.ScanCode =3D SCAN_F7; + F7.Key.UnicodeChar =3D CHAR_NULL; + F7.KeyState.KeyShiftState =3D EFI_SHIFT_STATE_VALID; + F7.KeyState.KeyToggleState =3D 0; + Status =3D EfiBootManagerGetBootManagerMenu (&BootOption); + ASSERT_EFI_ERROR (Status); + // + RegisterBootOptionHotkey ((UINT16) BootOption.OptionNumber, &F7.Key, TRU= E); + EfiBootManagerFreeLoadOption (&BootOption); + + F2.Key.ScanCode =3D SCAN_F2; + F2.Key.UnicodeChar =3D CHAR_NULL; + F2.KeyState.KeyShiftState =3D EFI_SHIFT_STATE_VALID; + F2.KeyState.KeyToggleState =3D 0; + mUiAppBoot =3D !EnterSetup; + RegisterBootOptionHotkey ((UINT16) mUiAppOptionNumber, &F2.Key, mUiAppBo= ot); +} + +UINT8 +BootOptionType ( + IN EFI_DEVICE_PATH_PROTOCOL *DevicePath + ) +{ + EFI_DEVICE_PATH_PROTOCOL *Node; + EFI_DEVICE_PATH_PROTOCOL *NextNode; + + for (Node =3D DevicePath; !IsDevicePathEndType (Node); Node =3D NextDevi= cePathNode (Node)) { + if (DevicePathType (Node) =3D=3D MESSAGING_DEVICE_PATH) { + // + // Make sure the device path points to the driver device. + // + NextNode =3D NextDevicePathNode (Node); + if (DevicePathSubType(NextNode) =3D=3D MSG_DEVICE_LOGICAL_UNIT_DP) { + // + // If the next node type is Device Logical Unit, which specify the= Logical Unit Number (LUN), + // skip it. + // + NextNode =3D NextDevicePathNode (NextNode); + } + if (IsDevicePathEndType (NextNode)) { + if ((DevicePathType (Node) =3D=3D MESSAGING_DEVICE_PATH)) { + return DevicePathSubType (Node); + } else { + return MSG_SATA_DP; + } + } + } + } + + return (UINT8) -1; +} + +/** + Returns the priority number. + =20 + OptionType Default Priority + ------------------------------------ + PXE 5 + DVD 2 + USB 1 + NVME 4 + HDD 3 + EFI Shell 6 + Others 100 + + @param BootOption +**/ +UINTN +BootOptionPriority ( + CONST EFI_BOOT_MANAGER_LOAD_OPTION *BootOption + ) +{ + // + // EFI boot options. + // + switch (BootOptionType (BootOption->FilePath)) { + case MSG_MAC_ADDR_DP: + case MSG_VLAN_DP: + case MSG_IPv4_DP: + case MSG_IPv6_DP: + return 5; + case MSG_SATA_DP: + case MSG_ATAPI_DP: + return 2; + case MSG_USB_DP: + return 1; + } + =20 + if (StrCmp (BootOption->Description, INTERNAL_UEFI_SHELL_NAME) =3D=3D = 0) { + return 6; + } + if (StrCmp (BootOption->Description, UEFI_HARD_DRIVE_NAME) =3D=3D 0) { + return 3; + } + if (StrCmp (BootOption->Description, UEFI_NVME_DRIVE_NAME) =3D=3D 0) { + return 4; + } + =20 + return 100; +} + +INTN +EFIAPI +CompareBootOption ( + CONST EFI_BOOT_MANAGER_LOAD_OPTION *Left, + CONST EFI_BOOT_MANAGER_LOAD_OPTION *Right + ) +{ + return BootOptionPriority (Left) - BootOptionPriority (Right); +} diff --git a/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformData.= c b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformData.c new file mode 100644 index 0000000..90b0533 --- /dev/null +++ b/Vlv2TbltDevicePkg/Library/PlatformBootManagerLib/PlatformData.c @@ -0,0 +1,179 @@ +/** @file + This file include all platform action which can be customized by IBV/OEM. + + Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.
+ + This program and the accompanying materials + are licensed and made available under the terms and conditions of the BS= D License + which accompanies this distribution. The full text of the license may b= e found at + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMP= LIED. + +**/ + +#include "PlatformBootManager.h" + +#define PCI_DEVICE_NUMBER_PCH_LPC 31 +#define PCI_FUNCTION_NUMBER_PCH_LPC 0 + +#define SA_IGD_DEV 0x02 +#define SA_IGD_FUN 0x00 + +// +// Predefined platform root bridge. +// +GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_ROOT_BRIDGE_DEVICE_PATH gPlatformR= ootBridge0 =3D { + mPciRootBridge, + mEndEntire +}; + +GLOBAL_REMOVE_IF_UNREFERENCED EFI_DEVICE_PATH_PROTOCOL *mPlatform= RootBridges[] =3D { + (EFI_DEVICE_PATH_PROTOCOL *) &gPlatformRootBridge0, + NULL +}; + +// +// Platform specific keyboard device path. +// +GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_KEYBOARD_DEVICE_PATH mKeyboardD= evicePath =3D { + mPciRootBridge, + { + HARDWARE_DEVICE_PATH, + HW_PCI_DP, + (UINT8) (sizeof (PCI_DEVICE_PATH)), + (UINT8) ((sizeof (PCI_DEVICE_PATH)) >> 8), + PCI_FUNCTION_NUMBER_PCH_LPC, + PCI_DEVICE_NUMBER_PCH_LPC + }, + { + ACPI_DEVICE_PATH, + ACPI_DP, + (UINT8) (sizeof (ACPI_HID_DEVICE_PATH)), + (UINT8) ((sizeof (ACPI_HID_DEVICE_PATH)) >> 8), + EISA_PNP_ID(0x0303), + 0 + }, + mEndEntire +}; + +// +// Platform specific serial device path. +// +GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_ISA_SERIAL_DEVICE_PATH mSerialDev= icePath =3D { + mPciRootBridge, + { + HARDWARE_DEVICE_PATH, + HW_PCI_DP, + (UINT8) (sizeof (PCI_DEVICE_PATH)), + (UINT8) ((sizeof (PCI_DEVICE_PATH)) >> 8), + PCI_FUNCTION_NUMBER_PCH_LPC, + PCI_DEVICE_NUMBER_PCH_LPC + }, + { + ACPI_DEVICE_PATH, + ACPI_DP, + (UINT8) (sizeof (ACPI_HID_DEVICE_PATH)), + (UINT8) ((sizeof (ACPI_HID_DEVICE_PATH)) >> 8), + EISA_PNP_ID(0x0501), + 0 + }, + { + MESSAGING_DEVICE_PATH, + MSG_UART_DP, + (UINT8) (sizeof (UART_DEVICE_PATH)), + (UINT8) ((sizeof (UART_DEVICE_PATH)) >> 8), + 0, + 115200, + 8, + 1, + 1 + }, + { + MESSAGING_DEVICE_PATH, + MSG_VENDOR_DP, + (UINT8) (sizeof (VENDOR_DEVICE_PATH)), + (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8), + DEVICE_PATH_MESSAGING_PC_ANSI + }, + mEndEntire +}; + +GLOBAL_REMOVE_IF_UNREFERENCED USB_CLASS_FORMAT_DEVICE_PATH mUsbClassKeyboa= rdDevicePath =3D { + { + { + MESSAGING_DEVICE_PATH, + MSG_USB_CLASS_DP, + (UINT8) (sizeof (USB_CLASS_DEVICE_PATH)), + (UINT8) ((sizeof (USB_CLASS_DEVICE_PATH)) >> 8) + }, + 0xffff, // VendorId=20 + 0xffff, // ProductId=20 + CLASS_HID, // DeviceClass=20 + SUBCLASS_BOOT, // DeviceSubClass + PROTOCOL_KEYBOARD // DeviceProtocol + }, + + {=20 + END_DEVICE_PATH_TYPE,=20 + END_ENTIRE_DEVICE_PATH_SUBTYPE,=20 + END_DEVICE_PATH_LENGTH,=20 + 0 + } +}; + +// +// Onboard VGA controller device path. +// +GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_ONBOARD_CONTROLLER_DEVICE_PATH = mPlatformIGDDevice =3D { + mPciRootBridge, + { + HARDWARE_DEVICE_PATH, + HW_PCI_DP, + (UINT8) (sizeof (PCI_DEVICE_PATH)), + (UINT8) ((sizeof (PCI_DEVICE_PATH)) >> 8), + SA_IGD_FUN, + SA_IGD_DEV + }, + mEndEntire +}; + +// +// Predefined platform default console device path. +// +GLOBAL_REMOVE_IF_UNREFERENCED BDS_CONSOLE_CONNECT_ENTRY mPlatformC= onsole[] =3D { + { + (EFI_DEVICE_PATH_PROTOCOL *) &mSerialDevicePath, + (CONSOLE_OUT | CONSOLE_IN) + }, + { + (EFI_DEVICE_PATH_PROTOCOL *) &mKeyboardDevicePath, + CONSOLE_IN + }, + { + (EFI_DEVICE_PATH_PROTOCOL *) &mUsbClassKeyboardDevicePath,=20 + CONSOLE_IN + }, + { + NULL, + 0 + } +}; + +GLOBAL_REMOVE_IF_UNREFERENCED USB_CLASS_FORMAT_DEVICE_PATH gUsbClassMassSt= orageDevice =3D { + { + { + MESSAGING_DEVICE_PATH, + MSG_USB_CLASS_DP, + (UINT8) (sizeof (USB_CLASS_DEVICE_PATH)), + (UINT8) ((sizeof (USB_CLASS_DEVICE_PATH)) >> 8) + }, + 0xffff, // VendorId=20 + 0xffff, // ProductId=20 + 0x08, // DeviceClass - USB Mass Storage Class + 0x06, // DeviceSubClass - SCSI Transparent Command Set + 0xff // DeviceProtocol - Match any Device Protocol + }, + mEndEntire +}; --=20 2.10.1.windows.1 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel