Home | History | Annotate | Download | only in Ia32
      1 /*++
      2 
      3 Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
      4 This program and the accompanying materials
      5 are licensed and made available under the terms and conditions of the BSD License
      6 which accompanies this distribution.  The full text of the license may be found at
      7 http://opensource.org/licenses/bsd-license.php
      8 
      9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     11 
     12 Module Name:
     13 
     14   DivU64x32.c
     15 
     16 Abstract:
     17 
     18   64-bit division function for IA-32
     19 
     20 --*/
     21 
     22 #include "Tiano.h"
     23 
     24 UINT64
     25 DivU64x32 (
     26   IN UINT64   Dividend,
     27   IN UINTN    Divisor,
     28   OUT UINTN   *Remainder OPTIONAL
     29   )
     30 /*++
     31 
     32 Routine Description:
     33 
     34   This routine allows a 64 bit value to be divided with a 32 bit value returns
     35   64bit result and the Remainder.
     36 
     37 Arguments:
     38 
     39   Dividend  - dividend
     40   Divisor   - divisor
     41   Remainder - buffer for remainder
     42 
     43 Returns:
     44 
     45   Dividend  / Divisor
     46   Remainder = Dividend mod Divisor
     47 
     48 N.B. only works for 31bit divisors!!
     49 
     50 --*/
     51 {
     52   __asm {
     53     xor edx, edx                    ; Clear EDX
     54 
     55     mov eax, dword ptr Dividend[4]  ; Put high 32 bits of 64-bit dividend in EAX
     56     mov ecx, Divisor                ; Put 32 bits divisor in ECX
     57     div ecx                         ; Dividend   Divisor  Quoitent...Remainder
     58                                     ;  0:EAX  /  ECX   =  EAX      EDX
     59 
     60     push eax                        ; Push quoitent in stack
     61 
     62     mov eax, dword ptr Dividend[0]  ; Put low 32 bits of 64-bit dividend in EAX
     63     div ecx                         ; Leave the REMAINDER in EDX as High 32-bit of new dividend
     64                                     ; Dividend   Divisor  Quoitent...Remainder
     65                                     ;  EDX:EAX  /  ECX   =  EAX      EDX
     66 
     67     mov ecx, Remainder              ; Put &REMAINDER to ecx
     68 
     69     jecxz Label1                    ; If ecx == 0, no remainder exist, return with quoitent in EDX directly
     70     mov dword ptr [ecx], edx        ; Put EDX through REMAINDER pointer in ECX
     71 
     72 Label1:
     73     pop edx                         ; Pop High 32-bit QUOITENT to EDX
     74   }
     75 }
     76