random: Take at max 25% from RDRAND
[libgcrypt.git] / cipher / serpent.c
1 /* serpent.c - Implementation of the Serpent encryption algorithm.
2  *      Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
3  *
4  * This file is part of Libgcrypt.
5  *
6  * Libgcrypt is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU Lesser general Public License as
8  * published by the Free Software Foundation; either version 2.1 of
9  * the License, or (at your option) any later version.
10  *
11  * Libgcrypt is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
19  * 02111-1307, USA.
20  */
21
22 #include <config.h>
23
24 #include <string.h>
25 #include <stdio.h>
26
27 #include "types.h"
28 #include "g10lib.h"
29 #include "cipher.h"
30 #include "bithelp.h"
31 #include "bufhelp.h"
32 #include "cipher-internal.h"
33 #include "cipher-selftest.h"
34
35
36 /* USE_SSE2 indicates whether to compile with AMD64 SSE2 code. */
37 #undef USE_SSE2
38 #if defined(__x86_64__) && (defined(HAVE_COMPATIBLE_GCC_AMD64_PLATFORM_AS) || \
39     defined(HAVE_COMPATIBLE_GCC_WIN64_PLATFORM_AS))
40 # define USE_SSE2 1
41 #endif
42
43 /* USE_AVX2 indicates whether to compile with AMD64 AVX2 code. */
44 #undef USE_AVX2
45 #if defined(__x86_64__) && (defined(HAVE_COMPATIBLE_GCC_AMD64_PLATFORM_AS) || \
46     defined(HAVE_COMPATIBLE_GCC_WIN64_PLATFORM_AS))
47 # if defined(ENABLE_AVX2_SUPPORT)
48 #  define USE_AVX2 1
49 # endif
50 #endif
51
52 /* USE_NEON indicates whether to enable ARM NEON assembly code. */
53 #undef USE_NEON
54 #ifdef ENABLE_NEON_SUPPORT
55 # if defined(HAVE_ARM_ARCH_V6) && defined(__ARMEL__) \
56      && defined(HAVE_COMPATIBLE_GCC_ARM_PLATFORM_AS) \
57      && defined(HAVE_GCC_INLINE_ASM_NEON)
58 #  define USE_NEON 1
59 # endif
60 #endif /*ENABLE_NEON_SUPPORT*/
61
62 /* Number of rounds per Serpent encrypt/decrypt operation.  */
63 #define ROUNDS 32
64
65 /* Magic number, used during generating of the subkeys.  */
66 #define PHI 0x9E3779B9
67
68 /* Serpent works on 128 bit blocks.  */
69 typedef u32 serpent_block_t[4];
70
71 /* Serpent key, provided by the user.  If the original key is shorter
72    than 256 bits, it is padded.  */
73 typedef u32 serpent_key_t[8];
74
75 /* The key schedule consists of 33 128 bit subkeys.  */
76 typedef u32 serpent_subkeys_t[ROUNDS + 1][4];
77
78 /* A Serpent context.  */
79 typedef struct serpent_context
80 {
81   serpent_subkeys_t keys;       /* Generated subkeys.  */
82
83 #ifdef USE_AVX2
84   int use_avx2;
85 #endif
86 #ifdef USE_NEON
87   int use_neon;
88 #endif
89 } serpent_context_t;
90
91
92 /* Assembly implementations use SystemV ABI, ABI conversion and additional
93  * stack to store XMM6-XMM15 needed on Win64. */
94 #undef ASM_FUNC_ABI
95 #if defined(USE_SSE2) || defined(USE_AVX2)
96 # ifdef HAVE_COMPATIBLE_GCC_WIN64_PLATFORM_AS
97 #  define ASM_FUNC_ABI __attribute__((sysv_abi))
98 # else
99 #  define ASM_FUNC_ABI
100 # endif
101 #endif
102
103
104 #ifdef USE_SSE2
105 /* Assembler implementations of Serpent using SSE2.  Process 8 block in
106    parallel.
107  */
108 extern void _gcry_serpent_sse2_ctr_enc(serpent_context_t *ctx,
109                                        unsigned char *out,
110                                        const unsigned char *in,
111                                        unsigned char *ctr) ASM_FUNC_ABI;
112
113 extern void _gcry_serpent_sse2_cbc_dec(serpent_context_t *ctx,
114                                        unsigned char *out,
115                                        const unsigned char *in,
116                                        unsigned char *iv) ASM_FUNC_ABI;
117
118 extern void _gcry_serpent_sse2_cfb_dec(serpent_context_t *ctx,
119                                        unsigned char *out,
120                                        const unsigned char *in,
121                                        unsigned char *iv) ASM_FUNC_ABI;
122
123 extern void _gcry_serpent_sse2_ocb_enc(serpent_context_t *ctx,
124                                        unsigned char *out,
125                                        const unsigned char *in,
126                                        unsigned char *offset,
127                                        unsigned char *checksum,
128                                        const u64 Ls[8]) ASM_FUNC_ABI;
129
130 extern void _gcry_serpent_sse2_ocb_dec(serpent_context_t *ctx,
131                                        unsigned char *out,
132                                        const unsigned char *in,
133                                        unsigned char *offset,
134                                        unsigned char *checksum,
135                                        const u64 Ls[8]) ASM_FUNC_ABI;
136
137 extern void _gcry_serpent_sse2_ocb_auth(serpent_context_t *ctx,
138                                         const unsigned char *abuf,
139                                         unsigned char *offset,
140                                         unsigned char *checksum,
141                                         const u64 Ls[8]) ASM_FUNC_ABI;
142 #endif
143
144 #ifdef USE_AVX2
145 /* Assembler implementations of Serpent using AVX2.  Process 16 block in
146    parallel.
147  */
148 extern void _gcry_serpent_avx2_ctr_enc(serpent_context_t *ctx,
149                                        unsigned char *out,
150                                        const unsigned char *in,
151                                        unsigned char *ctr) ASM_FUNC_ABI;
152
153 extern void _gcry_serpent_avx2_cbc_dec(serpent_context_t *ctx,
154                                        unsigned char *out,
155                                        const unsigned char *in,
156                                        unsigned char *iv) ASM_FUNC_ABI;
157
158 extern void _gcry_serpent_avx2_cfb_dec(serpent_context_t *ctx,
159                                        unsigned char *out,
160                                        const unsigned char *in,
161                                        unsigned char *iv) ASM_FUNC_ABI;
162
163 extern void _gcry_serpent_avx2_ocb_enc(serpent_context_t *ctx,
164                                        unsigned char *out,
165                                        const unsigned char *in,
166                                        unsigned char *offset,
167                                        unsigned char *checksum,
168                                        const u64 Ls[16]) ASM_FUNC_ABI;
169
170 extern void _gcry_serpent_avx2_ocb_dec(serpent_context_t *ctx,
171                                        unsigned char *out,
172                                        const unsigned char *in,
173                                        unsigned char *offset,
174                                        unsigned char *checksum,
175                                        const u64 Ls[16]) ASM_FUNC_ABI;
176
177 extern void _gcry_serpent_avx2_ocb_auth(serpent_context_t *ctx,
178                                         const unsigned char *abuf,
179                                         unsigned char *offset,
180                                         unsigned char *checksum,
181                                         const u64 Ls[16]) ASM_FUNC_ABI;
182 #endif
183
184 #ifdef USE_NEON
185 /* Assembler implementations of Serpent using ARM NEON.  Process 8 block in
186    parallel.
187  */
188 extern void _gcry_serpent_neon_ctr_enc(serpent_context_t *ctx,
189                                        unsigned char *out,
190                                        const unsigned char *in,
191                                        unsigned char *ctr);
192
193 extern void _gcry_serpent_neon_cbc_dec(serpent_context_t *ctx,
194                                        unsigned char *out,
195                                        const unsigned char *in,
196                                        unsigned char *iv);
197
198 extern void _gcry_serpent_neon_cfb_dec(serpent_context_t *ctx,
199                                        unsigned char *out,
200                                        const unsigned char *in,
201                                        unsigned char *iv);
202
203 extern void _gcry_serpent_neon_ocb_enc(serpent_context_t *ctx,
204                                        unsigned char *out,
205                                        const unsigned char *in,
206                                        unsigned char *offset,
207                                        unsigned char *checksum,
208                                        const void *Ls[8]);
209
210 extern void _gcry_serpent_neon_ocb_dec(serpent_context_t *ctx,
211                                        unsigned char *out,
212                                        const unsigned char *in,
213                                        unsigned char *offset,
214                                        unsigned char *checksum,
215                                        const void *Ls[8]);
216
217 extern void _gcry_serpent_neon_ocb_auth(serpent_context_t *ctx,
218                                         const unsigned char *abuf,
219                                         unsigned char *offset,
220                                         unsigned char *checksum,
221                                         const void *Ls[8]);
222 #endif
223
224
225 /* A prototype.  */
226 static const char *serpent_test (void);
227
228
229 /*
230  * These are the S-Boxes of Serpent from following research paper.
231  *
232  *  D. A. Osvik, “Speeding up Serpent,” in Third AES Candidate Conference,
233  *   (New York, New York, USA), p. 317–329, National Institute of Standards and
234  *   Technology, 2000.
235  *
236  * Paper is also available at: http://www.ii.uib.no/~osvik/pub/aes3.pdf
237  *
238  */
239
240 #define SBOX0(r0, r1, r2, r3, w, x, y, z) \
241   { \
242     u32 r4; \
243     \
244     r3 ^= r0; r4 =  r1; \
245     r1 &= r3; r4 ^= r2; \
246     r1 ^= r0; r0 |= r3; \
247     r0 ^= r4; r4 ^= r3; \
248     r3 ^= r2; r2 |= r1; \
249     r2 ^= r4; r4 = ~r4; \
250     r4 |= r1; r1 ^= r3; \
251     r1 ^= r4; r3 |= r0; \
252     r1 ^= r3; r4 ^= r3; \
253     \
254     w = r1; x = r4; y = r2; z = r0; \
255   }
256
257 #define SBOX0_INVERSE(r0, r1, r2, r3, w, x, y, z) \
258   { \
259     u32 r4; \
260     \
261     r2 = ~r2; r4 =  r1; \
262     r1 |= r0; r4 = ~r4; \
263     r1 ^= r2; r2 |= r4; \
264     r1 ^= r3; r0 ^= r4; \
265     r2 ^= r0; r0 &= r3; \
266     r4 ^= r0; r0 |= r1; \
267     r0 ^= r2; r3 ^= r4; \
268     r2 ^= r1; r3 ^= r0; \
269     r3 ^= r1; \
270     r2 &= r3; \
271     r4 ^= r2; \
272     \
273     w = r0; x = r4; y = r1; z = r3; \
274   }
275
276 #define SBOX1(r0, r1, r2, r3, w, x, y, z) \
277   { \
278     u32 r4; \
279     \
280     r0 = ~r0; r2 = ~r2; \
281     r4 =  r0; r0 &= r1; \
282     r2 ^= r0; r0 |= r3; \
283     r3 ^= r2; r1 ^= r0; \
284     r0 ^= r4; r4 |= r1; \
285     r1 ^= r3; r2 |= r0; \
286     r2 &= r4; r0 ^= r1; \
287     r1 &= r2; \
288     r1 ^= r0; r0 &= r2; \
289     r0 ^= r4; \
290     \
291     w = r2; x = r0; y = r3; z = r1; \
292   }
293
294 #define SBOX1_INVERSE(r0, r1, r2, r3, w, x, y, z) \
295   { \
296     u32 r4; \
297     \
298     r4 =  r1; r1 ^= r3; \
299     r3 &= r1; r4 ^= r2; \
300     r3 ^= r0; r0 |= r1; \
301     r2 ^= r3; r0 ^= r4; \
302     r0 |= r2; r1 ^= r3; \
303     r0 ^= r1; r1 |= r3; \
304     r1 ^= r0; r4 = ~r4; \
305     r4 ^= r1; r1 |= r0; \
306     r1 ^= r0; \
307     r1 |= r4; \
308     r3 ^= r1; \
309     \
310     w = r4; x = r0; y = r3; z = r2; \
311   }
312
313 #define SBOX2(r0, r1, r2, r3, w, x, y, z) \
314   { \
315     u32 r4; \
316     \
317     r4 =  r0; r0 &= r2; \
318     r0 ^= r3; r2 ^= r1; \
319     r2 ^= r0; r3 |= r4; \
320     r3 ^= r1; r4 ^= r2; \
321     r1 =  r3; r3 |= r4; \
322     r3 ^= r0; r0 &= r1; \
323     r4 ^= r0; r1 ^= r3; \
324     r1 ^= r4; r4 = ~r4; \
325     \
326     w = r2; x = r3; y = r1; z = r4; \
327   }
328
329 #define SBOX2_INVERSE(r0, r1, r2, r3, w, x, y, z) \
330   { \
331     u32 r4; \
332     \
333     r2 ^= r3; r3 ^= r0; \
334     r4 =  r3; r3 &= r2; \
335     r3 ^= r1; r1 |= r2; \
336     r1 ^= r4; r4 &= r3; \
337     r2 ^= r3; r4 &= r0; \
338     r4 ^= r2; r2 &= r1; \
339     r2 |= r0; r3 = ~r3; \
340     r2 ^= r3; r0 ^= r3; \
341     r0 &= r1; r3 ^= r4; \
342     r3 ^= r0; \
343     \
344     w = r1; x = r4; y = r2; z = r3; \
345   }
346
347 #define SBOX3(r0, r1, r2, r3, w, x, y, z) \
348   { \
349     u32 r4; \
350     \
351     r4 =  r0; r0 |= r3; \
352     r3 ^= r1; r1 &= r4; \
353     r4 ^= r2; r2 ^= r3; \
354     r3 &= r0; r4 |= r1; \
355     r3 ^= r4; r0 ^= r1; \
356     r4 &= r0; r1 ^= r3; \
357     r4 ^= r2; r1 |= r0; \
358     r1 ^= r2; r0 ^= r3; \
359     r2 =  r1; r1 |= r3; \
360     r1 ^= r0; \
361     \
362     w = r1; x = r2; y = r3; z = r4; \
363   }
364
365 #define SBOX3_INVERSE(r0, r1, r2, r3, w, x, y, z) \
366   { \
367     u32 r4; \
368     \
369     r4 =  r2; r2 ^= r1; \
370     r0 ^= r2; r4 &= r2; \
371     r4 ^= r0; r0 &= r1; \
372     r1 ^= r3; r3 |= r4; \
373     r2 ^= r3; r0 ^= r3; \
374     r1 ^= r4; r3 &= r2; \
375     r3 ^= r1; r1 ^= r0; \
376     r1 |= r2; r0 ^= r3; \
377     r1 ^= r4; \
378     r0 ^= r1; \
379     \
380     w = r2; x = r1; y = r3; z = r0; \
381   }
382
383 #define SBOX4(r0, r1, r2, r3, w, x, y, z) \
384   { \
385     u32 r4; \
386     \
387     r1 ^= r3; r3 = ~r3; \
388     r2 ^= r3; r3 ^= r0; \
389     r4 =  r1; r1 &= r3; \
390     r1 ^= r2; r4 ^= r3; \
391     r0 ^= r4; r2 &= r4; \
392     r2 ^= r0; r0 &= r1; \
393     r3 ^= r0; r4 |= r1; \
394     r4 ^= r0; r0 |= r3; \
395     r0 ^= r2; r2 &= r3; \
396     r0 = ~r0; r4 ^= r2; \
397     \
398     w = r1; x = r4; y = r0; z = r3; \
399   }
400
401 #define SBOX4_INVERSE(r0, r1, r2, r3, w, x, y, z) \
402   { \
403     u32 r4; \
404     \
405     r4 =  r2; r2 &= r3; \
406     r2 ^= r1; r1 |= r3; \
407     r1 &= r0; r4 ^= r2; \
408     r4 ^= r1; r1 &= r2; \
409     r0 = ~r0; r3 ^= r4; \
410     r1 ^= r3; r3 &= r0; \
411     r3 ^= r2; r0 ^= r1; \
412     r2 &= r0; r3 ^= r0; \
413     r2 ^= r4; \
414     r2 |= r3; r3 ^= r0; \
415     r2 ^= r1; \
416     \
417     w = r0; x = r3; y = r2; z = r4; \
418   }
419
420 #define SBOX5(r0, r1, r2, r3, w, x, y, z) \
421   { \
422     u32 r4; \
423     \
424     r0 ^= r1; r1 ^= r3; \
425     r3 = ~r3; r4 =  r1; \
426     r1 &= r0; r2 ^= r3; \
427     r1 ^= r2; r2 |= r4; \
428     r4 ^= r3; r3 &= r1; \
429     r3 ^= r0; r4 ^= r1; \
430     r4 ^= r2; r2 ^= r0; \
431     r0 &= r3; r2 = ~r2; \
432     r0 ^= r4; r4 |= r3; \
433     r2 ^= r4; \
434     \
435     w = r1; x = r3; y = r0; z = r2; \
436   }
437
438 #define SBOX5_INVERSE(r0, r1, r2, r3, w, x, y, z) \
439   { \
440     u32 r4; \
441     \
442     r1 = ~r1; r4 =  r3; \
443     r2 ^= r1; r3 |= r0; \
444     r3 ^= r2; r2 |= r1; \
445     r2 &= r0; r4 ^= r3; \
446     r2 ^= r4; r4 |= r0; \
447     r4 ^= r1; r1 &= r2; \
448     r1 ^= r3; r4 ^= r2; \
449     r3 &= r4; r4 ^= r1; \
450     r3 ^= r4; r4 = ~r4; \
451     r3 ^= r0; \
452     \
453     w = r1; x = r4; y = r3; z = r2; \
454   }
455
456 #define SBOX6(r0, r1, r2, r3, w, x, y, z) \
457   { \
458     u32 r4; \
459     \
460     r2 = ~r2; r4 =  r3; \
461     r3 &= r0; r0 ^= r4; \
462     r3 ^= r2; r2 |= r4; \
463     r1 ^= r3; r2 ^= r0; \
464     r0 |= r1; r2 ^= r1; \
465     r4 ^= r0; r0 |= r3; \
466     r0 ^= r2; r4 ^= r3; \
467     r4 ^= r0; r3 = ~r3; \
468     r2 &= r4; \
469     r2 ^= r3; \
470     \
471     w = r0; x = r1; y = r4; z = r2; \
472   }
473
474 #define SBOX6_INVERSE(r0, r1, r2, r3, w, x, y, z) \
475   { \
476     u32 r4; \
477     \
478     r0 ^= r2; r4 =  r2; \
479     r2 &= r0; r4 ^= r3; \
480     r2 = ~r2; r3 ^= r1; \
481     r2 ^= r3; r4 |= r0; \
482     r0 ^= r2; r3 ^= r4; \
483     r4 ^= r1; r1 &= r3; \
484     r1 ^= r0; r0 ^= r3; \
485     r0 |= r2; r3 ^= r1; \
486     r4 ^= r0; \
487     \
488     w = r1; x = r2; y = r4; z = r3; \
489   }
490
491 #define SBOX7(r0, r1, r2, r3, w, x, y, z) \
492   { \
493     u32 r4; \
494     \
495     r4 =  r1; r1 |= r2; \
496     r1 ^= r3; r4 ^= r2; \
497     r2 ^= r1; r3 |= r4; \
498     r3 &= r0; r4 ^= r2; \
499     r3 ^= r1; r1 |= r4; \
500     r1 ^= r0; r0 |= r4; \
501     r0 ^= r2; r1 ^= r4; \
502     r2 ^= r1; r1 &= r0; \
503     r1 ^= r4; r2 = ~r2; \
504     r2 |= r0; \
505     r4 ^= r2; \
506     \
507     w = r4; x = r3; y = r1; z = r0; \
508   }
509
510 #define SBOX7_INVERSE(r0, r1, r2, r3, w, x, y, z) \
511   { \
512     u32 r4; \
513     \
514     r4 =  r2; r2 ^= r0; \
515     r0 &= r3; r4 |= r3; \
516     r2 = ~r2; r3 ^= r1; \
517     r1 |= r0; r0 ^= r2; \
518     r2 &= r4; r3 &= r4; \
519     r1 ^= r2; r2 ^= r0; \
520     r0 |= r2; r4 ^= r1; \
521     r0 ^= r3; r3 ^= r4; \
522     r4 |= r0; r3 ^= r2; \
523     r4 ^= r2; \
524     \
525     w = r3; x = r0; y = r1; z = r4; \
526   }
527
528 /* XOR BLOCK1 into BLOCK0.  */
529 #define BLOCK_XOR(block0, block1) \
530   {                               \
531     block0[0] ^= block1[0];       \
532     block0[1] ^= block1[1];       \
533     block0[2] ^= block1[2];       \
534     block0[3] ^= block1[3];       \
535   }
536
537 /* Copy BLOCK_SRC to BLOCK_DST.  */
538 #define BLOCK_COPY(block_dst, block_src) \
539   {                                      \
540     block_dst[0] = block_src[0];         \
541     block_dst[1] = block_src[1];         \
542     block_dst[2] = block_src[2];         \
543     block_dst[3] = block_src[3];         \
544   }
545
546 /* Apply SBOX number WHICH to to the block found in ARRAY0, writing
547    the output to the block found in ARRAY1.  */
548 #define SBOX(which, array0, array1)                         \
549   SBOX##which (array0[0], array0[1], array0[2], array0[3],  \
550                array1[0], array1[1], array1[2], array1[3]);
551
552 /* Apply inverse SBOX number WHICH to to the block found in ARRAY0, writing
553    the output to the block found in ARRAY1.  */
554 #define SBOX_INVERSE(which, array0, array1)                           \
555   SBOX##which##_INVERSE (array0[0], array0[1], array0[2], array0[3],  \
556                          array1[0], array1[1], array1[2], array1[3]);
557
558 /* Apply the linear transformation to BLOCK.  */
559 #define LINEAR_TRANSFORMATION(block)                  \
560   {                                                   \
561     block[0] = rol (block[0], 13);                    \
562     block[2] = rol (block[2], 3);                     \
563     block[1] = block[1] ^ block[0] ^ block[2];        \
564     block[3] = block[3] ^ block[2] ^ (block[0] << 3); \
565     block[1] = rol (block[1], 1);                     \
566     block[3] = rol (block[3], 7);                     \
567     block[0] = block[0] ^ block[1] ^ block[3];        \
568     block[2] = block[2] ^ block[3] ^ (block[1] << 7); \
569     block[0] = rol (block[0], 5);                     \
570     block[2] = rol (block[2], 22);                    \
571   }
572
573 /* Apply the inverse linear transformation to BLOCK.  */
574 #define LINEAR_TRANSFORMATION_INVERSE(block)          \
575   {                                                   \
576     block[2] = ror (block[2], 22);                    \
577     block[0] = ror (block[0] , 5);                    \
578     block[2] = block[2] ^ block[3] ^ (block[1] << 7); \
579     block[0] = block[0] ^ block[1] ^ block[3];        \
580     block[3] = ror (block[3], 7);                     \
581     block[1] = ror (block[1], 1);                     \
582     block[3] = block[3] ^ block[2] ^ (block[0] << 3); \
583     block[1] = block[1] ^ block[0] ^ block[2];        \
584     block[2] = ror (block[2], 3);                     \
585     block[0] = ror (block[0], 13);                    \
586   }
587
588 /* Apply a Serpent round to BLOCK, using the SBOX number WHICH and the
589    subkeys contained in SUBKEYS.  Use BLOCK_TMP as temporary storage.
590    This macro increments `round'.  */
591 #define ROUND(which, subkeys, block, block_tmp) \
592   {                                             \
593     BLOCK_XOR (block, subkeys[round]);          \
594     round++;                                    \
595     SBOX (which, block, block_tmp);             \
596     LINEAR_TRANSFORMATION (block_tmp);          \
597     BLOCK_COPY (block, block_tmp);              \
598   }
599
600 /* Apply the last Serpent round to BLOCK, using the SBOX number WHICH
601    and the subkeys contained in SUBKEYS.  Use BLOCK_TMP as temporary
602    storage.  The result will be stored in BLOCK_TMP.  This macro
603    increments `round'.  */
604 #define ROUND_LAST(which, subkeys, block, block_tmp) \
605   {                                                  \
606     BLOCK_XOR (block, subkeys[round]);               \
607     round++;                                         \
608     SBOX (which, block, block_tmp);                  \
609     BLOCK_XOR (block_tmp, subkeys[round]);           \
610     round++;                                         \
611   }
612
613 /* Apply an inverse Serpent round to BLOCK, using the SBOX number
614    WHICH and the subkeys contained in SUBKEYS.  Use BLOCK_TMP as
615    temporary storage.  This macro increments `round'.  */
616 #define ROUND_INVERSE(which, subkey, block, block_tmp) \
617   {                                                    \
618     LINEAR_TRANSFORMATION_INVERSE (block);             \
619     SBOX_INVERSE (which, block, block_tmp);            \
620     BLOCK_XOR (block_tmp, subkey[round]);              \
621     round--;                                           \
622     BLOCK_COPY (block, block_tmp);                     \
623   }
624
625 /* Apply the first Serpent round to BLOCK, using the SBOX number WHICH
626    and the subkeys contained in SUBKEYS.  Use BLOCK_TMP as temporary
627    storage.  The result will be stored in BLOCK_TMP.  This macro
628    increments `round'.  */
629 #define ROUND_FIRST_INVERSE(which, subkeys, block, block_tmp) \
630   {                                                           \
631     BLOCK_XOR (block, subkeys[round]);                        \
632     round--;                                                  \
633     SBOX_INVERSE (which, block, block_tmp);                   \
634     BLOCK_XOR (block_tmp, subkeys[round]);                    \
635     round--;                                                  \
636   }
637
638 /* Convert the user provided key KEY of KEY_LENGTH bytes into the
639    internally used format.  */
640 static void
641 serpent_key_prepare (const byte *key, unsigned int key_length,
642                      serpent_key_t key_prepared)
643 {
644   int i;
645
646   /* Copy key.  */
647   key_length /= 4;
648   for (i = 0; i < key_length; i++)
649     key_prepared[i] = buf_get_le32 (key + i * 4);
650
651   if (i < 8)
652     {
653       /* Key must be padded according to the Serpent
654          specification.  */
655       key_prepared[i] = 0x00000001;
656
657       for (i++; i < 8; i++)
658         key_prepared[i] = 0;
659     }
660 }
661
662 /* Derive the 33 subkeys from KEY and store them in SUBKEYS.  */
663 static void
664 serpent_subkeys_generate (serpent_key_t key, serpent_subkeys_t subkeys)
665 {
666   u32 w[8];             /* The `prekey'.  */
667   u32 ws[4];
668   u32 wt[4];
669
670   /* Initialize with key values.  */
671   w[0] = key[0];
672   w[1] = key[1];
673   w[2] = key[2];
674   w[3] = key[3];
675   w[4] = key[4];
676   w[5] = key[5];
677   w[6] = key[6];
678   w[7] = key[7];
679
680   /* Expand to intermediate key using the affine recurrence.  */
681 #define EXPAND_KEY4(wo, r)                                                     \
682   wo[0] = w[(r+0)%8] =                                                         \
683     rol (w[(r+0)%8] ^ w[(r+3)%8] ^ w[(r+5)%8] ^ w[(r+7)%8] ^ PHI ^ (r+0), 11); \
684   wo[1] = w[(r+1)%8] =                                                         \
685     rol (w[(r+1)%8] ^ w[(r+4)%8] ^ w[(r+6)%8] ^ w[(r+0)%8] ^ PHI ^ (r+1), 11); \
686   wo[2] = w[(r+2)%8] =                                                         \
687     rol (w[(r+2)%8] ^ w[(r+5)%8] ^ w[(r+7)%8] ^ w[(r+1)%8] ^ PHI ^ (r+2), 11); \
688   wo[3] = w[(r+3)%8] =                                                         \
689     rol (w[(r+3)%8] ^ w[(r+6)%8] ^ w[(r+0)%8] ^ w[(r+2)%8] ^ PHI ^ (r+3), 11);
690
691 #define EXPAND_KEY(r)       \
692   EXPAND_KEY4(ws, (r));     \
693   EXPAND_KEY4(wt, (r + 4));
694
695   /* Calculate subkeys via S-Boxes, in bitslice mode.  */
696   EXPAND_KEY (0); SBOX (3, ws, subkeys[0]); SBOX (2, wt, subkeys[1]);
697   EXPAND_KEY (8); SBOX (1, ws, subkeys[2]); SBOX (0, wt, subkeys[3]);
698   EXPAND_KEY (16); SBOX (7, ws, subkeys[4]); SBOX (6, wt, subkeys[5]);
699   EXPAND_KEY (24); SBOX (5, ws, subkeys[6]); SBOX (4, wt, subkeys[7]);
700   EXPAND_KEY (32); SBOX (3, ws, subkeys[8]); SBOX (2, wt, subkeys[9]);
701   EXPAND_KEY (40); SBOX (1, ws, subkeys[10]); SBOX (0, wt, subkeys[11]);
702   EXPAND_KEY (48); SBOX (7, ws, subkeys[12]); SBOX (6, wt, subkeys[13]);
703   EXPAND_KEY (56); SBOX (5, ws, subkeys[14]); SBOX (4, wt, subkeys[15]);
704   EXPAND_KEY (64); SBOX (3, ws, subkeys[16]); SBOX (2, wt, subkeys[17]);
705   EXPAND_KEY (72); SBOX (1, ws, subkeys[18]); SBOX (0, wt, subkeys[19]);
706   EXPAND_KEY (80); SBOX (7, ws, subkeys[20]); SBOX (6, wt, subkeys[21]);
707   EXPAND_KEY (88); SBOX (5, ws, subkeys[22]); SBOX (4, wt, subkeys[23]);
708   EXPAND_KEY (96); SBOX (3, ws, subkeys[24]); SBOX (2, wt, subkeys[25]);
709   EXPAND_KEY (104); SBOX (1, ws, subkeys[26]); SBOX (0, wt, subkeys[27]);
710   EXPAND_KEY (112); SBOX (7, ws, subkeys[28]); SBOX (6, wt, subkeys[29]);
711   EXPAND_KEY (120); SBOX (5, ws, subkeys[30]); SBOX (4, wt, subkeys[31]);
712   EXPAND_KEY4 (ws, 128); SBOX (3, ws, subkeys[32]);
713
714   wipememory (ws, sizeof (ws));
715   wipememory (wt, sizeof (wt));
716   wipememory (w, sizeof (w));
717 }
718
719 /* Initialize CONTEXT with the key KEY of KEY_LENGTH bits.  */
720 static void
721 serpent_setkey_internal (serpent_context_t *context,
722                          const byte *key, unsigned int key_length)
723 {
724   serpent_key_t key_prepared;
725
726   serpent_key_prepare (key, key_length, key_prepared);
727   serpent_subkeys_generate (key_prepared, context->keys);
728
729 #ifdef USE_AVX2
730   context->use_avx2 = 0;
731   if ((_gcry_get_hw_features () & HWF_INTEL_AVX2))
732     {
733       context->use_avx2 = 1;
734     }
735 #endif
736
737 #ifdef USE_NEON
738   context->use_neon = 0;
739   if ((_gcry_get_hw_features () & HWF_ARM_NEON))
740     {
741       context->use_neon = 1;
742     }
743 #endif
744
745   wipememory (key_prepared, sizeof(key_prepared));
746 }
747
748 /* Initialize CTX with the key KEY of KEY_LENGTH bytes.  */
749 static gcry_err_code_t
750 serpent_setkey (void *ctx,
751                 const byte *key, unsigned int key_length)
752 {
753   serpent_context_t *context = ctx;
754   static const char *serpent_test_ret;
755   static int serpent_init_done;
756   gcry_err_code_t ret = GPG_ERR_NO_ERROR;
757
758   if (! serpent_init_done)
759     {
760       /* Execute a self-test the first time, Serpent is used.  */
761       serpent_init_done = 1;
762       serpent_test_ret = serpent_test ();
763       if (serpent_test_ret)
764         log_error ("Serpent test failure: %s\n", serpent_test_ret);
765     }
766
767   if (serpent_test_ret)
768     ret = GPG_ERR_SELFTEST_FAILED;
769   else
770     serpent_setkey_internal (context, key, key_length);
771
772   return ret;
773 }
774
775 static void
776 serpent_encrypt_internal (serpent_context_t *context,
777                           const byte *input, byte *output)
778 {
779   serpent_block_t b, b_next;
780   int round = 0;
781
782   b[0] = buf_get_le32 (input + 0);
783   b[1] = buf_get_le32 (input + 4);
784   b[2] = buf_get_le32 (input + 8);
785   b[3] = buf_get_le32 (input + 12);
786
787   ROUND (0, context->keys, b, b_next);
788   ROUND (1, context->keys, b, b_next);
789   ROUND (2, context->keys, b, b_next);
790   ROUND (3, context->keys, b, b_next);
791   ROUND (4, context->keys, b, b_next);
792   ROUND (5, context->keys, b, b_next);
793   ROUND (6, context->keys, b, b_next);
794   ROUND (7, context->keys, b, b_next);
795   ROUND (0, context->keys, b, b_next);
796   ROUND (1, context->keys, b, b_next);
797   ROUND (2, context->keys, b, b_next);
798   ROUND (3, context->keys, b, b_next);
799   ROUND (4, context->keys, b, b_next);
800   ROUND (5, context->keys, b, b_next);
801   ROUND (6, context->keys, b, b_next);
802   ROUND (7, context->keys, b, b_next);
803   ROUND (0, context->keys, b, b_next);
804   ROUND (1, context->keys, b, b_next);
805   ROUND (2, context->keys, b, b_next);
806   ROUND (3, context->keys, b, b_next);
807   ROUND (4, context->keys, b, b_next);
808   ROUND (5, context->keys, b, b_next);
809   ROUND (6, context->keys, b, b_next);
810   ROUND (7, context->keys, b, b_next);
811   ROUND (0, context->keys, b, b_next);
812   ROUND (1, context->keys, b, b_next);
813   ROUND (2, context->keys, b, b_next);
814   ROUND (3, context->keys, b, b_next);
815   ROUND (4, context->keys, b, b_next);
816   ROUND (5, context->keys, b, b_next);
817   ROUND (6, context->keys, b, b_next);
818
819   ROUND_LAST (7, context->keys, b, b_next);
820
821   buf_put_le32 (output + 0, b_next[0]);
822   buf_put_le32 (output + 4, b_next[1]);
823   buf_put_le32 (output + 8, b_next[2]);
824   buf_put_le32 (output + 12, b_next[3]);
825 }
826
827 static void
828 serpent_decrypt_internal (serpent_context_t *context,
829                           const byte *input, byte *output)
830 {
831   serpent_block_t b, b_next;
832   int round = ROUNDS;
833
834   b_next[0] = buf_get_le32 (input + 0);
835   b_next[1] = buf_get_le32 (input + 4);
836   b_next[2] = buf_get_le32 (input + 8);
837   b_next[3] = buf_get_le32 (input + 12);
838
839   ROUND_FIRST_INVERSE (7, context->keys, b_next, b);
840
841   ROUND_INVERSE (6, context->keys, b, b_next);
842   ROUND_INVERSE (5, context->keys, b, b_next);
843   ROUND_INVERSE (4, context->keys, b, b_next);
844   ROUND_INVERSE (3, context->keys, b, b_next);
845   ROUND_INVERSE (2, context->keys, b, b_next);
846   ROUND_INVERSE (1, context->keys, b, b_next);
847   ROUND_INVERSE (0, context->keys, b, b_next);
848   ROUND_INVERSE (7, context->keys, b, b_next);
849   ROUND_INVERSE (6, context->keys, b, b_next);
850   ROUND_INVERSE (5, context->keys, b, b_next);
851   ROUND_INVERSE (4, context->keys, b, b_next);
852   ROUND_INVERSE (3, context->keys, b, b_next);
853   ROUND_INVERSE (2, context->keys, b, b_next);
854   ROUND_INVERSE (1, context->keys, b, b_next);
855   ROUND_INVERSE (0, context->keys, b, b_next);
856   ROUND_INVERSE (7, context->keys, b, b_next);
857   ROUND_INVERSE (6, context->keys, b, b_next);
858   ROUND_INVERSE (5, context->keys, b, b_next);
859   ROUND_INVERSE (4, context->keys, b, b_next);
860   ROUND_INVERSE (3, context->keys, b, b_next);
861   ROUND_INVERSE (2, context->keys, b, b_next);
862   ROUND_INVERSE (1, context->keys, b, b_next);
863   ROUND_INVERSE (0, context->keys, b, b_next);
864   ROUND_INVERSE (7, context->keys, b, b_next);
865   ROUND_INVERSE (6, context->keys, b, b_next);
866   ROUND_INVERSE (5, context->keys, b, b_next);
867   ROUND_INVERSE (4, context->keys, b, b_next);
868   ROUND_INVERSE (3, context->keys, b, b_next);
869   ROUND_INVERSE (2, context->keys, b, b_next);
870   ROUND_INVERSE (1, context->keys, b, b_next);
871   ROUND_INVERSE (0, context->keys, b, b_next);
872
873   buf_put_le32 (output + 0, b_next[0]);
874   buf_put_le32 (output + 4, b_next[1]);
875   buf_put_le32 (output + 8, b_next[2]);
876   buf_put_le32 (output + 12, b_next[3]);
877 }
878
879 static unsigned int
880 serpent_encrypt (void *ctx, byte *buffer_out, const byte *buffer_in)
881 {
882   serpent_context_t *context = ctx;
883
884   serpent_encrypt_internal (context, buffer_in, buffer_out);
885   return /*burn_stack*/ (2 * sizeof (serpent_block_t));
886 }
887
888 static unsigned int
889 serpent_decrypt (void *ctx, byte *buffer_out, const byte *buffer_in)
890 {
891   serpent_context_t *context = ctx;
892
893   serpent_decrypt_internal (context, buffer_in, buffer_out);
894   return /*burn_stack*/ (2 * sizeof (serpent_block_t));
895 }
896
897 \f
898
899 /* Bulk encryption of complete blocks in CTR mode.  This function is only
900    intended for the bulk encryption feature of cipher.c.  CTR is expected to be
901    of size sizeof(serpent_block_t). */
902 void
903 _gcry_serpent_ctr_enc(void *context, unsigned char *ctr,
904                       void *outbuf_arg, const void *inbuf_arg,
905                       size_t nblocks)
906 {
907   serpent_context_t *ctx = context;
908   unsigned char *outbuf = outbuf_arg;
909   const unsigned char *inbuf = inbuf_arg;
910   unsigned char tmpbuf[sizeof(serpent_block_t)];
911   int burn_stack_depth = 2 * sizeof (serpent_block_t);
912   int i;
913
914 #ifdef USE_AVX2
915   if (ctx->use_avx2)
916     {
917       int did_use_avx2 = 0;
918
919       /* Process data in 16 block chunks. */
920       while (nblocks >= 16)
921         {
922           _gcry_serpent_avx2_ctr_enc(ctx, outbuf, inbuf, ctr);
923
924           nblocks -= 16;
925           outbuf += 16 * sizeof(serpent_block_t);
926           inbuf  += 16 * sizeof(serpent_block_t);
927           did_use_avx2 = 1;
928         }
929
930       if (did_use_avx2)
931         {
932           /* serpent-avx2 assembly code does not use stack */
933           if (nblocks == 0)
934             burn_stack_depth = 0;
935         }
936
937       /* Use generic/sse2 code to handle smaller chunks... */
938       /* TODO: use caching instead? */
939     }
940 #endif
941
942 #ifdef USE_SSE2
943   {
944     int did_use_sse2 = 0;
945
946     /* Process data in 8 block chunks. */
947     while (nblocks >= 8)
948       {
949         _gcry_serpent_sse2_ctr_enc(ctx, outbuf, inbuf, ctr);
950
951         nblocks -= 8;
952         outbuf += 8 * sizeof(serpent_block_t);
953         inbuf  += 8 * sizeof(serpent_block_t);
954         did_use_sse2 = 1;
955       }
956
957     if (did_use_sse2)
958       {
959         /* serpent-sse2 assembly code does not use stack */
960         if (nblocks == 0)
961           burn_stack_depth = 0;
962       }
963
964     /* Use generic code to handle smaller chunks... */
965     /* TODO: use caching instead? */
966   }
967 #endif
968
969 #ifdef USE_NEON
970   if (ctx->use_neon)
971     {
972       int did_use_neon = 0;
973
974       /* Process data in 8 block chunks. */
975       while (nblocks >= 8)
976         {
977           _gcry_serpent_neon_ctr_enc(ctx, outbuf, inbuf, ctr);
978
979           nblocks -= 8;
980           outbuf += 8 * sizeof(serpent_block_t);
981           inbuf  += 8 * sizeof(serpent_block_t);
982           did_use_neon = 1;
983         }
984
985       if (did_use_neon)
986         {
987           /* serpent-neon assembly code does not use stack */
988           if (nblocks == 0)
989             burn_stack_depth = 0;
990         }
991
992       /* Use generic code to handle smaller chunks... */
993       /* TODO: use caching instead? */
994     }
995 #endif
996
997   for ( ;nblocks; nblocks-- )
998     {
999       /* Encrypt the counter. */
1000       serpent_encrypt_internal(ctx, ctr, tmpbuf);
1001       /* XOR the input with the encrypted counter and store in output.  */
1002       buf_xor(outbuf, tmpbuf, inbuf, sizeof(serpent_block_t));
1003       outbuf += sizeof(serpent_block_t);
1004       inbuf  += sizeof(serpent_block_t);
1005       /* Increment the counter.  */
1006       for (i = sizeof(serpent_block_t); i > 0; i--)
1007         {
1008           ctr[i-1]++;
1009           if (ctr[i-1])
1010             break;
1011         }
1012     }
1013
1014   wipememory(tmpbuf, sizeof(tmpbuf));
1015   _gcry_burn_stack(burn_stack_depth);
1016 }
1017
1018 /* Bulk decryption of complete blocks in CBC mode.  This function is only
1019    intended for the bulk encryption feature of cipher.c. */
1020 void
1021 _gcry_serpent_cbc_dec(void *context, unsigned char *iv,
1022                       void *outbuf_arg, const void *inbuf_arg,
1023                       size_t nblocks)
1024 {
1025   serpent_context_t *ctx = context;
1026   unsigned char *outbuf = outbuf_arg;
1027   const unsigned char *inbuf = inbuf_arg;
1028   unsigned char savebuf[sizeof(serpent_block_t)];
1029   int burn_stack_depth = 2 * sizeof (serpent_block_t);
1030
1031 #ifdef USE_AVX2
1032   if (ctx->use_avx2)
1033     {
1034       int did_use_avx2 = 0;
1035
1036       /* Process data in 16 block chunks. */
1037       while (nblocks >= 16)
1038         {
1039           _gcry_serpent_avx2_cbc_dec(ctx, outbuf, inbuf, iv);
1040
1041           nblocks -= 16;
1042           outbuf += 16 * sizeof(serpent_block_t);
1043           inbuf  += 16 * sizeof(serpent_block_t);
1044           did_use_avx2 = 1;
1045         }
1046
1047       if (did_use_avx2)
1048         {
1049           /* serpent-avx2 assembly code does not use stack */
1050           if (nblocks == 0)
1051             burn_stack_depth = 0;
1052         }
1053
1054       /* Use generic/sse2 code to handle smaller chunks... */
1055     }
1056 #endif
1057
1058 #ifdef USE_SSE2
1059   {
1060     int did_use_sse2 = 0;
1061
1062     /* Process data in 8 block chunks. */
1063     while (nblocks >= 8)
1064       {
1065         _gcry_serpent_sse2_cbc_dec(ctx, outbuf, inbuf, iv);
1066
1067         nblocks -= 8;
1068         outbuf += 8 * sizeof(serpent_block_t);
1069         inbuf  += 8 * sizeof(serpent_block_t);
1070         did_use_sse2 = 1;
1071       }
1072
1073     if (did_use_sse2)
1074       {
1075         /* serpent-sse2 assembly code does not use stack */
1076         if (nblocks == 0)
1077           burn_stack_depth = 0;
1078       }
1079
1080     /* Use generic code to handle smaller chunks... */
1081   }
1082 #endif
1083
1084 #ifdef USE_NEON
1085   if (ctx->use_neon)
1086     {
1087       int did_use_neon = 0;
1088
1089       /* Process data in 8 block chunks. */
1090       while (nblocks >= 8)
1091         {
1092           _gcry_serpent_neon_cbc_dec(ctx, outbuf, inbuf, iv);
1093
1094           nblocks -= 8;
1095           outbuf += 8 * sizeof(serpent_block_t);
1096           inbuf  += 8 * sizeof(serpent_block_t);
1097           did_use_neon = 1;
1098         }
1099
1100       if (did_use_neon)
1101         {
1102           /* serpent-neon assembly code does not use stack */
1103           if (nblocks == 0)
1104             burn_stack_depth = 0;
1105         }
1106
1107       /* Use generic code to handle smaller chunks... */
1108     }
1109 #endif
1110
1111   for ( ;nblocks; nblocks-- )
1112     {
1113       /* INBUF is needed later and it may be identical to OUTBUF, so store
1114          the intermediate result to SAVEBUF.  */
1115       serpent_decrypt_internal (ctx, inbuf, savebuf);
1116
1117       buf_xor_n_copy_2(outbuf, savebuf, iv, inbuf, sizeof(serpent_block_t));
1118       inbuf += sizeof(serpent_block_t);
1119       outbuf += sizeof(serpent_block_t);
1120     }
1121
1122   wipememory(savebuf, sizeof(savebuf));
1123   _gcry_burn_stack(burn_stack_depth);
1124 }
1125
1126 /* Bulk decryption of complete blocks in CFB mode.  This function is only
1127    intended for the bulk encryption feature of cipher.c. */
1128 void
1129 _gcry_serpent_cfb_dec(void *context, unsigned char *iv,
1130                       void *outbuf_arg, const void *inbuf_arg,
1131                       size_t nblocks)
1132 {
1133   serpent_context_t *ctx = context;
1134   unsigned char *outbuf = outbuf_arg;
1135   const unsigned char *inbuf = inbuf_arg;
1136   int burn_stack_depth = 2 * sizeof (serpent_block_t);
1137
1138 #ifdef USE_AVX2
1139   if (ctx->use_avx2)
1140     {
1141       int did_use_avx2 = 0;
1142
1143       /* Process data in 16 block chunks. */
1144       while (nblocks >= 16)
1145         {
1146           _gcry_serpent_avx2_cfb_dec(ctx, outbuf, inbuf, iv);
1147
1148           nblocks -= 16;
1149           outbuf += 16 * sizeof(serpent_block_t);
1150           inbuf  += 16 * sizeof(serpent_block_t);
1151           did_use_avx2 = 1;
1152         }
1153
1154       if (did_use_avx2)
1155         {
1156           /* serpent-avx2 assembly code does not use stack */
1157           if (nblocks == 0)
1158             burn_stack_depth = 0;
1159         }
1160
1161       /* Use generic/sse2 code to handle smaller chunks... */
1162     }
1163 #endif
1164
1165 #ifdef USE_SSE2
1166   {
1167     int did_use_sse2 = 0;
1168
1169     /* Process data in 8 block chunks. */
1170     while (nblocks >= 8)
1171       {
1172         _gcry_serpent_sse2_cfb_dec(ctx, outbuf, inbuf, iv);
1173
1174         nblocks -= 8;
1175         outbuf += 8 * sizeof(serpent_block_t);
1176         inbuf  += 8 * sizeof(serpent_block_t);
1177         did_use_sse2 = 1;
1178       }
1179
1180     if (did_use_sse2)
1181       {
1182         /* serpent-sse2 assembly code does not use stack */
1183         if (nblocks == 0)
1184           burn_stack_depth = 0;
1185       }
1186
1187     /* Use generic code to handle smaller chunks... */
1188   }
1189 #endif
1190
1191 #ifdef USE_NEON
1192   if (ctx->use_neon)
1193     {
1194       int did_use_neon = 0;
1195
1196       /* Process data in 8 block chunks. */
1197       while (nblocks >= 8)
1198         {
1199           _gcry_serpent_neon_cfb_dec(ctx, outbuf, inbuf, iv);
1200
1201           nblocks -= 8;
1202           outbuf += 8 * sizeof(serpent_block_t);
1203           inbuf  += 8 * sizeof(serpent_block_t);
1204           did_use_neon = 1;
1205         }
1206
1207       if (did_use_neon)
1208         {
1209           /* serpent-neon assembly code does not use stack */
1210           if (nblocks == 0)
1211             burn_stack_depth = 0;
1212         }
1213
1214       /* Use generic code to handle smaller chunks... */
1215     }
1216 #endif
1217
1218   for ( ;nblocks; nblocks-- )
1219     {
1220       serpent_encrypt_internal(ctx, iv, iv);
1221       buf_xor_n_copy(outbuf, iv, inbuf, sizeof(serpent_block_t));
1222       outbuf += sizeof(serpent_block_t);
1223       inbuf  += sizeof(serpent_block_t);
1224     }
1225
1226   _gcry_burn_stack(burn_stack_depth);
1227 }
1228
1229 /* Bulk encryption/decryption of complete blocks in OCB mode. */
1230 size_t
1231 _gcry_serpent_ocb_crypt (gcry_cipher_hd_t c, void *outbuf_arg,
1232                         const void *inbuf_arg, size_t nblocks, int encrypt)
1233 {
1234 #if defined(USE_AVX2) || defined(USE_SSE2) || defined(USE_NEON)
1235   serpent_context_t *ctx = (void *)&c->context.c;
1236   unsigned char *outbuf = outbuf_arg;
1237   const unsigned char *inbuf = inbuf_arg;
1238   unsigned char l_tmp[sizeof(serpent_block_t)];
1239   int burn_stack_depth = 2 * sizeof (serpent_block_t);
1240   u64 blkn = c->u_mode.ocb.data_nblocks;
1241 #else
1242   (void)c;
1243   (void)outbuf_arg;
1244   (void)inbuf_arg;
1245   (void)encrypt;
1246 #endif
1247
1248 #ifdef USE_AVX2
1249   if (ctx->use_avx2)
1250     {
1251       int did_use_avx2 = 0;
1252       u64 Ls[16];
1253       unsigned int n = 16 - (blkn % 16);
1254       u64 *l;
1255       int i;
1256
1257       if (nblocks >= 16)
1258         {
1259           for (i = 0; i < 16; i += 8)
1260             {
1261               /* Use u64 to store pointers for x32 support (assembly function
1262                * assumes 64-bit pointers). */
1263               Ls[(i + 0 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1264               Ls[(i + 1 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1265               Ls[(i + 2 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1266               Ls[(i + 3 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[2];
1267               Ls[(i + 4 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1268               Ls[(i + 5 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1269               Ls[(i + 6 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1270             }
1271
1272           Ls[(7 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[3];
1273           l = &Ls[(15 + n) % 16];
1274
1275           /* Process data in 16 block chunks. */
1276           while (nblocks >= 16)
1277             {
1278               /* l_tmp will be used only every 65536-th block. */
1279               blkn += 16;
1280               *l = (uintptr_t)(void *)ocb_get_l(c, l_tmp, blkn - blkn % 16);
1281
1282               if (encrypt)
1283                 _gcry_serpent_avx2_ocb_enc(ctx, outbuf, inbuf, c->u_iv.iv,
1284                                           c->u_ctr.ctr, Ls);
1285               else
1286                 _gcry_serpent_avx2_ocb_dec(ctx, outbuf, inbuf, c->u_iv.iv,
1287                                           c->u_ctr.ctr, Ls);
1288
1289               nblocks -= 16;
1290               outbuf += 16 * sizeof(serpent_block_t);
1291               inbuf  += 16 * sizeof(serpent_block_t);
1292               did_use_avx2 = 1;
1293             }
1294         }
1295
1296       if (did_use_avx2)
1297         {
1298           /* serpent-avx2 assembly code does not use stack */
1299           if (nblocks == 0)
1300             burn_stack_depth = 0;
1301         }
1302
1303       /* Use generic code to handle smaller chunks... */
1304     }
1305 #endif
1306
1307 #ifdef USE_SSE2
1308   {
1309     int did_use_sse2 = 0;
1310     u64 Ls[8];
1311     unsigned int n = 8 - (blkn % 8);
1312     u64 *l;
1313
1314     if (nblocks >= 8)
1315       {
1316         /* Use u64 to store pointers for x32 support (assembly function
1317           * assumes 64-bit pointers). */
1318         Ls[(0 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1319         Ls[(1 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1320         Ls[(2 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1321         Ls[(3 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[2];
1322         Ls[(4 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1323         Ls[(5 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1324         Ls[(6 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1325         l = &Ls[(7 + n) % 8];
1326
1327         /* Process data in 8 block chunks. */
1328         while (nblocks >= 8)
1329           {
1330             /* l_tmp will be used only every 65536-th block. */
1331             blkn += 8;
1332             *l = (uintptr_t)(void *)ocb_get_l(c, l_tmp, blkn - blkn % 8);
1333
1334             if (encrypt)
1335               _gcry_serpent_sse2_ocb_enc(ctx, outbuf, inbuf, c->u_iv.iv,
1336                                           c->u_ctr.ctr, Ls);
1337             else
1338               _gcry_serpent_sse2_ocb_dec(ctx, outbuf, inbuf, c->u_iv.iv,
1339                                           c->u_ctr.ctr, Ls);
1340
1341             nblocks -= 8;
1342             outbuf += 8 * sizeof(serpent_block_t);
1343             inbuf  += 8 * sizeof(serpent_block_t);
1344             did_use_sse2 = 1;
1345           }
1346       }
1347
1348     if (did_use_sse2)
1349       {
1350         /* serpent-sse2 assembly code does not use stack */
1351         if (nblocks == 0)
1352           burn_stack_depth = 0;
1353       }
1354
1355     /* Use generic code to handle smaller chunks... */
1356   }
1357 #endif
1358
1359 #ifdef USE_NEON
1360   if (ctx->use_neon)
1361     {
1362       int did_use_neon = 0;
1363       const void *Ls[8];
1364       unsigned int n = 8 - (blkn % 8);
1365       const void **l;
1366
1367       if (nblocks >= 8)
1368         {
1369           Ls[(0 + n) % 8] = c->u_mode.ocb.L[0];
1370           Ls[(1 + n) % 8] = c->u_mode.ocb.L[1];
1371           Ls[(2 + n) % 8] = c->u_mode.ocb.L[0];
1372           Ls[(3 + n) % 8] = c->u_mode.ocb.L[2];
1373           Ls[(4 + n) % 8] = c->u_mode.ocb.L[0];
1374           Ls[(5 + n) % 8] = c->u_mode.ocb.L[1];
1375           Ls[(6 + n) % 8] = c->u_mode.ocb.L[0];
1376           l = &Ls[(7 + n) % 8];
1377
1378           /* Process data in 8 block chunks. */
1379           while (nblocks >= 8)
1380             {
1381               /* l_tmp will be used only every 65536-th block. */
1382               blkn += 8;
1383               *l = ocb_get_l(c, l_tmp, blkn - blkn % 8);
1384
1385               if (encrypt)
1386                 _gcry_serpent_neon_ocb_enc(ctx, outbuf, inbuf, c->u_iv.iv,
1387                                           c->u_ctr.ctr, Ls);
1388               else
1389                 _gcry_serpent_neon_ocb_dec(ctx, outbuf, inbuf, c->u_iv.iv,
1390                                           c->u_ctr.ctr, Ls);
1391
1392               nblocks -= 8;
1393               outbuf += 8 * sizeof(serpent_block_t);
1394               inbuf  += 8 * sizeof(serpent_block_t);
1395               did_use_neon = 1;
1396             }
1397         }
1398
1399       if (did_use_neon)
1400         {
1401           /* serpent-neon assembly code does not use stack */
1402           if (nblocks == 0)
1403             burn_stack_depth = 0;
1404         }
1405
1406       /* Use generic code to handle smaller chunks... */
1407     }
1408 #endif
1409
1410 #if defined(USE_AVX2) || defined(USE_SSE2) || defined(USE_NEON)
1411   c->u_mode.ocb.data_nblocks = blkn;
1412
1413   wipememory(&l_tmp, sizeof(l_tmp));
1414
1415   if (burn_stack_depth)
1416     _gcry_burn_stack (burn_stack_depth + 4 * sizeof(void *));
1417 #endif
1418
1419   return nblocks;
1420 }
1421
1422 /* Bulk authentication of complete blocks in OCB mode. */
1423 size_t
1424 _gcry_serpent_ocb_auth (gcry_cipher_hd_t c, const void *abuf_arg,
1425                         size_t nblocks)
1426 {
1427 #if defined(USE_AVX2) || defined(USE_SSE2) || defined(USE_NEON)
1428   serpent_context_t *ctx = (void *)&c->context.c;
1429   const unsigned char *abuf = abuf_arg;
1430   unsigned char l_tmp[sizeof(serpent_block_t)];
1431   int burn_stack_depth = 2 * sizeof(serpent_block_t);
1432   u64 blkn = c->u_mode.ocb.aad_nblocks;
1433 #else
1434   (void)c;
1435   (void)abuf_arg;
1436 #endif
1437
1438 #ifdef USE_AVX2
1439   if (ctx->use_avx2)
1440     {
1441       int did_use_avx2 = 0;
1442       u64 Ls[16];
1443       unsigned int n = 16 - (blkn % 16);
1444       u64 *l;
1445       int i;
1446
1447       if (nblocks >= 16)
1448         {
1449           for (i = 0; i < 16; i += 8)
1450             {
1451               /* Use u64 to store pointers for x32 support (assembly function
1452                * assumes 64-bit pointers). */
1453               Ls[(i + 0 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1454               Ls[(i + 1 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1455               Ls[(i + 2 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1456               Ls[(i + 3 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[2];
1457               Ls[(i + 4 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1458               Ls[(i + 5 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1459               Ls[(i + 6 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1460             }
1461
1462           Ls[(7 + n) % 16] = (uintptr_t)(void *)c->u_mode.ocb.L[3];
1463           l = &Ls[(15 + n) % 16];
1464
1465           /* Process data in 16 block chunks. */
1466           while (nblocks >= 16)
1467             {
1468               /* l_tmp will be used only every 65536-th block. */
1469               blkn += 16;
1470               *l = (uintptr_t)(void *)ocb_get_l(c, l_tmp, blkn - blkn % 16);
1471
1472               _gcry_serpent_avx2_ocb_auth(ctx, abuf, c->u_mode.ocb.aad_offset,
1473                                           c->u_mode.ocb.aad_sum, Ls);
1474
1475               nblocks -= 16;
1476               abuf += 16 * sizeof(serpent_block_t);
1477               did_use_avx2 = 1;
1478             }
1479         }
1480
1481       if (did_use_avx2)
1482         {
1483           /* serpent-avx2 assembly code does not use stack */
1484           if (nblocks == 0)
1485             burn_stack_depth = 0;
1486         }
1487
1488       /* Use generic code to handle smaller chunks... */
1489     }
1490 #endif
1491
1492 #ifdef USE_SSE2
1493   {
1494     int did_use_sse2 = 0;
1495     u64 Ls[8];
1496     unsigned int n = 8 - (blkn % 8);
1497     u64 *l;
1498
1499     if (nblocks >= 8)
1500       {
1501         /* Use u64 to store pointers for x32 support (assembly function
1502         * assumes 64-bit pointers). */
1503         Ls[(0 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1504         Ls[(1 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1505         Ls[(2 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1506         Ls[(3 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[2];
1507         Ls[(4 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1508         Ls[(5 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[1];
1509         Ls[(6 + n) % 8] = (uintptr_t)(void *)c->u_mode.ocb.L[0];
1510         l = &Ls[(7 + n) % 8];
1511
1512         /* Process data in 8 block chunks. */
1513         while (nblocks >= 8)
1514           {
1515             /* l_tmp will be used only every 65536-th block. */
1516             blkn += 8;
1517             *l = (uintptr_t)(void *)ocb_get_l(c, l_tmp, blkn - blkn % 8);
1518
1519             _gcry_serpent_sse2_ocb_auth(ctx, abuf, c->u_mode.ocb.aad_offset,
1520                                         c->u_mode.ocb.aad_sum, Ls);
1521
1522             nblocks -= 8;
1523             abuf += 8 * sizeof(serpent_block_t);
1524             did_use_sse2 = 1;
1525           }
1526       }
1527
1528     if (did_use_sse2)
1529       {
1530         /* serpent-avx2 assembly code does not use stack */
1531         if (nblocks == 0)
1532           burn_stack_depth = 0;
1533       }
1534
1535     /* Use generic code to handle smaller chunks... */
1536   }
1537 #endif
1538
1539 #ifdef USE_NEON
1540   if (ctx->use_neon)
1541     {
1542       int did_use_neon = 0;
1543       const void *Ls[8];
1544       unsigned int n = 8 - (blkn % 8);
1545       const void **l;
1546
1547       if (nblocks >= 8)
1548         {
1549           Ls[(0 + n) % 8] = c->u_mode.ocb.L[0];
1550           Ls[(1 + n) % 8] = c->u_mode.ocb.L[1];
1551           Ls[(2 + n) % 8] = c->u_mode.ocb.L[0];
1552           Ls[(3 + n) % 8] = c->u_mode.ocb.L[2];
1553           Ls[(4 + n) % 8] = c->u_mode.ocb.L[0];
1554           Ls[(5 + n) % 8] = c->u_mode.ocb.L[1];
1555           Ls[(6 + n) % 8] = c->u_mode.ocb.L[0];
1556           l = &Ls[(7 + n) % 8];
1557
1558           /* Process data in 8 block chunks. */
1559           while (nblocks >= 8)
1560             {
1561               /* l_tmp will be used only every 65536-th block. */
1562               blkn += 8;
1563               *l = ocb_get_l(c, l_tmp, blkn - blkn % 8);
1564
1565               _gcry_serpent_neon_ocb_auth(ctx, abuf, c->u_mode.ocb.aad_offset,
1566                                           c->u_mode.ocb.aad_sum, Ls);
1567
1568               nblocks -= 8;
1569               abuf += 8 * sizeof(serpent_block_t);
1570               did_use_neon = 1;
1571             }
1572         }
1573
1574       if (did_use_neon)
1575         {
1576           /* serpent-neon assembly code does not use stack */
1577           if (nblocks == 0)
1578             burn_stack_depth = 0;
1579         }
1580
1581       /* Use generic code to handle smaller chunks... */
1582     }
1583 #endif
1584
1585 #if defined(USE_AVX2) || defined(USE_SSE2) || defined(USE_NEON)
1586   c->u_mode.ocb.aad_nblocks = blkn;
1587
1588   wipememory(&l_tmp, sizeof(l_tmp));
1589
1590   if (burn_stack_depth)
1591     _gcry_burn_stack (burn_stack_depth + 4 * sizeof(void *));
1592 #endif
1593
1594   return nblocks;
1595 }
1596
1597 \f
1598
1599 /* Run the self-tests for SERPENT-CTR-128, tests IV increment of bulk CTR
1600    encryption.  Returns NULL on success. */
1601 static const char*
1602 selftest_ctr_128 (void)
1603 {
1604   const int nblocks = 16+8+1;
1605   const int blocksize = sizeof(serpent_block_t);
1606   const int context_size = sizeof(serpent_context_t);
1607
1608   return _gcry_selftest_helper_ctr("SERPENT", &serpent_setkey,
1609            &serpent_encrypt, &_gcry_serpent_ctr_enc, nblocks, blocksize,
1610            context_size);
1611 }
1612
1613
1614 /* Run the self-tests for SERPENT-CBC-128, tests bulk CBC decryption.
1615    Returns NULL on success. */
1616 static const char*
1617 selftest_cbc_128 (void)
1618 {
1619   const int nblocks = 16+8+2;
1620   const int blocksize = sizeof(serpent_block_t);
1621   const int context_size = sizeof(serpent_context_t);
1622
1623   return _gcry_selftest_helper_cbc("SERPENT", &serpent_setkey,
1624            &serpent_encrypt, &_gcry_serpent_cbc_dec, nblocks, blocksize,
1625            context_size);
1626 }
1627
1628
1629 /* Run the self-tests for SERPENT-CBC-128, tests bulk CBC decryption.
1630    Returns NULL on success. */
1631 static const char*
1632 selftest_cfb_128 (void)
1633 {
1634   const int nblocks = 16+8+2;
1635   const int blocksize = sizeof(serpent_block_t);
1636   const int context_size = sizeof(serpent_context_t);
1637
1638   return _gcry_selftest_helper_cfb("SERPENT", &serpent_setkey,
1639            &serpent_encrypt, &_gcry_serpent_cfb_dec, nblocks, blocksize,
1640            context_size);
1641 }
1642
1643
1644 /* Serpent test.  */
1645
1646 static const char *
1647 serpent_test (void)
1648 {
1649   serpent_context_t context;
1650   unsigned char scratch[16];
1651   unsigned int i;
1652   const char *r;
1653
1654   static struct test
1655   {
1656     int key_length;
1657     unsigned char key[32];
1658     unsigned char text_plain[16];
1659     unsigned char text_cipher[16];
1660   } test_data[] =
1661     {
1662       {
1663         16,
1664         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00",
1665         "\xD2\x9D\x57\x6F\xCE\xA3\xA3\xA7\xED\x90\x99\xF2\x92\x73\xD7\x8E",
1666         "\xB2\x28\x8B\x96\x8A\xE8\xB0\x86\x48\xD1\xCE\x96\x06\xFD\x99\x2D"
1667       },
1668       {
1669         24,
1670         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
1671         "\x00\x00\x00\x00\x00\x00\x00\x00",
1672         "\xD2\x9D\x57\x6F\xCE\xAB\xA3\xA7\xED\x98\x99\xF2\x92\x7B\xD7\x8E",
1673         "\x13\x0E\x35\x3E\x10\x37\xC2\x24\x05\xE8\xFA\xEF\xB2\xC3\xC3\xE9"
1674       },
1675       {
1676         32,
1677         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
1678         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00",
1679         "\xD0\x95\x57\x6F\xCE\xA3\xE3\xA7\xED\x98\xD9\xF2\x90\x73\xD7\x8E",
1680         "\xB9\x0E\xE5\x86\x2D\xE6\x91\x68\xF2\xBD\xD5\x12\x5B\x45\x47\x2B"
1681       },
1682       {
1683         32,
1684         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
1685         "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00",
1686         "\x00\x00\x00\x00\x01\x00\x00\x00\x02\x00\x00\x00\x03\x00\x00\x00",
1687         "\x20\x61\xA4\x27\x82\xBD\x52\xEC\x69\x1E\xC3\x83\xB0\x3B\xA7\x7C"
1688       },
1689       {
1690         0
1691       },
1692     };
1693
1694   for (i = 0; test_data[i].key_length; i++)
1695     {
1696       serpent_setkey_internal (&context, test_data[i].key,
1697                                test_data[i].key_length);
1698       serpent_encrypt_internal (&context, test_data[i].text_plain, scratch);
1699
1700       if (memcmp (scratch, test_data[i].text_cipher, sizeof (serpent_block_t)))
1701         switch (test_data[i].key_length)
1702           {
1703           case 16:
1704             return "Serpent-128 test encryption failed.";
1705           case  24:
1706             return "Serpent-192 test encryption failed.";
1707           case 32:
1708             return "Serpent-256 test encryption failed.";
1709           }
1710
1711     serpent_decrypt_internal (&context, test_data[i].text_cipher, scratch);
1712     if (memcmp (scratch, test_data[i].text_plain, sizeof (serpent_block_t)))
1713       switch (test_data[i].key_length)
1714         {
1715         case 16:
1716           return "Serpent-128 test decryption failed.";
1717         case  24:
1718           return "Serpent-192 test decryption failed.";
1719         case 32:
1720           return "Serpent-256 test decryption failed.";
1721         }
1722     }
1723
1724   if ( (r = selftest_ctr_128 ()) )
1725     return r;
1726
1727   if ( (r = selftest_cbc_128 ()) )
1728     return r;
1729
1730   if ( (r = selftest_cfb_128 ()) )
1731     return r;
1732
1733   return NULL;
1734 }
1735
1736 \f
1737
1738 /* "SERPENT" is an alias for "SERPENT128".  */
1739 static const char *cipher_spec_serpent128_aliases[] =
1740   {
1741     "SERPENT",
1742     NULL
1743   };
1744
1745 gcry_cipher_spec_t _gcry_cipher_spec_serpent128 =
1746   {
1747     GCRY_CIPHER_SERPENT128, {0, 0},
1748     "SERPENT128", cipher_spec_serpent128_aliases, NULL, 16, 128,
1749     sizeof (serpent_context_t),
1750     serpent_setkey, serpent_encrypt, serpent_decrypt
1751   };
1752
1753 gcry_cipher_spec_t _gcry_cipher_spec_serpent192 =
1754   {
1755     GCRY_CIPHER_SERPENT192, {0, 0},
1756     "SERPENT192", NULL, NULL, 16, 192,
1757     sizeof (serpent_context_t),
1758     serpent_setkey, serpent_encrypt, serpent_decrypt
1759   };
1760
1761 gcry_cipher_spec_t _gcry_cipher_spec_serpent256 =
1762   {
1763     GCRY_CIPHER_SERPENT256, {0, 0},
1764     "SERPENT256", NULL, NULL, 16, 256,
1765     sizeof (serpent_context_t),
1766     serpent_setkey, serpent_encrypt, serpent_decrypt
1767   };