diff --git a/MdeModulePkg/Core/Dxe/DxeMain.inf b/MdeModulePkg/Core/Dxe/DxeMain.inf index efbda12787..3ca09084b5 100644 --- a/MdeModulePkg/Core/Dxe/DxeMain.inf +++ b/MdeModulePkg/Core/Dxe/DxeMain.inf @@ -70,6 +70,9 @@ SysCall/SupportedProtocols.h SysCall/SupportedProtocols.c +[Sources.IA32] + SysCall/IA32/CoreBootServices.nasm + [Sources.X64] SysCall/X64/CoreBootServices.nasm diff --git a/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c b/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c index 61cb28e6b9..f3d44cceb1 100644 --- a/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c +++ b/MdeModulePkg/Core/Dxe/DxeMain/DxeMain.c @@ -768,24 +768,24 @@ CoreExitBootServices ( // if (gRing3Data != NULL) { CoreFreePages ( - (EFI_PHYSICAL_ADDRESS)gRing3Data, + (EFI_PHYSICAL_ADDRESS)(UINTN)gRing3Data, EFI_SIZE_TO_PAGES (sizeof (RING3_DATA)) ); - + gRing3Data = NULL; CoreFreePages ( - (EFI_PHYSICAL_ADDRESS)gRing3Interfaces, + (EFI_PHYSICAL_ADDRESS)(UINTN)gRing3Interfaces, RING3_INTERFACES_PAGES ); CoreFreePages ( - (EFI_PHYSICAL_ADDRESS)gCoreSysCallStackBase, + (EFI_PHYSICAL_ADDRESS)(UINTN)gCoreSysCallStackBase, EFI_SIZE_TO_PAGES (USER_STACK_SIZE) ); CoreFreePages ( - (EFI_PHYSICAL_ADDRESS)gRing3CallStackBase, + (EFI_PHYSICAL_ADDRESS)(UINTN)gRing3CallStackBase, EFI_SIZE_TO_PAGES (USER_STACK_SIZE) ); diff --git a/MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf b/MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf index 426e9e07c3..4c36e5a97e 100644 --- a/MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf +++ b/MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf @@ -28,6 +28,9 @@ Ring3UefiRuntimeServices.c Ring3Protocols.c +[Sources.IA32] + IA32/SysCall.nasm + [Sources.X64] X64/SysCall.nasm diff --git a/MdeModulePkg/Core/Dxe/DxeRing3/IA32/SysCall.nasm b/MdeModulePkg/Core/Dxe/DxeRing3/IA32/SysCall.nasm new file mode 100644 index 0000000000..2f37ffe619 --- /dev/null +++ b/MdeModulePkg/Core/Dxe/DxeRing3/IA32/SysCall.nasm @@ -0,0 +1,38 @@ +;------------------------------------------------------------------------------ +; Copyright (c) 2024, Mikhail Krichanov. All rights reserved. +; SPDX-License-Identifier: BSD-3-Clause +;------------------------------------------------------------------------------ + +extern ASM_PFX(Ring3Call) + +DEFAULT REL +SECTION .text + +;------------------------------------------------------------------------------ +; EFI_STATUS +; EFIAPI +; SysCall ( +; IN UINT8 Type, +; ... +; ); +;------------------------------------------------------------------------------ +global ASM_PFX(SysCall) +ASM_PFX(SysCall): + sysenter + + ret + +;------------------------------------------------------------------------------ +; VOID +; EFIAPI +; Ring3EntryPoint ( +; IN RING3_CALL_DATA *Data +; ); +; +; (rcx) RIP of Ring3EntryPoint saved for SYSRET in CallRing3(). +; (rdx) Data +;------------------------------------------------------------------------------ +global ASM_PFX(Ring3EntryPoint) +ASM_PFX(Ring3EntryPoint): + + call ASM_PFX(Ring3Call) diff --git a/MdeModulePkg/Core/Dxe/DxeRing3/Ring3UefiBootServices.c b/MdeModulePkg/Core/Dxe/DxeRing3/Ring3UefiBootServices.c index 54943444de..e42fa8752b 100644 --- a/MdeModulePkg/Core/Dxe/DxeRing3/Ring3UefiBootServices.c +++ b/MdeModulePkg/Core/Dxe/DxeRing3/Ring3UefiBootServices.c @@ -605,7 +605,7 @@ Ring3LocateHandleBuffer ( CopyMem (Pool, *Buffer, PoolSize); Status = Ring3FreePages ( - (EFI_PHYSICAL_ADDRESS)*Buffer, + (EFI_PHYSICAL_ADDRESS)(UINTN)*Buffer, EFI_SIZE_TO_PAGES (PoolSize) ); if (EFI_ERROR (Status)) { @@ -764,7 +764,7 @@ CoreAllocatePoolPagesI ( Ring3AllocatePages (AllocateAnyPages, EfiRing3MemoryType, NoPages, &Memory); - return (VOID *)Memory; + return (VOID *)(UINTN)Memory; } VOID diff --git a/MdeModulePkg/Core/Dxe/Image/Image.c b/MdeModulePkg/Core/Dxe/Image/Image.c index e2f00739a8..38507715eb 100644 --- a/MdeModulePkg/Core/Dxe/Image/Image.c +++ b/MdeModulePkg/Core/Dxe/Image/Image.c @@ -1692,7 +1692,7 @@ CoreStartImage ( if (Image->IsRing3EntryPoint) { Image->Status = InitializeRing3 (ImageHandle, Image); } else if (Image->IsUserImage) { - gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)Image->EntryPoint, &Attributes); + gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)(UINTN)Image->EntryPoint, &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); Image->Status = GoToRing3 ( diff --git a/MdeModulePkg/Core/Dxe/SysCall/BootServices.c b/MdeModulePkg/Core/Dxe/SysCall/BootServices.c index dadb6cd12a..323cbb4ce3 100644 --- a/MdeModulePkg/Core/Dxe/SysCall/BootServices.c +++ b/MdeModulePkg/Core/Dxe/SysCall/BootServices.c @@ -274,13 +274,14 @@ CallBootService ( EFI_DISK_IO_PROTOCOL *DiskIo; EFI_UNICODE_COLLATION_PROTOCOL *Unicode; - Argument4 = 0; - Argument5 = 0; - Argument6 = 0; + CoreProtocol = NULL; + Argument4 = 0; + Argument5 = 0; + Argument6 = 0; // // Check User variables. // - gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)UserRsp, &Attributes); + gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)(UINTN)UserRsp, &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); switch (Type) { @@ -398,7 +399,7 @@ CallBootService ( for (Index = 0; UserArgList[Index] != NULL; Index += 2) { gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)((UINTN)&UserArgList[Index + 2] - 1), &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); - gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)UserArgList[Index], &Attributes); + gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)(UINTN)UserArgList[Index], &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)((UINTN)UserArgList[Index] + sizeof (EFI_GUID) - 1), &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); @@ -415,7 +416,7 @@ CallBootService ( return Status; } - gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)UserArgList[Index + 1], &Attributes); + gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)(UINTN)UserArgList[Index + 1], &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); gCpu->GetMemoryAttributes (gCpu, (EFI_PHYSICAL_ADDRESS)((UINTN)UserArgList[Index + 1] + MemoryCoreSize - 1), &Attributes); ASSERT ((Attributes & EFI_MEMORY_USER) != 0); @@ -1167,7 +1168,7 @@ CallBootService ( FreePool ((VOID *)Argument4); } - return Status; + return EFI_SUCCESS; case SysCallUnicodeStrUpr: // @@ -1208,7 +1209,7 @@ CallBootService ( FreePool ((VOID *)Argument4); } - return Status; + return EFI_SUCCESS; case SysCallUnicodeFatToStr: // @@ -1328,12 +1329,12 @@ CallBootService ( } EnableSMAP (); - Unicode->StrToFat ( - Unicode, - (CHAR16 *)Argument4, - CoreRbp->Argument3, - (CHAR8 *)Argument5 - ); + Status = (EFI_STATUS)Unicode->StrToFat ( + Unicode, + (CHAR16 *)Argument4, + CoreRbp->Argument3, + (CHAR8 *)Argument5 + ); if ((VOID *)Argument4 != NULL) { FreePool ((VOID *)Argument4); @@ -1347,7 +1348,7 @@ CallBootService ( FreePool ((VOID *)Argument5); } - return EFI_SUCCESS; + return Status; default: DEBUG ((DEBUG_ERROR, "Ring0: Unknown syscall type.\n")); diff --git a/MdeModulePkg/Core/Dxe/SysCall/IA32/CoreBootServices.nasm b/MdeModulePkg/Core/Dxe/SysCall/IA32/CoreBootServices.nasm new file mode 100644 index 0000000000..99297a6ff2 --- /dev/null +++ b/MdeModulePkg/Core/Dxe/SysCall/IA32/CoreBootServices.nasm @@ -0,0 +1,98 @@ +;------------------------------------------------------------------------------ +; +; Copyright (c) 2024, Mikhail Krichanov. All rights reserved. +; SPDX-License-Identifier: BSD-3-Clause +; +;------------------------------------------------------------------------------ + +#include + +extern ASM_PFX(CallBootService) +extern ASM_PFX(gCoreSysCallStackTop) +extern ASM_PFX(gRing3CallStackTop) +extern ASM_PFX(gRing3EntryPoint) + +extern ASM_PFX(AsmReadMsr64) + +DEFAULT REL +SECTION .text + +;------------------------------------------------------------------------------ +; VOID +; EFIAPI +; DisableSMAP ( +; VOID +; ); +;------------------------------------------------------------------------------ +global ASM_PFX(DisableSMAP) +ASM_PFX(DisableSMAP): + pushfd + pop eax + or eax, 0x40000 ; Set AC (bit 18) + push eax + popfd + ret + +;------------------------------------------------------------------------------ +; VOID +; EFIAPI +; EnableSMAP ( +; VOID +; ); +;------------------------------------------------------------------------------ +global ASM_PFX(EnableSMAP) +ASM_PFX(EnableSMAP): + pushfd + pop eax + and eax, ~0x40000 ; Clear AC (bit 18) + push eax + popfd + ret + +;------------------------------------------------------------------------------ +; EFI_STATUS +; EFIAPI +; CallInstallMultipleProtocolInterfaces ( +; IN EFI_HANDLE *Handle, +; IN VOID **ArgList, +; IN UINT32 ArgListSize, +; IN VOID *Function +; ); +;------------------------------------------------------------------------------ +global ASM_PFX(CallInstallMultipleProtocolInterfaces) +ASM_PFX(CallInstallMultipleProtocolInterfaces): + ret + +;------------------------------------------------------------------------------ +; EFI_STATUS +; EFIAPI +; CoreBootServices ( +; IN UINT8 Type, +; ... +; ); +; +; (rcx) RIP of the next instruction saved by SYSCALL in SysCall(). +; (rdx) Argument 1 of the called function. +; (r8) Argument 2 of the called function. +; (r9) Argument 3 of the called function. +; (r10) Type. +; (r11) RFLAGS saved by SYSCALL in SysCall(). +; +; (On User Stack) Argument 4, 5, ... +;------------------------------------------------------------------------------ +global ASM_PFX(CoreBootServices) +ASM_PFX(CoreBootServices): + ret + +;------------------------------------------------------------------------------ +; EFI_STATUS +; EFIAPI +; CallRing3 ( +; IN RING3_CALL_DATA *Data +; ); +; +; (rcx) Data +;------------------------------------------------------------------------------ +global ASM_PFX(CallRing3) +ASM_PFX(CallRing3): + ret diff --git a/MdeModulePkg/Core/Dxe/SysCall/Initialization.c b/MdeModulePkg/Core/Dxe/SysCall/Initialization.c index ec1b645acb..be4e9f6a48 100644 --- a/MdeModulePkg/Core/Dxe/SysCall/Initialization.c +++ b/MdeModulePkg/Core/Dxe/SysCall/Initialization.c @@ -69,7 +69,7 @@ InitializeRing3 ( if (EFI_ERROR (Status)) { DEBUG ((DEBUG_ERROR, "Core: Failed to allocate memory for Ring3Interfaces.\n")); CoreFreePages ( - (EFI_PHYSICAL_ADDRESS)gRing3Data, + (EFI_PHYSICAL_ADDRESS)(UINTN)gRing3Data, EFI_SIZE_TO_PAGES (sizeof (RING3_DATA)) ); return Status; diff --git a/MdeModulePkg/Core/Dxe/SysCall/SupportedProtocols.c b/MdeModulePkg/Core/Dxe/SysCall/SupportedProtocols.c index 07dd4a9f6e..38f7d977cc 100644 --- a/MdeModulePkg/Core/Dxe/SysCall/SupportedProtocols.c +++ b/MdeModulePkg/Core/Dxe/SysCall/SupportedProtocols.c @@ -128,7 +128,7 @@ CoreDriverBindingSupported ( RemainingDevicePath ); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)This, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)This, 1); return Status; } @@ -156,7 +156,7 @@ CoreDriverBindingStart ( RemainingDevicePath ); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)This, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)This, 1); return Status; } @@ -186,7 +186,7 @@ CoreDriverBindingStop ( ChildHandleBuffer ); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)This, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)This, 1); return Status; } @@ -286,7 +286,7 @@ CoreFileRead ( *BufferSize = *Ring3BufferSize; EnableSMAP (); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return Status; } @@ -367,7 +367,7 @@ CoreFileGetPosition ( *Position = *Ring3Position; EnableSMAP (); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Position, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Position, 1); return Status; } @@ -446,7 +446,7 @@ CoreFileGetInfo ( *BufferSize = *Ring3BufferSize; EnableSMAP (); - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return Status; } @@ -571,7 +571,7 @@ CoreFileOpen ( EnableSMAP (); if (EFI_ERROR (Status)) { *NewHandle = NULL; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return Status; } @@ -586,14 +586,14 @@ CoreFileOpen ( ); if (EFI_ERROR (Status)) { *NewHandle = NULL; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return Status; } NewFile = AllocatePool (sizeof (RING3_EFI_FILE_PROTOCOL)); if (NewFile == NULL) { *NewHandle = NULL; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return EFI_OUT_OF_RESOURCES; } @@ -619,7 +619,7 @@ CoreFileOpen ( *NewHandle = (EFI_FILE_PROTOCOL *)NewFile; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Pages, PagesNumber); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Pages, PagesNumber); return Status; } @@ -658,14 +658,14 @@ CoreOpenVolume ( ); if (EFI_ERROR (Status)) { *Root = NULL; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Root, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Root, 1); return Status; } File = AllocatePool (sizeof (RING3_EFI_FILE_PROTOCOL)); if (File == NULL) { *Root = NULL; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Root, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Root, 1); return EFI_OUT_OF_RESOURCES; } @@ -707,7 +707,7 @@ CoreOpenVolume ( *Root = (EFI_FILE_PROTOCOL *)File; - CoreFreePages ((EFI_PHYSICAL_ADDRESS)Ring3Root, 1); + CoreFreePages ((EFI_PHYSICAL_ADDRESS)(UINTN)Ring3Root, 1); return Status; } diff --git a/MdeModulePkg/MdeModulePkg.dsc b/MdeModulePkg/MdeModulePkg.dsc index 08a6007878..eec2b9639e 100644 --- a/MdeModulePkg/MdeModulePkg.dsc +++ b/MdeModulePkg/MdeModulePkg.dsc @@ -316,7 +316,10 @@ MdeModulePkg/Bus/Spi/SpiHc/SpiHcDxe.inf MdeModulePkg/Bus/Spi/SpiHc/SpiHcSmm.inf - MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf + MdeModulePkg/Core/Dxe/DxeRing3/DxeRing3.inf { + + MemoryPoolLib|MdeModulePkg/Library/MemoryPoolLib/MemoryPoolLib.inf + } MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf MdeModulePkg/Core/Pei/PeiMain.inf MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf diff --git a/MdePkg/Library/BaseLib/BaseLib.inf b/MdePkg/Library/BaseLib/BaseLib.inf index dff5ca56af..f63ba3907f 100644 --- a/MdePkg/Library/BaseLib/BaseLib.inf +++ b/MdePkg/Library/BaseLib/BaseLib.inf @@ -154,6 +154,7 @@ Ia32/ARShiftU64.c | MSFT Ia32/EnableCache.c | MSFT Ia32/DisableCache.c | MSFT + Ia32/WriteEflags.nasm Ia32/GccInline.c | GCC diff --git a/MdePkg/Library/BaseLib/Ia32/WriteEflags.nasm b/MdePkg/Library/BaseLib/Ia32/WriteEflags.nasm new file mode 100644 index 0000000000..b462bff812 --- /dev/null +++ b/MdePkg/Library/BaseLib/Ia32/WriteEflags.nasm @@ -0,0 +1,33 @@ +;------------------------------------------------------------------------------ +; +; Copyright (c) 2024, Mikhail Krichanov. All rights reserved. +; SPDX-License-Identifier: BSD-3-Clause +; +; Module Name: +; +; WriteEflags.Asm +; +; Abstract: +; +; AsmWriteEflags function +; +; Notes: +; +;------------------------------------------------------------------------------ + + DEFAULT REL + SECTION .text + +;------------------------------------------------------------------------------ +; UINTN +; EFIAPI +; AsmWriteEflags ( +; UINTN Eflags +; ); +;------------------------------------------------------------------------------ +global ASM_PFX(AsmWriteEflags) +ASM_PFX(AsmWriteEflags): + push ecx + popfd + mov eax, ecx + ret