[BOOTMGFW]

- Define some core boot library structures -- reverse engineered to be compatible with MS. This is important if we want to load MS' own binaries for testing (such as MemTest.Efi)
- Define basic BCD structures
- Start implementing EFI->Windows Boot Library conversion routines. Last part remaining is EFI path conversion.
- Fix linking with RTL, by providing some stubs for now.

svn path=/trunk/; revision=69033
This commit is contained in:
Alex Ionescu 2015-09-05 16:05:20 +00:00
parent 4365775be6
commit 66cb7118b2
7 changed files with 992 additions and 12 deletions

View file

@ -10,6 +10,7 @@ add_definitions(-D_NTHAL_ -D_BLDR_ -D_NTSYSTEM_)
list(APPEND BOOTMGR_COMMON_SOURCE
app/bootmgr/bootmgr.h
lib/bootlib.c
lib/misc/bcd.c
lib/misc/util.c)
if(ARCH STREQUAL "i386")
@ -38,6 +39,7 @@ add_dependencies(bootmgr_common bugcodes)
list(APPEND BOOTMGR_BASE_SOURCE
app/bootmgr/efiemu.c
app/bootmgr/bootmgr.c
app/bootmgr/rtlcompat.c
)
add_executable(bootmgfw ${BOOTMGR_BASE_SOURCE})

View file

@ -9,9 +9,311 @@
/* INCLUDES ******************************************************************/
#include "bootmgr.h"
#include <bcd.h>
/* DATA STRUCTURES ***********************************************************/
typedef struct _BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH
{
BOOT_APPLICATION_PARAMETER_BLOCK;
BL_MEMORY_DATA BootMemoryData;
BL_MEMORY_DESCRIPTOR MemEntry;
UCHAR AppEntry[788];
} BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH;
/* DATA VARIABLES ************************************************************/
ULONG BlpApplicationFlags;
GUID EfiLoadedImageProtocol = EFI_LOADED_IMAGE_PROTOCOL_GUID;
GUID EfiDevicePathProtocol = EFI_DEVICE_PATH_PROTOCOL_GUID;
BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH EfiInitScratch;
/* FUNCTIONS *****************************************************************/
NTSTATUS
AhCreateLoadOptionsList (
_In_ PWCHAR CommandLine,
_In_ PBOOT_ENTRY_OPTION BootOptions,
_In_ ULONG MaximumLength,
_Out_ PULONG OptionSize,
_In_ PBOOT_ENTRY_OPTION* PreviousOption,
_In_ PULONG PreviousOptionSize
)
{
return STATUS_NOT_IMPLEMENTED;
}
NTSTATUS
EfiInitpConvertEfiFilePath (
_In_ EFI_DEVICE_PATH_PROTOCOL *FilePath,
_In_ ULONG PathType,
_In_ PBOOT_ENTRY_OPTION Option,
_In_ ULONG MaximumLength
)
{
return STATUS_NOT_IMPLEMENTED;
}
NTSTATUS
EfiInitpConvertEfiDevicePath (
_In_ EFI_DEVICE_PATH_PROTOCOL *DevicePath,
_In_ ULONG DeviceType,
_In_ PBOOT_ENTRY_OPTION Option,
_In_ ULONG MaximumLength
)
{
return STATUS_NOT_IMPLEMENTED;
}
VOID
EfiInitpCreateApplicationEntry (
__in EFI_SYSTEM_TABLE *SystemTable,
__in PBL_APPLICATION_ENTRY Entry,
__in ULONG MaximumLength,
__in EFI_DEVICE_PATH *DevicePath,
__in EFI_DEVICE_PATH *FilePath,
__in PWCHAR LoadOptions,
__in ULONG LoadOptionsSize,
__in ULONG Flags,
__out PULONG ResultLength,
__out PBL_DEVICE_DESCRIPTOR *AppEntryDevice
)
{
PBL_WINDOWS_LOAD_OPTIONS WindowsOptions;
PWCHAR ObjectString, CommandLine;
PBOOT_ENTRY_OPTION Option, PreviousOption;
ULONG HeaderSize, TotalOptionSize, Size, CommandLineSize, RemainingSize;
NTSTATUS Status;
UNICODE_STRING GuidString;
GUID ObjectGuid;
PBCDE_DEVICE BcdDevice;
BOOLEAN HaveBinaryOptions, HaveGuid;
PBL_FILE_PATH_DESCRIPTOR OsPath;
EFI_DEVICE_PATH *OsDevicePath;
/* Initialize everything */
TotalOptionSize = 0;
*AppEntryDevice = NULL;
HeaderSize = 0;
/* Check if the load options are in binary Windows format */
WindowsOptions = (PBL_WINDOWS_LOAD_OPTIONS)LoadOptions;
if ((WindowsOptions != NULL) &&
(LoadOptionsSize >= sizeof(BL_WINDOWS_LOAD_OPTIONS)) &&
(WindowsOptions->Length >= sizeof(BL_WINDOWS_LOAD_OPTIONS)) &&
!(strncmp(WindowsOptions->Signature, "WINDOWS", 7)))
{
/* They are, so firmware must have loaded us -- extract arguments */
CommandLine = WindowsOptions->LoadOptions;
CommandLineSize = LoadOptionsSize - FIELD_OFFSET(BL_WINDOWS_LOAD_OPTIONS,
LoadOptions);
/* Remember that we used binary options */
HaveBinaryOptions = TRUE;
}
else
{
/* Nope -- so treat them as raw command-line options */
CommandLine = LoadOptions;
CommandLineSize = LoadOptionsSize;
/* No binary options */
HaveBinaryOptions = FALSE;
}
/* EFI uses UTF-16LE, like NT, so convert to characters */
CommandLineSize /= sizeof(WCHAR);
if (CommandLineSize != 0)
{
/* And check if the options are not NULL-terminated */
if (wcsnlen(CommandLine, CommandLineSize) == CommandLineSize)
{
/* NULL-terminate them */
CommandLine[CommandLineSize - 1] = UNICODE_NULL;
}
}
/* Begin by making sure we at least have space for the app entry header */
RemainingSize = MaximumLength;
if (RemainingSize < sizeof(BL_APPLICATION_ENTRY))
{
Status = STATUS_INVALID_PARAMETER;
goto Quickie;
}
/* On exit, return that we've at least consumed this much */
HeaderSize = FIELD_OFFSET(BL_APPLICATION_ENTRY, BcdData);
/* Zero out the header, and write down the signature */
RtlZeroMemory(Entry, sizeof(BL_APPLICATION_ENTRY));
RtlCopyMemory(Entry->Signature, "BTAPENT", 7);
/* Check if a BCD object was passed on the command-line */
ObjectString = wcsstr(CommandLine, L"BCDOBJECT=");
if (ObjectString != NULL)
{
/* Convert the BCD object to a GUID */
RtlInitUnicodeString(&GuidString, ObjectString + 10);
RtlGUIDFromString(&GuidString, &ObjectGuid);
/* Store it in the application entry */
Entry->Guid = ObjectGuid;
/* Remember one was passed */
HaveGuid = TRUE;
}
else
{
/* Remember that no identifier was passed */
Entry->Flags |= BL_APPLICATION_ENTRY_FLAG_NO_GUID;
HaveGuid = FALSE;
}
/* At this point, the header is consumed, and we must now handle BCD options */
RemainingSize -= FIELD_OFFSET(BL_APPLICATION_ENTRY, BcdData);
/* Convert the device path into a BCD option */
Status = EfiInitpConvertEfiDevicePath(DevicePath,
BcdLibraryDevice_ApplicationDevice,
&Entry->BcdData,
RemainingSize);
if (!NT_SUCCESS(Status))
{
/* We failed, so mark the option as such and return an empty one */
Entry->BcdData.Failed = TRUE;
TotalOptionSize = sizeof(BOOT_ENTRY_OPTION);
goto Quickie;
}
/* Extract the device descriptor and return it */
BcdDevice = (PVOID)((ULONG_PTR)&Entry->BcdData + Entry->BcdData.DataOffset);
*AppEntryDevice = &BcdDevice->Device;
/* Calculate how big this option was and consume that from the buffer */
TotalOptionSize = BlGetBootOptionSize(&Entry->BcdData);
RemainingSize -= TotalOptionSize;
/* Calculate where the next option should go */
Option = (PVOID)((ULONG_PTR)&Entry->BcdData + TotalOptionSize);
/* Check if we're PXE booting or not */
if ((*AppEntryDevice)->DeviceType == UdpDevice)
{
/* lol */
Status = STATUS_NOT_IMPLEMENTED;
}
else
{
/* Convert the local file path into a BCD option */
Status = EfiInitpConvertEfiFilePath(FilePath,
BcdLibraryString_ApplicationPath,
Option,
RemainingSize);
}
/* Bail out on failure */
if (!NT_SUCCESS(Status))
{
goto Quickie;
}
/* The next option is right after this one */
Entry->BcdData.NextEntryOffset = TotalOptionSize;
/* Now compute the size of the next option, and add to the rolling sum */
Size = BlGetBootOptionSize(Option);
TotalOptionSize += Size;
/* Remember the previous option so we can update its next offset */
PreviousOption = Option;
/* Consume the option from the buffer */
RemainingSize -= Size;
/* Calculate where the next option should go */
Option = (PVOID)((ULONG_PTR)Option + Size);
/* Check if we were using binary options without a BCD GUID */
if ((HaveBinaryOptions) && !(HaveGuid))
{
/* Then this means we have to convert the OS paths to BCD too */
WindowsOptions = (PBL_WINDOWS_LOAD_OPTIONS)LoadOptions;
OsPath = (PVOID)((ULONG_PTR)WindowsOptions + WindowsOptions->OsPathOffset);
/* IS the OS path in EFI format? */
if ((OsPath->Length > FIELD_OFFSET(BL_FILE_PATH_DESCRIPTOR, Path)) &&
(OsPath->PathType == EfiPath))
{
/* Convert the device portion */
OsDevicePath = (EFI_DEVICE_PATH*)OsPath->Path;
Status = EfiInitpConvertEfiDevicePath(OsDevicePath,
BcdOSLoaderDevice_OSDevice,
Option,
RemainingSize);
if (!NT_SUCCESS(Status))
{
goto Quickie;
}
/* Update the offset of the previous option */
PreviousOption->NextEntryOffset = (ULONG_PTR)Option - (ULONG_PTR)&Entry->BcdData;
/* Now compute the size of the next option, and add to the rolling sum */
Size = BlGetBootOptionSize(Option);
TotalOptionSize += Size;
/* Remember the previous option so we can update its next offset */
PreviousOption = Option;
/* Consume the option from the buffer */
RemainingSize -= Size;
/* Calculate where the next option should go */
Option = (PVOID)((ULONG_PTR)Option + Size);
/* Convert the path oprtion */
Status = EfiInitpConvertEfiFilePath(OsDevicePath,
BcdOSLoaderString_SystemRoot,
Option,
RemainingSize);
if (!NT_SUCCESS(Status))
{
goto Quickie;
}
/* Update the offset of the previous option */
PreviousOption->NextEntryOffset = (ULONG_PTR)Option - (ULONG_PTR)&Entry->BcdData;
/* Now compute the size of the next option, and add to the rolling sum */
Size = BlGetBootOptionSize(Option);
TotalOptionSize += Size;
/* Remember the previous option so we can update its next offset */
PreviousOption = Option;
/* Consume the option from the buffer */
RemainingSize -= Size;
/* Calculate where the next option should go */
Option = (PVOID)((ULONG_PTR)Option + Size);
}
}
/* Now convert everything else */
AhCreateLoadOptionsList(CommandLine,
&Entry->BcdData,
RemainingSize,
&TotalOptionSize,
&PreviousOption,
&Size);
Quickie:
/* Return the final size */
*ResultLength = HeaderSize + TotalOptionSize;
}
/*++
* @name EfiInitCreateInputParametersEx
*
@ -34,11 +336,134 @@ EfiInitCreateInputParametersEx (
_In_ EFI_SYSTEM_TABLE *SystemTable
)
{
DBG_UNREFERENCED_PARAMETER(ImageHandle);
DBG_UNREFERENCED_PARAMETER(SystemTable);
EFI_BOOT_SERVICES* BootServices;
EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
PBL_FIRMWARE_DESCRIPTOR FirmwareData;
PBL_RETURN_ARGUMENTS ReturnArguments;
ULONG FirmwareOffset, ConsumedSize;
PBL_DEVICE_DESCRIPTOR AppDevice;
EFI_STATUS Status;
/* Not yet implemented */
return NULL;
/* Initialize the header with the signature and version */
EfiInitScratch.Signature[0] = BOOT_APPLICATION_SIGNATURE_1;
EfiInitScratch.Signature[1] = BOOT_APPLICATION_SIGNATURE_2;
EfiInitScratch.Version = BOOT_APPLICATION_VERSION;
/* Set the image type to x86 */
EfiInitScratch.ImageType = EFI_IMAGE_MACHINE_IA32;
/* Set the translation type to physical */
EfiInitScratch.MemoryTranslationType = BOOT_MEMORY_TRANSLATION_TYPE_PHYSICAL;
/* Indicate that the data was converted from EFI */
BlpApplicationFlags |= BL_APPLICATION_FLAG_CONVERTED_FROM_EFI;
/* Grab the loaded image protocol, which has our base and size */
BootServices = SystemTable->BootServices;
Status = BootServices->HandleProtocol(ImageHandle,
&EfiLoadedImageProtocol,
(VOID**)&LoadedImage);
if (Status != EFI_SUCCESS)
{
SystemTable->ConOut->OutputString(SystemTable->ConsoleOutHandle,
L"Loaded image failed\n");
return NULL;
}
/* Capture it in the boot application parameters */
EfiInitScratch.ImageBase = (ULONG_PTR)LoadedImage->ImageBase;
EfiInitScratch.ImageSize = (ULONG)LoadedImage->ImageSize;
/* Now grab our device path protocol, so we can convert the path later on */
Status = BootServices->HandleProtocol(ImageHandle,
&EfiDevicePathProtocol,
(VOID**)&DevicePath);
if (Status != EFI_SUCCESS)
{
SystemTable->ConOut->OutputString(SystemTable->ConsoleOutHandle,
L"Device path failed\n");
return NULL;
}
/* The built-in boot memory data comes right after our block */
EfiInitScratch.MemoryDataOffset =
FIELD_OFFSET(BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH, BootMemoryData);
/* Build the boot memory data structure, with 1 descriptor */
EfiInitScratch.BootMemoryData.Version = BL_MEMORY_DATA_VERSION;
EfiInitScratch.BootMemoryData.MdListOffset =
FIELD_OFFSET(BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH, MemEntry) -
EfiInitScratch.MemoryDataOffset;
EfiInitScratch.BootMemoryData.DescriptorSize = sizeof(BL_MEMORY_DESCRIPTOR);
EfiInitScratch.BootMemoryData.DescriptorCount = 1;
EfiInitScratch.BootMemoryData.Unknown = 8;
/* Build the memory entry descriptor for this image itself */
EfiInitScratch.MemEntry.Flags = 8;
EfiInitScratch.MemEntry.Type = BlLoaderMemory;
EfiInitScratch.MemEntry.BasePage = EfiInitScratch.ImageBase >> PAGE_SHIFT;
EfiInitScratch.MemEntry.PageCount = ALIGN_UP_BY(EfiInitScratch.ImageSize, PAGE_SIZE) >> PAGE_SHIFT;
/* The built-in application entry comes right after the memory descriptor*/
EfiInitScratch.AppEntryOffset =
FIELD_OFFSET(BOOT_APPLICATION_PARAMETER_BLOCK_SCRATCH, AppEntry);
/* Go and build it */
EfiInitpCreateApplicationEntry(SystemTable,
(PBL_APPLICATION_ENTRY)&EfiInitScratch.AppEntry,
sizeof(EfiInitScratch.AppEntry),
DevicePath,
LoadedImage->FilePath,
LoadedImage->LoadOptions,
LoadedImage->LoadOptionsSize,
EfiInitScratch.MemEntry.PageCount,
&ConsumedSize,
&AppDevice);
/* Boot device information comes right after the application entry */
EfiInitScratch.BootDeviceOffset = ConsumedSize + EfiInitScratch.AppEntryOffset;
/* Check if we have a boot device */
if (AppDevice != NULL)
{
/* We do -- copy it */
RtlCopyMemory(EfiInitScratch.AppEntry + ConsumedSize,
AppDevice,
AppDevice->Size);
/* Firmware data follows right after the boot device entry */
FirmwareOffset = AppDevice->Size + EfiInitScratch.BootDeviceOffset;
}
else
{
/* We do not, so zero out the space where a full boot device structure would fit */
RtlZeroMemory(EfiInitScratch.AppEntry + ConsumedSize,
sizeof(BL_DEVICE_DESCRIPTOR));
/* And start the firmware data past that */
FirmwareOffset = EfiInitScratch.BootDeviceOffset + sizeof(BL_DEVICE_DESCRIPTOR);
}
/* Set the computed firmware data offset */
EfiInitScratch.FirmwareParametersOffset = FirmwareOffset;
/* Fill out the firmware data that's there */
FirmwareData = (PVOID)((ULONG_PTR)&EfiInitScratch + EfiInitScratch.FirmwareParametersOffset);
FirmwareData->Version = BL_FIRMWARE_DESCRIPTOR_VERSION;
FirmwareData->ImageHandle = ImageHandle;
FirmwareData->SystemTable = SystemTable;
/* Finally, set the return argument offset */
EfiInitScratch.ReturnArgumentsOffset = FirmwareOffset + sizeof(BL_FIRMWARE_DESCRIPTOR);
/* And fill out the return argument data */
ReturnArguments = (PVOID)((ULONG_PTR)&EfiInitScratch + EfiInitScratch.ReturnArgumentsOffset);
ReturnArguments->Version = BL_RETURN_ARGUMENTS_VERSION;
/* We're done, compute the final size and return the block */
EfiInitScratch.Size = EfiInitScratch.ReturnArgumentsOffset + sizeof(BL_RETURN_ARGUMENTS);
return (PBOOT_APPLICATION_PARAMETER_BLOCK)&EfiInitScratch;
}
/*++

View file

@ -0,0 +1,77 @@
/*
* COPYRIGHT: See COPYING.ARM in the top level directory
* PROJECT: ReactOS UEFI Boot Manager
* FILE: boot/environ/app/rtlcompat.c
* PURPOSE: RTL Library Compatibility Routines
* PROGRAMMER: Alex Ionescu (alex.ionescu@reactos.org)
*/
/* INCLUDES ******************************************************************/
#include "bootmgr.h"
/* FUNCTIONS *****************************************************************/
#if DBG
VOID FASTCALL
CHECK_PAGED_CODE_RTL (
char *file,
int line
)
{
// boot-code is always ok
}
#endif
PVOID
NTAPI
RtlpAllocateMemory (
_In_ ULONG Bytes,
_In_ ULONG Tag
)
{
return NULL;
}
VOID
NTAPI
RtlpFreeMemory (
_In_ PVOID Mem,
_In_ ULONG Tag
)
{
return;
}
NTSTATUS
NTAPI
RtlpSafeCopyMemory (
_Out_writes_bytes_all_(Length) VOID UNALIGNED *Destination,
_In_reads_bytes_(Length) CONST VOID UNALIGNED *Source,
_In_ SIZE_T Length
)
{
RtlCopyMemory(Destination, Source, Length);
return STATUS_SUCCESS;
}
VOID
NTAPI
RtlAssert (
IN PVOID FailedAssertion,
IN PVOID FileName,
IN ULONG LineNumber,
IN PCHAR Message OPTIONAL
)
{
}
ULONG
DbgPrint (
const char *Format,
...
)
{
return 0;
}

View file

@ -0,0 +1,153 @@
/*
* COPYRIGHT: See COPYING.ARM in the top level directory
* PROJECT: ReactOS Boot Configuration Data
* FILE: boot/environ/include/bcd.h
* PURPOSE: BCD Main Header
* PROGRAMMER: Alex Ionescu (alex.ionescu@reactos.org)
*/
#ifndef _BCD_H
#define _BCD_H
/* ENUMERATIONS **************************************************************/
typedef enum BcdLibraryElementTypes
{
BcdLibraryDevice_ApplicationDevice = 0x11000001,
BcdLibraryString_ApplicationPath = 0x12000002,
BcdLibraryString_Description = 0x12000004,
BcdLibraryString_PreferredLocale = 0x12000005,
BcdLibraryObjectList_InheritedObjects = 0x14000006,
BcdLibraryInteger_TruncatePhysicalMemory = 0x15000007,
BcdLibraryObjectList_RecoverySequence = 0x14000008,
BcdLibraryBoolean_AutoRecoveryEnabled = 0x16000009,
BcdLibraryIntegerList_BadMemoryList = 0x1700000a,
BcdLibraryBoolean_AllowBadMemoryAccess = 0x1600000b,
BcdLibraryInteger_FirstMegabytePolicy = 0x1500000c,
BcdLibraryInteger_RelocatePhysicalMemory = 0x1500000D,
BcdLibraryInteger_AvoidLowPhysicalMemory = 0x1500000E,
BcdLibraryBoolean_DebuggerEnabled = 0x16000010,
BcdLibraryInteger_DebuggerType = 0x15000011,
BcdLibraryInteger_SerialDebuggerPortAddress = 0x15000012,
BcdLibraryInteger_SerialDebuggerPort = 0x15000013,
BcdLibraryInteger_SerialDebuggerBaudRate = 0x15000014,
BcdLibraryInteger_1394DebuggerChannel = 0x15000015,
BcdLibraryString_UsbDebuggerTargetName = 0x12000016,
BcdLibraryBoolean_DebuggerIgnoreUsermodeExceptions = 0x16000017,
BcdLibraryInteger_DebuggerStartPolicy = 0x15000018,
BcdLibraryString_DebuggerBusParameters = 0x12000019,
BcdLibraryInteger_DebuggerNetHostIP = 0x1500001A,
BcdLibraryInteger_DebuggerNetPort = 0x1500001B,
BcdLibraryBoolean_DebuggerNetDhcp = 0x1600001C,
BcdLibraryString_DebuggerNetKey = 0x1200001D,
BcdLibraryBoolean_EmsEnabled = 0x16000020,
BcdLibraryInteger_EmsPort = 0x15000022,
BcdLibraryInteger_EmsBaudRate = 0x15000023,
BcdLibraryString_LoadOptionsString = 0x12000030,
BcdLibraryBoolean_DisplayAdvancedOptions = 0x16000040,
BcdLibraryBoolean_DisplayOptionsEdit = 0x16000041,
BcdLibraryDevice_BsdLogDevice = 0x11000043,
BcdLibraryString_BsdLogPath = 0x12000044,
BcdLibraryBoolean_GraphicsModeDisabled = 0x16000046,
BcdLibraryInteger_ConfigAccessPolicy = 0x15000047,
BcdLibraryBoolean_DisableIntegrityChecks = 0x16000048,
BcdLibraryBoolean_AllowPrereleaseSignatures = 0x16000049,
BcdLibraryString_FontPath = 0x1200004A,
BcdLibraryInteger_SiPolicy = 0x1500004B,
BcdLibraryInteger_FveBandId = 0x1500004C,
BcdLibraryBoolean_ConsoleExtendedInput = 0x16000050,
BcdLibraryInteger_GraphicsResolution = 0x15000052,
BcdLibraryBoolean_RestartOnFailure = 0x16000053,
BcdLibraryBoolean_GraphicsForceHighestMode = 0x16000054,
BcdLibraryBoolean_IsolatedExecutionContext = 0x16000060,
BcdLibraryBoolean_BootUxDisable = 0x1600006C,
BcdLibraryBoolean_BootShutdownDisabled = 0x16000074,
BcdLibraryIntegerList_AllowedInMemorySettings = 0x17000077,
BcdLibraryBoolean_ForceFipsCrypto = 0x16000079
} BcdLibraryElementTypes;
typedef enum BcdOSLoaderElementTypes
{
BcdOSLoaderDevice_OSDevice = 0x21000001,
BcdOSLoaderString_SystemRoot = 0x22000002,
BcdOSLoaderObject_AssociatedResumeObject = 0x23000003,
BcdOSLoaderBoolean_DetectKernelAndHal = 0x26000010,
BcdOSLoaderString_KernelPath = 0x22000011,
BcdOSLoaderString_HalPath = 0x22000012,
BcdOSLoaderString_DbgTransportPath = 0x22000013,
BcdOSLoaderInteger_NxPolicy = 0x25000020,
BcdOSLoaderInteger_PAEPolicy = 0x25000021,
BcdOSLoaderBoolean_WinPEMode = 0x26000022,
BcdOSLoaderBoolean_DisableCrashAutoReboot = 0x26000024,
BcdOSLoaderBoolean_UseLastGoodSettings = 0x26000025,
BcdOSLoaderBoolean_AllowPrereleaseSignatures = 0x26000027,
BcdOSLoaderBoolean_NoLowMemory = 0x26000030,
BcdOSLoaderInteger_RemoveMemory = 0x25000031,
BcdOSLoaderInteger_IncreaseUserVa = 0x25000032,
BcdOSLoaderBoolean_UseVgaDriver = 0x26000040,
BcdOSLoaderBoolean_DisableBootDisplay = 0x26000041,
BcdOSLoaderBoolean_DisableVesaBios = 0x26000042,
BcdOSLoaderBoolean_DisableVgaMode = 0x26000043,
BcdOSLoaderInteger_ClusterModeAddressing = 0x25000050,
BcdOSLoaderBoolean_UsePhysicalDestination = 0x26000051,
BcdOSLoaderInteger_RestrictApicCluster = 0x25000052,
BcdOSLoaderBoolean_UseLegacyApicMode = 0x26000054,
BcdOSLoaderInteger_X2ApicPolicy = 0x25000055,
BcdOSLoaderBoolean_UseBootProcessorOnly = 0x26000060,
BcdOSLoaderInteger_NumberOfProcessors = 0x25000061,
BcdOSLoaderBoolean_ForceMaximumProcessors = 0x26000062,
BcdOSLoaderBoolean_ProcessorConfigurationFlags = 0x25000063,
BcdOSLoaderBoolean_MaximizeGroupsCreated = 0x26000064,
BcdOSLoaderBoolean_ForceGroupAwareness = 0x26000065,
BcdOSLoaderInteger_GroupSize = 0x25000066,
BcdOSLoaderInteger_UseFirmwarePciSettings = 0x26000070,
BcdOSLoaderInteger_MsiPolicy = 0x25000071,
BcdOSLoaderInteger_SafeBoot = 0x25000080,
BcdOSLoaderBoolean_SafeBootAlternateShell = 0x26000081,
BcdOSLoaderBoolean_BootLogInitialization = 0x26000090,
BcdOSLoaderBoolean_VerboseObjectLoadMode = 0x26000091,
BcdOSLoaderBoolean_KernelDebuggerEnabled = 0x260000a0,
BcdOSLoaderBoolean_DebuggerHalBreakpoint = 0x260000a1,
BcdOSLoaderBoolean_UsePlatformClock = 0x260000A2,
BcdOSLoaderBoolean_ForceLegacyPlatform = 0x260000A3,
BcdOSLoaderInteger_TscSyncPolicy = 0x250000A6,
BcdOSLoaderBoolean_EmsEnabled = 0x260000b0,
BcdOSLoaderInteger_DriverLoadFailurePolicy = 0x250000c1,
BcdOSLoaderInteger_BootMenuPolicy = 0x250000C2,
BcdOSLoaderBoolean_AdvancedOptionsOneTime = 0x260000C3,
BcdOSLoaderInteger_BootStatusPolicy = 0x250000E0,
BcdOSLoaderBoolean_DisableElamDrivers = 0x260000E1,
BcdOSLoaderInteger_HypervisorLaunchType = 0x250000F0,
BcdOSLoaderBoolean_HypervisorDebuggerEnabled = 0x260000F2,
BcdOSLoaderInteger_HypervisorDebuggerType = 0x250000F3,
BcdOSLoaderInteger_HypervisorDebuggerPortNumber = 0x250000F4,
BcdOSLoaderInteger_HypervisorDebuggerBaudrate = 0x250000F5,
BcdOSLoaderInteger_HypervisorDebugger1394Channel = 0x250000F6,
BcdOSLoaderInteger_BootUxPolicy = 0x250000F7,
BcdOSLoaderString_HypervisorDebuggerBusParams = 0x220000F9,
BcdOSLoaderInteger_HypervisorNumProc = 0x250000FA,
BcdOSLoaderInteger_HypervisorRootProcPerNode = 0x250000FB,
BcdOSLoaderBoolean_HypervisorUseLargeVTlb = 0x260000FC,
BcdOSLoaderInteger_HypervisorDebuggerNetHostIp = 0x250000FD,
BcdOSLoaderInteger_HypervisorDebuggerNetHostPort = 0x250000FE,
BcdOSLoaderInteger_TpmBootEntropyPolicy = 0x25000100,
BcdOSLoaderString_HypervisorDebuggerNetKey = 0x22000110,
BcdOSLoaderBoolean_HypervisorDebuggerNetDhcp = 0x26000114,
BcdOSLoaderInteger_HypervisorIommuPolicy = 0x25000115,
BcdOSLoaderInteger_XSaveDisable = 0x2500012b
} BcdOSLoaderElementTypes;
/* DATA STRUCTURES ***********************************************************/
typedef struct _BCDE_DEVICE
{
GUID AdditionalOptions;
BL_DEVICE_DESCRIPTOR Device;
} BCDE_DEVICE, *PBCDE_DEVICE;
typedef struct _BCDE_STRING
{
WCHAR String[ANYSIZE_ARRAY];
} BCDE_STRING, *PBCDE_STRING;
#endif

View file

@ -21,6 +21,88 @@
/* UEFI Headers */
#include <Uefi.h>
#include <DevicePath.h>
#include <LoadedImage.h>
/* DEFINES *******************************************************************/
#define BL_APPLICATION_FLAG_CONVERTED_FROM_EFI 0x01
#define BOOT_APPLICATION_SIGNATURE_1 'TOOB'
#define BOOT_APPLICATION_SIGNATURE_2 ' PPA'
#define BOOT_MEMORY_TRANSLATION_TYPE_PHYSICAL 0
#define BOOT_MEMORY_TRANSLATION_TYPE_VIRTUAL 1
#define BOOT_APPLICATION_VERSION 2
#define BL_MEMORY_DATA_VERSION 1
#define BL_RETURN_ARGUMENTS_VERSION 1
#define BL_FIRMWARE_DESCRIPTOR_VERSION 2
#define BL_APPLICATION_ENTRY_FLAG_NO_GUID 0x01
/* ENUMERATIONS **************************************************************/
//
// Boot Device Types
//
typedef enum _BL_DEVICE_TYPE
{
UdpDevice = 4
} BL_DEVICE_TYPE;
//
// File Path Types
//
typedef enum _BL_PATH_TYPE
{
EfiPath = 4
} BL_PATH_TYPE;
//
// Classes of Memory
//
typedef enum _BL_MEMORY_CLASS
{
BlLoaderClass = 0xD,
BlApplicationClass,
BlSystemClass
} BL_MEMORY_CLASS;
//
// Types of Memory
//
typedef enum _BL_MEMORY_TYPE
{
//
// Loader Memory
//
BlLoaderMemory = 0xD0000002,
BlLoaderPageDirectory = 0xD0000006,
BlLoaderReferencePage = 0xD0000007,
BlLoaderRamDisk = 0xD0000008,
BlLoaderData = 0xD000000A,
BlLoaderSelfMap = 0xD000000F,
//
// Application Memory
//
BlApplicationData = 0xE0000004,
//
// System Memory
//
BlConventionalMemory = 0xF0000001,
BlUnusableMemory = 0xF0000002,
BlReservedMemory = 0xF0000003,
BlEfiBootMemory = 0xF0000004,
BlEfiRuntimeMemory = 0xF0000006,
BlAcpiReclaimMemory = 0xF0000008,
BlAcpiNvsMemory = 0xF0000009,
BlDeviceIoMemory = 0xF000000A,
BlDevicePortMemory = 0xF000000B,
BlPalMemory = 0xF000000C,
} BL_MEMORY_TYPE;
/* DATA STRUCTURES ***********************************************************/
@ -38,20 +120,185 @@ typedef struct _BL_LIBRARY_PARAMETERS
/* This should eventually go into a more public header */
typedef struct _BOOT_APPLICATION_PARAMETER_BLOCK
{
/* This header tells the library what image we're dealing with */
ULONG Signature[2];
ULONG Version;
ULONG Size;
ULONG ImageType;
ULONG MemoryTranslationType;
/* Where is the image located */
ULONGLONG ImageBase;
ULONG ImageSize;
ULONG MemorySettingsOffset;
/* Offset to BL_MEMORY_DATA */
ULONG MemoryDataOffset;
/* Offset to BL_APPLICATION_ENTRY */
ULONG AppEntryOffset;
/* Offset to BL_DEVICE_DESCRPIPTOR */
ULONG BootDeviceOffset;
/* Offset to BL_FIRMWARE_PARAMETERS */
ULONG FirmwareParametersOffset;
ULONG FlagOffset;
/* Offset to BL_RETURN_ARGUMENTS */
ULONG ReturnArgumentsOffset;
} BOOT_APPLICATION_PARAMETER_BLOCK, *PBOOT_APPLICATION_PARAMETER_BLOCK;
typedef struct _BL_MEMORY_DATA
{
ULONG Version;
ULONG MdListOffset;
ULONG DescriptorCount;
ULONG DescriptorSize;
ULONG Unknown;
} BL_MEMORY_DATA, *PBL_MEMORY_DATA;
typedef struct _BL_FIRMWARE_DESCRIPTOR
{
ULONG Version;
ULONG Unknown;
EFI_HANDLE ImageHandle;
EFI_SYSTEM_TABLE *SystemTable;
} BL_FIRMWARE_DESCRIPTOR, *PBL_FIRMWARE_DESCRIPTOR;
typedef struct _BL_RETURN_ARGUMENTS
{
ULONG Version;
ULONG ReturnArgumentData[6];
} BL_RETURN_ARGUMENTS, *PBL_RETURN_ARGUMENTS;
typedef struct _BL_MEMORY_DESCRIPTOR
{
LIST_ENTRY ListEntry;
union
{
struct
{
ULONGLONG BasePage;
ULONGLONG VirtualPage;
};
struct
{
ULONGLONG BaseAddress;
ULONGLONG VirtualAddress;
};
};
ULONGLONG PageCount;
ULONG Flags;
BL_MEMORY_TYPE Type;
} BL_MEMORY_DESCRIPTOR, *PBL_MEMORY_DESCRIPTOR;
typedef struct _BOOT_ENTRY_OPTION
{
ULONG Type;
ULONG DataOffset;
ULONG DataSize;
ULONG ListOffset;
ULONG NextEntryOffset;
ULONG Failed;
} BOOT_ENTRY_OPTION, *PBOOT_ENTRY_OPTION;
typedef struct _BL_APPLICATION_ENTRY
{
CHAR Signature[8];
ULONG Flags;
GUID Guid;
ULONG Unknown[4];
BOOT_ENTRY_OPTION BcdData;
} BL_APPLICATION_ENTRY, *PBL_APPLICATION_ENTRY;
typedef struct _BL_HARDDISK_DEVICE
{
ULONG PartitionType;
union
{
struct
{
ULONG PartitionSignature;
} Mbr;
struct
{
GUID PartitionSignature;
} Gpt;
struct
{
ULONG DiskNumber;
} Raw;
};
} BL_HARDDISK_DEVICE;
typedef struct _BL_LOCAL_DEVICE
{
ULONG Type;
union
{
struct
{
ULONG DriveNumber;
} FloppyDisk;
BL_HARDDISK_DEVICE HardDisk;
struct
{
PHYSICAL_ADDRESS ImageBase;
LARGE_INTEGER ImageSize;
ULONG ImageOffset;
} RamDisk;
};
} BL_LOCAL_DEVICE;
typedef struct _BL_DEVICE_DESCRIPTOR
{
ULONG Size;
ULONG Flags;
DEVICE_TYPE DeviceType;
ULONG Unknown;
union
{
BL_LOCAL_DEVICE Local;
struct
{
ULONG Unknown;
} Remote;
struct
{
ULONG PartitionNumber;
BL_LOCAL_DEVICE Disk;
} MbrPartition;
struct
{
GUID PartitionGuid;
BL_LOCAL_DEVICE Disk;
} GptPartition;
};
} BL_DEVICE_DESCRIPTOR, *PBL_DEVICE_DESCRIPTOR;
typedef struct _BL_FILE_PATH_DESCRIPTOR
{
ULONG Version;
ULONG Length;
ULONG PathType;
UCHAR Path[ANYSIZE_ARRAY];
} BL_FILE_PATH_DESCRIPTOR, *PBL_FILE_PATH_DESCRIPTOR;
typedef struct _BL_WINDOWS_LOAD_OPTIONS
{
CHAR Signature[8];
ULONG Version;
ULONG Length;
ULONG OsPathOffset;
WCHAR LoadOptions[ANYSIZE_ARRAY];
} BL_WINDOWS_LOAD_OPTIONS, *PBL_WINDOWS_LOAD_OPTIONS;
/* INITIALIZATION ROUTINES ***************************************************/
NTSTATUS
@ -67,4 +314,11 @@ EfiGetEfiStatusCode(
_In_ NTSTATUS Status
);
/* BCD ROUTINES **************************************************************/
ULONG
BlGetBootOptionSize (
_In_ PBOOT_ENTRY_OPTION BcdOption
);
#endif

View file

@ -0,0 +1,69 @@
/*
* COPYRIGHT: See COPYING.ARM in the top level directory
* PROJECT: ReactOS UEFI Boot Library
* FILE: boot/environ/lib/misc/bcd.c
* PURPOSE: Boot Library BCD Routines
* PROGRAMMER: Alex Ionescu (alex.ionescu@reactos.org)
*/
/* INCLUDES ******************************************************************/
#include "bl.h"
/* FUNCTIONS *****************************************************************/
ULONG
BlGetBootOptionListSize (
_In_ PBOOT_ENTRY_OPTION BcdOption
)
{
ULONG Size = 0, NextOffset = 0;
PBOOT_ENTRY_OPTION NextOption;
/* Loop all the options*/
do
{
/* Move to the next one */
NextOption = (PBOOT_ENTRY_OPTION)((ULONG_PTR)BcdOption + NextOffset);
/* Compute the size of the next one */
Size += BlGetBootOptionSize(NextOption);
/* Update the offset */
NextOffset = NextOption->NextEntryOffset;
} while (NextOffset != 0);
/* Return final computed size */
return Size;
}
ULONG
BlGetBootOptionSize (
_In_ PBOOT_ENTRY_OPTION BcdOption
)
{
ULONG Size, Offset;
/* Check if there's any data */
if (BcdOption->DataOffset != 0)
{
/* Add the size of the data */
Size = BcdOption->DataOffset + BcdOption->DataSize;
}
else
{
/* No data, just the structure itself */
Size = sizeof(*BcdOption);
}
/* Any associated options? */
Offset = BcdOption->ListOffset;
if (Offset != 0)
{
/* Go get those too */
Size += BlGetBootOptionListSize((PVOID)((ULONG_PTR)BcdOption + Offset));
}
/* Return the final size */
return Size;
}

View file

@ -1,10 +1,10 @@
/*
* COPYRIGHT: See COPYING.ARM in the top level directory
* PROJECT: ReactOS UEFI Boot Library
* FILE: boot/environ/lib/bootlib.c
* PURPOSE: Boot Library Initialization
* PROGRAMMER: Alex Ionescu (alex.ionescu@reactos.org)
*/
* COPYRIGHT: See COPYING.ARM in the top level directory
* PROJECT: ReactOS UEFI Boot Library
* FILE: boot/environ/lib/misc/util.c
* PURPOSE: Boot Library Utility Functions
* PROGRAMMER: Alex Ionescu (alex.ionescu@reactos.org)
*/
/* INCLUDES ******************************************************************/