From 904c198e4cb400c856c69cea9be1f6c1bba9c878 Mon Sep 17 00:00:00 2001 From: Savva Mitrofanov Date: Fri, 10 Feb 2023 16:24:01 +0600 Subject: [PATCH] UefiCpuPkg/CpuPageTableLib: Add intrinsic lib to fix MSVC build For the bitfield access, MSVC apparently uses a right shift of the base type of the bitfield member. In our case, is is cased by IA32_PTE_4K and IA32_PAGE_LEAF_ENTRY_BIG_PAGESIZE and other structures which uses uint64 bitfields and 32-bit x86 doesn't have a 64-bit integer shift (except using MMX or SSE2). With -Od (NOOPT) even for constant counts it puts the data in EDX:EAX, the shift count in cl and calls __aullshr. Signed-off-by: Savva Mitrofanov --- .../IntrinsicLib/Ia32/MathDivU64xU64Rem.c | 91 +++++++++++++++++++ .../Library/IntrinsicLib/IntrinsicLib.inf | 2 + .../CpuPageTableLib/CpuPageTableLib.inf | 1 + UefiCpuPkg/UefiCpuPkg.dsc | 4 + 4 files changed, 98 insertions(+) create mode 100644 CryptoPkg/Library/IntrinsicLib/Ia32/MathDivU64xU64Rem.c diff --git a/CryptoPkg/Library/IntrinsicLib/Ia32/MathDivU64xU64Rem.c b/CryptoPkg/Library/IntrinsicLib/Ia32/MathDivU64xU64Rem.c new file mode 100644 index 0000000000..ca74d54d07 --- /dev/null +++ b/CryptoPkg/Library/IntrinsicLib/Ia32/MathDivU64xU64Rem.c @@ -0,0 +1,91 @@ +/** @file + 64-bit Math Worker Function. + The 32-bit versions of C compiler generate calls to library routines + to handle 64-bit math. These functions use non-standard calling conventions. + Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.
+ This program and the accompanying materials are licensed and made available + under the terms and conditions of the BSD License which accompanies this + distribution. The full text of the license may be found at + http://opensource.org/licenses/bsd-license.php. + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. +**/ + +#include + + +/* + * Divides a 64-bit unsigned value by another 64-bit unsigned value and returns + * the 64-bit unsigned remainder. + */ +__declspec(naked) void __cdecl +_aullrem(void) +{ + // + // Wrapper Implementation over EDKII DivU64x64Remainder() routine + // UINT64 + // EFIAPI + // DivU64x64Remainder ( + // IN UINT64 Dividend, + // IN UINT64 Divisor, + // OUT UINT64 *Remainder OPTIONAL + // ) + // + _asm { + ; Original local stack when calling _aullrem + ; ----------------- + ; | | + ; |---------------| + ; | | + ; |-- Divisor --| + ; | | + ; |---------------| + ; | | + ; |-- Dividend --| + ; | | + ; |---------------| + ; | ReturnAddr** | + ; ESP---->|---------------| + ; + + ; + ; Set up the local stack for Reminder pointer + ; + sub esp, 8 + push esp + + ; + ; Set up the local stack for Divisor parameter + ; + mov eax, [esp + 28] + push eax + mov eax, [esp + 28] + push eax + + ; + ; Set up the local stack for Dividend parameter + ; + mov eax, [esp + 28] + push eax + mov eax, [esp + 28] + push eax + + ; + ; Call native DivU64x64Remainder of BaseLib + ; + call DivU64x64Remainder + + ; + ; Put the Reminder in EDX:EAX as return value + ; + mov eax, [esp + 20] + mov edx, [esp + 24] + + ; + ; Adjust stack + ; + add esp, 28 + + ret 16 + } +} \ No newline at end of file diff --git a/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf b/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf index ae238ccc0b..8602a513b0 100644 --- a/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf +++ b/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf @@ -27,6 +27,7 @@ [Sources.IA32] CopyMem.c + Ia32/MathDivU64xU64Rem.c | MSFT Ia32/MathLShiftS64.c | MSFT Ia32/MathRShiftU64.c | MSFT Ia32/MathFtol.c | MSFT @@ -37,6 +38,7 @@ Ia32/MathLldiv.asm | MSFT Ia32/MathUllrem.asm | MSFT + Ia32/MathDivU64xU64Rem.c | INTEL Ia32/MathLShiftS64.c | INTEL Ia32/MathRShiftU64.c | INTEL Ia32/MathFtol.c | INTEL diff --git a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf index e4ead7441c..5d48feb81f 100644 --- a/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf +++ b/UefiCpuPkg/Library/CpuPageTableLib/CpuPageTableLib.inf @@ -33,3 +33,4 @@ BaseLib BaseMemoryLib DebugLib + IntrinsicLib diff --git a/UefiCpuPkg/UefiCpuPkg.dsc b/UefiCpuPkg/UefiCpuPkg.dsc index dc6150ce57..ff9768375d 100644 --- a/UefiCpuPkg/UefiCpuPkg.dsc +++ b/UefiCpuPkg/UefiCpuPkg.dsc @@ -74,6 +74,7 @@ LockBoxLib|MdeModulePkg/Library/SmmLockBoxLib/SmmLockBoxDxeLib.inf HobLib|MdeModulePkg/Library/BaseHobLibNull/BaseHobLibNull.inf MemoryAllocationLib|MdeModulePkg/Library/BaseMemoryAllocationLibNull/BaseMemoryAllocationLibNull.inf + IntrinsicLib|CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf [LibraryClasses.common.SEC] PlatformSecLib|UefiCpuPkg/Library/PlatformSecLibNull/PlatformSecLibNull.inf @@ -138,6 +139,9 @@ UefiCpuPkg/MicrocodeMeasurementDxe/MicrocodeMeasurementDxe.inf UefiCpuPkg/Library/MmUnblockMemoryLib/MmUnblockMemoryLib.inf +[Components.IA32] + CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf + [Components.IA32, Components.X64] UefiCpuPkg/CpuDxe/CpuDxe.inf UefiCpuPkg/CpuFeatures/CpuFeaturesPei.inf {