From: "Li, Yi" <yi1.li@intel.com>
To: devel@edk2.groups.io
Cc: Yi Li <yi1.li@intel.com>, Jiewen Yao <jiewen.yao@intel.com>,
Xiaoyu Lu <xiaoyu1.lu@intel.com>,
Guomin Jiang <guomin.jiang@intel.com>
Subject: [edk2-devel] [PATCH V2 17/29] CryptoPkg: Add instrinsics to support building openssl3 on IA32 windows
Date: Thu, 3 Aug 2023 12:37:35 +0800 [thread overview]
Message-ID: <0fac263e9500511f8ef4286e51b8887c1a10ddaa.1691031203.git.yi1.li@intel.com> (raw)
In-Reply-To: <cover.1691031203.git.yi1.li@intel.com>
This dependency is needed to build openssl lib with openssl3
under IA32 Windows, so added implementation for _alldiv, _aulldiv,
_aullrem and _alldvrm instrinsics.
Signed-off-by: Yi Li <yi1.li@intel.com>
Cc: Jiewen Yao <jiewen.yao@intel.com>
Cc: Xiaoyu Lu <xiaoyu1.lu@intel.com>
Cc: Guomin Jiang <guomin.jiang@intel.com>
---
.../Library/IntrinsicLib/Ia32/MathLldiv.asm | 203 ++++++++++++++++++
.../Library/IntrinsicLib/Ia32/MathUlldiv.asm | 157 ++++++++++++++
.../Library/IntrinsicLib/Ia32/MathUlldvrm.asm | 184 ++++++++++++++++
.../Library/IntrinsicLib/Ia32/MathUllrem.asm | 163 ++++++++++++++
.../Library/IntrinsicLib/IntrinsicLib.inf | 4 +
5 files changed, 711 insertions(+)
create mode 100644 CryptoPkg/Library/IntrinsicLib/Ia32/MathLldiv.asm
create mode 100644 CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldiv.asm
create mode 100644 CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldvrm.asm
create mode 100644 CryptoPkg/Library/IntrinsicLib/Ia32/MathUllrem.asm
diff --git a/CryptoPkg/Library/IntrinsicLib/Ia32/MathLldiv.asm b/CryptoPkg/Library/IntrinsicLib/Ia32/MathLldiv.asm
new file mode 100644
index 0000000000..2fccfd6dc0
--- /dev/null
+++ b/CryptoPkg/Library/IntrinsicLib/Ia32/MathLldiv.asm
@@ -0,0 +1,203 @@
+;***
+;lldiv.asm - signed long divide routine
+;
+; Copyright (c) Microsoft Corporation. All rights reserved.
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+;Purpose:
+; defines the signed long divide routine
+; __alldiv
+;
+;Original Implemenation: MSVC 14.29.30133
+;
+;*******************************************************************************
+ .686
+ .model flat,C
+ .code
+
+
+
+;***
+;lldiv - signed long divide
+;
+;Purpose:
+; Does a signed long divide of the arguments. Arguments are
+; not changed.
+;
+;Entry:
+; Arguments are passed on the stack:
+; 1st pushed: divisor (QWORD)
+; 2nd pushed: dividend (QWORD)
+;
+;Exit:
+; EDX:EAX contains the quotient (dividend/divisor)
+; NOTE: this routine removes the parameters from the stack.
+;
+;Uses:
+; ECX
+;
+;Exceptions:
+;
+;*******************************************************************************
+_alldiv PROC NEAR
+
+HIWORD EQU [4] ;
+LOWORD EQU [0]
+
+ push edi
+ push esi
+ push ebx
+
+; Set up the local stack and save the index registers. When this is done
+; the stack frame will look as follows (assuming that the expression a/b will
+; generate a call to lldiv(a, b)):
+;
+; -----------------
+; | |
+; |---------------|
+; | |
+; |--divisor (b)--|
+; | |
+; |---------------|
+; | |
+; |--dividend (a)-|
+; | |
+; |---------------|
+; | return addr** |
+; |---------------|
+; | EDI |
+; |---------------|
+; | ESI |
+; |---------------|
+; ESP---->| EBX |
+; -----------------
+;
+
+DVND equ [esp + 16] ; stack address of dividend (a)
+DVSR equ [esp + 24] ; stack address of divisor (b)
+
+
+; Determine sign of the result (edi = 0 if result is positive, non-zero
+; otherwise) and make operands positive.
+
+ xor edi,edi ; result sign assumed positive
+
+ mov eax,HIWORD(DVND) ; hi word of a
+ or eax,eax ; test to see if signed
+ jge short L1 ; skip rest if a is already positive
+ inc edi ; complement result sign flag
+ mov edx,LOWORD(DVND) ; lo word of a
+ neg eax ; make a positive
+ neg edx
+ sbb eax,0
+ mov HIWORD(DVND),eax ; save positive value
+ mov LOWORD(DVND),edx
+L1:
+ mov eax,HIWORD(DVSR) ; hi word of b
+ or eax,eax ; test to see if signed
+ jge short L2 ; skip rest if b is already positive
+ inc edi ; complement the result sign flag
+ mov edx,LOWORD(DVSR) ; lo word of a
+ neg eax ; make b positive
+ neg edx
+ sbb eax,0
+ mov HIWORD(DVSR),eax ; save positive value
+ mov LOWORD(DVSR),edx
+L2:
+
+;
+; Now do the divide. First look to see if the divisor is less than 4194304K.
+; If so, then we can use a simple algorithm with word divides, otherwise
+; things get a little more complex.
+;
+; NOTE - eax currently contains the high order word of DVSR
+;
+
+ or eax,eax ; check to see if divisor < 4194304K
+ jnz short L3 ; nope, gotta do this the hard way
+ mov ecx,LOWORD(DVSR) ; load divisor
+ mov eax,HIWORD(DVND) ; load high word of dividend
+ xor edx,edx
+ div ecx ; eax <- high order bits of quotient
+ mov ebx,eax ; save high bits of quotient
+ mov eax,LOWORD(DVND) ; edx:eax <- remainder:lo word of dividend
+ div ecx ; eax <- low order bits of quotient
+ mov edx,ebx ; edx:eax <- quotient
+ jmp short L4 ; set sign, restore stack and return
+
+;
+; Here we do it the hard way. Remember, eax contains the high word of DVSR
+;
+
+L3:
+ mov ebx,eax ; ebx:ecx <- divisor
+ mov ecx,LOWORD(DVSR)
+ mov edx,HIWORD(DVND) ; edx:eax <- dividend
+ mov eax,LOWORD(DVND)
+L5:
+ shr ebx,1 ; shift divisor right one bit
+ rcr ecx,1
+ shr edx,1 ; shift dividend right one bit
+ rcr eax,1
+ or ebx,ebx
+ jnz short L5 ; loop until divisor < 4194304K
+ div ecx ; now divide, ignore remainder
+ mov esi,eax ; save quotient
+
+;
+; We may be off by one, so to check, we will multiply the quotient
+; by the divisor and check the result against the orignal dividend
+; Note that we must also check for overflow, which can occur if the
+; dividend is close to 2**64 and the quotient is off by 1.
+;
+
+ mul dword ptr HIWORD(DVSR) ; QUOT * HIWORD(DVSR)
+ mov ecx,eax
+ mov eax,LOWORD(DVSR)
+ mul esi ; QUOT * LOWORD(DVSR)
+ add edx,ecx ; EDX:EAX = QUOT * DVSR
+ jc short L6 ; carry means Quotient is off by 1
+
+;
+; do long compare here between original dividend and the result of the
+; multiply in edx:eax. If original is larger or equal, we are ok, otherwise
+; subtract one (1) from the quotient.
+;
+
+ cmp edx,HIWORD(DVND) ; compare hi words of result and original
+ ja short L6 ; if result > original, do subtract
+ jb short L7 ; if result < original, we are ok
+ cmp eax,LOWORD(DVND) ; hi words are equal, compare lo words
+ jbe short L7 ; if less or equal we are ok, else subtract
+L6:
+ dec esi ; subtract 1 from quotient
+L7:
+ xor edx,edx ; edx:eax <- quotient
+ mov eax,esi
+
+;
+; Just the cleanup left to do. edx:eax contains the quotient. Set the sign
+; according to the save value, cleanup the stack, and return.
+;
+
+L4:
+ dec edi ; check to see if result is negative
+ jnz short L8 ; if EDI == 0, result should be negative
+ neg edx ; otherwise, negate the result
+ neg eax
+ sbb edx,0
+
+;
+; Restore the saved registers and return.
+;
+
+L8:
+ pop ebx
+ pop esi
+ pop edi
+
+ ret 16
+
+_alldiv ENDP
+
+end
diff --git a/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldiv.asm b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldiv.asm
new file mode 100644
index 0000000000..c9f07e3666
--- /dev/null
+++ b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldiv.asm
@@ -0,0 +1,157 @@
+;***
+;ulldiv.asm - unsigned long divide routine
+;
+; Copyright (c) Microsoft Corporation. All rights reserved.
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+;Purpose:
+; defines the unsigned long divide routine
+; __aulldiv
+;
+;Original Implemenation: MSVC 14.29.30133
+;
+;*******************************************************************************
+ .686
+ .model flat,C
+ .code
+
+;***
+;ulldiv - unsigned long divide
+;
+;Purpose:
+; Does a unsigned long divide of the arguments. Arguments are
+; not changed.
+;
+;Entry:
+; Arguments are passed on the stack:
+; 1st pushed: divisor (QWORD)
+; 2nd pushed: dividend (QWORD)
+;
+;Exit:
+; EDX:EAX contains the quotient (dividend/divisor)
+; NOTE: this routine removes the parameters from the stack.
+;
+;Uses:
+; ECX
+;
+;Exceptions:
+;
+;*******************************************************************************
+_aulldiv PROC NEAR
+
+HIWORD EQU [4] ;
+LOWORD EQU [0]
+
+ push ebx
+ push esi
+
+; Set up the local stack and save the index registers. When this is done
+; the stack frame will look as follows (assuming that the expression a/b will
+; generate a call to uldiv(a, b)):
+;
+; -----------------
+; | |
+; |---------------|
+; | |
+; |--divisor (b)--|
+; | |
+; |---------------|
+; | |
+; |--dividend (a)-|
+; | |
+; |---------------|
+; | return addr** |
+; |---------------|
+; | EBX |
+; |---------------|
+; ESP---->| ESI |
+; -----------------
+;
+
+DVND equ [esp + 12] ; stack address of dividend (a)
+DVSR equ [esp + 20] ; stack address of divisor (b)
+
+;
+; Now do the divide. First look to see if the divisor is less than 4194304K.
+; If so, then we can use a simple algorithm with word divides, otherwise
+; things get a little more complex.
+;
+
+ mov eax,HIWORD(DVSR) ; check to see if divisor < 4194304K
+ or eax,eax
+ jnz short L1 ; nope, gotta do this the hard way
+ mov ecx,LOWORD(DVSR) ; load divisor
+ mov eax,HIWORD(DVND) ; load high word of dividend
+ xor edx,edx
+ div ecx ; get high order bits of quotient
+ mov ebx,eax ; save high bits of quotient
+ mov eax,LOWORD(DVND) ; edx:eax <- remainder:lo word of dividend
+ div ecx ; get low order bits of quotient
+ mov edx,ebx ; edx:eax <- quotient hi:quotient lo
+ jmp short L2 ; restore stack and return
+
+;
+; Here we do it the hard way. Remember, eax contains DVSRHI
+;
+
+L1:
+ mov ecx,eax ; ecx:ebx <- divisor
+ mov ebx,LOWORD(DVSR)
+ mov edx,HIWORD(DVND) ; edx:eax <- dividend
+ mov eax,LOWORD(DVND)
+L3:
+ shr ecx,1 ; shift divisor right one bit; hi bit <- 0
+ rcr ebx,1
+ shr edx,1 ; shift dividend right one bit; hi bit <- 0
+ rcr eax,1
+ or ecx,ecx
+ jnz short L3 ; loop until divisor < 4194304K
+ div ebx ; now divide, ignore remainder
+ mov esi,eax ; save quotient
+
+;
+; We may be off by one, so to check, we will multiply the quotient
+; by the divisor and check the result against the original dividend
+; Note that we must also check for overflow, which can occur if the
+; dividend is close to 2**64 and the quotient is off by 1.
+;
+
+ mul dword ptr HIWORD(DVSR) ; QUOT * HIWORD(DVSR)
+ mov ecx,eax
+ mov eax,LOWORD(DVSR)
+ mul esi ; QUOT * LOWORD(DVSR)
+ add edx,ecx ; EDX:EAX = QUOT * DVSR
+ jc short L4 ; carry means Quotient is off by 1
+
+;
+; do long compare here between original dividend and the result of the
+; multiply in edx:eax. If original is larger or equal, we are ok, otherwise
+; subtract one (1) from the quotient.
+;
+
+ cmp edx,HIWORD(DVND) ; compare hi words of result and original
+ ja short L4 ; if result > original, do subtract
+ jb short L5 ; if result < original, we are ok
+ cmp eax,LOWORD(DVND) ; hi words are equal, compare lo words
+ jbe short L5 ; if less or equal we are ok, else subtract
+L4:
+ dec esi ; subtract 1 from quotient
+L5:
+ xor edx,edx ; edx:eax <- quotient
+ mov eax,esi
+
+;
+; Just the cleanup left to do. edx:eax contains the quotient.
+; Restore the saved registers and return.
+;
+
+L2:
+
+ pop esi
+ pop ebx
+
+ ret 16
+
+_aulldiv ENDP
+
+ end
diff --git a/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldvrm.asm b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldvrm.asm
new file mode 100644
index 0000000000..fc3a479e8a
--- /dev/null
+++ b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUlldvrm.asm
@@ -0,0 +1,184 @@
+;***
+;ulldvrm.asm - unsigned long divide and remainder routine
+;
+; Copyright (c) Microsoft Corporation. All rights reserved.
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+;Purpose:
+; defines the unsigned long divide and remainder routine
+; __aulldvrm
+;
+;Original Implemenation: MSVC 14.29.30133
+;
+;*******************************************************************************
+ .686
+ .model flat,C
+ .code
+
+
+;***
+;ulldvrm - unsigned long divide and remainder
+;
+;Purpose:
+; Does a unsigned long divide and remainder of the arguments. Arguments
+; are not changed.
+;
+;Entry:
+; Arguments are passed on the stack:
+; 1st pushed: divisor (QWORD)
+; 2nd pushed: dividend (QWORD)
+;
+;Exit:
+; EDX:EAX contains the quotient (dividend/divisor)
+; EBX:ECX contains the remainder (divided % divisor)
+; NOTE: this routine removes the parameters from the stack.
+;
+;Uses:
+; ECX
+;
+;Exceptions:
+;
+;*******************************************************************************
+_aulldvrm PROC NEAR
+
+HIWORD EQU [4] ;
+LOWORD EQU [0]
+ push esi
+
+; Set up the local stack and save the index registers. When this is done
+; the stack frame will look as follows (assuming that the expression a/b will
+; generate a call to aulldvrm(a, b)):
+;
+; -----------------
+; | |
+; |---------------|
+; | |
+; |--divisor (b)--|
+; | |
+; |---------------|
+; | |
+; |--dividend (a)-|
+; | |
+; |---------------|
+; | return addr** |
+; |---------------|
+; ESP---->| ESI |
+; -----------------
+;
+
+DVND equ [esp + 8] ; stack address of dividend (a)
+DVSR equ [esp + 16] ; stack address of divisor (b)
+
+;
+; Now do the divide. First look to see if the divisor is less than 4194304K.
+; If so, then we can use a simple algorithm with word divides, otherwise
+; things get a little more complex.
+;
+
+ mov eax,HIWORD(DVSR) ; check to see if divisor < 4194304K
+ or eax,eax
+ jnz short L1 ; nope, gotta do this the hard way
+ mov ecx,LOWORD(DVSR) ; load divisor
+ mov eax,HIWORD(DVND) ; load high word of dividend
+ xor edx,edx
+ div ecx ; get high order bits of quotient
+ mov ebx,eax ; save high bits of quotient
+ mov eax,LOWORD(DVND) ; edx:eax <- remainder:lo word of dividend
+ div ecx ; get low order bits of quotient
+ mov esi,eax ; ebx:esi <- quotient
+
+;
+; Now we need to do a multiply so that we can compute the remainder.
+;
+ mov eax,ebx ; set up high word of quotient
+ mul dword ptr LOWORD(DVSR) ; HIWORD(QUOT) * DVSR
+ mov ecx,eax ; save the result in ecx
+ mov eax,esi ; set up low word of quotient
+ mul dword ptr LOWORD(DVSR) ; LOWORD(QUOT) * DVSR
+ add edx,ecx ; EDX:EAX = QUOT * DVSR
+ jmp short L2 ; complete remainder calculation
+
+;
+; Here we do it the hard way. Remember, eax contains DVSRHI
+;
+
+L1:
+ mov ecx,eax ; ecx:ebx <- divisor
+ mov ebx,LOWORD(DVSR)
+ mov edx,HIWORD(DVND) ; edx:eax <- dividend
+ mov eax,LOWORD(DVND)
+L3:
+ shr ecx,1 ; shift divisor right one bit; hi bit <- 0
+ rcr ebx,1
+ shr edx,1 ; shift dividend right one bit; hi bit <- 0
+ rcr eax,1
+ or ecx,ecx
+ jnz short L3 ; loop until divisor < 4194304K
+ div ebx ; now divide, ignore remainder
+ mov esi,eax ; save quotient
+
+;
+; We may be off by one, so to check, we will multiply the quotient
+; by the divisor and check the result against the original dividend
+; Note that we must also check for overflow, which can occur if the
+; dividend is close to 2**64 and the quotient is off by 1.
+;
+
+ mul dword ptr HIWORD(DVSR) ; QUOT * HIWORD(DVSR)
+ mov ecx,eax
+ mov eax,LOWORD(DVSR)
+ mul esi ; QUOT * LOWORD(DVSR)
+ add edx,ecx ; EDX:EAX = QUOT * DVSR
+ jc short L4 ; carry means Quotient is off by 1
+
+;
+; do long compare here between original dividend and the result of the
+; multiply in edx:eax. If original is larger or equal, we are ok, otherwise
+; subtract one (1) from the quotient.
+;
+
+ cmp edx,HIWORD(DVND) ; compare hi words of result and original
+ ja short L4 ; if result > original, do subtract
+ jb short L5 ; if result < original, we are ok
+ cmp eax,LOWORD(DVND) ; hi words are equal, compare lo words
+ jbe short L5 ; if less or equal we are ok, else subtract
+L4:
+ dec esi ; subtract 1 from quotient
+ sub eax,LOWORD(DVSR) ; subtract divisor from result
+ sbb edx,HIWORD(DVSR)
+L5:
+ xor ebx,ebx ; ebx:esi <- quotient
+
+L2:
+;
+; Calculate remainder by subtracting the result from the original dividend.
+; Since the result is already in a register, we will do the subtract in the
+; opposite direction and negate the result.
+;
+
+ sub eax,LOWORD(DVND) ; subtract dividend from result
+ sbb edx,HIWORD(DVND)
+ neg edx ; otherwise, negate the result
+ neg eax
+ sbb edx,0
+
+;
+; Now we need to get the quotient into edx:eax and the remainder into ebx:ecx.
+;
+ mov ecx,edx
+ mov edx,ebx
+ mov ebx,ecx
+ mov ecx,eax
+ mov eax,esi
+;
+; Just the cleanup left to do. edx:eax contains the quotient.
+; Restore the saved registers and return.
+;
+
+ pop esi
+
+ ret 16
+
+_aulldvrm ENDP
+
+ end
diff --git a/CryptoPkg/Library/IntrinsicLib/Ia32/MathUllrem.asm b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUllrem.asm
new file mode 100644
index 0000000000..755fef24d0
--- /dev/null
+++ b/CryptoPkg/Library/IntrinsicLib/Ia32/MathUllrem.asm
@@ -0,0 +1,163 @@
+;***
+;ullrem.asm - unsigned long remainder routine
+;
+; Copyright (c) Microsoft Corporation. All rights reserved.
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+;Purpose:
+; defines the unsigned long remainder routine
+; __aullrem
+;
+;Original Implemenation: MSVC 14.29.30133
+;
+;*******************************************************************************
+ .686
+ .model flat,C
+ .code
+
+
+;***
+;ullrem - unsigned long remainder
+;
+;Purpose:
+; Does a unsigned long remainder of the arguments. Arguments are
+; not changed.
+;
+;Entry:
+; Arguments are passed on the stack:
+; 1st pushed: divisor (QWORD)
+; 2nd pushed: dividend (QWORD)
+;
+;Exit:
+; EDX:EAX contains the remainder (dividend%divisor)
+; NOTE: this routine removes the parameters from the stack.
+;
+;Uses:
+; ECX
+;
+;Exceptions:
+;
+;*******************************************************************************
+_aullrem PROC NEAR
+
+HIWORD EQU [4] ;
+LOWORD EQU [0]
+
+ push ebx
+
+; Set up the local stack and save the index registers. When this is done
+; the stack frame will look as follows (assuming that the expression a%b will
+; generate a call to ullrem(a, b)):
+;
+; -----------------
+; | |
+; |---------------|
+; | |
+; |--divisor (b)--|
+; | |
+; |---------------|
+; | |
+; |--dividend (a)-|
+; | |
+; |---------------|
+; | return addr** |
+; |---------------|
+; ESP---->| EBX |
+; -----------------
+;
+
+DVND equ [esp + 8] ; stack address of dividend (a)
+DVSR equ [esp + 16] ; stack address of divisor (b)
+
+; Now do the divide. First look to see if the divisor is less than 4194304K.
+; If so, then we can use a simple algorithm with word divides, otherwise
+; things get a little more complex.
+;
+
+ mov eax,HIWORD(DVSR) ; check to see if divisor < 4194304K
+ or eax,eax
+ jnz short L1 ; nope, gotta do this the hard way
+ mov ecx,LOWORD(DVSR) ; load divisor
+ mov eax,HIWORD(DVND) ; load high word of dividend
+ xor edx,edx
+ div ecx ; edx <- remainder, eax <- quotient
+ mov eax,LOWORD(DVND) ; edx:eax <- remainder:lo word of dividend
+ div ecx ; edx <- final remainder
+ mov eax,edx ; edx:eax <- remainder
+ xor edx,edx
+ jmp short L2 ; restore stack and return
+
+;
+; Here we do it the hard way. Remember, eax contains DVSRHI
+;
+
+L1:
+ mov ecx,eax ; ecx:ebx <- divisor
+ mov ebx,LOWORD(DVSR)
+ mov edx,HIWORD(DVND) ; edx:eax <- dividend
+ mov eax,LOWORD(DVND)
+L3:
+ shr ecx,1 ; shift divisor right one bit; hi bit <- 0
+ rcr ebx,1
+ shr edx,1 ; shift dividend right one bit; hi bit <- 0
+ rcr eax,1
+ or ecx,ecx
+ jnz short L3 ; loop until divisor < 4194304K
+ div ebx ; now divide, ignore remainder
+
+;
+; We may be off by one, so to check, we will multiply the quotient
+; by the divisor and check the result against the orignal dividend
+; Note that we must also check for overflow, which can occur if the
+; dividend is close to 2**64 and the quotient is off by 1.
+;
+
+ mov ecx,eax ; save a copy of quotient in ECX
+ mul dword ptr HIWORD(DVSR)
+ xchg ecx,eax ; put partial product in ECX, get quotient in EAX
+ mul dword ptr LOWORD(DVSR)
+ add edx,ecx ; EDX:EAX = QUOT * DVSR
+ jc short L4 ; carry means Quotient is off by 1
+
+;
+; do long compare here between original dividend and the result of the
+; multiply in edx:eax. If original is larger or equal, we're ok, otherwise
+; subtract the original divisor from the result.
+;
+
+ cmp edx,HIWORD(DVND) ; compare hi words of result and original
+ ja short L4 ; if result > original, do subtract
+ jb short L5 ; if result < original, we're ok
+ cmp eax,LOWORD(DVND) ; hi words are equal, compare lo words
+ jbe short L5 ; if less or equal we're ok, else subtract
+L4:
+ sub eax,LOWORD(DVSR) ; subtract divisor from result
+ sbb edx,HIWORD(DVSR)
+L5:
+
+;
+; Calculate remainder by subtracting the result from the original dividend.
+; Since the result is already in a register, we will perform the subtract in
+; the opposite direction and negate the result to make it positive.
+;
+
+ sub eax,LOWORD(DVND) ; subtract original dividend from result
+ sbb edx,HIWORD(DVND)
+ neg edx ; and negate it
+ neg eax
+ sbb edx,0
+
+;
+; Just the cleanup left to do. dx:ax contains the remainder.
+; Restore the saved registers and return.
+;
+
+L2:
+
+ pop ebx
+
+ ret 16
+
+_aullrem ENDP
+
+ end
diff --git a/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf b/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf
index 86e74b57b1..2ec987b260 100644
--- a/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf
+++ b/CryptoPkg/Library/IntrinsicLib/IntrinsicLib.inf
@@ -32,6 +32,10 @@
Ia32/MathFtol.c | MSFT
Ia32/MathLlmul.asm | MSFT
Ia32/MathLlshr.asm | MSFT
+ Ia32/MathUlldiv.asm | MSFT
+ Ia32/MathUlldvrm.asm | MSFT
+ Ia32/MathLldiv.asm | MSFT
+ Ia32/MathUllrem.asm | MSFT
Ia32/MathLShiftS64.c | INTEL
Ia32/MathRShiftU64.c | INTEL
--
2.31.1.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#107498): https://edk2.groups.io/g/devel/message/107498
Mute This Topic: https://groups.io/mt/100520600/7686176
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [rebecca@openfw.io]
-=-=-=-=-=-=-=-=-=-=-=-
next prev parent reply other threads:[~2023-08-03 4:39 UTC|newest]
Thread overview: 30+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-08-03 4:37 [edk2-devel] [PATCH V2 00/29] CryptoPkg: Update OpenSSL submodule to 3.0.9 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 01/29] CryptoPkg/openssl: update submodule to openssl-3.0.9 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 02/29] CryptoPkg/openssl: cleanup all openssl1.1.1 generated files and code Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 03/29] CryptoPkg/openssl: update Openssl*.inf files for openssl 3.0 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 04/29] CryptoPkg/openssl: add openssl3 configure scripts Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 05/29] CryptoPkg/openssl: UefiAsm.conf update for openssl 3.0 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 06/29] CryptoPkg/BaseCryptLib: no openssl deprecation warnings please Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 07/29] CryptoPkg/BaseCryptLib: adapt CryptSm3.c to openssl 3.0 changes Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 08/29] CryptoPkg/BaseCryptLib: drop BIO_* dummy functions Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 09/29] CryptoPkg/TlsLib: ERR_GET_FUNC is gone Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 10/29] CryptoPkg/openssl: adapt rand_pool.c to openssl 3.0 changes Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 11/29] CryptoPkg/openssl: move compiler_flags to buildinf.c Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 12/29] CryptoPkg/openssl: store dummy update for openssl 3.0 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 13/29] CryptoPkg/openssl: adapt EcSm2Null.c " Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 14/29] CryptoPkg: Move all UEFI implement of openssl to OpensslStub Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 15/29] CryptoPkg: use UEFI provider as default Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 16/29] CryptoPkg: adapt 3.0 change in SslNull.c Li, Yi
2023-08-03 4:37 ` Li, Yi [this message]
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 18/29] CryptoPkg: disable C4133 warning in openssl libraries Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 19/29] CryptoPkg/TlsLib: use unsigned long for ErrorCode Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 20/29] CryptoPkg: Align with 4096 when build with OpensslFullAccel Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 21/29] CryptoPkg: Enable memcpy sys call in RISCV64 build Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 22/29] CryptoPkg: add missing gcc instructions Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 23/29] CryptoPkg: add define of maximum unsigned size_t Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 24/29] CryptoPkg: add implemention of _ftol2_sse() to avoid build error Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 25/29] CryptoPkg: add more dummy implement of openssl for size optimization Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 26/29] CryptoPkg: run configure.py to update all generated files Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 27/29] CryptoPkg: remove strcmp to syscall Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 28/29] CryptoPkg/openssl: update CI config for openssl 3.0 Li, Yi
2023-08-03 4:37 ` [edk2-devel] [PATCH V2 29/29] CryptoPkg: remove BN and EC accel for size optimization Li, Yi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-list from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=0fac263e9500511f8ef4286e51b8887c1a10ddaa.1691031203.git.yi1.li@intel.com \
--to=devel@edk2.groups.io \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox