Annotation of coherent/b/kernel/emulator/reg_div.S, revision 1.1.1.1

1.1       root        1:        .file   "reg_div.S"
                      2: /*---------------------------------------------------------------------------+
                      3:  |  reg_div.S                                                                |
                      4:  |                                                                           |
                      5:  | Divide one FPU_REG by another and put the result in a destination FPU_REG.|
                      6:  |                                                                           |
                      7:  | Copyright (C) 1992    W. Metzenthen, 22 Parker St, Ormond, Vic 3163,      |
                      8:  |                       Australia.  E-mail [email protected]    |
                      9:  |                                                                           |
                     10:  | Call from C as:                                                           |
                     11:  |   void reg_div(FPU_REG *a, FPU_REG *b, FPU_REG *dest)                     |
                     12:  |                                                                           |
                     13:  +---------------------------------------------------------------------------*/
                     14: 
                     15: #include "exception.h"
                     16: #include "fpu_asm.h"
                     17: 
                     18: .text
                     19:        .align 2
                     20: 
                     21: .globl reg_div
                     22: reg_div:
                     23:        pushl   %ebp
                     24:        movl    %esp,%ebp
                     25: 
                     26:        pushl   %esi
                     27:        pushl   %edi
                     28:        pushl   %ebx
                     29: 
                     30:        movl    PARAM1,%esi
                     31:        movl    PARAM2,%ebx
                     32:        movl    PARAM3,%edi
                     33: 
                     34:        movb    TAG(%esi),%al
                     35:        orb     TAG(%ebx),%al
                     36: 
                     37:        jne     xL_div_special          // Not (both numbers TW_Valid)
                     38: 
                     39: 
                     40: // Both arguments are TW_Valid
                     41:        movl    EXP(%esi),%edx
                     42:        movl    EXP(%ebx),%eax
                     43:        subl    %eax,%edx
                     44:        addl    EXP_BIAS,%edx
                     45:        movl    %edx,EXP(%edi)
                     46: 
                     47:        movb    TW_Valid,TAG(%edi)
                     48: 
                     49:        movb    SIGN(%esi),%cl
                     50:        cmpb    %cl,SIGN(%ebx)
                     51: /      changed to get it through my assembler
                     52: /      setneb  (%edi)          // Set the sign, requires neg=1, pos=0
                     53:        setne   (%edi)
                     54:        add     $SIGL_OFFSET,%ebx
                     55:        add     $SIGL_OFFSET,%esi
                     56: 
                     57:        jmp     divide_kernel
                     58: 
                     59: 
                     60: /*-----------------------------------------------------------------------*/
                     61: xL_div_special:
                     62:        cmpb    TW_NaN,TAG(%esi)        // A NaN with anything to give NaN
                     63:        je      xL_arg1_NaN
                     64: 
                     65:        cmpb    TW_NaN,TAG(%ebx)        // A NaN with anything to give NaN
                     66:        jne     xL_no_NaN_arg
                     67: 
                     68: // Operations on NaNs
                     69: xL_arg1_NaN:
                     70: xL_arg2_NaN:
                     71:        pushl   %edi
                     72:        pushl   %ebx
                     73:        pushl   %esi
                     74:        call    real_2op_NaN
                     75:        jmp     xL78
                     76: 
                     77: // Invalid operations
                     78: xL_zero_zero:
                     79: xL_inf_inf:
                     80:        pushl   %esi
                     81:        call    arith_invalid
                     82:        jmp     xL78
                     83: 
                     84: xL_no_NaN_arg:
                     85:        cmpb    TW_Infinity,TAG(%esi)
                     86:        jne     xL_arg1_not_inf
                     87: 
                     88:        cmpb    TW_Infinity,TAG(%ebx)
                     89:        je      xL_inf_inf      // invalid operation
                     90: 
                     91:        // Note that p16-9 says that infinity/0 returns infinity
                     92:        jmp     xL_copy_arg1            // Answer is Inf
                     93: 
                     94: xL_arg1_not_inf:
                     95:        cmpb    TW_Zero,TAG(%ebx)               // Priority to div-by-zero error
                     96:        jne     xL_arg2_not_zero
                     97: 
                     98:        cmpb    TW_Zero,TAG(%esi)
                     99:        je      xL_zero_zero    // invalid operation
                    100: 
                    101: // Division by zero error
                    102:        pushl   %esi
                    103:        movb    SIGN(%esi),%al
                    104:        xorb    SIGN(%ebx),%al
                    105:        pushl   %eax            // lower 8 bits have the sign
                    106:        call    divide_by_zero
                    107:        jmp     xL78
                    108: 
                    109: xL_arg2_not_zero:
                    110:        cmpb    TW_Infinity,TAG(%ebx)
                    111:        jne     xL_arg2_not_inf
                    112: 
                    113:        jmp     xL_return_zero          // Answer is zero
                    114: 
                    115: xL_arg2_not_inf:
                    116:        cmpb    TW_Zero,TAG(%esi)
                    117:        jne     xL_unknown_tags
                    118: 
                    119: xL_copy_arg1:
                    120:        mov     TAG(%esi),%ax
                    121:        mov     %ax,TAG(%edi)
                    122:        movl    EXP(%esi),%eax
                    123:        movl    %eax,EXP(%edi)
                    124:        movl    SIGL(%esi),%eax
                    125:        movl    %eax,SIGL(%edi)
                    126:        movl    SIGH(%esi),%eax
                    127:        movl    %eax,SIGH(%edi)
                    128: 
                    129:        movb    SIGN(%esi),%cl
                    130:        cmpb    %cl,SIGN(%ebx)
                    131:        jne     xL76
                    132: 
                    133:        movb    SIGN_POS,SIGN(%edi)
                    134:        jmp     xL78
                    135: 
                    136: xL71:
                    137:        movb    SIGN(%esi),%cl
                    138:        cmpb    %cl,SIGN(%edi)
                    139:        jne     xL76
                    140: 
                    141:        movb    SIGN_POS,SIGN(%ebx)
                    142:        jmp     xL78
                    143: 
                    144:        .align 2,0x90
                    145: xL76:
                    146:        movb    SIGN_NEG,SIGN(%edi)
                    147: 
                    148: xL78:
                    149:        leal    -12(%ebp),%esp
                    150: 
                    151:        popl    %ebx
                    152:        popl    %edi
                    153:        popl    %esi
                    154:        leave
                    155:        ret
                    156: 
                    157: 
                    158: xL_return_zero:
                    159:        movb    TW_Zero,TAG(%edi)
                    160:        jmp     xL71
                    161: 
                    162: xL_unknown_tags:
                    163:        push    EX_INTERNAL | 0x208
                    164:        call    EXCEPTION
                    165: 
                    166:        // Generate a NaN for unknown tags
                    167:        movl    CONST_QNaN,%eax
                    168:        movl    %eax,(%edi)
                    169:        movl    CONST_QNaN+4,%eax
                    170:        movl    %eax,SIGL(%edi)
                    171:        movl    CONST_QNaN+8,%eax
                    172:        movl    %eax,SIGH(%edi)
                    173:        jmp     xL78

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.