1 /** @file
2   64-bit Math Worker Function.
3   The 32-bit versions of C compiler generate calls to library routines
4   to handle 64-bit math. These functions use non-standard calling conventions.
5 
6   Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>
7   This program and the accompanying materials are licensed and made available
8   under the terms and conditions of the BSD License which accompanies this
9   distribution.  The full text of the license may be found at
10   http://opensource.org/licenses/bsd-license.php.
11 
12   THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
13   WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
14 
15 **/
16 
17 #include <Library/BaseLib.h>
18 
19 
20 /*
21  * Divides a 64-bit signed value by another 64-bit signed value and returns
22  * the 64-bit signed result and the 64-bit signed remainder.
23  */
_alldvrm(void)24 __declspec(naked) void __cdecl _alldvrm(void)
25 {
26   //
27   // Wrapper Implementation over EDKII DivS64x64Remainder() routine
28   //    INT64
29   //    EFIAPI
30   //    DivS64x64Remainder (
31   //      IN      INT64     Dividend,
32   //      IN      INT64     Divisor,
33   //      OUT     INT64     *Remainder
34   //      )
35   //
36   _asm {
37     ; Original local stack when calling _alldvrm
38     ;               -----------------
39     ;               |               |
40     ;               |---------------|
41     ;               |               |
42     ;               |--  Divisor  --|
43     ;               |               |
44     ;               |---------------|
45     ;               |               |
46     ;               |--  Dividend --|
47     ;               |               |
48     ;               |---------------|
49     ;               |  ReturnAddr** |
50     ;       ESP---->|---------------|
51     ;
52     ;
53     ; On Exit:
54     ;       EDX:EAX contains the quotient (dividend/divisor)
55     ;       EBX:ECX contains the remainder (divided % divisor)
56     ;       NOTE: this routine removes the parameters from the stack.
57     ;
58 
59     ;
60     ; Set up the local stack for Reminder pointer
61     ;
62     sub  esp, 8
63     push esp
64 
65     ;
66     ; Set up the local stack for Divisor parameter
67     ;
68     mov  eax, [esp + 28]
69     push eax
70     mov  eax, [esp + 28]
71     push eax
72 
73     ;
74     ; Set up the local stack for Dividend parameter
75     ;
76     mov  eax, [esp + 28]
77     push eax
78     mov  eax, [esp + 28]
79     push eax
80 
81     ;
82     ; Call native DivS64x64Remainder of BaseLib
83     ;
84     call DivS64x64Remainder
85 
86     ;
87     ; EDX:EAX contains the quotient (dividend/divisor)
88     ; Put the Remainder in EBX:ECX
89     ;
90     mov  ecx, [esp + 20]
91     mov  ebx, [esp + 24]
92 
93     ;
94     ; Adjust stack
95     ;
96     add  esp, 28
97 
98     ret  16
99   }
100 }
101