1 /*
2 This file is for Niederreiter encryption
3 */
4
5 #include "encrypt.h"
6
7 #include "int32_sort.h"
8 #include "params.h"
9 #include "randombytes.h"
10 #include "util.h"
11
12 #include <assert.h>
13 #include <stdint.h>
14 #include <stdio.h>
15 #include <string.h>
16
17 #include "gf.h"
18
19 /* input: public key pk, error vector e */
20 /* output: syndrome s */
21 extern void PQCLEAN_MCELIECE460896F_AVX_syndrome_asm(unsigned char *s, const unsigned char *pk, unsigned char *e);
22
23 /* output: e, an error vector of weight t */
gen_e(unsigned char * e)24 static void gen_e(unsigned char *e) {
25 int i, j, eq, count;
26
27 uint16_t ind[ SYS_T * 2 ];
28 int32_t ind32[ SYS_T * 2 ];
29 uint64_t e_int[ (SYS_N + 63) / 64 ];
30 uint64_t one = 1;
31 uint64_t mask;
32 uint64_t val[ SYS_T ];
33
34 while (1) {
35 randombytes((uint8_t *) ind, sizeof(ind));
36
37 for (i = 0; i < SYS_T * 2; i++) {
38 ind[i] &= GFMASK;
39 }
40
41 // moving and counting indices in the correct range
42
43 count = 0;
44 for (i = 0; i < SYS_T * 2; i++) {
45 if (ind[i] < SYS_N) {
46 ind32[ count++ ] = ind[i];
47 }
48 }
49
50 if (count < SYS_T) {
51 continue;
52 }
53
54 // check for repetition
55
56 PQCLEAN_MCELIECE460896F_AVX_int32_sort(ind32, SYS_T);
57
58 eq = 0;
59 for (i = 1; i < SYS_T; i++) {
60 if (ind32[i - 1] == ind32[i]) {
61 eq = 1;
62 }
63 }
64
65 if (eq == 0) {
66 break;
67 }
68 }
69
70 for (j = 0; j < SYS_T; j++) {
71 val[j] = one << (ind32[j] & 63);
72 }
73
74 for (i = 0; i < (SYS_N + 63) / 64; i++) {
75 e_int[i] = 0;
76
77 for (j = 0; j < SYS_T; j++) {
78 mask = i ^ (ind32[j] >> 6);
79 mask -= 1;
80 mask >>= 63;
81 mask = -mask;
82
83 e_int[i] |= val[j] & mask;
84 }
85 }
86
87 for (i = 0; i < (SYS_N + 63) / 64; i++) {
88 PQCLEAN_MCELIECE460896F_AVX_store8(e, e_int[i]);
89 e += 8;
90 }
91 }
92
93 /* input: public key pk */
94 /* output: error vector e, syndrome s */
PQCLEAN_MCELIECE460896F_AVX_encrypt(unsigned char * s,unsigned char * e,const unsigned char * pk)95 void PQCLEAN_MCELIECE460896F_AVX_encrypt(unsigned char *s, unsigned char *e, const unsigned char *pk) {
96 gen_e(e);
97 PQCLEAN_MCELIECE460896F_AVX_syndrome_asm(s, pk, e);
98 }
99
100