Coverage Report

Created: 2024-11-21 07:03

/src/libgcrypt/cipher/mceliece6688128f.c
Line
Count
Source (jump to first uncovered line)
1
/* mceliece6688128f.c - Classic McEliece for libgcrypt
2
 * Copyright (C) 2023-2024 Simon Josefsson <simon@josefsson.org>
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, see <https://www.gnu.org/licenses/>.
18
 * SPDX-License-Identifier: LGPL-2.1-or-later
19
 *
20
 */
21
22
/* This file is extracted from libmceliece. */
23
24
/*
25
 * libmceliece is hereby placed into the public domain.
26
 *
27
 * [SPDX-License-Identifier](https://spdx.dev/ids/):
28
 * [LicenseRef-PD-hp](https://cr.yp.to/spdx.html)
29
 * OR
30
 * [CC0-1.0](https://spdx.org/licenses/CC0-1.0.html)
31
 * OR
32
 * [0BSD](https://spdx.org/licenses/0BSD.html)
33
 * OR
34
 * [MIT-0](https://spdx.org/licenses/MIT-0.html)
35
 * OR
36
 * [MIT](https://spdx.org/licenses/MIT.html)
37
 *
38
 * libmceliece is based on the official Classic McEliece software, which
39
 * was written by Tung Chou. See the following papers for the major
40
 * algorithms used for speed inside that software:
41
 *
42
 * * Daniel J. Bernstein, Tung Chou, Peter Schwabe. "McBits: fast
43
 *   constant-time code-based cryptography." CHES 2013.
44
 *   [https://tungchou.github.io/papers/mcbits.pdf](https://tungchou.github.io/papers/mcbits.pdf)
45
 *
46
 * * Tung Chou. "McBits revisited." CHES 2017.
47
 *   [https://tungchou.github.io/papers/mcbits_revisited.pdf](https://tungchou.github.io/papers/mcbits_revisited.pdf)
48
 *
49
 * The official Classic McEliece software includes `ref`, `vec`, `sse`, and
50
 * `avx` implementations; libmceliece includes only `vec` and `avx`.
51
 *
52
 * The following components of libmceliece are from Daniel J. Bernstein:
53
 *
54
 * * Small [changes](download.html#changelog)
55
 *   for namespacing, portability, etc.
56
 *
57
 * * Software to compute control bits (also used in the official software).
58
 *   See the following paper: Daniel J. Bernstein. "Verified fast formulas
59
 *   for control bits for permutation networks." 2020.
60
 *   [https://cr.yp.to/papers.html#controlbits](https://cr.yp.to/papers.html#controlbits)
61
 *
62
 * * `crypto_sort/int32`. See [https://sorting.cr.yp.to](https://sorting.cr.yp.to).
63
 *
64
 * * Infrastructure to build a library with automatic run-time selection of
65
 *   implementations based on the run-time CPU and a database of
66
 *   benchmarks. This infrastructure was introduced in
67
 *   [`lib25519`](https://lib25519.cr.yp.to), with some extensions and
68
 *   adaptations in libmceliece.
69
 *
70
 * * Various software for tests and benchmarks. This is based on
71
 *   public-domain code in the SUPERCOP benchmarking framework.
72
 *
73
 * This file is generated by mceliece6688128f.sh from these files:
74
 *
75
 * libmceliece-20230612/include-build/crypto_declassify.h
76
 * libmceliece-20230612/crypto_kem/6688128f/vec/params.h
77
 * libmceliece-20230612/inttypes/crypto_intN.h
78
 * libmceliece-20230612/inttypes/crypto_intN.h
79
 * libmceliece-20230612/inttypes/crypto_intN.h
80
 * libmceliece-20230612/inttypes/crypto_uintN.h
81
 * libmceliece-20230612/inttypes/crypto_uintN.h
82
 * libmceliece-20230612/inttypes/crypto_uintN.h
83
 * libmceliece-20230612/crypto_kem/6688128f/vec/vec.h
84
 * libmceliece-20230612/crypto_kem/6688128f/vec/benes.h
85
 * libmceliece-20230612/crypto_kem/6688128f/vec/bm.h
86
 * libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.h
87
 * libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.h
88
 * libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.h
89
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_consts.h
90
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft.h
91
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_powers.h
92
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_2x.h
93
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_4x.h
94
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.h
95
 * libmceliece-20230612/crypto_kem/6688128f/vec/gf.h
96
 * libmceliece-20230612/crypto_kem/6688128f/vec/hash.h
97
 * libmceliece-20230612/crypto_kem/6688128f/vec/int32_sort.h
98
 * libmceliece-20230612/crypto_kem/6688128f/vec/operations.h
99
 * libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.h
100
 * libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.h
101
 * libmceliece-20230612/crypto_kem/6688128f/vec/transpose.h
102
 * libmceliece-20230612/crypto_kem/6688128f/vec/uint16_sort.h
103
 * libmceliece-20230612/crypto_kem/6688128f/vec/uint64_sort.h
104
 * libmceliece-20230612/crypto_kem/6688128f/vec/util.h
105
 * libmceliece-20230612/crypto_kem/6688128f/vec/benes.c
106
 * libmceliece-20230612/crypto_kem/6688128f/vec/bm.c
107
 * libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.c
108
 * libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.c
109
 * libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.c
110
 * libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_consts.c
111
 * libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_powers.c
112
 * libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_2x.c
113
 * libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_4x.c
114
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft.c
115
 * libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.c
116
 * libmceliece-20230612/crypto_kem/6688128f/vec/gf.c
117
 * libmceliece-20230612/crypto_kem/6688128f/vec/kem_dec.c
118
 * libmceliece-20230612/crypto_kem/6688128f/vec/kem_enc.c
119
 * libmceliece-20230612/crypto_kem/6688128f/vec/kem_keypair.c
120
 * libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.c
121
 * libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.c
122
 * libmceliece-20230612/crypto_kem/6688128f/vec/vec.c
123
 * libmceliece-20230612/crypto_kem/6688128f/vec/wrap_dec.c
124
 * libmceliece-20230612/crypto_kem/6688128f/vec/wrap_enc.c
125
 * libmceliece-20230612/crypto_kem/6688128f/vec/wrap_keypair.c
126
 *
127
 */
128
129
#ifdef HAVE_CONFIG_H
130
#include <config.h>
131
#endif
132
133
#include "g10lib.h"
134
#include "mceliece6688128f.h"
135
136
#define int8 crypto_int8
137
#define uint8 crypto_uint8
138
0
#define int16 crypto_int16
139
#define uint16 crypto_uint16
140
0
#define int32 crypto_int32
141
#define uint32 crypto_uint32
142
#define int64 crypto_int64
143
#define uint64 crypto_uint64
144
145
static void
146
randombytes (uint8_t *out, size_t outlen)
147
0
{
148
0
  _gcry_randomize (out, outlen, GCRY_STRONG_RANDOM);
149
0
}
150
151
/* from libmceliece-20230612/include-build/crypto_declassify.h */
152
#ifndef crypto_declassify_h
153
#define crypto_declassify_h
154
155
0
static void crypto_declassify(void *crypto_declassify_v,long long crypto_declassify_vlen) {
156
0
  (void) crypto_declassify_v;
157
0
  (void) crypto_declassify_vlen;
158
0
}
159
160
#endif
161
162
/* from libmceliece-20230612/crypto_kem/6688128f/vec/params.h */
163
#ifndef PARAMS_H
164
#define PARAMS_H
165
166
0
#define GFBITS 13
167
0
#define SYS_N 6688
168
0
#define SYS_T 128
169
170
0
#define COND_BYTES ((1 << (GFBITS-4))*(2*GFBITS - 1))
171
0
#define IRR_BYTES (SYS_T * 2)
172
173
0
#define PK_NROWS (SYS_T*GFBITS)
174
0
#define PK_NCOLS (SYS_N - PK_NROWS)
175
0
#define PK_ROW_BYTES ((PK_NCOLS + 7)/8)
176
177
0
#define SYND_BYTES ((PK_NROWS + 7)/8)
178
179
0
#define GFMASK ((1 << GFBITS) - 1)
180
181
#endif
182
183
184
/* from libmceliece-20230612/inttypes/crypto_intN.h */
185
#ifndef crypto_int64_h
186
#define crypto_int64_h
187
188
#define crypto_int64 int64_t
189
190
GCC_ATTR_UNUSED
191
static crypto_int64 crypto_int64_negative_mask(crypto_int64 crypto_int64_x)
192
0
{
193
0
  return crypto_int64_x >> (64-1);
194
0
}
195
196
GCC_ATTR_UNUSED
197
static crypto_int64 crypto_int64_nonzero_mask(crypto_int64 crypto_int64_x)
198
0
{
199
0
  return crypto_int64_negative_mask(crypto_int64_x) | crypto_int64_negative_mask(-crypto_int64_x);
200
0
}
201
202
GCC_ATTR_UNUSED
203
static crypto_int64 crypto_int64_zero_mask(crypto_int64 crypto_int64_x)
204
0
{
205
0
  return ~crypto_int64_nonzero_mask(crypto_int64_x);
206
0
}
207
208
GCC_ATTR_UNUSED
209
static crypto_int64 crypto_int64_positive_mask(crypto_int64 crypto_int64_x)
210
0
{
211
0
  crypto_int64 crypto_int64_z = -crypto_int64_x;
212
0
  crypto_int64_z ^= crypto_int64_x & crypto_int64_z;
213
0
  return crypto_int64_negative_mask(crypto_int64_z);
214
0
}
215
216
GCC_ATTR_UNUSED
217
static crypto_int64 crypto_int64_unequal_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
218
0
{
219
0
  crypto_int64 crypto_int64_xy = crypto_int64_x ^ crypto_int64_y;
220
0
  return crypto_int64_nonzero_mask(crypto_int64_xy);
221
0
}
222
223
GCC_ATTR_UNUSED
224
static crypto_int64 crypto_int64_equal_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
225
0
{
226
0
  return ~crypto_int64_unequal_mask(crypto_int64_x,crypto_int64_y);
227
0
}
228
229
GCC_ATTR_UNUSED
230
static crypto_int64 crypto_int64_smaller_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
231
0
{
232
0
  crypto_int64 crypto_int64_xy = crypto_int64_x ^ crypto_int64_y;
233
0
  crypto_int64 crypto_int64_z = crypto_int64_x - crypto_int64_y;
234
0
  crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_x);
235
0
  return crypto_int64_negative_mask(crypto_int64_z);
236
0
}
237
238
GCC_ATTR_UNUSED
239
static crypto_int64 crypto_int64_min(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
240
0
{
241
0
  crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
242
0
  crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
243
0
  crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
244
0
  crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
245
0
  crypto_int64_z &= crypto_int64_xy;
246
0
  return crypto_int64_x ^ crypto_int64_z;
247
0
}
248
249
GCC_ATTR_UNUSED
250
static crypto_int64 crypto_int64_max(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
251
0
{
252
0
  crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
253
0
  crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
254
0
  crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
255
0
  crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
256
0
  crypto_int64_z &= crypto_int64_xy;
257
0
  return crypto_int64_y ^ crypto_int64_z;
258
0
}
259
260
GCC_ATTR_UNUSED
261
static void crypto_int64_minmax(crypto_int64 *crypto_int64_a,crypto_int64 *crypto_int64_b)
262
0
{
263
0
  crypto_int64 crypto_int64_x = *crypto_int64_a;
264
0
  crypto_int64 crypto_int64_y = *crypto_int64_b;
265
0
  crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
266
0
  crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
267
0
  crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
268
0
  crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
269
0
  crypto_int64_z &= crypto_int64_xy;
270
0
  *crypto_int64_a = crypto_int64_x ^ crypto_int64_z;
271
0
  *crypto_int64_b = crypto_int64_y ^ crypto_int64_z;
272
0
}
273
274
#endif
275
276
/* from libmceliece-20230612/inttypes/crypto_intN.h */
277
#ifndef crypto_int16_h
278
#define crypto_int16_h
279
280
0
#define crypto_int16 int16_t
281
282
GCC_ATTR_UNUSED
283
static crypto_int16 crypto_int16_negative_mask(crypto_int16 crypto_int16_x)
284
0
{
285
0
  return crypto_int16_x >> (16-1);
286
0
}
287
288
GCC_ATTR_UNUSED
289
static crypto_int16 crypto_int16_nonzero_mask(crypto_int16 crypto_int16_x)
290
0
{
291
0
  return crypto_int16_negative_mask(crypto_int16_x) | crypto_int16_negative_mask(-crypto_int16_x);
292
0
}
293
294
GCC_ATTR_UNUSED
295
static crypto_int16 crypto_int16_zero_mask(crypto_int16 crypto_int16_x)
296
0
{
297
0
  return ~crypto_int16_nonzero_mask(crypto_int16_x);
298
0
}
299
300
GCC_ATTR_UNUSED
301
static crypto_int16 crypto_int16_positive_mask(crypto_int16 crypto_int16_x)
302
0
{
303
0
  crypto_int16 crypto_int16_z = -crypto_int16_x;
304
0
  crypto_int16_z ^= crypto_int16_x & crypto_int16_z;
305
0
  return crypto_int16_negative_mask(crypto_int16_z);
306
0
}
307
308
GCC_ATTR_UNUSED
309
static crypto_int16 crypto_int16_unequal_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
310
0
{
311
0
  crypto_int16 crypto_int16_xy = crypto_int16_x ^ crypto_int16_y;
312
0
  return crypto_int16_nonzero_mask(crypto_int16_xy);
313
0
}
314
315
GCC_ATTR_UNUSED
316
static crypto_int16 crypto_int16_equal_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
317
0
{
318
0
  return ~crypto_int16_unequal_mask(crypto_int16_x,crypto_int16_y);
319
0
}
320
321
GCC_ATTR_UNUSED
322
static crypto_int16 crypto_int16_smaller_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
323
0
{
324
0
  crypto_int16 crypto_int16_xy = crypto_int16_x ^ crypto_int16_y;
325
0
  crypto_int16 crypto_int16_z = crypto_int16_x - crypto_int16_y;
326
0
  crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_x);
327
0
  return crypto_int16_negative_mask(crypto_int16_z);
328
0
}
329
330
GCC_ATTR_UNUSED
331
static crypto_int16 crypto_int16_min(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
332
0
{
333
0
  crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
334
0
  crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
335
0
  crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
336
0
  crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
337
0
  crypto_int16_z &= crypto_int16_xy;
338
0
  return crypto_int16_x ^ crypto_int16_z;
339
0
}
340
341
GCC_ATTR_UNUSED
342
static crypto_int16 crypto_int16_max(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
343
0
{
344
0
  crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
345
0
  crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
346
0
  crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
347
0
  crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
348
0
  crypto_int16_z &= crypto_int16_xy;
349
0
  return crypto_int16_y ^ crypto_int16_z;
350
0
}
351
352
GCC_ATTR_UNUSED
353
static void crypto_int16_minmax(crypto_int16 *crypto_int16_a,crypto_int16 *crypto_int16_b)
354
0
{
355
0
  crypto_int16 crypto_int16_x = *crypto_int16_a;
356
0
  crypto_int16 crypto_int16_y = *crypto_int16_b;
357
0
  crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
358
0
  crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
359
0
  crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
360
0
  crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
361
0
  crypto_int16_z &= crypto_int16_xy;
362
0
  *crypto_int16_a = crypto_int16_x ^ crypto_int16_z;
363
0
  *crypto_int16_b = crypto_int16_y ^ crypto_int16_z;
364
0
}
365
366
#endif
367
368
/* from libmceliece-20230612/inttypes/crypto_intN.h */
369
#ifndef crypto_int32_h
370
#define crypto_int32_h
371
372
0
#define crypto_int32 int32_t
373
374
GCC_ATTR_UNUSED
375
static crypto_int32 crypto_int32_negative_mask(crypto_int32 crypto_int32_x)
376
0
{
377
0
  return crypto_int32_x >> (32-1);
378
0
}
379
380
GCC_ATTR_UNUSED
381
static crypto_int32 crypto_int32_nonzero_mask(crypto_int32 crypto_int32_x)
382
0
{
383
0
  return crypto_int32_negative_mask(crypto_int32_x) | crypto_int32_negative_mask(-crypto_int32_x);
384
0
}
385
386
GCC_ATTR_UNUSED
387
static crypto_int32 crypto_int32_zero_mask(crypto_int32 crypto_int32_x)
388
0
{
389
0
  return ~crypto_int32_nonzero_mask(crypto_int32_x);
390
0
}
391
392
GCC_ATTR_UNUSED
393
static crypto_int32 crypto_int32_positive_mask(crypto_int32 crypto_int32_x)
394
0
{
395
0
  crypto_int32 crypto_int32_z = -crypto_int32_x;
396
0
  crypto_int32_z ^= crypto_int32_x & crypto_int32_z;
397
0
  return crypto_int32_negative_mask(crypto_int32_z);
398
0
}
399
400
GCC_ATTR_UNUSED
401
static crypto_int32 crypto_int32_unequal_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
402
0
{
403
0
  crypto_int32 crypto_int32_xy = crypto_int32_x ^ crypto_int32_y;
404
0
  return crypto_int32_nonzero_mask(crypto_int32_xy);
405
0
}
406
407
GCC_ATTR_UNUSED
408
static crypto_int32 crypto_int32_equal_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
409
0
{
410
0
  return ~crypto_int32_unequal_mask(crypto_int32_x,crypto_int32_y);
411
0
}
412
413
GCC_ATTR_UNUSED
414
static crypto_int32 crypto_int32_smaller_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
415
0
{
416
0
  crypto_int32 crypto_int32_xy = crypto_int32_x ^ crypto_int32_y;
417
0
  crypto_int32 crypto_int32_z = crypto_int32_x - crypto_int32_y;
418
0
  crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_x);
419
0
  return crypto_int32_negative_mask(crypto_int32_z);
420
0
}
421
422
GCC_ATTR_UNUSED
423
static crypto_int32 crypto_int32_min(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
424
0
{
425
0
  crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
426
0
  crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
427
0
  crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
428
0
  crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
429
0
  crypto_int32_z &= crypto_int32_xy;
430
0
  return crypto_int32_x ^ crypto_int32_z;
431
0
}
432
433
GCC_ATTR_UNUSED
434
static crypto_int32 crypto_int32_max(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
435
0
{
436
0
  crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
437
0
  crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
438
0
  crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
439
0
  crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
440
0
  crypto_int32_z &= crypto_int32_xy;
441
0
  return crypto_int32_y ^ crypto_int32_z;
442
0
}
443
444
GCC_ATTR_UNUSED
445
static void crypto_int32_minmax(crypto_int32 *crypto_int32_a,crypto_int32 *crypto_int32_b)
446
0
{
447
0
  crypto_int32 crypto_int32_x = *crypto_int32_a;
448
0
  crypto_int32 crypto_int32_y = *crypto_int32_b;
449
0
  crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
450
0
  crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
451
0
  crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
452
0
  crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
453
0
  crypto_int32_z &= crypto_int32_xy;
454
0
  *crypto_int32_a = crypto_int32_x ^ crypto_int32_z;
455
0
  *crypto_int32_b = crypto_int32_y ^ crypto_int32_z;
456
0
}
457
458
#endif
459
460
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
461
#ifndef crypto_uint64_h
462
#define crypto_uint64_h
463
464
0
#define crypto_uint64 uint64_t
465
#define crypto_uint64_signed int64_t
466
467
GCC_ATTR_UNUSED
468
static crypto_uint64_signed crypto_uint64_signed_negative_mask(crypto_uint64_signed crypto_uint64_signed_x)
469
0
{
470
0
  return crypto_uint64_signed_x >> (64-1);
471
0
}
472
473
GCC_ATTR_UNUSED
474
static crypto_uint64 crypto_uint64_nonzero_mask(crypto_uint64 crypto_uint64_x)
475
0
{
476
0
  return crypto_uint64_signed_negative_mask(crypto_uint64_x) | crypto_uint64_signed_negative_mask(-crypto_uint64_x);
477
0
}
478
479
GCC_ATTR_UNUSED
480
static crypto_uint64 crypto_uint64_zero_mask(crypto_uint64 crypto_uint64_x)
481
0
{
482
0
  return ~crypto_uint64_nonzero_mask(crypto_uint64_x);
483
0
}
484
485
GCC_ATTR_UNUSED
486
static crypto_uint64 crypto_uint64_unequal_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
487
0
{
488
0
  crypto_uint64 crypto_uint64_xy = crypto_uint64_x ^ crypto_uint64_y;
489
0
  return crypto_uint64_nonzero_mask(crypto_uint64_xy);
490
0
}
491
492
GCC_ATTR_UNUSED
493
static crypto_uint64 crypto_uint64_equal_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
494
0
{
495
0
  return ~crypto_uint64_unequal_mask(crypto_uint64_x,crypto_uint64_y);
496
0
}
497
498
GCC_ATTR_UNUSED
499
static crypto_uint64 crypto_uint64_smaller_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
500
0
{
501
0
  crypto_uint64 crypto_uint64_xy = crypto_uint64_x ^ crypto_uint64_y;
502
0
  crypto_uint64 crypto_uint64_z = crypto_uint64_x - crypto_uint64_y;
503
0
  crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_x ^ (((crypto_uint64) 1) << (64-1)));
504
0
  return crypto_uint64_signed_negative_mask(crypto_uint64_z);
505
0
}
506
507
GCC_ATTR_UNUSED
508
static crypto_uint64 crypto_uint64_min(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
509
0
{
510
0
  crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
511
0
  crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
512
0
  crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
513
0
  crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
514
0
  crypto_uint64_z &= crypto_uint64_xy;
515
0
  return crypto_uint64_x ^ crypto_uint64_z;
516
0
}
517
518
GCC_ATTR_UNUSED
519
static crypto_uint64 crypto_uint64_max(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
520
0
{
521
0
  crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
522
0
  crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
523
0
  crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
524
0
  crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
525
0
  crypto_uint64_z &= crypto_uint64_xy;
526
0
  return crypto_uint64_y ^ crypto_uint64_z;
527
0
}
528
529
GCC_ATTR_UNUSED
530
static void crypto_uint64_minmax(crypto_uint64 *crypto_uint64_a,crypto_uint64 *crypto_uint64_b)
531
0
{
532
0
  crypto_uint64 crypto_uint64_x = *crypto_uint64_a;
533
0
  crypto_uint64 crypto_uint64_y = *crypto_uint64_b;
534
0
  crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
535
0
  crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
536
0
  crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
537
0
  crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
538
0
  crypto_uint64_z &= crypto_uint64_xy;
539
0
  *crypto_uint64_a = crypto_uint64_x ^ crypto_uint64_z;
540
0
  *crypto_uint64_b = crypto_uint64_y ^ crypto_uint64_z;
541
0
}
542
543
#endif
544
545
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
546
#ifndef crypto_uint16_h
547
#define crypto_uint16_h
548
549
0
#define crypto_uint16 uint16_t
550
#define crypto_uint16_signed int16_t
551
552
GCC_ATTR_UNUSED
553
static crypto_uint16_signed crypto_uint16_signed_negative_mask(crypto_uint16_signed crypto_uint16_signed_x)
554
0
{
555
0
  return crypto_uint16_signed_x >> (16-1);
556
0
}
557
558
GCC_ATTR_UNUSED
559
static crypto_uint16 crypto_uint16_nonzero_mask(crypto_uint16 crypto_uint16_x)
560
0
{
561
0
  return crypto_uint16_signed_negative_mask(crypto_uint16_x) | crypto_uint16_signed_negative_mask(-crypto_uint16_x);
562
0
}
563
564
GCC_ATTR_UNUSED
565
static crypto_uint16 crypto_uint16_zero_mask(crypto_uint16 crypto_uint16_x)
566
0
{
567
0
  return ~crypto_uint16_nonzero_mask(crypto_uint16_x);
568
0
}
569
570
GCC_ATTR_UNUSED
571
static crypto_uint16 crypto_uint16_unequal_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
572
0
{
573
0
  crypto_uint16 crypto_uint16_xy = crypto_uint16_x ^ crypto_uint16_y;
574
0
  return crypto_uint16_nonzero_mask(crypto_uint16_xy);
575
0
}
576
577
GCC_ATTR_UNUSED
578
static crypto_uint16 crypto_uint16_equal_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
579
0
{
580
0
  return ~crypto_uint16_unequal_mask(crypto_uint16_x,crypto_uint16_y);
581
0
}
582
583
GCC_ATTR_UNUSED
584
static crypto_uint16 crypto_uint16_smaller_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
585
0
{
586
0
  crypto_uint16 crypto_uint16_xy = crypto_uint16_x ^ crypto_uint16_y;
587
0
  crypto_uint16 crypto_uint16_z = crypto_uint16_x - crypto_uint16_y;
588
0
  crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_x ^ (((crypto_uint16) 1) << (16-1)));
589
0
  return crypto_uint16_signed_negative_mask(crypto_uint16_z);
590
0
}
591
592
GCC_ATTR_UNUSED
593
static crypto_uint16 crypto_uint16_min(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
594
0
{
595
0
  crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
596
0
  crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
597
0
  crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
598
0
  crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
599
0
  crypto_uint16_z &= crypto_uint16_xy;
600
0
  return crypto_uint16_x ^ crypto_uint16_z;
601
0
}
602
603
GCC_ATTR_UNUSED
604
static crypto_uint16 crypto_uint16_max(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
605
0
{
606
0
  crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
607
0
  crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
608
0
  crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
609
0
  crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
610
0
  crypto_uint16_z &= crypto_uint16_xy;
611
0
  return crypto_uint16_y ^ crypto_uint16_z;
612
0
}
613
614
GCC_ATTR_UNUSED
615
static void crypto_uint16_minmax(crypto_uint16 *crypto_uint16_a,crypto_uint16 *crypto_uint16_b)
616
0
{
617
0
  crypto_uint16 crypto_uint16_x = *crypto_uint16_a;
618
0
  crypto_uint16 crypto_uint16_y = *crypto_uint16_b;
619
0
  crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
620
0
  crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
621
0
  crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
622
0
  crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
623
0
  crypto_uint16_z &= crypto_uint16_xy;
624
0
  *crypto_uint16_a = crypto_uint16_x ^ crypto_uint16_z;
625
0
  *crypto_uint16_b = crypto_uint16_y ^ crypto_uint16_z;
626
0
}
627
628
#endif
629
630
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
631
#ifndef crypto_uint32_h
632
#define crypto_uint32_h
633
634
0
#define crypto_uint32 uint32_t
635
#define crypto_uint32_signed int32_t
636
637
GCC_ATTR_UNUSED
638
static crypto_uint32_signed crypto_uint32_signed_negative_mask(crypto_uint32_signed crypto_uint32_signed_x)
639
0
{
640
0
  return crypto_uint32_signed_x >> (32-1);
641
0
}
642
643
GCC_ATTR_UNUSED
644
static crypto_uint32 crypto_uint32_nonzero_mask(crypto_uint32 crypto_uint32_x)
645
0
{
646
0
  return crypto_uint32_signed_negative_mask(crypto_uint32_x) | crypto_uint32_signed_negative_mask(-crypto_uint32_x);
647
0
}
648
649
GCC_ATTR_UNUSED
650
static crypto_uint32 crypto_uint32_zero_mask(crypto_uint32 crypto_uint32_x)
651
0
{
652
0
  return ~crypto_uint32_nonzero_mask(crypto_uint32_x);
653
0
}
654
655
GCC_ATTR_UNUSED
656
static crypto_uint32 crypto_uint32_unequal_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
657
0
{
658
0
  crypto_uint32 crypto_uint32_xy = crypto_uint32_x ^ crypto_uint32_y;
659
0
  return crypto_uint32_nonzero_mask(crypto_uint32_xy);
660
0
}
661
662
GCC_ATTR_UNUSED
663
static crypto_uint32 crypto_uint32_equal_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
664
0
{
665
0
  return ~crypto_uint32_unequal_mask(crypto_uint32_x,crypto_uint32_y);
666
0
}
667
668
GCC_ATTR_UNUSED
669
static crypto_uint32 crypto_uint32_smaller_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
670
0
{
671
0
  crypto_uint32 crypto_uint32_xy = crypto_uint32_x ^ crypto_uint32_y;
672
0
  crypto_uint32 crypto_uint32_z = crypto_uint32_x - crypto_uint32_y;
673
0
  crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_x ^ (((crypto_uint32) 1) << (32-1)));
674
0
  return crypto_uint32_signed_negative_mask(crypto_uint32_z);
675
0
}
676
677
GCC_ATTR_UNUSED
678
static crypto_uint32 crypto_uint32_min(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
679
0
{
680
0
  crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
681
0
  crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
682
0
  crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
683
0
  crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
684
0
  crypto_uint32_z &= crypto_uint32_xy;
685
0
  return crypto_uint32_x ^ crypto_uint32_z;
686
0
}
687
688
GCC_ATTR_UNUSED
689
static crypto_uint32 crypto_uint32_max(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
690
0
{
691
0
  crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
692
0
  crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
693
0
  crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
694
0
  crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
695
0
  crypto_uint32_z &= crypto_uint32_xy;
696
0
  return crypto_uint32_y ^ crypto_uint32_z;
697
0
}
698
699
GCC_ATTR_UNUSED
700
static void crypto_uint32_minmax(crypto_uint32 *crypto_uint32_a,crypto_uint32 *crypto_uint32_b)
701
0
{
702
0
  crypto_uint32 crypto_uint32_x = *crypto_uint32_a;
703
0
  crypto_uint32 crypto_uint32_y = *crypto_uint32_b;
704
0
  crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
705
0
  crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
706
0
  crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
707
0
  crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
708
0
  crypto_uint32_z &= crypto_uint32_xy;
709
0
  *crypto_uint32_a = crypto_uint32_x ^ crypto_uint32_z;
710
0
  *crypto_uint32_b = crypto_uint32_y ^ crypto_uint32_z;
711
0
}
712
713
#endif
714
715
/* from libmceliece-20230612/crypto_kem/6688128f/vec/vec.h */
716
#ifndef VEC_H
717
#define VEC_H
718
719
720
721
typedef uint64_t vec;
722
723
static inline vec vec_setbits(vec b)
724
0
{
725
0
  vec ret = -b;
726
727
0
  return ret;
728
0
}
729
730
static inline vec vec_set1_16b(uint16_t v)
731
0
{
732
0
  vec ret;
733
734
0
  ret = v;
735
0
  ret |= ret << 16;
736
0
  ret |= ret << 32;
737
738
0
  return ret;
739
0
}
740
741
static inline void vec_copy(vec * out, vec * in)
742
0
{
743
0
  int i;
744
745
0
  for (i = 0; i < GFBITS; i++)
746
0
    out[i] = in[i];
747
0
}
748
749
static inline vec vec_or_reduce(vec * a)
750
0
{
751
0
  int i;
752
0
  vec ret;
753
754
0
  ret = a[0];
755
0
  for (i = 1; i < GFBITS; i++)
756
0
    ret |= a[i];
757
758
0
  return ret;
759
0
}
760
761
static inline int vec_testz(vec a)
762
0
{
763
0
  a |= a >> 32;
764
0
  a |= a >> 16;
765
0
  a |= a >> 8;
766
0
  a |= a >> 4;
767
0
  a |= a >> 2;
768
0
  a |= a >> 1;
769
770
0
  return (a&1)^1;
771
0
}
772
773
static void vec_mul(vec *, const vec *, const vec *);
774
static void vec_sq(vec *, vec *);
775
static void vec_inv(vec *, vec *);
776
777
#endif
778
779
780
/* from libmceliece-20230612/crypto_kem/6688128f/vec/benes.h */
781
/*
782
  This file is for Benes network related functions
783
*/
784
785
#ifndef BENES_H
786
#define BENES_H
787
788
789
static void benes(vec *, const unsigned char *, int);
790
791
#endif
792
793
794
/* from libmceliece-20230612/crypto_kem/6688128f/vec/bm.h */
795
/*
796
  This file is for the inversion-free Berlekamp-Massey algorithm
797
  see https://ieeexplore.ieee.org/document/87857
798
*/
799
800
#ifndef BM_H
801
#define BM_H
802
803
804
static void bm(vec [][GFBITS], vec [][ GFBITS ]);
805
806
#endif
807
808
809
/* from libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.h */
810
/* This file is for implementing the Nassimi-Sahni algorithm */
811
/* See David Nassimi, Sartaj Sahni "Parallel algorithms to set up the Benes permutationnetwork" */
812
/* See also https://cr.yp.to/papers/controlbits-20200923.pdf */
813
814
#ifndef CONTROLBITS_H
815
#define CONTROLBITS_H
816
817
818
819
820
#endif
821
822
/* from libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.h */
823
/*
824
  This file is for Nieddereiter decryption
825
*/
826
827
#ifndef DECRYPT_H
828
#define DECRYPT_H
829
830
static int decrypt(unsigned char *, const unsigned char *, const unsigned char *);
831
832
#endif
833
834
835
/* from libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.h */
836
/*
837
  This file is for Niederreiter encryption
838
*/
839
/* 20230102 djb: rename encrypt() as pke_encrypt() */
840
841
#ifndef ENCRYPT_H
842
#define ENCRYPT_H
843
844
static void pke_encrypt(unsigned char *, const unsigned char *, unsigned char *);
845
846
#endif
847
848
849
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_consts.h */
850
#ifndef fft_consts_h
851
#define fft_consts_h
852
853
854
855
856
#endif
857
858
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft.h */
859
/*
860
  This file is for the Gao-Mateer FFT
861
  sse http://www.math.clemson.edu/~sgao/papers/GM10.pdf
862
*/
863
864
#ifndef FFT_H
865
#define FFT_H
866
867
868
static void fft(vec [][GFBITS], vec [][GFBITS]);
869
870
#endif
871
872
873
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_powers.h */
874
#ifndef fft_powers_h
875
#define fft_powers_h
876
877
878
879
880
#endif
881
882
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_2x.h */
883
#ifndef fft_scalars_2x_h
884
#define fft_scalars_2x_h
885
886
887
888
889
#endif
890
891
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_4x.h */
892
#ifndef fft_scalars_4x_h
893
#define fft_scalars_4x_h
894
895
896
897
898
#endif
899
900
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.h */
901
/*
902
  This file is for transpose of the Gao-Mateer FFT
903
*/
904
905
#ifndef FFT_TR_H
906
#define FFT_TR_H
907
908
909
static void fft_tr(vec out[][GFBITS], vec in[][ GFBITS ]);
910
911
#endif
912
913
914
/* from libmceliece-20230612/crypto_kem/6688128f/vec/gf.h */
915
/*
916
  This file is for functions for field arithmetic
917
*/
918
/* 20221231 djb: const for GF_mul */
919
920
#ifndef GF_H
921
#define GF_H
922
923
924
925
typedef uint16_t gf;
926
927
gf gf_iszero(gf);
928
gf gf_mul(gf, gf);
929
gf gf_frac(gf, gf);
930
gf gf_inv(gf);
931
932
static void GF_mul(gf *, const gf *, const gf *);
933
934
/* 2 field multiplications */
935
static inline uint64_t gf_mul2(gf a, gf b0, gf b1)
936
0
{
937
0
  int i;
938
939
0
  uint64_t tmp=0;
940
0
  uint64_t t0;
941
0
  uint64_t t1;
942
0
  uint64_t t;
943
0
  uint64_t mask = 0x0000000100000001;
944
945
0
  t0 = a;
946
0
  t1 = b1;
947
0
  t1 = (t1 << 32) | b0;
948
949
0
  for (i = 0; i < GFBITS; i++)
950
0
  {
951
0
    tmp ^= t0 * (t1 & mask);
952
0
    mask += mask;
953
0
  }
954
955
  /**/
956
957
0
  t = tmp & 0x01FF000001FF0000;
958
0
  tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
959
960
0
  t = tmp & 0x0000E0000000E000;
961
0
  tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
962
963
0
  return tmp & 0x00001FFF00001FFF;
964
0
}
965
966
#endif
967
968
969
/* from libmceliece-20230612/crypto_kem/6688128f/vec/hash.h */
970
971
0
#define shake crypto_xof_shake256
972
973
#define crypto_hash_32b(out,in,inlen) \
974
0
  shake(out,32,in,inlen)
975
976
/* from libmceliece-20230612/crypto_kem/6688128f/vec/int32_sort.h */
977
#ifndef int32_sort_h
978
#define int32_sort_h
979
980
981
982
0
#define int32_MINMAX(a,b) \
983
0
do { \
984
0
  int64_t ab = (int64_t)b ^ (int64_t)a; \
985
0
  int64_t c = (int64_t)b - (int64_t)a; \
986
0
  c ^= ab & (c ^ b); \
987
0
  c >>= 31; \
988
0
  c &= ab; \
989
0
  a ^= c; \
990
0
  b ^= c; \
991
0
} while(0)
992
993
static void int32_sort(int32_t *x,long long n)
994
0
{
995
0
  long long top,p,q,r,i;
996
997
0
  if (n < 2) return;
998
0
  top = 1;
999
0
  while (top < n - top) top += top;
1000
1001
0
  for (p = top;p > 0;p >>= 1) {
1002
0
    for (i = 0;i < n - p;++i)
1003
0
      if (!(i & p))
1004
0
        int32_MINMAX(x[i],x[i+p]);
1005
0
    i = 0;
1006
0
    for (q = top;q > p;q >>= 1) {
1007
0
      for (;i < n - q;++i) {
1008
0
        if (!(i & p)) {
1009
0
          int32_t a = x[i + p];
1010
0
          for (r = q;r > p;r >>= 1)
1011
0
            int32_MINMAX(a,x[i+r]);
1012
0
          x[i + p] = a;
1013
0
        }
1014
0
      }
1015
0
    }
1016
0
  }
1017
0
}
1018
1019
#endif
1020
1021
1022
/* from libmceliece-20230612/crypto_kem/6688128f/vec/operations.h */
1023
#ifndef OPERATIONS_H
1024
#define OPERATIONS_H
1025
1026
1027
static void operation_enc(
1028
       unsigned char *c,
1029
       unsigned char *key,
1030
       const unsigned char *pk
1031
);
1032
1033
static void operation_dec(
1034
       unsigned char *key,
1035
       const unsigned char *c,
1036
       const unsigned char *sk
1037
);
1038
1039
static void operation_keypair
1040
(
1041
       unsigned char *pk,
1042
       unsigned char *sk
1043
);
1044
1045
#endif
1046
1047
1048
/* from libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.h */
1049
/*
1050
  This file is for public-key generation
1051
*/
1052
1053
#ifndef PK_GEN_H
1054
#define PK_GEN_H
1055
1056
1057
static int pk_gen(unsigned char *, const unsigned char *, uint32_t *, int16_t *, uint64_t *);
1058
1059
#endif
1060
1061
1062
/* from libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.h */
1063
/*
1064
  This file is for secret-key generation
1065
*/
1066
1067
#ifndef SK_GEN_H
1068
#define SK_GEN_H
1069
1070
1071
1072
static int genpoly_gen(gf *, gf *);
1073
1074
#endif
1075
1076
1077
/* from libmceliece-20230612/crypto_kem/6688128f/vec/transpose.h */
1078
/*
1079
  This file is for matrix transposition
1080
*/
1081
1082
#ifndef TRANSPOSE_H
1083
#define TRANSPOSE_H
1084
1085
/* input: in, a 64x64 matrix over GF(2) */
1086
/* output: out, transpose of in */
1087
static inline void transpose_64x64(uint64_t * out, uint64_t * in)
1088
0
{
1089
0
  int i, j, s, d;
1090
1091
0
  uint64_t x, y;
1092
0
  uint64_t masks[6][2] = {
1093
0
                          {0x5555555555555555, 0xAAAAAAAAAAAAAAAA},
1094
0
                          {0x3333333333333333, 0xCCCCCCCCCCCCCCCC},
1095
0
                          {0x0F0F0F0F0F0F0F0F, 0xF0F0F0F0F0F0F0F0},
1096
0
                          {0x00FF00FF00FF00FF, 0xFF00FF00FF00FF00},
1097
0
                          {0x0000FFFF0000FFFF, 0xFFFF0000FFFF0000},
1098
0
                          {0x00000000FFFFFFFF, 0xFFFFFFFF00000000}
1099
0
                         };
1100
1101
0
  for (i = 0; i < 64; i++)
1102
0
    out[i] = in[i];
1103
1104
0
  for (d = 5; d >= 0; d--)
1105
0
  {
1106
0
    s = 1 << d;
1107
1108
0
    for (i = 0; i < 64; i += s*2)
1109
0
    for (j = i; j < i+s; j++)
1110
0
    {
1111
0
      x = (out[j] & masks[d][0]) | ((out[j+s] & masks[d][0]) << s);
1112
0
      y = ((out[j] & masks[d][1]) >> s) | (out[j+s] & masks[d][1]);
1113
1114
0
      out[j+0] = x;
1115
0
      out[j+s] = y;
1116
0
    }
1117
0
  }
1118
0
}
1119
1120
#endif
1121
1122
1123
/* from libmceliece-20230612/crypto_kem/6688128f/vec/uint16_sort.h */
1124
#ifndef uint16_sort_h
1125
#define uint16_sort_h
1126
1127
1128
1129
0
#define uint16_MINMAX(a,b) \
1130
0
do { \
1131
0
  uint16_t c = b - a; \
1132
0
  c >>= 15; \
1133
0
  c = -c; \
1134
0
  c &= a ^ b; \
1135
0
  a ^= c; \
1136
0
  b ^= c; \
1137
0
} while(0)
1138
1139
static void uint16_sort(uint16_t *x,long long n)
1140
0
{
1141
0
  long long top,p,q,r,i;
1142
1143
0
  if (n < 2) return;
1144
0
  top = 1;
1145
0
  while (top < n - top) top += top;
1146
1147
0
  for (p = top;p > 0;p >>= 1) {
1148
0
    for (i = 0;i < n - p;++i)
1149
0
      if (!(i & p))
1150
0
        uint16_MINMAX(x[i],x[i+p]);
1151
0
    i = 0;
1152
0
    for (q = top;q > p;q >>= 1) {
1153
0
      for (;i < n - q;++i) {
1154
0
        if (!(i & p)) {
1155
0
          int16_t a = x[i + p];
1156
0
          for (r = q;r > p;r >>= 1)
1157
0
            uint16_MINMAX(a,x[i+r]);
1158
0
          x[i + p] = a;
1159
0
        }
1160
0
      }
1161
0
    }
1162
0
  }
1163
0
}
1164
1165
#endif
1166
1167
1168
/* from libmceliece-20230612/crypto_kem/6688128f/vec/uint64_sort.h */
1169
#ifndef uint64_sort_h
1170
#define uint64_sort_h
1171
1172
1173
1174
0
#define uint64_MINMAX(a,b) \
1175
0
do { \
1176
0
  uint64_t c = b - a; \
1177
0
  c >>= 63; \
1178
0
  c = -c; \
1179
0
  c &= a ^ b; \
1180
0
  a ^= c; \
1181
0
  b ^= c; \
1182
0
} while(0)
1183
1184
static void uint64_sort(uint64_t *x,long long n)
1185
0
{
1186
0
  long long top,p,q,r,i;
1187
1188
0
  if (n < 2) return;
1189
0
  top = 1;
1190
0
  while (top < n - top) top += top;
1191
1192
0
  for (p = top;p > 0;p >>= 1) {
1193
0
    for (i = 0;i < n - p;++i)
1194
0
      if (!(i & p))
1195
0
        uint64_MINMAX(x[i],x[i+p]);
1196
0
    i = 0;
1197
0
    for (q = top;q > p;q >>= 1) {
1198
0
      for (;i < n - q;++i) {
1199
0
        if (!(i & p)) {
1200
0
          uint64_t a = x[i + p];
1201
0
          for (r = q;r > p;r >>= 1)
1202
0
            uint64_MINMAX(a,x[i+r]);
1203
0
          x[i + p] = a;
1204
0
        }
1205
0
      }
1206
0
    }
1207
0
  }
1208
0
}
1209
1210
#endif
1211
1212
1213
/* from libmceliece-20230612/crypto_kem/6688128f/vec/util.h */
1214
/*
1215
  This file is for loading/storing data in a little-endian fashion
1216
*/
1217
1218
#ifndef UTIL_H
1219
#define UTIL_H
1220
1221
1222
1223
static inline void store_i(unsigned char *out, uint64_t in, int i)
1224
0
{
1225
0
  int j;
1226
1227
0
  for (j = 0; j < i; j++)
1228
0
    out[j] = (in >> (j * 8)) & 0xFF;
1229
0
}
1230
1231
static inline void store_gf(unsigned char *dest, uint16_t a)
1232
0
{
1233
0
  dest[0] = a & 0xFF;
1234
0
  dest[1] = a >> 8;
1235
0
}
1236
1237
static inline uint16_t load_gf(const unsigned char *src)
1238
0
{
1239
0
  uint16_t a;
1240
1241
0
  a = src[1];
1242
0
  a <<= 8;
1243
0
  a |= src[0];
1244
1245
0
  return a & GFMASK;
1246
0
}
1247
1248
static inline uint32_t load4(const unsigned char *src)
1249
0
{
1250
0
  uint32_t a;
1251
1252
0
  a  = src[3]; a <<= 8;
1253
0
  a |= src[2]; a <<= 8;
1254
0
  a |= src[1]; a <<= 8;
1255
0
  a |= src[0];
1256
1257
0
  return a;
1258
0
}
1259
1260
static inline void irr_load(vec out[][GFBITS], const unsigned char * in)
1261
0
{
1262
0
  int i, j;
1263
0
  uint64_t v0 = 0, v1 = 0;
1264
0
  uint16_t irr[ SYS_T ];
1265
1266
0
  for (i = 0; i < SYS_T; i++)
1267
0
    irr[i] = load_gf(in + i*2);
1268
1269
0
  for (i = 0; i < GFBITS; i++)
1270
0
  {
1271
0
    for (j = 63; j >= 0; j--)
1272
0
    {
1273
0
      v0 <<= 1;
1274
0
      v1 <<= 1;
1275
0
      v0 |= (irr[j] >> i) & 1;
1276
0
      v1 |= (irr[j+64] >> i) & 1;
1277
0
    }
1278
1279
0
    out[0][i] = v0;
1280
0
    out[1][i] = v1;
1281
0
  }
1282
0
}
1283
1284
static inline void store8(unsigned char *out, uint64_t in)
1285
0
{
1286
0
  out[0] = (in >> 0x00) & 0xFF;
1287
0
  out[1] = (in >> 0x08) & 0xFF;
1288
0
  out[2] = (in >> 0x10) & 0xFF;
1289
0
  out[3] = (in >> 0x18) & 0xFF;
1290
0
  out[4] = (in >> 0x20) & 0xFF;
1291
0
  out[5] = (in >> 0x28) & 0xFF;
1292
0
  out[6] = (in >> 0x30) & 0xFF;
1293
0
  out[7] = (in >> 0x38) & 0xFF;
1294
0
}
1295
1296
static inline uint64_t load8(const unsigned char * in)
1297
0
{
1298
0
  int i;
1299
0
  uint64_t ret = in[7];
1300
1301
0
  for (i = 6; i >= 0; i--)
1302
0
  {
1303
0
    ret <<= 8;
1304
0
    ret |= in[i];
1305
0
  }
1306
1307
0
  return ret;
1308
0
}
1309
1310
#endif
1311
1312
1313
static void crypto_xof_shake256(unsigned char *h,long long hlen,
1314
        const unsigned char *m,long long mlen)
1315
0
{
1316
0
  gcry_md_hd_t mdh;
1317
0
  gcry_err_code_t ec;
1318
1319
0
  ec = _gcry_md_open (&mdh, GCRY_MD_SHAKE256, 0);
1320
0
  if (ec)
1321
0
    log_fatal ("internal md_open failed: %d\n", ec);
1322
0
  _gcry_md_write (mdh, m, mlen);
1323
0
  _gcry_md_extract (mdh, GCRY_MD_SHAKE256, h, hlen);
1324
0
  _gcry_md_close (mdh);
1325
0
}
1326
1327
/* from libmceliece-20230612/crypto_kem/6688128f/vec/benes.c */
1328
/*
1329
  This file is for Benes network related functions
1330
1331
  For the implementation strategy, see
1332
  https://eprint.iacr.org/2017/793.pdf
1333
*/
1334
/* 20221230 djb: add linker lines */
1335
1336
/* linker define benes */
1337
1338
1339
/* middle layers of the benes network */
1340
static void layer_in(uint64_t data[2][64], uint64_t * bits, int lgs)
1341
0
{
1342
0
  int i, j, s;
1343
1344
0
  uint64_t d;
1345
1346
0
  s = 1 << lgs;
1347
1348
0
  for (i = 0; i < 64; i += s*2)
1349
0
  for (j = i; j < i+s; j++)
1350
0
  {
1351
1352
0
    d = (data[0][j+0] ^ data[0][j+s]);
1353
0
    d &= (*bits++);
1354
0
    data[0][j+0] ^= d;
1355
0
    data[0][j+s] ^= d;
1356
1357
0
    d = (data[1][j+0] ^ data[1][j+s]);
1358
0
    d &= (*bits++);
1359
0
    data[1][j+0] ^= d;
1360
0
    data[1][j+s] ^= d;
1361
0
  }
1362
0
}
1363
1364
/* first and last layers of the benes network */
1365
static void layer_ex(uint64_t * data, uint64_t * bits, int lgs)
1366
0
{
1367
0
  int i, j, s;
1368
1369
0
  uint64_t d;
1370
1371
0
  s = 1 << lgs;
1372
1373
0
  for (i = 0; i < 128; i += s*2)
1374
0
  for (j = i; j < i+s; j++)
1375
0
  {
1376
1377
0
    d = (data[j+0] ^ data[j+s]);
1378
0
    d &= (*bits++);
1379
0
    data[j+0] ^= d;
1380
0
    data[j+s] ^= d;
1381
0
  }
1382
0
}
1383
1384
/* input: r, sequence of bits to be permuted */
1385
/*        bits, condition bits of the Benes network */
1386
/*        rev, 0 for normal application; !0 for inverse */
1387
/* output: r, permuted bits */
1388
static void benes(vec * r, const unsigned char * bits, int rev)
1389
0
{
1390
0
  int i, iter, inc;
1391
1392
0
  const unsigned char *bits_ptr;
1393
1394
0
  uint64_t r_int_v[2][64];
1395
0
  uint64_t r_int_h[2][64];
1396
0
  uint64_t b_int_v[64];
1397
0
  uint64_t b_int_h[64];
1398
1399
  /**/
1400
1401
0
  if (rev) { bits_ptr = bits + 12288; inc = -1024; }
1402
0
  else     { bits_ptr = bits;         inc = 0;    }
1403
1404
0
  for (i = 0; i < 64; i++)
1405
0
  {
1406
0
    r_int_v[0][i] = r[i*2 + 0];
1407
0
    r_int_v[1][i] = r[i*2 + 1];
1408
0
  }
1409
1410
0
  transpose_64x64(r_int_h[0], r_int_v[0]);
1411
0
  transpose_64x64(r_int_h[1], r_int_v[1]);
1412
1413
0
  for (iter = 0; iter <= 6; iter++)
1414
0
  {
1415
0
    for (i = 0; i < 64; i++)
1416
0
    {
1417
0
      b_int_v[i] = load8(bits_ptr); bits_ptr += 8;
1418
0
    }
1419
1420
0
    bits_ptr += inc;
1421
1422
0
    transpose_64x64(b_int_h, b_int_v);
1423
1424
0
    layer_ex(r_int_h[0], b_int_h, iter);
1425
0
  }
1426
1427
0
  transpose_64x64(r_int_v[0], r_int_h[0]);
1428
0
  transpose_64x64(r_int_v[1], r_int_h[1]);
1429
1430
0
  for (iter = 0; iter <= 5; iter++)
1431
0
  {
1432
0
    for (i = 0; i < 64; i++) { b_int_v[i] = load8(bits_ptr); bits_ptr += 8; }
1433
0
    bits_ptr += inc;
1434
1435
0
    layer_in(r_int_v, b_int_v, iter);
1436
0
  }
1437
1438
0
  for (iter = 4; iter >= 0; iter--)
1439
0
  {
1440
0
    for (i = 0; i < 64; i++) { b_int_v[i] = load8(bits_ptr); bits_ptr += 8; }
1441
0
    bits_ptr += inc;
1442
1443
0
    layer_in(r_int_v, b_int_v, iter);
1444
0
  }
1445
1446
0
  transpose_64x64(r_int_h[0], r_int_v[0]);
1447
0
  transpose_64x64(r_int_h[1], r_int_v[1]);
1448
1449
0
  for (iter = 6; iter >= 0; iter--)
1450
0
  {
1451
0
    for (i = 0; i < 64; i++)
1452
0
    {
1453
0
      b_int_v[i] = load8(bits_ptr); bits_ptr += 8;
1454
0
    }
1455
1456
0
    bits_ptr += inc;
1457
1458
0
    transpose_64x64(b_int_h, b_int_v);
1459
1460
0
    layer_ex(r_int_h[0], b_int_h, iter);
1461
0
  }
1462
1463
0
  transpose_64x64(r_int_v[0], r_int_h[0]);
1464
0
  transpose_64x64(r_int_v[1], r_int_h[1]);
1465
1466
0
  for (i = 0; i < 64; i++)
1467
0
  {
1468
0
    r[i*2+0] = r_int_v[0][i];
1469
0
    r[i*2+1] = r_int_v[1][i];
1470
0
  }
1471
0
}
1472
1473
1474
/* from libmceliece-20230612/crypto_kem/6688128f/vec/bm.c */
1475
/*
1476
  This file is for implementating the inversion-free Berlekamp-Massey algorithm
1477
  see https://ieeexplore.ieee.org/document/87857
1478
1479
  For the implementation strategy, see
1480
  https://eprint.iacr.org/2017/793.pdf
1481
*/
1482
/* 20221230 djb: add linker lines */
1483
1484
/* linker define bm */
1485
/* linker use vec_mul */
1486
/* linker use gf_inv */
1487
1488
1489
1490
static inline uint16_t mask_nonzero(gf a)
1491
0
{
1492
0
  uint32_t ret = a;
1493
1494
0
  ret -= 1;
1495
0
  ret >>= 31;
1496
0
  ret -= 1;
1497
1498
0
  return ret;
1499
0
}
1500
1501
static inline uint16_t mask_leq(uint16_t a, uint16_t b)
1502
0
{
1503
0
  uint32_t a_tmp = a;
1504
0
  uint32_t b_tmp = b;
1505
0
  uint32_t ret = b_tmp - a_tmp;
1506
1507
0
  ret >>= 31;
1508
0
  ret -= 1;
1509
1510
0
  return ret;
1511
0
}
1512
1513
static inline void vec_cmov(vec * out, vec * in, uint16_t mask)
1514
0
{
1515
0
  int i;
1516
1517
0
  vec m0, m1;
1518
1519
0
  m0 = vec_set1_16b(mask);
1520
0
  m1 = ~m0;
1521
1522
0
  for (i = 0; i < GFBITS; i++)
1523
0
  {
1524
0
    out[i] = (in[i] & m0) | (out[i] & m1);
1525
0
    out[i] = (in[i] & m0) | (out[i] & m1);
1526
0
  }
1527
0
}
1528
1529
static inline void interleave(vec *in, int idx0, int idx1, vec *mask, int b)
1530
0
{
1531
0
  int s = 1 << b;
1532
1533
0
  vec x, y;
1534
1535
0
  x = (in[idx0] & mask[0]) | ((in[idx1] & mask[0]) << s);
1536
0
  y = ((in[idx0] & mask[1]) >> s) | (in[idx1] & mask[1]);
1537
1538
0
  in[idx0] = x;
1539
0
  in[idx1] = y;
1540
0
}
1541
1542
/* input: in, field elements in bitsliced form */
1543
/* output: out, field elements in non-bitsliced form */
1544
static inline void get_coefs(gf *out, vec *in)
1545
0
{
1546
0
  int i, k;
1547
1548
0
  vec mask[4][2];
1549
0
  vec buf[16];
1550
1551
0
  for (i =  0; i < 13; i++) buf[i] = in[i];
1552
0
  for (i = 13; i < 16; i++) buf[i] = 0;
1553
1554
0
  mask[0][0] = vec_set1_16b(0x5555);
1555
0
  mask[0][1] = vec_set1_16b(0xAAAA);
1556
0
  mask[1][0] = vec_set1_16b(0x3333);
1557
0
  mask[1][1] = vec_set1_16b(0xCCCC);
1558
0
  mask[2][0] = vec_set1_16b(0x0F0F);
1559
0
  mask[2][1] = vec_set1_16b(0xF0F0);
1560
0
  mask[3][0] = vec_set1_16b(0x00FF);
1561
0
  mask[3][1] = vec_set1_16b(0xFF00);
1562
1563
0
  interleave(buf,  0,  8, mask[3], 3);
1564
0
  interleave(buf,  1,  9, mask[3], 3);
1565
0
  interleave(buf,  2, 10, mask[3], 3);
1566
0
  interleave(buf,  3, 11, mask[3], 3);
1567
0
  interleave(buf,  4, 12, mask[3], 3);
1568
0
  interleave(buf,  5, 13, mask[3], 3);
1569
0
  interleave(buf,  6, 14, mask[3], 3);
1570
0
  interleave(buf,  7, 15, mask[3], 3);
1571
1572
0
  interleave(buf,  0,  4, mask[2], 2);
1573
0
  interleave(buf,  1,  5, mask[2], 2);
1574
0
  interleave(buf,  2,  6, mask[2], 2);
1575
0
  interleave(buf,  3,  7, mask[2], 2);
1576
0
  interleave(buf,  8, 12, mask[2], 2);
1577
0
  interleave(buf,  9, 13, mask[2], 2);
1578
0
  interleave(buf, 10, 14, mask[2], 2);
1579
0
  interleave(buf, 11, 15, mask[2], 2);
1580
1581
0
  interleave(buf,  0,  2, mask[1], 1);
1582
0
  interleave(buf,  1,  3, mask[1], 1);
1583
0
  interleave(buf,  4,  6, mask[1], 1);
1584
0
  interleave(buf,  5,  7, mask[1], 1);
1585
0
  interleave(buf,  8, 10, mask[1], 1);
1586
0
  interleave(buf,  9, 11, mask[1], 1);
1587
0
  interleave(buf, 12, 14, mask[1], 1);
1588
0
  interleave(buf, 13, 15, mask[1], 1);
1589
1590
0
  interleave(buf,  0,  1, mask[0], 0);
1591
0
  interleave(buf,  2,  3, mask[0], 0);
1592
0
  interleave(buf,  4,  5, mask[0], 0);
1593
0
  interleave(buf,  6,  7, mask[0], 0);
1594
0
  interleave(buf,  8,  9, mask[0], 0);
1595
0
  interleave(buf, 10, 11, mask[0], 0);
1596
0
  interleave(buf, 12, 13, mask[0], 0);
1597
0
  interleave(buf, 14, 15, mask[0], 0);
1598
1599
0
  for (i = 0; i < 16; i++)
1600
0
  for (k = 0; k <  4; k++)
1601
0
    out[ k*16 + i ] = (buf[i] >> (k*16)) & GFMASK;
1602
0
}
1603
1604
static void update(vec in[][GFBITS], const gf e)
1605
0
{
1606
0
  int i;
1607
0
  vec tmp;
1608
1609
0
  for (i = 0; i < GFBITS; i++)
1610
0
  {
1611
0
    tmp = (e >> i) & 1;
1612
1613
0
    in[0][i] = (in[0][i] >> 1) | (in[1][i] << 63);
1614
0
    in[1][i] = (in[1][i] >> 1) | (tmp      << 63);
1615
0
  }
1616
0
}
1617
1618
static inline gf vec_reduce(vec in[][GFBITS])
1619
0
{
1620
0
  int i;
1621
0
  vec tmp;
1622
0
  gf ret = 0;
1623
1624
0
  for (i = GFBITS-1; i >= 0; i--)
1625
0
  {
1626
0
    tmp = in[0][i] ^ in[1][i];
1627
1628
0
    tmp ^= tmp >> 32;
1629
0
    tmp ^= tmp >> 16;
1630
0
    tmp ^= tmp >> 8;
1631
0
    tmp ^= tmp >> 4;
1632
0
    tmp ^= tmp >> 2;
1633
0
    tmp ^= tmp >> 1;
1634
1635
0
    ret <<= 1;
1636
0
    ret |= tmp & 1;
1637
0
  }
1638
1639
0
  return ret;
1640
0
}
1641
1642
/* input: in, sequence of field elements */
1643
/* output: out, minimal polynomial of in */
1644
static void bm(vec out[][ GFBITS ], vec in[][ GFBITS ])
1645
0
{
1646
0
  int i;
1647
0
  uint16_t N, L;
1648
0
  uint16_t mask;
1649
0
  uint64_t one = 1, t;
1650
1651
0
  vec prod[2][GFBITS];
1652
0
  vec interval[2][GFBITS];
1653
0
  vec dd[2][GFBITS], bb[2][GFBITS];
1654
0
  vec B[2][GFBITS], C[2][GFBITS];
1655
0
  vec B_tmp[2][GFBITS], C_tmp[2][GFBITS];
1656
0
  vec v[GFBITS];
1657
1658
0
  gf d, b, c0 = 1;
1659
0
  gf coefs[256];
1660
1661
  /* initialization */
1662
1663
0
  get_coefs(&coefs[  0], in[0]);
1664
0
  get_coefs(&coefs[ 64], in[1]);
1665
0
  get_coefs(&coefs[128], in[2]);
1666
0
  get_coefs(&coefs[192], in[3]);
1667
1668
0
  C[0][0] = 0;
1669
0
  C[1][0] = 0;
1670
0
  B[0][0] = 0;
1671
0
  B[1][0] = one << 63;
1672
1673
0
  for (i = 1; i < GFBITS; i++)
1674
0
    C[0][i] = C[1][i] = B[0][i] = B[1][i] = 0;
1675
1676
0
  b = 1;
1677
0
  L = 0;
1678
1679
  /**/
1680
1681
0
  for (i = 0; i < GFBITS; i++)
1682
0
    interval[0][i] = interval[1][i] = 0;
1683
1684
0
  for (N = 0; N < 256; N++)
1685
0
  {
1686
0
    vec_mul(prod[0], C[0], interval[0]);
1687
0
    vec_mul(prod[1], C[1], interval[1]);
1688
0
    update(interval, coefs[N]);
1689
0
    d = vec_reduce(prod);
1690
1691
0
    t = gf_mul2(c0, coefs[N], b);
1692
0
    d ^= t & 0xFFFFFFFF;
1693
1694
0
    mask = mask_nonzero(d) & mask_leq(L*2, N);
1695
1696
0
    for (i = 0; i < GFBITS; i++)
1697
0
    {
1698
0
      dd[0][i] = dd[1][i] = vec_setbits((d >> i) & 1);
1699
0
      bb[0][i] = bb[1][i] = vec_setbits((b >> i) & 1);
1700
0
    }
1701
1702
0
    vec_mul(B_tmp[0], dd[0], B[0]);
1703
0
    vec_mul(B_tmp[1], dd[1], B[1]);
1704
0
    vec_mul(C_tmp[0], bb[0], C[0]);
1705
0
    vec_mul(C_tmp[1], bb[1], C[1]);
1706
1707
0
    vec_cmov(B[0], C[0], mask);
1708
0
    vec_cmov(B[1], C[1], mask);
1709
0
    update(B, c0 & mask);
1710
1711
0
    for (i = 0; i < GFBITS; i++)
1712
0
    {
1713
0
      C[0][i] = B_tmp[0][i] ^ C_tmp[0][i];
1714
0
      C[1][i] = B_tmp[1][i] ^ C_tmp[1][i];
1715
0
    }
1716
1717
0
    c0 = t >> 32;
1718
0
    b = (d & mask) | (b & ~mask);
1719
0
    L = ((N+1-L) & mask) | (L & ~mask);
1720
0
  }
1721
1722
0
  c0 = gf_inv(c0);
1723
1724
0
  for (i = 0; i < GFBITS; i++)
1725
0
    v[i] = vec_setbits((c0 >> i) & 1);
1726
1727
0
  vec_mul(out[0], C[0], v);
1728
0
  vec_mul(out[1], C[1], v);
1729
0
}
1730
1731
1732
/* from libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.c */
1733
/* This file is for implementing the Nassimi-Sahni algorithm */
1734
/* See David Nassimi, Sartaj Sahni "Parallel algorithms to set up the Benes permutationnetwork" */
1735
/* See also https://cr.yp.to/papers/controlbits-20200923.pdf */
1736
1737
/* 20221230 djb: add linker line */
1738
1739
/* linker define controlbitsfrompermutation */
1740
1741
typedef int16_t int16;
1742
typedef int32_t int32;
1743
0
#define int32_min crypto_int32_min
1744
1745
/* parameters: 1 <= w <= 14; n = 2^w */
1746
/* input: permutation pi of {0,1,...,n-1} */
1747
/* output: (2m-1)n/2 control bits at positions pos,pos+step,... */
1748
/* output position pos is by definition 1&(out[pos/8]>>(pos&7)) */
1749
/* caller must 0-initialize positions first */
1750
/* temp must have space for int32[2*n] */
1751
static void cbrecursion(unsigned char *out,long long pos,long long step,const int16 *pi,long long w,long long n,int32 *temp)
1752
0
{
1753
0
#define A temp
1754
0
#define B (temp+n)
1755
0
#define q ((int16 *) (temp+n+n/4))
1756
/* q can start anywhere between temp+n and temp+n/2 */
1757
1758
0
  long long x,i,j,k;
1759
1760
0
  if (w == 1) {
1761
0
    out[pos>>3] ^= pi[0]<<(pos&7);
1762
0
    return;
1763
0
  }
1764
1765
0
  for (x = 0;x < n;++x) A[x] = ((pi[x]^1)<<16)|pi[x^1];
1766
0
  int32_sort(A,n); /* A = (id<<16)+pibar */
1767
1768
0
  for (x = 0;x < n;++x) {
1769
0
    int32 Ax = A[x];
1770
0
    int32 px = Ax&0xffff;
1771
0
    int32 cx = int32_min(px,x);
1772
0
    B[x] = (px<<16)|cx;
1773
0
  }
1774
  /* B = (p<<16)+c */
1775
1776
0
  for (x = 0;x < n;++x) A[x] = (A[x]<<16)|x; /* A = (pibar<<16)+id */
1777
0
  int32_sort(A,n); /* A = (id<<16)+pibar^-1 */
1778
1779
0
  for (x = 0;x < n;++x) A[x] = (A[x]<<16)+(B[x]>>16); /* A = (pibar^(-1)<<16)+pibar */
1780
0
  int32_sort(A,n); /* A = (id<<16)+pibar^2 */
1781
1782
0
  if (w <= 10) {
1783
0
    for (x = 0;x < n;++x) B[x] = ((A[x]&0xffff)<<10)|(B[x]&0x3ff);
1784
1785
0
    for (i = 1;i < w-1;++i) {
1786
      /* B = (p<<10)+c */
1787
1788
0
      for (x = 0;x < n;++x) A[x] = ((B[x]&~0x3ff)<<6)|x; /* A = (p<<16)+id */
1789
0
      int32_sort(A,n); /* A = (id<<16)+p^{-1} */
1790
1791
0
      for (x = 0;x < n;++x) A[x] = (A[x]<<20)|B[x]; /* A = (p^{-1}<<20)+(p<<10)+c */
1792
0
      int32_sort(A,n); /* A = (id<<20)+(pp<<10)+cp */
1793
1794
0
      for (x = 0;x < n;++x) {
1795
0
        int32 ppcpx = A[x]&0xfffff;
1796
0
        int32 ppcx = (A[x]&0xffc00)|(B[x]&0x3ff);
1797
0
        B[x] = int32_min(ppcx,ppcpx);
1798
0
      }
1799
0
    }
1800
0
    for (x = 0;x < n;++x) B[x] &= 0x3ff;
1801
0
  } else {
1802
0
    for (x = 0;x < n;++x) B[x] = (A[x]<<16)|(B[x]&0xffff);
1803
1804
0
    for (i = 1;i < w-1;++i) {
1805
      /* B = (p<<16)+c */
1806
1807
0
      for (x = 0;x < n;++x) A[x] = (B[x]&~0xffff)|x;
1808
0
      int32_sort(A,n); /* A = (id<<16)+p^(-1) */
1809
1810
0
      for (x = 0;x < n;++x) A[x] = (A[x]<<16)|(B[x]&0xffff);
1811
      /* A = p^(-1)<<16+c */
1812
1813
0
      if (i < w-2) {
1814
0
        for (x = 0;x < n;++x) B[x] = (A[x]&~0xffff)|(B[x]>>16);
1815
        /* B = (p^(-1)<<16)+p */
1816
0
        int32_sort(B,n); /* B = (id<<16)+p^(-2) */
1817
0
        for (x = 0;x < n;++x) B[x] = (B[x]<<16)|(A[x]&0xffff);
1818
        /* B = (p^(-2)<<16)+c */
1819
0
      }
1820
1821
0
      int32_sort(A,n);
1822
      /* A = id<<16+cp */
1823
0
      for (x = 0;x < n;++x) {
1824
0
        int32 cpx = (B[x]&~0xffff)|(A[x]&0xffff);
1825
0
        B[x] = int32_min(B[x],cpx);
1826
0
      }
1827
0
    }
1828
0
    for (x = 0;x < n;++x) B[x] &= 0xffff;
1829
0
  }
1830
1831
0
  for (x = 0;x < n;++x) A[x] = (((int32)pi[x])<<16)+x;
1832
0
  int32_sort(A,n); /* A = (id<<16)+pi^(-1) */
1833
1834
0
  for (j = 0;j < n/2;++j) {
1835
0
    long long lx = 2*j;
1836
0
    int32 fj = B[lx]&1; /* f[j] */
1837
0
    int32 Fx = lx+fj; /* F[x] */
1838
0
    int32 Fx1 = Fx^1; /* F[x+1] */
1839
1840
0
    out[pos>>3] ^= fj<<(pos&7);
1841
0
    pos += step;
1842
1843
0
    B[lx] = (A[lx]<<16)|Fx;
1844
0
    B[lx+1] = (A[lx+1]<<16)|Fx1;
1845
0
  }
1846
  /* B = (pi^(-1)<<16)+F */
1847
1848
0
  int32_sort(B,n); /* B = (id<<16)+F(pi) */
1849
1850
0
  pos += (2*w-3)*step*(n/2);
1851
1852
0
  for (k = 0;k < n/2;++k) {
1853
0
    long long y = 2*k;
1854
0
    int32 lk = B[y]&1; /* l[k] */
1855
0
    int32 Ly = y+lk; /* L[y] */
1856
0
    int32 Ly1 = Ly^1; /* L[y+1] */
1857
1858
0
    out[pos>>3] ^= lk<<(pos&7);
1859
0
    pos += step;
1860
1861
0
    A[y] = (Ly<<16)|(B[y]&0xffff);
1862
0
    A[y+1] = (Ly1<<16)|(B[y+1]&0xffff);
1863
0
  }
1864
  /* A = (L<<16)+F(pi) */
1865
1866
0
  int32_sort(A,n); /* A = (id<<16)+F(pi(L)) = (id<<16)+M */
1867
1868
0
  pos -= (2*w-2)*step*(n/2);
1869
1870
0
  for (j = 0;j < n/2;++j) {
1871
0
    q[j] = (A[2*j]&0xffff)>>1;
1872
0
    q[j+n/2] = (A[2*j+1]&0xffff)>>1;
1873
0
  }
1874
1875
0
  cbrecursion(out,pos,step*2,q,w-1,n/2,temp);
1876
0
  cbrecursion(out,pos+step,step*2,q+n/2,w-1,n/2,temp);
1877
0
}
1878
1879
/* input: p, an array of int16 */
1880
/* input: n, length of p */
1881
/* input: s, meaning that stride-2^s cswaps are performed */
1882
/* input: cb, the control bits */
1883
/* output: the result of apply the control bits to p */
1884
static void layer(int16_t *p, const unsigned char *cb, int s, int n)
1885
0
{
1886
0
  int i, j;
1887
0
  int stride = 1 << s;
1888
0
  int index = 0;
1889
0
  int16_t d, m;
1890
1891
0
  for (i = 0; i < n; i += stride*2)
1892
0
  {
1893
0
    for (j = 0; j < stride; j++)
1894
0
    {
1895
0
      d = p[ i+j ] ^ p[ i+j+stride ];
1896
0
      m = (cb[ index >> 3 ] >> (index & 7)) & 1;
1897
0
      m = -m;
1898
0
      d &= m;
1899
0
      p[ i+j ] ^= d;
1900
0
      p[ i+j+stride ] ^= d;
1901
0
      index++;
1902
0
    }
1903
0
  }
1904
0
}
1905
1906
/* parameters: 1 <= w <= 14; n = 2^w */
1907
/* input: permutation pi of {0,1,...,n-1} */
1908
/* output: (2m-1)n/2 control bits at positions 0,1,... */
1909
/* output position pos is by definition 1&(out[pos/8]>>(pos&7)) */
1910
static void controlbitsfrompermutation(unsigned char *out,const int16 *pi,long long w,long long n)
1911
0
{
1912
0
  int32 temp[2*n];
1913
0
  int16 pi_test[n], diff;
1914
0
  int i;
1915
0
  unsigned char *ptr;
1916
1917
0
  while (1)
1918
0
  {
1919
0
    memset(out,0,(((2*w-1)*n/2)+7)/8);
1920
0
    cbrecursion(out,0,1,pi,w,n,temp);
1921
1922
    /* check for correctness */
1923
1924
0
    for (i = 0; i < n; i++)
1925
0
      pi_test[i] = i;
1926
1927
0
    ptr = out;
1928
0
    for (i = 0; i < w; i++)
1929
0
    {
1930
0
      layer(pi_test, ptr, i, n);
1931
0
      ptr += n >> 4;
1932
0
    }
1933
1934
0
    for (i = w-2; i >= 0; i--)
1935
0
    {
1936
0
      layer(pi_test, ptr, i, n);
1937
0
      ptr += n >> 4;
1938
0
    }
1939
1940
0
    diff = 0;
1941
0
    for (i = 0; i < n; i++)
1942
0
      diff |= pi[i] ^ pi_test[i];
1943
1944
0
    diff = crypto_int16_nonzero_mask(diff);
1945
0
    crypto_declassify(&diff,sizeof diff);
1946
0
    if (diff == 0)
1947
0
      break;
1948
0
  }
1949
0
}
1950
1951
#undef A
1952
#undef B
1953
#undef q
1954
1955
/* from libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.c */
1956
/*
1957
  This file is for Niederreiter decryption
1958
*/
1959
/* 20221230 djb: add linker lines */
1960
1961
/* linker define decrypt */
1962
/* linker use benes bm fft fft_tr */
1963
/* linker use vec_mul vec_sq vec_inv */
1964
1965
1966
1967
1968
static void scaling(vec out[][GFBITS], vec inv[][GFBITS], const unsigned char *sk, vec *recv)
1969
0
{
1970
0
  int i, j;
1971
1972
0
  vec irr_int[2][ GFBITS ];
1973
0
  vec eval[128][ GFBITS ];
1974
0
  vec tmp[ GFBITS ];
1975
1976
  /**/
1977
1978
0
  irr_load(irr_int, sk);
1979
1980
0
  fft(eval, irr_int);
1981
1982
0
  for (i = 0; i < 128; i++)
1983
0
    vec_sq(eval[i], eval[i]);
1984
1985
0
  vec_copy(inv[0], eval[0]);
1986
1987
0
  for (i = 1; i < 128; i++)
1988
0
    vec_mul(inv[i], inv[i-1], eval[i]);
1989
1990
0
  vec_inv(tmp, inv[127]);
1991
1992
0
  for (i = 126; i >= 0; i--)
1993
0
  {
1994
0
    vec_mul(inv[i+1], tmp, inv[i]);
1995
0
    vec_mul(tmp, tmp, eval[i+1]);
1996
0
  }
1997
1998
0
  vec_copy(inv[0], tmp);
1999
2000
  /**/
2001
2002
0
  for (i = 0; i < 128; i++)
2003
0
  for (j = 0; j < GFBITS; j++)
2004
0
    out[i][j] = inv[i][j] & recv[i];
2005
0
}
2006
2007
static void preprocess(vec *recv, const unsigned char *s)
2008
0
{
2009
0
  int i;
2010
0
  unsigned char r[ 1024 ];
2011
2012
0
  for (i = 0; i < SYND_BYTES; i++)
2013
0
    r[i] = s[i];
2014
2015
0
  for (i = SYND_BYTES; i < 1024; i++)
2016
0
    r[i] = 0;
2017
2018
0
  for (i = 0; i < 128; i++)
2019
0
    recv[i] = load8(r + i*8);
2020
0
}
2021
2022
static void postprocess(unsigned char * e, vec * err)
2023
0
{
2024
0
  int i;
2025
0
  unsigned char error8[ (1 << GFBITS)/8 ];
2026
2027
0
  for (i = 0; i < 128; i++)
2028
0
    store8(error8 + i*8, err[i]);
2029
2030
0
  for (i = 0; i < SYS_N/8; i++)
2031
0
    e[i] = error8[i];
2032
0
}
2033
2034
static void scaling_inv(vec out[][GFBITS], vec inv[][GFBITS], vec *recv)
2035
0
{
2036
0
  int i, j;
2037
2038
0
  for (i = 0; i < 128; i++)
2039
0
  for (j = 0; j < GFBITS; j++)
2040
0
    out[i][j] = inv[i][j] & recv[i];
2041
0
}
2042
2043
static int weight_check(unsigned char * e, vec * error)
2044
0
{
2045
0
  int i;
2046
0
  uint16_t w0 = 0;
2047
0
  uint16_t w1 = 0;
2048
0
  uint16_t check;
2049
2050
0
  for (i = 0; i < (1 << GFBITS); i++)
2051
0
    w0 += (error[i/64] >> (i%64)) & 1;
2052
2053
0
  for (i = 0; i < SYS_N; i++)
2054
0
    w1 += (e[i/8] >> (i%8)) & 1;
2055
2056
0
  check = (w0 ^ SYS_T) | (w1 ^ SYS_T);
2057
0
  check -= 1;
2058
0
  check >>= 15;
2059
2060
0
  return check;
2061
0
}
2062
2063
static uint16_t synd_cmp(vec s0[][ GFBITS ] , vec s1[][ GFBITS ])
2064
0
{
2065
0
  int i, j;
2066
0
  vec diff = 0;
2067
2068
0
  for (i = 0; i < 4; i++)
2069
0
  for (j = 0; j < GFBITS; j++)
2070
0
    diff |= (s0[i][j] ^ s1[i][j]);
2071
2072
0
  return vec_testz(diff);
2073
0
}
2074
2075
/* Niederreiter decryption with the Berlekamp decoder */
2076
/* intput: sk, secret key */
2077
/*         s, ciphertext (syndrome) */
2078
/* output: e, error vector */
2079
/* return: 0 for success; 1 for failure */
2080
static int decrypt(unsigned char *e, const unsigned char *sk, const unsigned char *s)
2081
0
{
2082
0
  int i;
2083
2084
0
  uint16_t check_synd;
2085
0
  uint16_t check_weight;
2086
2087
0
  vec inv[ 128 ][ GFBITS ];
2088
0
  vec scaled[ 128 ][ GFBITS ];
2089
0
  vec eval[ 128 ][ GFBITS ];
2090
2091
0
  vec error[ 128 ];
2092
2093
0
  vec s_priv[ 4 ][ GFBITS ];
2094
0
  vec s_priv_cmp[ 4 ][ GFBITS ];
2095
0
  vec locator[2][ GFBITS ];
2096
2097
0
  vec recv[ 128 ];
2098
0
  vec allone;
2099
2100
  /* Berlekamp decoder */
2101
2102
0
  preprocess(recv, s);
2103
2104
0
  benes(recv, sk + IRR_BYTES, 1);
2105
0
  scaling(scaled, inv, sk, recv);
2106
0
  fft_tr(s_priv, scaled);
2107
0
  bm(locator, s_priv);
2108
2109
0
  fft(eval, locator);
2110
2111
  /* reencryption and weight check */
2112
2113
0
  allone = vec_setbits(1);
2114
2115
0
  for (i = 0; i < 128; i++)
2116
0
  {
2117
0
    error[i] = vec_or_reduce(eval[i]);
2118
0
    error[i] ^= allone;
2119
0
  }
2120
2121
0
  scaling_inv(scaled, inv, error);
2122
0
  fft_tr(s_priv_cmp, scaled);
2123
2124
0
  check_synd = synd_cmp(s_priv, s_priv_cmp);
2125
2126
  /**/
2127
2128
0
  benes(error, sk + IRR_BYTES, 0);
2129
2130
0
  postprocess(e, error);
2131
2132
0
  check_weight = weight_check(e, error);
2133
2134
#ifdef KAT
2135
  {
2136
    int k;
2137
    printf("decrypt e: positions");
2138
    for (k = 0;k < SYS_N;++k)
2139
      if (e[k/8] & (1 << (k&7)))
2140
        printf(" %d",k);
2141
    printf("\n");
2142
  }
2143
#endif
2144
2145
0
  return 1 - (check_synd & check_weight);
2146
0
}
2147
2148
2149
/* from libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.c */
2150
/* 20230102 djb: rename encrypt() as pke_encrypt() */
2151
/* 20221231 djb: move encrypt.h last for macos portability; tnx thom wiggers */
2152
/* 20221230 djb: add linker line */
2153
2154
/* linker define pke_encrypt */
2155
2156
/*
2157
  This file is for Niederreiter encryption
2158
*/
2159
2160
2161
2162
2163
2164
static inline crypto_uint16 uint16_is_smaller_declassify(uint16_t t,uint16_t u)
2165
0
{
2166
0
  crypto_uint16 mask = crypto_uint16_smaller_mask(t,u);
2167
0
  crypto_declassify(&mask,sizeof mask);
2168
0
  return mask;
2169
0
}
2170
2171
static inline crypto_uint32 uint32_is_equal_declassify(uint32_t t,uint32_t u)
2172
0
{
2173
0
  crypto_uint32 mask = crypto_uint32_equal_mask(t,u);
2174
0
  crypto_declassify(&mask,sizeof mask);
2175
0
  return mask;
2176
0
}
2177
2178
/* output: e, an error vector of weight t */
2179
static void gen_e(unsigned char *e)
2180
0
{
2181
0
  int i, j, eq, count;
2182
2183
0
  union
2184
0
  {
2185
0
    uint16_t nums[ SYS_T*2 ];
2186
0
    unsigned char bytes[ SYS_T*2 * sizeof(uint16_t) ];
2187
0
  } buf;
2188
2189
0
  uint16_t ind[ SYS_T ];
2190
0
  uint64_t e_int[ (SYS_N+63)/64 ];
2191
0
  uint64_t one = 1;
2192
0
  uint64_t mask;
2193
0
  uint64_t val[ SYS_T ];
2194
2195
0
  while (1)
2196
0
  {
2197
0
    randombytes(buf.bytes, sizeof(buf));
2198
2199
0
    for (i = 0; i < SYS_T*2; i++)
2200
0
      buf.nums[i] = load_gf(buf.bytes + i*2);
2201
2202
    /* moving and counting indices in the correct range */
2203
2204
0
    count = 0;
2205
0
    for (i = 0; i < SYS_T*2 && count < SYS_T; i++)
2206
0
      if (uint16_is_smaller_declassify(buf.nums[i],SYS_N))
2207
0
        ind[ count++ ] = buf.nums[i];
2208
2209
0
    if (count < SYS_T) continue;
2210
2211
    /* check for repetition */
2212
2213
0
    uint16_sort(ind, SYS_T);
2214
2215
0
    eq = 0;
2216
0
    for (i = 1; i < SYS_T; i++)
2217
0
      if (uint32_is_equal_declassify(ind[i-1],ind[i]))
2218
0
        eq = 1;
2219
2220
0
    if (eq == 0)
2221
0
      break;
2222
0
  }
2223
2224
0
  for (j = 0; j < SYS_T; j++)
2225
0
    val[j] = one << (ind[j] & 63);
2226
2227
0
  for (i = 0; i < (SYS_N+63)/64; i++)
2228
0
  {
2229
0
    e_int[i] = 0;
2230
2231
0
    for (j = 0; j < SYS_T; j++)
2232
0
    {
2233
0
      mask = i ^ (ind[j] >> 6);
2234
0
      mask -= 1;
2235
0
      mask >>= 63;
2236
0
      mask = -mask;
2237
2238
0
      e_int[i] |= val[j] & mask;
2239
0
    }
2240
0
  }
2241
2242
0
  for (i = 0; i < (SYS_N+63)/64 - 1; i++)
2243
0
    { store8(e, e_int[i]); e += 8; }
2244
2245
0
  for (j = 0; j < (SYS_N % 64); j+=8)
2246
0
    e[ j/8 ] = (e_int[i] >> j) & 0xFF;
2247
0
}
2248
2249
/* input: public key pk, error vector e */
2250
/* output: syndrome s */
2251
static void syndrome(unsigned char *s, const unsigned char *pk, unsigned char *e)
2252
0
{
2253
0
  uint64_t b;
2254
2255
0
  const uint64_t *pk_ptr;
2256
0
  const uint64_t *e_ptr = ((uint64_t *) (e + SYND_BYTES));
2257
2258
0
  int i, j;
2259
2260
  /**/
2261
2262
0
  for (i = 0; i < SYND_BYTES; i++)
2263
0
    s[i] = e[i];
2264
2265
0
  for (i = 0; i < PK_NROWS; i++)
2266
0
  {
2267
0
    pk_ptr = ((uint64_t *) (pk + PK_ROW_BYTES * i));
2268
2269
0
    b = 0;
2270
0
    for (j = 0; j < PK_NCOLS/64; j++)
2271
0
      b ^= pk_ptr[j] & e_ptr[j];
2272
2273
0
    b ^= ((uint32_t *) &pk_ptr[j])[0] & ((uint32_t *) &e_ptr[j])[0];
2274
2275
0
    b ^= b >> 32;
2276
0
    b ^= b >> 16;
2277
0
    b ^= b >> 8;
2278
0
    b ^= b >> 4;
2279
0
    b ^= b >> 2;
2280
0
    b ^= b >> 1;
2281
0
    b &= 1;
2282
2283
0
    s[ i/8 ] ^= (b << (i%8));
2284
0
  }
2285
0
}
2286
2287
/* input: public key pk */
2288
/* output: error vector e, syndrome s */
2289
static void pke_encrypt(unsigned char *s, const unsigned char *pk, unsigned char *e)
2290
0
{
2291
0
  gen_e(e);
2292
2293
#ifdef KAT
2294
  {
2295
    int k;
2296
    printf("encrypt e: positions");
2297
    for (k = 0;k < SYS_N;++k)
2298
      if (e[k/8] & (1 << (k&7)))
2299
        printf(" %d",k);
2300
    printf("\n");
2301
  }
2302
#endif
2303
2304
0
  syndrome(s, pk, e);
2305
0
}
2306
2307
2308
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_consts.c */
2309
/* linker define fft_consts */
2310
2311
2312
const vec fft_consts[128][GFBITS] = {
2313
{ 0x6969969669699696, 0x9966669966999966, 0x9966669966999966, 0xFF0000FF00FFFF00, 0xCC3333CCCC3333CC, 0x9966669966999966, 0x6666666666666666, 0xA55AA55AA55AA55A, 0xCCCC33333333CCCC, 0x5A5A5A5A5A5A5A5A, 0x55AAAA55AA5555AA, 0x0FF0F00FF00F0FF0, 0x5AA55AA5A55AA55A }, { 0x6969969669699696, 0x9966669966999966, 0x9966669966999966, 0xFF0000FF00FFFF00, 0xCC3333CCCC3333CC, 0x9966669966999966, 0x6666666666666666, 0xA55AA55AA55AA55A, 0xCCCC33333333CCCC, 0x5A5A5A5A5A5A5A5A, 0x55AAAA55AA5555AA, 0x0FF0F00FF00F0FF0, 0x5AA55AA5A55AA55A }, { 0xA55A5AA55AA5A55A, 0x6969696996969696, 0x5AA55AA5A55AA55A, 0x9999999966666666, 0x3C3CC3C3C3C33C3C, 0xFFFF0000FFFF0000, 0x0000000000000000, 0xCC33CC3333CC33CC, 0x0000000000000000, 0x3C3C3C3C3C3C3C3C, 0xAA5555AAAA5555AA, 0xC33C3CC33CC3C33C, 0x00FFFF0000FFFF00 }, { 0xA55A5AA55AA5A55A, 0x6969696996969696, 0x5AA55AA5A55AA55A, 0x6666666699999999, 0xC3C33C3C3C3CC3C3, 0x0000FFFF0000FFFF, 0x0000000000000000, 0x33CC33CCCC33CC33, 0x0000000000000000, 0x3C3C3C3C3C3C3C3C, 0xAA5555AAAA5555AA, 0xC33C3CC33CC3C33C, 0xFF0000FFFF0000FF }, { 0xFFFFFFFF00000000, 0xA5A5A5A55A5A5A5A, 0x0FF0F00FF00F0FF0, 0x9669966969966996, 0x0000FFFFFFFF0000, 0x33333333CCCCCCCC, 0xA55A5AA55AA5A55A, 0x00FFFF0000FFFF00, 0x0000000000000000, 0xC33CC33CC33CC33C, 0x0F0FF0F00F0FF0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAA55555555AAAA }, { 0xFFFFFFFF00000000, 0xA5A5A5A55A5A5A5A, 0x0FF0F00FF00F0FF0, 0x6996699696699669, 0xFFFF00000000FFFF, 0x33333333CCCCCCCC, 0x5AA5A55AA55A5AA5, 0xFF0000FFFF0000FF, 0xFFFFFFFFFFFFFFFF, 0xC33CC33CC33CC33C, 0x0F0FF0F00F0FF0F0, 0xCCCCCCCCCCCCCCCC, 0x5555AAAAAAAA5555 }, { 0xFFFFFFFF00000000, 0x5A5A5A5AA5A5A5A5, 0xF00F0FF00FF0F00F, 0x6996699696699669, 0x0000FFFFFFFF0000, 0x33333333CCCCCCCC, 0x5AA5A55AA55A5AA5, 0xFF0000FFFF0000FF, 0xFFFFFFFFFFFFFFFF, 0xC33CC33CC33CC33C, 0x0F0FF0F00F0FF0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAA55555555AAAA }, { 0xFFFFFFFF00000000, 0x5A5A5A5AA5A5A5A5, 0xF00F0FF00FF0F00F, 0x9669966969966996, 0xFFFF00000000FFFF, 0x33333333CCCCCCCC, 0xA55A5AA55AA5A55A, 0x00FFFF0000FFFF00, 0x0000000000000000, 0xC33CC33CC33CC33C, 0x0F0FF0F00F0FF0F0, 0xCCCCCCCCCCCCCCCC, 0x5555AAAAAAAA5555 }, { 0xC33C3CC33CC3C33C, 0x9966669966999966, 0x9966996699669966, 0x6969969669699696, 0xAA55AA5555AA55AA, 0x9966996699669966, 0x5AA5A55A5AA5A55A, 0xC3C3C3C33C3C3C3C, 0x3CC33CC3C33CC33C, 0x3333CCCC3333CCCC, 0x9999999966666666, 0xC33CC33CC33CC33C, 0x6666999999996666 }, { 0x3CC3C33CC33C3CC3, 0x6699996699666699, 0x6699669966996699, 0x6969969669699696, 0xAA55AA5555AA55AA, 0x9966996699669966, 0xA55A5AA5A55A5AA5, 0xC3C3C3C33C3C3C3C, 0x3CC33CC3C33CC33C, 0x3333CCCC3333CCCC, 0x6666666699999999, 0x3CC33CC33CC33CC3, 0x9999666666669999 }, { 0xC33C3CC33CC3C33C, 0x9966669966999966, 0x6699669966996699, 0x6969969669699696, 0xAA55AA5555AA55AA, 0x6699669966996699, 0x5AA5A55A5AA5A55A, 0x3C3C3C3CC3C3C3C3, 0xC33CC33C3CC33CC3, 0xCCCC3333CCCC3333, 0x6666666699999999, 0xC33CC33CC33CC33C, 0x9999666666669999 }, { 0x3CC3C33CC33C3CC3, 0x6699996699666699, 0x9966996699669966, 0x6969969669699696, 0xAA55AA5555AA55AA, 0x6699669966996699, 0xA55A5AA5A55A5AA5, 0x3C3C3C3CC3C3C3C3, 0xC33CC33C3CC33CC3, 0xCCCC3333CCCC3333, 0x9999999966666666, 0x3CC33CC33CC33CC3, 0x6666999999996666 }, { 0xC33C3CC33CC3C33C, 0x6699996699666699, 0x6699669966996699, 0x6969969669699696, 0x55AA55AAAA55AA55, 0x9966996699669966, 0x5AA5A55A5AA5A55A, 0xC3C3C3C33C3C3C3C, 0xC33CC33C3CC33CC3, 0x3333CCCC3333CCCC, 0x9999999966666666, 0xC33CC33CC33CC33C, 0x6666999999996666 }, { 0x3CC3C33CC33C3CC3, 0x9966669966999966, 0x9966996699669966, 0x6969969669699696, 0x55AA55AAAA55AA55, 0x9966996699669966, 0xA55A5AA5A55A5AA5, 0xC3C3C3C33C3C3C3C, 0xC33CC33C3CC33CC3, 0x3333CCCC3333CCCC, 0x6666666699999999, 0x3CC33CC33CC33CC3, 0x9999666666669999 }, { 0xC33C3CC33CC3C33C, 0x6699996699666699, 0x9966996699669966, 0x6969969669699696, 0x55AA55AAAA55AA55, 0x6699669966996699, 0x5AA5A55A5AA5A55A, 0x3C3C3C3CC3C3C3C3, 0x3CC33CC3C33CC33C, 0xCCCC3333CCCC3333, 0x6666666699999999, 0xC33CC33CC33CC33C, 0x9999666666669999 }, { 0x3CC3C33CC33C3CC3, 0x9966669966999966, 0x6699669966996699, 0x6969969669699696, 0x55AA55AAAA55AA55, 0x6699669966996699, 0xA55A5AA5A55A5AA5, 0x3C3C3C3CC3C3C3C3, 0x3CC33CC3C33CC33C, 0xCCCC3333CCCC3333, 0x9999999966666666, 0x3CC33CC33CC33CC3, 0x6666999999996666 }, { 0x3C3CC3C3C3C33C3C, 0x55555555AAAAAAAA, 0xF00FF00F0FF00FF0, 0x5AA55AA5A55AA55A, 0x55AAAA55AA5555AA, 0xF00F0FF0F00F0FF0, 0x9669699696696996, 0xA55AA55AA55AA55A, 0x55555555AAAAAAAA, 0xCCCC33333333CCCC, 0x0000FFFFFFFF0000, 0xFF0000FF00FFFF00, 0x6996699669966996 }, { 0xC3C33C3C3C3CC3C3, 0x55555555AAAAAAAA, 0x0FF00FF0F00FF00F, 0x5AA55AA5A55AA55A, 0x55AAAA55AA5555AA, 0xF00F0FF0F00F0FF0, 0x9669699696696996, 0x5AA55AA55AA55AA5, 0x55555555AAAAAAAA, 0x3333CCCCCCCC3333, 0x0000FFFFFFFF0000, 0x00FFFF00FF0000FF, 0x9669966996699669 }, { 0x3C3CC3C3C3C33C3C, 0x55555555AAAAAAAA, 0xF00FF00F0FF00FF0, 0xA55AA55A5AA55AA5, 0xAA5555AA55AAAA55, 0x0FF0F00F0FF0F00F, 0x9669699696696996, 0x5AA55AA55AA55AA5, 0xAAAAAAAA55555555, 0x3333CCCCCCCC3333, 0xFFFF00000000FFFF, 0xFF0000FF00FFFF00, 0x9669966996699669 }, { 0xC3C33C3C3C3CC3C3, 0x55555555AAAAAAAA, 0x0FF00FF0F00FF00F, 0xA55AA55A5AA55AA5, 0xAA5555AA55AAAA55, 0x0FF0F00F0FF0F00F, 0x9669699696696996, 0xA55AA55AA55AA55A, 0xAAAAAAAA55555555, 0xCCCC33333333CCCC, 0xFFFF00000000FFFF, 0x00FFFF00FF0000FF, 0x6996699669966996 }, { 0x3C3CC3C3C3C33C3C, 0x55555555AAAAAAAA, 0x0FF00FF0F00FF00F, 0xA55AA55A5AA55AA5, 0xAA5555AA55AAAA55, 0x0FF0F00F0FF0F00F, 0x6996966969969669, 0xA55AA55AA55AA55A, 0xAAAAAAAA55555555, 0xCCCC33333333CCCC, 0x0000FFFFFFFF0000, 0xFF0000FF00FFFF00, 0x6996699669966996 }, { 0xC3C33C3C3C3CC3C3, 0x55555555AAAAAAAA, 0xF00FF00F0FF00FF0, 0xA55AA55A5AA55AA5, 0xAA5555AA55AAAA55, 0x0FF0F00F0FF0F00F, 0x6996966969969669, 0x5AA55AA55AA55AA5, 0xAAAAAAAA55555555, 0x3333CCCCCCCC3333, 0x0000FFFFFFFF0000, 0x00FFFF00FF0000FF, 0x9669966996699669 }, { 0x3C3CC3C3C3C33C3C, 0x55555555AAAAAAAA, 0x0FF00FF0F00FF00F, 0x5AA55AA5A55AA55A, 0x55AAAA55AA5555AA, 0xF00F0FF0F00F0FF0, 0x6996966969969669, 0x5AA55AA55AA55AA5, 0x55555555AAAAAAAA, 0x3333CCCCCCCC3333, 0xFFFF00000000FFFF, 0xFF0000FF00FFFF00, 0x9669966996699669 }, { 0xC3C33C3C3C3CC3C3, 0x55555555AAAAAAAA, 0xF00FF00F0FF00FF0, 0x5AA55AA5A55AA55A, 0x55AAAA55AA5555AA, 0xF00F0FF0F00F0FF0, 0x6996966969969669, 0xA55AA55AA55AA55A, 0x55555555AAAAAAAA, 0xCCCC33333333CCCC, 0xFFFF00000000FFFF, 0x00FFFF00FF0000FF, 0x6996699669966996 }, { 0x3C3CC3C3C3C33C3C, 0xAAAAAAAA55555555, 0x0FF00FF0F00FF00F, 0x5AA55AA5A55AA55A, 0xAA5555AA55AAAA55, 0xF00F0FF0F00F0FF0, 0x9669699696696996, 0xA55AA55AA55AA55A, 0x55555555AAAAAAAA, 0xCCCC33333333CCCC, 0x0000FFFFFFFF0000, 0xFF0000FF00FFFF00, 0x6996699669966996 }, { 0xC3C33C3C3C3CC3C3, 0xAAAAAAAA55555555, 0xF00FF00F0FF00FF0, 0x5AA55AA5A55AA55A, 0xAA5555AA55AAAA55, 0xF00F0FF0F00F0FF0, 0x9669699696696996, 0x5AA55AA55AA55AA5, 0x55555555AAAAAAAA, 0x3333CCCCCCCC3333, 0x0000FFFFFFFF0000, 0x00FFFF00FF0000FF, 0x9669966996699669 }, { 0x3C3CC3C3C3C33C3C, 0xAAAAAAAA55555555, 0x0FF00FF0F00FF00F, 0xA55AA55A5AA55AA5, 0x55AAAA55AA5555AA, 0x0FF0F00F0FF0F00F, 0x9669699696696996, 0x5AA55AA55AA55AA5, 0xAAAAAAAA55555555, 0x3333CCCCCCCC3333, 0xFFFF00000000FFFF, 0xFF0000FF00FFFF00, 0x9669966996699669 }, { 0xC3C33C3C3C3CC3C3, 0xAAAAAAAA55555555, 0xF00FF00F0FF00FF0, 0xA55AA55A5AA55AA5, 0x55AAAA55AA5555AA, 0x0FF0F00F0FF0F00F, 0x9669699696696996, 0xA55AA55AA55AA55A, 0xAAAAAAAA55555555, 0xCCCC33333333CCCC, 0xFFFF00000000FFFF, 0x00FFFF00FF0000FF, 0x6996699669966996 }, { 0x3C3CC3C3C3C33C3C, 0xAAAAAAAA55555555, 0xF00FF00F0FF00FF0, 0xA55AA55A5AA55AA5, 0x55AAAA55AA5555AA, 0x0FF0F00F0FF0F00F, 0x6996966969969669, 0xA55AA55AA55AA55A, 0xAAAAAAAA55555555, 0xCCCC33333333CCCC, 0x0000FFFFFFFF0000, 0xFF0000FF00FFFF00, 0x6996699669966996 }, { 0xC3C33C3C3C3CC3C3, 0xAAAAAAAA55555555, 0x0FF00FF0F00FF00F, 0xA55AA55A5AA55AA5, 0x55AAAA55AA5555AA, 0x0FF0F00F0FF0F00F, 0x6996966969969669, 0x5AA55AA55AA55AA5, 0xAAAAAAAA55555555, 0x3333CCCCCCCC3333, 0x0000FFFFFFFF0000, 0x00FFFF00FF0000FF, 0x9669966996699669 }, { 0x3C3CC3C3C3C33C3C, 0xAAAAAAAA55555555, 0xF00FF00F0FF00FF0, 0x5AA55AA5A55AA55A, 0xAA5555AA55AAAA55, 0xF00F0FF0F00F0FF0, 0x6996966969969669, 0x5AA55AA55AA55AA5, 0x55555555AAAAAAAA, 0x3333CCCCCCCC3333, 0xFFFF00000000FFFF, 0xFF0000FF00FFFF00, 0x9669966996699669 }, { 0xC3C33C3C3C3CC3C3, 0xAAAAAAAA55555555, 0x0FF00FF0F00FF00F, 0x5AA55AA5A55AA55A, 0xAA5555AA55AAAA55, 0xF00F0FF0F00F0FF0, 0x6996966969969669, 0xA55AA55AA55AA55A, 0x55555555AAAAAAAA, 0xCCCC33333333CCCC, 0xFFFF00000000FFFF, 0x00FFFF00FF0000FF, 0x6996699669966996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0xAAAAAAAAAAAAAAAA, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0x0000FFFF0000FFFF, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0xC33C3CC3C33C3CC3, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0x55AA55AA55AA55AA, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0xFFFF0000FFFF0000, 0x0F0F0F0FF0F0F0F0, 0x00FFFF00FF0000FF, 0xCC3333CC33CCCC33, 0xFF0000FF00FFFF00, 0x6996966996696996, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x3CC3C33C3CC3C33C, 0x5555555555555555, 0xFFFF0000FFFF0000, 0x3CC3C33C3CC3C33C, 0xAA55AA55AA55AA55, 0x0000FFFF0000FFFF, 0xF0F0F0F00F0F0F0F, 0xFF0000FF00FFFF00, 0x33CCCC33CC3333CC, 0x00FFFF00FF0000FF, 0x9669699669969669, 0xA55A5AA55AA5A55A, 0x6996966996696996 }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF0000FFFF0000, 0xFF00FF00FF00FF00, 0xF0F0F0F0F0F0F0F0, 0xCCCCCCCCCCCCCCCC, 0xAAAAAAAAAAAAAAAA },
2314
};
2315
2316
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_powers.c */
2317
/* linker define fft_powers */
2318
2319
2320
const vec fft_powers[128][GFBITS] = {
2321
{ 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0x00000000FFFFFFFF, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0x5A5A5A5A5A5A5A5A, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0xCC33CC33CC33CC33, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0xCC33CC33CC33CC33, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x9696969669696969, 0xA5A5A5A5A5A5A5A5, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0x0F0FF0F00F0FF0F0 }, { 0xA55AA55A5AA55AA5, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0x5A5A5A5A5A5A5A5A, 0xA5A5A5A55A5A5A5A, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0x3CC33CC3C33CC33C, 0xA5A55A5AA5A55A5A, 0x0000FFFF0000FFFF, 0x33CC33CC33CC33CC, 0xF00FF00F0FF00FF0, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0x5555AAAAAAAA5555, 0xF00FF00FF00FF00F, 0xF0F00F0FF0F00F0F }, { 0x5AA55AA5A55AA55A, 0xC33CC33C3CC33CC3, 0xA5A55A5AA5A55A5A, 0xFFFF0000FFFF0000, 0x33CC33CC33CC33CC, 0x0FF00FF0F00FF00F, 0xFFFFFFFF00000000, 0x6969696996969696, 0xA5A5A5A5A5A5A5A5, 0x5A5A5A5AA5A5A5A5, 0xAAAA55555555AAAA, 0x0FF00FF00FF00FF0, 0x0F0FF0F00F0FF0F0 }
2322
};
2323
2324
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_2x.c */
2325
/* linker define fft_scalars_2x */
2326
2327
2328
const vec fft_scalars_2x[5][2][GFBITS] = {
2329
{{ 0X3C3CF30C0000C003, 0X0CCCC3F333C0000C, 0X03C33F33FCC0C03C, 0X0003000F3C03C0C0, 0XF33FF33030CF03F0, 0X0CF0303300F0CCC0, 0XFF3F0C0CC0FF3CC0, 0XCF3CF0FF003FC000, 0XC00FF3CF0303F300, 0X3CCC0CC00CF0CC00, 0XF30FFC3C3FCCFC00, 0X3F0FC3F0CCF0C000, 0X3000FF33CCF0F000 }, { 0X0C0F0FCF0F0CF330, 0XF0000FC33C3CCF3C, 0X3C0F3F00C3C300FC, 0X3C33CCC0F0F3CC30, 0XC0CFFFFFCCCC30CC, 0X3FC3F3CCFFFC033F, 0XFC3030CCCCC0CFCF, 0X0FCF0C00CCF333C3, 0XCFFCF33000CFF030, 0X00CFFCC330F30FCC, 0X3CCC3FCCC0F3FFF3, 0XF00F0C3FC003C0FF, 0X330CCFCC03C0FC33 }}, {{ 0X0F0F0FF0F000000F, 0X00FFFFFFFF0000F0, 0XFFFF00FF00000F00, 0XFFF000F00F0FF000, 0XFFF0000F0FF000F0, 0X00FF000FFF000000, 0XFF0F0FFF0F0FF000, 0X0FFF0000000F0000, 0X00F000F0FFF00F00, 0X00F00FF00F00F000, 0XFFF000F000F00000, 0X00F00F000FF00000, 0X0000FF0F0000F000 }, { 0XF0FFFFFFF0F00F00, 0X00FFF0FFFF0000FF, 0X00FF00000F0F0FFF, 0XF000F0000F00FF0F, 0XFF000000FFF00000, 0XF0FF000FF00F0FF0, 0X0F0F0F00FF000F0F, 0X0F0F00F0F0F0F000, 0X00F00F00F00F000F, 0X00F0F0F00000FFF0, 0XFFFFFF0FF00F0FFF, 0X0F0FFFF00FFFFFFF, 0XFFFF0F0FFF0FFF00 }}, {{ 0X00FF0000000000FF, 0XFFFFFFFFFF00FF00, 0XFF0000FF00FF0000, 0XFFFF000000FF0000, 0XFF00000000FF0000, 0X00FFFFFFFF000000, 0XFF0000FFFFFF0000, 0XFF00FF00FFFF0000, 0X00FFFFFFFF00FF00, 0XFFFF000000000000, 0X00FF0000FF000000, 0XFF00FF00FF000000, 0X00FF00FFFF000000 }, { 0X00FF00FF00FF0000, 0XFF00FFFF000000FF, 0X0000FFFF000000FF, 0X00FFFF00FF000000, 0XFFFFFF0000FF00FF, 0X0000FFFF00FFFF00, 0XFF00FF0000FFFF00, 0X00000000FFFFFFFF, 0X0000FF0000000000, 0XFF00FFFF00FFFF00, 0X00FFFF00000000FF, 0X0000FF00FF00FFFF, 0XFF0000FFFFFF0000 }}, {{ 0X000000000000FFFF, 0XFFFFFFFFFFFF0000, 0X0000000000000000, 0XFFFF0000FFFF0000, 0XFFFFFFFFFFFF0000, 0X0000FFFF00000000, 0X0000FFFFFFFF0000, 0XFFFF0000FFFF0000, 0X0000FFFF00000000, 0XFFFF000000000000, 0XFFFF000000000000, 0XFFFF000000000000, 0XFFFFFFFF00000000 }, { 0X0000FFFF00000000, 0XFFFFFFFF0000FFFF, 0X00000000FFFFFFFF, 0X0000000000000000, 0X0000FFFF00000000, 0XFFFF0000FFFF0000, 0X0000FFFFFFFF0000, 0X0000FFFF0000FFFF, 0XFFFFFFFF0000FFFF, 0X00000000FFFF0000, 0XFFFF0000FFFFFFFF, 0XFFFF0000FFFFFFFF, 0X0000000000000000 }}, {{ 0X00000000FFFFFFFF, 0X0000000000000000, 0XFFFFFFFF00000000, 0X0000000000000000, 0XFFFFFFFF00000000, 0XFFFFFFFF00000000, 0XFFFFFFFF00000000, 0X0000000000000000, 0XFFFFFFFF00000000, 0X0000000000000000, 0X0000000000000000, 0X0000000000000000, 0XFFFFFFFF00000000 }, { 0X0000000000000000, 0XFFFFFFFFFFFFFFFF, 0X0000000000000000, 0X0000000000000000, 0X00000000FFFFFFFF, 0XFFFFFFFF00000000, 0X0000000000000000, 0XFFFFFFFFFFFFFFFF, 0X00000000FFFFFFFF, 0XFFFFFFFF00000000, 0XFFFFFFFFFFFFFFFF, 0XFFFFFFFFFFFFFFFF, 0XFFFFFFFF00000000 }}
2330
};
2331
2332
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_4x.c */
2333
/* linker define fft_scalars_4x */
2334
2335
2336
const vec fft_scalars_4x[6][4][GFBITS] = {
2337
{{ 0x3C3CF30C0000C003, 0x0CCCC3F333C0000C, 0x03C33F33FCC0C03C, 0x0003000F3C03C0C0, 0xF33FF33030CF03F0, 0x0CF0303300F0CCC0, 0xFF3F0C0CC0FF3CC0, 0xCF3CF0FF003FC000, 0xC00FF3CF0303F300, 0x3CCC0CC00CF0CC00, 0xF30FFC3C3FCCFC00, 0x3F0FC3F0CCF0C000, 0x3000FF33CCF0F000 }, { 0x0C0F0FCF0F0CF330, 0xF0000FC33C3CCF3C, 0x3C0F3F00C3C300FC, 0x3C33CCC0F0F3CC30, 0xC0CFFFFFCCCC30CC, 0x3FC3F3CCFFFC033F, 0xFC3030CCCCC0CFCF, 0x0FCF0C00CCF333C3, 0xCFFCF33000CFF030, 0x00CFFCC330F30FCC, 0x3CCC3FCCC0F3FFF3, 0xF00F0C3FC003C0FF, 0x330CCFCC03C0FC33 }, { 0xF0F30C33CF03F03F, 0x00F30FC00C3300FF, 0xF3CC3CF3F3FCF33F, 0x3C0FC0FC303C3F3C, 0xFC30CF303F3FF00F, 0x33300C0CC3300CF3, 0x3C030CF3F03FF3F3, 0x3CCC03FCCC3FFC03, 0x033C3C3CF0003FC3, 0xFFC0FF00F0FF0F03, 0xF3F30CF003FCC303, 0x30CFCFC3CC0F3000, 0x0CF30CCF3FCFCC0F }, { 0x3F30CC0C000F3FCC, 0xFC3CF030FC3FFF03, 0x33FFFCFF0CCF3CC3, 0x003CFF33C3CC30CF, 0xCFF3CF33C00F3003, 0x00F3CC0CF3003CCF, 0x3C000CFCCC3C3333, 0xF3CF03C0FCF03FF0, 0x3F3C3CF0C330330C, 0x33CCFCC0FF0033F0, 0x33C300C0F0C003F3, 0x003FF0003F00C00C, 0xCFF3C3033F030FFF }}, {{ 0x0F0F0FF0F000000F, 0x00FFFFFFFF0000F0, 0xFFFF00FF00000F00, 0xFFF000F00F0FF000, 0xFFF0000F0FF000F0, 0x00FF000FFF000000, 0xFF0F0FFF0F0FF000, 0x0FFF0000000F0000, 0x00F000F0FFF00F00, 0x00F00FF00F00F000, 0xFFF000F000F00000, 0x00F00F000FF00000, 0x0000FF0F0000F000 }, { 0xF0FFFFFFF0F00F00, 0x00FFF0FFFF0000FF, 0x00FF00000F0F0FFF, 0xF000F0000F00FF0F, 0xFF000000FFF00000, 0xF0FF000FF00F0FF0, 0x0F0F0F00FF000F0F, 0x0F0F00F0F0F0F000, 0x00F00F00F00F000F, 0x00F0F0F00000FFF0, 0xFFFFFF0FF00F0FFF, 0x0F0FFFF00FFFFFFF, 0xFFFF0F0FFF0FFF00 }, { 0x0F0F00FF0FF0FFFF, 0xF000F0F00F00FF0F, 0x000FFFF0FFF0FF0F, 0x00F00FFF00000FF0, 0xFFFFF0000FFFF00F, 0xFFF0FFF0000FFFF0, 0xF0F0F0000F0F0F00, 0x00F000F0F00FFF00, 0xF0FF0F0FFF00F0FF, 0xF0FF0FFFF0F0F0FF, 0x00FFFFFFFFFFFFF0, 0x00FFF0F0FF000F0F, 0x000FFFF0000FFF00 }, { 0xFF0F0F00F000F0FF, 0x0FFFFFFFFF00000F, 0xF0FFFF000F00F0FF, 0x0F0000F00FFF0FFF, 0x0F0F0F00FF0F000F, 0x000F0F0FFFF0F000, 0xF0FFFF0F00F0FF0F, 0x0F0F000F0F00F0FF, 0x0000F0FF00FF0F0F, 0x00FFFF0FF0FFF0F0, 0x0000000F00F0FFF0, 0xF0F00000FF00F0F0, 0x0F0F0FFFFFFFFFFF }}, {{ 0x00FF0000000000FF, 0xFFFFFFFFFF00FF00, 0xFF0000FF00FF0000, 0xFFFF000000FF0000, 0xFF00000000FF0000, 0x00FFFFFFFF000000, 0xFF0000FFFFFF0000, 0xFF00FF00FFFF0000, 0x00FFFFFFFF00FF00, 0xFFFF000000000000, 0x00FF0000FF000000, 0xFF00FF00FF000000, 0x00FF00FFFF000000 }, { 0x00FF00FF00FF0000, 0xFF00FFFF000000FF, 0x0000FFFF000000FF, 0x00FFFF00FF000000, 0xFFFFFF0000FF00FF, 0x0000FFFF00FFFF00, 0xFF00FF0000FFFF00, 0x00000000FFFFFFFF, 0x0000FF0000000000, 0xFF00FFFF00FFFF00, 0x00FFFF00000000FF, 0x0000FF00FF00FFFF, 0xFF0000FFFFFF0000 }, { 0xFFFF00FF00FF00FF, 0x00FFFF000000FF00, 0xFFFF00FFFFFFFF00, 0x0000FFFF00FFFFFF, 0x00FF0000FF0000FF, 0xFFFF0000FF00FFFF, 0xFF000000FFFFFF00, 0x000000000000FFFF, 0xFF00FF00FFFF0000, 0xFFFF00FFFF00FFFF, 0xFFFFFFFFFF00FF00, 0xFFFF00FFFF0000FF, 0x0000FF00000000FF }, { 0xFF0000FFFFFF00FF, 0xFFFF0000FFFFFFFF, 0xFFFF000000FFFFFF, 0x00FFFF00FF0000FF, 0xFFFFFF00FFFFFF00, 0x00FFFF00FFFF00FF, 0x0000FFFF00FF0000, 0x000000FFFF000000, 0xFF00FF0000FF00FF, 0x00FF0000000000FF, 0xFF00FFFF00FF00FF, 0xFFFFFFFFFFFFFFFF, 0x0000FF000000FFFF }}, {{ 0x000000000000FFFF, 0xFFFFFFFFFFFF0000, 0x0000000000000000, 0xFFFF0000FFFF0000, 0xFFFFFFFFFFFF0000, 0x0000FFFF00000000, 0x0000FFFFFFFF0000, 0xFFFF0000FFFF0000, 0x0000FFFF00000000, 0xFFFF000000000000, 0xFFFF000000000000, 0xFFFF000000000000, 0xFFFFFFFF00000000 }, { 0x0000FFFF00000000, 0xFFFFFFFF0000FFFF, 0x00000000FFFFFFFF, 0x0000000000000000, 0x0000FFFF00000000, 0xFFFF0000FFFF0000, 0x0000FFFFFFFF0000, 0x0000FFFF0000FFFF, 0xFFFFFFFF0000FFFF, 0x00000000FFFF0000, 0xFFFF0000FFFFFFFF, 0xFFFF0000FFFFFFFF, 0x0000000000000000 }, { 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFF000000000000, 0x0000FFFF00000000, 0x00000000FFFF0000, 0x0000FFFFFFFFFFFF, 0x0000FFFFFFFFFFFF, 0xFFFFFFFF00000000, 0x000000000000FFFF, 0x000000000000FFFF, 0xFFFFFFFFFFFF0000, 0xFFFFFFFF0000FFFF, 0xFFFF0000FFFFFFFF }, { 0x0000FFFFFFFFFFFF, 0x0000FFFF0000FFFF, 0x0000FFFFFFFF0000, 0xFFFF0000FFFFFFFF, 0x00000000FFFF0000, 0xFFFF00000000FFFF, 0x0000FFFF0000FFFF, 0xFFFF00000000FFFF, 0x0000FFFF0000FFFF, 0x0000FFFF00000000, 0xFFFFFFFF00000000, 0x0000FFFFFFFF0000, 0x0000FFFFFFFFFFFF }}, {{ 0x00000000FFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0xFFFFFFFF00000000, 0xFFFFFFFF00000000, 0x0000000000000000, 0xFFFFFFFF00000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFF00000000 }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x00000000FFFFFFFF, 0xFFFFFFFF00000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x00000000FFFFFFFF, 0xFFFFFFFF00000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000 }, { 0x00000000FFFFFFFF, 0xFFFFFFFF00000000, 0xFFFFFFFF00000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0x00000000FFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF }, { 0xFFFFFFFFFFFFFFFF, 0x00000000FFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFF00000000, 0x00000000FFFFFFFF, 0xFFFFFFFF00000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFF00000000, 0xFFFFFFFF00000000 }}, {{ 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000 }, { 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000 }, { 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF }, { 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF, 0xFFFFFFFFFFFFFFFF, 0x0000000000000000, 0xFFFFFFFFFFFFFFFF }},
2338
};
2339
2340
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft.c */
2341
/*
2342
  This file is for implementing the Gao-Mateer FFT, see
2343
  http://www.math.clemson.edu/~sgao/papers/GM10.pdf
2344
2345
  For the implementation strategy, see
2346
  https://eprint.iacr.org/2017/793.pdf
2347
*/
2348
/* 20221230 djb: split these arrays into separate .c files */
2349
/* 20221230 djb: rename powers array as fft_powers */
2350
/* 20221230 djb: rename consts array as fft_consts */
2351
/* 20221230 djb: rename s array as fft_scalars_2x */
2352
/* 20221230 djb: add linker lines */
2353
2354
/* linker define fft */
2355
/* linker use vec_mul */
2356
/* linker use fft_scalars_2x fft_consts fft_powers */
2357
2358
2359
2360
2361
/* input: in, polynomial in bitsliced form */
2362
/* output: in, result of applying the radix conversions on in */
2363
static void radix_conversions(vec in[][GFBITS])
2364
0
{
2365
0
  int i, j, k;
2366
2367
0
  const vec mask[5][2] =
2368
0
  {
2369
0
    {0x8888888888888888, 0x4444444444444444},
2370
0
    {0xC0C0C0C0C0C0C0C0, 0x3030303030303030},
2371
0
    {0xF000F000F000F000, 0x0F000F000F000F00},
2372
0
    {0xFF000000FF000000, 0x00FF000000FF0000},
2373
0
    {0xFFFF000000000000, 0x0000FFFF00000000}
2374
0
  };
2375
2376
0
  for (j = 0; j <= 5; j++)
2377
0
  {
2378
0
    for (i = 0; i < GFBITS; i++)
2379
0
    {
2380
0
      in[1][i] ^= in[1][i] >> 32;
2381
0
      in[0][i] ^= in[1][i] << 32;
2382
0
    }
2383
2384
0
    for (i = 0; i < GFBITS; i++)
2385
0
    for (k = 4; k >= j; k--)
2386
0
    {
2387
0
      in[0][i] ^= (in[0][i] & mask[k][0]) >> (1 << k);
2388
0
      in[0][i] ^= (in[0][i] & mask[k][1]) >> (1 << k);
2389
0
      in[1][i] ^= (in[1][i] & mask[k][0]) >> (1 << k);
2390
0
      in[1][i] ^= (in[1][i] & mask[k][1]) >> (1 << k);
2391
0
    }
2392
2393
0
    if (j < 5)
2394
0
    {
2395
0
      vec_mul(in[0], in[0], fft_scalars_2x[j][0]);
2396
0
      vec_mul(in[1], in[1], fft_scalars_2x[j][1]);
2397
0
    }
2398
0
  }
2399
0
}
2400
2401
/* input: in, result of applying the radix conversions to the input polynomial */
2402
/* output: out, evaluation results (by applying the FFT butterflies) */
2403
static void butterflies(vec out[][ GFBITS ], vec in[][ GFBITS ])
2404
0
{
2405
0
  int i, j, k, s, b;
2406
2407
0
  vec tmp[ GFBITS ];
2408
0
  vec pre[8][ GFBITS ];
2409
0
  vec buf[128];
2410
2411
0
  uint64_t consts_ptr = 2;
2412
2413
0
  const unsigned char reversal[128] =
2414
0
  {
2415
0
    0, 64, 32, 96, 16, 80, 48, 112,
2416
0
    8, 72, 40, 104, 24, 88, 56, 120,
2417
0
    4, 68, 36, 100, 20, 84, 52, 116,
2418
0
    12, 76, 44, 108, 28, 92, 60, 124,
2419
0
    2, 66, 34, 98, 18, 82, 50, 114,
2420
0
    10, 74, 42, 106, 26, 90, 58, 122,
2421
0
    6, 70, 38, 102, 22, 86, 54, 118,
2422
0
    14, 78, 46, 110, 30, 94, 62, 126,
2423
0
    1, 65, 33, 97, 17, 81, 49, 113,
2424
0
    9, 73, 41, 105, 25, 89, 57, 121,
2425
0
    5, 69, 37, 101, 21, 85, 53, 117,
2426
0
    13, 77, 45, 109, 29, 93, 61, 125,
2427
0
    3, 67, 35, 99, 19, 83, 51, 115,
2428
0
    11, 75, 43, 107, 27, 91, 59, 123,
2429
0
    7, 71, 39, 103, 23, 87, 55, 119,
2430
0
    15, 79, 47, 111, 31, 95, 63, 127
2431
0
  };
2432
2433
0
  const uint16_t beta[7] = {2522, 7827, 7801, 8035, 6897, 8167, 3476};
2434
2435
  /**/
2436
2437
0
  for (i = 0; i < 7; i++)
2438
0
  {
2439
0
    for (j = 0; j < GFBITS; j++)
2440
0
    {
2441
0
      pre[i][j] = (beta[i] >> j) & 1;
2442
0
      pre[i][j] = -pre[i][j];
2443
0
    }
2444
2445
0
    vec_mul(pre[i], in[1], pre[i]);
2446
0
  }
2447
2448
0
  for (i = 0; i < GFBITS; i++)
2449
0
  {
2450
0
    buf[0] = in[0][i];
2451
2452
0
    buf[1] = buf[0] ^ pre[0][i];      buf[32] = in[0][i] ^ pre[5][i];
2453
0
    buf[3] = buf[1] ^ pre[1][i];      buf[96] = buf[32] ^ pre[6][i];
2454
0
                                              buf[97] = buf[96] ^ pre[0][i];
2455
0
    buf[2] = in[0][i] ^ pre[1][i];  buf[99] = buf[97] ^ pre[1][i];
2456
0
    buf[6] = buf[2] ^ pre[2][i];      buf[98] = buf[99] ^ pre[0][i];
2457
0
    buf[7] = buf[6] ^ pre[0][i];      buf[102] = buf[98] ^ pre[2][i];
2458
0
    buf[5] = buf[7] ^ pre[1][i];      buf[103] = buf[102] ^ pre[0][i];
2459
0
                                              buf[101] = buf[103] ^ pre[1][i];
2460
0
    buf[4] = in[0][i] ^ pre[2][i];  buf[100] = buf[101] ^ pre[0][i];
2461
0
    buf[12] = buf[4] ^ pre[3][i];     buf[108] = buf[100] ^ pre[3][i];
2462
0
    buf[13] = buf[12] ^ pre[0][i];    buf[109] = buf[108] ^ pre[0][i];
2463
0
    buf[15] = buf[13] ^ pre[1][i];    buf[111] = buf[109] ^ pre[1][i];
2464
0
    buf[14] = buf[15] ^ pre[0][i];    buf[110] = buf[111] ^ pre[0][i];
2465
0
    buf[10] = buf[14] ^ pre[2][i];    buf[106] = buf[110] ^ pre[2][i];
2466
0
    buf[11] = buf[10] ^ pre[0][i];    buf[107] = buf[106] ^ pre[0][i];
2467
0
    buf[9] = buf[11] ^ pre[1][i];     buf[105] = buf[107] ^ pre[1][i];
2468
0
                                              buf[104] = buf[105] ^ pre[0][i];
2469
0
    buf[8] = in[0][i] ^ pre[3][i];  buf[120] = buf[104] ^ pre[4][i];
2470
0
    buf[24] = buf[8] ^ pre[4][i];     buf[121] = buf[120] ^ pre[0][i];
2471
0
    buf[25] = buf[24] ^ pre[0][i];    buf[123] = buf[121] ^ pre[1][i];
2472
0
    buf[27] = buf[25] ^ pre[1][i];    buf[122] = buf[123] ^ pre[0][i];
2473
0
    buf[26] = buf[27] ^ pre[0][i];    buf[126] = buf[122] ^ pre[2][i];
2474
0
    buf[30] = buf[26] ^ pre[2][i];    buf[127] = buf[126] ^ pre[0][i];
2475
0
    buf[31] = buf[30] ^ pre[0][i];    buf[125] = buf[127] ^ pre[1][i];
2476
0
    buf[29] = buf[31] ^ pre[1][i];    buf[124] = buf[125] ^ pre[0][i];
2477
0
    buf[28] = buf[29] ^ pre[0][i];    buf[116] = buf[124] ^ pre[3][i];
2478
0
    buf[20] = buf[28] ^ pre[3][i];    buf[117] = buf[116] ^ pre[0][i];
2479
0
    buf[21] = buf[20] ^ pre[0][i];    buf[119] = buf[117] ^ pre[1][i];
2480
0
    buf[23] = buf[21] ^ pre[1][i];    buf[118] = buf[119] ^ pre[0][i];
2481
0
    buf[22] = buf[23] ^ pre[0][i];    buf[114] = buf[118] ^ pre[2][i];
2482
0
    buf[18] = buf[22] ^ pre[2][i];    buf[115] = buf[114] ^ pre[0][i];
2483
0
    buf[19] = buf[18] ^ pre[0][i];    buf[113] = buf[115] ^ pre[1][i];
2484
0
    buf[17] = buf[19] ^ pre[1][i];    buf[112] = buf[113] ^ pre[0][i];
2485
0
                                              buf[80] = buf[112] ^ pre[5][i];
2486
0
    buf[16] = in[0][i] ^ pre[4][i]; buf[81] = buf[80] ^ pre[0][i];
2487
0
    buf[48] = buf[16] ^ pre[5][i];    buf[83] = buf[81] ^ pre[1][i];
2488
0
    buf[49] = buf[48] ^ pre[0][i];    buf[82] = buf[83] ^ pre[0][i];
2489
0
    buf[51] = buf[49] ^ pre[1][i];    buf[86] = buf[82] ^ pre[2][i];
2490
0
    buf[50] = buf[51] ^ pre[0][i];    buf[87] = buf[86] ^ pre[0][i];
2491
0
    buf[54] = buf[50] ^ pre[2][i];    buf[85] = buf[87] ^ pre[1][i];
2492
0
    buf[55] = buf[54] ^ pre[0][i];    buf[84] = buf[85] ^ pre[0][i];
2493
0
    buf[53] = buf[55] ^ pre[1][i];    buf[92] = buf[84] ^ pre[3][i];
2494
0
    buf[52] = buf[53] ^ pre[0][i];    buf[93] = buf[92] ^ pre[0][i];
2495
0
    buf[60] = buf[52] ^ pre[3][i];    buf[95] = buf[93] ^ pre[1][i];
2496
0
    buf[61] = buf[60] ^ pre[0][i];    buf[94] = buf[95] ^ pre[0][i];
2497
0
    buf[63] = buf[61] ^ pre[1][i];    buf[90] = buf[94] ^ pre[2][i];
2498
0
    buf[62] = buf[63] ^ pre[0][i];    buf[91] = buf[90] ^ pre[0][i];
2499
0
    buf[58] = buf[62] ^ pre[2][i];    buf[89] = buf[91] ^ pre[1][i];
2500
0
    buf[59] = buf[58] ^ pre[0][i];    buf[88] = buf[89] ^ pre[0][i];
2501
0
    buf[57] = buf[59] ^ pre[1][i];    buf[72] = buf[88] ^ pre[4][i];
2502
0
    buf[56] = buf[57] ^ pre[0][i];    buf[73] = buf[72] ^ pre[0][i];
2503
0
    buf[40] = buf[56] ^ pre[4][i];    buf[75] = buf[73] ^ pre[1][i];
2504
0
    buf[41] = buf[40] ^ pre[0][i];    buf[74] = buf[75] ^ pre[0][i];
2505
0
    buf[43] = buf[41] ^ pre[1][i];    buf[78] = buf[74] ^ pre[2][i];
2506
0
    buf[42] = buf[43] ^ pre[0][i];    buf[79] = buf[78] ^ pre[0][i];
2507
0
    buf[46] = buf[42] ^ pre[2][i];    buf[77] = buf[79] ^ pre[1][i];
2508
0
    buf[47] = buf[46] ^ pre[0][i];    buf[76] = buf[77] ^ pre[0][i];
2509
0
    buf[45] = buf[47] ^ pre[1][i];    buf[68] = buf[76] ^ pre[3][i];
2510
0
    buf[44] = buf[45] ^ pre[0][i];    buf[69] = buf[68] ^ pre[0][i];
2511
0
    buf[36] = buf[44] ^ pre[3][i];    buf[71] = buf[69] ^ pre[1][i];
2512
0
    buf[37] = buf[36] ^ pre[0][i];    buf[70] = buf[71] ^ pre[0][i];
2513
0
    buf[39] = buf[37] ^ pre[1][i];    buf[66] = buf[70] ^ pre[2][i];
2514
0
    buf[38] = buf[39] ^ pre[0][i];    buf[67] = buf[66] ^ pre[0][i];
2515
0
    buf[34] = buf[38] ^ pre[2][i];    buf[65] = buf[67] ^ pre[1][i];
2516
0
    buf[35] = buf[34] ^ pre[0][i];
2517
0
    buf[33] = buf[35] ^ pre[1][i];    buf[64] = in[0][i] ^ pre[6][i];
2518
2519
0
    transpose_64x64(buf +  0, buf +  0);
2520
0
    transpose_64x64(buf + 64, buf + 64);
2521
2522
0
    for (j = 0; j < 128; j++)
2523
0
      out[ reversal[j] ][i] = buf[j];
2524
0
  }
2525
2526
0
  for (i = 1; i <= 6; i++)
2527
0
  {
2528
0
    s = 1 << i;
2529
2530
0
    for (j = 0; j < 128; j += 2*s)
2531
0
    for (k = j; k < j+s; k++)
2532
0
    {
2533
0
      vec_mul(tmp, out[k+s], fft_consts[ consts_ptr + (k-j) ]);
2534
2535
0
      for (b = 0; b < GFBITS; b++) out[k  ][b] ^= tmp[b];
2536
0
      for (b = 0; b < GFBITS; b++) out[k+s][b] ^= out[k][b];
2537
0
    }
2538
2539
0
    consts_ptr += (1 << i);
2540
0
  }
2541
2542
  /* adding the part contributed by x^128 */
2543
2544
0
  for (i = 0; i < 128; i++)
2545
0
  for (b = 0; b < GFBITS; b++)
2546
0
    out[i][b] ^= fft_powers[i][b];
2547
0
}
2548
2549
/* input: in, polynomial in bitsliced form */
2550
/* output: out, bitsliced results of evaluating in all the field elements */
2551
static void fft(vec out[][GFBITS], vec in[][GFBITS])
2552
0
{
2553
0
  radix_conversions(in);
2554
0
  butterflies(out, in);
2555
0
}
2556
2557
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.c */
2558
/*
2559
  This file is for transpose of the Gao-Mateer FFT
2560
  Functions with names ending with _tr are (roughly) the transpose of the corresponding functions in fft.c
2561
2562
  For the implementation strategy, see
2563
  https://eprint.iacr.org/2017/793.pdf
2564
*/
2565
/* 20221230 djb: split these arrays into separate .c files */
2566
/* 20221230 djb: rename consts array as fft_consts */
2567
/* 20221230 djb: rename s array as fft_scalars_4x */
2568
/* 20221230 djb: add linker lines */
2569
2570
/* linker define fft_tr */
2571
/* linker use vec_mul */
2572
/* linker use fft_scalars_4x fft_consts */
2573
2574
2575
2576
2577
static void radix_conversions_tr(vec in[][ GFBITS ])
2578
0
{
2579
0
  int i, j, k;
2580
2581
0
  const vec mask[6][2] =
2582
0
  {
2583
0
    {0x2222222222222222, 0x4444444444444444},
2584
0
    {0x0C0C0C0C0C0C0C0C, 0x3030303030303030},
2585
0
    {0x00F000F000F000F0, 0x0F000F000F000F00},
2586
0
    {0x0000FF000000FF00, 0x00FF000000FF0000},
2587
0
    {0x00000000FFFF0000, 0x0000FFFF00000000},
2588
0
    {0xFFFFFFFF00000000, 0x00000000FFFFFFFF}
2589
0
  };
2590
2591
  /**/
2592
2593
0
  for (j = 6; j >= 0; j--)
2594
0
  {
2595
0
    if (j < 6)
2596
0
    {
2597
0
      vec_mul(in[0], in[0], fft_scalars_4x[j][0]); /* scaling */
2598
0
      vec_mul(in[1], in[1], fft_scalars_4x[j][1]); /* scaling */
2599
0
      vec_mul(in[2], in[2], fft_scalars_4x[j][2]); /* scaling */
2600
0
      vec_mul(in[3], in[3], fft_scalars_4x[j][3]); /* scaling */
2601
0
    }
2602
2603
0
    for (k = j; k <= 4; k++)
2604
0
    for (i = 0; i < GFBITS; i++)
2605
0
    {
2606
0
      in[0][i] ^= (in[0][i] & mask[k][0]) << (1 << k);
2607
0
      in[0][i] ^= (in[0][i] & mask[k][1]) << (1 << k);
2608
0
      in[1][i] ^= (in[1][i] & mask[k][0]) << (1 << k);
2609
0
      in[1][i] ^= (in[1][i] & mask[k][1]) << (1 << k);
2610
0
      in[2][i] ^= (in[2][i] & mask[k][0]) << (1 << k);
2611
0
      in[2][i] ^= (in[2][i] & mask[k][1]) << (1 << k);
2612
0
      in[3][i] ^= (in[3][i] & mask[k][0]) << (1 << k);
2613
0
      in[3][i] ^= (in[3][i] & mask[k][1]) << (1 << k);
2614
0
    }
2615
2616
0
    if (j <= 5)
2617
0
    for (i = 0; i < GFBITS; i++)
2618
0
    {
2619
0
      in[1][i] ^= in[0][i] >> 32;
2620
0
      in[1][i] ^= in[1][i] << 32;
2621
2622
0
      in[3][i] ^= in[2][i] >> 32;
2623
0
      in[3][i] ^= in[3][i] << 32;
2624
0
    }
2625
2626
0
    for (i = 0; i < GFBITS; i++)
2627
0
      in[3][i] ^= in[2][i] ^= in[1][i];
2628
0
  }
2629
0
}
2630
2631
static void butterflies_tr(vec out[][ GFBITS ], vec in[][ GFBITS ])
2632
0
{
2633
0
  int i, j, k, s, b;
2634
2635
0
  vec tmp[ GFBITS ];
2636
0
  vec pre[6][2][ GFBITS ];
2637
0
  vec buf[2][64];
2638
2639
0
  uint64_t consts_ptr = 128;
2640
2641
0
  const unsigned char reversal[128] =
2642
0
  {
2643
0
    0, 64, 32, 96, 16, 80, 48, 112,
2644
0
    8, 72, 40, 104, 24, 88, 56, 120,
2645
0
    4, 68, 36, 100, 20, 84, 52, 116,
2646
0
    12, 76, 44, 108, 28, 92, 60, 124,
2647
0
    2, 66, 34, 98, 18, 82, 50, 114,
2648
0
    10, 74, 42, 106, 26, 90, 58, 122,
2649
0
    6, 70, 38, 102, 22, 86, 54, 118,
2650
0
    14, 78, 46, 110, 30, 94, 62, 126,
2651
0
    1, 65, 33, 97, 17, 81, 49, 113,
2652
0
    9, 73, 41, 105, 25, 89, 57, 121,
2653
0
    5, 69, 37, 101, 21, 85, 53, 117,
2654
0
    13, 77, 45, 109, 29, 93, 61, 125,
2655
0
    3, 67, 35, 99, 19, 83, 51, 115,
2656
0
    11, 75, 43, 107, 27, 91, 59, 123,
2657
0
    7, 71, 39, 103, 23, 87, 55, 119,
2658
0
    15, 79, 47, 111, 31, 95, 63, 127
2659
0
  };
2660
2661
0
  const uint16_t beta[6] = {5246, 5306, 6039, 6685, 4905, 6755};
2662
2663
  /**/
2664
2665
0
  for (i = 6; i >= 0; i--)
2666
0
  {
2667
0
    s = 1 << i;
2668
0
    consts_ptr -= s;
2669
2670
0
    for (j = 0; j < 128; j += 2*s)
2671
0
    for (k = j; k < j+s; k++)
2672
0
    {
2673
0
      for (b = 0; b < GFBITS; b++) in[k][b] ^= in[k+s][b];
2674
2675
0
      vec_mul(tmp, in[k], fft_consts[ consts_ptr + (k-j) ]);
2676
2677
0
      for (b = 0; b < GFBITS; b++) in[k+s][b] ^= tmp[b];
2678
0
    }
2679
0
  }
2680
2681
0
  for (i = 0; i < GFBITS; i++)
2682
0
  {
2683
0
    for (k = 0; k < 128; k++)
2684
0
      (&buf[0][0])[ k ] = in[ reversal[k] ][i];
2685
2686
0
    transpose_64x64(buf[0], buf[0]);
2687
0
    transpose_64x64(buf[1], buf[1]);
2688
2689
0
    for (k = 0; k < 2; k++)
2690
0
    {
2691
0
      pre[0][k][i] = buf[k][32]; buf[k][33] ^= buf[k][32];
2692
0
      pre[1][k][i] = buf[k][33]; buf[k][35] ^= buf[k][33];
2693
0
      pre[0][k][i] ^= buf[k][35]; buf[k][34] ^= buf[k][35];
2694
0
      pre[2][k][i] = buf[k][34]; buf[k][38] ^= buf[k][34];
2695
0
      pre[0][k][i] ^= buf[k][38]; buf[k][39] ^= buf[k][38];
2696
0
      pre[1][k][i] ^= buf[k][39]; buf[k][37] ^= buf[k][39];
2697
0
      pre[0][k][i] ^= buf[k][37]; buf[k][36] ^= buf[k][37];
2698
0
      pre[3][k][i] = buf[k][36]; buf[k][44] ^= buf[k][36];
2699
0
      pre[0][k][i] ^= buf[k][44]; buf[k][45] ^= buf[k][44];
2700
0
      pre[1][k][i] ^= buf[k][45]; buf[k][47] ^= buf[k][45];
2701
0
      pre[0][k][i] ^= buf[k][47]; buf[k][46] ^= buf[k][47];
2702
0
      pre[2][k][i] ^= buf[k][46]; buf[k][42] ^= buf[k][46];
2703
0
      pre[0][k][i] ^= buf[k][42]; buf[k][43] ^= buf[k][42];
2704
0
      pre[1][k][i] ^= buf[k][43]; buf[k][41] ^= buf[k][43];
2705
0
      pre[0][k][i] ^= buf[k][41]; buf[k][40] ^= buf[k][41];
2706
0
      pre[4][k][i] = buf[k][40]; buf[k][56] ^= buf[k][40];
2707
0
      pre[0][k][i] ^= buf[k][56]; buf[k][57] ^= buf[k][56];
2708
0
      pre[1][k][i] ^= buf[k][57]; buf[k][59] ^= buf[k][57];
2709
0
      pre[0][k][i] ^= buf[k][59]; buf[k][58] ^= buf[k][59];
2710
0
      pre[2][k][i] ^= buf[k][58]; buf[k][62] ^= buf[k][58];
2711
0
      pre[0][k][i] ^= buf[k][62]; buf[k][63] ^= buf[k][62];
2712
0
      pre[1][k][i] ^= buf[k][63]; buf[k][61] ^= buf[k][63];
2713
0
      pre[0][k][i] ^= buf[k][61]; buf[k][60] ^= buf[k][61];
2714
0
      pre[3][k][i] ^= buf[k][60]; buf[k][52] ^= buf[k][60];
2715
0
      pre[0][k][i] ^= buf[k][52]; buf[k][53] ^= buf[k][52];
2716
0
      pre[1][k][i] ^= buf[k][53]; buf[k][55] ^= buf[k][53];
2717
0
      pre[0][k][i] ^= buf[k][55]; buf[k][54] ^= buf[k][55];
2718
0
      pre[2][k][i] ^= buf[k][54]; buf[k][50] ^= buf[k][54];
2719
0
      pre[0][k][i] ^= buf[k][50]; buf[k][51] ^= buf[k][50];
2720
0
      pre[1][k][i] ^= buf[k][51]; buf[k][49] ^= buf[k][51];
2721
0
      pre[0][k][i] ^= buf[k][49]; buf[k][48] ^= buf[k][49];
2722
0
      pre[5][k][i] = buf[k][48]; buf[k][16] ^= buf[k][48];
2723
0
      pre[0][k][i] ^= buf[k][16]; buf[k][17] ^= buf[k][16];
2724
0
      pre[1][k][i] ^= buf[k][17]; buf[k][19] ^= buf[k][17];
2725
0
      pre[0][k][i] ^= buf[k][19]; buf[k][18] ^= buf[k][19];
2726
0
      pre[2][k][i] ^= buf[k][18]; buf[k][22] ^= buf[k][18];
2727
0
      pre[0][k][i] ^= buf[k][22]; buf[k][23] ^= buf[k][22];
2728
0
      pre[1][k][i] ^= buf[k][23]; buf[k][21] ^= buf[k][23];
2729
0
      pre[0][k][i] ^= buf[k][21]; buf[k][20] ^= buf[k][21];
2730
0
      pre[3][k][i] ^= buf[k][20]; buf[k][28] ^= buf[k][20];
2731
0
      pre[0][k][i] ^= buf[k][28]; buf[k][29] ^= buf[k][28];
2732
0
      pre[1][k][i] ^= buf[k][29]; buf[k][31] ^= buf[k][29];
2733
0
      pre[0][k][i] ^= buf[k][31]; buf[k][30] ^= buf[k][31];
2734
0
      pre[2][k][i] ^= buf[k][30]; buf[k][26] ^= buf[k][30];
2735
0
      pre[0][k][i] ^= buf[k][26]; buf[k][27] ^= buf[k][26];
2736
0
      pre[1][k][i] ^= buf[k][27]; buf[k][25] ^= buf[k][27];
2737
0
      pre[0][k][i] ^= buf[k][25]; buf[k][24] ^= buf[k][25];
2738
0
      pre[4][k][i] ^= buf[k][24]; buf[k][8] ^= buf[k][24];
2739
0
      pre[0][k][i] ^= buf[k][8]; buf[k][9] ^= buf[k][8];
2740
0
      pre[1][k][i] ^= buf[k][9]; buf[k][11] ^= buf[k][9];
2741
0
      pre[0][k][i] ^= buf[k][11]; buf[k][10] ^= buf[k][11];
2742
0
      pre[2][k][i] ^= buf[k][10]; buf[k][14] ^= buf[k][10];
2743
0
      pre[0][k][i] ^= buf[k][14]; buf[k][15] ^= buf[k][14];
2744
0
      pre[1][k][i] ^= buf[k][15]; buf[k][13] ^= buf[k][15];
2745
0
      pre[0][k][i] ^= buf[k][13]; buf[k][12] ^= buf[k][13];
2746
0
      pre[3][k][i] ^= buf[k][12]; buf[k][4] ^= buf[k][12];
2747
0
      pre[0][k][i] ^= buf[k][4]; buf[k][5] ^= buf[k][4];
2748
0
      pre[1][k][i] ^= buf[k][5]; buf[k][7] ^= buf[k][5];
2749
0
      pre[0][k][i] ^= buf[k][7]; buf[k][6] ^= buf[k][7];
2750
0
      pre[2][k][i] ^= buf[k][6]; buf[k][2] ^= buf[k][6];
2751
0
      pre[0][k][i] ^= buf[k][2]; buf[k][3] ^= buf[k][2];
2752
0
      pre[1][k][i] ^= buf[k][3]; buf[k][1] ^= buf[k][3];
2753
2754
0
      pre[0][k][i] ^= buf[k][1]; out[k][i] = buf[k][0] ^ buf[k][1];
2755
0
    }
2756
0
  }
2757
2758
0
  for (j = 0; j < GFBITS; j++) tmp[j] = vec_setbits((beta[0] >> j) & 1);
2759
2760
0
  vec_mul(out[2], pre[0][0], tmp);
2761
0
  vec_mul(out[3], pre[0][1], tmp);
2762
2763
0
  for (i = 1; i < 6; i++)
2764
0
  {
2765
0
    for (j = 0; j < GFBITS; j++) tmp[j] = vec_setbits((beta[i] >> j) & 1);
2766
2767
0
    vec_mul(pre[i][0], pre[i][0], tmp);
2768
0
    vec_mul(pre[i][1], pre[i][1], tmp);
2769
2770
0
    for (b = 0; b < GFBITS; b++)
2771
0
    {
2772
0
      out[2][b] ^= pre[i][0][b];
2773
0
      out[3][b] ^= pre[i][1][b];
2774
0
    }
2775
0
  }
2776
2777
0
}
2778
2779
static void fft_tr(vec out[][GFBITS], vec in[][ GFBITS ])
2780
0
{
2781
0
  butterflies_tr(out, in);
2782
2783
0
  radix_conversions_tr(out);
2784
0
}
2785
2786
2787
/* from libmceliece-20230612/crypto_kem/6688128f/vec/gf.c */
2788
/*
2789
  this file is for functions for field arithmetic
2790
*/
2791
/* 20221231 djb: const for GF_mul */
2792
/* 20221230 djb: add linker line */
2793
2794
/* linker define gf_iszero gf_mul gf_inv gf_frac GF_mul */
2795
2796
2797
2798
/* field multiplication */
2799
gf gf_mul(gf in0, gf in1)
2800
0
{
2801
0
  int i;
2802
2803
0
  uint64_t tmp;
2804
0
  uint64_t t0;
2805
0
  uint64_t t1;
2806
0
  uint64_t t;
2807
2808
0
  t0 = in0;
2809
0
  t1 = in1;
2810
2811
0
  tmp = t0 * (t1 & 1);
2812
2813
0
  for (i = 1; i < GFBITS; i++)
2814
0
    tmp ^= (t0 * (t1 & (1 << i)));
2815
2816
  /**/
2817
2818
0
  t = tmp & 0x1FF0000;
2819
0
  tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
2820
2821
0
  t = tmp & 0x000E000;
2822
0
  tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
2823
2824
0
  return tmp & GFMASK;
2825
0
}
2826
2827
/* 2 field squarings */
2828
static inline gf gf_sq2(gf in)
2829
0
{
2830
0
  int i;
2831
2832
0
  const uint64_t B[] = {0x1111111111111111,
2833
0
                        0x0303030303030303,
2834
0
                        0x000F000F000F000F,
2835
0
                        0x000000FF000000FF};
2836
2837
0
  const uint64_t M[] = {0x0001FF0000000000,
2838
0
                        0x000000FF80000000,
2839
0
                        0x000000007FC00000,
2840
0
                        0x00000000003FE000};
2841
2842
0
  uint64_t x = in;
2843
0
  uint64_t t;
2844
2845
0
  x = (x | (x << 24)) & B[3];
2846
0
  x = (x | (x << 12)) & B[2];
2847
0
  x = (x | (x << 6)) & B[1];
2848
0
  x = (x | (x << 3)) & B[0];
2849
2850
0
  for (i = 0; i < 4; i++)
2851
0
  {
2852
0
    t = x & M[i];
2853
0
    x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
2854
0
  }
2855
2856
0
  return x & GFMASK;
2857
0
}
2858
2859
/* square and multiply */
2860
static inline gf gf_sqmul(gf in, gf m)
2861
0
{
2862
0
  int i;
2863
2864
0
  uint64_t x;
2865
0
  uint64_t t0;
2866
0
  uint64_t t1;
2867
0
  uint64_t t;
2868
2869
0
  const uint64_t M[] = {0x0000001FF0000000,
2870
0
                        0x000000000FF80000,
2871
0
                        0x000000000007E000};
2872
2873
0
  t0 = in;
2874
0
  t1 = m;
2875
2876
0
  x = (t1 << 6) * (t0 & (1 << 6));
2877
2878
0
  t0 ^= (t0 << 7);
2879
2880
0
  x ^= (t1 * (t0 & (0x04001)));
2881
0
  x ^= (t1 * (t0 & (0x08002))) << 1;
2882
0
  x ^= (t1 * (t0 & (0x10004))) << 2;
2883
0
  x ^= (t1 * (t0 & (0x20008))) << 3;
2884
0
  x ^= (t1 * (t0 & (0x40010))) << 4;
2885
0
  x ^= (t1 * (t0 & (0x80020))) << 5;
2886
2887
0
  for (i = 0; i < 3; i++)
2888
0
  {
2889
0
    t = x & M[i];
2890
0
    x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
2891
0
  }
2892
2893
0
  return x & GFMASK;
2894
0
}
2895
2896
/* square twice and multiply */
2897
static inline gf gf_sq2mul(gf in, gf m)
2898
0
{
2899
0
  int i;
2900
2901
0
  uint64_t x;
2902
0
  uint64_t t0;
2903
0
  uint64_t t1;
2904
0
  uint64_t t;
2905
2906
0
  const uint64_t M[] = {0x1FF0000000000000,
2907
0
                  0x000FF80000000000,
2908
0
                  0x000007FC00000000,
2909
0
                        0x00000003FE000000,
2910
0
                        0x0000000001FE0000,
2911
0
                        0x000000000001E000};
2912
2913
0
  t0 = in;
2914
0
  t1 = m;
2915
2916
0
  x = (t1 << 18) * (t0 & (1 << 6));
2917
2918
0
  t0 ^= (t0 << 21);
2919
2920
0
  x ^= (t1 * (t0 & (0x010000001)));
2921
0
  x ^= (t1 * (t0 & (0x020000002))) << 3;
2922
0
  x ^= (t1 * (t0 & (0x040000004))) << 6;
2923
0
  x ^= (t1 * (t0 & (0x080000008))) << 9;
2924
0
  x ^= (t1 * (t0 & (0x100000010))) << 12;
2925
0
  x ^= (t1 * (t0 & (0x200000020))) << 15;
2926
2927
0
  for (i = 0; i < 6; i++)
2928
0
  {
2929
0
    t = x & M[i];
2930
0
    x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
2931
0
  }
2932
2933
0
  return x & GFMASK;
2934
0
}
2935
2936
/* return num/den */
2937
gf gf_frac(gf den, gf num)
2938
0
{
2939
0
  gf tmp_11;
2940
0
  gf tmp_1111;
2941
0
  gf out;
2942
2943
0
  tmp_11 = gf_sqmul(den, den); /* 11 */
2944
0
  tmp_1111 = gf_sq2mul(tmp_11, tmp_11); /* 1111 */
2945
0
  out = gf_sq2(tmp_1111);
2946
0
  out = gf_sq2mul(out, tmp_1111); /* 11111111 */
2947
0
  out = gf_sq2(out);
2948
0
  out = gf_sq2mul(out, tmp_1111); /* 111111111111 */
2949
2950
0
  return gf_sqmul(out, num); /* 1111111111110 */
2951
0
}
2952
2953
/* return 1/den */
2954
gf gf_inv(gf den)
2955
0
{
2956
0
  return gf_frac(den, ((gf) 1));
2957
0
}
2958
2959
/* check if a == 0 */
2960
gf gf_iszero(gf a)
2961
0
{
2962
0
  uint32_t t = a;
2963
2964
0
  t -= 1;
2965
0
  t >>= 19;
2966
2967
0
  return (gf) t;
2968
0
}
2969
2970
/* multiplication in GF((2^m)^t) */
2971
static void GF_mul(gf *out, const gf *in0, const gf *in1)
2972
0
{
2973
0
  int i, j;
2974
2975
0
  gf prod[255];
2976
2977
0
  for (i = 0; i < 255; i++)
2978
0
    prod[i] = 0;
2979
2980
0
  for (i = 0; i < 128; i++)
2981
0
    for (j = 0; j < 128; j++)
2982
0
      prod[i+j] ^= gf_mul(in0[i], in1[j]);
2983
2984
  /**/
2985
2986
0
  for (i = 254; i >= 128; i--)
2987
0
  {
2988
0
    prod[i - 121] ^= prod[i];
2989
0
    prod[i - 126] ^= prod[i];
2990
0
    prod[i - 127] ^= prod[i];
2991
0
    prod[i - 128] ^= prod[i];
2992
0
  }
2993
2994
0
  for (i = 0; i < 128; i++)
2995
0
    out[i] = prod[i];
2996
0
}
2997
2998
2999
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_dec.c */
3000
/* 20221230 djb: add linker lines */
3001
/* 20221230 djb: split out of operations.c */
3002
3003
/* linker define operation_dec */
3004
/* linker use decrypt */
3005
3006
3007
3008
3009
static void operation_dec(
3010
       unsigned char *key,
3011
       const unsigned char *c,
3012
       const unsigned char *sk
3013
)
3014
0
{
3015
0
  int i;
3016
3017
0
  unsigned char ret_decrypt = 0;
3018
3019
0
  uint16_t m;
3020
3021
0
  unsigned char e[ SYS_N/8 ];
3022
0
  unsigned char preimage[ 1 + SYS_N/8 + SYND_BYTES ];
3023
0
  unsigned char *x = preimage;
3024
0
  const unsigned char *s = sk + 40 + IRR_BYTES + COND_BYTES;
3025
3026
  /**/
3027
3028
0
  ret_decrypt = decrypt(e, sk + 40, c);
3029
3030
0
  m = ret_decrypt;
3031
0
  m -= 1;
3032
0
  m >>= 8;
3033
3034
0
  *x++ = m & 1;
3035
0
  for (i = 0; i < SYS_N/8; i++)
3036
0
    *x++ = (~m & s[i]) | (m & e[i]);
3037
3038
0
  for (i = 0; i < SYND_BYTES; i++)
3039
0
    *x++ = c[i];
3040
3041
0
  crypto_hash_32b(key, preimage, sizeof(preimage));
3042
0
}
3043
3044
3045
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_enc.c */
3046
/* 20230102 djb: rename encrypt() as pke_encrypt() */
3047
/* 20221230 djb: add linker lines */
3048
/* 20221230 djb: split out of operations.c */
3049
3050
/* linker define operation_enc */
3051
/* linker use pke_encrypt */
3052
3053
3054
3055
3056
static void operation_enc(
3057
       unsigned char *c,
3058
       unsigned char *key,
3059
       const unsigned char *pk
3060
)
3061
0
{
3062
0
  unsigned char e[ SYS_N/8 ];
3063
0
  unsigned char one_ec[ 1 + SYS_N/8 + SYND_BYTES ] = {1};
3064
3065
  /**/
3066
3067
0
  pke_encrypt(c, pk, e);
3068
3069
0
  memcpy(one_ec + 1, e, SYS_N/8);
3070
0
  memcpy(one_ec + 1 + SYS_N/8, c, SYND_BYTES);
3071
3072
0
  crypto_hash_32b(key, one_ec, sizeof(one_ec));
3073
0
}
3074
3075
3076
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_keypair.c */
3077
/* 20221230 djb: add linker lines */
3078
/* 20221230 djb: split out of operations.c */
3079
3080
/* linker define operation_keypair */
3081
/* linker use controlbitsfrompermutation genpoly_gen pk_gen */
3082
3083
3084
3085
3086
static void operation_keypair
3087
(
3088
       unsigned char *pk,
3089
       unsigned char *sk
3090
)
3091
0
{
3092
0
  int i;
3093
0
  unsigned char seed[ 33 ] = {64};
3094
0
  unsigned char r[ SYS_N/8 + (1 << GFBITS)*sizeof(uint32_t) + SYS_T*2 + 32 ];
3095
0
  unsigned char *rp, *skp;
3096
0
  uint64_t pivots = 0;
3097
3098
0
  gf f[ SYS_T ]; /* element in GF(2^mt) */
3099
0
  gf irr[ SYS_T ]; /* Goppa polynomial */
3100
0
  uint32_t perm[ 1 << GFBITS ]; /* random permutation as 32-bit integers */
3101
0
  int16_t pi[ 1 << GFBITS ]; /* random permutation */
3102
3103
0
  randombytes(seed+1, 32);
3104
3105
0
  while (1)
3106
0
  {
3107
0
    rp = &r[ sizeof(r)-32 ];
3108
0
    skp = sk;
3109
3110
    /* expanding and updating the seed */
3111
3112
0
    shake(r, sizeof(r), seed, 33);
3113
0
    memcpy(skp, seed+1, 32);
3114
0
    skp += 32 + 8;
3115
0
    memcpy(seed+1, &r[ sizeof(r)-32 ], 32);
3116
3117
    /* generating irreducible polynomial */
3118
3119
0
    rp -= sizeof(f);
3120
3121
0
    for (i = 0; i < SYS_T; i++)
3122
0
      f[i] = load_gf(rp + i*2);
3123
3124
0
    if (genpoly_gen(irr, f))
3125
0
      continue;
3126
3127
0
    for (i = 0; i < SYS_T; i++)
3128
0
      store_gf(skp + i*2, irr[i]);
3129
3130
0
    skp += IRR_BYTES;
3131
3132
    /* generating permutation */
3133
3134
0
    rp -= sizeof(perm);
3135
3136
0
    for (i = 0; i < (1 << GFBITS); i++)
3137
0
      perm[i] = load4(rp + i*4);
3138
3139
0
    if (pk_gen(pk, skp - IRR_BYTES, perm, pi, &pivots))
3140
0
      continue;
3141
3142
0
    controlbitsfrompermutation(skp, pi, GFBITS, 1 << GFBITS);
3143
0
    skp += COND_BYTES;
3144
3145
    /* storing the random string s */
3146
3147
0
    rp -= SYS_N/8;
3148
0
    memcpy(skp, rp, SYS_N/8);
3149
3150
    /* storing positions of the 32 pivots */
3151
3152
0
    store8(sk + 32, pivots);
3153
3154
0
    break;
3155
0
  }
3156
0
}
3157
3158
3159
/* from libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.c */
3160
/*
3161
  This file is for public-key generation
3162
*/
3163
/* 20221231 djb: remove unused min definition */
3164
/* 20221231 djb: more 0 initialization to clarify data flow; tnx thom wiggers */
3165
/* 20221230 djb: add linker lines */
3166
3167
/* linker define pk_gen */
3168
/* linker use fft vec_inv vec_mul */
3169
3170
3171
3172
static crypto_uint64 uint64_is_equal_declassify(uint64_t t,uint64_t u)
3173
0
{
3174
0
  crypto_uint64 mask = crypto_uint64_equal_mask(t,u);
3175
0
  crypto_declassify(&mask,sizeof mask);
3176
0
  return mask;
3177
0
}
3178
3179
static crypto_uint64 uint64_is_zero_declassify(uint64_t t)
3180
0
{
3181
0
  crypto_uint64 mask = crypto_uint64_zero_mask(t);
3182
0
  crypto_declassify(&mask,sizeof mask);
3183
0
  return mask;
3184
0
}
3185
3186
3187
static void de_bitslicing(uint64_t * out, const vec in[][GFBITS])
3188
0
{
3189
0
  int i, j, r;
3190
3191
0
  for (i = 0; i < (1 << GFBITS); i++)
3192
0
    out[i] = 0 ;
3193
3194
0
  for (i = 0; i < 128; i++)
3195
0
  for (j = GFBITS-1; j >= 0; j--)
3196
0
  for (r = 0; r < 64; r++)
3197
0
  {
3198
0
    out[i*64 + r] <<= 1;
3199
0
    out[i*64 + r] |= (in[i][j] >> r) & 1;
3200
0
  }
3201
0
}
3202
3203
static void to_bitslicing_2x(vec out0[][GFBITS], vec out1[][GFBITS], const uint64_t * in)
3204
0
{
3205
0
  int i, j, r;
3206
3207
0
  for (i = 0; i < 128; i++)
3208
0
  {
3209
0
    for (j = 0;j < GFBITS;++j) out0[i][j] = out1[i][j] = 0;
3210
3211
0
    for (j = GFBITS-1; j >= 0; j--)
3212
0
    for (r = 63; r >= 0; r--)
3213
0
    {
3214
0
      out1[i][j] <<= 1;
3215
0
      out1[i][j] |= (in[i*64 + r] >> (j + GFBITS)) & 1;
3216
0
    }
3217
3218
0
    for (j = GFBITS-1; j >= 0; j--)
3219
0
    for (r = 63; r >= 0; r--)
3220
0
    {
3221
0
      out0[i][GFBITS-1-j] <<= 1;
3222
0
      out0[i][GFBITS-1-j] |= (in[i*64 + r] >> j) & 1;
3223
0
    }
3224
0
  }
3225
0
}
3226
3227
/* return number of trailing zeros of in */
3228
static inline int ctz(uint64_t in)
3229
0
{
3230
0
  int i, b, m = 0, r = 0;
3231
3232
0
  for (i = 0; i < 64; i++)
3233
0
  {
3234
0
    b = (in >> i) & 1;
3235
0
    m |= b;
3236
0
    r += (m^1) & (b^1);
3237
0
  }
3238
3239
0
  return r;
3240
0
}
3241
3242
static inline uint64_t same_mask(uint16_t x, uint16_t y)
3243
0
{
3244
0
        uint64_t mask;
3245
3246
0
        mask = x ^ y;
3247
0
        mask -= 1;
3248
0
        mask >>= 63;
3249
0
        mask = -mask;
3250
3251
0
        return mask;
3252
0
}
3253
3254
static int mov_columns(uint64_t mat[][ (SYS_N + 63) / 64 ], int16_t * pi, uint64_t * pivots)
3255
0
{
3256
0
  int i, j, k, s, block_idx, row;
3257
0
  uint64_t buf[64], ctz_list[32], t, d, mask, one = 1;
3258
3259
0
  row = PK_NROWS - 32;
3260
0
  block_idx = row/64;
3261
3262
  /* extract the 32x64 matrix */
3263
3264
0
  for (i = 0; i < 32; i++)
3265
0
    buf[i] = (mat[ row + i ][ block_idx + 0 ] >> 32) |
3266
0
             (mat[ row + i ][ block_idx + 1 ] << 32);
3267
3268
  /* compute the column indices of pivots by Gaussian elimination. */
3269
  /* the indices are stored in ctz_list */
3270
3271
0
  *pivots = 0;
3272
3273
0
  for (i = 0; i < 32; i++)
3274
0
  {
3275
0
    t = buf[i];
3276
0
    for (j = i+1; j < 32; j++)
3277
0
      t |= buf[j];
3278
3279
0
    if (uint64_is_zero_declassify(t)) return -1; /* return if buf is not full rank */
3280
3281
0
    ctz_list[i] = s = ctz(t);
3282
0
    *pivots |= one << ctz_list[i];
3283
3284
0
    for (j = i+1; j < 32; j++) { mask = (buf[i] >> s) & 1; mask -= 1;    buf[i] ^= buf[j] & mask; }
3285
0
    for (j = i+1; j < 32; j++) { mask = (buf[j] >> s) & 1; mask = -mask; buf[j] ^= buf[i] & mask; }
3286
0
  }
3287
3288
  /* updating permutation */
3289
3290
0
  for (j = 0;   j < 32; j++)
3291
0
  for (k = j+1; k < 64; k++)
3292
0
  {
3293
0
      d = pi[ row + j ] ^ pi[ row + k ];
3294
0
      d &= same_mask(k, ctz_list[j]);
3295
0
      pi[ row + j ] ^= d;
3296
0
      pi[ row + k ] ^= d;
3297
0
  }
3298
3299
  /* moving columns of mat according to the column indices of pivots */
3300
3301
0
  for (i = 0; i < PK_NROWS; i++)
3302
0
  {
3303
0
    t = (mat[ i ][ block_idx + 0 ] >> 32) |
3304
0
        (mat[ i ][ block_idx + 1 ] << 32);
3305
3306
0
    for (j = 0; j < 32; j++)
3307
0
    {
3308
0
      d  = t >> j;
3309
0
      d ^= t >> ctz_list[j];
3310
0
      d &= 1;
3311
3312
0
      t ^= d << ctz_list[j];
3313
0
      t ^= d << j;
3314
0
    }
3315
3316
0
    mat[ i ][ block_idx + 0 ] = (mat[ i ][ block_idx + 0 ] << 32 >> 32) | (t << 32);
3317
0
    mat[ i ][ block_idx + 1 ] = (mat[ i ][ block_idx + 1 ] >> 32 << 32) | (t >> 32);
3318
0
  }
3319
3320
0
  return 0;
3321
0
}
3322
3323
static int pk_gen(unsigned char * pk, const unsigned char * irr, uint32_t * perm, int16_t * pi, uint64_t * pivots)
3324
0
{
3325
0
  const int nblocks_H = (SYS_N + 63) / 64;
3326
0
  const int nblocks_I = (PK_NROWS + 63) / 64;
3327
3328
0
  int i, j, k;
3329
0
  int row, c;
3330
3331
0
  uint64_t mat[ PK_NROWS ][ nblocks_H ];
3332
3333
0
  uint64_t mask;
3334
3335
0
  vec irr_int[2][ GFBITS ];
3336
3337
0
  vec consts[ 128 ][ GFBITS ];
3338
0
  vec eval[ 128 ][ GFBITS ];
3339
0
  vec prod[ 128 ][ GFBITS ];
3340
0
  vec tmp[ GFBITS ];
3341
3342
0
  uint64_t list[1 << GFBITS];
3343
3344
  /* compute the inverses */
3345
3346
0
  irr_load(irr_int, irr);
3347
3348
0
  fft(eval, irr_int);
3349
3350
0
  vec_copy(prod[0], eval[0]);
3351
3352
0
  for (i = 1; i < 128; i++)
3353
0
    vec_mul(prod[i], prod[i-1], eval[i]);
3354
3355
0
  vec_inv(tmp, prod[127]);
3356
3357
0
  for (i = 126; i >= 0; i--)
3358
0
  {
3359
0
    vec_mul(prod[i+1], prod[i], tmp);
3360
0
    vec_mul(tmp, tmp, eval[i+1]);
3361
0
  }
3362
3363
0
  vec_copy(prod[0], tmp);
3364
3365
  /* fill matrix */
3366
3367
0
  de_bitslicing(list, prod);
3368
3369
0
  for (i = 0; i < (1 << GFBITS); i++)
3370
0
  {
3371
0
    list[i] <<= GFBITS;
3372
0
    list[i] |= i;
3373
0
    list[i] |= ((uint64_t) perm[i]) << 31;
3374
0
  }
3375
3376
0
  uint64_sort(list, 1 << GFBITS);
3377
3378
0
  for (i = 1; i < (1 << GFBITS); i++)
3379
0
    if (uint64_is_equal_declassify(list[i-1] >> 31,list[i] >> 31))
3380
0
      return -1;
3381
3382
0
  to_bitslicing_2x(consts, prod, list);
3383
3384
0
  for (i = 0; i < (1 << GFBITS); i++)
3385
0
    pi[i] = list[i] & GFMASK;
3386
3387
0
  for (j = 0; j < nblocks_H; j++)
3388
0
  for (k = 0; k < GFBITS; k++)
3389
0
    mat[ k ][ j ] = prod[ j ][ k ];
3390
3391
0
  for (i = 1; i < SYS_T; i++)
3392
0
  for (j = 0; j < nblocks_H; j++)
3393
0
  {
3394
0
    vec_mul(prod[j], prod[j], consts[j]);
3395
3396
0
    for (k = 0; k < GFBITS; k++)
3397
0
      mat[ i*GFBITS + k ][ j ] = prod[ j ][ k ];
3398
0
  }
3399
3400
  /* gaussian elimination */
3401
3402
0
  for (row = 0; row < PK_NROWS; row++)
3403
0
  {
3404
0
    i = row >> 6;
3405
0
    j = row & 63;
3406
3407
0
    if (row == PK_NROWS - 32)
3408
0
    {
3409
0
      if (mov_columns(mat, pi, pivots))
3410
0
        return -1;
3411
0
    }
3412
3413
0
    for (k = row + 1; k < PK_NROWS; k++)
3414
0
    {
3415
0
      mask = mat[ row ][ i ] >> j;
3416
0
      mask &= 1;
3417
0
      mask -= 1;
3418
3419
0
      for (c = 0; c < nblocks_H; c++)
3420
0
        mat[ row ][ c ] ^= mat[ k ][ c ] & mask;
3421
0
    }
3422
3423
0
    if ( uint64_is_zero_declassify((mat[ row ][ i ] >> j) & 1) ) /* return if not systematic */
3424
0
    {
3425
0
      return -1;
3426
0
    }
3427
3428
0
    for (k = 0; k < row; k++)
3429
0
    {
3430
0
      mask = mat[ k ][ i ] >> j;
3431
0
      mask &= 1;
3432
0
      mask = -mask;
3433
3434
0
      for (c = 0; c < nblocks_H; c++)
3435
0
        mat[ k ][ c ] ^= mat[ row ][ c ] & mask;
3436
0
    }
3437
3438
0
    for (k = row+1; k < PK_NROWS; k++)
3439
0
    {
3440
0
      mask = mat[ k ][ i ] >> j;
3441
0
      mask &= 1;
3442
0
      mask = -mask;
3443
3444
0
      for (c = 0; c < nblocks_H; c++)
3445
0
        mat[ k ][ c ] ^= mat[ row ][ c ] & mask;
3446
0
    }
3447
0
  }
3448
3449
0
  for (i = 0; i < PK_NROWS; i++)
3450
0
  {
3451
0
    for (j = nblocks_I; j < nblocks_H-1; j++)
3452
0
    {
3453
0
      store8(pk, mat[i][j]);
3454
0
      pk += 8;
3455
0
    }
3456
3457
0
    store_i(pk, mat[i][j], PK_ROW_BYTES % 8);
3458
3459
0
                pk += PK_ROW_BYTES % 8;
3460
0
  }
3461
3462
  /**/
3463
3464
0
  return 0;
3465
0
}
3466
3467
3468
/* from libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.c */
3469
/*
3470
  This file is for secret-key generation
3471
*/
3472
/* 20221230 djb: add linker lines */
3473
3474
/* linker define genpoly_gen */
3475
/* linker use gf_iszero gf_mul gf_inv GF_mul */
3476
3477
3478
3479
static inline crypto_uint16 gf_is_zero_declassify(gf t)
3480
0
{
3481
0
  crypto_uint16 mask = crypto_uint16_zero_mask(t);
3482
0
  crypto_declassify(&mask,sizeof mask);
3483
0
  return mask;
3484
0
}
3485
3486
/* input: f, element in GF((2^m)^t) */
3487
/* output: out, minimal polynomial of f */
3488
/* return: 0 for success and -1 for failure */
3489
static int genpoly_gen(gf *out, gf *f)
3490
0
{
3491
0
  int i, j, k, c;
3492
3493
0
  gf mat[ SYS_T+1 ][ SYS_T ];
3494
0
  gf mask, inv, t;
3495
3496
  /* fill matrix */
3497
3498
0
  mat[0][0] = 1;
3499
3500
0
  for (i = 1; i < SYS_T; i++)
3501
0
    mat[0][i] = 0;
3502
3503
0
  for (i = 0; i < SYS_T; i++)
3504
0
    mat[1][i] = f[i];
3505
3506
0
  for (j = 2; j <= SYS_T; j++)
3507
0
    GF_mul(mat[j], mat[j-1], f);
3508
3509
  /* gaussian */
3510
3511
0
  for (j = 0; j < SYS_T; j++)
3512
0
  {
3513
0
    for (k = j + 1; k < SYS_T; k++)
3514
0
    {
3515
0
      mask = gf_iszero(mat[ j ][ j ]);
3516
3517
0
      for (c = j; c < SYS_T + 1; c++)
3518
0
        mat[ c ][ j ] ^= mat[ c ][ k ] & mask;
3519
3520
0
    }
3521
3522
0
    if ( gf_is_zero_declassify(mat[ j ][ j ]) ) /* return if not systematic */
3523
0
    {
3524
0
      return -1;
3525
0
    }
3526
3527
0
    inv = gf_inv(mat[j][j]);
3528
3529
0
    for (c = j; c < SYS_T + 1; c++)
3530
0
      mat[ c ][ j ] = gf_mul(mat[ c ][ j ], inv) ;
3531
3532
0
    for (k = 0; k < SYS_T; k++)
3533
0
    {
3534
0
      if (k != j)
3535
0
      {
3536
0
        t = mat[ j ][ k ];
3537
3538
0
        for (c = j; c < SYS_T + 1; c++)
3539
0
          mat[ c ][ k ] ^= gf_mul(mat[ c ][ j ], t);
3540
0
      }
3541
0
    }
3542
0
  }
3543
3544
0
  for (i = 0; i < SYS_T; i++)
3545
0
    out[i] = mat[ SYS_T ][ i ];
3546
3547
0
  return 0;
3548
0
}
3549
3550
3551
/* from libmceliece-20230612/crypto_kem/6688128f/vec/vec.c */
3552
/* 20221230 djb: add linker line */
3553
3554
/* linker define vec_mul vec_sq vec_inv */
3555
3556
3557
3558
static void vec_mul(vec * h, const vec * f, const vec * g)
3559
0
{
3560
0
  int i, j;
3561
0
  vec buf[ 2*GFBITS-1 ];
3562
3563
0
  for (i = 0; i < 2*GFBITS-1; i++)
3564
0
    buf[i] = 0;
3565
3566
0
  for (i = 0; i < GFBITS; i++)
3567
0
  for (j = 0; j < GFBITS; j++)
3568
0
    buf[i+j] ^= f[i] & g[j];
3569
3570
0
  for (i = 2*GFBITS-2; i >= GFBITS; i--)
3571
0
  {
3572
0
    buf[i-GFBITS+4] ^= buf[i];
3573
0
    buf[i-GFBITS+3] ^= buf[i];
3574
0
    buf[i-GFBITS+1] ^= buf[i];
3575
0
    buf[i-GFBITS+0] ^= buf[i];
3576
0
  }
3577
3578
0
  for (i = 0; i < GFBITS; i++)
3579
0
    h[i] = buf[i];
3580
0
}
3581
3582
/* bitsliced field squarings */
3583
static void vec_sq(vec * out, vec * in)
3584
0
{
3585
0
  int i;
3586
0
  vec result[GFBITS], t;
3587
3588
0
  t = in[11] ^ in[12];
3589
3590
0
  result[0] = in[0] ^ in[11];
3591
0
  result[1] = in[7] ^ t;
3592
0
  result[2] = in[1] ^ in[7];
3593
0
  result[3] = in[8] ^ t;
3594
0
  result[4] = in[2] ^ in[7];
3595
0
  result[4] = result[4] ^ in[8];
3596
0
  result[4] = result[4] ^ t;
3597
0
  result[5] = in[7] ^ in[9];
3598
0
  result[6] = in[3] ^ in[8];
3599
0
  result[6] = result[6] ^ in[9];
3600
0
  result[6] = result[6] ^ in[12];
3601
0
  result[7] = in[8] ^ in[10];
3602
0
  result[8] = in[4] ^ in[9];
3603
0
  result[8] = result[8] ^ in[10];
3604
0
  result[9] = in[9] ^ in[11];
3605
0
  result[10] = in[5] ^ in[10];
3606
0
  result[10] = result[10] ^ in[11];
3607
0
  result[11] = in[10] ^ in[12];
3608
0
  result[12] = in[6] ^ t;
3609
3610
0
  for (i = 0; i < GFBITS; i++)
3611
0
    out[i] = result[i];
3612
0
}
3613
3614
/* bitsliced field inverses */
3615
static void vec_inv(vec * out, vec * in)
3616
0
{
3617
0
  vec tmp_11[ GFBITS ];
3618
0
  vec tmp_1111[ GFBITS ];
3619
3620
0
  vec_copy(out, in);
3621
3622
0
  vec_sq(out, out);
3623
0
  vec_mul(tmp_11, out, in); /* ^11 */
3624
3625
0
  vec_sq(out, tmp_11);
3626
0
  vec_sq(out, out);
3627
0
  vec_mul(tmp_1111, out, tmp_11); /* ^1111 */
3628
3629
0
  vec_sq(out, tmp_1111);
3630
0
  vec_sq(out, out);
3631
0
  vec_sq(out, out);
3632
0
  vec_sq(out, out);
3633
0
  vec_mul(out, out, tmp_1111); /* ^11111111 */
3634
3635
0
  vec_sq(out, out);
3636
0
  vec_sq(out, out);
3637
0
  vec_sq(out, out);
3638
0
  vec_sq(out, out);
3639
0
  vec_mul(out, out, tmp_1111); /* ^111111111111 */
3640
3641
0
  vec_sq(out, out); /* ^1111111111110 */
3642
0
}
3643
3644
3645
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_dec.c */
3646
3647
void mceliece6688128f_dec(uint8_t *key,
3648
        const uint8_t *c,
3649
        const uint8_t *sk)
3650
0
{
3651
0
  operation_dec((unsigned char*) key,
3652
0
    (unsigned char*) c,
3653
0
    (unsigned char*) sk);
3654
0
}
3655
3656
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_enc.c */
3657
3658
void mceliece6688128f_enc(uint8_t *c,
3659
        uint8_t *key,
3660
        const uint8_t *pk)
3661
0
{
3662
0
  operation_enc((unsigned char*) c,
3663
0
    (unsigned char*) key,
3664
0
    (unsigned char*) pk);
3665
0
}
3666
3667
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_keypair.c */
3668
3669
void mceliece6688128f_keypair(uint8_t *pk,
3670
            uint8_t *sk)
3671
0
{
3672
0
  operation_keypair((unsigned char*) pk, (unsigned char*) sk);
3673
0
}