blob: cc96e3ba15d3c72302fb848fe29211c9f3945523 [file] [log] [blame]
yuezonghe824eb0c2024-06-27 02:32:26 -07001/* tfm.h
2 *
3 * Copyright (C) 2006-2021 wolfSSL Inc.
4 *
5 * This file is part of wolfSSL.
6 *
7 * wolfSSL is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * wolfSSL is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
20 */
21
22
23
24/*
25 * Based on public domain TomsFastMath 0.10 by Tom St Denis, tomstdenis@iahu.ca,
26 * http://math.libtomcrypt.com
27 */
28
29
30/**
31 * Edited by Moises Guimaraes (moises.guimaraes@phoebus.com.br)
32 * to fit CyaSSL's needs.
33 */
34
35/*!
36 \file wolfssl/wolfcrypt/tfm.h
37*/
38
39#ifndef WOLF_CRYPT_TFM_H
40#define WOLF_CRYPT_TFM_H
41
42#include <wolfssl/wolfcrypt/types.h>
43#ifndef CHAR_BIT
44 #include <limits.h>
45#endif
46
47#include <wolfssl/wolfcrypt/random.h>
48
49#ifdef __cplusplus
50 extern "C" {
51#endif
52
53#ifdef WOLFSSL_NO_ASM
54 #undef TFM_NO_ASM
55 #define TFM_NO_ASM
56#endif
57
58#ifdef NO_64BIT
59 #undef NO_TFM_64BIT
60 #define NO_TFM_64BIT
61#endif
62
63#ifndef NO_TFM_64BIT
64/* autodetect x86-64 and make sure we are using 64-bit digits with x86-64 asm */
65#if defined(__x86_64__)
66 #if defined(TFM_X86) || defined(TFM_SSE2) || defined(TFM_ARM)
67 #error x86-64 detected, x86-32/SSE2/ARM optimizations are not valid!
68 #endif
69 #if !defined(TFM_X86_64) && !defined(TFM_NO_ASM)
70 #define TFM_X86_64
71 #endif
72#endif
73#if defined(__aarch64__) && defined(__APPLE__)
74 #if !defined(TFM_AARCH_64) && !defined(TFM_NO_ASM)
75 #define TFM_AARCH_64
76 #endif
77#endif
78#if defined(TFM_X86_64) || defined(TFM_AARCH_64)
79 #if !defined(FP_64BIT)
80 #define FP_64BIT
81 #endif
82#endif
83/* use 64-bit digit even if not using asm on x86_64 */
84#if defined(__x86_64__) && !defined(FP_64BIT)
85 #define FP_64BIT
86#endif
87/* if intel compiler doesn't provide 128 bit type don't turn on 64bit */
88#if defined(FP_64BIT) && defined(__INTEL_COMPILER) && !defined(HAVE___UINT128_T)
89 #undef FP_64BIT
90 #undef TFM_X86_64
91#endif
92#endif /* NO_TFM_64BIT */
93
94/* try to detect x86-32 */
95#if defined(__i386__) && !defined(TFM_SSE2)
96 #if defined(TFM_X86_64) || defined(TFM_ARM)
97 #error x86-32 detected, x86-64/ARM optimizations are not valid!
98 #endif
99 #if !defined(TFM_X86) && !defined(TFM_NO_ASM)
100 #define TFM_X86
101 #endif
102#endif
103
104/* make sure we're 32-bit for x86-32/sse/arm/ppc32 */
105#if (defined(TFM_X86) || defined(TFM_SSE2) || defined(TFM_ARM) || defined(TFM_PPC32)) && defined(FP_64BIT)
106 #warning x86-32, SSE2 and ARM, PPC32 optimizations require 32-bit digits (undefining)
107 #undef FP_64BIT
108#endif
109
110/* multi asms? */
111#ifdef TFM_X86
112 #define TFM_ASM
113#endif
114#ifdef TFM_X86_64
115 #ifdef TFM_ASM
116 #error TFM_ASM already defined!
117 #endif
118 #define TFM_ASM
119#endif
120#ifdef TFM_SSE2
121 #ifdef TFM_ASM
122 #error TFM_ASM already defined!
123 #endif
124 #define TFM_ASM
125#endif
126#ifdef TFM_ARM
127 #ifdef TFM_ASM
128 #error TFM_ASM already defined!
129 #endif
130 #define TFM_ASM
131#endif
132#ifdef TFM_PPC32
133 #ifdef TFM_ASM
134 #error TFM_ASM already defined!
135 #endif
136 #define TFM_ASM
137#endif
138#ifdef TFM_PPC64
139 #ifdef TFM_ASM
140 #error TFM_ASM already defined!
141 #endif
142 #define TFM_ASM
143#endif
144#ifdef TFM_AVR32
145 #ifdef TFM_ASM
146 #error TFM_ASM already defined!
147 #endif
148 #define TFM_ASM
149#endif
150
151/* we want no asm? */
152#ifdef TFM_NO_ASM
153 #undef TFM_X86
154 #undef TFM_X86_64
155 #undef TFM_SSE2
156 #undef TFM_ARM
157 #undef TFM_PPC32
158 #undef TFM_PPC64
159 #undef TFM_AVR32
160 #undef TFM_ASM
161#endif
162
163/* ECC helpers */
164#ifdef TFM_ECC192
165 #ifdef FP_64BIT
166 #define TFM_MUL3
167 #define TFM_SQR3
168 #else
169 #define TFM_MUL6
170 #define TFM_SQR6
171 #endif
172#endif
173
174#ifdef TFM_ECC224
175 #ifdef FP_64BIT
176 #define TFM_MUL4
177 #define TFM_SQR4
178 #else
179 #define TFM_MUL7
180 #define TFM_SQR7
181 #endif
182#endif
183
184#ifdef TFM_ECC256
185 #ifdef FP_64BIT
186 #define TFM_MUL4
187 #define TFM_SQR4
188 #else
189 #define TFM_MUL8
190 #define TFM_SQR8
191 #endif
192#endif
193
194#ifdef TFM_ECC384
195 #ifdef FP_64BIT
196 #define TFM_MUL6
197 #define TFM_SQR6
198 #else
199 #define TFM_MUL12
200 #define TFM_SQR12
201 #endif
202#endif
203
204#ifdef TFM_ECC521
205 #ifdef FP_64BIT
206 #define TFM_MUL9
207 #define TFM_SQR9
208 #else
209 #define TFM_MUL17
210 #define TFM_SQR17
211 #endif
212#endif
213
214
215/* allow user to define on fp_digit, fp_word types */
216#ifndef WOLFSSL_BIGINT_TYPES
217
218/* some default configurations.
219 */
220#if defined(WC_16BIT_CPU)
221 typedef unsigned int fp_digit;
222 #define SIZEOF_FP_DIGIT 2
223 typedef unsigned long fp_word;
224#elif defined(FP_64BIT)
225 /* for GCC only on supported platforms */
226 typedef unsigned long long fp_digit; /* 64bit, 128 uses mode(TI) below */
227 #define SIZEOF_FP_DIGIT 8
228 typedef unsigned long fp_word __attribute__ ((mode(TI)));
229#else
230
231 #ifndef NO_TFM_64BIT
232 #if defined(_MSC_VER) || defined(__BORLANDC__)
233 typedef unsigned __int64 ulong64;
234 #else
235 typedef unsigned long long ulong64;
236 #endif
237 typedef unsigned int fp_digit;
238 #define SIZEOF_FP_DIGIT 4
239 typedef ulong64 fp_word;
240 #define FP_32BIT
241 #else
242 /* some procs like coldfire prefer not to place multiply into 64bit type
243 even though it exists */
244 typedef unsigned short fp_digit;
245 #define SIZEOF_FP_DIGIT 2
246 typedef unsigned int fp_word;
247 #endif
248#endif
249
250#endif /* WOLFSSL_BIGINT_TYPES */
251
252
253/* # of digits this is */
254#define DIGIT_BIT ((CHAR_BIT) * SIZEOF_FP_DIGIT)
255
256/* Max size of any number in bits. Basically the largest size you will be
257 * multiplying should be half [or smaller] of FP_MAX_SIZE-four_digit
258 *
259 * It defaults to 4096-bits [allowing multiplications up to 2048x2048 bits ]
260 */
261
262
263#ifndef FP_MAX_BITS
264 #define FP_MAX_BITS 4096
265#endif
266#ifdef WOLFSSL_OPENSSH
267 /* OpenSSH uses some BIG primes so we need to accommodate for that */
268 #undef FP_MAX_BITS
269 #define FP_MAX_BITS 16384
270#endif
271#define FP_MAX_SIZE (FP_MAX_BITS+(8*DIGIT_BIT))
272
273/* will this lib work? */
274#if (CHAR_BIT & 7)
275 #error CHAR_BIT must be a multiple of eight.
276#endif
277#if FP_MAX_BITS % CHAR_BIT
278 #error FP_MAX_BITS must be a multiple of CHAR_BIT
279#endif
280
281#define FP_MASK (fp_digit)(-1)
282#define FP_DIGIT_MAX FP_MASK
283#define FP_SIZE (FP_MAX_SIZE/DIGIT_BIT)
284
285#define FP_MAX_PRIME_SIZE (FP_MAX_BITS/(2*CHAR_BIT))
286/* In terms of FP_MAX_BITS, it is double the size possible for a number
287 * to allow for multiplication, divide that 2 out. Also divide by CHAR_BIT
288 * to convert from bits to bytes. (Note, FP_PRIME_SIZE is the number of
289 * values in the canned prime number list.) */
290
291/* signs */
292#define FP_ZPOS 0
293#define FP_NEG 1
294
295/* return codes */
296#define FP_OKAY 0
297#define FP_VAL -1
298#define FP_MEM -2
299#define FP_NOT_INF -3
300#define FP_WOULDBLOCK -4
301
302/* equalities */
303#define FP_LT -1 /* less than */
304#define FP_EQ 0 /* equal to */
305#define FP_GT 1 /* greater than */
306
307/* replies */
308#define FP_YES 1 /* yes response */
309#define FP_NO 0 /* no response */
310
311#ifdef HAVE_WOLF_BIGINT
312 /* raw big integer */
313 typedef struct WC_BIGINT {
314 byte* buf;
315 word32 len;
316 void* heap;
317 } WC_BIGINT;
318 #define WOLF_BIGINT_DEFINED
319#endif
320
321/* a FP type */
322typedef struct fp_int {
323 int used;
324 int sign;
325#if defined(ALT_ECC_SIZE) || defined(HAVE_WOLF_BIGINT)
326 int size;
327#endif
328 fp_digit dp[FP_SIZE];
329
330#ifdef HAVE_WOLF_BIGINT
331 struct WC_BIGINT raw; /* unsigned binary (big endian) */
332#endif
333} fp_int;
334
335/* Types */
336typedef fp_digit mp_digit;
337typedef fp_word mp_word;
338typedef fp_int mp_int;
339
340
341/* wolf big int and common functions */
342#include <wolfssl/wolfcrypt/wolfmath.h>
343
344
345/* externally define this symbol to ignore the default settings, useful for changing the build from the make process */
346#ifndef TFM_ALREADY_SET
347
348/* do we want the large set of small multiplications ?
349 Enable these if you are going to be doing a lot of small (<= 16 digit) multiplications say in ECC
350 Or if you're on a 64-bit machine doing RSA as a 1024-bit integer == 16 digits ;-)
351 */
352/* need to refactor the function */
353/*#define TFM_SMALL_SET */
354
355/* do we want huge code
356 Enable these if you are doing 20, 24, 28, 32, 48, 64 digit multiplications (useful for RSA)
357 Less important on 64-bit machines as 32 digits == 2048 bits
358 */
359#if 0
360#define TFM_MUL3
361#define TFM_MUL4
362#define TFM_MUL6
363#define TFM_MUL7
364#define TFM_MUL8
365#define TFM_MUL9
366#define TFM_MUL12
367#define TFM_MUL17
368#endif
369#ifdef TFM_HUGE_SET
370#define TFM_MUL20
371#define TFM_MUL24
372#define TFM_MUL28
373#define TFM_MUL32
374#if (FP_MAX_BITS >= 6144) && defined(FP_64BIT)
375 #define TFM_MUL48
376#endif
377#if (FP_MAX_BITS >= 8192) && defined(FP_64BIT)
378 #define TFM_MUL64
379#endif
380#endif
381
382#if 0
383#define TFM_SQR3
384#define TFM_SQR4
385#define TFM_SQR6
386#define TFM_SQR7
387#define TFM_SQR8
388#define TFM_SQR9
389#define TFM_SQR12
390#define TFM_SQR17
391#endif
392#ifdef TFM_HUGE_SET
393#define TFM_SQR20
394#define TFM_SQR24
395#define TFM_SQR28
396#define TFM_SQR32
397#define TFM_SQR48
398#define TFM_SQR64
399#endif
400
401/* Optional math checks (enable WOLFSSL_DEBUG_MATH to print info) */
402/* #define TFM_CHECK */
403
404/* Is the target a P4 Prescott
405 */
406/* #define TFM_PRESCOTT */
407
408/* Do we want timing resistant fp_exptmod() ?
409 * This makes it slower but also timing invariant with respect to the exponent
410 */
411/* #define TFM_TIMING_RESISTANT */
412
413#endif /* TFM_ALREADY_SET */
414
415/* functions */
416
417/* returns a TFM ident string useful for debugging... */
418/*const char *fp_ident(void);*/
419
420/* initialize [or zero] an fp int */
421void fp_init(fp_int *a);
422MP_API void fp_zero(fp_int *a);
423MP_API void fp_clear(fp_int *a); /* uses ForceZero to clear sensitive memory */
424MP_API void fp_forcezero (fp_int * a);
425MP_API void fp_free(fp_int* a);
426
427/* zero/one/even/odd/neg/word ? */
428#define fp_iszero(a) (((a)->used == 0) ? FP_YES : FP_NO)
429#define fp_isone(a) \
430 ((((a)->used == 1) && ((a)->dp[0] == 1) && ((a)->sign == FP_ZPOS)) \
431 ? FP_YES : FP_NO)
432#define fp_iseven(a) \
433 (((a)->used > 0 && (((a)->dp[0] & 1) == 0)) ? FP_YES : FP_NO)
434#define fp_isodd(a) \
435 (((a)->used > 0 && (((a)->dp[0] & 1) == 1)) ? FP_YES : FP_NO)
436#define fp_isneg(a) (((a)->sign != FP_ZPOS) ? FP_YES : FP_NO)
437#define fp_isword(a, w) \
438 (((((a)->used == 1) && ((a)->dp[0] == w)) || \
439 ((w == 0) && ((a)->used == 0))) ? FP_YES : FP_NO)
440
441/* set to a small digit */
442void fp_set(fp_int *a, fp_digit b);
443int fp_set_int(fp_int *a, unsigned long b);
444
445/* check if a bit is set */
446int fp_is_bit_set(fp_int *a, fp_digit b);
447/* set the b bit to 1 */
448int fp_set_bit (fp_int * a, fp_digit b);
449
450/* copy from a to b */
451void fp_copy(const fp_int *a, fp_int *b);
452void fp_init_copy(fp_int *a, fp_int *b);
453
454/* clamp digits */
455#define fp_clamp(a) { while ((a)->used && (a)->dp[(a)->used-1] == 0) --((a)->used); (a)->sign = (a)->used ? (a)->sign : FP_ZPOS; }
456#define mp_clamp(a) fp_clamp(a)
457#define mp_grow(a,s) MP_OKAY
458
459/* negate and absolute */
460#define fp_neg(a, b) { fp_copy(a, b); (b)->sign ^= 1; fp_clamp(b); }
461#define fp_abs(a, b) { fp_copy(a, b); (b)->sign = 0; }
462
463/* right shift x digits */
464void fp_rshd(fp_int *a, int x);
465
466/* right shift x bits */
467void fp_rshb(fp_int *a, int x);
468
469/* left shift x digits */
470int fp_lshd(fp_int *a, int x);
471
472/* signed comparison */
473int fp_cmp(fp_int *a, fp_int *b);
474
475/* unsigned comparison */
476int fp_cmp_mag(fp_int *a, fp_int *b);
477
478/* power of 2 operations */
479void fp_div_2d(fp_int *a, int b, fp_int *c, fp_int *d);
480void fp_mod_2d(fp_int *a, int b, fp_int *c);
481int fp_mul_2d(fp_int *a, int b, fp_int *c);
482void fp_2expt (fp_int *a, int b);
483int fp_mul_2(fp_int *a, fp_int *c);
484void fp_div_2(fp_int *a, fp_int *c);
485/* c = a / 2 (mod b) - constant time (a < b and positive) */
486int fp_div_2_mod_ct(fp_int *a, fp_int *b, fp_int *c);
487
488
489/* Counts the number of lsbs which are zero before the first zero bit */
490int fp_cnt_lsb(fp_int *a);
491
492/* c = a + b */
493int fp_add(fp_int *a, fp_int *b, fp_int *c);
494
495/* c = a - b */
496int fp_sub(fp_int *a, fp_int *b, fp_int *c);
497
498/* c = a * b */
499int fp_mul(fp_int *a, fp_int *b, fp_int *c);
500
501/* b = a*a */
502int fp_sqr(fp_int *a, fp_int *b);
503
504/* a/b => cb + d == a */
505int fp_div(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
506
507/* c = a mod b, 0 <= c < b */
508int fp_mod(fp_int *a, fp_int *b, fp_int *c);
509
510/* compare against a single digit */
511int fp_cmp_d(fp_int *a, fp_digit b);
512
513/* c = a + b */
514int fp_add_d(fp_int *a, fp_digit b, fp_int *c);
515
516/* c = a - b */
517int fp_sub_d(fp_int *a, fp_digit b, fp_int *c);
518
519/* c = a * b */
520int fp_mul_d(fp_int *a, fp_digit b, fp_int *c);
521
522/* a/b => cb + d == a */
523/*int fp_div_d(fp_int *a, fp_digit b, fp_int *c, fp_digit *d);*/
524
525/* c = a mod b, 0 <= c < b */
526/*int fp_mod_d(fp_int *a, fp_digit b, fp_digit *c);*/
527
528/* ---> number theory <--- */
529/* d = a + b (mod c) */
530/*int fp_addmod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);*/
531
532/* d = a - b (mod c) */
533/*int fp_submod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);*/
534
535/* d = a * b (mod c) */
536int fp_mulmod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
537
538/* d = a - b (mod c) */
539int fp_submod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
540
541/* d = a + b (mod c) */
542int fp_addmod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
543
544/* d = a - b (mod c) - constant time (a < c and b < c) */
545int fp_submod_ct(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
546
547/* d = a + b (mod c) - constant time (a < c and b < c) */
548int fp_addmod_ct(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
549
550/* c = a * a (mod b) */
551int fp_sqrmod(fp_int *a, fp_int *b, fp_int *c);
552
553/* c = 1/a (mod b) */
554int fp_invmod(fp_int *a, fp_int *b, fp_int *c);
555int fp_invmod_mont_ct(fp_int *a, fp_int *b, fp_int *c, fp_digit mp);
556
557/* c = (a, b) */
558/*int fp_gcd(fp_int *a, fp_int *b, fp_int *c);*/
559
560/* c = [a, b] */
561/*int fp_lcm(fp_int *a, fp_int *b, fp_int *c);*/
562
563/* setups the montgomery reduction */
564int fp_montgomery_setup(fp_int *a, fp_digit *mp);
565
566/* computes a = B**n mod b without division or multiplication useful for
567 * normalizing numbers in a Montgomery system.
568 */
569int fp_montgomery_calc_normalization(fp_int *a, fp_int *b);
570
571/* computes x/R == x (mod N) via Montgomery Reduction */
572int fp_montgomery_reduce(fp_int *a, fp_int *m, fp_digit mp);
573int fp_montgomery_reduce_ex(fp_int *a, fp_int *m, fp_digit mp, int ct);
574
575/* d = a**b (mod c) */
576int fp_exptmod(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
577int fp_exptmod_ex(fp_int *a, fp_int *b, int minDigits, fp_int *c, fp_int *d);
578int fp_exptmod_nct(fp_int *a, fp_int *b, fp_int *c, fp_int *d);
579
580#ifdef WC_RSA_NONBLOCK
581
582enum tfmExptModNbState {
583 TFM_EXPTMOD_NB_INIT = 0,
584 TFM_EXPTMOD_NB_MONT,
585 TFM_EXPTMOD_NB_MONT_RED,
586 TFM_EXPTMOD_NB_MONT_MUL,
587 TFM_EXPTMOD_NB_MONT_MOD,
588 TFM_EXPTMOD_NB_MONT_MODCHK,
589 TFM_EXPTMOD_NB_NEXT,
590 TFM_EXPTMOD_NB_MUL,
591 TFM_EXPTMOD_NB_MUL_RED,
592 TFM_EXPTMOD_NB_SQR,
593 TFM_EXPTMOD_NB_SQR_RED,
594 TFM_EXPTMOD_NB_RED,
595 TFM_EXPTMOD_NB_COUNT /* last item for total state count only */
596};
597
598typedef struct {
599#ifndef WC_NO_CACHE_RESISTANT
600 fp_int R[3];
601#else
602 fp_int R[2];
603#endif
604 fp_digit buf;
605 fp_digit mp;
606 int bitcnt;
607 int digidx;
608 int y;
609 int state; /* tfmExptModNbState */
610#ifdef WC_RSA_NONBLOCK_TIME
611 word32 maxBlockInst; /* maximum instructions to block */
612 word32 totalInst; /* tracks total instructions */
613#endif
614} exptModNb_t;
615
616#ifdef WC_RSA_NONBLOCK_TIME
617enum {
618 TFM_EXPTMOD_NB_STOP = 0, /* stop and return FP_WOULDBLOCK */
619 TFM_EXPTMOD_NB_CONTINUE = 1, /* keep blocking */
620};
621#endif
622
623/* non-blocking version of timing resistant fp_exptmod function */
624/* supports cache resistance */
625int fp_exptmod_nb(exptModNb_t* nb, fp_int* G, fp_int* X, fp_int* P, fp_int* Y);
626
627#endif /* WC_RSA_NONBLOCK */
628
629/* primality stuff */
630
631/* perform a Miller-Rabin test of a to the base b and store result in "result" */
632/*void fp_prime_miller_rabin (fp_int * a, fp_int * b, int *result);*/
633
634#define FP_PRIME_SIZE 256
635/* 256 trial divisions + 8 Miller-Rabins, returns FP_YES if probable prime */
636/*int fp_isprime(fp_int *a);*/
637/* extended version of fp_isprime, do 't' Miller-Rabins instead of only 8 */
638/*int fp_isprime_ex(fp_int *a, int t, int* result);*/
639
640/* Primality generation flags */
641/*#define TFM_PRIME_BBS 0x0001 */ /* BBS style prime */
642/*#define TFM_PRIME_SAFE 0x0002 */ /* Safe prime (p-1)/2 == prime */
643/*#define TFM_PRIME_2MSB_OFF 0x0004 */ /* force 2nd MSB to 0 */
644/*#define TFM_PRIME_2MSB_ON 0x0008 */ /* force 2nd MSB to 1 */
645
646/* callback for fp_prime_random, should fill dst with random bytes and return how many read [up to len] */
647/*typedef int tfm_prime_callback(unsigned char *dst, int len, void *dat);*/
648
649/*#define fp_prime_random(a, t, size, bbs, cb, dat) fp_prime_random_ex(a, t, ((size) * 8) + 1, (bbs==1)?TFM_PRIME_BBS:0, cb, dat)*/
650
651/*int fp_prime_random_ex(fp_int *a, int t, int size, int flags, tfm_prime_callback cb, void *dat);*/
652
653/* radix conversions */
654int fp_count_bits(const fp_int *a);
655int fp_leading_bit(fp_int *a);
656
657int fp_unsigned_bin_size(const fp_int *a);
658int fp_read_unsigned_bin(fp_int *a, const unsigned char *b, int c);
659int fp_to_unsigned_bin(fp_int *a, unsigned char *b);
660int fp_to_unsigned_bin_len(fp_int *a, unsigned char *b, int c);
661int fp_to_unsigned_bin_at_pos(int x, fp_int *t, unsigned char *b);
662
663/*int fp_read_radix(fp_int *a, char *str, int radix);*/
664/*int fp_toradix(fp_int *a, char *str, int radix);*/
665/*int fp_toradix_n(fp_int * a, char *str, int radix, int maxlen);*/
666
667
668/* VARIOUS LOW LEVEL STUFFS */
669int s_fp_add(fp_int *a, fp_int *b, fp_int *c);
670void s_fp_sub(fp_int *a, fp_int *b, fp_int *c);
671void fp_reverse(unsigned char *s, int len);
672
673int fp_mul_comba(fp_int *a, fp_int *b, fp_int *c);
674
675int fp_mul_comba_small(fp_int *a, fp_int *b, fp_int *c);
676int fp_mul_comba3(fp_int *a, fp_int *b, fp_int *c);
677int fp_mul_comba4(fp_int *a, fp_int *b, fp_int *c);
678int fp_mul_comba6(fp_int *a, fp_int *b, fp_int *c);
679int fp_mul_comba7(fp_int *a, fp_int *b, fp_int *c);
680int fp_mul_comba8(fp_int *a, fp_int *b, fp_int *c);
681int fp_mul_comba9(fp_int *a, fp_int *b, fp_int *c);
682int fp_mul_comba12(fp_int *a, fp_int *b, fp_int *c);
683int fp_mul_comba17(fp_int *a, fp_int *b, fp_int *c);
684int fp_mul_comba20(fp_int *a, fp_int *b, fp_int *c);
685int fp_mul_comba24(fp_int *a, fp_int *b, fp_int *c);
686int fp_mul_comba28(fp_int *a, fp_int *b, fp_int *c);
687int fp_mul_comba32(fp_int *a, fp_int *b, fp_int *c);
688int fp_mul_comba48(fp_int *a, fp_int *b, fp_int *c);
689int fp_mul_comba64(fp_int *a, fp_int *b, fp_int *c);
690int fp_sqr_comba(fp_int *a, fp_int *b);
691int fp_sqr_comba_small(fp_int *a, fp_int *b);
692int fp_sqr_comba3(fp_int *a, fp_int *b);
693int fp_sqr_comba4(fp_int *a, fp_int *b);
694int fp_sqr_comba6(fp_int *a, fp_int *b);
695int fp_sqr_comba7(fp_int *a, fp_int *b);
696int fp_sqr_comba8(fp_int *a, fp_int *b);
697int fp_sqr_comba9(fp_int *a, fp_int *b);
698int fp_sqr_comba12(fp_int *a, fp_int *b);
699int fp_sqr_comba17(fp_int *a, fp_int *b);
700int fp_sqr_comba20(fp_int *a, fp_int *b);
701int fp_sqr_comba24(fp_int *a, fp_int *b);
702int fp_sqr_comba28(fp_int *a, fp_int *b);
703int fp_sqr_comba32(fp_int *a, fp_int *b);
704int fp_sqr_comba48(fp_int *a, fp_int *b);
705int fp_sqr_comba64(fp_int *a, fp_int *b);
706
707
708/**
709 * Used by wolfSSL
710 */
711
712/* Constants */
713#define MP_LT FP_LT /* less than */
714#define MP_EQ FP_EQ /* equal to */
715#define MP_GT FP_GT /* greater than */
716#define MP_VAL FP_VAL /* invalid */
717#define MP_MEM FP_MEM /* memory error */
718#define MP_NOT_INF FP_NOT_INF /* point not at infinity */
719#define MP_OKAY FP_OKAY /* ok result */
720#define MP_NO FP_NO /* yes/no result */
721#define MP_YES FP_YES /* yes/no result */
722#define MP_ZPOS FP_ZPOS
723#define MP_NEG FP_NEG
724#define MP_MASK FP_MASK
725
726/* Prototypes */
727#define mp_zero(a) fp_zero(a)
728#define mp_isone(a) fp_isone(a)
729#define mp_iseven(a) fp_iseven(a)
730#define mp_isneg(a) fp_isneg(a)
731#define mp_isword(a, w) fp_isword(a, w)
732
733#define MP_RADIX_BIN 2
734#define MP_RADIX_OCT 8
735#define MP_RADIX_DEC 10
736#define MP_RADIX_HEX 16
737#define MP_RADIX_MAX 64
738
739#define mp_tobinary(M, S) mp_toradix((M), (S), MP_RADIX_BIN)
740#define mp_tooctal(M, S) mp_toradix((M), (S), MP_RADIX_OCT)
741#define mp_todecimal(M, S) mp_toradix((M), (S), MP_RADIX_DEC)
742#define mp_tohex(M, S) mp_toradix((M), (S), MP_RADIX_HEX)
743
744MP_API int mp_init (mp_int * a);
745MP_API int mp_init_copy(fp_int * a, fp_int * b);
746MP_API void mp_clear (mp_int * a);
747MP_API void mp_free (mp_int * a);
748MP_API void mp_forcezero (mp_int * a);
749MP_API int mp_init_multi(mp_int* a, mp_int* b, mp_int* c, mp_int* d, mp_int* e,
750 mp_int* f);
751
752MP_API int mp_add (mp_int * a, mp_int * b, mp_int * c);
753MP_API int mp_sub (mp_int * a, mp_int * b, mp_int * c);
754MP_API int mp_add_d (mp_int * a, mp_digit b, mp_int * c);
755
756MP_API int mp_mul (mp_int * a, mp_int * b, mp_int * c);
757MP_API int mp_mul_d (mp_int * a, mp_digit b, mp_int * c);
758MP_API int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d);
759MP_API int mp_submod (mp_int* a, mp_int* b, mp_int* c, mp_int* d);
760MP_API int mp_addmod (mp_int* a, mp_int* b, mp_int* c, mp_int* d);
761MP_API int mp_submod_ct (mp_int* a, mp_int* b, mp_int* c, mp_int* d);
762MP_API int mp_addmod_ct (mp_int* a, mp_int* b, mp_int* c, mp_int* d);
763MP_API int mp_mod(mp_int *a, mp_int *b, mp_int *c);
764MP_API int mp_invmod(mp_int *a, mp_int *b, mp_int *c);
765MP_API int mp_invmod_mont_ct(mp_int *a, mp_int *b, mp_int *c, fp_digit mp);
766MP_API int mp_exptmod (mp_int * g, mp_int * x, mp_int * p, mp_int * y);
767MP_API int mp_exptmod_ex (mp_int * g, mp_int * x, int minDigits, mp_int * p,
768 mp_int * y);
769MP_API int mp_exptmod_nct (mp_int * g, mp_int * x, mp_int * p, mp_int * y);
770MP_API int mp_mul_2d(mp_int *a, int b, mp_int *c);
771MP_API int mp_2expt(mp_int* a, int b);
772
773MP_API int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d);
774
775MP_API int mp_cmp(mp_int *a, mp_int *b);
776MP_API int mp_cmp_d(mp_int *a, mp_digit b);
777
778MP_API int mp_unsigned_bin_size(const mp_int * a);
779MP_API int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c);
780MP_API int mp_to_unsigned_bin_at_pos(int x, mp_int *t, unsigned char *b);
781MP_API int mp_to_unsigned_bin (mp_int * a, unsigned char *b);
782MP_API int mp_to_unsigned_bin_len(mp_int * a, unsigned char *b, int c);
783
784MP_API int mp_sub_d(fp_int *a, fp_digit b, fp_int *c);
785MP_API int mp_copy(const fp_int* a, fp_int* b);
786MP_API int mp_isodd(mp_int* a);
787MP_API int mp_iszero(mp_int* a);
788MP_API int mp_count_bits(const mp_int *a);
789MP_API int mp_leading_bit(mp_int *a);
790MP_API int mp_set_int(mp_int *a, unsigned long b);
791MP_API int mp_is_bit_set (mp_int * a, mp_digit b);
792MP_API int mp_set_bit (mp_int * a, mp_digit b);
793MP_API void mp_rshb(mp_int *a, int x);
794MP_API void mp_rshd(mp_int *a, int x);
795MP_API int mp_toradix (mp_int *a, char *str, int radix);
796MP_API int mp_radix_size (mp_int * a, int radix, int *size);
797
798#ifdef WOLFSSL_DEBUG_MATH
799 MP_API void mp_dump(const char* desc, mp_int* a, byte verbose);
800#else
801 #define mp_dump(desc, a, verbose)
802#endif
803
804#if !defined(NO_DSA) || defined(HAVE_ECC)
805 MP_API int mp_read_radix(mp_int* a, const char* str, int radix);
806#endif
807
808#ifdef HAVE_ECC
809 MP_API int mp_sqr(fp_int *a, fp_int *b);
810 MP_API int mp_montgomery_reduce(fp_int *a, fp_int *m, fp_digit mp);
811 MP_API int mp_montgomery_reduce_ex(fp_int *a, fp_int *m, fp_digit mp,
812 int ct);
813 MP_API int mp_montgomery_setup(fp_int *a, fp_digit *rho);
814 MP_API int mp_div_2(fp_int * a, fp_int * b);
815 MP_API int mp_div_2_mod_ct(mp_int *a, mp_int *b, mp_int *c);
816#endif
817
818#if defined(HAVE_ECC) || !defined(NO_RSA) || !defined(NO_DSA) || \
819 defined(WOLFSSL_KEY_GEN)
820 MP_API int mp_set(fp_int *a, fp_digit b);
821#endif
822
823#if defined(HAVE_ECC) || defined(WOLFSSL_KEY_GEN) || !defined(NO_RSA) || \
824 !defined(NO_DSA) || !defined(NO_DH)
825 MP_API int mp_sqrmod(mp_int* a, mp_int* b, mp_int* c);
826 MP_API int mp_montgomery_calc_normalization(mp_int *a, mp_int *b);
827#endif
828
829#if !defined(NO_DH) || !defined(NO_DSA) || !defined(NO_RSA) || defined(WOLFSSL_KEY_GEN)
830MP_API int mp_prime_is_prime(mp_int* a, int t, int* result);
831MP_API int mp_prime_is_prime_ex(mp_int* a, int t, int* result, WC_RNG* rng);
832#endif /* !NO_DH || !NO_DSA || !NO_RSA || WOLFSSL_KEY_GEN */
833#ifdef WOLFSSL_KEY_GEN
834MP_API int mp_gcd(fp_int *a, fp_int *b, fp_int *c);
835MP_API int mp_lcm(fp_int *a, fp_int *b, fp_int *c);
836MP_API int mp_rand_prime(mp_int* N, int len, WC_RNG* rng, void* heap);
837MP_API int mp_exch(mp_int *a, mp_int *b);
838#endif /* WOLFSSL_KEY_GEN */
839MP_API int mp_cond_swap_ct (mp_int * a, mp_int * b, int c, int m);
840
841MP_API int mp_cnt_lsb(fp_int *a);
842MP_API int mp_div_2d(fp_int *a, int b, fp_int *c, fp_int *d);
843MP_API int mp_mod_d(fp_int* a, fp_digit b, fp_digit* c);
844MP_API int mp_lshd (mp_int * a, int b);
845MP_API int mp_abs(mp_int* a, mp_int* b);
846
847WOLFSSL_API word32 CheckRunTimeFastMath(void);
848
849/* If user uses RSA, DH, DSA, or ECC math lib directly then fast math FP_SIZE
850 must match, return 1 if a match otherwise 0 */
851#define CheckFastMathSettings() (FP_SIZE == CheckRunTimeFastMath())
852
853
854#ifdef __cplusplus
855 }
856#endif
857
858#endif /* WOLF_CRYPT_TFM_H */
859