Page MenuHome GnuPG

No OneTemporary

diff --git a/cipher/mceliece6688128f.c b/cipher/mceliece6688128f.c
index fefed8ba..63d20a68 100644
--- a/cipher/mceliece6688128f.c
+++ b/cipher/mceliece6688128f.c
@@ -1,3673 +1,3673 @@
/* mceliece6688128f.c - Classic McEliece for libgcrypt
* Copyright (C) 2023-2024 Simon Josefsson <simon@josefsson.org>
*
* This file is part of Libgcrypt.
*
* Libgcrypt is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* Libgcrypt is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this program; if not, see <https://www.gnu.org/licenses/>.
* SPDX-License-Identifier: LGPL-2.1-or-later
*
*/
/* This file is extracted from libmceliece. */
/*
* libmceliece is hereby placed into the public domain.
*
* [SPDX-License-Identifier](https://spdx.dev/ids/):
* [LicenseRef-PD-hp](https://cr.yp.to/spdx.html)
* OR
* [CC0-1.0](https://spdx.org/licenses/CC0-1.0.html)
* OR
* [0BSD](https://spdx.org/licenses/0BSD.html)
* OR
* [MIT-0](https://spdx.org/licenses/MIT-0.html)
* OR
* [MIT](https://spdx.org/licenses/MIT.html)
*
* libmceliece is based on the official Classic McEliece software, which
* was written by Tung Chou. See the following papers for the major
* algorithms used for speed inside that software:
*
* * Daniel J. Bernstein, Tung Chou, Peter Schwabe. "McBits: fast
* constant-time code-based cryptography." CHES 2013.
* [https://tungchou.github.io/papers/mcbits.pdf](https://tungchou.github.io/papers/mcbits.pdf)
*
* * Tung Chou. "McBits revisited." CHES 2017.
* [https://tungchou.github.io/papers/mcbits_revisited.pdf](https://tungchou.github.io/papers/mcbits_revisited.pdf)
*
* The official Classic McEliece software includes `ref`, `vec`, `sse`, and
* `avx` implementations; libmceliece includes only `vec` and `avx`.
*
* The following components of libmceliece are from Daniel J. Bernstein:
*
* * Small [changes](download.html#changelog)
* for namespacing, portability, etc.
*
* * Software to compute control bits (also used in the official software).
* See the following paper: Daniel J. Bernstein. "Verified fast formulas
* for control bits for permutation networks." 2020.
* [https://cr.yp.to/papers.html#controlbits](https://cr.yp.to/papers.html#controlbits)
*
* * `crypto_sort/int32`. See [https://sorting.cr.yp.to](https://sorting.cr.yp.to).
*
* * Infrastructure to build a library with automatic run-time selection of
* implementations based on the run-time CPU and a database of
* benchmarks. This infrastructure was introduced in
* [`lib25519`](https://lib25519.cr.yp.to), with some extensions and
* adaptations in libmceliece.
*
* * Various software for tests and benchmarks. This is based on
* public-domain code in the SUPERCOP benchmarking framework.
*
* This file is generated by mceliece6688128f.sh from these files:
*
* libmceliece-20230612/include-build/crypto_declassify.h
* libmceliece-20230612/crypto_kem/6688128f/vec/params.h
* libmceliece-20230612/inttypes/crypto_intN.h
* libmceliece-20230612/inttypes/crypto_intN.h
* libmceliece-20230612/inttypes/crypto_intN.h
* libmceliece-20230612/inttypes/crypto_uintN.h
* libmceliece-20230612/inttypes/crypto_uintN.h
* libmceliece-20230612/inttypes/crypto_uintN.h
* libmceliece-20230612/crypto_kem/6688128f/vec/vec.h
* libmceliece-20230612/crypto_kem/6688128f/vec/benes.h
* libmceliece-20230612/crypto_kem/6688128f/vec/bm.h
* libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.h
* libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.h
* libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_consts.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_powers.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_2x.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_4x.h
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.h
* libmceliece-20230612/crypto_kem/6688128f/vec/gf.h
* libmceliece-20230612/crypto_kem/6688128f/vec/hash.h
* libmceliece-20230612/crypto_kem/6688128f/vec/int32_sort.h
* libmceliece-20230612/crypto_kem/6688128f/vec/operations.h
* libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.h
* libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.h
* libmceliece-20230612/crypto_kem/6688128f/vec/transpose.h
* libmceliece-20230612/crypto_kem/6688128f/vec/uint16_sort.h
* libmceliece-20230612/crypto_kem/6688128f/vec/uint64_sort.h
* libmceliece-20230612/crypto_kem/6688128f/vec/util.h
* libmceliece-20230612/crypto_kem/6688128f/vec/benes.c
* libmceliece-20230612/crypto_kem/6688128f/vec/bm.c
* libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.c
* libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.c
* libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.c
* libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_consts.c
* libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_powers.c
* libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_2x.c
* libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_4x.c
* libmceliece-20230612/crypto_kem/6688128f/vec/fft.c
* libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.c
* libmceliece-20230612/crypto_kem/6688128f/vec/gf.c
* libmceliece-20230612/crypto_kem/6688128f/vec/kem_dec.c
* libmceliece-20230612/crypto_kem/6688128f/vec/kem_enc.c
* libmceliece-20230612/crypto_kem/6688128f/vec/kem_keypair.c
* libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.c
* libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.c
* libmceliece-20230612/crypto_kem/6688128f/vec/vec.c
* libmceliece-20230612/crypto_kem/6688128f/vec/wrap_dec.c
* libmceliece-20230612/crypto_kem/6688128f/vec/wrap_enc.c
* libmceliece-20230612/crypto_kem/6688128f/vec/wrap_keypair.c
*
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include "g10lib.h"
#include "mceliece6688128f.h"
#define int8 crypto_int8
#define uint8 crypto_uint8
#define int16 crypto_int16
#define uint16 crypto_uint16
#define int32 crypto_int32
#define uint32 crypto_uint32
#define int64 crypto_int64
#define uint64 crypto_uint64
static void
randombytes (uint8_t *out, size_t outlen)
{
_gcry_randomize (out, outlen, GCRY_STRONG_RANDOM);
}
/* from libmceliece-20230612/include-build/crypto_declassify.h */
#ifndef crypto_declassify_h
#define crypto_declassify_h
static void crypto_declassify(void *crypto_declassify_v,long long crypto_declassify_vlen) {
(void) crypto_declassify_v;
(void) crypto_declassify_vlen;
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/params.h */
#ifndef PARAMS_H
#define PARAMS_H
#define GFBITS 13
#define SYS_N 6688
#define SYS_T 128
#define COND_BYTES ((1 << (GFBITS-4))*(2*GFBITS - 1))
#define IRR_BYTES (SYS_T * 2)
#define PK_NROWS (SYS_T*GFBITS)
#define PK_NCOLS (SYS_N - PK_NROWS)
#define PK_ROW_BYTES ((PK_NCOLS + 7)/8)
#define SYND_BYTES ((PK_NROWS + 7)/8)
#define GFMASK ((1 << GFBITS) - 1)
#endif
/* from libmceliece-20230612/inttypes/crypto_intN.h */
#ifndef crypto_int64_h
#define crypto_int64_h
#define crypto_int64 int64_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_negative_mask(crypto_int64 crypto_int64_x)
{
return crypto_int64_x >> (64-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_nonzero_mask(crypto_int64 crypto_int64_x)
{
return crypto_int64_negative_mask(crypto_int64_x) | crypto_int64_negative_mask(-crypto_int64_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_zero_mask(crypto_int64 crypto_int64_x)
{
return ~crypto_int64_nonzero_mask(crypto_int64_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_positive_mask(crypto_int64 crypto_int64_x)
{
crypto_int64 crypto_int64_z = -crypto_int64_x;
crypto_int64_z ^= crypto_int64_x & crypto_int64_z;
return crypto_int64_negative_mask(crypto_int64_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_unequal_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
{
crypto_int64 crypto_int64_xy = crypto_int64_x ^ crypto_int64_y;
return crypto_int64_nonzero_mask(crypto_int64_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_equal_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
{
return ~crypto_int64_unequal_mask(crypto_int64_x,crypto_int64_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_smaller_mask(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
{
crypto_int64 crypto_int64_xy = crypto_int64_x ^ crypto_int64_y;
crypto_int64 crypto_int64_z = crypto_int64_x - crypto_int64_y;
crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_x);
return crypto_int64_negative_mask(crypto_int64_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_min(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
{
crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
crypto_int64_z &= crypto_int64_xy;
return crypto_int64_x ^ crypto_int64_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int64 crypto_int64_max(crypto_int64 crypto_int64_x,crypto_int64 crypto_int64_y)
{
crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
crypto_int64_z &= crypto_int64_xy;
return crypto_int64_y ^ crypto_int64_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_int64_minmax(crypto_int64 *crypto_int64_a,crypto_int64 *crypto_int64_b)
{
crypto_int64 crypto_int64_x = *crypto_int64_a;
crypto_int64 crypto_int64_y = *crypto_int64_b;
crypto_int64 crypto_int64_xy = crypto_int64_y ^ crypto_int64_x;
crypto_int64 crypto_int64_z = crypto_int64_y - crypto_int64_x;
crypto_int64_z ^= crypto_int64_xy & (crypto_int64_z ^ crypto_int64_y);
crypto_int64_z = crypto_int64_negative_mask(crypto_int64_z);
crypto_int64_z &= crypto_int64_xy;
*crypto_int64_a = crypto_int64_x ^ crypto_int64_z;
*crypto_int64_b = crypto_int64_y ^ crypto_int64_z;
}
#endif
/* from libmceliece-20230612/inttypes/crypto_intN.h */
#ifndef crypto_int16_h
#define crypto_int16_h
#define crypto_int16 int16_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_negative_mask(crypto_int16 crypto_int16_x)
{
return crypto_int16_x >> (16-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_nonzero_mask(crypto_int16 crypto_int16_x)
{
return crypto_int16_negative_mask(crypto_int16_x) | crypto_int16_negative_mask(-crypto_int16_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_zero_mask(crypto_int16 crypto_int16_x)
{
return ~crypto_int16_nonzero_mask(crypto_int16_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_positive_mask(crypto_int16 crypto_int16_x)
{
crypto_int16 crypto_int16_z = -crypto_int16_x;
crypto_int16_z ^= crypto_int16_x & crypto_int16_z;
return crypto_int16_negative_mask(crypto_int16_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_unequal_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
{
crypto_int16 crypto_int16_xy = crypto_int16_x ^ crypto_int16_y;
return crypto_int16_nonzero_mask(crypto_int16_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_equal_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
{
return ~crypto_int16_unequal_mask(crypto_int16_x,crypto_int16_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_smaller_mask(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
{
crypto_int16 crypto_int16_xy = crypto_int16_x ^ crypto_int16_y;
crypto_int16 crypto_int16_z = crypto_int16_x - crypto_int16_y;
crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_x);
return crypto_int16_negative_mask(crypto_int16_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_min(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
{
crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
crypto_int16_z &= crypto_int16_xy;
return crypto_int16_x ^ crypto_int16_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int16 crypto_int16_max(crypto_int16 crypto_int16_x,crypto_int16 crypto_int16_y)
{
crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
crypto_int16_z &= crypto_int16_xy;
return crypto_int16_y ^ crypto_int16_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_int16_minmax(crypto_int16 *crypto_int16_a,crypto_int16 *crypto_int16_b)
{
crypto_int16 crypto_int16_x = *crypto_int16_a;
crypto_int16 crypto_int16_y = *crypto_int16_b;
crypto_int16 crypto_int16_xy = crypto_int16_y ^ crypto_int16_x;
crypto_int16 crypto_int16_z = crypto_int16_y - crypto_int16_x;
crypto_int16_z ^= crypto_int16_xy & (crypto_int16_z ^ crypto_int16_y);
crypto_int16_z = crypto_int16_negative_mask(crypto_int16_z);
crypto_int16_z &= crypto_int16_xy;
*crypto_int16_a = crypto_int16_x ^ crypto_int16_z;
*crypto_int16_b = crypto_int16_y ^ crypto_int16_z;
}
#endif
/* from libmceliece-20230612/inttypes/crypto_intN.h */
#ifndef crypto_int32_h
#define crypto_int32_h
#define crypto_int32 int32_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_negative_mask(crypto_int32 crypto_int32_x)
{
return crypto_int32_x >> (32-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_nonzero_mask(crypto_int32 crypto_int32_x)
{
return crypto_int32_negative_mask(crypto_int32_x) | crypto_int32_negative_mask(-crypto_int32_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_zero_mask(crypto_int32 crypto_int32_x)
{
return ~crypto_int32_nonzero_mask(crypto_int32_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_positive_mask(crypto_int32 crypto_int32_x)
{
crypto_int32 crypto_int32_z = -crypto_int32_x;
crypto_int32_z ^= crypto_int32_x & crypto_int32_z;
return crypto_int32_negative_mask(crypto_int32_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_unequal_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
{
crypto_int32 crypto_int32_xy = crypto_int32_x ^ crypto_int32_y;
return crypto_int32_nonzero_mask(crypto_int32_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_equal_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
{
return ~crypto_int32_unequal_mask(crypto_int32_x,crypto_int32_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_smaller_mask(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
{
crypto_int32 crypto_int32_xy = crypto_int32_x ^ crypto_int32_y;
crypto_int32 crypto_int32_z = crypto_int32_x - crypto_int32_y;
crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_x);
return crypto_int32_negative_mask(crypto_int32_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_min(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
{
crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
crypto_int32_z &= crypto_int32_xy;
return crypto_int32_x ^ crypto_int32_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_int32 crypto_int32_max(crypto_int32 crypto_int32_x,crypto_int32 crypto_int32_y)
{
crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
crypto_int32_z &= crypto_int32_xy;
return crypto_int32_y ^ crypto_int32_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_int32_minmax(crypto_int32 *crypto_int32_a,crypto_int32 *crypto_int32_b)
{
crypto_int32 crypto_int32_x = *crypto_int32_a;
crypto_int32 crypto_int32_y = *crypto_int32_b;
crypto_int32 crypto_int32_xy = crypto_int32_y ^ crypto_int32_x;
crypto_int32 crypto_int32_z = crypto_int32_y - crypto_int32_x;
crypto_int32_z ^= crypto_int32_xy & (crypto_int32_z ^ crypto_int32_y);
crypto_int32_z = crypto_int32_negative_mask(crypto_int32_z);
crypto_int32_z &= crypto_int32_xy;
*crypto_int32_a = crypto_int32_x ^ crypto_int32_z;
*crypto_int32_b = crypto_int32_y ^ crypto_int32_z;
}
#endif
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
#ifndef crypto_uint64_h
#define crypto_uint64_h
#define crypto_uint64 uint64_t
#define crypto_uint64_signed int64_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64_signed crypto_uint64_signed_negative_mask(crypto_uint64_signed crypto_uint64_signed_x)
{
return crypto_uint64_signed_x >> (64-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_nonzero_mask(crypto_uint64 crypto_uint64_x)
{
return crypto_uint64_signed_negative_mask(crypto_uint64_x) | crypto_uint64_signed_negative_mask(-crypto_uint64_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_zero_mask(crypto_uint64 crypto_uint64_x)
{
return ~crypto_uint64_nonzero_mask(crypto_uint64_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_unequal_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
{
crypto_uint64 crypto_uint64_xy = crypto_uint64_x ^ crypto_uint64_y;
return crypto_uint64_nonzero_mask(crypto_uint64_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_equal_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
{
return ~crypto_uint64_unequal_mask(crypto_uint64_x,crypto_uint64_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_smaller_mask(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
{
crypto_uint64 crypto_uint64_xy = crypto_uint64_x ^ crypto_uint64_y;
crypto_uint64 crypto_uint64_z = crypto_uint64_x - crypto_uint64_y;
crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_x ^ (((crypto_uint64) 1) << (64-1)));
return crypto_uint64_signed_negative_mask(crypto_uint64_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_min(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
{
crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
crypto_uint64_z &= crypto_uint64_xy;
return crypto_uint64_x ^ crypto_uint64_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint64 crypto_uint64_max(crypto_uint64 crypto_uint64_x,crypto_uint64 crypto_uint64_y)
{
crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
crypto_uint64_z &= crypto_uint64_xy;
return crypto_uint64_y ^ crypto_uint64_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_uint64_minmax(crypto_uint64 *crypto_uint64_a,crypto_uint64 *crypto_uint64_b)
{
crypto_uint64 crypto_uint64_x = *crypto_uint64_a;
crypto_uint64 crypto_uint64_y = *crypto_uint64_b;
crypto_uint64 crypto_uint64_xy = crypto_uint64_y ^ crypto_uint64_x;
crypto_uint64 crypto_uint64_z = crypto_uint64_y - crypto_uint64_x;
crypto_uint64_z ^= crypto_uint64_xy & (crypto_uint64_z ^ crypto_uint64_y ^ (((crypto_uint64) 1) << (64-1)));
crypto_uint64_z = crypto_uint64_signed_negative_mask(crypto_uint64_z);
crypto_uint64_z &= crypto_uint64_xy;
*crypto_uint64_a = crypto_uint64_x ^ crypto_uint64_z;
*crypto_uint64_b = crypto_uint64_y ^ crypto_uint64_z;
}
#endif
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
#ifndef crypto_uint16_h
#define crypto_uint16_h
#define crypto_uint16 uint16_t
#define crypto_uint16_signed int16_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16_signed crypto_uint16_signed_negative_mask(crypto_uint16_signed crypto_uint16_signed_x)
{
return crypto_uint16_signed_x >> (16-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_nonzero_mask(crypto_uint16 crypto_uint16_x)
{
return crypto_uint16_signed_negative_mask(crypto_uint16_x) | crypto_uint16_signed_negative_mask(-crypto_uint16_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_zero_mask(crypto_uint16 crypto_uint16_x)
{
return ~crypto_uint16_nonzero_mask(crypto_uint16_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_unequal_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
{
crypto_uint16 crypto_uint16_xy = crypto_uint16_x ^ crypto_uint16_y;
return crypto_uint16_nonzero_mask(crypto_uint16_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_equal_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
{
return ~crypto_uint16_unequal_mask(crypto_uint16_x,crypto_uint16_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_smaller_mask(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
{
crypto_uint16 crypto_uint16_xy = crypto_uint16_x ^ crypto_uint16_y;
crypto_uint16 crypto_uint16_z = crypto_uint16_x - crypto_uint16_y;
crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_x ^ (((crypto_uint16) 1) << (16-1)));
return crypto_uint16_signed_negative_mask(crypto_uint16_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_min(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
{
crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
crypto_uint16_z &= crypto_uint16_xy;
return crypto_uint16_x ^ crypto_uint16_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint16 crypto_uint16_max(crypto_uint16 crypto_uint16_x,crypto_uint16 crypto_uint16_y)
{
crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
crypto_uint16_z &= crypto_uint16_xy;
return crypto_uint16_y ^ crypto_uint16_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_uint16_minmax(crypto_uint16 *crypto_uint16_a,crypto_uint16 *crypto_uint16_b)
{
crypto_uint16 crypto_uint16_x = *crypto_uint16_a;
crypto_uint16 crypto_uint16_y = *crypto_uint16_b;
crypto_uint16 crypto_uint16_xy = crypto_uint16_y ^ crypto_uint16_x;
crypto_uint16 crypto_uint16_z = crypto_uint16_y - crypto_uint16_x;
crypto_uint16_z ^= crypto_uint16_xy & (crypto_uint16_z ^ crypto_uint16_y ^ (((crypto_uint16) 1) << (16-1)));
crypto_uint16_z = crypto_uint16_signed_negative_mask(crypto_uint16_z);
crypto_uint16_z &= crypto_uint16_xy;
*crypto_uint16_a = crypto_uint16_x ^ crypto_uint16_z;
*crypto_uint16_b = crypto_uint16_y ^ crypto_uint16_z;
}
#endif
/* from libmceliece-20230612/inttypes/crypto_uintN.h */
#ifndef crypto_uint32_h
#define crypto_uint32_h
#define crypto_uint32 uint32_t
#define crypto_uint32_signed int32_t
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32_signed crypto_uint32_signed_negative_mask(crypto_uint32_signed crypto_uint32_signed_x)
{
return crypto_uint32_signed_x >> (32-1);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_nonzero_mask(crypto_uint32 crypto_uint32_x)
{
return crypto_uint32_signed_negative_mask(crypto_uint32_x) | crypto_uint32_signed_negative_mask(-crypto_uint32_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_zero_mask(crypto_uint32 crypto_uint32_x)
{
return ~crypto_uint32_nonzero_mask(crypto_uint32_x);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_unequal_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
{
crypto_uint32 crypto_uint32_xy = crypto_uint32_x ^ crypto_uint32_y;
return crypto_uint32_nonzero_mask(crypto_uint32_xy);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_equal_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
{
return ~crypto_uint32_unequal_mask(crypto_uint32_x,crypto_uint32_y);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_smaller_mask(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
{
crypto_uint32 crypto_uint32_xy = crypto_uint32_x ^ crypto_uint32_y;
crypto_uint32 crypto_uint32_z = crypto_uint32_x - crypto_uint32_y;
crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_x ^ (((crypto_uint32) 1) << (32-1)));
return crypto_uint32_signed_negative_mask(crypto_uint32_z);
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_min(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
{
crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
crypto_uint32_z &= crypto_uint32_xy;
return crypto_uint32_x ^ crypto_uint32_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static crypto_uint32 crypto_uint32_max(crypto_uint32 crypto_uint32_x,crypto_uint32 crypto_uint32_y)
{
crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
crypto_uint32_z &= crypto_uint32_xy;
return crypto_uint32_y ^ crypto_uint32_z;
}
-__attribute__((unused))
+GCC_ATTR_UNUSED
static void crypto_uint32_minmax(crypto_uint32 *crypto_uint32_a,crypto_uint32 *crypto_uint32_b)
{
crypto_uint32 crypto_uint32_x = *crypto_uint32_a;
crypto_uint32 crypto_uint32_y = *crypto_uint32_b;
crypto_uint32 crypto_uint32_xy = crypto_uint32_y ^ crypto_uint32_x;
crypto_uint32 crypto_uint32_z = crypto_uint32_y - crypto_uint32_x;
crypto_uint32_z ^= crypto_uint32_xy & (crypto_uint32_z ^ crypto_uint32_y ^ (((crypto_uint32) 1) << (32-1)));
crypto_uint32_z = crypto_uint32_signed_negative_mask(crypto_uint32_z);
crypto_uint32_z &= crypto_uint32_xy;
*crypto_uint32_a = crypto_uint32_x ^ crypto_uint32_z;
*crypto_uint32_b = crypto_uint32_y ^ crypto_uint32_z;
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/vec.h */
#ifndef VEC_H
#define VEC_H
typedef uint64_t vec;
static inline vec vec_setbits(vec b)
{
vec ret = -b;
return ret;
}
static inline vec vec_set1_16b(uint16_t v)
{
vec ret;
ret = v;
ret |= ret << 16;
ret |= ret << 32;
return ret;
}
static inline void vec_copy(vec * out, vec * in)
{
int i;
for (i = 0; i < GFBITS; i++)
out[i] = in[i];
}
static inline vec vec_or_reduce(vec * a)
{
int i;
vec ret;
ret = a[0];
for (i = 1; i < GFBITS; i++)
ret |= a[i];
return ret;
}
static inline int vec_testz(vec a)
{
a |= a >> 32;
a |= a >> 16;
a |= a >> 8;
a |= a >> 4;
a |= a >> 2;
a |= a >> 1;
return (a&1)^1;
}
static void vec_mul(vec *, const vec *, const vec *);
static void vec_sq(vec *, vec *);
static void vec_inv(vec *, vec *);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/benes.h */
/*
This file is for Benes network related functions
*/
#ifndef BENES_H
#define BENES_H
static void benes(vec *, const unsigned char *, int);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/bm.h */
/*
This file is for the inversion-free Berlekamp-Massey algorithm
see https://ieeexplore.ieee.org/document/87857
*/
#ifndef BM_H
#define BM_H
static void bm(vec [][GFBITS], vec [][ GFBITS ]);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.h */
/* This file is for implementing the Nassimi-Sahni algorithm */
/* See David Nassimi, Sartaj Sahni "Parallel algorithms to set up the Benes permutationnetwork" */
/* See also https://cr.yp.to/papers/controlbits-20200923.pdf */
#ifndef CONTROLBITS_H
#define CONTROLBITS_H
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.h */
/*
This file is for Nieddereiter decryption
*/
#ifndef DECRYPT_H
#define DECRYPT_H
static int decrypt(unsigned char *, const unsigned char *, const unsigned char *);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.h */
/*
This file is for Niederreiter encryption
*/
/* 20230102 djb: rename encrypt() as pke_encrypt() */
#ifndef ENCRYPT_H
#define ENCRYPT_H
static void pke_encrypt(unsigned char *, const unsigned char *, unsigned char *);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_consts.h */
#ifndef fft_consts_h
#define fft_consts_h
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft.h */
/*
This file is for the Gao-Mateer FFT
sse http://www.math.clemson.edu/~sgao/papers/GM10.pdf
*/
#ifndef FFT_H
#define FFT_H
static void fft(vec [][GFBITS], vec [][GFBITS]);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_powers.h */
#ifndef fft_powers_h
#define fft_powers_h
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_2x.h */
#ifndef fft_scalars_2x_h
#define fft_scalars_2x_h
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_scalars_4x.h */
#ifndef fft_scalars_4x_h
#define fft_scalars_4x_h
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.h */
/*
This file is for transpose of the Gao-Mateer FFT
*/
#ifndef FFT_TR_H
#define FFT_TR_H
static void fft_tr(vec out[][GFBITS], vec in[][ GFBITS ]);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/gf.h */
/*
This file is for functions for field arithmetic
*/
/* 20221231 djb: const for GF_mul */
#ifndef GF_H
#define GF_H
typedef uint16_t gf;
gf gf_iszero(gf);
gf gf_mul(gf, gf);
gf gf_frac(gf, gf);
gf gf_inv(gf);
static void GF_mul(gf *, const gf *, const gf *);
/* 2 field multiplications */
static inline uint64_t gf_mul2(gf a, gf b0, gf b1)
{
int i;
uint64_t tmp=0;
uint64_t t0;
uint64_t t1;
uint64_t t;
uint64_t mask = 0x0000000100000001;
t0 = a;
t1 = b1;
t1 = (t1 << 32) | b0;
for (i = 0; i < GFBITS; i++)
{
tmp ^= t0 * (t1 & mask);
mask += mask;
}
/**/
t = tmp & 0x01FF000001FF0000;
tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
t = tmp & 0x0000E0000000E000;
tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
return tmp & 0x00001FFF00001FFF;
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/hash.h */
#define shake crypto_xof_shake256
#define crypto_hash_32b(out,in,inlen) \
shake(out,32,in,inlen)
/* from libmceliece-20230612/crypto_kem/6688128f/vec/int32_sort.h */
#ifndef int32_sort_h
#define int32_sort_h
#define int32_MINMAX(a,b) \
do { \
int64_t ab = (int64_t)b ^ (int64_t)a; \
int64_t c = (int64_t)b - (int64_t)a; \
c ^= ab & (c ^ b); \
c >>= 31; \
c &= ab; \
a ^= c; \
b ^= c; \
} while(0)
static void int32_sort(int32_t *x,long long n)
{
long long top,p,q,r,i;
if (n < 2) return;
top = 1;
while (top < n - top) top += top;
for (p = top;p > 0;p >>= 1) {
for (i = 0;i < n - p;++i)
if (!(i & p))
int32_MINMAX(x[i],x[i+p]);
i = 0;
for (q = top;q > p;q >>= 1) {
for (;i < n - q;++i) {
if (!(i & p)) {
int32_t a = x[i + p];
for (r = q;r > p;r >>= 1)
int32_MINMAX(a,x[i+r]);
x[i + p] = a;
}
}
}
}
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/operations.h */
#ifndef OPERATIONS_H
#define OPERATIONS_H
static void operation_enc(
unsigned char *c,
unsigned char *key,
const unsigned char *pk
);
static void operation_dec(
unsigned char *key,
const unsigned char *c,
const unsigned char *sk
);
static void operation_keypair
(
unsigned char *pk,
unsigned char *sk
);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.h */
/*
This file is for public-key generation
*/
#ifndef PK_GEN_H
#define PK_GEN_H
static int pk_gen(unsigned char *, const unsigned char *, uint32_t *, int16_t *, uint64_t *);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.h */
/*
This file is for secret-key generation
*/
#ifndef SK_GEN_H
#define SK_GEN_H
static int genpoly_gen(gf *, gf *);
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/transpose.h */
/*
This file is for matrix transposition
*/
#ifndef TRANSPOSE_H
#define TRANSPOSE_H
/* input: in, a 64x64 matrix over GF(2) */
/* output: out, transpose of in */
static inline void transpose_64x64(uint64_t * out, uint64_t * in)
{
int i, j, s, d;
uint64_t x, y;
uint64_t masks[6][2] = {
{0x5555555555555555, 0xAAAAAAAAAAAAAAAA},
{0x3333333333333333, 0xCCCCCCCCCCCCCCCC},
{0x0F0F0F0F0F0F0F0F, 0xF0F0F0F0F0F0F0F0},
{0x00FF00FF00FF00FF, 0xFF00FF00FF00FF00},
{0x0000FFFF0000FFFF, 0xFFFF0000FFFF0000},
{0x00000000FFFFFFFF, 0xFFFFFFFF00000000}
};
for (i = 0; i < 64; i++)
out[i] = in[i];
for (d = 5; d >= 0; d--)
{
s = 1 << d;
for (i = 0; i < 64; i += s*2)
for (j = i; j < i+s; j++)
{
x = (out[j] & masks[d][0]) | ((out[j+s] & masks[d][0]) << s);
y = ((out[j] & masks[d][1]) >> s) | (out[j+s] & masks[d][1]);
out[j+0] = x;
out[j+s] = y;
}
}
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/uint16_sort.h */
#ifndef uint16_sort_h
#define uint16_sort_h
#define uint16_MINMAX(a,b) \
do { \
uint16_t c = b - a; \
c >>= 15; \
c = -c; \
c &= a ^ b; \
a ^= c; \
b ^= c; \
} while(0)
static void uint16_sort(uint16_t *x,long long n)
{
long long top,p,q,r,i;
if (n < 2) return;
top = 1;
while (top < n - top) top += top;
for (p = top;p > 0;p >>= 1) {
for (i = 0;i < n - p;++i)
if (!(i & p))
uint16_MINMAX(x[i],x[i+p]);
i = 0;
for (q = top;q > p;q >>= 1) {
for (;i < n - q;++i) {
if (!(i & p)) {
int16_t a = x[i + p];
for (r = q;r > p;r >>= 1)
uint16_MINMAX(a,x[i+r]);
x[i + p] = a;
}
}
}
}
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/uint64_sort.h */
#ifndef uint64_sort_h
#define uint64_sort_h
#define uint64_MINMAX(a,b) \
do { \
uint64_t c = b - a; \
c >>= 63; \
c = -c; \
c &= a ^ b; \
a ^= c; \
b ^= c; \
} while(0)
static void uint64_sort(uint64_t *x,long long n)
{
long long top,p,q,r,i;
if (n < 2) return;
top = 1;
while (top < n - top) top += top;
for (p = top;p > 0;p >>= 1) {
for (i = 0;i < n - p;++i)
if (!(i & p))
uint64_MINMAX(x[i],x[i+p]);
i = 0;
for (q = top;q > p;q >>= 1) {
for (;i < n - q;++i) {
if (!(i & p)) {
uint64_t a = x[i + p];
for (r = q;r > p;r >>= 1)
uint64_MINMAX(a,x[i+r]);
x[i + p] = a;
}
}
}
}
}
#endif
/* from libmceliece-20230612/crypto_kem/6688128f/vec/util.h */
/*
This file is for loading/storing data in a little-endian fashion
*/
#ifndef UTIL_H
#define UTIL_H
static inline void store_i(unsigned char *out, uint64_t in, int i)
{
int j;
for (j = 0; j < i; j++)
out[j] = (in >> (j * 8)) & 0xFF;
}
static inline void store_gf(unsigned char *dest, uint16_t a)
{
dest[0] = a & 0xFF;
dest[1] = a >> 8;
}
static inline uint16_t load_gf(const unsigned char *src)
{
uint16_t a;
a = src[1];
a <<= 8;
a |= src[0];
return a & GFMASK;
}
static inline uint32_t load4(const unsigned char *src)
{
uint32_t a;
a = src[3]; a <<= 8;
a |= src[2]; a <<= 8;
a |= src[1]; a <<= 8;
a |= src[0];
return a;
}
static inline void irr_load(vec out[][GFBITS], const unsigned char * in)
{
int i, j;
uint64_t v0 = 0, v1 = 0;
uint16_t irr[ SYS_T ];
for (i = 0; i < SYS_T; i++)
irr[i] = load_gf(in + i*2);
for (i = 0; i < GFBITS; i++)
{
for (j = 63; j >= 0; j--)
{
v0 <<= 1;
v1 <<= 1;
v0 |= (irr[j] >> i) & 1;
v1 |= (irr[j+64] >> i) & 1;
}
out[0][i] = v0;
out[1][i] = v1;
}
}
static inline void store8(unsigned char *out, uint64_t in)
{
out[0] = (in >> 0x00) & 0xFF;
out[1] = (in >> 0x08) & 0xFF;
out[2] = (in >> 0x10) & 0xFF;
out[3] = (in >> 0x18) & 0xFF;
out[4] = (in >> 0x20) & 0xFF;
out[5] = (in >> 0x28) & 0xFF;
out[6] = (in >> 0x30) & 0xFF;
out[7] = (in >> 0x38) & 0xFF;
}
static inline uint64_t load8(const unsigned char * in)
{
int i;
uint64_t ret = in[7];
for (i = 6; i >= 0; i--)
{
ret <<= 8;
ret |= in[i];
}
return ret;
}
#endif
static void crypto_xof_shake256(unsigned char *h,long long hlen,
const unsigned char *m,long long mlen)
{
gcry_md_hd_t mdh;
gcry_err_code_t ec;
ec = _gcry_md_open (&mdh, GCRY_MD_SHAKE256, 0);
if (ec)
log_fatal ("internal md_open failed: %d\n", ec);
_gcry_md_write (mdh, m, mlen);
_gcry_md_extract (mdh, GCRY_MD_SHAKE256, h, hlen);
_gcry_md_close (mdh);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/benes.c */
/*
This file is for Benes network related functions
For the implementation strategy, see
https://eprint.iacr.org/2017/793.pdf
*/
/* 20221230 djb: add linker lines */
/* linker define benes */
/* middle layers of the benes network */
static void layer_in(uint64_t data[2][64], uint64_t * bits, int lgs)
{
int i, j, s;
uint64_t d;
s = 1 << lgs;
for (i = 0; i < 64; i += s*2)
for (j = i; j < i+s; j++)
{
d = (data[0][j+0] ^ data[0][j+s]);
d &= (*bits++);
data[0][j+0] ^= d;
data[0][j+s] ^= d;
d = (data[1][j+0] ^ data[1][j+s]);
d &= (*bits++);
data[1][j+0] ^= d;
data[1][j+s] ^= d;
}
}
/* first and last layers of the benes network */
static void layer_ex(uint64_t * data, uint64_t * bits, int lgs)
{
int i, j, s;
uint64_t d;
s = 1 << lgs;
for (i = 0; i < 128; i += s*2)
for (j = i; j < i+s; j++)
{
d = (data[j+0] ^ data[j+s]);
d &= (*bits++);
data[j+0] ^= d;
data[j+s] ^= d;
}
}
/* input: r, sequence of bits to be permuted */
/* bits, condition bits of the Benes network */
/* rev, 0 for normal application; !0 for inverse */
/* output: r, permuted bits */
static void benes(vec * r, const unsigned char * bits, int rev)
{
int i, iter, inc;
const unsigned char *bits_ptr;
uint64_t r_int_v[2][64];
uint64_t r_int_h[2][64];
uint64_t b_int_v[64];
uint64_t b_int_h[64];
/**/
if (rev) { bits_ptr = bits + 12288; inc = -1024; }
else { bits_ptr = bits; inc = 0; }
for (i = 0; i < 64; i++)
{
r_int_v[0][i] = r[i*2 + 0];
r_int_v[1][i] = r[i*2 + 1];
}
transpose_64x64(r_int_h[0], r_int_v[0]);
transpose_64x64(r_int_h[1], r_int_v[1]);
for (iter = 0; iter <= 6; iter++)
{
for (i = 0; i < 64; i++)
{
b_int_v[i] = load8(bits_ptr); bits_ptr += 8;
}
bits_ptr += inc;
transpose_64x64(b_int_h, b_int_v);
layer_ex(r_int_h[0], b_int_h, iter);
}
transpose_64x64(r_int_v[0], r_int_h[0]);
transpose_64x64(r_int_v[1], r_int_h[1]);
for (iter = 0; iter <= 5; iter++)
{
for (i = 0; i < 64; i++) { b_int_v[i] = load8(bits_ptr); bits_ptr += 8; }
bits_ptr += inc;
layer_in(r_int_v, b_int_v, iter);
}
for (iter = 4; iter >= 0; iter--)
{
for (i = 0; i < 64; i++) { b_int_v[i] = load8(bits_ptr); bits_ptr += 8; }
bits_ptr += inc;
layer_in(r_int_v, b_int_v, iter);
}
transpose_64x64(r_int_h[0], r_int_v[0]);
transpose_64x64(r_int_h[1], r_int_v[1]);
for (iter = 6; iter >= 0; iter--)
{
for (i = 0; i < 64; i++)
{
b_int_v[i] = load8(bits_ptr); bits_ptr += 8;
}
bits_ptr += inc;
transpose_64x64(b_int_h, b_int_v);
layer_ex(r_int_h[0], b_int_h, iter);
}
transpose_64x64(r_int_v[0], r_int_h[0]);
transpose_64x64(r_int_v[1], r_int_h[1]);
for (i = 0; i < 64; i++)
{
r[i*2+0] = r_int_v[0][i];
r[i*2+1] = r_int_v[1][i];
}
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/bm.c */
/*
This file is for implementating the inversion-free Berlekamp-Massey algorithm
see https://ieeexplore.ieee.org/document/87857
For the implementation strategy, see
https://eprint.iacr.org/2017/793.pdf
*/
/* 20221230 djb: add linker lines */
/* linker define bm */
/* linker use vec_mul */
/* linker use gf_inv */
static inline uint16_t mask_nonzero(gf a)
{
uint32_t ret = a;
ret -= 1;
ret >>= 31;
ret -= 1;
return ret;
}
static inline uint16_t mask_leq(uint16_t a, uint16_t b)
{
uint32_t a_tmp = a;
uint32_t b_tmp = b;
uint32_t ret = b_tmp - a_tmp;
ret >>= 31;
ret -= 1;
return ret;
}
static inline void vec_cmov(vec * out, vec * in, uint16_t mask)
{
int i;
vec m0, m1;
m0 = vec_set1_16b(mask);
m1 = ~m0;
for (i = 0; i < GFBITS; i++)
{
out[i] = (in[i] & m0) | (out[i] & m1);
out[i] = (in[i] & m0) | (out[i] & m1);
}
}
static inline void interleave(vec *in, int idx0, int idx1, vec *mask, int b)
{
int s = 1 << b;
vec x, y;
x = (in[idx0] & mask[0]) | ((in[idx1] & mask[0]) << s);
y = ((in[idx0] & mask[1]) >> s) | (in[idx1] & mask[1]);
in[idx0] = x;
in[idx1] = y;
}
/* input: in, field elements in bitsliced form */
/* output: out, field elements in non-bitsliced form */
static inline void get_coefs(gf *out, vec *in)
{
int i, k;
vec mask[4][2];
vec buf[16];
for (i = 0; i < 13; i++) buf[i] = in[i];
for (i = 13; i < 16; i++) buf[i] = 0;
mask[0][0] = vec_set1_16b(0x5555);
mask[0][1] = vec_set1_16b(0xAAAA);
mask[1][0] = vec_set1_16b(0x3333);
mask[1][1] = vec_set1_16b(0xCCCC);
mask[2][0] = vec_set1_16b(0x0F0F);
mask[2][1] = vec_set1_16b(0xF0F0);
mask[3][0] = vec_set1_16b(0x00FF);
mask[3][1] = vec_set1_16b(0xFF00);
interleave(buf, 0, 8, mask[3], 3);
interleave(buf, 1, 9, mask[3], 3);
interleave(buf, 2, 10, mask[3], 3);
interleave(buf, 3, 11, mask[3], 3);
interleave(buf, 4, 12, mask[3], 3);
interleave(buf, 5, 13, mask[3], 3);
interleave(buf, 6, 14, mask[3], 3);
interleave(buf, 7, 15, mask[3], 3);
interleave(buf, 0, 4, mask[2], 2);
interleave(buf, 1, 5, mask[2], 2);
interleave(buf, 2, 6, mask[2], 2);
interleave(buf, 3, 7, mask[2], 2);
interleave(buf, 8, 12, mask[2], 2);
interleave(buf, 9, 13, mask[2], 2);
interleave(buf, 10, 14, mask[2], 2);
interleave(buf, 11, 15, mask[2], 2);
interleave(buf, 0, 2, mask[1], 1);
interleave(buf, 1, 3, mask[1], 1);
interleave(buf, 4, 6, mask[1], 1);
interleave(buf, 5, 7, mask[1], 1);
interleave(buf, 8, 10, mask[1], 1);
interleave(buf, 9, 11, mask[1], 1);
interleave(buf, 12, 14, mask[1], 1);
interleave(buf, 13, 15, mask[1], 1);
interleave(buf, 0, 1, mask[0], 0);
interleave(buf, 2, 3, mask[0], 0);
interleave(buf, 4, 5, mask[0], 0);
interleave(buf, 6, 7, mask[0], 0);
interleave(buf, 8, 9, mask[0], 0);
interleave(buf, 10, 11, mask[0], 0);
interleave(buf, 12, 13, mask[0], 0);
interleave(buf, 14, 15, mask[0], 0);
for (i = 0; i < 16; i++)
for (k = 0; k < 4; k++)
out[ k*16 + i ] = (buf[i] >> (k*16)) & GFMASK;
}
static void update(vec in[][GFBITS], const gf e)
{
int i;
vec tmp;
for (i = 0; i < GFBITS; i++)
{
tmp = (e >> i) & 1;
in[0][i] = (in[0][i] >> 1) | (in[1][i] << 63);
in[1][i] = (in[1][i] >> 1) | (tmp << 63);
}
}
static inline gf vec_reduce(vec in[][GFBITS])
{
int i;
vec tmp;
gf ret = 0;
for (i = GFBITS-1; i >= 0; i--)
{
tmp = in[0][i] ^ in[1][i];
tmp ^= tmp >> 32;
tmp ^= tmp >> 16;
tmp ^= tmp >> 8;
tmp ^= tmp >> 4;
tmp ^= tmp >> 2;
tmp ^= tmp >> 1;
ret <<= 1;
ret |= tmp & 1;
}
return ret;
}
/* input: in, sequence of field elements */
/* output: out, minimal polynomial of in */
static void bm(vec out[][ GFBITS ], vec in[][ GFBITS ])
{
int i;
uint16_t N, L;
uint16_t mask;
uint64_t one = 1, t;
vec prod[2][GFBITS];
vec interval[2][GFBITS];
vec dd[2][GFBITS], bb[2][GFBITS];
vec B[2][GFBITS], C[2][GFBITS];
vec B_tmp[2][GFBITS], C_tmp[2][GFBITS];
vec v[GFBITS];
gf d, b, c0 = 1;
gf coefs[256];
/* initialization */
get_coefs(&coefs[ 0], in[0]);
get_coefs(&coefs[ 64], in[1]);
get_coefs(&coefs[128], in[2]);
get_coefs(&coefs[192], in[3]);
C[0][0] = 0;
C[1][0] = 0;
B[0][0] = 0;
B[1][0] = one << 63;
for (i = 1; i < GFBITS; i++)
C[0][i] = C[1][i] = B[0][i] = B[1][i] = 0;
b = 1;
L = 0;
/**/
for (i = 0; i < GFBITS; i++)
interval[0][i] = interval[1][i] = 0;
for (N = 0; N < 256; N++)
{
vec_mul(prod[0], C[0], interval[0]);
vec_mul(prod[1], C[1], interval[1]);
update(interval, coefs[N]);
d = vec_reduce(prod);
t = gf_mul2(c0, coefs[N], b);
d ^= t & 0xFFFFFFFF;
mask = mask_nonzero(d) & mask_leq(L*2, N);
for (i = 0; i < GFBITS; i++)
{
dd[0][i] = dd[1][i] = vec_setbits((d >> i) & 1);
bb[0][i] = bb[1][i] = vec_setbits((b >> i) & 1);
}
vec_mul(B_tmp[0], dd[0], B[0]);
vec_mul(B_tmp[1], dd[1], B[1]);
vec_mul(C_tmp[0], bb[0], C[0]);
vec_mul(C_tmp[1], bb[1], C[1]);
vec_cmov(B[0], C[0], mask);
vec_cmov(B[1], C[1], mask);
update(B, c0 & mask);
for (i = 0; i < GFBITS; i++)
{
C[0][i] = B_tmp[0][i] ^ C_tmp[0][i];
C[1][i] = B_tmp[1][i] ^ C_tmp[1][i];
}
c0 = t >> 32;
b = (d & mask) | (b & ~mask);
L = ((N+1-L) & mask) | (L & ~mask);
}
c0 = gf_inv(c0);
for (i = 0; i < GFBITS; i++)
v[i] = vec_setbits((c0 >> i) & 1);
vec_mul(out[0], C[0], v);
vec_mul(out[1], C[1], v);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/controlbits.c */
/* This file is for implementing the Nassimi-Sahni algorithm */
/* See David Nassimi, Sartaj Sahni "Parallel algorithms to set up the Benes permutationnetwork" */
/* See also https://cr.yp.to/papers/controlbits-20200923.pdf */
/* 20221230 djb: add linker line */
/* linker define controlbitsfrompermutation */
typedef int16_t int16;
typedef int32_t int32;
#define int32_min crypto_int32_min
/* parameters: 1 <= w <= 14; n = 2^w */
/* input: permutation pi of {0,1,...,n-1} */
/* output: (2m-1)n/2 control bits at positions pos,pos+step,... */
/* output position pos is by definition 1&(out[pos/8]>>(pos&7)) */
/* caller must 0-initialize positions first */
/* temp must have space for int32[2*n] */
static void cbrecursion(unsigned char *out,long long pos,long long step,const int16 *pi,long long w,long long n,int32 *temp)
{
#define A temp
#define B (temp+n)
#define q ((int16 *) (temp+n+n/4))
/* q can start anywhere between temp+n and temp+n/2 */
long long x,i,j,k;
if (w == 1) {
out[pos>>3] ^= pi[0]<<(pos&7);
return;
}
for (x = 0;x < n;++x) A[x] = ((pi[x]^1)<<16)|pi[x^1];
int32_sort(A,n); /* A = (id<<16)+pibar */
for (x = 0;x < n;++x) {
int32 Ax = A[x];
int32 px = Ax&0xffff;
int32 cx = int32_min(px,x);
B[x] = (px<<16)|cx;
}
/* B = (p<<16)+c */
for (x = 0;x < n;++x) A[x] = (A[x]<<16)|x; /* A = (pibar<<16)+id */
int32_sort(A,n); /* A = (id<<16)+pibar^-1 */
for (x = 0;x < n;++x) A[x] = (A[x]<<16)+(B[x]>>16); /* A = (pibar^(-1)<<16)+pibar */
int32_sort(A,n); /* A = (id<<16)+pibar^2 */
if (w <= 10) {
for (x = 0;x < n;++x) B[x] = ((A[x]&0xffff)<<10)|(B[x]&0x3ff);
for (i = 1;i < w-1;++i) {
/* B = (p<<10)+c */
for (x = 0;x < n;++x) A[x] = ((B[x]&~0x3ff)<<6)|x; /* A = (p<<16)+id */
int32_sort(A,n); /* A = (id<<16)+p^{-1} */
for (x = 0;x < n;++x) A[x] = (A[x]<<20)|B[x]; /* A = (p^{-1}<<20)+(p<<10)+c */
int32_sort(A,n); /* A = (id<<20)+(pp<<10)+cp */
for (x = 0;x < n;++x) {
int32 ppcpx = A[x]&0xfffff;
int32 ppcx = (A[x]&0xffc00)|(B[x]&0x3ff);
B[x] = int32_min(ppcx,ppcpx);
}
}
for (x = 0;x < n;++x) B[x] &= 0x3ff;
} else {
for (x = 0;x < n;++x) B[x] = (A[x]<<16)|(B[x]&0xffff);
for (i = 1;i < w-1;++i) {
/* B = (p<<16)+c */
for (x = 0;x < n;++x) A[x] = (B[x]&~0xffff)|x;
int32_sort(A,n); /* A = (id<<16)+p^(-1) */
for (x = 0;x < n;++x) A[x] = (A[x]<<16)|(B[x]&0xffff);
/* A = p^(-1)<<16+c */
if (i < w-2) {
for (x = 0;x < n;++x) B[x] = (A[x]&~0xffff)|(B[x]>>16);
/* B = (p^(-1)<<16)+p */
int32_sort(B,n); /* B = (id<<16)+p^(-2) */
for (x = 0;x < n;++x) B[x] = (B[x]<<16)|(A[x]&0xffff);
/* B = (p^(-2)<<16)+c */
}
int32_sort(A,n);
/* A = id<<16+cp */
for (x = 0;x < n;++x) {
int32 cpx = (B[x]&~0xffff)|(A[x]&0xffff);
B[x] = int32_min(B[x],cpx);
}
}
for (x = 0;x < n;++x) B[x] &= 0xffff;
}
for (x = 0;x < n;++x) A[x] = (((int32)pi[x])<<16)+x;
int32_sort(A,n); /* A = (id<<16)+pi^(-1) */
for (j = 0;j < n/2;++j) {
long long lx = 2*j;
int32 fj = B[lx]&1; /* f[j] */
int32 Fx = lx+fj; /* F[x] */
int32 Fx1 = Fx^1; /* F[x+1] */
out[pos>>3] ^= fj<<(pos&7);
pos += step;
B[lx] = (A[lx]<<16)|Fx;
B[lx+1] = (A[lx+1]<<16)|Fx1;
}
/* B = (pi^(-1)<<16)+F */
int32_sort(B,n); /* B = (id<<16)+F(pi) */
pos += (2*w-3)*step*(n/2);
for (k = 0;k < n/2;++k) {
long long y = 2*k;
int32 lk = B[y]&1; /* l[k] */
int32 Ly = y+lk; /* L[y] */
int32 Ly1 = Ly^1; /* L[y+1] */
out[pos>>3] ^= lk<<(pos&7);
pos += step;
A[y] = (Ly<<16)|(B[y]&0xffff);
A[y+1] = (Ly1<<16)|(B[y+1]&0xffff);
}
/* A = (L<<16)+F(pi) */
int32_sort(A,n); /* A = (id<<16)+F(pi(L)) = (id<<16)+M */
pos -= (2*w-2)*step*(n/2);
for (j = 0;j < n/2;++j) {
q[j] = (A[2*j]&0xffff)>>1;
q[j+n/2] = (A[2*j+1]&0xffff)>>1;
}
cbrecursion(out,pos,step*2,q,w-1,n/2,temp);
cbrecursion(out,pos+step,step*2,q+n/2,w-1,n/2,temp);
}
/* input: p, an array of int16 */
/* input: n, length of p */
/* input: s, meaning that stride-2^s cswaps are performed */
/* input: cb, the control bits */
/* output: the result of apply the control bits to p */
static void layer(int16_t *p, const unsigned char *cb, int s, int n)
{
int i, j;
int stride = 1 << s;
int index = 0;
int16_t d, m;
for (i = 0; i < n; i += stride*2)
{
for (j = 0; j < stride; j++)
{
d = p[ i+j ] ^ p[ i+j+stride ];
m = (cb[ index >> 3 ] >> (index & 7)) & 1;
m = -m;
d &= m;
p[ i+j ] ^= d;
p[ i+j+stride ] ^= d;
index++;
}
}
}
/* parameters: 1 <= w <= 14; n = 2^w */
/* input: permutation pi of {0,1,...,n-1} */
/* output: (2m-1)n/2 control bits at positions 0,1,... */
/* output position pos is by definition 1&(out[pos/8]>>(pos&7)) */
static void controlbitsfrompermutation(unsigned char *out,const int16 *pi,long long w,long long n)
{
int32 temp[2*n];
int16 pi_test[n], diff;
int i;
unsigned char *ptr;
while (1)
{
memset(out,0,(((2*w-1)*n/2)+7)/8);
cbrecursion(out,0,1,pi,w,n,temp);
/* check for correctness */
for (i = 0; i < n; i++)
pi_test[i] = i;
ptr = out;
for (i = 0; i < w; i++)
{
layer(pi_test, ptr, i, n);
ptr += n >> 4;
}
for (i = w-2; i >= 0; i--)
{
layer(pi_test, ptr, i, n);
ptr += n >> 4;
}
diff = 0;
for (i = 0; i < n; i++)
diff |= pi[i] ^ pi_test[i];
diff = crypto_int16_nonzero_mask(diff);
crypto_declassify(&diff,sizeof diff);
if (diff == 0)
break;
}
}
#undef A
#undef B
#undef q
/* from libmceliece-20230612/crypto_kem/6688128f/vec/decrypt.c */
/*
This file is for Niederreiter decryption
*/
/* 20221230 djb: add linker lines */
/* linker define decrypt */
/* linker use benes bm fft fft_tr */
/* linker use vec_mul vec_sq vec_inv */
static void scaling(vec out[][GFBITS], vec inv[][GFBITS], const unsigned char *sk, vec *recv)
{
int i, j;
vec irr_int[2][ GFBITS ];
vec eval[128][ GFBITS ];
vec tmp[ GFBITS ];
/**/
irr_load(irr_int, sk);
fft(eval, irr_int);
for (i = 0; i < 128; i++)
vec_sq(eval[i], eval[i]);
vec_copy(inv[0], eval[0]);
for (i = 1; i < 128; i++)
vec_mul(inv[i], inv[i-1], eval[i]);
vec_inv(tmp, inv[127]);
for (i = 126; i >= 0; i--)
{
vec_mul(inv[i+1], tmp, inv[i]);
vec_mul(tmp, tmp, eval[i+1]);
}
vec_copy(inv[0], tmp);
/**/
for (i = 0; i < 128; i++)
for (j = 0; j < GFBITS; j++)
out[i][j] = inv[i][j] & recv[i];
}
static void preprocess(vec *recv, const unsigned char *s)
{
int i;
unsigned char r[ 1024 ];
for (i = 0; i < SYND_BYTES; i++)
r[i] = s[i];
for (i = SYND_BYTES; i < 1024; i++)
r[i] = 0;
for (i = 0; i < 128; i++)
recv[i] = load8(r + i*8);
}
static void postprocess(unsigned char * e, vec * err)
{
int i;
unsigned char error8[ (1 << GFBITS)/8 ];
for (i = 0; i < 128; i++)
store8(error8 + i*8, err[i]);
for (i = 0; i < SYS_N/8; i++)
e[i] = error8[i];
}
static void scaling_inv(vec out[][GFBITS], vec inv[][GFBITS], vec *recv)
{
int i, j;
for (i = 0; i < 128; i++)
for (j = 0; j < GFBITS; j++)
out[i][j] = inv[i][j] & recv[i];
}
static int weight_check(unsigned char * e, vec * error)
{
int i;
uint16_t w0 = 0;
uint16_t w1 = 0;
uint16_t check;
for (i = 0; i < (1 << GFBITS); i++)
w0 += (error[i/64] >> (i%64)) & 1;
for (i = 0; i < SYS_N; i++)
w1 += (e[i/8] >> (i%8)) & 1;
check = (w0 ^ SYS_T) | (w1 ^ SYS_T);
check -= 1;
check >>= 15;
return check;
}
static uint16_t synd_cmp(vec s0[][ GFBITS ] , vec s1[][ GFBITS ])
{
int i, j;
vec diff = 0;
for (i = 0; i < 4; i++)
for (j = 0; j < GFBITS; j++)
diff |= (s0[i][j] ^ s1[i][j]);
return vec_testz(diff);
}
/* Niederreiter decryption with the Berlekamp decoder */
/* intput: sk, secret key */
/* s, ciphertext (syndrome) */
/* output: e, error vector */
/* return: 0 for success; 1 for failure */
static int decrypt(unsigned char *e, const unsigned char *sk, const unsigned char *s)
{
int i;
uint16_t check_synd;
uint16_t check_weight;
vec inv[ 128 ][ GFBITS ];
vec scaled[ 128 ][ GFBITS ];
vec eval[ 128 ][ GFBITS ];
vec error[ 128 ];
vec s_priv[ 4 ][ GFBITS ];
vec s_priv_cmp[ 4 ][ GFBITS ];
vec locator[2][ GFBITS ];
vec recv[ 128 ];
vec allone;
/* Berlekamp decoder */
preprocess(recv, s);
benes(recv, sk + IRR_BYTES, 1);
scaling(scaled, inv, sk, recv);
fft_tr(s_priv, scaled);
bm(locator, s_priv);
fft(eval, locator);
/* reencryption and weight check */
allone = vec_setbits(1);
for (i = 0; i < 128; i++)
{
error[i] = vec_or_reduce(eval[i]);
error[i] ^= allone;
}
scaling_inv(scaled, inv, error);
fft_tr(s_priv_cmp, scaled);
check_synd = synd_cmp(s_priv, s_priv_cmp);
/**/
benes(error, sk + IRR_BYTES, 0);
postprocess(e, error);
check_weight = weight_check(e, error);
#ifdef KAT
{
int k;
printf("decrypt e: positions");
for (k = 0;k < SYS_N;++k)
if (e[k/8] & (1 << (k&7)))
printf(" %d",k);
printf("\n");
}
#endif
return 1 - (check_synd & check_weight);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/encrypt.c */
/* 20230102 djb: rename encrypt() as pke_encrypt() */
/* 20221231 djb: move encrypt.h last for macos portability; tnx thom wiggers */
/* 20221230 djb: add linker line */
/* linker define pke_encrypt */
/*
This file is for Niederreiter encryption
*/
static inline crypto_uint16 uint16_is_smaller_declassify(uint16_t t,uint16_t u)
{
crypto_uint16 mask = crypto_uint16_smaller_mask(t,u);
crypto_declassify(&mask,sizeof mask);
return mask;
}
static inline crypto_uint32 uint32_is_equal_declassify(uint32_t t,uint32_t u)
{
crypto_uint32 mask = crypto_uint32_equal_mask(t,u);
crypto_declassify(&mask,sizeof mask);
return mask;
}
/* output: e, an error vector of weight t */
static void gen_e(unsigned char *e)
{
int i, j, eq, count;
union
{
uint16_t nums[ SYS_T*2 ];
unsigned char bytes[ SYS_T*2 * sizeof(uint16_t) ];
} buf;
uint16_t ind[ SYS_T ];
uint64_t e_int[ (SYS_N+63)/64 ];
uint64_t one = 1;
uint64_t mask;
uint64_t val[ SYS_T ];
while (1)
{
randombytes(buf.bytes, sizeof(buf));
for (i = 0; i < SYS_T*2; i++)
buf.nums[i] = load_gf(buf.bytes + i*2);
/* moving and counting indices in the correct range */
count = 0;
for (i = 0; i < SYS_T*2 && count < SYS_T; i++)
if (uint16_is_smaller_declassify(buf.nums[i],SYS_N))
ind[ count++ ] = buf.nums[i];
if (count < SYS_T) continue;
/* check for repetition */
uint16_sort(ind, SYS_T);
eq = 0;
for (i = 1; i < SYS_T; i++)
if (uint32_is_equal_declassify(ind[i-1],ind[i]))
eq = 1;
if (eq == 0)
break;
}
for (j = 0; j < SYS_T; j++)
val[j] = one << (ind[j] & 63);
for (i = 0; i < (SYS_N+63)/64; i++)
{
e_int[i] = 0;
for (j = 0; j < SYS_T; j++)
{
mask = i ^ (ind[j] >> 6);
mask -= 1;
mask >>= 63;
mask = -mask;
e_int[i] |= val[j] & mask;
}
}
for (i = 0; i < (SYS_N+63)/64 - 1; i++)
{ store8(e, e_int[i]); e += 8; }
for (j = 0; j < (SYS_N % 64); j+=8)
e[ j/8 ] = (e_int[i] >> j) & 0xFF;
}
/* input: public key pk, error vector e */
/* output: syndrome s */
static void syndrome(unsigned char *s, const unsigned char *pk, unsigned char *e)
{
uint64_t b;
const uint64_t *pk_ptr;
const uint64_t *e_ptr = ((uint64_t *) (e + SYND_BYTES));
int i, j;
/**/
for (i = 0; i < SYND_BYTES; i++)
s[i] = e[i];
for (i = 0; i < PK_NROWS; i++)
{
pk_ptr = ((uint64_t *) (pk + PK_ROW_BYTES * i));
b = 0;
for (j = 0; j < PK_NCOLS/64; j++)
b ^= pk_ptr[j] & e_ptr[j];
b ^= ((uint32_t *) &pk_ptr[j])[0] & ((uint32_t *) &e_ptr[j])[0];
b ^= b >> 32;
b ^= b >> 16;
b ^= b >> 8;
b ^= b >> 4;
b ^= b >> 2;
b ^= b >> 1;
b &= 1;
s[ i/8 ] ^= (b << (i%8));
}
}
/* input: public key pk */
/* output: error vector e, syndrome s */
static void pke_encrypt(unsigned char *s, const unsigned char *pk, unsigned char *e)
{
gen_e(e);
#ifdef KAT
{
int k;
printf("encrypt e: positions");
for (k = 0;k < SYS_N;++k)
if (e[k/8] & (1 << (k&7)))
printf(" %d",k);
printf("\n");
}
#endif
syndrome(s, pk, e);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_consts.c */
/* linker define fft_consts */
const vec fft_consts[128][GFBITS] = {
{ 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 },
};
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_powers.c */
/* linker define fft_powers */
const vec fft_powers[128][GFBITS] = {
{ 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 }
};
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_2x.c */
/* linker define fft_scalars_2x */
const vec fft_scalars_2x[5][2][GFBITS] = {
{{ 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 }}
};
/* from libmceliece-20230612/crypto_kem/6688128f/vec/shared-fft_scalars_4x.c */
/* linker define fft_scalars_4x */
const vec fft_scalars_4x[6][4][GFBITS] = {
{{ 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 }},
};
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft.c */
/*
This file is for implementing the Gao-Mateer FFT, see
http://www.math.clemson.edu/~sgao/papers/GM10.pdf
For the implementation strategy, see
https://eprint.iacr.org/2017/793.pdf
*/
/* 20221230 djb: split these arrays into separate .c files */
/* 20221230 djb: rename powers array as fft_powers */
/* 20221230 djb: rename consts array as fft_consts */
/* 20221230 djb: rename s array as fft_scalars_2x */
/* 20221230 djb: add linker lines */
/* linker define fft */
/* linker use vec_mul */
/* linker use fft_scalars_2x fft_consts fft_powers */
/* input: in, polynomial in bitsliced form */
/* output: in, result of applying the radix conversions on in */
static void radix_conversions(vec in[][GFBITS])
{
int i, j, k;
const vec mask[5][2] =
{
{0x8888888888888888, 0x4444444444444444},
{0xC0C0C0C0C0C0C0C0, 0x3030303030303030},
{0xF000F000F000F000, 0x0F000F000F000F00},
{0xFF000000FF000000, 0x00FF000000FF0000},
{0xFFFF000000000000, 0x0000FFFF00000000}
};
for (j = 0; j <= 5; j++)
{
for (i = 0; i < GFBITS; i++)
{
in[1][i] ^= in[1][i] >> 32;
in[0][i] ^= in[1][i] << 32;
}
for (i = 0; i < GFBITS; i++)
for (k = 4; k >= j; k--)
{
in[0][i] ^= (in[0][i] & mask[k][0]) >> (1 << k);
in[0][i] ^= (in[0][i] & mask[k][1]) >> (1 << k);
in[1][i] ^= (in[1][i] & mask[k][0]) >> (1 << k);
in[1][i] ^= (in[1][i] & mask[k][1]) >> (1 << k);
}
if (j < 5)
{
vec_mul(in[0], in[0], fft_scalars_2x[j][0]);
vec_mul(in[1], in[1], fft_scalars_2x[j][1]);
}
}
}
/* input: in, result of applying the radix conversions to the input polynomial */
/* output: out, evaluation results (by applying the FFT butterflies) */
static void butterflies(vec out[][ GFBITS ], vec in[][ GFBITS ])
{
int i, j, k, s, b;
vec tmp[ GFBITS ];
vec pre[8][ GFBITS ];
vec buf[128];
uint64_t consts_ptr = 2;
const unsigned char reversal[128] =
{
0, 64, 32, 96, 16, 80, 48, 112,
8, 72, 40, 104, 24, 88, 56, 120,
4, 68, 36, 100, 20, 84, 52, 116,
12, 76, 44, 108, 28, 92, 60, 124,
2, 66, 34, 98, 18, 82, 50, 114,
10, 74, 42, 106, 26, 90, 58, 122,
6, 70, 38, 102, 22, 86, 54, 118,
14, 78, 46, 110, 30, 94, 62, 126,
1, 65, 33, 97, 17, 81, 49, 113,
9, 73, 41, 105, 25, 89, 57, 121,
5, 69, 37, 101, 21, 85, 53, 117,
13, 77, 45, 109, 29, 93, 61, 125,
3, 67, 35, 99, 19, 83, 51, 115,
11, 75, 43, 107, 27, 91, 59, 123,
7, 71, 39, 103, 23, 87, 55, 119,
15, 79, 47, 111, 31, 95, 63, 127
};
const uint16_t beta[7] = {2522, 7827, 7801, 8035, 6897, 8167, 3476};
/**/
for (i = 0; i < 7; i++)
{
for (j = 0; j < GFBITS; j++)
{
pre[i][j] = (beta[i] >> j) & 1;
pre[i][j] = -pre[i][j];
}
vec_mul(pre[i], in[1], pre[i]);
}
for (i = 0; i < GFBITS; i++)
{
buf[0] = in[0][i];
buf[1] = buf[0] ^ pre[0][i]; buf[32] = in[0][i] ^ pre[5][i];
buf[3] = buf[1] ^ pre[1][i]; buf[96] = buf[32] ^ pre[6][i];
buf[97] = buf[96] ^ pre[0][i];
buf[2] = in[0][i] ^ pre[1][i]; buf[99] = buf[97] ^ pre[1][i];
buf[6] = buf[2] ^ pre[2][i]; buf[98] = buf[99] ^ pre[0][i];
buf[7] = buf[6] ^ pre[0][i]; buf[102] = buf[98] ^ pre[2][i];
buf[5] = buf[7] ^ pre[1][i]; buf[103] = buf[102] ^ pre[0][i];
buf[101] = buf[103] ^ pre[1][i];
buf[4] = in[0][i] ^ pre[2][i]; buf[100] = buf[101] ^ pre[0][i];
buf[12] = buf[4] ^ pre[3][i]; buf[108] = buf[100] ^ pre[3][i];
buf[13] = buf[12] ^ pre[0][i]; buf[109] = buf[108] ^ pre[0][i];
buf[15] = buf[13] ^ pre[1][i]; buf[111] = buf[109] ^ pre[1][i];
buf[14] = buf[15] ^ pre[0][i]; buf[110] = buf[111] ^ pre[0][i];
buf[10] = buf[14] ^ pre[2][i]; buf[106] = buf[110] ^ pre[2][i];
buf[11] = buf[10] ^ pre[0][i]; buf[107] = buf[106] ^ pre[0][i];
buf[9] = buf[11] ^ pre[1][i]; buf[105] = buf[107] ^ pre[1][i];
buf[104] = buf[105] ^ pre[0][i];
buf[8] = in[0][i] ^ pre[3][i]; buf[120] = buf[104] ^ pre[4][i];
buf[24] = buf[8] ^ pre[4][i]; buf[121] = buf[120] ^ pre[0][i];
buf[25] = buf[24] ^ pre[0][i]; buf[123] = buf[121] ^ pre[1][i];
buf[27] = buf[25] ^ pre[1][i]; buf[122] = buf[123] ^ pre[0][i];
buf[26] = buf[27] ^ pre[0][i]; buf[126] = buf[122] ^ pre[2][i];
buf[30] = buf[26] ^ pre[2][i]; buf[127] = buf[126] ^ pre[0][i];
buf[31] = buf[30] ^ pre[0][i]; buf[125] = buf[127] ^ pre[1][i];
buf[29] = buf[31] ^ pre[1][i]; buf[124] = buf[125] ^ pre[0][i];
buf[28] = buf[29] ^ pre[0][i]; buf[116] = buf[124] ^ pre[3][i];
buf[20] = buf[28] ^ pre[3][i]; buf[117] = buf[116] ^ pre[0][i];
buf[21] = buf[20] ^ pre[0][i]; buf[119] = buf[117] ^ pre[1][i];
buf[23] = buf[21] ^ pre[1][i]; buf[118] = buf[119] ^ pre[0][i];
buf[22] = buf[23] ^ pre[0][i]; buf[114] = buf[118] ^ pre[2][i];
buf[18] = buf[22] ^ pre[2][i]; buf[115] = buf[114] ^ pre[0][i];
buf[19] = buf[18] ^ pre[0][i]; buf[113] = buf[115] ^ pre[1][i];
buf[17] = buf[19] ^ pre[1][i]; buf[112] = buf[113] ^ pre[0][i];
buf[80] = buf[112] ^ pre[5][i];
buf[16] = in[0][i] ^ pre[4][i]; buf[81] = buf[80] ^ pre[0][i];
buf[48] = buf[16] ^ pre[5][i]; buf[83] = buf[81] ^ pre[1][i];
buf[49] = buf[48] ^ pre[0][i]; buf[82] = buf[83] ^ pre[0][i];
buf[51] = buf[49] ^ pre[1][i]; buf[86] = buf[82] ^ pre[2][i];
buf[50] = buf[51] ^ pre[0][i]; buf[87] = buf[86] ^ pre[0][i];
buf[54] = buf[50] ^ pre[2][i]; buf[85] = buf[87] ^ pre[1][i];
buf[55] = buf[54] ^ pre[0][i]; buf[84] = buf[85] ^ pre[0][i];
buf[53] = buf[55] ^ pre[1][i]; buf[92] = buf[84] ^ pre[3][i];
buf[52] = buf[53] ^ pre[0][i]; buf[93] = buf[92] ^ pre[0][i];
buf[60] = buf[52] ^ pre[3][i]; buf[95] = buf[93] ^ pre[1][i];
buf[61] = buf[60] ^ pre[0][i]; buf[94] = buf[95] ^ pre[0][i];
buf[63] = buf[61] ^ pre[1][i]; buf[90] = buf[94] ^ pre[2][i];
buf[62] = buf[63] ^ pre[0][i]; buf[91] = buf[90] ^ pre[0][i];
buf[58] = buf[62] ^ pre[2][i]; buf[89] = buf[91] ^ pre[1][i];
buf[59] = buf[58] ^ pre[0][i]; buf[88] = buf[89] ^ pre[0][i];
buf[57] = buf[59] ^ pre[1][i]; buf[72] = buf[88] ^ pre[4][i];
buf[56] = buf[57] ^ pre[0][i]; buf[73] = buf[72] ^ pre[0][i];
buf[40] = buf[56] ^ pre[4][i]; buf[75] = buf[73] ^ pre[1][i];
buf[41] = buf[40] ^ pre[0][i]; buf[74] = buf[75] ^ pre[0][i];
buf[43] = buf[41] ^ pre[1][i]; buf[78] = buf[74] ^ pre[2][i];
buf[42] = buf[43] ^ pre[0][i]; buf[79] = buf[78] ^ pre[0][i];
buf[46] = buf[42] ^ pre[2][i]; buf[77] = buf[79] ^ pre[1][i];
buf[47] = buf[46] ^ pre[0][i]; buf[76] = buf[77] ^ pre[0][i];
buf[45] = buf[47] ^ pre[1][i]; buf[68] = buf[76] ^ pre[3][i];
buf[44] = buf[45] ^ pre[0][i]; buf[69] = buf[68] ^ pre[0][i];
buf[36] = buf[44] ^ pre[3][i]; buf[71] = buf[69] ^ pre[1][i];
buf[37] = buf[36] ^ pre[0][i]; buf[70] = buf[71] ^ pre[0][i];
buf[39] = buf[37] ^ pre[1][i]; buf[66] = buf[70] ^ pre[2][i];
buf[38] = buf[39] ^ pre[0][i]; buf[67] = buf[66] ^ pre[0][i];
buf[34] = buf[38] ^ pre[2][i]; buf[65] = buf[67] ^ pre[1][i];
buf[35] = buf[34] ^ pre[0][i];
buf[33] = buf[35] ^ pre[1][i]; buf[64] = in[0][i] ^ pre[6][i];
transpose_64x64(buf + 0, buf + 0);
transpose_64x64(buf + 64, buf + 64);
for (j = 0; j < 128; j++)
out[ reversal[j] ][i] = buf[j];
}
for (i = 1; i <= 6; i++)
{
s = 1 << i;
for (j = 0; j < 128; j += 2*s)
for (k = j; k < j+s; k++)
{
vec_mul(tmp, out[k+s], fft_consts[ consts_ptr + (k-j) ]);
for (b = 0; b < GFBITS; b++) out[k ][b] ^= tmp[b];
for (b = 0; b < GFBITS; b++) out[k+s][b] ^= out[k][b];
}
consts_ptr += (1 << i);
}
/* adding the part contributed by x^128 */
for (i = 0; i < 128; i++)
for (b = 0; b < GFBITS; b++)
out[i][b] ^= fft_powers[i][b];
}
/* input: in, polynomial in bitsliced form */
/* output: out, bitsliced results of evaluating in all the field elements */
static void fft(vec out[][GFBITS], vec in[][GFBITS])
{
radix_conversions(in);
butterflies(out, in);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/fft_tr.c */
/*
This file is for transpose of the Gao-Mateer FFT
Functions with names ending with _tr are (roughly) the transpose of the corresponding functions in fft.c
For the implementation strategy, see
https://eprint.iacr.org/2017/793.pdf
*/
/* 20221230 djb: split these arrays into separate .c files */
/* 20221230 djb: rename consts array as fft_consts */
/* 20221230 djb: rename s array as fft_scalars_4x */
/* 20221230 djb: add linker lines */
/* linker define fft_tr */
/* linker use vec_mul */
/* linker use fft_scalars_4x fft_consts */
static void radix_conversions_tr(vec in[][ GFBITS ])
{
int i, j, k;
const vec mask[6][2] =
{
{0x2222222222222222, 0x4444444444444444},
{0x0C0C0C0C0C0C0C0C, 0x3030303030303030},
{0x00F000F000F000F0, 0x0F000F000F000F00},
{0x0000FF000000FF00, 0x00FF000000FF0000},
{0x00000000FFFF0000, 0x0000FFFF00000000},
{0xFFFFFFFF00000000, 0x00000000FFFFFFFF}
};
/**/
for (j = 6; j >= 0; j--)
{
if (j < 6)
{
vec_mul(in[0], in[0], fft_scalars_4x[j][0]); /* scaling */
vec_mul(in[1], in[1], fft_scalars_4x[j][1]); /* scaling */
vec_mul(in[2], in[2], fft_scalars_4x[j][2]); /* scaling */
vec_mul(in[3], in[3], fft_scalars_4x[j][3]); /* scaling */
}
for (k = j; k <= 4; k++)
for (i = 0; i < GFBITS; i++)
{
in[0][i] ^= (in[0][i] & mask[k][0]) << (1 << k);
in[0][i] ^= (in[0][i] & mask[k][1]) << (1 << k);
in[1][i] ^= (in[1][i] & mask[k][0]) << (1 << k);
in[1][i] ^= (in[1][i] & mask[k][1]) << (1 << k);
in[2][i] ^= (in[2][i] & mask[k][0]) << (1 << k);
in[2][i] ^= (in[2][i] & mask[k][1]) << (1 << k);
in[3][i] ^= (in[3][i] & mask[k][0]) << (1 << k);
in[3][i] ^= (in[3][i] & mask[k][1]) << (1 << k);
}
if (j <= 5)
for (i = 0; i < GFBITS; i++)
{
in[1][i] ^= in[0][i] >> 32;
in[1][i] ^= in[1][i] << 32;
in[3][i] ^= in[2][i] >> 32;
in[3][i] ^= in[3][i] << 32;
}
for (i = 0; i < GFBITS; i++)
in[3][i] ^= in[2][i] ^= in[1][i];
}
}
static void butterflies_tr(vec out[][ GFBITS ], vec in[][ GFBITS ])
{
int i, j, k, s, b;
vec tmp[ GFBITS ];
vec pre[6][2][ GFBITS ];
vec buf[2][64];
uint64_t consts_ptr = 128;
const unsigned char reversal[128] =
{
0, 64, 32, 96, 16, 80, 48, 112,
8, 72, 40, 104, 24, 88, 56, 120,
4, 68, 36, 100, 20, 84, 52, 116,
12, 76, 44, 108, 28, 92, 60, 124,
2, 66, 34, 98, 18, 82, 50, 114,
10, 74, 42, 106, 26, 90, 58, 122,
6, 70, 38, 102, 22, 86, 54, 118,
14, 78, 46, 110, 30, 94, 62, 126,
1, 65, 33, 97, 17, 81, 49, 113,
9, 73, 41, 105, 25, 89, 57, 121,
5, 69, 37, 101, 21, 85, 53, 117,
13, 77, 45, 109, 29, 93, 61, 125,
3, 67, 35, 99, 19, 83, 51, 115,
11, 75, 43, 107, 27, 91, 59, 123,
7, 71, 39, 103, 23, 87, 55, 119,
15, 79, 47, 111, 31, 95, 63, 127
};
const uint16_t beta[6] = {5246, 5306, 6039, 6685, 4905, 6755};
/**/
for (i = 6; i >= 0; i--)
{
s = 1 << i;
consts_ptr -= s;
for (j = 0; j < 128; j += 2*s)
for (k = j; k < j+s; k++)
{
for (b = 0; b < GFBITS; b++) in[k][b] ^= in[k+s][b];
vec_mul(tmp, in[k], fft_consts[ consts_ptr + (k-j) ]);
for (b = 0; b < GFBITS; b++) in[k+s][b] ^= tmp[b];
}
}
for (i = 0; i < GFBITS; i++)
{
for (k = 0; k < 128; k++)
(&buf[0][0])[ k ] = in[ reversal[k] ][i];
transpose_64x64(buf[0], buf[0]);
transpose_64x64(buf[1], buf[1]);
for (k = 0; k < 2; k++)
{
pre[0][k][i] = buf[k][32]; buf[k][33] ^= buf[k][32];
pre[1][k][i] = buf[k][33]; buf[k][35] ^= buf[k][33];
pre[0][k][i] ^= buf[k][35]; buf[k][34] ^= buf[k][35];
pre[2][k][i] = buf[k][34]; buf[k][38] ^= buf[k][34];
pre[0][k][i] ^= buf[k][38]; buf[k][39] ^= buf[k][38];
pre[1][k][i] ^= buf[k][39]; buf[k][37] ^= buf[k][39];
pre[0][k][i] ^= buf[k][37]; buf[k][36] ^= buf[k][37];
pre[3][k][i] = buf[k][36]; buf[k][44] ^= buf[k][36];
pre[0][k][i] ^= buf[k][44]; buf[k][45] ^= buf[k][44];
pre[1][k][i] ^= buf[k][45]; buf[k][47] ^= buf[k][45];
pre[0][k][i] ^= buf[k][47]; buf[k][46] ^= buf[k][47];
pre[2][k][i] ^= buf[k][46]; buf[k][42] ^= buf[k][46];
pre[0][k][i] ^= buf[k][42]; buf[k][43] ^= buf[k][42];
pre[1][k][i] ^= buf[k][43]; buf[k][41] ^= buf[k][43];
pre[0][k][i] ^= buf[k][41]; buf[k][40] ^= buf[k][41];
pre[4][k][i] = buf[k][40]; buf[k][56] ^= buf[k][40];
pre[0][k][i] ^= buf[k][56]; buf[k][57] ^= buf[k][56];
pre[1][k][i] ^= buf[k][57]; buf[k][59] ^= buf[k][57];
pre[0][k][i] ^= buf[k][59]; buf[k][58] ^= buf[k][59];
pre[2][k][i] ^= buf[k][58]; buf[k][62] ^= buf[k][58];
pre[0][k][i] ^= buf[k][62]; buf[k][63] ^= buf[k][62];
pre[1][k][i] ^= buf[k][63]; buf[k][61] ^= buf[k][63];
pre[0][k][i] ^= buf[k][61]; buf[k][60] ^= buf[k][61];
pre[3][k][i] ^= buf[k][60]; buf[k][52] ^= buf[k][60];
pre[0][k][i] ^= buf[k][52]; buf[k][53] ^= buf[k][52];
pre[1][k][i] ^= buf[k][53]; buf[k][55] ^= buf[k][53];
pre[0][k][i] ^= buf[k][55]; buf[k][54] ^= buf[k][55];
pre[2][k][i] ^= buf[k][54]; buf[k][50] ^= buf[k][54];
pre[0][k][i] ^= buf[k][50]; buf[k][51] ^= buf[k][50];
pre[1][k][i] ^= buf[k][51]; buf[k][49] ^= buf[k][51];
pre[0][k][i] ^= buf[k][49]; buf[k][48] ^= buf[k][49];
pre[5][k][i] = buf[k][48]; buf[k][16] ^= buf[k][48];
pre[0][k][i] ^= buf[k][16]; buf[k][17] ^= buf[k][16];
pre[1][k][i] ^= buf[k][17]; buf[k][19] ^= buf[k][17];
pre[0][k][i] ^= buf[k][19]; buf[k][18] ^= buf[k][19];
pre[2][k][i] ^= buf[k][18]; buf[k][22] ^= buf[k][18];
pre[0][k][i] ^= buf[k][22]; buf[k][23] ^= buf[k][22];
pre[1][k][i] ^= buf[k][23]; buf[k][21] ^= buf[k][23];
pre[0][k][i] ^= buf[k][21]; buf[k][20] ^= buf[k][21];
pre[3][k][i] ^= buf[k][20]; buf[k][28] ^= buf[k][20];
pre[0][k][i] ^= buf[k][28]; buf[k][29] ^= buf[k][28];
pre[1][k][i] ^= buf[k][29]; buf[k][31] ^= buf[k][29];
pre[0][k][i] ^= buf[k][31]; buf[k][30] ^= buf[k][31];
pre[2][k][i] ^= buf[k][30]; buf[k][26] ^= buf[k][30];
pre[0][k][i] ^= buf[k][26]; buf[k][27] ^= buf[k][26];
pre[1][k][i] ^= buf[k][27]; buf[k][25] ^= buf[k][27];
pre[0][k][i] ^= buf[k][25]; buf[k][24] ^= buf[k][25];
pre[4][k][i] ^= buf[k][24]; buf[k][8] ^= buf[k][24];
pre[0][k][i] ^= buf[k][8]; buf[k][9] ^= buf[k][8];
pre[1][k][i] ^= buf[k][9]; buf[k][11] ^= buf[k][9];
pre[0][k][i] ^= buf[k][11]; buf[k][10] ^= buf[k][11];
pre[2][k][i] ^= buf[k][10]; buf[k][14] ^= buf[k][10];
pre[0][k][i] ^= buf[k][14]; buf[k][15] ^= buf[k][14];
pre[1][k][i] ^= buf[k][15]; buf[k][13] ^= buf[k][15];
pre[0][k][i] ^= buf[k][13]; buf[k][12] ^= buf[k][13];
pre[3][k][i] ^= buf[k][12]; buf[k][4] ^= buf[k][12];
pre[0][k][i] ^= buf[k][4]; buf[k][5] ^= buf[k][4];
pre[1][k][i] ^= buf[k][5]; buf[k][7] ^= buf[k][5];
pre[0][k][i] ^= buf[k][7]; buf[k][6] ^= buf[k][7];
pre[2][k][i] ^= buf[k][6]; buf[k][2] ^= buf[k][6];
pre[0][k][i] ^= buf[k][2]; buf[k][3] ^= buf[k][2];
pre[1][k][i] ^= buf[k][3]; buf[k][1] ^= buf[k][3];
pre[0][k][i] ^= buf[k][1]; out[k][i] = buf[k][0] ^ buf[k][1];
}
}
for (j = 0; j < GFBITS; j++) tmp[j] = vec_setbits((beta[0] >> j) & 1);
vec_mul(out[2], pre[0][0], tmp);
vec_mul(out[3], pre[0][1], tmp);
for (i = 1; i < 6; i++)
{
for (j = 0; j < GFBITS; j++) tmp[j] = vec_setbits((beta[i] >> j) & 1);
vec_mul(pre[i][0], pre[i][0], tmp);
vec_mul(pre[i][1], pre[i][1], tmp);
for (b = 0; b < GFBITS; b++)
{
out[2][b] ^= pre[i][0][b];
out[3][b] ^= pre[i][1][b];
}
}
}
static void fft_tr(vec out[][GFBITS], vec in[][ GFBITS ])
{
butterflies_tr(out, in);
radix_conversions_tr(out);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/gf.c */
/*
this file is for functions for field arithmetic
*/
/* 20221231 djb: const for GF_mul */
/* 20221230 djb: add linker line */
/* linker define gf_iszero gf_mul gf_inv gf_frac GF_mul */
/* field multiplication */
gf gf_mul(gf in0, gf in1)
{
int i;
uint64_t tmp;
uint64_t t0;
uint64_t t1;
uint64_t t;
t0 = in0;
t1 = in1;
tmp = t0 * (t1 & 1);
for (i = 1; i < GFBITS; i++)
tmp ^= (t0 * (t1 & (1 << i)));
/**/
t = tmp & 0x1FF0000;
tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
t = tmp & 0x000E000;
tmp ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
return tmp & GFMASK;
}
/* 2 field squarings */
static inline gf gf_sq2(gf in)
{
int i;
const uint64_t B[] = {0x1111111111111111,
0x0303030303030303,
0x000F000F000F000F,
0x000000FF000000FF};
const uint64_t M[] = {0x0001FF0000000000,
0x000000FF80000000,
0x000000007FC00000,
0x00000000003FE000};
uint64_t x = in;
uint64_t t;
x = (x | (x << 24)) & B[3];
x = (x | (x << 12)) & B[2];
x = (x | (x << 6)) & B[1];
x = (x | (x << 3)) & B[0];
for (i = 0; i < 4; i++)
{
t = x & M[i];
x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
}
return x & GFMASK;
}
/* square and multiply */
static inline gf gf_sqmul(gf in, gf m)
{
int i;
uint64_t x;
uint64_t t0;
uint64_t t1;
uint64_t t;
const uint64_t M[] = {0x0000001FF0000000,
0x000000000FF80000,
0x000000000007E000};
t0 = in;
t1 = m;
x = (t1 << 6) * (t0 & (1 << 6));
t0 ^= (t0 << 7);
x ^= (t1 * (t0 & (0x04001)));
x ^= (t1 * (t0 & (0x08002))) << 1;
x ^= (t1 * (t0 & (0x10004))) << 2;
x ^= (t1 * (t0 & (0x20008))) << 3;
x ^= (t1 * (t0 & (0x40010))) << 4;
x ^= (t1 * (t0 & (0x80020))) << 5;
for (i = 0; i < 3; i++)
{
t = x & M[i];
x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
}
return x & GFMASK;
}
/* square twice and multiply */
static inline gf gf_sq2mul(gf in, gf m)
{
int i;
uint64_t x;
uint64_t t0;
uint64_t t1;
uint64_t t;
const uint64_t M[] = {0x1FF0000000000000,
0x000FF80000000000,
0x000007FC00000000,
0x00000003FE000000,
0x0000000001FE0000,
0x000000000001E000};
t0 = in;
t1 = m;
x = (t1 << 18) * (t0 & (1 << 6));
t0 ^= (t0 << 21);
x ^= (t1 * (t0 & (0x010000001)));
x ^= (t1 * (t0 & (0x020000002))) << 3;
x ^= (t1 * (t0 & (0x040000004))) << 6;
x ^= (t1 * (t0 & (0x080000008))) << 9;
x ^= (t1 * (t0 & (0x100000010))) << 12;
x ^= (t1 * (t0 & (0x200000020))) << 15;
for (i = 0; i < 6; i++)
{
t = x & M[i];
x ^= (t >> 9) ^ (t >> 10) ^ (t >> 12) ^ (t >> 13);
}
return x & GFMASK;
}
/* return num/den */
gf gf_frac(gf den, gf num)
{
gf tmp_11;
gf tmp_1111;
gf out;
tmp_11 = gf_sqmul(den, den); /* 11 */
tmp_1111 = gf_sq2mul(tmp_11, tmp_11); /* 1111 */
out = gf_sq2(tmp_1111);
out = gf_sq2mul(out, tmp_1111); /* 11111111 */
out = gf_sq2(out);
out = gf_sq2mul(out, tmp_1111); /* 111111111111 */
return gf_sqmul(out, num); /* 1111111111110 */
}
/* return 1/den */
gf gf_inv(gf den)
{
return gf_frac(den, ((gf) 1));
}
/* check if a == 0 */
gf gf_iszero(gf a)
{
uint32_t t = a;
t -= 1;
t >>= 19;
return (gf) t;
}
/* multiplication in GF((2^m)^t) */
static void GF_mul(gf *out, const gf *in0, const gf *in1)
{
int i, j;
gf prod[255];
for (i = 0; i < 255; i++)
prod[i] = 0;
for (i = 0; i < 128; i++)
for (j = 0; j < 128; j++)
prod[i+j] ^= gf_mul(in0[i], in1[j]);
/**/
for (i = 254; i >= 128; i--)
{
prod[i - 121] ^= prod[i];
prod[i - 126] ^= prod[i];
prod[i - 127] ^= prod[i];
prod[i - 128] ^= prod[i];
}
for (i = 0; i < 128; i++)
out[i] = prod[i];
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_dec.c */
/* 20221230 djb: add linker lines */
/* 20221230 djb: split out of operations.c */
/* linker define operation_dec */
/* linker use decrypt */
static void operation_dec(
unsigned char *key,
const unsigned char *c,
const unsigned char *sk
)
{
int i;
unsigned char ret_decrypt = 0;
uint16_t m;
unsigned char e[ SYS_N/8 ];
unsigned char preimage[ 1 + SYS_N/8 + SYND_BYTES ];
unsigned char *x = preimage;
const unsigned char *s = sk + 40 + IRR_BYTES + COND_BYTES;
/**/
ret_decrypt = decrypt(e, sk + 40, c);
m = ret_decrypt;
m -= 1;
m >>= 8;
*x++ = m & 1;
for (i = 0; i < SYS_N/8; i++)
*x++ = (~m & s[i]) | (m & e[i]);
for (i = 0; i < SYND_BYTES; i++)
*x++ = c[i];
crypto_hash_32b(key, preimage, sizeof(preimage));
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_enc.c */
/* 20230102 djb: rename encrypt() as pke_encrypt() */
/* 20221230 djb: add linker lines */
/* 20221230 djb: split out of operations.c */
/* linker define operation_enc */
/* linker use pke_encrypt */
static void operation_enc(
unsigned char *c,
unsigned char *key,
const unsigned char *pk
)
{
unsigned char e[ SYS_N/8 ];
unsigned char one_ec[ 1 + SYS_N/8 + SYND_BYTES ] = {1};
/**/
pke_encrypt(c, pk, e);
memcpy(one_ec + 1, e, SYS_N/8);
memcpy(one_ec + 1 + SYS_N/8, c, SYND_BYTES);
crypto_hash_32b(key, one_ec, sizeof(one_ec));
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/kem_keypair.c */
/* 20221230 djb: add linker lines */
/* 20221230 djb: split out of operations.c */
/* linker define operation_keypair */
/* linker use controlbitsfrompermutation genpoly_gen pk_gen */
static void operation_keypair
(
unsigned char *pk,
unsigned char *sk
)
{
int i;
unsigned char seed[ 33 ] = {64};
unsigned char r[ SYS_N/8 + (1 << GFBITS)*sizeof(uint32_t) + SYS_T*2 + 32 ];
unsigned char *rp, *skp;
uint64_t pivots = 0;
gf f[ SYS_T ]; /* element in GF(2^mt) */
gf irr[ SYS_T ]; /* Goppa polynomial */
uint32_t perm[ 1 << GFBITS ]; /* random permutation as 32-bit integers */
int16_t pi[ 1 << GFBITS ]; /* random permutation */
randombytes(seed+1, 32);
while (1)
{
rp = &r[ sizeof(r)-32 ];
skp = sk;
/* expanding and updating the seed */
shake(r, sizeof(r), seed, 33);
memcpy(skp, seed+1, 32);
skp += 32 + 8;
memcpy(seed+1, &r[ sizeof(r)-32 ], 32);
/* generating irreducible polynomial */
rp -= sizeof(f);
for (i = 0; i < SYS_T; i++)
f[i] = load_gf(rp + i*2);
if (genpoly_gen(irr, f))
continue;
for (i = 0; i < SYS_T; i++)
store_gf(skp + i*2, irr[i]);
skp += IRR_BYTES;
/* generating permutation */
rp -= sizeof(perm);
for (i = 0; i < (1 << GFBITS); i++)
perm[i] = load4(rp + i*4);
if (pk_gen(pk, skp - IRR_BYTES, perm, pi, &pivots))
continue;
controlbitsfrompermutation(skp, pi, GFBITS, 1 << GFBITS);
skp += COND_BYTES;
/* storing the random string s */
rp -= SYS_N/8;
memcpy(skp, rp, SYS_N/8);
/* storing positions of the 32 pivots */
store8(sk + 32, pivots);
break;
}
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/pk_gen.c */
/*
This file is for public-key generation
*/
/* 20221231 djb: remove unused min definition */
/* 20221231 djb: more 0 initialization to clarify data flow; tnx thom wiggers */
/* 20221230 djb: add linker lines */
/* linker define pk_gen */
/* linker use fft vec_inv vec_mul */
static crypto_uint64 uint64_is_equal_declassify(uint64_t t,uint64_t u)
{
crypto_uint64 mask = crypto_uint64_equal_mask(t,u);
crypto_declassify(&mask,sizeof mask);
return mask;
}
static crypto_uint64 uint64_is_zero_declassify(uint64_t t)
{
crypto_uint64 mask = crypto_uint64_zero_mask(t);
crypto_declassify(&mask,sizeof mask);
return mask;
}
static void de_bitslicing(uint64_t * out, const vec in[][GFBITS])
{
int i, j, r;
for (i = 0; i < (1 << GFBITS); i++)
out[i] = 0 ;
for (i = 0; i < 128; i++)
for (j = GFBITS-1; j >= 0; j--)
for (r = 0; r < 64; r++)
{
out[i*64 + r] <<= 1;
out[i*64 + r] |= (in[i][j] >> r) & 1;
}
}
static void to_bitslicing_2x(vec out0[][GFBITS], vec out1[][GFBITS], const uint64_t * in)
{
int i, j, r;
for (i = 0; i < 128; i++)
{
for (j = 0;j < GFBITS;++j) out0[i][j] = out1[i][j] = 0;
for (j = GFBITS-1; j >= 0; j--)
for (r = 63; r >= 0; r--)
{
out1[i][j] <<= 1;
out1[i][j] |= (in[i*64 + r] >> (j + GFBITS)) & 1;
}
for (j = GFBITS-1; j >= 0; j--)
for (r = 63; r >= 0; r--)
{
out0[i][GFBITS-1-j] <<= 1;
out0[i][GFBITS-1-j] |= (in[i*64 + r] >> j) & 1;
}
}
}
/* return number of trailing zeros of in */
static inline int ctz(uint64_t in)
{
int i, b, m = 0, r = 0;
for (i = 0; i < 64; i++)
{
b = (in >> i) & 1;
m |= b;
r += (m^1) & (b^1);
}
return r;
}
static inline uint64_t same_mask(uint16_t x, uint16_t y)
{
uint64_t mask;
mask = x ^ y;
mask -= 1;
mask >>= 63;
mask = -mask;
return mask;
}
static int mov_columns(uint64_t mat[][ (SYS_N + 63) / 64 ], int16_t * pi, uint64_t * pivots)
{
int i, j, k, s, block_idx, row;
uint64_t buf[64], ctz_list[32], t, d, mask, one = 1;
row = PK_NROWS - 32;
block_idx = row/64;
/* extract the 32x64 matrix */
for (i = 0; i < 32; i++)
buf[i] = (mat[ row + i ][ block_idx + 0 ] >> 32) |
(mat[ row + i ][ block_idx + 1 ] << 32);
/* compute the column indices of pivots by Gaussian elimination. */
/* the indices are stored in ctz_list */
*pivots = 0;
for (i = 0; i < 32; i++)
{
t = buf[i];
for (j = i+1; j < 32; j++)
t |= buf[j];
if (uint64_is_zero_declassify(t)) return -1; /* return if buf is not full rank */
ctz_list[i] = s = ctz(t);
*pivots |= one << ctz_list[i];
for (j = i+1; j < 32; j++) { mask = (buf[i] >> s) & 1; mask -= 1; buf[i] ^= buf[j] & mask; }
for (j = i+1; j < 32; j++) { mask = (buf[j] >> s) & 1; mask = -mask; buf[j] ^= buf[i] & mask; }
}
/* updating permutation */
for (j = 0; j < 32; j++)
for (k = j+1; k < 64; k++)
{
d = pi[ row + j ] ^ pi[ row + k ];
d &= same_mask(k, ctz_list[j]);
pi[ row + j ] ^= d;
pi[ row + k ] ^= d;
}
/* moving columns of mat according to the column indices of pivots */
for (i = 0; i < PK_NROWS; i++)
{
t = (mat[ i ][ block_idx + 0 ] >> 32) |
(mat[ i ][ block_idx + 1 ] << 32);
for (j = 0; j < 32; j++)
{
d = t >> j;
d ^= t >> ctz_list[j];
d &= 1;
t ^= d << ctz_list[j];
t ^= d << j;
}
mat[ i ][ block_idx + 0 ] = (mat[ i ][ block_idx + 0 ] << 32 >> 32) | (t << 32);
mat[ i ][ block_idx + 1 ] = (mat[ i ][ block_idx + 1 ] >> 32 << 32) | (t >> 32);
}
return 0;
}
static int pk_gen(unsigned char * pk, const unsigned char * irr, uint32_t * perm, int16_t * pi, uint64_t * pivots)
{
const int nblocks_H = (SYS_N + 63) / 64;
const int nblocks_I = (PK_NROWS + 63) / 64;
int i, j, k;
int row, c;
uint64_t mat[ PK_NROWS ][ nblocks_H ];
uint64_t mask;
vec irr_int[2][ GFBITS ];
vec consts[ 128 ][ GFBITS ];
vec eval[ 128 ][ GFBITS ];
vec prod[ 128 ][ GFBITS ];
vec tmp[ GFBITS ];
uint64_t list[1 << GFBITS];
/* compute the inverses */
irr_load(irr_int, irr);
fft(eval, irr_int);
vec_copy(prod[0], eval[0]);
for (i = 1; i < 128; i++)
vec_mul(prod[i], prod[i-1], eval[i]);
vec_inv(tmp, prod[127]);
for (i = 126; i >= 0; i--)
{
vec_mul(prod[i+1], prod[i], tmp);
vec_mul(tmp, tmp, eval[i+1]);
}
vec_copy(prod[0], tmp);
/* fill matrix */
de_bitslicing(list, prod);
for (i = 0; i < (1 << GFBITS); i++)
{
list[i] <<= GFBITS;
list[i] |= i;
list[i] |= ((uint64_t) perm[i]) << 31;
}
uint64_sort(list, 1 << GFBITS);
for (i = 1; i < (1 << GFBITS); i++)
if (uint64_is_equal_declassify(list[i-1] >> 31,list[i] >> 31))
return -1;
to_bitslicing_2x(consts, prod, list);
for (i = 0; i < (1 << GFBITS); i++)
pi[i] = list[i] & GFMASK;
for (j = 0; j < nblocks_H; j++)
for (k = 0; k < GFBITS; k++)
mat[ k ][ j ] = prod[ j ][ k ];
for (i = 1; i < SYS_T; i++)
for (j = 0; j < nblocks_H; j++)
{
vec_mul(prod[j], prod[j], consts[j]);
for (k = 0; k < GFBITS; k++)
mat[ i*GFBITS + k ][ j ] = prod[ j ][ k ];
}
/* gaussian elimination */
for (row = 0; row < PK_NROWS; row++)
{
i = row >> 6;
j = row & 63;
if (row == PK_NROWS - 32)
{
if (mov_columns(mat, pi, pivots))
return -1;
}
for (k = row + 1; k < PK_NROWS; k++)
{
mask = mat[ row ][ i ] >> j;
mask &= 1;
mask -= 1;
for (c = 0; c < nblocks_H; c++)
mat[ row ][ c ] ^= mat[ k ][ c ] & mask;
}
if ( uint64_is_zero_declassify((mat[ row ][ i ] >> j) & 1) ) /* return if not systematic */
{
return -1;
}
for (k = 0; k < row; k++)
{
mask = mat[ k ][ i ] >> j;
mask &= 1;
mask = -mask;
for (c = 0; c < nblocks_H; c++)
mat[ k ][ c ] ^= mat[ row ][ c ] & mask;
}
for (k = row+1; k < PK_NROWS; k++)
{
mask = mat[ k ][ i ] >> j;
mask &= 1;
mask = -mask;
for (c = 0; c < nblocks_H; c++)
mat[ k ][ c ] ^= mat[ row ][ c ] & mask;
}
}
for (i = 0; i < PK_NROWS; i++)
{
for (j = nblocks_I; j < nblocks_H-1; j++)
{
store8(pk, mat[i][j]);
pk += 8;
}
store_i(pk, mat[i][j], PK_ROW_BYTES % 8);
pk += PK_ROW_BYTES % 8;
}
/**/
return 0;
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/sk_gen.c */
/*
This file is for secret-key generation
*/
/* 20221230 djb: add linker lines */
/* linker define genpoly_gen */
/* linker use gf_iszero gf_mul gf_inv GF_mul */
static inline crypto_uint16 gf_is_zero_declassify(gf t)
{
crypto_uint16 mask = crypto_uint16_zero_mask(t);
crypto_declassify(&mask,sizeof mask);
return mask;
}
/* input: f, element in GF((2^m)^t) */
/* output: out, minimal polynomial of f */
/* return: 0 for success and -1 for failure */
static int genpoly_gen(gf *out, gf *f)
{
int i, j, k, c;
gf mat[ SYS_T+1 ][ SYS_T ];
gf mask, inv, t;
/* fill matrix */
mat[0][0] = 1;
for (i = 1; i < SYS_T; i++)
mat[0][i] = 0;
for (i = 0; i < SYS_T; i++)
mat[1][i] = f[i];
for (j = 2; j <= SYS_T; j++)
GF_mul(mat[j], mat[j-1], f);
/* gaussian */
for (j = 0; j < SYS_T; j++)
{
for (k = j + 1; k < SYS_T; k++)
{
mask = gf_iszero(mat[ j ][ j ]);
for (c = j; c < SYS_T + 1; c++)
mat[ c ][ j ] ^= mat[ c ][ k ] & mask;
}
if ( gf_is_zero_declassify(mat[ j ][ j ]) ) /* return if not systematic */
{
return -1;
}
inv = gf_inv(mat[j][j]);
for (c = j; c < SYS_T + 1; c++)
mat[ c ][ j ] = gf_mul(mat[ c ][ j ], inv) ;
for (k = 0; k < SYS_T; k++)
{
if (k != j)
{
t = mat[ j ][ k ];
for (c = j; c < SYS_T + 1; c++)
mat[ c ][ k ] ^= gf_mul(mat[ c ][ j ], t);
}
}
}
for (i = 0; i < SYS_T; i++)
out[i] = mat[ SYS_T ][ i ];
return 0;
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/vec.c */
/* 20221230 djb: add linker line */
/* linker define vec_mul vec_sq vec_inv */
static void vec_mul(vec * h, const vec * f, const vec * g)
{
int i, j;
vec buf[ 2*GFBITS-1 ];
for (i = 0; i < 2*GFBITS-1; i++)
buf[i] = 0;
for (i = 0; i < GFBITS; i++)
for (j = 0; j < GFBITS; j++)
buf[i+j] ^= f[i] & g[j];
for (i = 2*GFBITS-2; i >= GFBITS; i--)
{
buf[i-GFBITS+4] ^= buf[i];
buf[i-GFBITS+3] ^= buf[i];
buf[i-GFBITS+1] ^= buf[i];
buf[i-GFBITS+0] ^= buf[i];
}
for (i = 0; i < GFBITS; i++)
h[i] = buf[i];
}
/* bitsliced field squarings */
static void vec_sq(vec * out, vec * in)
{
int i;
vec result[GFBITS], t;
t = in[11] ^ in[12];
result[0] = in[0] ^ in[11];
result[1] = in[7] ^ t;
result[2] = in[1] ^ in[7];
result[3] = in[8] ^ t;
result[4] = in[2] ^ in[7];
result[4] = result[4] ^ in[8];
result[4] = result[4] ^ t;
result[5] = in[7] ^ in[9];
result[6] = in[3] ^ in[8];
result[6] = result[6] ^ in[9];
result[6] = result[6] ^ in[12];
result[7] = in[8] ^ in[10];
result[8] = in[4] ^ in[9];
result[8] = result[8] ^ in[10];
result[9] = in[9] ^ in[11];
result[10] = in[5] ^ in[10];
result[10] = result[10] ^ in[11];
result[11] = in[10] ^ in[12];
result[12] = in[6] ^ t;
for (i = 0; i < GFBITS; i++)
out[i] = result[i];
}
/* bitsliced field inverses */
static void vec_inv(vec * out, vec * in)
{
vec tmp_11[ GFBITS ];
vec tmp_1111[ GFBITS ];
vec_copy(out, in);
vec_sq(out, out);
vec_mul(tmp_11, out, in); /* ^11 */
vec_sq(out, tmp_11);
vec_sq(out, out);
vec_mul(tmp_1111, out, tmp_11); /* ^1111 */
vec_sq(out, tmp_1111);
vec_sq(out, out);
vec_sq(out, out);
vec_sq(out, out);
vec_mul(out, out, tmp_1111); /* ^11111111 */
vec_sq(out, out);
vec_sq(out, out);
vec_sq(out, out);
vec_sq(out, out);
vec_mul(out, out, tmp_1111); /* ^111111111111 */
vec_sq(out, out); /* ^1111111111110 */
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_dec.c */
void mceliece6688128f_dec(uint8_t *key,
const uint8_t *c,
const uint8_t *sk)
{
operation_dec((unsigned char*) key,
(unsigned char*) c,
(unsigned char*) sk);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_enc.c */
void mceliece6688128f_enc(uint8_t *c,
uint8_t *key,
const uint8_t *pk)
{
operation_enc((unsigned char*) c,
(unsigned char*) key,
(unsigned char*) pk);
}
/* from libmceliece-20230612/crypto_kem/6688128f/vec/wrap_keypair.c */
void mceliece6688128f_keypair(uint8_t *pk,
uint8_t *sk)
{
operation_keypair((unsigned char*) pk, (unsigned char*) sk);
}
diff --git a/cipher/mceliece6688128f.h b/cipher/mceliece6688128f.h
index 60944cb6..eb9f23a0 100644
--- a/cipher/mceliece6688128f.h
+++ b/cipher/mceliece6688128f.h
@@ -1,56 +1,63 @@
/* mceliece6688128f.h - Classic McEliece for libgcrypt
* Copyright (C) 2023-2024 Simon Josefsson <simon@josefsson.org>
*
* This file is part of Libgcrypt.
*
* Libgcrypt is free software; you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* Libgcrypt is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this program; if not, see <https://www.gnu.org/licenses/>.
* SPDX-License-Identifier: LGPL-2.1-or-later
*
*/
#ifndef MCELIECE6688128F_H
#define MCELIECE6688128F_H
#include <string.h>
#include <stdint.h>
#ifdef _GCRYPT_IN_LIBGCRYPT
/**** Start of the glue code to libgcrypt ****/
+#include "g10lib.h" /* for GCC_ATTR_UNUSED */
#include "gcrypt-int.h"
#define mceliece6688128f_keypair _gcry_mceliece6688128f_keypair
#define mceliece6688128f_enc _gcry_mceliece6688128f_enc
#define mceliece6688128f_dec _gcry_mceliece6688128f_dec
/**** End of the glue code ****/
#else
+#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 5 )
+#define GCC_ATTR_UNUSED __attribute__ ((unused))
+#else
+#define GCC_ATTR_UNUSED
+#endif
+
#define MCELIECE6688128F_SECRETKEY_SIZE 13932
#define MCELIECE6688128F_PUBLICKEY_SIZE 1044992
#define MCELIECE6688128F_CIPHERTEXT_SIZE 208
#define MCELIECE6688128F_SIZE 32
#endif
typedef void mceliece6688128f_random_func (void *ctx,
size_t length,
uint8_t *dst);
void
mceliece6688128f_keypair (uint8_t *pk, uint8_t *sk);
void
mceliece6688128f_enc (uint8_t *c, uint8_t *k, const uint8_t *pk);
void
mceliece6688128f_dec (uint8_t *k, const uint8_t *c, const uint8_t *sk);
#endif /* MCELIECE6688128F_H */

File Metadata

Mime Type
text/x-diff
Expires
Fri, Mar 13, 10:18 PM (1 d, 14 h)
Storage Engine
local-disk
Storage Format
Raw Data
Storage Handle
5f/f3/7dbac26a44a9a438b0f9d02763a5

Event Timeline