+++ /dev/null
-/*
- * 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)
- */
-
-/* INCLUDES ******************************************************************/
-
-#include "bl.h"
-
-/* DATA VARIABLES ************************************************************/
-
-BL_LIBRARY_PARAMETERS BlpLibraryParameters;
-PBL_DEVICE_DESCRIPTOR BlpBootDevice;
-PWCHAR BlpApplicationBaseDirectory;
-PBOOT_APPLICATION_PARAMETER_BLOCK BlpApplicationParameters;
-BL_LOADED_APPLICATION_ENTRY BlpApplicationEntry;
-BOOLEAN BlpLibraryParametersInitialized;
-ULONG BlpApplicationFlags;
-
-ULONG PdPersistAllocations;
-LIST_ENTRY BlpPdListHead;
-
-/* FUNCTIONS *****************************************************************/
-
-/*++
- * @name InitializeLibrary
- *
- * The InitializeLibrary function initializes the Boot Library.
- *
- * @param BootParameters
- * Pointer to the Boot Application Parameter Block.
- *
- * @param LibraryParameters
- * Pointer to the Boot Library Parameters.
- *
- * @return NT_SUCCESS if the boot library was loaded correctly, relevant error
- * otherwise.
- *
- *--*/
-NTSTATUS
-InitializeLibrary (
- _In_ PBOOT_APPLICATION_PARAMETER_BLOCK BootAppParameters,
- _In_ PBL_LIBRARY_PARAMETERS LibraryParameters
- )
-{
- NTSTATUS Status;
- PBL_MEMORY_DATA MemoryData;
- PBL_APPLICATION_ENTRY AppEntry;
- PBL_FIRMWARE_DESCRIPTOR FirmwareDescriptor;
- LARGE_INTEGER BootFrequency;
- ULONG_PTR ParamPointer;
-
- /* Validate correct Boot Application data */
- ParamPointer = (ULONG_PTR)BootAppParameters;
- if (!(BootAppParameters) ||
- (BootAppParameters->Signature[0] != BOOT_APPLICATION_SIGNATURE_1) ||
- (BootAppParameters->Signature[1] != BOOT_APPLICATION_SIGNATURE_2) ||
- (BootAppParameters->Size < sizeof(*BootAppParameters)))
- {
- Status = STATUS_INVALID_PARAMETER;
- goto Quickie;
- }
-
- /* Get sub-structures */
- MemoryData = (PBL_MEMORY_DATA)(ParamPointer + BootAppParameters->MemoryDataOffset);
- FirmwareDescriptor = (PBL_FIRMWARE_DESCRIPTOR)(ParamPointer + BootAppParameters->FirmwareParametersOffset);
- AppEntry = (PBL_APPLICATION_ENTRY)(ParamPointer + BootAppParameters->AppEntryOffset);
- BlpBootDevice = (PBL_DEVICE_DESCRIPTOR)(ParamPointer + BootAppParameters->BootDeviceOffset);
- BlpApplicationBaseDirectory = LibraryParameters->ApplicationBaseDirectory;
-
- /* Initialize the firmware table */
- Status = BlpFwInitialize(0, FirmwareDescriptor);
- if (!NT_SUCCESS(Status))
- {
- goto Quickie;
- }
-
- /* Find boot application entry */
- if (strncmp(AppEntry->Signature, BL_APP_ENTRY_SIGNATURE, 7))
- {
- Status = STATUS_INVALID_PARAMETER_9;
- goto Quickie;
- }
-
- /* Read parameters */
- BlpApplicationParameters = BootAppParameters;
- BlpLibraryParameters = *LibraryParameters;
-
- /* Check if the caller sent us their internal BCD options */
- if (AppEntry->Flags & BL_APPLICATION_ENTRY_BCD_OPTIONS_INTERNAL)
- {
- /* These are external to us now, as far as we are concerned */
- AppEntry->Flags &= ~BL_APPLICATION_ENTRY_BCD_OPTIONS_INTERNAL;
- AppEntry->Flags |= BL_APPLICATION_ENTRY_BCD_OPTIONS_EXTERNAL;
- }
-
- /* Save the application entry flags */
- BlpApplicationEntry.Flags = AppEntry->Flags;
-
- /* Copy the GUID and point to the options */
- BlpApplicationEntry.Guid = AppEntry->Guid;
- BlpApplicationEntry.BcdData = &AppEntry->BcdData;
-
- /* Everything has been captured */
- BlpLibraryParametersInitialized = TRUE;
-
- /* Initialize the architecture (PM or RM) switching */
- Status = BlpArchInitialize(0);
- if (!NT_SUCCESS(Status))
- {
- goto Quickie;
- }
-
- /* Initialize the memory manager */
- Status = BlpMmInitialize(MemoryData,
- BootAppParameters->MemoryTranslationType,
- LibraryParameters);
- if (!NT_SUCCESS(Status))
- {
- EfiPrintf(L"MM init failed!\r\n");
- goto Quickie;
- }
-
- /* Initialize firmware now that the heap, etc works */
- Status = BlpFwInitialize(1, FirmwareDescriptor);
- if (!NT_SUCCESS(Status))
- {
- /* Destroy memory manager in phase 1 */
- //BlpMmDestroy(1);
- EfiPrintf(L"Firmware2 init failed!\r\n");
- return Status;
- }
-
- /* Modern systems have an undocumented BCD system for the boot frequency */
- Status = BlGetBootOptionInteger(BlpApplicationEntry.BcdData,
- 0x15000075,
- (PULONGLONG)&BootFrequency.QuadPart);
- if (NT_SUCCESS(Status) && (BootFrequency.QuadPart))
- {
- /* Use it if present */
- BlpTimePerformanceFrequency = BootFrequency.QuadPart;
- }
- else
- {
- /* Use the TSC for calibration */
- Status = BlpTimeCalibratePerformanceCounter();
- if (!NT_SUCCESS(Status))
- {
- /* Destroy memory manager in phase 1 */
- EfiPrintf(L"TSC calibration failed\r\n");
- //BlpMmDestroy(1);
- return Status;
- }
- }
-
- /* Now setup the rest of the architecture (IDT, etc) */
- Status = BlpArchInitialize(1);
- if (!NT_SUCCESS(Status))
- {
- /* Destroy memory manager in phase 1 */
- EfiPrintf(L"Arch2 init failed\r\n");
- //BlpMmDestroy(1);
- return Status;
- }
-
-#ifdef BL_TPM_SUPPORT
- /* Initialize support for Trusted Platform Module v1.2 */
- BlpTpmInitialize();
-#endif
-
-#ifdef BL_TPM_SUPPORT
- /* Initialize the event manager */
- EnSubsystemInitialized = 1;
- InitializeListHead(&EnEventNotificationList);
-#endif
-
- /* Initialize the I/O Manager */
- Status = BlpIoInitialize();
- if (!NT_SUCCESS(Status))
- {
- /* Destroy memory manager in phase 1 and the event manager */
- EfiPrintf(L"IO init failed\r\n");
-#ifdef BL_TPM_SUPPORT
- if (EnSubsystemInitialized)
- {
- BlpEnDestroy();
- }
-#endif
- //BlpMmDestroy(1);
- return Status;
- }
-
-#ifdef BL_NET_SUPPORT
- /* Initialize the network stack */
- Status = BlNetInitialize();
- if (!NT_SUCCESS(Status))
- {
- /* Destroy the I/O, event, and memory managers in phase 1 */
- BlpIoDestroy();
-#ifdef BL_TPM_SUPPORT
- if (EnSubsystemInitialized)
- {
- BlpEnDestroy();
- }
-#endif
- BlpMmDestroy(1);
- return Status;
- }
-#endif
-
- /* Initialize the utility library */
- Status = BlUtlInitialize();
- if (!NT_SUCCESS(Status))
- {
- /* Destroy the network, I/O, event, and memory managers in phase 1 */
-#ifdef BL_NET_SUPPORT
- BlNetDestroy();
-#endif
- //BlpIoDestroy();
-#ifdef BL_TPM_SUPPORT
- if (EnSubsystemInitialized)
- {
- BlpEnDestroy();
- }
-#endif
- //BlpMmDestroy(1);
- EfiPrintf(L"Util init failed\r\n");
- return Status;
- }
-
-#ifdef BL_KD_SUPPORT
- /* Initialize PCI Platform Support */
- PltInitializePciConfiguration();
-#endif
-
-#ifdef BL_SECURE_BOOT_SUPPORT
- /* Read the current SecureBoot Policy*/
- Status = BlSecureBootSetActivePolicyFromPersistedData();
- if (!NT_SUCCESS(Status))
- {
- /* Destroy everything that we've currently set up */
-#ifdef BL_KD_SUPPORT
- PltDestroyPciConfiguration();
-#endif
-#ifdef BL_NET_SUPPORT
- BlNetDestroy();
-#endif
- BlpIoDestroy();
-#ifdef BL_TPM_SUPPORT
- if (EnSubsystemInitialized)
- {
- BlpEnDestroy();
- }
-#endif
- BlpMmDestroy(1);
- return Status;
- }
-#endif
-
-#ifdef BL_TPM_SUPPORT
- /* Initialize phase 0 of the security subsystem */
- SipInitializePhase0();
-#endif
-
-#ifdef BL_KD_SUPPORT
- /* Bring up the boot debugger, now that SecureBoot has been processed */
- BlBdInitialize();
-#endif
-
-#ifdef BL_ETW_SUPPORT
- /* Initialize internal logging */
- BlpLogInitialize();
-#endif
-
- /* Are graphics enabled? */
- if (!(LibraryParameters->LibraryFlags & BL_LIBRARY_FLAG_NO_DISPLAY))
- {
- /* Initialize the graphics library */
- BlpDisplayInitialize(LibraryParameters->LibraryFlags);
- }
-
- /* Initialize the boot application persistent data */
- PdPersistAllocations = 0;
- InitializeListHead(&BlpPdListHead);
-
-#ifdef BL_TPM_SUPPORT
- /* Now setup the security subsystem in phase 1 */
- BlpSiInitialize(1);
-#endif
-
- /* Setup the text, UI and font resources */
- Status = BlpResourceInitialize();
- if (!NT_SUCCESS(Status))
- {
- /* Tear down everything if this failed */
- if (!(LibraryParameters->LibraryFlags & BL_LIBRARY_FLAG_NO_DISPLAY))
- {
-// BlpDisplayDestroy();
- }
-#ifdef BL_KD_SUPPORT
- BlpBdDestroy();
- PltDestroyPciConfiguration();
-#endif
-#ifdef BL_NET_SUPPORT
- BlNetDestroy();
-#endif
- //BlpIoDestroy();
-#ifdef BL_TPM_SUPPORT
- if (EnSubsystemInitialized)
- {
- BlpEnDestroy();
- }
-#endif
- //BlpMmDestroy(1);
- return Status;
- }
-
-#if BL_BITLOCKER_SUPPORT
- /* Setup the boot cryptography library */
- g_pEnvironmentData = &SymCryptEnvironmentWindowsBootLibrary;
- if (SymCryptEnvWindowsBootLibInit)
- {
- SymCryptEnvWindowsBootLibInit();
- }
-#endif
-
- /* We are fully initialized, remember this and exit with success */
- BlpLibraryParameters.LibraryFlags |= BL_LIBRARY_FLAG_INITIALIZATION_COMPLETED;
- Status = STATUS_SUCCESS;
-
-Quickie:
- return Status;
-}
-
-/*++
- * @name BlInitializeLibrary
- *
- * The BlInitializeLibrary function initializes, or re-initializes, the
- * Boot Library.
- *
- * @param BootParameters
- * Pointer to the Boot Application Parameter Block.
- *
- * @param LibraryParameters
- * Pointer to the Boot Library Parameters.
- *
- * @return NT_SUCCESS if the boot library was loaded correctly, relevant error
- * otherwise.
- *
- *--*/
-NTSTATUS
-BlInitializeLibrary(
- _In_ PBOOT_APPLICATION_PARAMETER_BLOCK BootAppParameters,
- _In_ PBL_LIBRARY_PARAMETERS LibraryParameters
- )
-{
- NTSTATUS Status;
-
- /* Are we re-initializing the library? */
- if (LibraryParameters->LibraryFlags & BL_LIBRARY_FLAG_REINITIALIZE)
- {
- /* From scratch? */
- BlpLibraryParameters = *LibraryParameters;
- if (LibraryParameters->LibraryFlags & BL_LIBRARY_FLAG_REINITIALIZE_ALL)
- {
-#ifdef BL_TPM_SUPPORT
- /* Reinitialize the TPM security enclave as BCD hash changed */
- BlpSiInitialize(1);
-#endif
-#ifdef BL_KD_SUPPORT
- /* Reinitialize the boot debugger as BCD debug options changed */
- BlBdInitialize();
-#endif
-
- /* Reparse the bad page list now that the BCD has been reloaded */
- BlMmRemoveBadMemory();
-
- /* Reparse the low/high physical address limits as well */
- BlpMmInitializeConstraints();
-
- /* Redraw the graphics console as needed */
- BlpDisplayInitialize(LibraryParameters->LibraryFlags);
-
- /* Reinitialize resources (language may have changed) */
- BlpResourceInitialize();
- }
-
- /* Nothing to do, we're done */
- Status = STATUS_SUCCESS;
- }
- else
- {
- /* Nope, this is first time initialization */
- Status = InitializeLibrary(BootAppParameters, LibraryParameters);
- }
-
- /* Return initialization status */
- return Status;
-}
-
-VOID
-BlDestroyLibrary (
- VOID
- )
-{
- EfiPrintf(L"Destroy not yet implemented\r\n");
- return;
-}
-
-PGUID
-BlGetApplicationIdentifier (
- VOID
- )
-{
- /* Return the GUID, if one was present */
- return (BlpApplicationEntry.Flags & BL_APPLICATION_ENTRY_FLAG_NO_GUID) ?
- NULL : &BlpApplicationEntry.Guid;
-}
-
-NTSTATUS
-BlGetApplicationBaseAndSize (
- _Out_ PVOID* ImageBase,
- _Out_ PULONG ImageSize
- )
-{
- /* Fail if output parameters are missing */
- if (!ImageBase || !ImageSize)
- {
- return STATUS_INVALID_PARAMETER;
- }
-
- /* Return the requested data */
- *ImageBase = (PVOID)(ULONG_PTR)BlpApplicationParameters->ImageBase;
- *ImageSize = BlpApplicationParameters->ImageSize;
- return STATUS_SUCCESS;
-}
-
-VOID
-BlDestroyBootEntry (
- _In_ PBL_LOADED_APPLICATION_ENTRY AppEntry
- )
-{
- /* Check if we had allocated BCD options */
- if (AppEntry->Flags & BL_APPLICATION_ENTRY_BCD_OPTIONS_INTERNAL)
- {
- BlMmFreeHeap(AppEntry->BcdData);
- }
-
- /* Free the entry itself */
- BlMmFreeHeap(AppEntry);
-}
-
-NTSTATUS
-BlPdQueryData (
- _In_ const GUID* DataGuid,
- _In_ PVOID Unknown,
- _Inout_ PBL_PD_DATA_BLOB DataBlob
- )
-{
- /* Check for invalid or missing parameters */
- if (!(DataBlob) ||
- !(DataGuid) ||
- ((DataBlob->BlobSize) && !(DataBlob->Data)))
- {
- return STATUS_INVALID_PARAMETER;
- }
-
- /* Check if there's no persistent data blobs */
- if (IsListEmpty(&BlpPdListHead))
- {
- return STATUS_NOT_FOUND;
- }
-
- /* Not yet handled, TODO */
- EfiPrintf(L"Boot persistent data not yet implemented\r\n");
- return STATUS_NOT_IMPLEMENTED;
-}