11da177e4SLinus Torvalds| 21da177e4SLinus Torvalds| srem_mod.sa 3.1 12/10/90 31da177e4SLinus Torvalds| 41da177e4SLinus Torvalds| The entry point sMOD computes the floating point MOD of the 51da177e4SLinus Torvalds| input values X and Y. The entry point sREM computes the floating 61da177e4SLinus Torvalds| point (IEEE) REM of the input values X and Y. 71da177e4SLinus Torvalds| 81da177e4SLinus Torvalds| INPUT 91da177e4SLinus Torvalds| ----- 101da177e4SLinus Torvalds| Double-extended value Y is pointed to by address in register 111da177e4SLinus Torvalds| A0. Double-extended value X is located in -12(A0). The values 121da177e4SLinus Torvalds| of X and Y are both nonzero and finite; although either or both 131da177e4SLinus Torvalds| of them can be denormalized. The special cases of zeros, NaNs, 141da177e4SLinus Torvalds| and infinities are handled elsewhere. 151da177e4SLinus Torvalds| 161da177e4SLinus Torvalds| OUTPUT 171da177e4SLinus Torvalds| ------ 181da177e4SLinus Torvalds| FREM(X,Y) or FMOD(X,Y), depending on entry point. 191da177e4SLinus Torvalds| 201da177e4SLinus Torvalds| ALGORITHM 211da177e4SLinus Torvalds| --------- 221da177e4SLinus Torvalds| 231da177e4SLinus Torvalds| Step 1. Save and strip signs of X and Y: signX := sign(X), 241da177e4SLinus Torvalds| signY := sign(Y), X := |X|, Y := |Y|, 251da177e4SLinus Torvalds| signQ := signX EOR signY. Record whether MOD or REM 261da177e4SLinus Torvalds| is requested. 271da177e4SLinus Torvalds| 281da177e4SLinus Torvalds| Step 2. Set L := expo(X)-expo(Y), k := 0, Q := 0. 291da177e4SLinus Torvalds| If (L < 0) then 301da177e4SLinus Torvalds| R := X, go to Step 4. 311da177e4SLinus Torvalds| else 321da177e4SLinus Torvalds| R := 2^(-L)X, j := L. 331da177e4SLinus Torvalds| endif 341da177e4SLinus Torvalds| 351da177e4SLinus Torvalds| Step 3. Perform MOD(X,Y) 361da177e4SLinus Torvalds| 3.1 If R = Y, go to Step 9. 371da177e4SLinus Torvalds| 3.2 If R > Y, then { R := R - Y, Q := Q + 1} 381da177e4SLinus Torvalds| 3.3 If j = 0, go to Step 4. 391da177e4SLinus Torvalds| 3.4 k := k + 1, j := j - 1, Q := 2Q, R := 2R. Go to 401da177e4SLinus Torvalds| Step 3.1. 411da177e4SLinus Torvalds| 421da177e4SLinus Torvalds| Step 4. At this point, R = X - QY = MOD(X,Y). Set 431da177e4SLinus Torvalds| Last_Subtract := false (used in Step 7 below). If 441da177e4SLinus Torvalds| MOD is requested, go to Step 6. 451da177e4SLinus Torvalds| 461da177e4SLinus Torvalds| Step 5. R = MOD(X,Y), but REM(X,Y) is requested. 471da177e4SLinus Torvalds| 5.1 If R < Y/2, then R = MOD(X,Y) = REM(X,Y). Go to 481da177e4SLinus Torvalds| Step 6. 491da177e4SLinus Torvalds| 5.2 If R > Y/2, then { set Last_Subtract := true, 501da177e4SLinus Torvalds| Q := Q + 1, Y := signY*Y }. Go to Step 6. 511da177e4SLinus Torvalds| 5.3 This is the tricky case of R = Y/2. If Q is odd, 521da177e4SLinus Torvalds| then { Q := Q + 1, signX := -signX }. 531da177e4SLinus Torvalds| 541da177e4SLinus Torvalds| Step 6. R := signX*R. 551da177e4SLinus Torvalds| 561da177e4SLinus Torvalds| Step 7. If Last_Subtract = true, R := R - Y. 571da177e4SLinus Torvalds| 581da177e4SLinus Torvalds| Step 8. Return signQ, last 7 bits of Q, and R as required. 591da177e4SLinus Torvalds| 601da177e4SLinus Torvalds| Step 9. At this point, R = 2^(-j)*X - Q Y = Y. Thus, 611da177e4SLinus Torvalds| X = 2^(j)*(Q+1)Y. set Q := 2^(j)*(Q+1), 621da177e4SLinus Torvalds| R := 0. Return signQ, last 7 bits of Q, and R. 631da177e4SLinus Torvalds| 641da177e4SLinus Torvalds| 651da177e4SLinus Torvalds 661da177e4SLinus Torvalds| Copyright (C) Motorola, Inc. 1990 671da177e4SLinus Torvalds| All Rights Reserved 681da177e4SLinus Torvalds| 69*e00d82d0SMatt Waddel| For details on the license for this file, please see the 70*e00d82d0SMatt Waddel| file, README, in this same directory. 711da177e4SLinus Torvalds 721da177e4SLinus TorvaldsSREM_MOD: |idnt 2,1 | Motorola 040 Floating Point Software Package 731da177e4SLinus Torvalds 741da177e4SLinus Torvalds |section 8 751da177e4SLinus Torvalds 761da177e4SLinus Torvalds#include "fpsp.h" 771da177e4SLinus Torvalds 781da177e4SLinus Torvalds .set Mod_Flag,L_SCR3 791da177e4SLinus Torvalds .set SignY,FP_SCR3+4 801da177e4SLinus Torvalds .set SignX,FP_SCR3+8 811da177e4SLinus Torvalds .set SignQ,FP_SCR3+12 821da177e4SLinus Torvalds .set Sc_Flag,FP_SCR4 831da177e4SLinus Torvalds 841da177e4SLinus Torvalds .set Y,FP_SCR1 851da177e4SLinus Torvalds .set Y_Hi,Y+4 861da177e4SLinus Torvalds .set Y_Lo,Y+8 871da177e4SLinus Torvalds 881da177e4SLinus Torvalds .set R,FP_SCR2 891da177e4SLinus Torvalds .set R_Hi,R+4 901da177e4SLinus Torvalds .set R_Lo,R+8 911da177e4SLinus Torvalds 921da177e4SLinus Torvalds 931da177e4SLinus TorvaldsScale: .long 0x00010000,0x80000000,0x00000000,0x00000000 941da177e4SLinus Torvalds 951da177e4SLinus Torvalds |xref t_avoid_unsupp 961da177e4SLinus Torvalds 971da177e4SLinus Torvalds .global smod 981da177e4SLinus Torvaldssmod: 991da177e4SLinus Torvalds 1001da177e4SLinus Torvalds movel #0,Mod_Flag(%a6) 1011da177e4SLinus Torvalds bras Mod_Rem 1021da177e4SLinus Torvalds 1031da177e4SLinus Torvalds .global srem 1041da177e4SLinus Torvaldssrem: 1051da177e4SLinus Torvalds 1061da177e4SLinus Torvalds movel #1,Mod_Flag(%a6) 1071da177e4SLinus Torvalds 1081da177e4SLinus TorvaldsMod_Rem: 1091da177e4SLinus Torvalds|..Save sign of X and Y 1101da177e4SLinus Torvalds moveml %d2-%d7,-(%a7) | ...save data registers 1111da177e4SLinus Torvalds movew (%a0),%d3 1121da177e4SLinus Torvalds movew %d3,SignY(%a6) 1131da177e4SLinus Torvalds andil #0x00007FFF,%d3 | ...Y := |Y| 1141da177e4SLinus Torvalds 1151da177e4SLinus Torvalds| 1161da177e4SLinus Torvalds movel 4(%a0),%d4 1171da177e4SLinus Torvalds movel 8(%a0),%d5 | ...(D3,D4,D5) is |Y| 1181da177e4SLinus Torvalds 1191da177e4SLinus Torvalds tstl %d3 1201da177e4SLinus Torvalds bnes Y_Normal 1211da177e4SLinus Torvalds 1221da177e4SLinus Torvalds movel #0x00003FFE,%d3 | ...$3FFD + 1 1231da177e4SLinus Torvalds tstl %d4 1241da177e4SLinus Torvalds bnes HiY_not0 1251da177e4SLinus Torvalds 1261da177e4SLinus TorvaldsHiY_0: 1271da177e4SLinus Torvalds movel %d5,%d4 1281da177e4SLinus Torvalds clrl %d5 1291da177e4SLinus Torvalds subil #32,%d3 1301da177e4SLinus Torvalds clrl %d6 1311da177e4SLinus Torvalds bfffo %d4{#0:#32},%d6 1321da177e4SLinus Torvalds lsll %d6,%d4 1331da177e4SLinus Torvalds subl %d6,%d3 | ...(D3,D4,D5) is normalized 1341da177e4SLinus Torvalds| ...with bias $7FFD 1351da177e4SLinus Torvalds bras Chk_X 1361da177e4SLinus Torvalds 1371da177e4SLinus TorvaldsHiY_not0: 1381da177e4SLinus Torvalds clrl %d6 1391da177e4SLinus Torvalds bfffo %d4{#0:#32},%d6 1401da177e4SLinus Torvalds subl %d6,%d3 1411da177e4SLinus Torvalds lsll %d6,%d4 1421da177e4SLinus Torvalds movel %d5,%d7 | ...a copy of D5 1431da177e4SLinus Torvalds lsll %d6,%d5 1441da177e4SLinus Torvalds negl %d6 1451da177e4SLinus Torvalds addil #32,%d6 1461da177e4SLinus Torvalds lsrl %d6,%d7 1471da177e4SLinus Torvalds orl %d7,%d4 | ...(D3,D4,D5) normalized 1481da177e4SLinus Torvalds| ...with bias $7FFD 1491da177e4SLinus Torvalds bras Chk_X 1501da177e4SLinus Torvalds 1511da177e4SLinus TorvaldsY_Normal: 1521da177e4SLinus Torvalds addil #0x00003FFE,%d3 | ...(D3,D4,D5) normalized 1531da177e4SLinus Torvalds| ...with bias $7FFD 1541da177e4SLinus Torvalds 1551da177e4SLinus TorvaldsChk_X: 1561da177e4SLinus Torvalds movew -12(%a0),%d0 1571da177e4SLinus Torvalds movew %d0,SignX(%a6) 1581da177e4SLinus Torvalds movew SignY(%a6),%d1 1591da177e4SLinus Torvalds eorl %d0,%d1 1601da177e4SLinus Torvalds andil #0x00008000,%d1 1611da177e4SLinus Torvalds movew %d1,SignQ(%a6) | ...sign(Q) obtained 1621da177e4SLinus Torvalds andil #0x00007FFF,%d0 1631da177e4SLinus Torvalds movel -8(%a0),%d1 1641da177e4SLinus Torvalds movel -4(%a0),%d2 | ...(D0,D1,D2) is |X| 1651da177e4SLinus Torvalds tstl %d0 1661da177e4SLinus Torvalds bnes X_Normal 1671da177e4SLinus Torvalds movel #0x00003FFE,%d0 1681da177e4SLinus Torvalds tstl %d1 1691da177e4SLinus Torvalds bnes HiX_not0 1701da177e4SLinus Torvalds 1711da177e4SLinus TorvaldsHiX_0: 1721da177e4SLinus Torvalds movel %d2,%d1 1731da177e4SLinus Torvalds clrl %d2 1741da177e4SLinus Torvalds subil #32,%d0 1751da177e4SLinus Torvalds clrl %d6 1761da177e4SLinus Torvalds bfffo %d1{#0:#32},%d6 1771da177e4SLinus Torvalds lsll %d6,%d1 1781da177e4SLinus Torvalds subl %d6,%d0 | ...(D0,D1,D2) is normalized 1791da177e4SLinus Torvalds| ...with bias $7FFD 1801da177e4SLinus Torvalds bras Init 1811da177e4SLinus Torvalds 1821da177e4SLinus TorvaldsHiX_not0: 1831da177e4SLinus Torvalds clrl %d6 1841da177e4SLinus Torvalds bfffo %d1{#0:#32},%d6 1851da177e4SLinus Torvalds subl %d6,%d0 1861da177e4SLinus Torvalds lsll %d6,%d1 1871da177e4SLinus Torvalds movel %d2,%d7 | ...a copy of D2 1881da177e4SLinus Torvalds lsll %d6,%d2 1891da177e4SLinus Torvalds negl %d6 1901da177e4SLinus Torvalds addil #32,%d6 1911da177e4SLinus Torvalds lsrl %d6,%d7 1921da177e4SLinus Torvalds orl %d7,%d1 | ...(D0,D1,D2) normalized 1931da177e4SLinus Torvalds| ...with bias $7FFD 1941da177e4SLinus Torvalds bras Init 1951da177e4SLinus Torvalds 1961da177e4SLinus TorvaldsX_Normal: 1971da177e4SLinus Torvalds addil #0x00003FFE,%d0 | ...(D0,D1,D2) normalized 1981da177e4SLinus Torvalds| ...with bias $7FFD 1991da177e4SLinus Torvalds 2001da177e4SLinus TorvaldsInit: 2011da177e4SLinus Torvalds| 2021da177e4SLinus Torvalds movel %d3,L_SCR1(%a6) | ...save biased expo(Y) 2031da177e4SLinus Torvalds movel %d0,L_SCR2(%a6) |save d0 2041da177e4SLinus Torvalds subl %d3,%d0 | ...L := expo(X)-expo(Y) 2051da177e4SLinus Torvalds| Move.L D0,L ...D0 is j 2061da177e4SLinus Torvalds clrl %d6 | ...D6 := carry <- 0 2071da177e4SLinus Torvalds clrl %d3 | ...D3 is Q 2081da177e4SLinus Torvalds moveal #0,%a1 | ...A1 is k; j+k=L, Q=0 2091da177e4SLinus Torvalds 2101da177e4SLinus Torvalds|..(Carry,D1,D2) is R 2111da177e4SLinus Torvalds tstl %d0 2121da177e4SLinus Torvalds bges Mod_Loop 2131da177e4SLinus Torvalds 2141da177e4SLinus Torvalds|..expo(X) < expo(Y). Thus X = mod(X,Y) 2151da177e4SLinus Torvalds| 2161da177e4SLinus Torvalds movel L_SCR2(%a6),%d0 |restore d0 2171da177e4SLinus Torvalds bra Get_Mod 2181da177e4SLinus Torvalds 2191da177e4SLinus Torvalds|..At this point R = 2^(-L)X; Q = 0; k = 0; and k+j = L 2201da177e4SLinus Torvalds 2211da177e4SLinus Torvalds 2221da177e4SLinus TorvaldsMod_Loop: 2231da177e4SLinus Torvalds tstl %d6 | ...test carry bit 2241da177e4SLinus Torvalds bgts R_GT_Y 2251da177e4SLinus Torvalds 2261da177e4SLinus Torvalds|..At this point carry = 0, R = (D1,D2), Y = (D4,D5) 2271da177e4SLinus Torvalds cmpl %d4,%d1 | ...compare hi(R) and hi(Y) 2281da177e4SLinus Torvalds bnes R_NE_Y 2291da177e4SLinus Torvalds cmpl %d5,%d2 | ...compare lo(R) and lo(Y) 2301da177e4SLinus Torvalds bnes R_NE_Y 2311da177e4SLinus Torvalds 2321da177e4SLinus Torvalds|..At this point, R = Y 2331da177e4SLinus Torvalds bra Rem_is_0 2341da177e4SLinus Torvalds 2351da177e4SLinus TorvaldsR_NE_Y: 2361da177e4SLinus Torvalds|..use the borrow of the previous compare 2371da177e4SLinus Torvalds bcss R_LT_Y | ...borrow is set iff R < Y 2381da177e4SLinus Torvalds 2391da177e4SLinus TorvaldsR_GT_Y: 2401da177e4SLinus Torvalds|..If Carry is set, then Y < (Carry,D1,D2) < 2Y. Otherwise, Carry = 0 2411da177e4SLinus Torvalds|..and Y < (D1,D2) < 2Y. Either way, perform R - Y 2421da177e4SLinus Torvalds subl %d5,%d2 | ...lo(R) - lo(Y) 2431da177e4SLinus Torvalds subxl %d4,%d1 | ...hi(R) - hi(Y) 2441da177e4SLinus Torvalds clrl %d6 | ...clear carry 2451da177e4SLinus Torvalds addql #1,%d3 | ...Q := Q + 1 2461da177e4SLinus Torvalds 2471da177e4SLinus TorvaldsR_LT_Y: 2481da177e4SLinus Torvalds|..At this point, Carry=0, R < Y. R = 2^(k-L)X - QY; k+j = L; j >= 0. 2491da177e4SLinus Torvalds tstl %d0 | ...see if j = 0. 2501da177e4SLinus Torvalds beqs PostLoop 2511da177e4SLinus Torvalds 2521da177e4SLinus Torvalds addl %d3,%d3 | ...Q := 2Q 2531da177e4SLinus Torvalds addl %d2,%d2 | ...lo(R) = 2lo(R) 2541da177e4SLinus Torvalds roxll #1,%d1 | ...hi(R) = 2hi(R) + carry 2551da177e4SLinus Torvalds scs %d6 | ...set Carry if 2(R) overflows 2561da177e4SLinus Torvalds addql #1,%a1 | ...k := k+1 2571da177e4SLinus Torvalds subql #1,%d0 | ...j := j - 1 2581da177e4SLinus Torvalds|..At this point, R=(Carry,D1,D2) = 2^(k-L)X - QY, j+k=L, j >= 0, R < 2Y. 2591da177e4SLinus Torvalds 2601da177e4SLinus Torvalds bras Mod_Loop 2611da177e4SLinus Torvalds 2621da177e4SLinus TorvaldsPostLoop: 2631da177e4SLinus Torvalds|..k = L, j = 0, Carry = 0, R = (D1,D2) = X - QY, R < Y. 2641da177e4SLinus Torvalds 2651da177e4SLinus Torvalds|..normalize R. 2661da177e4SLinus Torvalds movel L_SCR1(%a6),%d0 | ...new biased expo of R 2671da177e4SLinus Torvalds tstl %d1 2681da177e4SLinus Torvalds bnes HiR_not0 2691da177e4SLinus Torvalds 2701da177e4SLinus TorvaldsHiR_0: 2711da177e4SLinus Torvalds movel %d2,%d1 2721da177e4SLinus Torvalds clrl %d2 2731da177e4SLinus Torvalds subil #32,%d0 2741da177e4SLinus Torvalds clrl %d6 2751da177e4SLinus Torvalds bfffo %d1{#0:#32},%d6 2761da177e4SLinus Torvalds lsll %d6,%d1 2771da177e4SLinus Torvalds subl %d6,%d0 | ...(D0,D1,D2) is normalized 2781da177e4SLinus Torvalds| ...with bias $7FFD 2791da177e4SLinus Torvalds bras Get_Mod 2801da177e4SLinus Torvalds 2811da177e4SLinus TorvaldsHiR_not0: 2821da177e4SLinus Torvalds clrl %d6 2831da177e4SLinus Torvalds bfffo %d1{#0:#32},%d6 2841da177e4SLinus Torvalds bmis Get_Mod | ...already normalized 2851da177e4SLinus Torvalds subl %d6,%d0 2861da177e4SLinus Torvalds lsll %d6,%d1 2871da177e4SLinus Torvalds movel %d2,%d7 | ...a copy of D2 2881da177e4SLinus Torvalds lsll %d6,%d2 2891da177e4SLinus Torvalds negl %d6 2901da177e4SLinus Torvalds addil #32,%d6 2911da177e4SLinus Torvalds lsrl %d6,%d7 2921da177e4SLinus Torvalds orl %d7,%d1 | ...(D0,D1,D2) normalized 2931da177e4SLinus Torvalds 2941da177e4SLinus Torvalds| 2951da177e4SLinus TorvaldsGet_Mod: 2961da177e4SLinus Torvalds cmpil #0x000041FE,%d0 2971da177e4SLinus Torvalds bges No_Scale 2981da177e4SLinus TorvaldsDo_Scale: 2991da177e4SLinus Torvalds movew %d0,R(%a6) 3001da177e4SLinus Torvalds clrw R+2(%a6) 3011da177e4SLinus Torvalds movel %d1,R_Hi(%a6) 3021da177e4SLinus Torvalds movel %d2,R_Lo(%a6) 3031da177e4SLinus Torvalds movel L_SCR1(%a6),%d6 3041da177e4SLinus Torvalds movew %d6,Y(%a6) 3051da177e4SLinus Torvalds clrw Y+2(%a6) 3061da177e4SLinus Torvalds movel %d4,Y_Hi(%a6) 3071da177e4SLinus Torvalds movel %d5,Y_Lo(%a6) 3081da177e4SLinus Torvalds fmovex R(%a6),%fp0 | ...no exception 3091da177e4SLinus Torvalds movel #1,Sc_Flag(%a6) 3101da177e4SLinus Torvalds bras ModOrRem 3111da177e4SLinus TorvaldsNo_Scale: 3121da177e4SLinus Torvalds movel %d1,R_Hi(%a6) 3131da177e4SLinus Torvalds movel %d2,R_Lo(%a6) 3141da177e4SLinus Torvalds subil #0x3FFE,%d0 3151da177e4SLinus Torvalds movew %d0,R(%a6) 3161da177e4SLinus Torvalds clrw R+2(%a6) 3171da177e4SLinus Torvalds movel L_SCR1(%a6),%d6 3181da177e4SLinus Torvalds subil #0x3FFE,%d6 3191da177e4SLinus Torvalds movel %d6,L_SCR1(%a6) 3201da177e4SLinus Torvalds fmovex R(%a6),%fp0 3211da177e4SLinus Torvalds movew %d6,Y(%a6) 3221da177e4SLinus Torvalds movel %d4,Y_Hi(%a6) 3231da177e4SLinus Torvalds movel %d5,Y_Lo(%a6) 3241da177e4SLinus Torvalds movel #0,Sc_Flag(%a6) 3251da177e4SLinus Torvalds 3261da177e4SLinus Torvalds| 3271da177e4SLinus Torvalds 3281da177e4SLinus Torvalds 3291da177e4SLinus TorvaldsModOrRem: 3301da177e4SLinus Torvalds movel Mod_Flag(%a6),%d6 3311da177e4SLinus Torvalds beqs Fix_Sign 3321da177e4SLinus Torvalds 3331da177e4SLinus Torvalds movel L_SCR1(%a6),%d6 | ...new biased expo(Y) 3341da177e4SLinus Torvalds subql #1,%d6 | ...biased expo(Y/2) 3351da177e4SLinus Torvalds cmpl %d6,%d0 3361da177e4SLinus Torvalds blts Fix_Sign 3371da177e4SLinus Torvalds bgts Last_Sub 3381da177e4SLinus Torvalds 3391da177e4SLinus Torvalds cmpl %d4,%d1 3401da177e4SLinus Torvalds bnes Not_EQ 3411da177e4SLinus Torvalds cmpl %d5,%d2 3421da177e4SLinus Torvalds bnes Not_EQ 3431da177e4SLinus Torvalds bra Tie_Case 3441da177e4SLinus Torvalds 3451da177e4SLinus TorvaldsNot_EQ: 3461da177e4SLinus Torvalds bcss Fix_Sign 3471da177e4SLinus Torvalds 3481da177e4SLinus TorvaldsLast_Sub: 3491da177e4SLinus Torvalds| 3501da177e4SLinus Torvalds fsubx Y(%a6),%fp0 | ...no exceptions 3511da177e4SLinus Torvalds addql #1,%d3 | ...Q := Q + 1 3521da177e4SLinus Torvalds 3531da177e4SLinus Torvalds| 3541da177e4SLinus Torvalds 3551da177e4SLinus TorvaldsFix_Sign: 3561da177e4SLinus Torvalds|..Get sign of X 3571da177e4SLinus Torvalds movew SignX(%a6),%d6 3581da177e4SLinus Torvalds bges Get_Q 3591da177e4SLinus Torvalds fnegx %fp0 3601da177e4SLinus Torvalds 3611da177e4SLinus Torvalds|..Get Q 3621da177e4SLinus Torvalds| 3631da177e4SLinus TorvaldsGet_Q: 3641da177e4SLinus Torvalds clrl %d6 3651da177e4SLinus Torvalds movew SignQ(%a6),%d6 | ...D6 is sign(Q) 3661da177e4SLinus Torvalds movel #8,%d7 3671da177e4SLinus Torvalds lsrl %d7,%d6 3681da177e4SLinus Torvalds andil #0x0000007F,%d3 | ...7 bits of Q 3691da177e4SLinus Torvalds orl %d6,%d3 | ...sign and bits of Q 3701da177e4SLinus Torvalds swap %d3 3711da177e4SLinus Torvalds fmovel %fpsr,%d6 3721da177e4SLinus Torvalds andil #0xFF00FFFF,%d6 3731da177e4SLinus Torvalds orl %d3,%d6 3741da177e4SLinus Torvalds fmovel %d6,%fpsr | ...put Q in fpsr 3751da177e4SLinus Torvalds 3761da177e4SLinus Torvalds| 3771da177e4SLinus TorvaldsRestore: 3781da177e4SLinus Torvalds moveml (%a7)+,%d2-%d7 3791da177e4SLinus Torvalds fmovel USER_FPCR(%a6),%fpcr 3801da177e4SLinus Torvalds movel Sc_Flag(%a6),%d0 3811da177e4SLinus Torvalds beqs Finish 3821da177e4SLinus Torvalds fmulx Scale(%pc),%fp0 | ...may cause underflow 3831da177e4SLinus Torvalds bra t_avoid_unsupp |check for denorm as a 3841da177e4SLinus Torvalds| ;result of the scaling 3851da177e4SLinus Torvalds 3861da177e4SLinus TorvaldsFinish: 3871da177e4SLinus Torvalds fmovex %fp0,%fp0 |capture exceptions & round 3881da177e4SLinus Torvalds rts 3891da177e4SLinus Torvalds 3901da177e4SLinus TorvaldsRem_is_0: 3911da177e4SLinus Torvalds|..R = 2^(-j)X - Q Y = Y, thus R = 0 and quotient = 2^j (Q+1) 3921da177e4SLinus Torvalds addql #1,%d3 3931da177e4SLinus Torvalds cmpil #8,%d0 | ...D0 is j 3941da177e4SLinus Torvalds bges Q_Big 3951da177e4SLinus Torvalds 3961da177e4SLinus Torvalds lsll %d0,%d3 3971da177e4SLinus Torvalds bras Set_R_0 3981da177e4SLinus Torvalds 3991da177e4SLinus TorvaldsQ_Big: 4001da177e4SLinus Torvalds clrl %d3 4011da177e4SLinus Torvalds 4021da177e4SLinus TorvaldsSet_R_0: 4031da177e4SLinus Torvalds fmoves #0x00000000,%fp0 4041da177e4SLinus Torvalds movel #0,Sc_Flag(%a6) 4051da177e4SLinus Torvalds bra Fix_Sign 4061da177e4SLinus Torvalds 4071da177e4SLinus TorvaldsTie_Case: 4081da177e4SLinus Torvalds|..Check parity of Q 4091da177e4SLinus Torvalds movel %d3,%d6 4101da177e4SLinus Torvalds andil #0x00000001,%d6 4111da177e4SLinus Torvalds tstl %d6 4121da177e4SLinus Torvalds beq Fix_Sign | ...Q is even 4131da177e4SLinus Torvalds 4141da177e4SLinus Torvalds|..Q is odd, Q := Q + 1, signX := -signX 4151da177e4SLinus Torvalds addql #1,%d3 4161da177e4SLinus Torvalds movew SignX(%a6),%d6 4171da177e4SLinus Torvalds eoril #0x00008000,%d6 4181da177e4SLinus Torvalds movew %d6,SignX(%a6) 4191da177e4SLinus Torvalds bra Fix_Sign 4201da177e4SLinus Torvalds 4211da177e4SLinus Torvalds |end 422