Implement BlGetVirtualAddress() and BlPhysicalListToVirtual() routines
All checks were successful
Builds / ExectOS (amd64) (push) Successful in 32s
Builds / ExectOS (i686) (push) Successful in 32s

This commit is contained in:
Rafal Kupiec 2024-01-29 18:03:58 +01:00
parent 8115ae07b6
commit d27a4cde4b
Signed by: belliash
GPG Key ID: 4E829243E0CFE6B4
4 changed files with 142 additions and 0 deletions

View File

@ -80,6 +80,7 @@ typedef VOID (*PBL_GET_MAPPINGS_COUNT)(IN PXTBL_PAGE_MAPPING PageMap, OUT PULONG
typedef EFI_STATUS (*PBL_GET_MEMORY_MAP)(OUT PEFI_MEMORY_MAP MemoryMap);
typedef PLIST_ENTRY (*PBL_GET_MODULES_LIST)();
typedef INT_PTR (*PBL_GET_SECURE_BOOT_STATUS)();
typedef PVOID (*PBL_GET_VIRTUAL_ADDRESS)(IN PXTBL_PAGE_MAPPING PageMap, IN PVOID PhysicalAddress);
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_INVOKE_BOOT_PROTOCOL)(IN PLIST_ENTRY OptionsList);
@ -92,6 +93,7 @@ typedef EFI_STATUS (*PBL_OPEN_VOLUME)(IN PEFI_DEVICE_PATH_PROTOCOL DevicePath, O
typedef EFI_STATUS (*PBL_OPEN_PROTOCOL)(OUT PEFI_HANDLE Handle, OUT PVOID *ProtocolHandler, IN PEFI_GUID ProtocolGuid);
typedef EFI_STATUS (*PBL_OPEN_PROTOCOL_HANDLE)(IN EFI_HANDLE Handle, OUT PVOID *ProtocolHandler, IN PEFI_GUID ProtocolGuid);
typedef PVOID (*PBL_PHYSICAL_ADDRESS_TO_VIRTUAL)(IN PVOID PhysicalAddress, IN PVOID PhysicalBase, IN PVOID VirtualBase);
typedef EFI_STATUS (*PBL_PHYSICAL_LIST_TO_VIRTUAL)(IN PXTBL_PAGE_MAPPING PageMap, IN OUT PLIST_ENTRY ListHead, IN PVOID PhysicalBase, IN PVOID VirtualBase);
typedef EFI_STATUS (*PBL_POWER_SYSTEM)();
typedef EFI_STATUS (*PBL_READ_FILE)(IN PEFI_FILE_HANDLE DirHandle, IN CONST PWCHAR FileName, OUT PVOID *FileData, OUT PSIZE_T FileSize);
typedef EFI_STATUS (*PBL_REGISTER_BOOT_PROTOCOL)(IN PWCHAR SystemType, IN PEFI_GUID BootProtocolGuid);
@ -312,11 +314,13 @@ typedef struct _XTBL_LOADER_PROTOCOL
PBL_FREE_POOL FreePool;
PBL_GET_MAPPINGS_COUNT GetMappingsCount;
PBL_GET_MEMORY_MAP GetMemoryMap;
PBL_GET_VIRTUAL_ADDRESS GetVirtualAddress;
PBL_INITIALIZE_PAGE_MAP InitializePageMap;
PBL_MAP_EFI_MEMORY MapEfiMemory;
PBL_MAP_PAGE MapPage;
PBL_MAP_VIRTUAL_MEMORY MapVirtualMemory;
PBL_PHYSICAL_ADDRESS_TO_VIRTUAL PhysicalAddressToVirtual;
PBL_PHYSICAL_LIST_TO_VIRTUAL PhysicalListToVirtual;
PBL_SET_MEMORY SetMemory;
PBL_ZERO_MEMORY ZeroMemory;
} Memory;

View File

@ -152,6 +152,11 @@ XTCDECL
INT_PTR
BlGetSecureBootStatus();
XTCDECL
PVOID
BlGetVirtualAddress(IN PXTBL_PAGE_MAPPING PageMap,
IN PVOID PhysicalAddress);
XTCDECL
EFI_STATUS
BlGetVolumeDevicePath(IN PWCHAR SystemPath,
@ -253,6 +258,13 @@ BlPhysicalAddressToVirtual(IN PVOID PhysicalAddress,
IN PVOID PhysicalBase,
IN PVOID VirtualBase);
XTCDECL
EFI_STATUS
BlPhysicalListToVirtual(IN PXTBL_PAGE_MAPPING PageMap,
IN OUT PLIST_ENTRY ListHead,
IN PVOID PhysicalBase,
IN PVOID VirtualBase);
XTCDECL
VOID
BlQueryConsoleMode(OUT PUINT_PTR ResX,

View File

@ -176,6 +176,54 @@ BlGetMemoryMap(OUT PEFI_MEMORY_MAP MemoryMap)
return STATUS_EFI_SUCCESS;
}
/**
* Attempts to find a virtual address of the specified physical address in memory mappings.
*
* @param PageMap
* Supplies a pointer to the page mapping structure.
*
* @param PhysicalAddress
* Supplies a physical address to search for in the mappings.
*
* @return This routine returns a corresponding virtual address found in the mappings.
*
* @since XT 1.0
*/
XTCDECL
PVOID
BlGetVirtualAddress(IN PXTBL_PAGE_MAPPING PageMap,
IN PVOID PhysicalAddress)
{
PLOADER_MEMORY_MAPPING Mapping;
PLIST_ENTRY ListEntry;
/* Iterate over memory mappings in order to find descriptor containing a physical address */
ListEntry = PageMap->MemoryMap.Flink;
while(ListEntry != &PageMap->MemoryMap)
{
/* Get mapping from linked list */
Mapping = CONTAIN_RECORD(ListEntry, LOADER_MEMORY_MAPPING, ListEntry);
/* Make sure any virtual address is set */
if(Mapping->VirtualAddress)
{
/* Check if provided physical address is in range of this mapping */
if((PhysicalAddress >= Mapping->PhysicalAddress) &&
(PhysicalAddress < Mapping->PhysicalAddress + (Mapping->NumberOfPages * EFI_PAGE_SIZE)))
{
/* Calculate virtual address based on the mapping and return it */
return PhysicalAddress - Mapping->PhysicalAddress + Mapping->VirtualAddress;
}
}
/* Get next element from the list */
ListEntry = ListEntry->Flink;
}
/* Mapping not found, return 0 */
return 0;
}
/**
* Initializes the page mapping structures.
*
@ -514,6 +562,82 @@ BlPhysicalAddressToVirtual(IN PVOID PhysicalAddress,
return (PUCHAR)VirtualBase + ((PUCHAR)PhysicalAddress - (PUCHAR)PhysicalBase);
}
/**
* Converts whole linked list addressing from physical to virtual for future use after enabling paging.
*
* @param PageMap
* Supplies a pointer to the page mapping structure.
*
* @param ListHead
* Supplies a pointer to a structure that serves as the list header.
*
* @param PhysicalBase
* Supplies a physical base address.
*
* @param VirtualBase
* Supplies a virtual base address.
*
* @return This routine returns a status code.
*
* @since XT 1.0
*/
XTCDECL
EFI_STATUS
BlPhysicalListToVirtual(IN PXTBL_PAGE_MAPPING PageMap,
IN OUT PLIST_ENTRY ListHead,
IN PVOID PhysicalBase,
IN PVOID VirtualBase)
{
PLIST_ENTRY ListEntry, NextEntry;
/* Make sure list is properly initialized */
if(ListHead->Flink == 0 || ListHead->Blink == 0)
{
/* List not initialized, return error code */
return STATUS_EFI_INVALID_PARAMETER;
}
/* Iterate through all elements */
ListEntry = ListHead->Flink;
while(ListEntry != ListHead)
{
/* Save physical address of the next element */
NextEntry = ListEntry->Flink;
/* Convert the address of this element to VirtualAddress */
if(ListEntry->Flink == ListHead)
{
/* Convert list head */
ListEntry->Flink = ListHead->Flink->Blink;
}
else
{
/* Convert list entry */
ListEntry->Flink = BlPhysicalAddressToVirtual(ListEntry->Flink, (PVOID)PhysicalBase, VirtualBase);
}
if(ListEntry->Blink == ListHead)
{
/* Find virtual address of list head */
ListEntry->Blink = BlGetVirtualAddress(PageMap, ListEntry->Blink);
}
else
{
/* Convert list entry */
ListEntry->Blink = BlPhysicalAddressToVirtual(ListEntry->Blink, (PVOID)PhysicalBase, VirtualBase);
}
/* Get to the next element*/
ListEntry = NextEntry;
}
/* Convert list head */
ListHead->Flink = BlPhysicalAddressToVirtual(ListHead->Flink, (PVOID)PhysicalBase, VirtualBase);
ListHead->Blink = BlPhysicalAddressToVirtual(ListHead->Blink, (PVOID)PhysicalBase, VirtualBase);
/* Return success */
return STATUS_EFI_SUCCESS;
}
/**
* Converts EFI memory type to XTLDR memory type.
*

View File

@ -632,11 +632,13 @@ BlpInstallXtLoaderProtocol()
BlpLdrProtocol.Memory.FreePool = BlFreeMemoryPool;
BlpLdrProtocol.Memory.GetMappingsCount = BlGetMappingsCount;
BlpLdrProtocol.Memory.GetMemoryMap = BlGetMemoryMap;
BlpLdrProtocol.Memory.GetVirtualAddress = BlGetVirtualAddress;
BlpLdrProtocol.Memory.InitializePageMap = BlInitializePageMap;
BlpLdrProtocol.Memory.MapEfiMemory = BlMapEfiMemory;
BlpLdrProtocol.Memory.MapPage = BlMapPage;
BlpLdrProtocol.Memory.MapVirtualMemory = BlMapVirtualMemory;
BlpLdrProtocol.Memory.PhysicalAddressToVirtual = BlPhysicalAddressToVirtual;
BlpLdrProtocol.Memory.PhysicalListToVirtual = BlPhysicalListToVirtual;
BlpLdrProtocol.Memory.SetMemory = RtlSetMemory;
BlpLdrProtocol.Memory.ZeroMemory = RtlZeroMemory;
BlpLdrProtocol.Protocol.Close = BlCloseProtocol;