Add Poly1305 MAC
[libgcrypt.git] / cipher / sha256-ssse3-amd64.S
1 /*
2 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
3 ; Copyright (c) 2012, Intel Corporation
4 ;
5 ; All rights reserved.
6 ;
7 ; Redistribution and use in source and binary forms, with or without
8 ; modification, are permitted provided that the following conditions are
9 ; met:
10 ;
11 ; * Redistributions of source code must retain the above copyright
12 ;   notice, this list of conditions and the following disclaimer.
13 ;
14 ; * Redistributions in binary form must reproduce the above copyright
15 ;   notice, this list of conditions and the following disclaimer in the
16 ;   documentation and/or other materials provided with the
17 ;   distribution.
18 ;
19 ; * Neither the name of the Intel Corporation nor the names of its
20 ;   contributors may be used to endorse or promote products derived from
21 ;   this software without specific prior written permission.
22 ;
23 ;
24 ; THIS SOFTWARE IS PROVIDED BY INTEL CORPORATION "AS IS" AND ANY
25 ; EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26 ; IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
27 ; PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL CORPORATION OR
28 ; CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
29 ; EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
30 ; PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
31 ; PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
32 ; LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
33 ; NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
34 ; SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
36 ;
37 ; This code is described in an Intel White-Paper:
38 ; "Fast SHA-256 Implementations on Intel Architecture Processors"
39 ;
40 ; To find it, surf to http://www.intel.com/p/en_US/embedded
41 ; and search for that title.
42 ; The paper is expected to be released roughly at the end of April, 2012
43 ;
44 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
45 ; This code schedules 1 blocks at a time, with 4 lanes per block
46 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
47 */
48 /*
49  * Conversion to GAS assembly and integration to libgcrypt
50  *  by Jussi Kivilinna <jussi.kivilinna@iki.fi>
51  *
52  * Note: original implementation was named as SHA256-SSE4. However, only SSSE3
53  *       is required.
54  */
55
56 #ifdef __x86_64
57 #include <config.h>
58 #if defined(HAVE_COMPATIBLE_GCC_AMD64_PLATFORM_AS) && \
59     defined(HAVE_INTEL_SYNTAX_PLATFORM_AS) && \
60     defined(HAVE_GCC_INLINE_ASM_SSSE3) && defined(USE_SHA256)
61
62 #ifdef __PIC__
63 #  define ADD_RIP +rip
64 #else
65 #  define ADD_RIP
66 #endif
67
68 .intel_syntax noprefix
69
70 #define MOVDQ movdqu /* assume buffers not aligned */
71
72 /*;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Define Macros*/
73
74 /* addm [mem], reg
75  * Add reg to mem using reg-mem add and store */
76 .macro addm p1 p2
77         add     \p2, \p1
78         mov     \p1, \p2
79 .endm
80
81 /*;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;*/
82
83 /* COPY_XMM_AND_BSWAP xmm, [mem], byte_flip_mask
84  * Load xmm with mem and byte swap each dword */
85 .macro COPY_XMM_AND_BSWAP p1 p2 p3
86         MOVDQ \p1, \p2
87         pshufb \p1, \p3
88 .endm
89
90 /*;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;*/
91
92 X0 = xmm4
93 X1 = xmm5
94 X2 = xmm6
95 X3 = xmm7
96
97 XTMP0 = xmm0
98 XTMP1 = xmm1
99 XTMP2 = xmm2
100 XTMP3 = xmm3
101 XTMP4 = xmm8
102 XFER  = xmm9
103
104 SHUF_00BA = xmm10 /* shuffle xBxA -> 00BA */
105 SHUF_DC00 = xmm11 /* shuffle xDxC -> DC00 */
106 BYTE_FLIP_MASK = xmm12
107
108 NUM_BLKS = rdx  /* 3rd arg */
109 CTX = rsi       /* 2nd arg */
110 INP = rdi       /* 1st arg */
111
112 SRND = rdi      /* clobbers INP */
113 c = ecx
114 d = r8d
115 e = edx
116
117 TBL = rbp
118 a = eax
119 b = ebx
120
121 f = r9d
122 g = r10d
123 h = r11d
124
125 y0 = r13d
126 y1 = r14d
127 y2 = r15d
128
129
130
131 #define _INP_END_SIZE   8
132 #define _INP_SIZE       8
133 #define _XFER_SIZE      8
134 #define _XMM_SAVE_SIZE  0
135 /* STACK_SIZE plus pushes must be an odd multiple of 8 */
136 #define _ALIGN_SIZE     8
137
138 #define _INP_END        0
139 #define _INP            (_INP_END  + _INP_END_SIZE)
140 #define _XFER           (_INP      + _INP_SIZE)
141 #define _XMM_SAVE       (_XFER     + _XFER_SIZE + _ALIGN_SIZE)
142 #define STACK_SIZE      (_XMM_SAVE + _XMM_SAVE_SIZE)
143
144 /* rotate_Xs
145  * Rotate values of symbols X0...X3 */
146 .macro rotate_Xs
147 X_ = X0
148 X0 = X1
149 X1 = X2
150 X2 = X3
151 X3 = X_
152 .endm
153
154 /* ROTATE_ARGS
155  * Rotate values of symbols a...h */
156 .macro ROTATE_ARGS
157 TMP_ = h
158 h = g
159 g = f
160 f = e
161 e = d
162 d = c
163 c = b
164 b = a
165 a = TMP_
166 .endm
167
168 .macro FOUR_ROUNDS_AND_SCHED
169                 /* compute s0 four at a time and s1 two at a time
170                  * compute W[-16] + W[-7] 4 at a time */
171                 movdqa  XTMP0, X3
172         mov     y0, e           /* y0 = e */
173         ror     y0, (25-11)     /* y0 = e >> (25-11) */
174         mov     y1, a           /* y1 = a */
175                 palignr XTMP0, X2, 4    /* XTMP0 = W[-7] */
176         ror     y1, (22-13)     /* y1 = a >> (22-13) */
177         xor     y0, e           /* y0 = e ^ (e >> (25-11)) */
178         mov     y2, f           /* y2 = f */
179         ror     y0, (11-6)      /* y0 = (e >> (11-6)) ^ (e >> (25-6)) */
180                 movdqa  XTMP1, X1
181         xor     y1, a           /* y1 = a ^ (a >> (22-13) */
182         xor     y2, g           /* y2 = f^g */
183                 paddd   XTMP0, X0       /* XTMP0 = W[-7] + W[-16] */
184         xor     y0, e           /* y0 = e ^ (e >> (11-6)) ^ (e >> (25-6)) */
185         and     y2, e           /* y2 = (f^g)&e */
186         ror     y1, (13-2)      /* y1 = (a >> (13-2)) ^ (a >> (22-2)) */
187                 /* compute s0 */
188                 palignr XTMP1, X0, 4    /* XTMP1 = W[-15] */
189         xor     y1, a           /* y1 = a ^ (a >> (13-2)) ^ (a >> (22-2)) */
190         ror     y0, 6           /* y0 = S1 = (e>>6) & (e>>11) ^ (e>>25) */
191         xor     y2, g           /* y2 = CH = ((f^g)&e)^g */
192                 movdqa  XTMP2, XTMP1    /* XTMP2 = W[-15] */
193         ror     y1, 2           /* y1 = S0 = (a>>2) ^ (a>>13) ^ (a>>22) */
194         add     y2, y0          /* y2 = S1 + CH */
195         add     y2, [rsp + _XFER + 0*4] /* y2 = k + w + S1 + CH */
196                 movdqa  XTMP3, XTMP1    /* XTMP3 = W[-15] */
197         mov     y0, a           /* y0 = a */
198         add     h, y2           /* h = h + S1 + CH + k + w */
199         mov     y2, a           /* y2 = a */
200                 pslld   XTMP1, (32-7)
201         or      y0, c           /* y0 = a|c */
202         add     d, h            /* d = d + h + S1 + CH + k + w */
203         and     y2, c           /* y2 = a&c */
204                 psrld   XTMP2, 7
205         and     y0, b           /* y0 = (a|c)&b */
206         add     h, y1           /* h = h + S1 + CH + k + w + S0 */
207                 por     XTMP1, XTMP2    /* XTMP1 = W[-15] ror 7 */
208         or      y0, y2          /* y0 = MAJ = (a|c)&b)|(a&c) */
209         lea     h, [h + y0]     /* h = h + S1 + CH + k + w + S0 + MAJ */
210
211 ROTATE_ARGS
212                 movdqa  XTMP2, XTMP3    /* XTMP2 = W[-15] */
213         mov     y0, e           /* y0 = e */
214         mov     y1, a           /* y1 = a */
215                 movdqa  XTMP4, XTMP3    /* XTMP4 = W[-15] */
216         ror     y0, (25-11)     /* y0 = e >> (25-11) */
217         xor     y0, e           /* y0 = e ^ (e >> (25-11)) */
218         mov     y2, f           /* y2 = f */
219         ror     y1, (22-13)     /* y1 = a >> (22-13) */
220                 pslld   XTMP3, (32-18)
221         xor     y1, a           /* y1 = a ^ (a >> (22-13) */
222         ror     y0, (11-6)      /* y0 = (e >> (11-6)) ^ (e >> (25-6)) */
223         xor     y2, g           /* y2 = f^g */
224                 psrld   XTMP2, 18
225         ror     y1, (13-2)      /* y1 = (a >> (13-2)) ^ (a >> (22-2)) */
226         xor     y0, e           /* y0 = e ^ (e >> (11-6)) ^ (e >> (25-6)) */
227         and     y2, e           /* y2 = (f^g)&e */
228         ror     y0, 6           /* y0 = S1 = (e>>6) & (e>>11) ^ (e>>25) */
229                 pxor    XTMP1, XTMP3
230         xor     y1, a           /* y1 = a ^ (a >> (13-2)) ^ (a >> (22-2)) */
231         xor     y2, g           /* y2 = CH = ((f^g)&e)^g */
232                 psrld   XTMP4, 3        /* XTMP4 = W[-15] >> 3 */
233         add     y2, y0          /* y2 = S1 + CH */
234         add     y2, [rsp + _XFER + 1*4] /* y2 = k + w + S1 + CH */
235         ror     y1, 2           /* y1 = S0 = (a>>2) ^ (a>>13) ^ (a>>22) */
236                 pxor    XTMP1, XTMP2    /* XTMP1 = W[-15] ror 7 ^ W[-15] ror 18 */
237         mov     y0, a           /* y0 = a */
238         add     h, y2           /* h = h + S1 + CH + k + w */
239         mov     y2, a           /* y2 = a */
240                 pxor    XTMP1, XTMP4    /* XTMP1 = s0 */
241         or      y0, c           /* y0 = a|c */
242         add     d, h            /* d = d + h + S1 + CH + k + w */
243         and     y2, c           /* y2 = a&c */
244                 /* compute low s1 */
245                 pshufd  XTMP2, X3, 0b11111010   /* XTMP2 = W[-2] {BBAA} */
246         and     y0, b           /* y0 = (a|c)&b */
247         add     h, y1           /* h = h + S1 + CH + k + w + S0 */
248                 paddd   XTMP0, XTMP1    /* XTMP0 = W[-16] + W[-7] + s0 */
249         or      y0, y2          /* y0 = MAJ = (a|c)&b)|(a&c) */
250         lea     h, [h + y0]     /* h = h + S1 + CH + k + w + S0 + MAJ */
251
252 ROTATE_ARGS
253                 movdqa  XTMP3, XTMP2    /* XTMP3 = W[-2] {BBAA} */
254         mov     y0, e           /* y0 = e */
255         mov     y1, a           /* y1 = a */
256         ror     y0, (25-11)     /* y0 = e >> (25-11) */
257                 movdqa  XTMP4, XTMP2    /* XTMP4 = W[-2] {BBAA} */
258         xor     y0, e           /* y0 = e ^ (e >> (25-11)) */
259         ror     y1, (22-13)     /* y1 = a >> (22-13) */
260         mov     y2, f           /* y2 = f */
261         xor     y1, a           /* y1 = a ^ (a >> (22-13) */
262         ror     y0, (11-6)      /* y0 = (e >> (11-6)) ^ (e >> (25-6)) */
263                 psrlq   XTMP2, 17       /* XTMP2 = W[-2] ror 17 {xBxA} */
264         xor     y2, g           /* y2 = f^g */
265                 psrlq   XTMP3, 19       /* XTMP3 = W[-2] ror 19 {xBxA} */
266         xor     y0, e           /* y0 = e ^ (e >> (11-6)) ^ (e >> (25-6)) */
267         and     y2, e           /* y2 = (f^g)&e */
268                 psrld   XTMP4, 10       /* XTMP4 = W[-2] >> 10 {BBAA} */
269         ror     y1, (13-2)      /* y1 = (a >> (13-2)) ^ (a >> (22-2)) */
270         xor     y1, a           /* y1 = a ^ (a >> (13-2)) ^ (a >> (22-2)) */
271         xor     y2, g           /* y2 = CH = ((f^g)&e)^g */
272         ror     y0, 6           /* y0 = S1 = (e>>6) & (e>>11) ^ (e>>25) */
273                 pxor    XTMP2, XTMP3
274         add     y2, y0          /* y2 = S1 + CH */
275         ror     y1, 2           /* y1 = S0 = (a>>2) ^ (a>>13) ^ (a>>22) */
276         add     y2, [rsp + _XFER + 2*4] /* y2 = k + w + S1 + CH */
277                 pxor    XTMP4, XTMP2    /* XTMP4 = s1 {xBxA} */
278         mov     y0, a           /* y0 = a */
279         add     h, y2           /* h = h + S1 + CH + k + w */
280         mov     y2, a           /* y2 = a */
281                 pshufb  XTMP4, SHUF_00BA        /* XTMP4 = s1 {00BA} */
282         or      y0, c           /* y0 = a|c */
283         add     d, h            /* d = d + h + S1 + CH + k + w */
284         and     y2, c           /* y2 = a&c */
285                 paddd   XTMP0, XTMP4    /* XTMP0 = {..., ..., W[1], W[0]} */
286         and     y0, b           /* y0 = (a|c)&b */
287         add     h, y1           /* h = h + S1 + CH + k + w + S0 */
288                 /* compute high s1 */
289                 pshufd  XTMP2, XTMP0, 0b01010000 /* XTMP2 = W[-2] {DDCC} */
290         or      y0, y2          /* y0 = MAJ = (a|c)&b)|(a&c) */
291         lea     h, [h + y0]     /* h = h + S1 + CH + k + w + S0 + MAJ */
292
293 ROTATE_ARGS
294                 movdqa  XTMP3, XTMP2    /* XTMP3 = W[-2] {DDCC} */
295         mov     y0, e           /* y0 = e */
296         ror     y0, (25-11)     /* y0 = e >> (25-11) */
297         mov     y1, a           /* y1 = a */
298                 movdqa  X0,    XTMP2    /* X0    = W[-2] {DDCC} */
299         ror     y1, (22-13)     /* y1 = a >> (22-13) */
300         xor     y0, e           /* y0 = e ^ (e >> (25-11)) */
301         mov     y2, f           /* y2 = f */
302         ror     y0, (11-6)      /* y0 = (e >> (11-6)) ^ (e >> (25-6)) */
303                 psrlq   XTMP2, 17       /* XTMP2 = W[-2] ror 17 {xDxC} */
304         xor     y1, a           /* y1 = a ^ (a >> (22-13) */
305         xor     y2, g           /* y2 = f^g */
306                 psrlq   XTMP3, 19       /* XTMP3 = W[-2] ror 19 {xDxC} */
307         xor     y0, e           /* y0 = e ^ (e >> (11-6)) ^ (e >> (25-6)) */
308         and     y2, e           /* y2 = (f^g)&e */
309         ror     y1, (13-2)      /* y1 = (a >> (13-2)) ^ (a >> (22-2)) */
310                 psrld   X0,    10       /* X0 = W[-2] >> 10 {DDCC} */
311         xor     y1, a           /* y1 = a ^ (a >> (13-2)) ^ (a >> (22-2)) */
312         ror     y0, 6           /* y0 = S1 = (e>>6) & (e>>11) ^ (e>>25) */
313         xor     y2, g           /* y2 = CH = ((f^g)&e)^g */
314                 pxor    XTMP2, XTMP3
315         ror     y1, 2           /* y1 = S0 = (a>>2) ^ (a>>13) ^ (a>>22) */
316         add     y2, y0          /* y2 = S1 + CH */
317         add     y2, [rsp + _XFER + 3*4] /* y2 = k + w + S1 + CH */
318                 pxor    X0, XTMP2       /* X0 = s1 {xDxC} */
319         mov     y0, a           /* y0 = a */
320         add     h, y2           /* h = h + S1 + CH + k + w */
321         mov     y2, a           /* y2 = a */
322                 pshufb  X0, SHUF_DC00   /* X0 = s1 {DC00} */
323         or      y0, c           /* y0 = a|c */
324         add     d, h            /* d = d + h + S1 + CH + k + w */
325         and     y2, c           /* y2 = a&c */
326                 paddd   X0, XTMP0       /* X0 = {W[3], W[2], W[1], W[0]} */
327         and     y0, b           /* y0 = (a|c)&b */
328         add     h, y1           /* h = h + S1 + CH + k + w + S0 */
329         or      y0, y2          /* y0 = MAJ = (a|c)&b)|(a&c) */
330         lea     h, [h + y0]     /* h = h + S1 + CH + k + w + S0 + MAJ */
331
332 ROTATE_ARGS
333 rotate_Xs
334 .endm
335
336 /* input is [rsp + _XFER + %1 * 4] */
337 .macro DO_ROUND i1
338         mov     y0, e           /* y0 = e */
339         ror     y0, (25-11)     /* y0 = e >> (25-11) */
340         mov     y1, a           /* y1 = a */
341         xor     y0, e           /* y0 = e ^ (e >> (25-11)) */
342         ror     y1, (22-13)     /* y1 = a >> (22-13) */
343         mov     y2, f           /* y2 = f */
344         xor     y1, a           /* y1 = a ^ (a >> (22-13) */
345         ror     y0, (11-6)      /* y0 = (e >> (11-6)) ^ (e >> (25-6)) */
346         xor     y2, g           /* y2 = f^g */
347         xor     y0, e           /* y0 = e ^ (e >> (11-6)) ^ (e >> (25-6)) */
348         ror     y1, (13-2)      /* y1 = (a >> (13-2)) ^ (a >> (22-2)) */
349         and     y2, e           /* y2 = (f^g)&e */
350         xor     y1, a           /* y1 = a ^ (a >> (13-2)) ^ (a >> (22-2)) */
351         ror     y0, 6           /* y0 = S1 = (e>>6) & (e>>11) ^ (e>>25) */
352         xor     y2, g           /* y2 = CH = ((f^g)&e)^g */
353         add     y2, y0          /* y2 = S1 + CH */
354         ror     y1, 2           /* y1 = S0 = (a>>2) ^ (a>>13) ^ (a>>22) */
355         add     y2, [rsp + _XFER + \i1 * 4]     /* y2 = k + w + S1 + CH */
356         mov     y0, a           /* y0 = a */
357         add     h, y2           /* h = h + S1 + CH + k + w */
358         mov     y2, a           /* y2 = a */
359         or      y0, c           /* y0 = a|c */
360         add     d, h            /* d = d + h + S1 + CH + k + w */
361         and     y2, c           /* y2 = a&c */
362         and     y0, b           /* y0 = (a|c)&b */
363         add     h, y1           /* h = h + S1 + CH + k + w + S0 */
364         or      y0, y2          /* y0 = MAJ = (a|c)&b)|(a&c) */
365         lea     h, [h + y0]     /* h = h + S1 + CH + k + w + S0 + MAJ */
366         ROTATE_ARGS
367 .endm
368
369 /*
370 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
371 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
372 ;; void sha256_sse4(void *input_data, UINT32 digest[8], UINT64 num_blks)
373 ;; arg 1 : pointer to input data
374 ;; arg 2 : pointer to digest
375 ;; arg 3 : Num blocks
376 */
377 .text
378 .globl _gcry_sha256_transform_amd64_ssse3
379 .type  _gcry_sha256_transform_amd64_ssse3,@function;
380 .align 16
381 _gcry_sha256_transform_amd64_ssse3:
382         push    rbx
383         push    rbp
384         push    r13
385         push    r14
386         push    r15
387
388         sub     rsp, STACK_SIZE
389
390         shl     NUM_BLKS, 6     /* convert to bytes */
391         jz      .Ldone_hash
392         add     NUM_BLKS, INP   /* pointer to end of data */
393         mov     [rsp + _INP_END], NUM_BLKS
394
395         /* load initial digest */
396         mov     a,[4*0 + CTX]
397         mov     b,[4*1 + CTX]
398         mov     c,[4*2 + CTX]
399         mov     d,[4*3 + CTX]
400         mov     e,[4*4 + CTX]
401         mov     f,[4*5 + CTX]
402         mov     g,[4*6 + CTX]
403         mov     h,[4*7 + CTX]
404
405         movdqa  BYTE_FLIP_MASK, [.LPSHUFFLE_BYTE_FLIP_MASK ADD_RIP]
406         movdqa  SHUF_00BA, [.L_SHUF_00BA ADD_RIP]
407         movdqa  SHUF_DC00, [.L_SHUF_DC00 ADD_RIP]
408
409 .Loop0:
410         lea     TBL, [.LK256 ADD_RIP]
411
412         /* byte swap first 16 dwords */
413         COPY_XMM_AND_BSWAP      X0, [INP + 0*16], BYTE_FLIP_MASK
414         COPY_XMM_AND_BSWAP      X1, [INP + 1*16], BYTE_FLIP_MASK
415         COPY_XMM_AND_BSWAP      X2, [INP + 2*16], BYTE_FLIP_MASK
416         COPY_XMM_AND_BSWAP      X3, [INP + 3*16], BYTE_FLIP_MASK
417
418         mov     [rsp + _INP], INP
419
420         /* schedule 48 input dwords, by doing 3 rounds of 16 each */
421         mov     SRND, 3
422 .align 16
423 .Loop1:
424         movdqa  XFER, [TBL + 0*16]
425         paddd   XFER, X0
426         movdqa  [rsp + _XFER], XFER
427         FOUR_ROUNDS_AND_SCHED
428
429         movdqa  XFER, [TBL + 1*16]
430         paddd   XFER, X0
431         movdqa  [rsp + _XFER], XFER
432         FOUR_ROUNDS_AND_SCHED
433
434         movdqa  XFER, [TBL + 2*16]
435         paddd   XFER, X0
436         movdqa  [rsp + _XFER], XFER
437         FOUR_ROUNDS_AND_SCHED
438
439         movdqa  XFER, [TBL + 3*16]
440         paddd   XFER, X0
441         movdqa  [rsp + _XFER], XFER
442         add     TBL, 4*16
443         FOUR_ROUNDS_AND_SCHED
444
445         sub     SRND, 1
446         jne     .Loop1
447
448         mov     SRND, 2
449 .Loop2:
450         paddd   X0, [TBL + 0*16]
451         movdqa  [rsp + _XFER], X0
452         DO_ROUND        0
453         DO_ROUND        1
454         DO_ROUND        2
455         DO_ROUND        3
456         paddd   X1, [TBL + 1*16]
457         movdqa  [rsp + _XFER], X1
458         add     TBL, 2*16
459         DO_ROUND        0
460         DO_ROUND        1
461         DO_ROUND        2
462         DO_ROUND        3
463
464         movdqa  X0, X2
465         movdqa  X1, X3
466
467         sub     SRND, 1
468         jne     .Loop2
469
470         addm    [4*0 + CTX],a
471         addm    [4*1 + CTX],b
472         addm    [4*2 + CTX],c
473         addm    [4*3 + CTX],d
474         addm    [4*4 + CTX],e
475         addm    [4*5 + CTX],f
476         addm    [4*6 + CTX],g
477         addm    [4*7 + CTX],h
478
479         mov     INP, [rsp + _INP]
480         add     INP, 64
481         cmp     INP, [rsp + _INP_END]
482         jne     .Loop0
483
484         pxor    xmm0, xmm0
485         pxor    xmm1, xmm1
486         pxor    xmm2, xmm2
487         pxor    xmm3, xmm3
488         pxor    xmm4, xmm4
489         pxor    xmm5, xmm5
490         pxor    xmm6, xmm6
491         pxor    xmm7, xmm7
492         pxor    xmm8, xmm8
493         pxor    xmm9, xmm9
494         pxor    xmm10, xmm10
495         pxor    xmm11, xmm11
496         pxor    xmm12, xmm12
497
498 .Ldone_hash:
499         add     rsp, STACK_SIZE
500
501         pop     r15
502         pop     r14
503         pop     r13
504         pop     rbp
505         pop     rbx
506
507         mov     eax, STACK_SIZE + 5*8
508
509         ret
510
511
512 .data
513 .align 16
514 .LK256:
515         .long   0x428a2f98,0x71374491,0xb5c0fbcf,0xe9b5dba5
516         .long   0x3956c25b,0x59f111f1,0x923f82a4,0xab1c5ed5
517         .long   0xd807aa98,0x12835b01,0x243185be,0x550c7dc3
518         .long   0x72be5d74,0x80deb1fe,0x9bdc06a7,0xc19bf174
519         .long   0xe49b69c1,0xefbe4786,0x0fc19dc6,0x240ca1cc
520         .long   0x2de92c6f,0x4a7484aa,0x5cb0a9dc,0x76f988da
521         .long   0x983e5152,0xa831c66d,0xb00327c8,0xbf597fc7
522         .long   0xc6e00bf3,0xd5a79147,0x06ca6351,0x14292967
523         .long   0x27b70a85,0x2e1b2138,0x4d2c6dfc,0x53380d13
524         .long   0x650a7354,0x766a0abb,0x81c2c92e,0x92722c85
525         .long   0xa2bfe8a1,0xa81a664b,0xc24b8b70,0xc76c51a3
526         .long   0xd192e819,0xd6990624,0xf40e3585,0x106aa070
527         .long   0x19a4c116,0x1e376c08,0x2748774c,0x34b0bcb5
528         .long   0x391c0cb3,0x4ed8aa4a,0x5b9cca4f,0x682e6ff3
529         .long   0x748f82ee,0x78a5636f,0x84c87814,0x8cc70208
530         .long   0x90befffa,0xa4506ceb,0xbef9a3f7,0xc67178f2
531
532 .LPSHUFFLE_BYTE_FLIP_MASK: .octa 0x0c0d0e0f08090a0b0405060700010203
533
534 /* shuffle xBxA -> 00BA */
535 .L_SHUF_00BA:              .octa 0xFFFFFFFFFFFFFFFF0b0a090803020100
536
537 /* shuffle xDxC -> DC00 */
538 .L_SHUF_DC00:              .octa 0x0b0a090803020100FFFFFFFFFFFFFFFF
539
540 #endif
541 #endif