Support AMD Piledriver by bulldozer kernels.
[platform/upstream/openblas.git] / kernel / x86 / trsm_kernel_LT_2x4_sse2.S
1 /*********************************************************************/
2 /* Copyright 2009, 2010 The University of Texas at Austin.           */
3 /* All rights reserved.                                              */
4 /*                                                                   */
5 /* Redistribution and use in source and binary forms, with or        */
6 /* without modification, are permitted provided that the following   */
7 /* conditions are met:                                               */
8 /*                                                                   */
9 /*   1. Redistributions of source code must retain the above         */
10 /*      copyright notice, this list of conditions and the following  */
11 /*      disclaimer.                                                  */
12 /*                                                                   */
13 /*   2. Redistributions in binary form must reproduce the above      */
14 /*      copyright notice, this list of conditions and the following  */
15 /*      disclaimer in the documentation and/or other materials       */
16 /*      provided with the distribution.                              */
17 /*                                                                   */
18 /*    THIS  SOFTWARE IS PROVIDED  BY THE  UNIVERSITY OF  TEXAS AT    */
19 /*    AUSTIN  ``AS IS''  AND ANY  EXPRESS OR  IMPLIED WARRANTIES,    */
20 /*    INCLUDING, BUT  NOT LIMITED  TO, THE IMPLIED  WARRANTIES OF    */
21 /*    MERCHANTABILITY  AND FITNESS FOR  A PARTICULAR  PURPOSE ARE    */
22 /*    DISCLAIMED.  IN  NO EVENT SHALL THE UNIVERSITY  OF TEXAS AT    */
23 /*    AUSTIN OR CONTRIBUTORS BE  LIABLE FOR ANY DIRECT, INDIRECT,    */
24 /*    INCIDENTAL,  SPECIAL, EXEMPLARY,  OR  CONSEQUENTIAL DAMAGES    */
25 /*    (INCLUDING, BUT  NOT LIMITED TO,  PROCUREMENT OF SUBSTITUTE    */
26 /*    GOODS  OR  SERVICES; LOSS  OF  USE,  DATA,  OR PROFITS;  OR    */
27 /*    BUSINESS INTERRUPTION) HOWEVER CAUSED  AND ON ANY THEORY OF    */
28 /*    LIABILITY, WHETHER  IN CONTRACT, STRICT  LIABILITY, OR TORT    */
29 /*    (INCLUDING NEGLIGENCE OR OTHERWISE)  ARISING IN ANY WAY OUT    */
30 /*    OF  THE  USE OF  THIS  SOFTWARE,  EVEN  IF ADVISED  OF  THE    */
31 /*    POSSIBILITY OF SUCH DAMAGE.                                    */
32 /*                                                                   */
33 /* The views and conclusions contained in the software and           */
34 /* documentation are those of the authors and should not be          */
35 /* interpreted as representing official policies, either expressed   */
36 /* or implied, of The University of Texas at Austin.                 */
37 /*********************************************************************/
38
39 #define ASSEMBLER
40 #include "common.h"
41
42 #define STACK   16
43 #define ARGS     0
44         
45 #define OLD_M    4 + STACK + ARGS(%esi)
46 #define OLD_N    8 + STACK + ARGS(%esi)
47 #define OLD_K   12 + STACK + ARGS(%esi)
48 #define OLD_ALPHA       16 + STACK + ARGS(%esi)
49 #define OLD_A   24 + STACK + ARGS(%esi)
50 #define OLD_B   28 + STACK + ARGS(%esi)
51 #define OLD_C   32 + STACK + ARGS(%esi)
52 #define OLD_LDC 36 + STACK + ARGS(%esi)
53 #define OLD_OFFT        40 + STACK + ARGS(%esi)
54
55 #define K       16(%esp)
56 #define N       20(%esp)
57 #define M       24(%esp)
58 #define A       28(%esp)
59 #define C       32(%esp)
60 #define J       36(%esp)
61 #define OLD_STACK 40(%esp)
62 #define OFFSET  44(%esp)
63 #define KK      48(%esp)
64 #define KKK     52(%esp)
65 #define AORIG   56(%esp)
66 #define BORIG   60(%esp)
67 #define BUFFER 128(%esp)
68
69 #define STACK_ALIGN     4096
70 #define STACK_OFFSET    1024
71
72 #if defined(OPTERON) || defined(BARCELONA) || defined(BOBCAT) || defined(BARCELONA_OPTIMIZATION)
73 #define PREFETCH     prefetch
74 #define PREFETCHSIZE (8 * 10 + 4)
75 #endif
76
77 #define B       %edi
78 #define AA      %edx
79 #define BB      %ecx
80 #define LDC     %ebp
81 #define CO1     %esi
82
83 #define KERNEL1(address) \
84         mulpd   %xmm0, %xmm2; \
85         addpd   %xmm2, %xmm4; \
86         PREFETCH (PREFETCHSIZE +  0) * SIZE + (address) * 1 * SIZE(AA); \
87         movapd   2 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
88         mulpd   %xmm0, %xmm2; \
89         addpd   %xmm2, %xmm5; \
90         movapd   4 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
91         mulpd   %xmm0, %xmm2; \
92         mulpd    6 * SIZE + (address) * 4 * SIZE(BB), %xmm0; \
93         addpd   %xmm2, %xmm6; \
94         movapd  16 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
95         addpd   %xmm0, %xmm7; \
96         movapd   2 * SIZE + (address) * 1 * SIZE(AA), %xmm0
97
98 #define KERNEL2(address) \
99         mulpd   %xmm0, %xmm3; \
100         addpd   %xmm3, %xmm4; \
101         movapd  10 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
102         mulpd   %xmm0, %xmm3; \
103         addpd   %xmm3, %xmm5; \
104         movapd  12 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
105         mulpd   %xmm0, %xmm3; \
106         mulpd   14 * SIZE + (address) * 4 * SIZE(BB), %xmm0; \
107         addpd   %xmm3, %xmm6; \
108         movapd  24 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
109         addpd   %xmm0, %xmm7; \
110         movapd   4 * SIZE + (address) * 1 * SIZE(AA), %xmm0
111
112 #define KERNEL3(address) \
113         mulpd   %xmm0, %xmm2; \
114         addpd   %xmm2, %xmm4; \
115         movapd  18 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
116         mulpd   %xmm0, %xmm2; \
117         addpd   %xmm2, %xmm5; \
118         movapd  20 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
119         mulpd   %xmm0, %xmm2; \
120         mulpd   22 * SIZE + (address) * 4 * SIZE(BB), %xmm0; \
121         addpd   %xmm2, %xmm6; \
122         movapd  32 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
123         addpd   %xmm0, %xmm7; \
124         movapd   6 * SIZE + (address) * 1 * SIZE(AA), %xmm0
125
126 #define KERNEL4(address) \
127         mulpd   %xmm0, %xmm3; \
128         addpd   %xmm3, %xmm4; \
129         movapd  26 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
130         mulpd   %xmm0, %xmm3; \
131         addpd   %xmm3, %xmm5; \
132         movapd  28 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
133         mulpd   %xmm0, %xmm3; \
134         mulpd   30 * SIZE + (address) * 4 * SIZE(BB), %xmm0; \
135         addpd   %xmm3, %xmm6; \
136         movapd  40 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
137         addpd   %xmm0, %xmm7; \
138         movapd  16 * SIZE + (address) * 1 * SIZE(AA), %xmm0
139
140 #define KERNEL5(address) \
141         PREFETCH (PREFETCHSIZE + 8) * SIZE + (address) * 1 * SIZE(AA); \
142         mulpd   %xmm1, %xmm2; \
143         addpd   %xmm2, %xmm4; \
144         movapd  34 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
145         mulpd   %xmm1, %xmm2; \
146         addpd   %xmm2, %xmm5; \
147         movapd  36 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
148         mulpd   %xmm1, %xmm2; \
149         mulpd   38 * SIZE + (address) * 4 * SIZE(BB), %xmm1; \
150         addpd   %xmm2, %xmm6; \
151         movapd  48 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
152         addpd   %xmm1, %xmm7; \
153         movapd  10 * SIZE + (address) * 1 * SIZE(AA), %xmm1
154
155 #define KERNEL6(address) \
156         mulpd   %xmm1, %xmm3; \
157         addpd   %xmm3, %xmm4; \
158         movapd  42 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
159         mulpd   %xmm1, %xmm3; \
160         addpd   %xmm3, %xmm5; \
161         movapd  44 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
162         mulpd   %xmm1, %xmm3; \
163         mulpd   46 * SIZE + (address) * 4 * SIZE(BB), %xmm1; \
164         addpd   %xmm3, %xmm6; \
165         movapd  56 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
166         addpd   %xmm1, %xmm7; \
167         movapd  12 * SIZE + (address) * 1 * SIZE(AA), %xmm1
168
169 #define KERNEL7(address) \
170         mulpd   %xmm1, %xmm2; \
171         addpd   %xmm2, %xmm4; \
172         movapd  50 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
173         mulpd   %xmm1, %xmm2; \
174         addpd   %xmm2, %xmm5; \
175         movapd  52 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
176         mulpd   %xmm1, %xmm2; \
177         mulpd   54 * SIZE + (address) * 4 * SIZE(BB), %xmm1; \
178         addpd   %xmm2, %xmm6; \
179         movapd  64 * SIZE + (address) * 4 * SIZE(BB), %xmm2; \
180         addpd   %xmm1, %xmm7; \
181         movapd  14 * SIZE + (address) * 1 * SIZE(AA), %xmm1
182
183 #define KERNEL8(address) \
184         mulpd   %xmm1, %xmm3; \
185         addpd   %xmm3, %xmm4; \
186         movapd  58 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
187         mulpd   %xmm1, %xmm3; \
188         addpd   %xmm3, %xmm5; \
189         movapd  60 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
190         mulpd   %xmm1, %xmm3; \
191         mulpd   62 * SIZE + (address) * 4 * SIZE(BB), %xmm1; \
192         addpd   %xmm3, %xmm6; \
193         movapd  72 * SIZE + (address) * 4 * SIZE(BB), %xmm3; \
194         addpd   %xmm1, %xmm7; \
195         movapd  24 * SIZE + (address) * 1 * SIZE(AA), %xmm1
196
197         PROLOGUE
198
199         pushl   %ebp
200         pushl   %edi
201         pushl   %esi
202         pushl   %ebx
203
204         PROFCODE
205
206         EMMS
207
208         movl    %esp, %esi      # save old stack
209
210         subl    $128 + LOCAL_BUFFER_SIZE + STACK_OFFSET, %esp
211         andl    $-STACK_ALIGN, %esp
212         addl    $STACK_OFFSET, %esp
213
214         STACK_TOUCHING
215
216         movl    OLD_M, %ebx
217         movl    OLD_N, %eax
218         movl    OLD_K, %ecx
219         movl    OLD_A, %edx
220
221         movl    %ebx, M
222         movl    %eax, N
223         movl    %ecx, K
224         movl    %edx, A
225         movl    %esi, OLD_STACK
226         movd    OLD_OFFT, %mm4
227
228         movl    OLD_B, B
229         movl    OLD_C, %ebx
230
231         movl    %ebx, C
232         movl    OLD_LDC, LDC
233
234         movd    %mm4, OFFSET
235         movd    %mm4, KK
236
237         leal    (, LDC, SIZE), LDC
238
239 #ifdef LN
240        movl     M, %eax
241        leal     (, %eax, SIZE), %eax
242        addl     %eax, C
243        imull    K, %eax
244        addl     %eax, A
245 #endif
246
247 #ifdef RT
248        movl     N, %eax
249        leal     (, %eax, SIZE), %eax
250        imull    K, %eax
251        addl     %eax, B
252        movl     N, %eax
253        imull    LDC, %eax
254        addl     %eax, C
255 #endif
256
257 #ifdef RN
258         negl    KK
259 #endif  
260
261 #ifdef RT
262        movl     N, %eax
263        subl     OFFSET, %eax
264        movl     %eax, KK
265 #endif
266
267         movl    N,  %eax
268         sarl    $2, %eax
269         movl    %eax, J
270         jle     .L30
271         ALIGN_2
272
273 .L01:
274 #ifdef LN
275         movl    OFFSET, %eax
276         addl    M, %eax
277         movl    %eax, KK
278 #endif  
279
280         leal    BUFFER, BB
281
282 #ifdef RT
283        movl     K, %eax
284        sall     $2 + BASE_SHIFT, %eax
285        subl     %eax, B
286 #endif
287
288 #if defined(LN) || defined(RT)
289         movl    KK, %eax
290         movl    B, BORIG
291         leal    (, %eax, SIZE), %eax
292         leal    (B,  %eax, 4), B
293         leal    (BB, %eax, 8), BB
294 #endif  
295
296 #ifdef LT
297         movl    OFFSET, %eax
298         movl    %eax, KK
299 #endif
300
301 #if defined(LT) || defined(RN)
302         movl    KK, %eax
303 #else
304         movl    K, %eax
305         subl    KK, %eax
306 #endif
307         sarl    $1, %eax
308         jle     .L05
309         ALIGN_4
310         
311 .L02:
312 #define COPYPREFETCH 40
313
314         prefetchnta     (COPYPREFETCH) * SIZE(B)
315
316         movq     0 * SIZE(B), %mm0
317         movq     1 * SIZE(B), %mm1
318         movq     2 * SIZE(B), %mm2
319         movq     3 * SIZE(B), %mm3
320         movq     4 * SIZE(B), %mm4
321         movq     5 * SIZE(B), %mm5
322         movq     6 * SIZE(B), %mm6
323         movq     7 * SIZE(B), %mm7
324
325         movq    %mm0,  0 * SIZE(BB)
326         movq    %mm0,  1 * SIZE(BB)
327         movq    %mm1,  2 * SIZE(BB)
328         movq    %mm1,  3 * SIZE(BB)
329         movq    %mm2,  4 * SIZE(BB)
330         movq    %mm2,  5 * SIZE(BB)
331         movq    %mm3,  6 * SIZE(BB)
332         movq    %mm3,  7 * SIZE(BB)
333
334         movq    %mm4,  8 * SIZE(BB)
335         movq    %mm4,  9 * SIZE(BB)
336         movq    %mm5, 10 * SIZE(BB)
337         movq    %mm5, 11 * SIZE(BB)
338         movq    %mm6, 12 * SIZE(BB)
339         movq    %mm6, 13 * SIZE(BB)
340         movq    %mm7, 14 * SIZE(BB)
341         movq    %mm7, 15 * SIZE(BB)
342
343         addl    $ 8 * SIZE, B
344         addl    $16 * SIZE, BB
345         decl    %eax
346         jne     .L02
347         ALIGN_2
348
349 .L05:
350 #if defined(LT) || defined(RN)
351         movl    KK, %eax
352 #else
353         movl    K, %eax
354         subl    KK, %eax
355 #endif
356         andl    $1, %eax
357         BRANCH
358         jle     .L10
359
360         movq     0 * SIZE(B), %mm0
361         movq     1 * SIZE(B), %mm1
362         movq     2 * SIZE(B), %mm2
363         movq     3 * SIZE(B), %mm3
364
365         movq    %mm0,  0 * SIZE(BB)
366         movq    %mm0,  1 * SIZE(BB)
367         movq    %mm1,  2 * SIZE(BB)
368         movq    %mm1,  3 * SIZE(BB)
369         movq    %mm2,  4 * SIZE(BB)
370         movq    %mm2,  5 * SIZE(BB)
371         movq    %mm3,  6 * SIZE(BB)
372         movq    %mm3,  7 * SIZE(BB)
373
374         addl    $4 * SIZE, B
375         ALIGN_4
376         
377 .L10:
378 #if defined(LT) || defined(RN)
379         movl    A, AA
380 #else
381         movl    A, %eax
382         movl    %eax, AORIG
383 #endif
384
385         leal    (, LDC, 4), %eax
386
387 #ifdef RT
388         subl    %eax, C
389 #endif
390         movl    C, CO1
391 #ifndef RT
392         addl    %eax, C
393 #endif
394
395         movl    M,  %ebx
396         sarl    $1, %ebx        # i = (m >> 2)
397         jle     .L20
398         ALIGN_4
399
400 .L11:
401 #ifdef LN
402        movl     K, %eax
403        sall     $1 + BASE_SHIFT, %eax
404        subl     %eax, AORIG
405 #endif
406
407 #if defined(LN) || defined(RT)
408         movl    KK, %eax
409         movl    AORIG, AA
410         leal    (, %eax, SIZE), %eax
411         leal    (AA, %eax, 2), AA
412 #endif
413
414         leal    BUFFER, BB
415
416 #if defined(LN) || defined(RT)
417         movl    KK, %eax
418         sall    $3 + BASE_SHIFT, %eax
419         addl    %eax, BB
420 #endif  
421
422         pxor    %xmm4, %xmm4
423         pxor    %xmm5, %xmm5
424         pxor    %xmm6, %xmm6
425         pxor    %xmm7, %xmm7
426
427         movapd   0 * SIZE(AA), %xmm0
428         movapd   8 * SIZE(AA), %xmm1
429         movapd   0 * SIZE(BB), %xmm2
430         movapd   8 * SIZE(BB), %xmm3
431
432         leal    (LDC, LDC, 2), %eax
433
434 #ifdef LN
435         prefetchw       -2 * SIZE(CO1)
436         prefetchw       -2 * SIZE(CO1, LDC)
437         prefetchw       -2 * SIZE(CO1, LDC, 2)
438         prefetchw       -2 * SIZE(CO1, %eax)
439 #else
440         prefetchw        1 * SIZE(CO1)
441         prefetchw        1 * SIZE(CO1, LDC)
442         prefetchw        1 * SIZE(CO1, LDC, 2)
443         prefetchw        1 * SIZE(CO1, %eax)
444 #endif
445
446 #if defined(LT) || defined(RN)
447         movl    KK, %eax
448 #else
449         movl    K, %eax
450         subl    KK, %eax
451 #endif
452
453 #if 1
454         andl    $-8, %eax
455         sall    $4, %eax
456         je      .L15
457 .L1X:   
458         KERNEL1(16  *  0)
459         KERNEL2(16  *  0)
460         KERNEL3(16  *  0)
461         KERNEL4(16  *  0)
462         KERNEL5(16  *  0)
463         KERNEL6(16  *  0)
464         KERNEL7(16  *  0)
465         KERNEL8(16  *  0)
466         cmpl    $128 *  1, %eax
467         jle     .L12
468         KERNEL1(16  *  1)
469         KERNEL2(16  *  1)
470         KERNEL3(16  *  1)
471         KERNEL4(16  *  1)
472         KERNEL5(16  *  1)
473         KERNEL6(16  *  1)
474         KERNEL7(16  *  1)
475         KERNEL8(16  *  1)
476         cmpl    $128 *  2, %eax
477         jle     .L12
478         KERNEL1(16  *  2)
479         KERNEL2(16  *  2)
480         KERNEL3(16  *  2)
481         KERNEL4(16  *  2)
482         KERNEL5(16  *  2)
483         KERNEL6(16  *  2)
484         KERNEL7(16  *  2)
485         KERNEL8(16  *  2)
486         cmpl    $128 *  3, %eax
487         jle     .L12
488         KERNEL1(16  *  3)
489         KERNEL2(16  *  3)
490         KERNEL3(16  *  3)
491         KERNEL4(16  *  3)
492         KERNEL5(16  *  3)
493         KERNEL6(16  *  3)
494         KERNEL7(16  *  3)
495         KERNEL8(16  *  3)
496         cmpl    $128 *  4, %eax
497         jle     .L12
498         KERNEL1(16  *  4)
499         KERNEL2(16  *  4)
500         KERNEL3(16  *  4)
501         KERNEL4(16  *  4)
502         KERNEL5(16  *  4)
503         KERNEL6(16  *  4)
504         KERNEL7(16  *  4)
505         KERNEL8(16  *  4)
506         cmpl    $128 *  5, %eax
507         jle     .L12
508         KERNEL1(16  *  5)
509         KERNEL2(16  *  5)
510         KERNEL3(16  *  5)
511         KERNEL4(16  *  5)
512         KERNEL5(16  *  5)
513         KERNEL6(16  *  5)
514         KERNEL7(16  *  5)
515         KERNEL8(16  *  5)
516         cmpl    $128 *  6, %eax
517         jle     .L12
518         KERNEL1(16  *  6)
519         KERNEL2(16  *  6)
520         KERNEL3(16  *  6)
521         KERNEL4(16  *  6)
522         KERNEL5(16  *  6)
523         KERNEL6(16  *  6)
524         KERNEL7(16  *  6)
525         KERNEL8(16  *  6)
526         cmpl    $128 *  7, %eax
527         jle     .L12
528         KERNEL1(16  *  7)
529         KERNEL2(16  *  7)
530         KERNEL3(16  *  7)
531         KERNEL4(16  *  7)
532         KERNEL5(16  *  7)
533         KERNEL6(16  *  7)
534         KERNEL7(16  *  7)
535         KERNEL8(16  *  7)
536
537         addl    $128 * 4  * SIZE, BB
538         addl    $128 * 1  * SIZE, AA
539         subl    $128 * 8, %eax
540         jg      .L1X
541         jmp     .L15
542
543 .L12:
544         leal    (AA, %eax, 1), AA
545         leal    (BB, %eax, 4), BB
546         ALIGN_4
547 #else
548
549         sarl    $3, %eax
550         je      .L15
551         ALIGN_4
552
553 .L12:
554         KERNEL1(16  *  0)
555         KERNEL2(16  *  0)
556         KERNEL3(16  *  0)
557         KERNEL4(16  *  0)
558         KERNEL5(16  *  0)
559         KERNEL6(16  *  0)
560         KERNEL7(16  *  0)
561         KERNEL8(16  *  0)
562
563         addl   $64 * SIZE, BB
564         addl   $16 * SIZE, AA
565         decl   %eax
566         jne    .L12
567         ALIGN_4
568 #endif
569
570 .L15:
571 #if defined(LT) || defined(RN)
572         movl    KK, %eax
573 #else
574         movl    K, %eax
575         subl    KK, %eax
576 #endif
577         andl    $7, %eax                # if (k & 1)
578         BRANCH
579         je .L18
580         ALIGN_3
581
582 .L16:
583         mulpd    %xmm0, %xmm2
584         addpd    %xmm2, %xmm4
585         movapd   2 * SIZE(BB), %xmm2
586         mulpd    %xmm0, %xmm2
587         addpd    %xmm2, %xmm5
588         movapd   4 * SIZE(BB), %xmm2
589         mulpd    %xmm0, %xmm2
590         mulpd    6 * SIZE(BB), %xmm0
591         addpd    %xmm2, %xmm6
592         movapd   8 * SIZE(BB), %xmm2
593         addpd    %xmm0, %xmm7
594         movapd   2 * SIZE(AA), %xmm0
595
596         addl    $2 * SIZE, AA
597         addl    $8 * SIZE, BB
598         decl    %eax
599         jg      .L16
600         ALIGN_4
601
602 .L18:
603 #if defined(LN) || defined(RT)
604         movl    KK, %eax
605 #ifdef LN
606         subl    $2, %eax
607 #else
608         subl    $4, %eax
609 #endif
610
611         movl    AORIG, AA
612         movl    BORIG, B
613         leal    BUFFER, BB
614
615         leal    (, %eax, SIZE), %eax
616         leal    (AA, %eax, 2), AA
617         leal    (B,  %eax, 4), B
618         leal    (BB, %eax, 8), BB
619 #endif
620
621 #if defined(LN) || defined(LT)
622         movapd   %xmm4, %xmm0
623         unpcklpd %xmm5, %xmm4
624         unpckhpd %xmm5, %xmm0
625
626         movapd   %xmm6, %xmm1
627         unpcklpd %xmm7, %xmm6
628         unpckhpd %xmm7, %xmm1
629
630         movapd   0 * SIZE(B), %xmm2
631         movapd   2 * SIZE(B), %xmm5
632         movapd   4 * SIZE(B), %xmm3
633         movapd   6 * SIZE(B), %xmm7
634
635         subpd   %xmm4,  %xmm2
636         subpd   %xmm6,  %xmm5
637         subpd   %xmm0,  %xmm3
638         subpd   %xmm1,  %xmm7
639 #else
640         movapd   0 * SIZE(AA), %xmm0
641         movapd   2 * SIZE(AA), %xmm1
642         movapd   4 * SIZE(AA), %xmm2
643         movapd   6 * SIZE(AA), %xmm3
644
645         subpd   %xmm4, %xmm0
646         subpd   %xmm5, %xmm1
647         subpd   %xmm6, %xmm2
648         subpd   %xmm7, %xmm3
649 #endif
650
651 #ifdef LN
652         movlpd   3 * SIZE(AA), %xmm4
653         movhpd   3 * SIZE(AA), %xmm4
654         mulpd    %xmm4, %xmm3
655         mulpd    %xmm4, %xmm7
656
657         movlpd   2 * SIZE(AA), %xmm4
658         movhpd   2 * SIZE(AA), %xmm4
659         movapd   %xmm4, %xmm6
660         mulpd    %xmm3, %xmm4
661         subpd    %xmm4, %xmm2
662         mulpd    %xmm7, %xmm6
663         subpd    %xmm6, %xmm5
664
665         movlpd   0 * SIZE(AA), %xmm4
666         movhpd   0 * SIZE(AA), %xmm4
667         mulpd    %xmm4, %xmm2
668         mulpd    %xmm4, %xmm5
669
670 #endif
671
672 #ifdef LT
673         movlpd   0 * SIZE(AA), %xmm4
674         movhpd   0 * SIZE(AA), %xmm4
675         mulpd    %xmm4, %xmm2
676         mulpd    %xmm4, %xmm5
677
678         movlpd   1 * SIZE(AA), %xmm4
679         movhpd   1 * SIZE(AA), %xmm4
680         movapd   %xmm4, %xmm6
681         mulpd    %xmm2, %xmm4
682         subpd    %xmm4, %xmm3
683         mulpd    %xmm5, %xmm6
684         subpd    %xmm6, %xmm7
685
686         movlpd   3 * SIZE(AA), %xmm4
687         movhpd   3 * SIZE(AA), %xmm4
688         mulpd    %xmm4, %xmm3
689         mulpd    %xmm4, %xmm7
690 #endif
691
692 #ifdef RN
693         movlpd   0 * SIZE(B), %xmm4
694         movhpd   0 * SIZE(B), %xmm4
695         mulpd    %xmm4, %xmm0
696         movlpd   1 * SIZE(B), %xmm4
697         movhpd   1 * SIZE(B), %xmm4
698         mulpd    %xmm0, %xmm4
699         subpd    %xmm4, %xmm1
700         movlpd   2 * SIZE(B), %xmm4
701         movhpd   2 * SIZE(B), %xmm4
702         mulpd    %xmm0, %xmm4
703         subpd    %xmm4, %xmm2
704         movlpd   3 * SIZE(B), %xmm4
705         movhpd   3 * SIZE(B), %xmm4
706         mulpd    %xmm0, %xmm4
707         subpd    %xmm4, %xmm3
708
709         movlpd   5 * SIZE(B), %xmm4
710         movhpd   5 * SIZE(B), %xmm4
711         mulpd    %xmm4, %xmm1
712         movlpd   6 * SIZE(B), %xmm4
713         movhpd   6 * SIZE(B), %xmm4
714         mulpd    %xmm1, %xmm4
715         subpd    %xmm4, %xmm2
716         movlpd   7 * SIZE(B), %xmm4
717         movhpd   7 * SIZE(B), %xmm4
718         mulpd    %xmm1, %xmm4
719         subpd    %xmm4, %xmm3
720
721         movlpd  10 * SIZE(B), %xmm4
722         movhpd  10 * SIZE(B), %xmm4
723         mulpd    %xmm4, %xmm2
724         movlpd  11 * SIZE(B), %xmm4
725         movhpd  11 * SIZE(B), %xmm4
726         mulpd    %xmm2, %xmm4
727         subpd    %xmm4, %xmm3
728
729         movlpd  15 * SIZE(B), %xmm4
730         movhpd  15 * SIZE(B), %xmm4
731         mulpd    %xmm4, %xmm3
732 #endif
733
734 #ifdef RT
735         movlpd  15 * SIZE(B), %xmm4
736         movhpd  15 * SIZE(B), %xmm4
737         mulpd    %xmm4, %xmm3
738         movlpd  14 * SIZE(B), %xmm4
739         movhpd  14 * SIZE(B), %xmm4
740         mulpd    %xmm3, %xmm4
741         subpd    %xmm4, %xmm2
742         movlpd  13 * SIZE(B), %xmm4
743         movhpd  13 * SIZE(B), %xmm4
744         mulpd    %xmm3, %xmm4
745         subpd    %xmm4, %xmm1
746         movlpd  12 * SIZE(B), %xmm4
747         movhpd  12 * SIZE(B), %xmm4
748         mulpd    %xmm3, %xmm4
749         subpd    %xmm4, %xmm0
750
751         movlpd  10 * SIZE(B), %xmm4
752         movhpd  10 * SIZE(B), %xmm4
753         mulpd    %xmm4, %xmm2
754         movlpd   9 * SIZE(B), %xmm4
755         movhpd   9 * SIZE(B), %xmm4
756         mulpd    %xmm2, %xmm4
757         subpd    %xmm4, %xmm1
758         movlpd   8 * SIZE(B), %xmm4
759         movhpd   8 * SIZE(B), %xmm4
760         mulpd    %xmm2, %xmm4
761         subpd    %xmm4, %xmm0
762
763         movlpd   5 * SIZE(B), %xmm4
764         movhpd   5 * SIZE(B), %xmm4
765         mulpd    %xmm4, %xmm1
766         movlpd   4 * SIZE(B), %xmm4
767         movhpd   4 * SIZE(B), %xmm4
768         mulpd    %xmm1, %xmm4
769         subpd    %xmm4, %xmm0
770
771         movlpd   0 * SIZE(B), %xmm4
772         movhpd   0 * SIZE(B), %xmm4
773         mulpd    %xmm4, %xmm0
774 #endif
775
776 #if defined(LN) || defined(LT)
777         movapd  %xmm2,   0 * SIZE(B)
778         movapd  %xmm5,   2 * SIZE(B)
779         movapd  %xmm3,   4 * SIZE(B)
780         movapd  %xmm7,   6 * SIZE(B)
781
782         movlpd  %xmm2,   0 * SIZE(BB)
783         movlpd  %xmm2,   1 * SIZE(BB)
784         movhpd  %xmm2,   2 * SIZE(BB)
785         movhpd  %xmm2,   3 * SIZE(BB)
786         movlpd  %xmm5,   4 * SIZE(BB)
787         movlpd  %xmm5,   5 * SIZE(BB)
788         movhpd  %xmm5,   6 * SIZE(BB)
789         movhpd  %xmm5,   7 * SIZE(BB)
790         movlpd  %xmm3,   8 * SIZE(BB)
791         movlpd  %xmm3,   9 * SIZE(BB)
792         movhpd  %xmm3,  10 * SIZE(BB)
793         movhpd  %xmm3,  11 * SIZE(BB)
794         movlpd  %xmm7,  12 * SIZE(BB)
795         movlpd  %xmm7,  13 * SIZE(BB)
796         movhpd  %xmm7,  14 * SIZE(BB)
797         movhpd  %xmm7,  15 * SIZE(BB)
798 #else
799         movapd  %xmm0,   0 * SIZE(AA)
800         movapd  %xmm1,   2 * SIZE(AA)
801         movapd  %xmm2,   4 * SIZE(AA)
802         movapd  %xmm3,   6 * SIZE(AA)
803 #endif
804
805 #ifdef LN
806         subl    $2 * SIZE, CO1
807 #endif
808
809         leal    (LDC, LDC, 2), %eax
810
811 #if defined(LN) || defined(LT)
812         movlpd  %xmm2, 0 * SIZE(CO1)
813         movlpd  %xmm3, 1 * SIZE(CO1)
814         movhpd  %xmm2, 0 * SIZE(CO1, LDC, 1)
815         movhpd  %xmm3, 1 * SIZE(CO1, LDC, 1)
816         movlpd  %xmm5, 0 * SIZE(CO1, LDC, 2)
817         movlpd  %xmm7, 1 * SIZE(CO1, LDC, 2)
818         movhpd  %xmm5, 0 * SIZE(CO1, %eax, 1)
819         movhpd  %xmm7, 1 * SIZE(CO1, %eax, 1)
820 #else
821         movlpd  %xmm0, 0 * SIZE(CO1)
822         movhpd  %xmm0, 1 * SIZE(CO1)
823         movlpd  %xmm1, 0 * SIZE(CO1, LDC, 1)
824         movhpd  %xmm1, 1 * SIZE(CO1, LDC, 1)
825         movlpd  %xmm2, 0 * SIZE(CO1, LDC, 2)
826         movhpd  %xmm2, 1 * SIZE(CO1, LDC, 2)
827         movlpd  %xmm3, 0 * SIZE(CO1, %eax, 1)
828         movhpd  %xmm3, 1 * SIZE(CO1, %eax, 1)
829 #endif
830
831 #ifndef LN
832         addl    $2 * SIZE, CO1
833 #endif
834
835 #if defined(LT) || defined(RN)
836         movl    K,  %eax
837         subl    KK, %eax
838         leal    (,%eax, SIZE), %eax
839         leal    (AA, %eax, 2), AA
840 #ifdef LT
841         addl    $8 * SIZE, B
842 #endif
843 #endif
844
845 #ifdef LN
846         subl    $2, KK
847         movl    BORIG, B
848 #endif
849
850 #ifdef LT
851         addl    $2, KK
852 #endif
853
854 #ifdef RT
855         movl    K, %eax
856         movl    BORIG, B
857         sall    $1 + BASE_SHIFT, %eax
858         addl    %eax, AORIG
859 #endif
860
861         decl    %ebx                    # i --
862         jg      .L11
863         ALIGN_4
864
865 .L20:
866         movl    M,  %ebx
867         testl   $1, %ebx        # i = (m >> 2)
868         jle     .L29
869
870 #ifdef LN
871        movl     K, %eax
872        sall     $BASE_SHIFT, %eax
873        subl     %eax, AORIG
874 #endif
875
876 #if defined(LN) || defined(RT)
877         movl    KK, %eax
878         movl    AORIG, AA
879         leal    (AA, %eax, SIZE), AA
880 #endif
881
882         leal    BUFFER, BB
883
884 #if defined(LN) || defined(RT)
885         movl    KK, %eax
886         sall    $3 + BASE_SHIFT, %eax
887         addl    %eax, BB
888 #endif  
889
890         pxor    %xmm4, %xmm4
891         pxor    %xmm5, %xmm5
892         pxor    %xmm6, %xmm6
893         pxor    %xmm7, %xmm7
894
895         movlpd   0 * SIZE(AA), %xmm0
896         movlpd   4 * SIZE(AA), %xmm1
897         movlpd   0 * SIZE(BB), %xmm2
898         movlpd   8 * SIZE(BB), %xmm3
899
900 #if defined(LT) || defined(RN)
901         movl    KK, %eax
902 #else
903         movl    K, %eax
904         subl    KK, %eax
905 #endif
906         sarl    $3, %eax
907         je      .L25
908         ALIGN_4
909
910 .L22:
911         mulsd   %xmm0, %xmm2
912         addsd   %xmm2, %xmm4
913 #if defined(OPTERON) || defined(BARCELONA) || defined(BOBCAT) || defined(BARCELONA_OPTIMIZATION)
914         PREFETCH (PREFETCHSIZE  + 0) * SIZE(AA)
915 #endif
916         movlpd   2 * SIZE(BB), %xmm2
917         mulsd   %xmm0, %xmm2
918         addsd   %xmm2, %xmm5
919         movlpd   4 * SIZE(BB), %xmm2
920         mulsd   %xmm0, %xmm2
921         mulsd    6 * SIZE(BB), %xmm0
922         addsd   %xmm2, %xmm6
923         movlpd  16 * SIZE(BB), %xmm2
924         addsd   %xmm0, %xmm7
925         movlpd   1 * SIZE(AA), %xmm0
926         mulsd   %xmm0, %xmm3
927         addsd   %xmm3, %xmm4
928         movlpd  10 * SIZE(BB), %xmm3
929         mulsd   %xmm0, %xmm3
930         addsd   %xmm3, %xmm5
931         movlpd  12 * SIZE(BB), %xmm3
932         mulsd   %xmm0, %xmm3
933         mulsd   14 * SIZE(BB), %xmm0
934         addsd   %xmm3, %xmm6
935         movlpd  24 * SIZE(BB), %xmm3
936         addsd   %xmm0, %xmm7
937         movlpd   2 * SIZE(AA), %xmm0
938         mulsd   %xmm0, %xmm2
939         addsd   %xmm2, %xmm4
940         movlpd  18 * SIZE(BB), %xmm2
941         mulsd   %xmm0, %xmm2
942         addsd   %xmm2, %xmm5
943         movlpd  20 * SIZE(BB), %xmm2
944         mulsd   %xmm0, %xmm2
945         mulsd   22 * SIZE(BB), %xmm0
946         addsd   %xmm2, %xmm6
947         movlpd  32 * SIZE(BB), %xmm2
948         addsd   %xmm0, %xmm7
949         movlpd   3 * SIZE(AA), %xmm0
950         mulsd   %xmm0, %xmm3
951         addsd   %xmm3, %xmm4
952         movlpd  26 * SIZE(BB), %xmm3
953         mulsd   %xmm0, %xmm3
954         addsd   %xmm3, %xmm5
955         movlpd  28 * SIZE(BB), %xmm3
956         mulsd   %xmm0, %xmm3
957         mulsd   30 * SIZE(BB), %xmm0
958         addsd   %xmm3, %xmm6
959         movlpd  40 * SIZE(BB), %xmm3
960         addsd   %xmm0, %xmm7
961         movlpd   8 * SIZE(AA), %xmm0
962 #if defined(OPTERON) || defined(BARCELONA) || defined(BOBCAT) || defined(BARCELONA_OPTIMIZATION)
963         PREFETCH (PREFETCHSIZE  + 8) * SIZE(AA)
964 #endif
965         mulsd   %xmm1, %xmm2
966         addsd   %xmm2, %xmm4
967         movlpd  34 * SIZE(BB), %xmm2
968         mulsd   %xmm1, %xmm2
969         addsd   %xmm2, %xmm5
970         movlpd  36 * SIZE(BB), %xmm2
971         mulsd   %xmm1, %xmm2
972         mulsd   38 * SIZE(BB), %xmm1
973         addsd   %xmm2, %xmm6
974         movlpd  48 * SIZE(BB), %xmm2
975         addsd   %xmm1, %xmm7
976         movlpd   5 * SIZE(AA), %xmm1
977         mulsd   %xmm1, %xmm3
978         addsd   %xmm3, %xmm4
979         movlpd  42 * SIZE(BB), %xmm3
980         mulsd   %xmm1, %xmm3
981         addsd   %xmm3, %xmm5
982         movlpd  44 * SIZE(BB), %xmm3
983         mulsd   %xmm1, %xmm3
984         mulsd   46 * SIZE(BB), %xmm1
985         addsd   %xmm3, %xmm6
986         movlpd  56 * SIZE(BB), %xmm3
987         addsd   %xmm1, %xmm7
988         movlpd   6 * SIZE(AA), %xmm1
989         mulsd   %xmm1, %xmm2
990         addsd   %xmm2, %xmm4
991         movlpd  50 * SIZE(BB), %xmm2
992         mulsd   %xmm1, %xmm2
993         addsd   %xmm2, %xmm5
994         movlpd  52 * SIZE(BB), %xmm2
995         mulsd   %xmm1, %xmm2
996         mulsd   54 * SIZE(BB), %xmm1
997         addsd   %xmm2, %xmm6
998         movlpd  64 * SIZE(BB), %xmm2
999         addsd   %xmm1, %xmm7
1000         movlpd   7 * SIZE(AA), %xmm1
1001         mulsd   %xmm1, %xmm3
1002         addsd   %xmm3, %xmm4
1003         movlpd  58 * SIZE(BB), %xmm3
1004         mulsd   %xmm1, %xmm3
1005         addsd   %xmm3, %xmm5
1006         movlpd  60 * SIZE(BB), %xmm3
1007         mulsd   %xmm1, %xmm3
1008         mulsd   62 * SIZE(BB), %xmm1
1009         addsd   %xmm3, %xmm6
1010         movlpd  72 * SIZE(BB), %xmm3
1011         addl   $64 * SIZE, BB
1012         addsd   %xmm1, %xmm7
1013         movlpd  12 * SIZE(AA), %xmm1
1014         addl   $8 * SIZE, AA
1015         decl   %eax
1016         jne    .L22
1017         ALIGN_4
1018
1019 .L25:
1020 #if defined(LT) || defined(RN)
1021         movl    KK, %eax
1022 #else
1023         movl    K, %eax
1024         subl    KK, %eax
1025 #endif
1026         andl    $7, %eax                # if (k & 1)
1027         BRANCH
1028         je .L28
1029
1030 .L26:
1031         mulsd   %xmm0, %xmm2
1032         addsd   %xmm2, %xmm4
1033         movlpd   2 * SIZE(BB), %xmm2
1034         mulsd   %xmm0, %xmm2
1035         addsd   %xmm2, %xmm5
1036         movlpd   4 * SIZE(BB), %xmm2
1037         mulsd   %xmm0, %xmm2
1038         mulsd    6 * SIZE(BB), %xmm0
1039         addsd   %xmm2, %xmm6
1040         movlpd   8 * SIZE(BB), %xmm2
1041         addsd   %xmm0, %xmm7
1042         movlpd   1 * SIZE(AA), %xmm0
1043
1044         addl    $1 * SIZE, AA
1045         addl    $8 * SIZE, BB
1046         decl    %eax
1047         jg      .L26
1048         ALIGN_4
1049
1050 .L28:
1051 #if defined(LN) || defined(RT)
1052         movl    KK, %eax
1053 #ifdef LN
1054         subl    $1, %eax
1055 #else
1056         subl    $4, %eax
1057 #endif
1058
1059         movl    AORIG, AA
1060         movl    BORIG, B
1061         leal    BUFFER, BB
1062
1063         leal    (, %eax, SIZE), %eax
1064         addl    %eax, AA
1065         leal    (B,  %eax, 4), B
1066         leal    (BB, %eax, 8), BB
1067 #endif
1068
1069 #if defined(LN) || defined(LT)
1070         unpcklpd %xmm5, %xmm4
1071         unpcklpd %xmm7, %xmm6
1072
1073         movapd   0 * SIZE(B), %xmm2
1074         movapd   2 * SIZE(B), %xmm5
1075
1076         subpd   %xmm4,  %xmm2
1077         subpd   %xmm6,  %xmm5
1078 #else
1079         movlpd   0 * SIZE(AA), %xmm0
1080         movlpd   1 * SIZE(AA), %xmm1
1081         movlpd   2 * SIZE(AA), %xmm2
1082         movlpd   3 * SIZE(AA), %xmm3
1083
1084         subsd   %xmm4, %xmm0
1085         subsd   %xmm5, %xmm1
1086         subsd   %xmm6, %xmm2
1087         subsd   %xmm7, %xmm3
1088 #endif
1089
1090 #ifdef LN
1091         movlpd   0 * SIZE(AA), %xmm4
1092         movhpd   0 * SIZE(AA), %xmm4
1093         mulpd    %xmm4, %xmm2
1094         mulpd    %xmm4, %xmm5
1095 #endif
1096
1097 #ifdef LT
1098         movlpd   0 * SIZE(AA), %xmm4
1099         movhpd   0 * SIZE(AA), %xmm4
1100         mulpd    %xmm4, %xmm2
1101         mulpd    %xmm4, %xmm5
1102 #endif
1103
1104 #ifdef RN
1105         movlpd   0 * SIZE(B), %xmm4
1106         mulsd    %xmm4, %xmm0
1107         movlpd   1 * SIZE(B), %xmm4
1108         mulsd    %xmm0, %xmm4
1109         subsd    %xmm4, %xmm1
1110         movlpd   2 * SIZE(B), %xmm4
1111         mulsd    %xmm0, %xmm4
1112         subsd    %xmm4, %xmm2
1113         movlpd   3 * SIZE(B), %xmm4
1114         mulsd    %xmm0, %xmm4
1115         subsd    %xmm4, %xmm3
1116
1117         movlpd   5 * SIZE(B), %xmm4
1118         mulsd    %xmm4, %xmm1
1119         movlpd   6 * SIZE(B), %xmm4
1120         mulsd    %xmm1, %xmm4
1121         subsd    %xmm4, %xmm2
1122         movlpd   7 * SIZE(B), %xmm4
1123         mulsd    %xmm1, %xmm4
1124         subsd    %xmm4, %xmm3
1125
1126         movlpd  10 * SIZE(B), %xmm4
1127         mulsd    %xmm4, %xmm2
1128         movlpd  11 * SIZE(B), %xmm4
1129         mulsd    %xmm2, %xmm4
1130         subsd    %xmm4, %xmm3
1131
1132         movlpd  15 * SIZE(B), %xmm4
1133         mulsd    %xmm4, %xmm3
1134 #endif
1135
1136 #ifdef RT
1137         movlpd  15 * SIZE(B), %xmm4
1138         mulsd    %xmm4, %xmm3
1139         movlpd  14 * SIZE(B), %xmm4
1140         mulsd    %xmm3, %xmm4
1141         subsd    %xmm4, %xmm2
1142         movlpd  13 * SIZE(B), %xmm4
1143         mulsd    %xmm3, %xmm4
1144         subsd    %xmm4, %xmm1
1145         movlpd  12 * SIZE(B), %xmm4
1146         mulsd    %xmm3, %xmm4
1147         subsd    %xmm4, %xmm0
1148
1149         movlpd  10 * SIZE(B), %xmm4
1150         mulsd    %xmm4, %xmm2
1151         movlpd   9 * SIZE(B), %xmm4
1152         mulsd    %xmm2, %xmm4
1153         subsd    %xmm4, %xmm1
1154         movlpd   8 * SIZE(B), %xmm4
1155         mulsd    %xmm2, %xmm4
1156         subsd    %xmm4, %xmm0
1157
1158         movlpd   5 * SIZE(B), %xmm4
1159         mulsd    %xmm4, %xmm1
1160         movlpd   4 * SIZE(B), %xmm4
1161         mulsd    %xmm1, %xmm4
1162         subsd    %xmm4, %xmm0
1163
1164         movlpd   0 * SIZE(B), %xmm4
1165         mulsd    %xmm4, %xmm0
1166 #endif
1167
1168 #if defined(LN) || defined(LT)
1169         movapd  %xmm2,   0 * SIZE(B)
1170         movapd  %xmm5,   2 * SIZE(B)
1171
1172         movlpd  %xmm2,   0 * SIZE(BB)
1173         movlpd  %xmm2,   1 * SIZE(BB)
1174         movhpd  %xmm2,   2 * SIZE(BB)
1175         movhpd  %xmm2,   3 * SIZE(BB)
1176         movlpd  %xmm5,   4 * SIZE(BB)
1177         movlpd  %xmm5,   5 * SIZE(BB)
1178         movhpd  %xmm5,   6 * SIZE(BB)
1179         movhpd  %xmm5,   7 * SIZE(BB)
1180 #else
1181         movlpd  %xmm0,   0 * SIZE(AA)
1182         movlpd  %xmm1,   1 * SIZE(AA)
1183         movlpd  %xmm2,   2 * SIZE(AA)
1184         movlpd  %xmm3,   3 * SIZE(AA)
1185 #endif
1186
1187 #ifdef LN
1188         subl    $1 * SIZE, CO1
1189 #endif
1190
1191         leal    (LDC, LDC, 2), %eax
1192
1193 #if defined(LN) || defined(LT)
1194         movlpd  %xmm2, 0 * SIZE(CO1)
1195         movhpd  %xmm2, 0 * SIZE(CO1, LDC, 1)
1196         movlpd  %xmm5, 0 * SIZE(CO1, LDC, 2)
1197         movhpd  %xmm5, 0 * SIZE(CO1, %eax, 1)
1198 #else
1199         movlpd  %xmm0, 0 * SIZE(CO1)
1200         movlpd  %xmm1, 0 * SIZE(CO1, LDC, 1)
1201         movlpd  %xmm2, 0 * SIZE(CO1, LDC, 2)
1202         movlpd  %xmm3, 0 * SIZE(CO1, %eax, 1)
1203 #endif
1204
1205 #ifndef LN
1206         addl    $1 * SIZE, CO1
1207 #endif
1208
1209 #if defined(LT) || defined(RN)
1210         movl    K,  %eax
1211         subl    KK, %eax
1212         leal    (AA,%eax, SIZE), AA
1213 #ifdef LT
1214         addl    $4 * SIZE, B
1215 #endif
1216 #endif
1217
1218 #ifdef LN
1219         subl    $1, KK
1220         movl    BORIG, B
1221 #endif
1222
1223 #ifdef LT
1224         addl    $1, KK
1225 #endif
1226
1227 #ifdef RT
1228         movl    K, %eax
1229         movl    BORIG, B
1230         sall    $BASE_SHIFT, %eax
1231         addl    %eax, AORIG
1232 #endif
1233         ALIGN_4
1234
1235 .L29:
1236 #ifdef LN
1237        movl     K, %eax
1238        leal     (, %eax, SIZE), %eax
1239        leal     (B, %eax, 4), B
1240 #endif
1241
1242 #if defined(LT) || defined(RN)
1243         movl    K,  %eax
1244         subl    KK, %eax
1245         leal    (,%eax, SIZE), %eax
1246         leal    (B,  %eax, 4), B
1247 #endif
1248
1249 #ifdef RN
1250         addl    $4, KK
1251 #endif
1252
1253 #ifdef RT
1254         subl    $4, KK
1255 #endif
1256
1257         decl    J                       # j --
1258         jg      .L01
1259         ALIGN_4
1260
1261 .L30:
1262         testl   $2, N
1263         je      .L60
1264
1265 #ifdef LN
1266         movl    OFFSET, %eax
1267         addl    M, %eax
1268         movl    %eax, KK
1269 #endif  
1270
1271         leal    BUFFER, BB
1272
1273 #ifdef RT
1274        movl     K, %eax
1275        sall     $1 + BASE_SHIFT, %eax
1276        subl     %eax, B
1277 #endif
1278
1279 #if defined(LN) || defined(RT)
1280         movl    KK, %eax
1281         movl    B, BORIG
1282         leal    (, %eax, SIZE), %eax
1283         leal    (B,  %eax, 2), B
1284         leal    (BB, %eax, 4), BB
1285 #endif  
1286
1287 #ifdef LT
1288         movl    OFFSET, %eax
1289         movl    %eax, KK
1290 #endif
1291
1292 #if defined(LT) || defined(RN)
1293         movl    KK, %eax
1294 #else
1295         movl    K, %eax
1296         subl    KK, %eax
1297 #endif
1298         sarl    $2, %eax
1299         jle     .L35
1300         ALIGN_4
1301         
1302 .L32:
1303 #define COPYPREFETCH 40
1304
1305         prefetchnta     (COPYPREFETCH) * SIZE(B)
1306
1307         movq     0 * SIZE(B), %mm0
1308         movq     1 * SIZE(B), %mm1
1309         movq     2 * SIZE(B), %mm2
1310         movq     3 * SIZE(B), %mm3
1311         movq     4 * SIZE(B), %mm4
1312         movq     5 * SIZE(B), %mm5
1313         movq     6 * SIZE(B), %mm6
1314         movq     7 * SIZE(B), %mm7
1315
1316         movq    %mm0,  0 * SIZE(BB)
1317         movq    %mm0,  1 * SIZE(BB)
1318         movq    %mm1,  2 * SIZE(BB)
1319         movq    %mm1,  3 * SIZE(BB)
1320         movq    %mm2,  4 * SIZE(BB)
1321         movq    %mm2,  5 * SIZE(BB)
1322         movq    %mm3,  6 * SIZE(BB)
1323         movq    %mm3,  7 * SIZE(BB)
1324
1325         movq    %mm4,  8 * SIZE(BB)
1326         movq    %mm4,  9 * SIZE(BB)
1327         movq    %mm5, 10 * SIZE(BB)
1328         movq    %mm5, 11 * SIZE(BB)
1329         movq    %mm6, 12 * SIZE(BB)
1330         movq    %mm6, 13 * SIZE(BB)
1331         movq    %mm7, 14 * SIZE(BB)
1332         movq    %mm7, 15 * SIZE(BB)
1333
1334         addl    $ 8 * SIZE, B
1335         addl    $16 * SIZE, BB
1336         decl    %eax
1337         jne     .L32
1338         ALIGN_2
1339
1340 .L35:
1341 #if defined(LT) || defined(RN)
1342         movl    KK, %eax
1343 #else
1344         movl    K, %eax
1345         subl    KK, %eax
1346 #endif
1347         andl    $3, %eax
1348         BRANCH
1349         jle     .L40
1350         ALIGN_2
1351
1352 .L36:
1353         movq     0 * SIZE(B), %mm0
1354         movq     1 * SIZE(B), %mm1
1355
1356         movq    %mm0,  0 * SIZE(BB)
1357         movq    %mm0,  1 * SIZE(BB)
1358         movq    %mm1,  2 * SIZE(BB)
1359         movq    %mm1,  3 * SIZE(BB)
1360
1361         addl    $2 * SIZE, B
1362         addl    $4 * SIZE, BB
1363         decl    %eax
1364         jne     .L36
1365         ALIGN_4
1366         
1367 .L40:
1368 #if defined(LT) || defined(RN)
1369         movl    A, AA
1370 #else
1371         movl    A, %eax
1372         movl    %eax, AORIG
1373 #endif
1374
1375         leal    (, LDC, 2), %eax
1376
1377 #ifdef RT
1378         subl    %eax, C
1379 #endif
1380         movl    C, CO1
1381 #ifndef RT
1382         addl    %eax, C
1383 #endif
1384
1385         movl    M,  %ebx
1386         sarl    $1, %ebx        # i = (m >> 2)
1387         jle     .L50
1388         ALIGN_4
1389
1390 .L41:
1391 #ifdef LN
1392        movl     K, %eax
1393        sall     $1 + BASE_SHIFT, %eax
1394        subl     %eax, AORIG
1395 #endif
1396
1397 #if defined(LN) || defined(RT)
1398         movl    KK, %eax
1399         movl    AORIG, AA
1400         leal    (, %eax, SIZE), %eax
1401         leal    (AA, %eax, 2), AA
1402 #endif
1403
1404         leal    BUFFER, BB
1405
1406 #if defined(LN) || defined(RT)
1407         movl    KK, %eax
1408         sall    $2 + BASE_SHIFT, %eax
1409         addl    %eax, BB
1410 #endif  
1411
1412         pxor    %xmm4, %xmm4
1413         pxor    %xmm5, %xmm5
1414         pxor    %xmm6, %xmm6
1415         pxor    %xmm7, %xmm7
1416
1417         movapd   0 * SIZE(AA), %xmm0
1418         movapd   8 * SIZE(AA), %xmm1
1419         movapd   0 * SIZE(BB), %xmm2
1420         movapd   8 * SIZE(BB), %xmm3
1421
1422 #ifdef LN
1423         prefetchw       -2 * SIZE(CO1)
1424         prefetchw       -2 * SIZE(CO1, LDC)
1425 #else
1426         prefetchw        1 * SIZE(CO1)
1427         prefetchw        1 * SIZE(CO1, LDC)
1428 #endif
1429
1430 #if defined(LT) || defined(RN)
1431         movl    KK, %eax
1432 #else
1433         movl    K, %eax
1434         subl    KK, %eax
1435 #endif
1436         sarl    $3, %eax
1437         je      .L45
1438         ALIGN_4
1439
1440 .L42:
1441         mulpd   %xmm0, %xmm2
1442 #if defined(OPTERON) || defined(BARCELONA) || defined(BOBCAT) || defined(BARCELONA_OPTIMIZATION)
1443         prefetcht0 (PREFETCHSIZE  + 0) * SIZE(AA)
1444 #endif
1445         mulpd    2 * SIZE(BB), %xmm0
1446         addpd   %xmm2, %xmm4
1447         movapd   4 * SIZE(BB), %xmm2
1448         addpd   %xmm0, %xmm5
1449         movapd   2 * SIZE(AA), %xmm0
1450
1451         mulpd   %xmm0, %xmm2
1452         mulpd    6 * SIZE(BB), %xmm0
1453         addpd   %xmm2, %xmm6
1454         movapd  16 * SIZE(BB), %xmm2
1455         addpd   %xmm0, %xmm7
1456         movapd   4 * SIZE(AA), %xmm0
1457
1458         mulpd   %xmm0, %xmm3
1459         mulpd   10 * SIZE(BB), %xmm0
1460         addpd   %xmm3, %xmm4
1461         movapd  12 * SIZE(BB), %xmm3
1462         addpd   %xmm0, %xmm5
1463         movapd   6 * SIZE(AA), %xmm0
1464
1465         mulpd   %xmm0, %xmm3
1466         mulpd   14 * SIZE(BB), %xmm0
1467         addpd   %xmm3, %xmm6
1468         movapd  24 * SIZE(BB), %xmm3
1469         addpd   %xmm0, %xmm7
1470         movapd  16 * SIZE(AA), %xmm0
1471
1472 #if defined(OPTERON) || defined(BARCELONA) || defined(BOBCAT) || defined(BARCELONA_OPTIMIZATION)
1473         prefetcht0 (PREFETCHSIZE  + 8) * SIZE(AA)
1474 #endif
1475         mulpd   %xmm1, %xmm2
1476         mulpd   18 * SIZE(BB), %xmm1
1477         addpd   %xmm2, %xmm4
1478         movapd  20 * SIZE(BB), %xmm2
1479         addpd   %xmm1, %xmm5
1480         movapd  10 * SIZE(AA), %xmm1
1481
1482         mulpd   %xmm1, %xmm2
1483         mulpd   22 * SIZE(BB), %xmm1
1484         addpd   %xmm2, %xmm6
1485         movapd  32 * SIZE(BB), %xmm2
1486         addpd   %xmm1, %xmm7
1487         movapd  12 * SIZE(AA), %xmm1
1488
1489         mulpd   %xmm1, %xmm3
1490         mulpd   26 * SIZE(BB), %xmm1
1491         addpd   %xmm3, %xmm4
1492         movapd  28 * SIZE(BB), %xmm3
1493         addpd   %xmm1, %xmm5
1494         movapd  14 * SIZE(AA), %xmm1
1495
1496         mulpd   %xmm1, %xmm3
1497         mulpd   30 * SIZE(BB), %xmm1
1498         addpd   %xmm3, %xmm6
1499         movapd  40 * SIZE(BB), %xmm3
1500         addpd   %xmm1, %xmm7
1501         movapd  24 * SIZE(AA), %xmm1
1502
1503         addl   $16 * SIZE, AA
1504         addl   $32 * SIZE, BB
1505         decl   %eax
1506         jne    .L42
1507         ALIGN_4
1508
1509 .L45:
1510 #if defined(LT) || defined(RN)
1511         movl    KK, %eax
1512 #else
1513         movl    K, %eax
1514         subl    KK, %eax
1515 #endif
1516         andl    $7, %eax                # if (k & 1)
1517         BRANCH
1518         je .L48
1519         ALIGN_3
1520
1521 .L46:
1522         mulpd   %xmm0, %xmm2
1523         mulpd    2 * SIZE(BB), %xmm0
1524         addpd   %xmm2, %xmm4
1525         movapd   4 * SIZE(BB), %xmm2
1526         addpd   %xmm0, %xmm5
1527         movapd   2 * SIZE(AA), %xmm0
1528
1529         addl    $2 * SIZE, AA
1530         addl    $4 * SIZE, BB
1531         decl    %eax
1532         jg      .L46
1533         ALIGN_4
1534
1535 .L48:
1536         addpd   %xmm6, %xmm4
1537         addpd   %xmm7, %xmm5
1538
1539 #if defined(LN) || defined(RT)
1540         movl    KK, %eax
1541 #ifdef LN
1542         subl    $2, %eax
1543 #else
1544         subl    $2, %eax
1545 #endif
1546
1547         movl    AORIG, AA
1548         movl    BORIG, B
1549         leal    BUFFER, BB
1550
1551         leal    (, %eax, SIZE), %eax
1552         leal    (AA, %eax, 2), AA
1553         leal    (B,  %eax, 2), B
1554         leal    (BB, %eax, 4), BB
1555 #endif
1556
1557 #if defined(LN) || defined(LT)
1558         movapd   %xmm4, %xmm0
1559         unpcklpd %xmm5, %xmm4
1560         unpckhpd %xmm5, %xmm0
1561
1562         movapd   0 * SIZE(B), %xmm2
1563         movapd   2 * SIZE(B), %xmm3
1564
1565         subpd   %xmm4,  %xmm2
1566         subpd   %xmm0,  %xmm3
1567 #else
1568         movapd   0 * SIZE(AA), %xmm0
1569         movapd   2 * SIZE(AA), %xmm1
1570
1571         subpd   %xmm4, %xmm0
1572         subpd   %xmm5, %xmm1
1573 #endif
1574
1575 #ifdef LN
1576         movlpd   3 * SIZE(AA), %xmm4
1577         movhpd   3 * SIZE(AA), %xmm4
1578         mulpd    %xmm4, %xmm3
1579
1580         movlpd   2 * SIZE(AA), %xmm4
1581         movhpd   2 * SIZE(AA), %xmm4
1582         mulpd    %xmm3, %xmm4
1583         subpd    %xmm4, %xmm2
1584
1585         movlpd   0 * SIZE(AA), %xmm4
1586         movhpd   0 * SIZE(AA), %xmm4
1587         mulpd    %xmm4, %xmm2
1588
1589 #endif
1590
1591 #ifdef LT
1592         movlpd   0 * SIZE(AA), %xmm4
1593         movhpd   0 * SIZE(AA), %xmm4
1594         mulpd    %xmm4, %xmm2
1595
1596         movlpd   1 * SIZE(AA), %xmm4
1597         movhpd   1 * SIZE(AA), %xmm4
1598         mulpd    %xmm2, %xmm4
1599         subpd    %xmm4, %xmm3
1600
1601         movlpd   3 * SIZE(AA), %xmm4
1602         movhpd   3 * SIZE(AA), %xmm4
1603         mulpd    %xmm4, %xmm3
1604 #endif
1605
1606 #ifdef RN
1607         movlpd   0 * SIZE(B), %xmm4
1608         movhpd   0 * SIZE(B), %xmm4
1609         mulpd    %xmm4, %xmm0
1610         movlpd   1 * SIZE(B), %xmm4
1611         movhpd   1 * SIZE(B), %xmm4
1612         mulpd    %xmm0, %xmm4
1613         subpd    %xmm4, %xmm1
1614
1615         movlpd   3 * SIZE(B), %xmm4
1616         movhpd   3 * SIZE(B), %xmm4
1617         mulpd    %xmm4, %xmm1
1618 #endif
1619
1620 #ifdef RT
1621         movlpd   3 * SIZE(B), %xmm4
1622         movhpd   3 * SIZE(B), %xmm4
1623         mulpd    %xmm4, %xmm1
1624         movlpd   2 * SIZE(B), %xmm4
1625         movhpd   2 * SIZE(B), %xmm4
1626         mulpd    %xmm1, %xmm4
1627         subpd    %xmm4, %xmm0
1628
1629         movlpd   0 * SIZE(B), %xmm4
1630         movhpd   0 * SIZE(B), %xmm4
1631         mulpd    %xmm4, %xmm0
1632 #endif
1633
1634 #if defined(LN) || defined(LT)
1635         movapd  %xmm2,   0 * SIZE(B)
1636         movapd  %xmm3,   2 * SIZE(B)
1637
1638         movlpd  %xmm2,   0 * SIZE(BB)
1639         movlpd  %xmm2,   1 * SIZE(BB)
1640         movhpd  %xmm2,   2 * SIZE(BB)
1641         movhpd  %xmm2,   3 * SIZE(BB)
1642         movlpd  %xmm3,   4 * SIZE(BB)
1643         movlpd  %xmm3,   5 * SIZE(BB)
1644         movhpd  %xmm3,   6 * SIZE(BB)
1645         movhpd  %xmm3,   7 * SIZE(BB)
1646 #else
1647         movapd  %xmm0,   0 * SIZE(AA)
1648         movapd  %xmm1,   2 * SIZE(AA)
1649 #endif
1650
1651 #ifdef LN
1652         subl    $2 * SIZE, CO1
1653 #endif
1654
1655 #if defined(LN) || defined(LT)
1656         movlpd  %xmm2, 0 * SIZE(CO1)
1657         movlpd  %xmm3, 1 * SIZE(CO1)
1658         movhpd  %xmm2, 0 * SIZE(CO1, LDC, 1)
1659         movhpd  %xmm3, 1 * SIZE(CO1, LDC, 1)
1660 #else
1661         movlpd  %xmm0, 0 * SIZE(CO1)
1662         movhpd  %xmm0, 1 * SIZE(CO1)
1663         movlpd  %xmm1, 0 * SIZE(CO1, LDC, 1)
1664         movhpd  %xmm1, 1 * SIZE(CO1, LDC, 1)
1665 #endif
1666
1667 #ifndef LN
1668         addl    $2 * SIZE, CO1
1669 #endif
1670
1671 #if defined(LT) || defined(RN)
1672         movl    K,  %eax
1673         subl    KK, %eax
1674         leal    (,%eax, SIZE), %eax
1675         leal    (AA, %eax, 2), AA
1676 #ifdef LT
1677         addl    $4 * SIZE, B
1678 #endif
1679 #endif
1680
1681 #ifdef LN
1682         subl    $2, KK
1683         movl    BORIG, B
1684 #endif
1685
1686 #ifdef LT
1687         addl    $2, KK
1688 #endif
1689
1690 #ifdef RT
1691         movl    K, %eax
1692         movl    BORIG, B
1693         sall    $1 + BASE_SHIFT, %eax
1694         addl    %eax, AORIG
1695 #endif
1696
1697         decl    %ebx                    # i --
1698         jg      .L41
1699         ALIGN_4
1700
1701 .L50:
1702         movl    M,  %ebx
1703         testl   $1, %ebx        # i = (m >> 2)
1704         jle     .L59
1705
1706 #ifdef LN
1707        movl     K, %eax
1708        sall     $BASE_SHIFT, %eax
1709        subl     %eax, AORIG
1710 #endif
1711
1712 #if defined(LN) || defined(RT)
1713         movl    KK, %eax
1714         movl    AORIG, AA
1715         leal    (AA, %eax, SIZE), AA
1716 #endif
1717
1718         leal    BUFFER, BB
1719
1720 #if defined(LN) || defined(RT)
1721         movl    KK, %eax
1722         sall    $2 + BASE_SHIFT, %eax
1723         addl    %eax, BB
1724 #endif  
1725
1726         pxor    %xmm4, %xmm4
1727         pxor    %xmm5, %xmm5
1728         pxor    %xmm6, %xmm6
1729         pxor    %xmm7, %xmm7
1730
1731         movlpd   0 * SIZE(AA), %xmm0
1732         movlpd   4 * SIZE(AA), %xmm1
1733         movlpd   0 * SIZE(BB), %xmm2
1734         movlpd   8 * SIZE(BB), %xmm3
1735
1736 #if defined(LT) || defined(RN)
1737         movl    KK, %eax
1738 #else
1739         movl    K, %eax
1740         subl    KK, %eax
1741 #endif
1742         sarl    $3, %eax
1743         je      .L55
1744         ALIGN_4
1745
1746 .L52:
1747         mulsd   %xmm0, %xmm2
1748         PREFETCH (PREFETCHSIZE  + 0) * SIZE(AA)
1749         mulsd    2 * SIZE(BB), %xmm0
1750         addsd   %xmm2, %xmm4
1751         movlpd   4 * SIZE(BB), %xmm2
1752         addsd   %xmm0, %xmm5
1753         movlpd   1 * SIZE(AA), %xmm0
1754
1755         mulsd   %xmm0, %xmm2
1756         mulsd    6 * SIZE(BB), %xmm0
1757         addsd   %xmm2, %xmm6
1758         movlpd  16 * SIZE(BB), %xmm2
1759         addsd   %xmm0, %xmm7
1760         movlpd   2 * SIZE(AA), %xmm0
1761
1762         mulsd   %xmm0, %xmm3
1763         mulsd   10 * SIZE(BB), %xmm0
1764         addsd   %xmm3, %xmm4
1765         movlpd  12 * SIZE(BB), %xmm3
1766         addsd   %xmm0, %xmm5
1767         movlpd   3 * SIZE(AA), %xmm0
1768
1769         mulsd   %xmm0, %xmm3
1770         mulsd   14 * SIZE(BB), %xmm0
1771         addsd   %xmm3, %xmm6
1772         movlpd  24 * SIZE(BB), %xmm3
1773         addsd   %xmm0, %xmm7
1774         movlpd   8 * SIZE(AA), %xmm0
1775
1776         mulsd   %xmm1, %xmm2
1777         mulsd   18 * SIZE(BB), %xmm1
1778         addsd   %xmm2, %xmm4
1779         movlpd  20 * SIZE(BB), %xmm2
1780         addsd   %xmm1, %xmm5
1781         movlpd   5 * SIZE(AA), %xmm1
1782
1783         mulsd   %xmm1, %xmm2
1784         mulsd   22 * SIZE(BB), %xmm1
1785         addsd   %xmm2, %xmm6
1786         movlpd  32 * SIZE(BB), %xmm2
1787         addsd   %xmm1, %xmm7
1788         movlpd   6 * SIZE(AA), %xmm1
1789
1790         mulsd   %xmm1, %xmm3
1791         mulsd   26 * SIZE(BB), %xmm1
1792         addsd   %xmm3, %xmm4
1793         movlpd  28 * SIZE(BB), %xmm3
1794         addsd   %xmm1, %xmm5
1795         movlpd   7 * SIZE(AA), %xmm1
1796
1797         mulsd   %xmm1, %xmm3
1798         mulsd   30 * SIZE(BB), %xmm1
1799         addsd   %xmm3, %xmm6
1800         movlpd  40 * SIZE(BB), %xmm3
1801         addsd   %xmm1, %xmm7
1802         movlpd  12 * SIZE(AA), %xmm1
1803
1804         addl   $ 8 * SIZE, AA
1805         addl   $32 * SIZE, BB
1806         decl   %eax
1807         jne    .L52
1808         ALIGN_4
1809
1810 .L55:
1811 #if defined(LT) || defined(RN)
1812         movl    KK, %eax
1813 #else
1814         movl    K, %eax
1815         subl    KK, %eax
1816 #endif
1817         andl    $7, %eax                # if (k & 1)
1818         BRANCH
1819         je .L58
1820
1821 .L56:
1822         mulsd   %xmm0, %xmm2
1823         mulsd    2 * SIZE(BB), %xmm0
1824         addsd   %xmm2, %xmm4
1825         movlpd   4 * SIZE(BB), %xmm2
1826         addsd   %xmm0, %xmm5
1827         movlpd   1 * SIZE(AA), %xmm0
1828
1829         addl    $1 * SIZE, AA
1830         addl    $4 * SIZE, BB
1831         decl    %eax
1832         jg      .L56
1833         ALIGN_4
1834
1835 .L58:
1836         addsd   %xmm6, %xmm4
1837         addsd   %xmm7, %xmm5
1838
1839 #if defined(LN) || defined(RT)
1840         movl    KK, %eax
1841 #ifdef LN
1842         subl    $1, %eax
1843 #else
1844         subl    $2, %eax
1845 #endif
1846
1847         movl    AORIG, AA
1848         movl    BORIG, B
1849         leal    BUFFER, BB
1850
1851         leal    (, %eax, SIZE), %eax
1852         addl    %eax, AA
1853         leal    (B,  %eax, 2), B
1854         leal    (BB, %eax, 4), BB
1855 #endif
1856
1857 #if defined(LN) || defined(LT)
1858         unpcklpd %xmm5, %xmm4
1859
1860         movapd   0 * SIZE(B), %xmm2
1861
1862         subpd   %xmm4,  %xmm2
1863 #else
1864         movlpd   0 * SIZE(AA), %xmm0
1865         movlpd   1 * SIZE(AA), %xmm1
1866
1867         subsd   %xmm4, %xmm0
1868         subsd   %xmm5, %xmm1
1869 #endif
1870
1871 #ifdef LN
1872         movlpd   0 * SIZE(AA), %xmm4
1873         movhpd   0 * SIZE(AA), %xmm4
1874         mulpd    %xmm4, %xmm2
1875 #endif
1876
1877 #ifdef LT
1878         movlpd   0 * SIZE(AA), %xmm4
1879         movhpd   0 * SIZE(AA), %xmm4
1880         mulpd    %xmm4, %xmm2
1881 #endif
1882
1883 #ifdef RN
1884         movlpd   0 * SIZE(B), %xmm4
1885         mulsd    %xmm4, %xmm0
1886         movlpd   1 * SIZE(B), %xmm4
1887         mulsd    %xmm0, %xmm4
1888         subsd    %xmm4, %xmm1
1889
1890         movlpd   3 * SIZE(B), %xmm4
1891         mulsd    %xmm4, %xmm1
1892 #endif
1893
1894 #ifdef RT
1895         movlpd   3 * SIZE(B), %xmm4
1896         mulsd    %xmm4, %xmm1
1897         movlpd   2 * SIZE(B), %xmm4
1898         mulsd    %xmm1, %xmm4
1899         subsd    %xmm4, %xmm0
1900
1901         movlpd   0 * SIZE(B), %xmm4
1902         mulsd    %xmm4, %xmm0
1903 #endif
1904
1905 #if defined(LN) || defined(LT)
1906         movapd  %xmm2,   0 * SIZE(B)
1907
1908         movlpd  %xmm2,   0 * SIZE(BB)
1909         movlpd  %xmm2,   1 * SIZE(BB)
1910         movhpd  %xmm2,   2 * SIZE(BB)
1911         movhpd  %xmm2,   3 * SIZE(BB)
1912 #else
1913         movlpd  %xmm0,   0 * SIZE(AA)
1914         movlpd  %xmm1,   1 * SIZE(AA)
1915 #endif
1916
1917 #ifdef LN
1918         subl    $1 * SIZE, CO1
1919 #endif
1920
1921 #if defined(LN) || defined(LT)
1922         movlpd  %xmm2, 0 * SIZE(CO1)
1923         movhpd  %xmm2, 0 * SIZE(CO1, LDC, 1)
1924 #else
1925         movlpd  %xmm0, 0 * SIZE(CO1)
1926         movlpd  %xmm1, 0 * SIZE(CO1, LDC, 1)
1927 #endif
1928
1929 #ifndef LN
1930         addl    $1 * SIZE, CO1
1931 #endif
1932
1933 #if defined(LT) || defined(RN)
1934         movl    K,  %eax
1935         subl    KK, %eax
1936         leal    (AA,%eax, SIZE), AA
1937 #ifdef LT
1938         addl    $2 * SIZE, B
1939 #endif
1940 #endif
1941
1942 #ifdef LN
1943         subl    $1, KK
1944         movl    BORIG, B
1945 #endif
1946
1947 #ifdef LT
1948         addl    $1, KK
1949 #endif
1950
1951 #ifdef RT
1952         movl    K, %eax
1953         movl    BORIG, B
1954         sall    $BASE_SHIFT, %eax
1955         addl    %eax, AORIG
1956 #endif
1957         ALIGN_4
1958
1959 .L59:
1960 #ifdef LN
1961        movl     K, %eax
1962        leal     (, %eax, SIZE), %eax
1963        leal     (B, %eax, 2), B
1964 #endif
1965
1966 #if defined(LT) || defined(RN)
1967         movl    K,  %eax
1968         subl    KK, %eax
1969         leal    (,%eax, SIZE), %eax
1970         leal    (B,  %eax, 2), B
1971 #endif
1972
1973 #ifdef RN
1974         addl    $2, KK
1975 #endif
1976
1977 #ifdef RT
1978         subl    $2, KK
1979 #endif
1980         ALIGN_4
1981
1982 .L60:
1983         testl   $1, N
1984         je      .L999
1985
1986 #ifdef LN
1987         movl    OFFSET, %eax
1988         addl    M, %eax
1989         movl    %eax, KK
1990 #endif  
1991
1992         leal    BUFFER, BB
1993
1994 #ifdef RT
1995        movl     K, %eax
1996        sall     $BASE_SHIFT, %eax
1997        subl     %eax, B
1998 #endif
1999
2000 #if defined(LN) || defined(RT)
2001         movl    KK, %eax
2002         movl    B, BORIG
2003         leal    (, %eax, SIZE), %eax
2004         leal    (B,  %eax, 1), B
2005         leal    (BB, %eax, 2), BB
2006 #endif  
2007
2008 #ifdef LT
2009         movl    OFFSET, %eax
2010         movl    %eax, KK
2011 #endif
2012
2013 #if defined(LT) || defined(RN)
2014         movl    KK, %eax
2015 #else
2016         movl    K, %eax
2017         subl    KK, %eax
2018 #endif
2019         sarl    $3, %eax
2020         jle     .L65
2021         ALIGN_4
2022         
2023 .L62:
2024 #define COPYPREFETCH 40
2025
2026         prefetchnta     (COPYPREFETCH) * SIZE(B)
2027
2028         movq     0 * SIZE(B), %mm0
2029         movq     1 * SIZE(B), %mm1
2030         movq     2 * SIZE(B), %mm2
2031         movq     3 * SIZE(B), %mm3
2032         movq     4 * SIZE(B), %mm4
2033         movq     5 * SIZE(B), %mm5
2034         movq     6 * SIZE(B), %mm6
2035         movq     7 * SIZE(B), %mm7
2036
2037         movq    %mm0,  0 * SIZE(BB)
2038         movq    %mm0,  1 * SIZE(BB)
2039         movq    %mm1,  2 * SIZE(BB)
2040         movq    %mm1,  3 * SIZE(BB)
2041         movq    %mm2,  4 * SIZE(BB)
2042         movq    %mm2,  5 * SIZE(BB)
2043         movq    %mm3,  6 * SIZE(BB)
2044         movq    %mm3,  7 * SIZE(BB)
2045
2046         movq    %mm4,  8 * SIZE(BB)
2047         movq    %mm4,  9 * SIZE(BB)
2048         movq    %mm5, 10 * SIZE(BB)
2049         movq    %mm5, 11 * SIZE(BB)
2050         movq    %mm6, 12 * SIZE(BB)
2051         movq    %mm6, 13 * SIZE(BB)
2052         movq    %mm7, 14 * SIZE(BB)
2053         movq    %mm7, 15 * SIZE(BB)
2054
2055         addl    $ 8 * SIZE, B
2056         addl    $16 * SIZE, BB
2057         decl    %eax
2058         jne     .L62
2059         ALIGN_2
2060
2061 .L65:
2062 #if defined(LT) || defined(RN)
2063         movl    KK, %eax
2064 #else
2065         movl    K, %eax
2066         subl    KK, %eax
2067 #endif
2068         andl    $7, %eax
2069         BRANCH
2070         jle     .L70
2071         ALIGN_2
2072
2073 .L66:
2074         movq     0 * SIZE(B), %mm0
2075
2076         movq    %mm0,  0 * SIZE(BB)
2077         movq    %mm0,  1 * SIZE(BB)
2078
2079         addl    $1 * SIZE, B
2080         addl    $2 * SIZE, BB
2081         decl    %eax
2082         jne     .L66
2083         ALIGN_4
2084         
2085 .L70:
2086 #if defined(LT) || defined(RN)
2087         movl    A, AA
2088 #else
2089         movl    A, %eax
2090         movl    %eax, AORIG
2091 #endif
2092
2093 #ifdef RT
2094         subl    LDC, C
2095 #endif
2096         movl    C, CO1
2097 #ifndef RT
2098         addl    LDC, C
2099 #endif
2100
2101         movl    M,  %ebx
2102         sarl    $1, %ebx        # i = (m >> 2)
2103         jle     .L80
2104         ALIGN_4
2105
2106 .L71:
2107 #ifdef LN
2108        movl     K, %eax
2109        sall     $1 + BASE_SHIFT, %eax
2110        subl     %eax, AORIG
2111 #endif
2112
2113 #if defined(LN) || defined(RT)
2114         movl    KK, %eax
2115         movl    AORIG, AA
2116         leal    (, %eax, SIZE), %eax
2117         leal    (AA, %eax, 2), AA
2118 #endif
2119
2120         leal    BUFFER, BB
2121
2122 #if defined(LN) || defined(RT)
2123         movl    KK, %eax
2124         sall    $1 + BASE_SHIFT, %eax
2125         addl    %eax, BB
2126 #endif  
2127
2128         pxor    %xmm4, %xmm4
2129         pxor    %xmm5, %xmm5
2130         pxor    %xmm6, %xmm6
2131         pxor    %xmm7, %xmm7
2132
2133         movapd   0 * SIZE(AA), %xmm0
2134         movapd   8 * SIZE(AA), %xmm1
2135         movapd   0 * SIZE(BB), %xmm2
2136         movapd   8 * SIZE(BB), %xmm3
2137
2138 #ifdef LN
2139         prefetchw       -2 * SIZE(CO1)
2140 #else
2141         prefetchw        1 * SIZE(CO1)
2142 #endif
2143
2144 #if defined(LT) || defined(RN)
2145         movl    KK, %eax
2146 #else
2147         movl    K, %eax
2148         subl    KK, %eax
2149 #endif
2150         sarl    $3, %eax
2151         je      .L75
2152         ALIGN_4
2153
2154 .L72:
2155         mulpd   %xmm0, %xmm2
2156         addpd   %xmm2, %xmm4
2157         prefetcht0 (PREFETCHSIZE  + 0) * SIZE(AA)
2158         movapd  16 * SIZE(BB), %xmm2
2159
2160         movapd   2 * SIZE(AA), %xmm0
2161         mulpd    2 * SIZE(BB), %xmm0
2162         addpd   %xmm0, %xmm4
2163         movapd   4 * SIZE(AA), %xmm0
2164         mulpd    4 * SIZE(BB), %xmm0
2165         addpd   %xmm0, %xmm4
2166         movapd   6 * SIZE(AA), %xmm0
2167         mulpd    6 * SIZE(BB), %xmm0
2168         addpd   %xmm0, %xmm4
2169
2170         movapd  16 * SIZE(AA), %xmm0
2171         prefetcht0 (PREFETCHSIZE  + 8) * SIZE(AA)
2172         mulpd   %xmm1, %xmm3
2173         addpd   %xmm3, %xmm4
2174         movapd  24 * SIZE(BB), %xmm3
2175
2176         movapd  10 * SIZE(AA), %xmm1
2177         mulpd   10 * SIZE(BB), %xmm1
2178         addpd   %xmm1, %xmm4
2179         movapd  12 * SIZE(AA), %xmm1
2180         mulpd   12 * SIZE(BB), %xmm1
2181         addpd   %xmm1, %xmm4
2182         movapd  14 * SIZE(AA), %xmm1
2183         mulpd   14 * SIZE(BB), %xmm1
2184         addpd   %xmm1, %xmm4
2185         movapd  24 * SIZE(AA), %xmm1
2186
2187         addl   $16 * SIZE, AA
2188         addl   $16 * SIZE, BB
2189         decl   %eax
2190         jne    .L72
2191         ALIGN_4
2192
2193 .L75:
2194 #if defined(LT) || defined(RN)
2195         movl    KK, %eax
2196 #else
2197         movl    K, %eax
2198         subl    KK, %eax
2199 #endif
2200         andl    $7, %eax                # if (k & 1)
2201         BRANCH
2202         je .L78
2203         ALIGN_3
2204
2205 .L76:
2206         mulpd   %xmm0, %xmm2
2207         addpd   %xmm2, %xmm4
2208         movapd   2 * SIZE(AA), %xmm0
2209         movapd   2 * SIZE(BB), %xmm2
2210
2211         addl    $2 * SIZE, AA
2212         addl    $2 * SIZE, BB
2213         decl    %eax
2214         jg      .L76
2215         ALIGN_4
2216
2217 .L78:
2218 #if defined(LN) || defined(RT)
2219         movl    KK, %eax
2220 #ifdef LN
2221         subl    $2, %eax
2222 #else
2223         subl    $1, %eax
2224 #endif
2225
2226         movl    AORIG, AA
2227         movl    BORIG, B
2228         leal    BUFFER, BB
2229
2230         leal    (, %eax, SIZE), %eax
2231         leal    (AA, %eax, 2), AA
2232         leal    (B,  %eax, 1), B
2233         leal    (BB, %eax, 2), BB
2234 #endif
2235
2236 #if defined(LN) || defined(LT)
2237         movapd   0 * SIZE(B), %xmm2
2238
2239         subpd   %xmm4,  %xmm2
2240 #else
2241         movapd   0 * SIZE(AA), %xmm0
2242
2243         subpd   %xmm4, %xmm0
2244 #endif
2245
2246 #ifdef LN
2247         movapd   %xmm2, %xmm3
2248         unpckhpd %xmm3, %xmm3
2249
2250         movlpd   3 * SIZE(AA), %xmm4
2251         mulsd    %xmm4, %xmm3
2252
2253         movlpd   2 * SIZE(AA), %xmm4
2254         mulsd    %xmm3, %xmm4
2255         subsd    %xmm4, %xmm2
2256
2257         movlpd   0 * SIZE(AA), %xmm4
2258         mulsd    %xmm4, %xmm2
2259
2260         unpcklpd %xmm3, %xmm2
2261 #endif
2262
2263 #ifdef LT
2264         movapd   %xmm2, %xmm3
2265         unpckhpd %xmm3, %xmm3
2266
2267         movlpd   0 * SIZE(AA), %xmm4
2268         mulsd    %xmm4, %xmm2
2269
2270         movlpd   1 * SIZE(AA), %xmm4
2271         mulsd    %xmm2, %xmm4
2272         subsd    %xmm4, %xmm3
2273
2274         movlpd   3 * SIZE(AA), %xmm4
2275         mulsd    %xmm4, %xmm3
2276
2277         unpcklpd %xmm3, %xmm2
2278 #endif
2279
2280 #ifdef RN
2281         movlpd   0 * SIZE(B), %xmm4
2282         movhpd   0 * SIZE(B), %xmm4
2283         mulpd    %xmm4, %xmm0
2284 #endif
2285
2286 #ifdef RT
2287         movlpd   0 * SIZE(B), %xmm4
2288         movhpd   0 * SIZE(B), %xmm4
2289         mulpd    %xmm4, %xmm0
2290 #endif
2291
2292 #if defined(LN) || defined(LT)
2293         movapd  %xmm2,   0 * SIZE(B)
2294
2295         movlpd  %xmm2,   0 * SIZE(BB)
2296         movlpd  %xmm2,   1 * SIZE(BB)
2297         movhpd  %xmm2,   2 * SIZE(BB)
2298         movhpd  %xmm2,   3 * SIZE(BB)
2299 #else
2300         movapd  %xmm0,   0 * SIZE(AA)
2301 #endif
2302
2303 #ifdef LN
2304         subl    $2 * SIZE, CO1
2305 #endif
2306
2307 #if defined(LN) || defined(LT)
2308         movlpd  %xmm2, 0 * SIZE(CO1)
2309         movhpd  %xmm2, 1 * SIZE(CO1)
2310 #else
2311         movlpd  %xmm0, 0 * SIZE(CO1)
2312         movhpd  %xmm0, 1 * SIZE(CO1)
2313 #endif
2314
2315 #ifndef LN
2316         addl    $2 * SIZE, CO1
2317 #endif
2318
2319 #if defined(LT) || defined(RN)
2320         movl    K,  %eax
2321         subl    KK, %eax
2322         leal    (,%eax, SIZE), %eax
2323         leal    (AA, %eax, 2), AA
2324 #ifdef LT
2325         addl    $2 * SIZE, B
2326 #endif
2327 #endif
2328
2329 #ifdef LN
2330         subl    $2, KK
2331         movl    BORIG, B
2332 #endif
2333
2334 #ifdef LT
2335         addl    $2, KK
2336 #endif
2337
2338 #ifdef RT
2339         movl    K, %eax
2340         movl    BORIG, B
2341         sall    $1 + BASE_SHIFT, %eax
2342         addl    %eax, AORIG
2343 #endif
2344
2345         decl    %ebx                    # i --
2346         jg      .L71
2347         ALIGN_4
2348
2349 .L80:
2350         movl    M,  %ebx
2351         testl   $1, %ebx        # i = (m >> 2)
2352         jle     .L99
2353
2354 #ifdef LN
2355        movl     K, %eax
2356        sall     $BASE_SHIFT, %eax
2357        subl     %eax, AORIG
2358 #endif
2359
2360 #if defined(LN) || defined(RT)
2361         movl    KK, %eax
2362         movl    AORIG, AA
2363         leal    (AA, %eax, SIZE), AA
2364 #endif
2365
2366         leal    BUFFER, BB
2367
2368 #if defined(LN) || defined(RT)
2369         movl    KK, %eax
2370         sall    $1 + BASE_SHIFT, %eax
2371         addl    %eax, BB
2372 #endif  
2373
2374         pxor    %xmm4, %xmm4
2375         pxor    %xmm5, %xmm5
2376         pxor    %xmm6, %xmm6
2377         pxor    %xmm7, %xmm7
2378
2379         movlpd   0 * SIZE(AA), %xmm0
2380         movlpd   4 * SIZE(AA), %xmm1
2381         movlpd   0 * SIZE(BB), %xmm2
2382         movlpd   8 * SIZE(BB), %xmm3
2383
2384 #if defined(LT) || defined(RN)
2385         movl    KK, %eax
2386 #else
2387         movl    K, %eax
2388         subl    KK, %eax
2389 #endif
2390         sarl    $3, %eax
2391         je      .L85
2392         ALIGN_4
2393
2394 .L82:
2395         mulsd   %xmm0, %xmm2
2396         prefetcht0 (PREFETCHSIZE  + 0) * SIZE(AA)
2397         movlpd   1 * SIZE(AA), %xmm0
2398         mulsd    2 * SIZE(BB), %xmm0
2399         addsd   %xmm2, %xmm4
2400         movlpd  16 * SIZE(BB), %xmm2
2401         addsd   %xmm0, %xmm5
2402         movlpd   2 * SIZE(AA), %xmm0
2403         mulsd    4 * SIZE(BB), %xmm0
2404         addsd   %xmm0, %xmm6
2405         movlpd   3 * SIZE(AA), %xmm0
2406         mulsd    6 * SIZE(BB), %xmm0
2407         addsd   %xmm0, %xmm7
2408         movlpd   8 * SIZE(AA), %xmm0
2409         mulsd   %xmm1, %xmm3
2410         movlpd   5 * SIZE(AA), %xmm1
2411         mulsd   10 * SIZE(BB), %xmm1
2412         addsd   %xmm3, %xmm4
2413         movlpd  24 * SIZE(BB), %xmm3
2414         addsd   %xmm1, %xmm5
2415         movlpd   6 * SIZE(AA), %xmm1
2416         mulsd   12 * SIZE(BB), %xmm1
2417         addsd   %xmm1, %xmm6
2418         movlpd   7 * SIZE(AA), %xmm1
2419         mulsd   14 * SIZE(BB), %xmm1
2420         addsd   %xmm1, %xmm7
2421         movlpd  12 * SIZE(AA), %xmm1
2422
2423         addl   $ 8 * SIZE, AA
2424         addl   $16 * SIZE, BB
2425         decl   %eax
2426         jne    .L82
2427         ALIGN_4
2428
2429 .L85:
2430 #if defined(LT) || defined(RN)
2431         movl    KK, %eax
2432 #else
2433         movl    K, %eax
2434         subl    KK, %eax
2435 #endif
2436         andl    $7, %eax                # if (k & 1)
2437         BRANCH
2438         je .L88
2439
2440 .L86:
2441         mulsd   %xmm0, %xmm2
2442         addsd   %xmm2, %xmm4
2443         movlpd   2 * SIZE(BB), %xmm2
2444         movlpd   1 * SIZE(AA), %xmm0
2445
2446         addl    $1 * SIZE, AA
2447         addl    $2 * SIZE, BB
2448         decl    %eax
2449         jg      .L86
2450         ALIGN_4
2451
2452 .L88:
2453         addsd   %xmm5, %xmm4
2454         addsd   %xmm7, %xmm6
2455         addsd   %xmm6, %xmm4
2456
2457 #if defined(LN) || defined(RT)
2458         movl    KK, %eax
2459 #ifdef LN
2460         subl    $1, %eax
2461 #else
2462         subl    $1, %eax
2463 #endif
2464
2465         movl    AORIG, AA
2466         movl    BORIG, B
2467         leal    BUFFER, BB
2468
2469         leal    (, %eax, SIZE), %eax
2470         addl    %eax, AA
2471         addl    %eax, B
2472         leal    (BB, %eax, 2), BB
2473 #endif
2474
2475 #if defined(LN) || defined(LT)
2476         movlpd   0 * SIZE(B), %xmm2
2477         subsd   %xmm4, %xmm2
2478 #else
2479         movlpd   0 * SIZE(AA), %xmm0
2480         subsd   %xmm4, %xmm0
2481 #endif
2482
2483 #ifdef LN
2484         movlpd   0 * SIZE(AA), %xmm4
2485         mulsd    %xmm4, %xmm2
2486 #endif
2487
2488 #ifdef LT
2489         movlpd   0 * SIZE(AA), %xmm4
2490         mulsd    %xmm4, %xmm2
2491 #endif
2492
2493 #ifdef RN
2494         movlpd   0 * SIZE(B), %xmm4
2495         mulsd    %xmm4, %xmm0
2496 #endif
2497
2498 #ifdef RT
2499         movlpd   0 * SIZE(B), %xmm4
2500         mulsd    %xmm4, %xmm0
2501 #endif
2502
2503 #if defined(LN) || defined(LT)
2504         movlpd  %xmm2,   0 * SIZE(B)
2505
2506         movlpd  %xmm2,   0 * SIZE(BB)
2507         movlpd  %xmm2,   1 * SIZE(BB)
2508 #else
2509         movlpd  %xmm0,   0 * SIZE(AA)
2510 #endif
2511
2512 #ifdef LN
2513         subl    $1 * SIZE, CO1
2514 #endif
2515
2516 #if defined(LN) || defined(LT)
2517         movlpd  %xmm2, 0 * SIZE(CO1)
2518 #else
2519         movlpd  %xmm0, 0 * SIZE(CO1)
2520 #endif
2521
2522 #ifndef LN
2523         addl    $1 * SIZE, CO1
2524 #endif
2525
2526 #if defined(LT) || defined(RN)
2527         movl    K,  %eax
2528         subl    KK, %eax
2529         leal    (AA,%eax, SIZE), AA
2530 #ifdef LT
2531         addl    $1 * SIZE, B
2532 #endif
2533 #endif
2534
2535 #ifdef LN
2536         subl    $1, KK
2537         movl    BORIG, B
2538 #endif
2539
2540 #ifdef LT
2541         addl    $1, KK
2542 #endif
2543
2544 #ifdef RT
2545         movl    K, %eax
2546         movl    BORIG, B
2547         sall    $BASE_SHIFT, %eax
2548         addl    %eax, AORIG
2549 #endif
2550         ALIGN_4
2551
2552 .L99:
2553 #ifdef LN
2554        movl     K, %eax
2555        leal     (B, %eax, SIZE), B
2556 #endif
2557
2558 #if defined(LT) || defined(RN)
2559         movl    K,  %eax
2560         subl    KK, %eax
2561         leal    (B,%eax, SIZE), B
2562 #endif
2563
2564 #ifdef RN
2565         addl    $1, KK
2566 #endif
2567
2568 #ifdef RT
2569         subl    $1, KK
2570 #endif
2571         ALIGN_4
2572
2573 .L999:
2574         movl    OLD_STACK, %esp
2575         EMMS
2576         
2577         popl    %ebx
2578         popl    %esi
2579         popl    %edi
2580         popl    %ebp
2581         ret
2582
2583         EPILOGUE