From 31bb486c913795c8b67d1c4dbaae2bdec4943fc9 Mon Sep 17 00:00:00 2001 From: raywu Date: Thu, 13 Sep 2018 16:11:56 +0800 Subject: SLP1.0 / SLP2.0 / Default Password / Logo / Fix Boot Order --- Board/EM/FixedBootOrder/FBOSetOrder.c | 1699 +++++++++++++++++++++++++++++++++ 1 file changed, 1699 insertions(+) create mode 100644 Board/EM/FixedBootOrder/FBOSetOrder.c (limited to 'Board/EM/FixedBootOrder/FBOSetOrder.c') diff --git a/Board/EM/FixedBootOrder/FBOSetOrder.c b/Board/EM/FixedBootOrder/FBOSetOrder.c new file mode 100644 index 0000000..35d7b11 --- /dev/null +++ b/Board/EM/FixedBootOrder/FBOSetOrder.c @@ -0,0 +1,1699 @@ +//********************************************************************** +//********************************************************************** +//** ** +//** (C)Copyright 1985-2012, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 6145-F Northbelt Pkwy, Norcross, GA 30071 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//********************************************************************** +//********************************************************************** +//********************************************************************** +// $Archive: /Alaska/BIN/Modules/Template/FixedBootOrder Demo/Board/em/FixedBootOrder/FBOSetOrder.c $ +// +// $Author: Walonli $ +// +// $Revision: 31 $ +// +// $Date: 3/26/15 10:50p $ +// +//*****************************************************************// +//*****************************************************************// +// Revision History +// ---------------- +// $Log: /Alaska/BIN/Modules/Template/FixedBootOrder Demo/Board/em/FixedBootOrder/FBOSetOrder.c $ +// +// 31 3/26/15 10:50p Walonli +// [TAG] EIP210628 +// [Category] Improvement +// [Description] Fixed build error when USE_BCP_DEFAULT_PRIORITIES token +// enable. +// [Files] Board\em\FixedBootOrder\FBOSetOrder.c +// Board\em\FixedBootOrder\FixedBootOrderTSE.c +// FixedBootOrder.cif +// +// 30 5/20/14 3:48a Klzhan +// [TAG] EIP167196 +// [Category] Improvement +// [Description] Runtime attribute set for the some of the variable used +// by FixedBootOrder needs to be reviewed. +// [Files] Board\em\FixedBootOrder\FixedBootOrder.sdl +// Board\em\FixedBootOrder\FixedBootOrder.mak +// Board\em\FixedBootOrder\FBOSetOrder.c +// Board\em\FixedBootOrder\FixedBootOrderTSE.c +// Board\em\FixedBootOrder\FixedBootOrder.h +// Board\em\FixedBootOrder\FixedBootOrder.c +// Board\em\FixedBootOrder\FixedBootOrder.chm +// Board\em\FixedBootOrder\FixedBootOrderHII.c +// Board\em\FixedBootOrder\FixedBootOrderHII.h +// FixedBootOrder.cif +// +// 29 4/16/14 5:16a Walonli +// +// 28 4/15/14 2:26a Klzhan +// [TAG] EIP143078 +// [Category] Improvement +// [Description] Set LOAD_OPTION_ACTIVE must be 0 when +// LOAD_OPTION_HIDDEN=1 +// [Files] Board\em\FixedBootOrder\FixedBootOrder.sdl +// Board\em\FixedBootOrder\FixedBootOrder.mak +// Board\em\FixedBootOrder\FBOSetOrder.c +// Board\em\FixedBootOrder\FixedBootOrderTSE.c +// Board\em\FixedBootOrder\FixedBootOrder.h +// Board\em\FixedBootOrder\FixedBootOrder.c +// Board\em\FixedBootOrder\FixedBootOrder.chm +// Board\em\FixedBootOrder\FixedBootOrderHII.c +// Board\em\FixedBootOrder\FixedBootOrderHII.h +// FixedBootOrder.cif +// +// 27 12/05/13 1:00a Klzhan +// [TAG] EIP143740 +// [Category] Improvement +// [Description] 1. Add a token for setting Windows To Go boot option to +// 1st priority. +// 2. Clean up code for windows to go +// [Files] Board\em\FixedBootOrder\FixedBootOrder.sdl +// Board\em\FixedBootOrder\FBOSetOrder.c +// FixedBootOrder.cif +// +// 26 10/21/13 5:41a Easonchen +// [TAG] EIP129692 +// [Category] Bug Fix +// [Severity] Normal +// [Symptom] BBS Priorities become DISABLE when set ENABLE in Boot +// Option Priorities +// [RootCause] Variable "UefiDevOrder" not set "Disable" Mask. +// [Solution] Add "Disable" mask to variable "UefiDevOrder" +// [Files] FboSetOrder.c +// FixedBootOrderTse.c +// +// 25 8/12/13 11:24p Easonchen +// [TAG] EIP128779 +// [Category] Bug Fix +// [Severity] Minor +// [Symptom] UEFI USB CD/DVD Drive BBS Priotites displayed incorrectly +// [RootCause] Boot#### Boot Option record disable status. when group +// set to disable, group sub-menu display too. +// [Solution] Not change Boot#### disable status, Use variable +// "UefiDevOrder" record boot option disable status. +// [Files] FBOSetOrder.c +// +// 24 8/12/13 4:17a Easonchen +// [TAG] N/A +// [Category] Improvement +// [Description] CppCheck error fix. +// [Files] FBOSetOrder.c +// +// 23 5/28/13 5:25a Easonchen +// [TAG] EIP122146 +// [Category] Improvement +// [Description] Support Dual mode default priority with tool AMIBCP. +// [Files] +// FboSetOrder.c +// FixedBootOrder.c +// FixedBoorOrderTse.c +// DefaultFixedBootOrder.c +// DefaultFixedBootOrder.sd +// DefaultFixedBootOrder.uni +// +// 22 4/22/13 11:04p Easonchen +// [TAG] EIP101213 +// [Category] Improvement +// [Description] FixedBootOrder should match the BootOrder variable +// [Files] FboSetOrder.c +// FixedBootOrder.sdl +// +// 21 4/09/13 9:07a Easonchen +// [TAG] EIP118170 +// [Category] Bug Fix +// [Severity] Minor +// [Symptom] Windows Boot Manager will become disable on BBS Priorities +// when change Boot option filter +// [RootCause] when CsmOptOut module set legacy only, windows boot +// mangger boot option attribute become LOAD_OPTION_HIDDEN. +// [Solution] Check boot option attribute LOAD_OPTION_HIDDEN then don't +// disable boot option. +// [Files] FboSetOrder.c +// +// 20 2/19/13 1:49a Easonchen +// [TAG] EIP114186 +// [Category] Bug Fix +// [Severity] Important +// [Symptom] BSU Exit Page, Boot Override appears ¡§Unknown Device¡¨ +// [RootCause] same boot option priority. +// [Solution] reassign boot option priority. +// [Files] FboSetOrder.c +// +// 19 2/05/13 3:46a Easonchen +// [TAG] EIP107268 +// [Category] New Feature +// [Description] Add support managing default boot order list using +// AMIBCP. +// [Files] +// FBOSetOrder.c +// FixedBootOrder.c +// FixedBootOrderTSE.c +// FixedBootOrder.sdl +// DefaultFixedBootOrder.sd +// DefaultFixedBootOrder.uni +// +// 18 12/07/12 2:03a Easonchen +// [TAG] EIP107440 +// [Category] Bug Fix +// [Severity] Important +// [Symptom] In UEFI mode, system should be only boot with EFI boot +// device.However, system will boot into DOS when enter "exit" in EFI +// shell. +// [RootCause] BootOption LOAD_OPTION_ACTIVE not setting. +// [Solution] Add BootOption LOAD_OPTION_ACTIVE set disable in UEFI +// mode. +// +// 17 11/09/12 4:56a Easonchen +// [TAG] EIP99368 +// [Category] Improvement +// [Description] WHCK - Boot from USB +// [Files] FBOSetOrder.c +// +// 16 9/20/12 2:45a Easonchen +// [TAG] EIP100223 +// [Category] Bug Fix +// [Severity] Minor +// [Symptom] does not recognize a USB device correctly. +// [RootCause] First plug USB CDROM boot option number is 0003, unplug +// and plug USB HDD boot option number is 0003 again. +// [Solution] Add device type check to filter. +// [Files] FBOSetOrder.c +// +// 15 6/28/12 11:22a Easonchen +// Make a new FixedBootOrder module by utilizing 4.6.4.1 BDS +// functionality. +// +// 14 6/11/12 10:04a Easonchen +// [TAG] EIP92141 +// [Category] Bug Fix +// [Severity] Minor +// [Symptom] build error with TSE 1227 +// [RootCause] TSE EDKhelper.c change function name DivU64x32 to +// AmiTseDivU64x32. +// [Solution] Change to use function Div64 +// [Files] FBOSetOrder.c +// +// 12 5/02/12 2:49a Easonchen +// [TAG] EIP87316 +// [Category] Improvement +// [Description] FixedBootOrder Module needs support CsmOptOut Boot +// Filter UEFI Only. Set BBS Table BootPriority to BBS_IGNORE_ENTRY. +// [Files] FBOSetOrder.c +// +// 11 6/17/11 3:44a Easonchen +// [TAG] EIP57950 +// [Category] Improvement +// [Description] +// Replace BBS_TABLE BootPriority BBS_UNPRIORITIZED_ENTRY to +// BBS_DO_NOT_BOOT_FROM. +// +// 10 4/14/11 4:01a Easonchen +// TAG: EIP35562 +// In Core 4.6.4.1 or Last, Fixed boot variable name - hex digits should +// be in upper case +// +// TAG: EIP54209 +// Improvement: NetBootHotKey eModule Functionality with TSE 1210 +// Verification Check +// [Description] +// Check TSE gBootFlow status in function FBOCheckNormalBoot +// +// TAG: EIP57727 +// Improvement: It always increase one device while reboot in F12 (Boot +// device menu) even you only insert one HDD in it. +// [Description] +// Modify function UpdateBootOrder() and AddUEFIDevice() to support +// 4.6.4.1 +// +// 9 3/31/11 2:03a Easonchen +// [TAG] EIP57272 +// [Category] Improvement +// [Description] Check BootMode BOOT_ON_S4_RESUME and exit +// [Files] FBOSetOrder.c +// +// 8 3/22/11 4:35a Easonchen +// [TAG] EIP51709 +// [Category] Improvement +// [Description] 1.Code is reformatted in accordance with the coding +// standards. +// 2.Remove file boot.vfr and setup.c, OEM need patch boot.vfr to remove +// original boot options. +// +// 7 12/10/10 4:41a Easonchen +// Minor bug fix (EIP47257.2) +// +// 6 11/12/10 2:57a Easonchen +// Add TSE ELINK ProcessProceedToBootNowHook. +// +// TAG: EIP33514 +// Improvement: The FixedBootOrder function caused the side effect +// -"AMT_TC010( IDE-Redirection). +// [Description] +// Check variable "AmtBootOption" created, OemFixedBootOrder() don't +// change BBS_TABE Boot priority. +// +// TAG: EIP47257 +// Improvement: Load Default user define HDD order will lost. +// [Description] +// Modified routine BbsChecksum(), If can't get hard disk serial number. +// use device name to make checksum. +// +// 5 9/14/10 3:04a Easonchen +// TAG: EIP33514 +// Improvement: Modify function FixedBootOrderSaveChange(). +// [Description] +// 1.Change BOOT#### LoadOption Bit Active status. +// 2.Update variable BootOrder after SaveChange. +// TAG: EIP33900 +// Improvement: add function FixedBootOrderLoadedConfigDefaults() for TSE +// ELINK LoadedConfigDefaults(). +// [Description] +// 1.Add function CreateDefaultDevOrder(). +// 2.Call FixedBootOrderProtocol->load_default_string(). +// TAG: EIP30275 +// Improvement: Windows Boot Manager delete and restore. +// [Description] +// 1.Add function WindowsBootManager(). +// TAG: EIP26947 +// Improvement: Update variable "BootOrder" and "LegacyDevOrder" +// [Description] +// 1.Add function UpdateBootOrder(). +// TAG: EIP22689 +// Improvement: Support submenu function. +// +// 4 3/31/10 6:54a Jameswang +// [Tag] EIP35944 +// [Bug fix] Fixed USB CDROM will be analyzed as USB key with some CD +// medium(HD format) +// [Severity] Medium +// [Root cause] We only checked the USB device size to determined if it is +// a USB key, if USB CDROM has a medium that is emulated as a HDD / Floppy +// between 2MB and 64GB then it will also be determined as USB key. +// [Solution] Not only checks the size but also checks BBS types for HDD +// and Floppy, excludes CDROM. +// +// 3 4/15/09 6:12a Jameswang +// TAG: EIP19998 +// Improvement: New type:BOOT_USB_KEY is added and boot option can display +// the device name. +// [Description] +// 1. Added BOOT_USB_KEY type: 64GB > USB KEY!=USB floppy >= 2MB +// 2. SetPriorityForStringInit is added for pre-running the boot order for +// each boot options, so the FixedBootOrderStringInit can add device names +// to strings accordingly. +// 3. When FixedBootOrderStringInit signaling a protocol event, +// SetPriorityForStringInit::SetPriorityForStringInit will be called and +// gInitStrPhase=TRUE, the BBS_TABLE[].BootPriority = BOOT_XXXX enum value +// if the device is present. +// 4. FBORegisterEvent is linked to MinisetupDriverEntryHook and register +// a fake protocol so FixedBootOrderStringInit can signal it and callback +// to SetPriorityForStringInit accross the EDK. +// +// 2 3/26/09 2:46a Jameswang +// All include use <> only without any path. So that include files can be +// override by CIF2MAK "/x" option. +// All debug message add "\n". +// +// 1 3/02/09 3:31a Jameswang +// Separate OemFixedBootOrder here to be linked with minisetup because we +// changed to use eLinks instead of using events. We will not need to +// modify bbs.c using eLinks. +// +//*****************************************************************// + +// +//---------------------------------------------------------------------- +// +// Name: FBOSetOrder.c +// +// Description: FixedBootOrder Boot Option control +// +//---------------------------------------------------------------------- +// + +//---------------------------------------------------------------------- +// Include Files +//---------------------------------------------------------------------- +#include +#include +#include + +#include +#include +#include + +#if CSM_SUPPORT +#include +#include +#endif + +#include "FixedBootOrder.h" +typedef CHAR8 *VA_LIST; +#include "Core\EfiCommonLib.h" +#include "SetupStrTokens.h" +//--------------------------------------------------------------------------- +// Global Variable declarations +//--------------------------------------------------------------------------- +EFI_GUID gFixedBootOrderGuid = FIXED_BOOT_ORDER_GUID; +//--------------------------------------------------------------------------- +// External functions +//--------------------------------------------------------------------------- +EFI_HANDLE GetPhysicalBlockIoHandle(EFI_HANDLE BlockIoHandle); +UINT32 GetUefiBootOptionTag(IN EFI_DEVICE_PATH_PROTOCOL *Dp); +UINT16 GetDevicePortNumber(BBS_TABLE *BbsTable); +UINT32 FindPositionInTheGroupByBbsIndex(LEGACY_DEVICE_ORDER *Group, UINT16 BbsIndex); +//--------------------------------------------------------------------------- +// Function Definitions +//--------------------------------------------------------------------------- +VOID BuildFboLegacyDevOrder(VOID); +//--------------------------------------------------------------------------- +// Type definitions +//--------------------------------------------------------------------------- +#define DEFAULTS_GUID {0x4599d26f, 0x1a11, 0x49b8, 0xb9, 0x1f, 0x85, 0x87, 0x45, 0xcf, 0xf8, 0x24} +//--------------------------------------------------------------------------- +// Constant and Variables declarations +//--------------------------------------------------------------------------- +FBODevMap *pFBODualDevMap = NULL; +FBODevMap *pFBOLegacyDevMap = NULL; +FBODevMap *pFBOUefiDevMap = NULL; +UINT16 NewBootOptionNumber=0xffff; //(EIP101213+) + +UINT16 GetDevMapDataCount(FBODevMap *pFBODevMap) +{ + UINT16 count = 0; + + if( !pFBODevMap ) return 0; //end of data + + do{ + if( pFBODevMap[count].DevType == 0 ) break; + count++; + }while(1); + + return count; +} + +// +//--------------------------------------------------------------------------- +// +// Procedure: SearchDevMapByType +// +// Description: Search DevMap data index by device type. +// +// Input: +// IN FBODevMap *pFBODevMap +// IN UINT16 DevType +// +// Output: +// OUT UINT16 +// +// Modified: None +// +// Referrals: None +// +// Notes: None +// +//--------------------------------------------------------------------------- +// +UINT16 SearchDevMapByType(FBODevMap *pFBODevMap, UINT16 DevType) +{ + UINT16 i=0; + + do{ + if(pFBODevMap[i].DevType == 0 ) break; //end of data + if(pFBODevMap[i].DevType == DevType) + return i; + i++; + }while(1); + + return 0; +} + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_FindTagPriority +// +// Description: For the passed Tag entry, return the correct boot priority based on +// the BootOptionTagPriorities global variable that is filled out +// based on the SDL Token BOOT_OPTION_TAG_PRIORITIES. +// +// Input: UINT16 Tag - one of the following items of the BOOT_OPTION_TAG enum: +// +// Output: The index of this item in the FBODevMapData structure, which +// also corresponds to the boot priority that should be assigned to this +// class of device +//---------------------------------------------------------------------------- +// +UINT32 FBO_FindTagPriority(UINT16 Tag){ + UINT32 i=0; + UINT16 DeviceMapCount; + + DeviceMapCount=GetDevMapDataCount( pFBOLegacyDevMap ); + + for( i=0; i +//---------------------------------------------------------------------------- +// Procedure: IsUSBkeyByHandle +// +// Description: determine the device type of the USBKey size. +// +// Input: EFI_HANDLE Handle +// +// Output: BOOLEAN +//---------------------------------------------------------------------------- +// +BOOLEAN IsUSBkeyByHandle(EFI_HANDLE Handle) +{ + EFI_BLOCK_IO_PROTOCOL *BlkIo; + UINT64 SizeInMb; + EFI_GUID gEfiBlockIoProtocolGuid = EFI_BLOCK_IO_PROTOCOL_GUID; + + + if ( !EFI_ERROR( pBS->HandleProtocol( + Handle, + &gEfiBlockIoProtocolGuid, + &BlkIo))) + { + SizeInMb = MultU64x32(BlkIo->Media->LastBlock + 1, BlkIo->Media->BlockSize); + SizeInMb = DivU64x32(SizeInMb, 1000000, NULL); + + if (SizeInMb <= USBKEY_RANGE_SIZE ) + return TRUE; + } + + return FALSE; +} + +#if CSM_SUPPORT +// +//---------------------------------------------------------------------------- +// Procedure: CheckIsUSBkey +// +// Description: Using the passed BBS_TABLE entry pointer, determine the device +// type of the USBKey +// +// Input: BBS_TABLE *BbsEntry - pointer to a BBS_TABLE entry +// +// Output: BOOLEAN +//---------------------------------------------------------------------------- +// +BOOLEAN CheckIsUSBkey(BBS_TABLE *BbsEntry) +{ + if( BbsEntry->DeviceType == BBS_HARDDISK ) + return IsUSBkeyByHandle( *(VOID**)(&BbsEntry->IBV1) ); + else + return FALSE; +} +#endif + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_GetBbsEntryDeviceType +// +// Description: Using the passed BBS_TABLE entry pointer, determine the device +// type of the associated device +// +// Input: BBS_TABLE *BbsEntry - pointer to a BBS_TABLE entry +// +// Output: UINT16 - device type +// +//---------------------------------------------------------------------------- +// +UINT16 FBO_GetBbsEntryDeviceType(BBS_TABLE *BbsEntry){ + +#ifdef CSM_SUPPORT + UINT16 i; + UINT16 DeviceType = BbsEntry->DeviceType; + BOOLEAN IsUSBDevice, IsUSBKey = FALSE; + UINT16 Matched=0, OldMatched=0, DevMapIndex = 0xff; + UINT16 DeviceMapCount=0; + CHAR8 *AsciiNameStr; + + IsUSBDevice = (BbsEntry->Class == 0xc) && (BbsEntry->SubClass == 0x3); + + if( IsUSBDevice ) + IsUSBKey = CheckIsUSBkey( BbsEntry ); + +#if BBS_NETWORK_DEVICE_TYPE_SUPPORT + if ( BbsEntry->Class == PCI_CL_NETWORK + && BbsEntry->DeviceType == BBS_BEV_DEVICE + ) DeviceType = BBS_EMBED_NETWORK; +#endif + + //Name from BBS table + AsciiNameStr = (CHAR8*)(UINTN)((BbsEntry->DescStringSegment<<4) + + BbsEntry->DescStringOffset); + + TRACE((-1,"%s (IsUSBDevice=%d)(IsUSBKey=%d)\n", AsciiNameStr, IsUSBDevice, IsUSBKey)); + + DeviceMapCount=GetDevMapDataCount( pFBOLegacyDevMap ); + for( i=0; i OldMatched ) + { + OldMatched = Matched; + DevMapIndex = i; + } + } + + if( DevMapIndex != 0xff ) + return pFBOLegacyDevMap[DevMapIndex].DevType; + + TRACE((-1,"FBODevMapData not found\n")); + return BBS_UNKNOWN; +#else + return 0; +#endif //#ifdef CSM_SUPPORT + +} + +// +//---------------------------------------------------------------------------- +// Procedure: BuildUEFIDevOrder +// +// Description: Go through the master boot option list and create +// memory representation of the uefi dev order variable +// +// Input: DLIST *BootOptionList - the master boot option list +// +// Output: none +// +// Note: +//---------------------------------------------------------------------------- +// +VOID BuildUEFIDevOrder( +){ + EFI_STATUS Status; + UINT16 i,j; + DLINK *Link; + BOOT_OPTION *Option; + UINTN OldDvOrderSize=0; + UEFI_DEVICE_ORDER *OldDevOrder=NULL, *OldDevOrder2=NULL, *DevOrder=NULL, *DevOrder2=NULL; + EFI_GUID FixedBootOrderGuid = FIXED_BOOT_ORDER_GUID; + UINT16 DeviceMapCount; + UINT16 BootOrderFlag[128]; + + pBS->SetMem( BootOrderFlag, 128, 0); + + Status = GetEfiVariable(L"UefiDevOrder", &FixedBootOrderGuid, NULL, &OldDvOrderSize, &OldDevOrder); + TRACE((-1,"FBOSetOrder.c BuildUEFIDevOrder:: GetEfiVariable UefiDevOrder (%r)\n", Status)); + if( EFI_ERROR(Status) ) + { + OldDvOrderSize = 0; + OldDevOrder = NULL; + } + + DevOrder2 = DevOrder = Malloc(512); + if( DevOrder == NULL ) + return; + + DeviceMapCount=GetDevMapDataCount( pFBOUefiDevMap ); + for(i=0; iType = DevType; + DevOrder->Length=2; + + j=0; + //(EIP101213+)> + //collect new UEFI device to first position of group. + if(NewBootOptionNumber != 0xffff) + { + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if(Option->BootOptionNumber == NewBootOptionNumber) + { + if(GetUefiBootOptionTag(Option->FilePathList) == DevType) + { + DevOrder->Length += 2; + DevOrder->Device[j] = Option->BootOptionNumber; + BootOrderFlag[Option->BootOptionNumber]=0xffff; //mask flag. + if(!(Option->Attributes & LOAD_OPTION_ACTIVE)) + DevOrder->Device[j] |= 0xff00; + j++; + break; + } + } + } + } + //<(EIP101213+) + + //------------------------------------------------------------------------------ + //Get Previous boot priority. + for( OldDevOrder2 = OldDevOrder + ;(UINT8*)OldDevOrder2<(UINT8*)OldDevOrder+OldDvOrderSize + ; OldDevOrder2 = (UEFI_DEVICE_ORDER*)((UINT8*)OldDevOrder2 + OldDevOrder2->Length + sizeof(OldDevOrder2->Type)) ) + { + if( DevType != OldDevOrder2->Type ) continue; + + { + UINT16 k; + + for(k=0;k<(OldDevOrder2->Length-2)/sizeof(UINT16);k++) + { + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + + if( BootOrderFlag[Option->BootOptionNumber] ) continue; //not zero? //(EIP129692) + if(GetUefiBootOptionTag(Option->FilePathList) != DevType) continue; //(EIP100223+) + if(Option->BootOptionNumber == (OldDevOrder2->Device[k] & 0xff)) + { + DevOrder->Length += 2; + DevOrder->Device[j] = Option->BootOptionNumber; + BootOrderFlag[Option->BootOptionNumber]=0xffff; //mask flag. + if(OldDevOrder2->Device[k] & 0xff00) //(EIP129692) + DevOrder->Device[j] |= 0xff00; + j++; + } + } + } + } + } + //------------------------------------------------------------------------------ + + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + + if( IsLegacyBootOption(Option) || Option->GroupHeader) continue; + if( BootOrderFlag[Option->BootOptionNumber] ) continue; //not zero? + + if( GetUefiBootOptionTag(Option->FilePathList) == DevType ) + { + DevOrder->Length += 2; + DevOrder->Device[j] = Option->BootOptionNumber; + if(!(Option->Attributes & LOAD_OPTION_ACTIVE)) + DevOrder->Device[j] |= 0xff00; + j++; + } + } + + if( DevOrder->Length > 2) + { //(EIP129692+)> + //re-alignment, move all disable item to last. + UINT16 DeviceCount; + DeviceCount=(DevOrder->Length-2)/sizeof(UINT16); + { + UEFI_DEVICE_ORDER *NewOrder=Malloc(DevOrder->Length+sizeof(DevOrder->Type)); + if( NewOrder ) + { + UINT16 NewOrderCount=0; + + NewOrder->Type=DevOrder->Type; + NewOrder->Length=DevOrder->Length; + + for(j=0; jDevice[j] & 0xff00) continue; + NewOrder->Device[NewOrderCount]=DevOrder->Device[j]; + NewOrderCount++; + } + + for(j=0; jDevice[j] & 0xff00)) continue; + NewOrder->Device[NewOrderCount]=DevOrder->Device[j]; + NewOrderCount++; + } + pBS->CopyMem( DevOrder, NewOrder, DevOrder->Length+sizeof(DevOrder->Type) ); + pBS->FreePool(NewOrder); + } + } + DevOrder = (UEFI_DEVICE_ORDER*)((UINT8*)DevOrder + DevOrder->Length + sizeof(DevOrder->Type)); + } + //<(EIP129692+) + } + + { + UINTN DevOrderSize; + DevOrderSize = (UINT8*)DevOrder - (UINT8*)DevOrder2; + + if(DevOrderSize) + { + pRS->SetVariable( + L"UefiDevOrder", &FixedBootOrderGuid, + BS_NV_VARIABLE_ATTRIBUTES, DevOrderSize, DevOrder2); + + pRS->SetVariable( + L"OldUefiDevOrder", &FixedBootOrderGuid, + BS_NV_VARIABLE_ATTRIBUTES, DevOrderSize, DevOrder2); + } + else + { + pRS->SetVariable( + L"UefiDevOrder", &FixedBootOrderGuid, + 0, 0, NULL); + + pRS->SetVariable( + L"OldUefiDevOrder", &FixedBootOrderGuid, + 0, 0, NULL); + } + + } + + pBS->FreePool( DevOrder2 ); +} + +// +//---------------------------------------------------------------------------- +// +// Procedure: FBO_CompareTagThenBbsIndex +// +// Description: This function returns result of compairing two DLINK tags. +// +// Input: +// Link1 - pointer to the first tag for compare +// Link1 - pointer to the second tag for compare +// +// Output: INT32 - result of comparing. +// +//---------------------------------------------------------------------------- +// +INT32 FBO_CompareTagThenBbsIndex( IN DLINK *Link1, IN DLINK *Link2 ) +{ + BOOT_OPTION *Option1 = (BOOT_OPTION*)Link1; + BOOT_OPTION *Option2 = (BOOT_OPTION*)Link2; + + // Compare Tags first + if (Option1->Tag < Option2->Tag) + return -1; + else if (Option1->Tag > Option2->Tag) + return 1; + + // Compare by BBS index + if (Option1->BbsIndex < Option2->BbsIndex) + return -1; + else if (Option1->BbsIndex > Option2->BbsIndex) + return 1; + + return 0; +} + + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_SetDefaultUEFIDevOrder +// +// Description: Go through the master boot option list and create +// memory representation of the default uefi order variable +// +// Input: DLIST *BootOptionList - the master boot option list +// +// Output: none +// +// Note: +//---------------------------------------------------------------------------- +// +VOID FBO_SetDefaultUEFIDevOrder( +){ + UINT16 i,j; + DLINK *Link; + BOOT_OPTION *Option; + UEFI_DEVICE_ORDER *DevOrder=NULL, *DevOrder2=NULL; + EFI_GUID FixedBootOrderGuid = FIXED_BOOT_ORDER_GUID; + UINT16 DeviceMapCount; + + DevOrder2 = DevOrder = Malloc(512); + + if( DevOrder == NULL ) + return; + + SortList(BootOptionList, FBO_CompareTagThenBbsIndex); + + DeviceMapCount=GetDevMapDataCount( pFBOUefiDevMap ); + for(i=0; iType = DevType; + DevOrder->Length=2; + + j=0; + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + + if ( IsLegacyBootOption(Option) || Option->GroupHeader) continue; + + if( GetUefiBootOptionTag(Option->FilePathList) == DevType ) + { + DevOrder->Length += 2; + DevOrder->Device[j] = Option->BootOptionNumber; + + j++; + } + } + + //TRACE((-1,"DevType=%x DevOrder->Length=%x\n", DevType, DevOrder->Length)); + if( DevOrder->Length > 2) + DevOrder = (UEFI_DEVICE_ORDER*)((UINT8*)DevOrder + DevOrder->Length + sizeof(DevOrder->Type)); + } + + { + UINTN DevOrderSize; + DevOrderSize = (UINT8*)DevOrder - (UINT8*)DevOrder2; + + if( DevOrderSize ) + { + pRS->SetVariable( + L"DefaultUefiDevOrder", &FixedBootOrderGuid, + BS_NV_VARIABLE_ATTRIBUTES, DevOrderSize, DevOrder2); + } + else + { + pRS->SetVariable( + L"DefaultUefiDevOrder", &FixedBootOrderGuid, + 0, 0, NULL); + } + + } + + pBS->FreePool( DevOrder2 ); +} + +// +//---------------------------------------------------------------------------- +// Procedure: SetLegacyBootOptionPriority +// +// Description: Set legacy boot option list priority. +// +// Input: DeviceType - Legacy Device type +// Priority - pointer of Priority(UINT32). +// +// Output: none +// +// Note: +//---------------------------------------------------------------------------- +// +SetLegacyBootOptionPriority(UINT16 DeviceType, UINT32 *Priority) +{ + DLINK *Link; + BOOT_OPTION *Option; + BBS_BBS_DEVICE_PATH *BbsDp; + + //Search Group Header + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + BbsDp = (BBS_BBS_DEVICE_PATH*)Option->FilePathList; + if(BbsDp->DeviceType != DeviceType ) continue; + if(!Option->GroupHeader) continue; + + Option->Priority=++(*Priority); + Option->Attributes&=~LOAD_OPTION_HIDDEN; + Option->Attributes|=LOAD_OPTION_ACTIVE; + + TRACE((-1,"[FBOSetOrder.c]Legacy Option->Priority=%x Name=%S\n", Option->Priority, Option->Description)); +// (*Priority)++; + break; + } + + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (!IsLegacyBootOption(Option)) continue; //Is Uefi? continue; + if(Option->GroupHeader) continue; + + BbsDp = (BBS_BBS_DEVICE_PATH*)Option->FilePathList; + if(BbsDp->DeviceType != DeviceType ) continue; + Option->Priority=++(*Priority); +// Option->Attributes|=LOAD_OPTION_ACTIVE; + TRACE((-1,"[FBOSetOrder.c]Legacy Option->Priority=%x Name=%S\n", Option->Priority, Option->Description)); + } +} + +// +//---------------------------------------------------------------------------- +// Procedure: SetUefiBootOptionPriority +// +// Description: Set uefi boot option list priority. +// +// Input: DeviceType - Uefi Device type +// Priority - pointer of Priority(UINT32). +// +// Output: none +// +// Note: +//---------------------------------------------------------------------------- +// +SetUefiBootOptionPriority(UINT16 DeviceType, UINT32 *Priority) +{ + EFI_GUID FixedBootOrderGuid = FIXED_BOOT_ORDER_GUID; + UEFI_DEVICE_ORDER *DevOrder=NULL, *DevOrder2=NULL; + UINTN DevOrderSize=0; + DLINK *Link; + BOOT_OPTION *Option; + UINT16 j; + + GetEfiVariable(L"UefiDevOrder", &FixedBootOrderGuid, NULL, &DevOrderSize, &DevOrder); + + DevOrder2=DevOrder; + + for( DevOrder=DevOrder2 + ;(UINT8*)DevOrder<(UINT8*)DevOrder2+DevOrderSize + ; DevOrder = (UEFI_DEVICE_ORDER*)((UINT8*)DevOrder + DevOrder->Length + sizeof(DevOrder->Type)) ) + { + if( DeviceType != DevOrder->Type ) continue; + + for(j=0; j<(DevOrder->Length-2)/sizeof(UINT16); j++) + { + TRACE((-1,"[FBOSetOrder.c]DevOrder->Device[%d]=%x\n", j, DevOrder->Device[j])); + + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if(IsLegacyBootOption(Option)) continue; + if( Option->BootOptionNumber != (DevOrder->Device[j] & 0xff)) continue; + + if( DevOrder->Device[j] & 0xff00 ) + Option->Attributes&=~LOAD_OPTION_ACTIVE; //Disable + else + { //(EIP128779+) + Option->Attributes|=LOAD_OPTION_ACTIVE; //Enable + Option->Priority=++(*Priority); //(EIP128779+) + } //(EIP128779+) + + Option->Attributes&=~LOAD_OPTION_HIDDEN; + TRACE((-1,"[FBOSetOrder.c]UEFI BootOptionNumber=%x Priority=%x Name=%S\n", Option->BootOptionNumber, Option->Priority, Option->Description)); + break; + } + } + } + + if( DevOrder2 ) + pBS->FreePool( DevOrder2 ); +} + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_UpdateBootListPriority +// +// Description: use setup data LegacyPriorities/UefiPriorities/DualPriorities +// ,set legacy/uefi boot option list priority. +// +// Input: None +// +// Output: None +// +//---------------------------------------------------------------------------- +// +VOID FBO_UpdateBootListPriority() +{ + EFI_STATUS Status; + EFI_GUID gSetupGuid=SETUP_GUID; + SETUP_DATA *pSetupData=NULL; + UINT32 SetupAttr; + UINTN SetupSize=0; + DLINK *Link; + BOOT_OPTION *Option; + UINT16 i; //,j; + UINT16 DeviceMapCount=0; + UINT16 TypeIndex; + UINT32 PreviousPriority=0; + +//(EIP99368+)>> + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) continue; + if(!Wcscmp(Option->Description,L"USB Entry for Windows To Go Logo Test")) + return; + } +//<<(EIP99368+) + + BuildUEFIDevOrder(); + + Status = GetEfiVariable(L"Setup", &gSetupGuid, &SetupAttr, &SetupSize, &pSetupData); + + if (EFI_ERROR(Status)) return; + +#if FBO_DUAL_MODE + if(pSetupData->BootMode == 2) //Is Dual boot mode? + { + //----------------------------------------------------- + //Search Legacy Group Header and Set is disable + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) //(EIP114186+) + Option->Priority=UNASSIGNED_HIGHEST_TAG; //(EIP114186+) + if(!Option->GroupHeader) continue; + Option->Attributes&=~LOAD_OPTION_ACTIVE; + Option->Priority=LOWEST_BOOT_OPTION_PRIORITY; + } + //----------------------------------------------------- + //Set All Uefi device Disable + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) continue; + + if(Option->Attributes & LOAD_OPTION_HIDDEN) continue; //(EIP118170+) + + Option->Attributes&=~LOAD_OPTION_ACTIVE; //Disable + Option->Priority=LOWEST_BOOT_OPTION_PRIORITY; + } + //----------------------------------------------------- + DeviceMapCount=GetDevMapDataCount( pFBODualDevMap ); + for(i=0;iDualPriorities[i]; + if( !pFBODualDevMap[TypeIndex].BBSType ) //0, Uefi device + { + TRACE((-1,"[FBOSetOrder.c]DualPriorities[%d] pFBODualDevMap[%d].DevType=%x\n", i, TypeIndex, pFBODualDevMap[TypeIndex].DevType)); + SetUefiBootOptionPriority( pFBODualDevMap[TypeIndex].DevType, &PreviousPriority ); + } + else + { + if( pFBODualDevMap[TypeIndex].DevType == 0 ) continue; //Disable? //(EIP114186+) + TRACE((-1,"[FBOSetOrder.c]DualPriorities[%d] pFBODualDevMap[%d].DevType=%x\n", i, TypeIndex, pFBODualDevMap[TypeIndex].DevType)); + SetLegacyBootOptionPriority( pFBODualDevMap[TypeIndex].DevType, &PreviousPriority ); + } + } + } + else +#endif + if(pSetupData->BootMode == 1) //Is Uefi boot mode? + { + //----------------------------------------------------- + //Set All device Disable + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) //(EIP107440) + if(!Option->GroupHeader) continue; //(EIP107440+) + + if(Option->Attributes & LOAD_OPTION_HIDDEN) continue; //(EIP118170+) + + Option->Attributes&=~LOAD_OPTION_ACTIVE; //Disable + Option->Priority=LOWEST_BOOT_OPTION_PRIORITY; + } + //----------------------------------------------------- + DeviceMapCount=GetDevMapDataCount( pFBOUefiDevMap ); + for(i=0; iUefiPriorities[i]; + + TRACE((-1,"[FBOSetOrder.c]UefiPriorities[%d] pFBOUefiDevMap[TypeIndex].DevType=%x\n", i, pFBOUefiDevMap[TypeIndex].DevType)); + SetUefiBootOptionPriority( pFBOUefiDevMap[TypeIndex].DevType, &PreviousPriority ); + } + + //----------------------------------------------------- + //Set Other UEFI device priority + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + + if (IsLegacyBootOption(Option) + || (Option->Priority != LOWEST_BOOT_OPTION_PRIORITY) ) continue; + + Option->Priority=++PreviousPriority; + TRACE((-1,"UEFI device Option->Priority=%x Name=%S\n", Option->Priority, Option->Description)); + + } + //----------------------------------------------------- + + //----------------------------------------------------- + //Set Other Legacy device priority and hide + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + + if (!IsLegacyBootOption(Option)) continue; + + Option->Priority=++PreviousPriority; + Option->Attributes|=LOAD_OPTION_HIDDEN; + TRACE((-1,"[FBOSetOrder.c]Legacy Option->Priority=%x Name=%S\n", Option->Priority, Option->Description)); + } + //----------------------------------------------------- + } + else + if(pSetupData->BootMode == 0) //Is Legacy boot mode? + { + //----------------------------------------------------- + //Search Legacy Group Header and Set is disable + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) //(EIP114186+) + Option->Priority=UNASSIGNED_HIGHEST_TAG; //(EIP114186+) + if(!Option->GroupHeader) continue; + Option->Attributes&=~LOAD_OPTION_ACTIVE; + } + + DeviceMapCount=GetDevMapDataCount( pFBOLegacyDevMap ); + TRACE((-1,"[FBOSetOrder.c] DeviceMapCount=%x\n", DeviceMapCount)); + for(i=0; iLegacyPriorities[i]; + if( pFBOLegacyDevMap[TypeIndex].DevType == 0 ) continue; //Disable? //(EIP114186+) + SetLegacyBootOptionPriority( pFBOLegacyDevMap[TypeIndex].DevType, &PreviousPriority ); + } + + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option){ + if (IsLegacyBootOption(Option)) continue; + Option->Priority=++PreviousPriority; + Option->Attributes |= LOAD_OPTION_HIDDEN; + TRACE((-1,"[FBOSetOrder.c]UEFI Option->Priority=%x Name=%S\n", Option->Priority, Option->Description)); + } + } + BuildFboLegacyDevOrder(); + + // + // Undesried boot options should be not able to boot (ACTIVE=0) + // This code must not be executed before BuildFboLegacyDevOrder + // in order to keep the FboLegacyDevOrder has the same disabled information as setup + // + FOR_EACH_BOOT_OPTION(BootOptionList, Link, Option) + { + UINT16 LegacyFlag = IsLegacyBootOption(Option); + + if (pSetupData->BootMode == 2 // Dual mode? + || (pSetupData->BootMode == 0 && LegacyFlag) // legacy mode and legacy option? + || (pSetupData->BootMode == 1 && !LegacyFlag) // UEFI mode and UEFI option? + ) + { + // option should be ACTIVE to boot and NOT HIDDEN for TSE + Option->Attributes &= ~LOAD_OPTION_HIDDEN; // clear HIDDEN for all legacy boot options + } + else + { + // undesried boot options for selected boot mode + // HIDDEN for TSE not sees it + // NOT ACTIVE for not booting from it + Option->Attributes |= LOAD_OPTION_HIDDEN; // HIDDEN + Option->Attributes &= ~LOAD_OPTION_ACTIVE; // Disable undesired UEFI boot options + } + } + pBS->FreePool(pSetupData); + + DUMP_BOOT_OPTION_LIST(BootOptionList,"After UpdateBootListPriority"); +} +// +//---------------------------------------------------------------------------- +// +// Procedure: BuildFboLegacyDevOrder +// +// Description: Build FboLegacyDevOrder variable from BootOptionList. +// This variable should be set before we disable the undesried boot +// options for selected boot mode. So we can get the correct +// BootOptionList.Attributes reflecting the selection of setup. +// +// Input: None +// +// Output: FboLegacyDevOrder variable updated +// +//---------------------------------------------------------------------------- +// + +VOID BuildFboLegacyDevOrder() +{ +#if CSM_SUPPORT + UINTN DevOrderSize; + LEGACY_DEVICE_ORDER *DevOrder, *DevOrderStart; + LEGACY_DEVICE_ORDER *NewDevOrder, *NewDevOrderStart; + UINT16 DeviceCount; + UINT16 i, j; + + // return if no BootOption + if(!BootOptionList->Size) + return; + + SortList(BootOptionList, ComparePriorityThenBootOptionNumber); + BuildLegacyDevOrderBuffer(&DevOrder, &DevOrderSize); + + DevOrderStart = DevOrder; + // + // Crerate the NewDevOrder from DevOrder for changing order + // + NewDevOrderStart = NewDevOrder = MallocZ(DevOrderSize); + if (NewDevOrder == NULL) + { + pBS->FreePool(DevOrderStart); + return; + } + pBS->CopyMem(NewDevOrder, DevOrder, DevOrderSize); + + // + // We need to keep the disabled ones at last + // + for (; (UINT8*)NewDevOrder < (UINT8*)NewDevOrderStart + DevOrderSize;) + { + j = 0; + DeviceCount = DEVORDER_COUNT(NewDevOrder); + + // + // Save the enabled ones first + // + for (i = 0; i < DeviceCount; i++) + { + if (DevOrder->Device[i] & FBO_LEGACY_DISABLED_MASK) + { + continue; + } + NewDevOrder->Device[j++] = DevOrder->Device[i]; + } + // + // Save the disabled ones later + // + for (i = 0; i < DeviceCount; i++) + { + if (!(DevOrder->Device[i] & FBO_LEGACY_DISABLED_MASK)) + { + continue; + } + NewDevOrder->Device[j++] = DevOrder->Device[i]; + } + + // + // Next + // + NewDevOrder = (LEGACY_DEVICE_ORDER*)((UINT8*)NewDevOrder + NewDevOrder->Length + sizeof(NewDevOrder->Type)); + DevOrder = (LEGACY_DEVICE_ORDER*)((UINT8*)DevOrder + DevOrder->Length + sizeof(DevOrder->Type)); + } + + pRS->SetVariable( + L"FboLegacyDevOrder", &gFixedBootOrderGuid, + BS_NV_VARIABLE_ATTRIBUTES, DevOrderSize, NewDevOrderStart + ); + + pBS->FreePool(DevOrderStart); + pBS->FreePool(NewDevOrderStart); +#endif //#if CSM_SUPPORT +} + //(EIP101213+)> +// +//---------------------------------------------------------------------------- +// Procedure: FBO_AdjustWtgPriority() +// +// Description: First boot order of group, Change this gorup +// uefi Priorities to Top position. +// +// Input: None +// +// Output: None +// +//---------------------------------------------------------------------------- +// +void FBO_AdjustWtgPriority() +{ + EFI_STATUS Status; + UINT16 *BootOrder = NULL; + UINTN BootOrderSize = 0; + UINT32 SetupAttr; + UINTN SetupSize = 0; + SETUP_DATA *pSetupData = NULL; + DLINK *Link; + BOOT_OPTION *Option; + EFI_GUID gSetupGuid = SETUP_GUID; + UINT16 i, TypeIndex; + UINT16 DeviceMapCount = 0; + BOOLEAN UpdateSetup = FALSE, WindowsToGoFound = FALSE; + + Status = GetEfiVariable(L"Setup", &gSetupGuid, &SetupAttr, &SetupSize, &pSetupData); + if (EFI_ERROR(Status)) + return; + + // Search for Windwos To Go Boot Option + FOR_EACH_BOOT_OPTION(BootOptionList,Link,Option) + { + if (IsLegacyBootOption(Option)) + continue; + + // Found !! + if(!Wcscmp(Option->Description,L"USB Entry for Windows To Go")) //if WTG? + { + Status=GetEfiVariable( + L"BootOrder", + &EfiVariableGuid, + NULL, + &BootOrderSize, + &BootOrder); + + if(EFI_ERROR(Status)) + { + pBS->FreePool( pSetupData ); + return; + } + + // There are 2 Options in "Windows To Go Startup Options" + // Choose Yes, Windows will set Windows to Go BootOption to Frist Priority in BootOrder. + // Choose No, User Need to change PC's Firmware Setting. + // So, We Only handle the "Yes" Option + + if(BootOrder[0] != Option->BootOptionNumber) + { + pBS->FreePool( pSetupData ); + pBS->FreePool( BootOrder ); + return; + }else + { + WindowsToGoFound = TRUE; + break; + } + } + } + if(!WindowsToGoFound) + { + pBS->FreePool( pSetupData ); + return; + } + +#if FBO_DUAL_MODE + TypeIndex = SearchDevMapByType( pFBODualDevMap,GetUefiBootOptionTag(Option->FilePathList)); + DeviceMapCount=GetDevMapDataCount( pFBODualDevMap ); + + for(i=0;iDualPriorities[i]) + { + UINT16 j; + UINT16 FirstPriority = pSetupData->DualPriorities[i]; + + for(j=i;j>0;j--) + pSetupData->DualPriorities[j] = pSetupData->DualPriorities[j-1]; + + pSetupData->DualPriorities[0] = FirstPriority; + UpdateSetup=TRUE; + break; + } + } +#endif + TypeIndex = SearchDevMapByType( pFBOUefiDevMap,GetUefiBootOptionTag(Option->FilePathList)); + DeviceMapCount = GetDevMapDataCount( pFBOUefiDevMap ); + for(i = 0 ; i < DeviceMapCount ; i++) + { + if(TypeIndex == pSetupData->UefiPriorities[i]) + { + UINT16 j; + UINT16 FirstPriority = pSetupData->UefiPriorities[i]; + + for(j = i ; j > 0 ; j--) + pSetupData->UefiPriorities[j] = pSetupData->UefiPriorities[j-1]; + + pSetupData->UefiPriorities[0] = FirstPriority; + UpdateSetup=TRUE; + break; + } + } + + if(UpdateSetup) + Status = pRS->SetVariable(L"Setup",&gSetupGuid, SetupAttr, SetupSize, pSetupData); + + pBS->FreePool( pSetupData ); + pBS->FreePool( BootOrder ); + + return; +} + + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_AdjustPriority() +// +// Description: first boot order of group, Change this gorup +// uefi and dual Priorities to Top position. +// +// Input: None +// +// Output: None +// +//---------------------------------------------------------------------------- +// +void FBO_AdjustPriority() +{ + FBO_AdjustWtgPriority(); +} + +// +//---------------------------------------------------------------------------- +// Procedure: FBO_Init +// +// Description: Initialize the module memory, and device map data. +// +// Input: None +// +// Output: None +// +//---------------------------------------------------------------------------- +// +EFI_STATUS FBO_Init(IN void) +{ + EFI_STATUS Status; + EFI_GUID FixedBootOrderGuid=FIXED_BOOT_ORDER_GUID; + EFI_FIXED_BOOT_ORDER_PROTOCOL *pFBO=NULL; + EFI_GUID gSetupGuid=SETUP_GUID; + SETUP_DATA *pSetupData=NULL; + UINT32 SetupAttr; + UINTN SetupSize=0; + UINT16 i, DeviceMapCount; + + Status = pBS->LocateProtocol( &FixedBootOrderGuid, NULL, &pFBO ); + + if(!EFI_ERROR(Status)) + { + pFBOLegacyDevMap = pFBO->GetLegacyDevMap(); + pFBOUefiDevMap = pFBO->GetUefiDevMap(); +#if FBO_DUAL_MODE + pFBODualDevMap = pFBO->GetDualDevMap(); +#endif + } + + Status = GetEfiVariable(L"Setup", &gSetupGuid, &SetupAttr, &SetupSize, &pSetupData); + if( !EFI_ERROR(Status) ) + { + if( !pSetupData->FBO_Init ) + { + pSetupData->FBO_Init=1; + //(EIP107268+)> +#if USE_BCP_DEFAULT_PRIORITIES + DeviceMapCount=GetDevMapDataCount( pFBOLegacyDevMap ); + for( i=0; iLegacyPriorities[i]=pSetupData->BcpDefaultLegacyPriorities[i]; + + DeviceMapCount=GetDevMapDataCount( pFBOUefiDevMap ); + for( i=0; iUefiPriorities[i]=pSetupData->BcpDefaultUefiPriorities[i]; + //(EIP122146+)> +#if FBO_DUAL_MODE + DeviceMapCount=GetDevMapDataCount( pFBODualDevMap ); + for( i=0; iDualPriorities[i]=pSetupData->BcpDefaultDualPriorities[i]; +#endif + //<(EIP122146+) +#else //<(EIP107268+) + DeviceMapCount=GetDevMapDataCount( pFBOLegacyDevMap ); + for( i=0; iLegacyPriorities[i]=i; + + DeviceMapCount=GetDevMapDataCount( pFBOUefiDevMap ); + for( i=0; iUefiPriorities[i]=i; + +#if FBO_DUAL_MODE + DeviceMapCount=GetDevMapDataCount( pFBODualDevMap ); + for( i=0; iDualPriorities[i]=i; +#endif + +#endif //#if USE_BCP_DEFAULT_PRIORITIES //(EIP107268+) + + Status = pRS->SetVariable(L"Setup",&gSetupGuid, SetupAttr, SetupSize, pSetupData); + pBS->FreePool( pSetupData ); + } + } + + return Status; +} +// +//---------------------------------------------------------------------------- +// Procedure: FindLegacyDeviceGroupByType +// +// Description: Go through the legacy device order structure and find the legacy dev order +// group type that we want then return this group. +// +// Input: LEGACY_DEVICE_ORDER *DevOrder - pointer to the legacy device order +// UINTN DevOrderSize - size of the legacy dev order structure +// UINT32 Type - Group type to match +// +// Output: LEGACY_DEVICE_ORDER * +// +//---------------------------------------------------------------------------- +// +LEGACY_DEVICE_ORDER* FindLegacyDeviceGroupByType( + LEGACY_DEVICE_ORDER *DevOrder, UINTN DevOrderSize, UINT32 Type +) +{ + LEGACY_DEVICE_ORDER *LegacyGroup = DevOrder; + + for (; (UINT8*)LegacyGroup < (UINT8*)DevOrder + DevOrderSize + ; (UINT8*)LegacyGroup += LegacyGroup->Length + sizeof(LegacyGroup->Type)) + { + if (LegacyGroup->Type == Type) { + return LegacyGroup; + } + } + + return NULL; +} +// +//---------------------------------------------------------------------------- +// Procedure: FboSyncBootOptionsFromDevOrder +// +// Description: UefiDevOrder and FboLegacyDevOrder variables contain the +// disabled flags saved by setup. Need to update the disabled +// flag to BootOptionList right before any other functions +// that will process the BootOptionList. +// BootOptionList will be set to NOT ACTIVE for disabled +// DevOrder, ACTIVE for enabled one. +// +// Input: None +// +// Output: None +// +//---------------------------------------------------------------------------- +// +FboSyncBootOptionsFromDevOrder() +{ + LEGACY_DEVICE_ORDER *LegacyOrder = NULL, *LegacyGroup = NULL; + LEGACY_DEVICE_ORDER *OldLegacyOrder = NULL, *OldLegacyGroup = NULL; + UEFI_DEVICE_ORDER *UefiOrder = NULL, *UefiGroup = NULL; + UINTN DevOrderSize = 0; + UINTN OldDevOrderSize = 0; + DLINK *Link; + BOOT_OPTION *Option; + INT32 j; + EFI_STATUS Status; + UINT16 DeviceCount; + INT32 DevIndex; + UINT32 Type; + + // + // Set ACTIVE information according to UefiDevOrder + // + Status = GetEfiVariable(L"UefiDevOrder", &gFixedBootOrderGuid, NULL, &DevOrderSize, &UefiOrder); + TRACE((-1, "[fbo] Get UefiDevOrder: %r\n", Status)); + if (!EFI_ERROR(Status)) + { + for (UefiGroup = UefiOrder + ; (UINT8*)UefiGroup < (UINT8*)UefiOrder + DevOrderSize + ; UefiGroup = (UEFI_DEVICE_ORDER*)((UINT8*)UefiGroup + UefiGroup->Length + sizeof(UefiGroup->Type))) + { + DeviceCount = DEVORDER_COUNT(UefiGroup); + + // loop through boot option numbers within this group + for (j = 0; j < DeviceCount; j++) + { + // set up Option->Attributes.LOAD_OPTION_ACTIVE + FOR_EACH_BOOT_OPTION(BootOptionList, Link, Option) + { + if (IsLegacyBootOption(Option)) + continue; + + if ((UefiGroup->Device[j]&FBO_UEFI_ORDER_MASK) == Option->BootOptionNumber) // [31:24] = disabled flag + { + TRACE((-1, "[fbo] %S.Device[%d] = %x\n", Option->Description, j, UefiGroup->Device[j])); + if (UefiGroup->Device[j] & FBO_UEFI_DISABLED_MASK) // disabled? + Option->Attributes &= ~LOAD_OPTION_ACTIVE; + else + Option->Attributes |= LOAD_OPTION_ACTIVE; + } + } + } + } + + } + + + // + // Set ACTIVE information according to FboLegacyDevOrder + // + + // The flow of this FboLegacyDevOrder variable: + // 1. Updated the BootOptionList.Attributes from FboLegacyDevOrder right after boot options are + // read from NVRAM in FboSyncBootOptionsFromDevOrder() to reflect the setup controls. + // 2. Attributes will be changed to HIDDEN and NOT ACTIVE according to boot mode in FBO_UpdateBootListPriority(). + // 3. Save the disabled information here for setup to use before we modifying the Attributes later + // in FBO_UpdateBootListPriority(). + // 4. OldLegacyDevOrder variable indicates the sequence of legacy boot options by group in BootOptionList + // after reading from NVRAM, we need it to compare with FboLegacyDevOrder variable to find out options + // should set ACTIVE attribute or INACTIVE attribute. + + Status = GetEfiVariable(L"FboLegacyDevOrder", &gFixedBootOrderGuid, NULL, &DevOrderSize, &LegacyOrder); + TRACE((-1, "[fbo] Get FboLegacyDevOrder: %r\n", Status)); + + if (!EFI_ERROR(Status)) + { + Status = GetEfiVariable(L"OldLegacyDevOrder", &LegacyDevOrderGuid, NULL, &OldDevOrderSize, &OldLegacyOrder); + TRACE((-1, "[fbo] Get OldLegacyDevOrder: %r\n", Status)); + + // + // Only TRUE if.. + // 1. Get variable successfully + // 2. Same size + // 3. Different contents + // + if (!EFI_ERROR(Status) + && OldDevOrderSize == DevOrderSize + && MemCmp(LegacyOrder, OldLegacyOrder, DevOrderSize)) + { + UINT16 BootOptionNumber = INVALID_BOOT_OPTION_NUMBER; + + FOR_EACH_BOOT_OPTION(BootOptionList, Link, Option) + { + if (!IsLegacyBootOption(Option) || Option->GroupHeader) continue; + + if (BootOptionNumber != Option->BootOptionNumber) { + + Type = BOOT_OPTION_GET_BBS_ENTRY_DEVICE_TYPE_FUNCTION(Option->BbsEntry); + LegacyGroup = FindLegacyDeviceGroupByType(LegacyOrder, DevOrderSize, Type); + OldLegacyGroup = FindLegacyDeviceGroupByType(OldLegacyOrder, OldDevOrderSize, Type); + + j = 0; + BootOptionNumber = Option->BootOptionNumber; + } + + if (LegacyGroup == NULL || OldLegacyGroup == NULL) continue; + + DevIndex = FindPositionInTheGroupByBbsIndex(LegacyGroup, OldLegacyGroup->Device[j]); + // FixedBootOrderSaveChange function doesn't save FboLegacyDevOrder variable as + // group sequence we change in Setup, and that cause AdjustLegacyBootOptionPriorities + // function update the wrong Priority to Option, hence, we disable + // AdjustLegacyBootOptionPriorities function by SDL and update correct priority here. + Option->Priority += (DevIndex - j) * DEFAULT_PRIORITY_INCREMENT; + j++; + + if (LegacyGroup->Device[DevIndex] & FBO_LEGACY_DISABLED_MASK) + { + Option->Attributes &= ~LOAD_OPTION_ACTIVE; + } + else + { + Option->Attributes |= LOAD_OPTION_ACTIVE; + } + } + } + } + + if (OldLegacyOrder != NULL) + pBS->FreePool(OldLegacyOrder); + if (LegacyOrder != NULL) + pBS->FreePool(LegacyOrder); + if (UefiOrder != NULL) + pBS->FreePool(UefiOrder); + +} +//********************************************************************** +//********************************************************************** +//** ** +//** (C)Copyright 1985-2012, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 6145-F Northbelt Pkwy, Norcross, GA 30071 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//********************************************************************** +//********************************************************************** -- cgit v1.2.3