Bug Summary

File:src/lib/libcrypto/curve25519/curve25519.c
Warning:line 3955, column 3
Value stored to 's16' is never read

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple amd64-unknown-openbsd7.0 -analyze -disable-free -disable-llvm-verifier -discard-value-names -main-file-name curve25519.c -analyzer-store=region -analyzer-opt-analyze-nested-blocks -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 1 -fhalf-no-semantic-interposition -mframe-pointer=all -relaxed-aliasing -fno-rounding-math -mconstructor-aliases -munwind-tables -target-cpu x86-64 -target-feature +retpoline-indirect-calls -target-feature +retpoline-indirect-branches -tune-cpu generic -debugger-tuning=gdb -fcoverage-compilation-dir=/usr/src/lib/libcrypto/obj -resource-dir /usr/local/lib/clang/13.0.0 -D LIBRESSL_INTERNAL -D LIBRESSL_CRYPTO_INTERNAL -D DSO_DLFCN -D HAVE_DLFCN_H -D HAVE_FUNOPEN -D OPENSSL_NO_HW_PADLOCK -I /usr/src/lib/libcrypto -I /usr/src/lib/libcrypto/asn1 -I /usr/src/lib/libcrypto/bio -I /usr/src/lib/libcrypto/bn -I /usr/src/lib/libcrypto/bytestring -I /usr/src/lib/libcrypto/dh -I /usr/src/lib/libcrypto/dsa -I /usr/src/lib/libcrypto/ec -I /usr/src/lib/libcrypto/ecdh -I /usr/src/lib/libcrypto/ecdsa -I /usr/src/lib/libcrypto/evp -I /usr/src/lib/libcrypto/hmac -I /usr/src/lib/libcrypto/modes -I /usr/src/lib/libcrypto/ocsp -I /usr/src/lib/libcrypto/rsa -I /usr/src/lib/libcrypto/x509 -I /usr/src/lib/libcrypto/obj -D AES_ASM -D BSAES_ASM -D VPAES_ASM -D OPENSSL_IA32_SSE2 -D RSA_ASM -D OPENSSL_BN_ASM_MONT -D OPENSSL_BN_ASM_MONT5 -D OPENSSL_BN_ASM_GF2m -D MD5_ASM -D GHASH_ASM -D RC4_MD5_ASM -D SHA1_ASM -D SHA256_ASM -D SHA512_ASM -D WHIRLPOOL_ASM -D OPENSSL_CPUID_OBJ -D PIC -internal-isystem /usr/local/lib/clang/13.0.0/include -internal-externc-isystem /usr/include -O2 -fdebug-compilation-dir=/usr/src/lib/libcrypto/obj -ferror-limit 19 -fwrapv -D_RET_PROTECTOR -ret-protector -fgnuc-version=4.2.1 -vectorize-loops -vectorize-slp -fno-builtin-malloc -fno-builtin-calloc -fno-builtin-realloc -fno-builtin-valloc -fno-builtin-free -fno-builtin-strdup -fno-builtin-strndup -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /home/ben/Projects/vmm/scan-build/2022-01-12-194120-40624-1 -x c /usr/src/lib/libcrypto/curve25519/curve25519.c
1/* $OpenBSD: curve25519.c,v 1.5 2019/05/11 15:55:52 tb Exp $ */
2/*
3 * Copyright (c) 2015, Google Inc.
4 *
5 * Permission to use, copy, modify, and/or distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
12 * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
14 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
15 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16 */
17
18/*
19 * This code is mostly taken from the ref10 version of Ed25519 in SUPERCOP
20 * 20141124 (http://bench.cr.yp.to/supercop.html). That code is released as
21 * public domain but this file has the ISC license just to keep licencing
22 * simple.
23 *
24 * The field functions are shared by Ed25519 and X25519 where possible.
25 */
26
27#include <stdlib.h>
28#include <string.h>
29
30#include <openssl/curve25519.h>
31
32#ifdef ED25519
33#include <openssl/sha.h>
34#endif
35
36#include "curve25519_internal.h"
37
38static const int64_t kBottom25Bits = 0x1ffffffLL;
39static const int64_t kBottom26Bits = 0x3ffffffLL;
40static const int64_t kTop39Bits = 0xfffffffffe000000LL;
41static const int64_t kTop38Bits = 0xfffffffffc000000LL;
42
43static uint64_t load_3(const uint8_t *in) {
44 uint64_t result;
45 result = (uint64_t)in[0];
46 result |= ((uint64_t)in[1]) << 8;
47 result |= ((uint64_t)in[2]) << 16;
48 return result;
49}
50
51static uint64_t load_4(const uint8_t *in) {
52 uint64_t result;
53 result = (uint64_t)in[0];
54 result |= ((uint64_t)in[1]) << 8;
55 result |= ((uint64_t)in[2]) << 16;
56 result |= ((uint64_t)in[3]) << 24;
57 return result;
58}
59
60static void fe_frombytes(fe h, const uint8_t *s) {
61 /* Ignores top bit of h. */
62 int64_t h0 = load_4(s);
63 int64_t h1 = load_3(s + 4) << 6;
64 int64_t h2 = load_3(s + 7) << 5;
65 int64_t h3 = load_3(s + 10) << 3;
66 int64_t h4 = load_3(s + 13) << 2;
67 int64_t h5 = load_4(s + 16);
68 int64_t h6 = load_3(s + 20) << 7;
69 int64_t h7 = load_3(s + 23) << 5;
70 int64_t h8 = load_3(s + 26) << 4;
71 int64_t h9 = (load_3(s + 29) & 8388607) << 2;
72 int64_t carry0;
73 int64_t carry1;
74 int64_t carry2;
75 int64_t carry3;
76 int64_t carry4;
77 int64_t carry5;
78 int64_t carry6;
79 int64_t carry7;
80 int64_t carry8;
81 int64_t carry9;
82
83 carry9 = h9 + (1 << 24); h0 += (carry9 >> 25) * 19; h9 -= carry9 & kTop39Bits;
84 carry1 = h1 + (1 << 24); h2 += carry1 >> 25; h1 -= carry1 & kTop39Bits;
85 carry3 = h3 + (1 << 24); h4 += carry3 >> 25; h3 -= carry3 & kTop39Bits;
86 carry5 = h5 + (1 << 24); h6 += carry5 >> 25; h5 -= carry5 & kTop39Bits;
87 carry7 = h7 + (1 << 24); h8 += carry7 >> 25; h7 -= carry7 & kTop39Bits;
88
89 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
90 carry2 = h2 + (1 << 25); h3 += carry2 >> 26; h2 -= carry2 & kTop38Bits;
91 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
92 carry6 = h6 + (1 << 25); h7 += carry6 >> 26; h6 -= carry6 & kTop38Bits;
93 carry8 = h8 + (1 << 25); h9 += carry8 >> 26; h8 -= carry8 & kTop38Bits;
94
95 h[0] = h0;
96 h[1] = h1;
97 h[2] = h2;
98 h[3] = h3;
99 h[4] = h4;
100 h[5] = h5;
101 h[6] = h6;
102 h[7] = h7;
103 h[8] = h8;
104 h[9] = h9;
105}
106
107/* Preconditions:
108 * |h| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc.
109 *
110 * Write p=2^255-19; q=floor(h/p).
111 * Basic claim: q = floor(2^(-255)(h + 19 2^(-25)h9 + 2^(-1))).
112 *
113 * Proof:
114 * Have |h|<=p so |q|<=1 so |19^2 2^(-255) q|<1/4.
115 * Also have |h-2^230 h9|<2^231 so |19 2^(-255)(h-2^230 h9)|<1/4.
116 *
117 * Write y=2^(-1)-19^2 2^(-255)q-19 2^(-255)(h-2^230 h9).
118 * Then 0<y<1.
119 *
120 * Write r=h-pq.
121 * Have 0<=r<=p-1=2^255-20.
122 * Thus 0<=r+19(2^-255)r<r+19(2^-255)2^255<=2^255-1.
123 *
124 * Write x=r+19(2^-255)r+y.
125 * Then 0<x<2^255 so floor(2^(-255)x) = 0 so floor(q+2^(-255)x) = q.
126 *
127 * Have q+2^(-255)x = 2^(-255)(h + 19 2^(-25) h9 + 2^(-1))
128 * so floor(2^(-255)(h + 19 2^(-25) h9 + 2^(-1))) = q. */
129static void fe_tobytes(uint8_t *s, const fe h) {
130 int32_t h0 = h[0];
131 int32_t h1 = h[1];
132 int32_t h2 = h[2];
133 int32_t h3 = h[3];
134 int32_t h4 = h[4];
135 int32_t h5 = h[5];
136 int32_t h6 = h[6];
137 int32_t h7 = h[7];
138 int32_t h8 = h[8];
139 int32_t h9 = h[9];
140 int32_t q;
141
142 q = (19 * h9 + (((int32_t) 1) << 24)) >> 25;
143 q = (h0 + q) >> 26;
144 q = (h1 + q) >> 25;
145 q = (h2 + q) >> 26;
146 q = (h3 + q) >> 25;
147 q = (h4 + q) >> 26;
148 q = (h5 + q) >> 25;
149 q = (h6 + q) >> 26;
150 q = (h7 + q) >> 25;
151 q = (h8 + q) >> 26;
152 q = (h9 + q) >> 25;
153
154 /* Goal: Output h-(2^255-19)q, which is between 0 and 2^255-20. */
155 h0 += 19 * q;
156 /* Goal: Output h-2^255 q, which is between 0 and 2^255-20. */
157
158 h1 += h0 >> 26; h0 &= kBottom26Bits;
159 h2 += h1 >> 25; h1 &= kBottom25Bits;
160 h3 += h2 >> 26; h2 &= kBottom26Bits;
161 h4 += h3 >> 25; h3 &= kBottom25Bits;
162 h5 += h4 >> 26; h4 &= kBottom26Bits;
163 h6 += h5 >> 25; h5 &= kBottom25Bits;
164 h7 += h6 >> 26; h6 &= kBottom26Bits;
165 h8 += h7 >> 25; h7 &= kBottom25Bits;
166 h9 += h8 >> 26; h8 &= kBottom26Bits;
167 h9 &= kBottom25Bits;
168 /* h10 = carry9 */
169
170 /* Goal: Output h0+...+2^255 h10-2^255 q, which is between 0 and 2^255-20.
171 * Have h0+...+2^230 h9 between 0 and 2^255-1;
172 * evidently 2^255 h10-2^255 q = 0.
173 * Goal: Output h0+...+2^230 h9. */
174
175 s[0] = h0 >> 0;
176 s[1] = h0 >> 8;
177 s[2] = h0 >> 16;
178 s[3] = (h0 >> 24) | ((uint32_t)(h1) << 2);
179 s[4] = h1 >> 6;
180 s[5] = h1 >> 14;
181 s[6] = (h1 >> 22) | ((uint32_t)(h2) << 3);
182 s[7] = h2 >> 5;
183 s[8] = h2 >> 13;
184 s[9] = (h2 >> 21) | ((uint32_t)(h3) << 5);
185 s[10] = h3 >> 3;
186 s[11] = h3 >> 11;
187 s[12] = (h3 >> 19) | ((uint32_t)(h4) << 6);
188 s[13] = h4 >> 2;
189 s[14] = h4 >> 10;
190 s[15] = h4 >> 18;
191 s[16] = h5 >> 0;
192 s[17] = h5 >> 8;
193 s[18] = h5 >> 16;
194 s[19] = (h5 >> 24) | ((uint32_t)(h6) << 1);
195 s[20] = h6 >> 7;
196 s[21] = h6 >> 15;
197 s[22] = (h6 >> 23) | ((uint32_t)(h7) << 3);
198 s[23] = h7 >> 5;
199 s[24] = h7 >> 13;
200 s[25] = (h7 >> 21) | ((uint32_t)(h8) << 4);
201 s[26] = h8 >> 4;
202 s[27] = h8 >> 12;
203 s[28] = (h8 >> 20) | ((uint32_t)(h9) << 6);
204 s[29] = h9 >> 2;
205 s[30] = h9 >> 10;
206 s[31] = h9 >> 18;
207}
208
209/* h = f */
210static void fe_copy(fe h, const fe f) {
211 memmove(h, f, sizeof(int32_t) * 10);
212}
213
214/* h = 0 */
215static void fe_0(fe h) { memset(h, 0, sizeof(int32_t) * 10); }
216
217/* h = 1 */
218static void fe_1(fe h) {
219 memset(h, 0, sizeof(int32_t) * 10);
220 h[0] = 1;
221}
222
223/* h = f + g
224 * Can overlap h with f or g.
225 *
226 * Preconditions:
227 * |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc.
228 * |g| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc.
229 *
230 * Postconditions:
231 * |h| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. */
232static void fe_add(fe h, const fe f, const fe g) {
233 unsigned i;
234 for (i = 0; i < 10; i++) {
235 h[i] = f[i] + g[i];
236 }
237}
238
239/* h = f - g
240 * Can overlap h with f or g.
241 *
242 * Preconditions:
243 * |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc.
244 * |g| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc.
245 *
246 * Postconditions:
247 * |h| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. */
248static void fe_sub(fe h, const fe f, const fe g) {
249 unsigned i;
250 for (i = 0; i < 10; i++) {
251 h[i] = f[i] - g[i];
252 }
253}
254
255/* h = f * g
256 * Can overlap h with f or g.
257 *
258 * Preconditions:
259 * |f| bounded by 1.65*2^26,1.65*2^25,1.65*2^26,1.65*2^25,etc.
260 * |g| bounded by 1.65*2^26,1.65*2^25,1.65*2^26,1.65*2^25,etc.
261 *
262 * Postconditions:
263 * |h| bounded by 1.01*2^25,1.01*2^24,1.01*2^25,1.01*2^24,etc.
264 *
265 * Notes on implementation strategy:
266 *
267 * Using schoolbook multiplication.
268 * Karatsuba would save a little in some cost models.
269 *
270 * Most multiplications by 2 and 19 are 32-bit precomputations;
271 * cheaper than 64-bit postcomputations.
272 *
273 * There is one remaining multiplication by 19 in the carry chain;
274 * one *19 precomputation can be merged into this,
275 * but the resulting data flow is considerably less clean.
276 *
277 * There are 12 carries below.
278 * 10 of them are 2-way parallelizable and vectorizable.
279 * Can get away with 11 carries, but then data flow is much deeper.
280 *
281 * With tighter constraints on inputs can squeeze carries into int32. */
282static void fe_mul(fe h, const fe f, const fe g) {
283 int32_t f0 = f[0];
284 int32_t f1 = f[1];
285 int32_t f2 = f[2];
286 int32_t f3 = f[3];
287 int32_t f4 = f[4];
288 int32_t f5 = f[5];
289 int32_t f6 = f[6];
290 int32_t f7 = f[7];
291 int32_t f8 = f[8];
292 int32_t f9 = f[9];
293 int32_t g0 = g[0];
294 int32_t g1 = g[1];
295 int32_t g2 = g[2];
296 int32_t g3 = g[3];
297 int32_t g4 = g[4];
298 int32_t g5 = g[5];
299 int32_t g6 = g[6];
300 int32_t g7 = g[7];
301 int32_t g8 = g[8];
302 int32_t g9 = g[9];
303 int32_t g1_19 = 19 * g1; /* 1.959375*2^29 */
304 int32_t g2_19 = 19 * g2; /* 1.959375*2^30; still ok */
305 int32_t g3_19 = 19 * g3;
306 int32_t g4_19 = 19 * g4;
307 int32_t g5_19 = 19 * g5;
308 int32_t g6_19 = 19 * g6;
309 int32_t g7_19 = 19 * g7;
310 int32_t g8_19 = 19 * g8;
311 int32_t g9_19 = 19 * g9;
312 int32_t f1_2 = 2 * f1;
313 int32_t f3_2 = 2 * f3;
314 int32_t f5_2 = 2 * f5;
315 int32_t f7_2 = 2 * f7;
316 int32_t f9_2 = 2 * f9;
317 int64_t f0g0 = f0 * (int64_t) g0;
318 int64_t f0g1 = f0 * (int64_t) g1;
319 int64_t f0g2 = f0 * (int64_t) g2;
320 int64_t f0g3 = f0 * (int64_t) g3;
321 int64_t f0g4 = f0 * (int64_t) g4;
322 int64_t f0g5 = f0 * (int64_t) g5;
323 int64_t f0g6 = f0 * (int64_t) g6;
324 int64_t f0g7 = f0 * (int64_t) g7;
325 int64_t f0g8 = f0 * (int64_t) g8;
326 int64_t f0g9 = f0 * (int64_t) g9;
327 int64_t f1g0 = f1 * (int64_t) g0;
328 int64_t f1g1_2 = f1_2 * (int64_t) g1;
329 int64_t f1g2 = f1 * (int64_t) g2;
330 int64_t f1g3_2 = f1_2 * (int64_t) g3;
331 int64_t f1g4 = f1 * (int64_t) g4;
332 int64_t f1g5_2 = f1_2 * (int64_t) g5;
333 int64_t f1g6 = f1 * (int64_t) g6;
334 int64_t f1g7_2 = f1_2 * (int64_t) g7;
335 int64_t f1g8 = f1 * (int64_t) g8;
336 int64_t f1g9_38 = f1_2 * (int64_t) g9_19;
337 int64_t f2g0 = f2 * (int64_t) g0;
338 int64_t f2g1 = f2 * (int64_t) g1;
339 int64_t f2g2 = f2 * (int64_t) g2;
340 int64_t f2g3 = f2 * (int64_t) g3;
341 int64_t f2g4 = f2 * (int64_t) g4;
342 int64_t f2g5 = f2 * (int64_t) g5;
343 int64_t f2g6 = f2 * (int64_t) g6;
344 int64_t f2g7 = f2 * (int64_t) g7;
345 int64_t f2g8_19 = f2 * (int64_t) g8_19;
346 int64_t f2g9_19 = f2 * (int64_t) g9_19;
347 int64_t f3g0 = f3 * (int64_t) g0;
348 int64_t f3g1_2 = f3_2 * (int64_t) g1;
349 int64_t f3g2 = f3 * (int64_t) g2;
350 int64_t f3g3_2 = f3_2 * (int64_t) g3;
351 int64_t f3g4 = f3 * (int64_t) g4;
352 int64_t f3g5_2 = f3_2 * (int64_t) g5;
353 int64_t f3g6 = f3 * (int64_t) g6;
354 int64_t f3g7_38 = f3_2 * (int64_t) g7_19;
355 int64_t f3g8_19 = f3 * (int64_t) g8_19;
356 int64_t f3g9_38 = f3_2 * (int64_t) g9_19;
357 int64_t f4g0 = f4 * (int64_t) g0;
358 int64_t f4g1 = f4 * (int64_t) g1;
359 int64_t f4g2 = f4 * (int64_t) g2;
360 int64_t f4g3 = f4 * (int64_t) g3;
361 int64_t f4g4 = f4 * (int64_t) g4;
362 int64_t f4g5 = f4 * (int64_t) g5;
363 int64_t f4g6_19 = f4 * (int64_t) g6_19;
364 int64_t f4g7_19 = f4 * (int64_t) g7_19;
365 int64_t f4g8_19 = f4 * (int64_t) g8_19;
366 int64_t f4g9_19 = f4 * (int64_t) g9_19;
367 int64_t f5g0 = f5 * (int64_t) g0;
368 int64_t f5g1_2 = f5_2 * (int64_t) g1;
369 int64_t f5g2 = f5 * (int64_t) g2;
370 int64_t f5g3_2 = f5_2 * (int64_t) g3;
371 int64_t f5g4 = f5 * (int64_t) g4;
372 int64_t f5g5_38 = f5_2 * (int64_t) g5_19;
373 int64_t f5g6_19 = f5 * (int64_t) g6_19;
374 int64_t f5g7_38 = f5_2 * (int64_t) g7_19;
375 int64_t f5g8_19 = f5 * (int64_t) g8_19;
376 int64_t f5g9_38 = f5_2 * (int64_t) g9_19;
377 int64_t f6g0 = f6 * (int64_t) g0;
378 int64_t f6g1 = f6 * (int64_t) g1;
379 int64_t f6g2 = f6 * (int64_t) g2;
380 int64_t f6g3 = f6 * (int64_t) g3;
381 int64_t f6g4_19 = f6 * (int64_t) g4_19;
382 int64_t f6g5_19 = f6 * (int64_t) g5_19;
383 int64_t f6g6_19 = f6 * (int64_t) g6_19;
384 int64_t f6g7_19 = f6 * (int64_t) g7_19;
385 int64_t f6g8_19 = f6 * (int64_t) g8_19;
386 int64_t f6g9_19 = f6 * (int64_t) g9_19;
387 int64_t f7g0 = f7 * (int64_t) g0;
388 int64_t f7g1_2 = f7_2 * (int64_t) g1;
389 int64_t f7g2 = f7 * (int64_t) g2;
390 int64_t f7g3_38 = f7_2 * (int64_t) g3_19;
391 int64_t f7g4_19 = f7 * (int64_t) g4_19;
392 int64_t f7g5_38 = f7_2 * (int64_t) g5_19;
393 int64_t f7g6_19 = f7 * (int64_t) g6_19;
394 int64_t f7g7_38 = f7_2 * (int64_t) g7_19;
395 int64_t f7g8_19 = f7 * (int64_t) g8_19;
396 int64_t f7g9_38 = f7_2 * (int64_t) g9_19;
397 int64_t f8g0 = f8 * (int64_t) g0;
398 int64_t f8g1 = f8 * (int64_t) g1;
399 int64_t f8g2_19 = f8 * (int64_t) g2_19;
400 int64_t f8g3_19 = f8 * (int64_t) g3_19;
401 int64_t f8g4_19 = f8 * (int64_t) g4_19;
402 int64_t f8g5_19 = f8 * (int64_t) g5_19;
403 int64_t f8g6_19 = f8 * (int64_t) g6_19;
404 int64_t f8g7_19 = f8 * (int64_t) g7_19;
405 int64_t f8g8_19 = f8 * (int64_t) g8_19;
406 int64_t f8g9_19 = f8 * (int64_t) g9_19;
407 int64_t f9g0 = f9 * (int64_t) g0;
408 int64_t f9g1_38 = f9_2 * (int64_t) g1_19;
409 int64_t f9g2_19 = f9 * (int64_t) g2_19;
410 int64_t f9g3_38 = f9_2 * (int64_t) g3_19;
411 int64_t f9g4_19 = f9 * (int64_t) g4_19;
412 int64_t f9g5_38 = f9_2 * (int64_t) g5_19;
413 int64_t f9g6_19 = f9 * (int64_t) g6_19;
414 int64_t f9g7_38 = f9_2 * (int64_t) g7_19;
415 int64_t f9g8_19 = f9 * (int64_t) g8_19;
416 int64_t f9g9_38 = f9_2 * (int64_t) g9_19;
417 int64_t h0 = f0g0+f1g9_38+f2g8_19+f3g7_38+f4g6_19+f5g5_38+f6g4_19+f7g3_38+f8g2_19+f9g1_38;
418 int64_t h1 = f0g1+f1g0 +f2g9_19+f3g8_19+f4g7_19+f5g6_19+f6g5_19+f7g4_19+f8g3_19+f9g2_19;
419 int64_t h2 = f0g2+f1g1_2 +f2g0 +f3g9_38+f4g8_19+f5g7_38+f6g6_19+f7g5_38+f8g4_19+f9g3_38;
420 int64_t h3 = f0g3+f1g2 +f2g1 +f3g0 +f4g9_19+f5g8_19+f6g7_19+f7g6_19+f8g5_19+f9g4_19;
421 int64_t h4 = f0g4+f1g3_2 +f2g2 +f3g1_2 +f4g0 +f5g9_38+f6g8_19+f7g7_38+f8g6_19+f9g5_38;
422 int64_t h5 = f0g5+f1g4 +f2g3 +f3g2 +f4g1 +f5g0 +f6g9_19+f7g8_19+f8g7_19+f9g6_19;
423 int64_t h6 = f0g6+f1g5_2 +f2g4 +f3g3_2 +f4g2 +f5g1_2 +f6g0 +f7g9_38+f8g8_19+f9g7_38;
424 int64_t h7 = f0g7+f1g6 +f2g5 +f3g4 +f4g3 +f5g2 +f6g1 +f7g0 +f8g9_19+f9g8_19;
425 int64_t h8 = f0g8+f1g7_2 +f2g6 +f3g5_2 +f4g4 +f5g3_2 +f6g2 +f7g1_2 +f8g0 +f9g9_38;
426 int64_t h9 = f0g9+f1g8 +f2g7 +f3g6 +f4g5 +f5g4 +f6g3 +f7g2 +f8g1 +f9g0 ;
427 int64_t carry0;
428 int64_t carry1;
429 int64_t carry2;
430 int64_t carry3;
431 int64_t carry4;
432 int64_t carry5;
433 int64_t carry6;
434 int64_t carry7;
435 int64_t carry8;
436 int64_t carry9;
437
438 /* |h0| <= (1.65*1.65*2^52*(1+19+19+19+19)+1.65*1.65*2^50*(38+38+38+38+38))
439 * i.e. |h0| <= 1.4*2^60; narrower ranges for h2, h4, h6, h8
440 * |h1| <= (1.65*1.65*2^51*(1+1+19+19+19+19+19+19+19+19))
441 * i.e. |h1| <= 1.7*2^59; narrower ranges for h3, h5, h7, h9 */
442
443 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
444 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
445 /* |h0| <= 2^25 */
446 /* |h4| <= 2^25 */
447 /* |h1| <= 1.71*2^59 */
448 /* |h5| <= 1.71*2^59 */
449
450 carry1 = h1 + (1 << 24); h2 += carry1 >> 25; h1 -= carry1 & kTop39Bits;
451 carry5 = h5 + (1 << 24); h6 += carry5 >> 25; h5 -= carry5 & kTop39Bits;
452 /* |h1| <= 2^24; from now on fits into int32 */
453 /* |h5| <= 2^24; from now on fits into int32 */
454 /* |h2| <= 1.41*2^60 */
455 /* |h6| <= 1.41*2^60 */
456
457 carry2 = h2 + (1 << 25); h3 += carry2 >> 26; h2 -= carry2 & kTop38Bits;
458 carry6 = h6 + (1 << 25); h7 += carry6 >> 26; h6 -= carry6 & kTop38Bits;
459 /* |h2| <= 2^25; from now on fits into int32 unchanged */
460 /* |h6| <= 2^25; from now on fits into int32 unchanged */
461 /* |h3| <= 1.71*2^59 */
462 /* |h7| <= 1.71*2^59 */
463
464 carry3 = h3 + (1 << 24); h4 += carry3 >> 25; h3 -= carry3 & kTop39Bits;
465 carry7 = h7 + (1 << 24); h8 += carry7 >> 25; h7 -= carry7 & kTop39Bits;
466 /* |h3| <= 2^24; from now on fits into int32 unchanged */
467 /* |h7| <= 2^24; from now on fits into int32 unchanged */
468 /* |h4| <= 1.72*2^34 */
469 /* |h8| <= 1.41*2^60 */
470
471 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
472 carry8 = h8 + (1 << 25); h9 += carry8 >> 26; h8 -= carry8 & kTop38Bits;
473 /* |h4| <= 2^25; from now on fits into int32 unchanged */
474 /* |h8| <= 2^25; from now on fits into int32 unchanged */
475 /* |h5| <= 1.01*2^24 */
476 /* |h9| <= 1.71*2^59 */
477
478 carry9 = h9 + (1 << 24); h0 += (carry9 >> 25) * 19; h9 -= carry9 & kTop39Bits;
479 /* |h9| <= 2^24; from now on fits into int32 unchanged */
480 /* |h0| <= 1.1*2^39 */
481
482 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
483 /* |h0| <= 2^25; from now on fits into int32 unchanged */
484 /* |h1| <= 1.01*2^24 */
485
486 h[0] = h0;
487 h[1] = h1;
488 h[2] = h2;
489 h[3] = h3;
490 h[4] = h4;
491 h[5] = h5;
492 h[6] = h6;
493 h[7] = h7;
494 h[8] = h8;
495 h[9] = h9;
496}
497
498/* h = f * f
499 * Can overlap h with f.
500 *
501 * Preconditions:
502 * |f| bounded by 1.65*2^26,1.65*2^25,1.65*2^26,1.65*2^25,etc.
503 *
504 * Postconditions:
505 * |h| bounded by 1.01*2^25,1.01*2^24,1.01*2^25,1.01*2^24,etc.
506 *
507 * See fe_mul.c for discussion of implementation strategy. */
508static void fe_sq(fe h, const fe f) {
509 int32_t f0 = f[0];
510 int32_t f1 = f[1];
511 int32_t f2 = f[2];
512 int32_t f3 = f[3];
513 int32_t f4 = f[4];
514 int32_t f5 = f[5];
515 int32_t f6 = f[6];
516 int32_t f7 = f[7];
517 int32_t f8 = f[8];
518 int32_t f9 = f[9];
519 int32_t f0_2 = 2 * f0;
520 int32_t f1_2 = 2 * f1;
521 int32_t f2_2 = 2 * f2;
522 int32_t f3_2 = 2 * f3;
523 int32_t f4_2 = 2 * f4;
524 int32_t f5_2 = 2 * f5;
525 int32_t f6_2 = 2 * f6;
526 int32_t f7_2 = 2 * f7;
527 int32_t f5_38 = 38 * f5; /* 1.959375*2^30 */
528 int32_t f6_19 = 19 * f6; /* 1.959375*2^30 */
529 int32_t f7_38 = 38 * f7; /* 1.959375*2^30 */
530 int32_t f8_19 = 19 * f8; /* 1.959375*2^30 */
531 int32_t f9_38 = 38 * f9; /* 1.959375*2^30 */
532 int64_t f0f0 = f0 * (int64_t) f0;
533 int64_t f0f1_2 = f0_2 * (int64_t) f1;
534 int64_t f0f2_2 = f0_2 * (int64_t) f2;
535 int64_t f0f3_2 = f0_2 * (int64_t) f3;
536 int64_t f0f4_2 = f0_2 * (int64_t) f4;
537 int64_t f0f5_2 = f0_2 * (int64_t) f5;
538 int64_t f0f6_2 = f0_2 * (int64_t) f6;
539 int64_t f0f7_2 = f0_2 * (int64_t) f7;
540 int64_t f0f8_2 = f0_2 * (int64_t) f8;
541 int64_t f0f9_2 = f0_2 * (int64_t) f9;
542 int64_t f1f1_2 = f1_2 * (int64_t) f1;
543 int64_t f1f2_2 = f1_2 * (int64_t) f2;
544 int64_t f1f3_4 = f1_2 * (int64_t) f3_2;
545 int64_t f1f4_2 = f1_2 * (int64_t) f4;
546 int64_t f1f5_4 = f1_2 * (int64_t) f5_2;
547 int64_t f1f6_2 = f1_2 * (int64_t) f6;
548 int64_t f1f7_4 = f1_2 * (int64_t) f7_2;
549 int64_t f1f8_2 = f1_2 * (int64_t) f8;
550 int64_t f1f9_76 = f1_2 * (int64_t) f9_38;
551 int64_t f2f2 = f2 * (int64_t) f2;
552 int64_t f2f3_2 = f2_2 * (int64_t) f3;
553 int64_t f2f4_2 = f2_2 * (int64_t) f4;
554 int64_t f2f5_2 = f2_2 * (int64_t) f5;
555 int64_t f2f6_2 = f2_2 * (int64_t) f6;
556 int64_t f2f7_2 = f2_2 * (int64_t) f7;
557 int64_t f2f8_38 = f2_2 * (int64_t) f8_19;
558 int64_t f2f9_38 = f2 * (int64_t) f9_38;
559 int64_t f3f3_2 = f3_2 * (int64_t) f3;
560 int64_t f3f4_2 = f3_2 * (int64_t) f4;
561 int64_t f3f5_4 = f3_2 * (int64_t) f5_2;
562 int64_t f3f6_2 = f3_2 * (int64_t) f6;
563 int64_t f3f7_76 = f3_2 * (int64_t) f7_38;
564 int64_t f3f8_38 = f3_2 * (int64_t) f8_19;
565 int64_t f3f9_76 = f3_2 * (int64_t) f9_38;
566 int64_t f4f4 = f4 * (int64_t) f4;
567 int64_t f4f5_2 = f4_2 * (int64_t) f5;
568 int64_t f4f6_38 = f4_2 * (int64_t) f6_19;
569 int64_t f4f7_38 = f4 * (int64_t) f7_38;
570 int64_t f4f8_38 = f4_2 * (int64_t) f8_19;
571 int64_t f4f9_38 = f4 * (int64_t) f9_38;
572 int64_t f5f5_38 = f5 * (int64_t) f5_38;
573 int64_t f5f6_38 = f5_2 * (int64_t) f6_19;
574 int64_t f5f7_76 = f5_2 * (int64_t) f7_38;
575 int64_t f5f8_38 = f5_2 * (int64_t) f8_19;
576 int64_t f5f9_76 = f5_2 * (int64_t) f9_38;
577 int64_t f6f6_19 = f6 * (int64_t) f6_19;
578 int64_t f6f7_38 = f6 * (int64_t) f7_38;
579 int64_t f6f8_38 = f6_2 * (int64_t) f8_19;
580 int64_t f6f9_38 = f6 * (int64_t) f9_38;
581 int64_t f7f7_38 = f7 * (int64_t) f7_38;
582 int64_t f7f8_38 = f7_2 * (int64_t) f8_19;
583 int64_t f7f9_76 = f7_2 * (int64_t) f9_38;
584 int64_t f8f8_19 = f8 * (int64_t) f8_19;
585 int64_t f8f9_38 = f8 * (int64_t) f9_38;
586 int64_t f9f9_38 = f9 * (int64_t) f9_38;
587 int64_t h0 = f0f0 +f1f9_76+f2f8_38+f3f7_76+f4f6_38+f5f5_38;
588 int64_t h1 = f0f1_2+f2f9_38+f3f8_38+f4f7_38+f5f6_38;
589 int64_t h2 = f0f2_2+f1f1_2 +f3f9_76+f4f8_38+f5f7_76+f6f6_19;
590 int64_t h3 = f0f3_2+f1f2_2 +f4f9_38+f5f8_38+f6f7_38;
591 int64_t h4 = f0f4_2+f1f3_4 +f2f2 +f5f9_76+f6f8_38+f7f7_38;
592 int64_t h5 = f0f5_2+f1f4_2 +f2f3_2 +f6f9_38+f7f8_38;
593 int64_t h6 = f0f6_2+f1f5_4 +f2f4_2 +f3f3_2 +f7f9_76+f8f8_19;
594 int64_t h7 = f0f7_2+f1f6_2 +f2f5_2 +f3f4_2 +f8f9_38;
595 int64_t h8 = f0f8_2+f1f7_4 +f2f6_2 +f3f5_4 +f4f4 +f9f9_38;
596 int64_t h9 = f0f9_2+f1f8_2 +f2f7_2 +f3f6_2 +f4f5_2;
597 int64_t carry0;
598 int64_t carry1;
599 int64_t carry2;
600 int64_t carry3;
601 int64_t carry4;
602 int64_t carry5;
603 int64_t carry6;
604 int64_t carry7;
605 int64_t carry8;
606 int64_t carry9;
607
608 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
609 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
610
611 carry1 = h1 + (1 << 24); h2 += carry1 >> 25; h1 -= carry1 & kTop39Bits;
612 carry5 = h5 + (1 << 24); h6 += carry5 >> 25; h5 -= carry5 & kTop39Bits;
613
614 carry2 = h2 + (1 << 25); h3 += carry2 >> 26; h2 -= carry2 & kTop38Bits;
615 carry6 = h6 + (1 << 25); h7 += carry6 >> 26; h6 -= carry6 & kTop38Bits;
616
617 carry3 = h3 + (1 << 24); h4 += carry3 >> 25; h3 -= carry3 & kTop39Bits;
618 carry7 = h7 + (1 << 24); h8 += carry7 >> 25; h7 -= carry7 & kTop39Bits;
619
620 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
621 carry8 = h8 + (1 << 25); h9 += carry8 >> 26; h8 -= carry8 & kTop38Bits;
622
623 carry9 = h9 + (1 << 24); h0 += (carry9 >> 25) * 19; h9 -= carry9 & kTop39Bits;
624
625 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
626
627 h[0] = h0;
628 h[1] = h1;
629 h[2] = h2;
630 h[3] = h3;
631 h[4] = h4;
632 h[5] = h5;
633 h[6] = h6;
634 h[7] = h7;
635 h[8] = h8;
636 h[9] = h9;
637}
638
639static void fe_invert(fe out, const fe z) {
640 fe t0;
641 fe t1;
642 fe t2;
643 fe t3;
644 int i;
645
646 fe_sq(t0, z);
647 for (i = 1; i < 1; ++i) {
648 fe_sq(t0, t0);
649 }
650 fe_sq(t1, t0);
651 for (i = 1; i < 2; ++i) {
652 fe_sq(t1, t1);
653 }
654 fe_mul(t1, z, t1);
655 fe_mul(t0, t0, t1);
656 fe_sq(t2, t0);
657 for (i = 1; i < 1; ++i) {
658 fe_sq(t2, t2);
659 }
660 fe_mul(t1, t1, t2);
661 fe_sq(t2, t1);
662 for (i = 1; i < 5; ++i) {
663 fe_sq(t2, t2);
664 }
665 fe_mul(t1, t2, t1);
666 fe_sq(t2, t1);
667 for (i = 1; i < 10; ++i) {
668 fe_sq(t2, t2);
669 }
670 fe_mul(t2, t2, t1);
671 fe_sq(t3, t2);
672 for (i = 1; i < 20; ++i) {
673 fe_sq(t3, t3);
674 }
675 fe_mul(t2, t3, t2);
676 fe_sq(t2, t2);
677 for (i = 1; i < 10; ++i) {
678 fe_sq(t2, t2);
679 }
680 fe_mul(t1, t2, t1);
681 fe_sq(t2, t1);
682 for (i = 1; i < 50; ++i) {
683 fe_sq(t2, t2);
684 }
685 fe_mul(t2, t2, t1);
686 fe_sq(t3, t2);
687 for (i = 1; i < 100; ++i) {
688 fe_sq(t3, t3);
689 }
690 fe_mul(t2, t3, t2);
691 fe_sq(t2, t2);
692 for (i = 1; i < 50; ++i) {
693 fe_sq(t2, t2);
694 }
695 fe_mul(t1, t2, t1);
696 fe_sq(t1, t1);
697 for (i = 1; i < 5; ++i) {
698 fe_sq(t1, t1);
699 }
700 fe_mul(out, t1, t0);
701}
702
703/* h = -f
704 *
705 * Preconditions:
706 * |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc.
707 *
708 * Postconditions:
709 * |h| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. */
710static void fe_neg(fe h, const fe f) {
711 unsigned i;
712 for (i = 0; i < 10; i++) {
713 h[i] = -f[i];
714 }
715}
716
717/* Replace (f,g) with (g,g) if b == 1;
718 * replace (f,g) with (f,g) if b == 0.
719 *
720 * Preconditions: b in {0,1}. */
721static void fe_cmov(fe f, const fe g, unsigned b) {
722 b = 0-b;
723 unsigned i;
724 for (i = 0; i < 10; i++) {
725 int32_t x = f[i] ^ g[i];
726 x &= b;
727 f[i] ^= x;
728 }
729}
730
731/* return 0 if f == 0
732 * return 1 if f != 0
733 *
734 * Preconditions:
735 * |f| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. */
736static int fe_isnonzero(const fe f) {
737 uint8_t s[32];
738 fe_tobytes(s, f);
739
740 static const uint8_t zero[32] = {0};
741 return timingsafe_memcmp(s, zero, sizeof(zero)) != 0;
742}
743
744/* return 1 if f is in {1,3,5,...,q-2}
745 * return 0 if f is in {0,2,4,...,q-1}
746 *
747 * Preconditions:
748 * |f| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. */
749static int fe_isnegative(const fe f) {
750 uint8_t s[32];
751 fe_tobytes(s, f);
752 return s[0] & 1;
753}
754
755/* h = 2 * f * f
756 * Can overlap h with f.
757 *
758 * Preconditions:
759 * |f| bounded by 1.65*2^26,1.65*2^25,1.65*2^26,1.65*2^25,etc.
760 *
761 * Postconditions:
762 * |h| bounded by 1.01*2^25,1.01*2^24,1.01*2^25,1.01*2^24,etc.
763 *
764 * See fe_mul.c for discussion of implementation strategy. */
765static void fe_sq2(fe h, const fe f) {
766 int32_t f0 = f[0];
767 int32_t f1 = f[1];
768 int32_t f2 = f[2];
769 int32_t f3 = f[3];
770 int32_t f4 = f[4];
771 int32_t f5 = f[5];
772 int32_t f6 = f[6];
773 int32_t f7 = f[7];
774 int32_t f8 = f[8];
775 int32_t f9 = f[9];
776 int32_t f0_2 = 2 * f0;
777 int32_t f1_2 = 2 * f1;
778 int32_t f2_2 = 2 * f2;
779 int32_t f3_2 = 2 * f3;
780 int32_t f4_2 = 2 * f4;
781 int32_t f5_2 = 2 * f5;
782 int32_t f6_2 = 2 * f6;
783 int32_t f7_2 = 2 * f7;
784 int32_t f5_38 = 38 * f5; /* 1.959375*2^30 */
785 int32_t f6_19 = 19 * f6; /* 1.959375*2^30 */
786 int32_t f7_38 = 38 * f7; /* 1.959375*2^30 */
787 int32_t f8_19 = 19 * f8; /* 1.959375*2^30 */
788 int32_t f9_38 = 38 * f9; /* 1.959375*2^30 */
789 int64_t f0f0 = f0 * (int64_t) f0;
790 int64_t f0f1_2 = f0_2 * (int64_t) f1;
791 int64_t f0f2_2 = f0_2 * (int64_t) f2;
792 int64_t f0f3_2 = f0_2 * (int64_t) f3;
793 int64_t f0f4_2 = f0_2 * (int64_t) f4;
794 int64_t f0f5_2 = f0_2 * (int64_t) f5;
795 int64_t f0f6_2 = f0_2 * (int64_t) f6;
796 int64_t f0f7_2 = f0_2 * (int64_t) f7;
797 int64_t f0f8_2 = f0_2 * (int64_t) f8;
798 int64_t f0f9_2 = f0_2 * (int64_t) f9;
799 int64_t f1f1_2 = f1_2 * (int64_t) f1;
800 int64_t f1f2_2 = f1_2 * (int64_t) f2;
801 int64_t f1f3_4 = f1_2 * (int64_t) f3_2;
802 int64_t f1f4_2 = f1_2 * (int64_t) f4;
803 int64_t f1f5_4 = f1_2 * (int64_t) f5_2;
804 int64_t f1f6_2 = f1_2 * (int64_t) f6;
805 int64_t f1f7_4 = f1_2 * (int64_t) f7_2;
806 int64_t f1f8_2 = f1_2 * (int64_t) f8;
807 int64_t f1f9_76 = f1_2 * (int64_t) f9_38;
808 int64_t f2f2 = f2 * (int64_t) f2;
809 int64_t f2f3_2 = f2_2 * (int64_t) f3;
810 int64_t f2f4_2 = f2_2 * (int64_t) f4;
811 int64_t f2f5_2 = f2_2 * (int64_t) f5;
812 int64_t f2f6_2 = f2_2 * (int64_t) f6;
813 int64_t f2f7_2 = f2_2 * (int64_t) f7;
814 int64_t f2f8_38 = f2_2 * (int64_t) f8_19;
815 int64_t f2f9_38 = f2 * (int64_t) f9_38;
816 int64_t f3f3_2 = f3_2 * (int64_t) f3;
817 int64_t f3f4_2 = f3_2 * (int64_t) f4;
818 int64_t f3f5_4 = f3_2 * (int64_t) f5_2;
819 int64_t f3f6_2 = f3_2 * (int64_t) f6;
820 int64_t f3f7_76 = f3_2 * (int64_t) f7_38;
821 int64_t f3f8_38 = f3_2 * (int64_t) f8_19;
822 int64_t f3f9_76 = f3_2 * (int64_t) f9_38;
823 int64_t f4f4 = f4 * (int64_t) f4;
824 int64_t f4f5_2 = f4_2 * (int64_t) f5;
825 int64_t f4f6_38 = f4_2 * (int64_t) f6_19;
826 int64_t f4f7_38 = f4 * (int64_t) f7_38;
827 int64_t f4f8_38 = f4_2 * (int64_t) f8_19;
828 int64_t f4f9_38 = f4 * (int64_t) f9_38;
829 int64_t f5f5_38 = f5 * (int64_t) f5_38;
830 int64_t f5f6_38 = f5_2 * (int64_t) f6_19;
831 int64_t f5f7_76 = f5_2 * (int64_t) f7_38;
832 int64_t f5f8_38 = f5_2 * (int64_t) f8_19;
833 int64_t f5f9_76 = f5_2 * (int64_t) f9_38;
834 int64_t f6f6_19 = f6 * (int64_t) f6_19;
835 int64_t f6f7_38 = f6 * (int64_t) f7_38;
836 int64_t f6f8_38 = f6_2 * (int64_t) f8_19;
837 int64_t f6f9_38 = f6 * (int64_t) f9_38;
838 int64_t f7f7_38 = f7 * (int64_t) f7_38;
839 int64_t f7f8_38 = f7_2 * (int64_t) f8_19;
840 int64_t f7f9_76 = f7_2 * (int64_t) f9_38;
841 int64_t f8f8_19 = f8 * (int64_t) f8_19;
842 int64_t f8f9_38 = f8 * (int64_t) f9_38;
843 int64_t f9f9_38 = f9 * (int64_t) f9_38;
844 int64_t h0 = f0f0 +f1f9_76+f2f8_38+f3f7_76+f4f6_38+f5f5_38;
845 int64_t h1 = f0f1_2+f2f9_38+f3f8_38+f4f7_38+f5f6_38;
846 int64_t h2 = f0f2_2+f1f1_2 +f3f9_76+f4f8_38+f5f7_76+f6f6_19;
847 int64_t h3 = f0f3_2+f1f2_2 +f4f9_38+f5f8_38+f6f7_38;
848 int64_t h4 = f0f4_2+f1f3_4 +f2f2 +f5f9_76+f6f8_38+f7f7_38;
849 int64_t h5 = f0f5_2+f1f4_2 +f2f3_2 +f6f9_38+f7f8_38;
850 int64_t h6 = f0f6_2+f1f5_4 +f2f4_2 +f3f3_2 +f7f9_76+f8f8_19;
851 int64_t h7 = f0f7_2+f1f6_2 +f2f5_2 +f3f4_2 +f8f9_38;
852 int64_t h8 = f0f8_2+f1f7_4 +f2f6_2 +f3f5_4 +f4f4 +f9f9_38;
853 int64_t h9 = f0f9_2+f1f8_2 +f2f7_2 +f3f6_2 +f4f5_2;
854 int64_t carry0;
855 int64_t carry1;
856 int64_t carry2;
857 int64_t carry3;
858 int64_t carry4;
859 int64_t carry5;
860 int64_t carry6;
861 int64_t carry7;
862 int64_t carry8;
863 int64_t carry9;
864
865 h0 += h0;
866 h1 += h1;
867 h2 += h2;
868 h3 += h3;
869 h4 += h4;
870 h5 += h5;
871 h6 += h6;
872 h7 += h7;
873 h8 += h8;
874 h9 += h9;
875
876 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
877 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
878
879 carry1 = h1 + (1 << 24); h2 += carry1 >> 25; h1 -= carry1 & kTop39Bits;
880 carry5 = h5 + (1 << 24); h6 += carry5 >> 25; h5 -= carry5 & kTop39Bits;
881
882 carry2 = h2 + (1 << 25); h3 += carry2 >> 26; h2 -= carry2 & kTop38Bits;
883 carry6 = h6 + (1 << 25); h7 += carry6 >> 26; h6 -= carry6 & kTop38Bits;
884
885 carry3 = h3 + (1 << 24); h4 += carry3 >> 25; h3 -= carry3 & kTop39Bits;
886 carry7 = h7 + (1 << 24); h8 += carry7 >> 25; h7 -= carry7 & kTop39Bits;
887
888 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
889 carry8 = h8 + (1 << 25); h9 += carry8 >> 26; h8 -= carry8 & kTop38Bits;
890
891 carry9 = h9 + (1 << 24); h0 += (carry9 >> 25) * 19; h9 -= carry9 & kTop39Bits;
892
893 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
894
895 h[0] = h0;
896 h[1] = h1;
897 h[2] = h2;
898 h[3] = h3;
899 h[4] = h4;
900 h[5] = h5;
901 h[6] = h6;
902 h[7] = h7;
903 h[8] = h8;
904 h[9] = h9;
905}
906
907static void fe_pow22523(fe out, const fe z) {
908 fe t0;
909 fe t1;
910 fe t2;
911 int i;
912
913 fe_sq(t0, z);
914 for (i = 1; i < 1; ++i) {
915 fe_sq(t0, t0);
916 }
917 fe_sq(t1, t0);
918 for (i = 1; i < 2; ++i) {
919 fe_sq(t1, t1);
920 }
921 fe_mul(t1, z, t1);
922 fe_mul(t0, t0, t1);
923 fe_sq(t0, t0);
924 for (i = 1; i < 1; ++i) {
925 fe_sq(t0, t0);
926 }
927 fe_mul(t0, t1, t0);
928 fe_sq(t1, t0);
929 for (i = 1; i < 5; ++i) {
930 fe_sq(t1, t1);
931 }
932 fe_mul(t0, t1, t0);
933 fe_sq(t1, t0);
934 for (i = 1; i < 10; ++i) {
935 fe_sq(t1, t1);
936 }
937 fe_mul(t1, t1, t0);
938 fe_sq(t2, t1);
939 for (i = 1; i < 20; ++i) {
940 fe_sq(t2, t2);
941 }
942 fe_mul(t1, t2, t1);
943 fe_sq(t1, t1);
944 for (i = 1; i < 10; ++i) {
945 fe_sq(t1, t1);
946 }
947 fe_mul(t0, t1, t0);
948 fe_sq(t1, t0);
949 for (i = 1; i < 50; ++i) {
950 fe_sq(t1, t1);
951 }
952 fe_mul(t1, t1, t0);
953 fe_sq(t2, t1);
954 for (i = 1; i < 100; ++i) {
955 fe_sq(t2, t2);
956 }
957 fe_mul(t1, t2, t1);
958 fe_sq(t1, t1);
959 for (i = 1; i < 50; ++i) {
960 fe_sq(t1, t1);
961 }
962 fe_mul(t0, t1, t0);
963 fe_sq(t0, t0);
964 for (i = 1; i < 2; ++i) {
965 fe_sq(t0, t0);
966 }
967 fe_mul(out, t0, z);
968}
969
970void x25519_ge_tobytes(uint8_t *s, const ge_p2 *h) {
971 fe recip;
972 fe x;
973 fe y;
974
975 fe_invert(recip, h->Z);
976 fe_mul(x, h->X, recip);
977 fe_mul(y, h->Y, recip);
978 fe_tobytes(s, y);
979 s[31] ^= fe_isnegative(x) << 7;
980}
981
982#ifdef ED25519
983static void ge_p3_tobytes(uint8_t *s, const ge_p3 *h) {
984 fe recip;
985 fe x;
986 fe y;
987
988 fe_invert(recip, h->Z);
989 fe_mul(x, h->X, recip);
990 fe_mul(y, h->Y, recip);
991 fe_tobytes(s, y);
992 s[31] ^= fe_isnegative(x) << 7;
993}
994#endif
995
996static const fe d = {-10913610, 13857413, -15372611, 6949391, 114729,
997 -8787816, -6275908, -3247719, -18696448, -12055116};
998
999static const fe sqrtm1 = {-32595792, -7943725, 9377950, 3500415, 12389472,
1000 -272473, -25146209, -2005654, 326686, 11406482};
1001
1002int x25519_ge_frombytes_vartime(ge_p3 *h, const uint8_t *s) {
1003 fe u;
1004 fe v;
1005 fe v3;
1006 fe vxx;
1007 fe check;
1008
1009 fe_frombytes(h->Y, s);
1010 fe_1(h->Z);
1011 fe_sq(u, h->Y);
1012 fe_mul(v, u, d);
1013 fe_sub(u, u, h->Z); /* u = y^2-1 */
1014 fe_add(v, v, h->Z); /* v = dy^2+1 */
1015
1016 fe_sq(v3, v);
1017 fe_mul(v3, v3, v); /* v3 = v^3 */
1018 fe_sq(h->X, v3);
1019 fe_mul(h->X, h->X, v);
1020 fe_mul(h->X, h->X, u); /* x = uv^7 */
1021
1022 fe_pow22523(h->X, h->X); /* x = (uv^7)^((q-5)/8) */
1023 fe_mul(h->X, h->X, v3);
1024 fe_mul(h->X, h->X, u); /* x = uv^3(uv^7)^((q-5)/8) */
1025
1026 fe_sq(vxx, h->X);
1027 fe_mul(vxx, vxx, v);
1028 fe_sub(check, vxx, u); /* vx^2-u */
1029 if (fe_isnonzero(check)) {
1030 fe_add(check, vxx, u); /* vx^2+u */
1031 if (fe_isnonzero(check)) {
1032 return -1;
1033 }
1034 fe_mul(h->X, h->X, sqrtm1);
1035 }
1036
1037 if (fe_isnegative(h->X) != (s[31] >> 7)) {
1038 fe_neg(h->X, h->X);
1039 }
1040
1041 fe_mul(h->T, h->X, h->Y);
1042 return 0;
1043}
1044
1045static void ge_p2_0(ge_p2 *h) {
1046 fe_0(h->X);
1047 fe_1(h->Y);
1048 fe_1(h->Z);
1049}
1050
1051static void ge_p3_0(ge_p3 *h) {
1052 fe_0(h->X);
1053 fe_1(h->Y);
1054 fe_1(h->Z);
1055 fe_0(h->T);
1056}
1057
1058static void ge_cached_0(ge_cached *h) {
1059 fe_1(h->YplusX);
1060 fe_1(h->YminusX);
1061 fe_1(h->Z);
1062 fe_0(h->T2d);
1063}
1064
1065static void ge_precomp_0(ge_precomp *h) {
1066 fe_1(h->yplusx);
1067 fe_1(h->yminusx);
1068 fe_0(h->xy2d);
1069}
1070
1071/* r = p */
1072static void ge_p3_to_p2(ge_p2 *r, const ge_p3 *p) {
1073 fe_copy(r->X, p->X);
1074 fe_copy(r->Y, p->Y);
1075 fe_copy(r->Z, p->Z);
1076}
1077
1078static const fe d2 = {-21827239, -5839606, -30745221, 13898782, 229458,
1079 15978800, -12551817, -6495438, 29715968, 9444199};
1080
1081/* r = p */
1082void x25519_ge_p3_to_cached(ge_cached *r, const ge_p3 *p) {
1083 fe_add(r->YplusX, p->Y, p->X);
1084 fe_sub(r->YminusX, p->Y, p->X);
1085 fe_copy(r->Z, p->Z);
1086 fe_mul(r->T2d, p->T, d2);
1087}
1088
1089/* r = p */
1090void x25519_ge_p1p1_to_p2(ge_p2 *r, const ge_p1p1 *p) {
1091 fe_mul(r->X, p->X, p->T);
1092 fe_mul(r->Y, p->Y, p->Z);
1093 fe_mul(r->Z, p->Z, p->T);
1094}
1095
1096/* r = p */
1097void x25519_ge_p1p1_to_p3(ge_p3 *r, const ge_p1p1 *p) {
1098 fe_mul(r->X, p->X, p->T);
1099 fe_mul(r->Y, p->Y, p->Z);
1100 fe_mul(r->Z, p->Z, p->T);
1101 fe_mul(r->T, p->X, p->Y);
1102}
1103
1104/* r = p */
1105static void ge_p1p1_to_cached(ge_cached *r, const ge_p1p1 *p) {
1106 ge_p3 t;
1107 x25519_ge_p1p1_to_p3(&t, p);
1108 x25519_ge_p3_to_cached(r, &t);
1109}
1110
1111/* r = 2 * p */
1112static void ge_p2_dbl(ge_p1p1 *r, const ge_p2 *p) {
1113 fe t0;
1114
1115 fe_sq(r->X, p->X);
1116 fe_sq(r->Z, p->Y);
1117 fe_sq2(r->T, p->Z);
1118 fe_add(r->Y, p->X, p->Y);
1119 fe_sq(t0, r->Y);
1120 fe_add(r->Y, r->Z, r->X);
1121 fe_sub(r->Z, r->Z, r->X);
1122 fe_sub(r->X, t0, r->Y);
1123 fe_sub(r->T, r->T, r->Z);
1124}
1125
1126/* r = 2 * p */
1127static void ge_p3_dbl(ge_p1p1 *r, const ge_p3 *p) {
1128 ge_p2 q;
1129 ge_p3_to_p2(&q, p);
1130 ge_p2_dbl(r, &q);
1131}
1132
1133/* r = p + q */
1134static void ge_madd(ge_p1p1 *r, const ge_p3 *p, const ge_precomp *q) {
1135 fe t0;
1136
1137 fe_add(r->X, p->Y, p->X);
1138 fe_sub(r->Y, p->Y, p->X);
1139 fe_mul(r->Z, r->X, q->yplusx);
1140 fe_mul(r->Y, r->Y, q->yminusx);
1141 fe_mul(r->T, q->xy2d, p->T);
1142 fe_add(t0, p->Z, p->Z);
1143 fe_sub(r->X, r->Z, r->Y);
1144 fe_add(r->Y, r->Z, r->Y);
1145 fe_add(r->Z, t0, r->T);
1146 fe_sub(r->T, t0, r->T);
1147}
1148
1149#ifdef ED25519
1150/* r = p - q */
1151static void ge_msub(ge_p1p1 *r, const ge_p3 *p, const ge_precomp *q) {
1152 fe t0;
1153
1154 fe_add(r->X, p->Y, p->X);
1155 fe_sub(r->Y, p->Y, p->X);
1156 fe_mul(r->Z, r->X, q->yminusx);
1157 fe_mul(r->Y, r->Y, q->yplusx);
1158 fe_mul(r->T, q->xy2d, p->T);
1159 fe_add(t0, p->Z, p->Z);
1160 fe_sub(r->X, r->Z, r->Y);
1161 fe_add(r->Y, r->Z, r->Y);
1162 fe_sub(r->Z, t0, r->T);
1163 fe_add(r->T, t0, r->T);
1164}
1165#endif
1166
1167/* r = p + q */
1168void x25519_ge_add(ge_p1p1 *r, const ge_p3 *p, const ge_cached *q) {
1169 fe t0;
1170
1171 fe_add(r->X, p->Y, p->X);
1172 fe_sub(r->Y, p->Y, p->X);
1173 fe_mul(r->Z, r->X, q->YplusX);
1174 fe_mul(r->Y, r->Y, q->YminusX);
1175 fe_mul(r->T, q->T2d, p->T);
1176 fe_mul(r->X, p->Z, q->Z);
1177 fe_add(t0, r->X, r->X);
1178 fe_sub(r->X, r->Z, r->Y);
1179 fe_add(r->Y, r->Z, r->Y);
1180 fe_add(r->Z, t0, r->T);
1181 fe_sub(r->T, t0, r->T);
1182}
1183
1184/* r = p - q */
1185void x25519_ge_sub(ge_p1p1 *r, const ge_p3 *p, const ge_cached *q) {
1186 fe t0;
1187
1188 fe_add(r->X, p->Y, p->X);
1189 fe_sub(r->Y, p->Y, p->X);
1190 fe_mul(r->Z, r->X, q->YminusX);
1191 fe_mul(r->Y, r->Y, q->YplusX);
1192 fe_mul(r->T, q->T2d, p->T);
1193 fe_mul(r->X, p->Z, q->Z);
1194 fe_add(t0, r->X, r->X);
1195 fe_sub(r->X, r->Z, r->Y);
1196 fe_add(r->Y, r->Z, r->Y);
1197 fe_sub(r->Z, t0, r->T);
1198 fe_add(r->T, t0, r->T);
1199}
1200
1201static uint8_t equal(signed char b, signed char c) {
1202 uint8_t ub = b;
1203 uint8_t uc = c;
1204 uint8_t x = ub ^ uc; /* 0: yes; 1..255: no */
1205 uint32_t y = x; /* 0: yes; 1..255: no */
1206 y -= 1; /* 4294967295: yes; 0..254: no */
1207 y >>= 31; /* 1: yes; 0: no */
1208 return y;
1209}
1210
1211static void cmov(ge_precomp *t, const ge_precomp *u, uint8_t b) {
1212 fe_cmov(t->yplusx, u->yplusx, b);
1213 fe_cmov(t->yminusx, u->yminusx, b);
1214 fe_cmov(t->xy2d, u->xy2d, b);
1215}
1216
1217void x25519_ge_scalarmult_small_precomp(
1218 ge_p3 *h, const uint8_t a[32], const uint8_t precomp_table[15 * 2 * 32]) {
1219 /* precomp_table is first expanded into matching |ge_precomp|
1220 * elements. */
1221 ge_precomp multiples[15];
1222
1223 unsigned i;
1224 for (i = 0; i < 15; i++) {
1225 const uint8_t *bytes = &precomp_table[i*(2 * 32)];
1226 fe x, y;
1227 fe_frombytes(x, bytes);
1228 fe_frombytes(y, bytes + 32);
1229
1230 ge_precomp *out = &multiples[i];
1231 fe_add(out->yplusx, y, x);
1232 fe_sub(out->yminusx, y, x);
1233 fe_mul(out->xy2d, x, y);
1234 fe_mul(out->xy2d, out->xy2d, d2);
1235 }
1236
1237 /* See the comment above |k25519SmallPrecomp| about the structure of the
1238 * precomputed elements. This loop does 64 additions and 64 doublings to
1239 * calculate the result. */
1240 ge_p3_0(h);
1241
1242 for (i = 63; i < 64; i--) {
1243 unsigned j;
1244 signed char index = 0;
1245
1246 for (j = 0; j < 4; j++) {
1247 const uint8_t bit = 1 & (a[(8 * j) + (i / 8)] >> (i & 7));
1248 index |= (bit << j);
1249 }
1250
1251 ge_precomp e;
1252 ge_precomp_0(&e);
1253
1254 for (j = 1; j < 16; j++) {
1255 cmov(&e, &multiples[j-1], equal(index, j));
1256 }
1257
1258 ge_cached cached;
1259 ge_p1p1 r;
1260 x25519_ge_p3_to_cached(&cached, h);
1261 x25519_ge_add(&r, h, &cached);
1262 x25519_ge_p1p1_to_p3(h, &r);
1263
1264 ge_madd(&r, h, &e);
1265 x25519_ge_p1p1_to_p3(h, &r);
1266 }
1267}
1268
1269#if defined(OPENSSL_SMALL)
1270
1271/* This block of code replaces the standard base-point table with a much smaller
1272 * one. The standard table is 30,720 bytes while this one is just 960.
1273 *
1274 * This table contains 15 pairs of group elements, (x, y), where each field
1275 * element is serialised with |fe_tobytes|. If |i| is the index of the group
1276 * element then consider i+1 as a four-bit number: (i₀, i₁, i₂, i₃) (where i₀
1277 * is the most significant bit). The value of the group element is then:
1278 * (i₀×2^192 + i₁×2^128 + i₂×2^64 + i₃)G, where G is the generator. */
1279static const uint8_t k25519SmallPrecomp[15 * 2 * 32] = {
1280 0x1a, 0xd5, 0x25, 0x8f, 0x60, 0x2d, 0x56, 0xc9, 0xb2, 0xa7, 0x25, 0x95,
1281 0x60, 0xc7, 0x2c, 0x69, 0x5c, 0xdc, 0xd6, 0xfd, 0x31, 0xe2, 0xa4, 0xc0,
1282 0xfe, 0x53, 0x6e, 0xcd, 0xd3, 0x36, 0x69, 0x21, 0x58, 0x66, 0x66, 0x66,
1283 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66,
1284 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66, 0x66,
1285 0x66, 0x66, 0x66, 0x66, 0x02, 0xa2, 0xed, 0xf4, 0x8f, 0x6b, 0x0b, 0x3e,
1286 0xeb, 0x35, 0x1a, 0xd5, 0x7e, 0xdb, 0x78, 0x00, 0x96, 0x8a, 0xa0, 0xb4,
1287 0xcf, 0x60, 0x4b, 0xd4, 0xd5, 0xf9, 0x2d, 0xbf, 0x88, 0xbd, 0x22, 0x62,
1288 0x13, 0x53, 0xe4, 0x82, 0x57, 0xfa, 0x1e, 0x8f, 0x06, 0x2b, 0x90, 0xba,
1289 0x08, 0xb6, 0x10, 0x54, 0x4f, 0x7c, 0x1b, 0x26, 0xed, 0xda, 0x6b, 0xdd,
1290 0x25, 0xd0, 0x4e, 0xea, 0x42, 0xbb, 0x25, 0x03, 0xa2, 0xfb, 0xcc, 0x61,
1291 0x67, 0x06, 0x70, 0x1a, 0xc4, 0x78, 0x3a, 0xff, 0x32, 0x62, 0xdd, 0x2c,
1292 0xab, 0x50, 0x19, 0x3b, 0xf2, 0x9b, 0x7d, 0xb8, 0xfd, 0x4f, 0x29, 0x9c,
1293 0xa7, 0x91, 0xba, 0x0e, 0x46, 0x5e, 0x51, 0xfe, 0x1d, 0xbf, 0xe5, 0xe5,
1294 0x9b, 0x95, 0x0d, 0x67, 0xf8, 0xd1, 0xb5, 0x5a, 0xa1, 0x93, 0x2c, 0xc3,
1295 0xde, 0x0e, 0x97, 0x85, 0x2d, 0x7f, 0xea, 0xab, 0x3e, 0x47, 0x30, 0x18,
1296 0x24, 0xe8, 0xb7, 0x60, 0xae, 0x47, 0x80, 0xfc, 0xe5, 0x23, 0xe7, 0xc2,
1297 0xc9, 0x85, 0xe6, 0x98, 0xa0, 0x29, 0x4e, 0xe1, 0x84, 0x39, 0x2d, 0x95,
1298 0x2c, 0xf3, 0x45, 0x3c, 0xff, 0xaf, 0x27, 0x4c, 0x6b, 0xa6, 0xf5, 0x4b,
1299 0x11, 0xbd, 0xba, 0x5b, 0x9e, 0xc4, 0xa4, 0x51, 0x1e, 0xbe, 0xd0, 0x90,
1300 0x3a, 0x9c, 0xc2, 0x26, 0xb6, 0x1e, 0xf1, 0x95, 0x7d, 0xc8, 0x6d, 0x52,
1301 0xe6, 0x99, 0x2c, 0x5f, 0x9a, 0x96, 0x0c, 0x68, 0x29, 0xfd, 0xe2, 0xfb,
1302 0xe6, 0xbc, 0xec, 0x31, 0x08, 0xec, 0xe6, 0xb0, 0x53, 0x60, 0xc3, 0x8c,
1303 0xbe, 0xc1, 0xb3, 0x8a, 0x8f, 0xe4, 0x88, 0x2b, 0x55, 0xe5, 0x64, 0x6e,
1304 0x9b, 0xd0, 0xaf, 0x7b, 0x64, 0x2a, 0x35, 0x25, 0x10, 0x52, 0xc5, 0x9e,
1305 0x58, 0x11, 0x39, 0x36, 0x45, 0x51, 0xb8, 0x39, 0x93, 0xfc, 0x9d, 0x6a,
1306 0xbe, 0x58, 0xcb, 0xa4, 0x0f, 0x51, 0x3c, 0x38, 0x05, 0xca, 0xab, 0x43,
1307 0x63, 0x0e, 0xf3, 0x8b, 0x41, 0xa6, 0xf8, 0x9b, 0x53, 0x70, 0x80, 0x53,
1308 0x86, 0x5e, 0x8f, 0xe3, 0xc3, 0x0d, 0x18, 0xc8, 0x4b, 0x34, 0x1f, 0xd8,
1309 0x1d, 0xbc, 0xf2, 0x6d, 0x34, 0x3a, 0xbe, 0xdf, 0xd9, 0xf6, 0xf3, 0x89,
1310 0xa1, 0xe1, 0x94, 0x9f, 0x5d, 0x4c, 0x5d, 0xe9, 0xa1, 0x49, 0x92, 0xef,
1311 0x0e, 0x53, 0x81, 0x89, 0x58, 0x87, 0xa6, 0x37, 0xf1, 0xdd, 0x62, 0x60,
1312 0x63, 0x5a, 0x9d, 0x1b, 0x8c, 0xc6, 0x7d, 0x52, 0xea, 0x70, 0x09, 0x6a,
1313 0xe1, 0x32, 0xf3, 0x73, 0x21, 0x1f, 0x07, 0x7b, 0x7c, 0x9b, 0x49, 0xd8,
1314 0xc0, 0xf3, 0x25, 0x72, 0x6f, 0x9d, 0xed, 0x31, 0x67, 0x36, 0x36, 0x54,
1315 0x40, 0x92, 0x71, 0xe6, 0x11, 0x28, 0x11, 0xad, 0x93, 0x32, 0x85, 0x7b,
1316 0x3e, 0xb7, 0x3b, 0x49, 0x13, 0x1c, 0x07, 0xb0, 0x2e, 0x93, 0xaa, 0xfd,
1317 0xfd, 0x28, 0x47, 0x3d, 0x8d, 0xd2, 0xda, 0xc7, 0x44, 0xd6, 0x7a, 0xdb,
1318 0x26, 0x7d, 0x1d, 0xb8, 0xe1, 0xde, 0x9d, 0x7a, 0x7d, 0x17, 0x7e, 0x1c,
1319 0x37, 0x04, 0x8d, 0x2d, 0x7c, 0x5e, 0x18, 0x38, 0x1e, 0xaf, 0xc7, 0x1b,
1320 0x33, 0x48, 0x31, 0x00, 0x59, 0xf6, 0xf2, 0xca, 0x0f, 0x27, 0x1b, 0x63,
1321 0x12, 0x7e, 0x02, 0x1d, 0x49, 0xc0, 0x5d, 0x79, 0x87, 0xef, 0x5e, 0x7a,
1322 0x2f, 0x1f, 0x66, 0x55, 0xd8, 0x09, 0xd9, 0x61, 0x38, 0x68, 0xb0, 0x07,
1323 0xa3, 0xfc, 0xcc, 0x85, 0x10, 0x7f, 0x4c, 0x65, 0x65, 0xb3, 0xfa, 0xfa,
1324 0xa5, 0x53, 0x6f, 0xdb, 0x74, 0x4c, 0x56, 0x46, 0x03, 0xe2, 0xd5, 0x7a,
1325 0x29, 0x1c, 0xc6, 0x02, 0xbc, 0x59, 0xf2, 0x04, 0x75, 0x63, 0xc0, 0x84,
1326 0x2f, 0x60, 0x1c, 0x67, 0x76, 0xfd, 0x63, 0x86, 0xf3, 0xfa, 0xbf, 0xdc,
1327 0xd2, 0x2d, 0x90, 0x91, 0xbd, 0x33, 0xa9, 0xe5, 0x66, 0x0c, 0xda, 0x42,
1328 0x27, 0xca, 0xf4, 0x66, 0xc2, 0xec, 0x92, 0x14, 0x57, 0x06, 0x63, 0xd0,
1329 0x4d, 0x15, 0x06, 0xeb, 0x69, 0x58, 0x4f, 0x77, 0xc5, 0x8b, 0xc7, 0xf0,
1330 0x8e, 0xed, 0x64, 0xa0, 0xb3, 0x3c, 0x66, 0x71, 0xc6, 0x2d, 0xda, 0x0a,
1331 0x0d, 0xfe, 0x70, 0x27, 0x64, 0xf8, 0x27, 0xfa, 0xf6, 0x5f, 0x30, 0xa5,
1332 0x0d, 0x6c, 0xda, 0xf2, 0x62, 0x5e, 0x78, 0x47, 0xd3, 0x66, 0x00, 0x1c,
1333 0xfd, 0x56, 0x1f, 0x5d, 0x3f, 0x6f, 0xf4, 0x4c, 0xd8, 0xfd, 0x0e, 0x27,
1334 0xc9, 0x5c, 0x2b, 0xbc, 0xc0, 0xa4, 0xe7, 0x23, 0x29, 0x02, 0x9f, 0x31,
1335 0xd6, 0xe9, 0xd7, 0x96, 0xf4, 0xe0, 0x5e, 0x0b, 0x0e, 0x13, 0xee, 0x3c,
1336 0x09, 0xed, 0xf2, 0x3d, 0x76, 0x91, 0xc3, 0xa4, 0x97, 0xae, 0xd4, 0x87,
1337 0xd0, 0x5d, 0xf6, 0x18, 0x47, 0x1f, 0x1d, 0x67, 0xf2, 0xcf, 0x63, 0xa0,
1338 0x91, 0x27, 0xf8, 0x93, 0x45, 0x75, 0x23, 0x3f, 0xd1, 0xf1, 0xad, 0x23,
1339 0xdd, 0x64, 0x93, 0x96, 0x41, 0x70, 0x7f, 0xf7, 0xf5, 0xa9, 0x89, 0xa2,
1340 0x34, 0xb0, 0x8d, 0x1b, 0xae, 0x19, 0x15, 0x49, 0x58, 0x23, 0x6d, 0x87,
1341 0x15, 0x4f, 0x81, 0x76, 0xfb, 0x23, 0xb5, 0xea, 0xcf, 0xac, 0x54, 0x8d,
1342 0x4e, 0x42, 0x2f, 0xeb, 0x0f, 0x63, 0xdb, 0x68, 0x37, 0xa8, 0xcf, 0x8b,
1343 0xab, 0xf5, 0xa4, 0x6e, 0x96, 0x2a, 0xb2, 0xd6, 0xbe, 0x9e, 0xbd, 0x0d,
1344 0xb4, 0x42, 0xa9, 0xcf, 0x01, 0x83, 0x8a, 0x17, 0x47, 0x76, 0xc4, 0xc6,
1345 0x83, 0x04, 0x95, 0x0b, 0xfc, 0x11, 0xc9, 0x62, 0xb8, 0x0c, 0x76, 0x84,
1346 0xd9, 0xb9, 0x37, 0xfa, 0xfc, 0x7c, 0xc2, 0x6d, 0x58, 0x3e, 0xb3, 0x04,
1347 0xbb, 0x8c, 0x8f, 0x48, 0xbc, 0x91, 0x27, 0xcc, 0xf9, 0xb7, 0x22, 0x19,
1348 0x83, 0x2e, 0x09, 0xb5, 0x72, 0xd9, 0x54, 0x1c, 0x4d, 0xa1, 0xea, 0x0b,
1349 0xf1, 0xc6, 0x08, 0x72, 0x46, 0x87, 0x7a, 0x6e, 0x80, 0x56, 0x0a, 0x8a,
1350 0xc0, 0xdd, 0x11, 0x6b, 0xd6, 0xdd, 0x47, 0xdf, 0x10, 0xd9, 0xd8, 0xea,
1351 0x7c, 0xb0, 0x8f, 0x03, 0x00, 0x2e, 0xc1, 0x8f, 0x44, 0xa8, 0xd3, 0x30,
1352 0x06, 0x89, 0xa2, 0xf9, 0x34, 0xad, 0xdc, 0x03, 0x85, 0xed, 0x51, 0xa7,
1353 0x82, 0x9c, 0xe7, 0x5d, 0x52, 0x93, 0x0c, 0x32, 0x9a, 0x5b, 0xe1, 0xaa,
1354 0xca, 0xb8, 0x02, 0x6d, 0x3a, 0xd4, 0xb1, 0x3a, 0xf0, 0x5f, 0xbe, 0xb5,
1355 0x0d, 0x10, 0x6b, 0x38, 0x32, 0xac, 0x76, 0x80, 0xbd, 0xca, 0x94, 0x71,
1356 0x7a, 0xf2, 0xc9, 0x35, 0x2a, 0xde, 0x9f, 0x42, 0x49, 0x18, 0x01, 0xab,
1357 0xbc, 0xef, 0x7c, 0x64, 0x3f, 0x58, 0x3d, 0x92, 0x59, 0xdb, 0x13, 0xdb,
1358 0x58, 0x6e, 0x0a, 0xe0, 0xb7, 0x91, 0x4a, 0x08, 0x20, 0xd6, 0x2e, 0x3c,
1359 0x45, 0xc9, 0x8b, 0x17, 0x79, 0xe7, 0xc7, 0x90, 0x99, 0x3a, 0x18, 0x25,
1360};
1361
1362void x25519_ge_scalarmult_base(ge_p3 *h, const uint8_t a[32]) {
1363 x25519_ge_scalarmult_small_precomp(h, a, k25519SmallPrecomp);
1364}
1365
1366#else
1367
1368/* k25519Precomp[i][j] = (j+1)*256^i*B */
1369static const ge_precomp k25519Precomp[32][8] = {
1370 {
1371 {
1372 {25967493, -14356035, 29566456, 3660896, -12694345, 4014787,
1373 27544626, -11754271, -6079156, 2047605},
1374 {-12545711, 934262, -2722910, 3049990, -727428, 9406986, 12720692,
1375 5043384, 19500929, -15469378},
1376 {-8738181, 4489570, 9688441, -14785194, 10184609, -12363380,
1377 29287919, 11864899, -24514362, -4438546},
1378 },
1379 {
1380 {-12815894, -12976347, -21581243, 11784320, -25355658, -2750717,
1381 -11717903, -3814571, -358445, -10211303},
1382 {-21703237, 6903825, 27185491, 6451973, -29577724, -9554005,
1383 -15616551, 11189268, -26829678, -5319081},
1384 {26966642, 11152617, 32442495, 15396054, 14353839, -12752335,
1385 -3128826, -9541118, -15472047, -4166697},
1386 },
1387 {
1388 {15636291, -9688557, 24204773, -7912398, 616977, -16685262,
1389 27787600, -14772189, 28944400, -1550024},
1390 {16568933, 4717097, -11556148, -1102322, 15682896, -11807043,
1391 16354577, -11775962, 7689662, 11199574},
1392 {30464156, -5976125, -11779434, -15670865, 23220365, 15915852,
1393 7512774, 10017326, -17749093, -9920357},
1394 },
1395 {
1396 {-17036878, 13921892, 10945806, -6033431, 27105052, -16084379,
1397 -28926210, 15006023, 3284568, -6276540},
1398 {23599295, -8306047, -11193664, -7687416, 13236774, 10506355,
1399 7464579, 9656445, 13059162, 10374397},
1400 {7798556, 16710257, 3033922, 2874086, 28997861, 2835604, 32406664,
1401 -3839045, -641708, -101325},
1402 },
1403 {
1404 {10861363, 11473154, 27284546, 1981175, -30064349, 12577861,
1405 32867885, 14515107, -15438304, 10819380},
1406 {4708026, 6336745, 20377586, 9066809, -11272109, 6594696, -25653668,
1407 12483688, -12668491, 5581306},
1408 {19563160, 16186464, -29386857, 4097519, 10237984, -4348115,
1409 28542350, 13850243, -23678021, -15815942},
1410 },
1411 {
1412 {-15371964, -12862754, 32573250, 4720197, -26436522, 5875511,
1413 -19188627, -15224819, -9818940, -12085777},
1414 {-8549212, 109983, 15149363, 2178705, 22900618, 4543417, 3044240,
1415 -15689887, 1762328, 14866737},
1416 {-18199695, -15951423, -10473290, 1707278, -17185920, 3916101,
1417 -28236412, 3959421, 27914454, 4383652},
1418 },
1419 {
1420 {5153746, 9909285, 1723747, -2777874, 30523605, 5516873, 19480852,
1421 5230134, -23952439, -15175766},
1422 {-30269007, -3463509, 7665486, 10083793, 28475525, 1649722,
1423 20654025, 16520125, 30598449, 7715701},
1424 {28881845, 14381568, 9657904, 3680757, -20181635, 7843316,
1425 -31400660, 1370708, 29794553, -1409300},
1426 },
1427 {
1428 {14499471, -2729599, -33191113, -4254652, 28494862, 14271267,
1429 30290735, 10876454, -33154098, 2381726},
1430 {-7195431, -2655363, -14730155, 462251, -27724326, 3941372,
1431 -6236617, 3696005, -32300832, 15351955},
1432 {27431194, 8222322, 16448760, -3907995, -18707002, 11938355,
1433 -32961401, -2970515, 29551813, 10109425},
1434 },
1435 },
1436 {
1437 {
1438 {-13657040, -13155431, -31283750, 11777098, 21447386, 6519384,
1439 -2378284, -1627556, 10092783, -4764171},
1440 {27939166, 14210322, 4677035, 16277044, -22964462, -12398139,
1441 -32508754, 12005538, -17810127, 12803510},
1442 {17228999, -15661624, -1233527, 300140, -1224870, -11714777,
1443 30364213, -9038194, 18016357, 4397660},
1444 },
1445 {
1446 {-10958843, -7690207, 4776341, -14954238, 27850028, -15602212,
1447 -26619106, 14544525, -17477504, 982639},
1448 {29253598, 15796703, -2863982, -9908884, 10057023, 3163536, 7332899,
1449 -4120128, -21047696, 9934963},
1450 {5793303, 16271923, -24131614, -10116404, 29188560, 1206517,
1451 -14747930, 4559895, -30123922, -10897950},
1452 },
1453 {
1454 {-27643952, -11493006, 16282657, -11036493, 28414021, -15012264,
1455 24191034, 4541697, -13338309, 5500568},
1456 {12650548, -1497113, 9052871, 11355358, -17680037, -8400164,
1457 -17430592, 12264343, 10874051, 13524335},
1458 {25556948, -3045990, 714651, 2510400, 23394682, -10415330, 33119038,
1459 5080568, -22528059, 5376628},
1460 },
1461 {
1462 {-26088264, -4011052, -17013699, -3537628, -6726793, 1920897,
1463 -22321305, -9447443, 4535768, 1569007},
1464 {-2255422, 14606630, -21692440, -8039818, 28430649, 8775819,
1465 -30494562, 3044290, 31848280, 12543772},
1466 {-22028579, 2943893, -31857513, 6777306, 13784462, -4292203,
1467 -27377195, -2062731, 7718482, 14474653},
1468 },
1469 {
1470 {2385315, 2454213, -22631320, 46603, -4437935, -15680415, 656965,
1471 -7236665, 24316168, -5253567},
1472 {13741529, 10911568, -33233417, -8603737, -20177830, -1033297,
1473 33040651, -13424532, -20729456, 8321686},
1474 {21060490, -2212744, 15712757, -4336099, 1639040, 10656336,
1475 23845965, -11874838, -9984458, 608372},
1476 },
1477 {
1478 {-13672732, -15087586, -10889693, -7557059, -6036909, 11305547,
1479 1123968, -6780577, 27229399, 23887},
1480 {-23244140, -294205, -11744728, 14712571, -29465699, -2029617,
1481 12797024, -6440308, -1633405, 16678954},
1482 {-29500620, 4770662, -16054387, 14001338, 7830047, 9564805,
1483 -1508144, -4795045, -17169265, 4904953},
1484 },
1485 {
1486 {24059557, 14617003, 19037157, -15039908, 19766093, -14906429,
1487 5169211, 16191880, 2128236, -4326833},
1488 {-16981152, 4124966, -8540610, -10653797, 30336522, -14105247,
1489 -29806336, 916033, -6882542, -2986532},
1490 {-22630907, 12419372, -7134229, -7473371, -16478904, 16739175,
1491 285431, 2763829, 15736322, 4143876},
1492 },
1493 {
1494 {2379352, 11839345, -4110402, -5988665, 11274298, 794957, 212801,
1495 -14594663, 23527084, -16458268},
1496 {33431127, -11130478, -17838966, -15626900, 8909499, 8376530,
1497 -32625340, 4087881, -15188911, -14416214},
1498 {1767683, 7197987, -13205226, -2022635, -13091350, 448826, 5799055,
1499 4357868, -4774191, -16323038},
1500 },
1501 },
1502 {
1503 {
1504 {6721966, 13833823, -23523388, -1551314, 26354293, -11863321,
1505 23365147, -3949732, 7390890, 2759800},
1506 {4409041, 2052381, 23373853, 10530217, 7676779, -12885954, 21302353,
1507 -4264057, 1244380, -12919645},
1508 {-4421239, 7169619, 4982368, -2957590, 30256825, -2777540, 14086413,
1509 9208236, 15886429, 16489664},
1510 },
1511 {
1512 {1996075, 10375649, 14346367, 13311202, -6874135, -16438411,
1513 -13693198, 398369, -30606455, -712933},
1514 {-25307465, 9795880, -2777414, 14878809, -33531835, 14780363,
1515 13348553, 12076947, -30836462, 5113182},
1516 {-17770784, 11797796, 31950843, 13929123, -25888302, 12288344,
1517 -30341101, -7336386, 13847711, 5387222},
1518 },
1519 {
1520 {-18582163, -3416217, 17824843, -2340966, 22744343, -10442611,
1521 8763061, 3617786, -19600662, 10370991},
1522 {20246567, -14369378, 22358229, -543712, 18507283, -10413996,
1523 14554437, -8746092, 32232924, 16763880},
1524 {9648505, 10094563, 26416693, 14745928, -30374318, -6472621,
1525 11094161, 15689506, 3140038, -16510092},
1526 },
1527 {
1528 {-16160072, 5472695, 31895588, 4744994, 8823515, 10365685,
1529 -27224800, 9448613, -28774454, 366295},
1530 {19153450, 11523972, -11096490, -6503142, -24647631, 5420647,
1531 28344573, 8041113, 719605, 11671788},
1532 {8678025, 2694440, -6808014, 2517372, 4964326, 11152271, -15432916,
1533 -15266516, 27000813, -10195553},
1534 },
1535 {
1536 {-15157904, 7134312, 8639287, -2814877, -7235688, 10421742, 564065,
1537 5336097, 6750977, -14521026},
1538 {11836410, -3979488, 26297894, 16080799, 23455045, 15735944,
1539 1695823, -8819122, 8169720, 16220347},
1540 {-18115838, 8653647, 17578566, -6092619, -8025777, -16012763,
1541 -11144307, -2627664, -5990708, -14166033},
1542 },
1543 {
1544 {-23308498, -10968312, 15213228, -10081214, -30853605, -11050004,
1545 27884329, 2847284, 2655861, 1738395},
1546 {-27537433, -14253021, -25336301, -8002780, -9370762, 8129821,
1547 21651608, -3239336, -19087449, -11005278},
1548 {1533110, 3437855, 23735889, 459276, 29970501, 11335377, 26030092,
1549 5821408, 10478196, 8544890},
1550 },
1551 {
1552 {32173121, -16129311, 24896207, 3921497, 22579056, -3410854,
1553 19270449, 12217473, 17789017, -3395995},
1554 {-30552961, -2228401, -15578829, -10147201, 13243889, 517024,
1555 15479401, -3853233, 30460520, 1052596},
1556 {-11614875, 13323618, 32618793, 8175907, -15230173, 12596687,
1557 27491595, -4612359, 3179268, -9478891},
1558 },
1559 {
1560 {31947069, -14366651, -4640583, -15339921, -15125977, -6039709,
1561 -14756777, -16411740, 19072640, -9511060},
1562 {11685058, 11822410, 3158003, -13952594, 33402194, -4165066,
1563 5977896, -5215017, 473099, 5040608},
1564 {-20290863, 8198642, -27410132, 11602123, 1290375, -2799760,
1565 28326862, 1721092, -19558642, -3131606},
1566 },
1567 },
1568 {
1569 {
1570 {7881532, 10687937, 7578723, 7738378, -18951012, -2553952, 21820786,
1571 8076149, -27868496, 11538389},
1572 {-19935666, 3899861, 18283497, -6801568, -15728660, -11249211,
1573 8754525, 7446702, -5676054, 5797016},
1574 {-11295600, -3793569, -15782110, -7964573, 12708869, -8456199,
1575 2014099, -9050574, -2369172, -5877341},
1576 },
1577 {
1578 {-22472376, -11568741, -27682020, 1146375, 18956691, 16640559,
1579 1192730, -3714199, 15123619, 10811505},
1580 {14352098, -3419715, -18942044, 10822655, 32750596, 4699007, -70363,
1581 15776356, -28886779, -11974553},
1582 {-28241164, -8072475, -4978962, -5315317, 29416931, 1847569,
1583 -20654173, -16484855, 4714547, -9600655},
1584 },
1585 {
1586 {15200332, 8368572, 19679101, 15970074, -31872674, 1959451,
1587 24611599, -4543832, -11745876, 12340220},
1588 {12876937, -10480056, 33134381, 6590940, -6307776, 14872440,
1589 9613953, 8241152, 15370987, 9608631},
1590 {-4143277, -12014408, 8446281, -391603, 4407738, 13629032, -7724868,
1591 15866074, -28210621, -8814099},
1592 },
1593 {
1594 {26660628, -15677655, 8393734, 358047, -7401291, 992988, -23904233,
1595 858697, 20571223, 8420556},
1596 {14620715, 13067227, -15447274, 8264467, 14106269, 15080814,
1597 33531827, 12516406, -21574435, -12476749},
1598 {236881, 10476226, 57258, -14677024, 6472998, 2466984, 17258519,
1599 7256740, 8791136, 15069930},
1600 },
1601 {
1602 {1276410, -9371918, 22949635, -16322807, -23493039, -5702186,
1603 14711875, 4874229, -30663140, -2331391},
1604 {5855666, 4990204, -13711848, 7294284, -7804282, 1924647, -1423175,
1605 -7912378, -33069337, 9234253},
1606 {20590503, -9018988, 31529744, -7352666, -2706834, 10650548,
1607 31559055, -11609587, 18979186, 13396066},
1608 },
1609 {
1610 {24474287, 4968103, 22267082, 4407354, 24063882, -8325180,
1611 -18816887, 13594782, 33514650, 7021958},
1612 {-11566906, -6565505, -21365085, 15928892, -26158305, 4315421,
1613 -25948728, -3916677, -21480480, 12868082},
1614 {-28635013, 13504661, 19988037, -2132761, 21078225, 6443208,
1615 -21446107, 2244500, -12455797, -8089383},
1616 },
1617 {
1618 {-30595528, 13793479, -5852820, 319136, -25723172, -6263899,
1619 33086546, 8957937, -15233648, 5540521},
1620 {-11630176, -11503902, -8119500, -7643073, 2620056, 1022908,
1621 -23710744, -1568984, -16128528, -14962807},
1622 {23152971, 775386, 27395463, 14006635, -9701118, 4649512, 1689819,
1623 892185, -11513277, -15205948},
1624 },
1625 {
1626 {9770129, 9586738, 26496094, 4324120, 1556511, -3550024, 27453819,
1627 4763127, -19179614, 5867134},
1628 {-32765025, 1927590, 31726409, -4753295, 23962434, -16019500,
1629 27846559, 5931263, -29749703, -16108455},
1630 {27461885, -2977536, 22380810, 1815854, -23033753, -3031938,
1631 7283490, -15148073, -19526700, 7734629},
1632 },
1633 },
1634 {
1635 {
1636 {-8010264, -9590817, -11120403, 6196038, 29344158, -13430885,
1637 7585295, -3176626, 18549497, 15302069},
1638 {-32658337, -6171222, -7672793, -11051681, 6258878, 13504381,
1639 10458790, -6418461, -8872242, 8424746},
1640 {24687205, 8613276, -30667046, -3233545, 1863892, -1830544,
1641 19206234, 7134917, -11284482, -828919},
1642 },
1643 {
1644 {11334899, -9218022, 8025293, 12707519, 17523892, -10476071,
1645 10243738, -14685461, -5066034, 16498837},
1646 {8911542, 6887158, -9584260, -6958590, 11145641, -9543680, 17303925,
1647 -14124238, 6536641, 10543906},
1648 {-28946384, 15479763, -17466835, 568876, -1497683, 11223454,
1649 -2669190, -16625574, -27235709, 8876771},
1650 },
1651 {
1652 {-25742899, -12566864, -15649966, -846607, -33026686, -796288,
1653 -33481822, 15824474, -604426, -9039817},
1654 {10330056, 70051, 7957388, -9002667, 9764902, 15609756, 27698697,
1655 -4890037, 1657394, 3084098},
1656 {10477963, -7470260, 12119566, -13250805, 29016247, -5365589,
1657 31280319, 14396151, -30233575, 15272409},
1658 },
1659 {
1660 {-12288309, 3169463, 28813183, 16658753, 25116432, -5630466,
1661 -25173957, -12636138, -25014757, 1950504},
1662 {-26180358, 9489187, 11053416, -14746161, -31053720, 5825630,
1663 -8384306, -8767532, 15341279, 8373727},
1664 {28685821, 7759505, -14378516, -12002860, -31971820, 4079242,
1665 298136, -10232602, -2878207, 15190420},
1666 },
1667 {
1668 {-32932876, 13806336, -14337485, -15794431, -24004620, 10940928,
1669 8669718, 2742393, -26033313, -6875003},
1670 {-1580388, -11729417, -25979658, -11445023, -17411874, -10912854,
1671 9291594, -16247779, -12154742, 6048605},
1672 {-30305315, 14843444, 1539301, 11864366, 20201677, 1900163,
1673 13934231, 5128323, 11213262, 9168384},
1674 },
1675 {
1676 {-26280513, 11007847, 19408960, -940758, -18592965, -4328580,
1677 -5088060, -11105150, 20470157, -16398701},
1678 {-23136053, 9282192, 14855179, -15390078, -7362815, -14408560,
1679 -22783952, 14461608, 14042978, 5230683},
1680 {29969567, -2741594, -16711867, -8552442, 9175486, -2468974,
1681 21556951, 3506042, -5933891, -12449708},
1682 },
1683 {
1684 {-3144746, 8744661, 19704003, 4581278, -20430686, 6830683,
1685 -21284170, 8971513, -28539189, 15326563},
1686 {-19464629, 10110288, -17262528, -3503892, -23500387, 1355669,
1687 -15523050, 15300988, -20514118, 9168260},
1688 {-5353335, 4488613, -23803248, 16314347, 7780487, -15638939,
1689 -28948358, 9601605, 33087103, -9011387},
1690 },
1691 {
1692 {-19443170, -15512900, -20797467, -12445323, -29824447, 10229461,
1693 -27444329, -15000531, -5996870, 15664672},
1694 {23294591, -16632613, -22650781, -8470978, 27844204, 11461195,
1695 13099750, -2460356, 18151676, 13417686},
1696 {-24722913, -4176517, -31150679, 5988919, -26858785, 6685065,
1697 1661597, -12551441, 15271676, -15452665},
1698 },
1699 },
1700 {
1701 {
1702 {11433042, -13228665, 8239631, -5279517, -1985436, -725718,
1703 -18698764, 2167544, -6921301, -13440182},
1704 {-31436171, 15575146, 30436815, 12192228, -22463353, 9395379,
1705 -9917708, -8638997, 12215110, 12028277},
1706 {14098400, 6555944, 23007258, 5757252, -15427832, -12950502,
1707 30123440, 4617780, -16900089, -655628},
1708 },
1709 {
1710 {-4026201, -15240835, 11893168, 13718664, -14809462, 1847385,
1711 -15819999, 10154009, 23973261, -12684474},
1712 {-26531820, -3695990, -1908898, 2534301, -31870557, -16550355,
1713 18341390, -11419951, 32013174, -10103539},
1714 {-25479301, 10876443, -11771086, -14625140, -12369567, 1838104,
1715 21911214, 6354752, 4425632, -837822},
1716 },
1717 {
1718 {-10433389, -14612966, 22229858, -3091047, -13191166, 776729,
1719 -17415375, -12020462, 4725005, 14044970},
1720 {19268650, -7304421, 1555349, 8692754, -21474059, -9910664, 6347390,
1721 -1411784, -19522291, -16109756},
1722 {-24864089, 12986008, -10898878, -5558584, -11312371, -148526,
1723 19541418, 8180106, 9282262, 10282508},
1724 },
1725 {
1726 {-26205082, 4428547, -8661196, -13194263, 4098402, -14165257,
1727 15522535, 8372215, 5542595, -10702683},
1728 {-10562541, 14895633, 26814552, -16673850, -17480754, -2489360,
1729 -2781891, 6993761, -18093885, 10114655},
1730 {-20107055, -929418, 31422704, 10427861, -7110749, 6150669,
1731 -29091755, -11529146, 25953725, -106158},
1732 },
1733 {
1734 {-4234397, -8039292, -9119125, 3046000, 2101609, -12607294,
1735 19390020, 6094296, -3315279, 12831125},
1736 {-15998678, 7578152, 5310217, 14408357, -33548620, -224739,
1737 31575954, 6326196, 7381791, -2421839},
1738 {-20902779, 3296811, 24736065, -16328389, 18374254, 7318640,
1739 6295303, 8082724, -15362489, 12339664},
1740 },
1741 {
1742 {27724736, 2291157, 6088201, -14184798, 1792727, 5857634, 13848414,
1743 15768922, 25091167, 14856294},
1744 {-18866652, 8331043, 24373479, 8541013, -701998, -9269457, 12927300,
1745 -12695493, -22182473, -9012899},
1746 {-11423429, -5421590, 11632845, 3405020, 30536730, -11674039,
1747 -27260765, 13866390, 30146206, 9142070},
1748 },
1749 {
1750 {3924129, -15307516, -13817122, -10054960, 12291820, -668366,
1751 -27702774, 9326384, -8237858, 4171294},
1752 {-15921940, 16037937, 6713787, 16606682, -21612135, 2790944,
1753 26396185, 3731949, 345228, -5462949},
1754 {-21327538, 13448259, 25284571, 1143661, 20614966, -8849387,
1755 2031539, -12391231, -16253183, -13582083},
1756 },
1757 {
1758 {31016211, -16722429, 26371392, -14451233, -5027349, 14854137,
1759 17477601, 3842657, 28012650, -16405420},
1760 {-5075835, 9368966, -8562079, -4600902, -15249953, 6970560,
1761 -9189873, 16292057, -8867157, 3507940},
1762 {29439664, 3537914, 23333589, 6997794, -17555561, -11018068,
1763 -15209202, -15051267, -9164929, 6580396},
1764 },
1765 },
1766 {
1767 {
1768 {-12185861, -7679788, 16438269, 10826160, -8696817, -6235611,
1769 17860444, -9273846, -2095802, 9304567},
1770 {20714564, -4336911, 29088195, 7406487, 11426967, -5095705,
1771 14792667, -14608617, 5289421, -477127},
1772 {-16665533, -10650790, -6160345, -13305760, 9192020, -1802462,
1773 17271490, 12349094, 26939669, -3752294},
1774 },
1775 {
1776 {-12889898, 9373458, 31595848, 16374215, 21471720, 13221525,
1777 -27283495, -12348559, -3698806, 117887},
1778 {22263325, -6560050, 3984570, -11174646, -15114008, -566785,
1779 28311253, 5358056, -23319780, 541964},
1780 {16259219, 3261970, 2309254, -15534474, -16885711, -4581916,
1781 24134070, -16705829, -13337066, -13552195},
1782 },
1783 {
1784 {9378160, -13140186, -22845982, -12745264, 28198281, -7244098,
1785 -2399684, -717351, 690426, 14876244},
1786 {24977353, -314384, -8223969, -13465086, 28432343, -1176353,
1787 -13068804, -12297348, -22380984, 6618999},
1788 {-1538174, 11685646, 12944378, 13682314, -24389511, -14413193,
1789 8044829, -13817328, 32239829, -5652762},
1790 },
1791 {
1792 {-18603066, 4762990, -926250, 8885304, -28412480, -3187315, 9781647,
1793 -10350059, 32779359, 5095274},
1794 {-33008130, -5214506, -32264887, -3685216, 9460461, -9327423,
1795 -24601656, 14506724, 21639561, -2630236},
1796 {-16400943, -13112215, 25239338, 15531969, 3987758, -4499318,
1797 -1289502, -6863535, 17874574, 558605},
1798 },
1799 {
1800 {-13600129, 10240081, 9171883, 16131053, -20869254, 9599700,
1801 33499487, 5080151, 2085892, 5119761},
1802 {-22205145, -2519528, -16381601, 414691, -25019550, 2170430,
1803 30634760, -8363614, -31999993, -5759884},
1804 {-6845704, 15791202, 8550074, -1312654, 29928809, -12092256,
1805 27534430, -7192145, -22351378, 12961482},
1806 },
1807 {
1808 {-24492060, -9570771, 10368194, 11582341, -23397293, -2245287,
1809 16533930, 8206996, -30194652, -5159638},
1810 {-11121496, -3382234, 2307366, 6362031, -135455, 8868177, -16835630,
1811 7031275, 7589640, 8945490},
1812 {-32152748, 8917967, 6661220, -11677616, -1192060, -15793393,
1813 7251489, -11182180, 24099109, -14456170},
1814 },
1815 {
1816 {5019558, -7907470, 4244127, -14714356, -26933272, 6453165,
1817 -19118182, -13289025, -6231896, -10280736},
1818 {10853594, 10721687, 26480089, 5861829, -22995819, 1972175,
1819 -1866647, -10557898, -3363451, -6441124},
1820 {-17002408, 5906790, 221599, -6563147, 7828208, -13248918, 24362661,
1821 -2008168, -13866408, 7421392},
1822 },
1823 {
1824 {8139927, -6546497, 32257646, -5890546, 30375719, 1886181,
1825 -21175108, 15441252, 28826358, -4123029},
1826 {6267086, 9695052, 7709135, -16603597, -32869068, -1886135,
1827 14795160, -7840124, 13746021, -1742048},
1828 {28584902, 7787108, -6732942, -15050729, 22846041, -7571236,
1829 -3181936, -363524, 4771362, -8419958},
1830 },
1831 },
1832 {
1833 {
1834 {24949256, 6376279, -27466481, -8174608, -18646154, -9930606,
1835 33543569, -12141695, 3569627, 11342593},
1836 {26514989, 4740088, 27912651, 3697550, 19331575, -11472339, 6809886,
1837 4608608, 7325975, -14801071},
1838 {-11618399, -14554430, -24321212, 7655128, -1369274, 5214312,
1839 -27400540, 10258390, -17646694, -8186692},
1840 },
1841 {
1842 {11431204, 15823007, 26570245, 14329124, 18029990, 4796082,
1843 -31446179, 15580664, 9280358, -3973687},
1844 {-160783, -10326257, -22855316, -4304997, -20861367, -13621002,
1845 -32810901, -11181622, -15545091, 4387441},
1846 {-20799378, 12194512, 3937617, -5805892, -27154820, 9340370,
1847 -24513992, 8548137, 20617071, -7482001},
1848 },
1849 {
1850 {-938825, -3930586, -8714311, 16124718, 24603125, -6225393,
1851 -13775352, -11875822, 24345683, 10325460},
1852 {-19855277, -1568885, -22202708, 8714034, 14007766, 6928528,
1853 16318175, -1010689, 4766743, 3552007},
1854 {-21751364, -16730916, 1351763, -803421, -4009670, 3950935, 3217514,
1855 14481909, 10988822, -3994762},
1856 },
1857 {
1858 {15564307, -14311570, 3101243, 5684148, 30446780, -8051356,
1859 12677127, -6505343, -8295852, 13296005},
1860 {-9442290, 6624296, -30298964, -11913677, -4670981, -2057379,
1861 31521204, 9614054, -30000824, 12074674},
1862 {4771191, -135239, 14290749, -13089852, 27992298, 14998318,
1863 -1413936, -1556716, 29832613, -16391035},
1864 },
1865 {
1866 {7064884, -7541174, -19161962, -5067537, -18891269, -2912736,
1867 25825242, 5293297, -27122660, 13101590},
1868 {-2298563, 2439670, -7466610, 1719965, -27267541, -16328445,
1869 32512469, -5317593, -30356070, -4190957},
1870 {-30006540, 10162316, -33180176, 3981723, -16482138, -13070044,
1871 14413974, 9515896, 19568978, 9628812},
1872 },
1873 {
1874 {33053803, 199357, 15894591, 1583059, 27380243, -4580435, -17838894,
1875 -6106839, -6291786, 3437740},
1876 {-18978877, 3884493, 19469877, 12726490, 15913552, 13614290,
1877 -22961733, 70104, 7463304, 4176122},
1878 {-27124001, 10659917, 11482427, -16070381, 12771467, -6635117,
1879 -32719404, -5322751, 24216882, 5944158},
1880 },
1881 {
1882 {8894125, 7450974, -2664149, -9765752, -28080517, -12389115,
1883 19345746, 14680796, 11632993, 5847885},
1884 {26942781, -2315317, 9129564, -4906607, 26024105, 11769399,
1885 -11518837, 6367194, -9727230, 4782140},
1886 {19916461, -4828410, -22910704, -11414391, 25606324, -5972441,
1887 33253853, 8220911, 6358847, -1873857},
1888 },
1889 {
1890 {801428, -2081702, 16569428, 11065167, 29875704, 96627, 7908388,
1891 -4480480, -13538503, 1387155},
1892 {19646058, 5720633, -11416706, 12814209, 11607948, 12749789,
1893 14147075, 15156355, -21866831, 11835260},
1894 {19299512, 1155910, 28703737, 14890794, 2925026, 7269399, 26121523,
1895 15467869, -26560550, 5052483},
1896 },
1897 },
1898 {
1899 {
1900 {-3017432, 10058206, 1980837, 3964243, 22160966, 12322533, -6431123,
1901 -12618185, 12228557, -7003677},
1902 {32944382, 14922211, -22844894, 5188528, 21913450, -8719943,
1903 4001465, 13238564, -6114803, 8653815},
1904 {22865569, -4652735, 27603668, -12545395, 14348958, 8234005,
1905 24808405, 5719875, 28483275, 2841751},
1906 },
1907 {
1908 {-16420968, -1113305, -327719, -12107856, 21886282, -15552774,
1909 -1887966, -315658, 19932058, -12739203},
1910 {-11656086, 10087521, -8864888, -5536143, -19278573, -3055912,
1911 3999228, 13239134, -4777469, -13910208},
1912 {1382174, -11694719, 17266790, 9194690, -13324356, 9720081,
1913 20403944, 11284705, -14013818, 3093230},
1914 },
1915 {
1916 {16650921, -11037932, -1064178, 1570629, -8329746, 7352753, -302424,
1917 16271225, -24049421, -6691850},
1918 {-21911077, -5927941, -4611316, -5560156, -31744103, -10785293,
1919 24123614, 15193618, -21652117, -16739389},
1920 {-9935934, -4289447, -25279823, 4372842, 2087473, 10399484,
1921 31870908, 14690798, 17361620, 11864968},
1922 },
1923 {
1924 {-11307610, 6210372, 13206574, 5806320, -29017692, -13967200,
1925 -12331205, -7486601, -25578460, -16240689},
1926 {14668462, -12270235, 26039039, 15305210, 25515617, 4542480,
1927 10453892, 6577524, 9145645, -6443880},
1928 {5974874, 3053895, -9433049, -10385191, -31865124, 3225009,
1929 -7972642, 3936128, -5652273, -3050304},
1930 },
1931 {
1932 {30625386, -4729400, -25555961, -12792866, -20484575, 7695099,
1933 17097188, -16303496, -27999779, 1803632},
1934 {-3553091, 9865099, -5228566, 4272701, -5673832, -16689700,
1935 14911344, 12196514, -21405489, 7047412},
1936 {20093277, 9920966, -11138194, -5343857, 13161587, 12044805,
1937 -32856851, 4124601, -32343828, -10257566},
1938 },
1939 {
1940 {-20788824, 14084654, -13531713, 7842147, 19119038, -13822605,
1941 4752377, -8714640, -21679658, 2288038},
1942 {-26819236, -3283715, 29965059, 3039786, -14473765, 2540457,
1943 29457502, 14625692, -24819617, 12570232},
1944 {-1063558, -11551823, 16920318, 12494842, 1278292, -5869109,
1945 -21159943, -3498680, -11974704, 4724943},
1946 },
1947 {
1948 {17960970, -11775534, -4140968, -9702530, -8876562, -1410617,
1949 -12907383, -8659932, -29576300, 1903856},
1950 {23134274, -14279132, -10681997, -1611936, 20684485, 15770816,
1951 -12989750, 3190296, 26955097, 14109738},
1952 {15308788, 5320727, -30113809, -14318877, 22902008, 7767164,
1953 29425325, -11277562, 31960942, 11934971},
1954 },
1955 {
1956 {-27395711, 8435796, 4109644, 12222639, -24627868, 14818669,
1957 20638173, 4875028, 10491392, 1379718},
1958 {-13159415, 9197841, 3875503, -8936108, -1383712, -5879801,
1959 33518459, 16176658, 21432314, 12180697},
1960 {-11787308, 11500838, 13787581, -13832590, -22430679, 10140205,
1961 1465425, 12689540, -10301319, -13872883},
1962 },
1963 },
1964 {
1965 {
1966 {5414091, -15386041, -21007664, 9643570, 12834970, 1186149,
1967 -2622916, -1342231, 26128231, 6032912},
1968 {-26337395, -13766162, 32496025, -13653919, 17847801, -12669156,
1969 3604025, 8316894, -25875034, -10437358},
1970 {3296484, 6223048, 24680646, -12246460, -23052020, 5903205,
1971 -8862297, -4639164, 12376617, 3188849},
1972 },
1973 {
1974 {29190488, -14659046, 27549113, -1183516, 3520066, -10697301,
1975 32049515, -7309113, -16109234, -9852307},
1976 {-14744486, -9309156, 735818, -598978, -20407687, -5057904,
1977 25246078, -15795669, 18640741, -960977},
1978 {-6928835, -16430795, 10361374, 5642961, 4910474, 12345252,
1979 -31638386, -494430, 10530747, 1053335},
1980 },
1981 {
1982 {-29265967, -14186805, -13538216, -12117373, -19457059, -10655384,
1983 -31462369, -2948985, 24018831, 15026644},
1984 {-22592535, -3145277, -2289276, 5953843, -13440189, 9425631,
1985 25310643, 13003497, -2314791, -15145616},
1986 {-27419985, -603321, -8043984, -1669117, -26092265, 13987819,
1987 -27297622, 187899, -23166419, -2531735},
1988 },
1989 {
1990 {-21744398, -13810475, 1844840, 5021428, -10434399, -15911473,
1991 9716667, 16266922, -5070217, 726099},
1992 {29370922, -6053998, 7334071, -15342259, 9385287, 2247707,
1993 -13661962, -4839461, 30007388, -15823341},
1994 {-936379, 16086691, 23751945, -543318, -1167538, -5189036, 9137109,
1995 730663, 9835848, 4555336},
1996 },
1997 {
1998 {-23376435, 1410446, -22253753, -12899614, 30867635, 15826977,
1999 17693930, 544696, -11985298, 12422646},
2000 {31117226, -12215734, -13502838, 6561947, -9876867, -12757670,
2001 -5118685, -4096706, 29120153, 13924425},
2002 {-17400879, -14233209, 19675799, -2734756, -11006962, -5858820,
2003 -9383939, -11317700, 7240931, -237388},
2004 },
2005 {
2006 {-31361739, -11346780, -15007447, -5856218, -22453340, -12152771,
2007 1222336, 4389483, 3293637, -15551743},
2008 {-16684801, -14444245, 11038544, 11054958, -13801175, -3338533,
2009 -24319580, 7733547, 12796905, -6335822},
2010 {-8759414, -10817836, -25418864, 10783769, -30615557, -9746811,
2011 -28253339, 3647836, 3222231, -11160462},
2012 },
2013 {
2014 {18606113, 1693100, -25448386, -15170272, 4112353, 10045021,
2015 23603893, -2048234, -7550776, 2484985},
2016 {9255317, -3131197, -12156162, -1004256, 13098013, -9214866,
2017 16377220, -2102812, -19802075, -3034702},
2018 {-22729289, 7496160, -5742199, 11329249, 19991973, -3347502,
2019 -31718148, 9936966, -30097688, -10618797},
2020 },
2021 {
2022 {21878590, -5001297, 4338336, 13643897, -3036865, 13160960,
2023 19708896, 5415497, -7360503, -4109293},
2024 {27736861, 10103576, 12500508, 8502413, -3413016, -9633558,
2025 10436918, -1550276, -23659143, -8132100},
2026 {19492550, -12104365, -29681976, -852630, -3208171, 12403437,
2027 30066266, 8367329, 13243957, 8709688},
2028 },
2029 },
2030 {
2031 {
2032 {12015105, 2801261, 28198131, 10151021, 24818120, -4743133,
2033 -11194191, -5645734, 5150968, 7274186},
2034 {2831366, -12492146, 1478975, 6122054, 23825128, -12733586,
2035 31097299, 6083058, 31021603, -9793610},
2036 {-2529932, -2229646, 445613, 10720828, -13849527, -11505937,
2037 -23507731, 16354465, 15067285, -14147707},
2038 },
2039 {
2040 {7840942, 14037873, -33364863, 15934016, -728213, -3642706,
2041 21403988, 1057586, -19379462, -12403220},
2042 {915865, -16469274, 15608285, -8789130, -24357026, 6060030,
2043 -17371319, 8410997, -7220461, 16527025},
2044 {32922597, -556987, 20336074, -16184568, 10903705, -5384487,
2045 16957574, 52992, 23834301, 6588044},
2046 },
2047 {
2048 {32752030, 11232950, 3381995, -8714866, 22652988, -10744103,
2049 17159699, 16689107, -20314580, -1305992},
2050 {-4689649, 9166776, -25710296, -10847306, 11576752, 12733943,
2051 7924251, -2752281, 1976123, -7249027},
2052 {21251222, 16309901, -2983015, -6783122, 30810597, 12967303, 156041,
2053 -3371252, 12331345, -8237197},
2054 },
2055 {
2056 {8651614, -4477032, -16085636, -4996994, 13002507, 2950805,
2057 29054427, -5106970, 10008136, -4667901},
2058 {31486080, 15114593, -14261250, 12951354, 14369431, -7387845,
2059 16347321, -13662089, 8684155, -10532952},
2060 {19443825, 11385320, 24468943, -9659068, -23919258, 2187569,
2061 -26263207, -6086921, 31316348, 14219878},
2062 },
2063 {
2064 {-28594490, 1193785, 32245219, 11392485, 31092169, 15722801,
2065 27146014, 6992409, 29126555, 9207390},
2066 {32382935, 1110093, 18477781, 11028262, -27411763, -7548111,
2067 -4980517, 10843782, -7957600, -14435730},
2068 {2814918, 7836403, 27519878, -7868156, -20894015, -11553689,
2069 -21494559, 8550130, 28346258, 1994730},
2070 },
2071 {
2072 {-19578299, 8085545, -14000519, -3948622, 2785838, -16231307,
2073 -19516951, 7174894, 22628102, 8115180},
2074 {-30405132, 955511, -11133838, -15078069, -32447087, -13278079,
2075 -25651578, 3317160, -9943017, 930272},
2076 {-15303681, -6833769, 28856490, 1357446, 23421993, 1057177,
2077 24091212, -1388970, -22765376, -10650715},
2078 },
2079 {
2080 {-22751231, -5303997, -12907607, -12768866, -15811511, -7797053,
2081 -14839018, -16554220, -1867018, 8398970},
2082 {-31969310, 2106403, -4736360, 1362501, 12813763, 16200670,
2083 22981545, -6291273, 18009408, -15772772},
2084 {-17220923, -9545221, -27784654, 14166835, 29815394, 7444469,
2085 29551787, -3727419, 19288549, 1325865},
2086 },
2087 {
2088 {15100157, -15835752, -23923978, -1005098, -26450192, 15509408,
2089 12376730, -3479146, 33166107, -8042750},
2090 {20909231, 13023121, -9209752, 16251778, -5778415, -8094914,
2091 12412151, 10018715, 2213263, -13878373},
2092 {32529814, -11074689, 30361439, -16689753, -9135940, 1513226,
2093 22922121, 6382134, -5766928, 8371348},
2094 },
2095 },
2096 {
2097 {
2098 {9923462, 11271500, 12616794, 3544722, -29998368, -1721626,
2099 12891687, -8193132, -26442943, 10486144},
2100 {-22597207, -7012665, 8587003, -8257861, 4084309, -12970062, 361726,
2101 2610596, -23921530, -11455195},
2102 {5408411, -1136691, -4969122, 10561668, 24145918, 14240566,
2103 31319731, -4235541, 19985175, -3436086},
2104 },
2105 {
2106 {-13994457, 16616821, 14549246, 3341099, 32155958, 13648976,
2107 -17577068, 8849297, 65030, 8370684},
2108 {-8320926, -12049626, 31204563, 5839400, -20627288, -1057277,
2109 -19442942, 6922164, 12743482, -9800518},
2110 {-2361371, 12678785, 28815050, 4759974, -23893047, 4884717,
2111 23783145, 11038569, 18800704, 255233},
2112 },
2113 {
2114 {-5269658, -1773886, 13957886, 7990715, 23132995, 728773, 13393847,
2115 9066957, 19258688, -14753793},
2116 {-2936654, -10827535, -10432089, 14516793, -3640786, 4372541,
2117 -31934921, 2209390, -1524053, 2055794},
2118 {580882, 16705327, 5468415, -2683018, -30926419, -14696000,
2119 -7203346, -8994389, -30021019, 7394435},
2120 },
2121 {
2122 {23838809, 1822728, -15738443, 15242727, 8318092, -3733104,
2123 -21672180, -3492205, -4821741, 14799921},
2124 {13345610, 9759151, 3371034, -16137791, 16353039, 8577942, 31129804,
2125 13496856, -9056018, 7402518},
2126 {2286874, -4435931, -20042458, -2008336, -13696227, 5038122,
2127 11006906, -15760352, 8205061, 1607563},
2128 },
2129 {
2130 {14414086, -8002132, 3331830, -3208217, 22249151, -5594188,
2131 18364661, -2906958, 30019587, -9029278},
2132 {-27688051, 1585953, -10775053, 931069, -29120221, -11002319,
2133 -14410829, 12029093, 9944378, 8024},
2134 {4368715, -3709630, 29874200, -15022983, -20230386, -11410704,
2135 -16114594, -999085, -8142388, 5640030},
2136 },
2137 {
2138 {10299610, 13746483, 11661824, 16234854, 7630238, 5998374, 9809887,
2139 -16694564, 15219798, -14327783},
2140 {27425505, -5719081, 3055006, 10660664, 23458024, 595578, -15398605,
2141 -1173195, -18342183, 9742717},
2142 {6744077, 2427284, 26042789, 2720740, -847906, 1118974, 32324614,
2143 7406442, 12420155, 1994844},
2144 },
2145 {
2146 {14012521, -5024720, -18384453, -9578469, -26485342, -3936439,
2147 -13033478, -10909803, 24319929, -6446333},
2148 {16412690, -4507367, 10772641, 15929391, -17068788, -4658621,
2149 10555945, -10484049, -30102368, -4739048},
2150 {22397382, -7767684, -9293161, -12792868, 17166287, -9755136,
2151 -27333065, 6199366, 21880021, -12250760},
2152 },
2153 {
2154 {-4283307, 5368523, -31117018, 8163389, -30323063, 3209128,
2155 16557151, 8890729, 8840445, 4957760},
2156 {-15447727, 709327, -6919446, -10870178, -29777922, 6522332,
2157 -21720181, 12130072, -14796503, 5005757},
2158 {-2114751, -14308128, 23019042, 15765735, -25269683, 6002752,
2159 10183197, -13239326, -16395286, -2176112},
2160 },
2161 },
2162 {
2163 {
2164 {-19025756, 1632005, 13466291, -7995100, -23640451, 16573537,
2165 -32013908, -3057104, 22208662, 2000468},
2166 {3065073, -1412761, -25598674, -361432, -17683065, -5703415,
2167 -8164212, 11248527, -3691214, -7414184},
2168 {10379208, -6045554, 8877319, 1473647, -29291284, -12507580,
2169 16690915, 2553332, -3132688, 16400289},
2170 },
2171 {
2172 {15716668, 1254266, -18472690, 7446274, -8448918, 6344164,
2173 -22097271, -7285580, 26894937, 9132066},
2174 {24158887, 12938817, 11085297, -8177598, -28063478, -4457083,
2175 -30576463, 64452, -6817084, -2692882},
2176 {13488534, 7794716, 22236231, 5989356, 25426474, -12578208, 2350710,
2177 -3418511, -4688006, 2364226},
2178 },
2179 {
2180 {16335052, 9132434, 25640582, 6678888, 1725628, 8517937, -11807024,
2181 -11697457, 15445875, -7798101},
2182 {29004207, -7867081, 28661402, -640412, -12794003, -7943086,
2183 31863255, -4135540, -278050, -15759279},
2184 {-6122061, -14866665, -28614905, 14569919, -10857999, -3591829,
2185 10343412, -6976290, -29828287, -10815811},
2186 },
2187 {
2188 {27081650, 3463984, 14099042, -4517604, 1616303, -6205604, 29542636,
2189 15372179, 17293797, 960709},
2190 {20263915, 11434237, -5765435, 11236810, 13505955, -10857102,
2191 -16111345, 6493122, -19384511, 7639714},
2192 {-2830798, -14839232, 25403038, -8215196, -8317012, -16173699,
2193 18006287, -16043750, 29994677, -15808121},
2194 },
2195 {
2196 {9769828, 5202651, -24157398, -13631392, -28051003, -11561624,
2197 -24613141, -13860782, -31184575, 709464},
2198 {12286395, 13076066, -21775189, -1176622, -25003198, 4057652,
2199 -32018128, -8890874, 16102007, 13205847},
2200 {13733362, 5599946, 10557076, 3195751, -5557991, 8536970, -25540170,
2201 8525972, 10151379, 10394400},
2202 },
2203 {
2204 {4024660, -16137551, 22436262, 12276534, -9099015, -2686099,
2205 19698229, 11743039, -33302334, 8934414},
2206 {-15879800, -4525240, -8580747, -2934061, 14634845, -698278,
2207 -9449077, 3137094, -11536886, 11721158},
2208 {17555939, -5013938, 8268606, 2331751, -22738815, 9761013, 9319229,
2209 8835153, -9205489, -1280045},
2210 },
2211 {
2212 {-461409, -7830014, 20614118, 16688288, -7514766, -4807119,
2213 22300304, 505429, 6108462, -6183415},
2214 {-5070281, 12367917, -30663534, 3234473, 32617080, -8422642,
2215 29880583, -13483331, -26898490, -7867459},
2216 {-31975283, 5726539, 26934134, 10237677, -3173717, -605053,
2217 24199304, 3795095, 7592688, -14992079},
2218 },
2219 {
2220 {21594432, -14964228, 17466408, -4077222, 32537084, 2739898,
2221 6407723, 12018833, -28256052, 4298412},
2222 {-20650503, -11961496, -27236275, 570498, 3767144, -1717540,
2223 13891942, -1569194, 13717174, 10805743},
2224 {-14676630, -15644296, 15287174, 11927123, 24177847, -8175568,
2225 -796431, 14860609, -26938930, -5863836},
2226 },
2227 },
2228 {
2229 {
2230 {12962541, 5311799, -10060768, 11658280, 18855286, -7954201,
2231 13286263, -12808704, -4381056, 9882022},
2232 {18512079, 11319350, -20123124, 15090309, 18818594, 5271736,
2233 -22727904, 3666879, -23967430, -3299429},
2234 {-6789020, -3146043, 16192429, 13241070, 15898607, -14206114,
2235 -10084880, -6661110, -2403099, 5276065},
2236 },
2237 {
2238 {30169808, -5317648, 26306206, -11750859, 27814964, 7069267,
2239 7152851, 3684982, 1449224, 13082861},
2240 {10342826, 3098505, 2119311, 193222, 25702612, 12233820, 23697382,
2241 15056736, -21016438, -8202000},
2242 {-33150110, 3261608, 22745853, 7948688, 19370557, -15177665,
2243 -26171976, 6482814, -10300080, -11060101},
2244 },
2245 {
2246 {32869458, -5408545, 25609743, 15678670, -10687769, -15471071,
2247 26112421, 2521008, -22664288, 6904815},
2248 {29506923, 4457497, 3377935, -9796444, -30510046, 12935080, 1561737,
2249 3841096, -29003639, -6657642},
2250 {10340844, -6630377, -18656632, -2278430, 12621151, -13339055,
2251 30878497, -11824370, -25584551, 5181966},
2252 },
2253 {
2254 {25940115, -12658025, 17324188, -10307374, -8671468, 15029094,
2255 24396252, -16450922, -2322852, -12388574},
2256 {-21765684, 9916823, -1300409, 4079498, -1028346, 11909559, 1782390,
2257 12641087, 20603771, -6561742},
2258 {-18882287, -11673380, 24849422, 11501709, 13161720, -4768874,
2259 1925523, 11914390, 4662781, 7820689},
2260 },
2261 {
2262 {12241050, -425982, 8132691, 9393934, 32846760, -1599620, 29749456,
2263 12172924, 16136752, 15264020},
2264 {-10349955, -14680563, -8211979, 2330220, -17662549, -14545780,
2265 10658213, 6671822, 19012087, 3772772},
2266 {3753511, -3421066, 10617074, 2028709, 14841030, -6721664, 28718732,
2267 -15762884, 20527771, 12988982},
2268 },
2269 {
2270 {-14822485, -5797269, -3707987, 12689773, -898983, -10914866,
2271 -24183046, -10564943, 3299665, -12424953},
2272 {-16777703, -15253301, -9642417, 4978983, 3308785, 8755439, 6943197,
2273 6461331, -25583147, 8991218},
2274 {-17226263, 1816362, -1673288, -6086439, 31783888, -8175991,
2275 -32948145, 7417950, -30242287, 1507265},
2276 },
2277 {
2278 {29692663, 6829891, -10498800, 4334896, 20945975, -11906496,
2279 -28887608, 8209391, 14606362, -10647073},
2280 {-3481570, 8707081, 32188102, 5672294, 22096700, 1711240, -33020695,
2281 9761487, 4170404, -2085325},
2282 {-11587470, 14855945, -4127778, -1531857, -26649089, 15084046,
2283 22186522, 16002000, -14276837, -8400798},
2284 },
2285 {
2286 {-4811456, 13761029, -31703877, -2483919, -3312471, 7869047,
2287 -7113572, -9620092, 13240845, 10965870},
2288 {-7742563, -8256762, -14768334, -13656260, -23232383, 12387166,
2289 4498947, 14147411, 29514390, 4302863},
2290 {-13413405, -12407859, 20757302, -13801832, 14785143, 8976368,
2291 -5061276, -2144373, 17846988, -13971927},
2292 },
2293 },
2294 {
2295 {
2296 {-2244452, -754728, -4597030, -1066309, -6247172, 1455299,
2297 -21647728, -9214789, -5222701, 12650267},
2298 {-9906797, -16070310, 21134160, 12198166, -27064575, 708126, 387813,
2299 13770293, -19134326, 10958663},
2300 {22470984, 12369526, 23446014, -5441109, -21520802, -9698723,
2301 -11772496, -11574455, -25083830, 4271862},
2302 },
2303 {
2304 {-25169565, -10053642, -19909332, 15361595, -5984358, 2159192,
2305 75375, -4278529, -32526221, 8469673},
2306 {15854970, 4148314, -8893890, 7259002, 11666551, 13824734,
2307 -30531198, 2697372, 24154791, -9460943},
2308 {15446137, -15806644, 29759747, 14019369, 30811221, -9610191,
2309 -31582008, 12840104, 24913809, 9815020},
2310 },
2311 {
2312 {-4709286, -5614269, -31841498, -12288893, -14443537, 10799414,
2313 -9103676, 13438769, 18735128, 9466238},
2314 {11933045, 9281483, 5081055, -5183824, -2628162, -4905629, -7727821,
2315 -10896103, -22728655, 16199064},
2316 {14576810, 379472, -26786533, -8317236, -29426508, -10812974,
2317 -102766, 1876699, 30801119, 2164795},
2318 },
2319 {
2320 {15995086, 3199873, 13672555, 13712240, -19378835, -4647646,
2321 -13081610, -15496269, -13492807, 1268052},
2322 {-10290614, -3659039, -3286592, 10948818, 23037027, 3794475,
2323 -3470338, -12600221, -17055369, 3565904},
2324 {29210088, -9419337, -5919792, -4952785, 10834811, -13327726,
2325 -16512102, -10820713, -27162222, -14030531},
2326 },
2327 {
2328 {-13161890, 15508588, 16663704, -8156150, -28349942, 9019123,
2329 -29183421, -3769423, 2244111, -14001979},
2330 {-5152875, -3800936, -9306475, -6071583, 16243069, 14684434,
2331 -25673088, -16180800, 13491506, 4641841},
2332 {10813417, 643330, -19188515, -728916, 30292062, -16600078,
2333 27548447, -7721242, 14476989, -12767431},
2334 },
2335 {
2336 {10292079, 9984945, 6481436, 8279905, -7251514, 7032743, 27282937,
2337 -1644259, -27912810, 12651324},
2338 {-31185513, -813383, 22271204, 11835308, 10201545, 15351028,
2339 17099662, 3988035, 21721536, -3148940},
2340 {10202177, -6545839, -31373232, -9574638, -32150642, -8119683,
2341 -12906320, 3852694, 13216206, 14842320},
2342 },
2343 {
2344 {-15815640, -10601066, -6538952, -7258995, -6984659, -6581778,
2345 -31500847, 13765824, -27434397, 9900184},
2346 {14465505, -13833331, -32133984, -14738873, -27443187, 12990492,
2347 33046193, 15796406, -7051866, -8040114},
2348 {30924417, -8279620, 6359016, -12816335, 16508377, 9071735,
2349 -25488601, 15413635, 9524356, -7018878},
2350 },
2351 {
2352 {12274201, -13175547, 32627641, -1785326, 6736625, 13267305,
2353 5237659, -5109483, 15663516, 4035784},
2354 {-2951309, 8903985, 17349946, 601635, -16432815, -4612556,
2355 -13732739, -15889334, -22258478, 4659091},
2356 {-16916263, -4952973, -30393711, -15158821, 20774812, 15897498,
2357 5736189, 15026997, -2178256, -13455585},
2358 },
2359 },
2360 {
2361 {
2362 {-8858980, -2219056, 28571666, -10155518, -474467, -10105698,
2363 -3801496, 278095, 23440562, -290208},
2364 {10226241, -5928702, 15139956, 120818, -14867693, 5218603, 32937275,
2365 11551483, -16571960, -7442864},
2366 {17932739, -12437276, -24039557, 10749060, 11316803, 7535897,
2367 22503767, 5561594, -3646624, 3898661},
2368 },
2369 {
2370 {7749907, -969567, -16339731, -16464, -25018111, 15122143, -1573531,
2371 7152530, 21831162, 1245233},
2372 {26958459, -14658026, 4314586, 8346991, -5677764, 11960072,
2373 -32589295, -620035, -30402091, -16716212},
2374 {-12165896, 9166947, 33491384, 13673479, 29787085, 13096535,
2375 6280834, 14587357, -22338025, 13987525},
2376 },
2377 {
2378 {-24349909, 7778775, 21116000, 15572597, -4833266, -5357778,
2379 -4300898, -5124639, -7469781, -2858068},
2380 {9681908, -6737123, -31951644, 13591838, -6883821, 386950, 31622781,
2381 6439245, -14581012, 4091397},
2382 {-8426427, 1470727, -28109679, -1596990, 3978627, -5123623,
2383 -19622683, 12092163, 29077877, -14741988},
2384 },
2385 {
2386 {5269168, -6859726, -13230211, -8020715, 25932563, 1763552,
2387 -5606110, -5505881, -20017847, 2357889},
2388 {32264008, -15407652, -5387735, -1160093, -2091322, -3946900,
2389 23104804, -12869908, 5727338, 189038},
2390 {14609123, -8954470, -6000566, -16622781, -14577387, -7743898,
2391 -26745169, 10942115, -25888931, -14884697},
2392 },
2393 {
2394 {20513500, 5557931, -15604613, 7829531, 26413943, -2019404,
2395 -21378968, 7471781, 13913677, -5137875},
2396 {-25574376, 11967826, 29233242, 12948236, -6754465, 4713227,
2397 -8940970, 14059180, 12878652, 8511905},
2398 {-25656801, 3393631, -2955415, -7075526, -2250709, 9366908,
2399 -30223418, 6812974, 5568676, -3127656},
2400 },
2401 {
2402 {11630004, 12144454, 2116339, 13606037, 27378885, 15676917,
2403 -17408753, -13504373, -14395196, 8070818},
2404 {27117696, -10007378, -31282771, -5570088, 1127282, 12772488,
2405 -29845906, 10483306, -11552749, -1028714},
2406 {10637467, -5688064, 5674781, 1072708, -26343588, -6982302,
2407 -1683975, 9177853, -27493162, 15431203},
2408 },
2409 {
2410 {20525145, 10892566, -12742472, 12779443, -29493034, 16150075,
2411 -28240519, 14943142, -15056790, -7935931},
2412 {-30024462, 5626926, -551567, -9981087, 753598, 11981191, 25244767,
2413 -3239766, -3356550, 9594024},
2414 {-23752644, 2636870, -5163910, -10103818, 585134, 7877383, 11345683,
2415 -6492290, 13352335, -10977084},
2416 },
2417 {
2418 {-1931799, -5407458, 3304649, -12884869, 17015806, -4877091,
2419 -29783850, -7752482, -13215537, -319204},
2420 {20239939, 6607058, 6203985, 3483793, -18386976, -779229, -20723742,
2421 15077870, -22750759, 14523817},
2422 {27406042, -6041657, 27423596, -4497394, 4996214, 10002360,
2423 -28842031, -4545494, -30172742, -4805667},
2424 },
2425 },
2426 {
2427 {
2428 {11374242, 12660715, 17861383, -12540833, 10935568, 1099227,
2429 -13886076, -9091740, -27727044, 11358504},
2430 {-12730809, 10311867, 1510375, 10778093, -2119455, -9145702,
2431 32676003, 11149336, -26123651, 4985768},
2432 {-19096303, 341147, -6197485, -239033, 15756973, -8796662, -983043,
2433 13794114, -19414307, -15621255},
2434 },
2435 {
2436 {6490081, 11940286, 25495923, -7726360, 8668373, -8751316, 3367603,
2437 6970005, -1691065, -9004790},
2438 {1656497, 13457317, 15370807, 6364910, 13605745, 8362338, -19174622,
2439 -5475723, -16796596, -5031438},
2440 {-22273315, -13524424, -64685, -4334223, -18605636, -10921968,
2441 -20571065, -7007978, -99853, -10237333},
2442 },
2443 {
2444 {17747465, 10039260, 19368299, -4050591, -20630635, -16041286,
2445 31992683, -15857976, -29260363, -5511971},
2446 {31932027, -4986141, -19612382, 16366580, 22023614, 88450, 11371999,
2447 -3744247, 4882242, -10626905},
2448 {29796507, 37186, 19818052, 10115756, -11829032, 3352736, 18551198,
2449 3272828, -5190932, -4162409},
2450 },
2451 {
2452 {12501286, 4044383, -8612957, -13392385, -32430052, 5136599,
2453 -19230378, -3529697, 330070, -3659409},
2454 {6384877, 2899513, 17807477, 7663917, -2358888, 12363165, 25366522,
2455 -8573892, -271295, 12071499},
2456 {-8365515, -4042521, 25133448, -4517355, -6211027, 2265927,
2457 -32769618, 1936675, -5159697, 3829363},
2458 },
2459 {
2460 {28425966, -5835433, -577090, -4697198, -14217555, 6870930, 7921550,
2461 -6567787, 26333140, 14267664},
2462 {-11067219, 11871231, 27385719, -10559544, -4585914, -11189312,
2463 10004786, -8709488, -21761224, 8930324},
2464 {-21197785, -16396035, 25654216, -1725397, 12282012, 11008919,
2465 1541940, 4757911, -26491501, -16408940},
2466 },
2467 {
2468 {13537262, -7759490, -20604840, 10961927, -5922820, -13218065,
2469 -13156584, 6217254, -15943699, 13814990},
2470 {-17422573, 15157790, 18705543, 29619, 24409717, -260476, 27361681,
2471 9257833, -1956526, -1776914},
2472 {-25045300, -10191966, 15366585, 15166509, -13105086, 8423556,
2473 -29171540, 12361135, -18685978, 4578290},
2474 },
2475 {
2476 {24579768, 3711570, 1342322, -11180126, -27005135, 14124956,
2477 -22544529, 14074919, 21964432, 8235257},
2478 {-6528613, -2411497, 9442966, -5925588, 12025640, -1487420,
2479 -2981514, -1669206, 13006806, 2355433},
2480 {-16304899, -13605259, -6632427, -5142349, 16974359, -10911083,
2481 27202044, 1719366, 1141648, -12796236},
2482 },
2483 {
2484 {-12863944, -13219986, -8318266, -11018091, -6810145, -4843894,
2485 13475066, -3133972, 32674895, 13715045},
2486 {11423335, -5468059, 32344216, 8962751, 24989809, 9241752,
2487 -13265253, 16086212, -28740881, -15642093},
2488 {-1409668, 12530728, -6368726, 10847387, 19531186, -14132160,
2489 -11709148, 7791794, -27245943, 4383347},
2490 },
2491 },
2492 {
2493 {
2494 {-28970898, 5271447, -1266009, -9736989, -12455236, 16732599,
2495 -4862407, -4906449, 27193557, 6245191},
2496 {-15193956, 5362278, -1783893, 2695834, 4960227, 12840725, 23061898,
2497 3260492, 22510453, 8577507},
2498 {-12632451, 11257346, -32692994, 13548177, -721004, 10879011,
2499 31168030, 13952092, -29571492, -3635906},
2500 },
2501 {
2502 {3877321, -9572739, 32416692, 5405324, -11004407, -13656635,
2503 3759769, 11935320, 5611860, 8164018},
2504 {-16275802, 14667797, 15906460, 12155291, -22111149, -9039718,
2505 32003002, -8832289, 5773085, -8422109},
2506 {-23788118, -8254300, 1950875, 8937633, 18686727, 16459170, -905725,
2507 12376320, 31632953, 190926},
2508 },
2509 {
2510 {-24593607, -16138885, -8423991, 13378746, 14162407, 6901328,
2511 -8288749, 4508564, -25341555, -3627528},
2512 {8884438, -5884009, 6023974, 10104341, -6881569, -4941533, 18722941,
2513 -14786005, -1672488, 827625},
2514 {-32720583, -16289296, -32503547, 7101210, 13354605, 2659080,
2515 -1800575, -14108036, -24878478, 1541286},
2516 },
2517 {
2518 {2901347, -1117687, 3880376, -10059388, -17620940, -3612781,
2519 -21802117, -3567481, 20456845, -1885033},
2520 {27019610, 12299467, -13658288, -1603234, -12861660, -4861471,
2521 -19540150, -5016058, 29439641, 15138866},
2522 {21536104, -6626420, -32447818, -10690208, -22408077, 5175814,
2523 -5420040, -16361163, 7779328, 109896},
2524 },
2525 {
2526 {30279744, 14648750, -8044871, 6425558, 13639621, -743509, 28698390,
2527 12180118, 23177719, -554075},
2528 {26572847, 3405927, -31701700, 12890905, -19265668, 5335866,
2529 -6493768, 2378492, 4439158, -13279347},
2530 {-22716706, 3489070, -9225266, -332753, 18875722, -1140095,
2531 14819434, -12731527, -17717757, -5461437},
2532 },
2533 {
2534 {-5056483, 16566551, 15953661, 3767752, -10436499, 15627060,
2535 -820954, 2177225, 8550082, -15114165},
2536 {-18473302, 16596775, -381660, 15663611, 22860960, 15585581,
2537 -27844109, -3582739, -23260460, -8428588},
2538 {-32480551, 15707275, -8205912, -5652081, 29464558, 2713815,
2539 -22725137, 15860482, -21902570, 1494193},
2540 },
2541 {
2542 {-19562091, -14087393, -25583872, -9299552, 13127842, 759709,
2543 21923482, 16529112, 8742704, 12967017},
2544 {-28464899, 1553205, 32536856, -10473729, -24691605, -406174,
2545 -8914625, -2933896, -29903758, 15553883},
2546 {21877909, 3230008, 9881174, 10539357, -4797115, 2841332, 11543572,
2547 14513274, 19375923, -12647961},
2548 },
2549 {
2550 {8832269, -14495485, 13253511, 5137575, 5037871, 4078777, 24880818,
2551 -6222716, 2862653, 9455043},
2552 {29306751, 5123106, 20245049, -14149889, 9592566, 8447059, -2077124,
2553 -2990080, 15511449, 4789663},
2554 {-20679756, 7004547, 8824831, -9434977, -4045704, -3750736,
2555 -5754762, 108893, 23513200, 16652362},
2556 },
2557 },
2558 {
2559 {
2560 {-33256173, 4144782, -4476029, -6579123, 10770039, -7155542,
2561 -6650416, -12936300, -18319198, 10212860},
2562 {2756081, 8598110, 7383731, -6859892, 22312759, -1105012, 21179801,
2563 2600940, -9988298, -12506466},
2564 {-24645692, 13317462, -30449259, -15653928, 21365574, -10869657,
2565 11344424, 864440, -2499677, -16710063},
2566 },
2567 {
2568 {-26432803, 6148329, -17184412, -14474154, 18782929, -275997,
2569 -22561534, 211300, 2719757, 4940997},
2570 {-1323882, 3911313, -6948744, 14759765, -30027150, 7851207,
2571 21690126, 8518463, 26699843, 5276295},
2572 {-13149873, -6429067, 9396249, 365013, 24703301, -10488939, 1321586,
2573 149635, -15452774, 7159369},
2574 },
2575 {
2576 {9987780, -3404759, 17507962, 9505530, 9731535, -2165514, 22356009,
2577 8312176, 22477218, -8403385},
2578 {18155857, -16504990, 19744716, 9006923, 15154154, -10538976,
2579 24256460, -4864995, -22548173, 9334109},
2580 {2986088, -4911893, 10776628, -3473844, 10620590, -7083203,
2581 -21413845, 14253545, -22587149, 536906},
2582 },
2583 {
2584 {4377756, 8115836, 24567078, 15495314, 11625074, 13064599, 7390551,
2585 10589625, 10838060, -15420424},
2586 {-19342404, 867880, 9277171, -3218459, -14431572, -1986443,
2587 19295826, -15796950, 6378260, 699185},
2588 {7895026, 4057113, -7081772, -13077756, -17886831, -323126, -716039,
2589 15693155, -5045064, -13373962},
2590 },
2591 {
2592 {-7737563, -5869402, -14566319, -7406919, 11385654, 13201616,
2593 31730678, -10962840, -3918636, -9669325},
2594 {10188286, -15770834, -7336361, 13427543, 22223443, 14896287,
2595 30743455, 7116568, -21786507, 5427593},
2596 {696102, 13206899, 27047647, -10632082, 15285305, -9853179,
2597 10798490, -4578720, 19236243, 12477404},
2598 },
2599 {
2600 {-11229439, 11243796, -17054270, -8040865, -788228, -8167967,
2601 -3897669, 11180504, -23169516, 7733644},
2602 {17800790, -14036179, -27000429, -11766671, 23887827, 3149671,
2603 23466177, -10538171, 10322027, 15313801},
2604 {26246234, 11968874, 32263343, -5468728, 6830755, -13323031,
2605 -15794704, -101982, -24449242, 10890804},
2606 },
2607 {
2608 {-31365647, 10271363, -12660625, -6267268, 16690207, -13062544,
2609 -14982212, 16484931, 25180797, -5334884},
2610 {-586574, 10376444, -32586414, -11286356, 19801893, 10997610,
2611 2276632, 9482883, 316878, 13820577},
2612 {-9882808, -4510367, -2115506, 16457136, -11100081, 11674996,
2613 30756178, -7515054, 30696930, -3712849},
2614 },
2615 {
2616 {32988917, -9603412, 12499366, 7910787, -10617257, -11931514,
2617 -7342816, -9985397, -32349517, 7392473},
2618 {-8855661, 15927861, 9866406, -3649411, -2396914, -16655781,
2619 -30409476, -9134995, 25112947, -2926644},
2620 {-2504044, -436966, 25621774, -5678772, 15085042, -5479877,
2621 -24884878, -13526194, 5537438, -13914319},
2622 },
2623 },
2624 {
2625 {
2626 {-11225584, 2320285, -9584280, 10149187, -33444663, 5808648,
2627 -14876251, -1729667, 31234590, 6090599},
2628 {-9633316, 116426, 26083934, 2897444, -6364437, -2688086, 609721,
2629 15878753, -6970405, -9034768},
2630 {-27757857, 247744, -15194774, -9002551, 23288161, -10011936,
2631 -23869595, 6503646, 20650474, 1804084},
2632 },
2633 {
2634 {-27589786, 15456424, 8972517, 8469608, 15640622, 4439847, 3121995,
2635 -10329713, 27842616, -202328},
2636 {-15306973, 2839644, 22530074, 10026331, 4602058, 5048462, 28248656,
2637 5031932, -11375082, 12714369},
2638 {20807691, -7270825, 29286141, 11421711, -27876523, -13868230,
2639 -21227475, 1035546, -19733229, 12796920},
2640 },
2641 {
2642 {12076899, -14301286, -8785001, -11848922, -25012791, 16400684,
2643 -17591495, -12899438, 3480665, -15182815},
2644 {-32361549, 5457597, 28548107, 7833186, 7303070, -11953545,
2645 -24363064, -15921875, -33374054, 2771025},
2646 {-21389266, 421932, 26597266, 6860826, 22486084, -6737172,
2647 -17137485, -4210226, -24552282, 15673397},
2648 },
2649 {
2650 {-20184622, 2338216, 19788685, -9620956, -4001265, -8740893,
2651 -20271184, 4733254, 3727144, -12934448},
2652 {6120119, 814863, -11794402, -622716, 6812205, -15747771, 2019594,
2653 7975683, 31123697, -10958981},
2654 {30069250, -11435332, 30434654, 2958439, 18399564, -976289,
2655 12296869, 9204260, -16432438, 9648165},
2656 },
2657 {
2658 {32705432, -1550977, 30705658, 7451065, -11805606, 9631813, 3305266,
2659 5248604, -26008332, -11377501},
2660 {17219865, 2375039, -31570947, -5575615, -19459679, 9219903, 294711,
2661 15298639, 2662509, -16297073},
2662 {-1172927, -7558695, -4366770, -4287744, -21346413, -8434326,
2663 32087529, -1222777, 32247248, -14389861},
2664 },
2665 {
2666 {14312628, 1221556, 17395390, -8700143, -4945741, -8684635,
2667 -28197744, -9637817, -16027623, -13378845},
2668 {-1428825, -9678990, -9235681, 6549687, -7383069, -468664, 23046502,
2669 9803137, 17597934, 2346211},
2670 {18510800, 15337574, 26171504, 981392, -22241552, 7827556,
2671 -23491134, -11323352, 3059833, -11782870},
2672 },
2673 {
2674 {10141598, 6082907, 17829293, -1947643, 9830092, 13613136,
2675 -25556636, -5544586, -33502212, 3592096},
2676 {33114168, -15889352, -26525686, -13343397, 33076705, 8716171,
2677 1151462, 1521897, -982665, -6837803},
2678 {-32939165, -4255815, 23947181, -324178, -33072974, -12305637,
2679 -16637686, 3891704, 26353178, 693168},
2680 },
2681 {
2682 {30374239, 1595580, -16884039, 13186931, 4600344, 406904, 9585294,
2683 -400668, 31375464, 14369965},
2684 {-14370654, -7772529, 1510301, 6434173, -18784789, -6262728,
2685 32732230, -13108839, 17901441, 16011505},
2686 {18171223, -11934626, -12500402, 15197122, -11038147, -15230035,
2687 -19172240, -16046376, 8764035, 12309598},
2688 },
2689 },
2690 {
2691 {
2692 {5975908, -5243188, -19459362, -9681747, -11541277, 14015782,
2693 -23665757, 1228319, 17544096, -10593782},
2694 {5811932, -1715293, 3442887, -2269310, -18367348, -8359541,
2695 -18044043, -15410127, -5565381, 12348900},
2696 {-31399660, 11407555, 25755363, 6891399, -3256938, 14872274,
2697 -24849353, 8141295, -10632534, -585479},
2698 },
2699 {
2700 {-12675304, 694026, -5076145, 13300344, 14015258, -14451394,
2701 -9698672, -11329050, 30944593, 1130208},
2702 {8247766, -6710942, -26562381, -7709309, -14401939, -14648910,
2703 4652152, 2488540, 23550156, -271232},
2704 {17294316, -3788438, 7026748, 15626851, 22990044, 113481, 2267737,
2705 -5908146, -408818, -137719},
2706 },
2707 {
2708 {16091085, -16253926, 18599252, 7340678, 2137637, -1221657,
2709 -3364161, 14550936, 3260525, -7166271},
2710 {-4910104, -13332887, 18550887, 10864893, -16459325, -7291596,
2711 -23028869, -13204905, -12748722, 2701326},
2712 {-8574695, 16099415, 4629974, -16340524, -20786213, -6005432,
2713 -10018363, 9276971, 11329923, 1862132},
2714 },
2715 {
2716 {14763076, -15903608, -30918270, 3689867, 3511892, 10313526,
2717 -21951088, 12219231, -9037963, -940300},
2718 {8894987, -3446094, 6150753, 3013931, 301220, 15693451, -31981216,
2719 -2909717, -15438168, 11595570},
2720 {15214962, 3537601, -26238722, -14058872, 4418657, -15230761,
2721 13947276, 10730794, -13489462, -4363670},
2722 },
2723 {
2724 {-2538306, 7682793, 32759013, 263109, -29984731, -7955452,
2725 -22332124, -10188635, 977108, 699994},
2726 {-12466472, 4195084, -9211532, 550904, -15565337, 12917920,
2727 19118110, -439841, -30534533, -14337913},
2728 {31788461, -14507657, 4799989, 7372237, 8808585, -14747943, 9408237,
2729 -10051775, 12493932, -5409317},
2730 },
2731 {
2732 {-25680606, 5260744, -19235809, -6284470, -3695942, 16566087,
2733 27218280, 2607121, 29375955, 6024730},
2734 {842132, -2794693, -4763381, -8722815, 26332018, -12405641,
2735 11831880, 6985184, -9940361, 2854096},
2736 {-4847262, -7969331, 2516242, -5847713, 9695691, -7221186, 16512645,
2737 960770, 12121869, 16648078},
2738 },
2739 {
2740 {-15218652, 14667096, -13336229, 2013717, 30598287, -464137,
2741 -31504922, -7882064, 20237806, 2838411},
2742 {-19288047, 4453152, 15298546, -16178388, 22115043, -15972604,
2743 12544294, -13470457, 1068881, -12499905},
2744 {-9558883, -16518835, 33238498, 13506958, 30505848, -1114596,
2745 -8486907, -2630053, 12521378, 4845654},
2746 },
2747 {
2748 {-28198521, 10744108, -2958380, 10199664, 7759311, -13088600,
2749 3409348, -873400, -6482306, -12885870},
2750 {-23561822, 6230156, -20382013, 10655314, -24040585, -11621172,
2751 10477734, -1240216, -3113227, 13974498},
2752 {12966261, 15550616, -32038948, -1615346, 21025980, -629444,
2753 5642325, 7188737, 18895762, 12629579},
2754 },
2755 },
2756 {
2757 {
2758 {14741879, -14946887, 22177208, -11721237, 1279741, 8058600,
2759 11758140, 789443, 32195181, 3895677},
2760 {10758205, 15755439, -4509950, 9243698, -4879422, 6879879, -2204575,
2761 -3566119, -8982069, 4429647},
2762 {-2453894, 15725973, -20436342, -10410672, -5803908, -11040220,
2763 -7135870, -11642895, 18047436, -15281743},
2764 },
2765 {
2766 {-25173001, -11307165, 29759956, 11776784, -22262383, -15820455,
2767 10993114, -12850837, -17620701, -9408468},
2768 {21987233, 700364, -24505048, 14972008, -7774265, -5718395,
2769 32155026, 2581431, -29958985, 8773375},
2770 {-25568350, 454463, -13211935, 16126715, 25240068, 8594567,
2771 20656846, 12017935, -7874389, -13920155},
2772 },
2773 {
2774 {6028182, 6263078, -31011806, -11301710, -818919, 2461772,
2775 -31841174, -5468042, -1721788, -2776725},
2776 {-12278994, 16624277, 987579, -5922598, 32908203, 1248608, 7719845,
2777 -4166698, 28408820, 6816612},
2778 {-10358094, -8237829, 19549651, -12169222, 22082623, 16147817,
2779 20613181, 13982702, -10339570, 5067943},
2780 },
2781 {
2782 {-30505967, -3821767, 12074681, 13582412, -19877972, 2443951,
2783 -19719286, 12746132, 5331210, -10105944},
2784 {30528811, 3601899, -1957090, 4619785, -27361822, -15436388,
2785 24180793, -12570394, 27679908, -1648928},
2786 {9402404, -13957065, 32834043, 10838634, -26580150, -13237195,
2787 26653274, -8685565, 22611444, -12715406},
2788 },
2789 {
2790 {22190590, 1118029, 22736441, 15130463, -30460692, -5991321,
2791 19189625, -4648942, 4854859, 6622139},
2792 {-8310738, -2953450, -8262579, -3388049, -10401731, -271929,
2793 13424426, -3567227, 26404409, 13001963},
2794 {-31241838, -15415700, -2994250, 8939346, 11562230, -12840670,
2795 -26064365, -11621720, -15405155, 11020693},
2796 },
2797 {
2798 {1866042, -7949489, -7898649, -10301010, 12483315, 13477547,
2799 3175636, -12424163, 28761762, 1406734},
2800 {-448555, -1777666, 13018551, 3194501, -9580420, -11161737,
2801 24760585, -4347088, 25577411, -13378680},
2802 {-24290378, 4759345, -690653, -1852816, 2066747, 10693769,
2803 -29595790, 9884936, -9368926, 4745410},
2804 },
2805 {
2806 {-9141284, 6049714, -19531061, -4341411, -31260798, 9944276,
2807 -15462008, -11311852, 10931924, -11931931},
2808 {-16561513, 14112680, -8012645, 4817318, -8040464, -11414606,
2809 -22853429, 10856641, -20470770, 13434654},
2810 {22759489, -10073434, -16766264, -1871422, 13637442, -10168091,
2811 1765144, -12654326, 28445307, -5364710},
2812 },
2813 {
2814 {29875063, 12493613, 2795536, -3786330, 1710620, 15181182,
2815 -10195717, -8788675, 9074234, 1167180},
2816 {-26205683, 11014233, -9842651, -2635485, -26908120, 7532294,
2817 -18716888, -9535498, 3843903, 9367684},
2818 {-10969595, -6403711, 9591134, 9582310, 11349256, 108879, 16235123,
2819 8601684, -139197, 4242895},
2820 },
2821 },
2822 {
2823 {
2824 {22092954, -13191123, -2042793, -11968512, 32186753, -11517388,
2825 -6574341, 2470660, -27417366, 16625501},
2826 {-11057722, 3042016, 13770083, -9257922, 584236, -544855, -7770857,
2827 2602725, -27351616, 14247413},
2828 {6314175, -10264892, -32772502, 15957557, -10157730, 168750,
2829 -8618807, 14290061, 27108877, -1180880},
2830 },
2831 {
2832 {-8586597, -7170966, 13241782, 10960156, -32991015, -13794596,
2833 33547976, -11058889, -27148451, 981874},
2834 {22833440, 9293594, -32649448, -13618667, -9136966, 14756819,
2835 -22928859, -13970780, -10479804, -16197962},
2836 {-7768587, 3326786, -28111797, 10783824, 19178761, 14905060,
2837 22680049, 13906969, -15933690, 3797899},
2838 },
2839 {
2840 {21721356, -4212746, -12206123, 9310182, -3882239, -13653110,
2841 23740224, -2709232, 20491983, -8042152},
2842 {9209270, -15135055, -13256557, -6167798, -731016, 15289673,
2843 25947805, 15286587, 30997318, -6703063},
2844 {7392032, 16618386, 23946583, -8039892, -13265164, -1533858,
2845 -14197445, -2321576, 17649998, -250080},
2846 },
2847 {
2848 {-9301088, -14193827, 30609526, -3049543, -25175069, -1283752,
2849 -15241566, -9525724, -2233253, 7662146},
2850 {-17558673, 1763594, -33114336, 15908610, -30040870, -12174295,
2851 7335080, -8472199, -3174674, 3440183},
2852 {-19889700, -5977008, -24111293, -9688870, 10799743, -16571957,
2853 40450, -4431835, 4862400, 1133},
2854 },
2855 {
2856 {-32856209, -7873957, -5422389, 14860950, -16319031, 7956142,
2857 7258061, 311861, -30594991, -7379421},
2858 {-3773428, -1565936, 28985340, 7499440, 24445838, 9325937, 29727763,
2859 16527196, 18278453, 15405622},
2860 {-4381906, 8508652, -19898366, -3674424, -5984453, 15149970,
2861 -13313598, 843523, -21875062, 13626197},
2862 },
2863 {
2864 {2281448, -13487055, -10915418, -2609910, 1879358, 16164207,
2865 -10783882, 3953792, 13340839, 15928663},
2866 {31727126, -7179855, -18437503, -8283652, 2875793, -16390330,
2867 -25269894, -7014826, -23452306, 5964753},
2868 {4100420, -5959452, -17179337, 6017714, -18705837, 12227141,
2869 -26684835, 11344144, 2538215, -7570755},
2870 },
2871 {
2872 {-9433605, 6123113, 11159803, -2156608, 30016280, 14966241,
2873 -20474983, 1485421, -629256, -15958862},
2874 {-26804558, 4260919, 11851389, 9658551, -32017107, 16367492,
2875 -20205425, -13191288, 11659922, -11115118},
2876 {26180396, 10015009, -30844224, -8581293, 5418197, 9480663, 2231568,
2877 -10170080, 33100372, -1306171},
2878 },
2879 {
2880 {15121113, -5201871, -10389905, 15427821, -27509937, -15992507,
2881 21670947, 4486675, -5931810, -14466380},
2882 {16166486, -9483733, -11104130, 6023908, -31926798, -1364923,
2883 2340060, -16254968, -10735770, -10039824},
2884 {28042865, -3557089, -12126526, 12259706, -3717498, -6945899,
2885 6766453, -8689599, 18036436, 5803270},
2886 },
2887 },
2888 {
2889 {
2890 {-817581, 6763912, 11803561, 1585585, 10958447, -2671165, 23855391,
2891 4598332, -6159431, -14117438},
2892 {-31031306, -14256194, 17332029, -2383520, 31312682, -5967183,
2893 696309, 50292, -20095739, 11763584},
2894 {-594563, -2514283, -32234153, 12643980, 12650761, 14811489, 665117,
2895 -12613632, -19773211, -10713562},
2896 },
2897 {
2898 {30464590, -11262872, -4127476, -12734478, 19835327, -7105613,
2899 -24396175, 2075773, -17020157, 992471},
2900 {18357185, -6994433, 7766382, 16342475, -29324918, 411174, 14578841,
2901 8080033, -11574335, -10601610},
2902 {19598397, 10334610, 12555054, 2555664, 18821899, -10339780,
2903 21873263, 16014234, 26224780, 16452269},
2904 },
2905 {
2906 {-30223925, 5145196, 5944548, 16385966, 3976735, 2009897, -11377804,
2907 -7618186, -20533829, 3698650},
2908 {14187449, 3448569, -10636236, -10810935, -22663880, -3433596,
2909 7268410, -10890444, 27394301, 12015369},
2910 {19695761, 16087646, 28032085, 12999827, 6817792, 11427614,
2911 20244189, -1312777, -13259127, -3402461},
2912 },
2913 {
2914 {30860103, 12735208, -1888245, -4699734, -16974906, 2256940,
2915 -8166013, 12298312, -8550524, -10393462},
2916 {-5719826, -11245325, -1910649, 15569035, 26642876, -7587760,
2917 -5789354, -15118654, -4976164, 12651793},
2918 {-2848395, 9953421, 11531313, -5282879, 26895123, -12697089,
2919 -13118820, -16517902, 9768698, -2533218},
2920 },
2921 {
2922 {-24719459, 1894651, -287698, -4704085, 15348719, -8156530,
2923 32767513, 12765450, 4940095, 10678226},
2924 {18860224, 15980149, -18987240, -1562570, -26233012, -11071856,
2925 -7843882, 13944024, -24372348, 16582019},
2926 {-15504260, 4970268, -29893044, 4175593, -20993212, -2199756,
2927 -11704054, 15444560, -11003761, 7989037},
2928 },
2929 {
2930 {31490452, 5568061, -2412803, 2182383, -32336847, 4531686,
2931 -32078269, 6200206, -19686113, -14800171},
2932 {-17308668, -15879940, -31522777, -2831, -32887382, 16375549,
2933 8680158, -16371713, 28550068, -6857132},
2934 {-28126887, -5688091, 16837845, -1820458, -6850681, 12700016,
2935 -30039981, 4364038, 1155602, 5988841},
2936 },
2937 {
2938 {21890435, -13272907, -12624011, 12154349, -7831873, 15300496,
2939 23148983, -4470481, 24618407, 8283181},
2940 {-33136107, -10512751, 9975416, 6841041, -31559793, 16356536,
2941 3070187, -7025928, 1466169, 10740210},
2942 {-1509399, -15488185, -13503385, -10655916, 32799044, 909394,
2943 -13938903, -5779719, -32164649, -15327040},
2944 },
2945 {
2946 {3960823, -14267803, -28026090, -15918051, -19404858, 13146868,
2947 15567327, 951507, -3260321, -573935},
2948 {24740841, 5052253, -30094131, 8961361, 25877428, 6165135,
2949 -24368180, 14397372, -7380369, -6144105},
2950 {-28888365, 3510803, -28103278, -1158478, -11238128, -10631454,
2951 -15441463, -14453128, -1625486, -6494814},
2952 },
2953 },
2954 {
2955 {
2956 {793299, -9230478, 8836302, -6235707, -27360908, -2369593, 33152843,
2957 -4885251, -9906200, -621852},
2958 {5666233, 525582, 20782575, -8038419, -24538499, 14657740, 16099374,
2959 1468826, -6171428, -15186581},
2960 {-4859255, -3779343, -2917758, -6748019, 7778750, 11688288,
2961 -30404353, -9871238, -1558923, -9863646},
2962 },
2963 {
2964 {10896332, -7719704, 824275, 472601, -19460308, 3009587, 25248958,
2965 14783338, -30581476, -15757844},
2966 {10566929, 12612572, -31944212, 11118703, -12633376, 12362879,
2967 21752402, 8822496, 24003793, 14264025},
2968 {27713862, -7355973, -11008240, 9227530, 27050101, 2504721,
2969 23886875, -13117525, 13958495, -5732453},
2970 },
2971 {
2972 {-23481610, 4867226, -27247128, 3900521, 29838369, -8212291,
2973 -31889399, -10041781, 7340521, -15410068},
2974 {4646514, -8011124, -22766023, -11532654, 23184553, 8566613,
2975 31366726, -1381061, -15066784, -10375192},
2976 {-17270517, 12723032, -16993061, 14878794, 21619651, -6197576,
2977 27584817, 3093888, -8843694, 3849921},
2978 },
2979 {
2980 {-9064912, 2103172, 25561640, -15125738, -5239824, 9582958,
2981 32477045, -9017955, 5002294, -15550259},
2982 {-12057553, -11177906, 21115585, -13365155, 8808712, -12030708,
2983 16489530, 13378448, -25845716, 12741426},
2984 {-5946367, 10645103, -30911586, 15390284, -3286982, -7118677,
2985 24306472, 15852464, 28834118, -7646072},
2986 },
2987 {
2988 {-17335748, -9107057, -24531279, 9434953, -8472084, -583362,
2989 -13090771, 455841, 20461858, 5491305},
2990 {13669248, -16095482, -12481974, -10203039, -14569770, -11893198,
2991 -24995986, 11293807, -28588204, -9421832},
2992 {28497928, 6272777, -33022994, 14470570, 8906179, -1225630,
2993 18504674, -14165166, 29867745, -8795943},
2994 },
2995 {
2996 {-16207023, 13517196, -27799630, -13697798, 24009064, -6373891,
2997 -6367600, -13175392, 22853429, -4012011},
2998 {24191378, 16712145, -13931797, 15217831, 14542237, 1646131,
2999 18603514, -11037887, 12876623, -2112447},
3000 {17902668, 4518229, -411702, -2829247, 26878217, 5258055, -12860753,
3001 608397, 16031844, 3723494},
3002 },
3003 {
3004 {-28632773, 12763728, -20446446, 7577504, 33001348, -13017745,
3005 17558842, -7872890, 23896954, -4314245},
3006 {-20005381, -12011952, 31520464, 605201, 2543521, 5991821, -2945064,
3007 7229064, -9919646, -8826859},
3008 {28816045, 298879, -28165016, -15920938, 19000928, -1665890,
3009 -12680833, -2949325, -18051778, -2082915},
3010 },
3011 {
3012 {16000882, -344896, 3493092, -11447198, -29504595, -13159789,
3013 12577740, 16041268, -19715240, 7847707},
3014 {10151868, 10572098, 27312476, 7922682, 14825339, 4723128,
3015 -32855931, -6519018, -10020567, 3852848},
3016 {-11430470, 15697596, -21121557, -4420647, 5386314, 15063598,
3017 16514493, -15932110, 29330899, -15076224},
3018 },
3019 },
3020 {
3021 {
3022 {-25499735, -4378794, -15222908, -6901211, 16615731, 2051784,
3023 3303702, 15490, -27548796, 12314391},
3024 {15683520, -6003043, 18109120, -9980648, 15337968, -5997823,
3025 -16717435, 15921866, 16103996, -3731215},
3026 {-23169824, -10781249, 13588192, -1628807, -3798557, -1074929,
3027 -19273607, 5402699, -29815713, -9841101},
3028 },
3029 {
3030 {23190676, 2384583, -32714340, 3462154, -29903655, -1529132,
3031 -11266856, 8911517, -25205859, 2739713},
3032 {21374101, -3554250, -33524649, 9874411, 15377179, 11831242,
3033 -33529904, 6134907, 4931255, 11987849},
3034 {-7732, -2978858, -16223486, 7277597, 105524, -322051, -31480539,
3035 13861388, -30076310, 10117930},
3036 },
3037 {
3038 {-29501170, -10744872, -26163768, 13051539, -25625564, 5089643,
3039 -6325503, 6704079, 12890019, 15728940},
3040 {-21972360, -11771379, -951059, -4418840, 14704840, 2695116, 903376,
3041 -10428139, 12885167, 8311031},
3042 {-17516482, 5352194, 10384213, -13811658, 7506451, 13453191,
3043 26423267, 4384730, 1888765, -5435404},
3044 },
3045 {
3046 {-25817338, -3107312, -13494599, -3182506, 30896459, -13921729,
3047 -32251644, -12707869, -19464434, -3340243},
3048 {-23607977, -2665774, -526091, 4651136, 5765089, 4618330, 6092245,
3049 14845197, 17151279, -9854116},
3050 {-24830458, -12733720, -15165978, 10367250, -29530908, -265356,
3051 22825805, -7087279, -16866484, 16176525},
3052 },
3053 {
3054 {-23583256, 6564961, 20063689, 3798228, -4740178, 7359225, 2006182,
3055 -10363426, -28746253, -10197509},
3056 {-10626600, -4486402, -13320562, -5125317, 3432136, -6393229,
3057 23632037, -1940610, 32808310, 1099883},
3058 {15030977, 5768825, -27451236, -2887299, -6427378, -15361371,
3059 -15277896, -6809350, 2051441, -15225865},
3060 },
3061 {
3062 {-3362323, -7239372, 7517890, 9824992, 23555850, 295369, 5148398,
3063 -14154188, -22686354, 16633660},
3064 {4577086, -16752288, 13249841, -15304328, 19958763, -14537274,
3065 18559670, -10759549, 8402478, -9864273},
3066 {-28406330, -1051581, -26790155, -907698, -17212414, -11030789,
3067 9453451, -14980072, 17983010, 9967138},
3068 },
3069 {
3070 {-25762494, 6524722, 26585488, 9969270, 24709298, 1220360, -1677990,
3071 7806337, 17507396, 3651560},
3072 {-10420457, -4118111, 14584639, 15971087, -15768321, 8861010,
3073 26556809, -5574557, -18553322, -11357135},
3074 {2839101, 14284142, 4029895, 3472686, 14402957, 12689363, -26642121,
3075 8459447, -5605463, -7621941},
3076 },
3077 {
3078 {-4839289, -3535444, 9744961, 2871048, 25113978, 3187018, -25110813,
3079 -849066, 17258084, -7977739},
3080 {18164541, -10595176, -17154882, -1542417, 19237078, -9745295,
3081 23357533, -15217008, 26908270, 12150756},
3082 {-30264870, -7647865, 5112249, -7036672, -1499807, -6974257, 43168,
3083 -5537701, -32302074, 16215819},
3084 },
3085 },
3086 {
3087 {
3088 {-6898905, 9824394, -12304779, -4401089, -31397141, -6276835,
3089 32574489, 12532905, -7503072, -8675347},
3090 {-27343522, -16515468, -27151524, -10722951, 946346, 16291093,
3091 254968, 7168080, 21676107, -1943028},
3092 {21260961, -8424752, -16831886, -11920822, -23677961, 3968121,
3093 -3651949, -6215466, -3556191, -7913075},
3094 },
3095 {
3096 {16544754, 13250366, -16804428, 15546242, -4583003, 12757258,
3097 -2462308, -8680336, -18907032, -9662799},
3098 {-2415239, -15577728, 18312303, 4964443, -15272530, -12653564,
3099 26820651, 16690659, 25459437, -4564609},
3100 {-25144690, 11425020, 28423002, -11020557, -6144921, -15826224,
3101 9142795, -2391602, -6432418, -1644817},
3102 },
3103 {
3104 {-23104652, 6253476, 16964147, -3768872, -25113972, -12296437,
3105 -27457225, -16344658, 6335692, 7249989},
3106 {-30333227, 13979675, 7503222, -12368314, -11956721, -4621693,
3107 -30272269, 2682242, 25993170, -12478523},
3108 {4364628, 5930691, 32304656, -10044554, -8054781, 15091131,
3109 22857016, -10598955, 31820368, 15075278},
3110 },
3111 {
3112 {31879134, -8918693, 17258761, 90626, -8041836, -4917709, 24162788,
3113 -9650886, -17970238, 12833045},
3114 {19073683, 14851414, -24403169, -11860168, 7625278, 11091125,
3115 -19619190, 2074449, -9413939, 14905377},
3116 {24483667, -11935567, -2518866, -11547418, -1553130, 15355506,
3117 -25282080, 9253129, 27628530, -7555480},
3118 },
3119 {
3120 {17597607, 8340603, 19355617, 552187, 26198470, -3176583, 4593324,
3121 -9157582, -14110875, 15297016},
3122 {510886, 14337390, -31785257, 16638632, 6328095, 2713355, -20217417,
3123 -11864220, 8683221, 2921426},
3124 {18606791, 11874196, 27155355, -5281482, -24031742, 6265446,
3125 -25178240, -1278924, 4674690, 13890525},
3126 },
3127 {
3128 {13609624, 13069022, -27372361, -13055908, 24360586, 9592974,
3129 14977157, 9835105, 4389687, 288396},
3130 {9922506, -519394, 13613107, 5883594, -18758345, -434263, -12304062,
3131 8317628, 23388070, 16052080},
3132 {12720016, 11937594, -31970060, -5028689, 26900120, 8561328,
3133 -20155687, -11632979, -14754271, -10812892},
3134 },
3135 {
3136 {15961858, 14150409, 26716931, -665832, -22794328, 13603569,
3137 11829573, 7467844, -28822128, 929275},
3138 {11038231, -11582396, -27310482, -7316562, -10498527, -16307831,
3139 -23479533, -9371869, -21393143, 2465074},
3140 {20017163, -4323226, 27915242, 1529148, 12396362, 15675764,
3141 13817261, -9658066, 2463391, -4622140},
3142 },
3143 {
3144 {-16358878, -12663911, -12065183, 4996454, -1256422, 1073572,
3145 9583558, 12851107, 4003896, 12673717},
3146 {-1731589, -15155870, -3262930, 16143082, 19294135, 13385325,
3147 14741514, -9103726, 7903886, 2348101},
3148 {24536016, -16515207, 12715592, -3862155, 1511293, 10047386,
3149 -3842346, -7129159, -28377538, 10048127},
3150 },
3151 },
3152 {
3153 {
3154 {-12622226, -6204820, 30718825, 2591312, -10617028, 12192840,
3155 18873298, -7297090, -32297756, 15221632},
3156 {-26478122, -11103864, 11546244, -1852483, 9180880, 7656409,
3157 -21343950, 2095755, 29769758, 6593415},
3158 {-31994208, -2907461, 4176912, 3264766, 12538965, -868111, 26312345,
3159 -6118678, 30958054, 8292160},
3160 },
3161 {
3162 {31429822, -13959116, 29173532, 15632448, 12174511, -2760094,
3163 32808831, 3977186, 26143136, -3148876},
3164 {22648901, 1402143, -22799984, 13746059, 7936347, 365344, -8668633,
3165 -1674433, -3758243, -2304625},
3166 {-15491917, 8012313, -2514730, -12702462, -23965846, -10254029,
3167 -1612713, -1535569, -16664475, 8194478},
3168 },
3169 {
3170 {27338066, -7507420, -7414224, 10140405, -19026427, -6589889,
3171 27277191, 8855376, 28572286, 3005164},
3172 {26287124, 4821776, 25476601, -4145903, -3764513, -15788984,
3173 -18008582, 1182479, -26094821, -13079595},
3174 {-7171154, 3178080, 23970071, 6201893, -17195577, -4489192,
3175 -21876275, -13982627, 32208683, -1198248},
3176 },
3177 {
3178 {-16657702, 2817643, -10286362, 14811298, 6024667, 13349505,
3179 -27315504, -10497842, -27672585, -11539858},
3180 {15941029, -9405932, -21367050, 8062055, 31876073, -238629,
3181 -15278393, -1444429, 15397331, -4130193},
3182 {8934485, -13485467, -23286397, -13423241, -32446090, 14047986,
3183 31170398, -1441021, -27505566, 15087184},
3184 },
3185 {
3186 {-18357243, -2156491, 24524913, -16677868, 15520427, -6360776,
3187 -15502406, 11461896, 16788528, -5868942},
3188 {-1947386, 16013773, 21750665, 3714552, -17401782, -16055433,
3189 -3770287, -10323320, 31322514, -11615635},
3190 {21426655, -5650218, -13648287, -5347537, -28812189, -4920970,
3191 -18275391, -14621414, 13040862, -12112948},
3192 },
3193 {
3194 {11293895, 12478086, -27136401, 15083750, -29307421, 14748872,
3195 14555558, -13417103, 1613711, 4896935},
3196 {-25894883, 15323294, -8489791, -8057900, 25967126, -13425460,
3197 2825960, -4897045, -23971776, -11267415},
3198 {-15924766, -5229880, -17443532, 6410664, 3622847, 10243618,
3199 20615400, 12405433, -23753030, -8436416},
3200 },
3201 {
3202 {-7091295, 12556208, -20191352, 9025187, -17072479, 4333801,
3203 4378436, 2432030, 23097949, -566018},
3204 {4565804, -16025654, 20084412, -7842817, 1724999, 189254, 24767264,
3205 10103221, -18512313, 2424778},
3206 {366633, -11976806, 8173090, -6890119, 30788634, 5745705, -7168678,
3207 1344109, -3642553, 12412659},
3208 },
3209 {
3210 {-24001791, 7690286, 14929416, -168257, -32210835, -13412986,
3211 24162697, -15326504, -3141501, 11179385},
3212 {18289522, -14724954, 8056945, 16430056, -21729724, 7842514,
3213 -6001441, -1486897, -18684645, -11443503},
3214 {476239, 6601091, -6152790, -9723375, 17503545, -4863900, 27672959,
3215 13403813, 11052904, 5219329},
3216 },
3217 },
3218 {
3219 {
3220 {20678546, -8375738, -32671898, 8849123, -5009758, 14574752,
3221 31186971, -3973730, 9014762, -8579056},
3222 {-13644050, -10350239, -15962508, 5075808, -1514661, -11534600,
3223 -33102500, 9160280, 8473550, -3256838},
3224 {24900749, 14435722, 17209120, -15292541, -22592275, 9878983,
3225 -7689309, -16335821, -24568481, 11788948},
3226 },
3227 {
3228 {-3118155, -11395194, -13802089, 14797441, 9652448, -6845904,
3229 -20037437, 10410733, -24568470, -1458691},
3230 {-15659161, 16736706, -22467150, 10215878, -9097177, 7563911,
3231 11871841, -12505194, -18513325, 8464118},
3232 {-23400612, 8348507, -14585951, -861714, -3950205, -6373419,
3233 14325289, 8628612, 33313881, -8370517},
3234 },
3235 {
3236 {-20186973, -4967935, 22367356, 5271547, -1097117, -4788838,
3237 -24805667, -10236854, -8940735, -5818269},
3238 {-6948785, -1795212, -32625683, -16021179, 32635414, -7374245,
3239 15989197, -12838188, 28358192, -4253904},
3240 {-23561781, -2799059, -32351682, -1661963, -9147719, 10429267,
3241 -16637684, 4072016, -5351664, 5596589},
3242 },
3243 {
3244 {-28236598, -3390048, 12312896, 6213178, 3117142, 16078565,
3245 29266239, 2557221, 1768301, 15373193},
3246 {-7243358, -3246960, -4593467, -7553353, -127927, -912245, -1090902,
3247 -4504991, -24660491, 3442910},
3248 {-30210571, 5124043, 14181784, 8197961, 18964734, -11939093,
3249 22597931, 7176455, -18585478, 13365930},
3250 },
3251 {
3252 {-7877390, -1499958, 8324673, 4690079, 6261860, 890446, 24538107,
3253 -8570186, -9689599, -3031667},
3254 {25008904, -10771599, -4305031, -9638010, 16265036, 15721635,
3255 683793, -11823784, 15723479, -15163481},
3256 {-9660625, 12374379, -27006999, -7026148, -7724114, -12314514,
3257 11879682, 5400171, 519526, -1235876},
3258 },
3259 {
3260 {22258397, -16332233, -7869817, 14613016, -22520255, -2950923,
3261 -20353881, 7315967, 16648397, 7605640},
3262 {-8081308, -8464597, -8223311, 9719710, 19259459, -15348212,
3263 23994942, -5281555, -9468848, 4763278},
3264 {-21699244, 9220969, -15730624, 1084137, -25476107, -2852390,
3265 31088447, -7764523, -11356529, 728112},
3266 },
3267 {
3268 {26047220, -11751471, -6900323, -16521798, 24092068, 9158119,
3269 -4273545, -12555558, -29365436, -5498272},
3270 {17510331, -322857, 5854289, 8403524, 17133918, -3112612, -28111007,
3271 12327945, 10750447, 10014012},
3272 {-10312768, 3936952, 9156313, -8897683, 16498692, -994647,
3273 -27481051, -666732, 3424691, 7540221},
3274 },
3275 {
3276 {30322361, -6964110, 11361005, -4143317, 7433304, 4989748, -7071422,
3277 -16317219, -9244265, 15258046},
3278 {13054562, -2779497, 19155474, 469045, -12482797, 4566042, 5631406,
3279 2711395, 1062915, -5136345},
3280 {-19240248, -11254599, -29509029, -7499965, -5835763, 13005411,
3281 -6066489, 12194497, 32960380, 1459310},
3282 },
3283 },
3284 {
3285 {
3286 {19852034, 7027924, 23669353, 10020366, 8586503, -6657907, 394197,
3287 -6101885, 18638003, -11174937},
3288 {31395534, 15098109, 26581030, 8030562, -16527914, -5007134,
3289 9012486, -7584354, -6643087, -5442636},
3290 {-9192165, -2347377, -1997099, 4529534, 25766844, 607986, -13222,
3291 9677543, -32294889, -6456008},
3292 },
3293 {
3294 {-2444496, -149937, 29348902, 8186665, 1873760, 12489863, -30934579,
3295 -7839692, -7852844, -8138429},
3296 {-15236356, -15433509, 7766470, 746860, 26346930, -10221762,
3297 -27333451, 10754588, -9431476, 5203576},
3298 {31834314, 14135496, -770007, 5159118, 20917671, -16768096,
3299 -7467973, -7337524, 31809243, 7347066},
3300 },
3301 {
3302 {-9606723, -11874240, 20414459, 13033986, 13716524, -11691881,
3303 19797970, -12211255, 15192876, -2087490},
3304 {-12663563, -2181719, 1168162, -3804809, 26747877, -14138091,
3305 10609330, 12694420, 33473243, -13382104},
3306 {33184999, 11180355, 15832085, -11385430, -1633671, 225884,
3307 15089336, -11023903, -6135662, 14480053},
3308 },
3309 {
3310 {31308717, -5619998, 31030840, -1897099, 15674547, -6582883,
3311 5496208, 13685227, 27595050, 8737275},
3312 {-20318852, -15150239, 10933843, -16178022, 8335352, -7546022,
3313 -31008351, -12610604, 26498114, 66511},
3314 {22644454, -8761729, -16671776, 4884562, -3105614, -13559366,
3315 30540766, -4286747, -13327787, -7515095},
3316 },
3317 {
3318 {-28017847, 9834845, 18617207, -2681312, -3401956, -13307506,
3319 8205540, 13585437, -17127465, 15115439},
3320 {23711543, -672915, 31206561, -8362711, 6164647, -9709987,
3321 -33535882, -1426096, 8236921, 16492939},
3322 {-23910559, -13515526, -26299483, -4503841, 25005590, -7687270,
3323 19574902, 10071562, 6708380, -6222424},
3324 },
3325 {
3326 {2101391, -4930054, 19702731, 2367575, -15427167, 1047675, 5301017,
3327 9328700, 29955601, -11678310},
3328 {3096359, 9271816, -21620864, -15521844, -14847996, -7592937,
3329 -25892142, -12635595, -9917575, 6216608},
3330 {-32615849, 338663, -25195611, 2510422, -29213566, -13820213,
3331 24822830, -6146567, -26767480, 7525079},
3332 },
3333 {
3334 {-23066649, -13985623, 16133487, -7896178, -3389565, 778788,
3335 -910336, -2782495, -19386633, 11994101},
3336 {21691500, -13624626, -641331, -14367021, 3285881, -3483596,
3337 -25064666, 9718258, -7477437, 13381418},
3338 {18445390, -4202236, 14979846, 11622458, -1727110, -3582980,
3339 23111648, -6375247, 28535282, 15779576},
3340 },
3341 {
3342 {30098053, 3089662, -9234387, 16662135, -21306940, 11308411,
3343 -14068454, 12021730, 9955285, -16303356},
3344 {9734894, -14576830, -7473633, -9138735, 2060392, 11313496,
3345 -18426029, 9924399, 20194861, 13380996},
3346 {-26378102, -7965207, -22167821, 15789297, -18055342, -6168792,
3347 -1984914, 15707771, 26342023, 10146099},
3348 },
3349 },
3350 {
3351 {
3352 {-26016874, -219943, 21339191, -41388, 19745256, -2878700,
3353 -29637280, 2227040, 21612326, -545728},
3354 {-13077387, 1184228, 23562814, -5970442, -20351244, -6348714,
3355 25764461, 12243797, -20856566, 11649658},
3356 {-10031494, 11262626, 27384172, 2271902, 26947504, -15997771, 39944,
3357 6114064, 33514190, 2333242},
3358 },
3359 {
3360 {-21433588, -12421821, 8119782, 7219913, -21830522, -9016134,
3361 -6679750, -12670638, 24350578, -13450001},
3362 {-4116307, -11271533, -23886186, 4843615, -30088339, 690623,
3363 -31536088, -10406836, 8317860, 12352766},
3364 {18200138, -14475911, -33087759, -2696619, -23702521, -9102511,
3365 -23552096, -2287550, 20712163, 6719373},
3366 },
3367 {
3368 {26656208, 6075253, -7858556, 1886072, -28344043, 4262326, 11117530,
3369 -3763210, 26224235, -3297458},
3370 {-17168938, -14854097, -3395676, -16369877, -19954045, 14050420,
3371 21728352, 9493610, 18620611, -16428628},
3372 {-13323321, 13325349, 11432106, 5964811, 18609221, 6062965,
3373 -5269471, -9725556, -30701573, -16479657},
3374 },
3375 {
3376 {-23860538, -11233159, 26961357, 1640861, -32413112, -16737940,
3377 12248509, -5240639, 13735342, 1934062},
3378 {25089769, 6742589, 17081145, -13406266, 21909293, -16067981,
3379 -15136294, -3765346, -21277997, 5473616},
3380 {31883677, -7961101, 1083432, -11572403, 22828471, 13290673,
3381 -7125085, 12469656, 29111212, -5451014},
3382 },
3383 {
3384 {24244947, -15050407, -26262976, 2791540, -14997599, 16666678,
3385 24367466, 6388839, -10295587, 452383},
3386 {-25640782, -3417841, 5217916, 16224624, 19987036, -4082269,
3387 -24236251, -5915248, 15766062, 8407814},
3388 {-20406999, 13990231, 15495425, 16395525, 5377168, 15166495,
3389 -8917023, -4388953, -8067909, 2276718},
3390 },
3391 {
3392 {30157918, 12924066, -17712050, 9245753, 19895028, 3368142,
3393 -23827587, 5096219, 22740376, -7303417},
3394 {2041139, -14256350, 7783687, 13876377, -25946985, -13352459,
3395 24051124, 13742383, -15637599, 13295222},
3396 {33338237, -8505733, 12532113, 7977527, 9106186, -1715251,
3397 -17720195, -4612972, -4451357, -14669444},
3398 },
3399 {
3400 {-20045281, 5454097, -14346548, 6447146, 28862071, 1883651,
3401 -2469266, -4141880, 7770569, 9620597},
3402 {23208068, 7979712, 33071466, 8149229, 1758231, -10834995, 30945528,
3403 -1694323, -33502340, -14767970},
3404 {1439958, -16270480, -1079989, -793782, 4625402, 10647766, -5043801,
3405 1220118, 30494170, -11440799},
3406 },
3407 {
3408 {-5037580, -13028295, -2970559, -3061767, 15640974, -6701666,
3409 -26739026, 926050, -1684339, -13333647},
3410 {13908495, -3549272, 30919928, -6273825, -21521863, 7989039,
3411 9021034, 9078865, 3353509, 4033511},
3412 {-29663431, -15113610, 32259991, -344482, 24295849, -12912123,
3413 23161163, 8839127, 27485041, 7356032},
3414 },
3415 },
3416 {
3417 {
3418 {9661027, 705443, 11980065, -5370154, -1628543, 14661173, -6346142,
3419 2625015, 28431036, -16771834},
3420 {-23839233, -8311415, -25945511, 7480958, -17681669, -8354183,
3421 -22545972, 14150565, 15970762, 4099461},
3422 {29262576, 16756590, 26350592, -8793563, 8529671, -11208050,
3423 13617293, -9937143, 11465739, 8317062},
3424 },
3425 {
3426 {-25493081, -6962928, 32500200, -9419051, -23038724, -2302222,
3427 14898637, 3848455, 20969334, -5157516},
3428 {-20384450, -14347713, -18336405, 13884722, -33039454, 2842114,
3429 -21610826, -3649888, 11177095, 14989547},
3430 {-24496721, -11716016, 16959896, 2278463, 12066309, 10137771,
3431 13515641, 2581286, -28487508, 9930240},
3432 },
3433 {
3434 {-17751622, -2097826, 16544300, -13009300, -15914807, -14949081,
3435 18345767, -13403753, 16291481, -5314038},
3436 {-33229194, 2553288, 32678213, 9875984, 8534129, 6889387, -9676774,
3437 6957617, 4368891, 9788741},
3438 {16660756, 7281060, -10830758, 12911820, 20108584, -8101676,
3439 -21722536, -8613148, 16250552, -11111103},
3440 },
3441 {
3442 {-19765507, 2390526, -16551031, 14161980, 1905286, 6414907, 4689584,
3443 10604807, -30190403, 4782747},
3444 {-1354539, 14736941, -7367442, -13292886, 7710542, -14155590,
3445 -9981571, 4383045, 22546403, 437323},
3446 {31665577, -12180464, -16186830, 1491339, -18368625, 3294682,
3447 27343084, 2786261, -30633590, -14097016},
3448 },
3449 {
3450 {-14467279, -683715, -33374107, 7448552, 19294360, 14334329,
3451 -19690631, 2355319, -19284671, -6114373},
3452 {15121312, -15796162, 6377020, -6031361, -10798111, -12957845,
3453 18952177, 15496498, -29380133, 11754228},
3454 {-2637277, -13483075, 8488727, -14303896, 12728761, -1622493,
3455 7141596, 11724556, 22761615, -10134141},
3456 },
3457 {
3458 {16918416, 11729663, -18083579, 3022987, -31015732, -13339659,
3459 -28741185, -12227393, 32851222, 11717399},
3460 {11166634, 7338049, -6722523, 4531520, -29468672, -7302055,
3461 31474879, 3483633, -1193175, -4030831},
3462 {-185635, 9921305, 31456609, -13536438, -12013818, 13348923,
3463 33142652, 6546660, -19985279, -3948376},
3464 },
3465 {
3466 {-32460596, 11266712, -11197107, -7899103, 31703694, 3855903,
3467 -8537131, -12833048, -30772034, -15486313},
3468 {-18006477, 12709068, 3991746, -6479188, -21491523, -10550425,
3469 -31135347, -16049879, 10928917, 3011958},
3470 {-6957757, -15594337, 31696059, 334240, 29576716, 14796075,
3471 -30831056, -12805180, 18008031, 10258577},
3472 },
3473 {
3474 {-22448644, 15655569, 7018479, -4410003, -30314266, -1201591,
3475 -1853465, 1367120, 25127874, 6671743},
3476 {29701166, -14373934, -10878120, 9279288, -17568, 13127210,
3477 21382910, 11042292, 25838796, 4642684},
3478 {-20430234, 14955537, -24126347, 8124619, -5369288, -5990470,
3479 30468147, -13900640, 18423289, 4177476},
3480 },
3481 },
3482};
3483
3484static uint8_t negative(signed char b) {
3485 uint32_t x = b;
3486 x >>= 31; /* 1: yes; 0: no */
3487 return x;
3488}
3489
3490static void table_select(ge_precomp *t, int pos, signed char b) {
3491 ge_precomp minust;
3492 uint8_t bnegative = negative(b);
3493 uint8_t babs = b - ((uint8_t)((-bnegative) & b) << 1);
3494
3495 ge_precomp_0(t);
3496 cmov(t, &k25519Precomp[pos][0], equal(babs, 1));
3497 cmov(t, &k25519Precomp[pos][1], equal(babs, 2));
3498 cmov(t, &k25519Precomp[pos][2], equal(babs, 3));
3499 cmov(t, &k25519Precomp[pos][3], equal(babs, 4));
3500 cmov(t, &k25519Precomp[pos][4], equal(babs, 5));
3501 cmov(t, &k25519Precomp[pos][5], equal(babs, 6));
3502 cmov(t, &k25519Precomp[pos][6], equal(babs, 7));
3503 cmov(t, &k25519Precomp[pos][7], equal(babs, 8));
3504 fe_copy(minust.yplusx, t->yminusx);
3505 fe_copy(minust.yminusx, t->yplusx);
3506 fe_neg(minust.xy2d, t->xy2d);
3507 cmov(t, &minust, bnegative);
3508}
3509
3510/* h = a * B
3511 * where a = a[0]+256*a[1]+...+256^31 a[31]
3512 * B is the Ed25519 base point (x,4/5) with x positive.
3513 *
3514 * Preconditions:
3515 * a[31] <= 127 */
3516void x25519_ge_scalarmult_base(ge_p3 *h, const uint8_t *a) {
3517 signed char e[64];
3518 signed char carry;
3519 ge_p1p1 r;
3520 ge_p2 s;
3521 ge_precomp t;
3522 int i;
3523
3524 for (i = 0; i < 32; ++i) {
3525 e[2 * i + 0] = (a[i] >> 0) & 15;
3526 e[2 * i + 1] = (a[i] >> 4) & 15;
3527 }
3528 /* each e[i] is between 0 and 15 */
3529 /* e[63] is between 0 and 7 */
3530
3531 carry = 0;
3532 for (i = 0; i < 63; ++i) {
3533 e[i] += carry;
3534 carry = e[i] + 8;
3535 carry >>= 4;
3536 e[i] -= carry << 4;
3537 }
3538 e[63] += carry;
3539 /* each e[i] is between -8 and 8 */
3540
3541 ge_p3_0(h);
3542 for (i = 1; i < 64; i += 2) {
3543 table_select(&t, i / 2, e[i]);
3544 ge_madd(&r, h, &t);
3545 x25519_ge_p1p1_to_p3(h, &r);
3546 }
3547
3548 ge_p3_dbl(&r, h);
3549 x25519_ge_p1p1_to_p2(&s, &r);
3550 ge_p2_dbl(&r, &s);
3551 x25519_ge_p1p1_to_p2(&s, &r);
3552 ge_p2_dbl(&r, &s);
3553 x25519_ge_p1p1_to_p2(&s, &r);
3554 ge_p2_dbl(&r, &s);
3555 x25519_ge_p1p1_to_p3(h, &r);
3556
3557 for (i = 0; i < 64; i += 2) {
3558 table_select(&t, i / 2, e[i]);
3559 ge_madd(&r, h, &t);
3560 x25519_ge_p1p1_to_p3(h, &r);
3561 }
3562}
3563
3564#endif
3565
3566static void cmov_cached(ge_cached *t, ge_cached *u, uint8_t b) {
3567 fe_cmov(t->YplusX, u->YplusX, b);
3568 fe_cmov(t->YminusX, u->YminusX, b);
3569 fe_cmov(t->Z, u->Z, b);
3570 fe_cmov(t->T2d, u->T2d, b);
3571}
3572
3573/* r = scalar * A.
3574 * where a = a[0]+256*a[1]+...+256^31 a[31]. */
3575void x25519_ge_scalarmult(ge_p2 *r, const uint8_t *scalar, const ge_p3 *A) {
3576 ge_p2 Ai_p2[8];
3577 ge_cached Ai[16];
3578 ge_p1p1 t;
3579
3580 ge_cached_0(&Ai[0]);
3581 x25519_ge_p3_to_cached(&Ai[1], A);
3582 ge_p3_to_p2(&Ai_p2[1], A);
3583
3584 unsigned i;
3585 for (i = 2; i < 16; i += 2) {
3586 ge_p2_dbl(&t, &Ai_p2[i / 2]);
3587 ge_p1p1_to_cached(&Ai[i], &t);
3588 if (i < 8) {
3589 x25519_ge_p1p1_to_p2(&Ai_p2[i], &t);
3590 }
3591 x25519_ge_add(&t, A, &Ai[i]);
3592 ge_p1p1_to_cached(&Ai[i + 1], &t);
3593 if (i < 7) {
3594 x25519_ge_p1p1_to_p2(&Ai_p2[i + 1], &t);
3595 }
3596 }
3597
3598 ge_p2_0(r);
3599 ge_p3 u;
3600
3601 for (i = 0; i < 256; i += 4) {
3602 ge_p2_dbl(&t, r);
3603 x25519_ge_p1p1_to_p2(r, &t);
3604 ge_p2_dbl(&t, r);
3605 x25519_ge_p1p1_to_p2(r, &t);
3606 ge_p2_dbl(&t, r);
3607 x25519_ge_p1p1_to_p2(r, &t);
3608 ge_p2_dbl(&t, r);
3609 x25519_ge_p1p1_to_p3(&u, &t);
3610
3611 uint8_t index = scalar[31 - i/8];
3612 index >>= 4 - (i & 4);
3613 index &= 0xf;
3614
3615 unsigned j;
3616 ge_cached selected;
3617 ge_cached_0(&selected);
3618 for (j = 0; j < 16; j++) {
3619 cmov_cached(&selected, &Ai[j], equal(j, index));
3620 }
3621
3622 x25519_ge_add(&t, &u, &selected);
3623 x25519_ge_p1p1_to_p2(r, &t);
3624 }
3625}
3626
3627#ifdef ED25519
3628static void slide(signed char *r, const uint8_t *a) {
3629 int i;
3630 int b;
3631 int k;
3632
3633 for (i = 0; i < 256; ++i) {
3634 r[i] = 1 & (a[i >> 3] >> (i & 7));
3635 }
3636
3637 for (i = 0; i < 256; ++i) {
3638 if (r[i]) {
3639 for (b = 1; b <= 6 && i + b < 256; ++b) {
3640 if (r[i + b]) {
3641 if (r[i] + (r[i + b] << b) <= 15) {
3642 r[i] += r[i + b] << b;
3643 r[i + b] = 0;
3644 } else if (r[i] - (r[i + b] << b) >= -15) {
3645 r[i] -= r[i + b] << b;
3646 for (k = i + b; k < 256; ++k) {
3647 if (!r[k]) {
3648 r[k] = 1;
3649 break;
3650 }
3651 r[k] = 0;
3652 }
3653 } else {
3654 break;
3655 }
3656 }
3657 }
3658 }
3659 }
3660}
3661
3662static const ge_precomp Bi[8] = {
3663 {
3664 {25967493, -14356035, 29566456, 3660896, -12694345, 4014787, 27544626,
3665 -11754271, -6079156, 2047605},
3666 {-12545711, 934262, -2722910, 3049990, -727428, 9406986, 12720692,
3667 5043384, 19500929, -15469378},
3668 {-8738181, 4489570, 9688441, -14785194, 10184609, -12363380, 29287919,
3669 11864899, -24514362, -4438546},
3670 },
3671 {
3672 {15636291, -9688557, 24204773, -7912398, 616977, -16685262, 27787600,
3673 -14772189, 28944400, -1550024},
3674 {16568933, 4717097, -11556148, -1102322, 15682896, -11807043, 16354577,
3675 -11775962, 7689662, 11199574},
3676 {30464156, -5976125, -11779434, -15670865, 23220365, 15915852, 7512774,
3677 10017326, -17749093, -9920357},
3678 },
3679 {
3680 {10861363, 11473154, 27284546, 1981175, -30064349, 12577861, 32867885,
3681 14515107, -15438304, 10819380},
3682 {4708026, 6336745, 20377586, 9066809, -11272109, 6594696, -25653668,
3683 12483688, -12668491, 5581306},
3684 {19563160, 16186464, -29386857, 4097519, 10237984, -4348115, 28542350,
3685 13850243, -23678021, -15815942},
3686 },
3687 {
3688 {5153746, 9909285, 1723747, -2777874, 30523605, 5516873, 19480852,
3689 5230134, -23952439, -15175766},
3690 {-30269007, -3463509, 7665486, 10083793, 28475525, 1649722, 20654025,
3691 16520125, 30598449, 7715701},
3692 {28881845, 14381568, 9657904, 3680757, -20181635, 7843316, -31400660,
3693 1370708, 29794553, -1409300},
3694 },
3695 {
3696 {-22518993, -6692182, 14201702, -8745502, -23510406, 8844726, 18474211,
3697 -1361450, -13062696, 13821877},
3698 {-6455177, -7839871, 3374702, -4740862, -27098617, -10571707, 31655028,
3699 -7212327, 18853322, -14220951},
3700 {4566830, -12963868, -28974889, -12240689, -7602672, -2830569, -8514358,
3701 -10431137, 2207753, -3209784},
3702 },
3703 {
3704 {-25154831, -4185821, 29681144, 7868801, -6854661, -9423865, -12437364,
3705 -663000, -31111463, -16132436},
3706 {25576264, -2703214, 7349804, -11814844, 16472782, 9300885, 3844789,
3707 15725684, 171356, 6466918},
3708 {23103977, 13316479, 9739013, -16149481, 817875, -15038942, 8965339,
3709 -14088058, -30714912, 16193877},
3710 },
3711 {
3712 {-33521811, 3180713, -2394130, 14003687, -16903474, -16270840, 17238398,
3713 4729455, -18074513, 9256800},
3714 {-25182317, -4174131, 32336398, 5036987, -21236817, 11360617, 22616405,
3715 9761698, -19827198, 630305},
3716 {-13720693, 2639453, -24237460, -7406481, 9494427, -5774029, -6554551,
3717 -15960994, -2449256, -14291300},
3718 },
3719 {
3720 {-3151181, -5046075, 9282714, 6866145, -31907062, -863023, -18940575,
3721 15033784, 25105118, -7894876},
3722 {-24326370, 15950226, -31801215, -14592823, -11662737, -5090925,
3723 1573892, -2625887, 2198790, -15804619},
3724 {-3099351, 10324967, -2241613, 7453183, -5446979, -2735503, -13812022,
3725 -16236442, -32461234, -12290683},
3726 },
3727};
3728
3729/* r = a * A + b * B
3730 * where a = a[0]+256*a[1]+...+256^31 a[31].
3731 * and b = b[0]+256*b[1]+...+256^31 b[31].
3732 * B is the Ed25519 base point (x,4/5) with x positive. */
3733static void
3734ge_double_scalarmult_vartime(ge_p2 *r, const uint8_t *a,
3735 const ge_p3 *A, const uint8_t *b) {
3736 signed char aslide[256];
3737 signed char bslide[256];
3738 ge_cached Ai[8]; /* A,3A,5A,7A,9A,11A,13A,15A */
3739 ge_p1p1 t;
3740 ge_p3 u;
3741 ge_p3 A2;
3742 int i;
3743
3744 slide(aslide, a);
3745 slide(bslide, b);
3746
3747 x25519_ge_p3_to_cached(&Ai[0], A);
3748 ge_p3_dbl(&t, A);
3749 x25519_ge_p1p1_to_p3(&A2, &t);
3750 x25519_ge_add(&t, &A2, &Ai[0]);
3751 x25519_ge_p1p1_to_p3(&u, &t);
3752 x25519_ge_p3_to_cached(&Ai[1], &u);
3753 x25519_ge_add(&t, &A2, &Ai[1]);
3754 x25519_ge_p1p1_to_p3(&u, &t);
3755 x25519_ge_p3_to_cached(&Ai[2], &u);
3756 x25519_ge_add(&t, &A2, &Ai[2]);
3757 x25519_ge_p1p1_to_p3(&u, &t);
3758 x25519_ge_p3_to_cached(&Ai[3], &u);
3759 x25519_ge_add(&t, &A2, &Ai[3]);
3760 x25519_ge_p1p1_to_p3(&u, &t);
3761 x25519_ge_p3_to_cached(&Ai[4], &u);
3762 x25519_ge_add(&t, &A2, &Ai[4]);
3763 x25519_ge_p1p1_to_p3(&u, &t);
3764 x25519_ge_p3_to_cached(&Ai[5], &u);
3765 x25519_ge_add(&t, &A2, &Ai[5]);
3766 x25519_ge_p1p1_to_p3(&u, &t);
3767 x25519_ge_p3_to_cached(&Ai[6], &u);
3768 x25519_ge_add(&t, &A2, &Ai[6]);
3769 x25519_ge_p1p1_to_p3(&u, &t);
3770 x25519_ge_p3_to_cached(&Ai[7], &u);
3771
3772 ge_p2_0(r);
3773
3774 for (i = 255; i >= 0; --i) {
3775 if (aslide[i] || bslide[i]) {
3776 break;
3777 }
3778 }
3779
3780 for (; i >= 0; --i) {
3781 ge_p2_dbl(&t, r);
3782
3783 if (aslide[i] > 0) {
3784 x25519_ge_p1p1_to_p3(&u, &t);
3785 x25519_ge_add(&t, &u, &Ai[aslide[i] / 2]);
3786 } else if (aslide[i] < 0) {
3787 x25519_ge_p1p1_to_p3(&u, &t);
3788 x25519_ge_sub(&t, &u, &Ai[(-aslide[i]) / 2]);
3789 }
3790
3791 if (bslide[i] > 0) {
3792 x25519_ge_p1p1_to_p3(&u, &t);
3793 ge_madd(&t, &u, &Bi[bslide[i] / 2]);
3794 } else if (bslide[i] < 0) {
3795 x25519_ge_p1p1_to_p3(&u, &t);
3796 ge_msub(&t, &u, &Bi[(-bslide[i]) / 2]);
3797 }
3798
3799 x25519_ge_p1p1_to_p2(r, &t);
3800 }
3801}
3802#endif
3803
3804/* The set of scalars is \Z/l
3805 * where l = 2^252 + 27742317777372353535851937790883648493. */
3806
3807/* Input:
3808 * s[0]+256*s[1]+...+256^63*s[63] = s
3809 *
3810 * Output:
3811 * s[0]+256*s[1]+...+256^31*s[31] = s mod l
3812 * where l = 2^252 + 27742317777372353535851937790883648493.
3813 * Overwrites s in place. */
3814void
3815x25519_sc_reduce(uint8_t *s) {
3816 int64_t s0 = 2097151 & load_3(s);
3817 int64_t s1 = 2097151 & (load_4(s + 2) >> 5);
3818 int64_t s2 = 2097151 & (load_3(s + 5) >> 2);
3819 int64_t s3 = 2097151 & (load_4(s + 7) >> 7);
3820 int64_t s4 = 2097151 & (load_4(s + 10) >> 4);
3821 int64_t s5 = 2097151 & (load_3(s + 13) >> 1);
3822 int64_t s6 = 2097151 & (load_4(s + 15) >> 6);
3823 int64_t s7 = 2097151 & (load_3(s + 18) >> 3);
3824 int64_t s8 = 2097151 & load_3(s + 21);
3825 int64_t s9 = 2097151 & (load_4(s + 23) >> 5);
3826 int64_t s10 = 2097151 & (load_3(s + 26) >> 2);
3827 int64_t s11 = 2097151 & (load_4(s + 28) >> 7);
3828 int64_t s12 = 2097151 & (load_4(s + 31) >> 4);
3829 int64_t s13 = 2097151 & (load_3(s + 34) >> 1);
3830 int64_t s14 = 2097151 & (load_4(s + 36) >> 6);
3831 int64_t s15 = 2097151 & (load_3(s + 39) >> 3);
3832 int64_t s16 = 2097151 & load_3(s + 42);
3833 int64_t s17 = 2097151 & (load_4(s + 44) >> 5);
3834 int64_t s18 = 2097151 & (load_3(s + 47) >> 2);
3835 int64_t s19 = 2097151 & (load_4(s + 49) >> 7);
3836 int64_t s20 = 2097151 & (load_4(s + 52) >> 4);
3837 int64_t s21 = 2097151 & (load_3(s + 55) >> 1);
3838 int64_t s22 = 2097151 & (load_4(s + 57) >> 6);
3839 int64_t s23 = (load_4(s + 60) >> 3);
3840 int64_t carry0;
3841 int64_t carry1;
3842 int64_t carry2;
3843 int64_t carry3;
3844 int64_t carry4;
3845 int64_t carry5;
3846 int64_t carry6;
3847 int64_t carry7;
3848 int64_t carry8;
3849 int64_t carry9;
3850 int64_t carry10;
3851 int64_t carry11;
3852 int64_t carry12;
3853 int64_t carry13;
3854 int64_t carry14;
3855 int64_t carry15;
3856 int64_t carry16;
3857
3858 s11 += s23 * 666643;
3859 s12 += s23 * 470296;
3860 s13 += s23 * 654183;
3861 s14 -= s23 * 997805;
3862 s15 += s23 * 136657;
3863 s16 -= s23 * 683901;
3864 s23 = 0;
3865
3866 s10 += s22 * 666643;
3867 s11 += s22 * 470296;
3868 s12 += s22 * 654183;
3869 s13 -= s22 * 997805;
3870 s14 += s22 * 136657;
3871 s15 -= s22 * 683901;
3872 s22 = 0;
3873
3874 s9 += s21 * 666643;
3875 s10 += s21 * 470296;
3876 s11 += s21 * 654183;
3877 s12 -= s21 * 997805;
3878 s13 += s21 * 136657;
3879 s14 -= s21 * 683901;
3880 s21 = 0;
3881
3882 s8 += s20 * 666643;
3883 s9 += s20 * 470296;
3884 s10 += s20 * 654183;
3885 s11 -= s20 * 997805;
3886 s12 += s20 * 136657;
3887 s13 -= s20 * 683901;
3888 s20 = 0;
3889
3890 s7 += s19 * 666643;
3891 s8 += s19 * 470296;
3892 s9 += s19 * 654183;
3893 s10 -= s19 * 997805;
3894 s11 += s19 * 136657;
3895 s12 -= s19 * 683901;
3896 s19 = 0;
3897
3898 s6 += s18 * 666643;
3899 s7 += s18 * 470296;
3900 s8 += s18 * 654183;
3901 s9 -= s18 * 997805;
3902 s10 += s18 * 136657;
3903 s11 -= s18 * 683901;
3904 s18 = 0;
3905
3906 carry6 = (s6 + (1 << 20)) >> 21;
3907 s7 += carry6;
3908 s6 -= carry6 << 21;
3909 carry8 = (s8 + (1 << 20)) >> 21;
3910 s9 += carry8;
3911 s8 -= carry8 << 21;
3912 carry10 = (s10 + (1 << 20)) >> 21;
3913 s11 += carry10;
3914 s10 -= carry10 << 21;
3915 carry12 = (s12 + (1 << 20)) >> 21;
3916 s13 += carry12;
3917 s12 -= carry12 << 21;
3918 carry14 = (s14 + (1 << 20)) >> 21;
3919 s15 += carry14;
3920 s14 -= carry14 << 21;
3921 carry16 = (s16 + (1 << 20)) >> 21;
3922 s17 += carry16;
3923 s16 -= carry16 << 21;
3924
3925 carry7 = (s7 + (1 << 20)) >> 21;
3926 s8 += carry7;
3927 s7 -= carry7 << 21;
3928 carry9 = (s9 + (1 << 20)) >> 21;
3929 s10 += carry9;
3930 s9 -= carry9 << 21;
3931 carry11 = (s11 + (1 << 20)) >> 21;
3932 s12 += carry11;
3933 s11 -= carry11 << 21;
3934 carry13 = (s13 + (1 << 20)) >> 21;
3935 s14 += carry13;
3936 s13 -= carry13 << 21;
3937 carry15 = (s15 + (1 << 20)) >> 21;
3938 s16 += carry15;
3939 s15 -= carry15 << 21;
3940
3941 s5 += s17 * 666643;
3942 s6 += s17 * 470296;
3943 s7 += s17 * 654183;
3944 s8 -= s17 * 997805;
3945 s9 += s17 * 136657;
3946 s10 -= s17 * 683901;
3947 s17 = 0;
3948
3949 s4 += s16 * 666643;
3950 s5 += s16 * 470296;
3951 s6 += s16 * 654183;
3952 s7 -= s16 * 997805;
3953 s8 += s16 * 136657;
3954 s9 -= s16 * 683901;
3955 s16 = 0;
Value stored to 's16' is never read
3956
3957 s3 += s15 * 666643;
3958 s4 += s15 * 470296;
3959 s5 += s15 * 654183;
3960 s6 -= s15 * 997805;
3961 s7 += s15 * 136657;
3962 s8 -= s15 * 683901;
3963 s15 = 0;
3964
3965 s2 += s14 * 666643;
3966 s3 += s14 * 470296;
3967 s4 += s14 * 654183;
3968 s5 -= s14 * 997805;
3969 s6 += s14 * 136657;
3970 s7 -= s14 * 683901;
3971 s14 = 0;
3972
3973 s1 += s13 * 666643;
3974 s2 += s13 * 470296;
3975 s3 += s13 * 654183;
3976 s4 -= s13 * 997805;
3977 s5 += s13 * 136657;
3978 s6 -= s13 * 683901;
3979 s13 = 0;
3980
3981 s0 += s12 * 666643;
3982 s1 += s12 * 470296;
3983 s2 += s12 * 654183;
3984 s3 -= s12 * 997805;
3985 s4 += s12 * 136657;
3986 s5 -= s12 * 683901;
3987 s12 = 0;
3988
3989 carry0 = (s0 + (1 << 20)) >> 21;
3990 s1 += carry0;
3991 s0 -= carry0 << 21;
3992 carry2 = (s2 + (1 << 20)) >> 21;
3993 s3 += carry2;
3994 s2 -= carry2 << 21;
3995 carry4 = (s4 + (1 << 20)) >> 21;
3996 s5 += carry4;
3997 s4 -= carry4 << 21;
3998 carry6 = (s6 + (1 << 20)) >> 21;
3999 s7 += carry6;
4000 s6 -= carry6 << 21;
4001 carry8 = (s8 + (1 << 20)) >> 21;
4002 s9 += carry8;
4003 s8 -= carry8 << 21;
4004 carry10 = (s10 + (1 << 20)) >> 21;
4005 s11 += carry10;
4006 s10 -= carry10 << 21;
4007
4008 carry1 = (s1 + (1 << 20)) >> 21;
4009 s2 += carry1;
4010 s1 -= carry1 << 21;
4011 carry3 = (s3 + (1 << 20)) >> 21;
4012 s4 += carry3;
4013 s3 -= carry3 << 21;
4014 carry5 = (s5 + (1 << 20)) >> 21;
4015 s6 += carry5;
4016 s5 -= carry5 << 21;
4017 carry7 = (s7 + (1 << 20)) >> 21;
4018 s8 += carry7;
4019 s7 -= carry7 << 21;
4020 carry9 = (s9 + (1 << 20)) >> 21;
4021 s10 += carry9;
4022 s9 -= carry9 << 21;
4023 carry11 = (s11 + (1 << 20)) >> 21;
4024 s12 += carry11;
4025 s11 -= carry11 << 21;
4026
4027 s0 += s12 * 666643;
4028 s1 += s12 * 470296;
4029 s2 += s12 * 654183;
4030 s3 -= s12 * 997805;
4031 s4 += s12 * 136657;
4032 s5 -= s12 * 683901;
4033 s12 = 0;
4034
4035 carry0 = s0 >> 21;
4036 s1 += carry0;
4037 s0 -= carry0 << 21;
4038 carry1 = s1 >> 21;
4039 s2 += carry1;
4040 s1 -= carry1 << 21;
4041 carry2 = s2 >> 21;
4042 s3 += carry2;
4043 s2 -= carry2 << 21;
4044 carry3 = s3 >> 21;
4045 s4 += carry3;
4046 s3 -= carry3 << 21;
4047 carry4 = s4 >> 21;
4048 s5 += carry4;
4049 s4 -= carry4 << 21;
4050 carry5 = s5 >> 21;
4051 s6 += carry5;
4052 s5 -= carry5 << 21;
4053 carry6 = s6 >> 21;
4054 s7 += carry6;
4055 s6 -= carry6 << 21;
4056 carry7 = s7 >> 21;
4057 s8 += carry7;
4058 s7 -= carry7 << 21;
4059 carry8 = s8 >> 21;
4060 s9 += carry8;
4061 s8 -= carry8 << 21;
4062 carry9 = s9 >> 21;
4063 s10 += carry9;
4064 s9 -= carry9 << 21;
4065 carry10 = s10 >> 21;
4066 s11 += carry10;
4067 s10 -= carry10 << 21;
4068 carry11 = s11 >> 21;
4069 s12 += carry11;
4070 s11 -= carry11 << 21;
4071
4072 s0 += s12 * 666643;
4073 s1 += s12 * 470296;
4074 s2 += s12 * 654183;
4075 s3 -= s12 * 997805;
4076 s4 += s12 * 136657;
4077 s5 -= s12 * 683901;
4078 s12 = 0;
4079
4080 carry0 = s0 >> 21;
4081 s1 += carry0;
4082 s0 -= carry0 << 21;
4083 carry1 = s1 >> 21;
4084 s2 += carry1;
4085 s1 -= carry1 << 21;
4086 carry2 = s2 >> 21;
4087 s3 += carry2;
4088 s2 -= carry2 << 21;
4089 carry3 = s3 >> 21;
4090 s4 += carry3;
4091 s3 -= carry3 << 21;
4092 carry4 = s4 >> 21;
4093 s5 += carry4;
4094 s4 -= carry4 << 21;
4095 carry5 = s5 >> 21;
4096 s6 += carry5;
4097 s5 -= carry5 << 21;
4098 carry6 = s6 >> 21;
4099 s7 += carry6;
4100 s6 -= carry6 << 21;
4101 carry7 = s7 >> 21;
4102 s8 += carry7;
4103 s7 -= carry7 << 21;
4104 carry8 = s8 >> 21;
4105 s9 += carry8;
4106 s8 -= carry8 << 21;
4107 carry9 = s9 >> 21;
4108 s10 += carry9;
4109 s9 -= carry9 << 21;
4110 carry10 = s10 >> 21;
4111 s11 += carry10;
4112 s10 -= carry10 << 21;
4113
4114 s[0] = s0 >> 0;
4115 s[1] = s0 >> 8;
4116 s[2] = (s0 >> 16) | (s1 << 5);
4117 s[3] = s1 >> 3;
4118 s[4] = s1 >> 11;
4119 s[5] = (s1 >> 19) | (s2 << 2);
4120 s[6] = s2 >> 6;
4121 s[7] = (s2 >> 14) | (s3 << 7);
4122 s[8] = s3 >> 1;
4123 s[9] = s3 >> 9;
4124 s[10] = (s3 >> 17) | (s4 << 4);
4125 s[11] = s4 >> 4;
4126 s[12] = s4 >> 12;
4127 s[13] = (s4 >> 20) | (s5 << 1);
4128 s[14] = s5 >> 7;
4129 s[15] = (s5 >> 15) | (s6 << 6);
4130 s[16] = s6 >> 2;
4131 s[17] = s6 >> 10;
4132 s[18] = (s6 >> 18) | (s7 << 3);
4133 s[19] = s7 >> 5;
4134 s[20] = s7 >> 13;
4135 s[21] = s8 >> 0;
4136 s[22] = s8 >> 8;
4137 s[23] = (s8 >> 16) | (s9 << 5);
4138 s[24] = s9 >> 3;
4139 s[25] = s9 >> 11;
4140 s[26] = (s9 >> 19) | (s10 << 2);
4141 s[27] = s10 >> 6;
4142 s[28] = (s10 >> 14) | (s11 << 7);
4143 s[29] = s11 >> 1;
4144 s[30] = s11 >> 9;
4145 s[31] = s11 >> 17;
4146}
4147
4148#ifdef ED25519
4149/* Input:
4150 * a[0]+256*a[1]+...+256^31*a[31] = a
4151 * b[0]+256*b[1]+...+256^31*b[31] = b
4152 * c[0]+256*c[1]+...+256^31*c[31] = c
4153 *
4154 * Output:
4155 * s[0]+256*s[1]+...+256^31*s[31] = (ab+c) mod l
4156 * where l = 2^252 + 27742317777372353535851937790883648493. */
4157static void
4158sc_muladd(uint8_t *s, const uint8_t *a, const uint8_t *b,
4159 const uint8_t *c)
4160{
4161 int64_t a0 = 2097151 & load_3(a);
4162 int64_t a1 = 2097151 & (load_4(a + 2) >> 5);
4163 int64_t a2 = 2097151 & (load_3(a + 5) >> 2);
4164 int64_t a3 = 2097151 & (load_4(a + 7) >> 7);
4165 int64_t a4 = 2097151 & (load_4(a + 10) >> 4);
4166 int64_t a5 = 2097151 & (load_3(a + 13) >> 1);
4167 int64_t a6 = 2097151 & (load_4(a + 15) >> 6);
4168 int64_t a7 = 2097151 & (load_3(a + 18) >> 3);
4169 int64_t a8 = 2097151 & load_3(a + 21);
4170 int64_t a9 = 2097151 & (load_4(a + 23) >> 5);
4171 int64_t a10 = 2097151 & (load_3(a + 26) >> 2);
4172 int64_t a11 = (load_4(a + 28) >> 7);
4173 int64_t b0 = 2097151 & load_3(b);
4174 int64_t b1 = 2097151 & (load_4(b + 2) >> 5);
4175 int64_t b2 = 2097151 & (load_3(b + 5) >> 2);
4176 int64_t b3 = 2097151 & (load_4(b + 7) >> 7);
4177 int64_t b4 = 2097151 & (load_4(b + 10) >> 4);
4178 int64_t b5 = 2097151 & (load_3(b + 13) >> 1);
4179 int64_t b6 = 2097151 & (load_4(b + 15) >> 6);
4180 int64_t b7 = 2097151 & (load_3(b + 18) >> 3);
4181 int64_t b8 = 2097151 & load_3(b + 21);
4182 int64_t b9 = 2097151 & (load_4(b + 23) >> 5);
4183 int64_t b10 = 2097151 & (load_3(b + 26) >> 2);
4184 int64_t b11 = (load_4(b + 28) >> 7);
4185 int64_t c0 = 2097151 & load_3(c);
4186 int64_t c1 = 2097151 & (load_4(c + 2) >> 5);
4187 int64_t c2 = 2097151 & (load_3(c + 5) >> 2);
4188 int64_t c3 = 2097151 & (load_4(c + 7) >> 7);
4189 int64_t c4 = 2097151 & (load_4(c + 10) >> 4);
4190 int64_t c5 = 2097151 & (load_3(c + 13) >> 1);
4191 int64_t c6 = 2097151 & (load_4(c + 15) >> 6);
4192 int64_t c7 = 2097151 & (load_3(c + 18) >> 3);
4193 int64_t c8 = 2097151 & load_3(c + 21);
4194 int64_t c9 = 2097151 & (load_4(c + 23) >> 5);
4195 int64_t c10 = 2097151 & (load_3(c + 26) >> 2);
4196 int64_t c11 = (load_4(c + 28) >> 7);
4197 int64_t s0;
4198 int64_t s1;
4199 int64_t s2;
4200 int64_t s3;
4201 int64_t s4;
4202 int64_t s5;
4203 int64_t s6;
4204 int64_t s7;
4205 int64_t s8;
4206 int64_t s9;
4207 int64_t s10;
4208 int64_t s11;
4209 int64_t s12;
4210 int64_t s13;
4211 int64_t s14;
4212 int64_t s15;
4213 int64_t s16;
4214 int64_t s17;
4215 int64_t s18;
4216 int64_t s19;
4217 int64_t s20;
4218 int64_t s21;
4219 int64_t s22;
4220 int64_t s23;
4221 int64_t carry0;
4222 int64_t carry1;
4223 int64_t carry2;
4224 int64_t carry3;
4225 int64_t carry4;
4226 int64_t carry5;
4227 int64_t carry6;
4228 int64_t carry7;
4229 int64_t carry8;
4230 int64_t carry9;
4231 int64_t carry10;
4232 int64_t carry11;
4233 int64_t carry12;
4234 int64_t carry13;
4235 int64_t carry14;
4236 int64_t carry15;
4237 int64_t carry16;
4238 int64_t carry17;
4239 int64_t carry18;
4240 int64_t carry19;
4241 int64_t carry20;
4242 int64_t carry21;
4243 int64_t carry22;
4244
4245 s0 = c0 + a0 * b0;
4246 s1 = c1 + a0 * b1 + a1 * b0;
4247 s2 = c2 + a0 * b2 + a1 * b1 + a2 * b0;
4248 s3 = c3 + a0 * b3 + a1 * b2 + a2 * b1 + a3 * b0;
4249 s4 = c4 + a0 * b4 + a1 * b3 + a2 * b2 + a3 * b1 + a4 * b0;
4250 s5 = c5 + a0 * b5 + a1 * b4 + a2 * b3 + a3 * b2 + a4 * b1 + a5 * b0;
4251 s6 = c6 + a0 * b6 + a1 * b5 + a2 * b4 + a3 * b3 + a4 * b2 + a5 * b1 + a6 * b0;
4252 s7 = c7 + a0 * b7 + a1 * b6 + a2 * b5 + a3 * b4 + a4 * b3 + a5 * b2 +
4253 a6 * b1 + a7 * b0;
4254 s8 = c8 + a0 * b8 + a1 * b7 + a2 * b6 + a3 * b5 + a4 * b4 + a5 * b3 +
4255 a6 * b2 + a7 * b1 + a8 * b0;
4256 s9 = c9 + a0 * b9 + a1 * b8 + a2 * b7 + a3 * b6 + a4 * b5 + a5 * b4 +
4257 a6 * b3 + a7 * b2 + a8 * b1 + a9 * b0;
4258 s10 = c10 + a0 * b10 + a1 * b9 + a2 * b8 + a3 * b7 + a4 * b6 + a5 * b5 +
4259 a6 * b4 + a7 * b3 + a8 * b2 + a9 * b1 + a10 * b0;
4260 s11 = c11 + a0 * b11 + a1 * b10 + a2 * b9 + a3 * b8 + a4 * b7 + a5 * b6 +
4261 a6 * b5 + a7 * b4 + a8 * b3 + a9 * b2 + a10 * b1 + a11 * b0;
4262 s12 = a1 * b11 + a2 * b10 + a3 * b9 + a4 * b8 + a5 * b7 + a6 * b6 + a7 * b5 +
4263 a8 * b4 + a9 * b3 + a10 * b2 + a11 * b1;
4264 s13 = a2 * b11 + a3 * b10 + a4 * b9 + a5 * b8 + a6 * b7 + a7 * b6 + a8 * b5 +
4265 a9 * b4 + a10 * b3 + a11 * b2;
4266 s14 = a3 * b11 + a4 * b10 + a5 * b9 + a6 * b8 + a7 * b7 + a8 * b6 + a9 * b5 +
4267 a10 * b4 + a11 * b3;
4268 s15 = a4 * b11 + a5 * b10 + a6 * b9 + a7 * b8 + a8 * b7 + a9 * b6 + a10 * b5 +
4269 a11 * b4;
4270 s16 = a5 * b11 + a6 * b10 + a7 * b9 + a8 * b8 + a9 * b7 + a10 * b6 + a11 * b5;
4271 s17 = a6 * b11 + a7 * b10 + a8 * b9 + a9 * b8 + a10 * b7 + a11 * b6;
4272 s18 = a7 * b11 + a8 * b10 + a9 * b9 + a10 * b8 + a11 * b7;
4273 s19 = a8 * b11 + a9 * b10 + a10 * b9 + a11 * b8;
4274 s20 = a9 * b11 + a10 * b10 + a11 * b9;
4275 s21 = a10 * b11 + a11 * b10;
4276 s22 = a11 * b11;
4277 s23 = 0;
4278
4279 carry0 = (s0 + (1 << 20)) >> 21;
4280 s1 += carry0;
4281 s0 -= carry0 << 21;
4282 carry2 = (s2 + (1 << 20)) >> 21;
4283 s3 += carry2;
4284 s2 -= carry2 << 21;
4285 carry4 = (s4 + (1 << 20)) >> 21;
4286 s5 += carry4;
4287 s4 -= carry4 << 21;
4288 carry6 = (s6 + (1 << 20)) >> 21;
4289 s7 += carry6;
4290 s6 -= carry6 << 21;
4291 carry8 = (s8 + (1 << 20)) >> 21;
4292 s9 += carry8;
4293 s8 -= carry8 << 21;
4294 carry10 = (s10 + (1 << 20)) >> 21;
4295 s11 += carry10;
4296 s10 -= carry10 << 21;
4297 carry12 = (s12 + (1 << 20)) >> 21;
4298 s13 += carry12;
4299 s12 -= carry12 << 21;
4300 carry14 = (s14 + (1 << 20)) >> 21;
4301 s15 += carry14;
4302 s14 -= carry14 << 21;
4303 carry16 = (s16 + (1 << 20)) >> 21;
4304 s17 += carry16;
4305 s16 -= carry16 << 21;
4306 carry18 = (s18 + (1 << 20)) >> 21;
4307 s19 += carry18;
4308 s18 -= carry18 << 21;
4309 carry20 = (s20 + (1 << 20)) >> 21;
4310 s21 += carry20;
4311 s20 -= carry20 << 21;
4312 carry22 = (s22 + (1 << 20)) >> 21;
4313 s23 += carry22;
4314 s22 -= carry22 << 21;
4315
4316 carry1 = (s1 + (1 << 20)) >> 21;
4317 s2 += carry1;
4318 s1 -= carry1 << 21;
4319 carry3 = (s3 + (1 << 20)) >> 21;
4320 s4 += carry3;
4321 s3 -= carry3 << 21;
4322 carry5 = (s5 + (1 << 20)) >> 21;
4323 s6 += carry5;
4324 s5 -= carry5 << 21;
4325 carry7 = (s7 + (1 << 20)) >> 21;
4326 s8 += carry7;
4327 s7 -= carry7 << 21;
4328 carry9 = (s9 + (1 << 20)) >> 21;
4329 s10 += carry9;
4330 s9 -= carry9 << 21;
4331 carry11 = (s11 + (1 << 20)) >> 21;
4332 s12 += carry11;
4333 s11 -= carry11 << 21;
4334 carry13 = (s13 + (1 << 20)) >> 21;
4335 s14 += carry13;
4336 s13 -= carry13 << 21;
4337 carry15 = (s15 + (1 << 20)) >> 21;
4338 s16 += carry15;
4339 s15 -= carry15 << 21;
4340 carry17 = (s17 + (1 << 20)) >> 21;
4341 s18 += carry17;
4342 s17 -= carry17 << 21;
4343 carry19 = (s19 + (1 << 20)) >> 21;
4344 s20 += carry19;
4345 s19 -= carry19 << 21;
4346 carry21 = (s21 + (1 << 20)) >> 21;
4347 s22 += carry21;
4348 s21 -= carry21 << 21;
4349
4350 s11 += s23 * 666643;
4351 s12 += s23 * 470296;
4352 s13 += s23 * 654183;
4353 s14 -= s23 * 997805;
4354 s15 += s23 * 136657;
4355 s16 -= s23 * 683901;
4356 s23 = 0;
4357
4358 s10 += s22 * 666643;
4359 s11 += s22 * 470296;
4360 s12 += s22 * 654183;
4361 s13 -= s22 * 997805;
4362 s14 += s22 * 136657;
4363 s15 -= s22 * 683901;
4364 s22 = 0;
4365
4366 s9 += s21 * 666643;
4367 s10 += s21 * 470296;
4368 s11 += s21 * 654183;
4369 s12 -= s21 * 997805;
4370 s13 += s21 * 136657;
4371 s14 -= s21 * 683901;
4372 s21 = 0;
4373
4374 s8 += s20 * 666643;
4375 s9 += s20 * 470296;
4376 s10 += s20 * 654183;
4377 s11 -= s20 * 997805;
4378 s12 += s20 * 136657;
4379 s13 -= s20 * 683901;
4380 s20 = 0;
4381
4382 s7 += s19 * 666643;
4383 s8 += s19 * 470296;
4384 s9 += s19 * 654183;
4385 s10 -= s19 * 997805;
4386 s11 += s19 * 136657;
4387 s12 -= s19 * 683901;
4388 s19 = 0;
4389
4390 s6 += s18 * 666643;
4391 s7 += s18 * 470296;
4392 s8 += s18 * 654183;
4393 s9 -= s18 * 997805;
4394 s10 += s18 * 136657;
4395 s11 -= s18 * 683901;
4396 s18 = 0;
4397
4398 carry6 = (s6 + (1 << 20)) >> 21;
4399 s7 += carry6;
4400 s6 -= carry6 << 21;
4401 carry8 = (s8 + (1 << 20)) >> 21;
4402 s9 += carry8;
4403 s8 -= carry8 << 21;
4404 carry10 = (s10 + (1 << 20)) >> 21;
4405 s11 += carry10;
4406 s10 -= carry10 << 21;
4407 carry12 = (s12 + (1 << 20)) >> 21;
4408 s13 += carry12;
4409 s12 -= carry12 << 21;
4410 carry14 = (s14 + (1 << 20)) >> 21;
4411 s15 += carry14;
4412 s14 -= carry14 << 21;
4413 carry16 = (s16 + (1 << 20)) >> 21;
4414 s17 += carry16;
4415 s16 -= carry16 << 21;
4416
4417 carry7 = (s7 + (1 << 20)) >> 21;
4418 s8 += carry7;
4419 s7 -= carry7 << 21;
4420 carry9 = (s9 + (1 << 20)) >> 21;
4421 s10 += carry9;
4422 s9 -= carry9 << 21;
4423 carry11 = (s11 + (1 << 20)) >> 21;
4424 s12 += carry11;
4425 s11 -= carry11 << 21;
4426 carry13 = (s13 + (1 << 20)) >> 21;
4427 s14 += carry13;
4428 s13 -= carry13 << 21;
4429 carry15 = (s15 + (1 << 20)) >> 21;
4430 s16 += carry15;
4431 s15 -= carry15 << 21;
4432
4433 s5 += s17 * 666643;
4434 s6 += s17 * 470296;
4435 s7 += s17 * 654183;
4436 s8 -= s17 * 997805;
4437 s9 += s17 * 136657;
4438 s10 -= s17 * 683901;
4439 s17 = 0;
4440
4441 s4 += s16 * 666643;
4442 s5 += s16 * 470296;
4443 s6 += s16 * 654183;
4444 s7 -= s16 * 997805;
4445 s8 += s16 * 136657;
4446 s9 -= s16 * 683901;
4447 s16 = 0;
4448
4449 s3 += s15 * 666643;
4450 s4 += s15 * 470296;
4451 s5 += s15 * 654183;
4452 s6 -= s15 * 997805;
4453 s7 += s15 * 136657;
4454 s8 -= s15 * 683901;
4455 s15 = 0;
4456
4457 s2 += s14 * 666643;
4458 s3 += s14 * 470296;
4459 s4 += s14 * 654183;
4460 s5 -= s14 * 997805;
4461 s6 += s14 * 136657;
4462 s7 -= s14 * 683901;
4463 s14 = 0;
4464
4465 s1 += s13 * 666643;
4466 s2 += s13 * 470296;
4467 s3 += s13 * 654183;
4468 s4 -= s13 * 997805;
4469 s5 += s13 * 136657;
4470 s6 -= s13 * 683901;
4471 s13 = 0;
4472
4473 s0 += s12 * 666643;
4474 s1 += s12 * 470296;
4475 s2 += s12 * 654183;
4476 s3 -= s12 * 997805;
4477 s4 += s12 * 136657;
4478 s5 -= s12 * 683901;
4479 s12 = 0;
4480
4481 carry0 = (s0 + (1 << 20)) >> 21;
4482 s1 += carry0;
4483 s0 -= carry0 << 21;
4484 carry2 = (s2 + (1 << 20)) >> 21;
4485 s3 += carry2;
4486 s2 -= carry2 << 21;
4487 carry4 = (s4 + (1 << 20)) >> 21;
4488 s5 += carry4;
4489 s4 -= carry4 << 21;
4490 carry6 = (s6 + (1 << 20)) >> 21;
4491 s7 += carry6;
4492 s6 -= carry6 << 21;
4493 carry8 = (s8 + (1 << 20)) >> 21;
4494 s9 += carry8;
4495 s8 -= carry8 << 21;
4496 carry10 = (s10 + (1 << 20)) >> 21;
4497 s11 += carry10;
4498 s10 -= carry10 << 21;
4499
4500 carry1 = (s1 + (1 << 20)) >> 21;
4501 s2 += carry1;
4502 s1 -= carry1 << 21;
4503 carry3 = (s3 + (1 << 20)) >> 21;
4504 s4 += carry3;
4505 s3 -= carry3 << 21;
4506 carry5 = (s5 + (1 << 20)) >> 21;
4507 s6 += carry5;
4508 s5 -= carry5 << 21;
4509 carry7 = (s7 + (1 << 20)) >> 21;
4510 s8 += carry7;
4511 s7 -= carry7 << 21;
4512 carry9 = (s9 + (1 << 20)) >> 21;
4513 s10 += carry9;
4514 s9 -= carry9 << 21;
4515 carry11 = (s11 + (1 << 20)) >> 21;
4516 s12 += carry11;
4517 s11 -= carry11 << 21;
4518
4519 s0 += s12 * 666643;
4520 s1 += s12 * 470296;
4521 s2 += s12 * 654183;
4522 s3 -= s12 * 997805;
4523 s4 += s12 * 136657;
4524 s5 -= s12 * 683901;
4525 s12 = 0;
4526
4527 carry0 = s0 >> 21;
4528 s1 += carry0;
4529 s0 -= carry0 << 21;
4530 carry1 = s1 >> 21;
4531 s2 += carry1;
4532 s1 -= carry1 << 21;
4533 carry2 = s2 >> 21;
4534 s3 += carry2;
4535 s2 -= carry2 << 21;
4536 carry3 = s3 >> 21;
4537 s4 += carry3;
4538 s3 -= carry3 << 21;
4539 carry4 = s4 >> 21;
4540 s5 += carry4;
4541 s4 -= carry4 << 21;
4542 carry5 = s5 >> 21;
4543 s6 += carry5;
4544 s5 -= carry5 << 21;
4545 carry6 = s6 >> 21;
4546 s7 += carry6;
4547 s6 -= carry6 << 21;
4548 carry7 = s7 >> 21;
4549 s8 += carry7;
4550 s7 -= carry7 << 21;
4551 carry8 = s8 >> 21;
4552 s9 += carry8;
4553 s8 -= carry8 << 21;
4554 carry9 = s9 >> 21;
4555 s10 += carry9;
4556 s9 -= carry9 << 21;
4557 carry10 = s10 >> 21;
4558 s11 += carry10;
4559 s10 -= carry10 << 21;
4560 carry11 = s11 >> 21;
4561 s12 += carry11;
4562 s11 -= carry11 << 21;
4563
4564 s0 += s12 * 666643;
4565 s1 += s12 * 470296;
4566 s2 += s12 * 654183;
4567 s3 -= s12 * 997805;
4568 s4 += s12 * 136657;
4569 s5 -= s12 * 683901;
4570 s12 = 0;
4571
4572 carry0 = s0 >> 21;
4573 s1 += carry0;
4574 s0 -= carry0 << 21;
4575 carry1 = s1 >> 21;
4576 s2 += carry1;
4577 s1 -= carry1 << 21;
4578 carry2 = s2 >> 21;
4579 s3 += carry2;
4580 s2 -= carry2 << 21;
4581 carry3 = s3 >> 21;
4582 s4 += carry3;
4583 s3 -= carry3 << 21;
4584 carry4 = s4 >> 21;
4585 s5 += carry4;
4586 s4 -= carry4 << 21;
4587 carry5 = s5 >> 21;
4588 s6 += carry5;
4589 s5 -= carry5 << 21;
4590 carry6 = s6 >> 21;
4591 s7 += carry6;
4592 s6 -= carry6 << 21;
4593 carry7 = s7 >> 21;
4594 s8 += carry7;
4595 s7 -= carry7 << 21;
4596 carry8 = s8 >> 21;
4597 s9 += carry8;
4598 s8 -= carry8 << 21;
4599 carry9 = s9 >> 21;
4600 s10 += carry9;
4601 s9 -= carry9 << 21;
4602 carry10 = s10 >> 21;
4603 s11 += carry10;
4604 s10 -= carry10 << 21;
4605
4606 s[0] = s0 >> 0;
4607 s[1] = s0 >> 8;
4608 s[2] = (s0 >> 16) | (s1 << 5);
4609 s[3] = s1 >> 3;
4610 s[4] = s1 >> 11;
4611 s[5] = (s1 >> 19) | (s2 << 2);
4612 s[6] = s2 >> 6;
4613 s[7] = (s2 >> 14) | (s3 << 7);
4614 s[8] = s3 >> 1;
4615 s[9] = s3 >> 9;
4616 s[10] = (s3 >> 17) | (s4 << 4);
4617 s[11] = s4 >> 4;
4618 s[12] = s4 >> 12;
4619 s[13] = (s4 >> 20) | (s5 << 1);
4620 s[14] = s5 >> 7;
4621 s[15] = (s5 >> 15) | (s6 << 6);
4622 s[16] = s6 >> 2;
4623 s[17] = s6 >> 10;
4624 s[18] = (s6 >> 18) | (s7 << 3);
4625 s[19] = s7 >> 5;
4626 s[20] = s7 >> 13;
4627 s[21] = s8 >> 0;
4628 s[22] = s8 >> 8;
4629 s[23] = (s8 >> 16) | (s9 << 5);
4630 s[24] = s9 >> 3;
4631 s[25] = s9 >> 11;
4632 s[26] = (s9 >> 19) | (s10 << 2);
4633 s[27] = s10 >> 6;
4634 s[28] = (s10 >> 14) | (s11 << 7);
4635 s[29] = s11 >> 1;
4636 s[30] = s11 >> 9;
4637 s[31] = s11 >> 17;
4638}
4639#endif
4640
4641#ifdef ED25519
4642void ED25519_keypair(uint8_t out_public_key[32], uint8_t out_private_key[64]) {
4643 uint8_t seed[32];
4644 arc4random_buf(seed, 32);
4645
4646 uint8_t az[SHA512_DIGEST_LENGTH];
4647 SHA512(seed, 32, az);
4648
4649 az[0] &= 248;
4650 az[31] &= 63;
4651 az[31] |= 64;
4652
4653 ge_p3 A;
4654 x25519_ge_scalarmult_base(&A, az);
4655 ge_p3_tobytes(out_public_key, &A);
4656
4657 memcpy(out_private_key, seed, 32);
4658 memmove(out_private_key + 32, out_public_key, 32);
4659}
4660
4661int ED25519_sign(uint8_t *out_sig, const uint8_t *message, size_t message_len,
4662 const uint8_t private_key[64]) {
4663 uint8_t az[SHA512_DIGEST_LENGTH];
4664 SHA512(private_key, 32, az);
4665
4666 az[0] &= 248;
4667 az[31] &= 63;
4668 az[31] |= 64;
4669
4670 SHA512_CTX hash_ctx;
4671 SHA512_Init(&hash_ctx);
4672 SHA512_Update(&hash_ctx, az + 32, 32);
4673 SHA512_Update(&hash_ctx, message, message_len);
4674 uint8_t nonce[SHA512_DIGEST_LENGTH];
4675 SHA512_Final(nonce, &hash_ctx);
4676
4677 x25519_sc_reduce(nonce);
4678 ge_p3 R;
4679 x25519_ge_scalarmult_base(&R, nonce);
4680 ge_p3_tobytes(out_sig, &R);
4681
4682 SHA512_Init(&hash_ctx);
4683 SHA512_Update(&hash_ctx, out_sig, 32);
4684 SHA512_Update(&hash_ctx, private_key + 32, 32);
4685 SHA512_Update(&hash_ctx, message, message_len);
4686 uint8_t hram[SHA512_DIGEST_LENGTH];
4687 SHA512_Final(hram, &hash_ctx);
4688
4689 x25519_sc_reduce(hram);
4690 sc_muladd(out_sig + 32, hram, az, nonce);
4691
4692 return 1;
4693}
4694
4695int ED25519_verify(const uint8_t *message, size_t message_len,
4696 const uint8_t signature[64], const uint8_t public_key[32]) {
4697 ge_p3 A;
4698 if ((signature[63] & 224) != 0 ||
4699 x25519_ge_frombytes_vartime(&A, public_key) != 0) {
4700 return 0;
4701 }
4702
4703 fe_neg(A.X, A.X);
4704 fe_neg(A.T, A.T);
4705
4706 uint8_t pkcopy[32];
4707 memcpy(pkcopy, public_key, 32);
4708 uint8_t rcopy[32];
4709 memcpy(rcopy, signature, 32);
4710 uint8_t scopy[32];
4711 memcpy(scopy, signature + 32, 32);
4712
4713 SHA512_CTX hash_ctx;
4714 SHA512_Init(&hash_ctx);
4715 SHA512_Update(&hash_ctx, signature, 32);
4716 SHA512_Update(&hash_ctx, public_key, 32);
4717 SHA512_Update(&hash_ctx, message, message_len);
4718 uint8_t h[SHA512_DIGEST_LENGTH];
4719 SHA512_Final(h, &hash_ctx);
4720
4721 x25519_sc_reduce(h);
4722
4723 ge_p2 R;
4724 ge_double_scalarmult_vartime(&R, h, &A, scopy);
4725
4726 uint8_t rcheck[32];
4727 x25519_ge_tobytes(rcheck, &R);
4728
4729 return timingsafe_memcmp(rcheck, rcopy, sizeof(rcheck)) == 0;
4730}
4731#endif
4732
4733/* Replace (f,g) with (g,f) if b == 1;
4734 * replace (f,g) with (f,g) if b == 0.
4735 *
4736 * Preconditions: b in {0,1}. */
4737static void fe_cswap(fe f, fe g, unsigned int b) {
4738 b = 0-b;
4739 unsigned i;
4740 for (i = 0; i < 10; i++) {
4741 int32_t x = f[i] ^ g[i];
4742 x &= b;
4743 f[i] ^= x;
4744 g[i] ^= x;
4745 }
4746}
4747
4748/* h = f * 121666
4749 * Can overlap h with f.
4750 *
4751 * Preconditions:
4752 * |f| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc.
4753 *
4754 * Postconditions:
4755 * |h| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. */
4756static void fe_mul121666(fe h, fe f) {
4757 int32_t f0 = f[0];
4758 int32_t f1 = f[1];
4759 int32_t f2 = f[2];
4760 int32_t f3 = f[3];
4761 int32_t f4 = f[4];
4762 int32_t f5 = f[5];
4763 int32_t f6 = f[6];
4764 int32_t f7 = f[7];
4765 int32_t f8 = f[8];
4766 int32_t f9 = f[9];
4767 int64_t h0 = f0 * (int64_t) 121666;
4768 int64_t h1 = f1 * (int64_t) 121666;
4769 int64_t h2 = f2 * (int64_t) 121666;
4770 int64_t h3 = f3 * (int64_t) 121666;
4771 int64_t h4 = f4 * (int64_t) 121666;
4772 int64_t h5 = f5 * (int64_t) 121666;
4773 int64_t h6 = f6 * (int64_t) 121666;
4774 int64_t h7 = f7 * (int64_t) 121666;
4775 int64_t h8 = f8 * (int64_t) 121666;
4776 int64_t h9 = f9 * (int64_t) 121666;
4777 int64_t carry0;
4778 int64_t carry1;
4779 int64_t carry2;
4780 int64_t carry3;
4781 int64_t carry4;
4782 int64_t carry5;
4783 int64_t carry6;
4784 int64_t carry7;
4785 int64_t carry8;
4786 int64_t carry9;
4787
4788 carry9 = h9 + (1 << 24); h0 += (carry9 >> 25) * 19; h9 -= carry9 & kTop39Bits;
4789 carry1 = h1 + (1 << 24); h2 += carry1 >> 25; h1 -= carry1 & kTop39Bits;
4790 carry3 = h3 + (1 << 24); h4 += carry3 >> 25; h3 -= carry3 & kTop39Bits;
4791 carry5 = h5 + (1 << 24); h6 += carry5 >> 25; h5 -= carry5 & kTop39Bits;
4792 carry7 = h7 + (1 << 24); h8 += carry7 >> 25; h7 -= carry7 & kTop39Bits;
4793
4794 carry0 = h0 + (1 << 25); h1 += carry0 >> 26; h0 -= carry0 & kTop38Bits;
4795 carry2 = h2 + (1 << 25); h3 += carry2 >> 26; h2 -= carry2 & kTop38Bits;
4796 carry4 = h4 + (1 << 25); h5 += carry4 >> 26; h4 -= carry4 & kTop38Bits;
4797 carry6 = h6 + (1 << 25); h7 += carry6 >> 26; h6 -= carry6 & kTop38Bits;
4798 carry8 = h8 + (1 << 25); h9 += carry8 >> 26; h8 -= carry8 & kTop38Bits;
4799
4800 h[0] = h0;
4801 h[1] = h1;
4802 h[2] = h2;
4803 h[3] = h3;
4804 h[4] = h4;
4805 h[5] = h5;
4806 h[6] = h6;
4807 h[7] = h7;
4808 h[8] = h8;
4809 h[9] = h9;
4810}
4811
4812void
4813x25519_scalar_mult_generic(uint8_t out[32], const uint8_t scalar[32],
4814 const uint8_t point[32]) {
4815 fe x1, x2, z2, x3, z3, tmp0, tmp1;
4816
4817 uint8_t e[32];
4818 memcpy(e, scalar, 32);
4819 e[0] &= 248;
4820 e[31] &= 127;
4821 e[31] |= 64;
4822 fe_frombytes(x1, point);
4823 fe_1(x2);
4824 fe_0(z2);
4825 fe_copy(x3, x1);
4826 fe_1(z3);
4827
4828 unsigned swap = 0;
4829 int pos;
4830 for (pos = 254; pos >= 0; --pos) {
4831 unsigned b = 1 & (e[pos / 8] >> (pos & 7));
4832 swap ^= b;
4833 fe_cswap(x2, x3, swap);
4834 fe_cswap(z2, z3, swap);
4835 swap = b;
4836 fe_sub(tmp0, x3, z3);
4837 fe_sub(tmp1, x2, z2);
4838 fe_add(x2, x2, z2);
4839 fe_add(z2, x3, z3);
4840 fe_mul(z3, tmp0, x2);
4841 fe_mul(z2, z2, tmp1);
4842 fe_sq(tmp0, tmp1);
4843 fe_sq(tmp1, x2);
4844 fe_add(x3, z3, z2);
4845 fe_sub(z2, z3, z2);
4846 fe_mul(x2, tmp1, tmp0);
4847 fe_sub(tmp1, tmp1, tmp0);
4848 fe_sq(z2, z2);
4849 fe_mul121666(z3, tmp1);
4850 fe_sq(x3, x3);
4851 fe_add(tmp0, tmp0, z3);
4852 fe_mul(z3, x1, z2);
4853 fe_mul(z2, tmp1, tmp0);
4854 }
4855 fe_cswap(x2, x3, swap);
4856 fe_cswap(z2, z3, swap);
4857
4858 fe_invert(z2, z2);
4859 fe_mul(x2, x2, z2);
4860 fe_tobytes(out, x2);
4861}
4862
4863#ifdef unused
4864void
4865x25519_public_from_private_generic(uint8_t out_public_value[32],
4866 const uint8_t private_key[32])
4867{
4868 uint8_t e[32];
4869
4870 memcpy(e, private_key, 32);
4871 e[0] &= 248;
4872 e[31] &= 127;
4873 e[31] |= 64;
4874
4875 ge_p3 A;
4876 x25519_ge_scalarmult_base(&A, e);
4877
4878 /* We only need the u-coordinate of the curve25519 point. The map is
4879 * u=(y+1)/(1-y). Since y=Y/Z, this gives u=(Z+Y)/(Z-Y). */
4880 fe zplusy, zminusy, zminusy_inv;
4881 fe_add(zplusy, A.Z, A.Y);
4882 fe_sub(zminusy, A.Z, A.Y);
4883 fe_invert(zminusy_inv, zminusy);
4884 fe_mul(zplusy, zplusy, zminusy_inv);
4885 fe_tobytes(out_public_value, zplusy);
4886}
4887#endif
4888
4889void
4890x25519_public_from_private(uint8_t out_public_value[32],
4891 const uint8_t private_key[32])
4892{
4893 static const uint8_t kMongomeryBasePoint[32] = {9};
4894
4895 x25519_scalar_mult(out_public_value, private_key, kMongomeryBasePoint);
4896}
4897
4898void
4899X25519_keypair(uint8_t out_public_value[X25519_KEY_LENGTH32],
4900 uint8_t out_private_key[X25519_KEY_LENGTH32])
4901{
4902 /* All X25519 implementations should decode scalars correctly (see
4903 * https://tools.ietf.org/html/rfc7748#section-5). However, if an
4904 * implementation doesn't then it might interoperate with random keys a
4905 * fraction of the time because they'll, randomly, happen to be correctly
4906 * formed.
4907 *
4908 * Thus we do the opposite of the masking here to make sure that our private
4909 * keys are never correctly masked and so, hopefully, any incorrect
4910 * implementations are deterministically broken.
4911 *
4912 * This does not affect security because, although we're throwing away
4913 * entropy, a valid implementation of scalarmult should throw away the exact
4914 * same bits anyway. */
4915 arc4random_buf(out_private_key, 32);
4916
4917 out_private_key[0] |= 7;
4918 out_private_key[31] &= 63;
4919 out_private_key[31] |= 128;
4920
4921 x25519_public_from_private(out_public_value, out_private_key);
4922}
4923
4924int
4925X25519(uint8_t out_shared_key[X25519_KEY_LENGTH32],
4926 const uint8_t private_key[X25519_KEY_LENGTH32],
4927 const uint8_t peer_public_value[X25519_KEY_LENGTH32])
4928{
4929 static const uint8_t kZeros[32] = {0};
4930
4931 x25519_scalar_mult(out_shared_key, private_key, peer_public_value);
4932
4933 /* The all-zero output results when the input is a point of small order. */
4934 return timingsafe_memcmp(kZeros, out_shared_key, 32) != 0;
4935}