Store last booted OS in NVRAM and make it default one on next boot
All checks were successful
Builds / ExectOS (amd64) (push) Successful in 35s
Builds / ExectOS (i686) (push) Successful in 33s

This commit is contained in:
Rafal Kupiec 2024-03-18 19:41:55 +01:00
parent ee23cd90cb
commit 1d26b81923
Signed by: belliash
GPG Key ID: 4E829243E0CFE6B4
4 changed files with 48 additions and 7 deletions

View File

@ -77,7 +77,7 @@ typedef PVOID (*PBL_GET_VIRTUAL_ADDRESS)(IN PXTBL_PAGE_MAPPING PageMap, IN PVOID
typedef EFI_STATUS (*PBL_INITIALIZE_ENTROPY)(PULONGLONG RNGBuffer); typedef EFI_STATUS (*PBL_INITIALIZE_ENTROPY)(PULONGLONG RNGBuffer);
typedef VOID (*PBL_INITIALIZE_PAGE_MAP)(OUT PXTBL_PAGE_MAPPING PageMap, IN SHORT PageMapLevel, IN PAGE_SIZE PageSize); typedef VOID (*PBL_INITIALIZE_PAGE_MAP)(OUT PXTBL_PAGE_MAPPING PageMap, IN SHORT PageMapLevel, IN PAGE_SIZE PageSize);
typedef EFI_STATUS (*PBL_INSTALL_XT_PROTOCOL)(IN PVOID Interface, IN PEFI_GUID Guid); typedef EFI_STATUS (*PBL_INSTALL_XT_PROTOCOL)(IN PVOID Interface, IN PEFI_GUID Guid);
typedef EFI_STATUS (*PBL_INVOKE_BOOT_PROTOCOL)(IN PLIST_ENTRY OptionsList); typedef EFI_STATUS (*PBL_INVOKE_BOOT_PROTOCOL)(IN PWCHAR ShortName, IN PLIST_ENTRY OptionsList);
typedef EFI_STATUS (*PBL_LOCATE_PROTOCOL_HANDLES)(OUT PEFI_HANDLE *Handles, OUT PUINT_PTR Count, IN PEFI_GUID ProtocolGuid); typedef EFI_STATUS (*PBL_LOCATE_PROTOCOL_HANDLES)(OUT PEFI_HANDLE *Handles, OUT PUINT_PTR Count, IN PEFI_GUID ProtocolGuid);
typedef EFI_STATUS (*PBL_LOAD_EFI_IMAGE)(IN PEFI_DEVICE_PATH_PROTOCOL DevicePath, IN PVOID ImageData, IN SIZE_T ImageSize, OUT PEFI_HANDLE ImageHandle); typedef EFI_STATUS (*PBL_LOAD_EFI_IMAGE)(IN PEFI_DEVICE_PATH_PROTOCOL DevicePath, IN PVOID ImageData, IN SIZE_T ImageSize, OUT PEFI_HANDLE ImageHandle);
typedef EFI_STATUS (*PBL_MAP_EFI_MEMORY)(IN OUT PXTBL_PAGE_MAPPING PageMap, IN OUT PVOID *MemoryMapAddress, IN PBL_GET_MEMTYPE_ROUTINE GetMemoryTypeRoutine); typedef EFI_STATUS (*PBL_MAP_EFI_MEMORY)(IN OUT PXTBL_PAGE_MAPPING PageMap, IN OUT PVOID *MemoryMapAddress, IN PBL_GET_MEMTYPE_ROUTINE GetMemoryTypeRoutine);
@ -146,6 +146,7 @@ typedef struct _XTBL_BOOT_PARAMETERS
typedef struct _XTBL_BOOTMENU_ITEM typedef struct _XTBL_BOOTMENU_ITEM
{ {
PWCHAR EntryName; PWCHAR EntryName;
PWCHAR ShortName;
PLIST_ENTRY Options; PLIST_ENTRY Options;
} XTBL_BOOTMENU_ITEM, *PXTBL_BOOTMENU_ITEM; } XTBL_BOOTMENU_ITEM, *PXTBL_BOOTMENU_ITEM;

View File

@ -207,7 +207,8 @@ BlInstallProtocol(IN PVOID Interface,
XTCDECL XTCDECL
EFI_STATUS EFI_STATUS
BlInvokeBootProtocol(IN PLIST_ENTRY OptionsList); BlInvokeBootProtocol(IN PWCHAR ShortName,
IN PLIST_ENTRY OptionsList);
XTCDECL XTCDECL
EFI_STATUS EFI_STATUS

View File

@ -135,7 +135,8 @@ BlDisplayBootMenu()
BlConsolePrint(L"Booting '%S' now...\n", MenuEntries[HighligtedEntryId].EntryName); BlConsolePrint(L"Booting '%S' now...\n", MenuEntries[HighligtedEntryId].EntryName);
/* Boot the highlighted (chosen) OS */ /* Boot the highlighted (chosen) OS */
Status = BlInvokeBootProtocol(MenuEntries[HighligtedEntryId].Options); Status = BlInvokeBootProtocol(MenuEntries[HighligtedEntryId].ShortName,
MenuEntries[HighligtedEntryId].Options);
if(Status != STATUS_SUCCESS) if(Status != STATUS_SUCCESS)
{ {
/* Failed to boot OS */ /* Failed to boot OS */
@ -279,7 +280,8 @@ BlDisplayBootMenu()
TimeOut = -1; TimeOut = -1;
/* Boot the highlighted (default) OS */ /* Boot the highlighted (default) OS */
Status = BlInvokeBootProtocol(MenuEntries[HighligtedEntryId].Options); Status = BlInvokeBootProtocol(MenuEntries[HighligtedEntryId].ShortName,
MenuEntries[HighligtedEntryId].Options);
if(Status != STATUS_SUCCESS) if(Status != STATUS_SUCCESS)
{ {
/* Failed to boot OS */ /* Failed to boot OS */

View File

@ -94,12 +94,14 @@ BlInitializeBootMenuList(OUT PXTBL_BOOTMENU_ITEM MenuEntries,
OUT PULONG EntriesCount, OUT PULONG EntriesCount,
OUT PULONG DefaultId) OUT PULONG DefaultId)
{ {
PWCHAR DefaultMenuEntry, MenuEntryName; EFI_GUID VendorGuid = XT_BOOT_LOADER_PROTOCOL_GUID;
PWCHAR DefaultMenuEntry, LastBooted, MenuEntryName;
PLIST_ENTRY MenuEntrySectionList, MenuEntryList; PLIST_ENTRY MenuEntrySectionList, MenuEntryList;
PXTBL_CONFIG_SECTION MenuEntrySection; PXTBL_CONFIG_SECTION MenuEntrySection;
PXTBL_CONFIG_ENTRY MenuEntryOption; PXTBL_CONFIG_ENTRY MenuEntryOption;
PXTBL_BOOTMENU_ITEM OsList;
ULONG DefaultOS, NumberOfEntries; ULONG DefaultOS, NumberOfEntries;
PXTBL_BOOTMENU_ITEM OsList;
EFI_STATUS Status;
/* Set default values */ /* Set default values */
DefaultOS = 0; DefaultOS = 0;
@ -109,6 +111,20 @@ BlInitializeBootMenuList(OUT PXTBL_BOOTMENU_ITEM MenuEntries,
/* Get default menu entry from configuration */ /* Get default menu entry from configuration */
DefaultMenuEntry = BlGetConfigValue(L"DEFAULT"); DefaultMenuEntry = BlGetConfigValue(L"DEFAULT");
/* Check if configuration allows to use last booted OS */
if(RtlCompareWideStringInsensitive(BlGetConfigValue(L"KEEPLASTBOOT"), L"TRUE", 0) == 0)
{
/* Attempt to get last booted Operating System from NVRAM */
Status = BlGetEfiVariable(&VendorGuid, L"XtLdrLastBootOS", (PVOID*)&LastBooted);
if(Status == STATUS_EFI_SUCCESS)
{
/* Set default menu entry to last booted OS */
DefaultMenuEntry = LastBooted;
}
BlDebugPrint(L"Last booted OS: '%S' - '%S'\n", LastBooted, DefaultMenuEntry);
BlSleepExecution(5000);
}
/* Iterate through all menu sections */ /* Iterate through all menu sections */
MenuEntrySectionList = BlpMenuList->Flink; MenuEntrySectionList = BlpMenuList->Flink;
while(MenuEntrySectionList != BlpMenuList) while(MenuEntrySectionList != BlpMenuList)
@ -146,6 +162,7 @@ BlInitializeBootMenuList(OUT PXTBL_BOOTMENU_ITEM MenuEntries,
/* Add OS to the boot menu list */ /* Add OS to the boot menu list */
OsList[NumberOfEntries].EntryName = MenuEntryName; OsList[NumberOfEntries].EntryName = MenuEntryName;
OsList[NumberOfEntries].ShortName = MenuEntrySection->SectionName;
OsList[NumberOfEntries].Options = &MenuEntrySection->Options; OsList[NumberOfEntries].Options = &MenuEntrySection->Options;
/* Get next menu entry */ /* Get next menu entry */
@ -162,6 +179,9 @@ BlInitializeBootMenuList(OUT PXTBL_BOOTMENU_ITEM MenuEntries,
/** /**
* Loads all necessary modules and invokes boot protocol. * Loads all necessary modules and invokes boot protocol.
* *
* @param ShortName
* Supplies a pointer to a short name of the chosen boot menu entry.
*
* @param OptionsList * @param OptionsList
* Supplies a pointer to list of options associated with chosen boot menu entry. * Supplies a pointer to list of options associated with chosen boot menu entry.
* *
@ -171,8 +191,10 @@ BlInitializeBootMenuList(OUT PXTBL_BOOTMENU_ITEM MenuEntries,
*/ */
XTCDECL XTCDECL
EFI_STATUS EFI_STATUS
BlInvokeBootProtocol(IN PLIST_ENTRY OptionsList) BlInvokeBootProtocol(IN PWCHAR ShortName,
IN PLIST_ENTRY OptionsList)
{ {
EFI_GUID VendorGuid = XT_BOOT_LOADER_PROTOCOL_GUID;
XTBL_BOOT_PARAMETERS BootParameters; XTBL_BOOT_PARAMETERS BootParameters;
PXTBL_BOOT_PROTOCOL BootProtocol; PXTBL_BOOT_PROTOCOL BootProtocol;
PLIST_ENTRY OptionsListEntry; PLIST_ENTRY OptionsListEntry;
@ -289,6 +311,21 @@ BlInvokeBootProtocol(IN PLIST_ENTRY OptionsList)
return Status; return Status;
} }
/* Check if chosen operating system should be saved */
if(RtlCompareWideStringInsensitive(BlGetConfigValue(L"KEEPLASTBOOT"), L"TRUE", 0) == 0)
{
/* Save chosen operating system in NVRAM */
Status = BlSetEfiVariable(&VendorGuid, L"XtLdrLastBootOS", (PVOID)ShortName, RtlWideStringLength(ShortName, 0) * sizeof(WCHAR));
if(Status != STATUS_EFI_SUCCESS)
{
/* Failed to save chosen Operating System */
BlDebugPrint(L"WARNING: Failed to save chosen Operating System in NVRAM (Status Code: 0x%zX)\n", Status);
}
BlDebugPrint(L"Now setting OS: '%S'\n", ShortName);
BlSleepExecution(5000);
}
/* Boot Operating System */ /* Boot Operating System */
return BootProtocol->BootSystem(&BootParameters); return BootProtocol->BootSystem(&BootParameters);
} }