Leancrypto 1.6.0
Post-Quantum Cryptographic Library
Loading...
Searching...
No Matches
lc_sphincs_shake_192s.h
Go to the documentation of this file.
1/*
2 * Copyright (C) 2024 - 2025, Stephan Mueller <smueller@chronox.de>
3 *
4 * License: see LICENSE file in root directory
5 *
6 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
7 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
8 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE, ALL OF
9 * WHICH ARE HEREBY DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE
10 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
11 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
12 * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
13 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
14 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
15 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
16 * USE OF THIS SOFTWARE, EVEN IF NOT ADVISED OF THE POSSIBILITY OF SUCH
17 * DAMAGE.
18 */
19/*
20 * This code is derived in parts from the code distribution provided with
21 * https://github.com/sphincs/sphincsplus
22 *
23 * That code is released under Public Domain
24 * (https://creativecommons.org/share-your-work/public-domain/cc0/).
25 */
26
27#ifndef LC_SPHINCS_SHAKE_192S_H
28#define LC_SPHINCS_SHAKE_192S_H
29
30#include "ext_headers.h"
31#include "lc_ascon_hash.h"
32#include "lc_hash.h"
33#include "lc_rng.h"
34#include "lc_sha3.h"
35
36#ifdef __cplusplus
37extern "C" {
38#endif
39
41
42/*
43 * Sphincs Plus security strength definition: Due to having multiple parameter
44 * sets per security strength, the "security strenght" is given in signature
45 * size.
46 *
47 * 7856 -> Sphincs Plus SHAKE 128s
48 * 17088 -> Sphincs Plus SHAKE 128f
49 * 16224 -> Sphincs Plus SHAKE 192s
50 * 35664 -> Sphincs Plus SHAKE 192f
51 * 29792 -> Sphincs Plus SHAKE 256s
52 * 49856 -> Sphincs Plus SHAKE 256f
53 */
54#define LC_SPHINCS_MODE 16224
55#define LC_SPHINCS_HASH_TYPE lc_shake256
56
57#if LC_SPHINCS_MODE == 7856
58
59#define LC_SPHINCS_NIST_CATEGORY 1
60
61/* Hash output length in bytes. */
62#define LC_SPX_N 16
63/* Height of the hypertree. */
64#define LC_SPX_FULL_HEIGHT 63
65/* Number of subtree layer. */
66#define LC_SPX_D 7
67/* FORS tree dimensions. */
68#define LC_SPX_FORS_HEIGHT 12
69#define LC_SPX_FORS_TREES 14
70/* Winternitz parameter, */
71#define LC_SPX_WOTS_W 16
72
73/* The hash function is defined by linking a different hash.c file, as opposed
74 to setting a #define constant. */
75
76/* For clarity */
77#define LC_SPX_ADDR_BYTES 32
78
79/* WOTS parameters. */
80#if LC_SPX_WOTS_W == 256
81 #define LC_SPX_WOTS_LOGW 8
82#elif LC_SPX_WOTS_W == 16
83 #define LC_SPX_WOTS_LOGW 4
84#else
85 #error LC_SPX_WOTS_W assumed 16 or 256
86#endif
87
88#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
89
90/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
91#if LC_SPX_WOTS_W == 256
92 #if LC_SPX_N <= 1
93 #define LC_SPX_WOTS_LEN2 1
94 #elif LC_SPX_N <= 256
95 #define LC_SPX_WOTS_LEN2 2
96 #else
97 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
98 #endif
99#elif LC_SPX_WOTS_W == 16
100 #if LC_SPX_N <= 8
101 #define LC_SPX_WOTS_LEN2 2
102 #elif LC_SPX_N <= 136
103 #define LC_SPX_WOTS_LEN2 3
104 #elif LC_SPX_N <= 256
105 #define LC_SPX_WOTS_LEN2 4
106 #else
107 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
108 #endif
109#endif
110
111#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
112#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
113#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
114
115/* Subtree size. */
116#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
117
118#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
119 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
120#endif
121
122/* FORS parameters. */
123#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
124#define LC_SPX_FORS_BYTES ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
125#define LC_SPX_FORS_PK_BYTES LC_SPX_N
126
127/* Resulting LC_SPX sizes. */
128#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
129 LC_SPX_FULL_HEIGHT * LC_SPX_N)
130#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
131#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
132
133#elif LC_SPHINCS_MODE == 17088
134
135#define LC_SPHINCS_NIST_CATEGORY 1
136
137/* Hash output length in bytes. */
138#define LC_SPX_N 16
139/* Height of the hypertree. */
140#define LC_SPX_FULL_HEIGHT 66
141/* Number of subtree layer. */
142#define LC_SPX_D 22
143/* FORS tree dimensions. */
144#define LC_SPX_FORS_HEIGHT 6
145#define LC_SPX_FORS_TREES 33
146/* Winternitz parameter, */
147#define LC_SPX_WOTS_W 16
148
149/* The hash function is defined by linking a different hash.c file, as opposed
150 to setting a #define constant. */
151
152/* For clarity */
153#define LC_SPX_ADDR_BYTES 32
154
155/* WOTS parameters. */
156#if LC_SPX_WOTS_W == 256
157 #define LC_SPX_WOTS_LOGW 8
158#elif LC_SPX_WOTS_W == 16
159 #define LC_SPX_WOTS_LOGW 4
160#else
161 #error LC_SPX_WOTS_W assumed 16 or 256
162#endif
163
164#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
165
166/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
167#if LC_SPX_WOTS_W == 256
168 #if LC_SPX_N <= 1
169 #define LC_SPX_WOTS_LEN2 1
170 #elif LC_SPX_N <= 256
171 #define LC_SPX_WOTS_LEN2 2
172 #else
173 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
174 #endif
175#elif LC_SPX_WOTS_W == 16
176 #if LC_SPX_N <= 8
177 #define LC_SPX_WOTS_LEN2 2
178 #elif LC_SPX_N <= 136
179 #define LC_SPX_WOTS_LEN2 3
180 #elif LC_SPX_N <= 256
181 #define LC_SPX_WOTS_LEN2 4
182 #else
183 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
184 #endif
185#endif
186
187#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
188#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
189#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
190
191/* Subtree size. */
192#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
193
194#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
195 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
196#endif
197
198/* FORS parameters. */
199#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
200#define LC_SPX_FORS_BYTES ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
201#define LC_SPX_FORS_PK_BYTES LC_SPX_N
202
203/* Resulting LC_SPX sizes. */
204#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
205 LC_SPX_FULL_HEIGHT * LC_SPX_N)
206#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
207#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
208
209#elif LC_SPHINCS_MODE == 16224
210
211#define LC_SPHINCS_NIST_CATEGORY 3
212
213/* Hash output length in bytes. */
214#define LC_SPX_N 24
215/* Height of the hypertree. */
216#define LC_SPX_FULL_HEIGHT 63
217/* Number of subtree layer. */
218#define LC_SPX_D 7
219/* FORS tree dimensions. */
220#define LC_SPX_FORS_HEIGHT 14
221#define LC_SPX_FORS_TREES 17
222/* Winternitz parameter, */
223#define LC_SPX_WOTS_W 16
224
225/* The hash function is defined by linking a different hash.c file, as opposed
226 to setting a #define constant. */
227
228/* For clarity */
229#define LC_SPX_ADDR_BYTES 32
230
231/* WOTS parameters. */
232#if LC_SPX_WOTS_W == 256
233 #define LC_SPX_WOTS_LOGW 8
234#elif LC_SPX_WOTS_W == 16
235 #define LC_SPX_WOTS_LOGW 4
236#else
237 #error LC_SPX_WOTS_W assumed 16 or 256
238#endif
239
240#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
241
242/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
243#if LC_SPX_WOTS_W == 256
244 #if LC_SPX_N <= 1
245 #define LC_SPX_WOTS_LEN2 1
246 #elif LC_SPX_N <= 256
247 #define LC_SPX_WOTS_LEN2 2
248 #else
249 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
250 #endif
251#elif LC_SPX_WOTS_W == 16
252 #if LC_SPX_N <= 8
253 #define LC_SPX_WOTS_LEN2 2
254 #elif LC_SPX_N <= 136
255 #define LC_SPX_WOTS_LEN2 3
256 #elif LC_SPX_N <= 256
257 #define LC_SPX_WOTS_LEN2 4
258 #else
259 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
260 #endif
261#endif
262
263#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
264#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
265#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
266
267/* Subtree size. */
268#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
269
270#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
271 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
272#endif
273
274/* FORS parameters. */
275#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
276#define LC_SPX_FORS_BYTES ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
277#define LC_SPX_FORS_PK_BYTES LC_SPX_N
278
279/* Resulting LC_SPX sizes. */
280#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
281 LC_SPX_FULL_HEIGHT * LC_SPX_N)
282#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
283#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
284
285#elif LC_SPHINCS_MODE == 35664
286
287#define LC_SPHINCS_NIST_CATEGORY 3
288
289/* Hash output length in bytes. */
290#define LC_SPX_N 24
291/* Height of the hypertree. */
292#define LC_SPX_FULL_HEIGHT 66
293/* Number of subtree layer. */
294#define LC_SPX_D 22
295/* FORS tree dimensions. */
296#define LC_SPX_FORS_HEIGHT 8
297#define LC_SPX_FORS_TREES 33
298/* Winternitz parameter, */
299#define LC_SPX_WOTS_W 16
300
301/* The hash function is defined by linking a different hash.c file, as opposed
302 to setting a #define constant. */
303
304/* For clarity */
305#define LC_SPX_ADDR_BYTES 32
306
307/* WOTS parameters. */
308#if LC_SPX_WOTS_W == 256
309 #define LC_SPX_WOTS_LOGW 8
310#elif LC_SPX_WOTS_W == 16
311 #define LC_SPX_WOTS_LOGW 4
312#else
313 #error LC_SPX_WOTS_W assumed 16 or 256
314#endif
315
316#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
317
318/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
319#if LC_SPX_WOTS_W == 256
320 #if LC_SPX_N <= 1
321 #define LC_SPX_WOTS_LEN2 1
322 #elif LC_SPX_N <= 256
323 #define LC_SPX_WOTS_LEN2 2
324 #else
325 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
326 #endif
327#elif LC_SPX_WOTS_W == 16
328 #if LC_SPX_N <= 8
329 #define LC_SPX_WOTS_LEN2 2
330 #elif LC_SPX_N <= 136
331 #define LC_SPX_WOTS_LEN2 3
332 #elif LC_SPX_N <= 256
333 #define LC_SPX_WOTS_LEN2 4
334 #else
335 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
336 #endif
337#endif
338
339#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
340#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
341#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
342
343/* Subtree size. */
344#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
345
346#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
347 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
348#endif
349
350/* FORS parameters. */
351#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
352#define LC_SPX_FORS_BYTES ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
353#define LC_SPX_FORS_PK_BYTES LC_SPX_N
354
355/* Resulting LC_SPX sizes. */
356#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
357 LC_SPX_FULL_HEIGHT * LC_SPX_N)
358#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
359#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
360
361#elif LC_SPHINCS_MODE == 29792
362
363#define LC_SPHINCS_NIST_CATEGORY 5
364
365/* Hash output length in bytes. */
366#define LC_SPX_N 32
367
368/* Height of the hypertree. */
369#define LC_SPX_FULL_HEIGHT 64
370/* Number of subtree layer. */
371#define LC_SPX_D 8
372/* FORS tree dimensions. */
373#define LC_SPX_FORS_HEIGHT 14
374#define LC_SPX_FORS_TREES 22
375/* Winternitz parameter, */
376#define LC_SPX_WOTS_W 16
377
378/* The hash function is defined by linking a different hash.c file, as opposed
379 to setting a #define constant. */
380
381/* For clarity */
382#define LC_SPX_ADDR_BYTES 32
383
384/* WOTS parameters. */
385#if LC_SPX_WOTS_W == 256
386 #define LC_SPX_WOTS_LOGW 8
387#elif LC_SPX_WOTS_W == 16
388 #define LC_SPX_WOTS_LOGW 4
389#else
390 #error LC_SPX_WOTS_W assumed 16 or 256
391#endif
392
393#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
394
395/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
396#if LC_SPX_WOTS_W == 256
397 #if LC_SPX_N <= 1
398 #define LC_SPX_WOTS_LEN2 1
399 #elif LC_SPX_N <= 256
400 #define LC_SPX_WOTS_LEN2 2
401 #else
402 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
403 #endif
404#elif LC_SPX_WOTS_W == 16
405 #if LC_SPX_N <= 8
406 #define LC_SPX_WOTS_LEN2 2
407 #elif LC_SPX_N <= 136
408 #define LC_SPX_WOTS_LEN2 3
409 #elif LC_SPX_N <= 256
410 #define LC_SPX_WOTS_LEN2 4
411 #else
412 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
413 #endif
414#endif
415
416#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
417#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
418#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
419
420/* Subtree size. */
421#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
422
423#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
424 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
425#endif
426
427/* FORS parameters. */
428#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
429#define LC_SPX_FORS_BYTES \
430 ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
431#define LC_SPX_FORS_PK_BYTES LC_SPX_N
432
433/* Resulting LC_SPX sizes. */
434#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
435 LC_SPX_FULL_HEIGHT * LC_SPX_N)
436#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
437#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
438
439#elif LC_SPHINCS_MODE == 49856
440
441#define LC_SPHINCS_NIST_CATEGORY 5
442
443/* Hash output length in bytes. */
444#define LC_SPX_N 32
445/* Height of the hypertree. */
446#define LC_SPX_FULL_HEIGHT 68
447/* Number of subtree layer. */
448#define LC_SPX_D 17
449/* FORS tree dimensions. */
450#define LC_SPX_FORS_HEIGHT 9
451#define LC_SPX_FORS_TREES 35
452/* Winternitz parameter, */
453#define LC_SPX_WOTS_W 16
454
455/* The hash function is defined by linking a different hash.c file, as opposed
456 to setting a #define constant. */
457
458/* For clarity */
459#define LC_SPX_ADDR_BYTES 32
460
461/* WOTS parameters. */
462#if LC_SPX_WOTS_W == 256
463 #define LC_SPX_WOTS_LOGW 8
464#elif LC_SPX_WOTS_W == 16
465 #define LC_SPX_WOTS_LOGW 4
466#else
467 #error LC_SPX_WOTS_W assumed 16 or 256
468#endif
469
470#define LC_SPX_WOTS_LEN1 (8 * LC_SPX_N / LC_SPX_WOTS_LOGW)
471
472/* LC_SPX_WOTS_LEN2 is floor(log(len_1 * (w - 1)) / log(w)) + 1; we precompute */
473#if LC_SPX_WOTS_W == 256
474 #if LC_SPX_N <= 1
475 #define LC_SPX_WOTS_LEN2 1
476 #elif LC_SPX_N <= 256
477 #define LC_SPX_WOTS_LEN2 2
478 #else
479 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
480 #endif
481#elif LC_SPX_WOTS_W == 16
482 #if LC_SPX_N <= 8
483 #define LC_SPX_WOTS_LEN2 2
484 #elif LC_SPX_N <= 136
485 #define LC_SPX_WOTS_LEN2 3
486 #elif LC_SPX_N <= 256
487 #define LC_SPX_WOTS_LEN2 4
488 #else
489 #error Did not precompute LC_SPX_WOTS_LEN2 for n outside {2, .., 256}
490 #endif
491#endif
492
493#define LC_SPX_WOTS_LEN (LC_SPX_WOTS_LEN1 + LC_SPX_WOTS_LEN2)
494#define LC_SPX_WOTS_BYTES (LC_SPX_WOTS_LEN * LC_SPX_N)
495#define LC_SPX_WOTS_PK_BYTES LC_SPX_WOTS_BYTES
496
497/* Subtree size. */
498#define LC_SPX_TREE_HEIGHT (LC_SPX_FULL_HEIGHT / LC_SPX_D)
499
500#if LC_SPX_TREE_HEIGHT * LC_SPX_D != LC_SPX_FULL_HEIGHT
501 #error LC_SPX_D should always divide LC_SPX_FULL_HEIGHT
502#endif
503
504/* FORS parameters. */
505#define LC_SPX_FORS_MSG_BYTES ((LC_SPX_FORS_HEIGHT * LC_SPX_FORS_TREES + 7) / 8)
506#define LC_SPX_FORS_BYTES ((LC_SPX_FORS_HEIGHT + 1) * LC_SPX_FORS_TREES * LC_SPX_N)
507#define LC_SPX_FORS_PK_BYTES LC_SPX_N
508
509/* Resulting LC_SPX sizes. */
510#define LC_SPX_BYTES (LC_SPX_N + LC_SPX_FORS_BYTES + LC_SPX_D * LC_SPX_WOTS_BYTES +\
511 LC_SPX_FULL_HEIGHT * LC_SPX_N)
512#define LC_SPX_PK_BYTES (2 * LC_SPX_N)
513#define LC_SPX_SK_BYTES (2 * LC_SPX_N + LC_SPX_PK_BYTES)
514
515#else
516#error "Undefined Sphincs Plus security strength"
517#endif
518
519#define LC_SPX_SEEDBYTES (3 * LC_SPX_N)
520
522
527 uint8_t sk_seed[LC_SPX_N];
528 uint8_t sk_prf[LC_SPX_N];
529 uint8_t pk[2 * LC_SPX_N];
530};
531
536 uint8_t pk[2 * LC_SPX_N];
537};
538
543 uint8_t r[LC_SPX_N];
544 uint8_t sigfors[LC_SPX_FORS_BYTES];
545 uint8_t sight[LC_SPX_D * LC_SPX_WOTS_BYTES + LC_SPX_FULL_HEIGHT * \
546 LC_SPX_N];
547};
548
549#ifndef LC_SPHINCS_CTX_ON_STACK
550struct lc_sphincs_ctx {
555 struct lc_hash_ctx sphincs_hash_ctx;
556
561 uint8_t shake_state[LC_SHA3_STATE_SIZE_ALIGN(LC_SHA3_256_CTX_SIZE)];
562
573 const struct lc_hash *sphincs_prehash_type;
574
581 size_t userctxlen;
582
588 const uint8_t *userctx;
589
601 unsigned int slh_dsa_internal:1;
602};
603
605#define LC_SPHINCS_CTX_SIZE \
606 sizeof(struct lc_sphincs_ctx)
607
608#define LC_SPHINCS_SET_CTX(name) \
609 (name)->sphincs_hash_ctx.hash = NULL; \
610 (name)->sphincs_prehash_type = NULL; \
611 (name)->slh_dsa_internal = 0; \
612 (name)->userctxlen = 0; \
613 (name)->userctx = NULL
614#endif
616
623#ifndef LC_SPHINCS_CTX_ON_STACK
624#define LC_SPHINCS_CTX_ON_STACK(name) \
625 _Pragma("GCC diagnostic push") _Pragma( \
626 "GCC diagnostic ignored \"-Wdeclaration-after-statement\"") \
627 LC_ALIGNED_BUFFER( \
628 name##_ctx_buf, LC_SPHINCS_CTX_SIZE, \
629 LC_HASH_COMMON_ALIGNMENT); \
630 struct lc_sphincs_ctx *name = \
631 (struct lc_sphincs_ctx *)name##_ctx_buf; \
632 LC_SPHINCS_SET_CTX(name); \
633 _Pragma("GCC diagnostic pop")
634#endif
635
644
651
658static inline void lc_sphincs_shake_192s_ctx_zero(struct lc_sphincs_ctx *ctx)
659{
660 if (!ctx)
661 return;
662
663 /* Only zeroize if the hash state has been initialized */
664 if (ctx->sphincs_hash_ctx.hash)
666}
667
671LC_PURE
672static inline unsigned int lc_sphincs_shake_192s_sk_size(void)
673{
674 return sizeof(struct lc_sphincs_shake_192s_sk);
675}
676
680LC_PURE
681static inline unsigned int lc_sphincs_shake_192s_pk_size(void)
682{
683 return sizeof(struct lc_sphincs_shake_192s_pk);
684}
685
689LC_PURE
690static inline unsigned int lc_sphincs_shake_192s_sig_size(void)
691{
692 return sizeof(struct lc_sphincs_shake_192s_sig);
693}
694
705 struct lc_rng_ctx *rng_ctx);
706
727 struct lc_sphincs_shake_192s_sk *sk,
728 const uint8_t *seed, size_t seedlen);
729
744 size_t mlen, const struct lc_sphincs_shake_192s_sk *sk,
745 struct lc_rng_ctx *rng_ctx);
746
765 struct lc_sphincs_ctx *ctx,
766 const uint8_t *m, size_t mlen,
767 const struct lc_sphincs_shake_192s_sk *sk,
768 struct lc_rng_ctx *rng_ctx);
769
798 const struct lc_sphincs_shake_192s_sk *sk);
799
814int lc_sphincs_shake_192s_sign_update(struct lc_sphincs_ctx *ctx, const uint8_t *m,
815 size_t mlen);
816
832 struct lc_sphincs_ctx *ctx,
833 const struct lc_sphincs_shake_192s_sk *sk,
834 struct lc_rng_ctx *rng_ctx);
835
847int lc_sphincs_shake_192s_verify(const struct lc_sphincs_shake_192s_sig *sig, const uint8_t *m,
848 size_t mlen, const struct lc_sphincs_shake_192s_pk *pk);
849
866 struct lc_sphincs_ctx *ctx,
867 const uint8_t *m, size_t mlen,
868 const struct lc_sphincs_shake_192s_pk *pk);
869
870
900 const struct lc_sphincs_shake_192s_pk *pk);
901
917int lc_sphincs_shake_192s_verify_update(struct lc_sphincs_ctx *ctx, const uint8_t *m,
918 size_t mlen);
919
933 struct lc_sphincs_ctx *ctx,
934 const struct lc_sphincs_shake_192s_pk *pk);
935
936/*
937 * To allow including the different lc_sphincs_*.h files, these macros need to
938 * be undefined. Only during compilation of leancrypto, these macros remain
939 * defined as this header file is not included multiple times.
940 */
941#ifndef LC_SPHINCS_INTERNAL
942#undef LC_SPHINCS_NIST_CATEGORY
943#undef LC_SPHINCS_HASH_TYPE
944#undef LC_SPHINCS_MODE
945#undef LC_SPX_N
946#undef LC_SPX_FULL_HEIGHT
947#undef LC_SPX_D
948#undef LC_SPX_FORS_HEIGHT
949#undef LC_SPX_FORS_TREES
950#undef LC_SPX_WOTS_W
951#undef LC_SPX_ADDR_BYTES
952#undef LC_SPX_WOTS_LOGW
953#undef LC_SPX_WOTS_LEN1
954#undef LC_SPX_WOTS_LEN2
955#undef LC_SPX_WOTS_LEN
956#undef LC_SPX_WOTS_BYTES
957#undef LC_SPX_WOTS_PK_BYTES
958#undef LC_SPX_TREE_HEIGHT
959#undef LC_SPX_FORS_MSG_BYTES
960#undef LC_SPX_FORS_BYTES
961#undef LC_SPX_FORS_PK_BYTES
962#undef LC_SPX_BYTES
963#undef LC_SPX_PK_BYTES
964#undef LC_SPX_SK_BYTES
965#endif /* LC_SPHINCS_INTERNAL */
966
967#ifdef __cplusplus
968}
969#endif
970
971#endif /* LC_SPHINCS_SHAKE_192S_H */
void lc_hash_zero(struct lc_hash_ctx *hash_ctx)
Zeroize Hash context allocated with either LC_HASH_CTX_ON_STACK or lc_hmac_alloc.
int lc_hash(const struct lc_hash *hash, const uint8_t *in, size_t inlen, uint8_t *digest)
Calculate message digest - one-shot.
int lc_sphincs_shake_192s_verify_init(struct lc_sphincs_ctx *ctx, const struct lc_sphincs_shake_192s_pk *pk)
Initializes a signature verification operation.
int lc_sphincs_shake_192s_sign_init(struct lc_sphincs_ctx *ctx, const struct lc_sphincs_shake_192s_sk *sk)
Initializes a signature operation.
int lc_sphincs_shake_192s_verify_update(struct lc_sphincs_ctx *ctx, const uint8_t *m, size_t mlen)
Add more data to an already initialized signature state.
static void lc_sphincs_shake_192s_ctx_zero(struct lc_sphincs_ctx *ctx)
Zeroize Sphincs context allocated with LC_SPHINCS_CTX_ON_STACK or lc_sphincs_ctx_alloc.
uint8_t sight[LC_SPX_D *LC_SPX_WOTS_BYTES+LC_SPX_FULL_HEIGHT *LC_SPX_N]
int lc_sphincs_shake_192s_sign(struct lc_sphincs_shake_192s_sig *sig, const uint8_t *m, size_t mlen, const struct lc_sphincs_shake_192s_sk *sk, struct lc_rng_ctx *rng_ctx)
Computes SLH-DSA signature in one shot.
uint8_t sigfors[LC_SPX_FORS_BYTES]
int lc_sphincs_shake_192s_sign_final(struct lc_sphincs_shake_192s_sig *sig, struct lc_sphincs_ctx *ctx, const struct lc_sphincs_shake_192s_sk *sk, struct lc_rng_ctx *rng_ctx)
Computes signature.
int lc_sphincs_shake_192s_keypair(struct lc_sphincs_shake_192s_pk *pk, struct lc_sphincs_shake_192s_sk *sk, struct lc_rng_ctx *rng_ctx)
Generates Sphincs public and private key.
static LC_PURE unsigned int lc_sphincs_shake_192s_sk_size(void)
Return the size of the Sphincs secret key.
int lc_sphincs_shake_192s_verify_ctx(const struct lc_sphincs_shake_192s_sig *sig, struct lc_sphincs_ctx *ctx, const uint8_t *m, size_t mlen, const struct lc_sphincs_shake_192s_pk *pk)
Verifies signature with Sphincs context in one shot.
void lc_sphincs_shake_192s_ctx_zero_free(struct lc_sphincs_ctx *ctx)
Zeroize and free Sphincs stream context.
int lc_sphincs_shake_192s_ctx_alloc(struct lc_sphincs_ctx **ctx)
Allocate Sphincs stream context on heap.
int lc_sphincs_shake_192s_keypair_from_seed(struct lc_sphincs_shake_192s_pk *pk, struct lc_sphincs_shake_192s_sk *sk, const uint8_t *seed, size_t seedlen)
Generates Sphincs public and private key from a given seed.
static LC_PURE unsigned int lc_sphincs_shake_192s_sig_size(void)
Return the size of the Sphincs signature.
int lc_sphincs_shake_192s_verify(const struct lc_sphincs_shake_192s_sig *sig, const uint8_t *m, size_t mlen, const struct lc_sphincs_shake_192s_pk *pk)
Verifies SLH-DSA signature in one shot.
int lc_sphincs_shake_192s_verify_final(const struct lc_sphincs_shake_192s_sig *sig, struct lc_sphincs_ctx *ctx, const struct lc_sphincs_shake_192s_pk *pk)
Verifies signature.
int lc_sphincs_shake_192s_sign_ctx(struct lc_sphincs_shake_192s_sig *sig, struct lc_sphincs_ctx *ctx, const uint8_t *m, size_t mlen, const struct lc_sphincs_shake_192s_sk *sk, struct lc_rng_ctx *rng_ctx)
Computes signature with Sphincs context in one shot.
int lc_sphincs_shake_192s_sign_update(struct lc_sphincs_ctx *ctx, const uint8_t *m, size_t mlen)
Add more data to an already initialized signature state.
static LC_PURE unsigned int lc_sphincs_shake_192s_pk_size(void)
Return the size of the Sphincs public key.
unsigned int slh_dsa_internal
When set to true, only the SLH-DSA.Sign_internal or SLH-DSA.Verify_internal are performed (see FIPS 2...
size_t userctxlen
length of the user context (allowed range between 0 and 255 bytes)
uint8_t shake_state[LC_SHA3_STATE_SIZE_ALIGN(LC_SHA3_256_CTX_SIZE)]
State memory of the hash context used internally to the library - it should not be touched by the use...
const uint8_t * userctx
buffer with a caller-specified context string
const struct lc_hash * sphincs_prehash_type
When using HashSLH-DSA, set the hash reference used for the hash operation. Allowed values are lc_sha...
struct lc_hash_ctx sphincs_hash_ctx
Hash context used internally to the library - it should not be touched by the user.