[BACK]Return to mul_1.s CVS log [TXT][DIR] Up to [local] / OpenXM_contrib / gmp / mpn / m88k

Annotation of OpenXM_contrib/gmp/mpn/m88k/mul_1.s, Revision 1.1.1.3

1.1.1.2   maekawa     1: ; mc88100 __gmpn_mul_1 -- Multiply a limb vector with a single limb and
1.1       maekawa     2: ; store the product in a second limb vector.
                      3:
1.1.1.3 ! ohara       4: ; Copyright 1992, 1994, 1995, 2000 Free Software Foundation, Inc.
1.1       maekawa     5:
                      6: ; This file is part of the GNU MP Library.
                      7:
                      8: ; The GNU MP Library is free software; you can redistribute it and/or modify
1.1.1.2   maekawa     9: ; it under the terms of the GNU Lesser General Public License as published by
                     10: ; the Free Software Foundation; either version 2.1 of the License, or (at your
1.1       maekawa    11: ; option) any later version.
                     12:
                     13: ; The GNU MP Library is distributed in the hope that it will be useful, but
                     14: ; WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
1.1.1.2   maekawa    15: ; or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
1.1       maekawa    16: ; License for more details.
                     17:
1.1.1.2   maekawa    18: ; You should have received a copy of the GNU Lesser General Public License
1.1       maekawa    19: ; along with the GNU MP Library; see the file COPYING.LIB.  If not, write to
                     20: ; the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
                     21: ; MA 02111-1307, USA.
                     22:
                     23:
                     24: ; INPUT PARAMETERS
                     25: ; res_ptr      r2
                     26: ; s1_ptr       r3
                     27: ; size         r4
                     28: ; s2_limb      r5
                     29:
                     30: ; Common overhead is about 11 cycles/invocation.
                     31:
                     32: ; The speed for S2_LIMB >= 0x10000 is approximately 21 cycles/limb.  (The
                     33: ; pipeline stalls 2 cycles due to WB contention.)
                     34:
                     35: ; The speed for S2_LIMB < 0x10000 is approximately 16 cycles/limb.  (The
                     36: ; pipeline stalls 2 cycles due to WB contention and 1 cycle due to latency.)
                     37:
                     38: ; To enhance speed:
                     39: ; 1. Unroll main loop 4-8 times.
                     40: ; 2. Schedule code to avoid WB contention.  It might be tempting to move the
                     41: ;    ld instruction in the loops down to save 2 cycles (less WB contention),
                     42: ;    but that looses because the ultimate value will be read from outside
                     43: ;    the allocated space.  But if we handle the ultimate multiplication in
                     44: ;    the tail, we can do this.
                     45: ; 3. Make the multiplication with less instructions.  I think the code for
                     46: ;    (S2_LIMB >= 0x10000) is not minimal.
                     47: ; With these techniques the (S2_LIMB >= 0x10000) case would run in 17 or
                     48: ; less cycles/limb; the (S2_LIMB < 0x10000) case would run in 11
                     49: ; cycles/limb.  (Assuming infinite unrolling.)
                     50:
                     51:        text
                     52:        align    16
1.1.1.2   maekawa    53:        global   ___gmpn_mul_1
                     54: ___gmpn_mul_1:
1.1       maekawa    55:
                     56:        ; Make S1_PTR and RES_PTR point at the end of their blocks
                     57:        ; and negate SIZE.
                     58:        lda      r3,r3[r4]
                     59:        lda      r6,r2[r4]      ; RES_PTR in r6 since r2 is retval
                     60:        subu     r4,r0,r4
                     61:
                     62:        addu.co  r2,r0,r0       ; r2 = cy = 0
                     63:        ld       r9,r3[r4]
                     64:        mask     r7,r5,0xffff   ; r7 = lo(S2_LIMB)
                     65:        extu     r8,r5,16       ; r8 = hi(S2_LIMB)
                     66:        bcnd.n   eq0,r8,Lsmall  ; jump if (hi(S2_LIMB) == 0)
                     67:         subu    r6,r6,4
                     68:
                     69: ; General code for any value of S2_LIMB.
                     70:
                     71:        ; Make a stack frame and save r25 and r26
                     72:        subu     r31,r31,16
                     73:        st.d     r25,r31,8
                     74:
                     75:        ; Enter the loop in the middle
                     76:        br.n    L1
                     77:        addu     r4,r4,1
                     78:
                     79: Loop:  ld       r9,r3[r4]
                     80:        st       r26,r6[r4]
                     81: ; bcnd ne0,r0,0                ; bubble
                     82:        addu     r4,r4,1
                     83: L1:    mul      r26,r9,r5      ; low word of product   mul_1   WB ld
                     84:        mask     r12,r9,0xffff  ; r12 = lo(s1_limb)     mask_1
                     85:        mul      r11,r12,r7     ; r11 =  prod_0         mul_2   WB mask_1
                     86:        mul      r10,r12,r8     ; r10 = prod_1a         mul_3
                     87:        extu     r13,r9,16      ; r13 = hi(s1_limb)     extu_1  WB mul_1
                     88:        mul      r12,r13,r7     ; r12 = prod_1b         mul_4   WB extu_1
                     89:        mul      r25,r13,r8     ; r25  = prod_2         mul_5   WB mul_2
                     90:        extu     r11,r11,16     ; r11 = hi(prod_0)      extu_2  WB mul_3
                     91:        addu     r10,r10,r11    ;                       addu_1  WB extu_2
                     92: ; bcnd ne0,r0,0                ; bubble                        WB addu_1
                     93:        addu.co  r10,r10,r12    ;                               WB mul_4
                     94:        mask.u   r10,r10,0xffff ; move the 16 most significant bits...
                     95:        addu.ci  r10,r10,r0     ; ...to the low half of the word...
                     96:        rot      r10,r10,16     ; ...and put carry in pos 16.
                     97:        addu.co  r26,r26,r2     ; add old carry limb
                     98:        bcnd.n   ne0,r4,Loop
                     99:         addu.ci r2,r25,r10     ; compute new carry limb
                    100:
                    101:        st       r26,r6[r4]
                    102:        ld.d     r25,r31,8
                    103:        jmp.n    r1
                    104:         addu    r31,r31,16
                    105:
                    106: ; Fast code for S2_LIMB < 0x10000
                    107: Lsmall:
                    108:        ; Enter the loop in the middle
                    109:        br.n    SL1
                    110:        addu     r4,r4,1
                    111:
                    112: SLoop: ld       r9,r3[r4]      ;
                    113:        st       r8,r6[r4]      ;
                    114:        addu     r4,r4,1        ;
                    115: SL1:   mul      r8,r9,r5       ; low word of product
                    116:        mask     r12,r9,0xffff  ; r12 = lo(s1_limb)
                    117:        extu     r13,r9,16      ; r13 = hi(s1_limb)
                    118:        mul      r11,r12,r7     ; r11 =  prod_0
                    119:        mul      r12,r13,r7     ; r12 = prod_1b
                    120:        addu.cio r8,r8,r2       ; add old carry limb
                    121:        extu     r10,r11,16     ; r11 = hi(prod_0)
                    122:        addu     r10,r10,r12    ;
                    123:        bcnd.n   ne0,r4,SLoop
                    124:        extu     r2,r10,16      ; r2 = new carry limb
                    125:
                    126:        jmp.n    r1
                    127:        st       r8,r6[r4]

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>