File: dos\mpmath_a.asm

    1 TITLE mpmath_a.asm (C) 1989, Mark C. Peterson, CompuServe [70441,3353]
    2 SUBTTL All rights reserved.
    3 ;
    4 ;  Code may be used in any program provided the author is credited
    5 ;    either during program execution or in the documentation.  Source
    6 ;    code may be distributed only in combination with public domain or
    7 ;    shareware source code.  Source code may be modified provided the
    8 ;    copyright notice and this message is left unchanged and all
    9 ;    modifications are clearly documented.
   10 ;
   11 ;    I would appreciate a copy of any work which incorporates this code,
   12 ;    however this is optional.
   13 ;
   14 ;    Mark C. Peterson
   15 ;    405-C Queen St., Suite #181
   16 ;    Southington, CT 06489
   17 ;    (203) 276-9721
   18 ;
   19 ;  Note: Remark statements following floating point commands generally indicate
   20 ;     the FPU stack contents after the command is completed.
   21 ;
   22 ;  References:
   23 ;     80386/80286 Assembly Language Programming
   24 ;        by William H. Murray, III and Chris H. Pappas
   25 ;        Published by Osborne McGraw-Hill, 1986
   26 ;
   27 ;
   28 ;
   29 
   30 
   31 IFDEF ??version
   32 MASM51
   33 QUIRKS
   34 ENDIF
   35 
   36 .model medium, c
   37 
   38 
   39 .data
   40 
   41 extrn cpu:WORD
   42 
   43 
   44 MP STRUC
   45    Exp   DW    0
   46    Mant  DD    0
   47 MP ENDS
   48 
   49 
   50 PUBLIC MPOverflow
   51 PUBLIC Ans
   52 MPOverflow  DW        0
   53 
   54 Ans         MP       
   55 Double      DQ        ?
   56 
   57 
   58 .code
   59 
   60 .8086
   61 
   62 fg2MP086    PROC     x:DWORD, fg:WORD
   63    mov   ax, WORD PTR [x]
   64    mov   dx, WORD PTR [x+2]
   65    mov   cx, ax
   66    or    cx, dx
   67    jz    ExitFg2MP
   68 
   69    mov   cx, 1 SHL 14 + 30
   70    sub   cx, fg
   71 
   72    or    dx, dx
   73    jns   BitScanRight
   74 
   75    or    ch, 80h
   76    not   ax
   77    not   dx
   78    add   ax, 1
   79    adc   dx, 0
   80 
   81 BitScanRight:
   82    shl   ax, 1
   83    rcl   dx, 1
   84    dec   cx
   85    or    dx, dx
   86    jns   BitScanRight
   87 
   88 ExitFg2MP:
   89    mov   Ans.Exp, cx
   90    mov   WORD PTR Ans.Mant+2, dx
   91    mov   WORD PTR Ans.Mant, ax
   92    lea   ax, Ans
   93    mov   dx, ds
   94    ret
   95 fg2MP086    ENDP
   96 
   97 
   98 
   99 MPcmp086    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, yMant:DWORD
  100 LOCAL Rev:WORD, Flag:WORD
  101    mov   Rev, 0
  102    mov   Flag, 0
  103    mov   ax, xExp
  104    mov   dx, WORD PTR [xMant]
  105    mov   si, WORD PTR [xMant+2]
  106    mov   bx, yExp
  107    mov   cx, WORD PTR [yMant]
  108    mov   di, WORD PTR [yMant+2]
  109    or    ax, ax
  110    jns   AtLeastOnePos
  111 
  112    or    bx, bx
  113    jns   AtLeastOnePos
  114 
  115    mov   Rev, 1
  116    and   ah, 7fh
  117    and   bh, 7fh
  118 
  119 AtLeastOnePos:
  120    cmp   ax, bx
  121    jle   Cmp1
  122 
  123    mov   Flag, 1
  124    jmp   ChkRev
  125 
  126 Cmp1:
  127    je    Cmp2
  128 
  129    mov   Flag, -1
  130    jmp   ChkRev
  131 
  132 Cmp2:
  133    cmp   si, di
  134    jbe   Cmp3
  135 
  136    mov   Flag, 1
  137    jmp   ChkRev
  138 
  139 Cmp3:
  140    je    Cmp4
  141 
  142    mov   Flag, -1
  143    jmp   ChkRev
  144 
  145 Cmp4:
  146    cmp   dx, cx
  147    jbe   Cmp5
  148 
  149    mov   Flag, 1
  150    jmp   ChkRev
  151 
  152 Cmp5:
  153    je    ChkRev
  154 
  155    mov   Flag, -1
  156 
  157 ChkRev:
  158         or    Rev, 0
  159    jz    ExitCmp
  160 
  161    neg   Flag
  162 
  163 ExitCmp:
  164    mov   ax, Flag
  165    ret
  166 MPcmp086    ENDP
  167 
  168 
  169 
  170 
  171 
  172 
  173 MPmul086    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, yMant:DWORD
  174    mov   ax, xExp
  175    mov   bx, yExp
  176    xor   ch, ch
  177    shl   bh, 1
  178    rcr   ch, 1
  179    shr   bh, 1
  180    xor   ah, ch
  181 
  182    sub   bx, (1 SHL 14) - 2
  183    add   ax, bx
  184    jno   NoOverflow
  185 
  186 Overflow:
  187    or    WORD PTR [xMant+2], 0
  188    jz    ZeroAns
  189    or    WORD PTR [yMant+2], 0
  190    jz    ZeroAns
  191 
  192    mov   MPOverflow, 1
  193 
  194 ZeroAns:
  195    xor   ax, ax
  196    xor   dx, dx
  197    mov   Ans.Exp, ax
  198    jmp   StoreMant
  199 
  200 NoOverflow:
  201    mov   Ans.Exp, ax
  202 
  203    mov   si, WORD PTR [xMant+2]
  204    mov   bx, WORD PTR [xMant]
  205    mov   di, WORD PTR [yMant+2]
  206    mov   cx, WORD PTR [yMant]
  207 
  208    mov   ax, si
  209    or    ax, bx
  210    jz    ZeroAns
  211 
  212    mov   ax, di
  213    or    ax, cx
  214    jz    ZeroAns
  215 
  216    mov   ax, cx
  217    mul   bx
  218    push  dx
  219 
  220    mov   ax, cx
  221    mul   si
  222    push  ax
  223    push  dx
  224 
  225    mov   ax, bx
  226    mul   di
  227    push  ax
  228    push  dx
  229 
  230    mov   ax, si
  231    mul   di
  232    pop   bx
  233    pop   cx
  234    pop   si
  235    pop   di
  236 
  237    add   ax, bx
  238    adc   dx, 0
  239    pop   bx
  240    add   di, bx
  241    adc   ax, 0
  242    adc   dx, 0
  243    add   di, cx
  244    adc   ax, si
  245    adc   dx, 0
  246 
  247    or    dx, dx
  248    js    StoreMant
  249 
  250    shl   di, 1
  251    rcl   ax, 1
  252    rcl   dx, 1
  253    sub   Ans.Exp, 1
  254    jo    Overflow
  255 
  256 StoreMant:
  257    mov   WORD PTR Ans.Mant+2, dx
  258    mov   WORD PTR Ans.Mant, ax
  259 
  260    lea   ax, Ans
  261    mov   dx, ds
  262    ret
  263 MPmul086    ENDP
  264 
  265 
  266 
  267 d2MP086     PROC     uses si di, x:QWORD
  268    mov   dx, WORD PTR [x+6]
  269    mov   ax, WORD PTR [x+4]
  270    mov   bx, WORD PTR [x+2]
  271    mov   cx, WORD PTR [x]
  272    mov   si, dx
  273    shl   si, 1
  274    or    si, bx
  275    or    si, ax
  276    or    si, dx
  277    or    si, cx
  278    jnz   NonZero
  279 
  280    xor   ax, ax
  281    xor   dx, dx
  282    jmp   StoreAns
  283 
  284 NonZero:
  285    mov   si, dx
  286    shl   si, 1
  287    pushf
  288    mov   cl, 4
  289    shr   si, cl
  290    popf
  291    rcr   si, 1
  292    add   si, (1 SHL 14) - (1 SHL 10)
  293 
  294    mov   di, ax                           ; shl dx:ax:bx 12 bits
  295    mov   cl, 12
  296    shl   dx, cl
  297    shl   ax, cl
  298    mov   cl, 4
  299    shr   di, cl
  300    shr   bx, cl
  301    or    dx, di
  302    or    ax, bx
  303    stc
  304    rcr   dx, 1
  305    rcr   ax, 1
  306 
  307 StoreAns:
  308    mov   Ans.Exp, si
  309    mov   WORD PTR Ans.Mant+2, dx
  310    mov   WORD PTR Ans.Mant, ax
  311 
  312    lea   ax, Ans
  313    mov   dx, ds
  314    ret
  315 d2MP086     ENDP
  316 
  317 
  318 
  319 MP2d086     PROC     uses si di, xExp:WORD, xMant:DWORD
  320    sub   xExp, (1 SHL 14) - (1 SHL 10)
  321    jo    Overflow
  322 
  323    mov   bx, xExp
  324    and   bx, 0111100000000000b
  325    jz    InRangeOfDouble
  326 
  327 Overflow:
  328    mov   MPOverflow, 1
  329    xor   ax, ax
  330    xor   dx, dx
  331    xor   bx, bx
  332    jmp   StoreAns
  333 
  334 InRangeOfDouble:
  335    mov   si, xExp
  336    mov   ax, si
  337    mov   cl, 5
  338    shl   si, cl
  339    shl   ax, 1
  340    rcr   si, 1
  341 
  342    mov   dx, WORD PTR [xMant+2]
  343    mov   ax, WORD PTR [xMant]
  344    shl   ax, 1
  345    rcl   dx, 1
  346 
  347    mov   bx, ax
  348    mov   di, dx
  349    mov   cl, 12
  350    shr   dx, cl
  351    shr   ax, cl
  352    mov   cl, 4
  353    shl   bx, cl
  354    shl   di, cl
  355    or    ax, di
  356    or    dx, si
  357 
  358 StoreAns:
  359    mov   WORD PTR Double+6, dx
  360    mov   WORD PTR Double+4, ax
  361    mov   WORD PTR Double+2, bx
  362    xor   bx, bx
  363    mov   WORD PTR Double, bx
  364 
  365    lea   ax, Double
  366    mov   dx, ds
  367    ret
  368 MP2d086     ENDP
  369 
  370 
  371 
  372 
  373 MPadd086    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, yMant:DWORD
  374    mov   si, xExp
  375    mov   dx, WORD PTR [xMant+2]
  376    mov   ax, WORD PTR [xMant]
  377 
  378    mov   di, yExp
  379 
  380    mov   cx, si
  381    xor   cx, di
  382    js    Subtract
  383    jz    SameMag
  384 
  385    cmp   si, di
  386    jg    XisGreater
  387 
  388    xchg  si, di
  389    xchg  dx, WORD PTR [yMant+2]
  390    xchg  ax, WORD PTR [yMant]
  391 
  392 XisGreater:
  393    mov   cx, si
  394    sub   cx, di
  395    cmp   cx, 32
  396    jl    ChkSixteen
  397    jmp   StoreAns
  398 
  399 ChkSixteen:
  400    cmp   cx, 16
  401    jl    SixteenBitShift
  402 
  403    sub   cx, 16
  404    mov   bx, WORD PTR [yMant+2]
  405    shr   bx, cl
  406    mov   WORD PTR [yMant], bx
  407    mov   WORD PTR [yMant+2], 0
  408    jmp   SameMag
  409 
  410 SixteenBitShift:
  411    mov   bx, WORD PTR [yMant+2]
  412    shr   WORD PTR [yMant+2], cl
  413    shr   WORD PTR [yMant], cl
  414    neg   cl
  415    add   cl, 16
  416    shl   bx, cl
  417    or    WORD PTR [yMant], bx
  418 
  419 SameMag:
  420    add   ax, WORD PTR [yMant]
  421    adc   dx, WORD PTR [yMant+2]
  422    jc    ShiftCarry
  423    jmp   StoreAns
  424 
  425 ShiftCarry:
  426    rcr   dx, 1
  427    rcr   ax, 1
  428    add   si, 1
  429    jo    Overflow
  430    jmp   StoreAns
  431 
  432 Overflow:
  433    mov   MPOverflow, 1
  434 
  435 ZeroAns:
  436    xor   si, si
  437    xor   ax, ax
  438    xor   dx, dx
  439    jmp   StoreAns
  440 
  441 Subtract:
  442    xor   di, 8000h
  443    mov   cx, si
  444    sub   cx, di
  445    jnz   DifferentMag
  446 
  447    cmp   dx, WORD PTR [yMant+2]
  448    jg    SubtractNumbers
  449    jne   SwapNumbers
  450 
  451    cmp   ax, WORD PTR [yMant]
  452    jg    SubtractNumbers
  453    je    ZeroAns
  454 
  455 SwapNumbers:
  456    xor   si, 8000h
  457    xchg  ax, WORD PTR [yMant]
  458    xchg  dx, WORD PTR [yMant+2]
  459    jmp   SubtractNumbers
  460 
  461 DifferentMag:
  462    or    cx, cx
  463    jns   NoSwap
  464 
  465    xchg  si, di
  466    xchg  ax, WORD PTR [yMant]
  467    xchg  dx, WORD PTR [yMant+2]
  468    xor   si, 8000h
  469    neg   cx
  470 
  471 NoSwap:
  472    cmp   cx, 32
  473    jge   StoreAns
  474 
  475    cmp   cx, 16
  476    jl    SixteenBitShift2
  477 
  478    sub   cx, 16
  479    mov   bx, WORD PTR [yMant+2]
  480    shr   bx, cl
  481    mov   WORD PTR [yMant], bx
  482    mov   WORD PTR [yMant+2], 0
  483    jmp   SubtractNumbers
  484 
  485 SixteenBitShift2:
  486    mov   bx, WORD PTR [yMant+2]
  487    shr   WORD PTR [yMant+2], cl
  488    shr   WORD PTR [yMant], cl
  489    neg   cl
  490    add   cl, 16
  491    shl   bx, cl
  492    or    WORD PTR [yMant], bx
  493 
  494 SubtractNumbers:
  495    sub   ax, WORD PTR [yMant]
  496    sbb   dx, WORD PTR [yMant+2]
  497 
  498 BitScanRight:
  499    or    dx, dx
  500    js    StoreAns
  501 
  502    shl   ax, 1
  503    rcl   dx, 1
  504    sub   si, 1
  505    jno   BitScanRight
  506    jmp   Overflow
  507 
  508 StoreAns:
  509    mov   Ans.Exp, si
  510    mov   WORD PTR Ans.Mant+2, dx
  511    mov   WORD PTR Ans.Mant, ax
  512 
  513    lea   ax, Ans
  514    mov   dx, ds
  515    ret
  516 MPadd086    ENDP
  517 
  518 
  519 
  520 MPdiv086    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, \
  521                      yMant:DWORD
  522    mov   ax, xExp
  523    mov   bx, yExp
  524    xor   ch, ch
  525    shl   bh, 1
  526    rcr   ch, 1
  527    shr   bh, 1
  528    xor   ah, ch
  529 
  530    sub   bx, (1 SHL 14) - 2
  531    sub   ax, bx
  532    jno   NoOverflow
  533 
  534 Overflow:
  535    mov   MPOverflow, 1
  536 
  537 ZeroAns:
  538    xor   ax, ax
  539    xor   dx, dx
  540    mov   Ans.Exp, dx
  541    jmp   StoreMant
  542 
  543 NoOverflow:
  544    mov   Ans.Exp, ax
  545 
  546    mov   dx, WORD PTR [xMant+2]
  547    mov   ax, WORD PTR [xMant]
  548    or    dx, dx
  549    jz    ZeroAns
  550 
  551    mov   cx, WORD PTR [yMant+2]
  552    mov   bx, WORD PTR [yMant]
  553    or    cx, cx
  554    jz    Overflow
  555 
  556    cmp   dx, cx
  557    jl    Divide
  558 
  559    shr   dx, 1
  560    rcr   ax, 1
  561    add   Ans.Exp, 1
  562    jo    Overflow
  563 
  564 Divide:
  565    div   cx
  566    mov   si, dx
  567    mov   dx, bx
  568    mov   bx, ax
  569    mul   dx
  570    xor   di, di
  571    cmp   dx, si
  572    jnc   RemReallyNeg
  573 
  574    xchg  ax, di
  575    xchg  dx, si
  576    sub   ax, di
  577    sbb   dx, si
  578 
  579    shr   dx, 1
  580    rcr   ax, 1
  581    div   cx
  582    mov   dx, bx
  583    shl   ax, 1
  584    adc   dx, 0
  585    jmp   StoreMant
  586 
  587 RemReallyNeg:
  588    sub   ax, di
  589    sbb   dx, si
  590 
  591    shr   dx, 1
  592    rcr   ax, 1
  593    div   cx
  594    mov   dx, bx
  595    mov   bx, ax
  596    xor   ax, ax
  597    xor   cx, cx
  598    shl   bx, 1
  599    rcl   cx, 1
  600    sub   ax, bx
  601    sbb   dx, cx
  602    jno   StoreMant
  603 
  604    shl   ax, 1
  605    rcl   dx, 1
  606    dec   Ans.Exp
  607 
  608 StoreMant:
  609    mov   WORD PTR Ans.Mant, ax
  610    mov   WORD PTR Ans.Mant+2, dx
  611    lea   ax, Ans
  612    mov   dx, ds
  613    ret
  614 MPdiv086    ENDP
  615 
  616 
  617 MPcmp386    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, yMant:DWORD
  618    mov   si, 0
  619    mov   di, si
  620 .386
  621    mov   ax, xExp
  622    mov   edx, xMant
  623    mov   bx, yExp
  624    mov   ecx, yMant
  625    or    ax, ax
  626    jns   AtLeastOnePos
  627 
  628    or    bx, bx
  629    jns   AtLeastOnePos
  630 
  631    mov   si, 1
  632    and   ah, 7fh
  633    and   bh, 7fh
  634 
  635 AtLeastOnePos:
  636    cmp   ax, bx
  637    jle   Cmp1
  638 
  639    mov   di, 1
  640    jmp   ChkRev
  641 
  642 Cmp1:
  643    je    Cmp2
  644 
  645    mov   di, -1
  646    jmp   ChkRev
  647 
  648 Cmp2:
  649    cmp   edx, ecx
  650    jbe   Cmp3
  651 
  652    mov   di, 1
  653    jmp   ChkRev
  654 
  655 Cmp3:
  656    je    ChkRev
  657 
  658    mov   di, -1
  659 
  660 ChkRev:
  661         or    si, si
  662    jz    ExitCmp
  663 
  664    neg   di
  665 
  666 ExitCmp:
  667    mov   ax, di
  668 .8086
  669    ret
  670 MPcmp386    ENDP
  671 
  672 
  673 
  674 d2MP386     PROC     uses si di, x:QWORD
  675    mov   si, WORD PTR [x+6]
  676 .386
  677    mov   edx, DWORD PTR [x+4]
  678    mov   eax, DWORD PTR [x]
  679 
  680    mov   ebx, edx
  681    shl   ebx, 1
  682    or    ebx, eax
  683    jnz   NonZero
  684 
  685    xor   si, si
  686    xor   edx, edx
  687    jmp   StoreAns
  688 
  689 NonZero:
  690    shl   si, 1
  691    pushf
  692    shr   si, 4
  693    popf
  694    rcr   si, 1
  695    add   si, (1 SHL 14) - (1 SHL 10)
  696 
  697    shld  edx, eax, 12
  698    stc
  699    rcr   edx, 1
  700 
  701 StoreAns:
  702    mov   Ans.Exp, si
  703    mov   Ans.Mant, edx
  704 
  705    lea   ax, Ans
  706    mov   dx, ds
  707 .8086
  708    ret
  709 d2MP386     ENDP
  710 
  711 
  712 
  713 
  714 MP2d386     PROC     uses si di, xExp:WORD, xMant:DWORD
  715    sub   xExp, (1 SHL 14) - (1 SHL 10)
  716 .386
  717    jo    Overflow
  718 
  719    mov   bx, xExp
  720    and   bx, 0111100000000000b
  721    jz    InRangeOfDouble
  722 
  723 Overflow:
  724    mov   MPOverflow, 1
  725    xor   eax, eax
  726    xor   edx, edx
  727    jmp   StoreAns
  728 
  729 InRangeOfDouble:
  730    mov   bx, xExp
  731    mov   ax, bx
  732    shl   bx, 5
  733    shl   ax, 1
  734    rcr   bx, 1
  735    shr   bx, 4
  736 
  737    mov   edx, xMant
  738    shl   edx, 1
  739    xor   eax, eax
  740    shrd  eax, edx, 12
  741    shrd  edx, ebx, 12
  742 
  743 StoreAns:
  744    mov   DWORD PTR Double+4, edx
  745    mov   DWORD PTR Double, eax
  746 
  747    lea   ax, Double
  748    mov   dx, ds
  749 .8086
  750    ret
  751 MP2d386     ENDP
  752 
  753 
  754 
  755 MPmul386    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, \
  756                      yMant:DWORD
  757    mov   ax, xExp
  758    mov   bx, yExp
  759 .386
  760    xor   ch, ch
  761    shl   bh, 1
  762    rcr   ch, 1
  763    shr   bh, 1
  764    xor   ah, ch
  765 
  766    sub   bx, (1 SHL 14) - 2
  767    add   ax, bx
  768    jno   NoOverflow
  769 
  770 Overflow:
  771    or    WORD PTR [xMant+2], 0
  772    jz    ZeroAns
  773    or    WORD PTR [yMant+2], 0
  774    jz    ZeroAns
  775 
  776    mov   MPOverflow, 1
  777 
  778 ZeroAns:
  779    xor   edx, edx
  780    mov   Ans.Exp, dx
  781    jmp   StoreMant
  782 
  783 NoOverflow:
  784    mov   Ans.Exp, ax
  785 
  786    mov   eax, xMant
  787    mov   edx, yMant
  788    or    eax, eax
  789    jz    ZeroAns
  790 
  791    or    edx, edx
  792    jz    ZeroAns
  793 
  794    mul   edx
  795 
  796    or    edx, edx
  797    js    StoreMant
  798 
  799    shld  edx, eax, 1
  800    sub   Ans.Exp, 1
  801    jo    Overflow
  802 
  803 StoreMant:
  804    mov   Ans.Mant, edx
  805    lea   ax, Ans
  806    mov   dx, ds
  807 .8086
  808    ret
  809 MPmul386    ENDP
  810 
  811 
  812 
  813 MPadd386    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, \
  814                      yMant:DWORD
  815    mov   si, xExp
  816 .386
  817    mov   eax, xMant
  818 
  819    mov   di, yExp
  820    mov   edx, yMant
  821 
  822    mov   cx, si
  823    xor   cx, di
  824    js    Subtract
  825    jz    SameMag
  826 
  827    cmp   si, di
  828    jg    XisGreater
  829 
  830    xchg  si, di
  831    xchg  eax, edx
  832 
  833 XisGreater:
  834    mov   cx, si
  835    sub   cx, di
  836    cmp   cx, 32
  837    jge   StoreAns
  838 
  839    shr   edx, cl
  840 
  841 SameMag:
  842    add   eax, edx
  843    jnc   StoreAns
  844 
  845    rcr   eax, 1
  846    add   si, 1
  847    jno   StoreAns
  848 
  849 Overflow:
  850    mov   MPOverflow, 1
  851 
  852 ZeroAns:
  853    xor   si, si
  854    xor   edx, edx
  855    jmp   StoreAns
  856 
  857 Subtract:
  858    xor   di, 8000h
  859    mov   cx, si
  860    sub   cx, di
  861    jnz   DifferentMag
  862 
  863    cmp   eax, edx
  864    jg    SubtractNumbers
  865    je    ZeroAns
  866 
  867    xor   si, 8000h
  868    xchg  eax, edx
  869    jmp   SubtractNumbers
  870 
  871 DifferentMag:
  872    or    cx, cx
  873    jns   NoSwap
  874 
  875    xchg  si, di
  876    xchg  eax, edx
  877    xor   si, 8000h
  878    neg   cx
  879 
  880 NoSwap:
  881    cmp   cx, 32
  882    jge   StoreAns
  883 
  884    shr   edx, cl
  885 
  886 SubtractNumbers:
  887    sub   eax, edx
  888    bsr   ecx, eax
  889    neg   cx
  890    add   cx, 31
  891    shl   eax, cl
  892    sub   si, cx
  893    jo    Overflow
  894 
  895 StoreAns:
  896    mov   Ans.Exp, si
  897    mov   Ans.Mant, eax
  898 
  899    lea   ax, Ans
  900    mov   dx, ds
  901 .8086
  902    ret
  903 MPadd386    ENDP
  904 
  905 
  906 
  907 
  908 
  909 MPdiv386    PROC     uses si di, xExp:WORD, xMant:DWORD, yExp:WORD, \
  910                      yMant:DWORD
  911    mov   ax, xExp
  912    mov   bx, yExp
  913 .386
  914    xor   ch, ch
  915    shl   bh, 1
  916    rcr   ch, 1
  917    shr   bh, 1
  918    xor   ah, ch
  919 
  920    sub   bx, (1 SHL 14) - 2
  921    sub   ax, bx
  922    jno   NoOverflow
  923 
  924 Overflow:
  925    mov   MPOverflow, 1
  926 
  927 ZeroAns:
  928    xor   eax, eax
  929    mov   Ans.Exp, ax
  930    jmp   StoreMant
  931 
  932 NoOverflow:
  933    mov   Ans.Exp, ax
  934 
  935    xor   eax, eax
  936    mov   edx, xMant
  937    mov   ecx, yMant
  938    or    edx, edx
  939    jz    ZeroAns
  940 
  941    or    ecx, ecx
  942    jz    Overflow
  943 
  944    cmp   edx, ecx
  945    jl    Divide
  946 
  947    shr   edx, 1
  948    rcr   eax, 1
  949    add   Ans.Exp, 1
  950    jo    Overflow
  951 
  952 Divide:
  953    div   ecx
  954 
  955 StoreMant:
  956    mov   Ans.Mant, eax
  957    lea   ax, Ans
  958    mov   dx, ds
  959 .8086
  960    ret
  961 MPdiv386    ENDP
  962 
  963 
  964 fg2MP386    PROC     x:DWORD, fg:WORD
  965    mov   bx, 1 SHL 14 + 30
  966    sub   bx, fg
  967 .386
  968    mov   edx, x
  969 
  970    or    edx, edx
  971    jnz   ChkNegMP
  972 
  973    mov   bx, dx
  974    jmp   StoreAns
  975 
  976 ChkNegMP:
  977    jns   BitScanRight
  978 
  979    or    bh, 80h
  980    neg   edx
  981 
  982 BitScanRight:
  983    bsr   ecx, edx
  984    neg   cx
  985    add   cx, 31
  986    sub   bx, cx
  987    shl   edx, cl
  988 
  989 StoreAns:
  990    mov   Ans.Exp, bx
  991    mov   Ans.Mant, edx
  992 .8086
  993    lea   ax, Ans
  994    mov   dx, ds
  995    ret
  996 fg2MP386    ENDP
  997 
  998 
  999 
 1000 PUBLIC MPcmp, MPmul, MPadd, MPdiv, MP2d, d2MP, fg2MP
 1001 
 1002 fg2MP:
 1003    cmp   cpu, 386
 1004    jae   Use386fg2MP
 1005    jmp   fg2MP086
 1006 
 1007 Use386fg2MP:
 1008    jmp   fg2MP386
 1009 
 1010 MPcmp:
 1011    cmp   cpu, 386
 1012    jae   Use386cmp
 1013    jmp   MPcmp086
 1014 
 1015 Use386cmp:
 1016    jmp   MPcmp386
 1017 
 1018 MPmul:
 1019    cmp   cpu, 386
 1020    jae   Use386mul
 1021    jmp   MPmul086
 1022 
 1023 Use386mul:
 1024    jmp   MPmul386
 1025 
 1026 d2MP:
 1027    cmp   cpu, 386
 1028    jae   Use386d2MP
 1029    jmp   d2MP086
 1030 
 1031 Use386d2MP:
 1032    jmp   d2MP386
 1033 
 1034 MPadd:
 1035    cmp   cpu, 386
 1036    jae   Use386add
 1037    jmp   MPadd086
 1038 
 1039 Use386add:
 1040    jmp   MPadd386
 1041 
 1042 MPdiv:
 1043    cmp   cpu, 386
 1044    jae   Use386div
 1045    jmp   MPdiv086
 1046 
 1047 Use386div:
 1048    jmp   MPdiv386
 1049 
 1050 MP2d:
 1051    cmp   cpu, 386
 1052    jae   Use386MP2d
 1053    jmp   MP2d086
 1054 
 1055 Use386MP2d:
 1056    jmp   MP2d386
 1057 
 1058 
 1059 END
 1060 
 1061