From 554310847afe2d6148e62343cd15d39fa7209937 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 16 Oct 2019 09:26:04 +0200 Subject: [PATCH 001/304] tommath.h: use enums --- makefile_include.mk | 2 +- tommath.h | 33 +++++---------------------------- 2 files changed, 6 insertions(+), 29 deletions(-) diff --git a/makefile_include.mk b/makefile_include.mk index cdf0fa7dd..7d0b997d9 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -62,7 +62,7 @@ endif ifdef CONV_WARNINGS LTM_CFLAGS += -std=c89 -Wconversion -Wsign-conversion ifeq ($(CONV_WARNINGS), strict) -LTM_CFLAGS += -DMP_USE_ENUMS -Wc++-compat +LTM_CFLAGS += -Wc++-compat endif else LTM_CFLAGS += -Wsystem-headers diff --git a/tommath.h b/tommath.h index 8dd3bb34c..5af5014e2 100644 --- a/tommath.h +++ b/tommath.h @@ -115,20 +115,22 @@ typedef uint64_t private_mp_word; #define LTM_PRIME_SAFE (MP_DEPRECATED_PRAGMA("LTM_PRIME_SAFE has been deprecated, use MP_PRIME_SAFE") MP_PRIME_SAFE) #define LTM_PRIME_2MSB_ON (MP_DEPRECATED_PRAGMA("LTM_PRIME_2MSB_ON has been deprecated, use MP_PRIME_2MSB_ON") MP_PRIME_2MSB_ON) -#ifdef MP_USE_ENUMS typedef enum { MP_ZPOS = 0, /* positive */ MP_NEG = 1 /* negative */ } mp_sign; + typedef enum { MP_LT = -1, /* less than */ MP_EQ = 0, /* equal */ MP_GT = 1 /* greater than */ } mp_ord; + typedef enum { MP_NO = 0, MP_YES = 1 } mp_bool; + typedef enum { MP_OKAY = 0, /* no error */ MP_ERR = -1, /* unknown error */ @@ -137,42 +139,17 @@ typedef enum { MP_ITER = -4, /* maximum iterations reached */ MP_BUF = -5, /* buffer overflow, supplied buffer too small */ } mp_err; + typedef enum { MP_LSB_FIRST = -1, MP_MSB_FIRST = 1 } mp_order; + typedef enum { MP_LITTLE_ENDIAN = -1, MP_NATIVE_ENDIAN = 0, MP_BIG_ENDIAN = 1 } mp_endian; -#else -typedef int mp_sign; -#define MP_ZPOS 0 /* positive integer */ -#define MP_NEG 1 /* negative */ -typedef int mp_ord; -#define MP_LT -1 /* less than */ -#define MP_EQ 0 /* equal to */ -#define MP_GT 1 /* greater than */ -typedef int mp_bool; -#define MP_YES 1 -#define MP_NO 0 -typedef int mp_err; -#define MP_OKAY 0 /* no error */ -#define MP_ERR -1 /* unknown error */ -#define MP_MEM -2 /* out of mem */ -#define MP_VAL -3 /* invalid input */ -#define MP_RANGE (MP_DEPRECATED_PRAGMA("MP_RANGE has been deprecated in favor of MP_VAL") MP_VAL) -#define MP_ITER -4 /* maximum iterations reached */ -#define MP_BUF -5 /* buffer overflow, supplied buffer too small */ -typedef int mp_order; -#define MP_LSB_FIRST -1 -#define MP_MSB_FIRST 1 -typedef int mp_endian; -#define MP_LITTLE_ENDIAN -1 -#define MP_NATIVE_ENDIAN 0 -#define MP_BIG_ENDIAN 1 -#endif /* tunable cutoffs */ From fce429d08bc7207e356e785e3fdaaa89140fedfe Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 24 Jul 2019 15:54:01 +0200 Subject: [PATCH 002/304] tommath.h: do not expose limits.h --- tommath.h | 5 ----- tommath_private.h | 5 ++--- 2 files changed, 2 insertions(+), 8 deletions(-) diff --git a/tommath.h b/tommath.h index 5af5014e2..130350952 100644 --- a/tommath.h +++ b/tommath.h @@ -6,7 +6,6 @@ #include #include -#include #ifdef LTM_NO_FILE # warning LTM_NO_FILE has been deprecated, use MP_NO_FILE. @@ -176,10 +175,6 @@ TOOM_SQR_CUTOFF; # define MP_PREC (MP_DEPRECATED_PRAGMA("MP_PREC is an internal macro") PRIVATE_MP_PREC) #endif -/* size of comba arrays, should be at least 2 * 2**(BITS_PER_WORD - BITS_PER_DIGIT*2) */ -#define PRIVATE_MP_WARRAY (int)(1uLL << (((CHAR_BIT * sizeof(private_mp_word)) - (2 * MP_DIGIT_BIT)) + 1)) -#define MP_WARRAY (MP_DEPRECATED_PRAGMA("MP_WARRAY is an internal macro") PRIVATE_MP_WARRAY) - #if defined(__GNUC__) && __GNUC__ >= 4 # define MP_NULL_TERMINATED __attribute__((sentinel)) #else diff --git a/tommath_private.h b/tommath_private.h index 7c167a5d5..5ccb4e260 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -6,6 +6,7 @@ #include "tommath.h" #include "tommath_class.h" +#include /* * Private symbols @@ -163,9 +164,7 @@ typedef private_mp_word mp_word; #define MP_SIZEOF_BITS(type) ((size_t)CHAR_BIT * sizeof(type)) #define MP_MAXFAST (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) -/* TODO: Remove PRIVATE_MP_WARRAY as soon as deprecated MP_WARRAY is removed from tommath.h */ -#undef MP_WARRAY -#define MP_WARRAY PRIVATE_MP_WARRAY +#define MP_WARRAY (1 << ((MP_SIZEOF_BITS(mp_word) - (2 * MP_DIGIT_BIT)) + 1)) /* TODO: Remove PRIVATE_MP_PREC as soon as deprecated MP_PREC is removed from tommath.h */ #ifdef PRIVATE_MP_PREC From 45a3bf76947c72bdd65fae1cd6f230ca36dd81b1 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 16 Oct 2019 09:21:19 +0200 Subject: [PATCH 003/304] remove deprecated functions --- bn_deprecated.c | 316 ----------------------------------- bn_mp_prime_is_prime.c | 4 +- bn_mp_prime_next_prime.c | 10 +- bn_mp_prime_rand.c | 2 +- bn_prime_tab.c | 16 +- bn_s_mp_prime_is_divisible.c | 2 +- demo/test.c | 15 -- makefile | 3 - makefile.mingw | 3 - makefile.msvc | 3 - makefile.shared | 3 - makefile.unix | 3 - tommath.h | 135 --------------- tommath_class.h | 84 ---------- tommath_private.h | 46 +++-- 15 files changed, 29 insertions(+), 616 deletions(-) diff --git a/bn_deprecated.c b/bn_deprecated.c index 2056b20e6..8dcaa2fbe 100644 --- a/bn_deprecated.c +++ b/bn_deprecated.c @@ -2,320 +2,4 @@ #ifdef BN_DEPRECATED_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ - -#ifdef BN_MP_GET_BIT_C -int mp_get_bit(const mp_int *a, int b) -{ - if (b < 0) { - return MP_VAL; - } - return (s_mp_get_bit(a, (unsigned int)b) == MP_YES) ? MP_YES : MP_NO; -} -#endif -#ifdef BN_MP_JACOBI_C -mp_err mp_jacobi(const mp_int *a, const mp_int *n, int *c) -{ - if (a->sign == MP_NEG) { - return MP_VAL; - } - if (mp_cmp_d(n, 0uL) != MP_GT) { - return MP_VAL; - } - return mp_kronecker(a, n, c); -} -#endif -#ifdef BN_MP_PRIME_RANDOM_EX_C -mp_err mp_prime_random_ex(mp_int *a, int t, int size, int flags, private_mp_prime_callback cb, void *dat) -{ - return s_mp_prime_random_ex(a, t, size, flags, cb, dat); -} -#endif -#ifdef BN_MP_RAND_DIGIT_C -mp_err mp_rand_digit(mp_digit *r) -{ - mp_err err = s_mp_rand_source(r, sizeof(mp_digit)); - *r &= MP_MASK; - return err; -} -#endif -#ifdef BN_FAST_MP_INVMOD_C -mp_err fast_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) -{ - return s_mp_invmod_fast(a, b, c); -} -#endif -#ifdef BN_FAST_MP_MONTGOMERY_REDUCE_C -mp_err fast_mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) -{ - return s_mp_montgomery_reduce_fast(x, n, rho); -} -#endif -#ifdef BN_FAST_S_MP_MUL_DIGS_C -mp_err fast_s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) -{ - return s_mp_mul_digs_fast(a, b, c, digs); -} -#endif -#ifdef BN_FAST_S_MP_MUL_HIGH_DIGS_C -mp_err fast_s_mp_mul_high_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) -{ - return s_mp_mul_high_digs_fast(a, b, c, digs); -} -#endif -#ifdef BN_FAST_S_MP_SQR_C -mp_err fast_s_mp_sqr(const mp_int *a, mp_int *b) -{ - return s_mp_sqr_fast(a, b); -} -#endif -#ifdef BN_MP_BALANCE_MUL_C -mp_err mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) -{ - return s_mp_balance_mul(a, b, c); -} -#endif -#ifdef BN_MP_EXPTMOD_FAST_C -mp_err mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) -{ - return s_mp_exptmod_fast(G, X, P, Y, redmode); -} -#endif -#ifdef BN_MP_INVMOD_SLOW_C -mp_err mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) -{ - return s_mp_invmod_slow(a, b, c); -} -#endif -#ifdef BN_MP_KARATSUBA_MUL_C -mp_err mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) -{ - return s_mp_karatsuba_mul(a, b, c); -} -#endif -#ifdef BN_MP_KARATSUBA_SQR_C -mp_err mp_karatsuba_sqr(const mp_int *a, mp_int *b) -{ - return s_mp_karatsuba_sqr(a, b); -} -#endif -#ifdef BN_MP_TOOM_MUL_C -mp_err mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) -{ - return s_mp_toom_mul(a, b, c); -} -#endif -#ifdef BN_MP_TOOM_SQR_C -mp_err mp_toom_sqr(const mp_int *a, mp_int *b) -{ - return s_mp_toom_sqr(a, b); -} -#endif -#ifdef S_MP_REVERSE_C -void bn_reverse(unsigned char *s, int len) -{ - if (len > 0) { - s_mp_reverse(s, (size_t)len); - } -} -#endif -#ifdef BN_MP_TC_AND_C -mp_err mp_tc_and(const mp_int *a, const mp_int *b, mp_int *c) -{ - return mp_and(a, b, c); -} -#endif -#ifdef BN_MP_TC_OR_C -mp_err mp_tc_or(const mp_int *a, const mp_int *b, mp_int *c) -{ - return mp_or(a, b, c); -} -#endif -#ifdef BN_MP_TC_XOR_C -mp_err mp_tc_xor(const mp_int *a, const mp_int *b, mp_int *c) -{ - return mp_xor(a, b, c); -} -#endif -#ifdef BN_MP_TC_DIV_2D_C -mp_err mp_tc_div_2d(const mp_int *a, int b, mp_int *c) -{ - return mp_signed_rsh(a, b, c); -} -#endif -#ifdef BN_MP_INIT_SET_INT_C -mp_err mp_init_set_int(mp_int *a, unsigned long b) -{ - return mp_init_u32(a, (uint32_t)b); -} -#endif -#ifdef BN_MP_SET_INT_C -mp_err mp_set_int(mp_int *a, unsigned long b) -{ - mp_set_u32(a, (uint32_t)b); - return MP_OKAY; -} -#endif -#ifdef BN_MP_SET_LONG_C -mp_err mp_set_long(mp_int *a, unsigned long b) -{ - mp_set_u64(a, b); - return MP_OKAY; -} -#endif -#ifdef BN_MP_SET_LONG_LONG_C -mp_err mp_set_long_long(mp_int *a, unsigned long long b) -{ - mp_set_u64(a, b); - return MP_OKAY; -} -#endif -#ifdef BN_MP_GET_INT_C -unsigned long mp_get_int(const mp_int *a) -{ - return (unsigned long)mp_get_mag_u32(a); -} -#endif -#ifdef BN_MP_GET_LONG_C -unsigned long mp_get_long(const mp_int *a) -{ - return (unsigned long)mp_get_mag_ul(a); -} -#endif -#ifdef BN_MP_GET_LONG_LONG_C -unsigned long long mp_get_long_long(const mp_int *a) -{ - return mp_get_mag_ull(a); -} -#endif -#ifdef BN_MP_PRIME_IS_DIVISIBLE_C -mp_err mp_prime_is_divisible(const mp_int *a, mp_bool *result) -{ - return s_mp_prime_is_divisible(a, result); -} -#endif -#ifdef BN_MP_EXPT_D_EX_C -mp_err mp_expt_d_ex(const mp_int *a, mp_digit b, mp_int *c, int fast) -{ - (void)fast; - if (b > MP_MIN(MP_DIGIT_MAX, UINT32_MAX)) { - return MP_VAL; - } - return mp_expt_u32(a, (uint32_t)b, c); -} -#endif -#ifdef BN_MP_EXPT_D_C -mp_err mp_expt_d(const mp_int *a, mp_digit b, mp_int *c) -{ - if (b > MP_MIN(MP_DIGIT_MAX, UINT32_MAX)) { - return MP_VAL; - } - return mp_expt_u32(a, (uint32_t)b, c); -} -#endif -#ifdef BN_MP_N_ROOT_EX_C -mp_err mp_n_root_ex(const mp_int *a, mp_digit b, mp_int *c, int fast) -{ - (void)fast; - if (b > MP_MIN(MP_DIGIT_MAX, UINT32_MAX)) { - return MP_VAL; - } - return mp_root_u32(a, (uint32_t)b, c); -} -#endif -#ifdef BN_MP_N_ROOT_C -mp_err mp_n_root(const mp_int *a, mp_digit b, mp_int *c) -{ - if (b > MP_MIN(MP_DIGIT_MAX, UINT32_MAX)) { - return MP_VAL; - } - return mp_root_u32(a, (uint32_t)b, c); -} -#endif -#ifdef BN_MP_UNSIGNED_BIN_SIZE_C -int mp_unsigned_bin_size(const mp_int *a) -{ - return (int)mp_ubin_size(a); -} -#endif -#ifdef BN_MP_READ_UNSIGNED_BIN_C -mp_err mp_read_unsigned_bin(mp_int *a, const unsigned char *b, int c) -{ - return mp_from_ubin(a, b, (size_t) c); -} -#endif -#ifdef BN_MP_TO_UNSIGNED_BIN_C -mp_err mp_to_unsigned_bin(const mp_int *a, unsigned char *b) -{ - return mp_to_ubin(a, b, SIZE_MAX, NULL); -} -#endif -#ifdef BN_MP_TO_UNSIGNED_BIN_N_C -mp_err mp_to_unsigned_bin_n(const mp_int *a, unsigned char *b, unsigned long *outlen) -{ - size_t n = mp_ubin_size(a); - if (*outlen < (unsigned long)n) { - return MP_VAL; - } - *outlen = (unsigned long)n; - return mp_to_ubin(a, b, n, NULL); -} -#endif -#ifdef BN_MP_SIGNED_BIN_SIZE_C -int mp_signed_bin_size(const mp_int *a) -{ - return (int)mp_sbin_size(a); -} -#endif -#ifdef BN_MP_READ_SIGNED_BIN_C -mp_err mp_read_signed_bin(mp_int *a, const unsigned char *b, int c) -{ - return mp_from_sbin(a, b, (size_t) c); -} -#endif -#ifdef BN_MP_TO_SIGNED_BIN_C -mp_err mp_to_signed_bin(const mp_int *a, unsigned char *b) -{ - return mp_to_sbin(a, b, SIZE_MAX, NULL); -} -#endif -#ifdef BN_MP_TO_SIGNED_BIN_N_C -mp_err mp_to_signed_bin_n(const mp_int *a, unsigned char *b, unsigned long *outlen) -{ - size_t n = mp_sbin_size(a); - if (*outlen < (unsigned long)n) { - return MP_VAL; - } - *outlen = (unsigned long)n; - return mp_to_sbin(a, b, n, NULL); -} -#endif -#ifdef BN_MP_TORADIX_N_C -mp_err mp_toradix_n(const mp_int *a, char *str, int radix, int maxlen) -{ - if (maxlen < 0) { - return MP_VAL; - } - return mp_to_radix(a, str, (size_t)maxlen, NULL, radix); -} -#endif -#ifdef BN_MP_TORADIX_C -mp_err mp_toradix(const mp_int *a, char *str, int radix) -{ - return mp_to_radix(a, str, SIZE_MAX, NULL, radix); -} -#endif -#ifdef BN_MP_IMPORT_C -mp_err mp_import(mp_int *rop, size_t count, int order, size_t size, int endian, size_t nails, - const void *op) -{ - return mp_unpack(rop, count, order, size, endian, nails, op); -} -#endif -#ifdef BN_MP_EXPORT_C -mp_err mp_export(void *rop, size_t *countp, int order, size_t size, - int endian, size_t nails, const mp_int *op) -{ - return mp_pack(rop, SIZE_MAX, countp, order, size, endian, nails, op); -} -#endif #endif diff --git a/bn_mp_prime_is_prime.c b/bn_mp_prime_is_prime.c index 7f9fc0b45..49fde93ba 100644 --- a/bn_mp_prime_is_prime.c +++ b/bn_mp_prime_is_prime.c @@ -51,7 +51,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) } /* is the input equal to one of the primes in the table? */ - for (ix = 0; ix < PRIVATE_MP_PRIME_TAB_SIZE; ix++) { + for (ix = 0; ix < MP_PRIME_TAB_SIZE; ix++) { if (mp_cmp_d(a, s_mp_prime_tab[ix]) == MP_EQ) { *result = MP_YES; return MP_OKAY; @@ -59,7 +59,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) } #ifdef MP_8BIT /* The search in the loop above was exhaustive in this case */ - if ((a->used == 1) && (PRIVATE_MP_PRIME_TAB_SIZE >= 31)) { + if ((a->used == 1) && (MP_PRIME_TAB_SIZE >= 31)) { return MP_OKAY; } #endif diff --git a/bn_mp_prime_next_prime.c b/bn_mp_prime_next_prime.c index 1e971fa4b..de27eabc7 100644 --- a/bn_mp_prime_next_prime.c +++ b/bn_mp_prime_next_prime.c @@ -13,16 +13,16 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) int x, y, cmp; mp_err err; mp_bool res = MP_NO; - mp_digit res_tab[PRIVATE_MP_PRIME_TAB_SIZE], step, kstep; + mp_digit res_tab[MP_PRIME_TAB_SIZE], step, kstep; mp_int b; /* force positive */ a->sign = MP_ZPOS; /* simple algo if a is less than the largest prime in the table */ - if (mp_cmp_d(a, s_mp_prime_tab[PRIVATE_MP_PRIME_TAB_SIZE-1]) == MP_LT) { + if (mp_cmp_d(a, s_mp_prime_tab[MP_PRIME_TAB_SIZE-1]) == MP_LT) { /* find which prime it is bigger than "a" */ - for (x = 0; x < PRIVATE_MP_PRIME_TAB_SIZE; x++) { + for (x = 0; x < MP_PRIME_TAB_SIZE; x++) { cmp = mp_cmp_d(a, s_mp_prime_tab[x]); if (cmp == MP_EQ) { continue; @@ -66,7 +66,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) } /* generate the restable */ - for (x = 1; x < PRIVATE_MP_PRIME_TAB_SIZE; x++) { + for (x = 1; x < MP_PRIME_TAB_SIZE; x++) { if ((err = mp_mod_d(a, s_mp_prime_tab[x], res_tab + x)) != MP_OKAY) { return err; } @@ -88,7 +88,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) step += kstep; /* compute the new residue without using division */ - for (x = 1; x < PRIVATE_MP_PRIME_TAB_SIZE; x++) { + for (x = 1; x < MP_PRIME_TAB_SIZE; x++) { /* add the step to each residue */ res_tab[x] += kstep; diff --git a/bn_mp_prime_rand.c b/bn_mp_prime_rand.c index 4530e9a5e..af19d76c3 100644 --- a/bn_mp_prime_rand.c +++ b/bn_mp_prime_rand.c @@ -18,7 +18,7 @@ */ /* This is possibly the mother of all prime generation functions, muahahahahaha! */ -mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, private_mp_prime_callback cb, void *dat) +mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat) { unsigned char *tmp, maskAND, maskOR_msb, maskOR_lsb; int bsize, maskOR_msb_offset; diff --git a/bn_prime_tab.c b/bn_prime_tab.c index a6c07f8da..6bd53fe36 100644 --- a/bn_prime_tab.c +++ b/bn_prime_tab.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -const mp_digit ltm_prime_tab[] = { +const mp_digit s_mp_prime_tab[] = { 0x0002, 0x0003, 0x0005, 0x0007, 0x000B, 0x000D, 0x0011, 0x0013, 0x0017, 0x001D, 0x001F, 0x0025, 0x0029, 0x002B, 0x002F, 0x0035, 0x003B, 0x003D, 0x0043, 0x0047, 0x0049, 0x004F, 0x0053, 0x0059, @@ -44,18 +44,4 @@ const mp_digit ltm_prime_tab[] = { #endif }; -#if defined(__GNUC__) && __GNUC__ >= 4 -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wdeprecated-declarations" -const mp_digit *s_mp_prime_tab = ltm_prime_tab; -#pragma GCC diagnostic pop -#elif defined(_MSC_VER) && _MSC_VER >= 1500 -#pragma warning(push) -#pragma warning(disable: 4996) -const mp_digit *s_mp_prime_tab = ltm_prime_tab; -#pragma warning(pop) -#else -const mp_digit *s_mp_prime_tab = ltm_prime_tab; -#endif - #endif diff --git a/bn_s_mp_prime_is_divisible.c b/bn_s_mp_prime_is_divisible.c index ffd5093e6..ca303a5ba 100644 --- a/bn_s_mp_prime_is_divisible.c +++ b/bn_s_mp_prime_is_divisible.c @@ -17,7 +17,7 @@ mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result) /* default to not */ *result = MP_NO; - for (ix = 0; ix < PRIVATE_MP_PRIME_TAB_SIZE; ix++) { + for (ix = 0; ix < MP_PRIME_TAB_SIZE; ix++) { /* what is a mod LBL_prime_tab[ix] */ if ((err = mp_mod_d(a, s_mp_prime_tab[ix], &res)) != MP_OKAY) { return err; diff --git a/demo/test.c b/demo/test.c index 7b29a4ce9..c1fc878f3 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1283,21 +1283,6 @@ static int test_mp_read_radix(void) if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LTM_ERR; printf(" '0' a == %s, length = %zu\n", buf, written); - - - /* Although deprecated it needs to function as long as it isn't dropped */ - /* - printf("Testing deprecated mp_toradix_n\n"); - if( (err = mp_read_radix(&a, "-123456", 10) ) != MP_OKAY) goto LTM_ERR; - if( (err = mp_toradix_n(&a, buf, 10, 3) ) != MP_OKAY) goto LTM_ERR; - printf("a == %s\n", buf); - if( (err = mp_toradix_n(&a, buf, 10, 4) ) != MP_OKAY) goto LTM_ERR; - printf("a == %s\n", buf); - if( (err = mp_toradix_n(&a, buf, 10, 30) ) != MP_OKAY) goto LTM_ERR; - printf("a == %s\n", buf); - */ - - while (0) { char *s = fgets(buf, sizeof(buf), stdin); if (s != buf) break; diff --git a/makefile b/makefile index de65c9cf0..56eeabad1 100644 --- a/makefile +++ b/makefile @@ -95,9 +95,6 @@ uninstall: rm $(DESTDIR)$(LIBPATH)/$(LIBNAME) rm $(HEADERS_PUB:%=$(DESTDIR)$(INCPATH)/%) -test_standalone: test - @echo "test_standalone is deprecated, please use make-target 'test'" - DEMOS=test mtest_opponent define DEMO_template diff --git a/makefile.mingw b/makefile.mingw index 7eee57dc4..b11edb742 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -86,9 +86,6 @@ test.exe: demo/shared.o demo/test.o $(LIBMAIN_S) $(CC) $(LTM_CFLAGS) $(LTM_LDFLAGS) $^ -o $@ @echo NOTICE: start the tests by launching test.exe -test_standalone: test.exe - @echo test_standalone is deprecated, please use make-target 'test.exe' - all: $(LIBMAIN_S) test.exe tune: $(LIBNAME_S) diff --git a/makefile.msvc b/makefile.msvc index d282e936d..5b2f85090 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -72,9 +72,6 @@ test.exe: $(LIBMAIN_S) demo/shared.obj demo/test.obj cl $(LTM_CFLAGS) $(TOBJECTS) $(LIBMAIN_S) $(LTM_LDFLAGS) demo/shared.c demo/test.c /Fe$@ @echo NOTICE: start the tests by launching test.exe -test_standalone: test.exe - @echo test_standalone is deprecated, please use make-target 'test.exe' - all: $(LIBMAIN_S) test.exe tune: $(LIBMAIN_S) diff --git a/makefile.shared b/makefile.shared index 680210736..5e0f4f2c4 100644 --- a/makefile.shared +++ b/makefile.shared @@ -79,9 +79,6 @@ uninstall: rm $(HEADERS_PUB:%=$(DESTDIR)$(INCPATH)/%) rm $(DESTDIR)$(LIBPATH)/pkgconfig/libtommath.pc -test_standalone: test - @echo "test_standalone is deprecated, please use make-target 'test'" - test mtest_opponent: demo/shared.o $(LIBNAME) | demo/test.o demo/mtest_opponent.o $(LTLINK) $(LTM_LDFLAGS) demo/$@.o $^ -o $@ diff --git a/makefile.unix b/makefile.unix index 750be5634..e7a6f257b 100644 --- a/makefile.unix +++ b/makefile.unix @@ -84,9 +84,6 @@ test: demo/shared.o demo/test.o $(LIBMAIN_S) $(CC) $(LTM_CFLAGS) $(LTM_LDFLAGS) $^ -o $@ @echo "NOTICE: start the tests by: ./test" -test_standalone: test - @echo "test_standalone is deprecated, please use make-target 'test'" - all: $(LIBMAIN_S) test tune: $(LIBMAIN_S) diff --git a/tommath.h b/tommath.h index 130350952..6c4e95774 100644 --- a/tommath.h +++ b/tommath.h @@ -7,11 +7,6 @@ #include #include -#ifdef LTM_NO_FILE -# warning LTM_NO_FILE has been deprecated, use MP_NO_FILE. -# define MP_NO_FILE -#endif - #ifndef MP_NO_FILE # include #endif @@ -97,11 +92,6 @@ typedef uint64_t private_mp_word; # endif #endif -/* mp_word is a private type */ -#define mp_word MP_DEPRECATED_PRAGMA("mp_word has been made private") private_mp_word - -#define MP_SIZEOF_MP_DIGIT (MP_DEPRECATED_PRAGMA("MP_SIZEOF_MP_DIGIT has been deprecated, use sizeof (mp_digit)") sizeof (mp_digit)) - #define MP_MASK ((((mp_digit)1)<<((mp_digit)MP_DIGIT_BIT))-((mp_digit)1)) #define MP_DIGIT_MAX MP_MASK @@ -110,10 +100,6 @@ typedef uint64_t private_mp_word; #define MP_PRIME_SAFE 0x0002 /* Safe prime (p-1)/2 == prime */ #define MP_PRIME_2MSB_ON 0x0008 /* force 2nd MSB to 1 */ -#define LTM_PRIME_BBS (MP_DEPRECATED_PRAGMA("LTM_PRIME_BBS has been deprecated, use MP_PRIME_BBS") MP_PRIME_BBS) -#define LTM_PRIME_SAFE (MP_DEPRECATED_PRAGMA("LTM_PRIME_SAFE has been deprecated, use MP_PRIME_SAFE") MP_PRIME_SAFE) -#define LTM_PRIME_2MSB_ON (MP_DEPRECATED_PRAGMA("LTM_PRIME_2MSB_ON has been deprecated, use MP_PRIME_2MSB_ON") MP_PRIME_2MSB_ON) - typedef enum { MP_ZPOS = 0, /* positive */ MP_NEG = 1 /* negative */ @@ -163,18 +149,6 @@ TOOM_SQR_CUTOFF; /* define this to use lower memory usage routines (exptmods mostly) */ /* #define MP_LOW_MEM */ -/* default precision */ -#ifndef MP_PREC -# ifndef MP_LOW_MEM -# define PRIVATE_MP_PREC 32 /* default digits of precision */ -# elif defined(MP_8BIT) -# define PRIVATE_MP_PREC 16 /* default digits of precision */ -# else -# define PRIVATE_MP_PREC 8 /* default digits of precision */ -# endif -# define MP_PREC (MP_DEPRECATED_PRAGMA("MP_PREC is an internal macro") PRIVATE_MP_PREC) -#endif - #if defined(__GNUC__) && __GNUC__ >= 4 # define MP_NULL_TERMINATED __attribute__((sentinel)) #else @@ -216,11 +190,6 @@ TOOM_SQR_CUTOFF; # define MP_DEPRECATED_PRAGMA(s) #endif -#define DIGIT_BIT (MP_DEPRECATED_PRAGMA("DIGIT_BIT macro is deprecated, MP_DIGIT_BIT instead") MP_DIGIT_BIT) -#define USED(m) (MP_DEPRECATED_PRAGMA("USED macro is deprecated, use z->used instead") (m)->used) -#define DIGIT(m, k) (MP_DEPRECATED_PRAGMA("DIGIT macro is deprecated, use z->dp instead") (m)->dp[(k)]) -#define SIGN(m) (MP_DEPRECATED_PRAGMA("SIGN macro is deprecated, use z->sign instead") (m)->sign) - /* the infamous mp_int structure */ typedef struct { int used, alloc; @@ -228,10 +197,6 @@ typedef struct { mp_digit *dp; } mp_int; -/* callback for mp_prime_random, should fill dst with random bytes and return how many read [upto len] */ -typedef int private_mp_prime_callback(unsigned char *dst, int len, void *dat); -typedef private_mp_prime_callback MP_DEPRECATED(mp_rand_source) ltm_prime_callback; - /* error code to char* string */ const char *mp_error_to_string(mp_err code) MP_WUR; @@ -323,15 +288,6 @@ mp_err mp_init_ull(mp_int *a, unsigned long long b) MP_WUR; void mp_set(mp_int *a, mp_digit b); mp_err mp_init_set(mp_int *a, mp_digit b) MP_WUR; -/* get integer, set integer and init with integer (deprecated) */ -MP_DEPRECATED(mp_get_mag_u32/mp_get_u32) unsigned long mp_get_int(const mp_int *a) MP_WUR; -MP_DEPRECATED(mp_get_mag_ul/mp_get_ul) unsigned long mp_get_long(const mp_int *a) MP_WUR; -MP_DEPRECATED(mp_get_mag_ull/mp_get_ull) unsigned long long mp_get_long_long(const mp_int *a) MP_WUR; -MP_DEPRECATED(mp_set_ul) mp_err mp_set_int(mp_int *a, unsigned long b); -MP_DEPRECATED(mp_set_ul) mp_err mp_set_long(mp_int *a, unsigned long b); -MP_DEPRECATED(mp_set_ull) mp_err mp_set_long_long(mp_int *a, unsigned long long b); -MP_DEPRECATED(mp_init_ul) mp_err mp_init_set_int(mp_int *a, unsigned long b) MP_WUR; - /* copy, b = a */ mp_err mp_copy(const mp_int *a, mp_int *b) MP_WUR; @@ -341,16 +297,6 @@ mp_err mp_init_copy(mp_int *a, const mp_int *b) MP_WUR; /* trim unused digits */ void mp_clamp(mp_int *a); - -/* export binary data */ -MP_DEPRECATED(mp_pack) mp_err mp_export(void *rop, size_t *countp, int order, size_t size, - int endian, size_t nails, const mp_int *op) MP_WUR; - -/* import binary data */ -MP_DEPRECATED(mp_unpack) mp_err mp_import(mp_int *rop, size_t count, int order, - size_t size, int endian, size_t nails, - const void *op) MP_WUR; - /* unpack binary data */ mp_err mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, mp_endian endian, size_t nails, const void *op) MP_WUR; @@ -396,46 +342,24 @@ int mp_cnt_lsb(const mp_int *a) MP_WUR; /* makes a pseudo-random mp_int of a given size */ mp_err mp_rand(mp_int *a, int digits) MP_WUR; -/* makes a pseudo-random small int of a given size */ -MP_DEPRECATED(mp_rand) mp_err mp_rand_digit(mp_digit *r) MP_WUR; /* use custom random data source instead of source provided the platform */ void mp_rand_source(mp_err(*source)(void *out, size_t size)); -#ifdef MP_PRNG_ENABLE_LTM_RNG -# warning MP_PRNG_ENABLE_LTM_RNG has been deprecated, use mp_rand_source instead. -/* A last resort to provide random data on systems without any of the other - * implemented ways to gather entropy. - * It is compatible with `rng_get_bytes()` from libtomcrypt so you could - * provide that one and then set `ltm_rng = rng_get_bytes;` */ -extern unsigned long (*ltm_rng)(unsigned char *out, unsigned long outlen, void (*callback)(void)); -extern void (*ltm_rng_callback)(void); -#endif - /* ---> binary operations <--- */ -/* Checks the bit at position b and returns MP_YES - * if the bit is 1, MP_NO if it is 0 and MP_VAL - * in case of error - */ -MP_DEPRECATED(s_mp_get_bit) int mp_get_bit(const mp_int *a, int b) MP_WUR; - /* c = a XOR b (two complement) */ -MP_DEPRECATED(mp_xor) mp_err mp_tc_xor(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* c = a OR b (two complement) */ -MP_DEPRECATED(mp_or) mp_err mp_tc_or(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* c = a AND b (two complement) */ -MP_DEPRECATED(mp_and) mp_err mp_tc_and(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* b = ~a (bitwise not, two complement) */ mp_err mp_complement(const mp_int *a, mp_int *b) MP_WUR; /* right shift with sign extension */ -MP_DEPRECATED(mp_signed_rsh) mp_err mp_tc_div_2d(const mp_int *a, int b, mp_int *c) MP_WUR; mp_err mp_signed_rsh(const mp_int *a, int b, mp_int *c) MP_WUR; /* ---> Basic arithmetic <--- */ @@ -527,8 +451,6 @@ mp_err mp_lcm(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; * returns error if a < 0 and b is even */ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) MP_WUR; -MP_DEPRECATED(mp_root_u32) mp_err mp_n_root(const mp_int *a, mp_digit b, mp_int *c) MP_WUR; -MP_DEPRECATED(mp_root_u32) mp_err mp_n_root_ex(const mp_int *a, mp_digit b, mp_int *c, int fast) MP_WUR; /* special sqrt algo */ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) MP_WUR; @@ -539,9 +461,6 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) MP_WU /* is number a square? */ mp_err mp_is_square(const mp_int *arg, mp_bool *ret) MP_WUR; -/* computes the jacobi c = (a | n) (or Legendre if b is prime) */ -MP_DEPRECATED(mp_kronecker) mp_err mp_jacobi(const mp_int *a, const mp_int *n, int *c) MP_WUR; - /* computes the Kronecker symbol c = (a | p) (like jacobi() but with {a,p} in Z */ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) MP_WUR; @@ -598,20 +517,6 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) /* ---> Primes <--- */ -/* number of primes */ -#ifdef MP_8BIT -# define PRIVATE_MP_PRIME_TAB_SIZE 31 -#else -# define PRIVATE_MP_PRIME_TAB_SIZE 256 -#endif -#define PRIME_SIZE (MP_DEPRECATED_PRAGMA("PRIME_SIZE has been made internal") PRIVATE_MP_PRIME_TAB_SIZE) - -/* table of first PRIME_SIZE primes */ -MP_DEPRECATED(internal) extern const mp_digit ltm_prime_tab[PRIVATE_MP_PRIME_TAB_SIZE]; - -/* result=1 if a is divisible by one of the first PRIME_SIZE primes */ -MP_DEPRECATED(mp_prime_is_prime) mp_err mp_prime_is_divisible(const mp_int *a, mp_bool *result) MP_WUR; - /* performs one Fermat test of "a" using base "b". * Sets result to 0 if composite or 1 if probable prime */ @@ -660,17 +565,6 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) MP_WUR; */ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) MP_WUR; -/* makes a truly random prime of a given size (bytes), - * call with bbs = 1 if you want it to be congruent to 3 mod 4 - * - * You have to supply a callback which fills in a buffer with random bytes. "dat" is a parameter you can - * have passed to the callback (e.g. a state or something). This function doesn't use "dat" itself - * so it can be NULL - * - * The prime generated will be larger than 2^(8*size). - */ -#define mp_prime_random(a, t, size, bbs, cb, dat) (MP_DEPRECATED_PRAGMA("mp_prime_random has been deprecated, use mp_prime_rand instead") mp_prime_random_ex(a, t, ((size) * 8) + 1, (bbs==1)?MP_PRIME_BBS:0, cb, dat)) - /* makes a truly random prime of a given size (bits), * * Flags are as follows: @@ -684,8 +578,6 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) MP_WUR; * so it can be NULL * */ -MP_DEPRECATED(mp_prime_rand) mp_err mp_prime_random_ex(mp_int *a, int t, int size, int flags, - private_mp_prime_callback cb, void *dat) MP_WUR; mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) MP_WUR; /* Integer logarithm to integer base */ @@ -693,23 +585,10 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) MP_WUR; /* c = a**b */ mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) MP_WUR; -MP_DEPRECATED(mp_expt_u32) mp_err mp_expt_d(const mp_int *a, mp_digit b, mp_int *c) MP_WUR; -MP_DEPRECATED(mp_expt_u32) mp_err mp_expt_d_ex(const mp_int *a, mp_digit b, mp_int *c, int fast) MP_WUR; /* ---> radix conversion <--- */ int mp_count_bits(const mp_int *a) MP_WUR; - -MP_DEPRECATED(mp_ubin_size) int mp_unsigned_bin_size(const mp_int *a) MP_WUR; -MP_DEPRECATED(mp_from_ubin) mp_err mp_read_unsigned_bin(mp_int *a, const unsigned char *b, int c) MP_WUR; -MP_DEPRECATED(mp_to_ubin) mp_err mp_to_unsigned_bin(const mp_int *a, unsigned char *b) MP_WUR; -MP_DEPRECATED(mp_to_ubin) mp_err mp_to_unsigned_bin_n(const mp_int *a, unsigned char *b, unsigned long *outlen) MP_WUR; - -MP_DEPRECATED(mp_sbin_size) int mp_signed_bin_size(const mp_int *a) MP_WUR; -MP_DEPRECATED(mp_from_sbin) mp_err mp_read_signed_bin(mp_int *a, const unsigned char *b, int c) MP_WUR; -MP_DEPRECATED(mp_to_sbin) mp_err mp_to_signed_bin(const mp_int *a, unsigned char *b) MP_WUR; -MP_DEPRECATED(mp_to_sbin) mp_err mp_to_signed_bin_n(const mp_int *a, unsigned char *b, unsigned long *outlen) MP_WUR; - size_t mp_ubin_size(const mp_int *a) MP_WUR; mp_err mp_from_ubin(mp_int *a, const unsigned char *buf, size_t size) MP_WUR; mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) MP_WUR; @@ -719,8 +598,6 @@ mp_err mp_from_sbin(mp_int *a, const unsigned char *buf, size_t size) MP_WUR; mp_err mp_to_sbin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) MP_WUR; mp_err mp_read_radix(mp_int *a, const char *str, int radix) MP_WUR; -MP_DEPRECATED(mp_to_radix) mp_err mp_toradix(const mp_int *a, char *str, int radix) MP_WUR; -MP_DEPRECATED(mp_to_radix) mp_err mp_toradix_n(const mp_int *a, char *str, int radix, int maxlen) MP_WUR; mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, int radix) MP_WUR; mp_err mp_radix_size(const mp_int *a, int radix, int *size) MP_WUR; @@ -729,18 +606,6 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) MP_WUR; #endif -#define mp_read_raw(mp, str, len) (MP_DEPRECATED_PRAGMA("replaced by mp_read_signed_bin") mp_read_signed_bin((mp), (str), (len))) -#define mp_raw_size(mp) (MP_DEPRECATED_PRAGMA("replaced by mp_signed_bin_size") mp_signed_bin_size(mp)) -#define mp_toraw(mp, str) (MP_DEPRECATED_PRAGMA("replaced by mp_to_signed_bin") mp_to_signed_bin((mp), (str))) -#define mp_read_mag(mp, str, len) (MP_DEPRECATED_PRAGMA("replaced by mp_read_unsigned_bin") mp_read_unsigned_bin((mp), (str), (len)) -#define mp_mag_size(mp) (MP_DEPRECATED_PRAGMA("replaced by mp_unsigned_bin_size") mp_unsigned_bin_size(mp)) -#define mp_tomag(mp, str) (MP_DEPRECATED_PRAGMA("replaced by mp_to_unsigned_bin") mp_to_unsigned_bin((mp), (str))) - -#define mp_tobinary(M, S) (MP_DEPRECATED_PRAGMA("replaced by mp_to_binary") mp_toradix((M), (S), 2)) -#define mp_tooctal(M, S) (MP_DEPRECATED_PRAGMA("replaced by mp_to_octal") mp_toradix((M), (S), 8)) -#define mp_todecimal(M, S) (MP_DEPRECATED_PRAGMA("replaced by mp_to_decimal") mp_toradix((M), (S), 10)) -#define mp_tohex(M, S) (MP_DEPRECATED_PRAGMA("replaced by mp_to_hex") mp_toradix((M), (S), 16)) - #define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), NULL, 2) #define mp_to_octal(M, S, N) mp_to_radix((M), (S), (N), NULL, 8) #define mp_to_decimal(M, S, N) mp_to_radix((M), (S), (N), NULL, 10) diff --git a/tommath_class.h b/tommath_class.h index 52ba585ec..b0a82f071 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -174,90 +174,6 @@ #endif #if defined(BN_DEPRECATED_C) -# define BN_FAST_MP_INVMOD_C -# define BN_FAST_MP_MONTGOMERY_REDUCE_C -# define BN_FAST_S_MP_MUL_DIGS_C -# define BN_FAST_S_MP_MUL_HIGH_DIGS_C -# define BN_FAST_S_MP_SQR_C -# define BN_MP_AND_C -# define BN_MP_BALANCE_MUL_C -# define BN_MP_CMP_D_C -# define BN_MP_EXPORT_C -# define BN_MP_EXPTMOD_FAST_C -# define BN_MP_EXPT_D_C -# define BN_MP_EXPT_D_EX_C -# define BN_MP_EXPT_U32_C -# define BN_MP_FROM_SBIN_C -# define BN_MP_FROM_UBIN_C -# define BN_MP_GET_BIT_C -# define BN_MP_GET_INT_C -# define BN_MP_GET_LONG_C -# define BN_MP_GET_LONG_LONG_C -# define BN_MP_GET_MAG_U32_C -# define BN_MP_GET_MAG_ULL_C -# define BN_MP_GET_MAG_UL_C -# define BN_MP_IMPORT_C -# define BN_MP_INIT_SET_INT_C -# define BN_MP_INIT_U32_C -# define BN_MP_INVMOD_SLOW_C -# define BN_MP_JACOBI_C -# define BN_MP_KARATSUBA_MUL_C -# define BN_MP_KARATSUBA_SQR_C -# define BN_MP_KRONECKER_C -# define BN_MP_N_ROOT_C -# define BN_MP_N_ROOT_EX_C -# define BN_MP_OR_C -# define BN_MP_PACK_C -# define BN_MP_PRIME_IS_DIVISIBLE_C -# define BN_MP_PRIME_RANDOM_EX_C -# define BN_MP_RAND_DIGIT_C -# define BN_MP_READ_SIGNED_BIN_C -# define BN_MP_READ_UNSIGNED_BIN_C -# define BN_MP_ROOT_U32_C -# define BN_MP_SBIN_SIZE_C -# define BN_MP_SET_INT_C -# define BN_MP_SET_LONG_C -# define BN_MP_SET_LONG_LONG_C -# define BN_MP_SET_U32_C -# define BN_MP_SET_U64_C -# define BN_MP_SIGNED_BIN_SIZE_C -# define BN_MP_SIGNED_RSH_C -# define BN_MP_TC_AND_C -# define BN_MP_TC_DIV_2D_C -# define BN_MP_TC_OR_C -# define BN_MP_TC_XOR_C -# define BN_MP_TOOM_MUL_C -# define BN_MP_TOOM_SQR_C -# define BN_MP_TORADIX_C -# define BN_MP_TORADIX_N_C -# define BN_MP_TO_RADIX_C -# define BN_MP_TO_SBIN_C -# define BN_MP_TO_SIGNED_BIN_C -# define BN_MP_TO_SIGNED_BIN_N_C -# define BN_MP_TO_UBIN_C -# define BN_MP_TO_UNSIGNED_BIN_C -# define BN_MP_TO_UNSIGNED_BIN_N_C -# define BN_MP_UBIN_SIZE_C -# define BN_MP_UNPACK_C -# define BN_MP_UNSIGNED_BIN_SIZE_C -# define BN_MP_XOR_C -# define BN_S_MP_BALANCE_MUL_C -# define BN_S_MP_EXPTMOD_FAST_C -# define BN_S_MP_GET_BIT_C -# define BN_S_MP_INVMOD_FAST_C -# define BN_S_MP_INVMOD_SLOW_C -# define BN_S_MP_KARATSUBA_MUL_C -# define BN_S_MP_KARATSUBA_SQR_C -# define BN_S_MP_MONTGOMERY_REDUCE_FAST_C -# define BN_S_MP_MUL_DIGS_FAST_C -# define BN_S_MP_MUL_HIGH_DIGS_FAST_C -# define BN_S_MP_PRIME_IS_DIVISIBLE_C -# define BN_S_MP_PRIME_RANDOM_EX_C -# define BN_S_MP_RAND_SOURCE_C -# define BN_S_MP_REVERSE_C -# define BN_S_MP_SQR_FAST_C -# define BN_S_MP_TOOM_MUL_C -# define BN_S_MP_TOOM_SQR_C #endif #if defined(BN_MP_2EXPT_C) diff --git a/tommath_private.h b/tommath_private.h index 5ccb4e260..0909fa529 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -147,7 +147,6 @@ extern void MP_FREE(void *mem, size_t size); #define MP_HAS(x) (sizeof(MP_STRINGIZE(BN_##x##_C)) == 1u) /* TODO: Remove private_mp_word as soon as deprecated mp_word is removed from tommath. */ -#undef mp_word typedef private_mp_word mp_word; #define MP_MIN(x, y) (((x) < (y)) ? (x) : (y)) @@ -166,10 +165,16 @@ typedef private_mp_word mp_word; #define MP_WARRAY (1 << ((MP_SIZEOF_BITS(mp_word) - (2 * MP_DIGIT_BIT)) + 1)) -/* TODO: Remove PRIVATE_MP_PREC as soon as deprecated MP_PREC is removed from tommath.h */ -#ifdef PRIVATE_MP_PREC -# undef MP_PREC -# define MP_PREC PRIVATE_MP_PREC + +/* default precision */ +#ifndef MP_PREC +# ifndef MP_LOW_MEM +# define MP_PREC 32 /* default digits of precision */ +# elif defined(MP_8BIT) +# define MP_PREC 16 /* default digits of precision */ +# else +# define MP_PREC 8 /* default digits of precision */ +# endif #endif /* Minimum number of available digits in mp_int, MP_PREC >= MP_MIN_PREC */ @@ -201,7 +206,8 @@ MP_PRIVATE mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_dig MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; -MP_PRIVATE mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, private_mp_prime_callback cb, void *dat); +typedef int mp_prime_callback(unsigned char *dst, int len, void *dat); +MP_PRIVATE mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat); MP_PRIVATE void s_mp_reverse(unsigned char *s, size_t len); MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); @@ -212,28 +218,14 @@ MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); extern MP_PRIVATE const char *const mp_s_rmap; extern MP_PRIVATE const uint8_t mp_s_rmap_reverse[]; extern MP_PRIVATE const size_t mp_s_rmap_reverse_sz; -extern MP_PRIVATE const mp_digit *s_mp_prime_tab; +extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; -/* deprecated functions */ -MP_DEPRECATED(s_mp_invmod_fast) mp_err fast_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c); -MP_DEPRECATED(s_mp_montgomery_reduce_fast) mp_err fast_mp_montgomery_reduce(mp_int *x, const mp_int *n, - mp_digit rho); -MP_DEPRECATED(s_mp_mul_digs_fast) mp_err fast_s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, - int digs); -MP_DEPRECATED(s_mp_mul_high_digs_fast) mp_err fast_s_mp_mul_high_digs(const mp_int *a, const mp_int *b, - mp_int *c, - int digs); -MP_DEPRECATED(s_mp_sqr_fast) mp_err fast_s_mp_sqr(const mp_int *a, mp_int *b); -MP_DEPRECATED(s_mp_balance_mul) mp_err mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c); -MP_DEPRECATED(s_mp_exptmod_fast) mp_err mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, - mp_int *Y, - int redmode); -MP_DEPRECATED(s_mp_invmod_slow) mp_err mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c); -MP_DEPRECATED(s_mp_karatsuba_mul) mp_err mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c); -MP_DEPRECATED(s_mp_karatsuba_sqr) mp_err mp_karatsuba_sqr(const mp_int *a, mp_int *b); -MP_DEPRECATED(s_mp_toom_mul) mp_err mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c); -MP_DEPRECATED(s_mp_toom_sqr) mp_err mp_toom_sqr(const mp_int *a, mp_int *b); -MP_DEPRECATED(s_mp_reverse) void bn_reverse(unsigned char *s, int len); +/* number of primes */ +#ifdef MP_8BIT +# define MP_PRIME_TAB_SIZE 31 +#else +# define MP_PRIME_TAB_SIZE 256 +#endif #define MP_GET_ENDIANNESS(x) \ do{\ From b4099e1ed249baa9e89ba9c16f1f3e9729a17733 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 16 Oct 2019 10:28:28 +0200 Subject: [PATCH 004/304] remove empty bn_deprecated.c file --- bn_deprecated.c | 5 ----- helper.pl | 12 +++--------- libtommath_VS2008.vcproj | 4 ---- makefile | 8 ++++---- makefile.mingw | 8 ++++---- makefile.msvc | 8 ++++---- makefile.shared | 8 ++++---- makefile.unix | 8 ++++---- tommath_class.h | 4 ---- 9 files changed, 23 insertions(+), 42 deletions(-) delete mode 100644 bn_deprecated.c diff --git a/bn_deprecated.c b/bn_deprecated.c deleted file mode 100644 index 8dcaa2fbe..000000000 --- a/bn_deprecated.c +++ /dev/null @@ -1,5 +0,0 @@ -#include "tommath_private.h" -#ifdef BN_DEPRECATED_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ -#endif diff --git a/helper.pl b/helper.pl index e60c1a775..69734ba18 100755 --- a/helper.pl +++ b/helper.pl @@ -358,15 +358,9 @@ sub update_dep my %depmap; foreach my $filename (glob 'bn*.c') { my $content; - if ($filename =~ "bn_deprecated.c") { - open(my $src, '<', $filename) or die "Can't open source file!\n"; - read $src, $content, -s $src; - close $src; - } else { - my $cc = $ENV{'CC'} || 'gcc'; - $content = `$cc -E -x c -DLTM_ALL $filename`; - $content =~ s/^# 1 "$filename".*?^# 2 "$filename"//ms; - } + my $cc = $ENV{'CC'} || 'gcc'; + $content = `$cc -E -x c -DLTM_ALL $filename`; + $content =~ s/^# 1 "$filename".*?^# 2 "$filename"//ms; # convert filename to upper case so we can use it as a define $filename =~ tr/[a-z]/[A-Z]/; diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 67cc89bf7..7e5192994 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -316,10 +316,6 @@ RelativePath="bn_cutoffs.c" > - - diff --git a/makefile b/makefile index 56eeabad1..0f2e6112c 100644 --- a/makefile +++ b/makefile @@ -26,10 +26,10 @@ endif LCOV_ARGS=--directory . #START_INS -OBJECTS=bn_cutoffs.o bn_deprecated.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o \ -bn_mp_and.o bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o \ -bn_mp_cnt_lsb.o bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o \ -bn_mp_div_2d.o bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ +OBJECTS=bn_cutoffs.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o bn_mp_and.o \ +bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o bn_mp_cnt_lsb.o \ +bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o bn_mp_div_2d.o \ +bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ bn_mp_error_to_string.o bn_mp_exch.o bn_mp_expt_u32.o bn_mp_exptmod.o bn_mp_exteuclid.o bn_mp_fread.o \ bn_mp_from_sbin.o bn_mp_from_ubin.o bn_mp_fwrite.o bn_mp_gcd.o bn_mp_get_double.o bn_mp_get_i32.o \ bn_mp_get_i64.o bn_mp_get_l.o bn_mp_get_ll.o bn_mp_get_mag_u32.o bn_mp_get_mag_u64.o bn_mp_get_mag_ul.o \ diff --git a/makefile.mingw b/makefile.mingw index b11edb742..20b2ffe3d 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -29,10 +29,10 @@ LIBMAIN_I =libtommath.dll.a LIBMAIN_D =libtommath.dll #List of objects to compile (all goes to libtommath.a) -OBJECTS=bn_cutoffs.o bn_deprecated.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o \ -bn_mp_and.o bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o \ -bn_mp_cnt_lsb.o bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o \ -bn_mp_div_2d.o bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ +OBJECTS=bn_cutoffs.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o bn_mp_and.o \ +bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o bn_mp_cnt_lsb.o \ +bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o bn_mp_div_2d.o \ +bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ bn_mp_error_to_string.o bn_mp_exch.o bn_mp_expt_u32.o bn_mp_exptmod.o bn_mp_exteuclid.o bn_mp_fread.o \ bn_mp_from_sbin.o bn_mp_from_ubin.o bn_mp_fwrite.o bn_mp_gcd.o bn_mp_get_double.o bn_mp_get_i32.o \ bn_mp_get_i64.o bn_mp_get_l.o bn_mp_get_ll.o bn_mp_get_mag_u32.o bn_mp_get_mag_u64.o bn_mp_get_mag_ul.o \ diff --git a/makefile.msvc b/makefile.msvc index 5b2f85090..8ad12be0a 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -21,10 +21,10 @@ LTM_LDFLAGS = advapi32.lib LIBMAIN_S =tommath.lib #List of objects to compile (all goes to tommath.lib) -OBJECTS=bn_cutoffs.obj bn_deprecated.obj bn_mp_2expt.obj bn_mp_abs.obj bn_mp_add.obj bn_mp_add_d.obj bn_mp_addmod.obj \ -bn_mp_and.obj bn_mp_clamp.obj bn_mp_clear.obj bn_mp_clear_multi.obj bn_mp_cmp.obj bn_mp_cmp_d.obj bn_mp_cmp_mag.obj \ -bn_mp_cnt_lsb.obj bn_mp_complement.obj bn_mp_copy.obj bn_mp_count_bits.obj bn_mp_decr.obj bn_mp_div.obj bn_mp_div_2.obj \ -bn_mp_div_2d.obj bn_mp_div_3.obj bn_mp_div_d.obj bn_mp_dr_is_modulus.obj bn_mp_dr_reduce.obj bn_mp_dr_setup.obj \ +OBJECTS=bn_cutoffs.obj bn_mp_2expt.obj bn_mp_abs.obj bn_mp_add.obj bn_mp_add_d.obj bn_mp_addmod.obj bn_mp_and.obj \ +bn_mp_clamp.obj bn_mp_clear.obj bn_mp_clear_multi.obj bn_mp_cmp.obj bn_mp_cmp_d.obj bn_mp_cmp_mag.obj bn_mp_cnt_lsb.obj \ +bn_mp_complement.obj bn_mp_copy.obj bn_mp_count_bits.obj bn_mp_decr.obj bn_mp_div.obj bn_mp_div_2.obj bn_mp_div_2d.obj \ +bn_mp_div_3.obj bn_mp_div_d.obj bn_mp_dr_is_modulus.obj bn_mp_dr_reduce.obj bn_mp_dr_setup.obj \ bn_mp_error_to_string.obj bn_mp_exch.obj bn_mp_expt_u32.obj bn_mp_exptmod.obj bn_mp_exteuclid.obj bn_mp_fread.obj \ bn_mp_from_sbin.obj bn_mp_from_ubin.obj bn_mp_fwrite.obj bn_mp_gcd.obj bn_mp_get_double.obj bn_mp_get_i32.obj \ bn_mp_get_i64.obj bn_mp_get_l.obj bn_mp_get_ll.obj bn_mp_get_mag_u32.obj bn_mp_get_mag_u64.obj bn_mp_get_mag_ul.obj \ diff --git a/makefile.shared b/makefile.shared index 5e0f4f2c4..9f6b1c585 100644 --- a/makefile.shared +++ b/makefile.shared @@ -23,10 +23,10 @@ LTLINK = $(LIBTOOL) --mode=link --tag=CC $(CC) LCOV_ARGS=--directory .libs --directory . #START_INS -OBJECTS=bn_cutoffs.o bn_deprecated.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o \ -bn_mp_and.o bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o \ -bn_mp_cnt_lsb.o bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o \ -bn_mp_div_2d.o bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ +OBJECTS=bn_cutoffs.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o bn_mp_and.o \ +bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o bn_mp_cnt_lsb.o \ +bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o bn_mp_div_2d.o \ +bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ bn_mp_error_to_string.o bn_mp_exch.o bn_mp_expt_u32.o bn_mp_exptmod.o bn_mp_exteuclid.o bn_mp_fread.o \ bn_mp_from_sbin.o bn_mp_from_ubin.o bn_mp_fwrite.o bn_mp_gcd.o bn_mp_get_double.o bn_mp_get_i32.o \ bn_mp_get_i64.o bn_mp_get_l.o bn_mp_get_ll.o bn_mp_get_mag_u32.o bn_mp_get_mag_u64.o bn_mp_get_mag_ul.o \ diff --git a/makefile.unix b/makefile.unix index e7a6f257b..4aa0d2720 100644 --- a/makefile.unix +++ b/makefile.unix @@ -30,10 +30,10 @@ LTM_LDFLAGS = $(LDFLAGS) #Library to be created (this makefile builds only static library) LIBMAIN_S = libtommath.a -OBJECTS=bn_cutoffs.o bn_deprecated.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o \ -bn_mp_and.o bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o \ -bn_mp_cnt_lsb.o bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o \ -bn_mp_div_2d.o bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ +OBJECTS=bn_cutoffs.o bn_mp_2expt.o bn_mp_abs.o bn_mp_add.o bn_mp_add_d.o bn_mp_addmod.o bn_mp_and.o \ +bn_mp_clamp.o bn_mp_clear.o bn_mp_clear_multi.o bn_mp_cmp.o bn_mp_cmp_d.o bn_mp_cmp_mag.o bn_mp_cnt_lsb.o \ +bn_mp_complement.o bn_mp_copy.o bn_mp_count_bits.o bn_mp_decr.o bn_mp_div.o bn_mp_div_2.o bn_mp_div_2d.o \ +bn_mp_div_3.o bn_mp_div_d.o bn_mp_dr_is_modulus.o bn_mp_dr_reduce.o bn_mp_dr_setup.o \ bn_mp_error_to_string.o bn_mp_exch.o bn_mp_expt_u32.o bn_mp_exptmod.o bn_mp_exteuclid.o bn_mp_fread.o \ bn_mp_from_sbin.o bn_mp_from_ubin.o bn_mp_fwrite.o bn_mp_gcd.o bn_mp_get_double.o bn_mp_get_i32.o \ bn_mp_get_i64.o bn_mp_get_l.o bn_mp_get_ll.o bn_mp_get_mag_u32.o bn_mp_get_mag_u64.o bn_mp_get_mag_ul.o \ diff --git a/tommath_class.h b/tommath_class.h index b0a82f071..b3c5dbda7 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -12,7 +12,6 @@ #define LTM1 #if defined(LTM_ALL) # define BN_CUTOFFS_C -# define BN_DEPRECATED_C # define BN_MP_2EXPT_C # define BN_MP_ABS_C # define BN_MP_ADD_C @@ -173,9 +172,6 @@ #if defined(BN_CUTOFFS_C) #endif -#if defined(BN_DEPRECATED_C) -#endif - #if defined(BN_MP_2EXPT_C) # define BN_MP_GROW_C # define BN_MP_ZERO_C From 55acc6ab5b1d17e7137dfbf53d5a43b3dbf0f211 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 16 Oct 2019 10:32:40 +0200 Subject: [PATCH 005/304] update docs --- doc/bn.tex | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 3174187f6..5512bcd55 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2089,19 +2089,17 @@ \section{Random Primes} The function mp\_prime\_rand() is suitable for generating primes which must be secret (as in the case of RSA) since there is no skew on the least significant bits. -\textit{Note:} This function replaces the deprecated mp\_prime\_random and mp\_prime\_random\_ex functions. - \begin{figure}[h] \begin{center} \begin{small} \begin{tabular}{|r|l|} \hline \textbf{Flag} & \textbf{Meaning} \\ -\hline LTM\_PRIME\_BBS & Make the prime congruent to $3$ modulo $4$ \\ -\hline LTM\_PRIME\_SAFE & Make a prime $p$ such that $(p - 1)/2$ is also prime. \\ - & This option implies LTM\_PRIME\_BBS as well. \\ -\hline LTM\_PRIME\_2MSB\_OFF & Makes sure that the bit adjacent to the most significant bit \\ +\hline MP\_PRIME\_BBS & Make the prime congruent to $3$ modulo $4$ \\ +\hline MP\_PRIME\_SAFE & Make a prime $p$ such that $(p - 1)/2$ is also prime. \\ + & This option implies MP\_PRIME\_BBS as well. \\ +\hline MP\_PRIME\_2MSB\_OFF & Makes sure that the bit adjacent to the most significant bit \\ & Is forced to zero. \\ -\hline LTM\_PRIME\_2MSB\_ON & Makes sure that the bit adjacent to the most significant bit \\ +\hline MP\_PRIME\_2MSB\_ON & Makes sure that the bit adjacent to the most significant bit \\ & Is forced to one. \\ \hline \end{tabular} @@ -2154,7 +2152,7 @@ \subsection{To ASCII} This stores in ``size'' the number of characters (including space for the NUL terminator) required. Upon error this function returns an error code and ``size'' will be zero. -If \texttt{LTM\_NO\_FILE} is not defined a function to write to a file is also available. +If \texttt{MP\_NO\_FILE} is not defined a function to write to a file is also available. \index{mp\_fwrite} \begin{alltt} int mp_fwrite(const mp_int *a, int radix, FILE *stream); @@ -2170,7 +2168,7 @@ \subsection{From ASCII} character it does not recognize (which happens to include th NUL char... imagine that...). A single leading $-$ sign can be used to denote a negative number. -If \texttt{LTM\_NO\_FILE} is not defined a function to read from a file is also available. +If \texttt{MP\_NO\_FILE} is not defined a function to read from a file is also available. \index{mp\_fread} \begin{alltt} int mp_fread(mp_int *a, int radix, FILE *stream); From 20dcc923f693de2110ab52fc14ac7675644445e5 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 17 Oct 2019 16:59:02 +0200 Subject: [PATCH 006/304] rename internal constant radix arrays --- bn_mp_fread.c | 4 ++-- bn_mp_radix_smap.c | 6 +++--- bn_mp_read_radix.c | 4 ++-- bn_mp_to_radix.c | 2 +- tommath_private.h | 6 +++--- 5 files changed, 11 insertions(+), 11 deletions(-) diff --git a/bn_mp_fread.c b/bn_mp_fread.c index 52ea773e4..1e5ecf79c 100644 --- a/bn_mp_fread.c +++ b/bn_mp_fread.c @@ -30,11 +30,11 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) do { int y; unsigned pos = (unsigned)(ch - (int)'('); - if (mp_s_rmap_reverse_sz < pos) { + if (MP_RMAP_REVERSE_SIZE < pos) { break; } - y = (int)mp_s_rmap_reverse[pos]; + y = (int)s_mp_rmap_reverse[pos]; if ((y == 0xff) || (y >= radix)) { break; diff --git a/bn_mp_radix_smap.c b/bn_mp_radix_smap.c index a16128d79..e7d7c06b6 100644 --- a/bn_mp_radix_smap.c +++ b/bn_mp_radix_smap.c @@ -4,8 +4,8 @@ /* SPDX-License-Identifier: Unlicense */ /* chars used in radix conversions */ -const char *const mp_s_rmap = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; -const uint8_t mp_s_rmap_reverse[] = { +const char s_mp_rmap[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; +const uint8_t s_mp_rmap_reverse[] = { 0xff, 0xff, 0xff, 0x3e, 0xff, 0xff, 0xff, 0x3f, /* ()*+,-./ */ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, /* 01234567 */ 0x08, 0x09, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 89:;<=>? */ @@ -18,5 +18,5 @@ const uint8_t mp_s_rmap_reverse[] = { 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, /* pqrstuvw */ 0x3b, 0x3c, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xff, /* xyz{|}~. */ }; -const size_t mp_s_rmap_reverse_sz = sizeof(mp_s_rmap_reverse); +MP_STATIC_ASSERT(correct_rmap_reverse_size, sizeof(s_mp_rmap_reverse) == MP_RMAP_REVERSE_SIZE) #endif diff --git a/bn_mp_read_radix.c b/bn_mp_read_radix.c index de18e06fc..456a387a3 100644 --- a/bn_mp_read_radix.c +++ b/bn_mp_read_radix.c @@ -43,10 +43,10 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) */ ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; pos = (unsigned)(ch - '('); - if (mp_s_rmap_reverse_sz < pos) { + if (MP_RMAP_REVERSE_SIZE < pos) { break; } - y = (int)mp_s_rmap_reverse[pos]; + y = (int)s_mp_rmap_reverse[pos]; /* if the char was found in the map * and is less than the given radix add it diff --git a/bn_mp_to_radix.c b/bn_mp_to_radix.c index 7fa86cae1..18cb50464 100644 --- a/bn_mp_to_radix.c +++ b/bn_mp_to_radix.c @@ -60,7 +60,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i if ((err = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { goto LBL_ERR; } - *str++ = mp_s_rmap[d]; + *str++ = s_mp_rmap[d]; ++digs; } /* reverse the digits of the string. In this case _s points diff --git a/tommath_private.h b/tommath_private.h index 0909fa529..3f4b23ae7 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -215,9 +215,9 @@ MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); -extern MP_PRIVATE const char *const mp_s_rmap; -extern MP_PRIVATE const uint8_t mp_s_rmap_reverse[]; -extern MP_PRIVATE const size_t mp_s_rmap_reverse_sz; +#define MP_RMAP_REVERSE_SIZE 88 +extern MP_PRIVATE const char s_mp_rmap[]; +extern MP_PRIVATE const uint8_t s_mp_rmap_reverse[]; extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; /* number of primes */ From 700a79ea66155eab0eca6fb7bcfca36278e8f3c5 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Fri, 18 Oct 2019 09:28:11 +0200 Subject: [PATCH 007/304] remove deprecated functions from tommath.def too --- helper.pl | 2 -- tommath.def | 7 ------- 2 files changed, 9 deletions(-) diff --git a/helper.pl b/helper.pl index 69734ba18..03b081ccc 100755 --- a/helper.pl +++ b/helper.pl @@ -428,8 +428,6 @@ sub generate_def { @files = map { my $x = $_; $x =~ s/^bn_|\.c$//g; $x; } @files; @files = grep(!/mp_radix_smap/, @files); - push(@files, qw(mp_set_int mp_set_long mp_set_long_long mp_get_int mp_get_long mp_get_long_long mp_init_set_int)); - my $files = join("\n ", sort(grep(/^mp_/, @files))); write_file "tommath.def", "; libtommath ; diff --git a/tommath.def b/tommath.def index 229fae49a..9c7f226f4 100644 --- a/tommath.def +++ b/tommath.def @@ -44,11 +44,8 @@ EXPORTS mp_get_double mp_get_i32 mp_get_i64 - mp_get_int mp_get_l mp_get_ll - mp_get_long - mp_get_long_long mp_get_mag_u32 mp_get_mag_u64 mp_get_mag_ul @@ -63,7 +60,6 @@ EXPORTS mp_init_ll mp_init_multi mp_init_set - mp_init_set_int mp_init_size mp_init_u32 mp_init_u64 @@ -118,11 +114,8 @@ EXPORTS mp_set_double mp_set_i32 mp_set_i64 - mp_set_int mp_set_l mp_set_ll - mp_set_long - mp_set_long_long mp_set_u32 mp_set_u64 mp_set_ul From 42ebcbfee4260e1bb76c84cd6c57849354f3dfc0 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 16 Oct 2019 10:08:15 +0200 Subject: [PATCH 008/304] enable MP_PRIVATE (visibility=hidden) --- tommath_private.h | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/tommath_private.h b/tommath_private.h index 3f4b23ae7..a6fd3e19e 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -14,11 +14,9 @@ * * On Unix symbols can be marked as hidden if libtommath is compiled * as a shared object. By default, symbols are visible. - * As of now, this feature is opt-in via the MP_PRIVATE_SYMBOLS define. - * * On Win32 a .def file must be used to specify the exported symbols. */ -#if defined (MP_PRIVATE_SYMBOLS) && defined(__GNUC__) && __GNUC__ >= 4 +#if defined(__GNUC__) && __GNUC__ >= 4 # define MP_PRIVATE __attribute__ ((visibility ("hidden"))) #else # define MP_PRIVATE From 3eaa268e2182f4463ee614e2712be4ec5d77ed12 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Fri, 18 Oct 2019 10:00:09 +0200 Subject: [PATCH 009/304] Adapt mingw-build of libtommath.dll to respect internal symbols too --- makefile.mingw | 2 +- tommath_private.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/makefile.mingw b/makefile.mingw index 20b2ffe3d..0ff00bc35 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -78,7 +78,7 @@ $(LIBMAIN_S): $(OBJECTS) #Create DLL + import library libtommath.dll.a $(LIBMAIN_D) $(LIBMAIN_I): $(OBJECTS) - $(CC) -s -shared -o $(LIBMAIN_D) $^ -Wl,--enable-auto-import,--export-all -Wl,--out-implib=$(LIBMAIN_I) $(LTM_LDFLAGS) + $(CC) -s -shared -o $(LIBMAIN_D) $^ tommath.def -Wl,--out-implib=$(LIBMAIN_I) $(LTM_LDFLAGS) $(STRIP) -S $(LIBMAIN_D) #Build test suite diff --git a/tommath_private.h b/tommath_private.h index a6fd3e19e..d87ee9b2f 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -16,7 +16,7 @@ * as a shared object. By default, symbols are visible. * On Win32 a .def file must be used to specify the exported symbols. */ -#if defined(__GNUC__) && __GNUC__ >= 4 +#if defined(__GNUC__) && __GNUC__ >= 4 && !defined(_WIN32) # define MP_PRIVATE __attribute__ ((visibility ("hidden"))) #else # define MP_PRIVATE From d4f6b43fa8ab24cd0bd71a31f1a89836bb528929 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 11 Oct 2019 00:29:20 +0200 Subject: [PATCH 010/304] use of mp_ilogb in mp_radix_size --- bn_mp_radix_size.c | 48 +++++++++++--------------------------- demo/test.c | 57 ++++++++++++++++++++++++++++++++++++++++++++++ tommath_class.h | 6 ++--- 3 files changed, 73 insertions(+), 38 deletions(-) diff --git a/bn_mp_radix_size.c b/bn_mp_radix_size.c index b96f4874c..33ef7d314 100644 --- a/bn_mp_radix_size.c +++ b/bn_mp_radix_size.c @@ -6,12 +6,8 @@ /* returns size of ASCII representation */ mp_err mp_radix_size(const mp_int *a, int radix, int *size) { - mp_err err; - int digs; - mp_int t; - mp_digit d; - - *size = 0; + mp_err err; + mp_int a_, b; /* make sure the radix is in range */ if ((radix < 2) || (radix > 64)) { @@ -23,43 +19,25 @@ mp_err mp_radix_size(const mp_int *a, int radix, int *size) return MP_OKAY; } - /* special case for binary */ - if (radix == 2) { - *size = (mp_count_bits(a) + ((a->sign == MP_NEG) ? 1 : 0) + 1); - return MP_OKAY; - } - - /* digs is the digit count */ - digs = 0; - - /* if it's negative add one for the sign */ - if (a->sign == MP_NEG) { - ++digs; + if ((err = mp_init(&b)) != MP_OKAY) { + goto LBL_ERR; } - /* init a copy of the input */ - if ((err = mp_init_copy(&t, a)) != MP_OKAY) { - return err; + a_ = *a; + a_.sign = MP_ZPOS; + if ((err = mp_ilogb(&a_, (uint32_t)radix, &b)) != MP_OKAY) { + goto LBL_ERR; } - /* force temp to positive */ - t.sign = MP_ZPOS; - - /* fetch out all of the digits */ - while (!MP_IS_ZERO(&t)) { - if ((err = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { - goto LBL_ERR; - } - ++digs; - } + *size = (int)mp_get_l(&b); - /* return digs + 1, the 1 is for the NULL byte that would be required. */ - *size = digs + 1; - err = MP_OKAY; + /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ + *size += 2 + (a->sign == MP_NEG); LBL_ERR: - mp_clear(&t); + mp_clear(&b); return err; } + #endif diff --git a/demo/test.c b/demo/test.c index c1fc878f3..4c3f1ccfd 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2282,6 +2282,62 @@ static int test_s_mp_toom_sqr(void) return EXIT_FAILURE; } +static int test_mp_radix_size(void) +{ + mp_err err; + mp_int a; + int radix, size; +/* *INDENT-OFF* */ + int results[65] = { + 0, 0, 1627, 1027, 814, 702, 630, 581, 543, + 514, 491, 471, 455, 441, 428, 418, 408, 399, + 391, 384, 378, 372, 366, 361, 356, 352, 347, + 343, 340, 336, 333, 330, 327, 324, 321, 318, + 316, 314, 311, 309, 307, 305, 303, 301, 299, + 298, 296, 294, 293, 291, 290, 288, 287, 285, + 284, 283, 281, 280, 279, 278, 277, 276, 275, + 273, 272 + }; +/* *INDENT-ON* */ + + mp_init(&a); + + /* number to result in a different size for every base: 67^(4 * 67) */ + mp_set(&a, 67); + if ((err = mp_expt_u32(&a, 268u, &a)) != MP_OKAY) { + goto LTM_ERR; + } + + for (radix = 2; radix < 65; radix++) { + if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { + goto LTM_ERR; + } + if (size != results[radix]) { + fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", + radix, size, results[radix]); + goto LTM_ERR; + } + a.sign = MP_NEG; + if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { + goto LTM_ERR; + } + if (size != (results[radix] + 1)) { + fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", + radix, size, results[radix]); + goto LTM_ERR; + } + a.sign = MP_ZPOS; + } + + mp_clear(&a); + return EXIT_SUCCESS; +LTM_ERR: + mp_clear(&a); + return EXIT_FAILURE; +} + + + static int test_mp_read_write_ubin(void) { mp_int a, b, c; @@ -2446,6 +2502,7 @@ static int unit_tests(int argc, char **argv) T1(mp_read_write_sbin, MP_TO_SBIN), T1(mp_reduce_2k, MP_REDUCE_2K), T1(mp_reduce_2k_l, MP_REDUCE_2K_L), + T1(mp_radix_size, MP_RADIX_SIZE), #if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) T1(mp_set_double, MP_SET_DOUBLE), #endif diff --git a/tommath_class.h b/tommath_class.h index b3c5dbda7..ec712d127 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -751,9 +751,9 @@ #if defined(BN_MP_RADIX_SIZE_C) # define BN_MP_CLEAR_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_D_C -# define BN_MP_INIT_COPY_C +# define BN_MP_GET_L_C +# define BN_MP_ILOGB_C +# define BN_MP_INIT_C #endif #if defined(BN_MP_RADIX_SMAP_C) From de606c034fee5b170adeade07ac59a29315f46b2 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Tue, 15 Oct 2019 20:48:37 +0200 Subject: [PATCH 011/304] adaption of mp_radeix_size to new mp_log_u32 --- bn_mp_radix_size.c | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/bn_mp_radix_size.c b/bn_mp_radix_size.c index 33ef7d314..5ed9ab1bd 100644 --- a/bn_mp_radix_size.c +++ b/bn_mp_radix_size.c @@ -7,7 +7,8 @@ mp_err mp_radix_size(const mp_int *a, int radix, int *size) { mp_err err; - mp_int a_, b; + mp_int a_; + uint32_t b; /* make sure the radix is in range */ if ((radix < 2) || (radix > 64)) { @@ -19,25 +20,18 @@ mp_err mp_radix_size(const mp_int *a, int radix, int *size) return MP_OKAY; } - if ((err = mp_init(&b)) != MP_OKAY) { - goto LBL_ERR; - } - a_ = *a; a_.sign = MP_ZPOS; - if ((err = mp_ilogb(&a_, (uint32_t)radix, &b)) != MP_OKAY) { + if ((err = mp_log_u32(&a_, (uint32_t)radix, &b)) != MP_OKAY) { goto LBL_ERR; } - *size = (int)mp_get_l(&b); + *size = (int)b; /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ *size += 2 + (a->sign == MP_NEG); LBL_ERR: - mp_clear(&b); return err; } - - #endif From 80f5818e0f7d35472c200dc40c09f584b7d2c314 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 16 Oct 2019 00:31:43 +0200 Subject: [PATCH 012/304] Addition of BN_MP_LOG_U32 to tommath_superclass.h --- tommath_class.h | 5 +---- tommath_superclass.h | 1 + 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/tommath_class.h b/tommath_class.h index ec712d127..209d80901 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -750,10 +750,7 @@ #endif #if defined(BN_MP_RADIX_SIZE_C) -# define BN_MP_CLEAR_C -# define BN_MP_GET_L_C -# define BN_MP_ILOGB_C -# define BN_MP_INIT_C +# define BN_MP_LOG_U32_C #endif #if defined(BN_MP_RADIX_SMAP_C) diff --git a/tommath_superclass.h b/tommath_superclass.h index d88bce9c7..bb606b5af 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -28,6 +28,7 @@ # define BN_MP_NEG_C # define BN_MP_PRIME_FROBENIUS_UNDERWOOD_C # define BN_MP_RADIX_SIZE_C +# define BN_MP_LOG_U32_C # define BN_MP_RAND_C # define BN_MP_REDUCE_C # define BN_MP_REDUCE_2K_L_C From 4d6a9682e560ca0d19e3108c18e8967eed36190b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sat, 19 Oct 2019 15:50:29 +0200 Subject: [PATCH 013/304] fix 'coverage' & add 'check' make-target --- makefile_include.mk | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/makefile_include.mk b/makefile_include.mk index 7d0b997d9..defa6ed79 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -116,10 +116,10 @@ endif # adjust coverage set ifneq ($(filter $(_ARCH), i386 i686 x86_64 amd64 ia64),) - COVERAGE = test_standalone timing + COVERAGE = test timing COVERAGE_APP = ./test && ./timing else - COVERAGE = test_standalone + COVERAGE = test COVERAGE_APP = ./test endif @@ -135,6 +135,10 @@ LIBPATH ?= $(PREFIX)/lib INCPATH ?= $(PREFIX)/include DATAPATH ?= $(PREFIX)/share/doc/libtommath/pdf +# build & run test-suite +check: test + ./test + #make the code coverage of the library # coverage: LTM_CFLAGS += -fprofile-arcs -ftest-coverage -DTIMING_NO_LOGS From 36fca2f9a0907f14c400463e0d9c403f6d31f9ac Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 9 Sep 2019 02:58:18 +0200 Subject: [PATCH 014/304] remove support for 8-bit (MP_8BIT) --- bn_mp_from_ubin.c | 9 +----- bn_mp_montgomery_setup.c | 4 +-- bn_mp_prime_frobenius_underwood.c | 5 +--- bn_mp_prime_is_prime.c | 41 ++-------------------------- bn_mp_prime_strong_lucas_selfridge.c | 8 +----- bn_mp_to_ubin.c | 4 --- bn_prime_tab.c | 5 +--- demo/shared.c | 3 -- demo/test.c | 11 -------- doc/bn.tex | 6 ++-- mtest/mtest.c | 4 --- tommath.h | 15 +++++----- 12 files changed, 17 insertions(+), 98 deletions(-) diff --git a/bn_mp_from_ubin.c b/bn_mp_from_ubin.c index 7f73cbccd..3e1885dd5 100644 --- a/bn_mp_from_ubin.c +++ b/bn_mp_from_ubin.c @@ -23,15 +23,8 @@ mp_err mp_from_ubin(mp_int *a, const unsigned char *buf, size_t size) if ((err = mp_mul_2d(a, 8, a)) != MP_OKAY) { return err; } - -#ifndef MP_8BIT - a->dp[0] |= *buf++; + a->dp[0] |= *b++; a->used += 1; -#else - a->dp[0] = (*buf & MP_MASK); - a->dp[1] |= ((*buf++ >> 7) & 1u); - a->used += 2; -#endif } mp_clamp(a); return MP_OKAY; diff --git a/bn_mp_montgomery_setup.c b/bn_mp_montgomery_setup.c index 39f6e9d24..8ad19c45c 100644 --- a/bn_mp_montgomery_setup.c +++ b/bn_mp_montgomery_setup.c @@ -24,10 +24,8 @@ mp_err mp_montgomery_setup(const mp_int *n, mp_digit *rho) x = (((b + 2u) & 4u) << 1) + b; /* here x*a==1 mod 2**4 */ x *= 2u - (b * x); /* here x*a==1 mod 2**8 */ -#if !defined(MP_8BIT) x *= 2u - (b * x); /* here x*a==1 mod 2**16 */ -#endif -#if defined(MP_64BIT) || !(defined(MP_8BIT) || defined(MP_16BIT)) +#if (defined(MP_64BIT) || defined(MP_16BIT)) x *= 2u - (b * x); /* here x*a==1 mod 2**32 */ #endif #ifdef MP_64BIT diff --git a/bn_mp_prime_frobenius_underwood.c b/bn_mp_prime_frobenius_underwood.c index 253e8d53b..618aa7c01 100644 --- a/bn_mp_prime_frobenius_underwood.c +++ b/bn_mp_prime_frobenius_underwood.c @@ -9,7 +9,6 @@ */ #ifndef LTM_USE_ONLY_MR -#ifdef MP_8BIT /* * floor of positive solution of * (2^16)-1 = (a+4)*(2*a+5) @@ -19,10 +18,8 @@ * But it is still a restriction of the set of available pseudoprimes * which makes this implementation less secure if used stand-alone. */ -#define LTM_FROBENIUS_UNDERWOOD_A 177 -#else #define LTM_FROBENIUS_UNDERWOOD_A 32764 -#endif + mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) { mp_int T1z, T2z, Np1z, sz, tz; diff --git a/bn_mp_prime_is_prime.c b/bn_mp_prime_is_prime.c index 49fde93ba..678eae4ea 100644 --- a/bn_mp_prime_is_prime.c +++ b/bn_mp_prime_is_prime.c @@ -57,13 +57,6 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) return MP_OKAY; } } -#ifdef MP_8BIT - /* The search in the loop above was exhaustive in this case */ - if ((a->used == 1) && (MP_PRIME_TAB_SIZE >= 31)) { - return MP_OKAY; - } -#endif - /* first perform trial division */ if ((err = s_mp_prime_is_divisible(a, &res)) != MP_OKAY) { return err; @@ -107,12 +100,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) */ #ifndef LTM_USE_ONLY_MR if (t >= 0) { - /* - * Use a Frobenius-Underwood test instead of the Lucas-Selfridge test for - * MP_8BIT (It is unknown if the Lucas-Selfridge test works with 16-bit - * integers but the necesssary analysis is on the todo-list). - */ -#if defined (MP_8BIT) || defined (LTM_USE_FROBENIUS_TEST) +#ifdef LTM_USE_FROBENIUS_TEST err = mp_prime_frobenius_underwood(a, &res); if ((err != MP_OKAY) && (err != MP_ITER)) { goto LBL_B; @@ -240,20 +228,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) * an unsigned int and "mask" on the other side is most probably not. */ fips_rand = (unsigned int)(b.dp[0] & (mp_digit) mask); -#ifdef MP_8BIT - /* - * One 8-bit digit is too small, so concatenate two if the size of - * unsigned int allows for it. - */ - if ((MP_SIZEOF_BITS(unsigned int)/2) >= MP_SIZEOF_BITS(mp_digit)) { - if ((err = mp_rand(&b, 1)) != MP_OKAY) { - goto LBL_B; - } - fips_rand <<= MP_SIZEOF_BITS(mp_digit); - fips_rand |= (unsigned int) b.dp[0]; - fips_rand &= mask; - } -#endif + if (fips_rand > (unsigned int)(INT_MAX - MP_DIGIT_BIT)) { len = INT_MAX / MP_DIGIT_BIT; } else { @@ -264,18 +239,6 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) ix--; continue; } - /* - * As mentioned above, one 8-bit digit is too small and - * although it can only happen in the unlikely case that - * an "unsigned int" is smaller than 16 bit a simple test - * is cheap and the correction even cheaper. - */ -#ifdef MP_8BIT - /* All "a" < 2^8 have been caught before */ - if (len == 1) { - len++; - } -#endif if ((err = mp_rand(&b, len)) != MP_OKAY) { goto LBL_B; } diff --git a/bn_mp_prime_strong_lucas_selfridge.c b/bn_mp_prime_strong_lucas_selfridge.c index b50bbcd2f..0f03792ad 100644 --- a/bn_mp_prime_strong_lucas_selfridge.c +++ b/bn_mp_prime_strong_lucas_selfridge.c @@ -9,12 +9,6 @@ */ #ifndef LTM_USE_ONLY_MR -/* - * 8-bit is just too small. You can try the Frobenius test - * but that frobenius test can fail, too, for the same reason. - */ -#ifndef MP_8BIT - /* * multiply bigint a with int d and put the result in c * Like mp_mul_d() but with a signed long as the small input @@ -284,6 +278,6 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) mp_clear_multi(&Q2kdz, &T4z, &T3z, &T2z, &T1z, &Qkdz, &Q2mz, &Qmz, &V2mz, &U2mz, &Vz, &Uz, &Np1, &gcd, &Dz, NULL); return err; } -#endif + #endif #endif diff --git a/bn_mp_to_ubin.c b/bn_mp_to_ubin.c index 1681ca7ce..a2c6e281b 100644 --- a/bn_mp_to_ubin.c +++ b/bn_mp_to_ubin.c @@ -20,11 +20,7 @@ mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *wr } for (x = count; x --> 0u;) { -#ifndef MP_8BIT buf[x] = (unsigned char)(t.dp[0] & 255u); -#else - buf[x] = (unsigned char)(t.dp[0] | ((t.dp[1] & 1u) << 7)); -#endif if ((err = mp_div_2d(&t, 8, &t, NULL)) != MP_OKAY) { goto LBL_ERR; } diff --git a/bn_prime_tab.c b/bn_prime_tab.c index 6bd53fe36..92a515971 100644 --- a/bn_prime_tab.c +++ b/bn_prime_tab.c @@ -7,9 +7,7 @@ const mp_digit s_mp_prime_tab[] = { 0x0002, 0x0003, 0x0005, 0x0007, 0x000B, 0x000D, 0x0011, 0x0013, 0x0017, 0x001D, 0x001F, 0x0025, 0x0029, 0x002B, 0x002F, 0x0035, 0x003B, 0x003D, 0x0043, 0x0047, 0x0049, 0x004F, 0x0053, 0x0059, - 0x0061, 0x0065, 0x0067, 0x006B, 0x006D, 0x0071, 0x007F, -#ifndef MP_8BIT - 0x0083, + 0x0061, 0x0065, 0x0067, 0x006B, 0x006D, 0x0071, 0x007F, 0x0083, 0x0089, 0x008B, 0x0095, 0x0097, 0x009D, 0x00A3, 0x00A7, 0x00AD, 0x00B3, 0x00B5, 0x00BF, 0x00C1, 0x00C5, 0x00C7, 0x00D3, 0x00DF, 0x00E3, 0x00E5, 0x00E9, 0x00EF, 0x00F1, 0x00FB, 0x0101, 0x0107, @@ -41,7 +39,6 @@ const mp_digit s_mp_prime_tab[] = { 0x05BF, 0x05C9, 0x05CB, 0x05CF, 0x05D1, 0x05D5, 0x05DB, 0x05E7, 0x05F3, 0x05FB, 0x0607, 0x060D, 0x0611, 0x0617, 0x061F, 0x0623, 0x062B, 0x062F, 0x063D, 0x0641, 0x0647, 0x0649, 0x064D, 0x0653 -#endif }; #endif diff --git a/demo/shared.c b/demo/shared.c index dc8e05a6a..e47e481d8 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -23,9 +23,6 @@ void ndraw(mp_int *a, const char *name) void print_header(void) { -#ifdef MP_8BIT - printf("Digit size 8 Bit \n"); -#endif #ifdef MP_16BIT printf("Digit size 16 Bit \n"); #endif diff --git a/demo/test.c b/demo/test.c index 4c3f1ccfd..9002e9631 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1022,7 +1022,6 @@ static int test_mp_prime_is_prime(void) } /* Check regarding problem #143 */ -#ifndef MP_8BIT mp_read_radix(&a, "FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A63A3620FFFFFFFFFFFFFFFF", 16); @@ -1041,8 +1040,6 @@ static int test_mp_prime_is_prime(void) putchar('\n'); goto LBL_ERR; } -#endif - printf("\n\n"); mp_clear_multi(&a, &b, NULL); @@ -2040,17 +2037,9 @@ static int test_mp_root_u32(void) if ((e = mp_init_multi(&a, &c, &r, NULL)) != MP_OKAY) { return EXIT_FAILURE; } -#ifdef MP_8BIT - for (i = 0; i < 1; i++) { -#else for (i = 0; i < 10; i++) { -#endif mp_read_radix(&a, input[i], 64); -#ifdef MP_8BIT - for (j = 3; j < 10; j++) { -#else for (j = 3; j < 100; j++) { -#endif mp_root_u32(&a, (uint32_t)j, &c); mp_read_radix(&r, root[i][j-3], 10); if (mp_cmp(&r, &c) != MP_EQ) { diff --git a/doc/bn.tex b/doc/bn.tex index 5512bcd55..27f27e75e 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2035,9 +2035,7 @@ \section{Frobenius (Underwood) Test} \begin{alltt} int mp_prime_frobenius_underwood(const mp_int *N, int *result) \end{alltt} -Performs the variant of the Frobenius test as described by Paul Underwood. The single internal use is in -\texttt{mp\_prime\_is\_prime} for \texttt{MP\_8BIT} only but can be included at build-time for all other sizes -if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined. +Performs the variant of the Frobenius test as described by Paul Underwood. It can be included at build-time if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined and will be used instead of the Lucas-Selfridge test. It returns \texttt{MP\_ITER} if the number of iterations is exhausted, assumes a composite as the input and sets \texttt{result} accordingly. This will reduce the set of available pseudoprimes by a very small amount: test with large datasets (more than $10^{10}$ numbers, both randomly chosen and sequences of odd numbers with a random start point) found only 31 (thirty-one) numbers with $a > 120$ and none at all with just an additional simple check for divisors $d < 2^8$. @@ -2053,7 +2051,7 @@ \section{Primality Testing} \begin{alltt} int mp_prime_is_prime (mp_int * a, int t, int *result) \end{alltt} -This will perform a trial division followed by two rounds of Miller-Rabin with bases 2 and 3 and a Lucas-Selfridge test. The Lucas-Selfridge test is replaced with a Frobenius-Underwood for \texttt{MP\_8BIT}. The Frobenius-Underwood test for all other sizes is available as a compile-time option with the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST}. See file +This will perform a trial division followed by two rounds of Miller-Rabin with bases 2 and 3 and a Lucas-Selfridge test. The Frobenius-Underwood is available as a compile-time option with the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST}. See file \texttt{bn\_mp\_prime\_is\_prime.c} for the necessary details. It shall be noted that both functions are much slower than the Miller-Rabin test and if speed is an essential issue, the macro \texttt{LTM\_USE\_ONLY\_MR} switches both functions, the Frobenius-Underwood test and the Lucas-Selfridge test off and their code will not even be compiled into the library. diff --git a/mtest/mtest.c b/mtest/mtest.c index 06c9afb1f..c8d9e9592 100644 --- a/mtest/mtest.c +++ b/mtest/mtest.c @@ -28,11 +28,7 @@ mulmod */ -#ifdef MP_8BIT -#define THE_MASK 127 -#else #define THE_MASK 32767 -#endif #include #include diff --git a/tommath.h b/tommath.h index 6c4e95774..cca54114f 100644 --- a/tommath.h +++ b/tommath.h @@ -6,6 +6,10 @@ #include #include +#ifdef MP_8BIT +# error "Support of 8-bit architectures has been dropped in this version of LTM." +#endif + #ifndef MP_NO_FILE # include @@ -35,7 +39,7 @@ extern "C" { defined(__sparcv9) || defined(__sparc_v9__) || defined(__sparc64__) || \ defined(__ia64) || defined(__ia64__) || defined(__itanium__) || defined(_M_IA64) || \ defined(__LP64__) || defined(_LP64) || defined(__64BIT__) -# if !(defined(MP_64BIT) || defined(MP_32BIT) || defined(MP_16BIT) || defined(MP_8BIT)) +# if !(defined(MP_64BIT) || defined(MP_32BIT) || defined(MP_16BIT)) # if defined(__GNUC__) && !defined(__hppa) /* we support 128bit integers only via: __attribute__((mode(TI))) */ # define MP_64BIT @@ -47,7 +51,7 @@ extern "C" { #endif #ifdef MP_DIGIT_BIT -# error Defining MP_DIGIT_BIT is disallowed, use MP_8/16/31/32/64BIT +# error Defining MP_DIGIT_BIT is disallowed, use MP_16/31/32/64BIT #endif /* some default configurations. @@ -59,11 +63,8 @@ extern "C" { * [any size beyond that is ok provided it doesn't overflow the data type] */ -#ifdef MP_8BIT -typedef uint8_t mp_digit; -typedef uint16_t private_mp_word; -# define MP_DIGIT_BIT 7 -#elif defined(MP_16BIT) + +#if defined(MP_16BIT) typedef uint16_t mp_digit; typedef uint32_t private_mp_word; # define MP_DIGIT_BIT 15 From 70589a00f932c11cc52c85bc20b0e3a6fc0139ab Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 9 Sep 2019 03:19:22 +0200 Subject: [PATCH 015/304] corrected preprocessor branch in bn_mp_montgomery_setup.c --- bn_mp_montgomery_setup.c | 2 +- bn_mp_prime_is_prime.c | 8 ++++++-- bn_mp_prime_strong_lucas_selfridge.c | 1 - 3 files changed, 7 insertions(+), 4 deletions(-) diff --git a/bn_mp_montgomery_setup.c b/bn_mp_montgomery_setup.c index 8ad19c45c..ad245eb8c 100644 --- a/bn_mp_montgomery_setup.c +++ b/bn_mp_montgomery_setup.c @@ -25,7 +25,7 @@ mp_err mp_montgomery_setup(const mp_int *n, mp_digit *rho) x = (((b + 2u) & 4u) << 1) + b; /* here x*a==1 mod 2**4 */ x *= 2u - (b * x); /* here x*a==1 mod 2**8 */ x *= 2u - (b * x); /* here x*a==1 mod 2**16 */ -#if (defined(MP_64BIT) || defined(MP_16BIT)) +#if defined(MP_64BIT) || !(defined(MP_16BIT)) x *= 2u - (b * x); /* here x*a==1 mod 2**32 */ #endif #ifdef MP_64BIT diff --git a/bn_mp_prime_is_prime.c b/bn_mp_prime_is_prime.c index 678eae4ea..1afa1ae80 100644 --- a/bn_mp_prime_is_prime.c +++ b/bn_mp_prime_is_prime.c @@ -100,7 +100,12 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) */ #ifndef LTM_USE_ONLY_MR if (t >= 0) { -#ifdef LTM_USE_FROBENIUS_TEST + /* + * Use a Frobenius-Underwood test instead of the Lucas-Selfridge test for + * MP_8BIT (It is unknown if the Lucas-Selfridge test works with 16-bit + * integers but the necesssary analysis is on the todo-list). + */ +#ifdef (LTM_USE_FROBENIUS_TEST) err = mp_prime_frobenius_underwood(a, &res); if ((err != MP_OKAY) && (err != MP_ITER)) { goto LBL_B; @@ -228,7 +233,6 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) * an unsigned int and "mask" on the other side is most probably not. */ fips_rand = (unsigned int)(b.dp[0] & (mp_digit) mask); - if (fips_rand > (unsigned int)(INT_MAX - MP_DIGIT_BIT)) { len = INT_MAX / MP_DIGIT_BIT; } else { diff --git a/bn_mp_prime_strong_lucas_selfridge.c b/bn_mp_prime_strong_lucas_selfridge.c index 0f03792ad..a5ea16de6 100644 --- a/bn_mp_prime_strong_lucas_selfridge.c +++ b/bn_mp_prime_strong_lucas_selfridge.c @@ -278,6 +278,5 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) mp_clear_multi(&Q2kdz, &T4z, &T3z, &T2z, &T1z, &Qkdz, &Q2mz, &Qmz, &V2mz, &U2mz, &Vz, &Uz, &Np1, &gcd, &Dz, NULL); return err; } - #endif #endif From be9a71fd5276021bd0407003cc2f35c6716adc67 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 9 Sep 2019 03:27:25 +0200 Subject: [PATCH 016/304] soothed preprocessor --- bn_mp_prime_is_prime.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bn_mp_prime_is_prime.c b/bn_mp_prime_is_prime.c index 1afa1ae80..86edcb692 100644 --- a/bn_mp_prime_is_prime.c +++ b/bn_mp_prime_is_prime.c @@ -105,7 +105,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) * MP_8BIT (It is unknown if the Lucas-Selfridge test works with 16-bit * integers but the necesssary analysis is on the todo-list). */ -#ifdef (LTM_USE_FROBENIUS_TEST) +#ifdef LTM_USE_FROBENIUS_TEST err = mp_prime_frobenius_underwood(a, &res); if ((err != MP_OKAY) && (err != MP_ITER)) { goto LBL_B; From 78588ed6d18fb8b46b2b16d55d689ff5a860588c Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 9 Sep 2019 03:54:26 +0200 Subject: [PATCH 017/304] removed the corect preprocessor branch in mp_to_unsigend_bin this time and removed 8-bit tests from testme.sh --- bn_mp_from_ubin.c | 2 +- testme.sh | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/bn_mp_from_ubin.c b/bn_mp_from_ubin.c index 3e1885dd5..f6d6e2aff 100644 --- a/bn_mp_from_ubin.c +++ b/bn_mp_from_ubin.c @@ -23,7 +23,7 @@ mp_err mp_from_ubin(mp_int *a, const unsigned char *buf, size_t size) if ((err = mp_mul_2d(a, 8, a)) != MP_OKAY) { return err; } - a->dp[0] |= *b++; + a->dp[0] |= *buf++; a->used += 1; } mp_clamp(a); diff --git a/testme.sh b/testme.sh index 40fa32d50..2f7235f96 100755 --- a/testme.sh +++ b/testme.sh @@ -378,13 +378,11 @@ do then _runvalgrind "$i $a" "$CFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runvalgrind "$i $a" "-DMP_8BIT $CFLAGS" _runvalgrind "$i $a" "-DMP_16BIT $CFLAGS" _runvalgrind "$i $a" "-DMP_32BIT $CFLAGS" else _runtest "$i $a" "$CFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runtest "$i $a" "-DMP_8BIT $CFLAGS" _runtest "$i $a" "-DMP_16BIT $CFLAGS" _runtest "$i $a" "-DMP_32BIT $CFLAGS" fi From de484635fa2b1d36d7dce2a028b6ce6f4ddf3062 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 19 May 2019 10:07:49 +0200 Subject: [PATCH 018/304] add move script --- move.sh | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) create mode 100755 move.sh diff --git a/move.sh b/move.sh new file mode 100755 index 000000000..1e1591af8 --- /dev/null +++ b/move.sh @@ -0,0 +1,38 @@ +#!/bin/bash +for i in *.c; do git mv $i ${i/bn_/}; done + +git mv cutoffs.c mp_cutoffs.c +git mv deprecated.c mp_deprecated.c +git mv prime_tab.c mp_prime_tab.c +sed -E -i "s/CUTOFFS_C/MP_CUTOFFS_C/g" tommath_class.h tommath_superclass.h mp_cutoffs.c +sed -E -i "s/DEPRECATED_C/MP_DEPRECATED_C/g" tommath_class.h tommath_superclass.h mp_deprecated.c +sed -E -i "s/PRIME_TAB_C/MP_PRIME_TAB_C/g" tommath_class.h tommath_superclass.h mp_prime_tab.c + +sed -E -i 's/BN_([_A-Z0-9]*_C)/\1/g' *.c */*.c etc/*.c *.h +sed -E -i "s/bn_([_a-z0-9]*\.c)/\1/g" *.c */*.c + +sed -E -i "s/'BN_' \. //g" helper.pl +sed -E -i "s/BN_//g" helper.pl +sed -E -i "s/bn\*.c/*mp_*.c/g" helper.pl +sed -E -i "s/bn\*.c/*mp_*.c/g" gen.pl + +sed -E -i "s/bn_//g" doc/bn.tex +sed -E -i 's/BN\\_//g' doc/bn.tex + +sed -E -i "s/BN_H_/TOMMATH_H_/g" tommath.h +sed -E -i "s/TOMMATH_PRIV_H_/TOMMATH_PRIVATE_H_/g" tommath_private.h +sed -E -i 's/BN_##//' tommath_private.h +sed -E -i "s/BN_MP_DIV_SMALL/MP_DIV_SMALL/g" *.c *.h + +sed -E -i 's/LTM_ERR/LBL_ERR/g' *.c */*.c + +./helper.pl -u + +git rm move.sh +git add . +git commit -m 'Execute move.sh - Rename files from bn_* to match the function names. + +* git blame is not affected +* git log --follow can be used to show log across renames' + +./helper.pl -a From 7a68f12873b1c58ea254e7c5e70e79846692a484 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sat, 19 Oct 2019 16:24:39 +0200 Subject: [PATCH 019/304] Execute move.sh - Rename files from bn_* to match the function names. * git blame is not affected * git log --follow can be used to show log across renames --- demo/test.c | 232 +- doc/bn.tex | 54 +- etc/tune.c | 26 +- gen.pl | 2 +- helper.pl | 8 +- libtommath_VS2008.vcproj | 312 +-- makefile | 52 +- makefile.mingw | 52 +- makefile.msvc | 52 +- makefile.shared | 52 +- makefile.unix | 52 +- move.sh | 38 - bn_mp_2expt.c => mp_2expt.c | 2 +- bn_mp_abs.c => mp_abs.c | 2 +- bn_mp_add.c => mp_add.c | 2 +- bn_mp_add_d.c => mp_add_d.c | 2 +- bn_mp_addmod.c => mp_addmod.c | 2 +- bn_mp_and.c => mp_and.c | 2 +- bn_mp_clamp.c => mp_clamp.c | 2 +- bn_mp_clear.c => mp_clear.c | 2 +- bn_mp_clear_multi.c => mp_clear_multi.c | 2 +- bn_mp_cmp.c => mp_cmp.c | 2 +- bn_mp_cmp_d.c => mp_cmp_d.c | 2 +- bn_mp_cmp_mag.c => mp_cmp_mag.c | 2 +- bn_mp_cnt_lsb.c => mp_cnt_lsb.c | 2 +- bn_mp_complement.c => mp_complement.c | 2 +- bn_mp_copy.c => mp_copy.c | 2 +- bn_mp_count_bits.c => mp_count_bits.c | 2 +- bn_cutoffs.c => mp_cutoffs.c | 2 +- bn_mp_decr.c => mp_decr.c | 2 +- bn_mp_div.c => mp_div.c | 4 +- bn_mp_div_2.c => mp_div_2.c | 2 +- bn_mp_div_2d.c => mp_div_2d.c | 2 +- bn_mp_div_3.c => mp_div_3.c | 2 +- bn_mp_div_d.c => mp_div_d.c | 2 +- bn_mp_dr_is_modulus.c => mp_dr_is_modulus.c | 2 +- bn_mp_dr_reduce.c => mp_dr_reduce.c | 2 +- bn_mp_dr_setup.c => mp_dr_setup.c | 2 +- ..._error_to_string.c => mp_error_to_string.c | 2 +- bn_mp_exch.c => mp_exch.c | 2 +- bn_mp_expt_u32.c => mp_expt_u32.c | 2 +- bn_mp_exptmod.c => mp_exptmod.c | 2 +- bn_mp_exteuclid.c => mp_exteuclid.c | 2 +- bn_mp_fread.c => mp_fread.c | 2 +- bn_mp_from_sbin.c => mp_from_sbin.c | 2 +- bn_mp_from_ubin.c => mp_from_ubin.c | 2 +- bn_mp_fwrite.c => mp_fwrite.c | 2 +- bn_mp_gcd.c => mp_gcd.c | 2 +- bn_mp_get_double.c => mp_get_double.c | 2 +- bn_mp_get_i32.c => mp_get_i32.c | 2 +- bn_mp_get_i64.c => mp_get_i64.c | 2 +- bn_mp_get_l.c => mp_get_l.c | 2 +- bn_mp_get_ll.c => mp_get_ll.c | 2 +- bn_mp_get_mag_u32.c => mp_get_mag_u32.c | 2 +- bn_mp_get_mag_u64.c => mp_get_mag_u64.c | 2 +- bn_mp_get_mag_ul.c => mp_get_mag_ul.c | 2 +- bn_mp_get_mag_ull.c => mp_get_mag_ull.c | 2 +- bn_mp_grow.c => mp_grow.c | 2 +- bn_mp_incr.c => mp_incr.c | 2 +- bn_mp_init.c => mp_init.c | 2 +- bn_mp_init_copy.c => mp_init_copy.c | 2 +- bn_mp_init_i32.c => mp_init_i32.c | 2 +- bn_mp_init_i64.c => mp_init_i64.c | 2 +- bn_mp_init_l.c => mp_init_l.c | 2 +- bn_mp_init_ll.c => mp_init_ll.c | 2 +- bn_mp_init_multi.c => mp_init_multi.c | 2 +- bn_mp_init_set.c => mp_init_set.c | 2 +- bn_mp_init_size.c => mp_init_size.c | 2 +- bn_mp_init_u32.c => mp_init_u32.c | 2 +- bn_mp_init_u64.c => mp_init_u64.c | 2 +- bn_mp_init_ul.c => mp_init_ul.c | 2 +- bn_mp_init_ull.c => mp_init_ull.c | 2 +- bn_mp_invmod.c => mp_invmod.c | 2 +- bn_mp_is_square.c => mp_is_square.c | 2 +- bn_mp_iseven.c => mp_iseven.c | 2 +- bn_mp_isodd.c => mp_isodd.c | 2 +- bn_mp_kronecker.c => mp_kronecker.c | 2 +- bn_mp_lcm.c => mp_lcm.c | 2 +- bn_mp_log_u32.c => mp_log_u32.c | 2 +- bn_mp_lshd.c => mp_lshd.c | 4 +- bn_mp_mod.c => mp_mod.c | 2 +- bn_mp_mod_2d.c => mp_mod_2d.c | 2 +- bn_mp_mod_d.c => mp_mod_d.c | 2 +- ...on.c => mp_montgomery_calc_normalization.c | 2 +- ...tgomery_reduce.c => mp_montgomery_reduce.c | 2 +- ...ontgomery_setup.c => mp_montgomery_setup.c | 2 +- bn_mp_mul.c => mp_mul.c | 2 +- bn_mp_mul_2.c => mp_mul_2.c | 2 +- bn_mp_mul_2d.c => mp_mul_2d.c | 2 +- bn_mp_mul_d.c => mp_mul_d.c | 2 +- bn_mp_mulmod.c => mp_mulmod.c | 2 +- bn_mp_neg.c => mp_neg.c | 2 +- bn_mp_or.c => mp_or.c | 2 +- bn_mp_pack.c => mp_pack.c | 2 +- bn_mp_pack_count.c => mp_pack_count.c | 2 +- bn_mp_prime_fermat.c => mp_prime_fermat.c | 2 +- ...erwood.c => mp_prime_frobenius_underwood.c | 4 +- bn_mp_prime_is_prime.c => mp_prime_is_prime.c | 2 +- ..._miller_rabin.c => mp_prime_miller_rabin.c | 2 +- ...rime_next_prime.c => mp_prime_next_prime.c | 2 +- ...trials.c => mp_prime_rabin_miller_trials.c | 2 +- bn_mp_prime_rand.c => mp_prime_rand.c | 2 +- ...dge.c => mp_prime_strong_lucas_selfridge.c | 4 +- bn_prime_tab.c => mp_prime_tab.c | 2 +- bn_mp_radix_size.c => mp_radix_size.c | 2 +- bn_mp_radix_smap.c => mp_radix_smap.c | 2 +- bn_mp_rand.c => mp_rand.c | 2 +- bn_mp_read_radix.c => mp_read_radix.c | 2 +- bn_mp_reduce.c => mp_reduce.c | 2 +- bn_mp_reduce_2k.c => mp_reduce_2k.c | 2 +- bn_mp_reduce_2k_l.c => mp_reduce_2k_l.c | 2 +- ..._reduce_2k_setup.c => mp_reduce_2k_setup.c | 2 +- ...uce_2k_setup_l.c => mp_reduce_2k_setup_l.c | 2 +- bn_mp_reduce_is_2k.c => mp_reduce_is_2k.c | 2 +- bn_mp_reduce_is_2k_l.c => mp_reduce_is_2k_l.c | 2 +- bn_mp_reduce_setup.c => mp_reduce_setup.c | 2 +- bn_mp_root_u32.c => mp_root_u32.c | 2 +- bn_mp_rshd.c => mp_rshd.c | 2 +- bn_mp_sbin_size.c => mp_sbin_size.c | 2 +- bn_mp_set.c => mp_set.c | 2 +- bn_mp_set_double.c => mp_set_double.c | 2 +- bn_mp_set_i32.c => mp_set_i32.c | 2 +- bn_mp_set_i64.c => mp_set_i64.c | 2 +- bn_mp_set_l.c => mp_set_l.c | 2 +- bn_mp_set_ll.c => mp_set_ll.c | 2 +- bn_mp_set_u32.c => mp_set_u32.c | 2 +- bn_mp_set_u64.c => mp_set_u64.c | 2 +- bn_mp_set_ul.c => mp_set_ul.c | 2 +- bn_mp_set_ull.c => mp_set_ull.c | 2 +- bn_mp_shrink.c => mp_shrink.c | 2 +- bn_mp_signed_rsh.c => mp_signed_rsh.c | 2 +- bn_mp_sqr.c => mp_sqr.c | 2 +- bn_mp_sqrmod.c => mp_sqrmod.c | 2 +- bn_mp_sqrt.c => mp_sqrt.c | 2 +- bn_mp_sqrtmod_prime.c => mp_sqrtmod_prime.c | 2 +- bn_mp_sub.c => mp_sub.c | 2 +- bn_mp_sub_d.c => mp_sub_d.c | 2 +- bn_mp_submod.c => mp_submod.c | 2 +- bn_mp_to_radix.c => mp_to_radix.c | 2 +- bn_mp_to_sbin.c => mp_to_sbin.c | 2 +- bn_mp_to_ubin.c => mp_to_ubin.c | 2 +- bn_mp_ubin_size.c => mp_ubin_size.c | 2 +- bn_mp_unpack.c => mp_unpack.c | 2 +- bn_mp_xor.c => mp_xor.c | 2 +- bn_mp_zero.c => mp_zero.c | 2 +- bn_s_mp_add.c => s_mp_add.c | 2 +- bn_s_mp_balance_mul.c => s_mp_balance_mul.c | 2 +- bn_s_mp_exptmod.c => s_mp_exptmod.c | 2 +- bn_s_mp_exptmod_fast.c => s_mp_exptmod_fast.c | 2 +- bn_s_mp_get_bit.c => s_mp_get_bit.c | 2 +- bn_s_mp_invmod_fast.c => s_mp_invmod_fast.c | 2 +- bn_s_mp_invmod_slow.c => s_mp_invmod_slow.c | 2 +- ...mp_karatsuba_mul.c => s_mp_karatsuba_mul.c | 2 +- ...mp_karatsuba_sqr.c => s_mp_karatsuba_sqr.c | 2 +- ...ce_fast.c => s_mp_montgomery_reduce_fast.c | 2 +- bn_s_mp_mul_digs.c => s_mp_mul_digs.c | 2 +- ...mp_mul_digs_fast.c => s_mp_mul_digs_fast.c | 2 +- ...mp_mul_high_digs.c => s_mp_mul_high_digs.c | 2 +- ...h_digs_fast.c => s_mp_mul_high_digs_fast.c | 2 +- ...s_divisible.c => s_mp_prime_is_divisible.c | 2 +- bn_s_mp_rand_jenkins.c => s_mp_rand_jenkins.c | 2 +- ...mp_rand_platform.c => s_mp_rand_platform.c | 14 +- bn_s_mp_reverse.c => s_mp_reverse.c | 2 +- bn_s_mp_sqr.c => s_mp_sqr.c | 2 +- bn_s_mp_sqr_fast.c => s_mp_sqr_fast.c | 2 +- bn_s_mp_sub.c => s_mp_sub.c | 2 +- bn_s_mp_toom_mul.c => s_mp_toom_mul.c | 2 +- bn_s_mp_toom_sqr.c => s_mp_toom_sqr.c | 2 +- tommath.def | 2 + tommath.h | 4 +- tommath_class.h | 1930 ++++++++--------- tommath_private.h | 6 +- tommath_superclass.h | 130 +- 173 files changed, 1635 insertions(+), 1701 deletions(-) delete mode 100755 move.sh rename bn_mp_2expt.c => mp_2expt.c (97%) rename bn_mp_abs.c => mp_abs.c (96%) rename bn_mp_add.c => mp_add.c (98%) rename bn_mp_add_d.c => mp_add_d.c (98%) rename bn_mp_addmod.c => mp_addmod.c (95%) rename bn_mp_and.c => mp_and.c (98%) rename bn_mp_clamp.c => mp_clamp.c (96%) rename bn_mp_clear.c => mp_clear.c (95%) rename bn_mp_clear_multi.c => mp_clear_multi.c (93%) rename bn_mp_cmp.c => mp_cmp.c (96%) rename bn_mp_cmp_d.c => mp_cmp_d.c (96%) rename bn_mp_cmp_mag.c => mp_cmp_mag.c (97%) rename bn_mp_cnt_lsb.c => mp_cnt_lsb.c (97%) rename bn_mp_complement.c => mp_complement.c (92%) rename bn_mp_copy.c => mp_copy.c (97%) rename bn_mp_count_bits.c => mp_count_bits.c (95%) rename bn_cutoffs.c => mp_cutoffs.c (95%) rename bn_mp_decr.c => mp_decr.c (97%) rename bn_mp_div.c => mp_div.c (99%) rename bn_mp_div_2.c => mp_div_2.c (97%) rename bn_mp_div_2d.c => mp_div_2d.c (98%) rename bn_mp_div_3.c => mp_div_3.c (98%) rename bn_mp_div_d.c => mp_div_d.c (98%) rename bn_mp_dr_is_modulus.c => mp_dr_is_modulus.c (95%) rename bn_mp_dr_reduce.c => mp_dr_reduce.c (98%) rename bn_mp_dr_setup.c => mp_dr_setup.c (94%) rename bn_mp_error_to_string.c => mp_error_to_string.c (94%) rename bn_mp_exch.c => mp_exch.c (94%) rename bn_mp_expt_u32.c => mp_expt_u32.c (97%) rename bn_mp_exptmod.c => mp_exptmod.c (98%) rename bn_mp_exteuclid.c => mp_exteuclid.c (99%) rename bn_mp_fread.c => mp_fread.c (98%) rename bn_mp_from_sbin.c => mp_from_sbin.c (96%) rename bn_mp_from_ubin.c => mp_from_ubin.c (96%) rename bn_mp_fwrite.c => mp_fwrite.c (97%) rename bn_mp_gcd.c => mp_gcd.c (99%) rename bn_mp_get_double.c => mp_get_double.c (94%) rename bn_mp_get_i32.c => mp_get_i32.c (90%) rename bn_mp_get_i64.c => mp_get_i64.c (90%) rename bn_mp_get_l.c => mp_get_l.c (90%) rename bn_mp_get_ll.c => mp_get_ll.c (90%) rename bn_mp_get_mag_u32.c => mp_get_mag_u32.c (87%) rename bn_mp_get_mag_u64.c => mp_get_mag_u64.c (87%) rename bn_mp_get_mag_ul.c => mp_get_mag_ul.c (87%) rename bn_mp_get_mag_ull.c => mp_get_mag_ull.c (87%) rename bn_mp_grow.c => mp_grow.c (98%) rename bn_mp_incr.c => mp_incr.c (97%) rename bn_mp_init.c => mp_init.c (96%) rename bn_mp_init_copy.c => mp_init_copy.c (94%) rename bn_mp_init_i32.c => mp_init_i32.c (88%) rename bn_mp_init_i64.c => mp_init_i64.c (88%) rename bn_mp_init_l.c => mp_init_l.c (89%) rename bn_mp_init_ll.c => mp_init_ll.c (89%) rename bn_mp_init_multi.c => mp_init_multi.c (97%) rename bn_mp_init_set.c => mp_init_set.c (93%) rename bn_mp_init_size.c => mp_init_size.c (95%) rename bn_mp_init_u32.c => mp_init_u32.c (88%) rename bn_mp_init_u64.c => mp_init_u64.c (88%) rename bn_mp_init_ul.c => mp_init_ul.c (89%) rename bn_mp_init_ull.c => mp_init_ull.c (89%) rename bn_mp_invmod.c => mp_invmod.c (96%) rename bn_mp_is_square.c => mp_is_square.c (99%) rename bn_mp_iseven.c => mp_iseven.c (91%) rename bn_mp_isodd.c => mp_isodd.c (91%) rename bn_mp_kronecker.c => mp_kronecker.c (99%) rename bn_mp_lcm.c => mp_lcm.c (98%) rename bn_mp_log_u32.c => mp_log_u32.c (99%) rename bn_mp_lshd.c => mp_lshd.c (92%) rename bn_mp_mod.c => mp_mod.c (97%) rename bn_mp_mod_2d.c => mp_mod_2d.c (97%) rename bn_mp_mod_d.c => mp_mod_d.c (92%) rename bn_mp_montgomery_calc_normalization.c => mp_montgomery_calc_normalization.c (96%) rename bn_mp_montgomery_reduce.c => mp_montgomery_reduce.c (98%) rename bn_mp_montgomery_setup.c => mp_montgomery_setup.c (97%) rename bn_mp_mul.c => mp_mul.c (99%) rename bn_mp_mul_2.c => mp_mul_2.c (98%) rename bn_mp_mul_2d.c => mp_mul_2d.c (98%) rename bn_mp_mul_d.c => mp_mul_d.c (98%) rename bn_mp_mulmod.c => mp_mulmod.c (95%) rename bn_mp_neg.c => mp_neg.c (96%) rename bn_mp_or.c => mp_or.c (98%) rename bn_mp_pack.c => mp_pack.c (98%) rename bn_mp_pack_count.c => mp_pack_count.c (93%) rename bn_mp_prime_fermat.c => mp_prime_fermat.c (97%) rename bn_mp_prime_frobenius_underwood.c => mp_prime_frobenius_underwood.c (97%) rename bn_mp_prime_is_prime.c => mp_prime_is_prime.c (99%) rename bn_mp_prime_miller_rabin.c => mp_prime_miller_rabin.c (98%) rename bn_mp_prime_next_prime.c => mp_prime_next_prime.c (99%) rename bn_mp_prime_rabin_miller_trials.c => mp_prime_rabin_miller_trials.c (97%) rename bn_mp_prime_rand.c => mp_prime_rand.c (99%) rename bn_mp_prime_strong_lucas_selfridge.c => mp_prime_strong_lucas_selfridge.c (98%) rename bn_prime_tab.c => mp_prime_tab.c (99%) rename bn_mp_radix_size.c => mp_radix_size.c (96%) rename bn_mp_radix_smap.c => mp_radix_smap.c (97%) rename bn_mp_rand.c => mp_rand.c (98%) rename bn_mp_read_radix.c => mp_read_radix.c (98%) rename bn_mp_reduce.c => mp_reduce.c (98%) rename bn_mp_reduce_2k.c => mp_reduce_2k.c (97%) rename bn_mp_reduce_2k_l.c => mp_reduce_2k_l.c (97%) rename bn_mp_reduce_2k_setup.c => mp_reduce_2k_setup.c (95%) rename bn_mp_reduce_2k_setup_l.c => mp_reduce_2k_setup_l.c (94%) rename bn_mp_reduce_is_2k.c => mp_reduce_is_2k.c (96%) rename bn_mp_reduce_is_2k_l.c => mp_reduce_is_2k_l.c (95%) rename bn_mp_reduce_setup.c => mp_reduce_setup.c (94%) rename bn_mp_root_u32.c => mp_root_u32.c (99%) rename bn_mp_rshd.c => mp_rshd.c (98%) rename bn_mp_sbin_size.c => mp_sbin_size.c (91%) rename bn_mp_set.c => mp_set.c (94%) rename bn_mp_set_double.c => mp_set_double.c (97%) rename bn_mp_set_i32.c => mp_set_i32.c (89%) rename bn_mp_set_i64.c => mp_set_i64.c (89%) rename bn_mp_set_l.c => mp_set_l.c (90%) rename bn_mp_set_ll.c => mp_set_ll.c (90%) rename bn_mp_set_u32.c => mp_set_u32.c (88%) rename bn_mp_set_u64.c => mp_set_u64.c (88%) rename bn_mp_set_ul.c => mp_set_ul.c (89%) rename bn_mp_set_ull.c => mp_set_ull.c (89%) rename bn_mp_shrink.c => mp_shrink.c (96%) rename bn_mp_signed_rsh.c => mp_signed_rsh.c (95%) rename bn_mp_sqr.c => mp_sqr.c (97%) rename bn_mp_sqrmod.c => mp_sqrmod.c (95%) rename bn_mp_sqrt.c => mp_sqrt.c (98%) rename bn_mp_sqrtmod_prime.c => mp_sqrtmod_prime.c (99%) rename bn_mp_sub.c => mp_sub.c (98%) rename bn_mp_sub_d.c => mp_sub_d.c (98%) rename bn_mp_submod.c => mp_submod.c (95%) rename bn_mp_to_radix.c => mp_to_radix.c (98%) rename bn_mp_to_sbin.c => mp_to_sbin.c (96%) rename bn_mp_to_ubin.c => mp_to_ubin.c (97%) rename bn_mp_ubin_size.c => mp_ubin_size.c (93%) rename bn_mp_unpack.c => mp_unpack.c (98%) rename bn_mp_xor.c => mp_xor.c (98%) rename bn_mp_zero.c => mp_zero.c (93%) rename bn_s_mp_add.c => s_mp_add.c (98%) rename bn_s_mp_balance_mul.c => s_mp_balance_mul.c (98%) rename bn_s_mp_exptmod.c => s_mp_exptmod.c (99%) rename bn_s_mp_exptmod_fast.c => s_mp_exptmod_fast.c (99%) rename bn_s_mp_get_bit.c => s_mp_get_bit.c (95%) rename bn_s_mp_invmod_fast.c => s_mp_invmod_fast.c (99%) rename bn_s_mp_invmod_slow.c => s_mp_invmod_slow.c (99%) rename bn_s_mp_karatsuba_mul.c => s_mp_karatsuba_mul.c (99%) rename bn_s_mp_karatsuba_sqr.c => s_mp_karatsuba_sqr.c (98%) rename bn_s_mp_montgomery_reduce_fast.c => s_mp_montgomery_reduce_fast.c (99%) rename bn_s_mp_mul_digs.c => s_mp_mul_digs.c (98%) rename bn_s_mp_mul_digs_fast.c => s_mp_mul_digs_fast.c (98%) rename bn_s_mp_mul_high_digs.c => s_mp_mul_high_digs.c (98%) rename bn_s_mp_mul_high_digs_fast.c => s_mp_mul_high_digs_fast.c (98%) rename bn_s_mp_prime_is_divisible.c => s_mp_prime_is_divisible.c (95%) rename bn_s_mp_rand_jenkins.c => s_mp_rand_jenkins.c (97%) rename bn_s_mp_rand_platform.c => s_mp_rand_platform.c (92%) rename bn_s_mp_reverse.c => s_mp_reverse.c (94%) rename bn_s_mp_sqr.c => s_mp_sqr.c (98%) rename bn_s_mp_sqr_fast.c => s_mp_sqr_fast.c (98%) rename bn_s_mp_sub.c => s_mp_sub.c (98%) rename bn_s_mp_toom_mul.c => s_mp_toom_mul.c (99%) rename bn_s_mp_toom_sqr.c => s_mp_toom_sqr.c (99%) diff --git a/demo/test.c b/demo/test.c index 9002e9631..acb81c520 100644 --- a/demo/test.c +++ b/demo/test.c @@ -62,25 +62,25 @@ void does_not_exist(void); static int test_feature_detection(void) { -#define BN_TEST_FEATURE1_C +#define TEST_FEATURE1_C if (!MP_HAS(TEST_FEATURE1)) { does_not_exist(); return EXIT_FAILURE; } -#define BN_TEST_FEATURE2_C 1 +#define TEST_FEATURE2_C 1 if (MP_HAS(TEST_FEATURE2)) { does_not_exist(); return EXIT_FAILURE; } -#define BN_TEST_FEATURE3_C 0 +#define TEST_FEATURE3_C 0 if (MP_HAS(TEST_FEATURE3)) { does_not_exist(); return EXIT_FAILURE; } -#define BN_TEST_FEATURE4_C something +#define TEST_FEATURE4_C something if (MP_HAS(TEST_FEATURE4)) { does_not_exist(); return EXIT_FAILURE; @@ -1254,30 +1254,30 @@ static int test_mp_read_radix(void) mp_err err; mp_int a; - if (mp_init_multi(&a, NULL)!= MP_OKAY) goto LTM_ERR; + if (mp_init_multi(&a, NULL)!= MP_OKAY) goto LBL_ERR; - if ((err = mp_read_radix(&a, "123456", 10)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_read_radix(&a, "123456", 10)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; printf(" '123456' a == %s, length = %zu\n", buf, written); - /* See comment in bn_mp_to_radix.c */ + /* See comment in mp_to_radix.c */ /* - if( (err = mp_to_radix(&a, buf, 3u, &written, 10) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_to_radix(&a, buf, 3u, &written, 10) ) != MP_OKAY) goto LBL_ERR; printf(" '56' a == %s, length = %zu\n", buf, written); - if( (err = mp_to_radix(&a, buf, 4u, &written, 10) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_to_radix(&a, buf, 4u, &written, 10) ) != MP_OKAY) goto LBL_ERR; printf(" '456' a == %s, length = %zu\n", buf, written); - if( (err = mp_to_radix(&a, buf, 30u, &written, 10) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_to_radix(&a, buf, 30u, &written, 10) ) != MP_OKAY) goto LBL_ERR; printf(" '123456' a == %s, length = %zu, error = %s\n", buf, written, mp_error_to_string(err)); */ - if ((err = mp_read_radix(&a, "-123456", 10)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_read_radix(&a, "-123456", 10)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; printf(" '-123456' a == %s, length = %zu\n", buf, written); - if ((err = mp_read_radix(&a, "0", 10)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_read_radix(&a, "0", 10)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; printf(" '0' a == %s, length = %zu\n", buf, written); while (0) { @@ -1291,7 +1291,7 @@ static int test_mp_read_radix(void) mp_clear(&a); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear(&a); return EXIT_FAILURE; } @@ -1696,61 +1696,61 @@ static int test_mp_incr(void) mp_err e = MP_OKAY; if ((e = mp_init_multi(&a, &b, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it increment inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); if ((e = mp_incr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp_d(&a, (MP_MASK/2uL) + 1uL) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it increment outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); mp_set(&b, MP_MASK); if ((e = mp_incr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_add_d(&b, 1uL, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it increment from -1 to 0? */ mp_set(&a, 1uL); a.sign = MP_NEG; if ((e = mp_incr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp_d(&a, 0uL) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it increment from -(MP_MASK + 1) to -MP_MASK? */ mp_set(&a, MP_MASK); if ((e = mp_add_d(&a, 1uL, &a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } a.sign = MP_NEG; if ((e = mp_incr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (a.sign != MP_NEG) { - goto LTM_ERR; + goto LBL_ERR; } a.sign = MP_ZPOS; if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, NULL); return EXIT_FAILURE; } @@ -1761,42 +1761,42 @@ static int test_mp_decr(void) mp_err e = MP_OKAY; if ((e = mp_init_multi(&a, &b, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it decrement inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); if ((e = mp_decr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp_d(&a, (MP_MASK/2uL) - 1uL) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it decrement outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); if ((e = mp_add_d(&a, 1uL, &a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_decr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } /* Does it decrement from 0 to -1? */ mp_zero(&a); if ((e = mp_decr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (a.sign == MP_NEG) { a.sign = MP_ZPOS; if (mp_cmp_d(&a, 1uL) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } } else { - goto LTM_ERR; + goto LBL_ERR; } @@ -1806,18 +1806,18 @@ static int test_mp_decr(void) mp_set(&b, MP_MASK); b.sign = MP_NEG; if ((e = mp_sub_d(&b, 1uL, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_decr(&a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, NULL); return EXIT_FAILURE; } @@ -2044,13 +2044,13 @@ static int test_mp_root_u32(void) mp_read_radix(&r, root[i][j-3], 10); if (mp_cmp(&r, &c) != MP_EQ) { fprintf(stderr, "mp_root_u32 failed at input #%d, root #%d\n", i, j); - goto LTM_ERR; + goto LBL_ERR; } } } mp_clear_multi(&a, &c, &r, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &c, &r, NULL); return EXIT_FAILURE; } @@ -2067,31 +2067,31 @@ static int test_s_mp_balance_mul(void) "HzrSq9WVt1jDTVlwUxSKqxctu2GVD+N8+SVGaPFRqdxyld6IxDBbj27BPJzYUdR96k3sWpkO8XnDBvupGPnehpQe4KlO/KmN1PjFov/UTZYM+LYzkFcBPyV6hkkL8ePC1rlFLAHzgJMBCXVp4mRqtkQrDsZXXlcqlbTFu69wF6zDEysiX2cAtn/kP9ldblJiwYPCD8hG"; if ((e = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_read_radix(&a, na, 64)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_read_radix(&b, nb, 64)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = s_mp_balance_mul(&a, &b, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_read_radix(&b, nc, 64)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&b, &c) != MP_EQ) { - goto LTM_ERR; + goto LBL_ERR; } mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, NULL); return EXIT_FAILURE; } @@ -2103,30 +2103,30 @@ static int test_s_mp_karatsuba_mul(void) int size, err; if ((err = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } for (size = MP_KARATSUBA_MUL_CUTOFF; size < MP_KARATSUBA_MUL_CUTOFF + 20; size++) { if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_karatsuba_mul(&a, &b, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_mul(&a,&b,&d)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Karatsuba multiplication failed at size %d\n", size); - goto LTM_ERR; + goto LBL_ERR; } } mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_FAILURE; } @@ -2137,27 +2137,27 @@ static int test_s_mp_karatsuba_sqr(void) int size, err; if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } for (size = MP_KARATSUBA_SQR_CUTOFF; size < MP_KARATSUBA_SQR_CUTOFF + 20; size++) { if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_karatsuba_sqr(&a, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_sqr(&a, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Karatsuba squaring failed at size %d\n", size); - goto LTM_ERR; + goto LBL_ERR; } } mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, NULL); return EXIT_FAILURE; } @@ -2172,70 +2172,70 @@ static int test_s_mp_toom_mul(void) #endif if ((err = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } /* This number construction is limb-size specific */ #if (MP_DIGIT_BIT == 60) if ((err = mp_rand(&a, 1196)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_mul_2d(&a,71787 - mp_count_bits(&a), &a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_rand(&b, 1338)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_mul_2d(&b, 80318 - mp_count_bits(&b), &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_mul_2d(&b, 6310, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_2expt(&c, 99000 - 1000)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } tc_cutoff = TOOM_MUL_CUTOFF; TOOM_MUL_CUTOFF = INT_MAX; if ((err = mp_mul(&a, &b, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } TOOM_MUL_CUTOFF = tc_cutoff; if ((err = mp_mul(&a, &b, &d)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed for edgecase f1 * f2\n"); - goto LTM_ERR; + goto LBL_ERR; } #endif for (size = MP_TOOM_MUL_CUTOFF; size < MP_TOOM_MUL_CUTOFF + 20; size++) { if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_toom_mul(&a, &b, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_mul(&a,&b,&d)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed at size %d\n", size); - goto LTM_ERR; + goto LBL_ERR; } } mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_FAILURE; } @@ -2246,27 +2246,27 @@ static int test_s_mp_toom_sqr(void) int size, err; if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } for (size = MP_TOOM_SQR_CUTOFF; size < MP_TOOM_SQR_CUTOFF + 20; size++) { if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_toom_sqr(&a, &b)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if ((err = s_mp_sqr(&a, &c)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way squaring failed at size %d\n", size); - goto LTM_ERR; + goto LBL_ERR; } } mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, NULL); return EXIT_FAILURE; } @@ -2294,33 +2294,33 @@ static int test_mp_radix_size(void) /* number to result in a different size for every base: 67^(4 * 67) */ mp_set(&a, 67); if ((err = mp_expt_u32(&a, 268u, &a)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } for (radix = 2; radix < 65; radix++) { if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (size != results[radix]) { fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", radix, size, results[radix]); - goto LTM_ERR; + goto LBL_ERR; } a.sign = MP_NEG; if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } if (size != (results[radix] + 1)) { fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", radix, size, results[radix]); - goto LTM_ERR; + goto LBL_ERR; } a.sign = MP_ZPOS; } mp_clear(&a); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: mp_clear(&a); return EXIT_FAILURE; } @@ -2335,11 +2335,11 @@ static int test_mp_read_write_ubin(void) unsigned char *buf = NULL; if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LBL_ERR; size = mp_ubin_size(&a); printf("mp_to_ubin_size %zu\n", size); @@ -2347,22 +2347,22 @@ static int test_mp_read_write_ubin(void) if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (u) failed to allocate %zu bytes\n", sizeof(*buf) * size); - goto LTM_ERR; + goto LBL_ERR; } - if ((err = mp_to_ubin(&a, buf, size, &len)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_to_ubin(&a, buf, size, &len)) != MP_OKAY) goto LBL_ERR; printf("mp_to_ubin len = %zu\n", len); - if ((err = mp_from_ubin(&c, buf, len)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_from_ubin(&c, buf, len)) != MP_OKAY) goto LBL_ERR; if (mp_cmp(&a, &c) != MP_EQ) { fprintf(stderr, "to/from ubin cycle failed\n"); - goto LTM_ERR; + goto LBL_ERR; } free(buf); mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: free(buf); mp_clear_multi(&a, &b, &c, NULL); return EXIT_FAILURE; @@ -2376,11 +2376,11 @@ static int test_mp_read_write_sbin(void) unsigned char *buf = NULL; if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LTM_ERR; + goto LBL_ERR; } - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LBL_ERR; size = mp_sbin_size(&a); printf("mp_to_sbin_size %zu\n", size); @@ -2388,23 +2388,23 @@ static int test_mp_read_write_sbin(void) if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (s) failed to allocate %zu bytes\n", sizeof(*buf) * size); - goto LTM_ERR; + goto LBL_ERR; } - if ((err = mp_to_sbin(&b, buf, size, &len)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_to_sbin(&b, buf, size, &len)) != MP_OKAY) goto LBL_ERR; printf("mp_to_sbin len = %zu\n", len); - if ((err = mp_from_sbin(&c, buf, len)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_from_sbin(&c, buf, len)) != MP_OKAY) goto LBL_ERR; if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "to/from ubin cycle failed\n"); - goto LTM_ERR; + goto LBL_ERR; } free(buf); mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: free(buf); mp_clear_multi(&a, &b, &c, NULL); return EXIT_FAILURE; @@ -2420,31 +2420,31 @@ static int test_mp_pack_unpack(void) mp_order order = MP_LSB_FIRST; mp_endian endianess = MP_NATIVE_ENDIAN; - if ((err = mp_init_multi(&a, &b, NULL)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_init_multi(&a, &b, NULL)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; count = mp_pack_count(&a, 0, 1); buf = malloc(count); if (buf == NULL) { fprintf(stderr, "test_pack_unpack failed to allocate\n"); - goto LTM_ERR; + goto LBL_ERR; } if ((err = mp_pack((void *)buf, count, &written, order, 1, - endianess, 0, &a)) != MP_OKAY) goto LTM_ERR; + endianess, 0, &a)) != MP_OKAY) goto LBL_ERR; if ((err = mp_unpack(&b, count, order, 1, - endianess, 0, (const void *)buf)) != MP_OKAY) goto LTM_ERR; + endianess, 0, (const void *)buf)) != MP_OKAY) goto LBL_ERR; if (mp_cmp(&a, &b) != MP_EQ) { fprintf(stderr, "pack/unpack cycle failed\n"); - goto LTM_ERR; + goto LBL_ERR; } free(buf); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; -LTM_ERR: +LBL_ERR: free(buf); mp_clear_multi(&a, &b, NULL); return EXIT_FAILURE; diff --git a/doc/bn.tex b/doc/bn.tex index 27f27e75e..fe6b5c6ee 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -174,11 +174,11 @@ \subsubsection{OpenBSD} cc -I./ -Wall -Wsign-compare -Wextra -Wshadow -Wsystem-headers -Wdeclaration-afo... cc -I./ -Wall -Wsign-compare -Wextra -Wshadow -Wsystem-headers -Wdeclaration-afo... cc -I./ -Wall -Wsign-compare -Wextra -Wshadow -Wsystem-headers -Wdeclaration-afo... -libtool --mode=link --tag=CC cc bn_error.lo bn_s_mp_invmod_fast.lo bn_fast_mp_mo -libtool: link: cc bn_error.lo bn_s_mp_invmod_fast.lo bn_s_mp_montgomery_reduce_fast0 -bn_error.lo: file not recognized: File format not recognized +libtool --mode=link --tag=CC cc error.lo s_mp_invmod_fast.lo fast_mp_mo +libtool: link: cc error.lo s_mp_invmod_fast.lo s_mp_montgomery_reduce_fast0 +error.lo: file not recognized: File format not recognized cc: error: linker command failed with exit code 1 (use -v to see invocation) -Error while executing cc bn_error.lo bn_s_mp_invmod_fast.lo bn_fast_mp_montgomery0 +Error while executing cc error.lo s_mp_invmod_fast.lo fast_mp_montgomery0 gmake: *** [makefile.shared:64: libtommath.la] Error 1 \end{alltt} @@ -259,7 +259,7 @@ \section{Build Configuration} \subsection{Build Depends} In the file tommath\_class.h you will see a large list of C ``defines'' followed by a series of ``ifdefs'' which further define symbols. All of the symbols (technically they're macros $\ldots$) represent a given C source -file. For instance, BN\_MP\_ADD\_C represents the file ``bn\_mp\_add.c''. When a define has been enabled the +file. For instance, MP\_ADD\_C represents the file ``bn\_mp\_add.c''. When a define has been enabled the function in the respective file will be compiled and linked into the library. Accordingly when the define is absent the file will not be compiled and not contribute any size to the library. @@ -275,7 +275,7 @@ \subsection{Build Tweaks} \begin{center} \begin{tabular}{|l|l|} \hline \textbf{Define} & \textbf{Purpose} \\ -\hline BN\_MP\_DIV\_SMALL & Enables a slower, smaller and equally \\ +\hline MP\_DIV\_SMALL & Enables a slower, smaller and equally \\ & functional mp\_div() function \\ \hline \end{tabular} @@ -293,20 +293,20 @@ \subsubsection{Moduli Related} \begin{center} \begin{tabular}{|l|l|} \hline \textbf{Restriction} & \textbf{Undefine} \\ -\hline Exponentiation with odd moduli only & BN\_S\_MP\_EXPTMOD\_C \\ - & BN\_MP\_REDUCE\_C \\ - & BN\_MP\_REDUCE\_SETUP\_C \\ - & BN\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ - & BN\_FAST\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ +\hline Exponentiation with odd moduli only & S\_MP\_EXPTMOD\_C \\ + & MP\_REDUCE\_C \\ + & MP\_REDUCE\_SETUP\_C \\ + & S\_MP\_MUL\_HIGH\_DIGS\_C \\ + & FAST\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ \hline Exponentiation with random odd moduli & (The above plus the following) \\ - & BN\_MP\_REDUCE\_2K\_C \\ - & BN\_MP\_REDUCE\_2K\_SETUP\_C \\ - & BN\_MP\_REDUCE\_IS\_2K\_C \\ - & BN\_MP\_DR\_IS\_MODULUS\_C \\ - & BN\_MP\_DR\_REDUCE\_C \\ - & BN\_MP\_DR\_SETUP\_C \\ -\hline Modular inverse odd moduli only & BN\_MP\_INVMOD\_SLOW\_C \\ -\hline Modular inverse (both, smaller/slower) & BN\_FAST\_MP\_INVMOD\_C \\ + & MP\_REDUCE\_2K\_C \\ + & MP\_REDUCE\_2K\_SETUP\_C \\ + & MP\_REDUCE\_IS\_2K\_C \\ + & MP\_DR\_IS\_MODULUS\_C \\ + & MP\_DR\_REDUCE\_C \\ + & MP\_DR\_SETUP\_C \\ +\hline Modular inverse odd moduli only & MP\_INVMOD\_SLOW\_C \\ +\hline Modular inverse (both, smaller/slower) & FAST\_MP\_INVMOD\_C \\ \hline \end{tabular} \end{center} @@ -317,14 +317,14 @@ \subsubsection{Operand Size Related} \begin{center} \begin{tabular}{|l|l|} \hline \textbf{Restriction} & \textbf{Undefine} \\ -\hline Moduli $\le 2560$ bits & BN\_MP\_MONTGOMERY\_REDUCE\_C \\ - & BN\_S\_MP\_MUL\_DIGS\_C \\ - & BN\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ - & BN\_S\_MP\_SQR\_C \\ -\hline Polynomial Schmolynomial & BN\_MP\_KARATSUBA\_MUL\_C \\ - & BN\_MP\_KARATSUBA\_SQR\_C \\ - & BN\_MP\_TOOM\_MUL\_C \\ - & BN\_MP\_TOOM\_SQR\_C \\ +\hline Moduli $\le 2560$ bits & MP\_MONTGOMERY\_REDUCE\_C \\ + & S\_MP\_MUL\_DIGS\_C \\ + & S\_MP\_MUL\_HIGH\_DIGS\_C \\ + & S\_MP\_SQR\_C \\ +\hline Polynomial Schmolynomial & MP\_KARATSUBA\_MUL\_C \\ + & MP\_KARATSUBA\_SQR\_C \\ + & MP\_TOOM\_MUL\_C \\ + & MP\_TOOM\_SQR\_C \\ \hline \end{tabular} diff --git a/etc/tune.c b/etc/tune.c index 057e372fc..389ce2f69 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -67,39 +67,39 @@ static uint64_t s_time_mul(int size) if ((e = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_rand(&a, size * s_offset)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_rand(&b, size)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } s_timer_start(); for (x = 0; x < s_number_of_test_loops; x++) { if ((e = mp_mul(&a,&b,&c)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if (s_check_result == 1) { if ((e = s_mp_mul(&a,&b,&d)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&c, &d) != MP_EQ) { /* Time of 0 cannot happen (famous last words?) */ t1 = 0uLL; - goto LTM_ERR; + goto LBL_ERR; } } } t1 = s_timer_stop(); -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, &d, NULL); return t1; } @@ -112,34 +112,34 @@ static uint64_t s_time_sqr(int size) if ((e = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if ((e = mp_rand(&a, size)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } s_timer_start(); for (x = 0; x < s_number_of_test_loops; x++) { if ((e = mp_sqr(&a,&b)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if (s_check_result == 1) { if ((e = s_mp_sqr(&a,&c)) != MP_OKAY) { t1 = UINT64_MAX; - goto LTM_ERR; + goto LBL_ERR; } if (mp_cmp(&c, &b) != MP_EQ) { t1 = 0uLL; - goto LTM_ERR; + goto LBL_ERR; } } } t1 = s_timer_stop(); -LTM_ERR: +LBL_ERR: mp_clear_multi(&a, &b, &c, NULL); return t1; } diff --git a/gen.pl b/gen.pl index 332994d5c..4db24b547 100644 --- a/gen.pl +++ b/gen.pl @@ -7,7 +7,7 @@ use warnings; open(my $out, '>', 'mpi.c') or die "Couldn't open mpi.c for writing: $!"; -foreach my $filename (glob 'bn*.c') { +foreach my $filename (glob '*mp_*.c') { open(my $src, '<', $filename) or die "Couldn't open $filename for reading: $!"; print {$out} "/* Start: $filename */\n"; print {$out} $_ while <$src>; diff --git a/helper.pl b/helper.pl index 03b081ccc..a519619ff 100755 --- a/helper.pl +++ b/helper.pl @@ -270,7 +270,7 @@ sub draw_func my ($deplist, $depmap, $out, $indent, $funcslist) = @_; my @funcs = split ',', $funcslist; # try this if you want to have a look at a minimized version of the callgraph without all the trivial functions - #if ($deplist =~ /$funcs[0]/ || $funcs[0] =~ /BN_MP_(ADD|SUB|CLEAR|CLEAR_\S+|DIV|MUL|COPY|ZERO|GROW|CLAMP|INIT|INIT_\S+|SET|ABS|CMP|CMP_D|EXCH)_C/) { + #if ($deplist =~ /$funcs[0]/ || $funcs[0] =~ /MP_(ADD|SUB|CLEAR|CLEAR_\S+|DIV|MUL|COPY|ZERO|GROW|CLAMP|INIT|INIT_\S+|SET|ABS|CMP|CMP_D|EXCH)_C/) { if ($deplist =~ /$funcs[0]/) { return $deplist; } else { @@ -309,7 +309,7 @@ sub update_dep #if defined(LTM_ALL) EOS - foreach my $filename (glob 'bn*.c') { + foreach my $filename (glob '*mp_*.c') { my $define = $filename; print "Processing $filename\n"; @@ -356,7 +356,7 @@ sub update_dep # now do classes my %depmap; - foreach my $filename (glob 'bn*.c') { + foreach my $filename (glob '*mp_*.c') { my $content; my $cc = $ENV{'CC'} || 'gcc'; $content = `$cc -E -x c -DLTM_ALL $filename`; @@ -379,7 +379,7 @@ sub update_dep my $a = $&; next if $a eq "mp_err"; $a =~ tr/[a-z]/[A-Z]/; - $a = 'BN_' . $a . '_C'; + $a = $a . '_C'; push @deps, $a; } } diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 7e5192994..ccbd1cc7f 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -313,627 +313,627 @@ is not affected -* git log --follow can be used to show log across renames' - -./helper.pl -a diff --git a/bn_mp_2expt.c b/mp_2expt.c similarity index 97% rename from bn_mp_2expt.c rename to mp_2expt.c index 0ae3df1bf..66e857478 100644 --- a/bn_mp_2expt.c +++ b/mp_2expt.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_2EXPT_C +#ifdef MP_2EXPT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_abs.c b/mp_abs.c similarity index 96% rename from bn_mp_abs.c rename to mp_abs.c index 00900bbdd..4ad1a4a90 100644 --- a/bn_mp_abs.c +++ b/mp_abs.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ABS_C +#ifdef MP_ABS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_add.c b/mp_add.c similarity index 98% rename from bn_mp_add.c rename to mp_add.c index dfa78de50..c78614b6f 100644 --- a/bn_mp_add.c +++ b/mp_add.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ADD_C +#ifdef MP_ADD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_add_d.c b/mp_add_d.c similarity index 98% rename from bn_mp_add_d.c rename to mp_add_d.c index f30157561..07242c6a8 100644 --- a/bn_mp_add_d.c +++ b/mp_add_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ADD_D_C +#ifdef MP_ADD_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_addmod.c b/mp_addmod.c similarity index 95% rename from bn_mp_addmod.c rename to mp_addmod.c index 1dcfb678c..beda87258 100644 --- a/bn_mp_addmod.c +++ b/mp_addmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ADDMOD_C +#ifdef MP_ADDMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_and.c b/mp_and.c similarity index 98% rename from bn_mp_and.c rename to mp_and.c index c259f8dec..92e6aed4a 100644 --- a/bn_mp_and.c +++ b/mp_and.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_AND_C +#ifdef MP_AND_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_clamp.c b/mp_clamp.c similarity index 96% rename from bn_mp_clamp.c rename to mp_clamp.c index ac23bfd3f..14c18148c 100644 --- a/bn_mp_clamp.c +++ b/mp_clamp.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CLAMP_C +#ifdef MP_CLAMP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_clear.c b/mp_clear.c similarity index 95% rename from bn_mp_clear.c rename to mp_clear.c index ff78324d9..55d76b298 100644 --- a/bn_mp_clear.c +++ b/mp_clear.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CLEAR_C +#ifdef MP_CLEAR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_clear_multi.c b/mp_clear_multi.c similarity index 93% rename from bn_mp_clear_multi.c rename to mp_clear_multi.c index 794e45fa5..74406c7a0 100644 --- a/bn_mp_clear_multi.c +++ b/mp_clear_multi.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CLEAR_MULTI_C +#ifdef MP_CLEAR_MULTI_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_cmp.c b/mp_cmp.c similarity index 96% rename from bn_mp_cmp.c rename to mp_cmp.c index ced484096..a9bd910a9 100644 --- a/bn_mp_cmp.c +++ b/mp_cmp.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CMP_C +#ifdef MP_CMP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_cmp_d.c b/mp_cmp_d.c similarity index 96% rename from bn_mp_cmp_d.c rename to mp_cmp_d.c index 5a8337b5b..03d8e2c6f 100644 --- a/bn_mp_cmp_d.c +++ b/mp_cmp_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CMP_D_C +#ifdef MP_CMP_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_cmp_mag.c b/mp_cmp_mag.c similarity index 97% rename from bn_mp_cmp_mag.c rename to mp_cmp_mag.c index f144ea9e6..b3a7b040f 100644 --- a/bn_mp_cmp_mag.c +++ b/mp_cmp_mag.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CMP_MAG_C +#ifdef MP_CMP_MAG_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_cnt_lsb.c b/mp_cnt_lsb.c similarity index 97% rename from bn_mp_cnt_lsb.c rename to mp_cnt_lsb.c index 4b2d206eb..a2cd5f892 100644 --- a/bn_mp_cnt_lsb.c +++ b/mp_cnt_lsb.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_CNT_LSB_C +#ifdef MP_CNT_LSB_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_complement.c b/mp_complement.c similarity index 92% rename from bn_mp_complement.c rename to mp_complement.c index fef1423c5..ad6bed344 100644 --- a/bn_mp_complement.c +++ b/mp_complement.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_COMPLEMENT_C +#ifdef MP_COMPLEMENT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_copy.c b/mp_copy.c similarity index 97% rename from bn_mp_copy.c rename to mp_copy.c index e72fcf6d5..a7ac34af3 100644 --- a/bn_mp_copy.c +++ b/mp_copy.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_COPY_C +#ifdef MP_COPY_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_count_bits.c b/mp_count_bits.c similarity index 95% rename from bn_mp_count_bits.c rename to mp_count_bits.c index b7c2cad10..76257c890 100644 --- a/bn_mp_count_bits.c +++ b/mp_count_bits.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_COUNT_BITS_C +#ifdef MP_COUNT_BITS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_cutoffs.c b/mp_cutoffs.c similarity index 95% rename from bn_cutoffs.c rename to mp_cutoffs.c index b02ab7161..5593b553f 100644 --- a/bn_cutoffs.c +++ b/mp_cutoffs.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_CUTOFFS_C +#ifdef MP_CUTOFFS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_decr.c b/mp_decr.c similarity index 97% rename from bn_mp_decr.c rename to mp_decr.c index c6a1572c6..55516cf13 100644 --- a/bn_mp_decr.c +++ b/mp_decr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DECR_C +#ifdef MP_DECR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_div.c b/mp_div.c similarity index 99% rename from bn_mp_div.c rename to mp_div.c index 71de55bea..1c87005ac 100644 --- a/bn_mp_div.c +++ b/mp_div.c @@ -1,9 +1,9 @@ #include "tommath_private.h" -#ifdef BN_MP_DIV_C +#ifdef MP_DIV_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#ifdef BN_MP_DIV_SMALL +#ifdef MP_DIV_SMALL /* slower bit-bang division... also smaller */ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) diff --git a/bn_mp_div_2.c b/mp_div_2.c similarity index 97% rename from bn_mp_div_2.c rename to mp_div_2.c index f56ea8199..60bd63d6e 100644 --- a/bn_mp_div_2.c +++ b/mp_div_2.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DIV_2_C +#ifdef MP_DIV_2_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_div_2d.c b/mp_div_2d.c similarity index 98% rename from bn_mp_div_2d.c rename to mp_div_2d.c index c47d5ce35..9b396acdc 100644 --- a/bn_mp_div_2d.c +++ b/mp_div_2d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DIV_2D_C +#ifdef MP_DIV_2D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_div_3.c b/mp_div_3.c similarity index 98% rename from bn_mp_div_3.c rename to mp_div_3.c index 3a23fdff2..5789b2d62 100644 --- a/bn_mp_div_3.c +++ b/mp_div_3.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DIV_3_C +#ifdef MP_DIV_3_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_div_d.c b/mp_div_d.c similarity index 98% rename from bn_mp_div_d.c rename to mp_div_d.c index b9d718bb0..331b28593 100644 --- a/bn_mp_div_d.c +++ b/mp_div_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DIV_D_C +#ifdef MP_DIV_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_dr_is_modulus.c b/mp_dr_is_modulus.c similarity index 95% rename from bn_mp_dr_is_modulus.c rename to mp_dr_is_modulus.c index 83760eacc..eed5e5f89 100644 --- a/bn_mp_dr_is_modulus.c +++ b/mp_dr_is_modulus.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DR_IS_MODULUS_C +#ifdef MP_DR_IS_MODULUS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_dr_reduce.c b/mp_dr_reduce.c similarity index 98% rename from bn_mp_dr_reduce.c rename to mp_dr_reduce.c index ffc33a6b5..fba0e2110 100644 --- a/bn_mp_dr_reduce.c +++ b/mp_dr_reduce.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DR_REDUCE_C +#ifdef MP_DR_REDUCE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_dr_setup.c b/mp_dr_setup.c similarity index 94% rename from bn_mp_dr_setup.c rename to mp_dr_setup.c index 32d5f3890..c5bb359a3 100644 --- a/bn_mp_dr_setup.c +++ b/mp_dr_setup.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_DR_SETUP_C +#ifdef MP_DR_SETUP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_error_to_string.c b/mp_error_to_string.c similarity index 94% rename from bn_mp_error_to_string.c rename to mp_error_to_string.c index e936ec170..a6f6fc78e 100644 --- a/bn_mp_error_to_string.c +++ b/mp_error_to_string.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ERROR_TO_STRING_C +#ifdef MP_ERROR_TO_STRING_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_exch.c b/mp_exch.c similarity index 94% rename from bn_mp_exch.c rename to mp_exch.c index 552094c6b..7bc4ee706 100644 --- a/bn_mp_exch.c +++ b/mp_exch.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_EXCH_C +#ifdef MP_EXCH_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_expt_u32.c b/mp_expt_u32.c similarity index 97% rename from bn_mp_expt_u32.c rename to mp_expt_u32.c index 2ab67ba53..a580fbf0c 100644 --- a/bn_mp_expt_u32.c +++ b/mp_expt_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_EXPT_U32_C +#ifdef MP_EXPT_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_exptmod.c b/mp_exptmod.c similarity index 98% rename from bn_mp_exptmod.c rename to mp_exptmod.c index 5f811ebd8..fcc894bd9 100644 --- a/bn_mp_exptmod.c +++ b/mp_exptmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_EXPTMOD_C +#ifdef MP_EXPTMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_exteuclid.c b/mp_exteuclid.c similarity index 99% rename from bn_mp_exteuclid.c rename to mp_exteuclid.c index faf47ba6a..5b850dab2 100644 --- a/bn_mp_exteuclid.c +++ b/mp_exteuclid.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_EXTEUCLID_C +#ifdef MP_EXTEUCLID_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_fread.c b/mp_fread.c similarity index 98% rename from bn_mp_fread.c rename to mp_fread.c index 1e5ecf79c..34dd1e79a 100644 --- a/bn_mp_fread.c +++ b/mp_fread.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_FREAD_C +#ifdef MP_FREAD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_from_sbin.c b/mp_from_sbin.c similarity index 96% rename from bn_mp_from_sbin.c rename to mp_from_sbin.c index 20e45971e..4335d8860 100644 --- a/bn_mp_from_sbin.c +++ b/mp_from_sbin.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_FROM_SBIN_C +#ifdef MP_FROM_SBIN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_from_ubin.c b/mp_from_ubin.c similarity index 96% rename from bn_mp_from_ubin.c rename to mp_from_ubin.c index f6d6e2aff..315ff080e 100644 --- a/bn_mp_from_ubin.c +++ b/mp_from_ubin.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_FROM_UBIN_C +#ifdef MP_FROM_UBIN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_fwrite.c b/mp_fwrite.c similarity index 97% rename from bn_mp_fwrite.c rename to mp_fwrite.c index abe2e6717..f9d3ab04d 100644 --- a/bn_mp_fwrite.c +++ b/mp_fwrite.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_FWRITE_C +#ifdef MP_FWRITE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_gcd.c b/mp_gcd.c similarity index 99% rename from bn_mp_gcd.c rename to mp_gcd.c index 53029baf3..79b6749d6 100644 --- a/bn_mp_gcd.c +++ b/mp_gcd.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GCD_C +#ifdef MP_GCD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_double.c b/mp_get_double.c similarity index 94% rename from bn_mp_get_double.c rename to mp_get_double.c index c9b1b19f4..122b71b03 100644 --- a/bn_mp_get_double.c +++ b/mp_get_double.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_DOUBLE_C +#ifdef MP_GET_DOUBLE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_i32.c b/mp_get_i32.c similarity index 90% rename from bn_mp_get_i32.c rename to mp_get_i32.c index 030b657a3..6b3b6addf 100644 --- a/bn_mp_get_i32.c +++ b/mp_get_i32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_I32_C +#ifdef MP_GET_I32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_i64.c b/mp_get_i64.c similarity index 90% rename from bn_mp_get_i64.c rename to mp_get_i64.c index 969c8d23c..8d38a1f25 100644 --- a/bn_mp_get_i64.c +++ b/mp_get_i64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_I64_C +#ifdef MP_GET_I64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_l.c b/mp_get_l.c similarity index 90% rename from bn_mp_get_l.c rename to mp_get_l.c index 55d78ec03..3a1a2f7bc 100644 --- a/bn_mp_get_l.c +++ b/mp_get_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_L_C +#ifdef MP_GET_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_ll.c b/mp_get_ll.c similarity index 90% rename from bn_mp_get_ll.c rename to mp_get_ll.c index 268753490..d31457df7 100644 --- a/bn_mp_get_ll.c +++ b/mp_get_ll.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_LL_C +#ifdef MP_GET_LL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_mag_u32.c b/mp_get_mag_u32.c similarity index 87% rename from bn_mp_get_mag_u32.c rename to mp_get_mag_u32.c index d77189be6..acddc5872 100644 --- a/bn_mp_get_mag_u32.c +++ b/mp_get_mag_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_MAG_U32_C +#ifdef MP_GET_MAG_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_mag_u64.c b/mp_get_mag_u64.c similarity index 87% rename from bn_mp_get_mag_u64.c rename to mp_get_mag_u64.c index 36dd73f62..f75463929 100644 --- a/bn_mp_get_mag_u64.c +++ b/mp_get_mag_u64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_MAG_U64_C +#ifdef MP_GET_MAG_U64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_mag_ul.c b/mp_get_mag_ul.c similarity index 87% rename from bn_mp_get_mag_ul.c rename to mp_get_mag_ul.c index e8819aef6..5c6043052 100644 --- a/bn_mp_get_mag_ul.c +++ b/mp_get_mag_ul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_MAG_UL_C +#ifdef MP_GET_MAG_UL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_get_mag_ull.c b/mp_get_mag_ull.c similarity index 87% rename from bn_mp_get_mag_ull.c rename to mp_get_mag_ull.c index 63a27412c..fea1ab117 100644 --- a/bn_mp_get_mag_ull.c +++ b/mp_get_mag_ull.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GET_MAG_ULL_C +#ifdef MP_GET_MAG_ULL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_grow.c b/mp_grow.c similarity index 98% rename from bn_mp_grow.c rename to mp_grow.c index 9e904c547..3354e5964 100644 --- a/bn_mp_grow.c +++ b/mp_grow.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_GROW_C +#ifdef MP_GROW_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_incr.c b/mp_incr.c similarity index 97% rename from bn_mp_incr.c rename to mp_incr.c index 7695ac73c..12dc20bbd 100644 --- a/bn_mp_incr.c +++ b/mp_incr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INCR_C +#ifdef MP_INCR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init.c b/mp_init.c similarity index 96% rename from bn_mp_init.c rename to mp_init.c index 2eb792409..9b8228262 100644 --- a/bn_mp_init.c +++ b/mp_init.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_C +#ifdef MP_INIT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_copy.c b/mp_init_copy.c similarity index 94% rename from bn_mp_init_copy.c rename to mp_init_copy.c index 1888203d2..4d0773bad 100644 --- a/bn_mp_init_copy.c +++ b/mp_init_copy.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_COPY_C +#ifdef MP_INIT_COPY_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_i32.c b/mp_init_i32.c similarity index 88% rename from bn_mp_init_i32.c rename to mp_init_i32.c index bc4de8d50..434788f8c 100644 --- a/bn_mp_init_i32.c +++ b/mp_init_i32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_I32_C +#ifdef MP_INIT_I32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_i64.c b/mp_init_i64.c similarity index 88% rename from bn_mp_init_i64.c rename to mp_init_i64.c index 2fa1516eb..718567809 100644 --- a/bn_mp_init_i64.c +++ b/mp_init_i64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_I64_C +#ifdef MP_INIT_I64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_l.c b/mp_init_l.c similarity index 89% rename from bn_mp_init_l.c rename to mp_init_l.c index bc380b539..16be8f63f 100644 --- a/bn_mp_init_l.c +++ b/mp_init_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_L_C +#ifdef MP_INIT_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_ll.c b/mp_init_ll.c similarity index 89% rename from bn_mp_init_ll.c rename to mp_init_ll.c index dc7c4a44e..d8b44a6c3 100644 --- a/bn_mp_init_ll.c +++ b/mp_init_ll.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_LL_C +#ifdef MP_INIT_LL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_multi.c b/mp_init_multi.c similarity index 97% rename from bn_mp_init_multi.c rename to mp_init_multi.c index d8390b5a0..6567cf1f2 100644 --- a/bn_mp_init_multi.c +++ b/mp_init_multi.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_MULTI_C +#ifdef MP_INIT_MULTI_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_set.c b/mp_init_set.c similarity index 93% rename from bn_mp_init_set.c rename to mp_init_set.c index 5068f2bf6..e1f2ee94d 100644 --- a/bn_mp_init_set.c +++ b/mp_init_set.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_SET_C +#ifdef MP_INIT_SET_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_size.c b/mp_init_size.c similarity index 95% rename from bn_mp_init_size.c rename to mp_init_size.c index d62268721..9aa98b970 100644 --- a/bn_mp_init_size.c +++ b/mp_init_size.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_SIZE_C +#ifdef MP_INIT_SIZE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_u32.c b/mp_init_u32.c similarity index 88% rename from bn_mp_init_u32.c rename to mp_init_u32.c index 015d89b90..d5a2b8f82 100644 --- a/bn_mp_init_u32.c +++ b/mp_init_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_U32_C +#ifdef MP_INIT_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_u64.c b/mp_init_u64.c similarity index 88% rename from bn_mp_init_u64.c rename to mp_init_u64.c index 2b35f7ef8..ca7508405 100644 --- a/bn_mp_init_u64.c +++ b/mp_init_u64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_U64_C +#ifdef MP_INIT_U64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_ul.c b/mp_init_ul.c similarity index 89% rename from bn_mp_init_ul.c rename to mp_init_ul.c index 5164f7287..21ca3be51 100644 --- a/bn_mp_init_ul.c +++ b/mp_init_ul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_UL_C +#ifdef MP_INIT_UL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_init_ull.c b/mp_init_ull.c similarity index 89% rename from bn_mp_init_ull.c rename to mp_init_ull.c index 84110c002..ef66c6a4b 100644 --- a/bn_mp_init_ull.c +++ b/mp_init_ull.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INIT_ULL_C +#ifdef MP_INIT_ULL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_invmod.c b/mp_invmod.c similarity index 96% rename from bn_mp_invmod.c rename to mp_invmod.c index 7b35a2431..b797d4eb8 100644 --- a/bn_mp_invmod.c +++ b/mp_invmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_INVMOD_C +#ifdef MP_INVMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_is_square.c b/mp_is_square.c similarity index 99% rename from bn_mp_is_square.c rename to mp_is_square.c index 69e77a21a..c2428f8da 100644 --- a/bn_mp_is_square.c +++ b/mp_is_square.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_IS_SQUARE_C +#ifdef MP_IS_SQUARE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_iseven.c b/mp_iseven.c similarity index 91% rename from bn_mp_iseven.c rename to mp_iseven.c index 5cb962284..4ebc9afc8 100644 --- a/bn_mp_iseven.c +++ b/mp_iseven.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ISEVEN_C +#ifdef MP_ISEVEN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_isodd.c b/mp_isodd.c similarity index 91% rename from bn_mp_isodd.c rename to mp_isodd.c index bf17646d7..f8a3e0e5b 100644 --- a/bn_mp_isodd.c +++ b/mp_isodd.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ISODD_C +#ifdef MP_ISODD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_kronecker.c b/mp_kronecker.c similarity index 99% rename from bn_mp_kronecker.c rename to mp_kronecker.c index 525a82034..3111a7884 100644 --- a/bn_mp_kronecker.c +++ b/mp_kronecker.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_KRONECKER_C +#ifdef MP_KRONECKER_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_lcm.c b/mp_lcm.c similarity index 98% rename from bn_mp_lcm.c rename to mp_lcm.c index c32b269e6..f2044f0e5 100644 --- a/bn_mp_lcm.c +++ b/mp_lcm.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_LCM_C +#ifdef MP_LCM_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_log_u32.c b/mp_log_u32.c similarity index 99% rename from bn_mp_log_u32.c rename to mp_log_u32.c index f7bca01de..fb9dd5a0f 100644 --- a/bn_mp_log_u32.c +++ b/mp_log_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_LOG_U32_C +#ifdef MP_LOG_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_lshd.c b/mp_lshd.c similarity index 92% rename from bn_mp_lshd.c rename to mp_lshd.c index 82345809c..eb9a5c33b 100644 --- a/bn_mp_lshd.c +++ b/mp_lshd.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_LSHD_C +#ifdef MP_LSHD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -37,7 +37,7 @@ mp_err mp_lshd(mp_int *a, int b) /* much like mp_rshd this is implemented using a sliding window * except the window goes the otherway around. Copying from - * the bottom to the top. see bn_mp_rshd.c for more info. + * the bottom to the top. see mp_rshd.c for more info. */ for (x = a->used - 1; x >= b; x--) { *top-- = *bottom--; diff --git a/bn_mp_mod.c b/mp_mod.c similarity index 97% rename from bn_mp_mod.c rename to mp_mod.c index 8fbfe08dc..349fecebb 100644 --- a/bn_mp_mod.c +++ b/mp_mod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MOD_C +#ifdef MP_MOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mod_2d.c b/mp_mod_2d.c similarity index 97% rename from bn_mp_mod_2d.c rename to mp_mod_2d.c index 5bf57a1a3..651c79a6c 100644 --- a/bn_mp_mod_2d.c +++ b/mp_mod_2d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MOD_2D_C +#ifdef MP_MOD_2D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mod_d.c b/mp_mod_d.c similarity index 92% rename from bn_mp_mod_d.c rename to mp_mod_d.c index 0b6c12a9e..3f7e1917f 100644 --- a/bn_mp_mod_d.c +++ b/mp_mod_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MOD_D_C +#ifdef MP_MOD_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_montgomery_calc_normalization.c b/mp_montgomery_calc_normalization.c similarity index 96% rename from bn_mp_montgomery_calc_normalization.c rename to mp_montgomery_calc_normalization.c index 837978925..0d0d5c482 100644 --- a/bn_mp_montgomery_calc_normalization.c +++ b/mp_montgomery_calc_normalization.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MONTGOMERY_CALC_NORMALIZATION_C +#ifdef MP_MONTGOMERY_CALC_NORMALIZATION_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_montgomery_reduce.c b/mp_montgomery_reduce.c similarity index 98% rename from bn_mp_montgomery_reduce.c rename to mp_montgomery_reduce.c index ffe8341ee..a872aba6b 100644 --- a/bn_mp_montgomery_reduce.c +++ b/mp_montgomery_reduce.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MONTGOMERY_REDUCE_C +#ifdef MP_MONTGOMERY_REDUCE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_montgomery_setup.c b/mp_montgomery_setup.c similarity index 97% rename from bn_mp_montgomery_setup.c rename to mp_montgomery_setup.c index ad245eb8c..de57dc342 100644 --- a/bn_mp_montgomery_setup.c +++ b/mp_montgomery_setup.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MONTGOMERY_SETUP_C +#ifdef MP_MONTGOMERY_SETUP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mul.c b/mp_mul.c similarity index 99% rename from bn_mp_mul.c rename to mp_mul.c index 561913a5e..bb0b65215 100644 --- a/bn_mp_mul.c +++ b/mp_mul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MUL_C +#ifdef MP_MUL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mul_2.c b/mp_mul_2.c similarity index 98% rename from bn_mp_mul_2.c rename to mp_mul_2.c index bc0691a0d..cd5589dd2 100644 --- a/bn_mp_mul_2.c +++ b/mp_mul_2.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MUL_2_C +#ifdef MP_MUL_2_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mul_2d.c b/mp_mul_2d.c similarity index 98% rename from bn_mp_mul_2d.c rename to mp_mul_2d.c index 87354de20..1ba53a0fc 100644 --- a/bn_mp_mul_2d.c +++ b/mp_mul_2d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MUL_2D_C +#ifdef MP_MUL_2D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mul_d.c b/mp_mul_d.c similarity index 98% rename from bn_mp_mul_d.c rename to mp_mul_d.c index b56dfa3c9..399dc7b47 100644 --- a/bn_mp_mul_d.c +++ b/mp_mul_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MUL_D_C +#ifdef MP_MUL_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_mulmod.c b/mp_mulmod.c similarity index 95% rename from bn_mp_mulmod.c rename to mp_mulmod.c index 160d1626a..55b635b79 100644 --- a/bn_mp_mulmod.c +++ b/mp_mulmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_MULMOD_C +#ifdef MP_MULMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_neg.c b/mp_neg.c similarity index 96% rename from bn_mp_neg.c rename to mp_neg.c index 264d90097..01fb27635 100644 --- a/bn_mp_neg.c +++ b/mp_neg.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_NEG_C +#ifdef MP_NEG_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_or.c b/mp_or.c similarity index 98% rename from bn_mp_or.c rename to mp_or.c index cdacbfbe5..7fa13756e 100644 --- a/bn_mp_or.c +++ b/mp_or.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_OR_C +#ifdef MP_OR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_pack.c b/mp_pack.c similarity index 98% rename from bn_mp_pack.c rename to mp_pack.c index 6e00b6fc6..ec0f62f69 100644 --- a/bn_mp_pack.c +++ b/mp_pack.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PACK_C +#ifdef MP_PACK_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_pack_count.c b/mp_pack_count.c similarity index 93% rename from bn_mp_pack_count.c rename to mp_pack_count.c index dfecdf98f..aa682ba6c 100644 --- a/bn_mp_pack_count.c +++ b/mp_pack_count.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PACK_COUNT_C +#ifdef MP_PACK_COUNT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_fermat.c b/mp_prime_fermat.c similarity index 97% rename from bn_mp_prime_fermat.c rename to mp_prime_fermat.c index af3e884bb..c6bc720f8 100644 --- a/bn_mp_prime_fermat.c +++ b/mp_prime_fermat.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_FERMAT_C +#ifdef MP_PRIME_FERMAT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c similarity index 97% rename from bn_mp_prime_frobenius_underwood.c rename to mp_prime_frobenius_underwood.c index 618aa7c01..ced0583a2 100644 --- a/bn_mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -1,11 +1,11 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_FROBENIUS_UNDERWOOD_C +#ifdef MP_PRIME_FROBENIUS_UNDERWOOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* - * See file bn_mp_prime_is_prime.c or the documentation in doc/bn.tex for the details + * See file mp_prime_is_prime.c or the documentation in doc/bn.tex for the details */ #ifndef LTM_USE_ONLY_MR diff --git a/bn_mp_prime_is_prime.c b/mp_prime_is_prime.c similarity index 99% rename from bn_mp_prime_is_prime.c rename to mp_prime_is_prime.c index 86edcb692..75d44c5f2 100644 --- a/bn_mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_IS_PRIME_C +#ifdef MP_PRIME_IS_PRIME_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_miller_rabin.c b/mp_prime_miller_rabin.c similarity index 98% rename from bn_mp_prime_miller_rabin.c rename to mp_prime_miller_rabin.c index 96470dba7..f6d698b9c 100644 --- a/bn_mp_prime_miller_rabin.c +++ b/mp_prime_miller_rabin.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_MILLER_RABIN_C +#ifdef MP_PRIME_MILLER_RABIN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_next_prime.c b/mp_prime_next_prime.c similarity index 99% rename from bn_mp_prime_next_prime.c rename to mp_prime_next_prime.c index de27eabc7..3e2571a72 100644 --- a/bn_mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_NEXT_PRIME_C +#ifdef MP_PRIME_NEXT_PRIME_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_rabin_miller_trials.c b/mp_prime_rabin_miller_trials.c similarity index 97% rename from bn_mp_prime_rabin_miller_trials.c rename to mp_prime_rabin_miller_trials.c index 8bbaf6cf9..1728142c5 100644 --- a/bn_mp_prime_rabin_miller_trials.c +++ b/mp_prime_rabin_miller_trials.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_RABIN_MILLER_TRIALS_C +#ifdef MP_PRIME_RABIN_MILLER_TRIALS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_rand.c b/mp_prime_rand.c similarity index 99% rename from bn_mp_prime_rand.c rename to mp_prime_rand.c index af19d76c3..b37089b17 100644 --- a/bn_mp_prime_rand.c +++ b/mp_prime_rand.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_RAND_C +#ifdef MP_PRIME_RAND_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c similarity index 98% rename from bn_mp_prime_strong_lucas_selfridge.c rename to mp_prime_strong_lucas_selfridge.c index a5ea16de6..693433627 100644 --- a/bn_mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -1,11 +1,11 @@ #include "tommath_private.h" -#ifdef BN_MP_PRIME_STRONG_LUCAS_SELFRIDGE_C +#ifdef MP_PRIME_STRONG_LUCAS_SELFRIDGE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* - * See file bn_mp_prime_is_prime.c or the documentation in doc/bn.tex for the details + * See file mp_prime_is_prime.c or the documentation in doc/bn.tex for the details */ #ifndef LTM_USE_ONLY_MR diff --git a/bn_prime_tab.c b/mp_prime_tab.c similarity index 99% rename from bn_prime_tab.c rename to mp_prime_tab.c index 92a515971..24b4016f4 100644 --- a/bn_prime_tab.c +++ b/mp_prime_tab.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_PRIME_TAB_C +#ifdef MP_PRIME_TAB_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_radix_size.c b/mp_radix_size.c similarity index 96% rename from bn_mp_radix_size.c rename to mp_radix_size.c index 5ed9ab1bd..387e0ec92 100644 --- a/bn_mp_radix_size.c +++ b/mp_radix_size.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_RADIX_SIZE_C +#ifdef MP_RADIX_SIZE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_radix_smap.c b/mp_radix_smap.c similarity index 97% rename from bn_mp_radix_smap.c rename to mp_radix_smap.c index e7d7c06b6..678e806a7 100644 --- a/bn_mp_radix_smap.c +++ b/mp_radix_smap.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_RADIX_SMAP_C +#ifdef MP_RADIX_SMAP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_rand.c b/mp_rand.c similarity index 98% rename from bn_mp_rand.c rename to mp_rand.c index 7e9052c2b..df665b7ba 100644 --- a/bn_mp_rand.c +++ b/mp_rand.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_RAND_C +#ifdef MP_RAND_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_read_radix.c b/mp_read_radix.c similarity index 98% rename from bn_mp_read_radix.c rename to mp_read_radix.c index 456a387a3..dc5e16782 100644 --- a/bn_mp_read_radix.c +++ b/mp_read_radix.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_READ_RADIX_C +#ifdef MP_READ_RADIX_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce.c b/mp_reduce.c similarity index 98% rename from bn_mp_reduce.c rename to mp_reduce.c index 3c669d491..1b4435c95 100644 --- a/bn_mp_reduce.c +++ b/mp_reduce.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_C +#ifdef MP_REDUCE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_2k.c b/mp_reduce_2k.c similarity index 97% rename from bn_mp_reduce_2k.c rename to mp_reduce_2k.c index 1cea6cb21..5d3c7f90c 100644 --- a/bn_mp_reduce_2k.c +++ b/mp_reduce_2k.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_2K_C +#ifdef MP_REDUCE_2K_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_2k_l.c b/mp_reduce_2k_l.c similarity index 97% rename from bn_mp_reduce_2k_l.c rename to mp_reduce_2k_l.c index 6a9f3d31b..6328cbc7d 100644 --- a/bn_mp_reduce_2k_l.c +++ b/mp_reduce_2k_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_2K_L_C +#ifdef MP_REDUCE_2K_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_2k_setup.c b/mp_reduce_2k_setup.c similarity index 95% rename from bn_mp_reduce_2k_setup.c rename to mp_reduce_2k_setup.c index 2eaf7addf..0f3fd291e 100644 --- a/bn_mp_reduce_2k_setup.c +++ b/mp_reduce_2k_setup.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_2K_SETUP_C +#ifdef MP_REDUCE_2K_SETUP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_2k_setup_l.c b/mp_reduce_2k_setup_l.c similarity index 94% rename from bn_mp_reduce_2k_setup_l.c rename to mp_reduce_2k_setup_l.c index 4f9aa14d1..b647c9d88 100644 --- a/bn_mp_reduce_2k_setup_l.c +++ b/mp_reduce_2k_setup_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_2K_SETUP_L_C +#ifdef MP_REDUCE_2K_SETUP_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_is_2k.c b/mp_reduce_is_2k.c similarity index 96% rename from bn_mp_reduce_is_2k.c rename to mp_reduce_is_2k.c index a9f4f9f2b..ec1233861 100644 --- a/bn_mp_reduce_is_2k.c +++ b/mp_reduce_is_2k.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_IS_2K_C +#ifdef MP_REDUCE_IS_2K_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_is_2k_l.c b/mp_reduce_is_2k_l.c similarity index 95% rename from bn_mp_reduce_is_2k_l.c rename to mp_reduce_is_2k_l.c index 4bc69bef8..1aa3d4e0c 100644 --- a/bn_mp_reduce_is_2k_l.c +++ b/mp_reduce_is_2k_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_IS_2K_L_C +#ifdef MP_REDUCE_IS_2K_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_reduce_setup.c b/mp_reduce_setup.c similarity index 94% rename from bn_mp_reduce_setup.c rename to mp_reduce_setup.c index f02160fa5..e12056e1e 100644 --- a/bn_mp_reduce_setup.c +++ b/mp_reduce_setup.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_REDUCE_SETUP_C +#ifdef MP_REDUCE_SETUP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_root_u32.c b/mp_root_u32.c similarity index 99% rename from bn_mp_root_u32.c rename to mp_root_u32.c index ba65549c6..f6827493c 100644 --- a/bn_mp_root_u32.c +++ b/mp_root_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ROOT_U32_C +#ifdef MP_ROOT_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_rshd.c b/mp_rshd.c similarity index 98% rename from bn_mp_rshd.c rename to mp_rshd.c index bb8743e3b..2eabb1234 100644 --- a/bn_mp_rshd.c +++ b/mp_rshd.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_RSHD_C +#ifdef MP_RSHD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sbin_size.c b/mp_sbin_size.c similarity index 91% rename from bn_mp_sbin_size.c rename to mp_sbin_size.c index e0993d690..2f40df3e1 100644 --- a/bn_mp_sbin_size.c +++ b/mp_sbin_size.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SBIN_SIZE_C +#ifdef MP_SBIN_SIZE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set.c b/mp_set.c similarity index 94% rename from bn_mp_set.c rename to mp_set.c index 44ac6df57..0777f09d7 100644 --- a/bn_mp_set.c +++ b/mp_set.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_C +#ifdef MP_SET_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_double.c b/mp_set_double.c similarity index 97% rename from bn_mp_set_double.c rename to mp_set_double.c index a42fc70d9..f7e3b8d14 100644 --- a/bn_mp_set_double.c +++ b/mp_set_double.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_DOUBLE_C +#ifdef MP_SET_DOUBLE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_i32.c b/mp_set_i32.c similarity index 89% rename from bn_mp_set_i32.c rename to mp_set_i32.c index df4513d37..123613ecc 100644 --- a/bn_mp_set_i32.c +++ b/mp_set_i32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_I32_C +#ifdef MP_SET_I32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_i64.c b/mp_set_i64.c similarity index 89% rename from bn_mp_set_i64.c rename to mp_set_i64.c index 395103bf5..4635ca3a5 100644 --- a/bn_mp_set_i64.c +++ b/mp_set_i64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_I64_C +#ifdef MP_SET_I64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_l.c b/mp_set_l.c similarity index 90% rename from bn_mp_set_l.c rename to mp_set_l.c index 1e445fb62..411f6eb08 100644 --- a/bn_mp_set_l.c +++ b/mp_set_l.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_L_C +#ifdef MP_SET_L_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_ll.c b/mp_set_ll.c similarity index 90% rename from bn_mp_set_ll.c rename to mp_set_ll.c index 3e2324f32..343012de2 100644 --- a/bn_mp_set_ll.c +++ b/mp_set_ll.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_LL_C +#ifdef MP_SET_LL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_u32.c b/mp_set_u32.c similarity index 88% rename from bn_mp_set_u32.c rename to mp_set_u32.c index 18ba5e14c..8ff84dc22 100644 --- a/bn_mp_set_u32.c +++ b/mp_set_u32.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_U32_C +#ifdef MP_SET_U32_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_u64.c b/mp_set_u64.c similarity index 88% rename from bn_mp_set_u64.c rename to mp_set_u64.c index 88fab6c54..9acb1fefe 100644 --- a/bn_mp_set_u64.c +++ b/mp_set_u64.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_U64_C +#ifdef MP_SET_U64_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_ul.c b/mp_set_ul.c similarity index 89% rename from bn_mp_set_ul.c rename to mp_set_ul.c index adfd85c7f..baf8e186e 100644 --- a/bn_mp_set_ul.c +++ b/mp_set_ul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_UL_C +#ifdef MP_SET_UL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_set_ull.c b/mp_set_ull.c similarity index 89% rename from bn_mp_set_ull.c rename to mp_set_ull.c index 8fbc1bd2c..cd10b1cd4 100644 --- a/bn_mp_set_ull.c +++ b/mp_set_ull.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SET_ULL_C +#ifdef MP_SET_ULL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_shrink.c b/mp_shrink.c similarity index 96% rename from bn_mp_shrink.c rename to mp_shrink.c index cf27ed9ec..6c3c95ba4 100644 --- a/bn_mp_shrink.c +++ b/mp_shrink.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SHRINK_C +#ifdef MP_SHRINK_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_signed_rsh.c b/mp_signed_rsh.c similarity index 95% rename from bn_mp_signed_rsh.c rename to mp_signed_rsh.c index 8d8d8414d..c56dfba6a 100644 --- a/bn_mp_signed_rsh.c +++ b/mp_signed_rsh.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SIGNED_RSH_C +#ifdef MP_SIGNED_RSH_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sqr.c b/mp_sqr.c similarity index 97% rename from bn_mp_sqr.c rename to mp_sqr.c index e0d0a73e4..e38130b64 100644 --- a/bn_mp_sqr.c +++ b/mp_sqr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SQR_C +#ifdef MP_SQR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sqrmod.c b/mp_sqrmod.c similarity index 95% rename from bn_mp_sqrmod.c rename to mp_sqrmod.c index 626ea2c29..f1a92eff4 100644 --- a/bn_mp_sqrmod.c +++ b/mp_sqrmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SQRMOD_C +#ifdef MP_SQRMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sqrt.c b/mp_sqrt.c similarity index 98% rename from bn_mp_sqrt.c rename to mp_sqrt.c index 82d682467..283986834 100644 --- a/bn_mp_sqrt.c +++ b/mp_sqrt.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SQRT_C +#ifdef MP_SQRT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c similarity index 99% rename from bn_mp_sqrtmod_prime.c rename to mp_sqrtmod_prime.c index a833ed7c1..bf72005b3 100644 --- a/bn_mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SQRTMOD_PRIME_C +#ifdef MP_SQRTMOD_PRIME_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sub.c b/mp_sub.c similarity index 98% rename from bn_mp_sub.c rename to mp_sub.c index c1ea39e11..c859026f5 100644 --- a/bn_mp_sub.c +++ b/mp_sub.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SUB_C +#ifdef MP_SUB_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_sub_d.c b/mp_sub_d.c similarity index 98% rename from bn_mp_sub_d.c rename to mp_sub_d.c index 3ebf9b485..16c61658a 100644 --- a/bn_mp_sub_d.c +++ b/mp_sub_d.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SUB_D_C +#ifdef MP_SUB_D_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_submod.c b/mp_submod.c similarity index 95% rename from bn_mp_submod.c rename to mp_submod.c index 5ebd37498..c5dc40155 100644 --- a/bn_mp_submod.c +++ b/mp_submod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_SUBMOD_C +#ifdef MP_SUBMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_to_radix.c b/mp_to_radix.c similarity index 98% rename from bn_mp_to_radix.c rename to mp_to_radix.c index 18cb50464..95def74d3 100644 --- a/bn_mp_to_radix.c +++ b/mp_to_radix.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_TO_RADIX_C +#ifdef MP_TO_RADIX_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_to_sbin.c b/mp_to_sbin.c similarity index 96% rename from bn_mp_to_sbin.c rename to mp_to_sbin.c index dbaf53e1f..ed21adcdb 100644 --- a/bn_mp_to_sbin.c +++ b/mp_to_sbin.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_TO_SBIN_C +#ifdef MP_TO_SBIN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_to_ubin.c b/mp_to_ubin.c similarity index 97% rename from bn_mp_to_ubin.c rename to mp_to_ubin.c index a2c6e281b..25835037d 100644 --- a/bn_mp_to_ubin.c +++ b/mp_to_ubin.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_TO_UBIN_C +#ifdef MP_TO_UBIN_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_ubin_size.c b/mp_ubin_size.c similarity index 93% rename from bn_mp_ubin_size.c rename to mp_ubin_size.c index 21230b48c..4f16404f4 100644 --- a/bn_mp_ubin_size.c +++ b/mp_ubin_size.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_UBIN_SIZE_C +#ifdef MP_UBIN_SIZE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_unpack.c b/mp_unpack.c similarity index 98% rename from bn_mp_unpack.c rename to mp_unpack.c index d4eb90e0c..5305b435a 100644 --- a/bn_mp_unpack.c +++ b/mp_unpack.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_UNPACK_C +#ifdef MP_UNPACK_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_xor.c b/mp_xor.c similarity index 98% rename from bn_mp_xor.c rename to mp_xor.c index 71e7ca187..ca2c2f1e8 100644 --- a/bn_mp_xor.c +++ b/mp_xor.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_XOR_C +#ifdef MP_XOR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_mp_zero.c b/mp_zero.c similarity index 93% rename from bn_mp_zero.c rename to mp_zero.c index 72a255efc..0b79f5008 100644 --- a/bn_mp_zero.c +++ b/mp_zero.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_MP_ZERO_C +#ifdef MP_ZERO_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_add.c b/s_mp_add.c similarity index 98% rename from bn_s_mp_add.c rename to s_mp_add.c index c946aa80d..922071996 100644 --- a/bn_s_mp_add.c +++ b/s_mp_add.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_ADD_C +#ifdef S_MP_ADD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_balance_mul.c b/s_mp_balance_mul.c similarity index 98% rename from bn_s_mp_balance_mul.c rename to s_mp_balance_mul.c index 7ece5d794..410883020 100644 --- a/bn_s_mp_balance_mul.c +++ b/s_mp_balance_mul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_BALANCE_MUL_C +#ifdef S_MP_BALANCE_MUL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_exptmod.c b/s_mp_exptmod.c similarity index 99% rename from bn_s_mp_exptmod.c rename to s_mp_exptmod.c index c3bfa95e8..2a89a2cbf 100644 --- a/bn_s_mp_exptmod.c +++ b/s_mp_exptmod.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_EXPTMOD_C +#ifdef S_MP_EXPTMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_exptmod_fast.c b/s_mp_exptmod_fast.c similarity index 99% rename from bn_s_mp_exptmod_fast.c rename to s_mp_exptmod_fast.c index 682ded845..d58112968 100644 --- a/bn_s_mp_exptmod_fast.c +++ b/s_mp_exptmod_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_EXPTMOD_FAST_C +#ifdef S_MP_EXPTMOD_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_get_bit.c b/s_mp_get_bit.c similarity index 95% rename from bn_s_mp_get_bit.c rename to s_mp_get_bit.c index 28598dfec..397499cbb 100644 --- a/bn_s_mp_get_bit.c +++ b/s_mp_get_bit.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_GET_BIT_C +#ifdef S_MP_GET_BIT_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_invmod_fast.c b/s_mp_invmod_fast.c similarity index 99% rename from bn_s_mp_invmod_fast.c rename to s_mp_invmod_fast.c index 677d7ab69..0d00ea91d 100644 --- a/bn_s_mp_invmod_fast.c +++ b/s_mp_invmod_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_INVMOD_FAST_C +#ifdef S_MP_INVMOD_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_invmod_slow.c b/s_mp_invmod_slow.c similarity index 99% rename from bn_s_mp_invmod_slow.c rename to s_mp_invmod_slow.c index 4c5db3300..4fecfb895 100644 --- a/bn_s_mp_invmod_slow.c +++ b/s_mp_invmod_slow.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_INVMOD_SLOW_C +#ifdef S_MP_INVMOD_SLOW_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_karatsuba_mul.c b/s_mp_karatsuba_mul.c similarity index 99% rename from bn_s_mp_karatsuba_mul.c rename to s_mp_karatsuba_mul.c index 85899fb87..df3daa7ee 100644 --- a/bn_s_mp_karatsuba_mul.c +++ b/s_mp_karatsuba_mul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_KARATSUBA_MUL_C +#ifdef S_MP_KARATSUBA_MUL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_karatsuba_sqr.c b/s_mp_karatsuba_sqr.c similarity index 98% rename from bn_s_mp_karatsuba_sqr.c rename to s_mp_karatsuba_sqr.c index f132d0719..7f2284287 100644 --- a/bn_s_mp_karatsuba_sqr.c +++ b/s_mp_karatsuba_sqr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_KARATSUBA_SQR_C +#ifdef S_MP_KARATSUBA_SQR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_montgomery_reduce_fast.c b/s_mp_montgomery_reduce_fast.c similarity index 99% rename from bn_s_mp_montgomery_reduce_fast.c rename to s_mp_montgomery_reduce_fast.c index 3f0c672ac..083e7a4f4 100644 --- a/bn_s_mp_montgomery_reduce_fast.c +++ b/s_mp_montgomery_reduce_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_MONTGOMERY_REDUCE_FAST_C +#ifdef S_MP_MONTGOMERY_REDUCE_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_mul_digs.c b/s_mp_mul_digs.c similarity index 98% rename from bn_s_mp_mul_digs.c rename to s_mp_mul_digs.c index 64509d4cb..ea0985b87 100644 --- a/bn_s_mp_mul_digs.c +++ b/s_mp_mul_digs.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_MUL_DIGS_C +#ifdef S_MP_MUL_DIGS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_mul_digs_fast.c b/s_mp_mul_digs_fast.c similarity index 98% rename from bn_s_mp_mul_digs_fast.c rename to s_mp_mul_digs_fast.c index b2a287b02..8988838fb 100644 --- a/bn_s_mp_mul_digs_fast.c +++ b/s_mp_mul_digs_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_MUL_DIGS_FAST_C +#ifdef S_MP_MUL_DIGS_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_mul_high_digs.c b/s_mp_mul_high_digs.c similarity index 98% rename from bn_s_mp_mul_high_digs.c rename to s_mp_mul_high_digs.c index 2bb2a5098..87cfbe54f 100644 --- a/bn_s_mp_mul_high_digs.c +++ b/s_mp_mul_high_digs.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_MUL_HIGH_DIGS_C +#ifdef S_MP_MUL_HIGH_DIGS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_mul_high_digs_fast.c b/s_mp_mul_high_digs_fast.c similarity index 98% rename from bn_s_mp_mul_high_digs_fast.c rename to s_mp_mul_high_digs_fast.c index a2c4fb692..06561a9fd 100644 --- a/bn_s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_digs_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_MUL_HIGH_DIGS_FAST_C +#ifdef S_MP_MUL_HIGH_DIGS_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_prime_is_divisible.c b/s_mp_prime_is_divisible.c similarity index 95% rename from bn_s_mp_prime_is_divisible.c rename to s_mp_prime_is_divisible.c index ca303a5ba..d8bdedc76 100644 --- a/bn_s_mp_prime_is_divisible.c +++ b/s_mp_prime_is_divisible.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_PRIME_IS_DIVISIBLE_C +#ifdef S_MP_PRIME_IS_DIVISIBLE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_rand_jenkins.c b/s_mp_rand_jenkins.c similarity index 97% rename from bn_s_mp_rand_jenkins.c rename to s_mp_rand_jenkins.c index da0771c5f..cbbe0668b 100644 --- a/bn_s_mp_rand_jenkins.c +++ b/s_mp_rand_jenkins.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_RAND_JENKINS_C +#ifdef S_MP_RAND_JENKINS_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_rand_platform.c b/s_mp_rand_platform.c similarity index 92% rename from bn_s_mp_rand_platform.c rename to s_mp_rand_platform.c index 07555db74..8f79d898d 100644 --- a/bn_s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_RAND_PLATFORM_C +#ifdef S_MP_RAND_PLATFORM_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -8,7 +8,7 @@ * - Windows */ #if defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__DragonFly__) -#define BN_S_READ_ARC4RANDOM_C +#define S_READ_ARC4RANDOM_C static mp_err s_read_arc4random(void *p, size_t n) { arc4random_buf(p, n); @@ -17,7 +17,7 @@ static mp_err s_read_arc4random(void *p, size_t n) #endif #if defined(_WIN32) || defined(_WIN32_WCE) -#define BN_S_READ_WINCSP_C +#define S_READ_WINCSP_C #ifndef _WIN32_WINNT #define _WIN32_WINNT 0x0400 @@ -55,9 +55,9 @@ static mp_err s_read_wincsp(void *p, size_t n) } #endif /* WIN32 */ -#if !defined(BN_S_READ_WINCSP_C) && defined(__linux__) && defined(__GLIBC_PREREQ) +#if !defined(S_READ_WINCSP_C) && defined(__linux__) && defined(__GLIBC_PREREQ) #if __GLIBC_PREREQ(2, 25) -#define BN_S_READ_GETRANDOM_C +#define S_READ_GETRANDOM_C #include #include @@ -83,8 +83,8 @@ static mp_err s_read_getrandom(void *p, size_t n) /* We assume all platforms besides windows provide "/dev/urandom". * In case yours doesn't, define MP_NO_DEV_URANDOM at compile-time. */ -#if !defined(BN_S_READ_WINCSP_C) && !defined(MP_NO_DEV_URANDOM) -#define BN_S_READ_URANDOM_C +#if !defined(S_READ_WINCSP_C) && !defined(MP_NO_DEV_URANDOM) +#define S_READ_URANDOM_C #ifndef MP_DEV_URANDOM #define MP_DEV_URANDOM "/dev/urandom" #endif diff --git a/bn_s_mp_reverse.c b/s_mp_reverse.c similarity index 94% rename from bn_s_mp_reverse.c rename to s_mp_reverse.c index c549e605e..d288dc560 100644 --- a/bn_s_mp_reverse.c +++ b/s_mp_reverse.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_REVERSE_C +#ifdef S_MP_REVERSE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_sqr.c b/s_mp_sqr.c similarity index 98% rename from bn_s_mp_sqr.c rename to s_mp_sqr.c index 505c9f053..61106ed73 100644 --- a/bn_s_mp_sqr.c +++ b/s_mp_sqr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_SQR_C +#ifdef S_MP_SQR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_sqr_fast.c b/s_mp_sqr_fast.c similarity index 98% rename from bn_s_mp_sqr_fast.c rename to s_mp_sqr_fast.c index 4a8a8912f..bcb1f5e6b 100644 --- a/bn_s_mp_sqr_fast.c +++ b/s_mp_sqr_fast.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_SQR_FAST_C +#ifdef S_MP_SQR_FAST_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_sub.c b/s_mp_sub.c similarity index 98% rename from bn_s_mp_sub.c rename to s_mp_sub.c index 5672dab51..bef1fce53 100644 --- a/bn_s_mp_sub.c +++ b/s_mp_sub.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_SUB_C +#ifdef S_MP_SUB_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_toom_mul.c b/s_mp_toom_mul.c similarity index 99% rename from bn_s_mp_toom_mul.c rename to s_mp_toom_mul.c index 8efd803c4..0b2d57d72 100644 --- a/bn_s_mp_toom_mul.c +++ b/s_mp_toom_mul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_TOOM_MUL_C +#ifdef S_MP_TOOM_MUL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/bn_s_mp_toom_sqr.c b/s_mp_toom_sqr.c similarity index 99% rename from bn_s_mp_toom_sqr.c rename to s_mp_toom_sqr.c index 9eaa9d037..884a532a7 100644 --- a/bn_s_mp_toom_sqr.c +++ b/s_mp_toom_sqr.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef BN_S_MP_TOOM_SQR_C +#ifdef S_MP_TOOM_SQR_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/tommath.def b/tommath.def index 9c7f226f4..7c241bc75 100644 --- a/tommath.def +++ b/tommath.def @@ -22,6 +22,7 @@ EXPORTS mp_complement mp_copy mp_count_bits + mp_cutoffs mp_decr mp_div mp_div_2 @@ -96,6 +97,7 @@ EXPORTS mp_prime_rabin_miller_trials mp_prime_rand mp_prime_strong_lucas_selfridge + mp_prime_tab mp_radix_size mp_rand mp_read_radix diff --git a/tommath.h b/tommath.h index cca54114f..b82477e05 100644 --- a/tommath.h +++ b/tommath.h @@ -1,8 +1,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#ifndef BN_H_ -#define BN_H_ +#ifndef TOMMATH_H_ +#define TOMMATH_H_ #include #include diff --git a/tommath_class.h b/tommath_class.h index 209d80901..c6dcde1fd 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -11,1208 +11,1208 @@ #endif #define LTM1 #if defined(LTM_ALL) -# define BN_CUTOFFS_C -# define BN_MP_2EXPT_C -# define BN_MP_ABS_C -# define BN_MP_ADD_C -# define BN_MP_ADD_D_C -# define BN_MP_ADDMOD_C -# define BN_MP_AND_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_CMP_MAG_C -# define BN_MP_CNT_LSB_C -# define BN_MP_COMPLEMENT_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DECR_C -# define BN_MP_DIV_C -# define BN_MP_DIV_2_C -# define BN_MP_DIV_2D_C -# define BN_MP_DIV_3_C -# define BN_MP_DIV_D_C -# define BN_MP_DR_IS_MODULUS_C -# define BN_MP_DR_REDUCE_C -# define BN_MP_DR_SETUP_C -# define BN_MP_ERROR_TO_STRING_C -# define BN_MP_EXCH_C -# define BN_MP_EXPT_U32_C -# define BN_MP_EXPTMOD_C -# define BN_MP_EXTEUCLID_C -# define BN_MP_FREAD_C -# define BN_MP_FROM_SBIN_C -# define BN_MP_FROM_UBIN_C -# define BN_MP_FWRITE_C -# define BN_MP_GCD_C -# define BN_MP_GET_DOUBLE_C -# define BN_MP_GET_I32_C -# define BN_MP_GET_I64_C -# define BN_MP_GET_L_C -# define BN_MP_GET_LL_C -# define BN_MP_GET_MAG_U32_C -# define BN_MP_GET_MAG_U64_C -# define BN_MP_GET_MAG_UL_C -# define BN_MP_GET_MAG_ULL_C -# define BN_MP_GROW_C -# define BN_MP_INCR_C -# define BN_MP_INIT_C -# define BN_MP_INIT_COPY_C -# define BN_MP_INIT_I32_C -# define BN_MP_INIT_I64_C -# define BN_MP_INIT_L_C -# define BN_MP_INIT_LL_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_INIT_SET_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_INIT_U32_C -# define BN_MP_INIT_U64_C -# define BN_MP_INIT_UL_C -# define BN_MP_INIT_ULL_C -# define BN_MP_INVMOD_C -# define BN_MP_IS_SQUARE_C -# define BN_MP_ISEVEN_C -# define BN_MP_ISODD_C -# define BN_MP_KRONECKER_C -# define BN_MP_LCM_C -# define BN_MP_LOG_U32_C -# define BN_MP_LSHD_C -# define BN_MP_MOD_C -# define BN_MP_MOD_2D_C -# define BN_MP_MOD_D_C -# define BN_MP_MONTGOMERY_CALC_NORMALIZATION_C -# define BN_MP_MONTGOMERY_REDUCE_C -# define BN_MP_MONTGOMERY_SETUP_C -# define BN_MP_MUL_C -# define BN_MP_MUL_2_C -# define BN_MP_MUL_2D_C -# define BN_MP_MUL_D_C -# define BN_MP_MULMOD_C -# define BN_MP_NEG_C -# define BN_MP_OR_C -# define BN_MP_PACK_C -# define BN_MP_PACK_COUNT_C -# define BN_MP_PRIME_FERMAT_C -# define BN_MP_PRIME_FROBENIUS_UNDERWOOD_C -# define BN_MP_PRIME_IS_PRIME_C -# define BN_MP_PRIME_MILLER_RABIN_C -# define BN_MP_PRIME_NEXT_PRIME_C -# define BN_MP_PRIME_RABIN_MILLER_TRIALS_C -# define BN_MP_PRIME_RAND_C -# define BN_MP_PRIME_STRONG_LUCAS_SELFRIDGE_C -# define BN_MP_RADIX_SIZE_C -# define BN_MP_RADIX_SMAP_C -# define BN_MP_RAND_C -# define BN_MP_READ_RADIX_C -# define BN_MP_REDUCE_C -# define BN_MP_REDUCE_2K_C -# define BN_MP_REDUCE_2K_L_C -# define BN_MP_REDUCE_2K_SETUP_C -# define BN_MP_REDUCE_2K_SETUP_L_C -# define BN_MP_REDUCE_IS_2K_C -# define BN_MP_REDUCE_IS_2K_L_C -# define BN_MP_REDUCE_SETUP_C -# define BN_MP_ROOT_U32_C -# define BN_MP_RSHD_C -# define BN_MP_SBIN_SIZE_C -# define BN_MP_SET_C -# define BN_MP_SET_DOUBLE_C -# define BN_MP_SET_I32_C -# define BN_MP_SET_I64_C -# define BN_MP_SET_L_C -# define BN_MP_SET_LL_C -# define BN_MP_SET_U32_C -# define BN_MP_SET_U64_C -# define BN_MP_SET_UL_C -# define BN_MP_SET_ULL_C -# define BN_MP_SHRINK_C -# define BN_MP_SIGNED_RSH_C -# define BN_MP_SQR_C -# define BN_MP_SQRMOD_C -# define BN_MP_SQRT_C -# define BN_MP_SQRTMOD_PRIME_C -# define BN_MP_SUB_C -# define BN_MP_SUB_D_C -# define BN_MP_SUBMOD_C -# define BN_MP_TO_RADIX_C -# define BN_MP_TO_SBIN_C -# define BN_MP_TO_UBIN_C -# define BN_MP_UBIN_SIZE_C -# define BN_MP_UNPACK_C -# define BN_MP_XOR_C -# define BN_MP_ZERO_C -# define BN_PRIME_TAB_C -# define BN_S_MP_ADD_C -# define BN_S_MP_BALANCE_MUL_C -# define BN_S_MP_EXPTMOD_C -# define BN_S_MP_EXPTMOD_FAST_C -# define BN_S_MP_GET_BIT_C -# define BN_S_MP_INVMOD_FAST_C -# define BN_S_MP_INVMOD_SLOW_C -# define BN_S_MP_KARATSUBA_MUL_C -# define BN_S_MP_KARATSUBA_SQR_C -# define BN_S_MP_MONTGOMERY_REDUCE_FAST_C -# define BN_S_MP_MUL_DIGS_C -# define BN_S_MP_MUL_DIGS_FAST_C -# define BN_S_MP_MUL_HIGH_DIGS_C -# define BN_S_MP_MUL_HIGH_DIGS_FAST_C -# define BN_S_MP_PRIME_IS_DIVISIBLE_C -# define BN_S_MP_RAND_JENKINS_C -# define BN_S_MP_RAND_PLATFORM_C -# define BN_S_MP_REVERSE_C -# define BN_S_MP_SQR_C -# define BN_S_MP_SQR_FAST_C -# define BN_S_MP_SUB_C -# define BN_S_MP_TOOM_MUL_C -# define BN_S_MP_TOOM_SQR_C -#endif -#endif -#if defined(BN_CUTOFFS_C) -#endif - -#if defined(BN_MP_2EXPT_C) -# define BN_MP_GROW_C -# define BN_MP_ZERO_C -#endif - -#if defined(BN_MP_ABS_C) -# define BN_MP_COPY_C -#endif - -#if defined(BN_MP_ADD_C) -# define BN_MP_CMP_MAG_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_ADD_D_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -# define BN_MP_SUB_D_C -#endif - -#if defined(BN_MP_ADDMOD_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_C -# define BN_MP_INIT_C -# define BN_MP_MOD_C -#endif - -#if defined(BN_MP_AND_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +# define MP_2EXPT_C +# define MP_ABS_C +# define MP_ADD_C +# define MP_ADD_D_C +# define MP_ADDMOD_C +# define MP_AND_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CMP_MAG_C +# define MP_CNT_LSB_C +# define MP_COMPLEMENT_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_CUTOFFS_C +# define MP_DECR_C +# define MP_DIV_C +# define MP_DIV_2_C +# define MP_DIV_2D_C +# define MP_DIV_3_C +# define MP_DIV_D_C +# define MP_DR_IS_MODULUS_C +# define MP_DR_REDUCE_C +# define MP_DR_SETUP_C +# define MP_ERROR_TO_STRING_C +# define MP_EXCH_C +# define MP_EXPT_U32_C +# define MP_EXPTMOD_C +# define MP_EXTEUCLID_C +# define MP_FREAD_C +# define MP_FROM_SBIN_C +# define MP_FROM_UBIN_C +# define MP_FWRITE_C +# define MP_GCD_C +# define MP_GET_DOUBLE_C +# define MP_GET_I32_C +# define MP_GET_I64_C +# define MP_GET_L_C +# define MP_GET_LL_C +# define MP_GET_MAG_U32_C +# define MP_GET_MAG_U64_C +# define MP_GET_MAG_UL_C +# define MP_GET_MAG_ULL_C +# define MP_GROW_C +# define MP_INCR_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_INIT_I32_C +# define MP_INIT_I64_C +# define MP_INIT_L_C +# define MP_INIT_LL_C +# define MP_INIT_MULTI_C +# define MP_INIT_SET_C +# define MP_INIT_SIZE_C +# define MP_INIT_U32_C +# define MP_INIT_U64_C +# define MP_INIT_UL_C +# define MP_INIT_ULL_C +# define MP_INVMOD_C +# define MP_IS_SQUARE_C +# define MP_ISEVEN_C +# define MP_ISODD_C +# define MP_KRONECKER_C +# define MP_LCM_C +# define MP_LOG_U32_C +# define MP_LSHD_C +# define MP_MOD_C +# define MP_MOD_2D_C +# define MP_MOD_D_C +# define MP_MONTGOMERY_CALC_NORMALIZATION_C +# define MP_MONTGOMERY_REDUCE_C +# define MP_MONTGOMERY_SETUP_C +# define MP_MUL_C +# define MP_MUL_2_C +# define MP_MUL_2D_C +# define MP_MUL_D_C +# define MP_MULMOD_C +# define MP_NEG_C +# define MP_OR_C +# define MP_PACK_C +# define MP_PACK_COUNT_C +# define MP_PRIME_FERMAT_C +# define MP_PRIME_FROBENIUS_UNDERWOOD_C +# define MP_PRIME_IS_PRIME_C +# define MP_PRIME_MILLER_RABIN_C +# define MP_PRIME_NEXT_PRIME_C +# define MP_PRIME_RABIN_MILLER_TRIALS_C +# define MP_PRIME_RAND_C +# define MP_PRIME_STRONG_LUCAS_SELFRIDGE_C +# define MP_PRIME_TAB_C +# define MP_RADIX_SIZE_C +# define MP_RADIX_SMAP_C +# define MP_RAND_C +# define MP_READ_RADIX_C +# define MP_REDUCE_C +# define MP_REDUCE_2K_C +# define MP_REDUCE_2K_L_C +# define MP_REDUCE_2K_SETUP_C +# define MP_REDUCE_2K_SETUP_L_C +# define MP_REDUCE_IS_2K_C +# define MP_REDUCE_IS_2K_L_C +# define MP_REDUCE_SETUP_C +# define MP_ROOT_U32_C +# define MP_RSHD_C +# define MP_SBIN_SIZE_C +# define MP_SET_C +# define MP_SET_DOUBLE_C +# define MP_SET_I32_C +# define MP_SET_I64_C +# define MP_SET_L_C +# define MP_SET_LL_C +# define MP_SET_U32_C +# define MP_SET_U64_C +# define MP_SET_UL_C +# define MP_SET_ULL_C +# define MP_SHRINK_C +# define MP_SIGNED_RSH_C +# define MP_SQR_C +# define MP_SQRMOD_C +# define MP_SQRT_C +# define MP_SQRTMOD_PRIME_C +# define MP_SUB_C +# define MP_SUB_D_C +# define MP_SUBMOD_C +# define MP_TO_RADIX_C +# define MP_TO_SBIN_C +# define MP_TO_UBIN_C +# define MP_UBIN_SIZE_C +# define MP_UNPACK_C +# define MP_XOR_C +# define MP_ZERO_C +# define S_MP_ADD_C +# define S_MP_BALANCE_MUL_C +# define S_MP_EXPTMOD_C +# define S_MP_EXPTMOD_FAST_C +# define S_MP_GET_BIT_C +# define S_MP_INVMOD_FAST_C +# define S_MP_INVMOD_SLOW_C +# define S_MP_KARATSUBA_MUL_C +# define S_MP_KARATSUBA_SQR_C +# define S_MP_MONTGOMERY_REDUCE_FAST_C +# define S_MP_MUL_DIGS_C +# define S_MP_MUL_DIGS_FAST_C +# define S_MP_MUL_HIGH_DIGS_C +# define S_MP_MUL_HIGH_DIGS_FAST_C +# define S_MP_PRIME_IS_DIVISIBLE_C +# define S_MP_RAND_JENKINS_C +# define S_MP_RAND_PLATFORM_C +# define S_MP_REVERSE_C +# define S_MP_SQR_C +# define S_MP_SQR_FAST_C +# define S_MP_SUB_C +# define S_MP_TOOM_MUL_C +# define S_MP_TOOM_SQR_C +#endif +#endif +#if defined(MP_2EXPT_C) +# define MP_GROW_C +# define MP_ZERO_C +#endif + +#if defined(MP_ABS_C) +# define MP_COPY_C +#endif + +#if defined(MP_ADD_C) +# define MP_CMP_MAG_C +# define S_MP_ADD_C +# define S_MP_SUB_C +#endif + +#if defined(MP_ADD_D_C) +# define MP_CLAMP_C +# define MP_GROW_C +# define MP_SUB_D_C +#endif + +#if defined(MP_ADDMOD_C) +# define MP_ADD_C +# define MP_CLEAR_C +# define MP_INIT_C +# define MP_MOD_C +#endif + +#if defined(MP_AND_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_MP_CLAMP_C) +#if defined(MP_CLAMP_C) #endif -#if defined(BN_MP_CLEAR_C) +#if defined(MP_CLEAR_C) #endif -#if defined(BN_MP_CLEAR_MULTI_C) -# define BN_MP_CLEAR_C +#if defined(MP_CLEAR_MULTI_C) +# define MP_CLEAR_C #endif -#if defined(BN_MP_CMP_C) -# define BN_MP_CMP_MAG_C +#if defined(MP_CMP_C) +# define MP_CMP_MAG_C #endif -#if defined(BN_MP_CMP_D_C) +#if defined(MP_CMP_D_C) #endif -#if defined(BN_MP_CMP_MAG_C) +#if defined(MP_CMP_MAG_C) #endif -#if defined(BN_MP_CNT_LSB_C) +#if defined(MP_CNT_LSB_C) #endif -#if defined(BN_MP_COMPLEMENT_C) -# define BN_MP_NEG_C -# define BN_MP_SUB_D_C +#if defined(MP_COMPLEMENT_C) +# define MP_NEG_C +# define MP_SUB_D_C #endif -#if defined(BN_MP_COPY_C) -# define BN_MP_GROW_C +#if defined(MP_COPY_C) +# define MP_GROW_C #endif -#if defined(BN_MP_COUNT_BITS_C) +#if defined(MP_COUNT_BITS_C) #endif -#if defined(BN_MP_DECR_C) -# define BN_MP_INCR_C -# define BN_MP_SET_C -# define BN_MP_SUB_D_C -# define BN_MP_ZERO_C +#if defined(MP_CUTOFFS_C) #endif -#if defined(BN_MP_DIV_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_CMP_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_2D_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_C -# define BN_MP_INIT_COPY_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_MUL_2D_C -# define BN_MP_MUL_D_C -# define BN_MP_RSHD_C -# define BN_MP_SUB_C -# define BN_MP_ZERO_C +#if defined(MP_DECR_C) +# define MP_INCR_C +# define MP_SET_C +# define MP_SUB_D_C +# define MP_ZERO_C #endif -#if defined(BN_MP_DIV_2_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(MP_DIV_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_MAG_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_EXCH_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_2D_C +# define MP_MUL_D_C +# define MP_RSHD_C +# define MP_SUB_C +# define MP_ZERO_C #endif -#if defined(BN_MP_DIV_2D_C) -# define BN_MP_CLAMP_C -# define BN_MP_COPY_C -# define BN_MP_MOD_2D_C -# define BN_MP_RSHD_C -# define BN_MP_ZERO_C +#if defined(MP_DIV_2_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_MP_DIV_3_C) -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C +#if defined(MP_DIV_2D_C) +# define MP_CLAMP_C +# define MP_COPY_C +# define MP_MOD_2D_C +# define MP_RSHD_C +# define MP_ZERO_C #endif -#if defined(BN_MP_DIV_D_C) -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_COPY_C -# define BN_MP_DIV_2D_C -# define BN_MP_DIV_3_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C +#if defined(MP_DIV_3_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C #endif -#if defined(BN_MP_DR_IS_MODULUS_C) +#if defined(MP_DIV_D_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_COPY_C +# define MP_DIV_2D_C +# define MP_DIV_3_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C #endif -#if defined(BN_MP_DR_REDUCE_C) -# define BN_MP_CLAMP_C -# define BN_MP_CMP_MAG_C -# define BN_MP_GROW_C -# define BN_S_MP_SUB_C +#if defined(MP_DR_IS_MODULUS_C) #endif -#if defined(BN_MP_DR_SETUP_C) +#if defined(MP_DR_REDUCE_C) +# define MP_CLAMP_C +# define MP_CMP_MAG_C +# define MP_GROW_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_ERROR_TO_STRING_C) +#if defined(MP_DR_SETUP_C) #endif -#if defined(BN_MP_EXCH_C) +#if defined(MP_ERROR_TO_STRING_C) #endif -#if defined(BN_MP_EXPT_U32_C) -# define BN_MP_CLEAR_C -# define BN_MP_INIT_COPY_C -# define BN_MP_MUL_C -# define BN_MP_SET_C -# define BN_MP_SQR_C +#if defined(MP_EXCH_C) #endif -#if defined(BN_MP_EXPTMOD_C) -# define BN_MP_ABS_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_DR_IS_MODULUS_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_INVMOD_C -# define BN_MP_REDUCE_IS_2K_C -# define BN_MP_REDUCE_IS_2K_L_C -# define BN_S_MP_EXPTMOD_C -# define BN_S_MP_EXPTMOD_FAST_C +#if defined(MP_EXPT_U32_C) +# define MP_CLEAR_C +# define MP_INIT_COPY_C +# define MP_MUL_C +# define MP_SET_C +# define MP_SQR_C #endif -#if defined(BN_MP_EXTEUCLID_C) -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_COPY_C -# define BN_MP_DIV_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MUL_C -# define BN_MP_NEG_C -# define BN_MP_SET_C -# define BN_MP_SUB_C +#if defined(MP_EXPTMOD_C) +# define MP_ABS_C +# define MP_CLEAR_MULTI_C +# define MP_DR_IS_MODULUS_C +# define MP_INIT_MULTI_C +# define MP_INVMOD_C +# define MP_REDUCE_IS_2K_C +# define MP_REDUCE_IS_2K_L_C +# define S_MP_EXPTMOD_C +# define S_MP_EXPTMOD_FAST_C #endif -#if defined(BN_MP_FREAD_C) -# define BN_MP_ADD_D_C -# define BN_MP_MUL_D_C -# define BN_MP_ZERO_C +#if defined(MP_EXTEUCLID_C) +# define MP_CLEAR_MULTI_C +# define MP_COPY_C +# define MP_DIV_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_NEG_C +# define MP_SET_C +# define MP_SUB_C #endif -#if defined(BN_MP_FROM_SBIN_C) -# define BN_MP_FROM_UBIN_C +#if defined(MP_FREAD_C) +# define MP_ADD_D_C +# define MP_MUL_D_C +# define MP_ZERO_C #endif -#if defined(BN_MP_FROM_UBIN_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -# define BN_MP_MUL_2D_C -# define BN_MP_ZERO_C +#if defined(MP_FROM_SBIN_C) +# define MP_FROM_UBIN_C #endif -#if defined(BN_MP_FWRITE_C) -# define BN_MP_RADIX_SIZE_C -# define BN_MP_TO_RADIX_C +#if defined(MP_FROM_UBIN_C) +# define MP_CLAMP_C +# define MP_GROW_C +# define MP_MUL_2D_C +# define MP_ZERO_C #endif -#if defined(BN_MP_GCD_C) -# define BN_MP_ABS_C -# define BN_MP_CLEAR_C -# define BN_MP_CMP_MAG_C -# define BN_MP_CNT_LSB_C -# define BN_MP_DIV_2D_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_COPY_C -# define BN_MP_MUL_2D_C -# define BN_S_MP_SUB_C +#if defined(MP_FWRITE_C) +# define MP_RADIX_SIZE_C +# define MP_TO_RADIX_C #endif -#if defined(BN_MP_GET_DOUBLE_C) +#if defined(MP_GCD_C) +# define MP_ABS_C +# define MP_CLEAR_C +# define MP_CMP_MAG_C +# define MP_CNT_LSB_C +# define MP_DIV_2D_C +# define MP_EXCH_C +# define MP_INIT_COPY_C +# define MP_MUL_2D_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_GET_I32_C) -# define BN_MP_GET_MAG_U32_C +#if defined(MP_GET_DOUBLE_C) #endif -#if defined(BN_MP_GET_I64_C) -# define BN_MP_GET_MAG_U64_C +#if defined(MP_GET_I32_C) +# define MP_GET_MAG_U32_C #endif -#if defined(BN_MP_GET_L_C) -# define BN_MP_GET_MAG_UL_C +#if defined(MP_GET_I64_C) +# define MP_GET_MAG_U64_C #endif -#if defined(BN_MP_GET_LL_C) -# define BN_MP_GET_MAG_ULL_C +#if defined(MP_GET_L_C) +# define MP_GET_MAG_UL_C #endif -#if defined(BN_MP_GET_MAG_U32_C) +#if defined(MP_GET_LL_C) +# define MP_GET_MAG_ULL_C #endif -#if defined(BN_MP_GET_MAG_U64_C) +#if defined(MP_GET_MAG_U32_C) #endif -#if defined(BN_MP_GET_MAG_UL_C) +#if defined(MP_GET_MAG_U64_C) #endif -#if defined(BN_MP_GET_MAG_ULL_C) +#if defined(MP_GET_MAG_UL_C) #endif -#if defined(BN_MP_GROW_C) +#if defined(MP_GET_MAG_ULL_C) #endif -#if defined(BN_MP_INCR_C) -# define BN_MP_ADD_D_C -# define BN_MP_DECR_C -# define BN_MP_SET_C +#if defined(MP_GROW_C) #endif -#if defined(BN_MP_INIT_C) +#if defined(MP_INCR_C) +# define MP_ADD_D_C +# define MP_DECR_C +# define MP_SET_C #endif -#if defined(BN_MP_INIT_COPY_C) -# define BN_MP_CLEAR_C -# define BN_MP_COPY_C -# define BN_MP_INIT_SIZE_C +#if defined(MP_INIT_C) #endif -#if defined(BN_MP_INIT_I32_C) -# define BN_MP_INIT_C -# define BN_MP_SET_I32_C +#if defined(MP_INIT_COPY_C) +# define MP_CLEAR_C +# define MP_COPY_C +# define MP_INIT_SIZE_C #endif -#if defined(BN_MP_INIT_I64_C) -# define BN_MP_INIT_C -# define BN_MP_SET_I64_C +#if defined(MP_INIT_I32_C) +# define MP_INIT_C +# define MP_SET_I32_C #endif -#if defined(BN_MP_INIT_L_C) -# define BN_MP_INIT_C -# define BN_MP_SET_L_C +#if defined(MP_INIT_I64_C) +# define MP_INIT_C +# define MP_SET_I64_C #endif -#if defined(BN_MP_INIT_LL_C) -# define BN_MP_INIT_C -# define BN_MP_SET_LL_C +#if defined(MP_INIT_L_C) +# define MP_INIT_C +# define MP_SET_L_C #endif -#if defined(BN_MP_INIT_MULTI_C) -# define BN_MP_CLEAR_C -# define BN_MP_INIT_C +#if defined(MP_INIT_LL_C) +# define MP_INIT_C +# define MP_SET_LL_C #endif -#if defined(BN_MP_INIT_SET_C) -# define BN_MP_INIT_C -# define BN_MP_SET_C +#if defined(MP_INIT_MULTI_C) +# define MP_CLEAR_C +# define MP_INIT_C #endif -#if defined(BN_MP_INIT_SIZE_C) +#if defined(MP_INIT_SET_C) +# define MP_INIT_C +# define MP_SET_C #endif -#if defined(BN_MP_INIT_U32_C) -# define BN_MP_INIT_C -# define BN_MP_SET_U32_C +#if defined(MP_INIT_SIZE_C) #endif -#if defined(BN_MP_INIT_U64_C) -# define BN_MP_INIT_C -# define BN_MP_SET_U64_C +#if defined(MP_INIT_U32_C) +# define MP_INIT_C +# define MP_SET_U32_C #endif -#if defined(BN_MP_INIT_UL_C) -# define BN_MP_INIT_C -# define BN_MP_SET_UL_C +#if defined(MP_INIT_U64_C) +# define MP_INIT_C +# define MP_SET_U64_C #endif -#if defined(BN_MP_INIT_ULL_C) -# define BN_MP_INIT_C -# define BN_MP_SET_ULL_C +#if defined(MP_INIT_UL_C) +# define MP_INIT_C +# define MP_SET_UL_C #endif -#if defined(BN_MP_INVMOD_C) -# define BN_MP_CMP_D_C -# define BN_S_MP_INVMOD_FAST_C -# define BN_S_MP_INVMOD_SLOW_C +#if defined(MP_INIT_ULL_C) +# define MP_INIT_C +# define MP_SET_ULL_C #endif -#if defined(BN_MP_IS_SQUARE_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_MAG_C -# define BN_MP_GET_I32_C -# define BN_MP_INIT_U32_C -# define BN_MP_MOD_C -# define BN_MP_MOD_D_C -# define BN_MP_SQRT_C -# define BN_MP_SQR_C +#if defined(MP_INVMOD_C) +# define MP_CMP_D_C +# define S_MP_INVMOD_FAST_C +# define S_MP_INVMOD_SLOW_C #endif -#if defined(BN_MP_ISEVEN_C) +#if defined(MP_IS_SQUARE_C) +# define MP_CLEAR_C +# define MP_CMP_MAG_C +# define MP_GET_I32_C +# define MP_INIT_U32_C +# define MP_MOD_C +# define MP_MOD_D_C +# define MP_SQRT_C +# define MP_SQR_C #endif -#if defined(BN_MP_ISODD_C) +#if defined(MP_ISEVEN_C) #endif -#if defined(BN_MP_KRONECKER_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_D_C -# define BN_MP_CNT_LSB_C -# define BN_MP_COPY_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_C -# define BN_MP_INIT_COPY_C -# define BN_MP_MOD_C +#if defined(MP_ISODD_C) #endif -#if defined(BN_MP_LCM_C) -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_MAG_C -# define BN_MP_DIV_C -# define BN_MP_GCD_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MUL_C +#if defined(MP_KRONECKER_C) +# define MP_CLEAR_C +# define MP_CMP_D_C +# define MP_CNT_LSB_C +# define MP_COPY_C +# define MP_DIV_2D_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_MOD_C #endif -#if defined(BN_MP_LOG_U32_C) -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_EXCH_C -# define BN_MP_EXPT_U32_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MUL_C -# define BN_MP_SET_C -# define BN_MP_SQR_C +#if defined(MP_LCM_C) +# define MP_CLEAR_MULTI_C +# define MP_CMP_MAG_C +# define MP_DIV_C +# define MP_GCD_C +# define MP_INIT_MULTI_C +# define MP_MUL_C #endif -#if defined(BN_MP_LSHD_C) -# define BN_MP_GROW_C +#if defined(MP_LOG_U32_C) +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_EXCH_C +# define MP_EXPT_U32_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_SET_C +# define MP_SQR_C #endif -#if defined(BN_MP_MOD_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_C -# define BN_MP_DIV_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C +#if defined(MP_LSHD_C) +# define MP_GROW_C #endif -#if defined(BN_MP_MOD_2D_C) -# define BN_MP_CLAMP_C -# define BN_MP_COPY_C -# define BN_MP_ZERO_C +#if defined(MP_MOD_C) +# define MP_ADD_C +# define MP_CLEAR_C +# define MP_DIV_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C #endif -#if defined(BN_MP_MOD_D_C) -# define BN_MP_DIV_D_C +#if defined(MP_MOD_2D_C) +# define MP_CLAMP_C +# define MP_COPY_C +# define MP_ZERO_C #endif -#if defined(BN_MP_MONTGOMERY_CALC_NORMALIZATION_C) -# define BN_MP_2EXPT_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_MUL_2_C -# define BN_MP_SET_C -# define BN_S_MP_SUB_C +#if defined(MP_MOD_D_C) +# define MP_DIV_D_C #endif -#if defined(BN_MP_MONTGOMERY_REDUCE_C) -# define BN_MP_CLAMP_C -# define BN_MP_CMP_MAG_C -# define BN_MP_GROW_C -# define BN_MP_RSHD_C -# define BN_S_MP_MONTGOMERY_REDUCE_FAST_C -# define BN_S_MP_SUB_C +#if defined(MP_MONTGOMERY_CALC_NORMALIZATION_C) +# define MP_2EXPT_C +# define MP_CMP_MAG_C +# define MP_COUNT_BITS_C +# define MP_MUL_2_C +# define MP_SET_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_MONTGOMERY_SETUP_C) +#if defined(MP_MONTGOMERY_REDUCE_C) +# define MP_CLAMP_C +# define MP_CMP_MAG_C +# define MP_GROW_C +# define MP_RSHD_C +# define S_MP_MONTGOMERY_REDUCE_FAST_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_MUL_C) -# define BN_S_MP_BALANCE_MUL_C -# define BN_S_MP_KARATSUBA_MUL_C -# define BN_S_MP_MUL_DIGS_C -# define BN_S_MP_MUL_DIGS_FAST_C -# define BN_S_MP_TOOM_MUL_C +#if defined(MP_MONTGOMERY_SETUP_C) #endif -#if defined(BN_MP_MUL_2_C) -# define BN_MP_GROW_C +#if defined(MP_MUL_C) +# define S_MP_BALANCE_MUL_C +# define S_MP_KARATSUBA_MUL_C +# define S_MP_MUL_DIGS_C +# define S_MP_MUL_DIGS_FAST_C +# define S_MP_TOOM_MUL_C #endif -#if defined(BN_MP_MUL_2D_C) -# define BN_MP_CLAMP_C -# define BN_MP_COPY_C -# define BN_MP_GROW_C -# define BN_MP_LSHD_C +#if defined(MP_MUL_2_C) +# define MP_GROW_C #endif -#if defined(BN_MP_MUL_D_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(MP_MUL_2D_C) +# define MP_CLAMP_C +# define MP_COPY_C +# define MP_GROW_C +# define MP_LSHD_C #endif -#if defined(BN_MP_MULMOD_C) -# define BN_MP_CLEAR_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_MOD_C -# define BN_MP_MUL_C +#if defined(MP_MUL_D_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_MP_NEG_C) -# define BN_MP_COPY_C -#endif - -#if defined(BN_MP_OR_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(MP_MULMOD_C) +# define MP_CLEAR_C +# define MP_INIT_SIZE_C +# define MP_MOD_C +# define MP_MUL_C #endif -#if defined(BN_MP_PACK_C) -# define BN_MP_CLEAR_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_COPY_C -# define BN_MP_PACK_COUNT_C -#endif - -#if defined(BN_MP_PACK_COUNT_C) -# define BN_MP_COUNT_BITS_C -#endif - -#if defined(BN_MP_PRIME_FERMAT_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_EXPTMOD_C -# define BN_MP_INIT_C -#endif - -#if defined(BN_MP_PRIME_FROBENIUS_UNDERWOOD_C) -# define BN_MP_ADD_C -# define BN_MP_ADD_D_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_EXCH_C -# define BN_MP_GCD_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_KRONECKER_C -# define BN_MP_MOD_C -# define BN_MP_MUL_2_C -# define BN_MP_MUL_C -# define BN_MP_MUL_D_C -# define BN_MP_SET_C -# define BN_MP_SET_U32_C -# define BN_MP_SQR_C -# define BN_MP_SUB_C -# define BN_MP_SUB_D_C -# define BN_S_MP_GET_BIT_C -#endif - -#if defined(BN_MP_PRIME_IS_PRIME_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_SET_C -# define BN_MP_IS_SQUARE_C -# define BN_MP_PRIME_MILLER_RABIN_C -# define BN_MP_PRIME_STRONG_LUCAS_SELFRIDGE_C -# define BN_MP_RAND_C -# define BN_MP_READ_RADIX_C -# define BN_MP_SET_C -# define BN_S_MP_PRIME_IS_DIVISIBLE_C -#endif - -#if defined(BN_MP_PRIME_MILLER_RABIN_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_CNT_LSB_C -# define BN_MP_DIV_2D_C -# define BN_MP_EXPTMOD_C -# define BN_MP_INIT_C -# define BN_MP_INIT_COPY_C -# define BN_MP_SQRMOD_C -# define BN_MP_SUB_D_C -#endif - -#if defined(BN_MP_PRIME_NEXT_PRIME_C) -# define BN_MP_ADD_D_C -# define BN_MP_CLEAR_C -# define BN_MP_CMP_D_C -# define BN_MP_INIT_C -# define BN_MP_MOD_D_C -# define BN_MP_PRIME_IS_PRIME_C -# define BN_MP_SET_C -# define BN_MP_SUB_D_C -#endif - -#if defined(BN_MP_PRIME_RABIN_MILLER_TRIALS_C) -#endif - -#if defined(BN_MP_PRIME_RAND_C) -# define BN_MP_ADD_D_C -# define BN_MP_DIV_2_C -# define BN_MP_FROM_UBIN_C -# define BN_MP_MUL_2_C -# define BN_MP_PRIME_IS_PRIME_C -# define BN_MP_SUB_D_C -# define BN_S_MP_PRIME_RANDOM_EX_C -# define BN_S_MP_RAND_CB_C -# define BN_S_MP_RAND_SOURCE_C -#endif - -#if defined(BN_MP_PRIME_STRONG_LUCAS_SELFRIDGE_C) -# define BN_MP_ADD_C -# define BN_MP_ADD_D_C -# define BN_MP_CLEAR_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_CNT_LSB_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_2D_C -# define BN_MP_DIV_2_C -# define BN_MP_GCD_C -# define BN_MP_INIT_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_KRONECKER_C -# define BN_MP_MOD_C -# define BN_MP_MUL_2_C -# define BN_MP_MUL_C -# define BN_MP_SET_C -# define BN_MP_SET_I32_C -# define BN_MP_SET_U32_C -# define BN_MP_SQR_C -# define BN_MP_SUB_C -# define BN_MP_SUB_D_C -# define BN_S_MP_GET_BIT_C -# define BN_S_MP_MUL_SI_C -#endif - -#if defined(BN_MP_RADIX_SIZE_C) -# define BN_MP_LOG_U32_C -#endif - -#if defined(BN_MP_RADIX_SMAP_C) -#endif - -#if defined(BN_MP_RAND_C) -# define BN_MP_GROW_C -# define BN_MP_RAND_SOURCE_C -# define BN_MP_ZERO_C -# define BN_S_MP_RAND_PLATFORM_C -# define BN_S_MP_RAND_SOURCE_C -#endif - -#if defined(BN_MP_READ_RADIX_C) -# define BN_MP_ADD_D_C -# define BN_MP_MUL_D_C -# define BN_MP_ZERO_C -#endif - -#if defined(BN_MP_REDUCE_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_INIT_COPY_C -# define BN_MP_LSHD_C -# define BN_MP_MOD_2D_C -# define BN_MP_MUL_C -# define BN_MP_RSHD_C -# define BN_MP_SET_C -# define BN_MP_SUB_C -# define BN_S_MP_MUL_DIGS_C -# define BN_S_MP_MUL_HIGH_DIGS_C -# define BN_S_MP_MUL_HIGH_DIGS_FAST_C -# define BN_S_MP_SUB_C +#if defined(MP_NEG_C) +# define MP_COPY_C +#endif + +#if defined(MP_OR_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_MP_REDUCE_2K_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_C -# define BN_MP_MUL_D_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C +#if defined(MP_PACK_C) +# define MP_CLEAR_C +# define MP_DIV_2D_C +# define MP_INIT_COPY_C +# define MP_PACK_COUNT_C +#endif + +#if defined(MP_PACK_COUNT_C) +# define MP_COUNT_BITS_C +#endif + +#if defined(MP_PRIME_FERMAT_C) +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_EXPTMOD_C +# define MP_INIT_C +#endif + +#if defined(MP_PRIME_FROBENIUS_UNDERWOOD_C) +# define MP_ADD_C +# define MP_ADD_D_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_COUNT_BITS_C +# define MP_EXCH_C +# define MP_GCD_C +# define MP_INIT_MULTI_C +# define MP_KRONECKER_C +# define MP_MOD_C +# define MP_MUL_2_C +# define MP_MUL_C +# define MP_MUL_D_C +# define MP_SET_C +# define MP_SET_U32_C +# define MP_SQR_C +# define MP_SUB_C +# define MP_SUB_D_C +# define S_MP_GET_BIT_C +#endif + +#if defined(MP_PRIME_IS_PRIME_C) +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_INIT_SET_C +# define MP_IS_SQUARE_C +# define MP_PRIME_MILLER_RABIN_C +# define MP_PRIME_STRONG_LUCAS_SELFRIDGE_C +# define MP_RAND_C +# define MP_READ_RADIX_C +# define MP_SET_C +# define S_MP_PRIME_IS_DIVISIBLE_C +#endif + +#if defined(MP_PRIME_MILLER_RABIN_C) +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CNT_LSB_C +# define MP_DIV_2D_C +# define MP_EXPTMOD_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_SQRMOD_C +# define MP_SUB_D_C +#endif + +#if defined(MP_PRIME_NEXT_PRIME_C) +# define MP_ADD_D_C +# define MP_CLEAR_C +# define MP_CMP_D_C +# define MP_INIT_C +# define MP_MOD_D_C +# define MP_PRIME_IS_PRIME_C +# define MP_SET_C +# define MP_SUB_D_C +#endif + +#if defined(MP_PRIME_RABIN_MILLER_TRIALS_C) +#endif + +#if defined(MP_PRIME_RAND_C) +# define MP_ADD_D_C +# define MP_DIV_2_C +# define MP_FROM_UBIN_C +# define MP_MUL_2_C +# define MP_PRIME_IS_PRIME_C +# define MP_SUB_D_C +# define S_MP_PRIME_RANDOM_EX_C +# define S_MP_RAND_CB_C +# define S_MP_RAND_SOURCE_C +#endif + +#if defined(MP_PRIME_STRONG_LUCAS_SELFRIDGE_C) +# define MP_ADD_C +# define MP_ADD_D_C +# define MP_CLEAR_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CNT_LSB_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_DIV_2_C +# define MP_GCD_C +# define MP_INIT_C +# define MP_INIT_MULTI_C +# define MP_KRONECKER_C +# define MP_MOD_C +# define MP_MUL_2_C +# define MP_MUL_C +# define MP_SET_C +# define MP_SET_I32_C +# define MP_SET_U32_C +# define MP_SQR_C +# define MP_SUB_C +# define MP_SUB_D_C +# define S_MP_GET_BIT_C +# define S_MP_MUL_SI_C +#endif + +#if defined(MP_PRIME_TAB_C) +#endif + +#if defined(MP_RADIX_SIZE_C) +# define MP_LOG_U32_C +#endif + +#if defined(MP_RADIX_SMAP_C) +#endif + +#if defined(MP_RAND_C) +# define MP_GROW_C +# define MP_RAND_SOURCE_C +# define MP_ZERO_C +# define S_MP_RAND_PLATFORM_C +# define S_MP_RAND_SOURCE_C +#endif + +#if defined(MP_READ_RADIX_C) +# define MP_ADD_D_C +# define MP_MUL_D_C +# define MP_ZERO_C +#endif + +#if defined(MP_REDUCE_C) +# define MP_ADD_C +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_INIT_COPY_C +# define MP_LSHD_C +# define MP_MOD_2D_C +# define MP_MUL_C +# define MP_RSHD_C +# define MP_SET_C +# define MP_SUB_C +# define S_MP_MUL_DIGS_C +# define S_MP_MUL_HIGH_DIGS_C +# define S_MP_MUL_HIGH_DIGS_FAST_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_REDUCE_2K_L_C) -# define BN_MP_CLEAR_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_C -# define BN_MP_MUL_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C +#if defined(MP_REDUCE_2K_C) +# define MP_CLEAR_C +# define MP_CMP_MAG_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_INIT_C +# define MP_MUL_D_C +# define S_MP_ADD_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_REDUCE_2K_SETUP_C) -# define BN_MP_2EXPT_C -# define BN_MP_CLEAR_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_INIT_C -# define BN_S_MP_SUB_C +#if defined(MP_REDUCE_2K_L_C) +# define MP_CLEAR_C +# define MP_CMP_MAG_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_INIT_C +# define MP_MUL_C +# define S_MP_ADD_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_REDUCE_2K_SETUP_L_C) -# define BN_MP_2EXPT_C -# define BN_MP_CLEAR_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_INIT_C -# define BN_S_MP_SUB_C +#if defined(MP_REDUCE_2K_SETUP_C) +# define MP_2EXPT_C +# define MP_CLEAR_C +# define MP_COUNT_BITS_C +# define MP_INIT_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_REDUCE_IS_2K_C) -# define BN_MP_COUNT_BITS_C +#if defined(MP_REDUCE_2K_SETUP_L_C) +# define MP_2EXPT_C +# define MP_CLEAR_C +# define MP_COUNT_BITS_C +# define MP_INIT_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_REDUCE_IS_2K_L_C) +#if defined(MP_REDUCE_IS_2K_C) +# define MP_COUNT_BITS_C #endif -#if defined(BN_MP_REDUCE_SETUP_C) -# define BN_MP_2EXPT_C -# define BN_MP_DIV_C +#if defined(MP_REDUCE_IS_2K_L_C) #endif -#if defined(BN_MP_ROOT_U32_C) -# define BN_MP_2EXPT_C -# define BN_MP_ADD_D_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DIV_C -# define BN_MP_EXCH_C -# define BN_MP_EXPT_U32_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MUL_C -# define BN_MP_MUL_D_C -# define BN_MP_SET_C -# define BN_MP_SUB_C -# define BN_MP_SUB_D_C +#if defined(MP_REDUCE_SETUP_C) +# define MP_2EXPT_C +# define MP_DIV_C #endif -#if defined(BN_MP_RSHD_C) -# define BN_MP_ZERO_C +#if defined(MP_ROOT_U32_C) +# define MP_2EXPT_C +# define MP_ADD_D_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_DIV_C +# define MP_EXCH_C +# define MP_EXPT_U32_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_MUL_D_C +# define MP_SET_C +# define MP_SUB_C +# define MP_SUB_D_C #endif -#if defined(BN_MP_SBIN_SIZE_C) -# define BN_MP_UBIN_SIZE_C +#if defined(MP_RSHD_C) +# define MP_ZERO_C #endif -#if defined(BN_MP_SET_C) +#if defined(MP_SBIN_SIZE_C) +# define MP_UBIN_SIZE_C #endif -#if defined(BN_MP_SET_DOUBLE_C) -# define BN_MP_DIV_2D_C -# define BN_MP_MUL_2D_C -# define BN_MP_SET_U64_C +#if defined(MP_SET_C) #endif -#if defined(BN_MP_SET_I32_C) -# define BN_MP_SET_U32_C +#if defined(MP_SET_DOUBLE_C) +# define MP_DIV_2D_C +# define MP_MUL_2D_C +# define MP_SET_U64_C #endif -#if defined(BN_MP_SET_I64_C) -# define BN_MP_SET_U64_C +#if defined(MP_SET_I32_C) +# define MP_SET_U32_C #endif -#if defined(BN_MP_SET_L_C) -# define BN_MP_SET_UL_C +#if defined(MP_SET_I64_C) +# define MP_SET_U64_C #endif -#if defined(BN_MP_SET_LL_C) -# define BN_MP_SET_ULL_C +#if defined(MP_SET_L_C) +# define MP_SET_UL_C #endif -#if defined(BN_MP_SET_U32_C) +#if defined(MP_SET_LL_C) +# define MP_SET_ULL_C #endif -#if defined(BN_MP_SET_U64_C) +#if defined(MP_SET_U32_C) #endif -#if defined(BN_MP_SET_UL_C) +#if defined(MP_SET_U64_C) #endif -#if defined(BN_MP_SET_ULL_C) +#if defined(MP_SET_UL_C) #endif -#if defined(BN_MP_SHRINK_C) +#if defined(MP_SET_ULL_C) #endif -#if defined(BN_MP_SIGNED_RSH_C) -# define BN_MP_ADD_D_C -# define BN_MP_DIV_2D_C -# define BN_MP_SUB_D_C +#if defined(MP_SHRINK_C) #endif -#if defined(BN_MP_SQR_C) -# define BN_S_MP_KARATSUBA_SQR_C -# define BN_S_MP_SQR_C -# define BN_S_MP_SQR_FAST_C -# define BN_S_MP_TOOM_SQR_C +#if defined(MP_SIGNED_RSH_C) +# define MP_ADD_D_C +# define MP_DIV_2D_C +# define MP_SUB_D_C #endif -#if defined(BN_MP_SQRMOD_C) -# define BN_MP_CLEAR_C -# define BN_MP_INIT_C -# define BN_MP_MOD_C -# define BN_MP_SQR_C +#if defined(MP_SQR_C) +# define S_MP_KARATSUBA_SQR_C +# define S_MP_SQR_C +# define S_MP_SQR_FAST_C +# define S_MP_TOOM_SQR_C #endif -#if defined(BN_MP_SQRT_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_C -# define BN_MP_CMP_MAG_C -# define BN_MP_DIV_2_C -# define BN_MP_DIV_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_C -# define BN_MP_INIT_COPY_C -# define BN_MP_RSHD_C -# define BN_MP_ZERO_C +#if defined(MP_SQRMOD_C) +# define MP_CLEAR_C +# define MP_INIT_C +# define MP_MOD_C +# define MP_SQR_C #endif -#if defined(BN_MP_SQRTMOD_PRIME_C) -# define BN_MP_ADD_D_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_D_C -# define BN_MP_COPY_C -# define BN_MP_DIV_2_C -# define BN_MP_EXPTMOD_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_KRONECKER_C -# define BN_MP_MOD_D_C -# define BN_MP_MULMOD_C -# define BN_MP_SET_C -# define BN_MP_SET_U32_C -# define BN_MP_SQRMOD_C -# define BN_MP_SUB_D_C -# define BN_MP_ZERO_C +#if defined(MP_SQRT_C) +# define MP_ADD_C +# define MP_CLEAR_C +# define MP_CMP_MAG_C +# define MP_DIV_2_C +# define MP_DIV_C +# define MP_EXCH_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_RSHD_C +# define MP_ZERO_C #endif -#if defined(BN_MP_SUB_C) -# define BN_MP_CMP_MAG_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C +#if defined(MP_SQRTMOD_PRIME_C) +# define MP_ADD_D_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_D_C +# define MP_COPY_C +# define MP_DIV_2_C +# define MP_EXPTMOD_C +# define MP_INIT_MULTI_C +# define MP_KRONECKER_C +# define MP_MOD_D_C +# define MP_MULMOD_C +# define MP_SET_C +# define MP_SET_U32_C +# define MP_SQRMOD_C +# define MP_SUB_D_C +# define MP_ZERO_C #endif -#if defined(BN_MP_SUB_D_C) -# define BN_MP_ADD_D_C -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(MP_SUB_C) +# define MP_CMP_MAG_C +# define S_MP_ADD_C +# define S_MP_SUB_C #endif -#if defined(BN_MP_SUBMOD_C) -# define BN_MP_CLEAR_C -# define BN_MP_INIT_C -# define BN_MP_MOD_C -# define BN_MP_SUB_C +#if defined(MP_SUB_D_C) +# define MP_ADD_D_C +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_MP_TO_RADIX_C) -# define BN_MP_CLEAR_C -# define BN_MP_DIV_D_C -# define BN_MP_INIT_COPY_C -# define BN_S_MP_REVERSE_C +#if defined(MP_SUBMOD_C) +# define MP_CLEAR_C +# define MP_INIT_C +# define MP_MOD_C +# define MP_SUB_C #endif -#if defined(BN_MP_TO_SBIN_C) -# define BN_MP_TO_UBIN_C +#if defined(MP_TO_RADIX_C) +# define MP_CLEAR_C +# define MP_DIV_D_C +# define MP_INIT_COPY_C +# define S_MP_REVERSE_C #endif -#if defined(BN_MP_TO_UBIN_C) -# define BN_MP_CLEAR_C -# define BN_MP_DIV_2D_C -# define BN_MP_INIT_COPY_C -# define BN_MP_UBIN_SIZE_C +#if defined(MP_TO_SBIN_C) +# define MP_TO_UBIN_C #endif -#if defined(BN_MP_UBIN_SIZE_C) -# define BN_MP_COUNT_BITS_C +#if defined(MP_TO_UBIN_C) +# define MP_CLEAR_C +# define MP_DIV_2D_C +# define MP_INIT_COPY_C +# define MP_UBIN_SIZE_C #endif -#if defined(BN_MP_UNPACK_C) -# define BN_MP_CLAMP_C -# define BN_MP_MUL_2D_C -# define BN_MP_ZERO_C -#endif - -#if defined(BN_MP_XOR_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -#endif - -#if defined(BN_MP_ZERO_C) -#endif - -#if defined(BN_PRIME_TAB_C) -#endif - -#if defined(BN_S_MP_ADD_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -#endif - -#if defined(BN_S_MP_BALANCE_MUL_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_MUL_C -#endif - -#if defined(BN_S_MP_EXPTMOD_C) -# define BN_MP_CLEAR_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_C -# define BN_MP_MOD_C -# define BN_MP_MUL_C -# define BN_MP_REDUCE_2K_L_C -# define BN_MP_REDUCE_2K_SETUP_L_C -# define BN_MP_REDUCE_C -# define BN_MP_REDUCE_SETUP_C -# define BN_MP_SET_C -# define BN_MP_SQR_C -#endif - -#if defined(BN_S_MP_EXPTMOD_FAST_C) -# define BN_MP_CLEAR_C -# define BN_MP_COPY_C -# define BN_MP_COUNT_BITS_C -# define BN_MP_DR_REDUCE_C -# define BN_MP_DR_SETUP_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_MOD_C -# define BN_MP_MONTGOMERY_CALC_NORMALIZATION_C -# define BN_MP_MONTGOMERY_REDUCE_C -# define BN_MP_MONTGOMERY_SETUP_C -# define BN_MP_MULMOD_C -# define BN_MP_MUL_C -# define BN_MP_REDUCE_2K_C -# define BN_MP_REDUCE_2K_SETUP_C -# define BN_MP_SET_C -# define BN_MP_SQR_C -# define BN_S_MP_MONTGOMERY_REDUCE_FAST_C +#if defined(MP_UBIN_SIZE_C) +# define MP_COUNT_BITS_C +#endif + +#if defined(MP_UNPACK_C) +# define MP_CLAMP_C +# define MP_MUL_2D_C +# define MP_ZERO_C +#endif + +#if defined(MP_XOR_C) +# define MP_CLAMP_C +# define MP_GROW_C +#endif + +#if defined(MP_ZERO_C) +#endif + +#if defined(S_MP_ADD_C) +# define MP_CLAMP_C +# define MP_GROW_C +#endif + +#if defined(S_MP_BALANCE_MUL_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_CLEAR_MULTI_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_C +#endif + +#if defined(S_MP_EXPTMOD_C) +# define MP_CLEAR_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_EXCH_C +# define MP_INIT_C +# define MP_MOD_C +# define MP_MUL_C +# define MP_REDUCE_2K_L_C +# define MP_REDUCE_2K_SETUP_L_C +# define MP_REDUCE_C +# define MP_REDUCE_SETUP_C +# define MP_SET_C +# define MP_SQR_C +#endif + +#if defined(S_MP_EXPTMOD_FAST_C) +# define MP_CLEAR_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_DR_REDUCE_C +# define MP_DR_SETUP_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C +# define MP_MOD_C +# define MP_MONTGOMERY_CALC_NORMALIZATION_C +# define MP_MONTGOMERY_REDUCE_C +# define MP_MONTGOMERY_SETUP_C +# define MP_MULMOD_C +# define MP_MUL_C +# define MP_REDUCE_2K_C +# define MP_REDUCE_2K_SETUP_C +# define MP_SET_C +# define MP_SQR_C +# define S_MP_MONTGOMERY_REDUCE_FAST_C #endif -#if defined(BN_S_MP_GET_BIT_C) +#if defined(S_MP_GET_BIT_C) #endif -#if defined(BN_S_MP_INVMOD_FAST_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COPY_C -# define BN_MP_DIV_2_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MOD_C -# define BN_MP_SET_C -# define BN_MP_SUB_C +#if defined(S_MP_INVMOD_FAST_C) +# define MP_ADD_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CMP_MAG_C +# define MP_COPY_C +# define MP_DIV_2_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_MOD_C +# define MP_SET_C +# define MP_SUB_C #endif -#if defined(BN_S_MP_INVMOD_SLOW_C) -# define BN_MP_ADD_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_CMP_C -# define BN_MP_CMP_D_C -# define BN_MP_CMP_MAG_C -# define BN_MP_COPY_C -# define BN_MP_DIV_2_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_MOD_C -# define BN_MP_SET_C -# define BN_MP_SUB_C -#endif - -#if defined(BN_S_MP_KARATSUBA_MUL_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_MUL_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C -#endif - -#if defined(BN_S_MP_KARATSUBA_SQR_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_SQR_C -# define BN_S_MP_ADD_C -# define BN_S_MP_SUB_C -#endif - -#if defined(BN_S_MP_MONTGOMERY_REDUCE_FAST_C) -# define BN_MP_CLAMP_C -# define BN_MP_CMP_MAG_C -# define BN_MP_GROW_C -# define BN_S_MP_SUB_C -#endif - -#if defined(BN_S_MP_MUL_DIGS_C) -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C -# define BN_S_MP_MUL_DIGS_FAST_C -#endif - -#if defined(BN_S_MP_MUL_DIGS_FAST_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -#endif - -#if defined(BN_S_MP_MUL_HIGH_DIGS_C) -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C -# define BN_S_MP_MUL_HIGH_DIGS_FAST_C -#endif - -#if defined(BN_S_MP_MUL_HIGH_DIGS_FAST_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C -#endif - -#if defined(BN_S_MP_PRIME_IS_DIVISIBLE_C) -# define BN_MP_MOD_D_C -#endif +#if defined(S_MP_INVMOD_SLOW_C) +# define MP_ADD_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CMP_MAG_C +# define MP_COPY_C +# define MP_DIV_2_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_MOD_C +# define MP_SET_C +# define MP_SUB_C +#endif + +#if defined(S_MP_KARATSUBA_MUL_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_C +# define S_MP_ADD_C +# define S_MP_SUB_C +#endif + +#if defined(S_MP_KARATSUBA_SQR_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_SQR_C +# define S_MP_ADD_C +# define S_MP_SUB_C +#endif + +#if defined(S_MP_MONTGOMERY_REDUCE_FAST_C) +# define MP_CLAMP_C +# define MP_CMP_MAG_C +# define MP_GROW_C +# define S_MP_SUB_C +#endif + +#if defined(S_MP_MUL_DIGS_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C +# define S_MP_MUL_DIGS_FAST_C +#endif + +#if defined(S_MP_MUL_DIGS_FAST_C) +# define MP_CLAMP_C +# define MP_GROW_C +#endif + +#if defined(S_MP_MUL_HIGH_DIGS_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C +# define S_MP_MUL_HIGH_DIGS_FAST_C +#endif + +#if defined(S_MP_MUL_HIGH_DIGS_FAST_C) +# define MP_CLAMP_C +# define MP_GROW_C +#endif + +#if defined(S_MP_PRIME_IS_DIVISIBLE_C) +# define MP_MOD_D_C +#endif -#if defined(BN_S_MP_RAND_JENKINS_C) -# define BN_S_MP_RAND_JENKINS_INIT_C +#if defined(S_MP_RAND_JENKINS_C) +# define S_MP_RAND_JENKINS_INIT_C #endif -#if defined(BN_S_MP_RAND_PLATFORM_C) +#if defined(S_MP_RAND_PLATFORM_C) #endif -#if defined(BN_S_MP_REVERSE_C) +#if defined(S_MP_REVERSE_C) #endif -#if defined(BN_S_MP_SQR_C) -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_EXCH_C -# define BN_MP_INIT_SIZE_C +#if defined(S_MP_SQR_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C #endif -#if defined(BN_S_MP_SQR_FAST_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(S_MP_SQR_FAST_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_S_MP_SUB_C) -# define BN_MP_CLAMP_C -# define BN_MP_GROW_C +#if defined(S_MP_SUB_C) +# define MP_CLAMP_C +# define MP_GROW_C #endif -#if defined(BN_S_MP_TOOM_MUL_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_DIV_2_C -# define BN_MP_DIV_3_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_MUL_2_C -# define BN_MP_MUL_C -# define BN_MP_SUB_C +#if defined(S_MP_TOOM_MUL_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_CLEAR_MULTI_C +# define MP_DIV_2_C +# define MP_DIV_3_C +# define MP_INIT_MULTI_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_2_C +# define MP_MUL_C +# define MP_SUB_C #endif -#if defined(BN_S_MP_TOOM_SQR_C) -# define BN_MP_ADD_C -# define BN_MP_CLAMP_C -# define BN_MP_CLEAR_C -# define BN_MP_DIV_2_C -# define BN_MP_INIT_C -# define BN_MP_INIT_SIZE_C -# define BN_MP_LSHD_C -# define BN_MP_MUL_2_C -# define BN_MP_MUL_C -# define BN_MP_SQR_C -# define BN_MP_SUB_C +#if defined(S_MP_TOOM_SQR_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_DIV_2_C +# define MP_INIT_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_2_C +# define MP_MUL_C +# define MP_SQR_C +# define MP_SUB_C #endif #ifdef LTM_INSIDE diff --git a/tommath_private.h b/tommath_private.h index d87ee9b2f..c44c72adb 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -1,8 +1,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#ifndef TOMMATH_PRIV_H_ -#define TOMMATH_PRIV_H_ +#ifndef TOMMATH_PRIVATE_H_ +#define TOMMATH_PRIVATE_H_ #include "tommath.h" #include "tommath_class.h" @@ -142,7 +142,7 @@ extern void MP_FREE(void *mem, size_t size); /* feature detection macro */ #define MP_STRINGIZE(x) MP__STRINGIZE(x) #define MP__STRINGIZE(x) ""#x"" -#define MP_HAS(x) (sizeof(MP_STRINGIZE(BN_##x##_C)) == 1u) +#define MP_HAS(x) (sizeof(MP_STRINGIZE(x##_C)) == 1u) /* TODO: Remove private_mp_word as soon as deprecated mp_word is removed from tommath. */ typedef private_mp_word mp_word; diff --git a/tommath_superclass.h b/tommath_superclass.h index bb606b5af..7179975b9 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -19,56 +19,56 @@ */ #ifdef SC_RSA_1_WITH_TESTS -# define BN_MP_ERROR_TO_STRING_C -# define BN_MP_FREAD_C -# define BN_MP_FWRITE_C -# define BN_MP_INCR_C -# define BN_MP_ISEVEN_C -# define BN_MP_ISODD_C -# define BN_MP_NEG_C -# define BN_MP_PRIME_FROBENIUS_UNDERWOOD_C -# define BN_MP_RADIX_SIZE_C -# define BN_MP_LOG_U32_C -# define BN_MP_RAND_C -# define BN_MP_REDUCE_C -# define BN_MP_REDUCE_2K_L_C -# define BN_MP_FROM_SBIN_C -# define BN_MP_ROOT_U32_C -# define BN_MP_SET_L_C -# define BN_MP_SET_UL_C -# define BN_MP_SBIN_SIZE_C -# define BN_MP_TO_RADIX_C -# define BN_MP_TO_SBIN_C -# define BN_S_MP_RAND_JENKINS_C -# define BN_S_MP_RAND_PLATFORM_C +# define MP_ERROR_TO_STRING_C +# define MP_FREAD_C +# define MP_FWRITE_C +# define MP_INCR_C +# define MP_ISEVEN_C +# define MP_ISODD_C +# define MP_NEG_C +# define MP_PRIME_FROBENIUS_UNDERWOOD_C +# define MP_RADIX_SIZE_C +# define MP_LOG_U32_C +# define MP_RAND_C +# define MP_REDUCE_C +# define MP_REDUCE_2K_L_C +# define MP_FROM_SBIN_C +# define MP_ROOT_U32_C +# define MP_SET_L_C +# define MP_SET_UL_C +# define MP_SBIN_SIZE_C +# define MP_TO_RADIX_C +# define MP_TO_SBIN_C +# define S_MP_RAND_JENKINS_C +# define S_MP_RAND_PLATFORM_C #endif /* Works for RSA only, mpi.o is 68KiB */ #if defined(SC_RSA_1) || defined (SC_RSA_1_WITH_TESTS) -# define BN_CUTOFFS_C -# define BN_MP_ADDMOD_C -# define BN_MP_CLEAR_MULTI_C -# define BN_MP_EXPTMOD_C -# define BN_MP_GCD_C -# define BN_MP_INIT_MULTI_C -# define BN_MP_INVMOD_C -# define BN_MP_LCM_C -# define BN_MP_MOD_C -# define BN_MP_MOD_D_C -# define BN_MP_MULMOD_C -# define BN_MP_PRIME_IS_PRIME_C -# define BN_MP_PRIME_RABIN_MILLER_TRIALS_C -# define BN_MP_PRIME_RAND_C -# define BN_MP_RADIX_SMAP_C -# define BN_MP_SET_INT_C -# define BN_MP_SHRINK_C -# define BN_MP_TO_UNSIGNED_BIN_C -# define BN_MP_UNSIGNED_BIN_SIZE_C -# define BN_PRIME_TAB_C -# define BN_S_MP_REVERSE_C +# define MP_CUTOFFS_C +# define MP_ADDMOD_C +# define MP_CLEAR_MULTI_C +# define MP_EXPTMOD_C +# define MP_GCD_C +# define MP_INIT_MULTI_C +# define MP_INVMOD_C +# define MP_LCM_C +# define MP_MOD_C +# define MP_MOD_D_C +# define MP_MULMOD_C +# define MP_PRIME_IS_PRIME_C +# define MP_PRIME_RABIN_MILLER_TRIALS_C +# define MP_PRIME_RAND_C +# define MP_RADIX_SMAP_C +# define MP_SET_INT_C +# define MP_SHRINK_C +# define MP_TO_UNSIGNED_BIN_C +# define MP_UNSIGNED_BIN_SIZE_C +# define MP_PRIME_TAB_C +# define S_MP_REVERSE_C /* other modifiers */ -# define BN_MP_DIV_SMALL /* Slower division, not critical */ +# define MP_DIV_SMALL /* Slower division, not critical */ /* here we are on the last pass so we turn things off. The functions classes are still there @@ -76,26 +76,26 @@ * like removing support for even moduli, etc... */ # ifdef LTM_LAST -# undef BN_MP_DR_IS_MODULUS_C -# undef BN_MP_DR_SETUP_C -# undef BN_MP_DR_REDUCE_C -# undef BN_MP_DIV_3_C -# undef BN_MP_REDUCE_2K_SETUP_C -# undef BN_MP_REDUCE_2K_C -# undef BN_MP_REDUCE_IS_2K_C -# undef BN_MP_REDUCE_SETUP_C -# undef BN_S_MP_BALANCE_MUL_C -# undef BN_S_MP_EXPTMOD_C -# undef BN_S_MP_INVMOD_FAST_C -# undef BN_S_MP_KARATSUBA_MUL_C -# undef BN_S_MP_KARATSUBA_SQR_C -# undef BN_S_MP_MUL_HIGH_DIGS_C -# undef BN_S_MP_MUL_HIGH_DIGS_FAST_C -# undef BN_S_MP_TOOM_MUL_C -# undef BN_S_MP_TOOM_SQR_C +# undef MP_DR_IS_MODULUS_C +# undef MP_DR_SETUP_C +# undef MP_DR_REDUCE_C +# undef MP_DIV_3_C +# undef MP_REDUCE_2K_SETUP_C +# undef MP_REDUCE_2K_C +# undef MP_REDUCE_IS_2K_C +# undef MP_REDUCE_SETUP_C +# undef S_MP_BALANCE_MUL_C +# undef S_MP_EXPTMOD_C +# undef S_MP_INVMOD_FAST_C +# undef S_MP_KARATSUBA_MUL_C +# undef S_MP_KARATSUBA_SQR_C +# undef S_MP_MUL_HIGH_DIGS_C +# undef S_MP_MUL_HIGH_DIGS_FAST_C +# undef S_MP_TOOM_MUL_C +# undef S_MP_TOOM_SQR_C # ifndef SC_RSA_1_WITH_TESTS -# undef BN_MP_REDUCE_C +# undef MP_REDUCE_C # endif /* To safely undefine these you have to make sure your RSA key won't exceed the Comba threshold @@ -103,9 +103,9 @@ * which means roughly speaking you can handle upto 2536-bit RSA keys with these defined without * trouble. */ -# undef BN_MP_MONTGOMERY_REDUCE_C -# undef BN_S_MP_MUL_DIGS_C -# undef BN_S_MP_SQR_C +# undef MP_MONTGOMERY_REDUCE_C +# undef S_MP_MUL_DIGS_C +# undef S_MP_SQR_C # endif #endif From e8fc3a58db29111f52c6ba7822f61d015e23aea5 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sat, 19 Oct 2019 19:39:29 +0200 Subject: [PATCH 020/304] removed code needed for MP_8BIT --- mp_prime_frobenius_underwood.c | 6 +----- tommath_class.h | 3 +-- 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c index ced0583a2..0e2ba64f1 100644 --- a/mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -39,12 +39,8 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) (a==14) || (a==18) || (a==23) || (a==26) || (a==28)) { continue; } - /* (32764^2 - 4) < 2^31, no bigint for >MP_8BIT needed) */ - mp_set_u32(&T1z, (uint32_t)a); - if ((err = mp_sqr(&T1z, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - - if ((err = mp_sub_d(&T1z, 4uL, &T1z)) != MP_OKAY) goto LBL_FU_ERR; + mp_set_i32(&T1z, (int32_t)((a * a) - 4)); if ((err = mp_kronecker(&T1z, N, &j)) != MP_OKAY) goto LBL_FU_ERR; diff --git a/tommath_class.h b/tommath_class.h index c6dcde1fd..52c5e45b5 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -659,10 +659,9 @@ # define MP_MUL_C # define MP_MUL_D_C # define MP_SET_C +# define MP_SET_I32_C # define MP_SET_U32_C -# define MP_SQR_C # define MP_SUB_C -# define MP_SUB_D_C # define S_MP_GET_BIT_C #endif From b34aac09cb680bae0b3df7d64ec2fb4a8cd10e69 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sat, 19 Oct 2019 16:24:55 +0200 Subject: [PATCH 021/304] remove extraneous comma --- tommath.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tommath.h b/tommath.h index b82477e05..29e9b207a 100644 --- a/tommath.h +++ b/tommath.h @@ -123,7 +123,7 @@ typedef enum { MP_MEM = -2, /* out of mem */ MP_VAL = -3, /* invalid input */ MP_ITER = -4, /* maximum iterations reached */ - MP_BUF = -5, /* buffer overflow, supplied buffer too small */ + MP_BUF = -5 /* buffer overflow, supplied buffer too small */ } mp_err; typedef enum { From e33311a1fed7dd03314155d7b89b557ac146c940 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sat, 19 Oct 2019 17:14:46 +0200 Subject: [PATCH 022/304] use enum type --- etc/2kprime.c | 2 +- etc/drprime.c | 3 ++- etc/mersenne.c | 7 ++++--- etc/pprime.c | 5 +++-- etc/tune.c | 6 ++++-- mp_prime_next_prime.c | 7 ++++--- s_mp_toom_mul.c | 3 ++- s_mp_toom_sqr.c | 3 ++- 8 files changed, 22 insertions(+), 14 deletions(-) diff --git a/etc/2kprime.c b/etc/2kprime.c index 55cb5f48f..fe25da3e6 100644 --- a/etc/2kprime.c +++ b/etc/2kprime.c @@ -8,7 +8,7 @@ int main(void) { char buf[2000]; size_t x; - int y; + mp_bool y; mp_int q, p; FILE *out; clock_t t1; diff --git a/etc/drprime.c b/etc/drprime.c index 146455e58..73838c40c 100644 --- a/etc/drprime.c +++ b/etc/drprime.c @@ -5,7 +5,8 @@ static int sizes[] = { 1+256/MP_DIGIT_BIT, 1+512/MP_DIGIT_BIT, 1+768/MP_DIGIT_BI int main(void) { - int res, x, y; + mp_bool res; + int x, y; char buf[4096]; FILE *out; mp_int a, b; diff --git a/etc/mersenne.c b/etc/mersenne.c index f6d7cb632..745847290 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -5,10 +5,11 @@ #include #include -static int is_mersenne(long s, int *pp) +static mp_err is_mersenne(long s, mp_bool *pp) { mp_int n, u; - int res, k; + mp_err res; + int k; *pp = 0; @@ -102,7 +103,7 @@ static int isprime(long k) int main(void) { - int pp; + mp_bool pp; long k; clock_t tt; diff --git a/etc/pprime.c b/etc/pprime.c index fa622f842..009a18cb9 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -179,10 +179,11 @@ static mp_digit prime_digit(void) /* makes a prime of at least k bits */ -static int pprime(int k, int li, mp_int *p, mp_int *q) +static mp_err pprime(int k, int li, mp_int *p, mp_int *q) { mp_int a, b, c, n, x, y, z, v; - int res, ii; + mp_err res; + int ii; static const mp_digit bases[] = { 2, 3, 5, 7, 11, 13, 17, 19 }; /* single digit ? */ diff --git a/etc/tune.c b/etc/tune.c index 389ce2f69..2260a701b 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -61,7 +61,8 @@ static int s_offset = 1; #define s_mp_mul(a, b, c) s_mp_mul_digs(a, b, c, (a)->used + (b)->used + 1) static uint64_t s_time_mul(int size) { - int x, e; + int x; + mp_err e; mp_int a, b, c, d; uint64_t t1; @@ -106,7 +107,8 @@ static uint64_t s_time_mul(int size) static uint64_t s_time_sqr(int size) { - int x, e; + int x; + mp_err e; mp_int a, b, c; uint64_t t1; diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index 3e2571a72..f8b22129e 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -10,9 +10,10 @@ */ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) { - int x, y, cmp; - mp_err err; - mp_bool res = MP_NO; + int x, y; + mp_ord cmp; + mp_err err; + mp_bool res = MP_NO; mp_digit res_tab[MP_PRIME_TAB_SIZE], step, kstep; mp_int b; diff --git a/s_mp_toom_mul.c b/s_mp_toom_mul.c index 0b2d57d72..93113b80c 100644 --- a/s_mp_toom_mul.c +++ b/s_mp_toom_mul.c @@ -32,7 +32,8 @@ mp_err s_mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_int S1, S2, T1, a0, a1, a2, b0, b1, b2; - int err, B, count; + int B, count; + mp_err err; /* init temps */ if ((err = mp_init_multi(&S1, &S2, &T1, NULL)) != MP_OKAY) { diff --git a/s_mp_toom_sqr.c b/s_mp_toom_sqr.c index 884a532a7..67c465c6a 100644 --- a/s_mp_toom_sqr.c +++ b/s_mp_toom_sqr.c @@ -22,7 +22,8 @@ mp_err s_mp_toom_sqr(const mp_int *a, mp_int *b) { mp_int S0, a0, a1, a2; mp_digit *tmpa, *tmpc; - mp_err err, B, count; + int B, count; + mp_err err; /* init temps */ From a1ab90be3cc6c7c473f9207a4f59a9885b728327 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sat, 19 Oct 2019 17:10:30 +0200 Subject: [PATCH 023/304] use enum value --- etc/2kprime.c | 8 ++++---- etc/drprime.c | 10 +++++----- etc/mersenne.c | 8 ++++---- 3 files changed, 13 insertions(+), 13 deletions(-) diff --git a/etc/2kprime.c b/etc/2kprime.c index fe25da3e6..95ed2de42 100644 --- a/etc/2kprime.c +++ b/etc/2kprime.c @@ -43,7 +43,7 @@ int main(void) /* quick test on q */ mp_prime_is_prime(&q, 1, &y); - if (y == 0) { + if (y == MP_NO) { continue; } @@ -51,20 +51,20 @@ int main(void) mp_sub_d(&q, 1uL, &p); mp_div_2(&p, &p); mp_prime_is_prime(&p, 3, &y); - if (y == 0) { + if (y == MP_NO) { continue; } /* test on q */ mp_prime_is_prime(&q, 3, &y); - if (y == 0) { + if (y == MP_NO) { continue; } break; } - if (y == 0) { + if (y == MP_NO) { ++sizes[x]; goto top; } diff --git a/etc/drprime.c b/etc/drprime.c index 73838c40c..64e31ef10 100644 --- a/etc/drprime.c +++ b/etc/drprime.c @@ -30,23 +30,23 @@ int main(void) a.used = sizes[x]; /* now loop */ - res = 0; + res = MP_NO; for (;;) { a.dp[0] += 4uL; if (a.dp[0] >= MP_MASK) break; mp_prime_is_prime(&a, 1, &res); - if (res == 0) continue; + if (res == MP_NO) continue; printf("."); fflush(stdout); mp_sub_d(&a, 1uL, &b); mp_div_2(&b, &b); mp_prime_is_prime(&b, 3, &res); - if (res == 0) continue; + if (res == MP_NO) continue; mp_prime_is_prime(&a, 3, &res); - if (res == 1) break; + if (res == MP_YES) break; } - if (res != 1) { + if (res != MP_YES) { printf("Error not DR modulus\n"); sizes[x] += 1; goto top; diff --git a/etc/mersenne.c b/etc/mersenne.c index 745847290..0c9f52fcf 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -11,7 +11,7 @@ static mp_err is_mersenne(long s, mp_bool *pp) mp_err res; int k; - *pp = 0; + *pp = MP_NO; if ((res = mp_init(&n)) != MP_OKAY) { return res; @@ -56,9 +56,9 @@ static mp_err is_mersenne(long s, mp_bool *pp) } /* if u == 0 then its prime */ - if (mp_iszero(&u) == 1) { + if (mp_iszero(&u) == MP_YES) { mp_prime_is_prime(&n, 8, pp); - if (*pp != 1) printf("FAILURE\n"); + if (*pp != MP_YES) printf("FAILURE\n"); } res = MP_OKAY; @@ -119,7 +119,7 @@ int main(void) return -1; } - if (pp == 1) { + if (pp == MP_YES) { /* count time */ tt = clock() - tt; From 99df8f7b25c7013ac4bee8807986074154b41a03 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 19 Oct 2019 18:33:39 +0200 Subject: [PATCH 024/304] mp_log_u32: remove obsolete todo --- mp_log_u32.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/mp_log_u32.c b/mp_log_u32.c index fb9dd5a0f..0523f7beb 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -66,10 +66,6 @@ static mp_digit s_digit_ilogb(mp_digit base, mp_digit n) return ret; } -/* TODO: output could be "int" because the output of mp_radix_size is int, too, - as is the output of mp_bitcount. - With the same problem: max size is INT_MAX * MP_DIGIT not INT_MAX only! -*/ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) { mp_err err; From 5c6391dd7cec7d91036cbff23a12b936dc39329a Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 19 Oct 2019 18:35:57 +0200 Subject: [PATCH 025/304] remove some MP_8BIT remnants --- mp_prime_is_prime.c | 5 ----- mp_prime_strong_lucas_selfridge.c | 1 - tommath.h | 12 ------------ tommath_private.h | 8 +------- 4 files changed, 1 insertion(+), 25 deletions(-) diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index 75d44c5f2..1a61bb6a1 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -100,11 +100,6 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) */ #ifndef LTM_USE_ONLY_MR if (t >= 0) { - /* - * Use a Frobenius-Underwood test instead of the Lucas-Selfridge test for - * MP_8BIT (It is unknown if the Lucas-Selfridge test works with 16-bit - * integers but the necesssary analysis is on the todo-list). - */ #ifdef LTM_USE_FROBENIUS_TEST err = mp_prime_frobenius_underwood(a, &res); if ((err != MP_OKAY) && (err != MP_ITER)) { diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index 693433627..895a48122 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -52,7 +52,6 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) { /* CZ TODO: choose better variable names! */ mp_int Dz, gcd, Np1, Uz, Vz, U2mz, V2mz, Qmz, Q2mz, Qkdz, T1z, T2z, T3z, T4z, Q2kdz; - /* CZ TODO: Some of them need the full 32 bit, hence the (temporary) exclusion of MP_8BIT */ int32_t D, Ds, J, sign, P, Q, r, s, u, Nbits; mp_err err; mp_bool oddness; diff --git a/tommath.h b/tommath.h index 29e9b207a..0aac377ce 100644 --- a/tommath.h +++ b/tommath.h @@ -6,23 +6,11 @@ #include #include -#ifdef MP_8BIT -# error "Support of 8-bit architectures has been dropped in this version of LTM." -#endif - #ifndef MP_NO_FILE # include #endif -#ifdef MP_8BIT -# ifdef _MSC_VER -# pragma message("8-bit (MP_8BIT) support is deprecated and will be dropped completely in the next version.") -# else -# warning "8-bit (MP_8BIT) support is deprecated and will be dropped completely in the next version." -# endif -#endif - #ifdef __cplusplus extern "C" { #endif diff --git a/tommath_private.h b/tommath_private.h index c44c72adb..45e0930f5 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -168,8 +168,6 @@ typedef private_mp_word mp_word; #ifndef MP_PREC # ifndef MP_LOW_MEM # define MP_PREC 32 /* default digits of precision */ -# elif defined(MP_8BIT) -# define MP_PREC 16 /* default digits of precision */ # else # define MP_PREC 8 /* default digits of precision */ # endif @@ -219,11 +217,7 @@ extern MP_PRIVATE const uint8_t s_mp_rmap_reverse[]; extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; /* number of primes */ -#ifdef MP_8BIT -# define MP_PRIME_TAB_SIZE 31 -#else -# define MP_PRIME_TAB_SIZE 256 -#endif +#define MP_PRIME_TAB_SIZE 256 #define MP_GET_ENDIANNESS(x) \ do{\ From f0c83aea6c397115f3ec3c28c4c1b35eeee5c80e Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 19 Oct 2019 19:25:55 +0200 Subject: [PATCH 026/304] split mp_log_u32 for more configurability --- libtommath_VS2008.vcproj | 8 +++ makefile | 7 +- makefile.mingw | 7 +- makefile.msvc | 7 +- makefile.shared | 7 +- makefile.unix | 7 +- mp_log_u32.c | 145 ++------------------------------------- s_mp_log.c | 82 ++++++++++++++++++++++ s_mp_log_d.c | 68 ++++++++++++++++++ tommath_class.h | 30 +++++--- tommath_private.h | 2 + 11 files changed, 206 insertions(+), 164 deletions(-) create mode 100644 s_mp_log.c create mode 100644 s_mp_log_d.c diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index ccbd1cc7f..d59f71cbd 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -880,6 +880,14 @@ RelativePath="s_mp_karatsuba_sqr.c" > + + + + diff --git a/makefile b/makefile index 117c84664..fb9c3910c 100644 --- a/makefile +++ b/makefile @@ -46,9 +46,10 @@ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_si mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o \ -s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ +s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ +s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 1a222f02b..c3a680fd8 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -49,9 +49,10 @@ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_si mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o \ -s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ +s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ +s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 35215b25b..84dce858b 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -41,9 +41,10 @@ mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shri mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj s_mp_exptmod.obj \ s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod_fast.obj s_mp_invmod_slow.obj s_mp_karatsuba_mul.obj \ -s_mp_karatsuba_sqr.obj s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj \ -s_mp_mul_high_digs.obj s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj \ -s_mp_rand_platform.obj s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj s_mp_toom_mul.obj s_mp_toom_sqr.obj +s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj \ +s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj \ +s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj \ +s_mp_toom_mul.obj s_mp_toom_sqr.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 4bfa0192e..336d648d9 100644 --- a/makefile.shared +++ b/makefile.shared @@ -43,9 +43,10 @@ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_si mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o \ -s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ +s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ +s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.unix b/makefile.unix index 4b7c49f31..6cad21092 100644 --- a/makefile.unix +++ b/makefile.unix @@ -50,9 +50,10 @@ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_si mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o \ -s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ +s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ +s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/mp_log_u32.c b/mp_log_u32.c index 0523f7beb..43748e533 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -3,78 +3,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* Compute log_{base}(a) */ -static mp_word s_pow(mp_word base, mp_word exponent) -{ - mp_word result = 1uLL; - while (exponent != 0u) { - if ((exponent & 1u) == 1u) { - result *= base; - } - exponent >>= 1; - base *= base; - } - - return result; -} - -static mp_digit s_digit_ilogb(mp_digit base, mp_digit n) -{ - mp_word bracket_low = 1uLL, bracket_mid, bracket_high, N; - mp_digit ret, high = 1uL, low = 0uL, mid; - - if (n < base) { - return 0uL; - } - if (n == base) { - return 1uL; - } - - bracket_high = (mp_word) base ; - N = (mp_word) n; - - while (bracket_high < N) { - low = high; - bracket_low = bracket_high; - high <<= 1; - bracket_high *= bracket_high; - } - - while (((mp_digit)(high - low)) > 1uL) { - mid = (low + high) >> 1; - bracket_mid = bracket_low * s_pow(base, (mp_word)(mid - low)); - - if (N < bracket_mid) { - high = mid ; - bracket_high = bracket_mid ; - } - if (N > bracket_mid) { - low = mid ; - bracket_low = bracket_mid ; - } - if (N == bracket_mid) { - return (mp_digit) mid; - } - } - - if (bracket_high == N) { - ret = high; - } else { - ret = low; - } - - return ret; -} - mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) { - mp_err err; - mp_ord cmp; - uint32_t high, low, mid; - mp_int bracket_low, bracket_high, bracket_mid, t, bi_base; - - err = MP_OKAY; - if (a->sign == MP_NEG) { return MP_VAL; } @@ -98,79 +28,16 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) return MP_OKAY; } - if (a->used == 1) { - *c = (uint32_t)s_digit_ilogb(base, a->dp[0]); - return err; - } - - cmp = mp_cmp_d(a, base); - if ((cmp == MP_LT) || (cmp == MP_EQ)) { - *c = cmp == MP_EQ; - return err; - } - - if ((err = - mp_init_multi(&bracket_low, &bracket_high, - &bracket_mid, &t, &bi_base, NULL)) != MP_OKAY) { - return err; - } - - low = 0u; - mp_set(&bracket_low, 1uL); - high = 1u; - - mp_set(&bracket_high, base); - - /* - A kind of Giant-step/baby-step algorithm. - Idea shamelessly stolen from https://programmingpraxis.com/2010/05/07/integer-logarithms/2/ - The effect is asymptotic, hence needs benchmarks to test if the Giant-step should be skipped - for small n. - */ - while (mp_cmp(&bracket_high, a) == MP_LT) { - low = high; - if ((err = mp_copy(&bracket_high, &bracket_low)) != MP_OKAY) { - goto LBL_ERR; - } - high <<= 1; - if ((err = mp_sqr(&bracket_high, &bracket_high)) != MP_OKAY) { - goto LBL_ERR; - } + if (MP_HAS(S_MP_LOG_D) && a->used == 1) { + *c = (uint32_t)s_mp_log_d(base, a->dp[0]); + return MP_OKAY; } - mp_set(&bi_base, base); - while ((high - low) > 1u) { - mid = (high + low) >> 1; - - if ((err = mp_expt_u32(&bi_base, (uint32_t)(mid - low), &t)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_mul(&bracket_low, &t, &bracket_mid)) != MP_OKAY) { - goto LBL_ERR; - } - cmp = mp_cmp(a, &bracket_mid); - if (cmp == MP_LT) { - high = mid; - mp_exch(&bracket_mid, &bracket_high); - } - if (cmp == MP_GT) { - low = mid; - mp_exch(&bracket_mid, &bracket_low); - } - if (cmp == MP_EQ) { - *c = mid; - goto LBL_END; - } + if (MP_HAS(S_MP_LOG)) { + return s_mp_log(a, base, c); } - *c = (mp_cmp(&bracket_high, a) == MP_EQ) ? high : low; - -LBL_END: -LBL_ERR: - mp_clear_multi(&bracket_low, &bracket_high, &bracket_mid, - &t, &bi_base, NULL); - return err; + return MP_VAL; } - #endif diff --git a/s_mp_log.c b/s_mp_log.c new file mode 100644 index 000000000..eba279ef7 --- /dev/null +++ b/s_mp_log.c @@ -0,0 +1,82 @@ +#include "tommath_private.h" +#ifdef S_MP_LOG_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) +{ + mp_err err; + mp_ord cmp; + uint32_t high, low, mid; + mp_int bracket_low, bracket_high, bracket_mid, t, bi_base; + + cmp = mp_cmp_d(a, base); + if ((cmp == MP_LT) || (cmp == MP_EQ)) { + *c = cmp == MP_EQ; + return MP_OKAY; + } + + if ((err = + mp_init_multi(&bracket_low, &bracket_high, + &bracket_mid, &t, &bi_base, NULL)) != MP_OKAY) { + return err; + } + + low = 0u; + mp_set(&bracket_low, 1uL); + high = 1u; + + mp_set(&bracket_high, base); + + /* + A kind of Giant-step/baby-step algorithm. + Idea shamelessly stolen from https://programmingpraxis.com/2010/05/07/integer-logarithms/2/ + The effect is asymptotic, hence needs benchmarks to test if the Giant-step should be skipped + for small n. + */ + while (mp_cmp(&bracket_high, a) == MP_LT) { + low = high; + if ((err = mp_copy(&bracket_high, &bracket_low)) != MP_OKAY) { + goto LBL_END; + } + high <<= 1; + if ((err = mp_sqr(&bracket_high, &bracket_high)) != MP_OKAY) { + goto LBL_END; + } + } + mp_set(&bi_base, base); + + while ((high - low) > 1u) { + mid = (high + low) >> 1; + + if ((err = mp_expt_u32(&bi_base, (uint32_t)(mid - low), &t)) != MP_OKAY) { + goto LBL_END; + } + if ((err = mp_mul(&bracket_low, &t, &bracket_mid)) != MP_OKAY) { + goto LBL_END; + } + cmp = mp_cmp(a, &bracket_mid); + if (cmp == MP_LT) { + high = mid; + mp_exch(&bracket_mid, &bracket_high); + } + if (cmp == MP_GT) { + low = mid; + mp_exch(&bracket_mid, &bracket_low); + } + if (cmp == MP_EQ) { + *c = mid; + goto LBL_END; + } + } + + *c = (mp_cmp(&bracket_high, a) == MP_EQ) ? high : low; + +LBL_END: + mp_clear_multi(&bracket_low, &bracket_high, &bracket_mid, + &t, &bi_base, NULL); + return err; +} + + +#endif diff --git a/s_mp_log_d.c b/s_mp_log_d.c new file mode 100644 index 000000000..44edd0755 --- /dev/null +++ b/s_mp_log_d.c @@ -0,0 +1,68 @@ +#include "tommath_private.h" +#ifdef S_MP_LOG_D_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +static mp_word s_pow(mp_word base, mp_word exponent) +{ + mp_word result = 1uLL; + while (exponent != 0u) { + if ((exponent & 1u) == 1u) { + result *= base; + } + exponent >>= 1; + base *= base; + } + + return result; +} + +mp_digit s_mp_log_d(mp_digit base, mp_digit n) +{ + mp_word bracket_low = 1uLL, bracket_mid, bracket_high, N; + mp_digit ret, high = 1uL, low = 0uL, mid; + + if (n < base) { + return 0uL; + } + if (n == base) { + return 1uL; + } + + bracket_high = (mp_word) base ; + N = (mp_word) n; + + while (bracket_high < N) { + low = high; + bracket_low = bracket_high; + high <<= 1; + bracket_high *= bracket_high; + } + + while (((mp_digit)(high - low)) > 1uL) { + mid = (low + high) >> 1; + bracket_mid = bracket_low * s_pow(base, (mp_word)(mid - low)); + + if (N < bracket_mid) { + high = mid ; + bracket_high = bracket_mid ; + } + if (N > bracket_mid) { + low = mid ; + bracket_low = bracket_mid ; + } + if (N == bracket_mid) { + return (mp_digit) mid; + } + } + + if (bracket_high == N) { + ret = high; + } else { + ret = low; + } + + return ret; +} + +#endif diff --git a/tommath_class.h b/tommath_class.h index 52c5e45b5..9b7f07541 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -153,6 +153,8 @@ # define S_MP_INVMOD_SLOW_C # define S_MP_KARATSUBA_MUL_C # define S_MP_KARATSUBA_SQR_C +# define S_MP_LOG_C +# define S_MP_LOG_D_C # define S_MP_MONTGOMERY_REDUCE_FAST_C # define S_MP_MUL_DIGS_C # define S_MP_MUL_DIGS_FAST_C @@ -529,17 +531,9 @@ #endif #if defined(MP_LOG_U32_C) -# define MP_CLEAR_MULTI_C -# define MP_CMP_C -# define MP_CMP_D_C -# define MP_COPY_C # define MP_COUNT_BITS_C -# define MP_EXCH_C -# define MP_EXPT_U32_C -# define MP_INIT_MULTI_C -# define MP_MUL_C -# define MP_SET_C -# define MP_SQR_C +# define S_MP_LOG_C +# define S_MP_LOG_D_C #endif #if defined(MP_LSHD_C) @@ -1121,6 +1115,22 @@ # define S_MP_SUB_C #endif +#if defined(S_MP_LOG_C) +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_COPY_C +# define MP_EXCH_C +# define MP_EXPT_U32_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_SET_C +# define MP_SQR_C +#endif + +#if defined(S_MP_LOG_D_C) +#endif + #if defined(S_MP_MONTGOMERY_REDUCE_FAST_C) # define MP_CLAMP_C # define MP_CMP_MAG_C diff --git a/tommath_private.h b/tommath_private.h index 45e0930f5..e285abc16 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -206,6 +206,8 @@ typedef int mp_prime_callback(unsigned char *dst, int len, void *dat); MP_PRIVATE mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat); MP_PRIVATE void s_mp_reverse(unsigned char *s, size_t len); MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); +MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); +MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); /* TODO: jenkins prng is not thread safe as of now */ MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; From d8da85a9a4bf90cabbe8528391b3bd30506c22cd Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 19 Oct 2019 19:54:20 +0200 Subject: [PATCH 027/304] mp_sqrtmod_prime: use mp_set --- mp_sqrtmod_prime.c | 4 ++-- tommath_class.h | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c index bf72005b3..03ebf8ae4 100644 --- a/mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -59,7 +59,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) } /* find a Z such that the Legendre symbol (Z|prime) == -1 */ - mp_set_u32(&Z, 2u); + mp_set(&Z, 2u); /* Z = 2 */ for (;;) { if ((err = mp_kronecker(&Z, prime, &legendre)) != MP_OKAY) goto cleanup; @@ -79,7 +79,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* T = n ^ Q mod prime */ if ((err = mp_copy(&S, &M)) != MP_OKAY) goto cleanup; /* M = S */ - mp_set_u32(&two, 2u); + mp_set(&two, 2u); for (;;) { if ((err = mp_copy(&T, &t1)) != MP_OKAY) goto cleanup; diff --git a/tommath_class.h b/tommath_class.h index 9b7f07541..f7812da01 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -945,7 +945,6 @@ # define MP_MOD_D_C # define MP_MULMOD_C # define MP_SET_C -# define MP_SET_U32_C # define MP_SQRMOD_C # define MP_SUB_D_C # define MP_ZERO_C From a825e0a3601f81ddf1a6753c45e5b74d44c23d78 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:37:46 +0200 Subject: [PATCH 028/304] handles MP_BUF in mp_error_to_string --- mp_error_to_string.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/mp_error_to_string.c b/mp_error_to_string.c index a6f6fc78e..1b34d02ed 100644 --- a/mp_error_to_string.c +++ b/mp_error_to_string.c @@ -17,6 +17,8 @@ const char *mp_error_to_string(mp_err code) return "Value out of range"; case MP_ITER: return "Max. iterations reached"; + case MP_BUF: + return "Buffer overflow"; default: return "Invalid error code"; } From 86aeb91bd8791aab279e3105fde6b07044f0f632 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:42:37 +0200 Subject: [PATCH 029/304] explicit operand for addition --- mp_radix_size.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mp_radix_size.c b/mp_radix_size.c index 387e0ec92..e9cfb9bb9 100644 --- a/mp_radix_size.c +++ b/mp_radix_size.c @@ -29,7 +29,7 @@ mp_err mp_radix_size(const mp_int *a, int radix, int *size) *size = (int)b; /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ - *size += 2 + (a->sign == MP_NEG); + *size += 2 + ((a->sign == MP_NEG) ? 1 : 0); LBL_ERR: return err; From 0de27bcbd92e7ec272fcfff6422d2d14aad748ff Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 17:27:04 +0200 Subject: [PATCH 030/304] explicit operator precedence --- mp_log_u32.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mp_log_u32.c b/mp_log_u32.c index 43748e533..2b49fe17b 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -28,7 +28,7 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) return MP_OKAY; } - if (MP_HAS(S_MP_LOG_D) && a->used == 1) { + if (MP_HAS(S_MP_LOG_D) && (a->used == 1)) { *c = (uint32_t)s_mp_log_d(base, a->dp[0]); return MP_OKAY; } From 4b7e73cddf34f6d5674c6078164edac500228d79 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 17:28:13 +0200 Subject: [PATCH 031/304] literal suffix --- mp_sqrtmod_prime.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c index 03ebf8ae4..723332ff4 100644 --- a/mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -59,7 +59,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) } /* find a Z such that the Legendre symbol (Z|prime) == -1 */ - mp_set(&Z, 2u); + mp_set(&Z, 2uL); /* Z = 2 */ for (;;) { if ((err = mp_kronecker(&Z, prime, &legendre)) != MP_OKAY) goto cleanup; @@ -79,7 +79,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* T = n ^ Q mod prime */ if ((err = mp_copy(&S, &M)) != MP_OKAY) goto cleanup; /* M = S */ - mp_set(&two, 2u); + mp_set(&two, 2uL); for (;;) { if ((err = mp_copy(&T, &t1)) != MP_OKAY) goto cleanup; From e2b95007a6c57f3155366eed729619496d541194 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:47:59 +0200 Subject: [PATCH 032/304] pprime uses mp_word --- etc/pprime.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/etc/pprime.c b/etc/pprime.c index 009a18cb9..944b5a6f1 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -8,6 +8,9 @@ #include #include "tommath.h" +/* TODO: Remove private_mp_word as soon as deprecated mp_word is removed from tommath. */ +typedef private_mp_word mp_word; + static int n_prime; static FILE *primes; From 8f7a3939f958ddec597df073fdfe8b4e12da61ba Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:51:51 +0200 Subject: [PATCH 033/304] name parameter in prototype --- etc/tune.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/etc/tune.c b/etc/tune.c index 2260a701b..5e887c703 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -156,7 +156,7 @@ struct tune_args { int increment_print; } args; -static void s_run(const char *name, uint64_t (*op)(int), int *cutoff) +static void s_run(const char *name, uint64_t (*op)(int size), int *cutoff) { int x, count = 0; uint64_t t1, t2; @@ -446,7 +446,7 @@ int main(int argc, char **argv) struct { const char *name; int *cutoff, *update; - uint64_t (*fn)(int); + uint64_t (*fn)(int size); } test[] = { #define T_MUL_SQR(n, o, f) { #n, &o##_CUTOFF, &(updated.o), MP_HAS(S_MP_##o) ? f : NULL } /* From 463205ecef022863297e387c2a20d4d6ab05388d Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:54:07 +0200 Subject: [PATCH 034/304] explicit condition --- etc/tune.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/etc/tune.c b/etc/tune.c index 5e887c703..e6850c69d 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -210,7 +210,7 @@ static long s_strtol(const char *str, char **endptr, const char *err) fprintf(stderr, "%s\n", err); exit(EXIT_FAILURE); } - if (endptr) *endptr = _endptr; + if (endptr != NULL) *endptr = _endptr; return val; } @@ -464,7 +464,7 @@ int main(int argc, char **argv) /* Turn all limits from bncore.c to the max */ set_cutoffs(&max_cutoffs); for (n = 0; n < sizeof(test)/sizeof(test[0]); ++n) { - if (test[n].fn) { + if (test[n].fn != NULL) { s_run(test[n].name, test[n].fn, test[n].cutoff); *test[n].update = *test[n].cutoff; *test[n].cutoff = INT_MAX; From 7f05df0a804ef52cb847f35d5ce536016afd639e Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 17:01:14 +0200 Subject: [PATCH 035/304] const parameter --- demo/mtest_opponent.c | 2 +- demo/shared.c | 2 +- demo/shared.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 7fbd35ebc..e77fec97a 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -6,7 +6,7 @@ #define LTM_MTEST_RAND_SEED 23 #endif -static void draw(mp_int *a) +static void draw(const mp_int *a) { ndraw(a, ""); } diff --git a/demo/shared.c b/demo/shared.c index e47e481d8..4e9880889 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -1,6 +1,6 @@ #include "shared.h" -void ndraw(mp_int *a, const char *name) +void ndraw(const mp_int *a, const char *name) { char *buf = NULL; int size; diff --git a/demo/shared.h b/demo/shared.h index 4d5eb53b2..14818acef 100644 --- a/demo/shared.h +++ b/demo/shared.h @@ -17,5 +17,5 @@ #define MP_WUR /* TODO: result checks disabled for now */ #include "tommath_private.h" -extern void ndraw(mp_int* a, const char* name); +extern void ndraw(const mp_int* a, const char* name); extern void print_header(void); From 315975db7a450ba7233ac88b9bb3825817e4eefb Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 16:58:40 +0200 Subject: [PATCH 036/304] remove useless initialization --- demo/shared.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/demo/shared.c b/demo/shared.c index 4e9880889..a4ac83322 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -2,7 +2,7 @@ void ndraw(const mp_int *a, const char *name) { - char *buf = NULL; + char *buf; int size; mp_radix_size(a, 10, &size); From 3995ece51bab45d58a5c7e599fd60abd97f1f8d1 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 17:05:55 +0200 Subject: [PATCH 037/304] const parameter --- demo/timing.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/timing.c b/demo/timing.c index f620b8cd4..ed906601c 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -21,7 +21,7 @@ #endif -static void ndraw(mp_int *a, const char *name) +static void ndraw(const mp_int *a, const char *name) { char buf[4096]; @@ -30,7 +30,7 @@ static void ndraw(mp_int *a, const char *name) printf("%s\n", buf); } -static void draw(mp_int *a) +static void draw(const mp_int *a) { ndraw(a, ""); } From 485be9de794478805b22ca96409745e8dd21f135 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Sun, 20 Oct 2019 17:07:43 +0200 Subject: [PATCH 038/304] explicit condition --- demo/timing.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/demo/timing.c b/demo/timing.c index ed906601c..47775dae8 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -149,7 +149,7 @@ int main(int argc, char **argv) printf("CLK_PER_SEC == %" PRIu64 "\n", CLK_PER_SEC); #ifdef LTM_TIMING_PRIME_IS_PRIME - if (should_test("prime", argc, argv)) { + if (should_test("prime", argc, argv) != 0) { for (m = 0; m < 2; ++m) { if (m == 0) { name = " Arnault"; @@ -185,7 +185,7 @@ int main(int argc, char **argv) } #endif - if (should_test("add", argc, argv)) { + if (should_test("add", argc, argv) != 0) { log = FOPEN("logs/add.log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; @@ -208,7 +208,7 @@ int main(int argc, char **argv) FCLOSE(log); } - if (should_test("sub", argc, argv)) { + if (should_test("sub", argc, argv) != 0) { log = FOPEN("logs/sub.log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; @@ -232,7 +232,7 @@ int main(int argc, char **argv) FCLOSE(log); } - if (should_test("mulsqr", argc, argv)) { + if (should_test("mulsqr", argc, argv) != 0) { /* do mult/square twice, first without karatsuba and second with */ old_kara_m = KARATSUBA_MUL_CUTOFF; old_kara_s = KARATSUBA_SQR_CUTOFF; @@ -291,7 +291,7 @@ int main(int argc, char **argv) } } - if (should_test("expt", argc, argv)) { + if (should_test("expt", argc, argv) != 0) { const char *primes[] = { /* 2K large moduli */ "179769313486231590772930519078902473361797697894230657273430081157732675805500963132708477322407536021120113879871393357658789768814416622492847430639474124377767893424865485276302219601246094119453082952085005768838150682342462881473913110540827237163350510684586239334100047359817950870678242457666208137217", @@ -369,7 +369,7 @@ int main(int argc, char **argv) FCLOSE(logd); } - if (should_test("invmod", argc, argv)) { + if (should_test("invmod", argc, argv) != 0) { log = FOPEN("logs/invmod.log", "w"); for (cnt = 4; cnt <= 32; cnt += 4) { SLEEP; From 7e5b56f2f3b749004d04ae22309501b07c19a0f2 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Tue, 15 Oct 2019 21:01:47 +0200 Subject: [PATCH 039/304] fix printf format --- etc/pprime.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/etc/pprime.c b/etc/pprime.c index 944b5a6f1..50be809ce 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -403,7 +403,7 @@ int main(void) pprime(k, li, &p, &q); t1 = clock() - t1; - printf("\n\nTook %d ticks, %d bits\n", t1, mp_count_bits(&p)); + printf("\n\nTook %lu ticks, %d bits\n", t1, mp_count_bits(&p)); mp_to_decimal(&p, buf, sizeof(buf)); printf("P == %s\n", buf); From 78d0c0c8430f0a9dec936b4b17e95647172a28e6 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Oct 2019 11:53:41 +0200 Subject: [PATCH 040/304] fix date in changelog...again :-\ [skip ci] --- changes.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/changes.txt b/changes.txt index ebf7382a0..1b3a7a3a4 100644 --- a/changes.txt +++ b/changes.txt @@ -1,4 +1,4 @@ -XXX XXth, 2019 +Oct 22nd, 2019 v1.2.0 -- A huge refactoring of the library happened - renaming, deprecating and replacing existing functions by improved API's. From 1d0affc0a9b317c39b92ea98d999adf5dc1f8f5d Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Oct 2019 11:54:34 +0200 Subject: [PATCH 041/304] update version --- makefile_include.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/makefile_include.mk b/makefile_include.mk index fb8ded18f..650b3e7e3 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -3,7 +3,7 @@ # #version of library -VERSION=1.2.0 +VERSION=1.2.0-develop VERSION_PC=1.2.0 VERSION_SO=3:0:2 From a29aa59baa529d341e2b234ff7331e827aba1ffb Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Mon, 21 Oct 2019 19:12:22 +0200 Subject: [PATCH 042/304] use size_t for mp_radix_size --- demo/shared.c | 10 +++++----- demo/test.c | 9 +++++---- mp_fwrite.c | 17 ++++++----------- mp_radix_size.c | 6 ++---- tommath.h | 2 +- 5 files changed, 19 insertions(+), 25 deletions(-) diff --git a/demo/shared.c b/demo/shared.c index a4ac83322..834b3a99d 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -3,19 +3,19 @@ void ndraw(const mp_int *a, const char *name) { char *buf; - int size; + size_t size; mp_radix_size(a, 10, &size); - buf = (char *)malloc((size_t) size); + buf = (char *)malloc(size); if (buf == NULL) { - fprintf(stderr, "\nndraw: malloc(%d) failed\n", size); + fprintf(stderr, "\nndraw: malloc(%zu) failed\n", size); exit(EXIT_FAILURE); } printf("%s: ", name); - mp_to_decimal(a, buf, (size_t) size); + mp_to_decimal(a, buf, size); printf("%s\n", buf); - mp_to_hex(a, buf, (size_t) size); + mp_to_hex(a, buf, size); printf("0x%s\n", buf); free(buf); diff --git a/demo/test.c b/demo/test.c index acb81c520..838f0eddf 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2275,9 +2275,10 @@ static int test_mp_radix_size(void) { mp_err err; mp_int a; - int radix, size; + int radix; + size_t size; /* *INDENT-OFF* */ - int results[65] = { + size_t results[65] = { 0, 0, 1627, 1027, 814, 702, 630, 581, 543, 514, 491, 471, 455, 441, 428, 418, 408, 399, 391, 384, 378, 372, 366, 361, 356, 352, 347, @@ -2302,7 +2303,7 @@ static int test_mp_radix_size(void) goto LBL_ERR; } if (size != results[radix]) { - fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", + fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", radix, size, results[radix]); goto LBL_ERR; } @@ -2311,7 +2312,7 @@ static int test_mp_radix_size(void) goto LBL_ERR; } if (size != (results[radix] + 1)) { - fprintf(stderr, "mp_radix_size: result for base %d was %d instead of %d\n", + fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", radix, size, results[radix]); goto LBL_ERR; } diff --git a/mp_fwrite.c b/mp_fwrite.c index f9d3ab04d..be78f7f28 100644 --- a/mp_fwrite.c +++ b/mp_fwrite.c @@ -8,24 +8,19 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) { char *buf; mp_err err; - int len; - size_t written; + size_t len, written; /* TODO: this function is not in this PR */ - if (MP_HAS(MP_RADIX_SIZE_OVERESTIMATE)) { - /* if ((err = mp_radix_size_overestimate(&t, base, &len)) != MP_OKAY) goto LBL_ERR; */ - } else { - if ((err = mp_radix_size(a, radix, &len)) != MP_OKAY) { - return err; - } + if ((err = mp_radix_size(a, radix, &len)) != MP_OKAY) { + return err; } - buf = (char *) MP_MALLOC((size_t)len); + buf = (char *) MP_MALLOC(len); if (buf == NULL) { return MP_MEM; } - if ((err = mp_to_radix(a, buf, (size_t)len, &written, radix)) != MP_OKAY) { + if ((err = mp_to_radix(a, buf, len, &written, radix)) != MP_OKAY) { goto LBL_ERR; } @@ -37,7 +32,7 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) LBL_ERR: - MP_FREE_BUFFER(buf, (size_t)len); + MP_FREE_BUFFER(buf, len); return err; } #endif diff --git a/mp_radix_size.c b/mp_radix_size.c index e9cfb9bb9..6c3e58220 100644 --- a/mp_radix_size.c +++ b/mp_radix_size.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* returns size of ASCII representation */ -mp_err mp_radix_size(const mp_int *a, int radix, int *size) +mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) { mp_err err; mp_int a_; @@ -26,10 +26,8 @@ mp_err mp_radix_size(const mp_int *a, int radix, int *size) goto LBL_ERR; } - *size = (int)b; - /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ - *size += 2 + ((a->sign == MP_NEG) ? 1 : 0); + *size = (size_t)b + 2U + ((a->sign == MP_NEG) ? 1U : 0U); LBL_ERR: return err; diff --git a/tommath.h b/tommath.h index 0aac377ce..a401be471 100644 --- a/tommath.h +++ b/tommath.h @@ -588,7 +588,7 @@ mp_err mp_to_sbin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *wr mp_err mp_read_radix(mp_int *a, const char *str, int radix) MP_WUR; mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, int radix) MP_WUR; -mp_err mp_radix_size(const mp_int *a, int radix, int *size) MP_WUR; +mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) MP_WUR; #ifndef MP_NO_FILE mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; From 9edd185f66ba92b1061aefa05c7925e68ffe18b5 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 4 Oct 2019 17:41:09 +0200 Subject: [PATCH 043/304] Addition of fast division (recursive divrem only) --- demo/test.c | 135 +++++++++++++++++++++++ libtommath_VS2008.vcproj | 12 +++ makefile | 12 +-- makefile.mingw | 12 +-- makefile.msvc | 12 +-- makefile.shared | 12 +-- makefile.unix | 12 +-- mp_div.c | 225 ++------------------------------------- s_mp_div_recursive.c | 182 +++++++++++++++++++++++++++++++ s_mp_div_school.c | 158 +++++++++++++++++++++++++++ s_mp_div_small.c | 51 +++++++++ tommath_class.h | 74 ++++++++++--- tommath_private.h | 5 + tommath_superclass.h | 2 +- 14 files changed, 641 insertions(+), 263 deletions(-) create mode 100644 s_mp_div_recursive.c create mode 100644 s_mp_div_school.c create mode 100644 s_mp_div_small.c diff --git a/demo/test.c b/demo/test.c index 838f0eddf..bfe934ba9 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2327,6 +2327,139 @@ static int test_mp_radix_size(void) } +/* Some larger values to test the fast division algorithm */ +static int test_s_mp_div_recursive(void) +{ + mp_int a, b, c_q, c_r, d_q, d_r; + int size, err; + + if ((err = mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)) != MP_OKAY) { + goto LBL_ERR; + } + + for (size = MP_KARATSUBA_MUL_CUTOFF; size < 3 * MP_KARATSUBA_MUL_CUTOFF; size += 10) { + fprintf(stderr,"sizes = %d / %d\n", 10 * size, size); + /* Relation 10:1 */ + if ((err = mp_rand(&a, 10 * size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = mp_rand(&b, size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { + goto LBL_ERR; + } + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "1. Recursive division failed at sizes %d / %d, wrong quotient\n", + 10 * size, size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "1. Recursive division failed at sizes %d / %d, wrong remainder\n", + 10 * size, size); + goto LBL_ERR; + } + fprintf(stderr,"sizes = %d / %d\n", 2 * size, size); + /* Relation 2:1 */ + if ((err = mp_rand(&a, 2 * size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = mp_rand(&b, size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { + goto LBL_ERR; + } + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "2. Recursive division failed at sizes %d / %d, wrong quotient\n", + 2 * size, size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "2. Recursive division failed at sizes %d / %d, wrong remainder\n", + 2 * size, size); + goto LBL_ERR; + } + fprintf(stderr,"sizes = %d / %d\n", 3 * size, 2 * size); + /* Upper limit 3:2 */ + if ((err = mp_rand(&a, 3 * size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = mp_rand(&b, 2 * size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { + goto LBL_ERR; + } + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "3. Recursive division failed at sizes %d / %d, wrong quotient\n", + 3 * size, 2 * size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "3. Recursive division failed at sizes %d / %d, wrong remainder\n", + 3 * size, 2 * size); + goto LBL_ERR; + } + } + + mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); + return EXIT_FAILURE; +} + +static int test_s_mp_div_small(void) +{ + mp_int a, b, c_q, c_r, d_q, d_r; + int size, err; + + if ((err = mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)) != MP_OKAY) { + goto LBL_ERR; + } + for (size = 1; size < MP_KARATSUBA_MUL_CUTOFF; size += 10) { + fprintf(stderr,"sizes = %d / %d\n", 2 * size, size); + /* Relation 10:1 */ + if ((err = mp_rand(&a, 2 * size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = mp_rand(&b, size)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_small(&a, &b, &c_q, &c_r)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { + goto LBL_ERR; + } + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "1. Small division failed at sizes %d / %d, wrong quotient\n", + 2 * size, size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "1. Small division failed at sizes %d / %d, wrong remainder\n", + 2 * size, size); + goto LBL_ERR; + } + } + mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); + return EXIT_FAILURE; +} + static int test_mp_read_write_ubin(void) { @@ -2500,6 +2633,8 @@ static int unit_tests(int argc, char **argv) T1(mp_sqrt, MP_SQRT), T1(mp_sqrtmod_prime, MP_SQRTMOD_PRIME), T1(mp_xor, MP_XOR), + T2(s_mp_div_recursive, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), + T2(s_mp_div_small, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), T1(s_mp_balance_mul, S_MP_BALANCE_MUL), T1(s_mp_karatsuba_mul, S_MP_KARATSUBA_MUL), T1(s_mp_karatsuba_sqr, S_MP_KARATSUBA_SQR), diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index d59f71cbd..481b5423c 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -852,6 +852,18 @@ RelativePath="s_mp_balance_mul.c" > + + + + + + diff --git a/makefile b/makefile index f713a8596..77150049a 100644 --- a/makefile +++ b/makefile @@ -44,12 +44,12 @@ mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l. mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ -s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ -s_mp_toom_mul.o s_mp_toom_sqr.o +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ +s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index c3a680fd8..3c3fcf7b5 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -47,12 +47,12 @@ mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l. mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ -s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ -s_mp_toom_mul.o s_mp_toom_sqr.o +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ +s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 9a13ffede..c42ca12de 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -39,12 +39,12 @@ mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is mp_root_u32.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj \ mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj mp_sqr.obj \ mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ -mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj s_mp_exptmod.obj \ -s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod_fast.obj s_mp_invmod_slow.obj s_mp_karatsuba_mul.obj \ -s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj \ -s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj \ -s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj \ -s_mp_toom_mul.obj s_mp_toom_sqr.obj +mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj \ +s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj \ +s_mp_invmod_fast.obj s_mp_invmod_slow.obj s_mp_karatsuba_mul.obj s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj \ +s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj \ +s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj \ +s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj s_mp_toom_mul.obj s_mp_toom_sqr.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 336d648d9..2c9c0e323 100644 --- a/makefile.shared +++ b/makefile.shared @@ -41,12 +41,12 @@ mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l. mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ -s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ -s_mp_toom_mul.o s_mp_toom_sqr.o +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ +s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.unix b/makefile.unix index 9a35dee8e..d9d7727d7 100644 --- a/makefile.unix +++ b/makefile.unix @@ -48,12 +48,12 @@ mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l. mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o \ -s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o \ -s_mp_mul_digs_fast.o s_mp_mul_high_digs.o s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o \ -s_mp_toom_mul.o s_mp_toom_sqr.o +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ +s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/mp_div.c b/mp_div.c index 1c87005ac..5fd957280 100644 --- a/mp_div.c +++ b/mp_div.c @@ -3,13 +3,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#ifdef MP_DIV_SMALL - -/* slower bit-bang division... also smaller */ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) { - mp_int ta, tb, tq, q; - int n, n2; mp_err err; /* is divisor zero ? */ @@ -17,7 +12,7 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) return MP_VAL; } - /* if a < b then q=0, r = a */ + /* if a < b then q = 0, r = a */ if (mp_cmp_mag(a, b) == MP_LT) { if (d != NULL) { err = mp_copy(a, d); @@ -30,221 +25,17 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) return err; } - /* init our temps */ - if ((err = mp_init_multi(&ta, &tb, &tq, &q, NULL)) != MP_OKAY) { - return err; - } - - - mp_set(&tq, 1uL); - n = mp_count_bits(a) - mp_count_bits(b); - if ((err = mp_abs(a, &ta)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_abs(b, &tb)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_mul_2d(&tb, n, &tb)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_mul_2d(&tq, n, &tq)) != MP_OKAY) goto LBL_ERR; - - while (n-- >= 0) { - if (mp_cmp(&tb, &ta) != MP_GT) { - if ((err = mp_sub(&ta, &tb, &ta)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_add(&q, &tq, &q)) != MP_OKAY) goto LBL_ERR; - } - if ((err = mp_div_2d(&tb, 1, &tb, NULL)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_div_2d(&tq, 1, &tq, NULL)) != MP_OKAY) goto LBL_ERR; - } - - /* now q == quotient and ta == remainder */ - n = a->sign; - n2 = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - if (c != NULL) { - mp_exch(c, &q); - c->sign = MP_IS_ZERO(c) ? MP_ZPOS : n2; - } - if (d != NULL) { - mp_exch(d, &ta); - d->sign = MP_IS_ZERO(d) ? MP_ZPOS : n; - } -LBL_ERR: - mp_clear_multi(&ta, &tb, &tq, &q, NULL); - return err; -} - -#else - -/* integer signed division. - * c*b + d == a [e.g. a/b, c=quotient, d=remainder] - * HAC pp.598 Algorithm 14.20 - * - * Note that the description in HAC is horribly - * incomplete. For example, it doesn't consider - * the case where digits are removed from 'x' in - * the inner loop. It also doesn't consider the - * case that y has fewer than three digits, etc.. - * - * The overall algorithm is as described as - * 14.20 from HAC but fixed to treat these cases. -*/ -mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) -{ - mp_int q, x, y, t1, t2; - int n, t, i, norm; - mp_sign neg; - mp_err err; - - /* is divisor zero ? */ - if (MP_IS_ZERO(b)) { - return MP_VAL; - } - - /* if a < b then q=0, r = a */ - if (mp_cmp_mag(a, b) == MP_LT) { - if (d != NULL) { - err = mp_copy(a, d); - } else { - err = MP_OKAY; - } - if (c != NULL) { - mp_zero(c); - } - return err; - } - - if ((err = mp_init_size(&q, a->used + 2)) != MP_OKAY) { - return err; - } - q.used = a->used + 2; - - if ((err = mp_init(&t1)) != MP_OKAY) goto LBL_Q; - - if ((err = mp_init(&t2)) != MP_OKAY) goto LBL_T1; - - if ((err = mp_init_copy(&x, a)) != MP_OKAY) goto LBL_T2; - - if ((err = mp_init_copy(&y, b)) != MP_OKAY) goto LBL_X; - - /* fix the sign */ - neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - x.sign = y.sign = MP_ZPOS; - - /* normalize both x and y, ensure that y >= b/2, [b == 2**MP_DIGIT_BIT] */ - norm = mp_count_bits(&y) % MP_DIGIT_BIT; - if (norm < (MP_DIGIT_BIT - 1)) { - norm = (MP_DIGIT_BIT - 1) - norm; - if ((err = mp_mul_2d(&x, norm, &x)) != MP_OKAY) goto LBL_Y; - if ((err = mp_mul_2d(&y, norm, &y)) != MP_OKAY) goto LBL_Y; + if (MP_HAS(S_MP_DIV_RECURSIVE) + && (b->used > MP_KARATSUBA_MUL_CUTOFF) + && (b->used <= ((a->used)/3*2))) { + err = s_mp_div_recursive(a, b, c, d); + } else if (MP_HAS(S_MP_DIV_SCHOOL)) { + err = s_mp_div_school(a, b, c, d); } else { - norm = 0; - } - - /* note hac does 0 based, so if used==5 then its 0,1,2,3,4, e.g. use 4 */ - n = x.used - 1; - t = y.used - 1; - - /* while (x >= y*b**n-t) do { q[n-t] += 1; x -= y*b**{n-t} } */ - /* y = y*b**{n-t} */ - if ((err = mp_lshd(&y, n - t)) != MP_OKAY) goto LBL_Y; - - while (mp_cmp(&x, &y) != MP_LT) { - ++(q.dp[n - t]); - if ((err = mp_sub(&x, &y, &x)) != MP_OKAY) goto LBL_Y; - } - - /* reset y by shifting it back down */ - mp_rshd(&y, n - t); - - /* step 3. for i from n down to (t + 1) */ - for (i = n; i >= (t + 1); i--) { - if (i > x.used) { - continue; - } - - /* step 3.1 if xi == yt then set q{i-t-1} to b-1, - * otherwise set q{i-t-1} to (xi*b + x{i-1})/yt */ - if (x.dp[i] == y.dp[t]) { - q.dp[(i - t) - 1] = ((mp_digit)1 << (mp_digit)MP_DIGIT_BIT) - (mp_digit)1; - } else { - mp_word tmp; - tmp = (mp_word)x.dp[i] << (mp_word)MP_DIGIT_BIT; - tmp |= (mp_word)x.dp[i - 1]; - tmp /= (mp_word)y.dp[t]; - if (tmp > (mp_word)MP_MASK) { - tmp = MP_MASK; - } - q.dp[(i - t) - 1] = (mp_digit)(tmp & (mp_word)MP_MASK); - } - - /* while (q{i-t-1} * (yt * b + y{t-1})) > - xi * b**2 + xi-1 * b + xi-2 - - do q{i-t-1} -= 1; - */ - q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] + 1uL) & (mp_digit)MP_MASK; - do { - q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] - 1uL) & (mp_digit)MP_MASK; - - /* find left hand */ - mp_zero(&t1); - t1.dp[0] = ((t - 1) < 0) ? 0u : y.dp[t - 1]; - t1.dp[1] = y.dp[t]; - t1.used = 2; - if ((err = mp_mul_d(&t1, q.dp[(i - t) - 1], &t1)) != MP_OKAY) goto LBL_Y; - - /* find right hand */ - t2.dp[0] = ((i - 2) < 0) ? 0u : x.dp[i - 2]; - t2.dp[1] = x.dp[i - 1]; /* i >= 1 always holds */ - t2.dp[2] = x.dp[i]; - t2.used = 3; - } while (mp_cmp_mag(&t1, &t2) == MP_GT); - - /* step 3.3 x = x - q{i-t-1} * y * b**{i-t-1} */ - if ((err = mp_mul_d(&y, q.dp[(i - t) - 1], &t1)) != MP_OKAY) goto LBL_Y; - - if ((err = mp_lshd(&t1, (i - t) - 1)) != MP_OKAY) goto LBL_Y; - - if ((err = mp_sub(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; - - /* if x < 0 then { x = x + y*b**{i-t-1}; q{i-t-1} -= 1; } */ - if (x.sign == MP_NEG) { - if ((err = mp_copy(&y, &t1)) != MP_OKAY) goto LBL_Y; - if ((err = mp_lshd(&t1, (i - t) - 1)) != MP_OKAY) goto LBL_Y; - if ((err = mp_add(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; - - q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] - 1uL) & MP_MASK; - } + err = s_mp_div_small(a, b, c, d); } - /* now q is the quotient and x is the remainder - * [which we have to normalize] - */ - - /* get sign before writing to c */ - x.sign = (x.used == 0) ? MP_ZPOS : a->sign; - - if (c != NULL) { - mp_clamp(&q); - mp_exch(&q, c); - c->sign = neg; - } - - if (d != NULL) { - if ((err = mp_div_2d(&x, norm, &x, NULL)) != MP_OKAY) goto LBL_Y; - mp_exch(&x, d); - } - - err = MP_OKAY; - -LBL_Y: - mp_clear(&y); -LBL_X: - mp_clear(&x); -LBL_T2: - mp_clear(&t2); -LBL_T1: - mp_clear(&t1); -LBL_Q: - mp_clear(&q); return err; } - #endif -#endif diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c new file mode 100644 index 000000000..67b4a054d --- /dev/null +++ b/s_mp_div_recursive.c @@ -0,0 +1,182 @@ +#include "tommath_private.h" +#ifdef S_MP_DIV_RECURSIVE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* + Direct implementation of algorithms 1.8 "RecursiveDivRem" and 1.9 "UnbalancedDivision" + from: + + Brent, Richard P., and Paul Zimmermann. "Modern computer arithmetic" + Vol. 18. Cambridge University Press, 2010 + Available online at https://arxiv.org/pdf/1004.4710 + + pages 19ff. in the above online document. +*/ + +static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) +{ + mp_err err; + int m, k; + mp_int A1, A2, B1, B0, Q1, Q0, R1, R0, t; + + m = a->used - b->used; + if (m < MP_KARATSUBA_MUL_CUTOFF) { + return s_mp_div_school(a, b, q, r); + } + + if ((err = mp_init_multi(&A1, &A2, &B1, &B0, &Q1, &Q0, &R1, &R0, &t, NULL)) != MP_OKAY) { + goto LBL_ERR; + } + + /* k = floor(m/2) */ + k = m/2; + + /* B1 = b / beta^k, B0 = b % beta^k*/ + if ((err = mp_div_2d(b, k * MP_DIGIT_BIT, &B1, &B0)) != MP_OKAY) goto LBL_ERR; + + /* (Q1, R1) = RecursiveDivRem(A / beta^(2k), B1) */ + if ((err = mp_div_2d(a, 2*k * MP_DIGIT_BIT, &A1, &t)) != MP_OKAY) goto LBL_ERR; + if ((err = s_mp_recursion(&A1, &B1, &Q1, &R1)) != MP_OKAY) goto LBL_ERR; + + /* A1 = (R1 * beta^(2k)) + (A % beta^(2k)) - (Q1 * B0 * beta^k) */ + if ((err = mp_lshd(&R1, 2*k)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&R1, &t, &A1)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_mul(&Q1, &B0, &t)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_lshd(&t, k)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; + + /* while A1 < 0 do Q1 = Q1 - 1, A1 = A1 + (beta^k * B) */ + if ((err = mp_mul_2d(b, k * MP_DIGIT_BIT, &t)) != MP_OKAY) goto LBL_ERR; + while (mp_cmp_d(&A1, 0) == MP_LT) { + if ((err = mp_decr(&Q1)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; + } + + /* (Q0, R0) = RecursiveDivRem(A1 / beta^(k), B1) */ + if ((err = mp_div_2d(&A1, k * MP_DIGIT_BIT, &A1, &t)) != MP_OKAY) goto LBL_ERR; + if ((err = s_mp_recursion(&A1, &B1, &Q0, &R0)) != MP_OKAY) goto LBL_ERR; + + /* A2 = (R0*beta^k) + (A1 % beta^k) - (Q0*B0) */ + if ((err = mp_lshd(&R0, k)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&R0, &t, &A2)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_mul(&Q0, &B0, &t)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&A2, &t, &A2)) != MP_OKAY) goto LBL_ERR; + + /* while A2 < 0 do Q0 = Q0 - 1, A2 = A2 + B */ + while (mp_cmp_d(&A2, 0) == MP_LT) { + if ((err = mp_decr(&Q0)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&A2, b, &A2)) != MP_OKAY) goto LBL_ERR; + } + /* return q = (Q1*beta^k) + Q0, r = A2 */ + if (q != NULL) { + if ((err = mp_lshd(&Q1, k)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&Q1, &Q0, q)) != MP_OKAY) goto LBL_ERR; + } + if (r != NULL) { + if ((err = mp_copy(&A2, r)) != MP_OKAY) goto LBL_ERR; + } + +LBL_ERR: + mp_clear_multi(&A1, &A2, &B1, &B0, &Q1, &Q0, &R1, &R0, &t, NULL); + return err; +} + + +mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) +{ + int j, m, n, sigma; + mp_err err; + mp_sign neg; + mp_digit msb_b, msb; + mp_int A, B, Q, Q1, R, A_div, A_mod; + + if ((err = mp_init_multi(&A, &B, &Q, &Q1, &R, &A_div, &A_mod, NULL)) != MP_OKAY) { + goto LBL_ERR; + } + + /* most significant bit of a limb */ + /* assumes MP_DIGIT_MAX < (sizeof(mp_digit) * CHAR_BIT) */ + msb = (MP_DIGIT_MAX + (mp_digit)(1)) >> 1; + + /* + Method to compute sigma shamelessly stolen from + + J. Burnikel and J. Ziegler, "Fast recursive division", Research Report + MPI-I-98-1-022, Max-Planck-Institut fuer Informatik, Saarbruecken, Germany, + October 1998. (available online) + + Vid. section 2.3. + */ + m = MP_KARATSUBA_MUL_CUTOFF; + while (m <= b->used) { + m <<= 1; + } + j = (b->used + m - 1) / m; + n = j * m; + + sigma = MP_DIGIT_BIT * (n - b->used); + msb_b = b->dp[b->used - 1]; + while (msb_b < msb) { + sigma++; + msb_b <<= 1; + } + /* Use that sigma to normalize B */ + if ((err = mp_mul_2d(b, sigma, &B)) != MP_OKAY) { + goto LBL_ERR; + } + if ((err = mp_mul_2d(a, sigma, &A)) != MP_OKAY) { + goto LBL_ERR; + } + + /* fix the sign */ + neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + A.sign = B.sign = MP_ZPOS; + + /* + If the magnitude of "A" is not more more than twice that of "B" we can work + on them directly, otherwise we need to work at "A" in chunks + */ + n = B.used; + m = A.used - B.used; + + /* Q = 0 */ + mp_zero(&Q); + while (m > n) { + /* (q, r) = RecursveDivRem(A / (beta^(m-n)), B) */ + j = (m - n) * MP_DIGIT_BIT; + if ((err = mp_div_2d(&A, j, &A_div, &A_mod)) != MP_OKAY) goto LBL_ERR; + if ((err = s_mp_recursion(&A_div, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; + /* Q = (Q*beta!(n)) + q */ + if ((err = mp_mul_2d(&Q, n * MP_DIGIT_BIT, &Q)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; + /* A = (r * beta^(m-n)) + (A % beta^(m-n))*/ + if ((err = mp_mul_2d(&R, (m - n) * MP_DIGIT_BIT, &R)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&R, &A_mod, &A)) != MP_OKAY) goto LBL_ERR; + /* m = m - n */ + m = m - n; + } + /* (q, r) = RecursveDivRem(A, B) */ + if ((err = s_mp_recursion(&A, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; + /* Q = (Q * beta^m) + q, R = r */ + if ((err = mp_mul_2d(&Q, m * MP_DIGIT_BIT, &Q)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; + + /* get sign before writing to c */ + Q.sign = (Q.used == 0) ? MP_ZPOS : a->sign; + + if (q != NULL) { + mp_exch(&Q, q); + q->sign = neg; + } + if (r != NULL) { + /* de-normalize the remainder */ + if ((err = mp_div_2d(&R, sigma, &R, NULL)) != MP_OKAY) goto LBL_ERR; + mp_exch(&R, r); + } +LBL_ERR: + mp_clear_multi(&A, &B, &Q, &Q1, &R, &A_div, &A_mod, NULL); + return err; +} + +#endif diff --git a/s_mp_div_school.c b/s_mp_div_school.c new file mode 100644 index 000000000..6ff427a1b --- /dev/null +++ b/s_mp_div_school.c @@ -0,0 +1,158 @@ +#include "tommath_private.h" +#ifdef S_MP_DIV_SCHOOL_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* integer signed division. + * c*b + d == a [e.g. a/b, c=quotient, d=remainder] + * HAC pp.598 Algorithm 14.20 + * + * Note that the description in HAC is horribly + * incomplete. For example, it doesn't consider + * the case where digits are removed from 'x' in + * the inner loop. It also doesn't consider the + * case that y has fewer than three digits, etc.. + * + * The overall algorithm is as described as + * 14.20 from HAC but fixed to treat these cases. +*/ +mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) +{ + mp_int q, x, y, t1, t2; + int n, t, i, norm; + mp_sign neg; + mp_err err; + + if ((err = mp_init_size(&q, a->used + 2)) != MP_OKAY) { + return err; + } + q.used = a->used + 2; + + if ((err = mp_init(&t1)) != MP_OKAY) goto LBL_Q; + if ((err = mp_init(&t2)) != MP_OKAY) goto LBL_T1; + if ((err = mp_init_copy(&x, a)) != MP_OKAY) goto LBL_T2; + if ((err = mp_init_copy(&y, b)) != MP_OKAY) goto LBL_X; + + /* fix the sign */ + neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + x.sign = y.sign = MP_ZPOS; + + /* normalize both x and y, ensure that y >= b/2, [b == 2**MP_DIGIT_BIT] */ + norm = mp_count_bits(&y) % MP_DIGIT_BIT; + if (norm < (MP_DIGIT_BIT - 1)) { + norm = (MP_DIGIT_BIT - 1) - norm; + if ((err = mp_mul_2d(&x, norm, &x)) != MP_OKAY) goto LBL_Y; + if ((err = mp_mul_2d(&y, norm, &y)) != MP_OKAY) goto LBL_Y; + } else { + norm = 0; + } + + /* note hac does 0 based, so if used==5 then its 0,1,2,3,4, e.g. use 4 */ + n = x.used - 1; + t = y.used - 1; + + /* while (x >= y*b**n-t) do { q[n-t] += 1; x -= y*b**{n-t} } */ + /* y = y*b**{n-t} */ + if ((err = mp_lshd(&y, n - t)) != MP_OKAY) goto LBL_Y; + + while (mp_cmp(&x, &y) != MP_LT) { + ++(q.dp[n - t]); + if ((err = mp_sub(&x, &y, &x)) != MP_OKAY) goto LBL_Y; + } + + /* reset y by shifting it back down */ + mp_rshd(&y, n - t); + + /* step 3. for i from n down to (t + 1) */ + for (i = n; i >= (t + 1); i--) { + if (i > x.used) { + continue; + } + + /* step 3.1 if xi == yt then set q{i-t-1} to b-1, + * otherwise set q{i-t-1} to (xi*b + x{i-1})/yt */ + if (x.dp[i] == y.dp[t]) { + q.dp[(i - t) - 1] = ((mp_digit)1 << (mp_digit)MP_DIGIT_BIT) - (mp_digit)1; + } else { + mp_word tmp; + tmp = (mp_word)x.dp[i] << (mp_word)MP_DIGIT_BIT; + tmp |= (mp_word)x.dp[i - 1]; + tmp /= (mp_word)y.dp[t]; + if (tmp > (mp_word)MP_MASK) { + tmp = MP_MASK; + } + q.dp[(i - t) - 1] = (mp_digit)(tmp & (mp_word)MP_MASK); + } + + /* while (q{i-t-1} * (yt * b + y{t-1})) > + xi * b**2 + xi-1 * b + xi-2 + + do q{i-t-1} -= 1; + */ + q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] + 1uL) & (mp_digit)MP_MASK; + do { + q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] - 1uL) & (mp_digit)MP_MASK; + + /* find left hand */ + mp_zero(&t1); + t1.dp[0] = ((t - 1) < 0) ? 0u : y.dp[t - 1]; + t1.dp[1] = y.dp[t]; + t1.used = 2; + if ((err = mp_mul_d(&t1, q.dp[(i - t) - 1], &t1)) != MP_OKAY) goto LBL_Y; + + /* find right hand */ + t2.dp[0] = ((i - 2) < 0) ? 0u : x.dp[i - 2]; + t2.dp[1] = x.dp[i - 1]; /* i >= 1 always holds */ + t2.dp[2] = x.dp[i]; + t2.used = 3; + } while (mp_cmp_mag(&t1, &t2) == MP_GT); + + /* step 3.3 x = x - q{i-t-1} * y * b**{i-t-1} */ + if ((err = mp_mul_d(&y, q.dp[(i - t) - 1], &t1)) != MP_OKAY) goto LBL_Y; + if ((err = mp_lshd(&t1, (i - t) - 1)) != MP_OKAY) goto LBL_Y; + if ((err = mp_sub(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; + + /* if x < 0 then { x = x + y*b**{i-t-1}; q{i-t-1} -= 1; } */ + if (x.sign == MP_NEG) { + if ((err = mp_copy(&y, &t1)) != MP_OKAY) goto LBL_Y; + if ((err = mp_lshd(&t1, (i - t) - 1)) != MP_OKAY) goto LBL_Y; + if ((err = mp_add(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; + + q.dp[(i - t) - 1] = (q.dp[(i - t) - 1] - 1uL) & MP_MASK; + } + } + + /* now q is the quotient and x is the remainder + * [which we have to normalize] + */ + + /* get sign before writing to c */ + x.sign = (x.used == 0) ? MP_ZPOS : a->sign; + + if (c != NULL) { + mp_clamp(&q); + mp_exch(&q, c); + c->sign = neg; + } + + if (d != NULL) { + if ((err = mp_div_2d(&x, norm, &x, NULL)) != MP_OKAY) goto LBL_Y; + mp_exch(&x, d); + } + + err = MP_OKAY; + +LBL_Y: + mp_clear(&y); +LBL_X: + mp_clear(&x); +LBL_T2: + mp_clear(&t2); +LBL_T1: + mp_clear(&t1); +LBL_Q: + mp_clear(&q); + return err; +} + +#endif diff --git a/s_mp_div_small.c b/s_mp_div_small.c new file mode 100644 index 000000000..56b1335d9 --- /dev/null +++ b/s_mp_div_small.c @@ -0,0 +1,51 @@ +#include "tommath_private.h" +#ifdef S_MP_DIV_SMALL_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* slower bit-bang division... also smaller */ +mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) +{ + mp_int ta, tb, tq, q; + int n; + mp_sign sign; + mp_err err; + + /* init our temps */ + if ((err = mp_init_multi(&ta, &tb, &tq, &q, NULL)) != MP_OKAY) { + return err; + } + + mp_set(&tq, 1uL); + n = mp_count_bits(a) - mp_count_bits(b); + if ((err = mp_abs(a, &ta)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_abs(b, &tb)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_mul_2d(&tb, n, &tb)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_mul_2d(&tq, n, &tq)) != MP_OKAY) goto LBL_ERR; + + while (n-- >= 0) { + if (mp_cmp(&tb, &ta) != MP_GT) { + if ((err = mp_sub(&ta, &tb, &ta)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&q, &tq, &q)) != MP_OKAY) goto LBL_ERR; + } + if ((err = mp_div_2d(&tb, 1, &tb, NULL)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_div_2d(&tq, 1, &tq, NULL)) != MP_OKAY) goto LBL_ERR; + } + + /* now q == quotient and ta == remainder */ + + sign = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + if (c != NULL) { + mp_exch(c, &q); + c->sign = MP_IS_ZERO(c) ? MP_ZPOS : sign; + } + if (d != NULL) { + mp_exch(d, &ta); + d->sign = MP_IS_ZERO(d) ? MP_ZPOS : a->sign; + } +LBL_ERR: + mp_clear_multi(&ta, &tb, &tq, &q, NULL); + return err; +} + +#endif diff --git a/tommath_class.h b/tommath_class.h index f7812da01..5373d91d3 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -146,6 +146,9 @@ # define MP_ZERO_C # define S_MP_ADD_C # define S_MP_BALANCE_MUL_C +# define S_MP_DIV_RECURSIVE_C +# define S_MP_DIV_SCHOOL_C +# define S_MP_DIV_SMALL_C # define S_MP_EXPTMOD_C # define S_MP_EXPTMOD_FAST_C # define S_MP_GET_BIT_C @@ -250,24 +253,12 @@ #endif #if defined(MP_DIV_C) -# define MP_ADD_C -# define MP_CLAMP_C -# define MP_CLEAR_C -# define MP_CMP_C # define MP_CMP_MAG_C # define MP_COPY_C -# define MP_COUNT_BITS_C -# define MP_DIV_2D_C -# define MP_EXCH_C -# define MP_INIT_C -# define MP_INIT_COPY_C -# define MP_INIT_SIZE_C -# define MP_LSHD_C -# define MP_MUL_2D_C -# define MP_MUL_D_C -# define MP_RSHD_C -# define MP_SUB_C # define MP_ZERO_C +# define S_MP_DIV_RECURSIVE_C +# define S_MP_DIV_SCHOOL_C +# define S_MP_DIV_SMALL_C #endif #if defined(MP_DIV_2_C) @@ -1022,6 +1013,59 @@ # define MP_MUL_C #endif +#if defined(S_MP_DIV_RECURSIVE_C) +# define MP_ADD_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_D_C +# define MP_COPY_C +# define MP_DECR_C +# define MP_DIV_2D_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_LSHD_C +# define MP_MUL_2D_C +# define MP_MUL_C +# define MP_SUB_C +# define MP_ZERO_C +# define S_MP_DIV_SCHOOL_C +# define S_MP_RECURSION_C +#endif + +#if defined(S_MP_DIV_SCHOOL_C) +# define MP_ADD_C +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_CMP_C +# define MP_CMP_MAG_C +# define MP_COPY_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_EXCH_C +# define MP_INIT_C +# define MP_INIT_COPY_C +# define MP_INIT_SIZE_C +# define MP_LSHD_C +# define MP_MUL_2D_C +# define MP_MUL_D_C +# define MP_RSHD_C +# define MP_SUB_C +# define MP_ZERO_C +#endif + +#if defined(S_MP_DIV_SMALL_C) +# define MP_ABS_C +# define MP_ADD_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_MUL_2D_C +# define MP_SET_C +# define MP_SUB_C +#endif + #if defined(S_MP_EXPTMOD_C) # define MP_CLEAR_C # define MP_COPY_C diff --git a/tommath_private.h b/tommath_private.h index 8fcc99138..e37def440 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -213,6 +213,11 @@ MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); + +MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r); +MP_PRIVATE mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); +MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); + /* TODO: jenkins prng is not thread safe as of now */ MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); diff --git a/tommath_superclass.h b/tommath_superclass.h index 7179975b9..6961a5968 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -68,7 +68,7 @@ # define S_MP_REVERSE_C /* other modifiers */ -# define MP_DIV_SMALL /* Slower division, not critical */ + /* here we are on the last pass so we turn things off. The functions classes are still there From 31e64aa640db47e65224f567e5dd65933c4db820 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 22 Oct 2019 15:04:36 +0200 Subject: [PATCH 044/304] mp_prime_next_prime: use mp_bool for bbs_style --- mp_prime_next_prime.c | 10 +++++----- tommath.h | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index f8b22129e..3256e37c2 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -6,9 +6,9 @@ /* finds the next prime after the number "a" using "t" trials * of Miller-Rabin. * - * bbs_style = 1 means the prime must be congruent to 3 mod 4 + * bbs_style = MP_YES means the prime must be congruent to 3 mod 4 */ -mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) +mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) { int x, y; mp_ord cmp; @@ -29,7 +29,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) continue; } if (cmp != MP_GT) { - if ((bbs_style == 1) && ((s_mp_prime_tab[x] & 3u) != 3u)) { + if ((bbs_style == MP_YES) && ((s_mp_prime_tab[x] & 3u) != 3u)) { /* try again until we get a prime congruent to 3 mod 4 */ continue; } else { @@ -42,7 +42,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) } /* generate a prime congruent to 3 mod 4 or 1/3 mod 4? */ - if (bbs_style == 1) { + if (bbs_style == MP_YES) { kstep = 4; } else { kstep = 2; @@ -50,7 +50,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) /* at this point we will use a combination of a sieve and Miller-Rabin */ - if (bbs_style == 1) { + if (bbs_style == MP_YES) { /* if a mod 4 != 3 subtract the correct value to make it so */ if ((a->dp[0] & 3u) != 3u) { if ((err = mp_sub_d(a, (a->dp[0] & 3u) + 1u, a)) != MP_OKAY) { diff --git a/tommath.h b/tommath.h index a401be471..9421c6da2 100644 --- a/tommath.h +++ b/tommath.h @@ -550,9 +550,9 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) MP_WUR; /* finds the next prime after the number "a" using "t" trials * of Miller-Rabin. * - * bbs_style = 1 means the prime must be congruent to 3 mod 4 + * bbs_style = MP_YES means the prime must be congruent to 3 mod 4 */ -mp_err mp_prime_next_prime(mp_int *a, int t, int bbs_style) MP_WUR; +mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) MP_WUR; /* makes a truly random prime of a given size (bits), * From 3180c66ca6da9ad275d06e5985af1ce47229ea2e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 23 Oct 2019 18:17:20 +0200 Subject: [PATCH 045/304] also use MP_YES/NO in tests --- demo/test.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/demo/test.c b/demo/test.c index bfe934ba9..0f0152a55 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1061,7 +1061,7 @@ static int test_mp_prime_next_prime(void) /* edge cases */ mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, 0)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 2u) != MP_EQ) { @@ -1072,7 +1072,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, 1)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1083,7 +1083,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, 0)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1094,7 +1094,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, 1)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1104,7 +1104,7 @@ static int test_mp_prime_next_prime(void) goto LBL_ERR; } mp_set(&a, 8); - if ((err = mp_prime_next_prime(&a, 5, 1)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 11u) != MP_EQ) { @@ -1130,7 +1130,7 @@ static int test_mp_prime_next_prime(void) if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { goto LBL_ERR; } - if ((err = mp_prime_next_prime(&a, 5, 0)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { @@ -1160,7 +1160,7 @@ static int test_mp_prime_next_prime(void) if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { goto LBL_ERR; } - if ((err = mp_prime_next_prime(&a, 5, 1)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { @@ -1284,7 +1284,7 @@ static int test_mp_read_radix(void) char *s = fgets(buf, sizeof(buf), stdin); if (s != buf) break; mp_read_radix(&a, buf, 10); - mp_prime_next_prime(&a, 5, 1); + mp_prime_next_prime(&a, 5, MP_YES); mp_to_radix(&a, buf, sizeof(buf), NULL, 10); printf("%s, %lu\n", buf, (unsigned long)a.dp[0] & 3uL); } From 00b263f303c22cab1334813fe1aea640a8a273c9 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 22 Oct 2019 17:52:26 +0200 Subject: [PATCH 046/304] remove private_mp_word --- etc/pprime.c | 3 --- tommath.h | 7 ------- tommath_private.h | 12 +++++++++--- 3 files changed, 9 insertions(+), 13 deletions(-) diff --git a/etc/pprime.c b/etc/pprime.c index 50be809ce..411e446a5 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -8,9 +8,6 @@ #include #include "tommath.h" -/* TODO: Remove private_mp_word as soon as deprecated mp_word is removed from tommath. */ -typedef private_mp_word mp_word; - static int n_prime; static FILE *primes; diff --git a/tommath.h b/tommath.h index 9421c6da2..f415a7fef 100644 --- a/tommath.h +++ b/tommath.h @@ -51,21 +51,14 @@ extern "C" { * [any size beyond that is ok provided it doesn't overflow the data type] */ - #if defined(MP_16BIT) typedef uint16_t mp_digit; -typedef uint32_t private_mp_word; # define MP_DIGIT_BIT 15 #elif defined(MP_64BIT) -/* for GCC only on supported platforms */ typedef uint64_t mp_digit; -#if defined(__GNUC__) -typedef unsigned long private_mp_word __attribute__((mode(TI))); -#endif # define MP_DIGIT_BIT 60 #else typedef uint32_t mp_digit; -typedef uint64_t private_mp_word; # ifdef MP_31BIT /* * This is an extension that uses 31-bit digits. diff --git a/tommath_private.h b/tommath_private.h index e37def440..b18663b8c 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -148,9 +148,6 @@ extern void MP_FREE(void *mem, size_t size); #define MP__STRINGIZE(x) ""#x"" #define MP_HAS(x) (sizeof(MP_STRINGIZE(x##_C)) == 1u) -/* TODO: Remove private_mp_word as soon as deprecated mp_word is removed from tommath. */ -typedef private_mp_word mp_word; - #define MP_MIN(x, y) (((x) < (y)) ? (x) : (y)) #define MP_MAX(x, y) (((x) > (y)) ? (x) : (y)) @@ -167,6 +164,15 @@ typedef private_mp_word mp_word; #define MP_WARRAY (1 << ((MP_SIZEOF_BITS(mp_word) - (2 * MP_DIGIT_BIT)) + 1)) +#if defined(MP_16BIT) +typedef uint32_t mp_word; +#elif defined(MP_64BIT) +typedef unsigned long mp_word __attribute__((mode(TI))); +#else +typedef uint64_t mp_word; +#endif + +MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == 2 * sizeof(mp_digit)) /* default precision */ #ifndef MP_PREC From 14642642f9443463f6c7a4a8a08e5df894460e92 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 22 Oct 2019 18:01:08 +0200 Subject: [PATCH 047/304] add prefix to cutoff variables --- demo/mtest_opponent.c | 4 ++-- demo/test.c | 6 +++--- demo/timing.c | 12 ++++++------ etc/tune.c | 42 +++++++++++++++++++++--------------------- mp_cutoffs.c | 8 ++++---- tommath.h | 8 ++++---- tommath_private.h | 5 ----- 7 files changed, 40 insertions(+), 45 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index e77fec97a..827c3f52e 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -37,8 +37,8 @@ static int mtest_opponent(void) #ifndef MP_FIXED_CUTOFFS /* force KARA and TOOM to enable despite cutoffs */ - KARATSUBA_SQR_CUTOFF = KARATSUBA_MUL_CUTOFF = 8; - TOOM_SQR_CUTOFF = TOOM_MUL_CUTOFF = 16; + MP_KARATSUBA_SQR_CUTOFF = MP_KARATSUBA_MUL_CUTOFF = 8; + MP_TOOM_SQR_CUTOFF = MP_TOOM_MUL_CUTOFF = 16; #endif for (;;) { diff --git a/demo/test.c b/demo/test.c index 0f0152a55..41c4182da 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2199,12 +2199,12 @@ static int test_s_mp_toom_mul(void) goto LBL_ERR; } - tc_cutoff = TOOM_MUL_CUTOFF; - TOOM_MUL_CUTOFF = INT_MAX; + tc_cutoff = MP_TOOM_MUL_CUTOFF; + MP_TOOM_MUL_CUTOFF = INT_MAX; if ((err = mp_mul(&a, &b, &c)) != MP_OKAY) { goto LBL_ERR; } - TOOM_MUL_CUTOFF = tc_cutoff; + MP_TOOM_MUL_CUTOFF = tc_cutoff; if ((err = mp_mul(&a, &b, &d)) != MP_OKAY) { goto LBL_ERR; } diff --git a/demo/timing.c b/demo/timing.c index 47775dae8..a421f8de8 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -234,18 +234,18 @@ int main(int argc, char **argv) if (should_test("mulsqr", argc, argv) != 0) { /* do mult/square twice, first without karatsuba and second with */ - old_kara_m = KARATSUBA_MUL_CUTOFF; - old_kara_s = KARATSUBA_SQR_CUTOFF; + old_kara_m = MP_KARATSUBA_MUL_CUTOFF; + old_kara_s = MP_KARATSUBA_SQR_CUTOFF; /* currently toom-cook cut-off is too high to kick in, so we just use the karatsuba values */ old_toom_m = old_kara_m; old_toom_s = old_kara_s; for (ix = 0; ix < 3; ix++) { printf("With%s Karatsuba, With%s Toom\n", (ix == 1) ? "" : "out", (ix == 2) ? "" : "out"); - KARATSUBA_MUL_CUTOFF = (ix == 1) ? old_kara_m : 9999; - KARATSUBA_SQR_CUTOFF = (ix == 1) ? old_kara_s : 9999; - TOOM_MUL_CUTOFF = (ix == 2) ? old_toom_m : 9999; - TOOM_SQR_CUTOFF = (ix == 2) ? old_toom_s : 9999; + MP_KARATSUBA_MUL_CUTOFF = (ix == 1) ? old_kara_m : 9999; + MP_KARATSUBA_SQR_CUTOFF = (ix == 1) ? old_kara_s : 9999; + MP_TOOM_MUL_CUTOFF = (ix == 2) ? old_toom_m : 9999; + MP_TOOM_SQR_CUTOFF = (ix == 2) ? old_toom_s : 9999; log = FOPEN((ix == 0) ? "logs/mult.log" : (ix == 1) ? "logs/mult_kara.log" : "logs/mult_toom.log", "w"); for (cnt = 4; cnt <= (10240 / MP_DIGIT_BIT); cnt += 2) { diff --git a/etc/tune.c b/etc/tune.c index e6850c69d..be78ce346 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -256,18 +256,18 @@ const struct cutoffs max_cutoffs = static void set_cutoffs(const struct cutoffs *c) { - KARATSUBA_MUL_CUTOFF = c->KARATSUBA_MUL; - KARATSUBA_SQR_CUTOFF = c->KARATSUBA_SQR; - TOOM_MUL_CUTOFF = c->TOOM_MUL; - TOOM_SQR_CUTOFF = c->TOOM_SQR; + MP_KARATSUBA_MUL_CUTOFF = c->KARATSUBA_MUL; + MP_KARATSUBA_SQR_CUTOFF = c->KARATSUBA_SQR; + MP_TOOM_MUL_CUTOFF = c->TOOM_MUL; + MP_TOOM_SQR_CUTOFF = c->TOOM_SQR; } static void get_cutoffs(struct cutoffs *c) { - c->KARATSUBA_MUL = KARATSUBA_MUL_CUTOFF; - c->KARATSUBA_SQR = KARATSUBA_SQR_CUTOFF; - c->TOOM_MUL = TOOM_MUL_CUTOFF; - c->TOOM_SQR = TOOM_SQR_CUTOFF; + c->KARATSUBA_MUL = MP_KARATSUBA_MUL_CUTOFF; + c->KARATSUBA_SQR = MP_KARATSUBA_SQR_CUTOFF; + c->TOOM_MUL = MP_TOOM_MUL_CUTOFF; + c->TOOM_SQR = MP_TOOM_SQR_CUTOFF; } @@ -414,13 +414,13 @@ int main(int argc, char **argv) s_usage(argv[0]); } str = argv[opt]; - KARATSUBA_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[1/4] No value for KARATSUBA_MUL_CUTOFF given"); + MP_KARATSUBA_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[1/4] No value for MP_KARATSUBA_MUL_CUTOFF given"); str = endptr + 1; - KARATSUBA_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[2/4] No value for KARATSUBA_SQR_CUTOFF given"); + MP_KARATSUBA_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[2/4] No value for MP_KARATSUBA_SQR_CUTOFF given"); str = endptr + 1; - TOOM_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[3/4] No value for TOOM_MUL_CUTOFF given"); + MP_TOOM_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[3/4] No value for MP_TOOM_MUL_CUTOFF given"); str = endptr + 1; - TOOM_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[4/4] No value for TOOM_SQR_CUTOFF given"); + MP_TOOM_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[4/4] No value for MP_TOOM_SQR_CUTOFF given"); break; case 'h': s_exit_code = EXIT_SUCCESS; @@ -448,7 +448,7 @@ int main(int argc, char **argv) int *cutoff, *update; uint64_t (*fn)(int size); } test[] = { -#define T_MUL_SQR(n, o, f) { #n, &o##_CUTOFF, &(updated.o), MP_HAS(S_MP_##o) ? f : NULL } +#define T_MUL_SQR(n, o, f) { #n, &MP_##o##_CUTOFF, &(updated.o), MP_HAS(S_MP_##o) ? f : NULL } /* The influence of the Comba multiplication cannot be eradicated programmatically. It depends on the size @@ -526,15 +526,15 @@ int main(int argc, char **argv) set_cutoffs(&orig); if (args.terse == 1) { printf("%d %d %d %d\n", - KARATSUBA_MUL_CUTOFF, - KARATSUBA_SQR_CUTOFF, - TOOM_MUL_CUTOFF, - TOOM_SQR_CUTOFF); + MP_KARATSUBA_MUL_CUTOFF, + MP_KARATSUBA_SQR_CUTOFF, + MP_TOOM_MUL_CUTOFF, + MP_TOOM_SQR_CUTOFF); } else { - printf("KARATSUBA_MUL_CUTOFF = %d\n", KARATSUBA_MUL_CUTOFF); - printf("KARATSUBA_SQR_CUTOFF = %d\n", KARATSUBA_SQR_CUTOFF); - printf("TOOM_MUL_CUTOFF = %d\n", TOOM_MUL_CUTOFF); - printf("TOOM_SQR_CUTOFF = %d\n", TOOM_SQR_CUTOFF); + printf("KARATSUBA_MUL_CUTOFF = %d\n", MP_KARATSUBA_MUL_CUTOFF); + printf("KARATSUBA_SQR_CUTOFF = %d\n", MP_KARATSUBA_SQR_CUTOFF); + printf("TOOM_MUL_CUTOFF = %d\n", MP_TOOM_MUL_CUTOFF); + printf("TOOM_SQR_CUTOFF = %d\n", MP_TOOM_SQR_CUTOFF); } } } diff --git a/mp_cutoffs.c b/mp_cutoffs.c index 5593b553f..46b04ef51 100644 --- a/mp_cutoffs.c +++ b/mp_cutoffs.c @@ -5,10 +5,10 @@ #ifndef MP_FIXED_CUTOFFS #include "tommath_cutoffs.h" -int KARATSUBA_MUL_CUTOFF = MP_DEFAULT_KARATSUBA_MUL_CUTOFF, - KARATSUBA_SQR_CUTOFF = MP_DEFAULT_KARATSUBA_SQR_CUTOFF, - TOOM_MUL_CUTOFF = MP_DEFAULT_TOOM_MUL_CUTOFF, - TOOM_SQR_CUTOFF = MP_DEFAULT_TOOM_SQR_CUTOFF; +int MP_KARATSUBA_MUL_CUTOFF = MP_DEFAULT_KARATSUBA_MUL_CUTOFF, + MP_KARATSUBA_SQR_CUTOFF = MP_DEFAULT_KARATSUBA_SQR_CUTOFF, + MP_TOOM_MUL_CUTOFF = MP_DEFAULT_TOOM_MUL_CUTOFF, + MP_TOOM_SQR_CUTOFF = MP_DEFAULT_TOOM_SQR_CUTOFF; #endif #endif diff --git a/tommath.h b/tommath.h index f415a7fef..b741674bb 100644 --- a/tommath.h +++ b/tommath.h @@ -122,10 +122,10 @@ typedef enum { #ifndef MP_FIXED_CUTOFFS extern int -KARATSUBA_MUL_CUTOFF, -KARATSUBA_SQR_CUTOFF, -TOOM_MUL_CUTOFF, -TOOM_SQR_CUTOFF; +MP_KARATSUBA_MUL_CUTOFF, +MP_KARATSUBA_SQR_CUTOFF, +MP_TOOM_MUL_CUTOFF, +MP_TOOM_SQR_CUTOFF; #endif /* define this to use lower memory usage routines (exptmods mostly) */ diff --git a/tommath_private.h b/tommath_private.h index b18663b8c..f1211a142 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -116,11 +116,6 @@ do { \ # define MP_KARATSUBA_SQR_CUTOFF MP_DEFAULT_KARATSUBA_SQR_CUTOFF # define MP_TOOM_MUL_CUTOFF MP_DEFAULT_TOOM_MUL_CUTOFF # define MP_TOOM_SQR_CUTOFF MP_DEFAULT_TOOM_SQR_CUTOFF -#else -# define MP_KARATSUBA_MUL_CUTOFF KARATSUBA_MUL_CUTOFF -# define MP_KARATSUBA_SQR_CUTOFF KARATSUBA_SQR_CUTOFF -# define MP_TOOM_MUL_CUTOFF TOOM_MUL_CUTOFF -# define MP_TOOM_SQR_CUTOFF TOOM_SQR_CUTOFF #endif /* define heap macros */ From 87b4e51794036cbcb7dc5c01b5a7b5b30bc69af2 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 23 Oct 2019 09:06:04 +0200 Subject: [PATCH 048/304] move out s_mp_log_pow2, fix limitation of base --- libtommath_VS2008.vcproj | 4 ++++ makefile | 2 +- makefile.mingw | 2 +- makefile.msvc | 2 +- makefile.shared | 2 +- makefile.unix | 2 +- mp_log_u32.c | 10 ++-------- s_mp_log_pow2.c | 12 ++++++++++++ tommath_class.h | 7 ++++++- tommath_private.h | 1 + 10 files changed, 30 insertions(+), 14 deletions(-) create mode 100644 s_mp_log_pow2.c diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 481b5423c..1f444cbb2 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -900,6 +900,10 @@ RelativePath="s_mp_log_d.c" > + + diff --git a/makefile b/makefile index 77150049a..179176b29 100644 --- a/makefile +++ b/makefile @@ -47,7 +47,7 @@ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_r mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o diff --git a/makefile.mingw b/makefile.mingw index 3c3fcf7b5..8f542f0c2 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -50,7 +50,7 @@ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_r mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o diff --git a/makefile.msvc b/makefile.msvc index c42ca12de..3050b6ca8 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -42,7 +42,7 @@ mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj \ s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj \ s_mp_invmod_fast.obj s_mp_invmod_slow.obj s_mp_karatsuba_mul.obj s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj \ -s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj \ +s_mp_log_pow2.obj s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj \ s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj \ s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj s_mp_toom_mul.obj s_mp_toom_sqr.obj diff --git a/makefile.shared b/makefile.shared index 2c9c0e323..cad119657 100644 --- a/makefile.shared +++ b/makefile.shared @@ -44,7 +44,7 @@ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_r mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o diff --git a/makefile.unix b/makefile.unix index d9d7727d7..bde330f47 100644 --- a/makefile.unix +++ b/makefile.unix @@ -51,7 +51,7 @@ mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_r mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o diff --git a/mp_log_u32.c b/mp_log_u32.c index 2b49fe17b..5568568b6 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -17,14 +17,8 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) return MP_VAL; } - /* A small shortcut for bases that are powers of two. */ - if ((base & (base - 1u)) == 0u) { - int y, bit_count; - for (y=0; (y < 7) && ((base & 1u) == 0u); y++) { - base >>= 1; - } - bit_count = mp_count_bits(a) - 1; - *c = (uint32_t)(bit_count/y); + if (MP_HAS(S_MP_LOG_POW2) && (base & (base - 1u)) == 0u) { + *c = s_mp_log_pow2(a, base); return MP_OKAY; } diff --git a/s_mp_log_pow2.c b/s_mp_log_pow2.c new file mode 100644 index 000000000..74271c68f --- /dev/null +++ b/s_mp_log_pow2.c @@ -0,0 +1,12 @@ +#include "tommath_private.h" +#ifdef S_MP_LOG_POW2_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base) +{ + int y; + for (y = 0; (base & 1u) == 0u; y++, base >>= 1) {} + return (uint32_t)((mp_count_bits(a) - 1) / y); +} +#endif diff --git a/tommath_class.h b/tommath_class.h index 5373d91d3..480c24abf 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -158,6 +158,7 @@ # define S_MP_KARATSUBA_SQR_C # define S_MP_LOG_C # define S_MP_LOG_D_C +# define S_MP_LOG_POW2_C # define S_MP_MONTGOMERY_REDUCE_FAST_C # define S_MP_MUL_DIGS_C # define S_MP_MUL_DIGS_FAST_C @@ -522,9 +523,9 @@ #endif #if defined(MP_LOG_U32_C) -# define MP_COUNT_BITS_C # define S_MP_LOG_C # define S_MP_LOG_D_C +# define S_MP_LOG_POW2_C #endif #if defined(MP_LSHD_C) @@ -1174,6 +1175,10 @@ #if defined(S_MP_LOG_D_C) #endif +#if defined(S_MP_LOG_POW2_C) +# define MP_COUNT_BITS_C +#endif + #if defined(S_MP_MONTGOMERY_REDUCE_FAST_C) # define MP_CLAMP_C # define MP_CMP_MAG_C diff --git a/tommath_private.h b/tommath_private.h index f1211a142..f3aeb8fe7 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -213,6 +213,7 @@ MP_PRIVATE void s_mp_reverse(unsigned char *s, size_t len); MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); +MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base); MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r); From 448d00804da1bd9eed2f26dc288121c2b6168b68 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Wed, 23 Oct 2019 23:25:37 +0200 Subject: [PATCH 049/304] Fix commit in helper.pl --- helper.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/helper.pl b/helper.pl index a519619ff..134469d69 100755 --- a/helper.pl +++ b/helper.pl @@ -51,7 +51,7 @@ sub check_source { push @{$troubles->{tab}}, $lineno if $l =~ /\t/ && basename($file) !~ /^makefile/i; push @{$troubles->{non_ascii_char}}, $lineno if $l =~ /[^[:ascii:]]/; push @{$troubles->{cpp_comment}}, $lineno if $file =~ /\.(c|h)$/ && ($l =~ /\s\/\// || $l =~ /\/\/\s/); - # we prefer using XMALLOC, XFREE, XREALLOC, XCALLOC ... + # we prefer using MP_MALLOC, MP_FREE, MP_REALLOC, MP_CALLOC ... push @{$troubles->{unwanted_malloc}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmalloc\s*\(/; push @{$troubles->{unwanted_realloc}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\brealloc\s*\(/; push @{$troubles->{unwanted_calloc}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bcalloc\s*\(/; From d0e26bb3ff18c31f1446b0620626187ad2ca8ffb Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Thu, 24 Oct 2019 18:26:25 +0200 Subject: [PATCH 050/304] explicit operator precedence --- mp_div.c | 2 +- mp_log_u32.c | 2 +- tommath_private.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/mp_div.c b/mp_div.c index 5fd957280..e9f4f5017 100644 --- a/mp_div.c +++ b/mp_div.c @@ -27,7 +27,7 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) if (MP_HAS(S_MP_DIV_RECURSIVE) && (b->used > MP_KARATSUBA_MUL_CUTOFF) - && (b->used <= ((a->used)/3*2))) { + && (b->used <= ((a->used/3)*2))) { err = s_mp_div_recursive(a, b, c, d); } else if (MP_HAS(S_MP_DIV_SCHOOL)) { err = s_mp_div_school(a, b, c, d); diff --git a/mp_log_u32.c b/mp_log_u32.c index 5568568b6..cff9e48f5 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -17,7 +17,7 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) return MP_VAL; } - if (MP_HAS(S_MP_LOG_POW2) && (base & (base - 1u)) == 0u) { + if (MP_HAS(S_MP_LOG_POW2) && ((base & (base - 1u)) == 0u)) { *c = s_mp_log_pow2(a, base); return MP_OKAY; } diff --git a/tommath_private.h b/tommath_private.h index f3aeb8fe7..1911747b1 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -167,7 +167,7 @@ typedef unsigned long mp_word __attribute__((mode(TI))); typedef uint64_t mp_word; #endif -MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == 2 * sizeof(mp_digit)) +MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2 * sizeof(mp_digit))) /* default precision */ #ifndef MP_PREC From 9051694850645bad6fc3aa9cc92209edc6f8eb85 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Thu, 24 Oct 2019 18:11:36 +0200 Subject: [PATCH 051/304] literal suffix --- s_mp_div_recursive.c | 4 ++-- tommath_private.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index 67b4a054d..d641123fd 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -48,7 +48,7 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int /* while A1 < 0 do Q1 = Q1 - 1, A1 = A1 + (beta^k * B) */ if ((err = mp_mul_2d(b, k * MP_DIGIT_BIT, &t)) != MP_OKAY) goto LBL_ERR; - while (mp_cmp_d(&A1, 0) == MP_LT) { + while (mp_cmp_d(&A1, 0uL) == MP_LT) { if ((err = mp_decr(&Q1)) != MP_OKAY) goto LBL_ERR; if ((err = mp_add(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; } @@ -64,7 +64,7 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int if ((err = mp_sub(&A2, &t, &A2)) != MP_OKAY) goto LBL_ERR; /* while A2 < 0 do Q0 = Q0 - 1, A2 = A2 + B */ - while (mp_cmp_d(&A2, 0) == MP_LT) { + while (mp_cmp_d(&A2, 0uL) == MP_LT) { if ((err = mp_decr(&Q0)) != MP_OKAY) goto LBL_ERR; if ((err = mp_add(&A2, b, &A2)) != MP_OKAY) goto LBL_ERR; } diff --git a/tommath_private.h b/tommath_private.h index 1911747b1..a03ae41a4 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -167,7 +167,7 @@ typedef unsigned long mp_word __attribute__((mode(TI))); typedef uint64_t mp_word; #endif -MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2 * sizeof(mp_digit))) +MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) /* default precision */ #ifndef MP_PREC From 17afe155f0e40d3b39e1bb5fa706b2bad5261d39 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Thu, 24 Oct 2019 18:16:05 +0200 Subject: [PATCH 052/304] needs mp_word --- etc/pprime.c | 1 + 1 file changed, 1 insertion(+) diff --git a/etc/pprime.c b/etc/pprime.c index 411e446a5..fe32a30c2 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -7,6 +7,7 @@ #include #include #include "tommath.h" +#include "tommath_private.h" /* mp_word */ static int n_prime; static FILE *primes; From c4622f53c8f399f8451743c007399139dea930d4 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 21:44:55 +0200 Subject: [PATCH 053/304] only include tommath_private.h --- etc/pprime.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/etc/pprime.c b/etc/pprime.c index fe32a30c2..1d59cab7f 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -6,8 +6,7 @@ */ #include #include -#include "tommath.h" -#include "tommath_private.h" /* mp_word */ +#include "tommath_private.h" static int n_prime; static FILE *primes; From 867f08b057a34ada79771a0bd1e6af8c3086a64e Mon Sep 17 00:00:00 2001 From: nijtmans Date: Sat, 26 Oct 2019 00:05:41 +0200 Subject: [PATCH 054/304] Ignore Eclipse .settings directory --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index d39d2758f..7cd346fb3 100644 --- a/.gitignore +++ b/.gitignore @@ -29,6 +29,7 @@ mtest_opponent.exe # ignore eclipse project files .cproject .project +.settings # special MS Visual Studio section # ignore non-compressed browse file (holds information for ClassView, IntelliSense and WizardBar) From a8ca1c3cc6c3aea84ee582478c0d1da45fc3cc64 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Fri, 25 Oct 2019 13:02:45 +0200 Subject: [PATCH 055/304] fix win32 includes, remove support for everything older than Windows XP --- s_mp_rand_platform.c | 17 ++++++++--------- tommath_private.h | 2 +- 2 files changed, 9 insertions(+), 10 deletions(-) diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 78225f969..6b6a22c10 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -16,15 +16,14 @@ static mp_err s_read_arc4random(void *p, size_t n) } #endif -#if defined(_WIN32) || defined(_WIN32_WCE) +#if defined(_WIN32) #define S_READ_WINCSP_C #ifndef _WIN32_WINNT -#define _WIN32_WINNT 0x0400 +#define _WIN32_WINNT 0x0501 #endif -#ifdef _WIN32_WCE -#define UNDER_CE -#define ARM +#ifndef WINVER +#define WINVER 0x0501 #endif #define WIN32_LEAN_AND_MEAN @@ -36,10 +35,10 @@ static mp_err s_read_wincsp(void *p, size_t n) static HCRYPTPROV hProv = 0; if (hProv == 0) { HCRYPTPROV h = 0; - if (!CryptAcquireContext(&h, NULL, MS_DEF_PROV, PROV_RSA_FULL, - (CRYPT_VERIFYCONTEXT | CRYPT_MACHINE_KEYSET)) && - !CryptAcquireContext(&h, NULL, MS_DEF_PROV, PROV_RSA_FULL, - CRYPT_VERIFYCONTEXT | CRYPT_MACHINE_KEYSET | CRYPT_NEWKEYSET)) { + if (!CryptAcquireContextW(&h, NULL, MS_DEF_PROV_W, PROV_RSA_FULL, + (CRYPT_VERIFYCONTEXT | CRYPT_MACHINE_KEYSET)) && + !CryptAcquireContextW(&h, NULL, MS_DEF_PROV_W, PROV_RSA_FULL, + CRYPT_VERIFYCONTEXT | CRYPT_MACHINE_KEYSET | CRYPT_NEWKEYSET)) { return MP_ERR; } hProv = h; diff --git a/tommath_private.h b/tommath_private.h index a03ae41a4..28326903e 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -16,7 +16,7 @@ * as a shared object. By default, symbols are visible. * On Win32 a .def file must be used to specify the exported symbols. */ -#if defined(__GNUC__) && __GNUC__ >= 4 && !defined(_WIN32) +#if defined(__GNUC__) && __GNUC__ >= 4 && !defined(_WIN32) && !defined(__CYGWIN__) # define MP_PRIVATE __attribute__ ((visibility ("hidden"))) #else # define MP_PRIVATE From b26bd5082e36b95986cee2bb1c427e7036934ff7 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Sat, 26 Oct 2019 00:31:11 +0200 Subject: [PATCH 056/304] Fix some comments --- mp_mul.c | 2 +- s_mp_mul_high_digs_fast.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/mp_mul.c b/mp_mul.c index bb0b65215..9c8f8aeda 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -17,7 +17,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) * The bigger one needs to be at least about one MP_KARATSUBA_MUL_CUTOFF bigger * to make some sense, but it depends on architecture, OS, position of the * stars... so YMMV. - * Using it to cut the input into slices small enough for fast_s_mp_mul_digs + * Using it to cut the input into slices small enough for s_mp_mul_digs_fast * was actually slower on the author's machine, but YMMV. */ (min_len >= MP_KARATSUBA_MUL_CUTOFF) && diff --git a/s_mp_mul_high_digs_fast.c b/s_mp_mul_high_digs_fast.c index 06561a9fd..1559ebcf4 100644 --- a/s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_digs_fast.c @@ -3,8 +3,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* this is a modified version of fast_s_mul_digs that only produces - * output digits *above* digs. See the comments for fast_s_mul_digs +/* this is a modified version of s_mp_mul_digs_fast that only produces + * output digits *above* digs. See the comments for s_mp_mul_digs_fast * to see how it works. * * This is used in the Barrett reduction since for one of the multiplications From f2efe7467643615db32518f56a32e9358d8e07e0 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Tue, 22 Oct 2019 17:53:27 +0200 Subject: [PATCH 057/304] more cast --- tommath_private.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tommath_private.h b/tommath_private.h index 28326903e..45aad4e51 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -157,7 +157,7 @@ extern void MP_FREE(void *mem, size_t size); #define MP_SIZEOF_BITS(type) ((size_t)CHAR_BIT * sizeof(type)) #define MP_MAXFAST (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) -#define MP_WARRAY (1 << ((MP_SIZEOF_BITS(mp_word) - (2 * MP_DIGIT_BIT)) + 1)) +#define MP_WARRAY (int)(1 << ((MP_SIZEOF_BITS(mp_word) - (2 * (size_t)MP_DIGIT_BIT)) + 1)) #if defined(MP_16BIT) typedef uint32_t mp_word; From 814d0387a64c4ec99ea53a2f3b1e56b8c1e0e97f Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Tue, 22 Oct 2019 17:54:33 +0200 Subject: [PATCH 058/304] literal suffix --- tommath_private.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tommath_private.h b/tommath_private.h index 45aad4e51..1916f87dc 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -157,7 +157,7 @@ extern void MP_FREE(void *mem, size_t size); #define MP_SIZEOF_BITS(type) ((size_t)CHAR_BIT * sizeof(type)) #define MP_MAXFAST (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) -#define MP_WARRAY (int)(1 << ((MP_SIZEOF_BITS(mp_word) - (2 * (size_t)MP_DIGIT_BIT)) + 1)) +#define MP_WARRAY (int)(1uL << ((MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT)) + 1u)) #if defined(MP_16BIT) typedef uint32_t mp_word; @@ -224,7 +224,7 @@ MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); -#define MP_RMAP_REVERSE_SIZE 88 +#define MP_RMAP_REVERSE_SIZE 88u extern MP_PRIVATE const char s_mp_rmap[]; extern MP_PRIVATE const uint8_t s_mp_rmap_reverse[]; extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; From 8b31c193bf8a44958fc3ca36708428a3b75c6a7b Mon Sep 17 00:00:00 2001 From: czurnieden Date: Thu, 24 Oct 2019 18:24:28 +0200 Subject: [PATCH 059/304] Cleanup and update of manual --- doc/bn.tex | 705 ++++++++++++++++++++++++++++------------------------- 1 file changed, 374 insertions(+), 331 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 8187de89c..292f68025 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -91,7 +91,7 @@ \section{License} release as well. This textbook is meant to compliment the project by providing a more solid walkthrough of the development algorithms used in the library. -Since both\footnote{Note that the MPI files under mtest/ are copyrighted by Michael Fromberger. They are not required to use LibTomMath.} are in the +Since both\footnote{Note that the MPI files under \texttt{mtest/} are copyrighted by Michael Fromberger. They are not required to use LibTomMath.} are in the public domain everyone is entitled to do with them as they see fit. \section{Building LibTomMath} @@ -142,7 +142,7 @@ \subsubsection{GNU based Operating Systems} \end{alltt} This requires the ``libtool'' package (common on most Linux/BSD systems). It will build LibTomMath as both shared and static then install (by default) into /usr/lib as well as install the header files in /usr/include. The shared -library (resource) will be called ``libtommath.la'' while the static library called ``libtommath.a''. Generally +library (resource) will be called \texttt{libtommath.la} while the static library called \texttt{libtommath.a}. Generally you use libtool to link your application against the shared object. To run a program to adapt the Toom-Cook cut-off values to your architecture type @@ -152,9 +152,9 @@ \subsubsection{GNU based Operating Systems} This will take some time. \subsubsection{Microsoft Windows based Operating Systems} -There is limited support for making a ``DLL'' in windows via the ``makefile.cygwin\_dll'' makefile. It requires +There is limited support for making a ``DLL'' in windows via the \texttt{makefile.cygwin\_dll} makefile. It requires Cygwin to work with since it requires the auto-export/import functionality. The resulting DLL and import library -``libtommath.dll.a'' can be used to link LibTomMath dynamically to any Windows program using Cygwin. +\texttt{libtommath.dll.a} can be used to link LibTomMath dynamically to any Windows program using Cygwin. \subsubsection{OpenBSD} OpenBSD replaced some of their GNU-tools, especially \texttt{libtool} with their own, slightly different versions. To ease the workload of LibTomMath's developer team, only a static library can be build with the included \texttt{makefile.unix}. @@ -223,16 +223,16 @@ \subsection{Testing} make test \end{alltt} -This will build the library, ``test'' and ``mtest/mtest''. The ``test'' program will accept test vectors and verify the -results. ``mtest/mtest'' will generate test vectors using the MPI library by Michael Fromberger\footnote{A copy of MPI -is included in the package}. Simply pipe mtest into test using +This will build the library, \texttt{test} and \texttt{mtest/mtest}. The \texttt{test} program will accept test vectors and verify the +results. \texttt{mtest/mtest} will generate test vectors using the MPI library by Michael Fromberger\footnote{A copy of MPI +is included in the package}. Simply pipe \texttt{mtest} into \texttt{test} using \begin{alltt} mtest/mtest | test \end{alltt} -If you do not have a ``/dev/urandom'' style RNG source you will have to write your own PRNG and simply pipe that into -mtest. For example, if your PRNG program is called ``myprng'' simply invoke +If you do not have a \texttt{/dev/urandom} style RNG source you will have to write your own PRNG and simply pipe that into +\texttt{mtest}. For example, if your PRNG program is called \texttt{myprng} simply invoke \begin{alltt} myprng | mtest/mtest | test @@ -247,24 +247,24 @@ \section{Build Configuration} Each phase changes how the library is built and they are applied one after another respectively. To make the system more powerful you can tweak the build process. Classes are defined in the file -``tommath\_superclass.h''. By default, the symbol ``LTM\_ALL'' shall be defined which simply +\texttt{tommath\_superclass.h}. By default, the symbol \texttt{LTM\_ALL} shall be defined which simply instructs the system to build all of the functions. This is how LibTomMath used to be packaged. This will give you access to every function LibTomMath offers. However, there are cases where such a build is not optional. For instance, you want to perform RSA operations. You -don't need the vast majority of the library to perform these operations. Aside from LTM\_ALL there is -another pre--defined class ``SC\_RSA\_1'' which works in conjunction with the RSA from LibTomCrypt. Additional +don't need the vast majority of the library to perform these operations. Aside from \texttt{LTM\_ALL} there is +another pre--defined class \texttt{SC\_RSA\_1} which works in conjunction with the RSA from LibTomCrypt. Additional classes can be defined base on the need of the user. \subsection{Build Depends} -In the file tommath\_class.h you will see a large list of C ``defines'' followed by a series of ``ifdefs'' +In the file \texttt{tommath\_class.h} you will see a large list of C ``defines'' followed by a series of ``ifdefs'' which further define symbols. All of the symbols (technically they're macros $\ldots$) represent a given C source -file. For instance, MP\_ADD\_C represents the file ``bn\_mp\_add.c''. When a define has been enabled the +file. For instance, \texttt{MP\_ADD\_C} represents the file \texttt{mp\_add.c}. When a define has been enabled the function in the respective file will be compiled and linked into the library. Accordingly when the define is absent the file will not be compiled and not contribute any size to the library. -You will also note that the header tommath\_class.h is actually recursively included (it includes itself twice). -This is to help resolve as many dependencies as possible. In the last pass the symbol LTM\_LAST will be defined. +You will also note that the header \texttt{tommath\_class.h} is actually recursively included (it includes itself twice). +This is to help resolve as many dependencies as possible. In the last pass the symbol \texttt{LTM\_LAST} will be defined. This is useful for ``trims''. \subsection{Build Tweaks} @@ -286,7 +286,7 @@ \subsection{Build Trims} A trim is a manner of removing functionality from a function that is not required. For instance, to perform RSA cryptography you only require exponentiation with odd moduli so even moduli support can be safely removed. Build trims are meant to be defined on the last pass of the configuration which means they are to be defined -only if LTM\_LAST has been defined. +only if \texttt{LTM\_LAST} has been defined. \subsubsection{Moduli Related} \begin{small} @@ -388,9 +388,9 @@ \section{Building Programs} libtommath.a). There is no library initialization required and the entire library is thread safe. \section{Return Codes} -There are three possible return codes a function may return. +There are five possible return codes a function may return. -\index{MP\_OKAY}\index{MP\_YES}\index{MP\_NO}\index{MP\_VAL}\index{MP\_MEM} +\index{MP\_OKAY}\index{MP\_YES}\index{MP\_NO}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{MP\_BUF} \begin{figure}[h!] \begin{center} \begin{small} @@ -399,6 +399,8 @@ \section{Return Codes} \hline MP\_OKAY & The function succeeded. \\ \hline MP\_VAL & The function input was invalid. \\ \hline MP\_MEM & Heap memory exhausted. \\ +\hline MP\_ITER & Maximum iterations reached. \\ +\hline MP\_BUF & Buffer overflow, supplied buffer too small.\\ \hline &\\ \hline MP\_YES & Response is yes. \\ \hline MP\_NO & Response is no. \\ @@ -409,6 +411,8 @@ \section{Return Codes} \caption{Return Codes} \end{figure} +The error codes \texttt{MP\_OKAY},\texttt{MP\_VAL}, \texttt{MP\_MEM}, \texttt{MP\_ITER}, and \texttt{MP\_BUF} are of the type \texttt{mp\_err}, the codes \texttt{MP\_YES} and \texttt{MP\_NO} are of type \texttt{mp\_bool}. + The last two codes listed are not actually ``return'ed'' by a function. They are placed in an integer (the caller must provide the address of an integer it can store to) which the caller can access. To convert one of the three return codes to a string use the following function. @@ -418,29 +422,29 @@ \section{Return Codes} char *mp_error_to_string(int code); \end{alltt} -This will return a pointer to a string which describes the given error code. It will not work for the return codes -MP\_YES and MP\_NO. +This will return a pointer to a string which describes the given error code. It will not work for the return codes \texttt{MP\_YES} and \texttt{MP\_NO}. \section{Data Types} -The basic ``multiple precision integer'' type is known as the ``mp\_int'' within LibTomMath. This data type is used to +The basic ``multiple precision integer'' type is known as the \texttt{mp\_int} within LibTomMath. This data type is used to organize all of the data required to manipulate the integer it represents. Within LibTomMath it has been prototyped as the following. \index{mp\_int} \begin{alltt} typedef struct \{ - int used, alloc, sign; - mp_digit *dp; + int used, alloc; + mp_sign sign; + mp_digit *dp; \} mp_int; \end{alltt} -Where ``mp\_digit'' is a data type that represents individual digits of the integer. By default, an mp\_digit is the -ISO C ``unsigned long'' data type and each digit is $28-$bits long. The mp\_digit type can be configured to suit other +Where \texttt{mp\_digit} is a data type that represents individual digits of the integer. By default, an \texttt{mp\_digit} is the +ISO C \texttt{unsigned long} data type and each digit is $28-$bits long. The \texttt{mp\_digit} type can be configured to suit other platforms by defining the appropriate macros. -All LTM functions that use the mp\_int type will expect a pointer to mp\_int structure. You must allocate memory to +All LTM functions that use the \texttt{mp\_int} type will expect a pointer to \texttt{mp\_int} structure. You must allocate memory to hold the structure itself by yourself (whether off stack or heap it doesn't matter). The very first thing that must be -done to use an mp\_int is that it must be initialized. +done to use an \texttt{mp\_int} is that it must be initialized. \section{Function Organization} @@ -465,22 +469,23 @@ \section{Function Organization} \section{Initialization} \subsection{Single Initialization} -A single mp\_int can be initialized with the ``mp\_init'' function. +A single \texttt{mp\_int} can be initialized with the \texttt{mp\_init} function. \index{mp\_init} \begin{alltt} -int mp_init (mp_int * a); +mp_err mp_init (mp_int *a); \end{alltt} -This function expects a pointer to an mp\_int structure and will initialize the members of the structure so the mp\_int -represents the default integer which is zero. If the functions returns MP\_OKAY then the mp\_int is ready to be used +This function expects a pointer to an \texttt{mp\_int} structure and will initialize the members of the structure so the \texttt{mp\_int} +represents the default integer which is zero. If the functions returns \texttt{MP\_OKAY} then the \texttt{mp\_int} is ready to be used by the other LibTomMath functions. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -492,26 +497,28 @@ \subsection{Single Initialization} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \subsection{Single Free} -When you are finished with an mp\_int it is ideal to return the heap it used back to the system. The following function +When you are finished with an \texttt{mp\_int} it is ideal to return the heap it used back to the system. The following function provides this functionality. \index{mp\_clear} \begin{alltt} -void mp_clear (mp_int * a); +void mp_clear (mp_int *a); \end{alltt} -The function expects a pointer to a previously initialized mp\_int structure and frees the heap it uses. It sets the -pointer\footnote{The ``dp'' member.} within the mp\_int to \textbf{NULL} which is used to prevent double free situations. -Is is legal to call mp\_clear() twice on the same mp\_int in a row. +The function expects a pointer to a previously initialized \texttt{mp\_int} structure and frees the heap it uses. It sets the +pointer\footnote{The \texttt{dp} member.} within the \texttt{mp\_int} to \texttt{NULL} which is used to prevent double free situations. +Is is legal to call \texttt{mp\_clear} twice on the same \texttt{mp\_int} in a row. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -526,30 +533,32 @@ \subsection{Single Free} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \subsection{Multiple Initializations} -Certain algorithms require more than one large integer. In these instances it is ideal to initialize all of the mp\_int +Certain algorithms require more than one large integer. In these instances it is ideal to initialize all of the \texttt{mp\_int} variables in an ``all or nothing'' fashion. That is, they are either all initialized successfully or they are all not initialized. -The mp\_init\_multi() function provides this functionality. +The \texttt{mp\_init\_multi} function provides this functionality. \index{mp\_init\_multi} \index{mp\_clear\_multi} \begin{alltt} -int mp_init_multi(mp_int *mp, ...); +mp_err mp_init_multi(mp_int *mp, ...); \end{alltt} -It accepts a \textbf{NULL} terminated list of pointers to mp\_int structures. It will attempt to initialize them all -at once. If the function returns MP\_OKAY then all of the mp\_int variables are ready to use, otherwise none of them -are available for use. A complementary mp\_clear\_multi() function allows multiple mp\_int variables to be free'd +It accepts a \texttt{NULL} terminated list of pointers to \texttt{mp\_int} structures. It will attempt to initialize them all +at once. If the function returns \texttt{MP\_OKAY} then all of the \texttt{mp\_int} variables are ready to use, otherwise none of them +are available for use. A complementary \texttt{mp\_clear\_multi} function allows multiple \texttt{mp\_int} variables to be free'd from the heap at the same time. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int num1, num2, num3; - int result; + mp_err result; if ((result = mp_init_multi(&num1, &num2, @@ -566,23 +575,25 @@ \subsection{Multiple Initializations} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \subsection{Other Initializers} -To initialized and make a copy of an mp\_int the mp\_init\_copy() function has been provided. +To initialized and make a copy of an \texttt{mp\_int} the \texttt{mp\_init\_copy} function has been provided. \index{mp\_init\_copy} \begin{alltt} -int mp_init_copy (mp_int * a, mp_int * b); +mp_err mp_init_copy (mp_int *a, mp_int *b); \end{alltt} This function will initialize $a$ and make it a copy of $b$ if all goes well. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int num1, num2; - int result; + mp_err result; /* initialize and do work on num1 ... */ @@ -600,25 +611,27 @@ \subsection{Other Initializers} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} -Another less common initializer is mp\_init\_size() which allows the user to initialize an mp\_int with a given -default number of digits. By default, all initializers allocate \textbf{MP\_PREC} digits. This function lets +Another less common initializer is \texttt{mp\_init\_size} which allows the user to initialize an \texttt{mp\_int} with a given +default number of digits. By default, all initializers allocate \texttt{MP\_PREC} digits. This function lets you override this behaviour. \index{mp\_init\_size} \begin{alltt} -int mp_init_size (mp_int * a, int size); +mp_err mp_init_size (mp_int *a, int size); \end{alltt} -The $size$ parameter must be greater than zero. If the function succeeds the mp\_int $a$ will be initialized +The $size$ parameter must be greater than zero. If the function succeeds the \texttt{mp\_int} $a$ will be initialized to have $size$ digits (which are all initially zero). -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; /* we need a 60-digit number */ if ((result = mp_init_size(&number, 60)) != MP_OKAY) \{ @@ -631,12 +644,13 @@ \subsection{Other Initializers} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \section{Maintenance Functions} \subsection{Clear Leading Zeros} -This is used to ensure that leading zero digits are trimed and the leading "used" digit will be non-zero. +This is used to ensure that leading zero digits are trimmed and the leading "used" digit will be non-zero. It also fixes the sign if there are no more leading digits. \index{mp\_clamp} @@ -655,24 +669,25 @@ \subsection{Zero Out} \subsection{Reducing Memory Usage} -When an mp\_int is in a state where it won't be changed again\footnote{A Diffie-Hellman modulus for instance.} excess -digits can be removed to return memory to the heap with the mp\_shrink() function. +When an \texttt{mp\_int} is in a state where it won't be changed again\footnote{A Diffie-Hellman modulus for instance.} excess +digits can be removed to return memory to the heap with the \texttt{mp\_shrink} function. \index{mp\_shrink} \begin{alltt} -int mp_shrink (mp_int * a); +mp_err mp_shrink (mp_int *a); \end{alltt} -This will remove excess digits of the mp\_int $a$. If the operation fails the mp\_int should be intact without the -excess digits being removed. Note that you can use a shrunk mp\_int in further computations, however, such operations -will require heap operations which can be slow. It is not ideal to shrink mp\_int variables that you will further +This will remove excess digits of the \texttt{mp\_int} $a$. If the operation fails the \texttt{mp\_int} should be intact without the +excess digits being removed. Note that you can use a shrunk \texttt{mp\_int} in further computations, however, such operations +will require heap operations which can be slow. It is not ideal to shrink \texttt{mp\_int} variables that you will further modify in the system (unless you are seriously low on memory). -\begin{small} \begin{alltt} +\begin{small} + \begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -697,29 +712,31 @@ \subsection{Reducing Memory Usage} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} + \end{small} \subsection{Adding additional digits} Within the mp\_int structure are two parameters which control the limitations of the array of digits that represent -the integer the mp\_int is meant to equal. The \textit{used} parameter dictates how many digits are significant, that is, -contribute to the value of the mp\_int. The \textit{alloc} parameter dictates how many digits are currently available in +the integer the mp\_int is meant to equal. The \texttt{used} parameter dictates how many digits are significant, that is, +contribute to the value of the mp\_int. The \texttt{alloc} parameter dictates how many digits are currently available in the array. If you need to perform an operation that requires more digits you will have to mp\_grow() the mp\_int to your desired size. \index{mp\_grow} \begin{alltt} -int mp_grow (mp_int * a, int size); +mp_err mp_grow (mp_int *a, int size); \end{alltt} -This will grow the array of digits of $a$ to $size$. If the \textit{alloc} parameter is already bigger than +This will grow the array of digits of $a$ to $size$. If the \texttt{alloc} parameter is already bigger than $size$ the function will not do anything. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -744,7 +761,8 @@ \subsection{Adding additional digits} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \chapter{Basic Operations} \section{Copying} @@ -753,14 +771,14 @@ \section{Copying} \index{mp\_copy} \begin{alltt} -int mp_copy (mp_int * a, mp_int *b); +mp_err mp_copy (const mp_int *a, mp_int *b); \end{alltt} You can also just swap $a$ and $b$. It does the normal pointer changing with a temporary pointer variable, just that you do not have to. \index{mp\_exch} \begin{alltt} -void mp_exch (mp_int * a, mp_int *b); +void mp_exch (mp_int *a, mp_int *b); \end{alltt} \section{Bit Counting} @@ -772,7 +790,7 @@ \section{Bit Counting} int mp_cnt_lsb(const mp_int *a); \end{alltt} -To get the position of the highest bit set (MSB, the Most Significant Bit; the number of bits in teh ``bignum'') +To get the position of the highest bit set (MSB, the Most Significant Bit; the number of bits in the ``bignum'') \index{mp\_count\_bits} \begin{alltt} @@ -781,7 +799,7 @@ \section{Bit Counting} \section{Small Constants} -Setting mp\_ints to small constants is a relatively common operation. To accommodate these instances there is a +Setting an \texttt{mp\_int} to a small constant is a relatively common operation. To accommodate these instances there is a small constant assignment function. This function is used to set a single digit constant. The reason for this function is efficiency. Setting a single digit is quick but the domain of a digit can change (it's always at least $0 \ldots 127$). @@ -792,18 +810,19 @@ \subsection{Single Digit} \index{mp\_set} \begin{alltt} -void mp_set (mp_int * a, mp_digit b); +void mp_set (mp_int *a, mp_digit b); \end{alltt} This will zero the contents of $a$ and make it represent an integer equal to the value of $b$. Note that this -function has a return type of \textbf{void}. It cannot cause an error so it is safe to assume the function +function has a return type of \texttt{void}. It cannot cause an error so it is safe to assume the function succeeded. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -819,7 +838,8 @@ \subsection{Single Digit} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} \subsection{Int32 and Int64 Constants} @@ -828,34 +848,35 @@ \subsection{Int32 and Int64 Constants} \index{mp\_set\_i32} \index{mp\_set\_u32} \index{mp\_set\_i64} \index{mp\_set\_u64} \begin{alltt} -void mp_set_i32 (mp_int * a, int32_t b); -void mp_set_u32 (mp_int * a, uint32_t b); -void mp_set_i64 (mp_int * a, int64_t b); -void mp_set_u64 (mp_int * a, uint64_t b); +void mp_set_i32 (mp_int *a, int32_t b); +void mp_set_u32 (mp_int *a, uint32_t b); +void mp_set_i64 (mp_int *a, int64_t b); +void mp_set_u64 (mp_int *a, uint64_t b); \end{alltt} -These functions assign the sign and value of the input \texttt{b} to \texttt{mp\_int a}. +These functions assign the sign and value of the input $b$ to the big integer $a$. The value can be obtained again by calling the following functions. \index{mp\_get\_i32} \index{mp\_get\_u32} \index{mp\_get\_mag\_u32} \index{mp\_get\_i64} \index{mp\_get\_u64} \index{mp\_get\_mag\_u64} \begin{alltt} -int32_t mp_get_i32 (mp_int * a); -uint32_t mp_get_u32 (mp_int * a); -uint32_t mp_get_mag_u32 (mp_int * a); -int64_t mp_get_i64 (mp_int * a); -uint64_t mp_get_u64 (mp_int * a); -uint64_t mp_get_mag_u64 (mp_int * a); +int32_t mp_get_i32 (const mp_int *a); +uint32_t mp_get_u32 (const mp_int *a); +uint32_t mp_get_mag_u32 (const mp_int *a); +int64_t mp_get_i64 (const mp_int *a); +uint64_t mp_get_u64 (const mp_int *a); +uint64_t mp_get_mag_u64 (const mp_int *a); \end{alltt} These functions return the 32 or 64 least significant bits of $a$ respectively. The unsigned functions -return negative values in a twos complement representation. The absolute value or magnitude can be obtained using the mp\_get\_mag functions. +return negative values in a twos complement representation. The absolute value or magnitude can be obtained using the \texttt{mp\_get\_mag*} functions. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -866,14 +887,15 @@ \subsection{Int32 and Int64 Constants} /* set the number to 654321 (note this is bigger than 127) */ mp_set_u32(&number, 654321); - printf("number == \%" PRIi32, mp_get_i32(&number)); + printf("number == \%" PRIi32 "\textbackslash{}n", mp_get_i32(&number)); /* we're done with it. */ mp_clear(&number); return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} This should output the following if the program succeeds. @@ -885,32 +907,32 @@ \subsection{Long Constants - platform dependant} \index{mp\_set\_l} \index{mp\_set\_ul} \begin{alltt} -void mp_set_l (mp_int * a, long b); -void mp_set_ul (mp_int * a, unsigned long b); +void mp_set_l (mp_int *a, long b); +void mp_set_ul (mp_int *a, unsigned long b); \end{alltt} -This will assign the value of the platform-dependent sized variable $b$ to the mp\_int $a$. +This will assign the value of the platform-dependent sized variable $b$ to the big integer $a$. To retrieve the value, the following functions can be used. \index{mp\_get\_l} \index{mp\_get\_ul} \index{mp\_get\_mag\_ul} \begin{alltt} -long mp_get_l (mp_int * a); -unsigned long mp_get_ul (mp_int * a); -unsigned long mp_get_mag_ul (mp_int * a); +long mp_get_l (const mp_int *a); +unsigned long mp_get_ul (const mp_int *a); +unsigned long mp_get_mag_ul (const mp_int *a); \end{alltt} -This will return the least significant bits of the mp\_int $a$ that fit into a ``long''. +This will return the least significant bits of the big integer $a$ that fit into the native data type \texttt{long}. \subsection{Long Long Constants - platform dependant} \index{mp\_set\_ll} \index{mp\_set\_ull} \begin{alltt} -void mp_set_ll (mp_int * a, long long b); -void mp_set_ull (mp_int * a, unsigned long long b); +void mp_set_ll (mp_int *a, long long b); +void mp_set_ull (mp_int *a, unsigned long long b); \end{alltt} -This will assign the value of the platform-dependent sized variable $b$ to the mp\_int $a$. +This will assign the value of the platform-dependent sized variable $b$ to the big integer $a$. To retrieve the value, the following functions can be used. @@ -918,35 +940,52 @@ \subsection{Long Long Constants - platform dependant} \index{mp\_get\_ull} \index{mp\_get\_mag\_ull} \begin{alltt} -long long mp_get_ll (mp_int * a); -unsigned long long mp_get_ull (mp_int * a); -unsigned long long mp_get_mag_ull (mp_int * a); +long long mp_get_ll (const mp_int *a); +unsigned long long mp_get_ull (const mp_int *a); +unsigned long long mp_get_mag_ull (const mp_int *a); +\end{alltt} + +This will return the least significant bits of $a$ that fit into the native data type \texttt{long long}. + +\subsection{Floating Point Constants - platform dependant} + +\index{mp\_set\_double} +\begin{alltt} +mp_err mp_set_double(mp_int *a, double b); +\end{alltt} + +If the platform supports the floating point data type \texttt{double} (binary64) this function will assign the integer part of \texttt{b} to the big integer $a$. This function will return \texttt{MP\_VAL} if \texttt{b} is \texttt{+/-inf} or \texttt{NaN}. + +To convert a big integer to a \texttt{double} use + +\index{mp\_get\_double} +\begin{alltt} +double mp_get_double(const mp_int *a); \end{alltt} -This will return the least significant bits of the mp\_int $a$ that fit into a ``long long''. \subsection{Initialize and Setting Constants} -To both initialize and set small constants the following two functions are available. +To both initialize and set small constants the following nine functions are available. \index{mp\_init\_set} \index{mp\_init\_set\_int} \begin{alltt} -int mp_init_set (mp_int * a, mp_digit b); -int mp_init_i32 (mp_int * a, int32_t b); -int mp_init_u32 (mp_int * a, uint32_t b); -int mp_init_i64 (mp_int * a, int64_t b); -int mp_init_u64 (mp_int * a, uint64_t b); -int mp_init_l (mp_int * a, long b); -int mp_init_ul (mp_int * a, unsigned long b); -int mp_init_ll (mp_int * a, long long b); -int mp_init_ull (mp_int * a, unsigned long long b); +mp_err mp_init_set (mp_int *a, mp_digit b); +mp_err mp_init_i32 (mp_int *a, int32_t b); +mp_err mp_init_u32 (mp_int *a, uint32_t b); +mp_err mp_init_i64 (mp_int *a, int64_t b); +mp_err mp_init_u64 (mp_int *a, uint64_t b); +mp_err mp_init_l (mp_int *a, long b); +mp_err mp_init_ul (mp_int *a, unsigned long b); +mp_err mp_init_ll (mp_int *a, long long b); +mp_err mp_init_ull (mp_int *a, unsigned long long b); \end{alltt} -Both functions work like the previous counterparts except they first mp\_init $a$ before setting the values. +Both functions work like the previous counterparts except they first initialize $a$ with the function \texttt{mp\_init} before setting the values. \begin{alltt} int main(void) \{ mp_int number1, number2; - int result; + mp_err result; /* initialize and set a single digit */ if ((result = mp_init_set(&number1, 100)) != MP_OKAY) \{ @@ -963,7 +1002,7 @@ \subsection{Initialize and Setting Constants} \} /* display */ - printf("Number1, Number2 == \%" PRIi32 ", \%" PRIi32, + printf("Number1, Number2 == \%" PRIi32 ", \%" PRIi32 "\textbackslash{}n", mp_get_i32(&number1), mp_get_i32(&number2)); /* clear */ @@ -978,6 +1017,8 @@ \subsection{Initialize and Setting Constants} Number1, Number2 == 100, 1023 \end{alltt} + + \section{Comparisons} Comparisons in LibTomMath are always performed in a ``left to right'' fashion. There are three possible return codes @@ -999,26 +1040,27 @@ \section{Comparisons} \end{figure} In figure \ref{fig:CMP} two integers $a$ and $b$ are being compared. In this case $a$ is said to be ``to the left'' of -$b$. +$b$. The return codes are of type \texttt{mp\_ord}. \subsection{Unsigned comparison} -An unsigned comparison considers only the digits themselves and not the associated \textit{sign} flag of the -mp\_int structures. This is analogous to an absolute comparison. The function mp\_cmp\_mag() will compare two -mp\_int variables based on their digits only. +An unsigned comparison considers only the digits themselves and not the associated \texttt{sign} flag of the +\texttt{mp\_int} structures. This is analogous to an absolute comparison. The function \texttt{mp\_cmp\_mag} will compare two +\texttt{mp\_int} variables based on their digits only. \index{mp\_cmp\_mag} \begin{alltt} -int mp_cmp_mag(mp_int * a, mp_int * b); +mp_ord mp_cmp_mag(mp_int *a, mp_int *b); \end{alltt} This will compare $a$ to $b$ placing $a$ to the left of $b$. This function cannot fail and will return one of the three compare codes listed in figure \ref{fig:CMP}. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number1, number2; - int result; + mp_err result; if ((result = mp_init_multi(&number1, &number2, NULL)) != MP_OKAY) \{ printf("Error initializing the numbers. \%s", @@ -1048,9 +1090,10 @@ \subsection{Unsigned comparison} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} -If this program\footnote{This function uses the mp\_neg() function which is discussed in section \ref{sec:NEG}.} completes +If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in section \ref{sec:NEG}.} completes successfully it should print the following. \begin{alltt} @@ -1061,22 +1104,23 @@ \subsection{Unsigned comparison} \subsection{Signed comparison} -To compare two mp\_int variables based on their signed value the mp\_cmp() function is provided. +To compare two \texttt{mp\_int} variables based on their signed value the \texttt{mp\_cmp} function is provided. \index{mp\_cmp} \begin{alltt} -int mp_cmp(mp_int * a, mp_int * b); +mp_ord mp_cmp(mp_int *a, mp_int *b); \end{alltt} -This will compare $a$ to the left of $b$. It will first compare the signs of the two mp\_int variables. If they +This will compare $a$ to the left of $b$. It will first compare the signs of the two \texttt{mp\_int} variables. If they differ it will return immediately based on their signs. If the signs are equal then it will compare the digits individually. This function will return one of the compare conditions codes listed in figure \ref{fig:CMP}. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number1, number2; - int result; + mp_err result; if ((result = mp_init_multi(&number1, &number2, NULL)) != MP_OKAY) \{ printf("Error initializing the numbers. \%s", @@ -1106,9 +1150,10 @@ \subsection{Signed comparison} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} -If this program\footnote{This function uses the mp\_neg() function which is discussed in section \ref{sec:NEG}.} completes +If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in section \ref{sec:NEG}.} completes successfully it should print the following. \begin{alltt} @@ -1117,11 +1162,11 @@ \subsection{Signed comparison} \subsection{Single Digit} -To compare a single digit against an mp\_int the following function has been provided. +To compare a single digit against an \texttt{mp\_int} the following function has been provided. \index{mp\_cmp\_d} \begin{alltt} -int mp_cmp_d(mp_int * a, mp_digit b); +mp_ord mp_cmp_d(mp_int *a, mp_digit b); \end{alltt} This will compare $a$ to the left of $b$ using a signed comparison. Note that it will always treat $b$ as @@ -1130,11 +1175,12 @@ \subsection{Single Digit} listed in figure \ref{fig:CMP}. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -1156,7 +1202,8 @@ \subsection{Single Digit} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} If this program functions properly it will print out the following. @@ -1177,18 +1224,19 @@ \subsection{Multiplication by two} When multiplying or dividing by two a special case routine can be used which are as follows. \index{mp\_mul\_2} \index{mp\_div\_2} \begin{alltt} -int mp_mul_2(mp_int * a, mp_int * b); -int mp_div_2(mp_int * a, mp_int * b); +mp_err mp_mul_2(const mp_int *a, mp_int *b); +mp_err mp_div_2(const mp_int *a, mp_int *b); \end{alltt} The former will assign twice $a$ to $b$ while the latter will assign half $a$ to $b$. These functions are fast since the shift counts and maskes are hardcoded into the routines. -\begin{small} \begin{alltt} +\begin{small} +\begin{alltt} int main(void) \{ mp_int number; - int result; + mp_err result; if ((result = mp_init(&number)) != MP_OKAY) \{ printf("Error initializing the number. \%s", @@ -1228,7 +1276,8 @@ \subsection{Multiplication by two} return EXIT_SUCCESS; \} -\end{alltt} \end{small} +\end{alltt} +\end{small} If this program is successful it will print out the following text. @@ -1243,29 +1292,29 @@ \subsection{Multiplication by two} \index{mp\_mul\_2d} \begin{alltt} -int mp_mul_2d(mp_int * a, int b, mp_int * c); +mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c); \end{alltt} -This will multiply $a$ by $2^b$ and store the result in ``c''. If the value of $b$ is less than or equal to -zero the function will copy $a$ to ``c'' without performing any further actions. The multiplication itself +This will multiply $a$ by $2^b$ and store the result in $c$. If the value of $b$ is less than or equal to +zero the function will copy $a$ to $c$ without performing any further actions. The multiplication itself is implemented as a right-shift operation of $a$ by $b$ bits. To divide by a power of two use the following. \index{mp\_div\_2d} \begin{alltt} -int mp_div_2d (mp_int * a, int b, mp_int * c, mp_int * d); +mp_err mp_div_2d (const mp_int *a, int b, mp_int *c, mp_int *d); \end{alltt} -Which will divide $a$ by $2^b$, store the quotient in ``c'' and the remainder in ``d'. If $b \le 0$ then the -function simply copies $a$ over to ``c'' and zeroes $d$. The variable $d$ may be passed as a \textbf{NULL} +Which will divide $a$ by $2^b$, store the quotient in $c$ and the remainder in $d$. If $b \le 0$ then the +function simply copies $a$ over to $c$ and zeroes $d$. The variable $d$ may be passed as a \texttt{NULL} value to signal that the remainder is not desired. The division itself is implemented as a left-shift operation of $a$ by $b$ bits. -It is also not very uncommon to need just the power of two $2^b$; for example the startvalue for the Newton method. +It is also not very uncommon to need just the power of two $2^b$; for example as a start-value for the Newton method. \index{mp\_2expt} \begin{alltt} -int mp_2expt(mp_int *a, int b); +mp_err mp_2expt(mp_int *a, int b); \end{alltt} It is faster than doing it by shifting $1$ with \texttt{mp\_mul\_2d}. @@ -1281,7 +1330,7 @@ \subsection{Polynomial Basis Operations} \index{mp\_lshd} \begin{alltt} -int mp_lshd (mp_int * a, int b); +mp_err mp_lshd (mp_int *a, int b); \end{alltt} This will multiply $a$ in place by $x^b$ which is equivalent to shifting the digits left $b$ places and inserting zeroes @@ -1289,7 +1338,7 @@ \subsection{Polynomial Basis Operations} \index{mp\_rshd} \begin{alltt} -void mp_rshd (mp_int * a, int b) +void mp_rshd (mp_int *a, int b) \end{alltt} This will divide $a$ in place by $x^b$ and discard the remainder. This function cannot fail as it performs the operations in place and no new digits are required to complete it. @@ -1301,33 +1350,24 @@ \subsection{AND, OR, XOR and COMPLEMENT Operations} \index{mp\_or} \index{mp\_and} \index{mp\_xor} \index{mp\_complement} \begin{alltt} -int mp_or (mp_int * a, mp_int * b, mp_int * c); -int mp_and (mp_int * a, mp_int * b, mp_int * c); -int mp_xor (mp_int * a, mp_int * b, mp_int * c); -int mp_complement(const mp_int *a, mp_int *b); -int mp_signed_rsh(mp_int * a, int b, mp_int * c, mp_int * d); +mp_err mp_or (const mp_int *a, mp_int *b, mp_int *c); +mp_err mp_and (const mp_int *a, mp_int *b, mp_int *c); +mp_err mp_xor (const mp_int *a, mp_int *b, mp_int *c); +mp_err mp_complement(const mp_int *a, mp_int *b); +mp_err mp_signed_rsh(const mp_int *a, int b, mp_int *c, mp_int *d); \end{alltt} The function \texttt{mp\_complement} computes a two-complement $b = \sim a$. The function \texttt{mp\_signed\_rsh} performs sign extending right shift. For positive numbers it is equivalent to \texttt{mp\_div\_2d}. -\subsection{Bit Picking} -\index{mp\_get\_bit} -\begin{alltt} -int mp_get_bit(mp_int *a, int b) -\end{alltt} - -Pick a bit: returns \texttt{MP\_YES} if the bit at position $b$ (0-index) is set, that is if it is 1 (one), \texttt{MP\_NO} -if the bit is 0 (zero) and \texttt{MP\_VAL} if $b < 0$. - \section{Addition and Subtraction} To compute an addition or subtraction the following two functions can be used. \index{mp\_add} \index{mp\_sub} \begin{alltt} -int mp_add (mp_int * a, mp_int * b, mp_int * c); -int mp_sub (mp_int * a, mp_int * b, mp_int * c) +mp_err mp_add (const mp_int *a, const mp_int *b, mp_int *c); +mp_err mp_sub (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} Which perform $c = a \odot b$ where $\odot$ is one of signed addition or subtraction. The operations are fully sign @@ -1340,7 +1380,7 @@ \subsection{Negation} \index{mp\_neg} \begin{alltt} -int mp_neg (mp_int * a, mp_int * b); +mp_err mp_neg (const mp_int *a, mp_int *b); \end{alltt} Which assigns $-a$ to $b$. @@ -1350,7 +1390,7 @@ \subsection{Absolute} \index{mp\_abs} \begin{alltt} -int mp_abs (mp_int * a, mp_int * b); +mp_err mp_abs (const mp_int *a, mp_int *b); \end{alltt} Which assigns $\vert a \vert$ to $b$. @@ -1360,12 +1400,12 @@ \section{Integer Division and Remainder} \index{mp\_div} \begin{alltt} -int mp_div (mp_int * a, mp_int * b, mp_int * c, mp_int * d); +mp_err mp_div (const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); \end{alltt} This divides $a$ by $b$ and stores the quotient in $c$ and $d$. The signed quotient is computed such that -$bc + d = a$. Note that either of $c$ or $d$ can be set to \textbf{NULL} if their value is not required. If -$b$ is zero the function returns \textbf{MP\_VAL}. +$bc + d = a$. Note that either of $c$ or $d$ can be set to \texttt{NULL} if their value is not required. If +$b$ is zero the function returns \texttt{MP\_VAL}. \chapter{Multiplication and Squaring} @@ -1373,7 +1413,7 @@ \section{Multiplication} A full signed integer multiplication can be performed with the following. \index{mp\_mul} \begin{alltt} -int mp_mul (mp_int * a, mp_int * b, mp_int * c); +mp_err mp_mul (const mp_int *a, const mp_int *b, mp_int *c); \end{alltt} Which assigns the full signed product $ab$ to $c$. This function actually breaks into one of four cases which are specific multiplication routines optimized for given parameters. First there are the Toom-Cook multiplications which @@ -1387,7 +1427,7 @@ \section{Multiplication} int main(void) \{ mp_int number1, number2; - int result; + mp_err result; /* Initialize the numbers */ if ((result = mp_init_multi(&number1, @@ -1427,23 +1467,23 @@ \section{Multiplication} \section{Squaring} Since squaring can be performed faster than multiplication it is performed it's own function instead of just using -mp\_mul(). +\texttt{mp\_mul}. \index{mp\_sqr} \begin{alltt} -int mp_sqr (mp_int * a, mp_int * b); +mp_err mp_sqr (const mp_int *a, mp_int *b); \end{alltt} Will square $a$ and store it in $b$. Like the case of multiplication there are four different squaring -algorithms all which can be called from mp\_sqr(). It is ideal to use mp\_sqr over mp\_mul when squaring terms because +algorithms all which can be called from the function \texttt{mp\_sqr}. It is ideal to use \texttt{mp\_sqr} over \texttt{mp\_mul} when squaring terms because of the speed difference. \section{Tuning Polynomial Basis Routines} Both of the Toom-Cook and Karatsuba multiplication algorithms are faster than the traditional $O(n^2)$ approach that the Comba and baseline algorithms use. At $O(n^{1.464973})$ and $O(n^{1.584962})$ running times respectively they require -considerably less work. For example, a 10000-digit multiplication would take roughly 724,000 single precision -multiplications with Toom-Cook or 100,000,000 single precision multiplications with the standard Comba (a factor +considerably less work. For example, a $10\,000$-digit multiplication would take roughly $724\,000$ single precision +multiplications with Toom-Cook or $100\,000\,000$ single precision multiplications with the standard Comba (a factor of 138). So why not always use Karatsuba or Toom-Cook? The simple answer is that they have so much overhead that they're not @@ -1451,9 +1491,6 @@ \section{Tuning Polynomial Basis Routines} GCC 3.3.1 and an Athlon XP processor the cutoff point is roughly 110 digits (about 70 for the Intel P4). That is, at 110 digits Karatsuba and Comba multiplications just about break even and for 110+ digits Karatsuba is faster. -Toom-Cook has incredible overhead and is probably only useful for very large inputs. So far no known cutoff points -exist and for the most part I just set the cutoff points very high to make sure they're not called. - To get reasonable values for the cut-off points for your architecture, type \begin{alltt} @@ -1480,14 +1517,14 @@ \chapter{Modular Reduction} fast reduction algorithms can be written for the limited range. Note that one of the four optimized reduction algorithms are automatically chosen in the modular exponentiation -algorithm mp\_exptmod when an appropriate modulus is detected. +algorithm \texttt{mp\_exptmod} when an appropriate modulus is detected. \section{Straight Division} In order to effect an arbitrary modular reduction the following algorithm is provided. \index{mp\_mod} \begin{alltt} -int mp_mod(mp_int *a, mp_int *b, mp_int *c); +mp_err mp_mod(const mp_int *a,const mp_int *b, mp_int *c); \end{alltt} This reduces $a$ modulo $b$ and stores the result in $c$. The sign of $c$ shall agree with the sign @@ -1500,7 +1537,7 @@ \section{Barrett Reduction} \index{mp\_reduce\_setup} \begin{alltt} -int mp_reduce_setup(mp_int *a, mp_int *b); +mp_err mp_reduce_setup(const mp_int *a, mp_int *b); \end{alltt} Given a modulus in $b$ this produces the required $\mu$ value in $a$. For any given modulus this only has to @@ -1508,7 +1545,7 @@ \section{Barrett Reduction} \index{mp\_reduce} \begin{alltt} -int mp_reduce(mp_int *a, mp_int *b, mp_int *c); +mp_err mp_reduce(const mp_int *a, const mp_int *b, mp_int *c); \end{alltt} This will reduce $a$ in place modulo $b$ with the precomputed $\mu$ value in $c$. $a$ must be in the range @@ -1518,7 +1555,7 @@ \section{Barrett Reduction} int main(void) \{ mp_int a, b, c, mu; - int result; + mp_err result; /* initialize a,b to desired values, mp_init mu, * c and set c to 1...we want to compute a^3 mod b @@ -1574,7 +1611,7 @@ \section{Montgomery Reduction} \index{mp\_montgomery\_setup} \begin{alltt} -int mp_montgomery_setup(mp_int *a, mp_digit *mp); +mp_err mp_montgomery_setup(const mp_int *a, mp_digit *mp); \end{alltt} For the given odd moduli $a$ the precomputation value is placed in $mp$. The reduction is computed with the @@ -1582,23 +1619,23 @@ \section{Montgomery Reduction} \index{mp\_montgomery\_reduce} \begin{alltt} -int mp_montgomery_reduce(mp_int *a, mp_int *m, mp_digit mp); +mp_err mp_montgomery_reduce(mp_int *a, mp_int *m, mp_digit mp); \end{alltt} This reduces $a$ in place modulo $m$ with the pre--computed value $mp$. $a$ must be in the range $0 \le a < b^2$. -Montgomery reduction is faster than Barrett reduction for moduli smaller than the ``comba'' limit. With the default +Montgomery reduction is faster than Barrett reduction for moduli smaller than the ``Comba'' limit. With the default setup for instance, the limit is $127$ digits ($3556$--bits). Note that this function is not limited to $127$ digits just that it falls back to a baseline algorithm after that point. An important observation is that this reduction does not return $a \mbox{ mod }m$ but $aR^{-1} \mbox{ mod }m$ -where $R = \beta^n$, $n$ is the n number of digits in $m$ and $\beta$ is radix used (default is $2^{28}$). +where $R = \beta^n$, $n$ is the n number of digits in $m$ and $\beta$ is the radix used (default is $2^{28}$). To quickly calculate $R$ the following function was provided. \index{mp\_montgomery\_calc\_normalization} \begin{alltt} -int mp_montgomery_calc_normalization(mp_int *a, mp_int *b); +mp_err mp_montgomery_calc_normalization(mp_int *a, mp_int *b); \end{alltt} Which calculates $a = R$ for the odd moduli $b$ without using multiplication or division. @@ -1611,7 +1648,7 @@ \section{Montgomery Reduction} \{ mp_int a, b, c, R; mp_digit mp; - int result; + mp_err result; /* initialize a,b to desired values, * mp_init R, c and set c to 1.... @@ -1683,7 +1720,7 @@ \section{Montgomery Reduction} normalizing the inputs the reduced results are always of the form $aR$ for some variable $a$. This allows a single final reduction to correct for the normalization and the fast reduction used within the algorithm. -For more details consider examining the file \textit{bn\_mp\_exptmod\_fast.c}. +For more details consider examining the file \texttt{bn\_mp\_exptmod\_fast.c}. \section{Restricted Diminished Radix} @@ -1695,16 +1732,23 @@ \section{Restricted Diminished Radix} \index{mp\_dr\_setup} \begin{alltt} -void mp_dr_setup(mp_int *a, mp_digit *d); +void mp_dr_setup(const mp_int *a, mp_digit *d); \end{alltt} This computes the value required for the modulus $a$ and stores it in $d$. This function cannot fail -and does not return any error codes. After the pre--computation a reduction can be performed with the -following. +and does not return any error codes. + +To determine if $a$ is a valid DR modulus: +\index{mp\_dr\_is\_modulus} +\begin{alltt} +mp_bool mp_dr_is_modulus(const mp_int *a); +\end{alltt} + +After the pre--computation a reduction can be performed with the following. \index{mp\_dr\_reduce} \begin{alltt} -int mp_dr_reduce(mp_int *a, mp_int *b, mp_digit mp); +mp_err mp_dr_reduce(mp_int *a, const mp_int *b, mp_digit mp); \end{alltt} This reduces $a$ in place modulo $b$ with the pre--computed value $mp$. $b$ must be of a restricted @@ -1724,20 +1768,30 @@ \section{Unrestricted Diminished Radix} form $2^k - p$ for $0 < p < \beta$. In this sense the unrestricted reductions are more flexible as they can be applied to a wider range of numbers. -\index{mp\_reduce\_2k\_setup} +\index{mp\_reduce\_2k\_setup}\index{mp\_reduce\_2k\_setup\_l} \begin{alltt} -int mp_reduce_2k_setup(mp_int *a, mp_digit *d); +mp_err mp_reduce_2k_setup(const mp_int *a, mp_digit *d); +mp_err mp_reduce_2k_setup_l(const mp_int *a, mp_int *d); \end{alltt} This will compute the required $d$ value for the given moduli $a$. -\index{mp\_reduce\_2k} +\index{mp\_reduce\_2k}\index{mp\_reduce\_2k\_l} \begin{alltt} -int mp_reduce_2k(mp_int *a, mp_int *n, mp_digit d); +mp_err mp_reduce_2k(mp_int *a, const mp_int *n, mp_digit d); +mp_err mp_reduce_2k_l(mp_int *a, const mp_int *n, const mp_int *d); \end{alltt} This will reduce $a$ in place modulo $n$ with the pre--computed value $d$. From my experience this routine is -slower than mp\_dr\_reduce but faster for most moduli sizes than the Montgomery reduction. +slower than the function \texttt{mp\_dr\_reduce} but faster for most moduli sizes than the Montgomery reduction. + +To determine if \texttt{mp\_reduce\_2k} can be used at all, ask the function \texttt{mp\_reduce\_is\_2k}. + +\index{mp\_reduce\_is\_2k}\index{mp\_reduce\_is\_2k\_l} +\begin{alltt} +mp_bool mp_reduce_is_2k(const mp_int *a); +mp_bool mp_reduce_is_2k_l(const mp_int *a); +\end{alltt} \section{Combined Modular Reduction} @@ -1746,38 +1800,38 @@ \section{Combined Modular Reduction} Addition $d = (a + b) \mod c$ \index{mp\_addmod} \begin{alltt} -int mp_addmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); +mp_err mp_addmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} Subtraction $d = (a - b) \mod c$ \begin{alltt} -int mp_submod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); +mp_err mp_submod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} Multiplication $d = (ab) \mod c$ \begin{alltt} -int mp_mulmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); +mp_err mp_mulmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} Squaring $d = (a^2) \mod c$ \begin{alltt} -int mp_sqrmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); +mp_err mp_sqrmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} \chapter{Exponentiation} \section{Single Digit Exponentiation} -\index{mp\_expt\_d} +\index{mp\_expt\_u32} \begin{alltt} -int mp_expt_d (mp_int * a, mp_digit b, mp_int * c) +mp_err mp_expt_u32 (const mp_int *a, uint32_t b, mp_int *c) \end{alltt} This function computes $c = a^b$. \section{Modular Exponentiation} \index{mp\_exptmod} \begin{alltt} -int mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y) +mp_err mp_exptmod (const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) \end{alltt} This computes $Y \equiv G^X \mbox{ (mod }P\mbox{)}$ using a variable width sliding window algorithm. This function will automatically detect the fastest modular reduction technique to use during the operation. For negative values of @@ -1792,14 +1846,14 @@ \section{Modular Exponentiation} \section{Modulus a Power of Two} \index{mp\_mod\_2d} \begin{alltt} -int mp_mod_2d(const mp_int *a, int b, mp_int *c) +mp_err mp_mod_2d(const mp_int *a, int b, mp_int *c) \end{alltt} It calculates $c = a \mod 2^b$. \section{Root Finding} \index{mp\_n\_root} \begin{alltt} -int mp_n_root (mp_int * a, mp_digit b, mp_int * c) +mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) \end{alltt} This computes $c = a^{1/b}$ such that $c^b \le a$ and $(c+1)^b > a$. Will return a positive root only for even roots and return a root with the sign of the input for odd roots. For example, performing $4^{1/2}$ will return $2$ whereas $(-8)^{1/3}$ @@ -1811,7 +1865,7 @@ \section{Root Finding} \index{mp\_sqrt} \begin{alltt} -int mp_sqrt (mp_int * a, mp_digit b, mp_int * c) +mp_err mp_sqrt(const mp_int *arg, mp_int *ret) \end{alltt} @@ -1820,7 +1874,7 @@ \section{Integer Logarithm} A logarithm function for positive integer input \texttt{a, base} computing $\floor{\log_bx}$ such that $(\log_b x)^b \le x$. \index{mp\_ilogb} \begin{alltt} -int mp_ilogb(mp_int *a, mp_digit base, mp_int *c) +mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) \end{alltt} \subsection{Example} \begin{alltt} @@ -1833,8 +1887,8 @@ \subsection{Example} int main(int argc, char **argv) { mp_int x, output; - mp_digit base; - int e; + uint32_t base; + mp_err e; if (argc != 3) { fprintf(stderr,"Usage %s base x\textbackslash{}n", argv[0]); @@ -1847,11 +1901,12 @@ \subsection{Example} } errno = 0; #ifdef MP_64BIT - base = (mp_digit)strtoull(argv[1], NULL, 10); + /* Check for overflow skipped */ + base = (uint32_t)strtoull(argv[1], NULL, 10); #else - base = (mp_digit)strtoul(argv[1], NULL, 10); + base = (uint32_t)strtoul(argv[1], NULL, 10); #endif - if ((errno == ERANGE) || (base > (base & MP_MASK))) { + if (errno == ERANGE) { fprintf(stderr,"strtoul(l) failed: input out of range\textbackslash{}n"); exit(EXIT_FAILURE); } @@ -1860,7 +1915,7 @@ \subsection{Example} mp_error_to_string(e)); exit(EXIT_FAILURE); } - if ((e = mp_ilogb(&x, base, &output)) != MP_OKAY) { + if ((e = mp_log_u32(&x, base, &output)) != MP_OKAY) { fprintf(stderr,"mp_ilogb failed: \textbackslash{}"%s\textbackslash{}"\textbackslash{}n", mp_error_to_string(e)); exit(EXIT_FAILURE); @@ -1878,23 +1933,12 @@ \subsection{Example} } \end{alltt} - - \chapter{Prime Numbers} -\section{Trial Division} -\index{mp\_prime\_is\_divisible} -\begin{alltt} -int mp_prime_is_divisible (mp_int * a, int *result) -\end{alltt} -This will attempt to evenly divide $a$ by a list of primes\footnote{Default is the first 256 primes.} and store the -outcome in ``result''. That is if $result = 0$ then $a$ is not divisible by the primes, otherwise it is. Note that -if the function does not return \textbf{MP\_OKAY} the value in ``result'' should be considered undefined\footnote{Currently -the default is to set it to zero first.}. \section{Fermat Test} \index{mp\_prime\_fermat} \begin{alltt} -int mp_prime_fermat (mp_int * a, mp_int * b, int *result) +mp_err mp_prime_fermat (const mp_int *a, const mp_int *b, int *result) \end{alltt} Performs a Fermat primality test to the base $b$. That is it computes $b^a \mbox{ mod }a$ and tests whether the value is equal to $b$ or not. If the values are equal then $a$ is probably prime and $result$ is set to one. Otherwise $result$ @@ -1903,13 +1947,13 @@ \section{Fermat Test} \section{Miller-Rabin Test} \index{mp\_prime\_miller\_rabin} \begin{alltt} -int mp_prime_miller_rabin (mp_int * a, mp_int * b, int *result) +mp_err mp_prime_miller_rabin (const mp_int *a, const mp_int *b, int *result) \end{alltt} Performs a Miller-Rabin test to the base $b$ of $a$. This test is much stronger than the Fermat test and is very hard to fool (besides with Carmichael numbers). If $a$ passes the test (therefore is probably prime) $result$ is set to one. Otherwise $result$ is set to zero. -Note that is suggested that you use the Miller-Rabin test instead of the Fermat test since all of the failures of +Note that it is suggested that you use the Miller-Rabin test instead of the Fermat test since all of the failures of Miller-Rabin are a subset of the failures of the Fermat test. \subsection{Required Number of Tests} @@ -1919,9 +1963,9 @@ \subsection{Required Number of Tests} \index{mp\_prime\_rabin\_miller\_trials} \begin{alltt} -int mp_prime_rabin_miller_trials(int size) +mp_err mp_prime_rabin_miller_trials(int size) \end{alltt} -This returns the number of trials required for a low probability of failure for a given ``size'' expressed in bits. This comes in handy specially since larger numbers are slower to test. For example, a 512-bit number would require 18 tests for a probability of $2^{-160}$ whereas a 1024-bit number would only require 12 tests for a probability of $2^{-192}$. The exact values as implemented are listed in table \ref{table:millerrabinrunsimpl}. +This returns the number of trials required for a low probability of failure for a given \texttt{size} expressed in bits. This comes in handy specially since larger numbers are slower to test. For example, a 512-bit number would require 18 tests for a probability of $2^{-160}$ whereas a 1024-bit number would only require 12 tests for a probability of $2^{-192}$. The exact values as implemented are listed in table \ref{table:millerrabinrunsimpl}. \begin{table}[h] \begin{center} @@ -1952,9 +1996,8 @@ \subsection{Required Number of Tests} \end{center} \end{table} -You should always still perform a trial division before a Miller-Rabin test though. +A small table, broke in two for typographical reasons, with the number of rounds of Miller-Rabin tests is shown below. The numbers have been computed with a PARI/GP script listed in appendix \ref{app:numberofmrcomp}. -A small table, broke in two for typographical reasons, with the number of rounds of Miller-Rabin tests is shown below. The numbers have been compute with a PARI/GP script listed in appendix \ref{app:numberofmrcomp}. The first column is the number of bits $b$ in the prime $p = 2^b$, the numbers in the first row represent the probability that the number that all of the Miller-Rabin tests deemed a pseudoprime is actually a composite. There is a deterministic test for numbers smaller than $2^{80}$. @@ -2029,7 +2072,7 @@ \subsection{Required Number of Tests} \section{Strong Lucas-Selfridge Test} \index{mp\_prime\_strong\_lucas\_selfridge} \begin{alltt} -int mp_prime_strong_lucas_selfridge(const mp_int *a, int *result) +mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) \end{alltt} Performs a strong Lucas-Selfridge test. The strong Lucas-Selfridge test together with the Rabin-Miler test with bases $2$ and $3$ resemble the BPSW test. The single internal use is a compile-time option in \texttt{mp\_prime\_is\_prime} and can be excluded from the Libtommath build if not needed. @@ -2037,7 +2080,7 @@ \section{Strong Lucas-Selfridge Test} \section{Frobenius (Underwood) Test} \index{mp\_prime\_frobenius\_underwood} \begin{alltt} -int mp_prime_frobenius_underwood(const mp_int *N, int *result) +mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) \end{alltt} Performs the variant of the Frobenius test as described by Paul Underwood. It can be included at build-time if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined and will be used instead of the Lucas-Selfridge test. @@ -2047,40 +2090,39 @@ \section{Primality Testing} Testing if a number is a square can be done a bit faster than just by calculating the square root. It is used by the primality testing function described below. \index{mp\_is\_square} \begin{alltt} -int mp_is_square(const mp_int *arg, int *ret); +mp_err mp_is_square(const mp_int *arg, mp_bool *ret); \end{alltt} \index{mp\_prime\_is\_prime} \begin{alltt} -int mp_prime_is_prime (mp_int * a, int t, int *result) +mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) \end{alltt} This will perform a trial division followed by two rounds of Miller-Rabin with bases 2 and 3 and a Lucas-Selfridge test. The Frobenius-Underwood is available as a compile-time option with the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST}. See file \texttt{bn\_mp\_prime\_is\_prime.c} for the necessary details. It shall be noted that both functions are much slower than -the Miller-Rabin test and if speed is an essential issue, the macro \texttt{LTM\_USE\_ONLY\_MR} switches both functions, the Frobenius-Underwood test and the Lucas-Selfridge test off and their code will not even be compiled into the library. +the Miller-Rabin test and if speed is an essential issue, the macro \texttt{LTM\_USE\_ONLY\_MR} switches the Frobenius-Underwood test and the Lucas-Selfridge test off and their code will not even be compiled into the library. -If $t$ is set to a positive value $t$ additional rounds of the Miller-Rabin test with random bases will be performed to allow for Fips 186.4 (vid.~p.~126ff) compliance. The function \texttt{mp\_prime\_rabin\_miller\_trials} can be used to determine the number of rounds. It is vital that the function \texttt{mp\_rand()} has a cryptographically strong random number generator available. +If $t$ is set to a positive value $t$ additional rounds of the Miller-Rabin test with random bases will be performed to allow for Fips 186.4 (vid.~p.~126ff) compliance. The function \texttt{mp\_prime\_rabin\_miller\_trials} can be used to determine the number of rounds. It is vital that the function \texttt{mp\_rand} has a cryptographically strong random number generator available. One Miller-Rabin tests with a random base will be run automatically, so by setting $t$ to a positive value this function will run $t + 1$ Miller-Rabin tests with random bases. -If $t$ is set to a negative value the test will run the deterministic Miller-Rabin test for the primes up to $3317044064679887385961981$. That limit has to be checked by the caller. +If $t$ is set to a negative value the test will run the deterministic Miller-Rabin test for the primes up to $3\,317\,044\,064\,679\,887\,385\,961\,981$\footnote{The semiprime $1287836182261\cdot 2575672364521$ with both factors smaller than $2^64$. An alternative with all factors smaller than $2^32$ is $4290067842\cdot 262853\cdot 1206721\cdot 2134439 + 3$}. That limit has to be checked by the caller. -If $a$ passes all of the tests $result$ is set to one, otherwise it is set to zero. +If $a$ passes all of the tests $result$ is set to \texttt{MP\_YES}, otherwise it is set to \texttt{MP\_NO}. \section{Next Prime} \index{mp\_prime\_next\_prime} \begin{alltt} -int mp_prime_next_prime(mp_int *a, int t, int bbs_style) +mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) \end{alltt} -This finds the next prime after $a$ that passes mp\_prime\_is\_prime() with $t$ tests but see the documentation for -mp\_prime\_is\_prime for details regarding the use of the argument $t$. Set $bbs\_style$ to one if you -want only the next prime congruent to $3 \mbox{ mod } 4$, otherwise set it to zero to find any next prime. +This finds the next prime after $a$ that passes the function \texttt{mp\_prime\_is\_prime} with $t$ tests but see the documentation for +\texttt{mp\_prime\_is\_prime} for details regarding the use of the argument $t$. Set $bbs\_style$ to \texttt{MP\_YES} if you +want only the next prime congruent to $3 \mbox{ mod } 4$, otherwise set it to \texttt{MP\_NO} to find any next prime. \section{Random Primes} \index{mp\_prime\_rand} \begin{alltt} -int mp_prime_rand(mp_int *a, int t, - int size, int flags); +mp_err mp_prime_rand(mp_int *a, int t, int size, int flags); \end{alltt} This will generate a prime in $a$ using $t$ tests of the primality testing algorithms. See the documentation for mp\_prime\_is\_prime for details regarding the use of the argument $t$. @@ -2115,88 +2157,95 @@ \chapter{Random Number Generation} \section{PRNG} \index{mp\_rand\_digit} \begin{alltt} -int mp_rand_digit(mp_digit *r) +mp_err mp_rand_digit(mp_digit *r) \end{alltt} -This function generates a random number in \texttt{r} of the size given in \texttt{r} (that is, the variable is used for in- and output) but not more than \texttt{MP\_MASK} bits. +This function generates a random number in \texttt{r} of the size given in \texttt{r} (that is, the variable is used for in- and output) but not more than \texttt{MP\_DIGIT\_MAX} bits. \index{mp\_rand} \begin{alltt} -int mp_rand(mp_int *a, int digits) +mp_err mp_rand(mp_int *a, int digits) \end{alltt} This function generates a random number of \texttt{digits} bits. The random number generated with these two functions is cryptographically secure if the source of random numbers the operating systems offers is cryptographically secure. It will use \texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev/urandom} on all operating systems that have it. +If you have a custom random source you might find the function \texttt(mp\_rand\_source) useful. +\index{mp\_rand\_source} +\begin{alltt} +void mp_rand_source(mp_err(*source)(void *out, size_t size)); +\end{alltt} + \chapter{Input and Output} \section{ASCII Conversions} \subsection{To ASCII} \index{mp\_to\_radix} \begin{alltt} -int mp_to_radix (mp_int *a, char *str, size_t maxlen, size_t *written, int radix); +mp_err mp_to_radix (const mp_int *a, char *str, size_t maxlen, size_t *written, int radix); \end{alltt} This stores $a$ in \texttt{str} of maximum length \texttt{maxlen} as a base-\texttt{radix} string of ASCII chars and appends a \texttt{NUL} character to terminate the string. -Valid values of \texttt{radix} line in the range $[2, 64]$. +Valid values of \texttt{radix} are in the range $[2, 64]$. The exact number of characters in \texttt{str} plus the \texttt{NUL} will be put in \texttt{written} if that variable is not set to \texttt{NULL}. If \texttt{str} is not big enough to hold $a$, \texttt{str} will be filled with the least-significant digits -of length \texttt{maxlen-1}, then \texttt{str} will be \texttt{NUL} terminated and the error \texttt{MP\_VAL} is returned. +of length \texttt{maxlen-1}, then \texttt{str} will be \texttt{NUL} terminated and the error \texttt{MP\_BUF} is returned. Please be aware that this function cannot evaluate the actual size of the buffer, it relies on the correctness of \texttt{maxlen}! \index{mp\_radix\_size} \begin{alltt} -int mp_radix_size (mp_int * a, int radix, int *size) +mp_err mp_radix_size (const mp_int *a, int radix, int *size) \end{alltt} -This stores in ``size'' the number of characters (including space for the NUL terminator) required. Upon error this -function returns an error code and ``size'' will be zero. +This stores in \texttt{size} the number of characters (including space for the NUL terminator) required. Upon error this +function returns an error code and \texttt{size} will be zero. If \texttt{MP\_NO\_FILE} is not defined a function to write to a file is also available. \index{mp\_fwrite} \begin{alltt} -int mp_fwrite(const mp_int *a, int radix, FILE *stream); +mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream); \end{alltt} \subsection{From ASCII} \index{mp\_read\_radix} \begin{alltt} -int mp_read_radix (mp_int * a, char *str, int radix); +mp_err mp_read_radix (mp_int *a, const char *str, int radix); \end{alltt} -This will read the base-``radix'' NUL terminated string from ``str'' into $a$. It will stop reading when it reads a -character it does not recognize (which happens to include th NUL char... imagine that...). A single leading $-$ sign +This will read a \texttt{NUL} terminated string in base \texttt{radix} from \texttt{str} into $a$. It will stop reading when it reads a +character it does not recognize (which happens to include the \texttt{NUL} char... imagine that...). A single leading $-$ sign can be used to denote a negative number. +The input encoding is currently restricted to ASCII only. If \texttt{MP\_NO\_FILE} is not defined a function to read from a file is also available. \index{mp\_fread} \begin{alltt} -int mp_fread(mp_int *a, int radix, FILE *stream); +mp_err mp_fread(mp_int *a, int radix, FILE *stream); \end{alltt} \section{Binary Conversions} -Converting an mp\_int to and from binary is another keen idea. +Converting an \texttt{mp\_int} to and from binary is another keen idea. \index{mp\_ubin\_size} \begin{alltt} -size_t mp_ubin_size(mp_int *a); +size_t mp_ubin_size(const mp_int *a); \end{alltt} This will return the number of bytes (octets) required to store the unsigned copy of the integer $a$. \index{mp\_to\_ubin} \begin{alltt} -int mp_to_unsigned_bin(mp_int *a, unsigned char *b, size_t maxlen, size_t *len); +mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) \end{alltt} This will store $a$ into the buffer $b$ of size \texttt{maxlen} in big--endian format storing the number of bytes written in \texttt{len}. Fortunately this is exactly what DER (or is it ASN?) requires. It does not store the sign of the integer. \index{mp\_from\_ubin} \begin{alltt} -int mp_from_ubin(mp_int *a, unsigned char *b, size_t size); +mp_err mp_from_ubin(mp_int *a, unsigned char *b, size_t size); \end{alltt} This will read in an unsigned big--endian array of bytes (octets) from $b$ of length \texttt{size} into $a$. The resulting big-integer $a$ will always be positive. @@ -2204,26 +2253,26 @@ \section{Binary Conversions} previous functions. \index{mp\_signed\_bin\_size} \index{mp\_to\_signed\_bin} \index{mp\_read\_signed\_bin} \begin{alltt} -int mp_sbin_size(mp_int *a); -int mp_from_sbin(mp_int *a, unsigned char *b, size_t size); -int mp_to_sbin(mp_int *a, unsigned char *b, size_t maxsize, size_t *len); +size_t mp_sbin_size(const mp_int *a); +mp_err mp_from_sbin(mp_int *a, const unsigned char *b, size_t size); +mp_err mp_to_sbin(const mp_int *a, unsigned char *b, size_t maxsize, size_t *len); \end{alltt} They operate essentially the same as the unsigned copies except they prefix the data with zero or non--zero -byte depending on the sign. If the sign is zpos (e.g. not negative) the prefix is zero, otherwise the prefix +byte depending on the sign. If the sign is \texttt{MP\_ZPOS} (e.g. not negative) the prefix is zero, otherwise the prefix is non--zero. The two functions \texttt{mp\_unpack} (get your gifts out of the box, import binary data) and \texttt{mp\_pack} (put your gifts into the box, export binary data) implement the similarly working GMP functions as described at \url{http://gmplib.org/manual/Integer-Import-and-Export.html} with the exception that \texttt{mp\_pack} will not allocate memory if \texttt{rop} is \texttt{NULL}. \index{mp\_unpack} \index{mp\_pack} \begin{alltt} -int mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, +mp_err mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, mp_endian endian, size_t nails, const void *op, size_t maxsize); -int mp_pack(void *rop, size_t *countp, mp_order order, size_t size, +mp_err mp_pack(void *rop, size_t *countp, mp_order order, size_t size, mp_endian endian, size_t nails, const mp_int *op); \end{alltt} The function \texttt{mp\_pack} has the additional variable \texttt{maxsize} which must hold the size of the buffer \texttt{rop} in bytes. Use \begin{alltt} /* Parameters "nails" and "size" are the same as in mp_pack */ -size_t mp_pack_size(mp_int *a, size_t nails, size_t size); +size_t mp_pack_count(const mp_int *a, size_t nails, size_t size); \end{alltt} To get the size in bytes necessary to be put in \texttt{maxsize}). @@ -2244,58 +2293,52 @@ \chapter{Algebraic Functions} \section{Extended Euclidean Algorithm} \index{mp\_exteuclid} \begin{alltt} -int mp_exteuclid(mp_int *a, mp_int *b, +mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp_int *U3); \end{alltt} -This finds the triple U1/U2/U3 using the Extended Euclidean algorithm such that the following equation holds. +This finds the triple $U_1$/$U_2$/$U_3$ using the Extended Euclidean algorithm such that the following equation holds. \begin{equation} -a \cdot U1 + b \cdot U2 = U3 +a \cdot U_1 + b \cdot U_2 = U_3 \end{equation} -Any of the U1/U2/U3 parameters can be set to \textbf{NULL} if they are not desired. +Any of the \texttt{U1}/\texttt{U2}/\texttt{U3} parameters can be set to \textbf{NULL} if they are not desired. \section{Greatest Common Divisor} \index{mp\_gcd} \begin{alltt} -int mp_gcd (mp_int * a, mp_int * b, mp_int * c) +mp_err mp_gcd (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} This will compute the greatest common divisor of $a$ and $b$ and store it in $c$. \section{Least Common Multiple} \index{mp\_lcm} \begin{alltt} -int mp_lcm (mp_int * a, mp_int * b, mp_int * c) +mp_err mp_lcm (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} This will compute the least common multiple of $a$ and $b$ and store it in $c$. -\section{Jacobi Symbol} -\index{mp\_jacobi} -\begin{alltt} -int mp_jacobi (mp_int * a, mp_int * p, int *c) -\end{alltt} -This will compute the Jacobi symbol for $a$ with respect to $p$. If $p$ is prime this essentially computes the Legendre -symbol. The result is stored in $c$ and can take on one of three values $\lbrace -1, 0, 1 \rbrace$. If $p$ is prime -then the result will be $-1$ when $a$ is not a quadratic residue modulo $p$. The result will be $0$ if $a$ divides $p$ -and the result will be $1$ if $a$ is a quadratic residue modulo $p$. \section{Kronecker Symbol} \index{mp\_kronecker} \begin{alltt} -int mp_kronecker (mp_int * a, mp_int * p, int *c) +mp_err mp_kronecker (const mp_int *a, const mp_int *p, int *c) \end{alltt} -Extension of the Jacoby symbol to all $\lbrace a, p \rbrace \in \mathbb{Z}$ . +This will compute the Kronecker symbol (an extension of the Jacobi symbol) for $a$ with respect to $p$ with $\lbrace a, p \rbrace \in \mathbb{Z}$. If $p$ is prime this essentially computes the Legendre +symbol. The result is stored in $c$ and can take on one of three values $\lbrace -1, 0, 1 \rbrace$. If $p$ is prime +then the result will be $-1$ when $a$ is not a quadratic residue modulo $p$. The result will be $0$ if $a$ divides $p$ +and the result will be $1$ if $a$ is a quadratic residue modulo $p$. \section{Modular square root} \index{mp\_sqrtmod\_prime} \begin{alltt} -int mp_sqrtmod_prime(mp_int *n, mp_int *p, mp_int *r) +mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *p, mp_int *r) \end{alltt} -This will solve the modular equatioon $r^2 = n \mod p$ where $p$ is a prime number greater than 2 (odd prime). -The result is returned in the third argument $r$, the function returns \textbf{MP\_OKAY} on success, +This will solve the modular equation $r^2 = n \mod p$ where $p$ is a prime number greater than 2 (odd prime). +The result is returned in the third argument $r$, the function returns \texttt{MP\_OKAY} on success, other return values indicate failure. The implementation is split for two different cases: @@ -2307,12 +2350,12 @@ \section{Modular square root} The function does not check the primality of parameter $p$ thus it is up to the caller to assure that this parameter is a prime number. When $p$ is a composite the function behaviour is undefined, it may even return a false-positive -\textbf{MP\_OKAY}. +\texttt{MP\_OKAY}. \section{Modular Inverse} \index{mp\_invmod} \begin{alltt} -int mp_invmod (mp_int * a, mp_int * b, mp_int * c) +mp_err mp_invmod (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} Computes the multiplicative inverse of $a$ modulo $b$ and stores the result in $c$ such that $ac \equiv 1 \mbox{ (mod }b\mbox{)}$. @@ -2322,21 +2365,21 @@ \section{Single Digit Functions} \index{mp\_add\_d} \index{mp\_sub\_d} \index{mp\_mul\_d} \index{mp\_div\_d} \index{mp\_mod\_d} \begin{alltt} -int mp_add_d(mp_int *a, mp_digit b, mp_int *c); -int mp_sub_d(mp_int *a, mp_digit b, mp_int *c); -int mp_mul_d(mp_int *a, mp_digit b, mp_int *c); -int mp_div_d(mp_int *a, mp_digit b, mp_int *c, mp_digit *d); -int mp_mod_d(mp_int *a, mp_digit b, mp_digit *c); +mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c); +mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c); +mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c); +mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d); +mp_err mp_mod_d(const mp_int *a, mp_digit b, mp_digit *c); \end{alltt} -These work like the full mp\_int capable variants except the second parameter $b$ is a mp\_digit. These +These work like the full \texttt{mp\_int} capable variants except the second parameter $b$ is a \texttt{mp\_digit}. These functions fairly handy if you have to work with relatively small numbers since you will not have to allocate -an entire mp\_int to store a number like $1$ or $2$. +an entire \texttt{mp\_int} to store a number like $1$ or $2$. The functions \texttt{mp\_incr} and \texttt{mp\_decr} mimic the postfix operators \texttt{++} and \texttt{--} respectively, to increment the input by one. They call the full single-digit functions if the addition would carry. Both functions need to be included in a minimized library because they call each other in case of a negative input, These functions change the inputs! \begin{alltt} -int mp_incr(mp_int *a); -int mp_decr(mp_int *a); +mp_err mp_incr(mp_int *a); +mp_err mp_decr(mp_int *a); \end{alltt} @@ -2344,7 +2387,7 @@ \section{Single Digit Functions} \index{mp\_div\_3} \begin{alltt} -int mp_div_3(const mp_int *a, mp_int *c, mp_digit *d); +mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d); \end{alltt} \chapter{Little Helpers} @@ -2354,26 +2397,26 @@ \section{Function Macros} \index{mp\_iseven} \begin{alltt} -int mp_iseven(mp_int *a) +mp_bool mp_iseven(const mp_int *a) \end{alltt} Checks if $a = 0 mod 2$ \index{mp\_isodd} \begin{alltt} -int mp_isodd(mp_int *a) +mp_bool mp_isodd(const mp_int *a) \end{alltt} Checks if $a = 1 mod 2$ \index{mp\_isneg} \begin{alltt} -int mp_isneg(mp_int *a) +mp_bool mp_isneg(mp_int *a) \end{alltt} Checks if $a < 0$ \index{mp\_iszero} \begin{alltt} -int mp_iszero(mp_int *a) +mp_bool mp_iszero(mp_int *a) \end{alltt} Checks if $a = 0$. It does not check if the amount of memory allocated for $a$ is also minimal. From 3947ffda95ada6f171a2624f5cd64b9d6a307425 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 25 Oct 2019 00:41:09 +0200 Subject: [PATCH 060/304] backup --- doc/.latexindent.yaml | 1 + doc/bn.tex | 7 ++++--- 2 files changed, 5 insertions(+), 3 deletions(-) create mode 100644 doc/.latexindent.yaml diff --git a/doc/.latexindent.yaml b/doc/.latexindent.yaml new file mode 100644 index 000000000..578bb4ec4 --- /dev/null +++ b/doc/.latexindent.yaml @@ -0,0 +1 @@ +defaultIndent: " " diff --git a/doc/bn.tex b/doc/bn.tex index 292f68025..caa3bb36d 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -352,9 +352,10 @@ \section{Purpose of LibTomMath} \newpage\begin{figure}[h] \begin{small} \begin{center} -\begin{tabular}{|l|c|c|l|} +\begin{tabular}{|p{4.5cm}|c|c|p{4.5cm}|} \hline \textbf{Criteria} & \textbf{Pro} & \textbf{Con} & \textbf{Notes} \\ -\hline Few lines of code per file & X & & GnuPG $ = 300.9$, LibTomMath $ = 71.97$ \\ +\hline Few lines of code per file & X & & GnuPG $ = 300.9$\\ +&&& LibTomMath $ = 71.97$\hfill \\ \hline Commented function prototypes & X && GnuPG function names are cryptic. \\ \hline Speed && X & LibTomMath is slower. \\ \hline Totally free & X & & GPL has unfavourable restrictions.\\ @@ -380,7 +381,7 @@ \section{Purpose of LibTomMath} Essentially the only time you wouldn't use LibTomMath is when blazing speed is the primary concern. However, on the other side of the coin LibTomMath offers you a totally free (public domain) well structured math library that is very flexible, complete and performs well in resource constrained environments. Fast RSA for example can -be performed with as little as 8KB of ram for data (again depending on build options). +be performed with as little as 8 Kibibytes of RAM for data (again depending on build options). \chapter{Getting Started with LibTomMath} \section{Building Programs} From 2efbdd543c6fc6a1ad0a0910aea6d3bd337e13ef Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 25 Oct 2019 02:44:42 +0200 Subject: [PATCH 061/304] more clean-ups and addition of a latexinden.pl configuration file --- doc/.latexindent.yaml | 36 +- doc/bn.tex | 1557 ++++++++++++++++++++++++----------------- doc/makefile | 7 + 3 files changed, 941 insertions(+), 659 deletions(-) diff --git a/doc/.latexindent.yaml b/doc/.latexindent.yaml index 578bb4ec4..7409a0449 100644 --- a/doc/.latexindent.yaml +++ b/doc/.latexindent.yaml @@ -1 +1,35 @@ -defaultIndent: " " +# 2 spaces +defaultIndent: " " +# verbatim environments- environments specified +# in this hash table will not be changed at all! +verbatimEnvironments: + verbatim: 1 + alltt: 1 +# verbatim commands such as \verb! body !, \lstinline$something else$ +verbatimCommands: + verb: 1 + +# no indent blocks (not necessarily verbatim +# environments) which are marked as %\begin{noindent} +# or anything else that the user puts in this hash +# table +noIndentBlock: + noindent: 1 + +# remove trailing whitespace from all lines +removeTrailingWhitespace: + beforeProcessing: 0 + afterProcessing: 1 + +indentAfterItems: + itemize: 1 + enumerate: 1 + description: 1 + list: 1 + +onlyOneBackUp: 1 + +modifyLineBreaks: + textWrapOptions: + columns: 100 + diff --git a/doc/bn.tex b/doc/bn.tex index caa3bb36d..430c82a06 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -46,6 +46,7 @@ \newcommand{\emailaddr}[1]{\mbox{$<${#1}$>$}} \def\twiddle{\raisebox{0.3ex}{\mbox{\tiny $\sim$}}} \def\gap{\vspace{0.5ex}} + \makeindex \begin{document} \frontmatter @@ -53,21 +54,22 @@ \title{LibTomMath User Manual \\ v1.2.0} \author{LibTom Projects \\ www.libtom.net} \maketitle -This text, the library and the accompanying textbook are all hereby placed in the public domain. This book has been +This text, the library and the accompanying textbook are all hereby placed in the public domain. +This book has been formatted for B5 [176x250] paper using the \LaTeX{} {\em book} macro package. \vspace{10cm} -\begin{flushright}Open Source. Open Academia. Open Minds. +\begin{flushright}Open Source. Open Academia. Open Minds. -\mbox{ } -LibTom Projects + \mbox{ } + LibTom Projects -\& originally + \& originally -Tom St Denis, + Tom St Denis, -Ontario, Canada + Ontario, Canada \end{flushright} \tableofcontents @@ -76,42 +78,54 @@ \pagestyle{headings} \chapter{Introduction} \section{What is LibTomMath?} -LibTomMath is a library of source code which provides a series of efficient and carefully written functions for manipulating -large integer numbers. It was written in portable ISO C source code so that it will build on any platform with a conforming -C compiler. +LibTomMath is a library of source code which provides a series of efficient and carefully written +functions for manipulating large integer numbers. It was written in portable ISO C source code so +that it will build on any platform with a conforming C compiler. -In a nutshell the library was written from scratch with verbose comments to help instruct computer science students how -to implement ``bignum'' math. However, the resulting code has proven to be very useful. It has been used by numerous -universities, commercial and open source software developers. It has been used on a variety of platforms ranging from -Linux and Windows based x86 to ARM based Gameboys and PPC based MacOS machines. +In a nutshell the library was written from scratch with verbose comments to help instruct computer +science students how to implement ``bignum'' math. However, the resulting code has proven to be +very useful. It has been used by numerous universities, commercial and open source software +developers. It has been used on a variety of platforms ranging from Linux and Windows based x86 to +ARM based Gameboys and PPC based MacOS machines. \section{License} -As of the v0.25 the library source code has been placed in the public domain with every new release. As of the v0.28 -release the textbook ``Implementing Multiple Precision Arithmetic'' has been placed in the public domain with every new -release as well. This textbook is meant to compliment the project by providing a more solid walkthrough of the development -algorithms used in the library. +As of the v0.25 the library source code has been placed in the public domain with every new +release. As of the v0.28 release the textbook ``Implementing Multiple Precision Arithmetic'' has +been placed in the public domain with every new release as well. This textbook is meant to +compliment the project by providing a more solid walkthrough of the development algorithms used in +the library. -Since both\footnote{Note that the MPI files under \texttt{mtest/} are copyrighted by Michael Fromberger. They are not required to use LibTomMath.} are in the -public domain everyone is entitled to do with them as they see fit. +Since both\footnote{Note that the MPI files under \texttt{mtest/} are copyrighted by Michael + Fromberger. They are not required to use LibTomMath.} are in the public domain everyone is +entitled +to do with them as they see fit. \section{Building LibTomMath} -LibTomMath is meant to be very ``GCC friendly'' as it comes with a makefile well suited for GCC. However, the library will -also build in MSVC, Borland C out of the box. For any other ISO C compiler a makefile will have to be made by the end -developer. Please consider to commit such a makefile to the LibTomMath developers, currently residing at +LibTomMath is meant to be very ``GCC friendly'' as it comes with a makefile well suited for GCC. +However, the library will also build in MSVC, Borland C out of the box. For any other ISO C +compiler a makefile will have to be made by the end +developer. Please consider to commit such a makefile to the LibTomMath developers, currently +residing at \url{http://github.com/libtom/libtommath}, if successfully done so. -Intel's C-compiler (ICC) is sufficiently compatible with GCC, at least the newer versions, to replace GCC for building the static and the shared library. Editing the makefiles is not needed, just set the shell variable \texttt{CC} as shown below. +Intel's C-compiler (ICC) is sufficiently compatible with GCC, at least the newer versions, to +replace GCC for building the static and the shared library. Editing the makefiles is not needed, +just set the shell variable \texttt{CC} as shown below. \begin{alltt} CC=/home/czurnieden/intel/bin/icc make \end{alltt} -ICC does not know all options available for GCC and LibTomMath uses two diagnostics \texttt{-Wbad-function-cast} and \texttt{-Wcast-align} that are not supported by ICC resulting in the warnings: +ICC does not know all options available for GCC and LibTomMath uses two diagnostics +\texttt{-Wbad-function-cast} and \texttt{-Wcast-align} that are not supported by ICC resulting in +the warnings: \begin{alltt} icc: command line warning #10148: option '-Wbad-function-cast' not supported icc: command line warning #10148: option '-Wcast-align' not supported \end{alltt} -It is possible to mute this ICC warning with the compiler flag \texttt{-diag-disable=10148}\footnote{It is not recommended to suppress warnings without a very good reason but there is no harm in doing so in this very special case.}. +It is possible to mute this ICC warning with the compiler flag +\texttt{-diag-disable=10148}\footnote{It is not recommended to suppress warnings without a very + good reason but there is no harm in doing so in this very special case.}. \subsection{Static Libraries} To build as a static library for GCC issue the following @@ -119,16 +133,17 @@ \subsection{Static Libraries} make \end{alltt} -command. This will build the library and archive the object files in ``libtommath.a''. Now you link against -that and include ``tommath.h'' within your programs. Alternatively to build with MSVC issue the following +command. This will build the library and archive the object files in ``libtommath.a''. Now you +link against that and include ``tommath.h'' within your programs. Alternatively to build with MSVC +issue the following \begin{alltt} nmake -f makefile.msvc \end{alltt} -This will build the library and archive the object files in ``tommath.lib''. This has been tested with MSVC -version 6.00 with service pack 5. +This will build the library and archive the object files in ``tommath.lib''. This has been tested +with MSVC version 6.00 with service pack 5. -To run a program to adapt the Toom-Cook cut-off values to your architecture type +To run a program to adapt the Toom--Cook cut--off values to your architecture type \begin{alltt} make tune \end{alltt} @@ -140,23 +155,28 @@ \subsubsection{GNU based Operating Systems} \begin{alltt} make -f makefile.shared \end{alltt} -This requires the ``libtool'' package (common on most Linux/BSD systems). It will build LibTomMath as both shared -and static then install (by default) into /usr/lib as well as install the header files in /usr/include. The shared -library (resource) will be called \texttt{libtommath.la} while the static library called \texttt{libtommath.a}. Generally -you use libtool to link your application against the shared object. +This requires the ``libtool'' package (common on most Linux/BSD systems). It will build LibTomMath +as both shared and static then install (by default) into /usr/lib as well as install the header +files in \texttt{/usr/include}. The shared library (resource) will be called +\texttt{libtommath.la} while the static library called \texttt{libtommath.a}. Generally you use +libtool to link your application against the shared object. -To run a program to adapt the Toom-Cook cut-off values to your architecture type +To run a program to adapt the Toom--Cook cut--off values to your architecture type \begin{alltt} make -f makefile.shared tune \end{alltt} This will take some time. \subsubsection{Microsoft Windows based Operating Systems} -There is limited support for making a ``DLL'' in windows via the \texttt{makefile.cygwin\_dll} makefile. It requires -Cygwin to work with since it requires the auto-export/import functionality. The resulting DLL and import library -\texttt{libtommath.dll.a} can be used to link LibTomMath dynamically to any Windows program using Cygwin. +There is limited support for making a ``DLL'' in windows via the \texttt{makefile.cygwin\_dll} +makefile. It requires Cygwin to work with since it requires the auto-export/import functionality. +The resulting DLL and import library \texttt{libtommath.dll.a} can be used to link LibTomMath +dynamically to any Windows program using Cygwin. + \subsubsection{OpenBSD} -OpenBSD replaced some of their GNU-tools, especially \texttt{libtool} with their own, slightly different versions. To ease the workload of LibTomMath's developer team, only a static library can be build with the included \texttt{makefile.unix}. +OpenBSD replaced some of their GNU-tools, especially \texttt{libtool} with their own, slightly +different versions. To ease the workload of LibTomMath's developer team, only a static library can +be build with the included \texttt{makefile.unix}. The wrong \texttt{make} will result in errors like: \begin{alltt} @@ -182,11 +202,15 @@ \subsubsection{OpenBSD} gmake: *** [makefile.shared:64: libtommath.la] Error 1 \end{alltt} -To build a shared library with OpenBSD\footnote{Tested with OpenBSD version 6.4} the GNU versions of \texttt{make} and \texttt{libtool} are needed. +To build a shared library with OpenBSD\footnote{Tested with OpenBSD version 6.4} the GNU versions +of \texttt{make} and \texttt{libtool} are needed. \begin{alltt} $ sudo pkg_add gmake libtool \end{alltt} -At this time two versions of \texttt{libtool} are installed and both are named \texttt{libtool}, unfortunately but GNU \texttt{libtool} has been placed in \texttt{/usr/local/bin/} and the native version in \texttt{/usr/bin/}. The path might be different in other versions of OpenBSD but both programms differ in the output of \texttt{libtool --version} +At this time two versions of \texttt{libtool} are installed and both are named \texttt{libtool}, +unfortunately but GNU \texttt{libtool} has been placed in \texttt{/usr/local/bin/} and the native +version in \texttt{/usr/bin/}. The path might be different in other versions of OpenBSD but both +programms differ in the output of \texttt{libtool --version} \begin{alltt} $ /usr/local/bin/libtool --version libtool (GNU libtool) 2.4.2 @@ -206,7 +230,8 @@ \subsubsection{OpenBSD} You might need to run a \texttt{gmake -f makefile.shared clean} first. \subsubsection{NetBSD} -NetBSD is not as strict as OpenBSD but still needs \texttt{gmake} to build the shared library. \texttt{libtool} may also not exist in a fresh install. +NetBSD is not as strict as OpenBSD but still needs \texttt{gmake} to build the shared library. +\texttt{libtool} may also not exist in a fresh install. \begin{alltt} pkg_add gmake libtool \end{alltt} @@ -223,212 +248,244 @@ \subsection{Testing} make test \end{alltt} -This will build the library, \texttt{test} and \texttt{mtest/mtest}. The \texttt{test} program will accept test vectors and verify the -results. \texttt{mtest/mtest} will generate test vectors using the MPI library by Michael Fromberger\footnote{A copy of MPI -is included in the package}. Simply pipe \texttt{mtest} into \texttt{test} using +This will build the library, \texttt{test} and \texttt{mtest/mtest}. The \texttt{test} program +will accept test vectors and verify the results. \texttt{mtest/mtest} will generate test vectors +using the MPI library by Michael Fromberger\footnote{A copy of MPI is included in the package}. +Simply pipe \texttt{mtest} into \texttt{test} using \begin{alltt} mtest/mtest | test \end{alltt} -If you do not have a \texttt{/dev/urandom} style RNG source you will have to write your own PRNG and simply pipe that into -\texttt{mtest}. For example, if your PRNG program is called \texttt{myprng} simply invoke +If you do not have a \texttt{/dev/urandom} style RNG source you will have to write your own PRNG +and simply pipe that into \texttt{mtest}. For example, if your PRNG program is called +\texttt{myprng} simply invoke \begin{alltt} myprng | mtest/mtest | test \end{alltt} -This will output a row of numbers that are increasing. Each column is a different test (such as addition, multiplication, etc) -that is being performed. The numbers represent how many times the test was invoked. If an error is detected the program -will exit with a dump of the relevant numbers it was working with. +This will output a row of numbers that are increasing. Each column is a different test (such as +addition, multiplication, etc) that is being performed. The numbers represent how many times the +test was invoked. If an error is detected the program will exit with a dump of the relevant +numbers it was working with. \section{Build Configuration} -LibTomMath can configured at build time in three phases we shall call ``depends'', ``tweaks'' and ``trims''. -Each phase changes how the library is built and they are applied one after another respectively. +LibTomMath can configured at build time in three phases we shall call ``depends'', ``tweaks'' and +``trims''. Each phase changes how the library is built and they are applied one after another +respectively. To make the system more powerful you can tweak the build process. Classes are defined in the file -\texttt{tommath\_superclass.h}. By default, the symbol \texttt{LTM\_ALL} shall be defined which simply -instructs the system to build all of the functions. This is how LibTomMath used to be packaged. This will give you -access to every function LibTomMath offers. +\texttt{tommath\_superclass.h}. By default, the symbol \texttt{LTM\_ALL} shall be defined which +simply instructs the system to build all of the functions. This is how LibTomMath used to be +packaged. This will give you access to every function LibTomMath offers. -However, there are cases where such a build is not optional. For instance, you want to perform RSA operations. You -don't need the vast majority of the library to perform these operations. Aside from \texttt{LTM\_ALL} there is -another pre--defined class \texttt{SC\_RSA\_1} which works in conjunction with the RSA from LibTomCrypt. Additional -classes can be defined base on the need of the user. +However, there are cases where such a build is not optional. For instance, you want to perform RSA +operations. You don't need the vast majority of the library to perform these operations. Aside +from \texttt{LTM\_ALL} there is another pre--defined class \texttt{SC\_RSA\_1} which works in +conjunction with the RSA from LibTomCrypt. Additional classes can be defined base on the need of +the user. \subsection{Build Depends} -In the file \texttt{tommath\_class.h} you will see a large list of C ``defines'' followed by a series of ``ifdefs'' -which further define symbols. All of the symbols (technically they're macros $\ldots$) represent a given C source -file. For instance, \texttt{MP\_ADD\_C} represents the file \texttt{mp\_add.c}. When a define has been enabled the -function in the respective file will be compiled and linked into the library. Accordingly when the define -is absent the file will not be compiled and not contribute any size to the library. +In the file \texttt{tommath\_class.h} you will see a large list of C ``defines'' followed by a +series of ``ifdefs'' which further define symbols. All of the symbols (technically they're macros +$\ldots$) represent a given C source file. For instance, \texttt{MP\_ADD\_C} represents the file +\texttt{mp\_add.c}. When a define has been enabled the function in the respective file will be +compiled and linked into the library. Accordingly when the define is absent the file will not be +compiled and not contribute any size to the library. -You will also note that the header \texttt{tommath\_class.h} is actually recursively included (it includes itself twice). -This is to help resolve as many dependencies as possible. In the last pass the symbol \texttt{LTM\_LAST} will be defined. -This is useful for ``trims''. +You will also note that the header \texttt{tommath\_class.h} is actually recursively included (it +includes itself twice). This is to help resolve as many dependencies as possible. In the last pass +the symbol \texttt{LTM\_LAST} will be defined. This is useful for ``trims''. \subsection{Build Tweaks} -A tweak is an algorithm ``alternative''. For example, to provide tradeoffs (usually between size and space). +A tweak is an algorithm ``alternative''. For example, to provide tradeoffs (usually between size +and space). They can be enabled at any pass of the configuration phase. \begin{small} -\begin{center} -\begin{tabular}{|l|l|} -\hline \textbf{Define} & \textbf{Purpose} \\ -\hline MP\_DIV\_SMALL & Enables a slower, smaller and equally \\ - & functional mp\_div() function \\ -\hline -\end{tabular} -\end{center} + \begin{center} + \begin{tabular}{|l|l|} + \hline \textbf{Define} & \textbf{Purpose} \\ + \hline MP\_DIV\_SMALL & Enables a slower, smaller and equally \\ + & functional mp\_div() function \\ + \hline + \end{tabular} + \end{center} \end{small} \subsection{Build Trims} -A trim is a manner of removing functionality from a function that is not required. For instance, to perform -RSA cryptography you only require exponentiation with odd moduli so even moduli support can be safely removed. -Build trims are meant to be defined on the last pass of the configuration which means they are to be defined -only if \texttt{LTM\_LAST} has been defined. +A trim is a manner of removing functionality from a function that is not required. For instance, +to perform RSA cryptography you only require exponentiation with odd moduli so even moduli support +can be safely removed. Build trims are meant to be defined on the last pass of the configuration +which means they are to be defined only if \texttt{LTM\_LAST} has been defined. \subsubsection{Moduli Related} \begin{small} -\begin{center} -\begin{tabular}{|l|l|} -\hline \textbf{Restriction} & \textbf{Undefine} \\ -\hline Exponentiation with odd moduli only & S\_MP\_EXPTMOD\_C \\ - & MP\_REDUCE\_C \\ - & MP\_REDUCE\_SETUP\_C \\ - & S\_MP\_MUL\_HIGH\_DIGS\_C \\ - & FAST\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ -\hline Exponentiation with random odd moduli & (The above plus the following) \\ - & MP\_REDUCE\_2K\_C \\ - & MP\_REDUCE\_2K\_SETUP\_C \\ - & MP\_REDUCE\_IS\_2K\_C \\ - & MP\_DR\_IS\_MODULUS\_C \\ - & MP\_DR\_REDUCE\_C \\ - & MP\_DR\_SETUP\_C \\ -\hline Modular inverse odd moduli only & MP\_INVMOD\_SLOW\_C \\ -\hline Modular inverse (both, smaller/slower) & FAST\_MP\_INVMOD\_C \\ -\hline -\end{tabular} -\end{center} + \begin{center} + \begin{tabular}{|l|l|} + \hline \textbf{Restriction} & \textbf{Undefine} \\ + \hline Exponentiation with odd moduli only & S\_MP\_EXPTMOD\_C \\ + & MP\_REDUCE\_C \\ + & MP\_REDUCE\_SETUP\_C \\ + & S\_MP\_MUL\_HIGH\_DIGS\_C \\ + & FAST\_S\_MP\_MUL\_HIGH\_DIGS\_C \\ + \hline Exponentiation with random odd moduli & (The above plus the following) \\ + & MP\_REDUCE\_2K\_C \\ + & MP\_REDUCE\_2K\_SETUP\_C \\ + & MP\_REDUCE\_IS\_2K\_C \\ + & MP\_DR\_IS\_MODULUS\_C \\ + & MP\_DR\_REDUCE\_C \\ + & MP\_DR\_SETUP\_C \\ + \hline Modular inverse odd moduli only & MP\_INVMOD\_SLOW\_C \\ + \hline Modular inverse (both, smaller/slower) & FAST\_MP\_INVMOD\_C \\ + \hline + \end{tabular} + \end{center} \end{small} \subsubsection{Operand Size Related} \begin{small} -\begin{center} -\begin{tabular}{|l|l|} -\hline \textbf{Restriction} & \textbf{Undefine} \\ -\hline Moduli $\le 2560$ bits & MP\_MONTGOMERY\_REDUCE\_C \\ - & S\_MP\_MUL\_DIGS\_C \\ - & S\_MP\_MUL\_HIGH\_DIGS\_C \\ - & S\_MP\_SQR\_C \\ -\hline Polynomial Schmolynomial & MP\_KARATSUBA\_MUL\_C \\ - & MP\_KARATSUBA\_SQR\_C \\ - & MP\_TOOM\_MUL\_C \\ - & MP\_TOOM\_SQR\_C \\ - -\hline -\end{tabular} -\end{center} + \begin{center} + \begin{tabular}{|l|l|} + \hline \textbf{Restriction} & \textbf{Undefine} \\ + \hline Moduli $\le 2560$ bits & MP\_MONTGOMERY\_REDUCE\_C \\ + & S\_MP\_MUL\_DIGS\_C \\ + & S\_MP\_MUL\_HIGH\_DIGS\_C \\ + & S\_MP\_SQR\_C \\ + \hline Polynomial Schmolynomial & MP\_KARATSUBA\_MUL\_C \\ + & MP\_KARATSUBA\_SQR\_C \\ + & MP\_TOOM\_MUL\_C \\ + & MP\_TOOM\_SQR\_C \\ + + \hline + \end{tabular} + \end{center} \end{small} - \section{Purpose of LibTomMath} -Unlike GNU MP (GMP) Library, LIP, OpenSSL or various other commercial kits (Miracl), LibTomMath was not written with -bleeding edge performance in mind. First and foremost LibTomMath was written to be entirely open. Not only is the -source code public domain (unlike various other GPL/etc licensed code), not only is the code freely downloadable but the -source code is also accessible for computer science students attempting to learn ``BigNum'' or multiple precision -arithmetic techniques. +Unlike GNU MP (GMP) Library, LIP, OpenSSL or various other commercial kits (Miracl), LibTomMath +was not written with bleeding edge performance in mind. First and foremost LibTomMath was written +to be entirely open. Not only is the source code public domain (unlike various other GPL/etc +licensed code), not only is the code freely downloadable but the source code is also accessible for +computer science students attempting to learn ``BigNum'' or multiple precision arithmetic +techniques. -LibTomMath was written to be an instructive collection of source code. This is why there are many comments, only one -function per source file and often I use a ``middle-road'' approach where I don't cut corners for an extra 2\% speed -increase. +LibTomMath was written to be an instructive collection of source code. This is why there are many +comments, only one function per source file and often I use a ``middle-road'' approach where I +don't cut corners for an extra 2\% speed increase. -Source code alone cannot really teach how the algorithms work which is why I also wrote a textbook that accompanies -the library (beat that!). +Source code alone cannot really teach how the algorithms work which is why I also wrote a textbook +that accompanies the library (beat that!). -So you may be thinking ``should I use LibTomMath?'' and the answer is a definite maybe. Let me tabulate what I think -are the pros and cons of LibTomMath by comparing it to the math routines from GnuPG\footnote{GnuPG v1.2.3 versus LibTomMath v0.28}. +So you may be thinking ``should I use LibTomMath?'' and the answer is a definite maybe. Let me +tabulate what I think are the pros and cons of LibTomMath by comparing it to the math routines from +GnuPG\footnote{GnuPG v1.2.3 versus LibTomMath v0.28}. \newpage\begin{figure}[h] -\begin{small} -\begin{center} -\begin{tabular}{|p{4.5cm}|c|c|p{4.5cm}|} -\hline \textbf{Criteria} & \textbf{Pro} & \textbf{Con} & \textbf{Notes} \\ -\hline Few lines of code per file & X & & GnuPG $ = 300.9$\\ -&&& LibTomMath $ = 71.97$\hfill \\ -\hline Commented function prototypes & X && GnuPG function names are cryptic. \\ -\hline Speed && X & LibTomMath is slower. \\ -\hline Totally free & X & & GPL has unfavourable restrictions.\\ -\hline Large function base & X & & GnuPG is barebones. \\ -\hline Five modular reduction algorithms & X & & Faster modular exponentiation for a variety of moduli. \\ -\hline Portable & X & & GnuPG requires configuration to build. \\ -\hline -\end{tabular} -\end{center} -\end{small} -\caption{LibTomMath Valuation} + \begin{small} + \begin{center} + \begin{tabular}{|p{4.5cm}|c|c|p{4.5cm}|} + \hline \textbf{Criteria} & \textbf{Pro} & \textbf{Con} & \textbf{Notes} + \\ + \hline Few lines of code per file & X & & GnuPG $ = 300.9$ + \\ + & & & LibTomMath $ = + 71.97$\hfill + \\ + \hline Commented function prototypes & X & & GnuPG function + names are cryptic. + \\ + \hline Speed & & X & LibTomMath is + slower. + \\ + \hline Totally free & X & & GPL has + unfavourable restrictions. + \\ + \hline Large function base & X & & GnuPG is + barebones. + \\ + \hline Five modular reduction algorithms & X & & Faster modular + exponentiation for a variety of + moduli. + \\ + \hline Portable & X & & GnuPG requires + configuration to build. + \\ + \hline + \end{tabular} + \end{center} + \end{small} + \caption{LibTomMath Valuation} \end{figure} -It may seem odd to compare LibTomMath to GnuPG since the math in GnuPG is only a small portion of the entire application. -However, LibTomMath was written with cryptography in mind. It provides essentially all of the functions a cryptosystem -would require when working with large integers. +It may seem odd to compare LibTomMath to GnuPG since the math in GnuPG is only a small portion of +the entire application. However, LibTomMath was written with cryptography in mind. It provides +essentially all of the functions a cryptosystem would require when working with large integers. -So it may feel tempting to just rip the math code out of GnuPG (or GnuMP where it was taken from originally) in your -own application but I think there are reasons not to. While LibTomMath is slower than libraries such as GnuMP it is -not normally significantly slower. On x86 machines the difference is normally a factor of two when performing modular -exponentiations. It depends largely on the processor, compiler and the moduli being used. +So it may feel tempting to just rip the math code out of GnuPG (or GnuMP where it was taken from +originally) in your own application but I think there are reasons not to. While LibTomMath is +slower than libraries such as GnuMP it is not normally significantly slower. On x86 machines the +difference is normally a factor of two when performing modular exponentiations. It depends largely +on the processor, compiler and the moduli being used. -Essentially the only time you wouldn't use LibTomMath is when blazing speed is the primary concern. However, -on the other side of the coin LibTomMath offers you a totally free (public domain) well structured math library -that is very flexible, complete and performs well in resource constrained environments. Fast RSA for example can -be performed with as little as 8 Kibibytes of RAM for data (again depending on build options). +Essentially the only time you wouldn't use LibTomMath is when blazing speed is the primary concern. +However, on the other side of the coin LibTomMath offers you a totally free (public domain) well +structured math library that is very flexible, complete and performs well in resource constrained +environments. Fast RSA for example can be performed with as little as 8 Kibibytes of RAM for data +(again depending on build options). \chapter{Getting Started with LibTomMath} \section{Building Programs} -In order to use LibTomMath you must include ``tommath.h'' and link against the appropriate library file (typically -libtommath.a). There is no library initialization required and the entire library is thread safe. +In order to use LibTomMath you must include ``tommath.h'' and link against the appropriate library +file (typically +libtommath.a). There is no library initialization required and the entire library is thread safe. \section{Return Codes} There are five possible return codes a function may return. -\index{MP\_OKAY}\index{MP\_YES}\index{MP\_NO}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{MP\_BUF} +\index{MP\_OKAY}\index{MP\_YES}\index{MP\_NO}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{M + P\_BUF} \begin{figure}[h!] -\begin{center} -\begin{small} -\begin{tabular}{|l|l|} -\hline \textbf{Code} & \textbf{Meaning} \\ -\hline MP\_OKAY & The function succeeded. \\ -\hline MP\_VAL & The function input was invalid. \\ -\hline MP\_MEM & Heap memory exhausted. \\ -\hline MP\_ITER & Maximum iterations reached. \\ -\hline MP\_BUF & Buffer overflow, supplied buffer too small.\\ -\hline &\\ -\hline MP\_YES & Response is yes. \\ -\hline MP\_NO & Response is no. \\ -\hline -\end{tabular} -\end{small} -\end{center} -\caption{Return Codes} + \begin{center} + \begin{small} + \begin{tabular}{|l|l|} + \hline \textbf{Code} & \textbf{Meaning} \\ + \hline MP\_OKAY & The function succeeded. \\ + \hline MP\_VAL & The function input was invalid. \\ + \hline MP\_MEM & Heap memory exhausted. \\ + \hline MP\_ITER & Maximum iterations reached. \\ + \hline MP\_BUF & Buffer overflow, supplied buffer too small. \\ + \hline & \\ + \hline MP\_YES & Response is yes. \\ + \hline MP\_NO & Response is no. \\ + \hline + \end{tabular} + \end{small} + \end{center} + \caption{Return Codes} \end{figure} -The error codes \texttt{MP\_OKAY},\texttt{MP\_VAL}, \texttt{MP\_MEM}, \texttt{MP\_ITER}, and \texttt{MP\_BUF} are of the type \texttt{mp\_err}, the codes \texttt{MP\_YES} and \texttt{MP\_NO} are of type \texttt{mp\_bool}. +The error codes \texttt{MP\_OKAY},\texttt{MP\_VAL}, \texttt{MP\_MEM}, \texttt{MP\_ITER}, and +\texttt{MP\_BUF} are of the type \texttt{mp\_err}, the codes \texttt{MP\_YES} and \texttt{MP\_NO} +are of type \texttt{mp\_bool}. -The last two codes listed are not actually ``return'ed'' by a function. They are placed in an integer (the caller must -provide the address of an integer it can store to) which the caller can access. To convert one of the three return codes -to a string use the following function. +The last two codes listed are not actually ``return'ed'' by a function. They are placed in an +integer (the caller must provide the address of an integer it can store to) which the caller can +access. To convert one of the three return codes to a string use the following function. \index{mp\_error\_to\_string} \begin{alltt} char *mp_error_to_string(int code); \end{alltt} -This will return a pointer to a string which describes the given error code. It will not work for the return codes \texttt{MP\_YES} and \texttt{MP\_NO}. +This will return a pointer to a string which describes the given error code. It will not work for +the return codes \texttt{MP\_YES} and \texttt{MP\_NO}. \section{Data Types} -The basic ``multiple precision integer'' type is known as the \texttt{mp\_int} within LibTomMath. This data type is used to -organize all of the data required to manipulate the integer it represents. Within LibTomMath it has been prototyped -as the following. +The basic ``multiple precision integer'' type is known as the \texttt{mp\_int} within LibTomMath. +This data type is used to organize all of the data required to manipulate the integer it +represents. Within LibTomMath it has been prototyped as the following. \index{mp\_int} \begin{alltt} @@ -439,34 +496,35 @@ \section{Data Types} \} mp_int; \end{alltt} -Where \texttt{mp\_digit} is a data type that represents individual digits of the integer. By default, an \texttt{mp\_digit} is the -ISO C \texttt{unsigned long} data type and each digit is $28-$bits long. The \texttt{mp\_digit} type can be configured to suit other -platforms by defining the appropriate macros. +Where \texttt{mp\_digit} is a data type that represents individual digits of the integer. By +default, an \texttt{mp\_digit} is the ISO C \texttt{unsigned long} data type and each digit is +$28-$bits long. The \texttt{mp\_digit} type can be configured to suit other platforms by defining +the appropriate macros. -All LTM functions that use the \texttt{mp\_int} type will expect a pointer to \texttt{mp\_int} structure. You must allocate memory to -hold the structure itself by yourself (whether off stack or heap it doesn't matter). The very first thing that must be -done to use an \texttt{mp\_int} is that it must be initialized. +All LTM functions that use the \texttt{mp\_int} type will expect a pointer to \texttt{mp\_int} +structure. You must allocate memory to hold the structure itself by yourself (whether off stack or +heap it doesn't matter). The very first thing that must be done to use an \texttt{mp\_int} is that +it must be initialized. \section{Function Organization} -The arithmetic functions of the library are all organized to have the same style prototype. That is source operands -are passed on the left and the destination is on the right. For instance, - +The arithmetic functions of the library are all organized to have the same style prototype. That +is source operands are passed on the left and the destination is on the right. For instance, \begin{alltt} mp_add(&a, &b, &c); /* c = a + b */ mp_mul(&a, &a, &c); /* c = a * a */ mp_div(&a, &b, &c, &d); /* c = [a/b], d = a mod b */ \end{alltt} -Another feature of the way the functions have been implemented is that source operands can be destination operands as well. -For instance, +Another feature of the way the functions have been implemented is that source operands can be +destination operands as well. For instance, \begin{alltt} mp_add(&a, &b, &b); /* b = a + b */ mp_div(&a, &b, &a, &c); /* a = [a/b], c = a mod b */ \end{alltt} -This allows operands to be re-used which can make programming simpler. +This allows operands to be re--used which can make programming simpler. \section{Initialization} \subsection{Single Initialization} @@ -477,12 +535,13 @@ \subsection{Single Initialization} mp_err mp_init (mp_int *a); \end{alltt} -This function expects a pointer to an \texttt{mp\_int} structure and will initialize the members of the structure so the \texttt{mp\_int} -represents the default integer which is zero. If the functions returns \texttt{MP\_OKAY} then the \texttt{mp\_int} is ready to be used -by the other LibTomMath functions. +This function expects a pointer to an \texttt{mp\_int} structure and will initialize the members +ofthe structure so the \texttt{mp\_int} represents the default integer which is zero. If the +functions returns \texttt{MP\_OKAY} then the \texttt{mp\_int} is ready to be used by the other +LibTomMath functions. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -498,24 +557,24 @@ \subsection{Single Initialization} return EXIT_SUCCESS; \} -\end{alltt} + \end{alltt} \end{small} \subsection{Single Free} -When you are finished with an \texttt{mp\_int} it is ideal to return the heap it used back to the system. The following function -provides this functionality. - +When you are finished with an \texttt{mp\_int} it is ideal to return the heap it used back to the +system. The following function provides this functionality. \index{mp\_clear} \begin{alltt} void mp_clear (mp_int *a); \end{alltt} -The function expects a pointer to a previously initialized \texttt{mp\_int} structure and frees the heap it uses. It sets the -pointer\footnote{The \texttt{dp} member.} within the \texttt{mp\_int} to \texttt{NULL} which is used to prevent double free situations. -Is is legal to call \texttt{mp\_clear} twice on the same \texttt{mp\_int} in a row. +The function expects a pointer to a previously initialized \texttt{mp\_int} structure and frees the +heap it uses. It sets the pointer\footnote{The \texttt{dp} member.} within the \texttt{mp\_int} to +\texttt{NULL} which is used to prevent double free situations. Is is legal to call +\texttt{mp\_clear} twice on the same \texttt{mp\_int} in a row. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -534,13 +593,13 @@ \subsection{Single Free} return EXIT_SUCCESS; \} -\end{alltt} + \end{alltt} \end{small} \subsection{Multiple Initializations} -Certain algorithms require more than one large integer. In these instances it is ideal to initialize all of the \texttt{mp\_int} -variables in an ``all or nothing'' fashion. That is, they are either all initialized successfully or they are all -not initialized. +Certain algorithms require more than one large integer. In these instances it is ideal to +initialize all of the \texttt{mp\_int} variables in an ``all or nothing'' fashion. That is, they +are either all initialized successfully or they are all not initialized. The \texttt{mp\_init\_multi} function provides this functionality. @@ -549,13 +608,16 @@ \subsection{Multiple Initializations} mp_err mp_init_multi(mp_int *mp, ...); \end{alltt} -It accepts a \texttt{NULL} terminated list of pointers to \texttt{mp\_int} structures. It will attempt to initialize them all -at once. If the function returns \texttt{MP\_OKAY} then all of the \texttt{mp\_int} variables are ready to use, otherwise none of them -are available for use. A complementary \texttt{mp\_clear\_multi} function allows multiple \texttt{mp\_int} variables to be free'd +It accepts a \texttt{NULL} terminated list of pointers to \texttt{mp\_int} structures. It will +attempt to initialize them all at once. If the function returns \texttt{MP\_OKAY} then all of the +\texttt{mp\_int} variables are ready to use, otherwise none of them are available for use. + +A complementary \texttt{mp\_clear\_multi} function allows multiple \texttt{mp\_int} variables to be +free'd from the heap at the same time. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int num1, num2, num3; @@ -580,7 +642,8 @@ \subsection{Multiple Initializations} \end{small} \subsection{Other Initializers} -To initialized and make a copy of an \texttt{mp\_int} the \texttt{mp\_init\_copy} function has been provided. +To initialized and make a copy of an \texttt{mp\_int} the \texttt{mp\_init\_copy} function has been +provided. \index{mp\_init\_copy} \begin{alltt} @@ -590,7 +653,7 @@ \subsection{Other Initializers} This function will initialize $a$ and make it a copy of $b$ if all goes well. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int num1, num2; @@ -615,20 +678,20 @@ \subsection{Other Initializers} \end{alltt} \end{small} -Another less common initializer is \texttt{mp\_init\_size} which allows the user to initialize an \texttt{mp\_int} with a given -default number of digits. By default, all initializers allocate \texttt{MP\_PREC} digits. This function lets -you override this behaviour. +Another less common initializer is \texttt{mp\_init\_size} which allows the user to initialize an +\texttt{mp\_int} with a given default number of digits. By default, all initializers allocate +\texttt{MP\_PREC} digits. This function lets you override this behaviour. \index{mp\_init\_size} \begin{alltt} mp_err mp_init_size (mp_int *a, int size); \end{alltt} -The $size$ parameter must be greater than zero. If the function succeeds the \texttt{mp\_int} $a$ will be initialized -to have $size$ digits (which are all initially zero). +The $size$ parameter must be greater than zero. If the function succeeds the \texttt{mp\_int} $a$ +will be initialized to have $size$ digits (which are all initially zero). \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -651,8 +714,8 @@ \subsection{Other Initializers} \section{Maintenance Functions} \subsection{Clear Leading Zeros} -This is used to ensure that leading zero digits are trimmed and the leading "used" digit will be non-zero. -It also fixes the sign if there are no more leading digits. +This is used to ensure that leading zero digits are trimmed and the leading "used" digit will be +non--zero. It also fixes the sign if there are no more leading digits. \index{mp\_clamp} \begin{alltt} @@ -668,23 +731,24 @@ \subsection{Zero Out} void mp_zero(mp_int *a); \end{alltt} - \subsection{Reducing Memory Usage} -When an \texttt{mp\_int} is in a state where it won't be changed again\footnote{A Diffie-Hellman modulus for instance.} excess -digits can be removed to return memory to the heap with the \texttt{mp\_shrink} function. +When an \texttt{mp\_int} is in a state where it won't be changed again\footnote{A Diffie--Hellman + modulus for instance.} excess digits can be removed to return memory to the heap with the +\texttt{mp\_shrink} function. \index{mp\_shrink} \begin{alltt} mp_err mp_shrink (mp_int *a); \end{alltt} -This will remove excess digits of the \texttt{mp\_int} $a$. If the operation fails the \texttt{mp\_int} should be intact without the -excess digits being removed. Note that you can use a shrunk \texttt{mp\_int} in further computations, however, such operations -will require heap operations which can be slow. It is not ideal to shrink \texttt{mp\_int} variables that you will further -modify in the system (unless you are seriously low on memory). +This will remove excess digits of the \texttt{mp\_int} $a$. If the operation fails the +\texttt{mp\_int} should be intact without the excess digits being removed. Note that you can use a +shrunk \texttt{mp\_int} in further computations, however, such operations will require heap +operations which can be slow. It is not ideal to shrink \texttt{mp\_int} variables that you will +further modify in the system (unless you are seriously low on memory). \begin{small} - \begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -714,26 +778,27 @@ \subsection{Reducing Memory Usage} return EXIT_SUCCESS; \} \end{alltt} - \end{small} +\end{small} \subsection{Adding additional digits} -Within the mp\_int structure are two parameters which control the limitations of the array of digits that represent -the integer the mp\_int is meant to equal. The \texttt{used} parameter dictates how many digits are significant, that is, -contribute to the value of the mp\_int. The \texttt{alloc} parameter dictates how many digits are currently available in -the array. If you need to perform an operation that requires more digits you will have to mp\_grow() the mp\_int to -your desired size. +Within the mp\_int structure are two parameters which control the limitations of the array of +digits that represent the integer the mp\_int is meant to equal. The \texttt{used} parameter +dictates how many digits are significant, that is, contribute to the value of the mp\_int. The +\texttt{alloc} parameter dictates how many digits are currently available in the array. If you +need to perform an operation that requires more digits you will have to \texttt{mp\_grow} the +\texttt{mp\_int} to your desired size. \index{mp\_grow} \begin{alltt} mp_err mp_grow (mp_int *a, int size); \end{alltt} -This will grow the array of digits of $a$ to $size$. If the \texttt{alloc} parameter is already bigger than -$size$ the function will not do anything. +This will grow the array of digits of $a$ to $size$. If the \texttt{alloc} parameter is already +bigger than $size$ the function will not do anything. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -768,14 +833,16 @@ \subsection{Adding additional digits} \chapter{Basic Operations} \section{Copying} -A so called ``deep copy'', where new memory is allocated and all contents of $a$ are copied verbatim into $b$ such that $b = a$ at the end. +A so called ``deep copy'', where new memory is allocated and all contents of $a$ are copied +verbatim into $b$ such that $b = a$ at the end. \index{mp\_copy} \begin{alltt} mp_err mp_copy (const mp_int *a, mp_int *b); \end{alltt} -You can also just swap $a$ and $b$. It does the normal pointer changing with a temporary pointer variable, just that you do not have to. +You can also just swap $a$ and $b$. It does the normal pointer changing with a temporary pointer +variable, just that you do not have to. \index{mp\_exch} \begin{alltt} @@ -784,26 +851,27 @@ \section{Copying} \section{Bit Counting} -To get the position of the lowest bit set (LSB, the Lowest Significant Bit; the number of bits which are zero before the first zero bit ) +To get the position of the lowest bit set (LSB, the Lowest Significant Bit; the number of bits +which are zero before the first zero bit ) \index{mp\_cnt\_lsb} \begin{alltt} int mp_cnt_lsb(const mp_int *a); \end{alltt} -To get the position of the highest bit set (MSB, the Most Significant Bit; the number of bits in the ``bignum'') +To get the position of the highest bit set (MSB, the Most Significant Bit; the number of bits in +the ``bignum'') \index{mp\_count\_bits} \begin{alltt} int mp_count_bits(const mp_int *a); \end{alltt} - \section{Small Constants} -Setting an \texttt{mp\_int} to a small constant is a relatively common operation. To accommodate these instances there is a -small constant assignment function. This function is used to set a single digit constant. -The reason for this function is efficiency. Setting a single digit is quick but the -domain of a digit can change (it's always at least $0 \ldots 127$). +Setting an \texttt{mp\_int} to a small constant is a relatively common operation. To accommodate +these instances there is a small constant assignment function. This function is used to set a +single digit constant. The reason for this function is efficiency. Setting a single digit is quick +but the domain of a digit can change (it's always at least $0 \ldots 127$). \subsection{Single Digit} @@ -814,12 +882,12 @@ \subsection{Single Digit} void mp_set (mp_int *a, mp_digit b); \end{alltt} -This will zero the contents of $a$ and make it represent an integer equal to the value of $b$. Note that this -function has a return type of \texttt{void}. It cannot cause an error so it is safe to assume the function -succeeded. +This will zero the contents of $a$ and make it represent an integer equal to the value of $b$. Note +that this function has a return type of \texttt{void}. It cannot cause an error so it is safe to +assume the function succeeded. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -869,11 +937,12 @@ \subsection{Int32 and Int64 Constants} uint64_t mp_get_mag_u64 (const mp_int *a); \end{alltt} -These functions return the 32 or 64 least significant bits of $a$ respectively. The unsigned functions -return negative values in a twos complement representation. The absolute value or magnitude can be obtained using the \texttt{mp\_get\_mag*} functions. +These functions return the 32 or 64 least significant bits of $a$ respectively. The unsigned +functions return negative values in a twos complement representation. The absolute value or +magnitude can be obtained using the \texttt{mp\_get\_mag*} functions. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -912,7 +981,7 @@ \subsection{Long Constants - platform dependant} void mp_set_ul (mp_int *a, unsigned long b); \end{alltt} -This will assign the value of the platform-dependent sized variable $b$ to the big integer $a$. +This will assign the value of the platform--dependent sized variable $b$ to the big integer $a$. To retrieve the value, the following functions can be used. @@ -923,7 +992,8 @@ \subsection{Long Constants - platform dependant} unsigned long mp_get_mag_ul (const mp_int *a); \end{alltt} -This will return the least significant bits of the big integer $a$ that fit into the native data type \texttt{long}. +This will return the least significant bits of the big integer $a$ that fit into the native data +type \texttt{long}. \subsection{Long Long Constants - platform dependant} @@ -933,7 +1003,7 @@ \subsection{Long Long Constants - platform dependant} void mp_set_ull (mp_int *a, unsigned long long b); \end{alltt} -This will assign the value of the platform-dependent sized variable $b$ to the big integer $a$. +This will assign the value of the platform--dependent sized variable $b$ to the big integer $a$. To retrieve the value, the following functions can be used. @@ -946,7 +1016,8 @@ \subsection{Long Long Constants - platform dependant} unsigned long long mp_get_mag_ull (const mp_int *a); \end{alltt} -This will return the least significant bits of $a$ that fit into the native data type \texttt{long long}. +This will return the least significant bits of $a$ that fit into the native data type \texttt{long + long}. \subsection{Floating Point Constants - platform dependant} @@ -955,7 +1026,9 @@ \subsection{Floating Point Constants - platform dependant} mp_err mp_set_double(mp_int *a, double b); \end{alltt} -If the platform supports the floating point data type \texttt{double} (binary64) this function will assign the integer part of \texttt{b} to the big integer $a$. This function will return \texttt{MP\_VAL} if \texttt{b} is \texttt{+/-inf} or \texttt{NaN}. +If the platform supports the floating point data type \texttt{double} (binary64) this function will +assign the integer part of \texttt{b} to the big integer $a$. This function will return +\texttt{MP\_VAL} if \texttt{b} is \texttt{+/-inf} or \texttt{NaN}. To convert a big integer to a \texttt{double} use @@ -964,7 +1037,6 @@ \subsection{Floating Point Constants - platform dependant} double mp_get_double(const mp_int *a); \end{alltt} - \subsection{Initialize and Setting Constants} To both initialize and set small constants the following nine functions are available. \index{mp\_init\_set} \index{mp\_init\_set\_int} @@ -980,9 +1052,10 @@ \subsection{Initialize and Setting Constants} mp_err mp_init_ull (mp_int *a, unsigned long long b); \end{alltt} -Both functions work like the previous counterparts except they first initialize $a$ with the function \texttt{mp\_init} before setting the values. - -\begin{alltt} +Both functions work like the previous counterparts except they first initialize $a$ with the +function \texttt{mp\_init} before setting the values. +\begin{small} + \begin{alltt} int main(void) \{ mp_int number1, number2; @@ -1012,52 +1085,52 @@ \subsection{Initialize and Setting Constants} return EXIT_SUCCESS; \} \end{alltt} +\end{small} If this program succeeds it shall output. \begin{alltt} Number1, Number2 == 100, 1023 \end{alltt} - - \section{Comparisons} -Comparisons in LibTomMath are always performed in a ``left to right'' fashion. There are three possible return codes -for any comparison. +Comparisons in LibTomMath are always performed in a ``left to right'' fashion. There are three +possible return codes for any comparison. \index{MP\_GT} \index{MP\_EQ} \index{MP\_LT} \begin{figure}[h] -\begin{center} -\begin{tabular}{|c|c|} -\hline \textbf{Result Code} & \textbf{Meaning} \\ -\hline MP\_GT & $a > b$ \\ -\hline MP\_EQ & $a = b$ \\ -\hline MP\_LT & $a < b$ \\ -\hline -\end{tabular} -\end{center} -\caption{Comparison Codes for $a, b$} -\label{fig:CMP} + \begin{center} + \begin{tabular}{|c|c|} + \hline \textbf{Result Code} & \textbf{Meaning} \\ + \hline MP\_GT & $a > b$ \\ + \hline MP\_EQ & $a = b$ \\ + \hline MP\_LT & $a < b$ \\ + \hline + \end{tabular} + \end{center} + \caption{Comparison Codes for $a, b$} + \label{fig:CMP} \end{figure} -In figure \ref{fig:CMP} two integers $a$ and $b$ are being compared. In this case $a$ is said to be ``to the left'' of -$b$. The return codes are of type \texttt{mp\_ord}. +In figure \ref{fig:CMP} two integers $a$ and $b$ are being compared. In this case $a$ is said to +be ``to the left'' of $b$. The return codes are of type \texttt{mp\_ord}. \subsection{Unsigned comparison} -An unsigned comparison considers only the digits themselves and not the associated \texttt{sign} flag of the -\texttt{mp\_int} structures. This is analogous to an absolute comparison. The function \texttt{mp\_cmp\_mag} will compare two -\texttt{mp\_int} variables based on their digits only. +An unsigned comparison considers only the digits themselves and not the associated \texttt{sign} +flag of the \texttt{mp\_int} structures. This is analogous to an absolute comparison. The +function \texttt{mp\_cmp\_mag} will compare two \texttt{mp\_int} variables based on their digits +only. \index{mp\_cmp\_mag} \begin{alltt} mp_ord mp_cmp_mag(mp_int *a, mp_int *b); \end{alltt} -This will compare $a$ to $b$ placing $a$ to the left of $b$. This function cannot fail and will return one of the -three compare codes listed in figure \ref{fig:CMP}. +This will compare $a$ to $b$ placing $a$ to the left of $b$. This function cannot fail and will +return one of the three compare codes listed in figure \ref{fig:CMP}. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number1, number2; @@ -1094,8 +1167,8 @@ \subsection{Unsigned comparison} \end{alltt} \end{small} -If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in section \ref{sec:NEG}.} completes -successfully it should print the following. +If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in + section \ref{sec:NEG}.} completes successfully it should print the following. \begin{alltt} |number1| < |number2| @@ -1105,19 +1178,21 @@ \subsection{Unsigned comparison} \subsection{Signed comparison} -To compare two \texttt{mp\_int} variables based on their signed value the \texttt{mp\_cmp} function is provided. +To compare two \texttt{mp\_int} variables based on their signed value the \texttt{mp\_cmp} function +is provided. \index{mp\_cmp} \begin{alltt} mp_ord mp_cmp(mp_int *a, mp_int *b); \end{alltt} -This will compare $a$ to the left of $b$. It will first compare the signs of the two \texttt{mp\_int} variables. If they -differ it will return immediately based on their signs. If the signs are equal then it will compare the digits -individually. This function will return one of the compare conditions codes listed in figure \ref{fig:CMP}. +This will compare $a$ to the left of $b$. It will first compare the signs of the two +\texttt{mp\_int} variables. If they differ it will return immediately based on their signs. If +the signs are equal then it will compare the digits individually. This function will return one of +the compare conditions codes listed in figure \ref{fig:CMP}. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number1, number2; @@ -1154,8 +1229,8 @@ \subsection{Signed comparison} \end{alltt} \end{small} -If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in section \ref{sec:NEG}.} completes -successfully it should print the following. +If this program\footnote{This function uses the \texttt{mp\_neg} function which is discussed in + section \ref{sec:NEG}.} completes successfully it should print the following. \begin{alltt} number1 > number2 @@ -1170,14 +1245,13 @@ \subsection{Single Digit} mp_ord mp_cmp_d(mp_int *a, mp_digit b); \end{alltt} -This will compare $a$ to the left of $b$ using a signed comparison. Note that it will always treat $b$ as -positive. This function is rather handy when you have to compare against small values such as $1$ (which often -comes up in cryptography). The function cannot fail and will return one of the tree compare condition codes -listed in figure \ref{fig:CMP}. - +This will compare $a$ to the left of $b$ using a signed comparison. Note that it will always +treat$b$ as positive. This function is rather handy when you have to compare against small values +such as $1$ (which often comes up in cryptography). The function cannot fail and will return one +of the tree compare condition codes listed in figure \ref{fig:CMP}. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -1214,13 +1288,13 @@ \subsection{Single Digit} \section{Logical Operations} -Logical operations are operations that can be performed either with simple shifts or boolean operators such as -AND, XOR and OR directly. These operations are very quick. +Logical operations are operations that can be performed either with simple shifts or boolean +operators such as AND, XOR and OR directly. These operations are very quick. \subsection{Multiplication by two} -Multiplications and divisions by any power of two can be performed with quick logical shifts either left or -right depending on the operation. +Multiplications and divisions by any power of two can be performed with quick logical shifts either +left or right depending on the operation. When multiplying or dividing by two a special case routine can be used which are as follows. \index{mp\_mul\_2} \index{mp\_div\_2} @@ -1229,11 +1303,11 @@ \subsection{Multiplication by two} mp_err mp_div_2(const mp_int *a, mp_int *b); \end{alltt} -The former will assign twice $a$ to $b$ while the latter will assign half $a$ to $b$. These functions are fast -since the shift counts and maskes are hardcoded into the routines. +The former will assign twice $a$ to $b$ while the latter will assign half $a$ to $b$. These +functions are fast since the shift counts and masks are hardcoded into the routines. \begin{small} -\begin{alltt} + \begin{alltt} int main(void) \{ mp_int number; @@ -1296,22 +1370,23 @@ \subsection{Multiplication by two} mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c); \end{alltt} -This will multiply $a$ by $2^b$ and store the result in $c$. If the value of $b$ is less than or equal to -zero the function will copy $a$ to $c$ without performing any further actions. The multiplication itself -is implemented as a right-shift operation of $a$ by $b$ bits. - -To divide by a power of two use the following. +This will multiply $a$ by $2^b$ and store the result in $c$. If the value of $b$ is less than or +equal to zero the function will copy $a$ to $c$ without performing any further actions. The +multiplication itself is implemented as a right--shift operation of $a$ by $b$ bits. To divide by a +power of two use the following. \index{mp\_div\_2d} \begin{alltt} mp_err mp_div_2d (const mp_int *a, int b, mp_int *c, mp_int *d); \end{alltt} -Which will divide $a$ by $2^b$, store the quotient in $c$ and the remainder in $d$. If $b \le 0$ then the -function simply copies $a$ over to $c$ and zeroes $d$. The variable $d$ may be passed as a \texttt{NULL} -value to signal that the remainder is not desired. The division itself is implemented as a left-shift -operation of $a$ by $b$ bits. +Which will divide $a$ by $2^b$, store the quotient in $c$ and the remainder in $d$. If $b \le 0$ +then the function simply copies $a$ over to $c$ and zeroes $d$. The variable $d$ may be +passed as a \texttt{NULL} value to signal that the remainder is not desired. The division itself +is implemented as a left--shift operation of $a$ by $b$ bits. -It is also not very uncommon to need just the power of two $2^b$; for example as a start-value for the Newton method. +It is also not very uncommon to need just the power of two $2^b$; for example as a start--value +for +the Newton method. \index{mp\_2expt} \begin{alltt} @@ -1321,33 +1396,36 @@ \subsection{Multiplication by two} \subsection{Polynomial Basis Operations} -Strictly speaking the organization of the integers within the mp\_int structures is what is known as a -``polynomial basis''. This simply means a field element is stored by divisions of a radix. For example, if -$f(x) = \sum_{i=0}^{k} y_ix^k$ for any vector $\vec y$ then the array of digits in $\vec y$ are said to be -the polynomial basis representation of $z$ if $f(\beta) = z$ for a given radix $\beta$. +Strictly speaking the organization of the integers within the mp\_int structures is what is known +as a ``polynomial basis''. This simply means a field element is stored by divisions of a radix. +For example, if $f(x) = \sum_{i=0}^{k} y_ix^k$ for any vector $\vec y$ then the array of digits in +$\vec y$ are said to be the polynomial basis representation of $z$ if $f(\beta) = z$ for a given +radix $\beta$. -To multiply by the polynomial $g(x) = x$ all you have todo is shift the digits of the basis left one place. The -following function provides this operation. +To multiply by the polynomial $g(x) = x$ all you have todo is shift the digits of the basis left +one place. The following function provides this operation. \index{mp\_lshd} \begin{alltt} mp_err mp_lshd (mp_int *a, int b); \end{alltt} -This will multiply $a$ in place by $x^b$ which is equivalent to shifting the digits left $b$ places and inserting zeroes -in the least significant digits. Similarly to divide by a power of $x$ the following function is provided. +This will multiply $a$ in place by $x^b$ which is equivalent to shifting the digits left $b$ places +and inserting zeroes in the least significant digits. Similarly to divide by a power of $x$ the +following function is provided. \index{mp\_rshd} \begin{alltt} void mp_rshd (mp_int *a, int b) \end{alltt} -This will divide $a$ in place by $x^b$ and discard the remainder. This function cannot fail as it performs the operations -in place and no new digits are required to complete it. +This will divide $a$ in place by $x^b$ and discard the remainder. This function cannot fail as it +performs the operations in place and no new digits are required to complete it. \subsection{AND, OR, XOR and COMPLEMENT Operations} -While AND, OR and XOR operations compute arbitrary-precision bitwise operations. Negative numbers -are treated as if they are in two-complement representation, while internally they are sign-magnitude however. +While AND, OR and XOR operations compute arbitrary--precision bitwise operations. Negative numbers +are treated as if they are in two--complement representation, while internally they are +sign--magnitude however. \index{mp\_or} \index{mp\_and} \index{mp\_xor} \index{mp\_complement} \begin{alltt} @@ -1358,9 +1436,9 @@ \subsection{AND, OR, XOR and COMPLEMENT Operations} mp_err mp_signed_rsh(const mp_int *a, int b, mp_int *c, mp_int *d); \end{alltt} -The function \texttt{mp\_complement} computes a two-complement $b = \sim a$. The function \texttt{mp\_signed\_rsh} performs -sign extending right shift. For positive numbers it is equivalent to \texttt{mp\_div\_2d}. - +The function \texttt{mp\_complement} computes a two--complement $b = \sim a$. The function +\texttt{mp\_signed\_rsh} performs sign extending right shift. For positive numbers it is equivalent +to \texttt{mp\_div\_2d}. \section{Addition and Subtraction} To compute an addition or subtraction the following two functions can be used. @@ -1371,8 +1449,8 @@ \section{Addition and Subtraction} mp_err mp_sub (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} -Which perform $c = a \odot b$ where $\odot$ is one of signed addition or subtraction. The operations are fully sign -aware. +Which perform $c = a \odot b$ where $\odot$ is one of signed addition or subtraction. The +operations are fully sign aware. \section{Sign Manipulation} \subsection{Negation} @@ -1404,10 +1482,9 @@ \section{Integer Division and Remainder} mp_err mp_div (const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); \end{alltt} -This divides $a$ by $b$ and stores the quotient in $c$ and $d$. The signed quotient is computed such that -$bc + d = a$. Note that either of $c$ or $d$ can be set to \texttt{NULL} if their value is not required. If -$b$ is zero the function returns \texttt{MP\_VAL}. - +This divides $a$ by $b$ and stores the quotient in $c$ and $d$. The signed quotient is computed +such that $bc + d = a$. Note that either of $c$ or $d$ can be set to \texttt{NULL} if their value +is not required. If $b$ is zero the function returns \texttt{MP\_VAL}. \chapter{Multiplication and Squaring} \section{Multiplication} @@ -1416,15 +1493,19 @@ \section{Multiplication} \begin{alltt} mp_err mp_mul (const mp_int *a, const mp_int *b, mp_int *c); \end{alltt} -Which assigns the full signed product $ab$ to $c$. This function actually breaks into one of four cases which are -specific multiplication routines optimized for given parameters. First there are the Toom-Cook multiplications which -should only be used with very large inputs. This is followed by the Karatsuba multiplications which are for moderate -sized inputs. Then followed by the Comba and baseline multipliers. +Which assigns the full signed product $ab$ to $c$. This function actually breaks into one of four +cases which are specific multiplication routines optimized for given parameters. First there are +the Toom--Cook multiplications which should only be used with very large inputs. This is followed +by the Karatsuba multiplications which are for moderate sized inputs. Then followed by the Comba +and baseline multipliers. -Fortunately for the developer you don't really need to know this unless you really want to fine tune the system. mp\_mul() -will determine on its own\footnote{Some tweaking may be required but \texttt{make tune} will put some reasonable values in \texttt{bncore.c}} what routine to use automatically when it is called. +Fortunately for the developer you don't really need to know this unless you really want to fine +tune the system. The function \texttt{mp\_mul} will determine on its own\footnote{Some tweaking may + be required but \texttt{make tune} will put some reasonable values in \texttt{bncore.c}} what +routine to use automatically when it is called. -\begin{alltt} +\begin{small} + \begin{alltt} int main(void) \{ mp_int number1, number2; @@ -1459,6 +1540,7 @@ \section{Multiplication} return EXIT_SUCCESS; \} \end{alltt} +\end{small} If this program succeeds it shall output the following. @@ -1467,7 +1549,8 @@ \section{Multiplication} \end{alltt} \section{Squaring} -Since squaring can be performed faster than multiplication it is performed it's own function instead of just using +Since squaring can be performed faster than multiplication it is performed it's own function +instead of just using \texttt{mp\_mul}. \index{mp\_sqr} @@ -1475,34 +1558,38 @@ \section{Squaring} mp_err mp_sqr (const mp_int *a, mp_int *b); \end{alltt} -Will square $a$ and store it in $b$. Like the case of multiplication there are four different squaring -algorithms all which can be called from the function \texttt{mp\_sqr}. It is ideal to use \texttt{mp\_sqr} over \texttt{mp\_mul} when squaring terms because -of the speed difference. +Will square $a$ and store it in $b$. Like the case of multiplication there are four different +squaring algorithms all which can be called from the function \texttt{mp\_sqr}. It is ideal to use +\texttt{mp\_sqr} over \texttt{mp\_mul} when squaring terms because of the speed difference. \section{Tuning Polynomial Basis Routines} -Both of the Toom-Cook and Karatsuba multiplication algorithms are faster than the traditional $O(n^2)$ approach that -the Comba and baseline algorithms use. At $O(n^{1.464973})$ and $O(n^{1.584962})$ running times respectively they require -considerably less work. For example, a $10\,000$-digit multiplication would take roughly $724\,000$ single precision -multiplications with Toom-Cook or $100\,000\,000$ single precision multiplications with the standard Comba (a factor -of 138). +Both of the Toom--Cook and Karatsuba multiplication algorithms are faster than the traditional +$O(n^2)$ approach that the Comba and baseline algorithms use. At $O(n^{1.464973})$ and +$O(n^{1.584962})$ running times respectively they require considerably less work. For example, a +$10\,000$-digit multiplication would take roughly $724\,000$ single precision multiplications with +Toom--Cook or $100\,000\,000$ single precision multiplications with the standard Comba (a factor of +$138$). -So why not always use Karatsuba or Toom-Cook? The simple answer is that they have so much overhead that they're not -actually faster than Comba until you hit distinct ``cutoff'' points. For Karatsuba with the default configuration, -GCC 3.3.1 and an Athlon XP processor the cutoff point is roughly 110 digits (about 70 for the Intel P4). That is, at -110 digits Karatsuba and Comba multiplications just about break even and for 110+ digits Karatsuba is faster. +So why not always use Karatsuba or Toom--Cook? The simple answer is that they have so much +overhead that they're not actually faster than Comba until you hit distinct ``cutoff'' points. +For Karatsuba with the default configuration, GCC 3.3.1 and an Athlon XP processor the cutoff point +is roughly 110 digits (about 70 for the Intel P4). That is, at 110 digits Karatsuba and Comba +multiplications just about break even and for 110+ digits Karatsuba is faster. -To get reasonable values for the cut-off points for your architecture, type +To get reasonable values for the cut--off points for your architecture, type \begin{alltt} make tune \end{alltt} -This will run a benchmark, computes the medians, rewrites \texttt{bncore.c}, and recompiles \texttt{bncore.c} and relinks the library. +This will run a benchmark, computes the medians, rewrites \texttt{bncore.c}, and recompiles +\texttt{bncore.c} and relinks the library. -The benchmark itself can be fine-tuned in the file \texttt{etc/tune\_it.sh}. +The benchmark itself can be fine--tuned in the file \texttt{etc/tune\_it.sh}. -The program \texttt{etc/tune} is also able to print a list of values for printing curves with e.g.: \texttt{gnuplot}. type \texttt{./etc/tune -h} to get a list of all available options. +The program \texttt{etc/tune} is also able to print a list of values for printing curves with e.g.: +\texttt{gnuplot}. type \texttt{./etc/tune -h} to get a list of all available options. \chapter{Modular Reduction} @@ -1510,15 +1597,15 @@ \chapter{Modular Reduction} as (\ref{eqn:mod}) the modular reduction is equivalent to the remainder of $b$ divided by $c$. \begin{equation} -a \equiv b \mbox{ (mod }c\mbox{)} -\label{eqn:mod} + a \equiv b \mbox{ (mod }c\mbox{)} + \label{eqn:mod} \end{equation} -Of particular interest to cryptography are reductions where $b$ is limited to the range $0 \le b < c^2$ since particularly -fast reduction algorithms can be written for the limited range. +Of particular interest to cryptography are reductions where $b$ is limited to the range $0 \le b < + c^2$ since particularly fast reduction algorithms can be written for the limited range. -Note that one of the four optimized reduction algorithms are automatically chosen in the modular exponentiation -algorithm \texttt{mp\_exptmod} when an appropriate modulus is detected. +Note that one of the four optimized reduction algorithms are automatically chosen in the modular +exponentiation algorithm \texttt{mp\_exptmod} when an appropriate modulus is detected. \section{Straight Division} In order to effect an arbitrary modular reduction the following algorithm is provided. @@ -1528,31 +1615,35 @@ \section{Straight Division} mp_err mp_mod(const mp_int *a,const mp_int *b, mp_int *c); \end{alltt} -This reduces $a$ modulo $b$ and stores the result in $c$. The sign of $c$ shall agree with the sign -of $b$. This algorithm accepts an input $a$ of any range and is not limited by $0 \le a < b^2$. +This reduces $a$ modulo $b$ and stores the result in $c$. The sign of $c$ shall agree with the +sign of $b$. This algorithm accepts an input $a$ of any range and is not limited by $0 \le a < + b^2$. \section{Barrett Reduction} -Barrett reduction is a generic optimized reduction algorithm that requires pre--computation to achieve -a decent speedup over straight division. First a $\mu$ value must be precomputed with the following function. +Barrett reduction is a generic optimized reduction algorithm that requires pre--computation to +achieve a decent speedup over straight division. First a $\mu$ value must be precomputed with the +following function. \index{mp\_reduce\_setup} \begin{alltt} mp_err mp_reduce_setup(const mp_int *a, mp_int *b); \end{alltt} -Given a modulus in $b$ this produces the required $\mu$ value in $a$. For any given modulus this only has to -be computed once. Modular reduction can now be performed with the following. +Given a modulus in $b$ this produces the required $\mu$ value in $a$. For any given modulus this +only has to be computed once. Modular reduction can now be performed with the following. \index{mp\_reduce} \begin{alltt} mp_err mp_reduce(const mp_int *a, const mp_int *b, mp_int *c); \end{alltt} -This will reduce $a$ in place modulo $b$ with the precomputed $\mu$ value in $c$. $a$ must be in the range +This will reduce $a$ in place modulo $b$ with the precomputed $\mu$ value in $c$. $a$ must be in +the range $0 \le a < b^2$. -\begin{alltt} +\begin{small} + \begin{alltt} int main(void) \{ mp_int a, b, c, mu; @@ -1602,21 +1693,22 @@ \section{Barrett Reduction} return EXIT_SUCCESS; \} \end{alltt} +\end{small} This program will calculate $a^3 \mbox{ mod }b$ if all the functions succeed. \section{Montgomery Reduction} -Montgomery is a specialized reduction algorithm for any odd moduli. Like Barrett reduction a pre--computation -step is required. This is accomplished with the following. +Montgomery is a specialized reduction algorithm for any odd moduli. Like Barrett reduction a +pre--computation step is required. This isaccomplished with the following. \index{mp\_montgomery\_setup} \begin{alltt} mp_err mp_montgomery_setup(const mp_int *a, mp_digit *mp); \end{alltt} -For the given odd moduli $a$ the precomputation value is placed in $mp$. The reduction is computed with the -following. +For the given odd moduli $a$ the precomputation value is placed in $mp$. The reduction is computed +with the following. \index{mp\_montgomery\_reduce} \begin{alltt} @@ -1625,12 +1717,14 @@ \section{Montgomery Reduction} This reduces $a$ in place modulo $m$ with the pre--computed value $mp$. $a$ must be in the range $0 \le a < b^2$. -Montgomery reduction is faster than Barrett reduction for moduli smaller than the ``Comba'' limit. With the default -setup for instance, the limit is $127$ digits ($3556$--bits). Note that this function is not limited to -$127$ digits just that it falls back to a baseline algorithm after that point. +Montgomery reduction is faster than Barrett reduction for moduli smaller than the ``Comba'' limit. +With the default setup for instance, the limit is $127$ digits ($3556$--bits). Note that this +function is not limited to $127$ digits just that it falls back to a baseline algorithm after that +point. -An important observation is that this reduction does not return $a \mbox{ mod }m$ but $aR^{-1} \mbox{ mod }m$ -where $R = \beta^n$, $n$ is the n number of digits in $m$ and $\beta$ is the radix used (default is $2^{28}$). +An important observation is that this reduction does not return $a \mbox{ mod }m$ but $aR^{-1} + \mbox{ mod }m$ where $R = \beta^n$, $n$ is the n number of digits in $m$ and $\beta$ is the radix +used (default is $2^{28}$). To quickly calculate $R$ the following function was provided. @@ -1640,11 +1734,12 @@ \section{Montgomery Reduction} \end{alltt} Which calculates $a = R$ for the odd moduli $b$ without using multiplication or division. -The normal modus operandi for Montgomery reductions is to normalize the integers before entering the system. For -example, to calculate $a^3 \mbox { mod }b$ using Montgomery reduction the value of $a$ can be normalized by -multiplying it by $R$. Consider the following code snippet. +The normal modus operandi for Montgomery reductions is to normalize the integers before entering +the system. For example, to calculate $a^3 \mbox { mod }b$ using Montgomery reduction the value of +$a$ can be normalized by multiplying it by $R$. Consider the following code snippet. -\begin{alltt} +\begin{small} + \begin{alltt} int main(void) \{ mp_int a, b, c, R; @@ -1716,28 +1811,32 @@ \section{Montgomery Reduction} return EXIT_SUCCESS; \} \end{alltt} +\end{small} -This particular example does not look too efficient but it demonstrates the point of the algorithm. By -normalizing the inputs the reduced results are always of the form $aR$ for some variable $a$. This allows -a single final reduction to correct for the normalization and the fast reduction used within the algorithm. +This particular example does not look too efficient but it demonstrates the point of the algorithm. +By normalizing the inputs the reduced results are always of the form $aR$ for some variable $a$. +This allows a single final reduction to correct for the normalization and the fast reduction used +within the algorithm. For more details consider examining the file \texttt{bn\_mp\_exptmod\_fast.c}. \section{Restricted Diminished Radix} -``Diminished Radix'' reduction refers to reduction with respect to moduli that are amenable to simple -digit shifting and small multiplications. In this case the ``restricted'' variant refers to moduli of the -form $\beta^k - p$ for some $k \ge 0$ and $0 < p < \beta$ where $\beta$ is the radix (default to $2^{28}$). +``Diminished Radix'' reduction refers to reduction with respect to moduli that are amenable to +simple digit shifting and small multiplications. In this case the ``restricted'' variant refers to +moduli of the form $\beta^k - p$ for some $k \ge 0$ and $0 < p < \beta$ where $\beta$ is the radix +(default to $2^{28}$). -As in the case of Montgomery reduction there is a pre--computation phase required for a given modulus. +As in the case of Montgomery reduction there is a pre--computation phase required for a given +modulus. \index{mp\_dr\_setup} \begin{alltt} void mp_dr_setup(const mp_int *a, mp_digit *d); \end{alltt} -This computes the value required for the modulus $a$ and stores it in $d$. This function cannot fail -and does not return any error codes. +This computes the value required for the modulus $a$ and stores it in $d$. This function cannot +fail and does not return any error codes. To determine if $a$ is a valid DR modulus: \index{mp\_dr\_is\_modulus} @@ -1752,22 +1851,23 @@ \section{Restricted Diminished Radix} mp_err mp_dr_reduce(mp_int *a, const mp_int *b, mp_digit mp); \end{alltt} -This reduces $a$ in place modulo $b$ with the pre--computed value $mp$. $b$ must be of a restricted -diminished radix form and $a$ must be in the range $0 \le a < b^2$. Diminished radix reductions are -much faster than both Barrett and Montgomery reductions as they have a much lower asymptotic running time. +This reduces $a$ in place modulo $b$ with the pre--computed value $mp$. $b$ must be of a restricted +diminished radix form and $a$ must be in the range $0 \le a < b^2$. Diminished radix reductions +are much faster than both Barrett and Montgomery reductions as they have a much lower asymptotic +running time. -Since the moduli are restricted this algorithm is not particularly useful for something like Rabin, RSA or -BBS cryptographic purposes. This reduction algorithm is useful for Diffie-Hellman and ECC where fixed -primes are acceptable. +Since the moduli are restricted this algorithm is not particularly useful for something like Rabin, +RSA or BBS cryptographic purposes. This reduction algorithm is useful for Diffie--Hellman and ECC +where fixed primes are acceptable. -Note that unlike Montgomery reduction there is no normalization process. The result of this function is -equal to the correct residue. +Note that unlike Montgomery reduction there is no normalization process. The result of this +function is equal to the correct residue. \section{Unrestricted Diminished Radix} -Unrestricted reductions work much like the restricted counterparts except in this case the moduli is of the -form $2^k - p$ for $0 < p < \beta$. In this sense the unrestricted reductions are more flexible as they -can be applied to a wider range of numbers. +Unrestricted reductions work much like the restricted counterparts except in this case the moduli +is of the form $2^k - p$ for $0 < p < \beta$. In this sense the unrestricted reductions are more +flexible as they can be applied to a wider range of numbers. \index{mp\_reduce\_2k\_setup}\index{mp\_reduce\_2k\_setup\_l} \begin{alltt} @@ -1783,10 +1883,12 @@ \section{Unrestricted Diminished Radix} mp_err mp_reduce_2k_l(mp_int *a, const mp_int *n, const mp_int *d); \end{alltt} -This will reduce $a$ in place modulo $n$ with the pre--computed value $d$. From my experience this routine is -slower than the function \texttt{mp\_dr\_reduce} but faster for most moduli sizes than the Montgomery reduction. +This will reduce $a$ in place modulo $n$ with the pre--computed value $d$. From my experience this +routine is slower than the function \texttt{mp\_dr\_reduce} but faster for most moduli sizes than +the Montgomery reduction. -To determine if \texttt{mp\_reduce\_2k} can be used at all, ask the function \texttt{mp\_reduce\_is\_2k}. +To determine if \texttt{mp\_reduce\_2k} can be used at all, ask the function +\texttt{mp\_reduce\_is\_2k}. \index{mp\_reduce\_is\_2k}\index{mp\_reduce\_is\_2k\_l} \begin{alltt} @@ -1796,7 +1898,8 @@ \section{Unrestricted Diminished Radix} \section{Combined Modular Reduction} -Some of the combinations of an arithmetic operations followed by a modular reduction can be done in a faster way. The ones implemented are: +Some of the combinations of an arithmetic operations followed by a modular reduction can be done in +a faster way. The ones implemented are: Addition $d = (a + b) \mod c$ \index{mp\_addmod} @@ -1819,8 +1922,6 @@ \section{Combined Modular Reduction} mp_err mp_sqrmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} - - \chapter{Exponentiation} \section{Single Digit Exponentiation} \index{mp\_expt\_u32} @@ -1834,15 +1935,15 @@ \section{Modular Exponentiation} \begin{alltt} mp_err mp_exptmod (const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) \end{alltt} -This computes $Y \equiv G^X \mbox{ (mod }P\mbox{)}$ using a variable width sliding window algorithm. This function -will automatically detect the fastest modular reduction technique to use during the operation. For negative values of -$X$ the operation is performed as $Y \equiv (G^{-1} \mbox{ mod }P)^{\vert X \vert} \mbox{ (mod }P\mbox{)}$ provided that -$gcd(G, P) = 1$. +This computes $Y \equiv G^X \mbox{ (mod }P\mbox{)}$ using a variable width sliding window +algorithm. This function will automatically detect the fastest modular reduction technique to use +during the operation. For negative values of $X$ the operation is performed as $Y \equiv (G^{-1} + \mbox{ mod }P)^{\vert X \vert} \mbox{ (mod }P\mbox{)}$ provided that $gcd(G, P) = 1$. -This function is actually a shell around the two internal exponentiation functions. This routine will automatically -detect when Barrett, Montgomery, Restricted and Unrestricted Diminished Radix based exponentiation can be used. Generally -moduli of the a ``restricted diminished radix'' form lead to the fastest modular exponentiations. Followed by Montgomery -and the other two algorithms. +This function is actually a shell around the two internal exponentiation functions. This routine +will automatically detect when Barrett, Montgomery, Restricted and Unrestricted Diminished Radix +based exponentiation can be used. Generally moduli of the a ``restricted diminished radix'' form +lead to the fastest modular exponentiations. Followed by Montgomery and the other two algorithms. \section{Modulus a Power of Two} \index{mp\_mod\_2d} @@ -1856,29 +1957,34 @@ \section{Root Finding} \begin{alltt} mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) \end{alltt} -This computes $c = a^{1/b}$ such that $c^b \le a$ and $(c+1)^b > a$. Will return a positive root only for even roots and return -a root with the sign of the input for odd roots. For example, performing $4^{1/2}$ will return $2$ whereas $(-8)^{1/3}$ -will return $-2$. +This computes $c = a^{1/b}$ such that $c^b \le a$ and $(c+1)^b > a$. Will return a positive root +only for even roots and return a root with the sign of the input for odd roots. For example, +performing $4^{1/2}$ will return $2$ whereas $(-8)^{1/3}$ will return $-2$. -This algorithm uses the ``Newton Approximation'' method and will converge on the correct root fairly quickly. +This algorithm uses the ``Newton Approximation'' method and will converge on the correct root +fairly quickly. -The square root $c = a^{1/2}$ (with the same conditions $c^2 \le a$ and $(c+1)^2 > a$) is implemented with a faster algorithm. +The square root $c = a^{1/2}$ (with the same conditions $c^2 \le a$ and $(c+1)^2 > a$) is +implemented with a faster algorithm. \index{mp\_sqrt} \begin{alltt} mp_err mp_sqrt(const mp_int *arg, mp_int *ret) \end{alltt} - \chapter{Logarithm} \section{Integer Logarithm} -A logarithm function for positive integer input \texttt{a, base} computing $\floor{\log_bx}$ such that $(\log_b x)^b \le x$. -\index{mp\_ilogb} +A logarithm function for positive integer input \texttt{a, base} computing $\floor{\log_bx}$ such +that $(\log_b x)^b \le x$. + +\index{mp\_log\_u32} \begin{alltt} mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) \end{alltt} + \subsection{Example} -\begin{alltt} +\begin{small} + \begin{alltt} #include #include #include @@ -1933,6 +2039,7 @@ \subsection{Example} exit(EXIT_SUCCESS); } \end{alltt} +\end{small} \chapter{Prime Numbers} @@ -1941,217 +2048,332 @@ \section{Fermat Test} \begin{alltt} mp_err mp_prime_fermat (const mp_int *a, const mp_int *b, int *result) \end{alltt} -Performs a Fermat primality test to the base $b$. That is it computes $b^a \mbox{ mod }a$ and tests whether the value is -equal to $b$ or not. If the values are equal then $a$ is probably prime and $result$ is set to one. Otherwise $result$ -is set to zero. +Performs a Fermat primality test to the base $b$. That is it computes $b^a \mbox{ mod }a$ and +tests whether the value is equal to $b$ or not. If the values are equal then $a$ is probably prime +and $result$ is set to one. Otherwise $result$ is set to zero. -\section{Miller-Rabin Test} +\section{Miller--Rabin Test} \index{mp\_prime\_miller\_rabin} \begin{alltt} mp_err mp_prime_miller_rabin (const mp_int *a, const mp_int *b, int *result) \end{alltt} -Performs a Miller-Rabin test to the base $b$ of $a$. This test is much stronger than the Fermat test and is very hard to -fool (besides with Carmichael numbers). If $a$ passes the test (therefore is probably prime) $result$ is set to one. -Otherwise $result$ is set to zero. +Performs a Miller--Rabin test to the base $b$ of $a$. This test is much stronger than the Fermat +test and is very hard to fool (besides with Carmichael numbers). If $a$ passes the test (therefore +is probably prime) $result$ is set to one. Otherwise $result$ is set to zero. -Note that it is suggested that you use the Miller-Rabin test instead of the Fermat test since all of the failures of -Miller-Rabin are a subset of the failures of the Fermat test. +Note that it is suggested that you use the Miller--Rabin test instead of the Fermat test since all +of the failures of Miller--Rabin are a subset of the failures of the Fermat test. \subsection{Required Number of Tests} -Generally to ensure a number is very likely to be prime you have to perform the Miller-Rabin with at least a half-dozen -or so unique bases. However, it has been proven that the probability of failure goes down as the size of the input goes up. -This is why a simple function has been provided to help out. +Generally to ensure a number is very likely to be prime you have to perform the Miller--Rabin with +at least a half--dozen or so unique bases. However, it has been proven that the probability of +failure goes down as the size of the input goes up. This is why a simple function has been provided +to help out. \index{mp\_prime\_rabin\_miller\_trials} \begin{alltt} mp_err mp_prime_rabin_miller_trials(int size) \end{alltt} -This returns the number of trials required for a low probability of failure for a given \texttt{size} expressed in bits. This comes in handy specially since larger numbers are slower to test. For example, a 512-bit number would require 18 tests for a probability of $2^{-160}$ whereas a 1024-bit number would only require 12 tests for a probability of $2^{-192}$. The exact values as implemented are listed in table \ref{table:millerrabinrunsimpl}. +This returns the number of trials required for a low probability of failure for a given +\texttt{size} expressed in bits. This comes in handy specially since larger numbers are slower to +test. For example, a 512--bit number would require 18 tests for a probability of $2^{-160}$ whereas +a 1024--bit number would only require 12 tests for a probability of $2^{-192}$. The exact values as +implemented are listed in table \ref{table:millerrabinrunsimpl}. \begin{table}[h] -\begin{center} -\begin{tabular}{c c c} -\textbf{bits} & \textbf{Rounds} & \textbf{Error}\\ - 80 & -1 & Use deterministic algorithm for size <= 80 bits \\ - 81 & 37 & $2^{-96}$ \\ - 96 & 32 & $2^{-96}$ \\ - 128 & 40 & $2^{-112}$ \\ - 160 & 35 & $2^{-112}$ \\ - 256 & 27 & $2^{-128}$ \\ - 384 & 16 & $2^{-128}$ \\ - 512 & 18 & $2^{-160}$ \\ - 768 & 11 & $2^{-160}$ \\ - 896 & 10 & $2^{-160}$ \\ - 1024 & 12 & $2^{-192}$ \\ - 1536 & 8 & $2^{-192}$ \\ - 2048 & 6 & $2^{-192}$ \\ - 3072 & 4 & $2^{-192}$ \\ - 4096 & 5 & $2^{-256}$ \\ - 5120 & 4 & $2^{-256}$ \\ - 6144 & 4 & $2^{-256}$ \\ - 8192 & 3 & $2^{-256}$ \\ - 9216 & 3 & $2^{-256}$ \\ - 10240 & 2 & $2^{-256}$ -\end{tabular} -\caption{ Number of Miller-Rabin rounds as implemented } \label{table:millerrabinrunsimpl} -\end{center} + \begin{center} + \begin{tabular}{c c c} + \textbf{bits} & \textbf{Rounds} & \textbf{Error} \\ + 80 & -1 & Use deterministic algorithm for size <= 80 bits \\ + 81 & 37 & $2^{-96}$ \\ + 96 & 32 & $2^{-96}$ \\ + 128 & 40 & $2^{-112}$ \\ + 160 & 35 & $2^{-112}$ \\ + 256 & 27 & $2^{-128}$ \\ + 384 & 16 & $2^{-128}$ \\ + 512 & 18 & $2^{-160}$ \\ + 768 & 11 & $2^{-160}$ \\ + 896 & 10 & $2^{-160}$ \\ + 1024 & 12 & $2^{-192}$ \\ + 1536 & 8 & $2^{-192}$ \\ + 2048 & 6 & $2^{-192}$ \\ + 3072 & 4 & $2^{-192}$ \\ + 4096 & 5 & $2^{-256}$ \\ + 5120 & 4 & $2^{-256}$ \\ + 6144 & 4 & $2^{-256}$ \\ + 8192 & 3 & $2^{-256}$ \\ + 9216 & 3 & $2^{-256}$ \\ + 10240 & 2 & $2^{-256}$ + \end{tabular} + \caption{ Number of Miller-Rabin rounds as implemented } \label{table:millerrabinrunsimpl} + \end{center} \end{table} -A small table, broke in two for typographical reasons, with the number of rounds of Miller-Rabin tests is shown below. The numbers have been computed with a PARI/GP script listed in appendix \ref{app:numberofmrcomp}. +A small table, broke in two for typographical reasons, with the number of rounds of Miller--Rabin +tests is shown below. The numbers have been computed with a PARI/GP script listed in appendix +\ref{app:numberofmrcomp}. -The first column is the number of bits $b$ in the prime $p = 2^b$, the numbers in the first row represent the -probability that the number that all of the Miller-Rabin tests deemed a pseudoprime is actually a composite. There is a deterministic test for numbers smaller than $2^{80}$. +The first column is the number of bits $b$ in the prime $p = 2^b$, the numbers in the first row +represent the probability that the number that all of the Miller--Rabin tests deemed a pseudoprime +is actually a composite. There is a deterministic test for numbers smaller than $2^{80}$. \begin{table}[h] -\begin{center} -\begin{tabular}{c c c c c c c} -\textbf{bits} & $\mathbf{2^{-80}}$ & $\mathbf{2^{-96}}$ & $\mathbf{2^{-112}}$ & $\mathbf{2^{-128}}$ & $\mathbf{2^{-160}}$ & $\mathbf{2^{-192}}$ \\ -80 & 31 & 39 & 47 & 55 & 71 & 87 \\ -96 & 29 & 37 & 45 & 53 & 69 & 85 \\ -128 & 24 & 32 & 40 & 48 & 64 & 80 \\ -160 & 19 & 27 & 35 & 43 & 59 & 75 \\ -192 & 15 & 21 & 29 & 37 & 53 & 69 \\ -256 & 10 & 15 & 20 & 27 & 43 & 59 \\ -384 & 7 & 9 & 12 & 16 & 25 & 38 \\ -512 & 5 & 7 & 9 & 12 & 18 & 26 \\ -768 & 4 & 5 & 6 & 8 & 11 & 16 \\ -1024 & 3 & 4 & 5 & 6 & 9 & 12 \\ -1536 & 2 & 3 & 3 & 4 & 6 & 8 \\ -2048 & 2 & 2 & 3 & 3 & 4 & 6 \\ -3072 & 1 & 2 & 2 & 2 & 3 & 4 \\ -4096 & 1 & 1 & 2 & 2 & 2 & 3 \\ -6144 & 1 & 1 & 1 & 1 & 2 & 2 \\ -8192 & 1 & 1 & 1 & 1 & 2 & 2 \\ -12288 & 1 & 1 & 1 & 1 & 1 & 1 \\ -16384 & 1 & 1 & 1 & 1 & 1 & 1 \\ -24576 & 1 & 1 & 1 & 1 & 1 & 1 \\ -32768 & 1 & 1 & 1 & 1 & 1 & 1 -\end{tabular} -\caption{ Number of Miller-Rabin rounds. Part I } \label{table:millerrabinrunsp1} -\end{center} + \begin{center} + \begin{tabular}{c c c c c c c} + \textbf{bits} & $\mathbf{2^{-80}}$ & $\mathbf{2^{-96}}$ & $\mathbf{2^{-112}}$ & + $\mathbf{2^{-128}}$ + & $\mathbf{2^{-160}}$ & $\mathbf{2^{-192}}$ + \\ + 80 & 31 & 39 & 47 & 55 + & 71 & 87 \\ + 96 & 29 & 37 & 45 & 53 + & 69 & 85 \\ + 128 & 24 & 32 & 40 & 48 + & 64 & 80 \\ + 160 & 19 & 27 & 35 & 43 + & 59 & 75 \\ + 192 & 15 & 21 & 29 & 37 + & 53 & 69 \\ + 256 & 10 & 15 & 20 & 27 + & 43 & 59 \\ + 384 & 7 & 9 & 12 & 16 + & 25 & 38 \\ + 512 & 5 & 7 & 9 & 12 + & 18 & 26 \\ + 768 & 4 & 5 & 6 & 8 + & 11 & 16 \\ + 1024 & 3 & 4 & 5 & 6 + & 9 & 12 \\ + 1536 & 2 & 3 & 3 & 4 + & 6 & 8 \\ + 2048 & 2 & 2 & 3 & 3 + & 4 & 6 \\ + 3072 & 1 & 2 & 2 & 2 + & 3 & 4 \\ + 4096 & 1 & 1 & 2 & 2 + & 2 & 3 \\ + 6144 & 1 & 1 & 1 & 1 + & 2 & 2 \\ + 8192 & 1 & 1 & 1 & 1 + & 2 & 2 \\ + 12288 & 1 & 1 & 1 & 1 + & 1 & 1 \\ + 16384 & 1 & 1 & 1 & 1 + & 1 & 1 \\ + 24576 & 1 & 1 & 1 & 1 + & 1 & 1 \\ + 32768 & 1 & 1 & 1 & 1 + & 1 & 1 + \end{tabular} + \caption{ Number of Miller-Rabin rounds. Part I } \label{table:millerrabinrunsp1} + \end{center} \end{table} \newpage \begin{table}[h] -\begin{center} -\begin{tabular}{c c c c c c c c} -\textbf{bits} &$\mathbf{2^{-224}}$ & $\mathbf{2^{-256}}$ & $\mathbf{2^{-288}}$ & $\mathbf{2^{-320}}$ & $\mathbf{2^{-352}}$ & $\mathbf{2^{-384}}$ & $\mathbf{2^{-416}}$\\ -80 & 103 & 119 & 135 & 151 & 167 & 183 & 199 \\ -96 & 101 & 117 & 133 & 149 & 165 & 181 & 197 \\ -128 & 96 & 112 & 128 & 144 & 160 & 176 & 192 \\ -160 & 91 & 107 & 123 & 139 & 155 & 171 & 187 \\ -192 & 85 & 101 & 117 & 133 & 149 & 165 & 181 \\ -256 & 75 & 91 & 107 & 123 & 139 & 155 & 171 \\ -384 & 54 & 70 & 86 & 102 & 118 & 134 & 150 \\ -512 & 36 & 49 & 65 & 81 & 97 & 113 & 129 \\ -768 & 22 & 29 & 37 & 47 & 58 & 70 & 86 \\ -1024 & 16 & 21 & 26 & 33 & 40 & 48 & 58 \\ -1536 & 10 & 13 & 17 & 21 & 25 & 30 & 35 \\ -2048 & 8 & 10 & 13 & 15 & 18 & 22 & 26 \\ -3072 & 5 & 7 & 8 & 10 & 12 & 14 & 17 \\ -4096 & 4 & 5 & 6 & 8 & 9 & 11 & 12 \\ -6144 & 3 & 4 & 4 & 5 & 6 & 7 & 8 \\ -8192 & 2 & 3 & 3 & 4 & 5 & 6 & 6 \\ -12288 & 2 & 2 & 2 & 3 & 3 & 4 & 4 \\ -16384 & 1 & 2 & 2 & 2 & 3 & 3 & 3 \\ -24576 & 1 & 1 & 2 & 2 & 2 & 2 & 2 \\ -32768 & 1 & 1 & 1 & 1 & 2 & 2 & 2 -\end{tabular} -\caption{ Number of Miller-Rabin rounds. Part II } \label{table:millerrabinrunsp2} -\end{center} + \begin{center} + \begin{tabular}{c c c c c c c c} + \textbf{bits} & $\mathbf{2^{-224}}$ & $\mathbf{2^{-256}}$ & $\mathbf{2^{-288}}$ & + $\mathbf{2^{-320}}$ & $\mathbf{2^{-352}}$ & $\mathbf{2^{-384}}$ & $\mathbf{2^{-416}}$ + \\ + 80 & 103 & 119 & 135 & 151 & + 167 & 183 & 199 + \\ + 96 & 101 & 117 & 133 & 149 & + 165 & 181 & 197 + \\ + 128 & 96 & 112 & 128 & 144 & + 160 & 176 & 192 + \\ + 160 & 91 & 107 & 123 & 139 & + 155 & 171 & 187 + \\ + 192 & 85 & 101 & 117 & 133 & + 149 & 165 & 181 + \\ + 256 & 75 & 91 & 107 & 123 & + 139 & 155 & 171 + \\ + 384 & 54 & 70 & 86 & 102 & + 118 & 134 & 150 + \\ + 512 & 36 & 49 & 65 & 81 & + 97 & 113 & 129 + \\ + 768 & 22 & 29 & 37 & 47 & + 58 & 70 & 86 + \\ + 1024 & 16 & 21 & 26 & 33 & + 40 & 48 & 58 + \\ + 1536 & 10 & 13 & 17 & 21 & + 25 & 30 & 35 + \\ + 2048 & 8 & 10 & 13 & 15 & + 18 & 22 & 26 + \\ + 3072 & 5 & 7 & 8 & 10 & + 12 & 14 & 17 + \\ + 4096 & 4 & 5 & 6 & 8 & + 9 & 11 & 12 + \\ + 6144 & 3 & 4 & 4 & 5 & + 6 & 7 & 8 + \\ + 8192 & 2 & 3 & 3 & 4 & + 5 & 6 & 6 + \\ + 12288 & 2 & 2 & 2 & 3 & + 3 & 4 & 4 + \\ + 16384 & 1 & 2 & 2 & 2 & + 3 & 3 & 3 + \\ + 24576 & 1 & 1 & 2 & 2 & + 2 & 2 & 2 + \\ + 32768 & 1 & 1 & 1 & 1 & + 2 & 2 & 2 + \end{tabular} + \caption{ Number of Miller-Rabin rounds. Part II } \label{table:millerrabinrunsp2} + \end{center} \end{table} -Determining the probability needed to pick the right column is a bit harder. Fips 186.4, for example has $2^{-80}$ for $512$ bit large numbers, $2^{-112}$ for $1024$ bits, and $2^{128}$ for $1536$ bits. It can be seen in table \ref{table:millerrabinrunsp1} that those combinations follow the diagonal from $(512,2^{-80})$ downwards and to the right to gain a lower probabilty of getting a composite declared a pseudoprime for the same amount of work or less. +Determining the probability needed to pick the right column is a bit harder. Fips 186.4, for +example has $2^{-80}$ for $512$ bit large numbers, $2^{-112}$ for $1024$ bits, and $2^{128}$ for +$1536$ bits. It can be seen in table \ref{table:millerrabinrunsp1} that those combinations follow +the diagonal from $(512,2^{-80})$ downwards and to the right to gain a lower probabilty of getting +a composite declared a pseudoprime for the same amount of work or less. -If this version of the library has the strong Lucas-Selfridge and/or the Frobenius-Underwood test implemented only one or two rounds of the Miller-Rabin test with a random base is necesssary for numbers larger than or equal to $1024$ bits. +If this version of the library has the strong Lucas--Selfridge and/or the Frobenius--Underwood test +implemented only one or two rounds of the Miller--Rabin test with a random base is necessary for +numbers larger than or equal to $1024$ bits. -This function is meant for RSA. The number of rounds for DSA is $\lceil -log_2(p)/2\rceil$ with $p$ the probability which is just the half of the absolute value of $p$ if given as a power of two. E.g.: with $p = 2^{-128}$, $\lceil -log_2(p)/2\rceil = 64$. +This function is meant for RSA. The number of rounds for DSA is $\lceil -log_2(p)/2\rceil$ with $p$ +the probability which is just the half of the absolute value of $p$ if given as a power of two. +E.g.: with $p = 2^{-128}$, $\lceil -log_2(p)/2\rceil = 64$. -This function can be used to test a DSA prime directly if these rounds are followed by a Lucas test. +This function can be used to test a DSA prime directly if these rounds are followed by a Lucas +test. See also table C.1 in FIPS 186-4. -\section{Strong Lucas-Selfridge Test} +\section{Strong Lucas--Selfridge Test} \index{mp\_prime\_strong\_lucas\_selfridge} \begin{alltt} mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) \end{alltt} -Performs a strong Lucas-Selfridge test. The strong Lucas-Selfridge test together with the Rabin-Miler test with bases $2$ and $3$ resemble the BPSW test. The single internal use is a compile-time option in \texttt{mp\_prime\_is\_prime} and can be excluded -from the Libtommath build if not needed. +Performs a strong Lucas--Selfridge test. The strong Lucas--Selfridge test together with the +Rabin--Miller test with bases $2$ and $3$ resemble the BPSW test. The single internal use is a +compile--time option in \texttt{mp\_prime\_is\_prime} and can be excluded from the Libtommath build +if not needed. -\section{Frobenius (Underwood) Test} +\section{Frobenius (Underwood) Test} \index{mp\_prime\_frobenius\_underwood} \begin{alltt} mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) \end{alltt} -Performs the variant of the Frobenius test as described by Paul Underwood. It can be included at build-time if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined and will be used instead of the Lucas-Selfridge test. +Performs the variant of the Frobenius test as described by Paul Underwood. It can be included at +build--time if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined and will be +used +instead of the Lucas--Selfridge test. -It returns \texttt{MP\_ITER} if the number of iterations is exhausted, assumes a composite as the input and sets \texttt{result} accordingly. This will reduce the set of available pseudoprimes by a very small amount: test with large datasets (more than $10^{10}$ numbers, both randomly chosen and sequences of odd numbers with a random start point) found only 31 (thirty-one) numbers with $a > 120$ and none at all with just an additional simple check for divisors $d < 2^8$. +It returns \texttt{MP\_ITER} if the number of iterations is exhausted, assumes a composite as the +input and sets \texttt{result} accordingly. This will reduce the set of available pseudoprimes by a +very small amount: test with large datasets (more than $10^{10}$ numbers, both randomly chosen and +sequences of odd numbers with a random start point) found only 31 (thirty--one) numbers with $a > + 120$ and none at all with just an additional simple check for divisors $d < 2^8$. \section{Primality Testing} -Testing if a number is a square can be done a bit faster than just by calculating the square root. It is used by the primality testing function described below. +Testing if a number is a square can be done a bit faster than just by calculating the square root. +It is used by the primality testing function described below. \index{mp\_is\_square} \begin{alltt} mp_err mp_is_square(const mp_int *arg, mp_bool *ret); \end{alltt} - \index{mp\_prime\_is\_prime} \begin{alltt} mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) \end{alltt} -This will perform a trial division followed by two rounds of Miller-Rabin with bases 2 and 3 and a Lucas-Selfridge test. The Frobenius-Underwood is available as a compile-time option with the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST}. See file -\texttt{bn\_mp\_prime\_is\_prime.c} for the necessary details. It shall be noted that both functions are much slower than -the Miller-Rabin test and if speed is an essential issue, the macro \texttt{LTM\_USE\_ONLY\_MR} switches the Frobenius-Underwood test and the Lucas-Selfridge test off and their code will not even be compiled into the library. - -If $t$ is set to a positive value $t$ additional rounds of the Miller-Rabin test with random bases will be performed to allow for Fips 186.4 (vid.~p.~126ff) compliance. The function \texttt{mp\_prime\_rabin\_miller\_trials} can be used to determine the number of rounds. It is vital that the function \texttt{mp\_rand} has a cryptographically strong random number generator available. - -One Miller-Rabin tests with a random base will be run automatically, so by setting $t$ to a positive value this function will run $t + 1$ Miller-Rabin tests with random bases. - -If $t$ is set to a negative value the test will run the deterministic Miller-Rabin test for the primes up to $3\,317\,044\,064\,679\,887\,385\,961\,981$\footnote{The semiprime $1287836182261\cdot 2575672364521$ with both factors smaller than $2^64$. An alternative with all factors smaller than $2^32$ is $4290067842\cdot 262853\cdot 1206721\cdot 2134439 + 3$}. That limit has to be checked by the caller. - -If $a$ passes all of the tests $result$ is set to \texttt{MP\_YES}, otherwise it is set to \texttt{MP\_NO}. +This will perform a trial division followed by two rounds of Miller--Rabin with bases 2 and 3 and a +Lucas--Selfridge test. The Frobenius--Underwood is available as a compile--time option with the +preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST}. See file \texttt{bn\_mp\_prime\_is\_prime.c} +for the necessary details. It shall be noted that both functions are much slower than the +Miller--Rabin test and if speed is an essential issue, the macro \texttt{LTM\_USE\_ONLY\_MR} +switches the Frobenius--Underwood test and the Lucas--Selfridge test off and their code will not +even be compiled into the library. + +If $t$ is set to a positive value $t$ additional rounds of the Miller--Rabin test with random bases +will be performed to allow for Fips 186.4 (vid.~p.~126ff) compliance. The function +\texttt{mp\_prime\_rabin\_miller\_trials} can be used to determine the number of rounds. It is +vital that the function \texttt{mp\_rand} has a cryptographically strong random number generator +available. + +One Miller--Rabin tests with a random base will be run automatically, so by setting $t$ to a +positive value this function will run $t + 1$ Miller--Rabin tests with random bases. + +If $t$ is set to a negative value the test will run the deterministic Miller--Rabin test for the +primes up to $3\,317\,044\,064\,679\,887\ 385\,961\,981$\footnote{The semiprime $1287836182261\cdot + 2575672364521$ with both factors smaller than $2^64$. An alternative with all factors smaller + than + $2^32$ is $4290067842\cdot 262853\cdot 1206721\cdot 2134439 + 3$}. That limit has to be checked +by +the caller. + +If $a$ passes all of the tests $result$ is set to \texttt{MP\_YES}, otherwise it is set to +\texttt{MP\_NO}. \section{Next Prime} \index{mp\_prime\_next\_prime} \begin{alltt} mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) \end{alltt} -This finds the next prime after $a$ that passes the function \texttt{mp\_prime\_is\_prime} with $t$ tests but see the documentation for -\texttt{mp\_prime\_is\_prime} for details regarding the use of the argument $t$. Set $bbs\_style$ to \texttt{MP\_YES} if you -want only the next prime congruent to $3 \mbox{ mod } 4$, otherwise set it to \texttt{MP\_NO} to find any next prime. +This finds the next prime after $a$ that passes the function \texttt{mp\_prime\_is\_prime} with $t$ +tests but see the documentation for \texttt{mp\_prime\_is\_prime} for details regarding the use of +the argument $t$. Set $bbs\_style$ to \texttt{MP\_YES} if you want only the next prime congruent +to $3 \mbox{ mod } 4$, otherwise set it to \texttt{MP\_NO} to find any next prime. \section{Random Primes} \index{mp\_prime\_rand} \begin{alltt} mp_err mp_prime_rand(mp_int *a, int t, int size, int flags); \end{alltt} -This will generate a prime in $a$ using $t$ tests of the primality testing algorithms. -See the documentation for mp\_prime\_is\_prime for details regarding the use of the argument $t$. -The variable $size$ specifies the bit length of the prime desired. -The variable $flags$ specifies one of several options available -(see fig. \ref{fig:primeopts}) which can be OR'ed together. +This will generate a prime in $a$ using $t$ tests of the primality testing algorithms. See the +documentation for the function \texttt{mp\_prime\_is\_prime} for details regarding the use of the +argument \texttt{t}. The parameter \texttt{size} specifies the bit--length of the prime desired. +The parameter \texttt{flags} specifies one of several options available (see fig. +\ref{fig:primeopts}) which can be OR'ed together. -The function mp\_prime\_rand() is suitable for generating primes which must be secret (as in the case of RSA) since there -is no skew on the least significant bits. +The function \texttt{mp\_prime\_rand} is suitable for generating primes which must be secret (as in +the case of RSA) since there is no skew on the least significant bits. \begin{figure}[h] -\begin{center} -\begin{small} -\begin{tabular}{|r|l|} -\hline \textbf{Flag} & \textbf{Meaning} \\ -\hline MP\_PRIME\_BBS & Make the prime congruent to $3$ modulo $4$ \\ -\hline MP\_PRIME\_SAFE & Make a prime $p$ such that $(p - 1)/2$ is also prime. \\ - & This option implies MP\_PRIME\_BBS as well. \\ -\hline MP\_PRIME\_2MSB\_OFF & Makes sure that the bit adjacent to the most significant bit \\ - & Is forced to zero. \\ -\hline MP\_PRIME\_2MSB\_ON & Makes sure that the bit adjacent to the most significant bit \\ - & Is forced to one. \\ -\hline -\end{tabular} -\end{small} -\end{center} -\caption{Primality Generation Options} -\label{fig:primeopts} + \begin{center} + \begin{small} + \begin{tabular}{|r|l|} + \hline \textbf{Flag} & \textbf{Meaning} + \\ + \hline MP\_PRIME\_BBS & Make the prime congruent to $3$ modulo $4$ + \\ + \hline MP\_PRIME\_SAFE & Make a prime $p$ such that $(p - 1)/2$ is also prime. + \\ + & This option implies MP\_PRIME\_BBS as well. + \\ + \hline MP\_PRIME\_2MSB\_OFF & Makes sure that the bit adjacent to the most significant bit + \\ + & Is forced to zero. + \\ + \hline MP\_PRIME\_2MSB\_ON & Makes sure that the bit adjacent to the most significant bit + \\ + & Is forced to one. + \\ + \hline + \end{tabular} + \end{small} + \end{center} + \caption{Primality Generation Options} + \label{fig:primeopts} \end{figure} \chapter{Random Number Generation} @@ -2160,7 +2382,8 @@ \section{PRNG} \begin{alltt} mp_err mp_rand_digit(mp_digit *r) \end{alltt} -This function generates a random number in \texttt{r} of the size given in \texttt{r} (that is, the variable is used for in- and output) but not more than \texttt{MP\_DIGIT\_MAX} bits. +This function generates a random number in \texttt{r} of the size given in \texttt{r} (that is, the +variable is used for in-- and output) but not more than \texttt{MP\_DIGIT\_MAX} bits. \index{mp\_rand} \begin{alltt} @@ -2168,7 +2391,10 @@ \section{PRNG} \end{alltt} This function generates a random number of \texttt{digits} bits. -The random number generated with these two functions is cryptographically secure if the source of random numbers the operating systems offers is cryptographically secure. It will use \texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev/urandom} on all operating systems that have it. +The random number generated with these two functions is cryptographically secure if the source of +random numbers the operating systems offers is cryptographically secure. It will use +\texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev urandom} on +all operating systems that have it. If you have a custom random source you might find the function \texttt(mp\_rand\_source) useful. \index{mp\_rand\_source} @@ -2176,7 +2402,6 @@ \section{PRNG} void mp_rand_source(mp_err(*source)(void *out, size_t size)); \end{alltt} - \chapter{Input and Output} \section{ASCII Conversions} \subsection{To ASCII} @@ -2184,41 +2409,45 @@ \subsection{To ASCII} \begin{alltt} mp_err mp_to_radix (const mp_int *a, char *str, size_t maxlen, size_t *written, int radix); \end{alltt} -This stores $a$ in \texttt{str} of maximum length \texttt{maxlen} as a base-\texttt{radix} string of ASCII chars and appends a \texttt{NUL} character to terminate the string. +This stores $a$ in \texttt{str} of maximum length \texttt{maxlen} as a base-\texttt{radix} string +of ASCII chars and appends a \texttt{NUL} character to terminate the string. Valid values of \texttt{radix} are in the range $[2, 64]$. -The exact number of characters in \texttt{str} plus the \texttt{NUL} will be put in \texttt{written} if that variable is not set to \texttt{NULL}. +The exact number of characters in \texttt{str} plus the \texttt{NUL} will be put in +\texttt{written} if that variable is not set to \texttt{NULL}. -If \texttt{str} is not big enough to hold $a$, \texttt{str} will be filled with the least-significant digits -of length \texttt{maxlen-1}, then \texttt{str} will be \texttt{NUL} terminated and the error \texttt{MP\_BUF} is returned. - -Please be aware that this function cannot evaluate the actual size of the buffer, it relies on the correctness of \texttt{maxlen}! +If \texttt{str} is not big enough to hold $a$, \texttt{str} will be filled with the least +significant digits of length \texttt{maxlen-1}, then \texttt{str} will be \texttt{NUL} terminated +and the error \texttt{MP\_BUF} is returned. +Please be aware that this function cannot evaluate the actual size of the buffer, it relies on the +correctness of \texttt{maxlen}! \index{mp\_radix\_size} \begin{alltt} mp_err mp_radix_size (const mp_int *a, int radix, int *size) \end{alltt} -This stores in \texttt{size} the number of characters (including space for the NUL terminator) required. Upon error this -function returns an error code and \texttt{size} will be zero. +This stores in \texttt{size} the number of characters (including space for the \texttt{NUL} +terminator) required. Upon error this function returns an error code and \texttt{size} will be +zero. If \texttt{MP\_NO\_FILE} is not defined a function to write to a file is also available. + \index{mp\_fwrite} \begin{alltt} mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream); \end{alltt} - \subsection{From ASCII} \index{mp\_read\_radix} \begin{alltt} mp_err mp_read_radix (mp_int *a, const char *str, int radix); \end{alltt} -This will read a \texttt{NUL} terminated string in base \texttt{radix} from \texttt{str} into $a$. It will stop reading when it reads a -character it does not recognize (which happens to include the \texttt{NUL} char... imagine that...). A single leading $-$ sign -can be used to denote a negative number. -The input encoding is currently restricted to ASCII only. +This will read a \texttt{NUL} terminated string in base \texttt{radix} from \texttt{str} into $a$. +It will stop reading when it reads a character it does not recognize (which happens to include the +\texttt{NUL} char\dots imagine that\dots). A single leading $-$ (ASCII \texttt{0x20}) sign can be +used to denote a negative number. The input encoding is currently restricted to ASCII only. If \texttt{MP\_NO\_FILE} is not defined a function to read from a file is also available. \index{mp\_fread} @@ -2226,7 +2455,6 @@ \subsection{From ASCII} mp_err mp_fread(mp_int *a, int radix, FILE *stream); \end{alltt} - \section{Binary Conversions} Converting an \texttt{mp\_int} to and from binary is another keen idea. @@ -2236,33 +2464,40 @@ \section{Binary Conversions} size_t mp_ubin_size(const mp_int *a); \end{alltt} -This will return the number of bytes (octets) required to store the unsigned copy of the integer $a$. +This will return the number of bytes (octets) required to store the unsigned copy of the integer +$a$. \index{mp\_to\_ubin} \begin{alltt} mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) \end{alltt} -This will store $a$ into the buffer $b$ of size \texttt{maxlen} in big--endian format storing the number of bytes written in \texttt{len}. Fortunately this is exactly what DER (or is it ASN?) requires. It does not store the sign of the integer. +This will store $a$ into the buffer \texttt{buf} of size \texttt{maxlen} in big--endian format +storing the number of bytes written in \texttt{len}. Fortunately this is exactly what DER (or is +it ASN?) requires. It does not store the sign of the integer. \index{mp\_from\_ubin} \begin{alltt} mp_err mp_from_ubin(mp_int *a, unsigned char *b, size_t size); \end{alltt} -This will read in an unsigned big--endian array of bytes (octets) from $b$ of length \texttt{size} into $a$. The resulting big-integer $a$ will always be positive. +This will read in an unsigned big--endian array of bytes (octets) from \texttt{b} of length +\texttt{size} into $a$. The resulting big--integer $a$ will always be positive. -For those who acknowledge the existence of negative numbers (heretic!) there are ``signed'' versions of the -previous functions. +For those who acknowledge the existence of negative numbers (heretic!) there are ``signed'' +versions of the previous functions. \index{mp\_signed\_bin\_size} \index{mp\_to\_signed\_bin} \index{mp\_read\_signed\_bin} \begin{alltt} size_t mp_sbin_size(const mp_int *a); mp_err mp_from_sbin(mp_int *a, const unsigned char *b, size_t size); mp_err mp_to_sbin(const mp_int *a, unsigned char *b, size_t maxsize, size_t *len); \end{alltt} -They operate essentially the same as the unsigned copies except they prefix the data with zero or non--zero -byte depending on the sign. If the sign is \texttt{MP\_ZPOS} (e.g. not negative) the prefix is zero, otherwise the prefix -is non--zero. +They operate essentially the same as the unsigned copies except they prefix the data with zero or +non--zero byte depending on the sign. If the sign is \texttt{MP\_ZPOS} (e.g. not negative) the +prefix is zero, otherwise the prefix is non--zero. -The two functions \texttt{mp\_unpack} (get your gifts out of the box, import binary data) and \texttt{mp\_pack} (put your gifts into the box, export binary data) implement the similarly working GMP functions as described at \url{http://gmplib.org/manual/Integer-Import-and-Export.html} with the exception that \texttt{mp\_pack} will not allocate memory if \texttt{rop} is \texttt{NULL}. +The two functions \texttt{mp\_unpack} (get your gifts out of the box, import binary data) and +\texttt{mp\_pack} (put your gifts into the box, export binary data) implement the similarly working +GMP functions as described at \url{http://gmplib.org/manual/Integer-Import-and-Export.html} with +the exception that \texttt{mp\_pack} will not allocate memory if \texttt{rop} is \texttt{NULL}. \index{mp\_unpack} \index{mp\_pack} \begin{alltt} mp_err mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, @@ -2270,14 +2505,16 @@ \section{Binary Conversions} mp_err mp_pack(void *rop, size_t *countp, mp_order order, size_t size, mp_endian endian, size_t nails, const mp_int *op); \end{alltt} -The function \texttt{mp\_pack} has the additional variable \texttt{maxsize} which must hold the size of the buffer \texttt{rop} in bytes. Use +The function \texttt{mp\_pack} has the additional variable \texttt{maxsize} which must hold the +size of the buffer \texttt{rop} in bytes. Use \begin{alltt} /* Parameters "nails" and "size" are the same as in mp_pack */ size_t mp_pack_count(const mp_int *a, size_t nails, size_t size); \end{alltt} To get the size in bytes necessary to be put in \texttt{maxsize}). -To enhance the readability of your code, the following enums have been wrought for your convenience. +To enhance the readability of your code, the following enums have been wrought for your +convenience. \begin{alltt} typedef enum { MP_LSB_FIRST = -1, @@ -2298,13 +2535,15 @@ \section{Extended Euclidean Algorithm} mp_int *U1, mp_int *U2, mp_int *U3); \end{alltt} -This finds the triple $U_1$/$U_2$/$U_3$ using the Extended Euclidean algorithm such that the following equation holds. +This finds the triple $U_1$/$U_2$/$U_3$ using the Extended Euclidean algorithm such that the +following equation holds. \begin{equation} -a \cdot U_1 + b \cdot U_2 = U_3 + a \cdot U_1 + b \cdot U_2 = U_3 \end{equation} -Any of the \texttt{U1}/\texttt{U2}/\texttt{U3} parameters can be set to \textbf{NULL} if they are not desired. +Any of the \texttt{U1}/\texttt{U2}/\texttt{U3} parameters can be set to \textbf{NULL} if they are +not desired. \section{Greatest Common Divisor} \index{mp\_gcd} @@ -2320,17 +2559,18 @@ \section{Least Common Multiple} \end{alltt} This will compute the least common multiple of $a$ and $b$ and store it in $c$. - \section{Kronecker Symbol} \index{mp\_kronecker} \begin{alltt} mp_err mp_kronecker (const mp_int *a, const mp_int *p, int *c) \end{alltt} -This will compute the Kronecker symbol (an extension of the Jacobi symbol) for $a$ with respect to $p$ with $\lbrace a, p \rbrace \in \mathbb{Z}$. If $p$ is prime this essentially computes the Legendre -symbol. The result is stored in $c$ and can take on one of three values $\lbrace -1, 0, 1 \rbrace$. If $p$ is prime -then the result will be $-1$ when $a$ is not a quadratic residue modulo $p$. The result will be $0$ if $a$ divides $p$ -and the result will be $1$ if $a$ is a quadratic residue modulo $p$. - +This will compute the Kronecker symbol (an extension of the Jacobi symbol) for $a$ with respect to +$p$ with $\lbrace a, p \rbrace \in \mathbb{Z}$. If $p$ is prime this essentially computes the +Legendre symbol. The result is stored in $c$ and can take on one of three values $\lbrace -1, 0, 1 + \rbrace$. If $p$ is prime then the result will be $-1$ when $a$ is not a quadratic residue +modulo +$p$. The result will be $0$ if $a$ divides $p$ and the result will be $1$ if $a$ is a quadratic +residue modulo $p$. \section{Modular square root} \index{mp\_sqrtmod\_prime} @@ -2338,27 +2578,29 @@ \section{Modular square root} mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *p, mp_int *r) \end{alltt} -This will solve the modular equation $r^2 = n \mod p$ where $p$ is a prime number greater than 2 (odd prime). -The result is returned in the third argument $r$, the function returns \texttt{MP\_OKAY} on success, -other return values indicate failure. +This will solve the modular equation $r^2 = n \mod p$ where $p$ is a prime number greater than 2 +(odd prime). The result is returned in the third argument $r$, the function returns +\texttt{MP\_OKAY} on success, other return values indicate failure. The implementation is split for two different cases: -1. if $p \mod 4 == 3$ we apply \href{http://cacr.uwaterloo.ca/hac/}{Handbook of Applied Cryptography algorithm 3.36} and compute $r$ directly as -$r = n^{(p+1)/4} \mod p$ +1. if $p \mod 4 == 3$ we apply \href{http://cacr.uwaterloo.ca/hac/}{Handbook of Applied + Cryptography algorithm 3.36} and compute $r$ directly as $r = n^{(p+1)/4} \mod p$ -2. otherwise we use \href{https://en.wikipedia.org/wiki/Tonelli-Shanks_algorithm}{Tonelli-Shanks algorithm} +2. otherwise we use \href{https://en.wikipedia.org/wiki/Tonelli-Shanks_algorithm}{Tonelli--Shanks + algorithm} -The function does not check the primality of parameter $p$ thus it is up to the caller to assure that this parameter -is a prime number. When $p$ is a composite the function behaviour is undefined, it may even return a false-positive -\texttt{MP\_OKAY}. +The function does not check the primality of parameter $p$ thus it is up to the caller to assure +that this parameter is a prime number. When $p$ is a composite the function behaviour is undefined, +it may even return a false--positive \texttt{MP\_OKAY}. \section{Modular Inverse} \index{mp\_invmod} \begin{alltt} mp_err mp_invmod (const mp_int *a, const mp_int *b, mp_int *c) \end{alltt} -Computes the multiplicative inverse of $a$ modulo $b$ and stores the result in $c$ such that $ac \equiv 1 \mbox{ (mod }b\mbox{)}$. +Computes the multiplicative inverse of $a$ modulo $b$ and stores the result in $c$ such that +$ac \equiv 1 \mbox{ (mod }b\mbox{)}$. \section{Single Digit Functions} @@ -2373,18 +2615,21 @@ \section{Single Digit Functions} mp_err mp_mod_d(const mp_int *a, mp_digit b, mp_digit *c); \end{alltt} -These work like the full \texttt{mp\_int} capable variants except the second parameter $b$ is a \texttt{mp\_digit}. These -functions fairly handy if you have to work with relatively small numbers since you will not have to allocate -an entire \texttt{mp\_int} to store a number like $1$ or $2$. +These work like the full \texttt{mp\_int} capable variants except the second parameter $b$ is a +\texttt{mp\_digit}. These functions fairly handy if you have to work with relatively small numbers +since you will not have to allocate an entire \texttt{mp\_int} to store a number like $1$ or $2$. -The functions \texttt{mp\_incr} and \texttt{mp\_decr} mimic the postfix operators \texttt{++} and \texttt{--} respectively, to increment the input by one. They call the full single-digit functions if the addition would carry. Both functions need to be included in a minimized library because they call each other in case of a negative input, These functions change the inputs! +The functions \texttt{mp\_incr} and \texttt{mp\_decr} mimic the postfix operators \texttt{++} and +\texttt{--} respectively, to increment the input by one. They call the full single--digit functions +if the addition would carry. Both functions need to be included in a minimized library because they +call each other in case of a negative input, These functions change the inputs! \begin{alltt} mp_err mp_incr(mp_int *a); mp_err mp_decr(mp_int *a); \end{alltt} - -The division by three can be made faster by replacing the division with a multiplication by the multiplicative inverse of three. +The division by three can be made faster by replacing the division with a multiplication by the +multiplicative inverse of three. \index{mp\_div\_3} \begin{alltt} @@ -2394,7 +2639,8 @@ \section{Single Digit Functions} \chapter{Little Helpers} It is never wrong to have some useful little shortcuts at hand. \section{Function Macros} -To make this overview simpler the macros are given as function prototypes. The return of logic macros is \texttt{MP\_NO} or \texttt{MP\_YES} respectively. +To make this overview simpler the macros are given as function prototypes. The return of logic +macros is \texttt{MP\_NO} or \texttt{MP\_YES} respectively. \index{mp\_iseven} \begin{alltt} @@ -2414,15 +2660,14 @@ \section{Function Macros} \end{alltt} Checks if $a < 0$ - \index{mp\_iszero} \begin{alltt} mp_bool mp_iszero(mp_int *a) \end{alltt} Checks if $a = 0$. It does not check if the amount of memory allocated for $a$ is also minimal. - -Other macros which are either shortcuts to normal functions or just other names for them do have their place in a programmer's life, too! +Other macros which are either shortcuts to normal functions or just other names for them do have +their place in a programmer's life, too! \subsection{Renamings} \index{mp\_mag\_size} @@ -2430,38 +2675,31 @@ \subsection{Renamings} #define mp_mag_size(mp) mp_unsigned_bin_size(mp) \end{alltt} - \index{mp\_raw\_size} \begin{alltt} #define mp_raw_size(mp) mp_signed_bin_size(mp) \end{alltt} - \index{mp\_read\_mag} \begin{alltt} #define mp_read_mag(mp, str, len) mp_read_unsigned_bin((mp), (str), (len)) \end{alltt} - \index{mp\_read\_raw} \begin{alltt} #define mp_read_raw(mp, str, len) mp_read_signed_bin((mp), (str), (len)) \end{alltt} - \index{mp\_tomag} \begin{alltt} #define mp_tomag(mp, str) mp_to_unsigned_bin((mp), (str)) \end{alltt} - \index{mp\_toraw} \begin{alltt} #define mp_toraw(mp, str) mp_to_signed_bin((mp), (str)) \end{alltt} - - \subsection{Shortcuts} \index{mp\_to\_binary} @@ -2469,31 +2707,33 @@ \subsection{Shortcuts} #define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), 2) \end{alltt} - \index{mp\_to\_octal} \begin{alltt} #define mp_to_octal(M, S, N) mp_to_radix((M), (S), (N), 8) \end{alltt} - \index{mp\_to\_decimal} \begin{alltt} #define mp_to_decimal(M, S, N) mp_to_radix((M), (S), (N), 10) \end{alltt} - \index{mp\_to\_hex} \begin{alltt} #define mp_to_hex(M, S, N) mp_to_radix((M), (S), (N), 16) \end{alltt} \begin{appendices} -\appendixpage -%\noappendicestocpagenum -\addappheadtotoc -\chapter{Computing Number of Miller-Rabin Trials}\label{app:numberofmrcomp} -The number of Miller-Rabin rounds in the tables \ref{millerrabinrunsimpl}, \ref{millerrabinrunsp1}, and \ref{millerrabinrunsp2} have been calculated with the formula in FIPS 186-4 appendix F.1 (page 117) implemented as a PARI/GP script. -\begin{alltt} + \appendixpage + %\noappendicestocpagenum + \addappheadtotoc + \chapter{Computing Number of Miller--Rabin Trials}\label{app:numberofmrcomp} + The number of Miller--Rabin rounds in the tables \ref{millerrabinrunsimpl}, + \ref{millerrabinrunsp1}, and \ref{millerrabinrunsp2} have been calculated with the formula in + FIPS + 186--4 appendix F.1 (page 117) implemented as a PARI/GP script. + + \begin{small} + \begin{alltt} log2(x) = log(x)/log(2) fips_f1_sums(k, M, t) = { @@ -2535,9 +2775,10 @@ \chapter{Computing Number of Miller-Rabin Trials}\label{app:numberofmrcomp} ); } \end{alltt} + \end{small} -To get the number of rounds for a $1024$ bit large prime with a probability of $2^{-160}$: -\begin{alltt} + To get the number of rounds for a $1024$ bit large prime with a probability of $2^{-160}$: + \begin{alltt} ? fips_f1_1(1024,2^(-160)) %1 = 9 \end{alltt} diff --git a/doc/makefile b/doc/makefile index 583becc54..124859ef9 100644 --- a/doc/makefile +++ b/doc/makefile @@ -38,5 +38,12 @@ manual: mandvi mv bn.bak bn.tex rm -f bn.aux bn.dvi bn.log bn.idx bn.lof bn.out bn.toc +# The file latexindent.pl is in several LaTeX distributions, if not: +# https://ctan.org/pkg/latexindent +# Its configuraion is well documented +# http://mirrors.ctan.org/support/latexindent/documentation/latexindent.pdf +pretty: + latexindent -w -m -l=.latexindent.yaml bn.tex + clean: rm -f *.idx *.toc *.log *.aux *.dvi *.lof *.ind *.ilg *.ps *.log tommath.tex From 59ee1416a00db881cdd92755c6241170305e9ab6 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Oct 2019 15:48:38 +0100 Subject: [PATCH 062/304] fix `./helper.pl -d` --- helper.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/helper.pl b/helper.pl index 134469d69..cdab930ea 100755 --- a/helper.pl +++ b/helper.pl @@ -108,7 +108,7 @@ sub check_doc { my $fails = 0; my $tex = read_file('doc/bn.tex'); my $tmh = read_file('tommath.h'); - my @functions = $tmh =~ /\n\s*[a-zA-Z0-9_* ]+?(mp_[a-z0-9_]+)\s*\([^\)]+\)\s*;/sg; + my @functions = $tmh =~ /\n\s*[a-zA-Z0-9_* ]+?(mp_[a-z0-9_]+)\s*\([^\)]+\)\s*[MP_WUR]+?;/sg; my @macros = $tmh =~ /\n\s*#define\s+([a-z0-9_]+)\s*\([^\)]+\)/sg; for my $n (sort @functions) { (my $nn = $n) =~ s/_/\\_/g; # mp_sub_d >> mp\_sub\_d From 9d954dc81922b2d614b0a01b931af94ec01003b2 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Oct 2019 16:19:02 +0100 Subject: [PATCH 063/304] also check doc when running `helper.pl -a` --- helper.pl | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/helper.pl b/helper.pl index cdab930ea..223c7ef60 100755 --- a/helper.pl +++ b/helper.pl @@ -447,6 +447,7 @@ sub die_usage { usage: $0 -s OR $0 --check-source $0 -o OR $0 --check-comments $0 -m OR $0 --check-makefiles + $0 -d OR $0 --check-doc $0 -a OR $0 --check-all $0 -u OR $0 --update-files MARKER @@ -464,7 +465,7 @@ sub die_usage { my $failure; $failure ||= check_source() if $check_all || $check_source; $failure ||= check_comments() if $check_all || $check_comments; -$failure ||= check_doc() if $check_doc; # temporarily excluded from --check-all +$failure ||= check_doc() if $check_all || $check_doc; $failure ||= process_makefiles(0) if $check_all || $check_makefiles; $failure ||= process_makefiles(1) if $update_files; $failure ||= update_dep() if $update_files; From 8862ca830edc727b97bb1f62c2e3be2a25ba2326 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Oct 2019 16:29:30 +0100 Subject: [PATCH 064/304] fix index added new API functions found by `helper.pl -d` removed old API functions found via ```sh awk -F',' '/item/ {print $1}' doc/bn.ind | \ awk '/mp/ {print $2}' | \ sed -e 's/\\//g' | \ xargs -I {} sh -c "grep -q {} tommath.h || echo {}" ``` --- doc/bn.tex | 52 ++++++++++------------------------------------------ 1 file changed, 10 insertions(+), 42 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 430c82a06..53c3251d9 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -1039,7 +1039,8 @@ \subsection{Floating Point Constants - platform dependant} \subsection{Initialize and Setting Constants} To both initialize and set small constants the following nine functions are available. -\index{mp\_init\_set} \index{mp\_init\_set\_int} +\index{mp\_init\_set} \index{mp\_init\_i32} \index{mp\_init\_i64} \index{mp\_init\_u32} \index{mp\_init\_u64} +\index{mp\_init\_l} \index{mp\_init\_ll} \index{mp\_init\_ul} \index{mp\_init\_ull} \begin{alltt} mp_err mp_init_set (mp_int *a, mp_digit b); mp_err mp_init_i32 (mp_int *a, int32_t b); @@ -1427,7 +1428,7 @@ \subsection{AND, OR, XOR and COMPLEMENT Operations} are treated as if they are in two--complement representation, while internally they are sign--magnitude however. -\index{mp\_or} \index{mp\_and} \index{mp\_xor} \index{mp\_complement} +\index{mp\_or} \index{mp\_and} \index{mp\_xor} \index{mp\_complement} \index{mp\_signed\_rsh} \begin{alltt} mp_err mp_or (const mp_int *a, mp_int *b, mp_int *c); mp_err mp_and (const mp_int *a, mp_int *b, mp_int *c); @@ -1908,16 +1909,19 @@ \section{Combined Modular Reduction} \end{alltt} Subtraction $d = (a - b) \mod c$ +\index{mp\_submod} \begin{alltt} mp_err mp_submod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} Multiplication $d = (ab) \mod c$ +\index{mp\_mulmod} \begin{alltt} mp_err mp_mulmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} Squaring $d = (a^2) \mod c$ +\index{mp\_sqrmod} \begin{alltt} mp_err mp_sqrmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d); \end{alltt} @@ -1953,7 +1957,7 @@ \section{Modulus a Power of Two} It calculates $c = a \mod 2^b$. \section{Root Finding} -\index{mp\_n\_root} +\index{mp\_root\_u32} \begin{alltt} mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) \end{alltt} @@ -2378,13 +2382,6 @@ \section{Random Primes} \chapter{Random Number Generation} \section{PRNG} -\index{mp\_rand\_digit} -\begin{alltt} -mp_err mp_rand_digit(mp_digit *r) -\end{alltt} -This function generates a random number in \texttt{r} of the size given in \texttt{r} (that is, the -variable is used for in-- and output) but not more than \texttt{MP\_DIGIT\_MAX} bits. - \index{mp\_rand} \begin{alltt} mp_err mp_rand(mp_int *a, int digits) @@ -2484,7 +2481,7 @@ \section{Binary Conversions} For those who acknowledge the existence of negative numbers (heretic!) there are ``signed'' versions of the previous functions. -\index{mp\_signed\_bin\_size} \index{mp\_to\_signed\_bin} \index{mp\_read\_signed\_bin} +\index{mp\_sbin\_size} \index{mp\_from\_sbin} \index{mp\_to\_sbin} \begin{alltt} size_t mp_sbin_size(const mp_int *a); mp_err mp_from_sbin(mp_int *a, const unsigned char *b, size_t size); @@ -2507,6 +2504,7 @@ \section{Binary Conversions} \end{alltt} The function \texttt{mp\_pack} has the additional variable \texttt{maxsize} which must hold the size of the buffer \texttt{rop} in bytes. Use +\index{mp\_pack\_count} \begin{alltt} /* Parameters "nails" and "size" are the same as in mp_pack */ size_t mp_pack_count(const mp_int *a, size_t nails, size_t size); @@ -2623,6 +2621,7 @@ \section{Single Digit Functions} \texttt{--} respectively, to increment the input by one. They call the full single--digit functions if the addition would carry. Both functions need to be included in a minimized library because they call each other in case of a negative input, These functions change the inputs! +\index{mp\_incr} \index{mp\_decr} \begin{alltt} mp_err mp_incr(mp_int *a); mp_err mp_decr(mp_int *a); @@ -2669,37 +2668,6 @@ \section{Function Macros} Other macros which are either shortcuts to normal functions or just other names for them do have their place in a programmer's life, too! -\subsection{Renamings} -\index{mp\_mag\_size} -\begin{alltt} -#define mp_mag_size(mp) mp_unsigned_bin_size(mp) -\end{alltt} - -\index{mp\_raw\_size} -\begin{alltt} -#define mp_raw_size(mp) mp_signed_bin_size(mp) -\end{alltt} - -\index{mp\_read\_mag} -\begin{alltt} -#define mp_read_mag(mp, str, len) mp_read_unsigned_bin((mp), (str), (len)) -\end{alltt} - -\index{mp\_read\_raw} -\begin{alltt} - #define mp_read_raw(mp, str, len) mp_read_signed_bin((mp), (str), (len)) -\end{alltt} - -\index{mp\_tomag} -\begin{alltt} -#define mp_tomag(mp, str) mp_to_unsigned_bin((mp), (str)) -\end{alltt} - -\index{mp\_toraw} -\begin{alltt} -#define mp_toraw(mp, str) mp_to_signed_bin((mp), (str)) -\end{alltt} - \subsection{Shortcuts} \index{mp\_to\_binary} From f21ea6ce184beea12d5b518ecdde1bded1ecf24a Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 23 Oct 2019 20:06:08 +0200 Subject: [PATCH 065/304] add fast path to mp_add_d and mp_sub_d --- mp_add_d.c | 9 +++++++++ mp_decr.c | 34 ---------------------------------- mp_incr.c | 30 ------------------------------ mp_sub_d.c | 9 +++++++++ tommath.h | 4 ++-- 5 files changed, 20 insertions(+), 66 deletions(-) delete mode 100644 mp_decr.c delete mode 100644 mp_incr.c diff --git a/mp_add_d.c b/mp_add_d.c index 07242c6a8..3be2d23f6 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -10,6 +10,15 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) int ix, oldused; mp_digit *tmpa, *tmpc; + /* fast path for a == c */ + if (a == c && + !MP_IS_ZERO(c) && + c->sign == MP_ZPOS && + c->dp[0] + b < MP_DIGIT_MAX) { + c->dp[0] += b; + return MP_OKAY; + } + /* grow c as required */ if (c->alloc < (a->used + 1)) { if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { diff --git a/mp_decr.c b/mp_decr.c deleted file mode 100644 index 55516cf13..000000000 --- a/mp_decr.c +++ /dev/null @@ -1,34 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_DECR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -/* Decrement "a" by one like "a--". Changes input! */ -mp_err mp_decr(mp_int *a) -{ - if (MP_IS_ZERO(a)) { - mp_set(a,1uL); - a->sign = MP_NEG; - return MP_OKAY; - } else if (a->sign == MP_NEG) { - mp_err err; - a->sign = MP_ZPOS; - if ((err = mp_incr(a)) != MP_OKAY) { - return err; - } - /* There is no -0 in LTM */ - if (!MP_IS_ZERO(a)) { - a->sign = MP_NEG; - } - return MP_OKAY; - } else if (a->dp[0] > 1uL) { - a->dp[0]--; - if (a->dp[0] == 0u) { - mp_zero(a); - } - return MP_OKAY; - } else { - return mp_sub_d(a, 1uL,a); - } -} -#endif diff --git a/mp_incr.c b/mp_incr.c deleted file mode 100644 index 12dc20bbd..000000000 --- a/mp_incr.c +++ /dev/null @@ -1,30 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_INCR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -/* Increment "a" by one like "a++". Changes input! */ -mp_err mp_incr(mp_int *a) -{ - if (MP_IS_ZERO(a)) { - mp_set(a,1uL); - return MP_OKAY; - } else if (a->sign == MP_NEG) { - mp_err err; - a->sign = MP_ZPOS; - if ((err = mp_decr(a)) != MP_OKAY) { - return err; - } - /* There is no -0 in LTM */ - if (!MP_IS_ZERO(a)) { - a->sign = MP_NEG; - } - return MP_OKAY; - } else if (a->dp[0] < MP_DIGIT_MAX) { - a->dp[0]++; - return MP_OKAY; - } else { - return mp_add_d(a, 1uL,a); - } -} -#endif diff --git a/mp_sub_d.c b/mp_sub_d.c index 16c61658a..a8a0d3866 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -10,6 +10,15 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) mp_err err; int ix, oldused; + /* fast path for a == c */ + if (a == c && + !MP_IS_ZERO(c) && + c->sign == MP_ZPOS && + c->dp[0] > b) { + c->dp[0] -= b; + return MP_OKAY; + } + /* grow c as required */ if (c->alloc < (a->used + 1)) { if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { diff --git a/tommath.h b/tommath.h index b741674bb..f7711e144 100644 --- a/tommath.h +++ b/tommath.h @@ -377,10 +377,10 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) MP_WUR; mp_err mp_mod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* Increment "a" by one like "a++". Changes input! */ -mp_err mp_incr(mp_int *a) MP_WUR; +#define mp_incr(a) mp_add_d((a), 1, (a)) /* Decrement "a" by one like "a--". Changes input! */ -mp_err mp_decr(mp_int *a) MP_WUR; +#define mp_decr(a) mp_sub_d((a), 1, (a)) /* ---> single digit functions <--- */ From eb70378bfb39906f97874904ce17380e13539ac4 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 23 Oct 2019 20:06:33 +0200 Subject: [PATCH 066/304] mp_iseven/mp_isodd should be inline --- mp_iseven.c | 10 ---------- mp_isodd.c | 10 ---------- tommath.h | 4 ++-- 3 files changed, 2 insertions(+), 22 deletions(-) delete mode 100644 mp_iseven.c delete mode 100644 mp_isodd.c diff --git a/mp_iseven.c b/mp_iseven.c deleted file mode 100644 index 4ebc9afc8..000000000 --- a/mp_iseven.c +++ /dev/null @@ -1,10 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_ISEVEN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_bool mp_iseven(const mp_int *a) -{ - return MP_IS_EVEN(a) ? MP_YES : MP_NO; -} -#endif diff --git a/mp_isodd.c b/mp_isodd.c deleted file mode 100644 index f8a3e0e5b..000000000 --- a/mp_isodd.c +++ /dev/null @@ -1,10 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_ISODD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_bool mp_isodd(const mp_int *a) -{ - return MP_IS_ODD(a) ? MP_YES : MP_NO; -} -#endif diff --git a/tommath.h b/tommath.h index f7711e144..5d0d2fe6f 100644 --- a/tommath.h +++ b/tommath.h @@ -209,9 +209,9 @@ mp_err mp_init_size(mp_int *a, int size) MP_WUR; /* ---> Basic Manipulations <--- */ #define mp_iszero(a) (((a)->used == 0) ? MP_YES : MP_NO) -mp_bool mp_iseven(const mp_int *a) MP_WUR; -mp_bool mp_isodd(const mp_int *a) MP_WUR; #define mp_isneg(a) (((a)->sign != MP_ZPOS) ? MP_YES : MP_NO) +#define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u) ? MP_YES : MP_NO) +#define mp_isodd(a) (((a)->used > 0) && (((a)->dp[0] & 1u) == 1u) ? MP_YES : MP_NO) /* set to zero */ void mp_zero(mp_int *a); From f8b2f5d6fe96f40790ee2baafb5acad58324e37d Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 23 Oct 2019 20:07:33 +0200 Subject: [PATCH 067/304] s_mp_reverse is only used by mp_to_radix --- mp_to_radix.c | 17 +++++++++++++++++ s_mp_reverse.c | 22 ---------------------- tommath_private.h | 1 - 3 files changed, 17 insertions(+), 23 deletions(-) delete mode 100644 s_mp_reverse.c diff --git a/mp_to_radix.c b/mp_to_radix.c index 95def74d3..b0564a153 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -3,6 +3,23 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ +/* reverse an array, used for radix code */ +static void s_mp_reverse(unsigned char *s, size_t len) +{ + size_t ix, iy; + unsigned char t; + + ix = 0u; + iy = len - 1u; + while (ix < iy) { + t = s[ix]; + s[ix] = s[iy]; + s[iy] = t; + ++ix; + --iy; + } +} + /* stores a bignum as a ASCII string in a given radix (2..64) * * Stores upto "size - 1" chars and always a NULL byte, puts the number of characters diff --git a/s_mp_reverse.c b/s_mp_reverse.c deleted file mode 100644 index d288dc560..000000000 --- a/s_mp_reverse.c +++ /dev/null @@ -1,22 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_REVERSE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -/* reverse an array, used for radix code */ -void s_mp_reverse(unsigned char *s, size_t len) -{ - size_t ix, iy; - unsigned char t; - - ix = 0u; - iy = len - 1u; - while (ix < iy) { - t = s[ix]; - s[ix] = s[iy]; - s[iy] = t; - ++ix; - --iy; - } -} -#endif diff --git a/tommath_private.h b/tommath_private.h index 1916f87dc..e26025f24 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -209,7 +209,6 @@ MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; typedef int mp_prime_callback(unsigned char *dst, int len, void *dat); MP_PRIVATE mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat); -MP_PRIVATE void s_mp_reverse(unsigned char *s, size_t len); MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); From a44e68e652347fb4e44de6fef72b767fdebca1a6 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 17:43:31 +0200 Subject: [PATCH 068/304] remove MP_IS_* macros --- mp_add_d.c | 2 +- mp_cnt_lsb.c | 2 +- mp_count_bits.c | 2 +- mp_div.c | 2 +- mp_div_d.c | 2 +- mp_exptmod.c | 2 +- mp_exteuclid.c | 2 +- mp_gcd.c | 6 +++--- mp_invmod.c | 2 +- mp_is_square.c | 2 +- mp_kronecker.c | 6 +++--- mp_log_u32.c | 2 +- mp_lshd.c | 2 +- mp_mod.c | 2 +- mp_neg.c | 2 +- mp_prime_frobenius_underwood.c | 2 +- mp_prime_is_prime.c | 2 +- mp_prime_next_prime.c | 2 +- mp_prime_strong_lucas_selfridge.c | 12 ++++++------ mp_radix_size.c | 2 +- mp_read_radix.c | 2 +- mp_set_double.c | 2 +- mp_sqrt.c | 2 +- mp_sqrtmod_prime.c | 2 +- mp_sub_d.c | 2 +- mp_to_radix.c | 4 ++-- s_mp_div_small.c | 4 ++-- s_mp_invmod_fast.c | 14 +++++++------- s_mp_invmod_slow.c | 14 +++++++------- tommath_private.h | 6 +----- 30 files changed, 53 insertions(+), 57 deletions(-) diff --git a/mp_add_d.c b/mp_add_d.c index 3be2d23f6..cd0d47a94 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -12,7 +12,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) /* fast path for a == c */ if (a == c && - !MP_IS_ZERO(c) && + !mp_iszero(c) && c->sign == MP_ZPOS && c->dp[0] + b < MP_DIGIT_MAX) { c->dp[0] += b; diff --git a/mp_cnt_lsb.c b/mp_cnt_lsb.c index a2cd5f892..7ae8bc13c 100644 --- a/mp_cnt_lsb.c +++ b/mp_cnt_lsb.c @@ -14,7 +14,7 @@ int mp_cnt_lsb(const mp_int *a) mp_digit q, qq; /* easy out */ - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { return 0; } diff --git a/mp_count_bits.c b/mp_count_bits.c index 76257c890..52b463d46 100644 --- a/mp_count_bits.c +++ b/mp_count_bits.c @@ -10,7 +10,7 @@ int mp_count_bits(const mp_int *a) mp_digit q; /* shortcut */ - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { return 0; } diff --git a/mp_div.c b/mp_div.c index e9f4f5017..23a2acf93 100644 --- a/mp_div.c +++ b/mp_div.c @@ -8,7 +8,7 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) mp_err err; /* is divisor zero ? */ - if (MP_IS_ZERO(b)) { + if (mp_iszero(b)) { return MP_VAL; } diff --git a/mp_div_d.c b/mp_div_d.c index 331b28593..98b6b248c 100644 --- a/mp_div_d.c +++ b/mp_div_d.c @@ -18,7 +18,7 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) } /* quick outs */ - if ((b == 1u) || MP_IS_ZERO(a)) { + if ((b == 1u) || mp_iszero(a)) { if (d != NULL) { *d = 0; } diff --git a/mp_exptmod.c b/mp_exptmod.c index fcc894bd9..8f8a9e977 100644 --- a/mp_exptmod.c +++ b/mp_exptmod.c @@ -62,7 +62,7 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) } /* if the modulus is odd or dr != 0 use the montgomery method */ - if (MP_HAS(S_MP_EXPTMOD_FAST) && (MP_IS_ODD(P) || (dr != 0))) { + if (MP_HAS(S_MP_EXPTMOD_FAST) && (mp_isodd(P) || (dr != 0))) { return s_mp_exptmod_fast(G, X, P, Y, dr); } else if (MP_HAS(S_MP_EXPTMOD)) { /* otherwise use the generic Barrett reduction technique */ diff --git a/mp_exteuclid.c b/mp_exteuclid.c index 5b850dab2..eb8ad3728 100644 --- a/mp_exteuclid.c +++ b/mp_exteuclid.c @@ -24,7 +24,7 @@ mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp if ((err = mp_copy(b, &v3)) != MP_OKAY) goto LBL_ERR; /* loop while v3 != 0 */ - while (!MP_IS_ZERO(&v3)) { + while (!mp_iszero(&v3)) { /* q = u3/v3 */ if ((err = mp_div(&u3, &v3, &q, NULL)) != MP_OKAY) goto LBL_ERR; diff --git a/mp_gcd.c b/mp_gcd.c index 79b6749d6..4f6b6cc29 100644 --- a/mp_gcd.c +++ b/mp_gcd.c @@ -11,10 +11,10 @@ mp_err mp_gcd(const mp_int *a, const mp_int *b, mp_int *c) mp_err err; /* either zero than gcd is the largest */ - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { return mp_abs(b, c); } - if (MP_IS_ZERO(b)) { + if (mp_iszero(b)) { return mp_abs(a, c); } @@ -59,7 +59,7 @@ mp_err mp_gcd(const mp_int *a, const mp_int *b, mp_int *c) } } - while (!MP_IS_ZERO(&v)) { + while (!mp_iszero(&v)) { /* make sure v is the largest */ if (mp_cmp_mag(&u, &v) == MP_GT) { /* swap u and v to make sure v is >= u */ diff --git a/mp_invmod.c b/mp_invmod.c index b797d4eb8..e43eb3ec2 100644 --- a/mp_invmod.c +++ b/mp_invmod.c @@ -12,7 +12,7 @@ mp_err mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) } /* if the modulus is odd we can use a faster routine instead */ - if (MP_HAS(S_MP_INVMOD_FAST) && MP_IS_ODD(b)) { + if (MP_HAS(S_MP_INVMOD_FAST) && mp_isodd(b)) { return s_mp_invmod_fast(a, b, c); } diff --git a/mp_is_square.c b/mp_is_square.c index c2428f8da..f1df73ee0 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -40,7 +40,7 @@ mp_err mp_is_square(const mp_int *arg, mp_bool *ret) return MP_VAL; } - if (MP_IS_ZERO(arg)) { + if (mp_iszero(arg)) { return MP_OKAY; } diff --git a/mp_kronecker.c b/mp_kronecker.c index 3111a7884..0ac6338b9 100644 --- a/mp_kronecker.c +++ b/mp_kronecker.c @@ -25,7 +25,7 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) static const int table[8] = {0, 1, 0, -1, 0, -1, 0, 1}; - if (MP_IS_ZERO(p)) { + if (mp_iszero(p)) { if ((a->used == 1) && (a->dp[0] == 1u)) { *c = 1; } else { @@ -34,7 +34,7 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) return MP_OKAY; } - if (MP_IS_EVEN(a) && MP_IS_EVEN(p)) { + if (mp_iseven(a) && mp_iseven(p)) { *c = 0; return MP_OKAY; } @@ -69,7 +69,7 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) } for (;;) { - if (MP_IS_ZERO(&a1)) { + if (mp_iszero(&a1)) { if (mp_cmp_d(&p1, 1uL) == MP_EQ) { *c = k; goto LBL_KRON; diff --git a/mp_log_u32.c b/mp_log_u32.c index cff9e48f5..31d96628c 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -9,7 +9,7 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) return MP_VAL; } - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { return MP_VAL; } diff --git a/mp_lshd.c b/mp_lshd.c index eb9a5c33b..b0a845486 100644 --- a/mp_lshd.c +++ b/mp_lshd.c @@ -15,7 +15,7 @@ mp_err mp_lshd(mp_int *a, int b) return MP_OKAY; } /* no need to shift 0 around */ - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { return MP_OKAY; } diff --git a/mp_mod.c b/mp_mod.c index 349fecebb..3eced35ce 100644 --- a/mp_mod.c +++ b/mp_mod.c @@ -17,7 +17,7 @@ mp_err mp_mod(const mp_int *a, const mp_int *b, mp_int *c) goto LBL_ERR; } - if (MP_IS_ZERO(&t) || (t.sign == b->sign)) { + if (mp_iszero(&t) || (t.sign == b->sign)) { err = MP_OKAY; mp_exch(&t, c); } else { diff --git a/mp_neg.c b/mp_neg.c index 01fb27635..2fc1854bf 100644 --- a/mp_neg.c +++ b/mp_neg.c @@ -13,7 +13,7 @@ mp_err mp_neg(const mp_int *a, mp_int *b) } } - if (!MP_IS_ZERO(b)) { + if (!mp_iszero(b)) { b->sign = (a->sign == MP_ZPOS) ? MP_NEG : MP_ZPOS; } else { b->sign = MP_ZPOS; diff --git a/mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c index 0e2ba64f1..bb56ea75e 100644 --- a/mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -112,7 +112,7 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) mp_set_u32(&T1z, (uint32_t)((2 * a) + 5)); if ((err = mp_mod(&T1z, N, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - if (MP_IS_ZERO(&sz) && (mp_cmp(&tz, &T1z) == MP_EQ)) { + if (mp_iszero(&sz) && (mp_cmp(&tz, &T1z) == MP_EQ)) { *result = MP_YES; } diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index 1a61bb6a1..e4f92146d 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -39,7 +39,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) } /* N must be odd */ - if (MP_IS_EVEN(a)) { + if (mp_iseven(a)) { return MP_OKAY; } /* N is not a perfect square: floor(sqrt(N))^2 != N */ diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index 3256e37c2..c8f76036a 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -58,7 +58,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) } } } else { - if (MP_IS_EVEN(a)) { + if (mp_iseven(a)) { /* force odd */ if ((err = mp_sub_d(a, 1uL, a)) != MP_OKAY) { return err; diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index 895a48122..0aee33de9 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -206,7 +206,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) if ((err = mp_mul(&U2mz, &Uz, &T4z)) != MP_OKAY) goto LBL_LS_ERR; if ((err = s_mp_mul_si(&T4z, Ds, &T4z)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_add(&T1z, &T2z, &Uz)) != MP_OKAY) goto LBL_LS_ERR; - if (MP_IS_ODD(&Uz)) { + if (mp_isodd(&Uz)) { if ((err = mp_add(&Uz, a, &Uz)) != MP_OKAY) goto LBL_LS_ERR; } /* CZ @@ -214,16 +214,16 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) * Thomas R. Nicely used GMP's mpz_fdiv_q_2exp(). * But mp_div_2() does not do so, it is truncating instead. */ - oddness = MP_IS_ODD(&Uz) ? MP_YES : MP_NO; + oddness = mp_isodd(&Uz) ? MP_YES : MP_NO; if ((err = mp_div_2(&Uz, &Uz)) != MP_OKAY) goto LBL_LS_ERR; if ((Uz.sign == MP_NEG) && (oddness != MP_NO)) { if ((err = mp_sub_d(&Uz, 1uL, &Uz)) != MP_OKAY) goto LBL_LS_ERR; } if ((err = mp_add(&T3z, &T4z, &Vz)) != MP_OKAY) goto LBL_LS_ERR; - if (MP_IS_ODD(&Vz)) { + if (mp_isodd(&Vz)) { if ((err = mp_add(&Vz, a, &Vz)) != MP_OKAY) goto LBL_LS_ERR; } - oddness = MP_IS_ODD(&Vz) ? MP_YES : MP_NO; + oddness = mp_isodd(&Vz) ? MP_YES : MP_NO; if ((err = mp_div_2(&Vz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if ((Vz.sign == MP_NEG) && (oddness != MP_NO)) { if ((err = mp_sub_d(&Vz, 1uL, &Vz)) != MP_OKAY) goto LBL_LS_ERR; @@ -239,7 +239,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) /* If U_d or V_d is congruent to 0 mod N, then N is a prime or a strong Lucas pseudoprime. */ - if (MP_IS_ZERO(&Uz) || MP_IS_ZERO(&Vz)) { + if (mp_iszero(&Uz) || mp_iszero(&Vz)) { *result = MP_YES; goto LBL_LS_ERR; } @@ -262,7 +262,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) if ((err = mp_sqr(&Vz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_sub(&Vz, &Q2kdz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mod(&Vz, a, &Vz)) != MP_OKAY) goto LBL_LS_ERR; - if (MP_IS_ZERO(&Vz)) { + if (mp_iszero(&Vz)) { *result = MP_YES; goto LBL_LS_ERR; } diff --git a/mp_radix_size.c b/mp_radix_size.c index 6c3e58220..47f2f68c3 100644 --- a/mp_radix_size.c +++ b/mp_radix_size.c @@ -15,7 +15,7 @@ mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) return MP_VAL; } - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { *size = 2; return MP_OKAY; } diff --git a/mp_read_radix.c b/mp_read_radix.c index dc5e16782..0e4f84824 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -71,7 +71,7 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) } /* set the sign only if a != 0 */ - if (!MP_IS_ZERO(a)) { + if (!mp_iszero(a)) { a->sign = neg; } return MP_OKAY; diff --git a/mp_set_double.c b/mp_set_double.c index f7e3b8d14..467d7fd85 100644 --- a/mp_set_double.c +++ b/mp_set_double.c @@ -30,7 +30,7 @@ mp_err mp_set_double(mp_int *a, double b) return err; } - if (((cast.bits >> 63) != 0uLL) && !MP_IS_ZERO(a)) { + if (((cast.bits >> 63) != 0uLL) && !mp_iszero(a)) { a->sign = MP_NEG; } diff --git a/mp_sqrt.c b/mp_sqrt.c index 283986834..b51f6151f 100644 --- a/mp_sqrt.c +++ b/mp_sqrt.c @@ -15,7 +15,7 @@ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) } /* easy out */ - if (MP_IS_ZERO(arg)) { + if (mp_iszero(arg)) { mp_zero(ret); return MP_OKAY; } diff --git a/mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c index 723332ff4..96b283689 100644 --- a/mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -51,7 +51,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* Q = prime - 1 */ mp_zero(&S); /* S = 0 */ - while (MP_IS_EVEN(&Q)) { + while (mp_iseven(&Q)) { if ((err = mp_div_2(&Q, &Q)) != MP_OKAY) goto cleanup; /* Q = Q / 2 */ if ((err = mp_add_d(&S, 1uL, &S)) != MP_OKAY) goto cleanup; diff --git a/mp_sub_d.c b/mp_sub_d.c index a8a0d3866..e453d36ed 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -12,7 +12,7 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) /* fast path for a == c */ if (a == c && - !MP_IS_ZERO(c) && + !mp_iszero(c) && c->sign == MP_ZPOS && c->dp[0] > b) { c->dp[0] -= b; diff --git a/mp_to_radix.c b/mp_to_radix.c index b0564a153..78ad98988 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -42,7 +42,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i } /* quick out if its zero */ - if (MP_IS_ZERO(a)) { + if (mp_iszero(a)) { *str++ = '0'; *str = '\0'; if (written != NULL) { @@ -68,7 +68,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i --maxlen; } digs = 0u; - while (!MP_IS_ZERO(&t)) { + while (!mp_iszero(&t)) { if (--maxlen < 1u) { /* no more room */ err = MP_BUF; diff --git a/s_mp_div_small.c b/s_mp_div_small.c index 56b1335d9..c89023af3 100644 --- a/s_mp_div_small.c +++ b/s_mp_div_small.c @@ -37,11 +37,11 @@ mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) sign = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; if (c != NULL) { mp_exch(c, &q); - c->sign = MP_IS_ZERO(c) ? MP_ZPOS : sign; + c->sign = mp_iszero(c) ? MP_ZPOS : sign; } if (d != NULL) { mp_exch(d, &ta); - d->sign = MP_IS_ZERO(d) ? MP_ZPOS : a->sign; + d->sign = mp_iszero(d) ? MP_ZPOS : a->sign; } LBL_ERR: mp_clear_multi(&ta, &tb, &tq, &q, NULL); diff --git a/s_mp_invmod_fast.c b/s_mp_invmod_fast.c index 0d00ea91d..ed1fc4a7d 100644 --- a/s_mp_invmod_fast.c +++ b/s_mp_invmod_fast.c @@ -16,7 +16,7 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) mp_err err; /* 2. [modified] b must be odd */ - if (MP_IS_EVEN(b)) { + if (mp_iseven(b)) { return MP_VAL; } @@ -32,7 +32,7 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) if ((err = mp_mod(a, b, &y)) != MP_OKAY) goto LBL_ERR; /* if one of x,y is zero return an error! */ - if (MP_IS_ZERO(&x) || MP_IS_ZERO(&y)) { + if (mp_iszero(&x) || mp_iszero(&y)) { err = MP_VAL; goto LBL_ERR; } @@ -44,12 +44,12 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) top: /* 4. while u is even do */ - while (MP_IS_EVEN(&u)) { + while (mp_iseven(&u)) { /* 4.1 u = u/2 */ if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; /* 4.2 if B is odd then */ - if (MP_IS_ODD(&B)) { + if (mp_isodd(&B)) { if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; } /* B = B/2 */ @@ -57,12 +57,12 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) } /* 5. while v is even do */ - while (MP_IS_EVEN(&v)) { + while (mp_iseven(&v)) { /* 5.1 v = v/2 */ if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; /* 5.2 if D is odd then */ - if (MP_IS_ODD(&D)) { + if (mp_isodd(&D)) { /* D = (D-x)/2 */ if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; } @@ -84,7 +84,7 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) } /* if not zero goto step 4 */ - if (!MP_IS_ZERO(&u)) { + if (!mp_iszero(&u)) { goto top; } diff --git a/s_mp_invmod_slow.c b/s_mp_invmod_slow.c index 4fecfb895..28cd6cd88 100644 --- a/s_mp_invmod_slow.c +++ b/s_mp_invmod_slow.c @@ -10,7 +10,7 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) mp_err err; /* b cannot be negative */ - if ((b->sign == MP_NEG) || MP_IS_ZERO(b)) { + if ((b->sign == MP_NEG) || mp_iszero(b)) { return MP_VAL; } @@ -25,7 +25,7 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) if ((err = mp_copy(b, &y)) != MP_OKAY) goto LBL_ERR; /* 2. [modified] if x,y are both even then return an error! */ - if (MP_IS_EVEN(&x) && MP_IS_EVEN(&y)) { + if (mp_iseven(&x) && mp_iseven(&y)) { err = MP_VAL; goto LBL_ERR; } @@ -38,12 +38,12 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) top: /* 4. while u is even do */ - while (MP_IS_EVEN(&u)) { + while (mp_iseven(&u)) { /* 4.1 u = u/2 */ if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; /* 4.2 if A or B is odd then */ - if (MP_IS_ODD(&A) || MP_IS_ODD(&B)) { + if (mp_isodd(&A) || mp_isodd(&B)) { /* A = (A+y)/2, B = (B-x)/2 */ if ((err = mp_add(&A, &y, &A)) != MP_OKAY) goto LBL_ERR; if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; @@ -54,12 +54,12 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) } /* 5. while v is even do */ - while (MP_IS_EVEN(&v)) { + while (mp_iseven(&v)) { /* 5.1 v = v/2 */ if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; /* 5.2 if C or D is odd then */ - if (MP_IS_ODD(&C) || MP_IS_ODD(&D)) { + if (mp_isodd(&C) || mp_isodd(&D)) { /* C = (C+y)/2, D = (D-x)/2 */ if ((err = mp_add(&C, &y, &C)) != MP_OKAY) goto LBL_ERR; if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; @@ -87,7 +87,7 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) } /* if not zero goto step 4 */ - if (!MP_IS_ZERO(&u)) { + if (!mp_iszero(&u)) { goto top; } diff --git a/tommath_private.h b/tommath_private.h index e26025f24..07a898526 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -1,3 +1,4 @@ + /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -149,11 +150,6 @@ extern void MP_FREE(void *mem, size_t size); /* Static assertion */ #define MP_STATIC_ASSERT(msg, cond) typedef char mp_static_assert_##msg[(cond) ? 1 : -1]; -/* ---> Basic Manipulations <--- */ -#define MP_IS_ZERO(a) ((a)->used == 0) -#define MP_IS_EVEN(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u)) -#define MP_IS_ODD(a) (((a)->used > 0) && (((a)->dp[0] & 1u) == 1u)) - #define MP_SIZEOF_BITS(type) ((size_t)CHAR_BIT * sizeof(type)) #define MP_MAXFAST (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) From 27e142bc438e6868478015c2e3d13c76d520df7a Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 17:52:03 +0200 Subject: [PATCH 069/304] remove unnecessary == MP_YES/MP_NO comparisons --- demo/test.c | 28 ++++++++++++++-------------- demo/timing.c | 2 +- etc/2kprime.c | 8 ++++---- etc/drprime.c | 8 ++++---- etc/mersenne.c | 6 +++--- mp_exptmod.c | 6 +++--- mp_is_square.c | 2 +- mp_prime_frobenius_underwood.c | 2 +- mp_prime_is_prime.c | 16 ++++++++-------- mp_prime_next_prime.c | 8 ++++---- mp_prime_rand.c | 4 ++-- mp_prime_strong_lucas_selfridge.c | 10 +++++----- mp_reduce_is_2k_l.c | 2 +- s_mp_get_bit.c | 2 +- tommath.h | 8 ++++---- 15 files changed, 56 insertions(+), 56 deletions(-) diff --git a/demo/test.c b/demo/test.c index 41c4182da..3cd3e3b24 100644 --- a/demo/test.c +++ b/demo/test.c @@ -120,12 +120,12 @@ static int test_trivial_stuff(void) } /* a: -5-> b: 5 */ mp_abs(&a, &b); - if (mp_isneg(&b) != MP_NO) { + if (mp_isneg(&b)) { goto LBL_ERR; } /* a: -5-> b: -4 */ mp_add_d(&a, 1uL, &b); - if (mp_isneg(&b) != MP_YES) { + if (!mp_isneg(&b)) { goto LBL_ERR; } if (mp_get_i32(&b) != -4) { @@ -841,7 +841,7 @@ static int test_mp_is_square(void) printf("\nfn:mp_is_square() error!"); goto LBL_ERR; } - if (res == MP_NO) { + if (!res) { printf("\nfn:mp_is_square() bad result!"); goto LBL_ERR; } @@ -852,7 +852,7 @@ static int test_mp_is_square(void) printf("\nfp:mp_is_square() error!"); goto LBL_ERR; } - if (res == MP_YES) { + if (res) { printf("\nfp:mp_is_square() bad result!"); goto LBL_ERR; } @@ -958,7 +958,7 @@ static int test_mp_prime_is_prime(void) "91xLNF3roobhzgTzoFIG6P13ZqhOVYSN60Fa7Cj2jVR1g0k89zdahO9/kAiRprpfO1VAp1aBHucLFV/qLKLFb+zonV7R2Vxp1K13ClwUXStpV0oxTNQVjwybmFb5NBEHImZ6V7P6+udRJuH8VbMEnS0H8/pSqQrg82OoQQ2fPpAk6G1hkjqoCv5s/Yr", 64); mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt); - if (cnt == MP_YES) { + if (cnt) { printf("Arnault's pseudoprime is not prime but mp_prime_is_prime says it is.\n"); goto LBL_ERR; } @@ -973,10 +973,10 @@ static int test_mp_prime_is_prime(void) printf("\nfailed with error: %s\n", mp_error_to_string(err)); } /* large problem */ - if (cnt == MP_NO) { + if (!cnt) { printf("A certified prime is a prime but mp_prime_is_prime says it is not.\n"); } - if ((err != MP_OKAY) || (cnt == MP_NO)) { + if ((err != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); mp_fwrite(&a,16,stdout); putchar('\n'); @@ -1003,14 +1003,14 @@ static int test_mp_prime_is_prime(void) printf("\nfailed with error: %s\n", mp_error_to_string(err)); } /* large problem */ - if (cnt == MP_NO) { + if (!cnt) { printf("\nsub is not prime!\n"); } mp_prime_frobenius_underwood(&b, &fu); - if (fu == MP_NO) { + if (!fu) { printf("\nfrobenius-underwood says sub is not prime!\n"); } - if ((err != MP_OKAY) || (cnt == MP_NO)) { + if ((err != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); mp_fwrite(&a,16,stdout); putchar('\n'); @@ -1031,10 +1031,10 @@ static int test_mp_prime_is_prime(void) printf("\nmp_prime_strong_lucas_selfridge failed with error: %s\n", mp_error_to_string(err)); } /* large problem */ - if (cnt == MP_NO) { + if (!cnt) { printf("\n\nissue #143 - mp_prime_strong_lucas_selfridge FAILED!\n"); } - if ((err != MP_OKAY) || (cnt == MP_NO)) { + if ((err != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); mp_fwrite(&a,16,stdout); putchar('\n'); @@ -1534,7 +1534,7 @@ static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) mp_int t; mp_digit d; *size = 0u; - if (mp_iszero(a) == MP_YES) { + if (mp_iszero(a)) { *size = 2u; return MP_OKAY; } @@ -1546,7 +1546,7 @@ static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) return res; } t.sign = MP_ZPOS; - while (mp_iszero(&t) == MP_NO) { + while (!mp_iszero(&t)) { if ((res = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { mp_clear(&t); return res; diff --git a/demo/timing.c b/demo/timing.c index a421f8de8..fa5669c72 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -173,7 +173,7 @@ int main(int argc, char **argv) gg = (TIMFUNC() - gg) >> 1; if (tt > gg) tt = gg; - if ((m == 0) && (n == MP_YES)) { + if ((m == 0) && n) { printf("Arnault's pseudoprime is not prime but mp_prime_is_prime says it is.\n"); return EXIT_FAILURE; } diff --git a/etc/2kprime.c b/etc/2kprime.c index 95ed2de42..6069e572e 100644 --- a/etc/2kprime.c +++ b/etc/2kprime.c @@ -43,7 +43,7 @@ int main(void) /* quick test on q */ mp_prime_is_prime(&q, 1, &y); - if (y == MP_NO) { + if (!y) { continue; } @@ -51,20 +51,20 @@ int main(void) mp_sub_d(&q, 1uL, &p); mp_div_2(&p, &p); mp_prime_is_prime(&p, 3, &y); - if (y == MP_NO) { + if (!y) { continue; } /* test on q */ mp_prime_is_prime(&q, 3, &y); - if (y == MP_NO) { + if (!y) { continue; } break; } - if (y == MP_NO) { + if (!y) { ++sizes[x]; goto top; } diff --git a/etc/drprime.c b/etc/drprime.c index 64e31ef10..6edb9659e 100644 --- a/etc/drprime.c +++ b/etc/drprime.c @@ -35,18 +35,18 @@ int main(void) a.dp[0] += 4uL; if (a.dp[0] >= MP_MASK) break; mp_prime_is_prime(&a, 1, &res); - if (res == MP_NO) continue; + if (!res) continue; printf("."); fflush(stdout); mp_sub_d(&a, 1uL, &b); mp_div_2(&b, &b); mp_prime_is_prime(&b, 3, &res); - if (res == MP_NO) continue; + if (!res) continue; mp_prime_is_prime(&a, 3, &res); - if (res == MP_YES) break; + if (res) break; } - if (res != MP_YES) { + if (!res) { printf("Error not DR modulus\n"); sizes[x] += 1; goto top; diff --git a/etc/mersenne.c b/etc/mersenne.c index 0c9f52fcf..e2159d142 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -56,9 +56,9 @@ static mp_err is_mersenne(long s, mp_bool *pp) } /* if u == 0 then its prime */ - if (mp_iszero(&u) == MP_YES) { + if (mp_iszero(&u)) { mp_prime_is_prime(&n, 8, pp); - if (*pp != MP_YES) printf("FAILURE\n"); + if (!*pp) printf("FAILURE\n"); } res = MP_OKAY; @@ -119,7 +119,7 @@ int main(void) return -1; } - if (pp == MP_YES) { + if (pp) { /* count time */ tt = clock() - tt; diff --git a/mp_exptmod.c b/mp_exptmod.c index 8f8a9e977..e643ded2e 100644 --- a/mp_exptmod.c +++ b/mp_exptmod.c @@ -49,16 +49,16 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) /* modified diminished radix reduction */ if (MP_HAS(MP_REDUCE_IS_2K_L) && MP_HAS(MP_REDUCE_2K_L) && MP_HAS(S_MP_EXPTMOD) && - (mp_reduce_is_2k_l(P) == MP_YES)) { + mp_reduce_is_2k_l(P)) { return s_mp_exptmod(G, X, P, Y, 1); } /* is it a DR modulus? default to no */ - dr = (MP_HAS(MP_DR_IS_MODULUS) && (mp_dr_is_modulus(P) == MP_YES)) ? 1 : 0; + dr = (MP_HAS(MP_DR_IS_MODULUS) && mp_dr_is_modulus(P)) ? 1 : 0; /* if not, is it a unrestricted DR modulus? */ if (MP_HAS(MP_REDUCE_IS_2K) && (dr == 0)) { - dr = (mp_reduce_is_2k(P) == MP_YES) ? 2 : 0; + dr = (mp_reduce_is_2k(P)) ? 2 : 0; } /* if the modulus is odd or dr != 0 use the montgomery method */ diff --git a/mp_is_square.c b/mp_is_square.c index f1df73ee0..0f9cd1f3f 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -85,7 +85,7 @@ mp_err mp_is_square(const mp_int *arg, mp_bool *ret) goto LBL_ERR; } - *ret = (mp_cmp_mag(&t, arg) == MP_EQ) ? MP_YES : MP_NO; + *ret = (mp_cmp_mag(&t, arg) == MP_EQ); LBL_ERR: mp_clear(&t); return err; diff --git a/mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c index bb56ea75e..0eaa36d44 100644 --- a/mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -92,7 +92,7 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) if ((err = mp_mul(&sz, &T2z, &tz)) != MP_OKAY) goto LBL_FU_ERR; if ((err = mp_mod(&tz, N, &tz)) != MP_OKAY) goto LBL_FU_ERR; if ((err = mp_mod(&T1z, N, &sz)) != MP_OKAY) goto LBL_FU_ERR; - if (s_mp_get_bit(&Np1z, (unsigned int)i) == MP_YES) { + if (s_mp_get_bit(&Np1z, (unsigned int)i)) { /* * temp = (a+2) * sz + tz * tz = 2 * tz - sz diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index e4f92146d..42d417e09 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -46,7 +46,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err = mp_is_square(a, &res)) != MP_OKAY) { return err; } - if (res != MP_NO) { + if (res) { return MP_OKAY; } @@ -63,7 +63,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) } /* return if it was trivially divisible */ - if (res == MP_YES) { + if (res) { return MP_OKAY; } @@ -77,7 +77,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err = mp_prime_miller_rabin(a, &b, &res)) != MP_OKAY) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } /* @@ -89,7 +89,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err = mp_prime_miller_rabin(a, &b, &res)) != MP_OKAY) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } @@ -105,14 +105,14 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err != MP_OKAY) && (err != MP_ITER)) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } #else if ((err = mp_prime_strong_lucas_selfridge(a, &res)) != MP_OKAY) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } #endif @@ -164,7 +164,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err = mp_prime_miller_rabin(a, &b, &res)) != MP_OKAY) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } } @@ -260,7 +260,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) if ((err = mp_prime_miller_rabin(a, &b, &res)) != MP_OKAY) { goto LBL_B; } - if (res == MP_NO) { + if (!res) { goto LBL_B; } } diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index c8f76036a..2165e3c63 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -29,7 +29,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) continue; } if (cmp != MP_GT) { - if ((bbs_style == MP_YES) && ((s_mp_prime_tab[x] & 3u) != 3u)) { + if ((bbs_style) && ((s_mp_prime_tab[x] & 3u) != 3u)) { /* try again until we get a prime congruent to 3 mod 4 */ continue; } else { @@ -42,7 +42,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) } /* generate a prime congruent to 3 mod 4 or 1/3 mod 4? */ - if (bbs_style == MP_YES) { + if (bbs_style) { kstep = 4; } else { kstep = 2; @@ -50,7 +50,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) /* at this point we will use a combination of a sieve and Miller-Rabin */ - if (bbs_style == MP_YES) { + if (bbs_style) { /* if a mod 4 != 3 subtract the correct value to make it so */ if ((a->dp[0] & 3u) != 3u) { if ((err = mp_sub_d(a, (a->dp[0] & 3u) + 1u, a)) != MP_OKAY) { @@ -118,7 +118,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { goto LBL_ERR; } - if (res == MP_YES) { + if (res) { break; } } diff --git a/mp_prime_rand.c b/mp_prime_rand.c index b37089b17..2ee8e74e1 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -85,7 +85,7 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { goto error; } - if (res == MP_NO) { + if (!res) { continue; } @@ -103,7 +103,7 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call goto error; } } - } while (res == MP_NO); + } while (!res); if ((flags & MP_PRIME_SAFE) != 0) { /* restore a to the original value */ diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index 0aee33de9..a0476517f 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -192,7 +192,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) if ((err = mp_mod(&Qmz, a, &Qmz)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mul_2(&Qmz, &Q2mz)) != MP_OKAY) goto LBL_LS_ERR; - if (s_mp_get_bit(&Dz, (unsigned int)u) == MP_YES) { + if (s_mp_get_bit(&Dz, (unsigned int)u)) { /* Formulas for addition of indices (carried out mod N); * * U_(m+n) = (U_m*V_n + U_n*V_m)/2 @@ -214,18 +214,18 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) * Thomas R. Nicely used GMP's mpz_fdiv_q_2exp(). * But mp_div_2() does not do so, it is truncating instead. */ - oddness = mp_isodd(&Uz) ? MP_YES : MP_NO; + oddness = mp_isodd(&Uz); if ((err = mp_div_2(&Uz, &Uz)) != MP_OKAY) goto LBL_LS_ERR; - if ((Uz.sign == MP_NEG) && (oddness != MP_NO)) { + if ((Uz.sign == MP_NEG) && oddness) { if ((err = mp_sub_d(&Uz, 1uL, &Uz)) != MP_OKAY) goto LBL_LS_ERR; } if ((err = mp_add(&T3z, &T4z, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if (mp_isodd(&Vz)) { if ((err = mp_add(&Vz, a, &Vz)) != MP_OKAY) goto LBL_LS_ERR; } - oddness = mp_isodd(&Vz) ? MP_YES : MP_NO; + oddness = mp_isodd(&Vz); if ((err = mp_div_2(&Vz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; - if ((Vz.sign == MP_NEG) && (oddness != MP_NO)) { + if ((Vz.sign == MP_NEG) && oddness) { if ((err = mp_sub_d(&Vz, 1uL, &Vz)) != MP_OKAY) goto LBL_LS_ERR; } if ((err = mp_mod(&Uz, a, &Uz)) != MP_OKAY) goto LBL_LS_ERR; diff --git a/mp_reduce_is_2k_l.c b/mp_reduce_is_2k_l.c index 1aa3d4e0c..cd6fc6294 100644 --- a/mp_reduce_is_2k_l.c +++ b/mp_reduce_is_2k_l.c @@ -19,7 +19,7 @@ mp_bool mp_reduce_is_2k_l(const mp_int *a) ++iy; } } - return (iy >= (a->used/2)) ? MP_YES : MP_NO; + return (iy >= (a->used/2)); } else { return MP_NO; } diff --git a/s_mp_get_bit.c b/s_mp_get_bit.c index 397499cbb..5114e9ec0 100644 --- a/s_mp_get_bit.c +++ b/s_mp_get_bit.c @@ -15,7 +15,7 @@ mp_bool s_mp_get_bit(const mp_int *a, unsigned int b) } bit = (mp_digit)1 << (b % MP_DIGIT_BIT); - return ((a->dp[limb] & bit) != 0u) ? MP_YES : MP_NO; + return ((a->dp[limb] & bit) != 0u); } #endif diff --git a/tommath.h b/tommath.h index 5d0d2fe6f..9a31bd3e9 100644 --- a/tommath.h +++ b/tommath.h @@ -208,10 +208,10 @@ mp_err mp_grow(mp_int *a, int size) MP_WUR; mp_err mp_init_size(mp_int *a, int size) MP_WUR; /* ---> Basic Manipulations <--- */ -#define mp_iszero(a) (((a)->used == 0) ? MP_YES : MP_NO) -#define mp_isneg(a) (((a)->sign != MP_ZPOS) ? MP_YES : MP_NO) -#define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u) ? MP_YES : MP_NO) -#define mp_isodd(a) (((a)->used > 0) && (((a)->dp[0] & 1u) == 1u) ? MP_YES : MP_NO) +#define mp_iszero(a) ((a)->used == 0) +#define mp_isneg(a) ((a)->sign != MP_ZPOS) +#define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u)) +#define mp_isodd(a) (((a)->used > 0) && (((a)->dp[0] & 1u) == 1u)) /* set to zero */ void mp_zero(mp_int *a); From 58fb93fd790974cedb670f115b8f05c715eca57b Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 18:14:18 +0200 Subject: [PATCH 070/304] cleanup prime rand function --- mp_prime_rand.c | 40 +++++++++++----------------------------- tommath_private.h | 5 ----- 2 files changed, 11 insertions(+), 34 deletions(-) diff --git a/mp_prime_rand.c b/mp_prime_rand.c index 2ee8e74e1..cc19fa273 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -18,7 +18,7 @@ */ /* This is possibly the mother of all prime generation functions, muahahahahaha! */ -mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat) +mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) { unsigned char *tmp, maskAND, maskOR_msb, maskOR_lsb; int bsize, maskOR_msb_offset; @@ -62,9 +62,8 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call do { /* read the bytes */ - if (cb(tmp, bsize, dat) != bsize) { - err = MP_VAL; - goto error; + if ((err = s_mp_rand_source(tmp, (size_t)bsize)) != MP_OKAY) { + goto LBL_ERR; } /* work over the MSbyte */ @@ -78,12 +77,12 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call /* read it in */ /* TODO: casting only for now until all lengths have been changed to the type "size_t"*/ if ((err = mp_from_ubin(a, tmp, (size_t)bsize)) != MP_OKAY) { - goto error; + goto LBL_ERR; } /* is it prime? */ if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { - goto error; + goto LBL_ERR; } if (!res) { continue; @@ -92,15 +91,15 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call if ((flags & MP_PRIME_SAFE) != 0) { /* see if (a-1)/2 is prime */ if ((err = mp_sub_d(a, 1uL, a)) != MP_OKAY) { - goto error; + goto LBL_ERR; } if ((err = mp_div_2(a, a)) != MP_OKAY) { - goto error; + goto LBL_ERR; } /* is it prime? */ if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { - goto error; + goto LBL_ERR; } } } while (!res); @@ -108,34 +107,17 @@ mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_call if ((flags & MP_PRIME_SAFE) != 0) { /* restore a to the original value */ if ((err = mp_mul_2(a, a)) != MP_OKAY) { - goto error; + goto LBL_ERR; } if ((err = mp_add_d(a, 1uL, a)) != MP_OKAY) { - goto error; + goto LBL_ERR; } } err = MP_OKAY; -error: +LBL_ERR: MP_FREE_BUFFER(tmp, (size_t)bsize); return err; } -static int s_mp_rand_cb(unsigned char *dst, int len, void *dat) -{ - (void)dat; - if (len <= 0) { - return len; - } - if (s_mp_rand_source(dst, (size_t)len) != MP_OKAY) { - return 0; - } - return len; -} - -mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) -{ - return s_mp_prime_random_ex(a, t, size, flags, s_mp_rand_cb, NULL); -} - #endif diff --git a/tommath_private.h b/tommath_private.h index 07a898526..8b30c6705 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -1,4 +1,3 @@ - /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -203,14 +202,10 @@ MP_PRIVATE mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_dig MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; -typedef int mp_prime_callback(unsigned char *dst, int len, void *dat); -MP_PRIVATE mp_err s_mp_prime_random_ex(mp_int *a, int t, int size, int flags, mp_prime_callback cb, void *dat); MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base); - - MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r); MP_PRIVATE mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); From c91c1ba2b109e0487c7825ef26e173a075f47611 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 21:32:31 +0200 Subject: [PATCH 071/304] rework mp_add_d and mp_sub_d --- mp_add_d.c | 18 ++++++++++++------ mp_sub_d.c | 17 +++++++++++------ 2 files changed, 23 insertions(+), 12 deletions(-) diff --git a/mp_add_d.c b/mp_add_d.c index cd0d47a94..4508cc87b 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -11,12 +11,18 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) mp_digit *tmpa, *tmpc; /* fast path for a == c */ - if (a == c && - !mp_iszero(c) && - c->sign == MP_ZPOS && - c->dp[0] + b < MP_DIGIT_MAX) { - c->dp[0] += b; - return MP_OKAY; + if (a == c) { + if ((c->sign == MP_ZPOS) && + !mp_iszero(c) && + ((c->dp[0] + b) < MP_DIGIT_MAX)) { + c->dp[0] += b; + return MP_OKAY; + } + if ((c->sign == MP_NEG) && + (c->dp[0] > b)) { + c->dp[0] -= b; + return MP_OKAY; + } } /* grow c as required */ diff --git a/mp_sub_d.c b/mp_sub_d.c index e453d36ed..96a747cb6 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -11,12 +11,17 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) int ix, oldused; /* fast path for a == c */ - if (a == c && - !mp_iszero(c) && - c->sign == MP_ZPOS && - c->dp[0] > b) { - c->dp[0] -= b; - return MP_OKAY; + if (a == c) { + if ((c->sign == MP_NEG) && + ((c->dp[0] + b) < MP_DIGIT_MAX)) { + c->dp[0] += b; + return MP_OKAY; + } + if ((c->sign == MP_ZPOS) && + (c->dp[0] > b)) { + c->dp[0] -= b; + return MP_OKAY; + } } /* grow c as required */ From bf9507a9d4cdd89ae779d1b5708f9abc7550ded5 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 22:02:29 +0200 Subject: [PATCH 072/304] replace mp_bool by stdbool * This gives the advantage that static analysis **understands** bool, but complains about using an enum type instead of bool. * If stdbool.h is not desired, true/false/bool can be replaced using sed as in the no-stdint-h branch. * We already include stdint.h and stdbool.h is not more harmful than this header --- demo/test.c | 20 ++++++++++---------- etc/2kprime.c | 2 +- etc/drprime.c | 4 ++-- etc/mersenne.c | 6 +++--- mp_dr_is_modulus.c | 8 ++++---- mp_is_square.c | 4 ++-- mp_prime_fermat.c | 6 +++--- mp_prime_frobenius_underwood.c | 6 +++--- mp_prime_is_prime.c | 14 +++++++------- mp_prime_miller_rabin.c | 6 +++--- mp_prime_next_prime.c | 6 +++--- mp_prime_rand.c | 2 +- mp_prime_strong_lucas_selfridge.c | 12 ++++++------ mp_reduce_is_2k.c | 12 ++++++------ mp_reduce_is_2k_l.c | 8 ++++---- s_mp_get_bit.c | 6 +++--- s_mp_prime_is_divisible.c | 6 +++--- tommath.h | 29 ++++++++++++----------------- tommath_private.h | 4 ++-- 19 files changed, 78 insertions(+), 83 deletions(-) diff --git a/demo/test.c b/demo/test.c index 3cd3e3b24..0d9b07303 100644 --- a/demo/test.c +++ b/demo/test.c @@ -823,7 +823,7 @@ static int test_mp_is_square(void) int i, n; mp_int a, b; - mp_bool res; + bool res; if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { return EXIT_FAILURE; @@ -945,7 +945,7 @@ static int test_mp_prime_is_prime(void) { int ix; mp_err err; - mp_bool cnt, fu; + bool cnt, fu; mp_int a, b; if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { @@ -1061,7 +1061,7 @@ static int test_mp_prime_next_prime(void) /* edge cases */ mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 2u) != MP_EQ) { @@ -1072,7 +1072,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1083,7 +1083,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1094,7 +1094,7 @@ static int test_mp_prime_next_prime(void) } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 3u) != MP_EQ) { @@ -1104,7 +1104,7 @@ static int test_mp_prime_next_prime(void) goto LBL_ERR; } mp_set(&a, 8); - if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp_d(&a, 11u) != MP_EQ) { @@ -1130,7 +1130,7 @@ static int test_mp_prime_next_prime(void) if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { goto LBL_ERR; } - if ((err = mp_prime_next_prime(&a, 5, MP_NO)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { @@ -1160,7 +1160,7 @@ static int test_mp_prime_next_prime(void) if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { goto LBL_ERR; } - if ((err = mp_prime_next_prime(&a, 5, MP_YES)) != MP_OKAY) { + if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { goto LBL_ERR; } if (mp_cmp(&a, &b) != MP_EQ) { @@ -1284,7 +1284,7 @@ static int test_mp_read_radix(void) char *s = fgets(buf, sizeof(buf), stdin); if (s != buf) break; mp_read_radix(&a, buf, 10); - mp_prime_next_prime(&a, 5, MP_YES); + mp_prime_next_prime(&a, 5, true); mp_to_radix(&a, buf, sizeof(buf), NULL, 10); printf("%s, %lu\n", buf, (unsigned long)a.dp[0] & 3uL); } diff --git a/etc/2kprime.c b/etc/2kprime.c index 6069e572e..3a3e28307 100644 --- a/etc/2kprime.c +++ b/etc/2kprime.c @@ -8,7 +8,7 @@ int main(void) { char buf[2000]; size_t x; - mp_bool y; + bool y; mp_int q, p; FILE *out; clock_t t1; diff --git a/etc/drprime.c b/etc/drprime.c index 6edb9659e..31dff4e99 100644 --- a/etc/drprime.c +++ b/etc/drprime.c @@ -5,7 +5,7 @@ static int sizes[] = { 1+256/MP_DIGIT_BIT, 1+512/MP_DIGIT_BIT, 1+768/MP_DIGIT_BI int main(void) { - mp_bool res; + bool res; int x, y; char buf[4096]; FILE *out; @@ -30,7 +30,7 @@ int main(void) a.used = sizes[x]; /* now loop */ - res = MP_NO; + res = false; for (;;) { a.dp[0] += 4uL; if (a.dp[0] >= MP_MASK) break; diff --git a/etc/mersenne.c b/etc/mersenne.c index e2159d142..54b2360cc 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -5,13 +5,13 @@ #include #include -static mp_err is_mersenne(long s, mp_bool *pp) +static mp_err is_mersenne(long s, bool *pp) { mp_int n, u; mp_err res; int k; - *pp = MP_NO; + *pp = false; if ((res = mp_init(&n)) != MP_OKAY) { return res; @@ -103,7 +103,7 @@ static int isprime(long k) int main(void) { - mp_bool pp; + bool pp; long k; clock_t tt; diff --git a/mp_dr_is_modulus.c b/mp_dr_is_modulus.c index eed5e5f89..72b3c9681 100644 --- a/mp_dr_is_modulus.c +++ b/mp_dr_is_modulus.c @@ -4,13 +4,13 @@ /* SPDX-License-Identifier: Unlicense */ /* determines if a number is a valid DR modulus */ -mp_bool mp_dr_is_modulus(const mp_int *a) +bool mp_dr_is_modulus(const mp_int *a) { int ix; /* must be at least two digits */ if (a->used < 2) { - return MP_NO; + return false; } /* must be of the form b**k - a [a <= b] so all @@ -18,10 +18,10 @@ mp_bool mp_dr_is_modulus(const mp_int *a) */ for (ix = 1; ix < a->used; ix++) { if (a->dp[ix] != MP_MASK) { - return MP_NO; + return false; } } - return MP_YES; + return true; } #endif diff --git a/mp_is_square.c b/mp_is_square.c index 0f9cd1f3f..f92ecbfb8 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -26,7 +26,7 @@ static const char rem_105[105] = { }; /* Store non-zero to ret if arg is square, and zero if not */ -mp_err mp_is_square(const mp_int *arg, mp_bool *ret) +mp_err mp_is_square(const mp_int *arg, bool *ret) { mp_err err; mp_digit c; @@ -34,7 +34,7 @@ mp_err mp_is_square(const mp_int *arg, mp_bool *ret) unsigned long r; /* Default to Non-square :) */ - *ret = MP_NO; + *ret = false; if (arg->sign == MP_NEG) { return MP_VAL; diff --git a/mp_prime_fermat.c b/mp_prime_fermat.c index c6bc720f8..50d2e5ea1 100644 --- a/mp_prime_fermat.c +++ b/mp_prime_fermat.c @@ -11,13 +11,13 @@ * * Sets result to 1 if the congruence holds, or zero otherwise. */ -mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, mp_bool *result) +mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, bool *result) { mp_int t; mp_err err; /* default to composite */ - *result = MP_NO; + *result = false; /* ensure b > 1 */ if (mp_cmp_d(b, 1uL) != MP_GT) { @@ -36,7 +36,7 @@ mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, mp_bool *result) /* is it equal to b? */ if (mp_cmp(&t, b) == MP_EQ) { - *result = MP_YES; + *result = true; } err = MP_OKAY; diff --git a/mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c index 0eaa36d44..543b8b4a2 100644 --- a/mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -20,14 +20,14 @@ */ #define LTM_FROBENIUS_UNDERWOOD_A 32764 -mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) +mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) { mp_int T1z, T2z, Np1z, sz, tz; int a, ap2, length, i, j; mp_err err; - *result = MP_NO; + *result = false; if ((err = mp_init_multi(&T1z, &T2z, &Np1z, &sz, &tz, NULL)) != MP_OKAY) { return err; @@ -113,7 +113,7 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) mp_set_u32(&T1z, (uint32_t)((2 * a) + 5)); if ((err = mp_mod(&T1z, N, &T1z)) != MP_OKAY) goto LBL_FU_ERR; if (mp_iszero(&sz) && (mp_cmp(&tz, &T1z) == MP_EQ)) { - *result = MP_YES; + *result = true; } LBL_FU_ERR: diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index 42d417e09..d0eca2c28 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -14,26 +14,26 @@ static unsigned int s_floor_ilog2(int value) } -mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) +mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) { mp_int b; int ix, p_max = 0, size_a, len; - mp_bool res; + bool res; mp_err err; unsigned int fips_rand, mask; /* default to no */ - *result = MP_NO; + *result = false; /* Some shortcuts */ /* N > 3 */ if (a->used == 1) { if ((a->dp[0] == 0u) || (a->dp[0] == 1u)) { - *result = MP_NO; + *result = false; return MP_OKAY; } if (a->dp[0] == 2u) { - *result = MP_YES; + *result = true; return MP_OKAY; } } @@ -53,7 +53,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) /* is the input equal to one of the primes in the table? */ for (ix = 0; ix < MP_PRIME_TAB_SIZE; ix++) { if (mp_cmp_d(a, s_mp_prime_tab[ix]) == MP_EQ) { - *result = MP_YES; + *result = true; return MP_OKAY; } } @@ -267,7 +267,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) } /* passed the test */ - *result = MP_YES; + *result = true; LBL_B: mp_clear(&b); return err; diff --git a/mp_prime_miller_rabin.c b/mp_prime_miller_rabin.c index f6d698b9c..a3af8bc8b 100644 --- a/mp_prime_miller_rabin.c +++ b/mp_prime_miller_rabin.c @@ -10,14 +10,14 @@ * Randomly the chance of error is no more than 1/4 and often * very much lower. */ -mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, mp_bool *result) +mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) { mp_int n1, y, r; mp_err err; int s, j; /* default */ - *result = MP_NO; + *result = false; /* ensure b > 1 */ if (mp_cmp_d(b, 1uL) != MP_GT) { @@ -79,7 +79,7 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, mp_bool *result) } /* probably prime now */ - *result = MP_YES; + *result = true; LBL_Y: mp_clear(&y); LBL_R: diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index 2165e3c63..40c94a4cf 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -6,14 +6,14 @@ /* finds the next prime after the number "a" using "t" trials * of Miller-Rabin. * - * bbs_style = MP_YES means the prime must be congruent to 3 mod 4 + * bbs_style = true means the prime must be congruent to 3 mod 4 */ -mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) +mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) { int x, y; mp_ord cmp; mp_err err; - mp_bool res = MP_NO; + bool res = false; mp_digit res_tab[MP_PRIME_TAB_SIZE], step, kstep; mp_int b; diff --git a/mp_prime_rand.c b/mp_prime_rand.c index cc19fa273..ff6df9c39 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -22,7 +22,7 @@ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) { unsigned char *tmp, maskAND, maskOR_msb, maskOR_lsb; int bsize, maskOR_msb_offset; - mp_bool res; + bool res; mp_err err; /* sanity check the input */ diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index a0476517f..df5de9637 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -33,7 +33,7 @@ static mp_err s_mp_mul_si(const mp_int *a, int32_t d, mp_int *c) } /* Strong Lucas-Selfridge test. - returns MP_YES if it is a strong L-S prime, MP_NO if it is composite + returns true if it is a strong L-S prime, false if it is composite Code ported from Thomas Ray Nicely's implementation of the BPSW test at http://www.trnicely.net/misc/bpsw.html @@ -48,15 +48,15 @@ static mp_err s_mp_mul_si(const mp_int *a, int32_t d, mp_int *c) (If that name sounds familiar, he is the guy who found the fdiv bug in the Pentium (P5x, I think) Intel processor) */ -mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) +mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) { /* CZ TODO: choose better variable names! */ mp_int Dz, gcd, Np1, Uz, Vz, U2mz, V2mz, Qmz, Q2mz, Qkdz, T1z, T2z, T3z, T4z, Q2kdz; int32_t D, Ds, J, sign, P, Q, r, s, u, Nbits; mp_err err; - mp_bool oddness; + bool oddness; - *result = MP_NO; + *result = false; /* Find the first element D in the sequence {5, -7, 9, -11, 13, ...} such that Jacobi(D,N) = -1 (Selfridge's algorithm). Theory @@ -240,7 +240,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) /* If U_d or V_d is congruent to 0 mod N, then N is a prime or a strong Lucas pseudoprime. */ if (mp_iszero(&Uz) || mp_iszero(&Vz)) { - *result = MP_YES; + *result = true; goto LBL_LS_ERR; } @@ -263,7 +263,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) if ((err = mp_sub(&Vz, &Q2kdz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mod(&Vz, a, &Vz)) != MP_OKAY) goto LBL_LS_ERR; if (mp_iszero(&Vz)) { - *result = MP_YES; + *result = true; goto LBL_LS_ERR; } /* Calculate Q^{d*2^r} for next r (final iteration irrelevant). */ diff --git a/mp_reduce_is_2k.c b/mp_reduce_is_2k.c index ec1233861..618ab54ab 100644 --- a/mp_reduce_is_2k.c +++ b/mp_reduce_is_2k.c @@ -4,15 +4,15 @@ /* SPDX-License-Identifier: Unlicense */ /* determines if mp_reduce_2k can be used */ -mp_bool mp_reduce_is_2k(const mp_int *a) +bool mp_reduce_is_2k(const mp_int *a) { int ix, iy, iw; mp_digit iz; if (a->used == 0) { - return MP_NO; + return false; } else if (a->used == 1) { - return MP_YES; + return true; } else if (a->used > 1) { iy = mp_count_bits(a); iz = 1; @@ -21,7 +21,7 @@ mp_bool mp_reduce_is_2k(const mp_int *a) /* Test every bit from the second digit up, must be 1 */ for (ix = MP_DIGIT_BIT; ix < iy; ix++) { if ((a->dp[iw] & iz) == 0u) { - return MP_NO; + return false; } iz <<= 1; if (iz > MP_DIGIT_MAX) { @@ -29,9 +29,9 @@ mp_bool mp_reduce_is_2k(const mp_int *a) iz = 1; } } - return MP_YES; + return true; } else { - return MP_YES; + return true; } } diff --git a/mp_reduce_is_2k_l.c b/mp_reduce_is_2k_l.c index cd6fc6294..30fc10d0c 100644 --- a/mp_reduce_is_2k_l.c +++ b/mp_reduce_is_2k_l.c @@ -4,14 +4,14 @@ /* SPDX-License-Identifier: Unlicense */ /* determines if reduce_2k_l can be used */ -mp_bool mp_reduce_is_2k_l(const mp_int *a) +bool mp_reduce_is_2k_l(const mp_int *a) { int ix, iy; if (a->used == 0) { - return MP_NO; + return false; } else if (a->used == 1) { - return MP_YES; + return true; } else if (a->used > 1) { /* if more than half of the digits are -1 we're sold */ for (iy = ix = 0; ix < a->used; ix++) { @@ -21,7 +21,7 @@ mp_bool mp_reduce_is_2k_l(const mp_int *a) } return (iy >= (a->used/2)); } else { - return MP_NO; + return false; } } diff --git a/s_mp_get_bit.c b/s_mp_get_bit.c index 5114e9ec0..f077f613c 100644 --- a/s_mp_get_bit.c +++ b/s_mp_get_bit.c @@ -4,14 +4,14 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* Get bit at position b and return MP_YES if the bit is 1, MP_NO if it is 0 */ -mp_bool s_mp_get_bit(const mp_int *a, unsigned int b) +/* Get bit at position b and return true if the bit is 1, false if it is 0 */ +bool s_mp_get_bit(const mp_int *a, unsigned int b) { mp_digit bit; int limb = (int)(b / MP_DIGIT_BIT); if (limb >= a->used) { - return MP_NO; + return false; } bit = (mp_digit)1 << (b % MP_DIGIT_BIT); diff --git a/s_mp_prime_is_divisible.c b/s_mp_prime_is_divisible.c index d8bdedc76..0cca5a6f1 100644 --- a/s_mp_prime_is_divisible.c +++ b/s_mp_prime_is_divisible.c @@ -8,14 +8,14 @@ * * sets result to 0 if not, 1 if yes */ -mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result) +mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result) { int ix; mp_err err; mp_digit res; /* default to not */ - *result = MP_NO; + *result = false; for (ix = 0; ix < MP_PRIME_TAB_SIZE; ix++) { /* what is a mod LBL_prime_tab[ix] */ @@ -25,7 +25,7 @@ mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result) /* is the residue zero? */ if (res == 0u) { - *result = MP_YES; + *result = true; return MP_OKAY; } } diff --git a/tommath.h b/tommath.h index 9a31bd3e9..a55c57f42 100644 --- a/tommath.h +++ b/tommath.h @@ -6,6 +6,7 @@ #include #include +#include #ifndef MP_NO_FILE # include @@ -93,11 +94,6 @@ typedef enum { MP_GT = 1 /* greater than */ } mp_ord; -typedef enum { - MP_NO = 0, - MP_YES = 1 -} mp_bool; - typedef enum { MP_OKAY = 0, /* no error */ MP_ERR = -1, /* unknown error */ @@ -119,7 +115,6 @@ typedef enum { } mp_endian; /* tunable cutoffs */ - #ifndef MP_FIXED_CUTOFFS extern int MP_KARATSUBA_MUL_CUTOFF, @@ -441,7 +436,7 @@ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) MP_WUR; mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) MP_WUR; /* is number a square? */ -mp_err mp_is_square(const mp_int *arg, mp_bool *ret) MP_WUR; +mp_err mp_is_square(const mp_int *arg, bool *ret) MP_WUR; /* computes the Kronecker symbol c = (a | p) (like jacobi() but with {a,p} in Z */ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) MP_WUR; @@ -468,7 +463,7 @@ mp_err mp_montgomery_calc_normalization(mp_int *a, const mp_int *b) MP_WUR; mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; /* returns 1 if a is a valid DR modulus */ -mp_bool mp_dr_is_modulus(const mp_int *a) MP_WUR; +bool mp_dr_is_modulus(const mp_int *a) MP_WUR; /* sets the value of "d" required for mp_dr_reduce */ void mp_dr_setup(const mp_int *a, mp_digit *d); @@ -477,7 +472,7 @@ void mp_dr_setup(const mp_int *a, mp_digit *d); mp_err mp_dr_reduce(mp_int *x, const mp_int *n, mp_digit k) MP_WUR; /* returns true if a can be reduced with mp_reduce_2k */ -mp_bool mp_reduce_is_2k(const mp_int *a) MP_WUR; +bool mp_reduce_is_2k(const mp_int *a) MP_WUR; /* determines k value for 2k reduction */ mp_err mp_reduce_2k_setup(const mp_int *a, mp_digit *d) MP_WUR; @@ -486,7 +481,7 @@ mp_err mp_reduce_2k_setup(const mp_int *a, mp_digit *d) MP_WUR; mp_err mp_reduce_2k(mp_int *a, const mp_int *n, mp_digit d) MP_WUR; /* returns true if a can be reduced with mp_reduce_2k_l */ -mp_bool mp_reduce_is_2k_l(const mp_int *a) MP_WUR; +bool mp_reduce_is_2k_l(const mp_int *a) MP_WUR; /* determines k value for 2k reduction */ mp_err mp_reduce_2k_setup_l(const mp_int *a, mp_int *d) MP_WUR; @@ -502,12 +497,12 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) /* performs one Fermat test of "a" using base "b". * Sets result to 0 if composite or 1 if probable prime */ -mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, mp_bool *result) MP_WUR; +mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, bool *result) MP_WUR; /* performs one Miller-Rabin test of "a" using base "b". * Sets result to 0 if composite or 1 if probable prime */ -mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, mp_bool *result) MP_WUR; +mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) MP_WUR; /* This gives [for a given bit size] the number of trials required * such that Miller-Rabin gives a prob of failure lower than 2^-96 @@ -517,12 +512,12 @@ int mp_prime_rabin_miller_trials(int size) MP_WUR; /* performs one strong Lucas-Selfridge test of "a". * Sets result to 0 if composite or 1 if probable prime */ -mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) MP_WUR; +mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) MP_WUR; /* performs one Frobenius test of "a" as described by Paul Underwood. * Sets result to 0 if composite or 1 if probable prime */ -mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) MP_WUR; +mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) MP_WUR; /* performs t random rounds of Miller-Rabin on "a" additional to * bases 2 and 3. Also performs an initial sieve of trial @@ -538,14 +533,14 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) MP_WUR; * * Sets result to 1 if probably prime, 0 otherwise */ -mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) MP_WUR; +mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) MP_WUR; /* finds the next prime after the number "a" using "t" trials * of Miller-Rabin. * - * bbs_style = MP_YES means the prime must be congruent to 3 mod 4 + * bbs_style = true means the prime must be congruent to 3 mod 4 */ -mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) MP_WUR; +mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) MP_WUR; /* makes a truly random prime of a given size (bits), * diff --git a/tommath_private.h b/tommath_private.h index 8b30c6705..2dbdca805 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -182,7 +182,7 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); /* lowlevel functions, do not call! */ -MP_PRIVATE mp_bool s_mp_get_bit(const mp_int *a, unsigned int b); +MP_PRIVATE bool s_mp_get_bit(const mp_int *a, unsigned int b); MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; @@ -202,7 +202,7 @@ MP_PRIVATE mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_dig MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; -MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, mp_bool *result); +MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result); MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base); From 9f01ba14bc450e869c70ac073bd27aac3231f0f5 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 26 Oct 2019 18:48:41 +0200 Subject: [PATCH 073/304] add "testme.sh --c89" and "make c89" * replace int*_t and bool by custom typedefs * the result is tested in CI --- .travis.yml | 1 + makefile | 23 +++++++++++++++++++++++ testme.sh | 6 ++++++ 3 files changed, 30 insertions(+) diff --git a/.travis.yml b/.travis.yml index 2f9461551..42960d058 100644 --- a/.travis.yml +++ b/.travis.yml @@ -140,6 +140,7 @@ matrix: # clang for x86-64 architecture (64-bit longs and 64-bit pointers) - env: SANITIZER=1 CONV_WARNINGS=relaxed BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --c89 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-6.0 --with-m64 --with-travis-valgrind' addons: apt: diff --git a/makefile b/makefile index 179176b29..be7ef0c21 100644 --- a/makefile +++ b/makefile @@ -152,6 +152,29 @@ new_file: perlcritic: perlcritic *.pl doc/*.pl +c89: + @echo "Applying substitutions for c89 compatibility..." + @sed -i \ + -e 's/#include //g' \ + -e 's/#include /#include "tommath_c89.h"/g' \ + -e 's/bool/mp_bool/g' \ + -e 's/true/MP_YES/g' \ + -e 's/false/MP_NO/g' \ + -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ + -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ + *.c *.h demo/*.c demo/*.h etc/*.c + @echo "/* please adapt this header to your needs */" > tommath_c89.h + @echo "typedef enum { MP_NO, MP_YES } mp_bool;" >> tommath_c89.h + @echo "typedef __INT8_TYPE__ mp_i8;" >> tommath_c89.h + @echo "typedef __INT16_TYPE__ mp_i16;" >> tommath_c89.h + @echo "typedef __INT32_TYPE__ mp_i32;" >> tommath_c89.h + @echo "typedef __INT64_TYPE__ mp_i64;" >> tommath_c89.h + @echo "typedef __UINT8_TYPE__ mp_u8;" >> tommath_c89.h + @echo "typedef __UINT16_TYPE__ mp_u16;" >> tommath_c89.h + @echo "typedef __UINT32_TYPE__ mp_u32;" >> tommath_c89.h + @echo "typedef __UINT64_TYPE__ mp_u64;" >> tommath_c89.h + + astyle: @echo " * run astyle on all sources" @astyle --options=astylerc --formatted $(OBJECTS:.o=.c) tommath*.h demo/*.c etc/*.c mtest/mtest.c diff --git a/testme.sh b/testme.sh index 2f7235f96..3375fa6cf 100755 --- a/testme.sh +++ b/testme.sh @@ -195,6 +195,7 @@ VALGRIND_OPTS=" --leak-check=full --show-leak-kinds=all --error-exitcode=1 " #VALGRIND_OPTS="" VALGRIND_BIN="" CHECK_FORMAT="" +C89="" TUNE_CMD="./etc/tune -t -r 10 -L 3" alive_pid=0 @@ -217,6 +218,9 @@ do "--with-m64" | "--with-m32" | "--with-mx32") ARCHFLAGS="$ARCHFLAGS ${1:6}" ;; + --c89) + C89="1" + ;; --with-cc=*) COMPILERS="$COMPILERS ${1#*=}" ;; @@ -291,6 +295,8 @@ function _check_git() { git diff-index --quiet HEAD -- . || ( echo "FAILURE: $*" && exit 1 ) } +[[ "$C89" == "1" ]] && make c89 + if [[ "$CHECK_FORMAT" == "1" ]] then make astyle From 17a846f2bc04ee012d13b93cd4d34316147f50ba Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sat, 26 Oct 2019 19:33:36 +0200 Subject: [PATCH 074/304] add "make c99" to convert back --- .travis.yml | 3 +++ makefile | 18 +++++++++++++++++- testme.sh | 12 ++++++++++++ tommath.h | 2 +- 4 files changed, 33 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 42960d058..738c62bd1 100644 --- a/.travis.yml +++ b/.travis.yml @@ -61,6 +61,9 @@ matrix: # We have only one program and the variable $BUILDOPTIONS # has only the options to that program: testme.sh + # Check c89 <-> c99 roundtrip + - env: BUILDOPTIONS='--c89-c99-roundtrip' + # Check source code format - env: BUILDOPTIONS='--format' addons: diff --git a/makefile b/makefile index be7ef0c21..c06849a86 100644 --- a/makefile +++ b/makefile @@ -154,8 +154,9 @@ perlcritic: c89: @echo "Applying substitutions for c89 compatibility..." + @if grep mp_bool tommath.h > /dev/null; then echo "Already applied"; exit 1; fi @sed -i \ - -e 's/#include //g' \ + -e '/#include /d' \ -e 's/#include /#include "tommath_c89.h"/g' \ -e 's/bool/mp_bool/g' \ -e 's/true/MP_YES/g' \ @@ -175,6 +176,21 @@ c89: @echo "typedef __UINT64_TYPE__ mp_u64;" >> tommath_c89.h +c99: + @echo "Applying substitutions for c99 compatibility..." + @if ! grep mp_bool tommath.h > /dev/null; then echo "Already applied"; exit 1; fi + @sed -i \ + -e 's/#include "tommath_c89.h"/#include \n#include /g' \ + -e 's/mp_bool/bool/g' \ + -e 's/MP_YES/true/g' \ + -e 's/MP_NO/false/g' \ + -e 's/false_/MP_NO_/g' \ + -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ + -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ + *.c *.h demo/*.c demo/*.h etc/*.c + @rm -f tommath_c89.h + + astyle: @echo " * run astyle on all sources" @astyle --options=astylerc --formatted $(OBJECTS:.o=.c) tommath*.h demo/*.c etc/*.c mtest/mtest.c diff --git a/testme.sh b/testme.sh index 3375fa6cf..6c71ac44f 100755 --- a/testme.sh +++ b/testme.sh @@ -196,6 +196,7 @@ VALGRIND_OPTS=" --leak-check=full --show-leak-kinds=all --error-exitcode=1 " VALGRIND_BIN="" CHECK_FORMAT="" C89="" +C89_C99_ROUNDTRIP="" TUNE_CMD="./etc/tune -t -r 10 -L 3" alive_pid=0 @@ -221,6 +222,9 @@ do --c89) C89="1" ;; + --c89-c99-roundtrip) + C89_C99_ROUNDTRIP="1" + ;; --with-cc=*) COMPILERS="$COMPILERS ${1#*=}" ;; @@ -297,6 +301,14 @@ function _check_git() { [[ "$C89" == "1" ]] && make c89 +if [[ "$C89_C99_ROUNDTRIP" == "1" ]] +then + make c89 + make c99 + _check_git "make c89; make c99" + exit $? +fi + if [[ "$CHECK_FORMAT" == "1" ]] then make astyle diff --git a/tommath.h b/tommath.h index a55c57f42..5ebd50c81 100644 --- a/tommath.h +++ b/tommath.h @@ -4,8 +4,8 @@ #ifndef TOMMATH_H_ #define TOMMATH_H_ -#include #include +#include #include #ifndef MP_NO_FILE From cf0042654ee6c762732ad235ff748ba616a8f365 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 08:54:09 +0100 Subject: [PATCH 075/304] define mp_isodd in terms of mp_iseven --- tommath.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tommath.h b/tommath.h index 5ebd50c81..e854d9658 100644 --- a/tommath.h +++ b/tommath.h @@ -206,7 +206,7 @@ mp_err mp_init_size(mp_int *a, int size) MP_WUR; #define mp_iszero(a) ((a)->used == 0) #define mp_isneg(a) ((a)->sign != MP_ZPOS) #define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u)) -#define mp_isodd(a) (((a)->used > 0) && (((a)->dp[0] & 1u) == 1u)) +#define mp_isodd(a) (!mp_iseven(a)) /* set to zero */ void mp_zero(mp_int *a); From 17d59c2c0f7e03af292c49978e077e3cc2f9a604 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 09:06:05 +0100 Subject: [PATCH 076/304] replace PRIx64 by MP_PRIx64 for c89 mode --- makefile | 19 ++++--------------- tommath_c89.h | 18 ++++++++++++++++++ 2 files changed, 22 insertions(+), 15 deletions(-) create mode 100644 tommath_c89.h diff --git a/makefile b/makefile index c06849a86..46941898d 100644 --- a/makefile +++ b/makefile @@ -161,20 +161,10 @@ c89: -e 's/bool/mp_bool/g' \ -e 's/true/MP_YES/g' \ -e 's/false/MP_NO/g' \ + -e 's/\(PRI[iux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ - *.c *.h demo/*.c demo/*.h etc/*.c - @echo "/* please adapt this header to your needs */" > tommath_c89.h - @echo "typedef enum { MP_NO, MP_YES } mp_bool;" >> tommath_c89.h - @echo "typedef __INT8_TYPE__ mp_i8;" >> tommath_c89.h - @echo "typedef __INT16_TYPE__ mp_i16;" >> tommath_c89.h - @echo "typedef __INT32_TYPE__ mp_i32;" >> tommath_c89.h - @echo "typedef __INT64_TYPE__ mp_i64;" >> tommath_c89.h - @echo "typedef __UINT8_TYPE__ mp_u8;" >> tommath_c89.h - @echo "typedef __UINT16_TYPE__ mp_u16;" >> tommath_c89.h - @echo "typedef __UINT32_TYPE__ mp_u32;" >> tommath_c89.h - @echo "typedef __UINT64_TYPE__ mp_u64;" >> tommath_c89.h - + *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c c99: @echo "Applying substitutions for c99 compatibility..." @@ -185,11 +175,10 @@ c99: -e 's/MP_YES/true/g' \ -e 's/MP_NO/false/g' \ -e 's/false_/MP_NO_/g' \ + -e 's/MP_\(PRI[iux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ - *.c *.h demo/*.c demo/*.h etc/*.c - @rm -f tommath_c89.h - + *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c astyle: @echo " * run astyle on all sources" diff --git a/tommath_c89.h b/tommath_c89.h new file mode 100644 index 000000000..e2beab842 --- /dev/null +++ b/tommath_c89.h @@ -0,0 +1,18 @@ +/* please adapt this header to your needs */ +typedef enum { MP_NO, MP_YES } mp_bool; +typedef __INT8_TYPE__ mp_i8; +typedef __INT16_TYPE__ mp_i16; +typedef __INT32_TYPE__ mp_i32; +typedef __INT64_TYPE__ mp_i64; +typedef __UINT8_TYPE__ mp_u8; +typedef __UINT16_TYPE__ mp_u16; +typedef __UINT32_TYPE__ mp_u32; +typedef __UINT64_TYPE__ mp_u64; +# if __WORDSIZE == 64 +# define MP_PRI64_PREFIX "l" +# else +# define MP_PRI64_PREFIX "ll" +# endif +#define MP_PRIi64 MP_PRI64_PREFIX "i" +#define MP_PRIu64 MP_PRI64_PREFIX "u" +#define MP_PRIx64 MP_PRI64_PREFIX "x" From 8ecf7eaea46b4f895222546eb5678a7201d5654c Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 09:19:32 +0100 Subject: [PATCH 077/304] better comment in tommath_c89.h --- tommath_c89.h | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) diff --git a/tommath_c89.h b/tommath_c89.h index e2beab842..35fb828c4 100644 --- a/tommath_c89.h +++ b/tommath_c89.h @@ -1,5 +1,23 @@ -/* please adapt this header to your needs */ +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* + * This header defines custom types which + * are used in c89 mode. + * + * By default, the source uses stdbool.h + * and stdint.h. The command `make c89` + * can be used to convert the source, + * such that this header is used instead. + * Use `make c99` to convert back. + * + * Please adapt the following definitions to your needs! + */ + +/* stdbool.h replacement types */ typedef enum { MP_NO, MP_YES } mp_bool; + +/* stdint.h replacement types */ typedef __INT8_TYPE__ mp_i8; typedef __INT16_TYPE__ mp_i16; typedef __INT32_TYPE__ mp_i32; @@ -8,6 +26,8 @@ typedef __UINT8_TYPE__ mp_u8; typedef __UINT16_TYPE__ mp_u16; typedef __UINT32_TYPE__ mp_u32; typedef __UINT64_TYPE__ mp_u64; + +/* inttypes.h replacement, printf format specifier */ # if __WORDSIZE == 64 # define MP_PRI64_PREFIX "l" # else From d27dff92f080f43670a9c1fe3cac32f32c50862c Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 18:39:14 +0100 Subject: [PATCH 078/304] update manual: replace mp_bool/MP_YES/MP_NO references by bool/true/false --- doc/bn.tex | 47 +++++++++++++++++++++-------------------------- 1 file changed, 21 insertions(+), 26 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 53c3251d9..5bdd8743a 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -444,7 +444,7 @@ \section{Building Programs} \section{Return Codes} There are five possible return codes a function may return. -\index{MP\_OKAY}\index{MP\_YES}\index{MP\_NO}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{M +\index{MP\_OKAY}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{M P\_BUF} \begin{figure}[h!] \begin{center} @@ -456,9 +456,6 @@ \section{Return Codes} \hline MP\_MEM & Heap memory exhausted. \\ \hline MP\_ITER & Maximum iterations reached. \\ \hline MP\_BUF & Buffer overflow, supplied buffer too small. \\ - \hline & \\ - \hline MP\_YES & Response is yes. \\ - \hline MP\_NO & Response is no. \\ \hline \end{tabular} \end{small} @@ -467,8 +464,7 @@ \section{Return Codes} \end{figure} The error codes \texttt{MP\_OKAY},\texttt{MP\_VAL}, \texttt{MP\_MEM}, \texttt{MP\_ITER}, and -\texttt{MP\_BUF} are of the type \texttt{mp\_err}, the codes \texttt{MP\_YES} and \texttt{MP\_NO} -are of type \texttt{mp\_bool}. +\texttt{MP\_BUF} are of the type \texttt{mp\_err}. The last two codes listed are not actually ``return'ed'' by a function. They are placed in an integer (the caller must provide the address of an integer it can store to) which the caller can @@ -476,11 +472,10 @@ \section{Return Codes} \index{mp\_error\_to\_string} \begin{alltt} -char *mp_error_to_string(int code); +char *mp_error_to_string(mp_err code); \end{alltt} -This will return a pointer to a string which describes the given error code. It will not work for -the return codes \texttt{MP\_YES} and \texttt{MP\_NO}. +This will return a pointer to a string which describes the given error code. \section{Data Types} The basic ``multiple precision integer'' type is known as the \texttt{mp\_int} within LibTomMath. @@ -1842,7 +1837,7 @@ \section{Restricted Diminished Radix} To determine if $a$ is a valid DR modulus: \index{mp\_dr\_is\_modulus} \begin{alltt} -mp_bool mp_dr_is_modulus(const mp_int *a); +bool mp_dr_is_modulus(const mp_int *a); \end{alltt} After the pre--computation a reduction can be performed with the following. @@ -1893,8 +1888,8 @@ \section{Unrestricted Diminished Radix} \index{mp\_reduce\_is\_2k}\index{mp\_reduce\_is\_2k\_l} \begin{alltt} -mp_bool mp_reduce_is_2k(const mp_int *a); -mp_bool mp_reduce_is_2k_l(const mp_int *a); +bool mp_reduce_is_2k(const mp_int *a); +bool mp_reduce_is_2k_l(const mp_int *a); \end{alltt} \section{Combined Modular Reduction} @@ -2265,7 +2260,7 @@ \subsection{Required Number of Tests} \section{Strong Lucas--Selfridge Test} \index{mp\_prime\_strong\_lucas\_selfridge} \begin{alltt} -mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, mp_bool *result) +mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) \end{alltt} Performs a strong Lucas--Selfridge test. The strong Lucas--Selfridge test together with the Rabin--Miller test with bases $2$ and $3$ resemble the BPSW test. The single internal use is a @@ -2275,7 +2270,7 @@ \section{Strong Lucas--Selfridge Test} \section{Frobenius (Underwood) Test} \index{mp\_prime\_frobenius\_underwood} \begin{alltt} -mp_err mp_prime_frobenius_underwood(const mp_int *N, mp_bool *result) +mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) \end{alltt} Performs the variant of the Frobenius test as described by Paul Underwood. It can be included at build--time if the preprocessor macro \texttt{LTM\_USE\_FROBENIUS\_TEST} is defined and will be @@ -2293,12 +2288,12 @@ \section{Primality Testing} It is used by the primality testing function described below. \index{mp\_is\_square} \begin{alltt} -mp_err mp_is_square(const mp_int *arg, mp_bool *ret); +mp_err mp_is_square(const mp_int *arg, bool *ret); \end{alltt} \index{mp\_prime\_is\_prime} \begin{alltt} -mp_err mp_prime_is_prime(const mp_int *a, int t, mp_bool *result) +mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) \end{alltt} This will perform a trial division followed by two rounds of Miller--Rabin with bases 2 and 3 and a Lucas--Selfridge test. The Frobenius--Underwood is available as a compile--time option with the @@ -2325,18 +2320,18 @@ \section{Primality Testing} by the caller. -If $a$ passes all of the tests $result$ is set to \texttt{MP\_YES}, otherwise it is set to -\texttt{MP\_NO}. +If $a$ passes all of the tests $result$ is set to \texttt{true}, otherwise it is set to +\texttt{false}. \section{Next Prime} \index{mp\_prime\_next\_prime} \begin{alltt} -mp_err mp_prime_next_prime(mp_int *a, int t, mp_bool bbs_style) +mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) \end{alltt} This finds the next prime after $a$ that passes the function \texttt{mp\_prime\_is\_prime} with $t$ tests but see the documentation for \texttt{mp\_prime\_is\_prime} for details regarding the use of -the argument $t$. Set $bbs\_style$ to \texttt{MP\_YES} if you want only the next prime congruent -to $3 \mbox{ mod } 4$, otherwise set it to \texttt{MP\_NO} to find any next prime. +the argument $t$. Set $bbs\_style$ to \texttt{true} if you want only the next prime congruent +to $3 \mbox{ mod } 4$, otherwise set it to \texttt{false} to find any next prime. \section{Random Primes} \index{mp\_prime\_rand} @@ -2639,29 +2634,29 @@ \chapter{Little Helpers} It is never wrong to have some useful little shortcuts at hand. \section{Function Macros} To make this overview simpler the macros are given as function prototypes. The return of logic -macros is \texttt{MP\_NO} or \texttt{MP\_YES} respectively. +macros is \texttt{false} or \texttt{true} respectively. \index{mp\_iseven} \begin{alltt} -mp_bool mp_iseven(const mp_int *a) +bool mp_iseven(const mp_int *a) \end{alltt} Checks if $a = 0 mod 2$ \index{mp\_isodd} \begin{alltt} -mp_bool mp_isodd(const mp_int *a) +bool mp_isodd(const mp_int *a) \end{alltt} Checks if $a = 1 mod 2$ \index{mp\_isneg} \begin{alltt} -mp_bool mp_isneg(mp_int *a) +bool mp_isneg(mp_int *a) \end{alltt} Checks if $a < 0$ \index{mp\_iszero} \begin{alltt} -mp_bool mp_iszero(mp_int *a) +bool mp_iszero(mp_int *a) \end{alltt} Checks if $a = 0$. It does not check if the amount of memory allocated for $a$ is also minimal. From 4376913928d26ed86372920db87ac13e7a96a06d Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 18:41:05 +0100 Subject: [PATCH 079/304] remove inttypes.h includes in c89 mode --- makefile | 2 ++ 1 file changed, 2 insertions(+) diff --git a/makefile b/makefile index 46941898d..f6c9ec307 100644 --- a/makefile +++ b/makefile @@ -158,6 +158,7 @@ c89: @sed -i \ -e '/#include /d' \ -e 's/#include /#include "tommath_c89.h"/g' \ + -e 's/#include /\/*#include *\//g' \ -e 's/bool/mp_bool/g' \ -e 's/true/MP_YES/g' \ -e 's/false/MP_NO/g' \ @@ -171,6 +172,7 @@ c99: @if ! grep mp_bool tommath.h > /dev/null; then echo "Already applied"; exit 1; fi @sed -i \ -e 's/#include "tommath_c89.h"/#include \n#include /g' \ + -e 's/\/\*#include \*\//#include /g' \ -e 's/mp_bool/bool/g' \ -e 's/MP_YES/true/g' \ -e 's/MP_NO/false/g' \ From f662e1f7e1b25c521f32a8335bd1893470eee11d Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 19:02:49 +0100 Subject: [PATCH 080/304] fix c89 issues --- makefile | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/makefile b/makefile index f6c9ec307..3259b2ab1 100644 --- a/makefile +++ b/makefile @@ -162,6 +162,13 @@ c89: -e 's/bool/mp_bool/g' \ -e 's/true/MP_YES/g' \ -e 's/false/MP_NO/g' \ + -e 's/UINT32_MAX/0xFFFFFFFFU/g' \ + -e 's/UINT64_MAX/0xFFFFFFFFFFFFFFFFULL/g' \ + -e 's/INT32_MAX/2147483647/g' \ + -e 's/INT32_MIN/(-2147483647-1)/g' \ + -e 's/INT64_MAX/((mp_i64)9223372036854775807LL)/g' \ + -e 's/INT64_MIN/((mp_i64)-9223372036854775807LL-1)/g' \ + -e 's/SIZE_MAX/((size_t)-1)/g' \ -e 's/\(PRI[iux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ @@ -177,6 +184,13 @@ c99: -e 's/MP_YES/true/g' \ -e 's/MP_NO/false/g' \ -e 's/false_/MP_NO_/g' \ + -e 's/0xFFFFFFFFU/UINT32_MAX/g' \ + -e 's/0xFFFFFFFFFFFFFFFFULL/UINT64_MAX/g' \ + -e 's/(-2147483647-1)/INT32_MIN/g' \ + -e 's/2147483647/INT32_MAX/g' \ + -e 's/((mp_i64)-9223372036854775807LL-1)/INT64_MIN/g' \ + -e 's/((mp_i64)9223372036854775807LL)/INT64_MAX/g' \ + -e 's/((size_t)-1)/SIZE_MAX/g' \ -e 's/MP_\(PRI[iux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ From 7afecabd9d368a48da05ec8791e202f2801e6013 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 24 Oct 2019 17:33:38 +0200 Subject: [PATCH 081/304] regen files --- libtommath_VS2008.vcproj | 24 ++++------------------ makefile | 44 ++++++++++++++++++++-------------------- makefile.mingw | 44 ++++++++++++++++++++-------------------- makefile.msvc | 44 ++++++++++++++++++++-------------------- makefile.shared | 44 ++++++++++++++++++++-------------------- makefile.unix | 44 ++++++++++++++++++++-------------------- tommath.def | 4 ---- tommath_class.h | 31 +--------------------------- 8 files changed, 115 insertions(+), 164 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 1f444cbb2..116275e8d 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -380,10 +380,6 @@ RelativePath="mp_cutoffs.c" > - - @@ -496,10 +492,6 @@ RelativePath="mp_grow.c" > - - @@ -560,14 +552,6 @@ RelativePath="mp_is_square.c" > - - - - @@ -936,10 +920,6 @@ RelativePath="s_mp_rand_platform.c" > - - @@ -964,6 +944,10 @@ RelativePath="tommath.h" > + + diff --git a/makefile b/makefile index 3259b2ab1..b14976f6a 100644 --- a/makefile +++ b/makefile @@ -28,28 +28,28 @@ LCOV_ARGS=--directory . #START_INS OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_decr.o mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o \ -mp_dr_setup.o mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o \ -mp_from_sbin.o mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o \ -mp_get_ll.o mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_incr.o \ -mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o \ -mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o \ -mp_iseven.o mp_isodd.o mp_kronecker.o mp_lcm.o mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o \ -mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ -mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ -mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ -mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o \ -mp_radix_size.o mp_radix_smap.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ -s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ -s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ +mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ +mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ +mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ +mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o mp_montgomery_calc_normalization.o \ +mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o \ +mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o \ +mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o \ +mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o \ +mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_div_recursive.o s_mp_div_school.o \ +s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o \ +s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 8f542f0c2..08b8e964c 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -31,28 +31,28 @@ LIBMAIN_D =libtommath.dll #List of objects to compile (all goes to libtommath.a) OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_decr.o mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o \ -mp_dr_setup.o mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o \ -mp_from_sbin.o mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o \ -mp_get_ll.o mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_incr.o \ -mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o \ -mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o \ -mp_iseven.o mp_isodd.o mp_kronecker.o mp_lcm.o mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o \ -mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ -mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ -mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ -mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o \ -mp_radix_size.o mp_radix_smap.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ -s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ -s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ +mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ +mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ +mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ +mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o mp_montgomery_calc_normalization.o \ +mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o \ +mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o \ +mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o \ +mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o \ +mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_div_recursive.o s_mp_div_school.o \ +s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o \ +s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 3050b6ca8..058d5ce75 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -23,28 +23,28 @@ LIBMAIN_S =tommath.lib #List of objects to compile (all goes to tommath.lib) OBJECTS=mp_2expt.obj mp_abs.obj mp_add.obj mp_add_d.obj mp_addmod.obj mp_and.obj mp_clamp.obj mp_clear.obj mp_clear_multi.obj \ mp_cmp.obj mp_cmp_d.obj mp_cmp_mag.obj mp_cnt_lsb.obj mp_complement.obj mp_copy.obj mp_count_bits.obj mp_cutoffs.obj \ -mp_decr.obj mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_3.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj \ -mp_dr_setup.obj mp_error_to_string.obj mp_exch.obj mp_expt_u32.obj mp_exptmod.obj mp_exteuclid.obj mp_fread.obj \ -mp_from_sbin.obj mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj \ -mp_get_ll.obj mp_get_mag_u32.obj mp_get_mag_u64.obj mp_get_mag_ul.obj mp_get_mag_ull.obj mp_grow.obj mp_incr.obj \ -mp_init.obj mp_init_copy.obj mp_init_i32.obj mp_init_i64.obj mp_init_l.obj mp_init_ll.obj mp_init_multi.obj mp_init_set.obj \ -mp_init_size.obj mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj mp_init_ull.obj mp_invmod.obj mp_is_square.obj \ -mp_iseven.obj mp_isodd.obj mp_kronecker.obj mp_lcm.obj mp_log_u32.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj mp_mod_d.obj \ -mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj \ -mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj \ -mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj \ -mp_prime_rabin_miller_trials.obj mp_prime_rand.obj mp_prime_strong_lucas_selfridge.obj mp_prime_tab.obj \ -mp_radix_size.obj mp_radix_smap.obj mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj \ -mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj \ -mp_root_u32.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj \ -mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj mp_sqr.obj \ -mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ -mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj \ -s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj \ -s_mp_invmod_fast.obj s_mp_invmod_slow.obj s_mp_karatsuba_mul.obj s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj \ -s_mp_log_pow2.obj s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj \ -s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj \ -s_mp_reverse.obj s_mp_sqr.obj s_mp_sqr_fast.obj s_mp_sub.obj s_mp_toom_mul.obj s_mp_toom_sqr.obj +mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_3.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj mp_dr_setup.obj \ +mp_error_to_string.obj mp_exch.obj mp_expt_u32.obj mp_exptmod.obj mp_exteuclid.obj mp_fread.obj mp_from_sbin.obj \ +mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj mp_get_ll.obj \ +mp_get_mag_u32.obj mp_get_mag_u64.obj mp_get_mag_ul.obj mp_get_mag_ull.obj mp_grow.obj mp_init.obj mp_init_copy.obj \ +mp_init_i32.obj mp_init_i64.obj mp_init_l.obj mp_init_ll.obj mp_init_multi.obj mp_init_set.obj mp_init_size.obj \ +mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj mp_init_ull.obj mp_invmod.obj mp_is_square.obj mp_kronecker.obj mp_lcm.obj \ +mp_log_u32.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj mp_mod_d.obj mp_montgomery_calc_normalization.obj \ +mp_montgomery_reduce.obj mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj \ +mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj mp_prime_frobenius_underwood.obj \ +mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj mp_prime_rabin_miller_trials.obj \ +mp_prime_rand.obj mp_prime_strong_lucas_selfridge.obj mp_prime_tab.obj mp_radix_size.obj mp_radix_smap.obj \ +mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj mp_reduce_2k_setup.obj \ +mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj mp_root_u32.obj mp_rshd.obj \ +mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj mp_set_ll.obj mp_set_u32.obj \ +mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj mp_sqr.obj mp_sqrmod.obj mp_sqrt.obj \ +mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ +mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_balance_mul.obj s_mp_div_recursive.obj s_mp_div_school.obj \ +s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod_fast.obj s_mp_invmod_slow.obj \ +s_mp_karatsuba_mul.obj s_mp_karatsuba_sqr.obj s_mp_log.obj s_mp_log_d.obj s_mp_log_pow2.obj \ +s_mp_montgomery_reduce_fast.obj s_mp_mul_digs.obj s_mp_mul_digs_fast.obj s_mp_mul_high_digs.obj \ +s_mp_mul_high_digs_fast.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj \ +s_mp_sqr_fast.obj s_mp_sub.obj s_mp_toom_mul.obj s_mp_toom_sqr.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index cad119657..51b0ee4b8 100644 --- a/makefile.shared +++ b/makefile.shared @@ -25,28 +25,28 @@ LCOV_ARGS=--directory .libs --directory . #START_INS OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_decr.o mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o \ -mp_dr_setup.o mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o \ -mp_from_sbin.o mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o \ -mp_get_ll.o mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_incr.o \ -mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o \ -mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o \ -mp_iseven.o mp_isodd.o mp_kronecker.o mp_lcm.o mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o \ -mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ -mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ -mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ -mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o \ -mp_radix_size.o mp_radix_smap.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ -s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ -s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ +mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ +mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ +mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ +mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o mp_montgomery_calc_normalization.o \ +mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o \ +mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o \ +mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o \ +mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o \ +mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_div_recursive.o s_mp_div_school.o \ +s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o \ +s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o #END_INS diff --git a/makefile.unix b/makefile.unix index bde330f47..5fff6b9e0 100644 --- a/makefile.unix +++ b/makefile.unix @@ -32,28 +32,28 @@ LIBMAIN_S = libtommath.a OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_decr.o mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o \ -mp_dr_setup.o mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o \ -mp_from_sbin.o mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o \ -mp_get_ll.o mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_incr.o \ -mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o \ -mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o \ -mp_iseven.o mp_isodd.o mp_kronecker.o mp_lcm.o mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o \ -mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ -mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ -mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ -mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o \ -mp_radix_size.o mp_radix_smap.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod_fast.o s_mp_invmod_slow.o s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o \ -s_mp_log_pow2.o s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ -s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o \ -s_mp_reverse.o s_mp_sqr.o s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o +mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ +mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ +mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ +mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ +mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_mod_d.o mp_montgomery_calc_normalization.o \ +mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o \ +mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o \ +mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o \ +mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o \ +mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_balance_mul.o s_mp_div_recursive.o s_mp_div_school.o \ +s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod_fast.o s_mp_invmod_slow.o \ +s_mp_karatsuba_mul.o s_mp_karatsuba_sqr.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ +s_mp_montgomery_reduce_fast.o s_mp_mul_digs.o s_mp_mul_digs_fast.o s_mp_mul_high_digs.o \ +s_mp_mul_high_digs_fast.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_fast.o s_mp_sub.o s_mp_toom_mul.o s_mp_toom_sqr.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/tommath.def b/tommath.def index 7c241bc75..db0aba447 100644 --- a/tommath.def +++ b/tommath.def @@ -23,7 +23,6 @@ EXPORTS mp_copy mp_count_bits mp_cutoffs - mp_decr mp_div mp_div_2 mp_div_2d @@ -52,7 +51,6 @@ EXPORTS mp_get_mag_ul mp_get_mag_ull mp_grow - mp_incr mp_init mp_init_copy mp_init_i32 @@ -68,8 +66,6 @@ EXPORTS mp_init_ull mp_invmod mp_is_square - mp_iseven - mp_isodd mp_kronecker mp_lcm mp_log_u32 diff --git a/tommath_class.h b/tommath_class.h index 480c24abf..3a3d54971 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -28,7 +28,6 @@ # define MP_COPY_C # define MP_COUNT_BITS_C # define MP_CUTOFFS_C -# define MP_DECR_C # define MP_DIV_C # define MP_DIV_2_C # define MP_DIV_2D_C @@ -57,7 +56,6 @@ # define MP_GET_MAG_UL_C # define MP_GET_MAG_ULL_C # define MP_GROW_C -# define MP_INCR_C # define MP_INIT_C # define MP_INIT_COPY_C # define MP_INIT_I32_C @@ -73,8 +71,6 @@ # define MP_INIT_ULL_C # define MP_INVMOD_C # define MP_IS_SQUARE_C -# define MP_ISEVEN_C -# define MP_ISODD_C # define MP_KRONECKER_C # define MP_LCM_C # define MP_LOG_U32_C @@ -167,7 +163,6 @@ # define S_MP_PRIME_IS_DIVISIBLE_C # define S_MP_RAND_JENKINS_C # define S_MP_RAND_PLATFORM_C -# define S_MP_REVERSE_C # define S_MP_SQR_C # define S_MP_SQR_FAST_C # define S_MP_SUB_C @@ -246,13 +241,6 @@ #if defined(MP_CUTOFFS_C) #endif -#if defined(MP_DECR_C) -# define MP_INCR_C -# define MP_SET_C -# define MP_SUB_D_C -# define MP_ZERO_C -#endif - #if defined(MP_DIV_C) # define MP_CMP_MAG_C # define MP_COPY_C @@ -411,12 +399,6 @@ #if defined(MP_GROW_C) #endif -#if defined(MP_INCR_C) -# define MP_ADD_D_C -# define MP_DECR_C -# define MP_SET_C -#endif - #if defined(MP_INIT_C) #endif @@ -496,12 +478,6 @@ # define MP_SQR_C #endif -#if defined(MP_ISEVEN_C) -#endif - -#if defined(MP_ISODD_C) -#endif - #if defined(MP_KRONECKER_C) # define MP_CLEAR_C # define MP_CMP_D_C @@ -701,8 +677,6 @@ # define MP_MUL_2_C # define MP_PRIME_IS_PRIME_C # define MP_SUB_D_C -# define S_MP_PRIME_RANDOM_EX_C -# define S_MP_RAND_CB_C # define S_MP_RAND_SOURCE_C #endif @@ -1019,7 +993,6 @@ # define MP_CLEAR_MULTI_C # define MP_CMP_D_C # define MP_COPY_C -# define MP_DECR_C # define MP_DIV_2D_C # define MP_EXCH_C # define MP_INIT_MULTI_C @@ -1027,6 +1000,7 @@ # define MP_MUL_2D_C # define MP_MUL_C # define MP_SUB_C +# define MP_SUB_D_C # define MP_ZERO_C # define S_MP_DIV_SCHOOL_C # define S_MP_RECURSION_C @@ -1223,9 +1197,6 @@ #if defined(S_MP_RAND_PLATFORM_C) #endif -#if defined(S_MP_REVERSE_C) -#endif - #if defined(S_MP_SQR_C) # define MP_CLAMP_C # define MP_CLEAR_C From e2f8df335842f0b9657b00dd311324c720de002b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Oct 2019 21:19:37 +0100 Subject: [PATCH 082/304] fix doc [skip ci] + ignore bak files generated by latexindent + silence latexindent --- .gitignore | 1 + doc/bn.tex | 3 +-- doc/makefile | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index 7cd346fb3..f1c0a0562 100644 --- a/.gitignore +++ b/.gitignore @@ -95,5 +95,6 @@ test_*.txt *.zip doc/pics/*.ps +doc/*.bak* callgraph.txt diff --git a/doc/bn.tex b/doc/bn.tex index 5bdd8743a..c65584845 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -444,8 +444,7 @@ \section{Building Programs} \section{Return Codes} There are five possible return codes a function may return. -\index{MP\_OKAY}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{M - P\_BUF} +\index{MP\_OKAY}\index{MP\_VAL}\index{MP\_MEM}\index{MP\_ITER}\index{MP\_BUF} \begin{figure}[h!] \begin{center} \begin{small} diff --git a/doc/makefile b/doc/makefile index 124859ef9..84c48e4b2 100644 --- a/doc/makefile +++ b/doc/makefile @@ -43,7 +43,7 @@ manual: mandvi # Its configuraion is well documented # http://mirrors.ctan.org/support/latexindent/documentation/latexindent.pdf pretty: - latexindent -w -m -l=.latexindent.yaml bn.tex + latexindent -s -w -m -l=.latexindent.yaml bn.tex clean: rm -f *.idx *.toc *.log *.aux *.dvi *.lof *.ind *.ilg *.ps *.log tommath.tex From 2122b5113994de61c7361b7c75cea183e73b14f5 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 19:48:13 +0100 Subject: [PATCH 083/304] manual: don't mention obsolete MP_DIV_SMALL --- doc/bn.tex | 18 +----------------- 1 file changed, 1 insertion(+), 17 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index c65584845..1e8ac7403 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -271,7 +271,7 @@ \subsection{Testing} numbers it was working with. \section{Build Configuration} -LibTomMath can configured at build time in three phases we shall call ``depends'', ``tweaks'' and +LibTomMath can configured at build time in two phases we shall call ``depends'' and ``trims''. Each phase changes how the library is built and they are applied one after another respectively. @@ -298,22 +298,6 @@ \subsection{Build Depends} includes itself twice). This is to help resolve as many dependencies as possible. In the last pass the symbol \texttt{LTM\_LAST} will be defined. This is useful for ``trims''. -\subsection{Build Tweaks} -A tweak is an algorithm ``alternative''. For example, to provide tradeoffs (usually between size -and space). -They can be enabled at any pass of the configuration phase. - -\begin{small} - \begin{center} - \begin{tabular}{|l|l|} - \hline \textbf{Define} & \textbf{Purpose} \\ - \hline MP\_DIV\_SMALL & Enables a slower, smaller and equally \\ - & functional mp\_div() function \\ - \hline - \end{tabular} - \end{center} -\end{small} - \subsection{Build Trims} A trim is a manner of removing functionality from a function that is not required. For instance, to perform RSA cryptography you only require exponentiation with odd moduli so even moduli support From 85699be1ac576bc4561e8daceac3ce6fbba32dd0 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 21:58:43 +0100 Subject: [PATCH 084/304] remove ltm_rng (deprecated function) --- s_mp_rand_platform.c | 17 ----------------- 1 file changed, 17 deletions(-) diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 6b6a22c10..06e92abc1 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -112,26 +112,10 @@ static mp_err s_read_urandom(void *p, size_t n) } #endif -#if defined(MP_PRNG_ENABLE_LTM_RNG) -#define BN_S_READ_LTM_RNG -unsigned long (*ltm_rng)(unsigned char *out, unsigned long outlen, void (*callback)(void)); -void (*ltm_rng_callback)(void); - -static mp_err s_read_ltm_rng(void *p, size_t n) -{ - unsigned long res; - if (ltm_rng == NULL) return MP_ERR; - res = ltm_rng(p, n, ltm_rng_callback); - if (res != n) return MP_ERR; - return MP_OKAY; -} -#endif - mp_err s_read_arc4random(void *p, size_t n); mp_err s_read_wincsp(void *p, size_t n); mp_err s_read_getrandom(void *p, size_t n); mp_err s_read_urandom(void *p, size_t n); -mp_err s_read_ltm_rng(void *p, size_t n); mp_err s_mp_rand_platform(void *p, size_t n) { @@ -140,7 +124,6 @@ mp_err s_mp_rand_platform(void *p, size_t n) if ((err != MP_OKAY) && MP_HAS(S_READ_WINCSP)) err = s_read_wincsp(p, n); if ((err != MP_OKAY) && MP_HAS(S_READ_GETRANDOM)) err = s_read_getrandom(p, n); if ((err != MP_OKAY) && MP_HAS(S_READ_URANDOM)) err = s_read_urandom(p, n); - if ((err != MP_OKAY) && MP_HAS(S_READ_LTM_RNG)) err = s_read_ltm_rng(p, n); return err; } From a5d5b10154fed29b4e18be56f33d91fb4181d0e9 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 23:51:38 +0100 Subject: [PATCH 085/304] mp_read_radix and mp_fread should behave the same --- mp_fread.c | 18 ++++++++++++------ mp_read_radix.c | 18 ++++-------------- tommath_private.h | 2 ++ 3 files changed, 18 insertions(+), 20 deletions(-) diff --git a/mp_fread.c b/mp_fread.c index 34dd1e79a..767e5a3c0 100644 --- a/mp_fread.c +++ b/mp_fread.c @@ -8,15 +8,19 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) { mp_err err; - mp_sign neg; + mp_sign neg = MP_ZPOS; + int ch; + + /* make sure the radix is ok */ + if ((radix < 2) || (radix > 64)) { + return MP_VAL; + } /* if first digit is - then set negative */ - int ch = fgetc(stream); + ch = fgetc(stream); if (ch == (int)'-') { neg = MP_NEG; ch = fgetc(stream); - } else { - neg = MP_ZPOS; } /* no digits, return error */ @@ -29,7 +33,9 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) do { int y; - unsigned pos = (unsigned)(ch - (int)'('); + unsigned pos; + ch = (radix <= 36) ? MP_TOUPPER(ch) : ch; + pos = (unsigned)(ch - (int)'('); if (MP_RMAP_REVERSE_SIZE < pos) { break; } @@ -49,7 +55,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) } } while ((ch = fgetc(stream)) != EOF); - if (a->used != 0) { + if (!mp_iszero(a)) { a->sign = neg; } diff --git a/mp_read_radix.c b/mp_read_radix.c index 0e4f84824..d4a3d1ecf 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -3,19 +3,11 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#define MP_TOUPPER(c) ((((c) >= 'a') && ((c) <= 'z')) ? (((c) + 'A') - 'a') : (c)) - /* read a string [ASCII] in a given radix */ mp_err mp_read_radix(mp_int *a, const char *str, int radix) { mp_err err; - int y; - mp_sign neg; - unsigned pos; - char ch; - - /* zero the digit bignum */ - mp_zero(a); + mp_sign neg = MP_ZPOS; /* make sure the radix is ok */ if ((radix < 2) || (radix > 64)) { @@ -28,8 +20,6 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) if (*str == '-') { ++str; neg = MP_NEG; - } else { - neg = MP_ZPOS; } /* set the integer to the default of zero */ @@ -41,8 +31,9 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) * this allows numbers like 1AB and 1ab to represent the same value * [e.g. in hex] */ - ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; - pos = (unsigned)(ch - '('); + int y; + char ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; + unsigned pos = (unsigned)(ch - '('); if (MP_RMAP_REVERSE_SIZE < pos) { break; } @@ -66,7 +57,6 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) /* if an illegal character was found, fail. */ if (!((*str == '\0') || (*str == '\r') || (*str == '\n'))) { - mp_zero(a); return MP_VAL; } diff --git a/tommath_private.h b/tommath_private.h index 2dbdca805..0f5ac9345 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -146,6 +146,8 @@ extern void MP_FREE(void *mem, size_t size); #define MP_MIN(x, y) (((x) < (y)) ? (x) : (y)) #define MP_MAX(x, y) (((x) > (y)) ? (x) : (y)) +#define MP_TOUPPER(c) ((((c) >= 'a') && ((c) <= 'z')) ? (((c) + 'A') - 'a') : (c)) + /* Static assertion */ #define MP_STATIC_ASSERT(msg, cond) typedef char mp_static_assert_##msg[(cond) ? 1 : -1]; From 1ece193af25159b65a8f4e53abfe2c7389095a5c Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 27 Oct 2019 22:48:53 +0100 Subject: [PATCH 086/304] replace gen.pl by cat, rename mpi.c to mp_all.c --- .gitignore | 4 ++-- gen.pl | 20 -------------------- makefile | 16 ++++++++-------- makefile_include.mk | 2 +- 4 files changed, 11 insertions(+), 31 deletions(-) delete mode 100644 gen.pl diff --git a/.gitignore b/.gitignore index f1c0a0562..a5a4aba3b 100644 --- a/.gitignore +++ b/.gitignore @@ -60,8 +60,8 @@ UpgradeLog*.htm perf.data perf.data.old -# ignore mpi.c generated by make -mpi.c +# ignore mp_all.c generated by make +mp_all.c # ignore file generated by make tune tuning_list diff --git a/gen.pl b/gen.pl deleted file mode 100644 index 4db24b547..000000000 --- a/gen.pl +++ /dev/null @@ -1,20 +0,0 @@ -#!/usr/bin/perl -w -# -# Generates a "single file" you can use to quickly -# add the whole source without any makefile troubles -# -use strict; -use warnings; - -open(my $out, '>', 'mpi.c') or die "Couldn't open mpi.c for writing: $!"; -foreach my $filename (glob '*mp_*.c') { - open(my $src, '<', $filename) or die "Couldn't open $filename for reading: $!"; - print {$out} "/* Start: $filename */\n"; - print {$out} $_ while <$src>; - print {$out} "\n/* End: $filename */\n\n"; - close $src or die "Error closing $filename after reading: $!"; -} -print {$out} "\n/* EOF */\n"; -close $out or die "Error closing mpi.c after writing: $!"; - -system('perl -pli -e "s/\s*$//" mpi.c'); diff --git a/makefile b/makefile index b14976f6a..7889c5ab7 100644 --- a/makefile +++ b/makefile @@ -71,13 +71,13 @@ profiled: #make a single object profiled library profiled_single: - perl gen.pl - $(CC) $(LTM_CFLAGS) -fprofile-arcs -DTESTING -c mpi.c -o mpi.o - $(CC) $(LTM_CFLAGS) -DTESTING -DTIMER demo/timing.c mpi.o -lgcov -o timing + cat *mp_*.c > mp_all.c + $(CC) $(LTM_CFLAGS) -fprofile-arcs -DTESTING -c mp_all.c -o mp_all.o + $(CC) $(LTM_CFLAGS) -DTESTING -DTIMER demo/timing.c mp_all.o -lgcov -o timing ./timing rm -f *.o timing - $(CC) $(LTM_CFLAGS) -fbranch-probabilities -DTESTING -c mpi.c -o mpi.o - $(AR) $(ARFLAGS) $(LIBNAME) mpi.o + $(CC) $(LTM_CFLAGS) -fbranch-probabilities -DTESTING -c mp_all.c -o mp_all.o + $(AR) $(ARFLAGS) $(LIBNAME) mp_all.o ranlib $(LIBNAME) install: $(LIBNAME) @@ -121,9 +121,9 @@ docs manual: .PHONY: pre_gen pre_gen: mkdir -p pre_gen - perl gen.pl - sed -e 's/[[:blank:]]*$$//' mpi.c > pre_gen/mpi.c - rm mpi.c + cat *mp_*.c > mp_all.c + sed -e 's/[[:blank:]]*$$//' mp_all.c > pre_gen/mp_all.c + rm mp_all.c zipup: clean astyle new_file docs @# Update the index, so diff-index won't fail in case the pdf has been created. diff --git a/makefile_include.mk b/makefile_include.mk index 650b3e7e3..b7946902e 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -164,7 +164,7 @@ cleancov: cleancov-clean clean clean: rm -f *.gcda *.gcno *.gcov *.bat *.o *.a *.obj *.lib *.exe *.dll etclib/*.o \ demo/*.o test timing mtest_opponent mtest/mtest mtest/mtest.exe tuning_list \ - *.s mpi.c *.da *.dyn *.dpi tommath.tex `find . -type f | grep [~] | xargs` *.lo *.la + *.s mp_all.c *.da *.dyn *.dpi tommath.tex `find . -type f | grep [~] | xargs` *.lo *.la rm -rf .libs/ demo/.libs ${MAKE} -C etc/ clean MAKE=${MAKE} ${MAKE} -C doc/ clean MAKE=${MAKE} From 43804ed7321e0ee3ba214951221d944759c5a13b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 13:39:08 +0100 Subject: [PATCH 087/304] remove logs and generated PNG's this fixes #423 --- .gitignore | 3 ++ logs/add.log | 16 --------- logs/addsub.png | Bin 5921 -> 0 bytes logs/expt.log | 7 ---- logs/expt.png | Bin 7290 -> 0 bytes logs/expt_2k.log | 6 ---- logs/expt_2kl.log | 3 -- logs/expt_dr.log | 7 ---- logs/invmod.log | 8 ----- logs/invmod.png | Bin 6294 -> 0 bytes logs/mult.log | 84 --------------------------------------------- logs/mult.png | Bin 8308 -> 0 bytes logs/mult_kara.log | 84 --------------------------------------------- logs/sqr.log | 84 --------------------------------------------- logs/sqr_kara.log | 84 --------------------------------------------- logs/sub.log | 16 --------- 16 files changed, 3 insertions(+), 399 deletions(-) delete mode 100644 logs/add.log delete mode 100644 logs/addsub.png delete mode 100644 logs/expt.log delete mode 100644 logs/expt.png delete mode 100644 logs/expt_2k.log delete mode 100644 logs/expt_2kl.log delete mode 100644 logs/expt_dr.log delete mode 100644 logs/invmod.log delete mode 100644 logs/invmod.png delete mode 100644 logs/mult.log delete mode 100644 logs/mult.png delete mode 100644 logs/mult_kara.log delete mode 100644 logs/sqr.log delete mode 100644 logs/sqr_kara.log delete mode 100644 logs/sub.log diff --git a/.gitignore b/.gitignore index a5a4aba3b..c623fd05b 100644 --- a/.gitignore +++ b/.gitignore @@ -97,4 +97,7 @@ test_*.txt doc/pics/*.ps doc/*.bak* +logs/*.png +logs/*-*.dem + callgraph.txt diff --git a/logs/add.log b/logs/add.log deleted file mode 100644 index 0ed7b70d9..000000000 --- a/logs/add.log +++ /dev/null @@ -1,16 +0,0 @@ - 480 48 - 960 61 - 1440 82 - 1920 97 - 2400 106 - 2880 112 - 3360 127 - 3840 130 - 4320 146 - 4800 157 - 5280 174 - 5760 185 - 6240 200 - 6720 214 - 7200 230 - 7680 244 diff --git a/logs/addsub.png b/logs/addsub.png deleted file mode 100644 index b8ffef74b32056352e53c3e0fa25585fbf9cb658..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5921 zcmd5=i9eLlyPp|@u@5R)%1Eh@vD0RTD6%9())65|mSo8?Z^#lw#3WhEE@R13V#bzz zDMTbgvM(b$v)otr_qq3T|ARZ9ci!iDzUQ20Iq&zJcZoJOy28UL!U=&uc=U9&O&|~$ z0D(X$2o?~5@yUJ%4HaVpGaV+A2_l)9nfrnafdEW0gb7(*CSxIOZ4gb@2__i@0kC9% zDQ^$NKpx}!h=?dDDH$3XIy*b#@%WUKl!}T9GMU`f)%EAk zA20+}Q89iw{{8SY^#+x~WG;_|GOHSh%gf9m2pA1=8$9EW#T=81vG`}l2n&0HsX!pz zkv$8L{S=vyp0CUUiA=mP6#$qzkX^ugF8L94I<~IbttNtNW8-HgfMVuAmP40cLi)!t z$Ks8#H{8&`0SIv50DuJ#0I(+m_Dog($>GBU))#YrR*4u=~bAID%Ykn{)X6Fxm)*&Lp_mJc8h-sb&3G)ab6 z6aqPzpr@^A=Kp3XjU)Lj>Hy@A*e{o!$4`TqlChNZ7E~s}tZwL{j~`5`V5eB?1{C!2 ze|`t9jz#4jVJwB`3Y&OuKZ^~zVa#d!UV5;zaDH$-)t6ePVg$2!J}_=p!C%@>O0a#m z@L1q0Otk`#%EGgF3O>B(KeXxCf9(}6I$sE`Be6GOjZtQ^c1OV)>jvBciSG4?Q;77Z)r23RD^nbHQSO+H&;^1Wm8E1CN{DZX@h6|SH#hb2 z<_ORc%Th>hI_fzHc9ykkW|6x^_z@*iI2izYmo|O5F*&70l+d)_|G0_Ng#+;Ld=x4+ z%24YwV>!aX0}jn-^bIoje0(=h4hrSEteSdj)B@`9ntX*E>N@gO@kdPk!PIbhNs+N_ zy>9(;kym2uf_s-vGBxM|&`zDrB)iY9YZnDnMHiDn58hRQ zCC8*3&(GbFIkKJHY))P!g!wz@o*L?19w*Je#UpOY{r+^~Y~|($D}4uj3ZjEFDC5a-sLm;)jrN(4C3vj8}bbQk`Ax@ei@4joS6TORU7A z(QA0$acjIJ;^rw+h_VE=U!8)otq^DT5ujSn_(7o)S|PiUfTskBehFK{%f&<@OC}el zT6y8&Zrg+OG%U6z9B;lWfwE~NJ zHiCQfnX=Y+w1u}M!XIsNZASXzSb^^jg7?s`+LCq*KSLTW``FcmbMSqItHTJUSN5|< z7mfJCfP63eSogQUR+Sx>!ttHE%WTjUr?J-#2aSmpLrLX3S^ef4CM$Qo&T(3&v=kb- z{k?XB)Oliz8}>_o)W@6KrU)pv8oC+%aOFS+>F@g6&euVs4TOVmS;&dV`AUy!SmEi) zl7OT93yhALp{Y^6`bEyqN8qu*TzE0e-1M%b{g|>dscq+XnRO!5FM@CA3DA=Hnt)Iz zR)}NbO3ddS;U8=hSC9DV zsCFLFeLjVUK)pa^XC{!Ogg`KAB1oLj2JxABi!gxFirM-npJap}5Fy(G^=xpsUr-b7 z2|#&F0-q-TY4gBy9kNA_w^Eb0^~z!lnjE+T==c+NPrq0 z(7yJEA%P0A|Gx4Fq}i_;H0=fgL6lV!8=C~(r|XacX_v6WfBhU6z!iJz&##doqJCrOK5Q}${M9}p~Ez$IH0Bu z75#&B1}h8HH!Wv4NDf&RROR1E7taXb}OOA_E{aBI8Eu~gykA$hoNNr8ed*9M4?B6^-+8+DM5d1Z@xZMTvI&tsKGBG;9m(TRy74HvK5}*#1NIuI*Jhw zUve-|tHj^;l(blc>n>m|XbN-kTSpB(+j;01ne#2?PV*>C1pXllK{xW%VtYIARX+CK z)T?oUlcQNfKkGN&@b`tn?&6vX5b8P*~U6^P;X`HOdtQLcTNSKFgnq`9(m6c#RI z@!v@tFOQ4V`+V6DPSa7?O&dvn|INJ?mlm%_t`biTnKYF^Y=?a%4O@8eWjVbnq*&c> z-q3)Z%cRRl(r!$+XsPn`_kYP?<*q1{G4)v^BI!oa_8%{%4(GYDq_>2VhK0N&H%BWT zns*|<&|-`C9}e6eHGF?5$dJ7gwFNBZb6j$T74)N zlti^KUvjh8V>~zo?lXB+E~42Z&d+}*E5=L`KZ7-lyuLJF2@sDw)$f#zCMnX-SD$@h zuQ`9?0JxTnc(i+Qeo21xppCw}U$pLg`x?dBCe^1)K$<}E)`YRt(>M;9f z;q}olpxWV3UFJ9&{PPR1?t={XGVv&0ReqB~ATeaSy2(7E$0yWD++HUn3-(-}(YL~? zFPv;xrX@zO%m$d$6{V_H<*tWlmaj$zyA$K0d0S!*(#sb3$l=SxD@i;}@+WV4Y_^a*-iSpdS0|^arUrJeuE-d)*fyJEXnVXc zJJ{}zP(Y}3Y?hV&T$4;$+!SskiKFcA_=1tpNO{?CQewD9{`7Ql`j`8uDzpmJx~7U| zr@=G487Yq=*x0a7u^&daLHyH9C&ep?f<9WI)bbW3hGiH4^&jM8E>2{Mc-X1cTp=lW z8b3SfF(X46KdqksCB~0VT@e#A``xfNr#S0(h_}#dhVCOwJI}*DSo3$n^9=1gAE>SB zVQ3EkFRYNpkuy;tMkq>vM*6*I{C!X3ZcB}YNc?k9IopSp7c+Yh(c60UZ3erTnPV@( zw0pIeowu;;Pin~a3@iKK@Tv}`F#`>@HL205y`o>B_%&M$ZH*0z|7(b8#37JWc3hJ< zgB1$pJKM*{3zk${0iA zYD@WOf5J@oLBo|@enzABW$ceP0a}3KZ_j+t;k3cQpM$A_ZW`I2PGf#VdHtazc%D{b z!>l)v$ZuxD5p|~?U;N1md`1Oe=J zTGOx9YQ^%dr~)qr4Wh)E>V4FS$gWMAJ#dDCrsoF}^X#D<_-kaN2*5ALnh>BcyTyI= z8JGcImH`wW0eX%xRXcGbKy1({OPn#*QjnTZh?B`?Aq4PXHY90dx?ZAY3|{=U-^tAf z4US`}+lT5@LE@zi_p)vY-!oxYV;aZ1-=uIE(OjC*R?eHb z;$6Y-9_Mg(F0=izwck?=w*R9keX|3l@vcO!pJiP?q92xvgcbz%H<&~?N!;aBJ28RN zy4fKgm?v;Ep_ih6b-1H%?xFlu)s2-%Hkp2&FX@Ss&4zke_c=bAV`=&^UCSJ|`ojj= z^s(#u&x_%=JG0i?bg{lP{TKJ(+9c(69qiq4?RIT!Bd+ka1j?oRojxzjgf3;k2Ajln zyhEe9N$>P*v9Iybi8X*3sUWcmJhvx)07$&AFOy~x%K~r%MT-Q;p-ND65O2j2s>d2wZg<>EFgtENUFg5wyc;9!@=EZlNnsi`Q^x<{E z49+sywZM&-kR8wK2W^V7=1vB~-)&g13Gp_~HVtC9@^@BmTj5#lB||M3J?`LqD%eP7 z&V_xT4{(+AZic4por;VZ{qHwjTtUdKiEP9$cspB)_rG|1xYA&~Gk&I*6`hHDeq0hY zfxc$KkEAP}_)mpMX88$Ls4K(C00zs(^<2P#)ATxz3#{{O?;#|;eC8_%GcH(SX)?eJ zr|yO|JnkTp-a#n}#J$UDP7Xr8Tk0 zNyG@P0{ZH?*PGM^!{wA>)Z`-ffzo!npxqpNm4cGL7OzdH`zFF)@1G>XV6rwclvY&~ z+1AH<+uRRxl+}}e|0~2W0ow9Sb@HK@$p3ylpTI$838l&>z>~N-#1u#2z{H`TYJYZ?9}Ko*~^77A2-@pqAz{2;_;~W z=|y3AlhR)uIEv2Ba8XV}Ymy*2F4Mtw;g*!;H;)%1w#pLI36wB7n)?d|aVFnYXXx+L zRBh}j^Hhwn-HB%xcmn`ufnldtU9gbF?9`q0b(gN+A; z{7P9^?aE4?cB+{!EuQnN4-er*Yj}i}u>Dk0_n$P>-_nq~esN2A_4KMJojESUV*0RV zrf>82Tbl=WBBm2vCC}nQdm5Ur$5m^RIODi)6NARDT+8M-71+xiJ{#n1yo;}i1L%F+ z?v;;w2$`u&cjD(?5eiQ~xn$Ow*sZ)pm%+s>S}w-|wzfMQckYOaLn|*lK>5~&7d%~$ z0X`jyld^xKnyDy`A5f(zhhGo03!}OM-CsND0(X126hcHx6O%fR1()If22Q^ExU=-; zamc_(;Dh!C)P<6Ubxj|dcRhTKRJ!qqzh89jO+&rVB2D8FrA8OGm_bWdf0szi$>_2_ z!tT>^D?qs9tgJhBM&G!p!kQ$caIyJpSdQT2mc}lnR2P2)z@^jDOWUw#UE~jM)1yz? zy`Z*fK3p?+ymmsiAK7!Z%TResAMsZM_P=EKAMIu5!bLUqElOJmePN-gtNWv|T)9xA z9&9hQetmv@?CqYRRhduCopW`ibxTL?XO;ts539B=$!MCH|zJAN%~&0>EH*J$HVs`D!HYO1~7>50CqQ3vgADA}fyKAy)T)9~zzUqM5aK zZSl_USwAWM;^|a8ka|A)glY}C zFg}b5AaSRY!1%` z{+<#)rk*MMSU4=>SDf9TgCL*ZZ(!*hueu6-L?v<+I@;CxYN)u^Q4D!mZh=cI<0jbv x5o;qwnJ{wdVr^=E_*SBv$xt(I`VR$ex8j$>T@pEqPb=>udOAkhC0h2O{{^}AW;Or- diff --git a/logs/expt.log b/logs/expt.log deleted file mode 100644 index 2e5ee308f..000000000 --- a/logs/expt.log +++ /dev/null @@ -1,7 +0,0 @@ - 513 446633 - 769 1110301 - 1025 2414927 - 2049 14870787 - 2561 26299761 - 3073 44323310 - 4097 98934292 diff --git a/logs/expt.png b/logs/expt.png deleted file mode 100644 index 27c53eecf1afe22f40ccdb638942365ef595df77..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 7290 zcmY*;2{=^I+xX124uu*^T9^^pmr9f{W2sd36cRHkqJ&71m}|+BVj^3~j4hNxva~QG zin3-aTQk{Z8#`mh{a?T5|9#Kzo9E8C=f3A%&w01G6KidGYP-;GAp`=k{j`~>Edl|6 z2n3QT$OA(FQMDfU!N}U&?gRuuFoa5_Zr$hz1PIX)5Mp+gjz=^$B8)u$LUarQ#M41Y ziwMRc5O@#)fe;Dm%2QE+N%72fm~Qv(-G>h!wy>~pcXua|Na^Y6Wo2b_I=#8Md31CX z7Qs4nh&)Sv^LvbSp2dWq*}-tAqPBQ;7W##Nr6I1uBS|h!P9x6#KhJT}(!Q`N2t-SC z>l9*3MF`RQ6B18?NY*S6giavXpxdG5cQNqj115^+L-cp&#f>_jwmRhK`g#Z_FcJ%BfQKq zHl0oY?Y(~?VNU<`0R_}lo$?2g5i{>Z21~}?@_Iy;awISblSu%E$X8O{(_;`kwk!Mb`7^wggv6T8^mT5VrYQmFMF7n-ld% z?n;l&!ECh6Bl4deFR$G^<|-p*YU1qF;5u-#gan9*jykll2cv?K(jJ*5fW~m{wTtl~ z^w$yhg;vrDYxW^=Uk{GCp{ zOSF|AI6;S9x}8@@o_V4>t{CbR(4soq*4|_{1(0Nb3$-nZen-;TAq6p^SMJR%FFhi? zm`eP+(0F&#i2g;35`$8^+^Hg`f_pPG@c6Rr-^DAVhn)`e_%ZMHc4s9WO>7x@;4OA5 z{a%C3KIPW0m2aC?n;Oa%-%GSW3(kvKr(9G)SS3Ol$jP8#u-i6&21zV4UkW} zpw~~_?XVbBn|<)^^a;!@&6arceZ8k=4ruhQHnFDgWFce_qK^pAa0H}4j5=N3n;^5Lz= zRdre~2oVgn08+SacSHeQ?&aLe=YcL<6KARO3En>ejRm(`OAW@sr~Hq09@og%^bsiZ z``Y?0?HrP@u|>l+wIe=>Rn!yu9Rj`Ur!+wEipLL4(c)6S%CaHeQdgOeh0t5-e@CxHM{h&yd`rnVS4C4X~i-Iuw7#1fBqYfR{*&b?l%(woj3k?qXc8={ z`2|_M#H@uU^wF->hXbuVci7iG=RD#^#`RixWLjIV5xY{g4@#fAdq{L*Se92!X1vX; zn1?0xCAW#V?9(N&Hf<@$TeN$;Z9;GJZd;$`pr4d;$??L^0A)~kWdT0pgpF%UTD#rT zPwC+9n_ti@_8U{>7!pPZd)bQg0A+`e~zGG?xSdd8V8UM25+>53u#9QaJ59RQcJ`qdv6;?VWQa$c)* z9kRk}dJ8w?`ucH#yCfDj@AFKL%6{fPx$F04_zr2p{wpfI@e#Jt>R!-Dr>!~C+)^~Y ztXiP#9~7V(p8__-*&GJg{J&p!-e*Td53j%k=LZbt%C^5QZ{h8mJJY*uJX%c_b?t_z zd$ImU;ghUY&2pg5FeO_WS`29i5Xe>M{^s*>*U3Bmx7R<}nx1F~kg0g)6ddzn=||3;CBOhl zJN}_txQhF44^gvSo%y#)6^WC&)~Wln|4!J-3Z~wCb!oVY5#hL8$w*?&{d%yG&=_rX z?Jf?FYeHv3BoUW;rCxJw$LTJtN${A^+ObZJp5FI_Pqy`hAM_7|l$rXEeA=oB-s;4d z70stW=MUL~<tumC-qPteCktNL<*D4`O@Y-APc=wuMSEJ@@&?uEce$ZeO}pvhiunf5M*c2*ci zxEEOX*m^g}IQ~Jm26M;wU5+;0aL1UXnIo`ZNX_WJ-Gl~^(1<4(vb(vOX}$Tt7B6o! z^sl-Rz4Il%sV}MWgqv>XPpvS1j4LhFaLp`3k@u>c1J5qAurP>e@Vh?97%%f>UCIn; z=tv(&o*PFY9R(){N__4wjU(1%Cl?|?HE|`(_m0=K_aA*iHr0v#@{BUxW^4@mXB^gU z%`gGCE8iRX>k>Uc2^C1?d+51K&_O|$^0iz3%WBr;j(a_--X(Q1*RZSkqb^cMAGvZP zz^_C@;Wk!CspF|`wPA0^&J&Es{j#4w*{mL;Dfw2uMlH_uK&JQl9YJu96EmE!R)a@X zP3#Hs>c77;nf5@1rNHyX`o-`9+Zke*`5YG(^S!d6=3dMSG144zuZUKfImK(+L#gUc;Txc_U@$|>me>e6X-0j|D^7&397skryuZjEman_5=fsE*9N)3gJ zSzJp-(B=L8yzgIn#M`Wo4S4krvituGk8d2`82`fUZ$~4;7wVpnNfqar~cj0 zug>#Y9tp6Y!765p+N=+yf3vBs&)+Z)BfyxKt~K4~R@7z2+fC*Tb0+IW7|@3%Db7wo z2aQ&W>^8LI<#T1HWY5owzW7pUd>*Z}J%;2Rha zUa;kfMda%~_)PM}m?;8=FDhNJYERMjMzpQ4Ja1RR9M;M#z;s2k1cV`bO1Z)TD3@-9 zz>}Hej~F=&Av+Z{PgcxT$=;B9$0sgYgt0QSsFwkGH`o?dqCv*5Z`g2IhuV=9uVXs^ntf6nhDYG_vei6F}A;i`~+Fub`k`BHRE7wwi4j zrI-sRCkh3!TJ~9uh3d$#u8qt9KO~Dv_Y+hm$4KL&s=jusT zj1=$X2p58bG?PrRi(MEDA!=uku}5MX4HRM>`SC*j52VtPY$l>99TZr859OiC}67^xBv9JTr z=vuTPF;0Ah5&`g>tWCB~B&7*>i3vKGO+L1L3Rml6KNjY)fM$L7NFwh)vUo{r$Mak* zC{vY6QE$-4c%E5oTelQEknL%5o_@X|#|3v)ru4Sh!y(RDw)M`1$dQ-&P=Pre!%vOm1;G9tuH1=>He_P-_w(ybU=B)dY{kGD{r>ytD6K{J1c4uL1U%`&FlQFLnvULoOXpdLe0sVTjxsPITycwe zBG<$$l*dkvshvQ1!42Q>CsoAd+r!cUGl_`ykA!9a0~nl z%cOJ)74Fxl&80GBdt%;7?c6+8oJf-Hld8PU+_oKpqxRx;wDt1l%g+3v>{O9U*ddCE z>5?AHkoen1koOUv1hiM9R&w&JfH!$wbP)^ykjhV8G;hPvdBnI87acnxsB4TN?!7MV zD;dFb-M;&YC^85Cot7_@cB1sl%ce+h2WFHpti7Gx7Z*Fxku}OV$M^fY&#W8P!UVuD z_nCEy?YX?EP{X_5!o;g!Jr&Lp+S{LC$0>E%+Y(Og`?lzr<~a7GtO8?UA~LZ)uD8P= zgBIv;kl%CnJL@vA(gXSAC03P}E1V0~yqB{uu~cG9ouPXs8&pff7)Bj5>r`f_&Fecb zxrPT@$`)Dby`w|>YIrs&ix!&e*(h)V;%!ZE%aqF));&#riA6692R<)2xw^#`eU&Tx zw7@-mlq&*b@;F0)!mC&py{d>3QlL^HpaeJAlO}yQ`Bzz1`vEx{i>&q)(b($+CIc`C zD-r;a3!-#JxF*@VJK9&_1*LOgaGd0BDS8|j>6P7(?9Ohn zJjpFOr5RL==@A8+$6M=(_c(R>m=h{+pSm;m0Gzc9UcuAE91VDSLJ9Bj4=%W8J zaK13MXt#GEGVt6BlE__S{#&}atDn$t+I8s~r*u{`AE;-xVyt4MB-rEfR0mF1lk^B` zKHC$COJ#njJk+yy*PVRWw^>~ilqO8%{ARzK)|W$l{{h)e5{~lq#KKj;{NIvh8oTO59QzLB$%EZ}MH-7nhJQS_lU(e=>V~ zX_@ghK2I($cxyFp69v4DS75^>WoPCyuJ8xFlpb`D@fX{264t)qG7RMtbht68T>!Vp z4tmL3zi0CAKr$*~qlHTidAjDyn^}Bn&)9I1SLg&u-l7TtX5Gn&k{thFrNU2fG4U7g z#cBVQl`K$8rs#0|tEAM5s~xg+w?Cd3_tOmgDmOam@eP+BTx-@zet2gqJH~2{z+PwG z)A2l80or@A*8lhGVy8*P)SKkO_A&K*qBPr_1*;dHj0g`Fne`$0)A>gDd}1 z%;G!tP>(qmJD%|gALIB>@T^QJHDGl`znxI6-qE+%<|_W#`CgqT5Av?v z1cOE*O@l#nzk)UzZaMfZUEY2`P+wXQss3tlE-W-b!r`Pck+lA3T@^#ks$jh)B`gIO z(Th^|e!S#1EForn?nS88>iq)Hae#hJ5Z?UMt|7*pCbWKu)*w`p#P|d1WAp8XC|$+= z?Q;)6mn3+b{m$&$^yFr6f?t6s)8$|#RFH9N!57+Hw!sB_aOI`Qk<~joVx{{RBK7kC zD3tLJt_$f6wQ6<0DYQP4%ljO0vf{|WCGNSE>Yr_sS-H&9Slk*jZ>#IoniY6Eu zMhpGZX_84EC$DIlO*No$=yZ~A%a*98T;Z2+ce|vIfmMonOOh#TRphlLru5?BRb@Cl zwOE5;<*x7WU9^(N6a?T7PArwJ<}ON$X&K}$3*VVJkEf52moz!$_DJM8lbl@LIp@uz5v`Yl1*k%eok zQ#BRII5909I}KW2P3{&r6d5~_nm3Qe(+kM$n%?hgW%2YhYnJ9$Zp9u9QD5*q2$&%UE=KZbIy z?N|x;F5$7&%xq3RuXg+WEAImJfj(A&5PEiU%`x{pHB2Ad-u4(Tw8XeUJn~F2cVMiz z>PE5LG#iZ4S&S5aO?h}rqqRn3NvP0b9Hs0)+xgs(Zy_==+nSqb$ea&{dz~HM2D~!K zhqz~DT<6S>@?ABoJGmJ7G-zF&0Cz$K$*lfnv@JE1#_4k!tEv-YO%dEDou3C8pIMw+ zt(>^k5RVs{(0-;qhEkqha5B$mIt;Y%h%7MpVd43dwdjYTS>o27Mk#Q+ipN=riB6c< zv=C0)gtmo&bIRtp&7`ytXKy|;VTWg-586IlLLdpY){FV>96$TvePS$$uM?|h`)V{Q z0Xsf5Q=IW)ODZ0J_o2t8(!lj#fcJJDFZa3!TU@ODiQLlbuUmK{ylT|-{e}~3{D2;r zKx-?nJg{}x?K`!~LTSsrzeX>BiD1xkoHF6&O27vR>VDz{?kg{t1q*d-`E~CW3vJ%! ze8P*t8d$!S-{dK-#@t~HQ}*ih&AyVYlbZ*|eirv(=TKs-_-*VX?KAyIWbtVR=ZOE` zK@hZ;|5a?XCGn{$@jAEfKWAMC9Ox-_+yaU#Gp#OiFIE)8(ZO?i=G>xsOW!Z7Ril*h z@(qu7bNnNyQnLbrQ&Na7oYk=}LQ8!1{|1t$FY_epW4|v&gd7L*Jlj2uME1mtpibw= zM(sTXs9P6ygts@N6R-Z^Gl};PSH@VH9<(w`{3e<@sQN|7Ov}pbHrKbeTA>8&T8K3D z-t_I|Cba{JKhQhvahKq@nfT=+`BgDVQT}CU)wH3)ZCSE;COME@Yaj(AgvY{pU3VT> z-;08ME9Z%#d`gH1+ojz_pSX>?nbo$M(!;y0Sk~UkO$nIQRv@murI1D0LG5HPYbMD; zc4RR}0vVwb`mRY}*|E-7pN>0O4Y2=R>xu|ISa=TKcB}YvDgUaibr$HdaC6qEM&3@58N5+(Lu26VDQBSO zCP%9}qx63B#=nfizzJ1my@$MAjN5t}Lyhg%`9%ATz3equ>?{z5*Lr@CCU z$D`z}ULvaM>@GjTN3WGot&bjISAkZOyUlj~O3rzHLA$k>&cO^cxfrpo%S!9~njJJr zqg4cW$4&qI|8HJ>)nYQN9aBk_{)lQ|gjC!czx+yx_J$2lW*vJn z%KY<025`^rvIAEIW5ucg9<{hgkQ->~q`xyyqrtI2-1g7u-#!C1#gUH+mkU6NryH~9 z1UrBlb<*r{O=QcwkE)nZN~P#p#m=}jgn=QGRzJw~yEA7ZCnjpl2{|!e#SMlaSXUXvhc`o8a1)%<k? zL7wk7S1^qE_EY0pih+)(0M3w8*ywV;79kZr$A(JkredfgGUT&8-+%oL@qecm$2V%9 zKNq+a6%f1}tSi&IZMVCFbg)A0q9QFYhV4Dq%?>f*_;xmPkU5?q^WrW3$V!20%lsP& z*v)ZT@DZRnl5E)muTrTIQ1> z)sbOJQ*n9~>bRm#wQK2c|M{!Ol3gh~=B-Zc$>?p!;`5R=5cu*bAiF`44St-eEO$;) zrv`@nE_eDj8q{Zbt%MCOy5QIMutD`JEj&MLN-mBEP6p(xNK0wfy&6yay0__vz3DM& zzSX|t{`@wk#g-al87CC|{%HyEC(c+lddpZh(;L6dl?Axmb1#qn6h!xYE@0Ci)f@|?Rd~~il6cbFexBZVZSfe2UUuK#6 Ts)ih83wHX1rRiH^V)*|9RE7^# diff --git a/logs/expt_2k.log b/logs/expt_2k.log deleted file mode 100644 index 140b92f2c..000000000 --- a/logs/expt_2k.log +++ /dev/null @@ -1,6 +0,0 @@ - 521 533515 - 607 675230 - 1279 2560713 - 2203 7468422 - 3217 17314246 - 4253 33899969 diff --git a/logs/expt_2kl.log b/logs/expt_2kl.log deleted file mode 100644 index 1dc495f9e..000000000 --- a/logs/expt_2kl.log +++ /dev/null @@ -1,3 +0,0 @@ - 1024 2210287 - 2048 7940364 - 4096 35903891 diff --git a/logs/expt_dr.log b/logs/expt_dr.log deleted file mode 100644 index 3752ea81a..000000000 --- a/logs/expt_dr.log +++ /dev/null @@ -1,7 +0,0 @@ - 532 642330 - 784 1138699 - 1036 1972796 - 1540 3912241 - 2072 7075836 - 3080 16420867 - 4116 32477173 diff --git a/logs/invmod.log b/logs/invmod.log deleted file mode 100644 index 7d22449ef..000000000 --- a/logs/invmod.log +++ /dev/null @@ -1,8 +0,0 @@ - 240 58197 - 480 86617 - 720 255279 - 960 399626 - 1200 533330 - 1440 470046 - 1680 906754 - 1920 1132009 diff --git a/logs/invmod.png b/logs/invmod.png deleted file mode 100644 index 5c09e9012ada8048ee3bcd686b361c40b110f9df..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6294 zcmbVQcU+S1*9Od;;`*v-=J;BUOf1WhnrNDlqcROLG`IAL|(&X`W81D1k<0>%dx1VYoXAUcRZz`{Y@-5>++Uv#Vt z2o1-g>1rLh8Gbx%EryQ*=6EGLBx?UO^zxe}DiskUQ{>l1r9TO}1x_lMfsS z0#X5i`Vzh@gBU5&L0`VnMbhagt93M*ZVaNJLl(25*5@9y*84WZ^Ad>@1!x)iOAsNB zkO3N;ESOBSf?x85p+!Jw5fL;TxX@@9EZT*RX5pv$ziwdLpMOG`^*Fc<^^fyd+Z_4P5jIDepK?jX}EH$fo&4#o?d zd6Zug1QO#hGcvHdmAjh98(u6UV&ox3@cIspqvAhsAsuxlk13jh!}`rSjgAku>5zYv z|9e-!kW2Qz-|W8`@-?cbhNrcrT_*?>Uptqs1NN3U{Ew7;m6~GX)G{4_*MdXy@DqbA*KEbv@dIZAyx;BDQD;_#2@ z34O&)NBQ#Qg$OO0Sh8B;O z^zUaoq0sA}5|p@;J{Y|5m>sihZlYFU*hPw!2Doo*ujEw1oQLzPH5^p%Xc`rykd>PjJ zuqv9%+`nI@kt^%SNAiYp8osZu7_JMY-JQymgbA8)IX7+yWhRqP?BD0C(qc5i)wsVK zV?l7ju2|?qqxGi_e>nG+)6RrPoSiXwY!WkY&A;)QkCMr8ezz;RxLEENuc~&)ZzP76 zZ;kFw-#Gp6!~qEPcHYBhUmv)gam6%0Qg`0%-fD(A%lUPvMa1?j9hsc}+Q~3-WKIX#~WaTo-cv_jE+nH}}FPFtrHP zM(1xaLY2Z)50xE!@98{;{_oAl9W8#i-p`+3hjp2-0q7q-D-3^mtIzhvq1A@qG$aQ0 zm!6MmSS=pbbzRdCY);9p*ya6oGe!+Sp03-S@NrmCJsD!L(aJg0dK?o4kG_}q+;gbx z;|(2!X2+BXk`x`ne=Di73THv|IdnRJt;ge~?%P-MtJ@!;;J#{;8t3lN+@SLtT)ZtI z(}zEF5}gQ-@gA^Sm92%j-*X5KxLPmYPGhY1-Lw}c5bP^M3p>YG+RCe%uVh@}J=%o=C zK?mU;W+zU}B%sg?tN=r>*+t|ZmcOVzjpfhFV;ZtKu8#%klhf4NV8V8Xeff))W6J_@ ziibST&84zp8T-M7?47=yn-wXm|L!!6)Jm|g(nYuS8ZlrO|Jie_pme~SUp8oYi^R~k|vV6r3`5} zXTnCmuR@4|oF>-}EV?n%E|7ojqEWdp0nrm8d8}>MjWp-~Eke(}{XOV#ft^jv-lx63 z@eeIt1?W#9?U=i>-*Gw{PIS-CAFw&iIMu+P;T2C%ih^dif9L~Q(a7PvQx~Akn3C|o zpM+@YpVq2Bp8Iu+guh? zfH>Ne$SF0{vOR7Z+Uk8Mkugel!|;*c2`W8EmYVu^98DY7D99SDufLX(Ae3h0L|jX1 zbr~O)+KGFp!%tovUK6Q=t5UNoC)`S&rD&y8ARH9%u-Hg>K{Jjbw0*mU(U%4SYyE`- z{>ni!g4Mvy^sB5T{lm>JuiZG$a+99eX7xFOz-rBm4$!ZeI#wszg7K`?M<4hoelu|eIT`oU zEDqHiR?xs-J>{{6iZY+gPczFYjTB-n#k=$YX3{>n#Y}SR@nRwqdyKIKi3uo);jE#Ig`F6?V5^^#?xneh&Sp*xAl+dN^ZSs^M{B@vI2;#)f>&*>k=-5YrbI(VqWtUuU}9Cfu==UQaF}EGWfM%SMUtucq0N5GM9&+x7;f>C zK}v#V+_~tFTDg`diC)vyJfh1hw>eY~%W+5cV9+)rwWCm~*lo%6Ga_mVmQ*pTfW`M>G15Fwgk8Y-5SaB@U6xqif81g%u)6ztf6auO zb|9(4+mYu<@g5Ah4{^TD(A{It=l&JDVE%a~Kd`Zj7&WB-D&WOg@Xb^l zWzQg`^qKZ_+Tq+*XIQU*11w+uwy4`u)_-b>hmIE zguU$dn*Yp3AsU)KjH%2MAd*Cj$W~ad&&vo0Xv21#cOkmp=04gn{2Ja;GIp`L*9vR$ zc?HouJ$jlt!bZ3|WE{YfjaxOfOI`LtIv%r-;?)dgkJ%5RLk{(qq$A?h&I0weW5|G= zk3EKqixqHDjkz<6l))RYnGHY33&LAkE>Z<#vCSL&-WBXIsHcb+#VIx{S!^druASFr z8PtWTWc#*kZ=>iEg5KpNfFtdl{>c0hYvSwfs<{Nufv7^2EK#TLLXL3sFm?BuSA|8T zjNRppGJO48xgm6~@K2YQktTaC@|Wf3`D?-KYzxwO;Q@ify+7H}qZG+o_D+RU{(IWH z6^VylPI8>bh#7*@(PfBk7KjWWYzj`A*r$ZKj{tO?D>yZ0)i5VmTa9@qXigX-=s%&ju{2vA*>mk|`n@ zjOmB>82Q`WM}5P+iw{O--f{3+Q%^l%oh~ws*bYf9<2`upEV#zz5o&|I_Kiz)<$4p^ zQa7>5=f2jio0;`eWd7wKNj1q&3!1_)SLe9L2<+ot4c?=D{kFsdz}}51Qlb6Ely)k5 z2Nu+@?TF`ZNHVMiC+Q3;fxTIY^Kb?Un`txyz4s1zY)?-HVaH|}Ns$G9tgV$Y7MRQV zk73&0hViLks}fX<^@U?1OVS8CTke;XF0o-dgV+SbWy5HATPa6M9C13?N4dbAMlO2# zTd9e$zl~pwe@U3Dc!-&??|Wfh{fli*~A@-)Zxj79QoL#L%*=|syvta*E?AEZFtdMNe2T7%qm5i!yfzNe zsH41R9IC(Bo-CDS5a}5uQ`moI3~jjGbw4>u3yak}9M&RtTJYUc7pI-u*SAR7`MCKo znDjTv{P1Rs>WtHRcS6RiLJ!)9FYH^V_>^w24p8Q1gKrSYbk`>tN;|dkE?bm)E9}eL zzW6^-y)7?+0;H^7!O&||k)+=_csMGnAO!m2w*5z?fj+y7RF#2~WDX(O?1lf~Ax8hg@QtMS{Df*Z z9xu-hC?WJF=>`5)4^pzOvcgF1MYmU6TI<)?@d&A)CfvhgUmD%}Kv;vXOry^o;32au zk>Udz6MoWeMyY*0)3I5Cwsa!p^DfmZ6bzl~gX}C7D>wxlTx{ecgTqm%4V8LAHn`%| zb^qx0)*Z=))KcA2yn-&SRqE|ll*WU+vfwWA13dPg(I*4incr6eHe46nmkhX1k@@c` zDDMwPA-F_S?Trwzl-nO`CdTiTwkR#~Y_A=CKI`17-XgDmupEh+x*FhLap$-VaX$TL zu?DydZwU!7kDAL$9otuo#IzsPbS{#tr0TF$0BTh|OZ&pKys^@UuJ=65UXWPXYr!&n zEUfhPnHI>(UJTR6r8Hlkai|vIBJzS6(QySxSB4C%K|?SR#zB2Efx>==ar$nnq&9;X z|FF`~Z|BD0yewx#$mCeyxfR0NYd-wG4W)EBH2e}Orr zv$7Y!L`D=MNzACguNW?-k5>cbA%wwoJC0%uVIZG@)7)Yiq$n4X7?hD%)E&wvCg~$9 zOer(!P&g`$i6b=x(_mD!9k*x9$%ww(K)Jxoz0V3G&rJCa(WXD?=h~BrPD^Dtr75%sYkyLsEP6?xZJD^gtII?OlYdF$!oU z5{D@e(hssBNC_mB;%(s>RFI+E5=oqE_RM2_!DbBSX9OXlTA>JO`M7lg)t#5Pr)Rz$ zLNYIH=kNB0Q}~O|i|n(Lf?kKe)h%6JqBl;Wp5RO@T;51yW{J!?bd z13W>*=;!jYbr5A?wN%|S=*nJ5YVpKv%ohhTpS)!#KM{BKeh9AW=tcNacGA9C0@1hA zeqU{eB~dsWb;Z=i=S4Ir&}- zfGQM1#96F_Bp6 zrdi*?Q6QB9w#5L}r(^8J$f==YGQ>NtJi%oMu$_tw@o20MyF1CABa_FJW?pCxn6>Q` z0dvw40O4VsgC43l`5FMuG%<$QV1&xf!I$ihgmIBmD4FJbkb$;1C1-dz(!;g^U0V@q zE}EK$V9!vV(jT+u^x!f5^SV$MJW9G`>pH8Kz)J`oQf{C?#Jr01~to4 zFfC6K`=0uUa(a{mo|8gd>6rJb>FxV1bH-Tl_g2l7InUq%v>%6}jQ9QhKmB7SIOJ!P zYIEC&6nAAqA=imuc)AXUca}jCY5MDbKT87cOd%9v;&yo2-m5o6eOcpM>gqf%KR)Ao zA^y=&qBYl-KK|Q&@ZFUWx6!9z2FV`2qIC{+p03HWT_&5yA|auHB`L57u|-siBc1Ks z=qG{iy?ckRTN)&sN{`|xJ8NiuDtf)}Q$@+un#xbrree13@Pfz+O_qh$^i(;Mz^sSuSLk0VOXFrz3 zO6K0NENSUQ`x=wVsyfT*$d{L4lR&ISIUV=mDJ^g8MNY%_(1^^5OwZV4j{wmY2UTQU zpsg21tA7tVp=wRL^=?TzKKS{Ow>i~Uj~!{qIhY-G!BjnXmoOfxDd%40ch$o++2goU zXqC!jDB11LZrZN-bAIjcLhlDOOJUW5NzX&)gm*{Z3m9_ly&s2g9Lw^!t_nE6I4g!b zA$O}P=8tI(dv1jVpT!F*;W0Y=TFs77tX{z+5^002{B$CP%UK1t@by#mGWe`0u0AE> z5`0?Jae<>f#NI%<>G-@xxDj|9U6|}q=DOf^#V}qq%OZc3YSPoh*AM{m9qpqV*Tvcz z1*z9_ar`s3($G9V>bID_SF7dS#3kP3&=IWm_R6|jr0~~@QBq3i=8wm}_v$>FP4RS} z+kz9lirVjd+;7zQ`|1>rHeK5J`MY@W%Xt4P>eM*L$EWPDtVv}Dss?oj1o0HdKbNVYF?qi;lZlmeDsH| zRnKJFU=c@zI_dP*AEY47hZI%L;hhpT>uVgEB3Aj>uRls?Y{YEk-Sx3Yn%4q7s^1KK zel@8wLtdJW-&^&z-s+nhv>ex)a>GAbd*+iv1dfz9-=_ zg;tE{D`Cx4djnJf^okh2oU_n{cxTdfIc704iWYh+z@q+v*!a!Z2hWYi@$=2gYdetg z)oMN4d!V2Zj)~`?)sOO`U;lh^9jf)FZm`p@pZzIKhcMR`g}rpMDzNKNrN{T{GT}7= z(H%o|S1C))@vZ297TxWuxEp#cp7mAZ9787HdD#HAx?Y0TREt=P?#9Tr?<W^&rg8*Mq@Ty;Lsh36U8++FHxdtG kQl^L1{-X-hKf9cT+)>X?`OCTikIF%2#=t`<{X3LroU5W>HouU{uF1W4emwbq-004b4 z{p$ddiUdIaAc6BO0b;%bg%WfDCs4oDjORN`iLLb>4bcn-2h;gbLBeOi*2}GTfMHZV zD#aXZ=^+i}1VA}Cp5Fppz>igQV`bM>?{z%rl!_Eg`IgA4MJp8b|GrX=hW>2~&+lom7@~=a(oFB6zn`9t z6?qQU7hJnqOEJ2J$t-hap{0wtSmUVyQT)6C6q@TQff(_#vNO}`ODz^bl|wInrBVxH zT)D`08D91kdDY_pTVCqQ!mRhJqx$JaZFk4Vd5=f`8Qz%4o%(9+>V=dw;=hsooVm5fq?_#@)_?uER(w{IE&$5;uzpdw~3J)8A zJcB$i9rv>2RQfN#*I!mdcX^a3l6XR_2Mt6Pxr#Y+S^^2Wts@K0%{wH21sr zUWccwQppvK>OTjKQLxsp-=`YzbuUDk`&Lg6ke-dypj@~$}f zr{k|}xV@w?)1u&PQTRv|{cUwZ`NxeGO~LpL7su1p&8LbUPxBOOlUOLqwCY?aG2KVgpz>yd`0!2B&Z&Z4rQM+< z?mIkx1b;;|#6fj!J{aj40UhS&&~F^E%VrZ5^taK+`iMEv{slZ2(ybG^m2(=DfWsZv z?A4J)n}?~q(G@>X{_gQ1iGLt4^FlMrO;G#55TkA;MbqC;buNe*#OkR@-fE`xTNgw` zLKWW&gz8Yz6;PvpOrT0#x__zd#Q_DWtDR6A)aVlO1GHV%S$?v};~|qh4E^2x7M2BNue@TmSY1ScNLEC;!3ah zFkQrADEI}}z(=}2p1~IVlT)=psE)pBly_eC_(!3|4whI__1}r9qi64Moze;C~{Im(!>@>OC*88w_NHcaE zgdoOG0AHISb~AI$;Vr!D^}Yflbr{v0A@-TWt6-BeIqq*9gMMTc23@Hn7wfB!ZQlx1 zh~`mfyz=>sYb?DAvM_+fK%k^(lKYvy*ZXwuG?S5{Y(w8bgF1|!$k|m98~8pgOyHbJ z9o4l(?$HGSiEhGjdrxOVrq?}-Vu6q<4lUp^mBgZwnW!Rm*=Voz1RlFuHQDno;dwRj z5g$>ZO^!PzXA344OLl47t4=KeQ{Hn36(P<6wyJmV7ki(tf^-Zt5}}6#<4d8*D={1u z@8FPcPHzSBMbTsMF7?@g`fZRt`yiezLQ&QT3%94+J(S*(o%LCJM-dG^9?`k6NbtKk zjwXt|#r>v-lA^;#?JpfIJR|lq?({X=OebXU9_qW=g)kNxl4@2b)t_QpOljNZQXsoS zm3oBhCn`cz(Jp7Y#=$wkzcppY=!66-`oqM4(x?zNKJh&Kdah?gSF0K5vT=o%+KmJg zZziqewHT70MBgV^@hT>RoFoI$Cs1@pnMcXJ4)Ls`TkcajlHH&!vft8Dj$E)oS7-Nr zZI065{89rCqWl_bTX(OTWZxIV#stIHy?qr!*bKTnT+b{Ij^!Yrd#$03 z4fKnb)w>@t0s0d#$vxrGbm?y9@Paoo4aDW+N2OfZ1+q+o43Uv1Dpaqh_ah|K0kO;2-`Kp^ z*BUY7hvP7*&vY<-3&%8RB5VvIH1N62C3O&kGaE93QlqB3N_sr)5HQp+_lJYYlWva~ zh;?x{IuxZ34(57nn+o|RN)SIicz{o!q?8t>Yn;Fb#e_Jj&wl$6Av@Jt-~s=56|x-o z7S_vqySxo#od#(lXd4p)k3A8fyZpPsD?)$inD(YXGSK8z_ke5Yjgr-V#Lbd!r%+Up z7i2v4va|7;!kf$mnjIDyqHhgkn!mJ^M+g{B>eW9QzvHu5G+6l3Ag;w@)vY;?_K9Ab zy9b?jzBu;JcV z{kIS^f8MJ_|3mLfI3m--%q*i1$lP^B?}))$?>5{`1EJ!{2SThxIu84f!C8Rhr!*Xa z0ml@DvIp!4$Lp6Fo}tokx~p@0eGbhV1o-BjI{BnyGqCK2JEfsP<Y!Fd2y?$tJa(e8t5D?;Kta>(wu^!r?m?LLXJ)AUVbw4 z$BaK6DT01&0uLZO-oQpvT2VHt#1BvTDK!%G`JBt{$c)i7s@8K1FliB0;)q>z`Xedy za#52waA+ui>a``r{=%HQHRL?xw1C~|I{Rc&YtDNz?NcVl2pI$WeiDL>X$|K@YmSL? z;!_fF{G6zyO8DMdXqmCb8VbyE0phfUH=Z+SX+B3mi5)O%^aMXKFd||y-=>2KgzVBx2?~kZ-#Xv8^97cobUb@p{PBeuhWfK&;fqr6+@BnkyNM=7|IX0Ktd(#R1MIr56 ze49Q(#`-*k&j6?ch`cXI?gJVMoBC+n|6HAhZA?ZYM-cN-2_9X?k{IXP8r1` z)|#qpGnbKn;Hqyat}fjr;OOsS7C#}Y5MQw*&d6z|y)P+}{`B=GN{9ZV2yb>X?f4VSn!OtBwerzhOL9yD_8Y`> zy__di^Yk)3ZT~Z>{R82#X6II`w0fw$xTsjBBlWI9-S)nxE8Lj<4X~imgysH7gez?w zKlS=#maQvMMn*Y4K}p^2UKx`AzHbhz=axvm(sNGSvrtx|!xdS$b|gaB)Zh2wFWv>_-fn#^4}O=5g=wTuhbk7V85Lg%+l5TH}_W# z)%Q;5$K1_3(*_8yw7ui<5p%>Nz`1+*8K~`v#_#l#23p$rapNRdar0LOrI(1otV{W~ z`7bk(J8({5j4o629)p1I^*upQX6aQ z6HIv|(9~~kpSXQfif;-W;?O~$)Ab_A1@L2bEd)BLlb<}$W1oZ-E?j5iS>c z%yh(?Shaw|tYAc=&mHQDKEeBSgOYpKoY{o~pq-4I#ZxBn7a@(t^zUEN@;O@oQLs$$ zPkEZ0z&AV+#=)>X33g5yYEJVVD^Xrwoa#ft;I`_8APPU$y&L@u4Fw9aZp=(L|20?{H;_ z+#Xj-ufngZPifxU9EhHX=?C_^fWZ$LBsTF1Gxe^9vM#LQs3NONneGT-7}Re;srZE{ z^JX%z(U_7~|LnJ2Y4MlS@+x+E_iCHNkG8jwMWw^^i z1~TM>#10Y-`(p;SJZYJg;FRG?RYi!L zU^ic`Km7hMiOTgyf1nmPb`r?Hb|zP?sb3|oyL0WIC;RsN!~lzqrQjct_G+3k^lr7f zM2zy;C@31I3R{d_m3lX!vK)Is$d)Fg<+S%zGD0HMeeVJ)M@=5n%41^xuv9 zCKKjh31PaBet1Z&%c>AYmYC!8uOu_@^n$7_PWzKbE}C(xU7!+*hm!_IN8|Kj1VF)wnieR7WB|VQR2$`KGCp8jy&l!(t zzIF{$5vxH(orsVHTH_fSPDgxR_E`JqBLWHi)Zf4nH^;YLDC=(XwH+YmZGCzTdc1qt zfWybjfj8gxDom$SQdD8Nk9Uwz(*3~Jn|dg`{ERyGQ6x^mI5F7i6~%>4G`vpWpIxL2 zr+p{-bW+I>bIbduHNv9VDXE3VBG9I2<-#>*A2n*@AEzTBpPQc^*fOOSK-+fNWl(c@ zZSpAH+~7e|-N*@v#K}--7zs_z(useZ5o63LU-p)P}q-IPs zMz|hjYJq&4vWMvJ|M3=KVIdOr5seWv#g{?RGN`~obyj3@AP+qcPaIU9aCagzZg_J^ zI#!LUpQr)VSzi#G?tr62)hU#dj-Dr@n!@o58VH=AoJsViFx@u_T3Kc-p1SyHued0C z_cz?&D03QS{Bdih`5(tLC)x~}ITfM732vVvr;~o9V6LzASeruG4VcoVqj}imdbv0; zZyOe!Ik-421>Q?T-xMnT42!8Ep|dej9TRM7wNjeEo>6!?T z1)i1I;SZYlo`oN_X09A<=jF3G5*zuZYdKI`xFn8amE4|r#j}~eQ5#w(J~s!Ej)(xW z?+~}y>`72#7%vIr0cH^@c=pp}SEp!FTe;PZKEc$tKku`q#ivQhsWCw;Q2z& zMO<$BJG;z<`p=5jtqZ4b8%|YA1s;;*b2$8Nb2w*l)V3Pz`Fj7=$AR-*N5SuGXWm7~ zpKsi5whX`DuT%gjX@WD7tpc?6e9C;5Mi*j5Ry7Jafd9OY-2SwEfpqUio0An0N5%Ny zTx^ZaN~R71OlBqg$ZFqc)=7qJ61E!Bg-O#4p z#Q&w|u_eo(>LT`cc!p}HKLOnMKi0&`LS~-MF+-Oom1@5M*_CjNq4dj1sY!f1e*fC@ zxW7)KScNz@{Y4d_$m35=oWS{sOi~dlJ9AW(iF8NL1mSKsx8jJ&Gwaa>S!cj# zb>mH1VdpX!l3f~w@A**IL#%t1qfT;;ww=DISBuPqf=ASeP0F%QNlq{`Ud5E|{fxTy z_kiV$==G?NT9a7!{^Q`d|M-_r<0NNi`vVO5k_51-pGNRk6plXsDp8Z52 zC&Abh7djIB3||*by7Hw$e6}v_knZ$&lh?)fScYI^2aC;aM@69V?NhtVWcDjpH1_4g zc3JLgFp<{A_kQV@K3x*{5q^n;r1;L`qFzmW5Kemrqe5nOquA)Zzz6FvJGg3B3Aq`( z^Zp>bv$zhuzkT)Gxe~WA>f3FK7k>o7gI95kWF2LIhb_@2_++mgb}}3NtKsO~e(9;5 zZL6F-@>L7t?G2exzdA}C2qS0p6&UXN^V?YWcW4GN8(z-nV6{PD@&3^b&eTj*QM zRoW;(Q=VurkT$;e$P$)vIwQUj%12t>l@N$G4J6Jt^`v7V&u`0!5Wl6Yy#L}Z`f;4H zrfdCXeFX>me3$n$R{be*J+|Ih`^&};^jFia;;;f0xOh)VoRX&N@Uv#CiTN?QxZ35M z03riwlRp7d&p;8$D+m43|CVz5$i2${#l17vtDtjxRc=2V8H5A_ku?)ozLD+6Ez9As z@JmHdB^&WaE(0$0?GrZYDNK_PjVg@o$!bTu#CUFI zJL+c2&@;`rCz!k0N4)eK$3b9&Bfvj8s+p5v2fZsZ%si|7l&ph?$wy$c-cb-x|0pp* zWD-`}?xYbEhAx0|ytKHF-`}IATb(mUM6zl-28HFCgL_YMkH#J&dy}_mInDh~qKQTS=-m~45<)t3o@z{LCw}3Y@ z4|X|$nKLG;8qaBZ>L_v@#UHgI3xkj5?gGs!Ilhf84>nKve1X>WBv*3$ogPj~3a+{l z(5YID?CF3eY0s{;OU8HqqiQD6W1)AXCf3rx|Alt-4l@y zDtUEw8a|wOcQ5z(q+8{(U+l*lZe>mz&1GcYlJ=O(h$+XW-L!r-6Ax$Ni!S{tDzp{p zv60?URKc~%QaZF0{-i!^wlrZ0qgzIsBp-fJmOFazFq2m-DUdb^rXt1I&h^fSxBLVH z^q8Zm&?vhep0sc0VxTomIW{htxR?|AF_VhVx&s5?^ZVh*&MKQA2yW}YpFTRMh(s))MCga-Lx7zVq zE>fSj`5}YB{ExjSo{srpKT{&W7%}T_9Zno_5xP@&rWyux0?%M$JtophE{u`WNbx=c2Dn*22;1Qy26m<}K5Wtp>zohzl<Z;<*rq{xMA>?C#ki*mUo$!YzX9bzdHo z_&bH%NAX0T`yN;bd97vp}v zyL}~>NYRYlnCjXH1#8Y%(_MlKbHmrJA13U__!Fv7du3N-$-2|$a zp7_@6C`4a~EP2waA+RI=@awWPT!Blh2r|q2;&bZ%#oPaS2e}~&KXqI7x-!zg9!K*B z)wa-DdJD;7APC1BjeRk*tuO3kN{DqbsVrY9KSWe2_yJ>76HWyZ^GesZL_{(RoBF$^ z1E-L$W{X3wm&?^FMgNPEe^LK>C>XMDs94!bH;-v?=nqW~yeGI&Xu!4cYze;}t*qX4 zx)Kbt)se4@%=l%3c{i5i^=aFn{9rq~VnA-yp)4y5@l30(usJb)Lg&t*<1tb`*gsSw zf^RJQxjfz>>ZEGQ-t|YboYk6puHTqa78;VPILW7kkAHCJ{W;LjPGnhRB#Etf6=E}1cInp0_$A$rw^Tgc7`N}~VK@~j?6KQb_54r; z*wM&YkwouY7UpqHt%Sdl_?>%pgB`tD$tTTUq4@QxkEXBf`xbZxO#FrjqlXr{!^SVb z<&*l^9eoCm@Y&4%G5j@SY69?N_1WxIWaLV_ic)L(CQ>Zh|3+o5oSQ4B{r*hj&G+>ZO-b4Q z{Y!%1dT!HS&6qRnT2RYZrgTvSsbj~9_EQGMM2yr>PdT^vPA#XmuZQrb z-2aqBeK;mHo6h<$?&|E;N7oiEW0k)-Om{X9x9>A)|Mwf|={y3Eul?*mfaQ)V@trro NK-W~KO3V4>e*vgMc6k5* diff --git a/logs/mult_kara.log b/logs/mult_kara.log deleted file mode 100644 index 91b59cbfd..000000000 --- a/logs/mult_kara.log +++ /dev/null @@ -1,84 +0,0 @@ - 240 133 - 360 250 - 474 396 - 599 585 - 720 637 - 840 1045 - 960 1212 - 1080 1543 - 1196 1780 - 1320 2005 - 1436 2274 - 1560 2446 - 1680 1985 - 1800 2368 - 1920 2791 - 2038 3620 - 2160 3763 - 2278 3444 - 2400 4158 - 2516 5869 - 2640 6368 - 2753 5384 - 2876 7449 - 3000 6471 - 3114 8540 - 3240 7217 - 3360 9685 - 3476 6759 - 3599 8518 - 3714 8911 - 3840 12345 - 3960 9787 - 4079 11018 - 4196 12033 - 4319 12740 - 4440 12471 - 4558 15251 - 4678 13353 - 4798 15998 - 4920 13395 - 5040 13699 - 5160 14552 - 5280 14972 - 5400 15825 - 5520 16512 - 5639 17379 - 5757 17596 - 5879 18350 - 6000 18976 - 6115 19601 - 6240 20076 - 6354 20515 - 6480 21670 - 6600 22312 - 6716 22647 - 6839 23437 - 6960 24164 - 7080 24723 - 7199 25454 - 7320 26092 - 7440 26912 - 7557 27521 - 7677 28015 - 7800 28885 - 7919 29483 - 8040 30115 - 8160 31236 - 8280 31975 - 8400 30835 - 8520 31565 - 8639 32380 - 8760 32760 - 8879 33590 - 8996 34553 - 9119 35185 - 9239 36146 - 9358 36815 - 9480 39630 - 9596 43022 - 9720 41219 - 9840 41596 - 9960 42354 - 10080 43352 - 10200 43915 diff --git a/logs/sqr.log b/logs/sqr.log deleted file mode 100644 index 93234a145..000000000 --- a/logs/sqr.log +++ /dev/null @@ -1,84 +0,0 @@ - 240 114 - 359 174 - 478 241 - 600 311 - 720 399 - 840 494 - 960 599 - 1080 799 - 1200 931 - 1320 911 - 1440 1016 - 1560 1143 - 1680 1281 - 1800 1459 - 1918 1617 - 2039 1763 - 2159 1913 - 2279 2071 - 2399 2240 - 2518 2412 - 2640 2600 - 2760 2792 - 2877 3008 - 2999 3220 - 3119 3405 - 3239 3637 - 3359 3859 - 3480 4094 - 3600 4328 - 3717 4571 - 3838 4840 - 3960 5098 - 4080 5349 - 4200 5617 - 4320 5891 - 4440 6147 - 4560 6444 - 4680 6745 - 4800 7057 - 4918 7317 - 5039 7637 - 5160 12833 - 5280 10098 - 5397 8666 - 5520 8999 - 5639 9376 - 5758 9727 - 5880 9996 - 6000 10427 - 6118 10868 - 6240 12218 - 6359 14010 - 6478 14838 - 6593 16135 - 6719 16503 - 6840 13267 - 6960 13648 - 7080 14118 - 7199 14525 - 7320 14803 - 7439 15378 - 7558 15871 - 7680 57530 - 7800 59550 - 7916 61091 - 8039 63004 - 8160 61136 - 8279 62803 - 8398 68671 - 8520 71001 - 8638 71537 - 8759 74757 - 8880 77164 - 9000 78963 - 9119 80982 - 9239 83142 - 9357 85292 - 9480 88190 - 9600 90343 - 9718 86710 - 9840 88818 - 9954 91034 - 10079 93350 - 10197 95592 diff --git a/logs/sqr_kara.log b/logs/sqr_kara.log deleted file mode 100644 index da108973f..000000000 --- a/logs/sqr_kara.log +++ /dev/null @@ -1,84 +0,0 @@ - 240 115 - 360 175 - 480 241 - 600 312 - 719 397 - 839 494 - 960 597 - 1080 696 - 1200 794 - 1320 908 - 1439 1022 - 1560 1141 - 1678 1284 - 1797 1461 - 1918 1590 - 2040 1764 - 2160 1911 - 2278 2072 - 2399 2263 - 2516 2425 - 2640 2627 - 2756 2809 - 2880 3017 - 3000 3220 - 3119 3413 - 3239 3627 - 3359 3864 - 3479 4087 - 3600 4327 - 3720 4603 - 3840 4867 - 3957 5095 - 4079 5079 - 4200 5623 - 4319 5878 - 4439 6177 - 4560 6467 - 4679 6749 - 4800 7056 - 4920 7384 - 5039 7681 - 5159 8004 - 5280 8332 - 5399 8664 - 5520 8929 - 5638 9340 - 5760 9631 - 5879 10109 - 5999 10458 - 6118 10816 - 6240 11215 - 6359 11550 - 6478 11958 - 6600 12390 - 6718 12801 - 6838 13197 - 6959 13609 - 7079 14033 - 7199 16182 - 7320 16539 - 7440 16952 - 7559 16255 - 7679 17593 - 7800 17107 - 7920 17362 - 8037 17723 - 8159 18072 - 8280 19804 - 8399 18966 - 8519 19510 - 8640 19958 - 8760 20364 - 8878 20674 - 9000 21682 - 9120 21665 - 9237 21945 - 9359 22394 - 9480 23105 - 9598 23334 - 9718 25301 - 9840 26053 - 9960 26565 - 10079 26812 - 10200 27300 diff --git a/logs/sub.log b/logs/sub.log deleted file mode 100644 index 87c0160f8..000000000 --- a/logs/sub.log +++ /dev/null @@ -1,16 +0,0 @@ - 480 36 - 960 51 - 1440 64 - 1920 78 - 2400 90 - 2880 105 - 3360 118 - 3840 133 - 4320 146 - 4800 161 - 5280 182 - 5760 201 - 6240 201 - 6720 214 - 7200 228 - 7680 243 From 8e3a440464ebb9a54b121f765cbd500e928d051e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 13:41:30 +0100 Subject: [PATCH 088/304] use pre_gen/mp_all.c for profiled_single + clean-up defines --- makefile | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/makefile b/makefile index 7889c5ab7..8dd22ef8f 100644 --- a/makefile +++ b/makefile @@ -64,19 +64,18 @@ $(LIBNAME): $(OBJECTS) # # So far I've seen improvements in the MP math profiled: - make CFLAGS="$(CFLAGS) -fprofile-arcs -DTESTING" timing + make CFLAGS="$(CFLAGS) -fprofile-arcs" timing ./timing rm -f *.a *.o timing make CFLAGS="$(CFLAGS) -fbranch-probabilities" #make a single object profiled library -profiled_single: - cat *mp_*.c > mp_all.c - $(CC) $(LTM_CFLAGS) -fprofile-arcs -DTESTING -c mp_all.c -o mp_all.o - $(CC) $(LTM_CFLAGS) -DTESTING -DTIMER demo/timing.c mp_all.o -lgcov -o timing +profiled_single: pre_gen + $(CC) $(LTM_CFLAGS) -fprofile-arcs -c pre_gen/mp_all.c -o mp_all.o + $(CC) $(LTM_CFLAGS) demo/timing.c mp_all.o -lgcov -o timing ./timing rm -f *.o timing - $(CC) $(LTM_CFLAGS) -fbranch-probabilities -DTESTING -c mp_all.c -o mp_all.o + $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/mp_all.c -o mp_all.o $(AR) $(ARFLAGS) $(LIBNAME) mp_all.o ranlib $(LIBNAME) @@ -103,8 +102,8 @@ $(foreach demo, $(strip $(DEMOS)), $(eval $(call DEMO_template,$(demo)))) mtest: cd mtest ; $(CC) $(LTM_CFLAGS) -O0 mtest.c $(LTM_LFLAGS) -o mtest -timing: $(LIBNAME) demo/timing.c - $(CC) $(LTM_CFLAGS) -DTIMER demo/timing.c $(LIBNAME) $(LTM_LFLAGS) -o timing +timing: demo/timing.c $(LIBNAME) + $(CC) $(LTM_CFLAGS) $^ $(LTM_LFLAGS) -o timing tune: $(LIBNAME) $(MAKE) -C etc tune CFLAGS="$(LTM_CFLAGS)" From 04ee1e75d7061b9a0c076b553c89be5b84d1f61e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 15:07:58 +0100 Subject: [PATCH 089/304] improve demo/timing a bit * less verbose output on console * allow changing name for logs * pre-heat caches before starting the timing --- demo/timing.c | 90 ++++++++++++++++++++++++++++++++------------------- 1 file changed, 56 insertions(+), 34 deletions(-) diff --git a/demo/timing.c b/demo/timing.c index fa5669c72..854125095 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -20,6 +20,11 @@ #define LTM_TIMING_RAND_SEED 23 #endif +#ifndef MP_VERSION +#define MP_TIMING_VERSION +#else +#define MP_TIMING_VERSION "-" MP_VERSION +#endif static void ndraw(const mp_int *a, const char *name) { @@ -85,25 +90,28 @@ static uint64_t TIMFUNC(void) #endif } +#define DO2(x) x; x +#define DO4(x) DO2(x); DO2(x) +#define DO8(x) DO4(x); DO4(x) + #if 1 -#define DO(x) x; x; +#define DO(x) DO2(x) #else -#define DO2(x) x; x; -#define DO4(x) DO2(x); DO2(x); -#define DO8(x) DO4(x); DO4(x); -#define DO(x) DO8(x); DO8(x); +#define DO(x) DO8(x); DO8(x) #endif #ifdef TIMING_NO_LOGS -#define FOPEN(a, b) NULL +#define FOPEN(a, b) NULL #define FPRINTF(a,b,c,d) #define FFLUSH(a) -#define FCLOSE(a) (void)(a) +#define FCLOSE(a) (void)(a) +#define PRINTLN(fm,b,n,m) printf(fm "\n", b, n, m) #else -#define FOPEN(a,b) fopen(a,b) -#define FPRINTF(a,b,c,d) fprintf(a,b,c,d) -#define FFLUSH(a) fflush(a) -#define FCLOSE(a) fclose(a) +#define FOPEN(a,b) fopen(a,b) +#define FPRINTF(a,b,c,d) fprintf(a,b,c,d) +#define FFLUSH(a) fflush(a) +#define FCLOSE(a) fclose(a) +#define PRINTLN(fm,b,n,m) do { printf("\r" fm, b, n, m); fflush(stdout); }while(0) #endif static int should_test(const char *test, int argc, char **argv) @@ -178,19 +186,20 @@ int main(int argc, char **argv) return EXIT_FAILURE; } } while (++rr < 100u); - printf("Prime-check\t%s(%2d) => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - name, cnt, CLK_PER_SEC / tt, tt); + PRINTLN("Prime-check\t%s(%2d) => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + name, cnt, CLK_PER_SEC / tt, tt); } } } #endif if (should_test("add", argc, argv) != 0) { - log = FOPEN("logs/add.log", "w"); + log = FOPEN("logs/add" MP_TIMING_VERSION ".log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; mp_rand(&a, cnt); mp_rand(&b, cnt); + DO8(mp_add(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; do { @@ -200,20 +209,22 @@ int main(int argc, char **argv) if (tt > gg) tt = gg; } while (++rr < 100000u); - printf("Adding\t\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Adding\t\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF(log, "%6d %9" PRIu64 "\n", cnt * MP_DIGIT_BIT, tt); FFLUSH(log); } FCLOSE(log); + printf("\n"); } if (should_test("sub", argc, argv) != 0) { - log = FOPEN("logs/sub.log", "w"); + log = FOPEN("logs/sub" MP_TIMING_VERSION ".log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; mp_rand(&a, cnt); mp_rand(&b, cnt); + DO8(mp_sub(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; do { @@ -224,12 +235,13 @@ int main(int argc, char **argv) tt = gg; } while (++rr < 100000u); - printf("Subtracting\t\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Subtracting\t\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF(log, "%6d %9" PRIu64 "\n", cnt * MP_DIGIT_BIT, tt); FFLUSH(log); } FCLOSE(log); + printf("\n\n"); } if (should_test("mulsqr", argc, argv) != 0) { @@ -247,11 +259,13 @@ int main(int argc, char **argv) MP_TOOM_MUL_CUTOFF = (ix == 2) ? old_toom_m : 9999; MP_TOOM_SQR_CUTOFF = (ix == 2) ? old_toom_s : 9999; - log = FOPEN((ix == 0) ? "logs/mult.log" : (ix == 1) ? "logs/mult_kara.log" : "logs/mult_toom.log", "w"); + log = FOPEN((ix == 0) ? "logs/mult" MP_TIMING_VERSION ".log" : (ix == 1) ? "logs/mult_kara" MP_TIMING_VERSION ".log" : + "logs/mult_toom" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= (10240 / MP_DIGIT_BIT); cnt += 2) { SLEEP; mp_rand(&a, cnt); mp_rand(&b, cnt); + DO8(mp_mul(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; do { @@ -261,17 +275,20 @@ int main(int argc, char **argv) if (tt > gg) tt = gg; } while (++rr < 100u); - printf("Multiplying\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Multiplying\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF(log, "%6d %9" PRIu64 "\n", mp_count_bits(&a), tt); FFLUSH(log); } FCLOSE(log); + printf("\n"); - log = FOPEN((ix == 0) ? "logs/sqr.log" : (ix == 1) ? "logs/sqr_kara.log" : "logs/sqr_toom.log", "w"); + log = FOPEN((ix == 0) ? "logs/sqr" MP_TIMING_VERSION ".log" : (ix == 1) ? "logs/sqr_kara" MP_TIMING_VERSION ".log" : + "logs/sqr_toom" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= (10240 / MP_DIGIT_BIT); cnt += 2) { SLEEP; mp_rand(&a, cnt); + DO8(mp_sqr(&a, &b)); rr = 0u; tt = UINT64_MAX; do { @@ -281,12 +298,13 @@ int main(int argc, char **argv) if (tt > gg) tt = gg; } while (++rr < 100u); - printf("Squaring\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Squaring\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF(log, "%6d %9" PRIu64 "\n", mp_count_bits(&a), tt); FFLUSH(log); } FCLOSE(log); + printf("\n\n"); } } @@ -324,10 +342,10 @@ int main(int argc, char **argv) "1214855636816562637502584060163403830270705000634713483015101384881871978446801224798536155406895823305035467591632531067547890948695117172076954220727075688048751022421198712032848890056357845974246560748347918630050853933697792254955890439720297560693579400297062396904306270145886830719309296352765295712183040773146419022875165382778007040109957609739589875590885701126197906063620133954893216612678838507540777138437797705602453719559017633986486649523611975865005712371194067612263330335590526176087004421363598470302731349138773205901447704682181517904064735636518462452242791676541725292378925568296858010151852326316777511935037531017413910506921922450666933202278489024521263798482237150056835746454842662048692127173834433089016107854491097456725016327709663199738238442164843147132789153725513257167915555162094970853584447993125488607696008169807374736711297007473812256272245489405898470297178738029484459690836250560495461579533254473316340608217876781986188705928270735695752830825527963838355419762516246028680280988020401914551825487349990306976304093109384451438813251211051597392127491464898797406789175453067960072008590614886532333015881171367104445044718144312416815712216611576221546455968770801413440778423979", NULL }; - log = FOPEN("logs/expt.log", "w"); - logb = FOPEN("logs/expt_dr.log", "w"); - logc = FOPEN("logs/expt_2k.log", "w"); - logd = FOPEN("logs/expt_2kl.log", "w"); + log = FOPEN("logs/expt" MP_TIMING_VERSION ".log", "w"); + logb = FOPEN("logs/expt_dr" MP_TIMING_VERSION ".log", "w"); + logc = FOPEN("logs/expt_2k" MP_TIMING_VERSION ".log", "w"); + logd = FOPEN("logs/expt_2kl" MP_TIMING_VERSION ".log", "w"); for (n = 0; primes[n] != NULL; n++) { SLEEP; mp_read_radix(&a, primes[n], 10); @@ -340,6 +358,7 @@ int main(int argc, char **argv) mp_sub_d(&a, 1uL, &c); mp_mod(&b, &c, &b); mp_set(&c, 3uL); + DO8(mp_exptmod(&c, &b, &a, &d)); rr = 0u; tt = UINT64_MAX; do { @@ -358,8 +377,8 @@ int main(int argc, char **argv) draw(&d); exit(0); } - printf("Exponentiating\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Exponentiating\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF((n < 3) ? logd : (n < 9) ? logc : (n < 16) ? logb : log, "%6d %9" PRIu64 "\n", mp_count_bits(&a), tt); } @@ -367,10 +386,11 @@ int main(int argc, char **argv) FCLOSE(logb); FCLOSE(logc); FCLOSE(logd); + printf("\n"); } if (should_test("invmod", argc, argv) != 0) { - log = FOPEN("logs/invmod.log", "w"); + log = FOPEN("logs/invmod" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= 32; cnt += 4) { SLEEP; mp_rand(&a, cnt); @@ -381,6 +401,7 @@ int main(int argc, char **argv) mp_gcd(&a, &b, &c); } while (mp_cmp_d(&c, 1uL) != MP_EQ); + DO2(mp_invmod(&b, &a, &c)); rr = 0u; tt = UINT64_MAX; do { @@ -395,11 +416,12 @@ int main(int argc, char **argv) printf("Failed to invert\n"); return 0; } - printf("Inverting mod\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles\n", - mp_count_bits(&a), CLK_PER_SEC / tt, tt); + PRINTLN("Inverting mod\t%4d-bit => %9" PRIu64 "/sec, %9" PRIu64 " cycles", + mp_count_bits(&a), CLK_PER_SEC / tt, tt); FPRINTF(log, "%6d %9" PRIu64 "\n", cnt * MP_DIGIT_BIT, tt); } FCLOSE(log); + printf("\n"); } return 0; From 02f4ee114ca2669a5e894702ba666ea7f0057b03 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 15:23:34 +0100 Subject: [PATCH 090/304] compare logs before and after single-object profiling --- logs/Makefile | 9 ++++++++- logs/before_after.dem | 36 ++++++++++++++++++++++++++++++++++++ logs/before_after.html | 28 ++++++++++++++++++++++++++++ logs/index.html | 3 --- makefile | 9 +++++++-- 5 files changed, 79 insertions(+), 6 deletions(-) create mode 100644 logs/before_after.dem create mode 100644 logs/before_after.html diff --git a/logs/Makefile b/logs/Makefile index c2ebaf754..59987e519 100644 --- a/logs/Makefile +++ b/logs/Makefile @@ -1,2 +1,9 @@ all: - gnuplot graphs.dem + sed -e 's@\.log@-$(VERSION)\.log@g' graphs.dem > graphs-$(VERSION).dem + gnuplot graphs-$(VERSION).dem + +cmp: + gnuplot before_after.dem + +clean: + rm -f *-*.log *.png graphs-*.dem diff --git a/logs/before_after.dem b/logs/before_after.dem new file mode 100644 index 000000000..edb59da49 --- /dev/null +++ b/logs/before_after.dem @@ -0,0 +1,36 @@ +set terminal png +set ylabel "Cycles per Operation" +set xlabel "Operand size (bits)" + +set output "addsub-ba.png" +plot 'add-before.log' smooth bezier title "Addition (before)", \ + 'add-after.log' smooth bezier title "Addition (after)", \ + 'sub-before.log' smooth bezier title "Subtraction (before)", \ + 'sub-after.log' smooth bezier title "Subtraction (after)" + +set output "mult-ba.png" +plot 'mult-before.log' smooth bezier title "Multiplication (without Karatsuba) (before)", \ + 'mult-after.log' smooth bezier title "Multiplication (without Karatsuba) (after)", \ + 'mult_kara-before.log' smooth bezier title "Multiplication (Karatsuba) (before)", \ + 'mult_kara-after.log' smooth bezier title "Multiplication (Karatsuba) (after)" + +set output "sqr-ba.png" +plot 'sqr-before.log' smooth bezier title "Squaring (without Karatsuba) (before)", \ + 'sqr-after.log' smooth bezier title "Squaring (without Karatsuba) (after)", \ + 'sqr_kara-before.log' smooth bezier title "Squaring (Karatsuba) (before)", \ + 'sqr_kara-after.log' smooth bezier title "Squaring (Karatsuba) (after)" + +set output "expt-ba.png" +plot 'expt-before.log' smooth bezier title "Exptmod (Montgomery) (before)", \ + 'expt-after.log' smooth bezier title "Exptmod (Montgomery) (after)", \ + 'expt_dr-before.log' smooth bezier title "Exptmod (Dimminished Radix) (before)", \ + 'expt_dr-after.log' smooth bezier title "Exptmod (Dimminished Radix) (after)", \ + 'expt_2k-before.log' smooth bezier title "Exptmod (2k Reduction) (before)", \ + 'expt_2k-after.log' smooth bezier title "Exptmod (2k Reduction) (after)", \ + 'expt_2kl-before.log' smooth bezier title "Exptmod (2k-l Reduction) (before)", \ + 'expt_2kl-after.log' smooth bezier title "Exptmod (2k-l Reduction) (after)" + +set output "invmod-ba.png" +plot 'invmod-before.log' smooth bezier title "Modular Inverse (before)", \ + 'invmod-after.log' smooth bezier title "Modular Inverse (after)" + diff --git a/logs/before_after.html b/logs/before_after.html new file mode 100644 index 000000000..bc866f240 --- /dev/null +++ b/logs/before_after.html @@ -0,0 +1,28 @@ + + +LibTomMath Log Plots + + + +

Addition and Subtraction

+
+
+ +

Multiplication

+
+
+ +

Squaring

+
+
+ +

Exptmod

+
+
+ +

Modular Inverse

+
+
+ + + diff --git a/logs/index.html b/logs/index.html index 4b68c25a5..8c1ed9d88 100644 --- a/logs/index.html +++ b/logs/index.html @@ -22,6 +22,3 @@

Modular Inverse

-/* $Source: /cvs/libtom/libtommath/logs/index.html,v $ */ -/* $Revision: 1.2 $ */ -/* $Date: 2005/05/05 14:38:47 $ */ diff --git a/makefile b/makefile index 8dd22ef8f..9a2b36150 100644 --- a/makefile +++ b/makefile @@ -72,7 +72,7 @@ profiled: #make a single object profiled library profiled_single: pre_gen $(CC) $(LTM_CFLAGS) -fprofile-arcs -c pre_gen/mp_all.c -o mp_all.o - $(CC) $(LTM_CFLAGS) demo/timing.c mp_all.o -lgcov -o timing + $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"before\" demo/timing.c mp_all.o -lgcov -o timing ./timing rm -f *.o timing $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/mp_all.c -o mp_all.o @@ -117,13 +117,18 @@ coveralls: lcov docs manual: $(MAKE) -C doc/ $@ V=$(V) -.PHONY: pre_gen +.PHONY: pre_gen cmp pre_gen: mkdir -p pre_gen cat *mp_*.c > mp_all.c sed -e 's/[[:blank:]]*$$//' mp_all.c > pre_gen/mp_all.c rm mp_all.c +cmp: profiled_single + $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"after\" demo/timing.c $(LIBNAME) -lgcov -o timing + ./timing + $(MAKE) -C logs/ cmp + zipup: clean astyle new_file docs @# Update the index, so diff-index won't fail in case the pdf has been created. @# As the pdf creation modifies the tex files, git sometimes detects the From a598e61b9031db85049706b0f56a3003dbd6fc2c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 15:42:23 +0100 Subject: [PATCH 091/304] rename to tommath_amalgam.c --- makefile | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/makefile b/makefile index 9a2b36150..cb7ba210b 100644 --- a/makefile +++ b/makefile @@ -71,12 +71,12 @@ profiled: #make a single object profiled library profiled_single: pre_gen - $(CC) $(LTM_CFLAGS) -fprofile-arcs -c pre_gen/mp_all.c -o mp_all.o - $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"before\" demo/timing.c mp_all.o -lgcov -o timing + $(CC) $(LTM_CFLAGS) -fprofile-arcs -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o + $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"before\" demo/timing.c tommath_amalgam.o -lgcov -o timing ./timing rm -f *.o timing - $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/mp_all.c -o mp_all.o - $(AR) $(ARFLAGS) $(LIBNAME) mp_all.o + $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o + $(AR) $(ARFLAGS) $(LIBNAME) tommath_amalgam.o ranlib $(LIBNAME) install: $(LIBNAME) @@ -120,9 +120,7 @@ docs manual: .PHONY: pre_gen cmp pre_gen: mkdir -p pre_gen - cat *mp_*.c > mp_all.c - sed -e 's/[[:blank:]]*$$//' mp_all.c > pre_gen/mp_all.c - rm mp_all.c + cat *mp_*.c > pre_gen/tommath_amalgam.c cmp: profiled_single $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"after\" demo/timing.c $(LIBNAME) -lgcov -o timing From d800071e81a27714fc8d890cc28a112cc528361a Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 28 Oct 2019 16:36:40 +0100 Subject: [PATCH 092/304] ignore&clean tommath_amalgam.c [skip ci] --- .gitignore | 4 ++-- makefile_include.mk | 3 ++- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index c623fd05b..61495ec6f 100644 --- a/.gitignore +++ b/.gitignore @@ -60,8 +60,8 @@ UpgradeLog*.htm perf.data perf.data.old -# ignore mp_all.c generated by make -mp_all.c +# ignore tommath_amalgam.c generated by make +tommath_amalgam.c # ignore file generated by make tune tuning_list diff --git a/makefile_include.mk b/makefile_include.mk index b7946902e..4b5961c28 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -164,7 +164,8 @@ cleancov: cleancov-clean clean clean: rm -f *.gcda *.gcno *.gcov *.bat *.o *.a *.obj *.lib *.exe *.dll etclib/*.o \ demo/*.o test timing mtest_opponent mtest/mtest mtest/mtest.exe tuning_list \ - *.s mp_all.c *.da *.dyn *.dpi tommath.tex `find . -type f | grep [~] | xargs` *.lo *.la + *.s tommath_amalgam.c pre_gen/tommath_amalgam.c *.da *.dyn *.dpi tommath.tex \ + `find . -type f | grep [~] | xargs` *.lo *.la rm -rf .libs/ demo/.libs ${MAKE} -C etc/ clean MAKE=${MAKE} ${MAKE} -C doc/ clean MAKE=${MAKE} From b250ec44e043a870fcc15059fdb9a42d9f5d176c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 29 Oct 2019 13:24:34 +0100 Subject: [PATCH 093/304] clean-up test.c * no more `MP_WUR` in test.c * clean-up console output --- demo/mtest_opponent.c | 1 + demo/shared.c | 16 +- demo/shared.h | 1 - demo/test.c | 996 +++++++++++++++--------------------------- tommath.h | 2 +- 5 files changed, 364 insertions(+), 652 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 827c3f52e..e6bfb8ef3 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -1,3 +1,4 @@ +#define MP_WUR /* TODO: result checks disabled for now, T.b.d. if it should even be done here */ #include "shared.h" #ifdef LTM_MTEST_REAL_RAND diff --git a/demo/shared.c b/demo/shared.c index 834b3a99d..5ada4603a 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -4,8 +4,12 @@ void ndraw(const mp_int *a, const char *name) { char *buf; size_t size; + mp_err err; - mp_radix_size(a, 10, &size); + if ((err = mp_radix_size(a, 10, &size)) != MP_OKAY) { + fprintf(stderr, "\nndraw: mp_radix_size(a, 10, %zu) failed - %s\n", size, mp_error_to_string(err)); + exit(EXIT_FAILURE); + } buf = (char *)malloc(size); if (buf == NULL) { fprintf(stderr, "\nndraw: malloc(%zu) failed\n", size); @@ -13,9 +17,15 @@ void ndraw(const mp_int *a, const char *name) } printf("%s: ", name); - mp_to_decimal(a, buf, size); + if ((err = mp_to_decimal(a, buf, size)) != MP_OKAY) { + fprintf(stderr, "\nndraw: mp_to_decimal(a, buf, %zu) failed - %s\n", size, mp_error_to_string(err)); + exit(EXIT_FAILURE); + } printf("%s\n", buf); - mp_to_hex(a, buf, size); + if ((err = mp_to_hex(a, buf, size)) != MP_OKAY) { + fprintf(stderr, "\nndraw: mp_to_hex(a, buf, %zu) failed - %s\n", size, mp_error_to_string(err)); + exit(EXIT_FAILURE); + } printf("0x%s\n", buf); free(buf); diff --git a/demo/shared.h b/demo/shared.h index 14818acef..47c2c29be 100644 --- a/demo/shared.h +++ b/demo/shared.h @@ -14,7 +14,6 @@ #define LTM_DEMO_TEST_REDUCE_2K_L 0 #endif -#define MP_WUR /* TODO: result checks disabled for now */ #include "tommath_private.h" extern void ndraw(const mp_int* a, const char* name); diff --git a/demo/test.c b/demo/test.c index 0d9b07303..efffbd588 100644 --- a/demo/test.c +++ b/demo/test.c @@ -94,78 +94,62 @@ static int test_feature_detection(void) return EXIT_SUCCESS; } +#define EXPECT(a) do { if (!(a)) { fprintf(stderr, "%d: EXPECT(%s) failed\n", __LINE__, #a); goto LBL_ERR; } } while(0) +#define DO_WHAT(a, what) do { mp_err err; if ((err = (a)) != MP_OKAY) { fprintf(stderr, "%d: DO(%s) failed: %s\n", __LINE__, #a, mp_error_to_string(err)); what; } } while(0) +#define DO(a) DO_WHAT(a, goto LBL_ERR) +#define DOR(a) DO_WHAT(a, return EXIT_FAILURE) + static int test_trivial_stuff(void) { mp_int a, b, c, d; - mp_err e; - if ((e = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { - return EXIT_FAILURE; - } - (void)mp_error_to_string(e); + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); + EXPECT(mp_error_to_string(MP_OKAY) != NULL); /* a: 0->5 */ mp_set(&a, 5u); /* a: 5-> b: -5 */ - mp_neg(&a, &b); - if (mp_cmp(&a, &b) != MP_GT) { - goto LBL_ERR; - } - if (mp_cmp(&b, &a) != MP_LT) { - goto LBL_ERR; - } + DO(mp_neg(&a, &b)); + EXPECT(mp_cmp(&a, &b) == MP_GT); + EXPECT(mp_cmp(&b, &a) == MP_LT); + EXPECT(mp_isneg(&b)); /* a: 5-> a: -5 */ - mp_neg(&a, &a); - if (mp_cmp(&b, &a) != MP_EQ) { - goto LBL_ERR; - } + DO(mp_neg(&a, &a)); + EXPECT(mp_cmp(&b, &a) == MP_EQ); + EXPECT(mp_isneg(&a)); /* a: -5-> b: 5 */ - mp_abs(&a, &b); - if (mp_isneg(&b)) { - goto LBL_ERR; - } + DO(mp_abs(&a, &b)); + EXPECT(!mp_isneg(&b)); /* a: -5-> b: -4 */ - mp_add_d(&a, 1uL, &b); - if (!mp_isneg(&b)) { - goto LBL_ERR; - } - if (mp_get_i32(&b) != -4) { - goto LBL_ERR; - } - if (mp_get_u32(&b) != (uint32_t)-4) { - goto LBL_ERR; - } - if (mp_get_mag_u32(&b) != 4) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 1uL, &b)); + EXPECT(mp_isneg(&b)); + EXPECT(mp_get_i32(&b) == -4); + EXPECT(mp_get_u32(&b) == (uint32_t)-4); + EXPECT(mp_get_mag_u32(&b) == 4); /* a: -5-> b: 1 */ - mp_add_d(&a, 6uL, &b); - if (mp_get_u32(&b) != 1) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 6uL, &b)); + EXPECT(mp_get_u32(&b) == 1); /* a: -5-> a: 1 */ - mp_add_d(&a, 6uL, &a); - if (mp_get_u32(&a) != 1) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 6uL, &a)); + EXPECT(mp_get_u32(&a) == 1); mp_zero(&a); /* a: 0-> a: 6 */ - mp_add_d(&a, 6uL, &a); - if (mp_get_u32(&a) != 6) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 6uL, &a)); + EXPECT(mp_get_u32(&a) == 6); mp_set(&a, 42u); mp_set(&b, 1u); - mp_neg(&b, &b); + DO(mp_neg(&b, &b)); mp_set(&c, 1u); - mp_exptmod(&a, &b, &c, &d); + /* I expected this works, but somehow the computer sez no + * DO(mp_exptmod(&a, &b, &c, &d)); + */ + EXPECT(mp_exptmod(&a, &b, &c, &d) != MP_OKAY); mp_set(&c, 7u); - mp_exptmod(&a, &b, &c, &d); + /* same here */ + EXPECT(mp_exptmod(&a, &b, &c, &d) != MP_OKAY); - if (mp_iseven(&a) == mp_isodd(&a)) { - goto LBL_ERR; - } + EXPECT(mp_iseven(&a) != mp_isodd(&a)); mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_SUCCESS; @@ -177,19 +161,21 @@ static int test_trivial_stuff(void) static int check_get_set_i32(mp_int *a, int32_t b) { mp_clear(a); - if (mp_shrink(a) != MP_OKAY) return EXIT_FAILURE; + DO(mp_shrink(a)); mp_set_i32(a, b); - if (mp_shrink(a) != MP_OKAY) return EXIT_FAILURE; - if (mp_get_i32(a) != b) return EXIT_FAILURE; - if (mp_get_u32(a) != (uint32_t)b) return EXIT_FAILURE; - if (mp_get_mag_u32(a) != uabs32(b)) return EXIT_FAILURE; + DO(mp_shrink(a)); + EXPECT(mp_get_i32(a) == b); + EXPECT(mp_get_u32(a) == (uint32_t)b); + EXPECT(mp_get_mag_u32(a) == uabs32(b)); mp_set_u32(a, (uint32_t)b); - if (mp_get_u32(a) != (uint32_t)b) return EXIT_FAILURE; - if (mp_get_i32(a) != (int32_t)(uint32_t)b) return EXIT_FAILURE; + EXPECT(mp_get_u32(a) == (uint32_t)b); + EXPECT(mp_get_i32(a) == (int32_t)(uint32_t)b); return EXIT_SUCCESS; +LBL_ERR: + return EXIT_FAILURE; } static int test_mp_get_set_i32(void) @@ -197,9 +183,7 @@ static int test_mp_get_set_i32(void) int i; mp_int a; - if (mp_init(&a) != MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init(&a)); check_get_set_i32(&a, 0); check_get_set_i32(&a, -1); @@ -209,9 +193,7 @@ static int test_mp_get_set_i32(void) for (i = 0; i < 1000; ++i) { int32_t b = rand_int32(); - if (check_get_set_i32(&a, b) != EXIT_SUCCESS) { - goto LBL_ERR; - } + EXPECT(check_get_set_i32(&a, b) == EXIT_SUCCESS); } mp_clear(&a); @@ -244,9 +226,7 @@ static int test_mp_get_set_i64(void) int i; mp_int a; - if (mp_init(&a) != MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init(&a)); check_get_set_i64(&a, 0); check_get_set_i64(&a, -1); @@ -271,24 +251,15 @@ static int test_mp_get_set_i64(void) static int test_mp_fread_fwrite(void) { mp_int a, b; - mp_err e; FILE *tmp = NULL; - if ((e = mp_init_multi(&a, &b, NULL)) != MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); mp_set_ul(&a, 123456uL); tmp = tmpfile(); - if ((e = mp_fwrite(&a, 64, tmp)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_fwrite(&a, 64, tmp)); rewind(tmp); - if ((e = mp_fread(&b, 64, tmp)) != MP_OKAY) { - goto LBL_ERR; - } - if (mp_get_u32(&b) != 123456uL) { - goto LBL_ERR; - } + DO(mp_fread(&b, 64, tmp)); + EXPECT(mp_get_u32(&b) == 123456uL); fclose(tmp); mp_clear_multi(&a, &b, NULL); @@ -309,34 +280,24 @@ static int test_mp_rand(void) { mp_int a, b; int n; - mp_err err; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + mp_err e = MP_OKAY; + DOR(mp_init_multi(&a, &b, NULL)); mp_rand_source(very_random_source); for (n = 1; n < 1024; ++n) { - if ((err = mp_rand(&a, n)) != MP_OKAY) { - printf("Failed mp_rand() %s.\n", mp_error_to_string(err)); - break; - } - if ((err = mp_incr(&a)) != MP_OKAY) { - printf("Failed mp_incr() %s.\n", mp_error_to_string(err)); - break; - } - if ((err = mp_div_2d(&a, n * MP_DIGIT_BIT, &b, NULL)) != MP_OKAY) { - printf("Failed mp_div_2d() %s.\n", mp_error_to_string(err)); - break; - } + DO(mp_rand(&a, n)); + DO(mp_incr(&a)); + DO(mp_div_2d(&a, n * MP_DIGIT_BIT, &b, NULL)); if (mp_cmp_d(&b, 1) != MP_EQ) { ndraw(&a, "mp_rand() a"); ndraw(&b, "mp_rand() b"); - err = MP_ERR; + e = MP_ERR; break; } } +LBL_ERR: mp_rand_source(s_mp_rand_jenkins); mp_clear_multi(&a, &b, NULL); - return err == MP_OKAY ? EXIT_SUCCESS : EXIT_FAILURE; + return e == MP_OKAY ? EXIT_SUCCESS : EXIT_FAILURE; } static int test_mp_kronecker(void) @@ -372,18 +333,12 @@ static int test_mp_kronecker(void) long k, m; int i, cnt; - mp_err err; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); mp_set_ul(&a, 0uL); mp_set_ul(&b, 1uL); - if ((err = mp_kronecker(&a, &b, &i)) != MP_OKAY) { - printf("Failed executing mp_kronecker(0 | 1) %s.\n", mp_error_to_string(err)); - goto LBL_ERR; - } + DO(mp_kronecker(&a, &b, &i)); if (i != 1) { printf("Failed trivial mp_kronecker(0 | 1) %d != 1\n", i); goto LBL_ERR; @@ -394,11 +349,8 @@ static int test_mp_kronecker(void) /* only test positive values of a */ for (m = -10; m <= 10; m++) { mp_set_l(&b, m); - if ((err = mp_kronecker(&a, &b, &i)) != MP_OKAY) { - printf("Failed executing mp_kronecker(%ld | %ld) %s.\n", kronecker[cnt].n, m, mp_error_to_string(err)); - goto LBL_ERR; - } - if ((err == MP_OKAY) && (i != kronecker[cnt].c[m + 10])) { + DO(mp_kronecker(&a, &b, &i)); + if (i != kronecker[cnt].c[m + 10]) { printf("Failed trivial mp_kronecker(%ld | %ld) %d != %d\n", kronecker[cnt].n, m, i, kronecker[cnt].c[m + 10]); goto LBL_ERR; } @@ -417,14 +369,12 @@ static int test_mp_complement(void) int i; mp_int a, b, c; - if (mp_init_multi(&a, &b, &c, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); for (i = 0; i < 1000; ++i) { long l = rand_long(); mp_set_l(&a, l); - mp_complement(&a, &b); + DO(mp_complement(&a, &b)); l = ~l; mp_set_l(&c, l); @@ -447,9 +397,7 @@ static int test_mp_signed_rsh(void) int i; mp_int a, b, d; - if (mp_init_multi(&a, &b, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &d, NULL)); for (i = 0; i < 1000; ++i) { long l; @@ -462,7 +410,7 @@ static int test_mp_signed_rsh(void) mp_set_l(&d, l >> em); - mp_signed_rsh(&a, em, &b); + DO(mp_signed_rsh(&a, em, &b)); if (mp_cmp(&b, &d) != MP_EQ) { printf("\nmp_signed_rsh() bad result!"); goto LBL_ERR; @@ -482,9 +430,7 @@ static int test_mp_xor(void) int i; mp_int a, b, c, d; - if (mp_init_multi(&a, &b, &c, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); for (i = 0; i < 1000; ++i) { long l, em; @@ -497,7 +443,7 @@ static int test_mp_xor(void) mp_set_l(&d, l ^ em); - mp_xor(&a, &b, &c); + DO(mp_xor(&a, &b, &c)); if (mp_cmp(&c, &d) != MP_EQ) { printf("\nmp_xor() bad result!"); goto LBL_ERR; @@ -517,9 +463,7 @@ static int test_mp_or(void) int i; mp_int a, b, c, d; - if (mp_init_multi(&a, &b, &c, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); for (i = 0; i < 1000; ++i) { long l, em; @@ -532,7 +476,7 @@ static int test_mp_or(void) mp_set_l(&d, l | em); - mp_or(&a, &b, &c); + DO(mp_or(&a, &b, &c)); if (mp_cmp(&c, &d) != MP_EQ) { printf("\nmp_or() bad result!"); goto LBL_ERR; @@ -551,9 +495,7 @@ static int test_mp_and(void) int i; mp_int a, b, c, d; - if (mp_init_multi(&a, &b, &c, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); for (i = 0; i < 1000; ++i) { long l, em; @@ -566,7 +508,7 @@ static int test_mp_and(void) mp_set_l(&d, l & em); - mp_and(&a, &b, &c); + DO(mp_and(&a, &b, &c)); if (mp_cmp(&c, &d) != MP_EQ) { printf("\nmp_and() bad result!"); goto LBL_ERR; @@ -583,9 +525,7 @@ static int test_mp_and(void) static int test_mp_invmod(void) { mp_int a, b, c, d; - if (mp_init_multi(&a, &b, &c, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); /* mp_invmod corner-case of https://github.com/libtom/libtommath/issues/118 */ { @@ -631,9 +571,7 @@ static int test_mp_set_double(void) int i; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); /* test mp_get_double/mp_set_double */ if (mp_set_double(&a, +1.0/0.0) != MP_VAL) { @@ -689,9 +627,7 @@ static int test_mp_get_u32(void) int i; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < 1000; ++i) { t = (unsigned long)rand_long() & 0xFFFFFFFFuL; @@ -725,9 +661,7 @@ static int test_mp_get_ul(void) int i; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < ((int)MP_SIZEOF_BITS(unsigned long) - 1); ++i) { t = (1UL << (i+1)) - 1; @@ -758,9 +692,7 @@ static int test_mp_get_u64(void) int i; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < (int)(MP_SIZEOF_BITS(unsigned long long) - 1); ++i) { r = (1ULL << (i+1)) - 1; @@ -791,20 +723,18 @@ static int test_mp_sqrt(void) int i, n; mp_int a, b, c; - if (mp_init_multi(&a, &b, &c, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); for (i = 0; i < 1000; ++i) { printf("%6d\r", i); fflush(stdout); n = (rand_int() & 15) + 1; - mp_rand(&a, n); + DO(mp_rand(&a, n)); if (mp_sqrt(&a, &b) != MP_OKAY) { printf("\nmp_sqrt() error!"); goto LBL_ERR; } - mp_root_u32(&a, 2uL, &c); + DO(mp_root_u32(&a, 2uL, &c)); if (mp_cmp_mag(&b, &c) != MP_EQ) { printf("mp_sqrt() bad result!\n"); goto LBL_ERR; @@ -825,9 +755,7 @@ static int test_mp_is_square(void) mp_int a, b; bool res; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < 1000; ++i) { printf("%6d\r", i); @@ -835,8 +763,8 @@ static int test_mp_is_square(void) /* test mp_is_square false negatives */ n = (rand_int() & 7) + 1; - mp_rand(&a, n); - mp_sqr(&a, &a); + DO(mp_rand(&a, n)); + DO(mp_sqr(&a, &a)); if (mp_is_square(&a, &res) != MP_OKAY) { printf("\nfn:mp_is_square() error!"); goto LBL_ERR; @@ -847,7 +775,7 @@ static int test_mp_is_square(void) } /* test for false positives */ - mp_add_d(&a, 1uL, &a); + DO(mp_add_d(&a, 1uL, &a)); if (mp_is_square(&a, &res) != MP_OKAY) { printf("\nfp:mp_is_square() error!"); goto LBL_ERR; @@ -858,7 +786,6 @@ static int test_mp_is_square(void) } } - printf("\n\n"); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -883,9 +810,7 @@ static int test_mp_sqrtmod_prime(void) int i; mp_int a, b, c; - if (mp_init_multi(&a, &b, &c, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); /* r^2 = n (mod p) */ for (i = 0; i < (int)(sizeof(sqrtmod_prime)/sizeof(sqrtmod_prime[0])); ++i) { @@ -912,19 +837,17 @@ static int test_mp_sqrtmod_prime(void) static int test_mp_prime_rand(void) { int ix; - mp_err err; + mp_err e; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); /* test for size */ for (ix = 10; ix < 128; ix++) { printf("Testing (not safe-prime): %9d bits \r", ix); fflush(stdout); - err = mp_prime_rand(&a, 8, ix, (rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON); - if (err != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(err)); + e = mp_prime_rand(&a, 8, ix, (rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON); + if (e != MP_OKAY) { + printf("\nfailed with error: %s\n", mp_error_to_string(e)); goto LBL_ERR; } if (mp_count_bits(&a) != ix) { @@ -932,7 +855,6 @@ static int test_mp_prime_rand(void) goto LBL_ERR; } } - printf("\n"); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -944,50 +866,50 @@ static int test_mp_prime_rand(void) static int test_mp_prime_is_prime(void) { int ix; - mp_err err; + mp_err e; bool cnt, fu; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); /* strong Miller-Rabin pseudoprime to the first 200 primes (F. Arnault) */ - puts("Testing mp_prime_is_prime() with Arnault's pseudoprime 803...901 \n"); - mp_read_radix(&a, - "91xLNF3roobhzgTzoFIG6P13ZqhOVYSN60Fa7Cj2jVR1g0k89zdahO9/kAiRprpfO1VAp1aBHucLFV/qLKLFb+zonV7R2Vxp1K13ClwUXStpV0oxTNQVjwybmFb5NBEHImZ6V7P6+udRJuH8VbMEnS0H8/pSqQrg82OoQQ2fPpAk6G1hkjqoCv5s/Yr", - 64); - mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt); + printf("Testing mp_prime_is_prime() with Arnault's pseudoprime 803...901"); + DO(mp_read_radix(&a, + "91xLNF3roobhzgTzoFIG6P13ZqhOVYSN60Fa7Cj2jVR1g0k89zdahO9/kAiRprpfO1VAp1aBHucLFV/qLKLFb+zonV7R2Vxp1K13ClwUXStpV0oxTNQVjwybmFb5NBEHImZ6V7P6+udRJuH8VbMEnS0H8/pSqQrg82OoQQ2fPpAk6G1hkjqoCv5s/Yr", + 64)); + DO(mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt)); if (cnt) { printf("Arnault's pseudoprime is not prime but mp_prime_is_prime says it is.\n"); goto LBL_ERR; } /* About the same size as Arnault's pseudoprime */ - puts("Testing mp_prime_is_prime() with certified prime 2^1119 + 53\n"); + printf("\rTesting mp_prime_is_prime() with certified prime 2^1119 + 53 "); mp_set(&a, 1uL); - mp_mul_2d(&a,1119,&a); - mp_add_d(&a, 53uL, &a); - err = mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt); + DO(mp_mul_2d(&a,1119,&a)); + DO(mp_add_d(&a, 53uL, &a)); + e = mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt); /* small problem */ - if (err != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(err)); + if (e != MP_OKAY) { + printf("\nfailed with error: %s\n", mp_error_to_string(e)); } /* large problem */ if (!cnt) { printf("A certified prime is a prime but mp_prime_is_prime says it is not.\n"); } - if ((err != MP_OKAY) || !cnt) { + if ((e != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); - mp_fwrite(&a,16,stdout); + DO(mp_fwrite(&a,16,stdout)); putchar('\n'); goto LBL_ERR; } + printf("\r "); + for (ix = 16; ix < 128; ix++) { - printf("Testing ( safe-prime): %9d bits \r", ix); + printf("\rTesting ( safe-prime): %9d bits ", ix); fflush(stdout); - err = mp_prime_rand(&a, 8, ix, ((rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON) | MP_PRIME_SAFE); - if (err != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(err)); + e = mp_prime_rand(&a, 8, ix, ((rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON) | MP_PRIME_SAFE); + if (e != MP_OKAY) { + printf("\nfailed with error: %s\n", mp_error_to_string(e)); goto LBL_ERR; } if (mp_count_bits(&a) != ix) { @@ -995,52 +917,51 @@ static int test_mp_prime_is_prime(void) goto LBL_ERR; } /* let's see if it's really a safe prime */ - mp_sub_d(&a, 1uL, &b); - mp_div_2(&b, &b); - err = mp_prime_is_prime(&b, mp_prime_rabin_miller_trials(mp_count_bits(&b)), &cnt); + DO(mp_sub_d(&a, 1uL, &b)); + DO(mp_div_2(&b, &b)); + e = mp_prime_is_prime(&b, mp_prime_rabin_miller_trials(mp_count_bits(&b)), &cnt); /* small problem */ - if (err != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(err)); + if (e != MP_OKAY) { + printf("\nfailed with error: %s\n", mp_error_to_string(e)); } /* large problem */ if (!cnt) { printf("\nsub is not prime!\n"); } - mp_prime_frobenius_underwood(&b, &fu); + DO(mp_prime_frobenius_underwood(&b, &fu)); if (!fu) { printf("\nfrobenius-underwood says sub is not prime!\n"); } - if ((err != MP_OKAY) || !cnt) { + if ((e != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); - mp_fwrite(&a,16,stdout); + DO(mp_fwrite(&a,16,stdout)); putchar('\n'); printf("sub tested was: 0x"); - mp_fwrite(&b,16,stdout); + DO(mp_fwrite(&b,16,stdout)); putchar('\n'); goto LBL_ERR; } } /* Check regarding problem #143 */ - mp_read_radix(&a, - "FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A63A3620FFFFFFFFFFFFFFFF", - 16); - err = mp_prime_strong_lucas_selfridge(&a, &cnt); + DO(mp_read_radix(&a, + "FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A63A3620FFFFFFFFFFFFFFFF", + 16)); + e = mp_prime_strong_lucas_selfridge(&a, &cnt); /* small problem */ - if (err != MP_OKAY) { - printf("\nmp_prime_strong_lucas_selfridge failed with error: %s\n", mp_error_to_string(err)); + if (e != MP_OKAY) { + printf("\nmp_prime_strong_lucas_selfridge failed with error: %s\n", mp_error_to_string(e)); } /* large problem */ if (!cnt) { printf("\n\nissue #143 - mp_prime_strong_lucas_selfridge FAILED!\n"); } - if ((err != MP_OKAY) || !cnt) { + if ((e != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); - mp_fwrite(&a,16,stdout); + DO(mp_fwrite(&a,16,stdout)); putchar('\n'); goto LBL_ERR; } - printf("\n\n"); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -1053,122 +974,91 @@ static int test_mp_prime_is_prime(void) static int test_mp_prime_next_prime(void) { - mp_err err; mp_int a, b, c; - mp_init_multi(&a, &b, &c, NULL); + DOR(mp_init_multi(&a, &b, &c, NULL)); /* edge cases */ mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_prime_next_prime(&a, 5, false)); if (mp_cmp_d(&a, 2u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 2 but was: "); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } mp_set(&a, 0u); - if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_prime_next_prime(&a, 5, true)); if (mp_cmp_d(&a, 3u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 3 but was: "); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_prime_next_prime(&a, 5, false)); if (mp_cmp_d(&a, 3u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 3 but was: "); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } mp_set(&a, 2u); - if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_prime_next_prime(&a, 5, true)); if (mp_cmp_d(&a, 3u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 3 but was: "); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } mp_set(&a, 8); - if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_prime_next_prime(&a, 5, true)); if (mp_cmp_d(&a, 11u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 11 but was: "); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } /* 2^300 + 157 is a 300 bit large prime to guarantee a multi-limb bigint */ - if ((err = mp_2expt(&a, 300)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_2expt(&a, 300)); mp_set_u32(&b, 157); - if ((err = mp_add(&a, &b, &a)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_copy(&a, &b)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add(&a, &b, &a)); + DO(mp_copy(&a, &b)); /* 2^300 + 385 is the next prime */ mp_set_u32(&c, 228); - if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_prime_next_prime(&a, 5, false)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add(&b, &c, &b)); + DO(mp_prime_next_prime(&a, 5, false)); if (mp_cmp(&a, &b) != MP_EQ) { printf("mp_prime_next_prime: output should have been\n"); - mp_fwrite(&b,10,stdout); + DO(mp_fwrite(&b,10,stdout)); putchar('\n'); printf("but was:\n"); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } /* Use another temporary variable or recompute? Mmh... */ - if ((err = mp_2expt(&a, 300)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_2expt(&a, 300)); mp_set_u32(&b, 157); - if ((err = mp_add(&a, &b, &a)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_copy(&a, &b)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add(&a, &b, &a)); + DO(mp_copy(&a, &b)); /* 2^300 + 631 is the next prime congruent to 3 mod 4*/ mp_set_u32(&c, 474); - if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_prime_next_prime(&a, 5, true)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add(&b, &c, &b)); + DO(mp_prime_next_prime(&a, 5, true)); if (mp_cmp(&a, &b) != MP_EQ) { printf("mp_prime_next_prime (bbs): output should have been\n"); - mp_fwrite(&b,10,stdout); + DO(mp_fwrite(&b,10,stdout)); putchar('\n'); printf("but was:\n"); - mp_fwrite(&a,10,stdout); + DO(mp_fwrite(&a,10,stdout)); putchar('\n'); goto LBL_ERR; } @@ -1189,9 +1079,7 @@ static int test_mp_montgomery_reduce(void) /* size_t written; */ mp_int a, b, c, d, e; - if (mp_init_multi(&a, &b, &c, &d, &e, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, &e, NULL)); /* test montgomery */ for (i = 1; i <= 10; i++) { @@ -1200,30 +1088,30 @@ static int test_mp_montgomery_reduce(void) printf(" digit size: %2d\r", i); fflush(stdout); for (n = 0; n < 1000; n++) { - mp_rand(&a, i); + DO(mp_rand(&a, i)); a.dp[0] |= 1; /* let's see if R is right */ - mp_montgomery_calc_normalization(&b, &a); - mp_montgomery_setup(&a, &mp); + DO(mp_montgomery_calc_normalization(&b, &a)); + DO(mp_montgomery_setup(&a, &mp)); /* now test a random reduction */ for (ix = 0; ix < 100; ix++) { - mp_rand(&c, 1 + abs(rand_int()) % (2*i)); - mp_copy(&c, &d); - mp_copy(&c, &e); + DO(mp_rand(&c, 1 + abs(rand_int()) % (2*i))); + DO(mp_copy(&c, &d)); + DO(mp_copy(&c, &e)); - mp_mod(&d, &a, &d); - mp_montgomery_reduce(&c, &a, mp); - mp_mulmod(&c, &b, &a, &c); + DO(mp_mod(&d, &a, &d)); + DO(mp_montgomery_reduce(&c, &a, mp)); + DO(mp_mulmod(&c, &b, &a, &c)); if (mp_cmp(&c, &d) != MP_EQ) { /* *INDENT-OFF* */ printf("d = e mod a, c = e MOD a\n"); - mp_to_decimal(&a, buf, sizeof(buf)); printf("a = %s\n", buf); - mp_to_decimal(&e, buf, sizeof(buf)); printf("e = %s\n", buf); - mp_to_decimal(&d, buf, sizeof(buf)); printf("d = %s\n", buf); - mp_to_decimal(&c, buf, sizeof(buf)); printf("c = %s\n", buf); + DO(mp_to_decimal(&a, buf, sizeof(buf))); printf("a = %s\n", buf); + DO(mp_to_decimal(&e, buf, sizeof(buf))); printf("e = %s\n", buf); + DO(mp_to_decimal(&d, buf, sizeof(buf))); printf("d = %s\n", buf); + DO(mp_to_decimal(&c, buf, sizeof(buf))); printf("c = %s\n", buf); printf("compare no compare!\n"); goto LBL_ERR; /* *INDENT-ON* */ @@ -1237,8 +1125,6 @@ static int test_mp_montgomery_reduce(void) } } - printf("\n\n"); - mp_clear_multi(&a, &b, &c, &d, &e, NULL); return EXIT_SUCCESS; LBL_ERR: @@ -1251,15 +1137,14 @@ static int test_mp_read_radix(void) { char buf[4096]; size_t written; - mp_err err; mp_int a; - if (mp_init_multi(&a, NULL)!= MP_OKAY) goto LBL_ERR; + DOR(mp_init_multi(&a, NULL)); - if ((err = mp_read_radix(&a, "123456", 10)) != MP_OKAY) goto LBL_ERR; + DO(mp_read_radix(&a, "123456", 10)); - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; - printf(" '123456' a == %s, length = %zu\n", buf, written); + DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + printf(" '123456' a == %s, length = %zu", buf, written); /* See comment in mp_to_radix.c */ /* @@ -1272,20 +1157,20 @@ static int test_mp_read_radix(void) printf(" '123456' a == %s, length = %zu, error = %s\n", buf, written, mp_error_to_string(err)); */ - if ((err = mp_read_radix(&a, "-123456", 10)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; - printf(" '-123456' a == %s, length = %zu\n", buf, written); + DO(mp_read_radix(&a, "-123456", 10)); + DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + printf("\r '-123456' a == %s, length = %zu", buf, written); - if ((err = mp_read_radix(&a, "0", 10)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_to_radix(&a, buf, SIZE_MAX, &written, 10)) != MP_OKAY) goto LBL_ERR; - printf(" '0' a == %s, length = %zu\n", buf, written); + DO(mp_read_radix(&a, "0", 10)); + DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + printf("\r '0' a == %s, length = %zu", buf, written); while (0) { char *s = fgets(buf, sizeof(buf), stdin); if (s != buf) break; - mp_read_radix(&a, buf, 10); - mp_prime_next_prime(&a, 5, true); - mp_to_radix(&a, buf, sizeof(buf), NULL, 10); + DO(mp_read_radix(&a, buf, 10)); + DO(mp_prime_next_prime(&a, 5, true)); + DO(mp_to_radix(&a, buf, sizeof(buf), NULL, 10)); printf("%s, %lu\n", buf, (unsigned long)a.dp[0] & 3uL); } @@ -1301,9 +1186,7 @@ static int test_mp_cnt_lsb(void) int ix; mp_int a, b; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); mp_set(&a, 1uL); for (ix = 0; ix < 1024; ix++) { @@ -1311,7 +1194,7 @@ static int test_mp_cnt_lsb(void) printf("Failed at %d, %d\n", ix, mp_cnt_lsb(&a)); goto LBL_ERR; } - mp_mul_2(&a, &a); + DO(mp_mul_2(&a, &a)); } mp_clear_multi(&a, &b, NULL); @@ -1327,30 +1210,28 @@ static int test_mp_reduce_2k(void) int ix, cnt; mp_int a, b, c, d; - if (mp_init_multi(&a, &b, &c, &d, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); /* test mp_reduce_2k */ for (cnt = 3; cnt <= 128; ++cnt) { mp_digit tmp; - mp_2expt(&a, cnt); - mp_sub_d(&a, 2uL, &a); /* a = 2**cnt - 2 */ + DO(mp_2expt(&a, cnt)); + DO(mp_sub_d(&a, 2uL, &a)); /* a = 2**cnt - 2 */ printf("\r %4d bits", cnt); printf("(%d)", mp_reduce_is_2k(&a)); - mp_reduce_2k_setup(&a, &tmp); + DO(mp_reduce_2k_setup(&a, &tmp)); printf("(%lu)", (unsigned long) tmp); for (ix = 0; ix < 1000; ix++) { if (!(ix & 127)) { printf("."); fflush(stdout); } - mp_rand(&b, (cnt / MP_DIGIT_BIT + 1) * 2); - mp_copy(&c, &b); - mp_mod(&c, &a, &c); - mp_reduce_2k(&b, &a, 2uL); + DO(mp_rand(&b, (cnt / MP_DIGIT_BIT + 1) * 2)); + DO(mp_copy(&c, &b)); + DO(mp_mod(&c, &a, &c)); + DO(mp_reduce_2k(&b, &a, 2uL)); if (mp_cmp(&c, &b) != MP_EQ) { printf("FAILED\n"); goto LBL_ERR; @@ -1370,9 +1251,7 @@ static int test_mp_div_3(void) int cnt; mp_int a, b, c, d, e; - if (mp_init_multi(&a, &b, &c, &d, &e, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, &d, &e, NULL)); /* test mp_div_3 */ mp_set(&d, 3uL); @@ -1380,19 +1259,19 @@ static int test_mp_div_3(void) mp_digit r2; if (!(++cnt & 127)) { - printf("%9d\r", cnt); + printf("\r %9d", cnt); fflush(stdout); } - mp_rand(&a, abs(rand_int()) % 128 + 1); - mp_div(&a, &d, &b, &e); - mp_div_3(&a, &c, &r2); + DO(mp_rand(&a, abs(rand_int()) % 128 + 1)); + DO(mp_div(&a, &d, &b, &e)); + DO(mp_div_3(&a, &c, &r2)); if (mp_cmp(&b, &c) || mp_cmp_d(&e, r2)) { printf("\nmp_div_3 => Failure\n"); goto LBL_ERR; } } - printf("\nPassed div_3 testing"); + printf("... passed!"); mp_clear_multi(&a, &b, &c, &d, &e, NULL); return EXIT_SUCCESS; @@ -1409,14 +1288,12 @@ static int test_mp_dr_reduce(void) int ix; mp_int a, b, c; - if (mp_init_multi(&a, &b, &c, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); /* test the DR reduction */ for (cnt = 2; cnt < 32; cnt++) { printf("\r%d digit modulus", cnt); - mp_grow(&a, cnt); + DO(mp_grow(&a, cnt)); mp_zero(&a); for (ix = 1; ix < cnt; ix++) { a.dp[ix] = MP_MASK; @@ -1424,8 +1301,8 @@ static int test_mp_dr_reduce(void) a.used = cnt; a.dp[0] = 3; - mp_rand(&b, cnt - 1); - mp_copy(&b, &c); + DO(mp_rand(&b, cnt - 1)); + DO(mp_copy(&b, &c)); rr = 0; do { @@ -1433,13 +1310,13 @@ static int test_mp_dr_reduce(void) printf("."); fflush(stdout); } - mp_sqr(&b, &b); - mp_add_d(&b, 1uL, &b); - mp_copy(&b, &c); + DO(mp_sqr(&b, &b)); + DO(mp_add_d(&b, 1uL, &b)); + DO(mp_copy(&b, &c)); - mp_mod(&b, &a, &b); + DO(mp_mod(&b, &a, &b)); mp_dr_setup(&a, &mp); - mp_dr_reduce(&c, &a, mp); + DO(mp_dr_reduce(&c, &a, mp)); if (mp_cmp(&b, &c) != MP_EQ) { printf("Failed on trial %u\n", rr); @@ -1464,52 +1341,50 @@ static int test_mp_reduce_2k_l(void) int cnt; char buf[4096]; size_t length[1]; - if (mp_init_multi(&a, &b, NULL)!= MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &b, NULL)); /* test the mp_reduce_2k_l code */ # if LTM_DEMO_TEST_REDUCE_2K_L == 1 /* first load P with 2^1024 - 0x2A434 B9FDEC95 D8F9D550 FFFFFFFF FFFFFFFF */ - mp_2expt(&a, 1024); - mp_read_radix(&b, "2A434B9FDEC95D8F9D550FFFFFFFFFFFFFFFF", 16); - mp_sub(&a, &b, &a); + DO(mp_2expt(&a, 1024)); + DO(mp_read_radix(&b, "2A434B9FDEC95D8F9D550FFFFFFFFFFFFFFFF", 16)); + DO(mp_sub(&a, &b, &a)); # elif LTM_DEMO_TEST_REDUCE_2K_L == 2 /* p = 2^2048 - 0x1 00000000 00000000 00000000 00000000 4945DDBF 8EA2A91D 5776399B B83E188F */ - mp_2expt(&a, 2048); - mp_read_radix(&b, - "1000000000000000000000000000000004945DDBF8EA2A91D5776399BB83E188F", - 16); - mp_sub(&a, &b, &a); + DO(mp_2expt(&a, 2048)); + DO(mp_read_radix(&b, + "1000000000000000000000000000000004945DDBF8EA2A91D5776399BB83E188F", + 16)); + DO(mp_sub(&a, &b, &a)); # else # error oops # endif *length = sizeof(buf); - mp_to_radix(&a, buf, length, 10); + DO(mp_to_radix(&a, buf, length, 10)); printf("\n\np==%s, length = %zu\n", buf, *length); /* now mp_reduce_is_2k_l() should return */ if (mp_reduce_is_2k_l(&a) != 1) { printf("mp_reduce_is_2k_l() return 0, should be 1\n"); goto LBL_ERR; } - mp_reduce_2k_setup_l(&a, &d); + DO(mp_reduce_2k_setup_l(&a, &d)); /* now do a million square+1 to see if it varies */ - mp_rand(&b, 64); - mp_mod(&b, &a, &b); - mp_copy(&b, &c); + DO(mp_rand(&b, 64)); + DO(mp_mod(&b, &a, &b)); + DO(mp_copy(&b, &c)); printf("Testing: mp_reduce_2k_l..."); fflush(stdout); for (cnt = 0; cnt < (int)(1uL << 20); cnt++) { - mp_sqr(&b, &b); - mp_add_d(&b, 1uL, &b); - mp_reduce_2k_l(&b, &a, &d); - mp_sqr(&c, &c); - mp_add_d(&c, 1uL, &c); - mp_mod(&c, &a, &c); + DO(mp_sqr(&b, &b)); + DO(mp_add_d(&b, 1uL, &b)); + DO(mp_reduce_2k_l(&b, &a, &d)); + DO(mp_sqr(&c, &c)); + DO(mp_add_d(&c, 1uL, &c)); + DO(mp_mod(&c, &a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("mp_reduce_2k_l() failed at step %d\n", cnt); - mp_to_hex(&b, buf, sizeof(buf)); + DO(mp_to_hex(&b, buf, sizeof(buf))); printf("b == %s\n", buf); - mp_to_hex(&c, buf, sizeof(buf)); + DO(mp_to_hex(&c, buf, sizeof(buf))); printf("c == %s\n", buf); goto LBL_ERR; } @@ -1542,9 +1417,7 @@ static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) *size = (uint32_t)mp_count_bits(a) + 1u; return MP_OKAY; } - if ((res = mp_init_copy(&t, a)) != MP_OKAY) { - return res; - } + DOR(mp_init_copy(&t, a)); t.sign = MP_ZPOS; while (!mp_iszero(&t)) { if ((res = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { @@ -1564,9 +1437,7 @@ static int test_mp_log_u32(void) uint32_t base, lb, size; const uint32_t max_base = MP_MIN(UINT32_MAX, MP_DIGIT_MAX); - if (mp_init(&a) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init(&a)); /* base a result @@ -1597,9 +1468,7 @@ static int test_mp_log_u32(void) for (d = 1; d < 4; d++) { mp_set(&a, d); - if (mp_log_u32(&a, base, &lb) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_log_u32(&a, base, &lb)); if (lb != ((d == 1)?0uL:1uL)) { goto LBL_ERR; } @@ -1618,9 +1487,7 @@ static int test_mp_log_u32(void) } for (d = 1; d < 4; d++) { mp_set(&a, d); - if (mp_log_u32(&a, base, &lb) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_log_u32(&a, base, &lb)); if (lb != ((d < base)?0uL:1uL)) { goto LBL_ERR; } @@ -1631,16 +1498,10 @@ static int test_mp_log_u32(void) The range of bases tested allows to check with radix_size. */ - if (mp_rand(&a, 10) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 10)); for (base = 2u; base < 65u; base++) { - if (mp_log_u32(&a, base, &lb) != MP_OKAY) { - goto LBL_ERR; - } - if (s_rs(&a,(int)base, &size) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_log_u32(&a, base, &lb)); + DO(s_rs(&a,(int)base, &size)); /* radix_size includes the memory needed for '\0', too*/ size -= 2; if (lb != size) { @@ -1652,16 +1513,10 @@ static int test_mp_log_u32(void) bases 2..64 with "a" a random small constant to test the part of mp_ilogb that uses native types. */ - if (mp_rand(&a, 1) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 1)); for (base = 2u; base < 65u; base++) { - if (mp_log_u32(&a, base, &lb) != MP_OKAY) { - goto LBL_ERR; - } - if (s_rs(&a,(int)base, &size) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_log_u32(&a, base, &lb)); + DO(s_rs(&a,(int)base, &size)); size -= 2; if (lb != size) { goto LBL_ERR; @@ -1670,15 +1525,9 @@ static int test_mp_log_u32(void) /*Test upper edgecase with base UINT32_MAX and number (UINT32_MAX/2)*UINT32_MAX^10 */ mp_set(&a, max_base); - if (mp_expt_u32(&a, 10uL, &a) != MP_OKAY) { - goto LBL_ERR; - } - if (mp_add_d(&a, max_base / 2, &a) != MP_OKAY) { - goto LBL_ERR; - } - if (mp_log_u32(&a, max_base, &lb) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_expt_u32(&a, 10uL, &a)); + DO(mp_add_d(&a, max_base / 2, &a)); + DO(mp_log_u32(&a, max_base, &lb)); if (lb != 10u) { goto LBL_ERR; } @@ -1693,17 +1542,12 @@ static int test_mp_log_u32(void) static int test_mp_incr(void) { mp_int a, b; - mp_err e = MP_OKAY; - if ((e = mp_init_multi(&a, &b, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, NULL)); /* Does it increment inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); - if ((e = mp_incr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_incr(&a)); if (mp_cmp_d(&a, (MP_MASK/2uL) + 1uL) != MP_EQ) { goto LBL_ERR; } @@ -1711,12 +1555,8 @@ static int test_mp_incr(void) /* Does it increment outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); mp_set(&b, MP_MASK); - if ((e = mp_incr(&a)) != MP_OKAY) { - goto LBL_ERR; - } - if ((e = mp_add_d(&b, 1uL, &b)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_incr(&a)); + DO(mp_add_d(&b, 1uL, &b)); if (mp_cmp(&a, &b) != MP_EQ) { goto LBL_ERR; } @@ -1724,22 +1564,16 @@ static int test_mp_incr(void) /* Does it increment from -1 to 0? */ mp_set(&a, 1uL); a.sign = MP_NEG; - if ((e = mp_incr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_incr(&a)); if (mp_cmp_d(&a, 0uL) != MP_EQ) { goto LBL_ERR; } /* Does it increment from -(MP_MASK + 1) to -MP_MASK? */ mp_set(&a, MP_MASK); - if ((e = mp_add_d(&a, 1uL, &a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 1uL, &a)); a.sign = MP_NEG; - if ((e = mp_incr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_incr(&a)); if (a.sign != MP_NEG) { goto LBL_ERR; } @@ -1758,38 +1592,27 @@ static int test_mp_incr(void) static int test_mp_decr(void) { mp_int a, b; - mp_err e = MP_OKAY; - if ((e = mp_init_multi(&a, &b, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, NULL)); /* Does it decrement inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); - if ((e = mp_decr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_decr(&a)); if (mp_cmp_d(&a, (MP_MASK/2uL) - 1uL) != MP_EQ) { goto LBL_ERR; } /* Does it decrement outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); - if ((e = mp_add_d(&a, 1uL, &a)) != MP_OKAY) { - goto LBL_ERR; - } - if ((e = mp_decr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_add_d(&a, 1uL, &a)); + DO(mp_decr(&a)); if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { goto LBL_ERR; } /* Does it decrement from 0 to -1? */ mp_zero(&a); - if ((e = mp_decr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_decr(&a)); if (a.sign == MP_NEG) { a.sign = MP_ZPOS; if (mp_cmp_d(&a, 1uL) != MP_EQ) { @@ -1805,12 +1628,8 @@ static int test_mp_decr(void) a.sign = MP_NEG; mp_set(&b, MP_MASK); b.sign = MP_NEG; - if ((e = mp_sub_d(&b, 1uL, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((e = mp_decr(&a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_sub_d(&b, 1uL, &b)); + DO(mp_decr(&a)); if (mp_cmp(&a, &b) != MP_EQ) { goto LBL_ERR; } @@ -1848,7 +1667,6 @@ static int test_mp_decr(void) static int test_mp_root_u32(void) { mp_int a, c, r; - mp_err e; int i, j; const char *input[] = { @@ -2034,14 +1852,12 @@ static int test_mp_root_u32(void) } }; - if ((e = mp_init_multi(&a, &c, &r, NULL)) != MP_OKAY) { - return EXIT_FAILURE; - } + DOR(mp_init_multi(&a, &c, &r, NULL)); for (i = 0; i < 10; i++) { - mp_read_radix(&a, input[i], 64); + DO(mp_read_radix(&a, input[i], 64)); for (j = 3; j < 100; j++) { - mp_root_u32(&a, (uint32_t)j, &c); - mp_read_radix(&r, root[i][j-3], 10); + DO(mp_root_u32(&a, (uint32_t)j, &c)); + DO(mp_read_radix(&r, root[i][j-3], 10)); if (mp_cmp(&r, &c) != MP_EQ) { fprintf(stderr, "mp_root_u32 failed at input #%d, root #%d\n", i, j); goto LBL_ERR; @@ -2058,7 +1874,6 @@ static int test_mp_root_u32(void) static int test_s_mp_balance_mul(void) { mp_int a, b, c; - mp_err e = MP_OKAY; const char *na = "4b0I5uMTujCysw+1OOuOyH2FX2WymrHUqi8BBDb7XpkV/4i7vXTbEYUy/kdIfCKu5jT5JEqYkdmnn3jAYo8XShPzNLxZx9yoLjxYRyptSuOI2B1DspvbIVYXY12sxPZ4/HCJ4Usm2MU5lO/006KnDMxuxiv1rm6YZJZ0eZU"; @@ -2066,24 +1881,14 @@ static int test_s_mp_balance_mul(void) const char *nc = "HzrSq9WVt1jDTVlwUxSKqxctu2GVD+N8+SVGaPFRqdxyld6IxDBbj27BPJzYUdR96k3sWpkO8XnDBvupGPnehpQe4KlO/KmN1PjFov/UTZYM+LYzkFcBPyV6hkkL8ePC1rlFLAHzgJMBCXVp4mRqtkQrDsZXXlcqlbTFu69wF6zDEysiX2cAtn/kP9ldblJiwYPCD8hG"; - if ((e = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); - if ((e = mp_read_radix(&a, na, 64)) != MP_OKAY) { - goto LBL_ERR; - } - if ((e = mp_read_radix(&b, nb, 64)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_read_radix(&a, na, 64)); + DO(mp_read_radix(&b, nb, 64)); - if ((e = s_mp_balance_mul(&a, &b, &c)) != MP_OKAY) { - goto LBL_ERR; - } + DO(s_mp_balance_mul(&a, &b, &c)); - if ((e = mp_read_radix(&b, nc, 64)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_read_radix(&b, nc, 64)); if (mp_cmp(&b, &c) != MP_EQ) { goto LBL_ERR; @@ -2100,24 +1905,14 @@ static int test_s_mp_balance_mul(void) static int test_s_mp_karatsuba_mul(void) { mp_int a, b, c, d; - int size, err; + int size; - if ((err = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); for (size = MP_KARATSUBA_MUL_CUTOFF; size < MP_KARATSUBA_MUL_CUTOFF + 20; size++) { - if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_karatsuba_mul(&a, &b, &c)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_mul(&a,&b,&d)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, size)); + DO(mp_rand(&b, size)); + DO(s_mp_karatsuba_mul(&a, &b, &c)); + DO(s_mp_mul(&a,&b,&d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Karatsuba multiplication failed at size %d\n", size); goto LBL_ERR; @@ -2134,21 +1929,13 @@ static int test_s_mp_karatsuba_mul(void) static int test_s_mp_karatsuba_sqr(void) { mp_int a, b, c; - int size, err; + int size; - if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); for (size = MP_KARATSUBA_SQR_CUTOFF; size < MP_KARATSUBA_SQR_CUTOFF + 20; size++) { - if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_karatsuba_sqr(&a, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_sqr(&a, &c)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, size)); + DO(s_mp_karatsuba_sqr(&a, &b)); + DO(s_mp_sqr(&a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Karatsuba squaring failed at size %d\n", size); goto LBL_ERR; @@ -2165,49 +1952,29 @@ static int test_s_mp_karatsuba_sqr(void) static int test_s_mp_toom_mul(void) { mp_int a, b, c, d; - int size, err; + int size; #if (MP_DIGIT_BIT == 60) int tc_cutoff; #endif - if ((err = mp_init_multi(&a, &b, &c, &d, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); /* This number construction is limb-size specific */ #if (MP_DIGIT_BIT == 60) - if ((err = mp_rand(&a, 1196)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_mul_2d(&a,71787 - mp_count_bits(&a), &a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 1196)); + DO(mp_mul_2d(&a,71787 - mp_count_bits(&a), &a)); - if ((err = mp_rand(&b, 1338)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_mul_2d(&b, 80318 - mp_count_bits(&b), &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_mul_2d(&b, 6310, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_2expt(&c, 99000 - 1000)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_add(&b, &c, &b)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&b, 1338)); + DO(mp_mul_2d(&b, 80318 - mp_count_bits(&b), &b)); + DO(mp_mul_2d(&b, 6310, &b)); + DO(mp_2expt(&c, 99000 - 1000)); + DO(mp_add(&b, &c, &b)); tc_cutoff = MP_TOOM_MUL_CUTOFF; MP_TOOM_MUL_CUTOFF = INT_MAX; - if ((err = mp_mul(&a, &b, &c)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_mul(&a, &b, &c)); MP_TOOM_MUL_CUTOFF = tc_cutoff; - if ((err = mp_mul(&a, &b, &d)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_mul(&a, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed for edgecase f1 * f2\n"); goto LBL_ERR; @@ -2215,18 +1982,10 @@ static int test_s_mp_toom_mul(void) #endif for (size = MP_TOOM_MUL_CUTOFF; size < MP_TOOM_MUL_CUTOFF + 20; size++) { - if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_toom_mul(&a, &b, &c)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_mul(&a,&b,&d)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, size)); + DO(mp_rand(&b, size)); + DO(s_mp_toom_mul(&a, &b, &c)); + DO(s_mp_mul(&a,&b,&d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed at size %d\n", size); goto LBL_ERR; @@ -2243,21 +2002,13 @@ static int test_s_mp_toom_mul(void) static int test_s_mp_toom_sqr(void) { mp_int a, b, c; - int size, err; + int size; - if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); for (size = MP_TOOM_SQR_CUTOFF; size < MP_TOOM_SQR_CUTOFF + 20; size++) { - if ((err = mp_rand(&a, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_toom_sqr(&a, &b)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_sqr(&a, &c)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, size)); + DO(s_mp_toom_sqr(&a, &b)); + DO(s_mp_sqr(&a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way squaring failed at size %d\n", size); goto LBL_ERR; @@ -2273,7 +2024,6 @@ static int test_s_mp_toom_sqr(void) static int test_mp_radix_size(void) { - mp_err err; mp_int a; int radix; size_t size; @@ -2290,27 +2040,21 @@ static int test_mp_radix_size(void) }; /* *INDENT-ON* */ - mp_init(&a); + DOR(mp_init(&a)); /* number to result in a different size for every base: 67^(4 * 67) */ mp_set(&a, 67); - if ((err = mp_expt_u32(&a, 268u, &a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_expt_u32(&a, 268u, &a)); for (radix = 2; radix < 65; radix++) { - if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_radix_size(&a, radix, &size)); if (size != results[radix]) { fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", radix, size, results[radix]); goto LBL_ERR; } a.sign = MP_NEG; - if ((err = mp_radix_size(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_radix_size(&a, radix, &size)); if (size != (results[radix] + 1)) { fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", radix, size, results[radix]); @@ -2326,32 +2070,23 @@ static int test_mp_radix_size(void) return EXIT_FAILURE; } +#define PRINTERR_V(...) /* Some larger values to test the fast division algorithm */ static int test_s_mp_div_recursive(void) { mp_int a, b, c_q, c_r, d_q, d_r; - int size, err; + int size; - if ((err = mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)); for (size = MP_KARATSUBA_MUL_CUTOFF; size < 3 * MP_KARATSUBA_MUL_CUTOFF; size += 10) { - fprintf(stderr,"sizes = %d / %d\n", 10 * size, size); + printf("\rsizes = %d / %d", 10 * size, size); /* Relation 10:1 */ - if ((err = mp_rand(&a, 10 * size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 10 * size)); + DO(mp_rand(&b, size)); + DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); if (mp_cmp(&c_q, &d_q) != MP_EQ) { fprintf(stderr, "1. Recursive division failed at sizes %d / %d, wrong quotient\n", 10 * size, size); @@ -2362,20 +2097,12 @@ static int test_s_mp_div_recursive(void) 10 * size, size); goto LBL_ERR; } - fprintf(stderr,"sizes = %d / %d\n", 2 * size, size); + printf("\rsizes = %d / %d", 2 * size, size); /* Relation 2:1 */ - if ((err = mp_rand(&a, 2 * size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 2 * size)); + DO(mp_rand(&b, size)); + DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); if (mp_cmp(&c_q, &d_q) != MP_EQ) { fprintf(stderr, "2. Recursive division failed at sizes %d / %d, wrong quotient\n", 2 * size, size); @@ -2386,20 +2113,12 @@ static int test_s_mp_div_recursive(void) 2 * size, size); goto LBL_ERR; } - fprintf(stderr,"sizes = %d / %d\n", 3 * size, 2 * size); + printf("\rsizes = %d / %d", 3 * size, 2 * size); /* Upper limit 3:2 */ - if ((err = mp_rand(&a, 3 * size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, 2 * size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_recursive(&a, &b, &c_q, &c_r)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 3 * size)); + DO(mp_rand(&b, 2 * size)); + DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); if (mp_cmp(&c_q, &d_q) != MP_EQ) { fprintf(stderr, "3. Recursive division failed at sizes %d / %d, wrong quotient\n", 3 * size, 2 * size); @@ -2422,26 +2141,16 @@ static int test_s_mp_div_recursive(void) static int test_s_mp_div_small(void) { mp_int a, b, c_q, c_r, d_q, d_r; - int size, err; + int size; - if ((err = mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)); for (size = 1; size < MP_KARATSUBA_MUL_CUTOFF; size += 10) { - fprintf(stderr,"sizes = %d / %d\n", 2 * size, size); + printf("\rsizes = %d / %d", 2 * size, size); /* Relation 10:1 */ - if ((err = mp_rand(&a, 2 * size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = mp_rand(&b, size)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_small(&a, &b, &c_q, &c_r)) != MP_OKAY) { - goto LBL_ERR; - } - if ((err = s_mp_div_school(&a, &b, &d_q, &d_r)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_rand(&a, 2 * size)); + DO(mp_rand(&b, size)); + DO(s_mp_div_small(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); if (mp_cmp(&c_q, &d_q) != MP_EQ) { fprintf(stderr, "1. Small division failed at sizes %d / %d, wrong quotient\n", 2 * size, size); @@ -2464,19 +2173,16 @@ static int test_s_mp_div_small(void) static int test_mp_read_write_ubin(void) { mp_int a, b, c; - int err; size_t size, len; unsigned char *buf = NULL; - if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LBL_ERR; + DO(mp_rand(&a, 15)); + DO(mp_neg(&a, &b)); size = mp_ubin_size(&a); - printf("mp_to_ubin_size %zu\n", size); + printf("mp_to_ubin_size %zu - ", size); buf = malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (u) failed to allocate %zu bytes\n", @@ -2484,10 +2190,10 @@ static int test_mp_read_write_ubin(void) goto LBL_ERR; } - if ((err = mp_to_ubin(&a, buf, size, &len)) != MP_OKAY) goto LBL_ERR; - printf("mp_to_ubin len = %zu\n", len); + DO(mp_to_ubin(&a, buf, size, &len)); + printf("mp_to_ubin len = %zu", len); - if ((err = mp_from_ubin(&c, buf, len)) != MP_OKAY) goto LBL_ERR; + DO(mp_from_ubin(&c, buf, len)); if (mp_cmp(&a, &c) != MP_EQ) { fprintf(stderr, "to/from ubin cycle failed\n"); @@ -2505,19 +2211,16 @@ static int test_mp_read_write_ubin(void) static int test_mp_read_write_sbin(void) { mp_int a, b, c; - int err; size_t size, len; unsigned char *buf = NULL; - if ((err = mp_init_multi(&a, &b, &c, NULL)) != MP_OKAY) { - goto LBL_ERR; - } + DOR(mp_init_multi(&a, &b, &c, NULL)); - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_neg(&a, &b)) != MP_OKAY) goto LBL_ERR; + DO(mp_rand(&a, 15)); + DO(mp_neg(&a, &b)); size = mp_sbin_size(&a); - printf("mp_to_sbin_size %zu\n", size); + printf("mp_to_sbin_size %zu - ", size); buf = malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (s) failed to allocate %zu bytes\n", @@ -2525,10 +2228,10 @@ static int test_mp_read_write_sbin(void) goto LBL_ERR; } - if ((err = mp_to_sbin(&b, buf, size, &len)) != MP_OKAY) goto LBL_ERR; - printf("mp_to_sbin len = %zu\n", len); + DO(mp_to_sbin(&b, buf, size, &len)); + printf("mp_to_sbin len = %zu", len); - if ((err = mp_from_sbin(&c, buf, len)) != MP_OKAY) goto LBL_ERR; + DO(mp_from_sbin(&c, buf, len)); if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "to/from ubin cycle failed\n"); @@ -2547,15 +2250,14 @@ static int test_mp_read_write_sbin(void) static int test_mp_pack_unpack(void) { mp_int a, b; - int err; size_t written, count; unsigned char *buf = NULL; mp_order order = MP_LSB_FIRST; mp_endian endianess = MP_NATIVE_ENDIAN; - if ((err = mp_init_multi(&a, &b, NULL)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_rand(&a, 15)) != MP_OKAY) goto LBL_ERR; + DOR(mp_init_multi(&a, &b, NULL)); + DO(mp_rand(&a, 15)); count = mp_pack_count(&a, 0, 1); @@ -2565,10 +2267,10 @@ static int test_mp_pack_unpack(void) goto LBL_ERR; } - if ((err = mp_pack((void *)buf, count, &written, order, 1, - endianess, 0, &a)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_unpack(&b, count, order, 1, - endianess, 0, (const void *)buf)) != MP_OKAY) goto LBL_ERR; + DO(mp_pack((void *)buf, count, &written, order, 1, + endianess, 0, &a)); + DO(mp_unpack(&b, count, order, 1, + endianess, 0, (const void *)buf)); if (mp_cmp(&a, &b) != MP_EQ) { fprintf(stderr, "pack/unpack cycle failed\n"); @@ -2600,7 +2302,7 @@ static int unit_tests(int argc, char **argv) T1(mp_and, MP_AND), T1(mp_cnt_lsb, MP_CNT_LSB), T1(mp_complement, MP_COMPLEMENT), - T1(mp_decr, MP_DECR), + T1(mp_decr, MP_SUB_D), T1(mp_div_3, MP_DIV_3), T1(mp_dr_reduce, MP_DR_REDUCE), T2(mp_pack_unpack,MP_PACK, MP_UNPACK), @@ -2609,7 +2311,7 @@ static int unit_tests(int argc, char **argv) T1(mp_get_u64, MP_GET_I64), T1(mp_get_ul, MP_GET_L), T1(mp_log_u32, MP_LOG_U32), - T1(mp_incr, MP_INCR), + T1(mp_incr, MP_ADD_D), T1(mp_invmod, MP_INVMOD), T1(mp_is_square, MP_IS_SQUARE), T1(mp_kronecker, MP_KRONECKER), @@ -2663,19 +2365,19 @@ static int unit_tests(int argc, char **argv) } if (j == argc) continue; } - printf("TEST %s\n\n", test[i].name); + printf("TEST %s\n", test[i].name); if (test[i].fn == NULL) { nop++; printf("NOP %s\n\n", test[i].name); } else if (test[i].fn() == EXIT_SUCCESS) { ok++; - printf("\n\n"); + printf("\n"); } else { fail++; printf("\n\nFAIL %s\n\n", test[i].name); } } - printf("Tests OK/NOP/FAIL: %lu/%lu/%lu\n", ok, nop, fail); + fprintf(fail?stderr:stdout, "Tests OK/NOP/FAIL: %lu/%lu/%lu\n", ok, nop, fail); if (fail != 0) return EXIT_FAILURE; else return EXIT_SUCCESS; diff --git a/tommath.h b/tommath.h index e854d9658..e00cc54b6 100644 --- a/tommath.h +++ b/tommath.h @@ -204,7 +204,7 @@ mp_err mp_init_size(mp_int *a, int size) MP_WUR; /* ---> Basic Manipulations <--- */ #define mp_iszero(a) ((a)->used == 0) -#define mp_isneg(a) ((a)->sign != MP_ZPOS) +#define mp_isneg(a) ((a)->sign == MP_NEG) #define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u)) #define mp_isodd(a) (!mp_iseven(a)) From 4500d066c1af3c92f4941b5c5a37b8561fbe3161 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 29 Oct 2019 14:41:33 +0100 Subject: [PATCH 094/304] also no MP_WUR in mtest_opponent() --- demo/mtest_opponent.c | 149 +++++++++++++++++++++--------------------- demo/shared.h | 7 ++ demo/test.c | 5 -- 3 files changed, 81 insertions(+), 80 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index e6bfb8ef3..6c49de23a 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -1,4 +1,3 @@ -#define MP_WUR /* TODO: result checks disabled for now, T.b.d. if it should even be done here */ #include "shared.h" #ifdef LTM_MTEST_REAL_RAND @@ -47,27 +46,27 @@ static int mtest_opponent(void) switch (abs(rand()) % 7) { case 0: mp_clear(&a); - mp_init(&a); + DO(mp_init(&a)); break; case 1: mp_clear(&b); - mp_init(&b); + DO(mp_init(&b)); break; case 2: mp_clear(&c); - mp_init(&c); + DO(mp_init(&c)); break; case 3: mp_clear(&d); - mp_init(&d); + DO(mp_init(&d)); break; case 4: mp_clear(&e); - mp_init(&e); + DO(mp_init(&e)); break; case 5: mp_clear(&f); - mp_init(&f); + DO(mp_init(&f)); break; case 6: break; /* don't clear any */ @@ -84,13 +83,13 @@ static int mtest_opponent(void) if (strcmp(cmd, "mul2d") == 0) { ++mul2d_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); sscanf(buf, "%u", &rr); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); - mp_mul_2d(&a, (int)rr, &a); + DO(mp_mul_2d(&a, (int)rr, &a)); a.sign = b.sign; if (mp_cmp(&a, &b) != MP_EQ) { printf("mul2d failed, rr == %u\n", rr); @@ -101,13 +100,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "div2d") == 0) { ++div2d_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); sscanf(buf, "%u", &rr); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); - mp_div_2d(&a, (int)rr, &a, &e); + DO(mp_div_2d(&a, (int)rr, &a, &e)); a.sign = b.sign; if ((a.used == b.used) && (a.used == 0)) { a.sign = b.sign = MP_ZPOS; @@ -121,13 +120,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "add") == 0) { ++add_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_copy(&a, &d); - mp_add(&d, &b, &d); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_copy(&a, &d)); + DO(mp_add(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("add %lu failure!\n", add_n); draw(&a); @@ -140,9 +139,9 @@ static int mtest_opponent(void) /* test the sign/unsigned storage functions */ rr = (unsigned)mp_sbin_size(&c); - mp_to_sbin(&c, (unsigned char *) cmd, (size_t)rr, NULL); + DO(mp_to_sbin(&c, (unsigned char *) cmd, (size_t)rr, NULL)); memset(cmd + rr, rand() & 0xFF, sizeof(cmd) - rr); - mp_from_sbin(&d, (unsigned char *) cmd, (size_t)rr); + DO(mp_from_sbin(&d, (unsigned char *) cmd, (size_t)rr)); if (mp_cmp(&c, &d) != MP_EQ) { printf("mp_signed_bin failure!\n"); draw(&c); @@ -151,9 +150,9 @@ static int mtest_opponent(void) } rr = (unsigned)mp_ubin_size(&c); - mp_to_ubin(&c, (unsigned char *) cmd, (size_t)rr, NULL); + DO(mp_to_ubin(&c, (unsigned char *) cmd, (size_t)rr, NULL)); memset(cmd + rr, rand() & 0xFF, sizeof(cmd) - rr); - mp_from_ubin(&d, (unsigned char *) cmd, (size_t)rr); + DO(mp_from_ubin(&d, (unsigned char *) cmd, (size_t)rr)); if (mp_cmp_mag(&c, &d) != MP_EQ) { printf("mp_unsigned_bin failure!\n"); draw(&c); @@ -164,13 +163,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "sub") == 0) { ++sub_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_copy(&a, &d); - mp_sub(&d, &b, &d); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_copy(&a, &d)); + DO(mp_sub(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("sub %lu failure!\n", sub_n); draw(&a); @@ -182,13 +181,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "mul") == 0) { ++mul_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_copy(&a, &d); - mp_mul(&d, &b, &d); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_copy(&a, &d)); + DO(mp_mul(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("mul %lu failure!\n", mul_n); draw(&a); @@ -200,15 +199,15 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "div") == 0) { ++div_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); + DO(mp_read_radix(&c, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&d, buf, 64); + DO(mp_read_radix(&d, buf, 64)); - mp_div(&a, &b, &e, &f); + DO(mp_div(&a, &b, &e, &f)); if ((mp_cmp(&c, &e) != MP_EQ) || (mp_cmp(&d, &f) != MP_EQ)) { printf("div %lu %d, %d, failure!\n", div_n, mp_cmp(&c, &e), mp_cmp(&d, &f)); @@ -224,11 +223,11 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "sqr") == 0) { ++sqr_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); - mp_copy(&a, &c); - mp_sqr(&c, &c); + DO(mp_read_radix(&b, buf, 64)); + DO(mp_copy(&a, &c)); + DO(mp_sqr(&c, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("sqr %lu failure!\n", sqr_n); draw(&a); @@ -239,13 +238,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "gcd") == 0) { ++gcd_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_copy(&a, &d); - mp_gcd(&d, &b, &d); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_copy(&a, &d)); + DO(mp_gcd(&d, &b, &d)); d.sign = c.sign; if (mp_cmp(&c, &d) != MP_EQ) { printf("gcd %lu failure!\n", gcd_n); @@ -258,13 +257,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "lcm") == 0) { ++lcm_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_copy(&a, &d); - mp_lcm(&d, &b, &d); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_copy(&a, &d)); + DO(mp_lcm(&d, &b, &d)); d.sign = c.sign; if (mp_cmp(&c, &d) != MP_EQ) { printf("lcm %lu failure!\n", lcm_n); @@ -277,15 +276,15 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "expt") == 0) { ++expt_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); + DO(mp_read_radix(&c, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&d, buf, 64); - mp_copy(&a, &e); - mp_exptmod(&e, &b, &c, &e); + DO(mp_read_radix(&d, buf, 64)); + DO(mp_copy(&a, &e)); + DO(mp_exptmod(&e, &b, &c, &e)); if (mp_cmp(&d, &e) != MP_EQ) { printf("expt %lu failure!\n", expt_n); draw(&a); @@ -298,13 +297,13 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "invmod") == 0) { ++inv_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); + DO(mp_read_radix(&b, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&c, buf, 64); - mp_invmod(&a, &b, &d); - mp_mulmod(&d, &a, &b, &e); + DO(mp_read_radix(&c, buf, 64)); + DO(mp_invmod(&a, &b, &d)); + DO(mp_mulmod(&d, &a, &b, &e)); if (mp_cmp_d(&e, 1uL) != MP_EQ) { printf("inv [wrong value from MPI?!] failure\n"); draw(&a); @@ -312,7 +311,7 @@ static int mtest_opponent(void) draw(&c); draw(&d); draw(&e); - mp_gcd(&a, &b, &e); + DO(mp_gcd(&a, &b, &e)); draw(&e); goto LBL_ERR; } @@ -320,10 +319,10 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "div2") == 0) { ++div2_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); - mp_div_2(&a, &c); + DO(mp_read_radix(&b, buf, 64)); + DO(mp_div_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { printf("div_2 %lu failure\n", div2_n); draw(&a); @@ -334,10 +333,10 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "mul2") == 0) { ++mul2_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); - mp_mul_2(&a, &c); + DO(mp_read_radix(&b, buf, 64)); + DO(mp_mul_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { printf("mul_2 %lu failure\n", mul2_n); draw(&a); @@ -348,12 +347,12 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "add_d") == 0) { ++add_d_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); sscanf(buf, "%d", &ix); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); - mp_add_d(&a, (mp_digit)ix, &c); + DO(mp_read_radix(&b, buf, 64)); + DO(mp_add_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("add_d %lu failure\n", add_d_n); draw(&a); @@ -365,12 +364,12 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "sub_d") == 0) { ++sub_d_n; FGETS(buf, 4095, stdin); - mp_read_radix(&a, buf, 64); + DO(mp_read_radix(&a, buf, 64)); FGETS(buf, 4095, stdin); sscanf(buf, "%d", &ix); FGETS(buf, 4095, stdin); - mp_read_radix(&b, buf, 64); - mp_sub_d(&a, (mp_digit)ix, &c); + DO(mp_read_radix(&b, buf, 64)); + DO(mp_sub_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("sub_d %lu failure\n", sub_d_n); draw(&a); diff --git a/demo/shared.h b/demo/shared.h index 47c2c29be..5eae9732c 100644 --- a/demo/shared.h +++ b/demo/shared.h @@ -16,5 +16,12 @@ #include "tommath_private.h" + +#define EXPECT(a) do { if (!(a)) { fprintf(stderr, "%d: EXPECT(%s) failed\n", __LINE__, #a); goto LBL_ERR; } } while(0) +#define DO_WHAT(a, what) do { mp_err err; if ((err = (a)) != MP_OKAY) { fprintf(stderr, "%d: DO(%s) failed: %s\n", __LINE__, #a, mp_error_to_string(err)); what; } } while(0) +#define DO(a) DO_WHAT(a, goto LBL_ERR) +#define DOR(a) DO_WHAT(a, return EXIT_FAILURE) + + extern void ndraw(const mp_int* a, const char* name); extern void print_header(void); diff --git a/demo/test.c b/demo/test.c index efffbd588..7a4233010 100644 --- a/demo/test.c +++ b/demo/test.c @@ -94,11 +94,6 @@ static int test_feature_detection(void) return EXIT_SUCCESS; } -#define EXPECT(a) do { if (!(a)) { fprintf(stderr, "%d: EXPECT(%s) failed\n", __LINE__, #a); goto LBL_ERR; } } while(0) -#define DO_WHAT(a, what) do { mp_err err; if ((err = (a)) != MP_OKAY) { fprintf(stderr, "%d: DO(%s) failed: %s\n", __LINE__, #a, mp_error_to_string(err)); what; } } while(0) -#define DO(a) DO_WHAT(a, goto LBL_ERR) -#define DOR(a) DO_WHAT(a, return EXIT_FAILURE) - static int test_trivial_stuff(void) { mp_int a, b, c, d; From e95dd24e4f3e132cd304e8605b69a9605859e3a4 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Oct 2019 21:34:23 +0100 Subject: [PATCH 095/304] introduce MP_NO_DEPRECATED_PRAGMA --- tommath.h | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/tommath.h b/tommath.h index e00cc54b6..4031b0df8 100644 --- a/tommath.h +++ b/tommath.h @@ -157,13 +157,22 @@ MP_TOOM_SQR_CUTOFF; #if defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__ >= 405) # define MP_DEPRECATED(x) __attribute__((deprecated("replaced by " #x))) +#elif defined(_MSC_VER) && _MSC_VER >= 1500 +# define MP_DEPRECATED(x) __declspec(deprecated("replaced by " #x)) +#else +# define MP_DEPRECATED(x) +#endif + +#ifndef MP_NO_DEPRECATED_PRAGMA +#if defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__ >= 301) # define PRIVATE_MP_DEPRECATED_PRAGMA(s) _Pragma(#s) # define MP_DEPRECATED_PRAGMA(s) PRIVATE_MP_DEPRECATED_PRAGMA(GCC warning s) #elif defined(_MSC_VER) && _MSC_VER >= 1500 -# define MP_DEPRECATED(x) __declspec(deprecated("replaced by " #x)) # define MP_DEPRECATED_PRAGMA(s) __pragma(message(s)) -#else -# define MP_DEPRECATED(s) +#endif +#endif + +#ifndef MP_DEPRECATED_PRAGMA # define MP_DEPRECATED_PRAGMA(s) #endif From 57fbf5a880e18109c0105f1b7aebc89c8fc7e80f Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 29 Oct 2019 13:14:31 +0100 Subject: [PATCH 096/304] also build support/ branches in CI (cherry picked from commit 783ffb82dd5ddddce3d3bbd88661bcda44162458) --- .travis.yml | 1 + appveyor.yml | 1 + 2 files changed, 2 insertions(+) diff --git a/.travis.yml b/.travis.yml index 738c62bd1..0f6f7872c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -33,6 +33,7 @@ branches: - master - develop - /^release/ + - /^support/ - /^travis/ # Additional installs: Valgrind for memory tests. diff --git a/appveyor.yml b/appveyor.yml index efe45688c..02c343057 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -4,6 +4,7 @@ branches: - master - develop - /^release/ + - /^support/ - /^travis/ image: - Visual Studio 2019 From 8456782cc51e1469afe86485239ec023ef6402a4 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 29 Oct 2019 15:40:47 +0100 Subject: [PATCH 097/304] don't allow disabling of WUR checks --- tommath.h | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/tommath.h b/tommath.h index 4031b0df8..874212628 100644 --- a/tommath.h +++ b/tommath.h @@ -142,17 +142,11 @@ MP_TOOM_SQR_CUTOFF; * Most functions in libtommath return an error code. * This error code must be checked in order to prevent crashes or invalid * results. - * - * If you still want to avoid the error checks for quick and dirty programs - * without robustness guarantees, you can `#define MP_WUR` before including - * tommath.h, disabling the warnings. */ -#ifndef MP_WUR -# if defined(__GNUC__) && __GNUC__ >= 4 -# define MP_WUR __attribute__((warn_unused_result)) -# else -# define MP_WUR -# endif +#if defined(__GNUC__) && __GNUC__ >= 4 +# define MP_WUR __attribute__((warn_unused_result)) +#else +# define MP_WUR #endif #if defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__ >= 405) From af376edcde0d0b36fbfe8415d5b4508322a7958a Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 29 Oct 2019 16:37:56 +0100 Subject: [PATCH 098/304] no more MP_WUR in timing.c --- demo/timing.c | 69 ++++++++++++++++++++++++++------------------------- 1 file changed, 35 insertions(+), 34 deletions(-) diff --git a/demo/timing.c b/demo/timing.c index 854125095..bb2d6c488 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -4,7 +4,6 @@ #include #include -#define MP_WUR #include #ifdef IOWNANATHLON @@ -26,12 +25,14 @@ #define MP_TIMING_VERSION "-" MP_VERSION #endif +#define CHECK_OK(x) do { mp_err err; if ((err = (x)) != MP_OKAY) { fprintf(stderr, "%d: CHECK_OK(%s) failed: %s\n", __LINE__, #x, mp_error_to_string(err)); exit(EXIT_FAILURE); } }while(0) + static void ndraw(const mp_int *a, const char *name) { char buf[4096]; printf("%s: ", name); - mp_to_radix(a, buf, sizeof(buf), NULL, 64); + CHECK_OK(mp_to_radix(a, buf, sizeof(buf), NULL, 64)); printf("%s\n", buf); } @@ -90,7 +91,7 @@ static uint64_t TIMFUNC(void) #endif } -#define DO2(x) x; x +#define DO2(x) do { mp_err err = x; err = x; (void)err; }while(0) #define DO4(x) DO2(x); DO2(x) #define DO8(x) DO4(x); DO4(x) @@ -140,12 +141,12 @@ int main(int argc, char **argv) int n, cnt, ix, old_kara_m, old_kara_s, old_toom_m, old_toom_s; unsigned rr; - mp_init(&a); - mp_init(&b); - mp_init(&c); - mp_init(&d); - mp_init(&e); - mp_init(&f); + CHECK_OK(mp_init(&a)); + CHECK_OK(mp_init(&b)); + CHECK_OK(mp_init(&c)); + CHECK_OK(mp_init(&d)); + CHECK_OK(mp_init(&e)); + CHECK_OK(mp_init(&f)); srand(LTM_TIMING_RAND_SEED); @@ -161,14 +162,14 @@ int main(int argc, char **argv) for (m = 0; m < 2; ++m) { if (m == 0) { name = " Arnault"; - mp_read_radix(&a, - "91xLNF3roobhzgTzoFIG6P13ZqhOVYSN60Fa7Cj2jVR1g0k89zdahO9/kAiRprpfO1VAp1aBHucLFV/qLKLFb+zonV7R2Vxp1K13ClwUXStpV0oxTNQVjwybmFb5NBEHImZ6V7P6+udRJuH8VbMEnS0H8/pSqQrg82OoQQ2fPpAk6G1hkjqoCv5s/Yr", - 64); + CHECK_OK(mp_read_radix(&a, + "91xLNF3roobhzgTzoFIG6P13ZqhOVYSN60Fa7Cj2jVR1g0k89zdahO9/kAiRprpfO1VAp1aBHucLFV/qLKLFb+zonV7R2Vxp1K13ClwUXStpV0oxTNQVjwybmFb5NBEHImZ6V7P6+udRJuH8VbMEnS0H8/pSqQrg82OoQQ2fPpAk6G1hkjqoCv5s/Yr", + 64)); } else { name = "2^1119 + 53"; mp_set(&a,1u); - mp_mul_2d(&a,1119,&a); - mp_add_d(&a,53,&a); + CHECK_OK(mp_mul_2d(&a,1119,&a)); + CHECK_OK(mp_add_d(&a,53,&a)); } cnt = mp_prime_rabin_miller_trials(mp_count_bits(&a)); ix = -cnt; @@ -197,8 +198,8 @@ int main(int argc, char **argv) log = FOPEN("logs/add" MP_TIMING_VERSION ".log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; - mp_rand(&a, cnt); - mp_rand(&b, cnt); + CHECK_OK(mp_rand(&a, cnt)); + CHECK_OK(mp_rand(&b, cnt)); DO8(mp_add(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; @@ -222,8 +223,8 @@ int main(int argc, char **argv) log = FOPEN("logs/sub" MP_TIMING_VERSION ".log", "w"); for (cnt = 8; cnt <= 128; cnt += 8) { SLEEP; - mp_rand(&a, cnt); - mp_rand(&b, cnt); + CHECK_OK(mp_rand(&a, cnt)); + CHECK_OK(mp_rand(&b, cnt)); DO8(mp_sub(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; @@ -263,8 +264,8 @@ int main(int argc, char **argv) "logs/mult_toom" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= (10240 / MP_DIGIT_BIT); cnt += 2) { SLEEP; - mp_rand(&a, cnt); - mp_rand(&b, cnt); + CHECK_OK(mp_rand(&a, cnt)); + CHECK_OK(mp_rand(&b, cnt)); DO8(mp_mul(&a, &b, &c)); rr = 0u; tt = UINT64_MAX; @@ -287,7 +288,7 @@ int main(int argc, char **argv) "logs/sqr_toom" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= (10240 / MP_DIGIT_BIT); cnt += 2) { SLEEP; - mp_rand(&a, cnt); + CHECK_OK(mp_rand(&a, cnt)); DO8(mp_sqr(&a, &b)); rr = 0u; tt = UINT64_MAX; @@ -348,15 +349,15 @@ int main(int argc, char **argv) logd = FOPEN("logs/expt_2kl" MP_TIMING_VERSION ".log", "w"); for (n = 0; primes[n] != NULL; n++) { SLEEP; - mp_read_radix(&a, primes[n], 10); + CHECK_OK(mp_read_radix(&a, primes[n], 10)); mp_zero(&b); for (rr = 0; rr < (unsigned) mp_count_bits(&a); rr++) { - mp_mul_2(&b, &b); + CHECK_OK(mp_mul_2(&b, &b)); b.dp[0] |= lbit(); b.used += 1; } - mp_sub_d(&a, 1uL, &c); - mp_mod(&b, &c, &b); + CHECK_OK(mp_sub_d(&a, 1uL, &c)); + CHECK_OK(mp_mod(&b, &c, &b)); mp_set(&c, 3uL); DO8(mp_exptmod(&c, &b, &a, &d)); rr = 0u; @@ -368,10 +369,10 @@ int main(int argc, char **argv) if (tt > gg) tt = gg; } while (++rr < 10u); - mp_sub_d(&a, 1uL, &e); - mp_sub(&e, &b, &b); - mp_exptmod(&c, &b, &a, &e); /* c^(p-1-b) mod a */ - mp_mulmod(&e, &d, &a, &d); /* c^b * c^(p-1-b) == c^p-1 == 1 */ + CHECK_OK(mp_sub_d(&a, 1uL, &e)); + CHECK_OK(mp_sub(&e, &b, &b)); + CHECK_OK(mp_exptmod(&c, &b, &a, &e)); /* c^(p-1-b) mod a */ + CHECK_OK(mp_mulmod(&e, &d, &a, &d)); /* c^b * c^(p-1-b) == c^p-1 == 1 */ if (mp_cmp_d(&d, 1uL) != MP_EQ) { printf("Different (%d)!!!\n", mp_count_bits(&a)); draw(&d); @@ -393,12 +394,12 @@ int main(int argc, char **argv) log = FOPEN("logs/invmod" MP_TIMING_VERSION ".log", "w"); for (cnt = 4; cnt <= 32; cnt += 4) { SLEEP; - mp_rand(&a, cnt); - mp_rand(&b, cnt); + CHECK_OK(mp_rand(&a, cnt)); + CHECK_OK(mp_rand(&b, cnt)); do { - mp_add_d(&b, 1uL, &b); - mp_gcd(&a, &b, &c); + CHECK_OK(mp_add_d(&b, 1uL, &b)); + CHECK_OK(mp_gcd(&a, &b, &c)); } while (mp_cmp_d(&c, 1uL) != MP_EQ); DO2(mp_invmod(&b, &a, &c)); @@ -411,7 +412,7 @@ int main(int argc, char **argv) if (tt > gg) tt = gg; } while (++rr < 1000u); - mp_mulmod(&b, &c, &a, &d); + CHECK_OK(mp_mulmod(&b, &c, &a, &d)); if (mp_cmp_d(&d, 1uL) != MP_EQ) { printf("Failed to invert\n"); return 0; From b9977adfb8115ab14ce050238fa4e1eb76d3f81c Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 08:44:51 +0100 Subject: [PATCH 099/304] use uint8_t instead of unsigned char --- demo/mtest_opponent.c | 8 ++++---- demo/test.c | 6 +++--- doc/bn.tex | 8 ++++---- mp_from_sbin.c | 4 ++-- mp_from_ubin.c | 4 ++-- mp_pack.c | 12 ++++++------ mp_prime_rand.c | 10 +++++----- mp_to_radix.c | 6 +++--- mp_to_sbin.c | 4 ++-- mp_to_ubin.c | 4 ++-- mp_unpack.c | 10 +++++----- tommath.h | 8 ++++---- 12 files changed, 42 insertions(+), 42 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 6c49de23a..1beab5fce 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -139,9 +139,9 @@ static int mtest_opponent(void) /* test the sign/unsigned storage functions */ rr = (unsigned)mp_sbin_size(&c); - DO(mp_to_sbin(&c, (unsigned char *) cmd, (size_t)rr, NULL)); + DO(mp_to_sbin(&c, (uint8_t *) cmd, (size_t)rr, NULL)); memset(cmd + rr, rand() & 0xFF, sizeof(cmd) - rr); - DO(mp_from_sbin(&d, (unsigned char *) cmd, (size_t)rr)); + DO(mp_from_sbin(&d, (uint8_t *) cmd, (size_t)rr)); if (mp_cmp(&c, &d) != MP_EQ) { printf("mp_signed_bin failure!\n"); draw(&c); @@ -150,9 +150,9 @@ static int mtest_opponent(void) } rr = (unsigned)mp_ubin_size(&c); - DO(mp_to_ubin(&c, (unsigned char *) cmd, (size_t)rr, NULL)); + DO(mp_to_ubin(&c, (uint8_t *) cmd, (size_t)rr, NULL)); memset(cmd + rr, rand() & 0xFF, sizeof(cmd) - rr); - DO(mp_from_ubin(&d, (unsigned char *) cmd, (size_t)rr)); + DO(mp_from_ubin(&d, (uint8_t *) cmd, (size_t)rr)); if (mp_cmp_mag(&c, &d) != MP_EQ) { printf("mp_unsigned_bin failure!\n"); draw(&c); diff --git a/demo/test.c b/demo/test.c index 7a4233010..8e37f712a 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2169,7 +2169,7 @@ static int test_mp_read_write_ubin(void) { mp_int a, b, c; size_t size, len; - unsigned char *buf = NULL; + uint8_t *buf = NULL; DOR(mp_init_multi(&a, &b, &c, NULL)); @@ -2207,7 +2207,7 @@ static int test_mp_read_write_sbin(void) { mp_int a, b, c; size_t size, len; - unsigned char *buf = NULL; + uint8_t *buf = NULL; DOR(mp_init_multi(&a, &b, &c, NULL)); @@ -2246,7 +2246,7 @@ static int test_mp_pack_unpack(void) { mp_int a, b; size_t written, count; - unsigned char *buf = NULL; + uint8_t *buf = NULL; mp_order order = MP_LSB_FIRST; mp_endian endianess = MP_NATIVE_ENDIAN; diff --git a/doc/bn.tex b/doc/bn.tex index 1e8ac7403..b8a6404b7 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2444,7 +2444,7 @@ \section{Binary Conversions} \index{mp\_to\_ubin} \begin{alltt} -mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) +mp_err mp_to_ubin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) \end{alltt} This will store $a$ into the buffer \texttt{buf} of size \texttt{maxlen} in big--endian format storing the number of bytes written in \texttt{len}. Fortunately this is exactly what DER (or is @@ -2452,7 +2452,7 @@ \section{Binary Conversions} \index{mp\_from\_ubin} \begin{alltt} -mp_err mp_from_ubin(mp_int *a, unsigned char *b, size_t size); +mp_err mp_from_ubin(mp_int *a, uint8_t *b, size_t size); \end{alltt} This will read in an unsigned big--endian array of bytes (octets) from \texttt{b} of length \texttt{size} into $a$. The resulting big--integer $a$ will always be positive. @@ -2462,8 +2462,8 @@ \section{Binary Conversions} \index{mp\_sbin\_size} \index{mp\_from\_sbin} \index{mp\_to\_sbin} \begin{alltt} size_t mp_sbin_size(const mp_int *a); -mp_err mp_from_sbin(mp_int *a, const unsigned char *b, size_t size); -mp_err mp_to_sbin(const mp_int *a, unsigned char *b, size_t maxsize, size_t *len); +mp_err mp_from_sbin(mp_int *a, const uint8_t *b, size_t size); +mp_err mp_to_sbin(const mp_int *a, uint8_t *b, size_t maxsize, size_t *len); \end{alltt} They operate essentially the same as the unsigned copies except they prefix the data with zero or non--zero byte depending on the sign. If the sign is \texttt{MP\_ZPOS} (e.g. not negative) the diff --git a/mp_from_sbin.c b/mp_from_sbin.c index 4335d8860..c6e87d7d0 100644 --- a/mp_from_sbin.c +++ b/mp_from_sbin.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* read signed bin, big endian, first byte is 0==positive or 1==negative */ -mp_err mp_from_sbin(mp_int *a, const unsigned char *buf, size_t size) +mp_err mp_from_sbin(mp_int *a, const uint8_t *buf, size_t size) { mp_err err; @@ -14,7 +14,7 @@ mp_err mp_from_sbin(mp_int *a, const unsigned char *buf, size_t size) } /* first byte is 0 for positive, non-zero for negative */ - if (buf[0] == (unsigned char)0) { + if (buf[0] == (uint8_t)0) { a->sign = MP_ZPOS; } else { a->sign = MP_NEG; diff --git a/mp_from_ubin.c b/mp_from_ubin.c index 315ff080e..ae79be3cf 100644 --- a/mp_from_ubin.c +++ b/mp_from_ubin.c @@ -3,8 +3,8 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* reads a unsigned char array, assumes the msb is stored first [big endian] */ -mp_err mp_from_ubin(mp_int *a, const unsigned char *buf, size_t size) +/* reads a uint8_t array, assumes the msb is stored first [big endian] */ +mp_err mp_from_ubin(mp_int *a, const uint8_t *buf, size_t size) { mp_err err; diff --git a/mp_pack.c b/mp_pack.c index ec0f62f69..447f1fdf9 100644 --- a/mp_pack.c +++ b/mp_pack.c @@ -11,7 +11,7 @@ mp_err mp_pack(void *rop, size_t maxcount, size_t *written, mp_order order, size { mp_err err; size_t odd_nails, nail_bytes, i, j, count; - unsigned char odd_nail_mask; + uint8_t odd_nail_mask; mp_int t; @@ -32,22 +32,22 @@ mp_err mp_pack(void *rop, size_t maxcount, size_t *written, mp_order order, size odd_nails = (nails % 8u); odd_nail_mask = 0xff; for (i = 0u; i < odd_nails; ++i) { - odd_nail_mask ^= (unsigned char)(1u << (7u - i)); + odd_nail_mask ^= (uint8_t)(1u << (7u - i)); } nail_bytes = nails / 8u; for (i = 0u; i < count; ++i) { for (j = 0u; j < size; ++j) { - unsigned char *byte = (unsigned char *)rop + - (((order == MP_LSB_FIRST) ? i : ((count - 1u) - i)) * size) + - ((endian == MP_LITTLE_ENDIAN) ? j : ((size - 1u) - j)); + uint8_t *byte = (uint8_t *)rop + + (((order == MP_LSB_FIRST) ? i : ((count - 1u) - i)) * size) + + ((endian == MP_LITTLE_ENDIAN) ? j : ((size - 1u) - j)); if (j >= (size - nail_bytes)) { *byte = 0; continue; } - *byte = (unsigned char)((j == ((size - nail_bytes) - 1u)) ? (t.dp[0] & odd_nail_mask) : (t.dp[0] & 0xFFuL)); + *byte = (uint8_t)((j == ((size - nail_bytes) - 1u)) ? (t.dp[0] & odd_nail_mask) : (t.dp[0] & 0xFFuL)); if ((err = mp_div_2d(&t, (j == ((size - nail_bytes) - 1u)) ? (int)(8u - odd_nails) : 8, &t, NULL)) != MP_OKAY) { goto LBL_ERR; diff --git a/mp_prime_rand.c b/mp_prime_rand.c index ff6df9c39..8476b4f80 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -20,7 +20,7 @@ /* This is possibly the mother of all prime generation functions, muahahahahaha! */ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) { - unsigned char *tmp, maskAND, maskOR_msb, maskOR_lsb; + uint8_t *tmp, maskAND, maskOR_msb, maskOR_lsb; int bsize, maskOR_msb_offset; bool res; mp_err err; @@ -39,19 +39,19 @@ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) bsize = (size>>3) + ((size&7)?1:0); /* we need a buffer of bsize bytes */ - tmp = (unsigned char *) MP_MALLOC((size_t)bsize); + tmp = (uint8_t *) MP_MALLOC((size_t)bsize); if (tmp == NULL) { return MP_MEM; } /* calc the maskAND value for the MSbyte*/ - maskAND = ((size&7) == 0) ? 0xFFu : (unsigned char)(0xFFu >> (8 - (size & 7))); + maskAND = ((size&7) == 0) ? 0xFFu : (uint8_t)(0xFFu >> (8 - (size & 7))); /* calc the maskOR_msb */ maskOR_msb = 0; maskOR_msb_offset = ((size & 7) == 1) ? 1 : 0; if ((flags & MP_PRIME_2MSB_ON) != 0) { - maskOR_msb |= (unsigned char)(0x80 >> ((9 - size) & 7)); + maskOR_msb |= (uint8_t)(0x80 >> ((9 - size) & 7)); } /* get the maskOR_lsb */ @@ -68,7 +68,7 @@ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) /* work over the MSbyte */ tmp[0] &= maskAND; - tmp[0] |= (unsigned char)(1 << ((size - 1) & 7)); + tmp[0] |= (uint8_t)(1 << ((size - 1) & 7)); /* mix in the maskORs */ tmp[maskOR_msb_offset] |= maskOR_msb; diff --git a/mp_to_radix.c b/mp_to_radix.c index 78ad98988..c1ea233ea 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -4,10 +4,10 @@ /* SPDX-License-Identifier: Unlicense */ /* reverse an array, used for radix code */ -static void s_mp_reverse(unsigned char *s, size_t len) +static void s_mp_reverse(uint8_t *s, size_t len) { size_t ix, iy; - unsigned char t; + uint8_t t; ix = 0u; iy = len - 1u; @@ -83,7 +83,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i /* reverse the digits of the string. In this case _s points * to the first digit [exluding the sign] of the number */ - s_mp_reverse((unsigned char *)_s, digs); + s_mp_reverse((uint8_t *)_s, digs); /* append a NULL so the string is properly terminated */ *str = '\0'; diff --git a/mp_to_sbin.c b/mp_to_sbin.c index ed21adcdb..8225d1306 100644 --- a/mp_to_sbin.c +++ b/mp_to_sbin.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* store in signed [big endian] format */ -mp_err mp_to_sbin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) +mp_err mp_to_sbin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) { mp_err err; if (maxlen == 0u) { @@ -16,7 +16,7 @@ mp_err mp_to_sbin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *wr if (written != NULL) { (*written)++; } - buf[0] = (a->sign == MP_ZPOS) ? (unsigned char)0 : (unsigned char)1; + buf[0] = (a->sign == MP_ZPOS) ? (uint8_t)0 : (uint8_t)1; return MP_OKAY; } #endif diff --git a/mp_to_ubin.c b/mp_to_ubin.c index 25835037d..e8643cc07 100644 --- a/mp_to_ubin.c +++ b/mp_to_ubin.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* store in unsigned [big endian] format */ -mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) +mp_err mp_to_ubin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) { size_t x, count; mp_err err; @@ -20,7 +20,7 @@ mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *wr } for (x = count; x --> 0u;) { - buf[x] = (unsigned char)(t.dp[0] & 255u); + buf[x] = (uint8_t)(t.dp[0] & 255u); if ((err = mp_div_2d(&t, 8, &t, NULL)) != MP_OKAY) { goto LBL_ERR; } diff --git a/mp_unpack.c b/mp_unpack.c index 5305b435a..f0127fa44 100644 --- a/mp_unpack.c +++ b/mp_unpack.c @@ -11,7 +11,7 @@ mp_err mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, { mp_err err; size_t odd_nails, nail_bytes, i, j; - unsigned char odd_nail_mask; + uint8_t odd_nail_mask; mp_zero(rop); @@ -22,15 +22,15 @@ mp_err mp_unpack(mp_int *rop, size_t count, mp_order order, size_t size, odd_nails = (nails % 8u); odd_nail_mask = 0xff; for (i = 0; i < odd_nails; ++i) { - odd_nail_mask ^= (unsigned char)(1u << (7u - i)); + odd_nail_mask ^= (uint8_t)(1u << (7u - i)); } nail_bytes = nails / 8u; for (i = 0; i < count; ++i) { for (j = 0; j < (size - nail_bytes); ++j) { - unsigned char byte = *((const unsigned char *)op + - (((order == MP_MSB_FIRST) ? i : ((count - 1u) - i)) * size) + - ((endian == MP_BIG_ENDIAN) ? (j + nail_bytes) : (((size - 1u) - j) - nail_bytes))); + uint8_t byte = *((const uint8_t *)op + + (((order == MP_MSB_FIRST) ? i : ((count - 1u) - i)) * size) + + ((endian == MP_BIG_ENDIAN) ? (j + nail_bytes) : (((size - 1u) - j) - nail_bytes))); if ((err = mp_mul_2d(rop, (j == 0u) ? (int)(8u - odd_nails) : 8, rop)) != MP_OKAY) { return err; diff --git a/tommath.h b/tommath.h index 874212628..86b19d3be 100644 --- a/tommath.h +++ b/tommath.h @@ -570,12 +570,12 @@ mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) MP_WUR; int mp_count_bits(const mp_int *a) MP_WUR; size_t mp_ubin_size(const mp_int *a) MP_WUR; -mp_err mp_from_ubin(mp_int *a, const unsigned char *buf, size_t size) MP_WUR; -mp_err mp_to_ubin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) MP_WUR; +mp_err mp_from_ubin(mp_int *a, const uint8_t *buf, size_t size) MP_WUR; +mp_err mp_to_ubin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) MP_WUR; size_t mp_sbin_size(const mp_int *a) MP_WUR; -mp_err mp_from_sbin(mp_int *a, const unsigned char *buf, size_t size) MP_WUR; -mp_err mp_to_sbin(const mp_int *a, unsigned char *buf, size_t maxlen, size_t *written) MP_WUR; +mp_err mp_from_sbin(mp_int *a, const uint8_t *buf, size_t size) MP_WUR; +mp_err mp_to_sbin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) MP_WUR; mp_err mp_read_radix(mp_int *a, const char *str, int radix) MP_WUR; mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, int radix) MP_WUR; From 3cdcec43e64a0b1e9438805551d1823a968981d2 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 18:41:25 +0100 Subject: [PATCH 100/304] first batch of simplifications --- mp_abs.c | 3 +- mp_add.c | 37 +++++++----------- mp_clear_multi.c | 7 ++-- mp_cmp.c | 15 +++----- mp_cmp_d.c | 10 ++--- mp_cmp_mag.c | 28 ++++---------- mp_cnt_lsb.c | 11 +++--- mp_copy.c | 14 ++----- mp_div.c | 13 ++++--- mp_div_3.c | 7 ++-- mp_exch.c | 6 +-- mp_exptmod.c | 12 +++--- mp_exteuclid.c | 1 - mp_fread.c | 6 +-- mp_from_sbin.c | 6 +-- mp_fwrite.c | 23 ++++-------- mp_grow.c | 16 +++----- mp_is_square.c | 8 ++-- mp_kronecker.c | 2 +- mp_lshd.c | 13 ++----- mp_mod_2d.c | 8 ++-- mp_montgomery_calc_normalization.c | 1 - mp_neg.c | 8 +--- mp_prime_rabin_miller_trials.c | 3 +- mp_read_radix.c | 8 ++-- mp_reduce.c | 22 +++++------ mp_reduce_is_2k.c | 8 +--- mp_reduce_is_2k_l.c | 3 +- mp_rshd.c | 18 +++------ mp_set.c | 3 +- mp_shrink.c | 10 ++--- mp_signed_rsh.c | 11 +++--- mp_sqrt.c | 18 ++++----- mp_sqrtmod_prime.c | 60 +++++++++++++++--------------- mp_sub.c | 42 ++++++++++----------- mp_to_radix.c | 14 ++----- mp_zero.c | 2 +- s_mp_div_recursive.c | 6 +-- s_mp_div_school.c | 2 - tommath_private.h | 6 ++- 40 files changed, 200 insertions(+), 291 deletions(-) diff --git a/mp_abs.c b/mp_abs.c index 4ad1a4a90..902279e93 100644 --- a/mp_abs.c +++ b/mp_abs.c @@ -9,10 +9,9 @@ */ mp_err mp_abs(const mp_int *a, mp_int *b) { - mp_err err; - /* copy a to b */ if (a != b) { + mp_err err; if ((err = mp_copy(a, b)) != MP_OKAY) { return err; } diff --git a/mp_add.c b/mp_add.c index c78614b6f..bf7a61e25 100644 --- a/mp_add.c +++ b/mp_add.c @@ -6,33 +6,24 @@ /* high level addition (handles signs) */ mp_err mp_add(const mp_int *a, const mp_int *b, mp_int *c) { - mp_sign sa, sb; - mp_err err; - - /* get sign of both inputs */ - sa = a->sign; - sb = b->sign; - /* handle two cases, not four */ - if (sa == sb) { + if (a->sign == b->sign) { /* both positive or both negative */ /* add their magnitudes, copy the sign */ - c->sign = sa; - err = s_mp_add(a, b, c); - } else { - /* one positive, the other negative */ - /* subtract the one with the greater magnitude from */ - /* the one of the lesser magnitude. The result gets */ - /* the sign of the one with the greater magnitude. */ - if (mp_cmp_mag(a, b) == MP_LT) { - c->sign = sb; - err = s_mp_sub(b, a, c); - } else { - c->sign = sa; - err = s_mp_sub(a, b, c); - } + c->sign = a->sign; + return s_mp_add(a, b, c); } - return err; + + /* one positive, the other negative */ + /* subtract the one with the greater magnitude from */ + /* the one of the lesser magnitude. The result gets */ + /* the sign of the one with the greater magnitude. */ + if (mp_cmp_mag(a, b) == MP_LT) { + MP_EXCH(const mp_int *, a, b); + } + + c->sign = a->sign; + return s_mp_sub(a, b, c); } #endif diff --git a/mp_clear_multi.c b/mp_clear_multi.c index 74406c7a0..9c7aed831 100644 --- a/mp_clear_multi.c +++ b/mp_clear_multi.c @@ -7,12 +7,11 @@ void mp_clear_multi(mp_int *mp, ...) { - mp_int *next_mp = mp; va_list args; va_start(args, mp); - while (next_mp != NULL) { - mp_clear(next_mp); - next_mp = va_arg(args, mp_int *); + while (mp != NULL) { + mp_clear(mp); + mp = va_arg(args, mp_int *); } va_end(args); } diff --git a/mp_cmp.c b/mp_cmp.c index a9bd910a9..b9c45920b 100644 --- a/mp_cmp.c +++ b/mp_cmp.c @@ -8,19 +8,14 @@ mp_ord mp_cmp(const mp_int *a, const mp_int *b) { /* compare based on sign */ if (a->sign != b->sign) { - if (a->sign == MP_NEG) { - return MP_LT; - } else { - return MP_GT; - } + return a->sign == MP_NEG ? MP_LT : MP_GT; } - /* compare digits */ + /* if negative compare opposite direction */ if (a->sign == MP_NEG) { - /* if negative compare opposite direction */ - return mp_cmp_mag(b, a); - } else { - return mp_cmp_mag(a, b); + MP_EXCH(const mp_int *, a, b); } + + return mp_cmp_mag(a, b); } #endif diff --git a/mp_cmp_d.c b/mp_cmp_d.c index 03d8e2c6f..0d98e05a0 100644 --- a/mp_cmp_d.c +++ b/mp_cmp_d.c @@ -17,12 +17,10 @@ mp_ord mp_cmp_d(const mp_int *a, mp_digit b) } /* compare the only digit of a to b */ - if (a->dp[0] > b) { - return MP_GT; - } else if (a->dp[0] < b) { - return MP_LT; - } else { - return MP_EQ; + if (a->dp[0] != b) { + return a->dp[0] > b ? MP_GT : MP_LT; } + + return MP_EQ; } #endif diff --git a/mp_cmp_mag.c b/mp_cmp_mag.c index b3a7b040f..e5e502b8c 100644 --- a/mp_cmp_mag.c +++ b/mp_cmp_mag.c @@ -6,34 +6,20 @@ /* compare maginitude of two ints (unsigned) */ mp_ord mp_cmp_mag(const mp_int *a, const mp_int *b) { - int n; - const mp_digit *tmpa, *tmpb; + int n; /* compare based on # of non-zero digits */ - if (a->used > b->used) { - return MP_GT; + if (a->used != b->used) { + return a->used > b->used ? MP_GT : MP_LT; } - if (a->used < b->used) { - return MP_LT; - } - - /* alias for a */ - tmpa = a->dp + (a->used - 1); - - /* alias for b */ - tmpb = b->dp + (a->used - 1); - /* compare based on digits */ - for (n = 0; n < a->used; ++n, --tmpa, --tmpb) { - if (*tmpa > *tmpb) { - return MP_GT; - } - - if (*tmpa < *tmpb) { - return MP_LT; + for (n = a->used; n --> 0;) { + if (a->dp[n] != b->dp[n]) { + return a->dp[n] > b->dp[n] ? MP_GT : MP_LT; } } + return MP_EQ; } #endif diff --git a/mp_cnt_lsb.c b/mp_cnt_lsb.c index 7ae8bc13c..8519ad1b0 100644 --- a/mp_cnt_lsb.c +++ b/mp_cnt_lsb.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -static const int lnz[16] = { +static const char lnz[16] = { 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0 }; @@ -11,7 +11,7 @@ static const int lnz[16] = { int mp_cnt_lsb(const mp_int *a) { int x; - mp_digit q, qq; + mp_digit q; /* easy out */ if (mp_iszero(a)) { @@ -25,11 +25,12 @@ int mp_cnt_lsb(const mp_int *a) /* now scan this digit until a 1 is found */ if ((q & 1u) == 0u) { + mp_digit p; do { - qq = q & 15u; - x += lnz[qq]; + p = q & 15u; + x += lnz[p]; q >>= 4; - } while (qq == 0u); + } while (p == 0u); } return x; } diff --git a/mp_copy.c b/mp_copy.c index a7ac34af3..cf4d5e0b4 100644 --- a/mp_copy.c +++ b/mp_copy.c @@ -7,8 +7,6 @@ mp_err mp_copy(const mp_int *a, mp_int *b) { int n; - mp_digit *tmpa, *tmpb; - mp_err err; /* if dst == src do nothing */ if (a == b) { @@ -17,27 +15,21 @@ mp_err mp_copy(const mp_int *a, mp_int *b) /* grow dest */ if (b->alloc < a->used) { + mp_err err; if ((err = mp_grow(b, a->used)) != MP_OKAY) { return err; } } /* zero b and copy the parameters over */ - /* pointer aliases */ - - /* source */ - tmpa = a->dp; - - /* destination */ - tmpb = b->dp; /* copy all the digits */ for (n = 0; n < a->used; n++) { - *tmpb++ = *tmpa++; + b->dp[n] = a->dp[n]; } /* clear high digits */ - MP_ZERO_DIGITS(tmpb, b->used - n); + MP_ZERO_DIGITS(b->dp + a->used, b->used - a->used); /* copy used count and sign */ b->used = a->used; diff --git a/mp_div.c b/mp_div.c index 23a2acf93..05b96dd51 100644 --- a/mp_div.c +++ b/mp_div.c @@ -15,14 +15,14 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) /* if a < b then q = 0, r = a */ if (mp_cmp_mag(a, b) == MP_LT) { if (d != NULL) { - err = mp_copy(a, d); - } else { - err = MP_OKAY; + if ((err = mp_copy(a, d)) != MP_OKAY) { + return err; + } } if (c != NULL) { mp_zero(c); } - return err; + return MP_OKAY; } if (MP_HAS(S_MP_DIV_RECURSIVE) @@ -31,11 +31,12 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) err = s_mp_div_recursive(a, b, c, d); } else if (MP_HAS(S_MP_DIV_SCHOOL)) { err = s_mp_div_school(a, b, c, d); - } else { + } else if (MP_HAS(S_MP_DIV_SMALL)) { err = s_mp_div_small(a, b, c, d); + } else { + err = MP_VAL; } return err; } #endif - diff --git a/mp_div_3.c b/mp_div_3.c index 5789b2d62..c26692cb2 100644 --- a/mp_div_3.c +++ b/mp_div_3.c @@ -7,7 +7,7 @@ mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) { mp_int q; - mp_word w, t; + mp_word w; mp_digit b; mp_err err; int ix; @@ -22,7 +22,8 @@ mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) q.used = a->used; q.sign = a->sign; w = 0; - for (ix = a->used - 1; ix >= 0; ix--) { + for (ix = a->used; ix --> 0;) { + mp_word t; w = (w << (mp_word)MP_DIGIT_BIT) | (mp_word)a->dp[ix]; if (w >= 3u) { @@ -57,7 +58,7 @@ mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) } mp_clear(&q); - return err; + return MP_OKAY; } #endif diff --git a/mp_exch.c b/mp_exch.c index 7bc4ee706..50b97d963 100644 --- a/mp_exch.c +++ b/mp_exch.c @@ -8,10 +8,6 @@ */ void mp_exch(mp_int *a, mp_int *b) { - mp_int t; - - t = *a; - *a = *b; - *b = t; + MP_EXCH(mp_int, *a, *b); } #endif diff --git a/mp_exptmod.c b/mp_exptmod.c index e643ded2e..b917c0bb8 100644 --- a/mp_exptmod.c +++ b/mp_exptmod.c @@ -64,13 +64,15 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) /* if the modulus is odd or dr != 0 use the montgomery method */ if (MP_HAS(S_MP_EXPTMOD_FAST) && (mp_isodd(P) || (dr != 0))) { return s_mp_exptmod_fast(G, X, P, Y, dr); - } else if (MP_HAS(S_MP_EXPTMOD)) { - /* otherwise use the generic Barrett reduction technique */ + } + + /* otherwise use the generic Barrett reduction technique */ + if (MP_HAS(S_MP_EXPTMOD)) { return s_mp_exptmod(G, X, P, Y, 0); - } else { - /* no exptmod for evens */ - return MP_VAL; } + + /* no exptmod for evens */ + return MP_VAL; } #endif diff --git a/mp_exteuclid.c b/mp_exteuclid.c index eb8ad3728..0d0bfd339 100644 --- a/mp_exteuclid.c +++ b/mp_exteuclid.c @@ -65,7 +65,6 @@ mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp mp_exch(U3, &u3); } - err = MP_OKAY; LBL_ERR: mp_clear_multi(&u1, &u2, &u3, &v1, &v2, &v3, &t1, &t2, &t3, &q, &tmp, NULL); return err; diff --git a/mp_fread.c b/mp_fread.c index 767e5a3c0..005c62ae9 100644 --- a/mp_fread.c +++ b/mp_fread.c @@ -32,7 +32,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) mp_zero(a); do { - int y; + uint8_t y; unsigned pos; ch = (radix <= 36) ? MP_TOUPPER(ch) : ch; pos = (unsigned)(ch - (int)'('); @@ -40,7 +40,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) break; } - y = (int)s_mp_rmap_reverse[pos]; + y = s_mp_rmap_reverse[pos]; if ((y == 0xff) || (y >= radix)) { break; @@ -50,7 +50,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) if ((err = mp_mul_d(a, (mp_digit)radix, a)) != MP_OKAY) { return err; } - if ((err = mp_add_d(a, (mp_digit)y, a)) != MP_OKAY) { + if ((err = mp_add_d(a, y, a)) != MP_OKAY) { return err; } } while ((ch = fgetc(stream)) != EOF); diff --git a/mp_from_sbin.c b/mp_from_sbin.c index c6e87d7d0..3ff7d5d8f 100644 --- a/mp_from_sbin.c +++ b/mp_from_sbin.c @@ -14,11 +14,7 @@ mp_err mp_from_sbin(mp_int *a, const uint8_t *buf, size_t size) } /* first byte is 0 for positive, non-zero for negative */ - if (buf[0] == (uint8_t)0) { - a->sign = MP_ZPOS; - } else { - a->sign = MP_NEG; - } + a->sign = (buf[0] == (uint8_t)0) ? MP_ZPOS : MP_NEG; return MP_OKAY; } diff --git a/mp_fwrite.c b/mp_fwrite.c index be78f7f28..42d728778 100644 --- a/mp_fwrite.c +++ b/mp_fwrite.c @@ -8,31 +8,24 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) { char *buf; mp_err err; - size_t len, written; + size_t size, written; - /* TODO: this function is not in this PR */ - if ((err = mp_radix_size(a, radix, &len)) != MP_OKAY) { + if ((err = mp_radix_size(a, radix, &size)) != MP_OKAY) { return err; } - buf = (char *) MP_MALLOC(len); + buf = (char *) MP_MALLOC(size); if (buf == NULL) { return MP_MEM; } - if ((err = mp_to_radix(a, buf, len, &written, radix)) != MP_OKAY) { - goto LBL_ERR; + if ((err = mp_to_radix(a, buf, size, &written, radix)) == MP_OKAY) { + if (fwrite(buf, written, 1uL, stream) != 1uL) { + err = MP_ERR; + } } - if (fwrite(buf, written, 1uL, stream) != 1uL) { - err = MP_ERR; - goto LBL_ERR; - } - err = MP_OKAY; - - -LBL_ERR: - MP_FREE_BUFFER(buf, len); + MP_FREE_BUFFER(buf, size); return err; } #endif diff --git a/mp_grow.c b/mp_grow.c index 3354e5964..25be5edd2 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -6,9 +6,6 @@ /* grow as required */ mp_err mp_grow(mp_int *a, int size) { - int i; - mp_digit *tmp; - /* if the alloc size is smaller alloc more ram */ if (a->alloc < size) { /* reallocate the array a->dp @@ -17,21 +14,20 @@ mp_err mp_grow(mp_int *a, int size) * in case the operation failed we don't want * to overwrite the dp member of a. */ - tmp = (mp_digit *) MP_REALLOC(a->dp, - (size_t)a->alloc * sizeof(mp_digit), - (size_t)size * sizeof(mp_digit)); - if (tmp == NULL) { + mp_digit *dp = (mp_digit *) MP_REALLOC(a->dp, + (size_t)a->alloc * sizeof(mp_digit), + (size_t)size * sizeof(mp_digit)); + if (dp == NULL) { /* reallocation failed but "a" is still valid [can be freed] */ return MP_MEM; } /* reallocation succeeded so set a->dp */ - a->dp = tmp; + a->dp = dp; /* zero excess digits */ - i = a->alloc; + MP_ZERO_DIGITS(a->dp + a->alloc, size - a->alloc); a->alloc = size; - MP_ZERO_DIGITS(a->dp + i, a->alloc - i); } return MP_OKAY; } diff --git a/mp_is_square.c b/mp_is_square.c index f92ecbfb8..47f830015 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -28,10 +28,10 @@ static const char rem_105[105] = { /* Store non-zero to ret if arg is square, and zero if not */ mp_err mp_is_square(const mp_int *arg, bool *ret) { - mp_err err; - mp_digit c; - mp_int t; - unsigned long r; + mp_err err; + mp_digit c; + mp_int t; + uint32_t r; /* Default to Non-square :) */ *ret = false; diff --git a/mp_kronecker.c b/mp_kronecker.c index 0ac6338b9..b106f7731 100644 --- a/mp_kronecker.c +++ b/mp_kronecker.c @@ -23,7 +23,7 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) mp_err err; int v, k; - static const int table[8] = {0, 1, 0, -1, 0, -1, 0, 1}; + static const char table[] = {0, 1, 0, -1, 0, -1, 0, 1}; if (mp_iszero(p)) { if ((a->used == 1) && (a->dp[0] == 1u)) { diff --git a/mp_lshd.c b/mp_lshd.c index b0a845486..6c1440261 100644 --- a/mp_lshd.c +++ b/mp_lshd.c @@ -7,8 +7,6 @@ mp_err mp_lshd(mp_int *a, int b) { int x; - mp_err err; - mp_digit *top, *bottom; /* if its less than zero return */ if (b <= 0) { @@ -21,6 +19,7 @@ mp_err mp_lshd(mp_int *a, int b) /* grow to fit the new digits */ if (a->alloc < (a->used + b)) { + mp_err err; if ((err = mp_grow(a, a->used + b)) != MP_OKAY) { return err; } @@ -29,18 +28,12 @@ mp_err mp_lshd(mp_int *a, int b) /* increment the used by the shift amount then copy upwards */ a->used += b; - /* top */ - top = a->dp + a->used - 1; - - /* base */ - bottom = (a->dp + a->used - 1) - b; - /* much like mp_rshd this is implemented using a sliding window * except the window goes the otherway around. Copying from * the bottom to the top. see mp_rshd.c for more info. */ - for (x = a->used - 1; x >= b; x--) { - *top-- = *bottom--; + for (x = a->used; x --> b;) { + a->dp[x] = a->dp[x - b]; } /* zero the lower digits */ diff --git a/mp_mod_2d.c b/mp_mod_2d.c index 651c79a6c..a94a314cd 100644 --- a/mp_mod_2d.c +++ b/mp_mod_2d.c @@ -9,8 +9,11 @@ mp_err mp_mod_2d(const mp_int *a, int b, mp_int *c) int x; mp_err err; - /* if b is <= 0 then zero the int */ - if (b <= 0) { + if (b < 0) { + return MP_VAL; + } + + if (b == 0) { mp_zero(c); return MP_OKAY; } @@ -20,7 +23,6 @@ mp_err mp_mod_2d(const mp_int *a, int b, mp_int *c) return mp_copy(a, c); } - /* copy */ if ((err = mp_copy(a, c)) != MP_OKAY) { return err; } diff --git a/mp_montgomery_calc_normalization.c b/mp_montgomery_calc_normalization.c index 0d0d5c482..cc07799dc 100644 --- a/mp_montgomery_calc_normalization.c +++ b/mp_montgomery_calc_normalization.c @@ -26,7 +26,6 @@ mp_err mp_montgomery_calc_normalization(mp_int *a, const mp_int *b) bits = 1; } - /* now compute C = A * B mod b */ for (x = bits - 1; x < (int)MP_DIGIT_BIT; x++) { if ((err = mp_mul_2(a, a)) != MP_OKAY) { diff --git a/mp_neg.c b/mp_neg.c index 2fc1854bf..f54ef3edd 100644 --- a/mp_neg.c +++ b/mp_neg.c @@ -6,18 +6,14 @@ /* b = -a */ mp_err mp_neg(const mp_int *a, mp_int *b) { - mp_err err; if (a != b) { + mp_err err; if ((err = mp_copy(a, b)) != MP_OKAY) { return err; } } - if (!mp_iszero(b)) { - b->sign = (a->sign == MP_ZPOS) ? MP_NEG : MP_ZPOS; - } else { - b->sign = MP_ZPOS; - } + b->sign = mp_iszero(b) || b->sign == MP_NEG ? MP_ZPOS : MP_NEG; return MP_OKAY; } diff --git a/mp_prime_rabin_miller_trials.c b/mp_prime_rabin_miller_trials.c index 1728142c5..9f66f8d77 100644 --- a/mp_prime_rabin_miller_trials.c +++ b/mp_prime_rabin_miller_trials.c @@ -36,7 +36,8 @@ int mp_prime_rabin_miller_trials(int size) for (x = 0; x < (int)(sizeof(sizes)/(sizeof(sizes[0]))); x++) { if (sizes[x].k == size) { return sizes[x].t; - } else if (sizes[x].k > size) { + } + if (sizes[x].k > size) { return (x == 0) ? sizes[0].t : sizes[x - 1].t; } } diff --git a/mp_read_radix.c b/mp_read_radix.c index d4a3d1ecf..df8059a55 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -31,13 +31,13 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) * this allows numbers like 1AB and 1ab to represent the same value * [e.g. in hex] */ - int y; + uint8_t y; char ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; unsigned pos = (unsigned)(ch - '('); if (MP_RMAP_REVERSE_SIZE < pos) { break; } - y = (int)s_mp_rmap_reverse[pos]; + y = s_mp_rmap_reverse[pos]; /* if the char was found in the map * and is less than the given radix add it @@ -49,14 +49,14 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) if ((err = mp_mul_d(a, (mp_digit)radix, a)) != MP_OKAY) { return err; } - if ((err = mp_add_d(a, (mp_digit)y, a)) != MP_OKAY) { + if ((err = mp_add_d(a, y, a)) != MP_OKAY) { return err; } ++str; } /* if an illegal character was found, fail. */ - if (!((*str == '\0') || (*str == '\r') || (*str == '\n'))) { + if ((*str != '\0') && (*str != '\r') && (*str != '\n')) { return MP_VAL; } diff --git a/mp_reduce.c b/mp_reduce.c index 1b4435c95..5226fe7d4 100644 --- a/mp_reduce.c +++ b/mp_reduce.c @@ -24,19 +24,19 @@ mp_err mp_reduce(mp_int *x, const mp_int *m, const mp_int *mu) /* according to HAC this optimization is ok */ if ((mp_digit)um > ((mp_digit)1 << (MP_DIGIT_BIT - 1))) { if ((err = mp_mul(&q, mu, &q)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } } else if (MP_HAS(S_MP_MUL_HIGH_DIGS)) { if ((err = s_mp_mul_high_digs(&q, mu, &q, um)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } } else if (MP_HAS(S_MP_MUL_HIGH_DIGS_FAST)) { if ((err = s_mp_mul_high_digs_fast(&q, mu, &q, um)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } } else { err = MP_VAL; - goto CLEANUP; + goto LBL_ERR; } /* q3 = q2 / b**(k+1) */ @@ -44,38 +44,38 @@ mp_err mp_reduce(mp_int *x, const mp_int *m, const mp_int *mu) /* x = x mod b**(k+1), quick (no division) */ if ((err = mp_mod_2d(x, MP_DIGIT_BIT * (um + 1), x)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } /* q = q * m mod b**(k+1), quick (no division) */ if ((err = s_mp_mul_digs(&q, m, &q, um + 1)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } /* x = x - q */ if ((err = mp_sub(x, &q, x)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } /* If x < 0, add b**(k+1) to it */ if (mp_cmp_d(x, 0uL) == MP_LT) { mp_set(&q, 1uL); if ((err = mp_lshd(&q, um + 1)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } if ((err = mp_add(x, &q, x)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } } /* Back off if it's too big */ while (mp_cmp(x, m) != MP_LT) { if ((err = s_mp_sub(x, m, x)) != MP_OKAY) { - goto CLEANUP; + goto LBL_ERR; } } -CLEANUP: +LBL_ERR: mp_clear(&q); return err; diff --git a/mp_reduce_is_2k.c b/mp_reduce_is_2k.c index 618ab54ab..a5798e62f 100644 --- a/mp_reduce_is_2k.c +++ b/mp_reduce_is_2k.c @@ -6,17 +6,13 @@ /* determines if mp_reduce_2k can be used */ bool mp_reduce_is_2k(const mp_int *a) { - int ix, iy, iw; - mp_digit iz; - if (a->used == 0) { return false; } else if (a->used == 1) { return true; } else if (a->used > 1) { - iy = mp_count_bits(a); - iz = 1; - iw = 1; + int ix, iy = mp_count_bits(a), iw = 1; + mp_digit iz = 1; /* Test every bit from the second digit up, must be 1 */ for (ix = MP_DIGIT_BIT; ix < iy; ix++) { diff --git a/mp_reduce_is_2k_l.c b/mp_reduce_is_2k_l.c index 30fc10d0c..dca2d7e01 100644 --- a/mp_reduce_is_2k_l.c +++ b/mp_reduce_is_2k_l.c @@ -6,14 +6,13 @@ /* determines if reduce_2k_l can be used */ bool mp_reduce_is_2k_l(const mp_int *a) { - int ix, iy; - if (a->used == 0) { return false; } else if (a->used == 1) { return true; } else if (a->used > 1) { /* if more than half of the digits are -1 we're sold */ + int ix, iy; for (iy = ix = 0; ix < a->used; ix++) { if (a->dp[ix] == MP_DIGIT_MAX) { ++iy; diff --git a/mp_rshd.c b/mp_rshd.c index 2eabb1234..d798907a2 100644 --- a/mp_rshd.c +++ b/mp_rshd.c @@ -6,8 +6,7 @@ /* shift right a certain amount of digits */ void mp_rshd(mp_int *a, int b) { - int x; - mp_digit *bottom, *top; + int x; /* if b <= 0 then ignore it */ if (b <= 0) { @@ -20,15 +19,8 @@ void mp_rshd(mp_int *a, int b) return; } - /* shift the digits down */ - - /* bottom */ - bottom = a->dp; - - /* top [offset into digits] */ - top = a->dp + b; - - /* this is implemented as a sliding window where + /* shift the digits down. + * this is implemented as a sliding window where * the window is b-digits long and digits from * the top of the window are copied to the bottom * @@ -39,11 +31,11 @@ void mp_rshd(mp_int *a, int b) \-------------------/ ----> */ for (x = 0; x < (a->used - b); x++) { - *bottom++ = *top++; + a->dp[x] = a->dp[x + b]; } /* zero the top digits */ - MP_ZERO_DIGITS(bottom, a->used - x); + MP_ZERO_DIGITS(a->dp + a->used - b, b); /* remove excess digits */ a->used -= b; diff --git a/mp_set.c b/mp_set.c index 0777f09d7..3ee5f81f7 100644 --- a/mp_set.c +++ b/mp_set.c @@ -6,9 +6,10 @@ /* set to a digit */ void mp_set(mp_int *a, mp_digit b) { + int oldused = a->used; a->dp[0] = b & MP_MASK; a->sign = MP_ZPOS; a->used = (a->dp[0] != 0u) ? 1 : 0; - MP_ZERO_DIGITS(a->dp + a->used, a->alloc - a->used); + MP_ZERO_DIGITS(a->dp + a->used, oldused - a->used); } #endif diff --git a/mp_shrink.c b/mp_shrink.c index 6c3c95ba4..e5814cbdf 100644 --- a/mp_shrink.c +++ b/mp_shrink.c @@ -6,15 +6,15 @@ /* shrink a bignum */ mp_err mp_shrink(mp_int *a) { - mp_digit *tmp; int alloc = MP_MAX(MP_MIN_PREC, a->used); if (a->alloc != alloc) { - if ((tmp = (mp_digit *) MP_REALLOC(a->dp, - (size_t)a->alloc * sizeof(mp_digit), - (size_t)alloc * sizeof(mp_digit))) == NULL) { + mp_digit *dp = (mp_digit *) MP_REALLOC(a->dp, + (size_t)a->alloc * sizeof(mp_digit), + (size_t)alloc * sizeof(mp_digit)); + if (dp == NULL) { return MP_MEM; } - a->dp = tmp; + a->dp = dp; a->alloc = alloc; } return MP_OKAY; diff --git a/mp_signed_rsh.c b/mp_signed_rsh.c index c56dfba6a..ecaaa2192 100644 --- a/mp_signed_rsh.c +++ b/mp_signed_rsh.c @@ -6,17 +6,16 @@ /* shift right by a certain bit count with sign extension */ mp_err mp_signed_rsh(const mp_int *a, int b, mp_int *c) { - mp_err res; + mp_err err; if (a->sign == MP_ZPOS) { return mp_div_2d(a, b, c, NULL); } - res = mp_add_d(a, 1uL, c); - if (res != MP_OKAY) { - return res; + if ((err = mp_add_d(a, 1uL, c)) != MP_OKAY) { + return err; } - res = mp_div_2d(c, b, c, NULL); - return (res == MP_OKAY) ? mp_sub_d(c, 1uL, c) : res; + err = mp_div_2d(c, b, c, NULL); + return (err == MP_OKAY) ? mp_sub_d(c, 1uL, c) : err; } #endif diff --git a/mp_sqrt.c b/mp_sqrt.c index b51f6151f..e36a81a9c 100644 --- a/mp_sqrt.c +++ b/mp_sqrt.c @@ -25,7 +25,7 @@ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) } if ((err = mp_init(&t2)) != MP_OKAY) { - goto E2; + goto LBL_ERR2; } /* First approx. (not very bad for large arg) */ @@ -33,33 +33,33 @@ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) /* t1 > 0 */ if ((err = mp_div(arg, &t1, &t2, NULL)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } if ((err = mp_add(&t1, &t2, &t1)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } /* And now t1 > sqrt(arg) */ do { if ((err = mp_div(arg, &t1, &t2, NULL)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } if ((err = mp_add(&t1, &t2, &t1)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) { - goto E1; + goto LBL_ERR1; } /* t1 >= sqrt(arg) >= t2 at this point */ } while (mp_cmp_mag(&t1, &t2) == MP_GT); mp_exch(&t1, ret); -E1: +LBL_ERR1: mp_clear(&t2); -E2: +LBL_ERR2: mp_clear(&t1); return err; } diff --git a/mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c index 96b283689..893018498 100644 --- a/mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -33,28 +33,28 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) * compute directly: err = n^(prime+1)/4 mod prime * Handbook of Applied Cryptography algorithm 3.36 */ - if ((err = mp_mod_d(prime, 4uL, &i)) != MP_OKAY) goto cleanup; + if ((err = mp_mod_d(prime, 4uL, &i)) != MP_OKAY) goto LBL_END; if (i == 3u) { - if ((err = mp_add_d(prime, 1uL, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_exptmod(n, &t1, prime, ret)) != MP_OKAY) goto cleanup; + if ((err = mp_add_d(prime, 1uL, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_exptmod(n, &t1, prime, ret)) != MP_OKAY) goto LBL_END; err = MP_OKAY; - goto cleanup; + goto LBL_END; } /* NOW: Tonelli-Shanks algorithm */ /* factor out powers of 2 from prime-1, defining Q and S as: prime-1 = Q*2^S */ - if ((err = mp_copy(prime, &Q)) != MP_OKAY) goto cleanup; - if ((err = mp_sub_d(&Q, 1uL, &Q)) != MP_OKAY) goto cleanup; + if ((err = mp_copy(prime, &Q)) != MP_OKAY) goto LBL_END; + if ((err = mp_sub_d(&Q, 1uL, &Q)) != MP_OKAY) goto LBL_END; /* Q = prime - 1 */ mp_zero(&S); /* S = 0 */ while (mp_iseven(&Q)) { - if ((err = mp_div_2(&Q, &Q)) != MP_OKAY) goto cleanup; + if ((err = mp_div_2(&Q, &Q)) != MP_OKAY) goto LBL_END; /* Q = Q / 2 */ - if ((err = mp_add_d(&S, 1uL, &S)) != MP_OKAY) goto cleanup; + if ((err = mp_add_d(&S, 1uL, &S)) != MP_OKAY) goto LBL_END; /* S = S + 1 */ } @@ -62,55 +62,55 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) mp_set(&Z, 2uL); /* Z = 2 */ for (;;) { - if ((err = mp_kronecker(&Z, prime, &legendre)) != MP_OKAY) goto cleanup; + if ((err = mp_kronecker(&Z, prime, &legendre)) != MP_OKAY) goto LBL_END; if (legendre == -1) break; - if ((err = mp_add_d(&Z, 1uL, &Z)) != MP_OKAY) goto cleanup; + if ((err = mp_add_d(&Z, 1uL, &Z)) != MP_OKAY) goto LBL_END; /* Z = Z + 1 */ } - if ((err = mp_exptmod(&Z, &Q, prime, &C)) != MP_OKAY) goto cleanup; + if ((err = mp_exptmod(&Z, &Q, prime, &C)) != MP_OKAY) goto LBL_END; /* C = Z ^ Q mod prime */ - if ((err = mp_add_d(&Q, 1uL, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto cleanup; + if ((err = mp_add_d(&Q, 1uL, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto LBL_END; /* t1 = (Q + 1) / 2 */ - if ((err = mp_exptmod(n, &t1, prime, &R)) != MP_OKAY) goto cleanup; + if ((err = mp_exptmod(n, &t1, prime, &R)) != MP_OKAY) goto LBL_END; /* R = n ^ ((Q + 1) / 2) mod prime */ - if ((err = mp_exptmod(n, &Q, prime, &T)) != MP_OKAY) goto cleanup; + if ((err = mp_exptmod(n, &Q, prime, &T)) != MP_OKAY) goto LBL_END; /* T = n ^ Q mod prime */ - if ((err = mp_copy(&S, &M)) != MP_OKAY) goto cleanup; + if ((err = mp_copy(&S, &M)) != MP_OKAY) goto LBL_END; /* M = S */ mp_set(&two, 2uL); for (;;) { - if ((err = mp_copy(&T, &t1)) != MP_OKAY) goto cleanup; + if ((err = mp_copy(&T, &t1)) != MP_OKAY) goto LBL_END; i = 0; for (;;) { if (mp_cmp_d(&t1, 1uL) == MP_EQ) break; - if ((err = mp_exptmod(&t1, &two, prime, &t1)) != MP_OKAY) goto cleanup; + if ((err = mp_exptmod(&t1, &two, prime, &t1)) != MP_OKAY) goto LBL_END; i++; } if (i == 0u) { - if ((err = mp_copy(&R, ret)) != MP_OKAY) goto cleanup; + if ((err = mp_copy(&R, ret)) != MP_OKAY) goto LBL_END; err = MP_OKAY; - goto cleanup; + goto LBL_END; } - if ((err = mp_sub_d(&M, i, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_sub_d(&t1, 1uL, &t1)) != MP_OKAY) goto cleanup; - if ((err = mp_exptmod(&two, &t1, prime, &t1)) != MP_OKAY) goto cleanup; + if ((err = mp_sub_d(&M, i, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_sub_d(&t1, 1uL, &t1)) != MP_OKAY) goto LBL_END; + if ((err = mp_exptmod(&two, &t1, prime, &t1)) != MP_OKAY) goto LBL_END; /* t1 = 2 ^ (M - i - 1) */ - if ((err = mp_exptmod(&C, &t1, prime, &t1)) != MP_OKAY) goto cleanup; + if ((err = mp_exptmod(&C, &t1, prime, &t1)) != MP_OKAY) goto LBL_END; /* t1 = C ^ (2 ^ (M - i - 1)) mod prime */ - if ((err = mp_sqrmod(&t1, prime, &C)) != MP_OKAY) goto cleanup; + if ((err = mp_sqrmod(&t1, prime, &C)) != MP_OKAY) goto LBL_END; /* C = (t1 * t1) mod prime */ - if ((err = mp_mulmod(&R, &t1, prime, &R)) != MP_OKAY) goto cleanup; + if ((err = mp_mulmod(&R, &t1, prime, &R)) != MP_OKAY) goto LBL_END; /* R = (R * t1) mod prime */ - if ((err = mp_mulmod(&T, &C, prime, &T)) != MP_OKAY) goto cleanup; + if ((err = mp_mulmod(&T, &C, prime, &T)) != MP_OKAY) goto LBL_END; /* T = (T * C) mod prime */ mp_set(&M, i); /* M = i */ } -cleanup: +LBL_END: mp_clear_multi(&t1, &C, &Q, &S, &Z, &M, &T, &R, &two, NULL); return err; } diff --git a/mp_sub.c b/mp_sub.c index c859026f5..810474045 100644 --- a/mp_sub.c +++ b/mp_sub.c @@ -6,35 +6,31 @@ /* high level subtraction (handles signs) */ mp_err mp_sub(const mp_int *a, const mp_int *b, mp_int *c) { - mp_sign sa = a->sign, sb = b->sign; - mp_err err; - - if (sa != sb) { + if (a->sign != b->sign) { /* subtract a negative from a positive, OR */ /* subtract a positive from a negative. */ /* In either case, ADD their magnitudes, */ /* and use the sign of the first number. */ - c->sign = sa; - err = s_mp_add(a, b, c); + c->sign = a->sign; + return s_mp_add(a, b, c); + } + + /* subtract a positive from a positive, OR */ + /* subtract a negative from a negative. */ + /* First, take the difference between their */ + /* magnitudes, then... */ + if (mp_cmp_mag(a, b) == MP_LT) { + /* The second has a larger magnitude */ + /* The result has the *opposite* sign from */ + /* the first number. */ + c->sign = (a->sign == MP_ZPOS) ? MP_NEG : MP_ZPOS; + MP_EXCH(const mp_int *, a, b); } else { - /* subtract a positive from a positive, OR */ - /* subtract a negative from a negative. */ - /* First, take the difference between their */ - /* magnitudes, then... */ - if (mp_cmp_mag(a, b) != MP_LT) { - /* Copy the sign from the first */ - c->sign = sa; - /* The first has a larger or equal magnitude */ - err = s_mp_sub(a, b, c); - } else { - /* The result has the *opposite* sign from */ - /* the first number. */ - c->sign = (sa == MP_ZPOS) ? MP_NEG : MP_ZPOS; - /* The second has a larger magnitude */ - err = s_mp_sub(b, a, c); - } + /* The first has a larger or equal magnitude */ + /* Copy the sign from the first */ + c->sign = a->sign; } - return err; + return s_mp_sub(a, b, c); } #endif diff --git a/mp_to_radix.c b/mp_to_radix.c index c1ea233ea..8b7728d87 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -4,17 +4,11 @@ /* SPDX-License-Identifier: Unlicense */ /* reverse an array, used for radix code */ -static void s_mp_reverse(uint8_t *s, size_t len) +static void s_mp_reverse(char *s, size_t len) { - size_t ix, iy; - uint8_t t; - - ix = 0u; - iy = len - 1u; + size_t ix = 0, iy = len - 1u; while (ix < iy) { - t = s[ix]; - s[ix] = s[iy]; - s[iy] = t; + MP_EXCH(char, s[ix], s[iy]); ++ix; --iy; } @@ -83,7 +77,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i /* reverse the digits of the string. In this case _s points * to the first digit [exluding the sign] of the number */ - s_mp_reverse((uint8_t *)_s, digs); + s_mp_reverse(_s, digs); /* append a NULL so the string is properly terminated */ *str = '\0'; diff --git a/mp_zero.c b/mp_zero.c index 0b79f5008..b7dddd2f3 100644 --- a/mp_zero.c +++ b/mp_zero.c @@ -7,7 +7,7 @@ void mp_zero(mp_int *a) { a->sign = MP_ZPOS; + MP_ZERO_DIGITS(a->dp, a->used); a->used = 0; - MP_ZERO_DIGITS(a->dp, a->alloc); } #endif diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index d641123fd..7007aef06 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -17,10 +17,9 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) { mp_err err; - int m, k; mp_int A1, A2, B1, B0, Q1, Q0, R1, R0, t; + int m = a->used - b->used, k = m/2; - m = a->used - b->used; if (m < MP_KARATSUBA_MUL_CUTOFF) { return s_mp_div_school(a, b, q, r); } @@ -29,9 +28,6 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int goto LBL_ERR; } - /* k = floor(m/2) */ - k = m/2; - /* B1 = b / beta^k, B0 = b % beta^k*/ if ((err = mp_div_2d(b, k * MP_DIGIT_BIT, &B1, &B0)) != MP_OKAY) goto LBL_ERR; diff --git a/s_mp_div_school.c b/s_mp_div_school.c index 6ff427a1b..cf34cc97b 100644 --- a/s_mp_div_school.c +++ b/s_mp_div_school.c @@ -140,8 +140,6 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) mp_exch(&x, d); } - err = MP_OKAY; - LBL_Y: mp_clear(&y); LBL_X: diff --git a/tommath_private.h b/tommath_private.h index 0f5ac9345..31f1ea578 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -148,6 +148,8 @@ extern void MP_FREE(void *mem, size_t size); #define MP_TOUPPER(c) ((((c) >= 'a') && ((c) <= 'z')) ? (((c) + 'A') - 'a') : (c)) +#define MP_EXCH(t, a, b) do { t _c = a; a = b; b = _c; } while (0) + /* Static assertion */ #define MP_STATIC_ASSERT(msg, cond) typedef char mp_static_assert_##msg[(cond) ? 1 : -1]; @@ -267,9 +269,9 @@ extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; #define MP_GET_MAG(name, type) \ type name(const mp_int* a) \ { \ - unsigned i = MP_MIN((unsigned)a->used, (unsigned)((MP_SIZEOF_BITS(type) + MP_DIGIT_BIT - 1) / MP_DIGIT_BIT)); \ + int i = MP_MIN(a->used, (int)((MP_SIZEOF_BITS(type) + MP_DIGIT_BIT - 1) / MP_DIGIT_BIT)); \ type res = 0u; \ - while (i --> 0u) { \ + while (i --> 0) { \ res <<= ((MP_SIZEOF_BITS(type) <= MP_DIGIT_BIT) ? 0 : MP_DIGIT_BIT); \ res |= (type)a->dp[i]; \ if (MP_SIZEOF_BITS(type) <= MP_DIGIT_BIT) { break; } \ From 2bbdbd0651216bd33b130a1e49e18e7cf2339dc6 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 3 Nov 2019 16:55:35 +0100 Subject: [PATCH 101/304] MP_MIN_PREC>=3 is needed for s_mp_div_school test with MP_PREC=MP_MIN_PREC --- .travis.yml | 1 + tommath_private.h | 8 +++++--- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index 0f6f7872c..6c7868968 100644 --- a/.travis.yml +++ b/.travis.yml @@ -145,6 +145,7 @@ matrix: - env: SANITIZER=1 CONV_WARNINGS=relaxed BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --c89 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind --cflags=-DMP_PREC=MP_MIN_PREC' - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-6.0 --with-m64 --with-travis-valgrind' addons: apt: diff --git a/tommath_private.h b/tommath_private.h index 31f1ea578..f2989d42b 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -177,9 +177,11 @@ MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) # endif #endif -/* Minimum number of available digits in mp_int, MP_PREC >= MP_MIN_PREC */ -#define MP_MIN_PREC ((((int)MP_SIZEOF_BITS(long long) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) - +/* Minimum number of available digits in mp_int, MP_PREC >= MP_MIN_PREC + * - Must be at least 3 for s_mp_div_school. + * - Must be large enough such that uint64_t can be stored in mp_int without growing + */ +#define MP_MIN_PREC MP_MAX(3, (((int)MP_SIZEOF_BITS(long long) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) /* random number source */ From e60149dec7e934acab47e69ce79b77823b3c1adc Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:26:25 +0100 Subject: [PATCH 102/304] simplifications: replace mp_mod_d by macro --- mp_mod_d.c | 10 ---------- tommath.h | 2 +- 2 files changed, 1 insertion(+), 11 deletions(-) delete mode 100644 mp_mod_d.c diff --git a/mp_mod_d.c b/mp_mod_d.c deleted file mode 100644 index 3f7e1917f..000000000 --- a/mp_mod_d.c +++ /dev/null @@ -1,10 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_MOD_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_err mp_mod_d(const mp_int *a, mp_digit b, mp_digit *c) -{ - return mp_div_d(a, b, NULL, c); -} -#endif diff --git a/tommath.h b/tommath.h index 86b19d3be..823154a48 100644 --- a/tommath.h +++ b/tommath.h @@ -398,7 +398,7 @@ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) MP_WUR; mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) MP_WUR; /* c = a mod b, 0 <= c < b */ -mp_err mp_mod_d(const mp_int *a, mp_digit b, mp_digit *c) MP_WUR; +#define mp_mod_d(a, b, c) mp_div_d((a), (b), NULL, (c)) /* ---> number theory <--- */ From 143e0376a16462198a3412243e776ff9b69742d5 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:02:32 +0100 Subject: [PATCH 103/304] simplifications: basic arithmetic functions --- mp_add_d.c | 39 ++++++++---------------- mp_div_2.c | 19 ++++-------- mp_div_2d.c | 34 ++++++++------------- mp_div_d.c | 9 ++---- mp_mul.c | 16 +++++----- mp_mul_2.c | 61 ++++++++++++++++---------------------- mp_mul_2d.c | 27 ++++++++--------- mp_mul_d.c | 27 +++++++---------- mp_sub_d.c | 27 +++++++---------- s_mp_add.c | 85 +++++++++++++++++++++-------------------------------- s_mp_sqr.c | 28 ++++++++---------- s_mp_sub.c | 75 +++++++++++++++++++--------------------------- 12 files changed, 176 insertions(+), 271 deletions(-) diff --git a/mp_add_d.c b/mp_add_d.c index 4508cc87b..43d50e879 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -6,9 +6,7 @@ /* single digit addition */ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) { - mp_err err; - int ix, oldused; - mp_digit *tmpa, *tmpc; + int oldused; /* fast path for a == c */ if (a == c) { @@ -27,6 +25,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) /* grow c as required */ if (c->alloc < (a->used + 1)) { + mp_err err; if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { return err; } @@ -34,6 +33,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) /* if a is negative and |a| >= b, call c = |a| - b */ if ((a->sign == MP_NEG) && ((a->used > 1) || (a->dp[0] >= b))) { + mp_err err; mp_int a_ = *a; /* temporarily fix sign of a */ a_.sign = MP_ZPOS; @@ -53,49 +53,34 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) /* old number of used digits in c */ oldused = c->used; - /* source alias */ - tmpa = a->dp; - - /* destination alias */ - tmpc = c->dp; - /* if a is positive */ if (a->sign == MP_ZPOS) { /* add digits, mu is carry */ + int i; mp_digit mu = b; - for (ix = 0; ix < a->used; ix++) { - *tmpc = *tmpa++ + mu; - mu = *tmpc >> MP_DIGIT_BIT; - *tmpc++ &= MP_MASK; + for (i = 0; i < a->used; i++) { + c->dp[i] = a->dp[i] + mu; + mu = c->dp[i] >> MP_DIGIT_BIT; + c->dp[i] &= MP_MASK; } /* set final carry */ - ix++; - *tmpc++ = mu; + c->dp[i] = mu; /* setup size */ c->used = a->used + 1; } else { /* a was negative and |a| < b */ - c->used = 1; + c->used = 1; /* the result is a single digit */ - if (a->used == 1) { - *tmpc++ = b - a->dp[0]; - } else { - *tmpc++ = b; - } - - /* setup count so the clearing of oldused - * can fall through correctly - */ - ix = 1; + c->dp[0] = (a->used == 1) ? b - a->dp[0] : b; } /* sign always positive */ c->sign = MP_ZPOS; /* now zero to oldused */ - MP_ZERO_DIGITS(tmpc, oldused - ix); + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/mp_div_2.c b/mp_div_2.c index 60bd63d6e..573570d9d 100644 --- a/mp_div_2.c +++ b/mp_div_2.c @@ -6,12 +6,11 @@ /* b = a/2 */ mp_err mp_div_2(const mp_int *a, mp_int *b) { - int x, oldused; - mp_digit r, rr, *tmpa, *tmpb; - mp_err err; + int x, oldused; + mp_digit r; - /* copy */ if (b->alloc < a->used) { + mp_err err; if ((err = mp_grow(b, a->used)) != MP_OKAY) { return err; } @@ -20,20 +19,14 @@ mp_err mp_div_2(const mp_int *a, mp_int *b) oldused = b->used; b->used = a->used; - /* source alias */ - tmpa = a->dp + b->used - 1; - - /* dest alias */ - tmpb = b->dp + b->used - 1; - /* carry */ r = 0; - for (x = b->used - 1; x >= 0; x--) { + for (x = b->used; x --> 0;) { /* get the carry for the next iteration */ - rr = *tmpa & 1u; + mp_digit rr = a->dp[x] & 1u; /* shift the current digit, add in carry and store */ - *tmpb-- = (*tmpa-- >> 1) | (r << (MP_DIGIT_BIT - 1)); + b->dp[x] = (a->dp[x] >> 1) | (r << (MP_DIGIT_BIT - 1)); /* forward carry to next iteration */ r = rr; diff --git a/mp_div_2d.c b/mp_div_2d.c index 9b396acdc..e523465af 100644 --- a/mp_div_2d.c +++ b/mp_div_2d.c @@ -6,23 +6,16 @@ /* shift right by a certain bit count (store quotient in c, optional remainder in d) */ mp_err mp_div_2d(const mp_int *a, int b, mp_int *c, mp_int *d) { - mp_digit D, r, rr; - int x; mp_err err; - /* if the shift count is <= 0 then we do no work */ - if (b <= 0) { - err = mp_copy(a, c); - if (d != NULL) { - mp_zero(d); - } - return err; + if (b < 0) { + return MP_VAL; } - /* copy */ if ((err = mp_copy(a, c)) != MP_OKAY) { return err; } + /* 'a' should not be used after here - it might be the same as d */ /* get the remainder */ @@ -38,28 +31,25 @@ mp_err mp_div_2d(const mp_int *a, int b, mp_int *c, mp_int *d) } /* shift any bit count < MP_DIGIT_BIT */ - D = (mp_digit)(b % MP_DIGIT_BIT); - if (D != 0u) { - mp_digit *tmpc, mask, shift; + b %= MP_DIGIT_BIT; + if (b != 0u) { + int x; + mp_digit r, mask, shift; /* mask */ - mask = ((mp_digit)1 << D) - 1uL; + mask = ((mp_digit)1 << b) - 1uL; /* shift for lsb */ - shift = (mp_digit)MP_DIGIT_BIT - D; - - /* alias */ - tmpc = c->dp + (c->used - 1); + shift = (mp_digit)(MP_DIGIT_BIT - b); /* carry */ r = 0; - for (x = c->used - 1; x >= 0; x--) { + for (x = c->used; x --> 0;) { /* get the lower bits of this word in a temp */ - rr = *tmpc & mask; + mp_digit rr = c->dp[x] & mask; /* shift the current word and mix in the carry bits from the previous word */ - *tmpc = (*tmpc >> D) | (r << shift); - --tmpc; + c->dp[x] = (c->dp[x] >> b) | (r << shift); /* set the carry to the carry bits of the current word found above */ r = rr; diff --git a/mp_div_d.c b/mp_div_d.c index 98b6b248c..472ab2796 100644 --- a/mp_div_d.c +++ b/mp_div_d.c @@ -8,7 +8,6 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) { mp_int q; mp_word w; - mp_digit t; mp_err err; int ix; @@ -56,14 +55,12 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) q.used = a->used; q.sign = a->sign; w = 0; - for (ix = a->used - 1; ix >= 0; ix--) { + for (ix = a->used; ix --> 0;) { + mp_digit t = 0; w = (w << (mp_word)MP_DIGIT_BIT) | (mp_word)a->dp[ix]; - if (w >= b) { t = (mp_digit)(w / b); w -= (mp_word)t * (mp_word)b; - } else { - t = 0; } q.dp[ix] = t; } @@ -78,7 +75,7 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) } mp_clear(&q); - return err; + return MP_OKAY; } #endif diff --git a/mp_mul.c b/mp_mul.c index 9c8f8aeda..1a7091c23 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -7,8 +7,8 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_err err; - int min_len = MP_MIN(a->used, b->used), - max_len = MP_MAX(a->used, b->used), + int min = MP_MIN(a->used, b->used), + max = MP_MAX(a->used, b->used), digs = a->used + b->used + 1; mp_sign neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; @@ -20,16 +20,16 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) * Using it to cut the input into slices small enough for s_mp_mul_digs_fast * was actually slower on the author's machine, but YMMV. */ - (min_len >= MP_KARATSUBA_MUL_CUTOFF) && - ((max_len / 2) >= MP_KARATSUBA_MUL_CUTOFF) && + (min >= MP_KARATSUBA_MUL_CUTOFF) && + ((max / 2) >= MP_KARATSUBA_MUL_CUTOFF) && /* Not much effect was observed below a ratio of 1:2, but again: YMMV. */ - (max_len >= (2 * min_len))) { + (max >= (2 * min))) { err = s_mp_balance_mul(a,b,c); } else if (MP_HAS(S_MP_TOOM_MUL) && - (min_len >= MP_TOOM_MUL_CUTOFF)) { + (min >= MP_TOOM_MUL_CUTOFF)) { err = s_mp_toom_mul(a, b, c); } else if (MP_HAS(S_MP_KARATSUBA_MUL) && - (min_len >= MP_KARATSUBA_MUL_CUTOFF)) { + (min >= MP_KARATSUBA_MUL_CUTOFF)) { err = s_mp_karatsuba_mul(a, b, c); } else if (MP_HAS(S_MP_MUL_DIGS_FAST) && /* can we use the fast multiplier? @@ -39,7 +39,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) * digits won't affect carry propagation */ (digs < MP_WARRAY) && - (min_len <= MP_MAXFAST)) { + (min <= MP_MAXFAST)) { err = s_mp_mul_digs_fast(a, b, c, digs); } else if (MP_HAS(S_MP_MUL_DIGS)) { err = s_mp_mul_digs(a, b, c, digs); diff --git a/mp_mul_2.c b/mp_mul_2.c index cd5589dd2..45b6f1cc5 100644 --- a/mp_mul_2.c +++ b/mp_mul_2.c @@ -6,11 +6,12 @@ /* b = a*2 */ mp_err mp_mul_2(const mp_int *a, mp_int *b) { - int x, oldused; - mp_err err; + int x, oldused; + mp_digit r; /* grow to accomodate result */ if (b->alloc < (a->used + 1)) { + mp_err err; if ((err = mp_grow(b, a->used + 1)) != MP_OKAY) { return err; } @@ -19,45 +20,35 @@ mp_err mp_mul_2(const mp_int *a, mp_int *b) oldused = b->used; b->used = a->used; - { - mp_digit r, rr, *tmpa, *tmpb; + /* carry */ + r = 0; + for (x = 0; x < a->used; x++) { - /* alias for source */ - tmpa = a->dp; - - /* alias for dest */ - tmpb = b->dp; - - /* carry */ - r = 0; - for (x = 0; x < a->used; x++) { + /* get what will be the *next* carry bit from the + * MSB of the current digit + */ + mp_digit rr = a->dp[x] >> (mp_digit)(MP_DIGIT_BIT - 1); - /* get what will be the *next* carry bit from the - * MSB of the current digit - */ - rr = *tmpa >> (mp_digit)(MP_DIGIT_BIT - 1); + /* now shift up this digit, add in the carry [from the previous] */ + b->dp[x] = ((a->dp[x] << 1uL) | r) & MP_MASK; - /* now shift up this digit, add in the carry [from the previous] */ - *tmpb++ = ((*tmpa++ << 1uL) | r) & MP_MASK; + /* copy the carry that would be from the source + * digit into the next iteration + */ + r = rr; + } - /* copy the carry that would be from the source - * digit into the next iteration - */ - r = rr; - } + /* new leading digit? */ + if (r != 0u) { + /* add a MSB which is always 1 at this point */ + b->dp[b->used++] = 1; + } - /* new leading digit? */ - if (r != 0u) { - /* add a MSB which is always 1 at this point */ - *tmpb = 1; - ++(b->used); - } + /* now zero any excess digits on the destination + * that we didn't write to + */ + MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); - /* now zero any excess digits on the destination - * that we didn't write to - */ - MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); - } b->sign = a->sign; return MP_OKAY; } diff --git a/mp_mul_2d.c b/mp_mul_2d.c index 1ba53a0fc..f1016ead5 100644 --- a/mp_mul_2d.c +++ b/mp_mul_2d.c @@ -6,17 +6,19 @@ /* shift left by a certain bit count */ mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c) { - mp_digit d; - mp_err err; + if (b < 0) { + return MP_VAL; + } - /* copy */ if (a != c) { + mp_err err; if ((err = mp_copy(a, c)) != MP_OKAY) { return err; } } if (c->alloc < (c->used + (b / MP_DIGIT_BIT) + 1)) { + mp_err err; if ((err = mp_grow(c, c->used + (b / MP_DIGIT_BIT) + 1)) != MP_OKAY) { return err; } @@ -24,35 +26,32 @@ mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c) /* shift by as many digits in the bit count */ if (b >= MP_DIGIT_BIT) { + mp_err err; if ((err = mp_lshd(c, b / MP_DIGIT_BIT)) != MP_OKAY) { return err; } } /* shift any bit count < MP_DIGIT_BIT */ - d = (mp_digit)(b % MP_DIGIT_BIT); - if (d != 0u) { - mp_digit *tmpc, shift, mask, r, rr; + b %= MP_DIGIT_BIT; + if (b != 0u) { + mp_digit shift, mask, r; int x; /* bitmask for carries */ - mask = ((mp_digit)1 << d) - (mp_digit)1; + mask = ((mp_digit)1 << b) - (mp_digit)1; /* shift for msbs */ - shift = (mp_digit)MP_DIGIT_BIT - d; - - /* alias */ - tmpc = c->dp; + shift = (mp_digit)(MP_DIGIT_BIT - b); /* carry */ r = 0; for (x = 0; x < c->used; x++) { /* get the higher bits of the current word */ - rr = (*tmpc >> shift) & mask; + mp_digit rr = (c->dp[x] >> shift) & mask; /* shift the current word and OR in the carry */ - *tmpc = ((*tmpc << d) | r) & MP_MASK; - ++tmpc; + c->dp[x] = ((c->dp[x] << b) | r) & MP_MASK; /* set the carry to the carry bits of the current word */ r = rr; diff --git a/mp_mul_d.c b/mp_mul_d.c index 399dc7b47..3e5335f42 100644 --- a/mp_mul_d.c +++ b/mp_mul_d.c @@ -6,10 +6,9 @@ /* multiply by a digit */ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) { - mp_digit u, *tmpa, *tmpc; - mp_word r; + mp_digit u; mp_err err; - int ix, olduse; + int ix, oldused; /* make sure c is big enough to hold a*b */ if (c->alloc < (a->used + 1)) { @@ -19,41 +18,35 @@ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) } /* get the original destinations used count */ - olduse = c->used; + oldused = c->used; /* set the sign */ c->sign = a->sign; - /* alias for a->dp [source] */ - tmpa = a->dp; - - /* alias for c->dp [dest] */ - tmpc = c->dp; - /* zero carry */ u = 0; /* compute columns */ for (ix = 0; ix < a->used; ix++) { /* compute product and carry sum for this term */ - r = (mp_word)u + ((mp_word)*tmpa++ * (mp_word)b); + mp_word r = (mp_word)u + ((mp_word)a->dp[ix] * (mp_word)b); /* mask off higher bits to get a single digit */ - *tmpc++ = (mp_digit)(r & (mp_word)MP_MASK); + c->dp[ix] = (mp_digit)(r & (mp_word)MP_MASK); /* send carry into next iteration */ u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); } /* store final carry [if any] and increment ix offset */ - *tmpc++ = u; - ++ix; - - /* now zero digits above the top */ - MP_ZERO_DIGITS(tmpc, olduse - ix); + c->dp[ix] = u; /* set used count */ c->used = a->used + 1; + + /* now zero digits above the top */ + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + mp_clamp(c); return MP_OKAY; diff --git a/mp_sub_d.c b/mp_sub_d.c index 96a747cb6..c5cf7266b 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -6,9 +6,7 @@ /* single digit subtraction */ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) { - mp_digit *tmpa, *tmpc; - mp_err err; - int ix, oldused; + int oldused; /* fast path for a == c */ if (a == c) { @@ -26,6 +24,7 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) /* grow c as required */ if (c->alloc < (a->used + 1)) { + mp_err err; if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { return err; } @@ -35,6 +34,7 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) * addition [with fudged signs] */ if (a->sign == MP_NEG) { + mp_err err; mp_int a_ = *a; a_.sign = MP_ZPOS; err = mp_add_d(&a_, b, c); @@ -46,24 +46,17 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) return err; } - /* setup regs */ oldused = c->used; - tmpa = a->dp; - tmpc = c->dp; /* if a <= b simply fix the single digit */ if (((a->used == 1) && (a->dp[0] <= b)) || (a->used == 0)) { - if (a->used == 1) { - *tmpc++ = b - *tmpa; - } else { - *tmpc++ = b; - } - ix = 1; + c->dp[0] = (a->used == 1) ? b - a->dp[0] : b; /* negative/1digit */ c->sign = MP_NEG; c->used = 1; } else { + int i; mp_digit mu = b; /* positive/size */ @@ -71,15 +64,15 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) c->used = a->used; /* subtract digits, mu is carry */ - for (ix = 0; ix < a->used; ix++) { - *tmpc = *tmpa++ - mu; - mu = *tmpc >> (MP_SIZEOF_BITS(mp_digit) - 1u); - *tmpc++ &= MP_MASK; + for (i = 0; i < a->used; i++) { + c->dp[i] = a->dp[i] - mu; + mu = c->dp[i] >> (MP_SIZEOF_BITS(mp_digit) - 1u); + c->dp[i] &= MP_MASK; } } /* zero excess digits */ - MP_ZERO_DIGITS(tmpc, oldused - ix); + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_add.c b/s_mp_add.c index 922071996..1dd09f8ee 100644 --- a/s_mp_add.c +++ b/s_mp_add.c @@ -6,84 +6,65 @@ /* low level addition, based on HAC pp.594, Algorithm 14.7 */ mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) { - const mp_int *x; - mp_err err; - int olduse, min, max; + int oldused, min, max, i; + mp_digit u; /* find sizes, we let |a| <= |b| which means we have to sort * them. "x" will point to the input with the most digits */ - if (a->used > b->used) { - min = b->used; - max = a->used; - x = a; - } else { - min = a->used; - max = b->used; - x = b; + if (a->used < b->used) { + MP_EXCH(const mp_int *, a, b); } + min = b->used; + max = a->used; + /* init result */ if (c->alloc < (max + 1)) { + mp_err err; if ((err = mp_grow(c, max + 1)) != MP_OKAY) { return err; } } /* get old used digit count and set new one */ - olduse = c->used; + oldused = c->used; c->used = max + 1; - { - mp_digit u, *tmpa, *tmpb, *tmpc; - int i; - - /* alias for digit pointers */ - - /* first input */ - tmpa = a->dp; + /* zero the carry */ + u = 0; + for (i = 0; i < min; i++) { + /* Compute the sum at one digit, T[i] = A[i] + B[i] + U */ + c->dp[i] = a->dp[i] + b->dp[i] + u; - /* second input */ - tmpb = b->dp; + /* U = carry bit of T[i] */ + u = c->dp[i] >> (mp_digit)MP_DIGIT_BIT; - /* destination */ - tmpc = c->dp; + /* take away carry bit from T[i] */ + c->dp[i] &= MP_MASK; + } - /* zero the carry */ - u = 0; - for (i = 0; i < min; i++) { - /* Compute the sum at one digit, T[i] = A[i] + B[i] + U */ - *tmpc = *tmpa++ + *tmpb++ + u; + /* now copy higher words if any, that is in A+B + * if A or B has more digits add those in + */ + if (min != max) { + for (; i < max; i++) { + /* T[i] = A[i] + U */ + c->dp[i] = a->dp[i] + u; /* U = carry bit of T[i] */ - u = *tmpc >> (mp_digit)MP_DIGIT_BIT; + u = c->dp[i] >> (mp_digit)MP_DIGIT_BIT; /* take away carry bit from T[i] */ - *tmpc++ &= MP_MASK; - } - - /* now copy higher words if any, that is in A+B - * if A or B has more digits add those in - */ - if (min != max) { - for (; i < max; i++) { - /* T[i] = X[i] + U */ - *tmpc = x->dp[i] + u; - - /* U = carry bit of T[i] */ - u = *tmpc >> (mp_digit)MP_DIGIT_BIT; - - /* take away carry bit from T[i] */ - *tmpc++ &= MP_MASK; - } + c->dp[i] &= MP_MASK; } + } - /* add carry */ - *tmpc++ = u; + /* add carry */ + c->dp[i] = u; - /* clear digits above oldused */ - MP_ZERO_DIGITS(tmpc, olduse - c->used); - } + /* clear digits above oldused */ + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_sqr.c b/s_mp_sqr.c index 61106ed73..4a2030638 100644 --- a/s_mp_sqr.c +++ b/s_mp_sqr.c @@ -7,10 +7,8 @@ mp_err s_mp_sqr(const mp_int *a, mp_int *b) { mp_int t; - int ix, iy, pa; + int ix, pa; mp_err err; - mp_word r; - mp_digit u, tmpx, *tmpt; pa = a->used; if ((err = mp_init_size(&t, (2 * pa) + 1)) != MP_OKAY) { @@ -21,10 +19,13 @@ mp_err s_mp_sqr(const mp_int *a, mp_int *b) t.used = (2 * pa) + 1; for (ix = 0; ix < pa; ix++) { + mp_digit u; + int iy; + /* first calculate the digit at 2*ix */ /* calculate double precision result */ - r = (mp_word)t.dp[2*ix] + - ((mp_word)a->dp[ix] * (mp_word)a->dp[ix]); + mp_word r = (mp_word)t.dp[2*ix] + + ((mp_word)a->dp[ix] * (mp_word)a->dp[ix]); /* store lower part in result */ t.dp[ix+ix] = (mp_digit)(r & (mp_word)MP_MASK); @@ -32,32 +33,27 @@ mp_err s_mp_sqr(const mp_int *a, mp_int *b) /* get the carry */ u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); - /* left hand side of A[ix] * A[iy] */ - tmpx = a->dp[ix]; - - /* alias for where to store the results */ - tmpt = t.dp + ((2 * ix) + 1); - for (iy = ix + 1; iy < pa; iy++) { /* first calculate the product */ - r = (mp_word)tmpx * (mp_word)a->dp[iy]; + r = (mp_word)a->dp[ix] * (mp_word)a->dp[iy]; /* now calculate the double precision result, note we use * addition instead of *2 since it's easier to optimize */ - r = (mp_word)*tmpt + r + r + (mp_word)u; + r = (mp_word)t.dp[ix + iy] + r + r + (mp_word)u; /* store lower part */ - *tmpt++ = (mp_digit)(r & (mp_word)MP_MASK); + t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); /* get carry */ u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); } /* propagate upwards */ while (u != 0uL) { - r = (mp_word)*tmpt + (mp_word)u; - *tmpt++ = (mp_digit)(r & (mp_word)MP_MASK); + r = (mp_word)t.dp[ix + iy] + (mp_word)u; + t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); + ++iy; } } diff --git a/s_mp_sub.c b/s_mp_sub.c index bef1fce53..05386e5f7 100644 --- a/s_mp_sub.c +++ b/s_mp_sub.c @@ -6,64 +6,51 @@ /* low level subtraction (assumes |a| > |b|), HAC pp.595 Algorithm 14.9 */ mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) { - int olduse, min, max; - mp_err err; - - /* find sizes */ - min = b->used; - max = a->used; + int oldused = c->used, min = b->used, max = a->used, i; + mp_digit u; /* init result */ if (c->alloc < max) { + mp_err err; if ((err = mp_grow(c, max)) != MP_OKAY) { return err; } } - olduse = c->used; - c->used = max; - - { - mp_digit u, *tmpa, *tmpb, *tmpc; - int i; - - /* alias for digit pointers */ - tmpa = a->dp; - tmpb = b->dp; - tmpc = c->dp; - - /* set carry to zero */ - u = 0; - for (i = 0; i < min; i++) { - /* T[i] = A[i] - B[i] - U */ - *tmpc = (*tmpa++ - *tmpb++) - u; - - /* U = carry bit of T[i] - * Note this saves performing an AND operation since - * if a carry does occur it will propagate all the way to the - * MSB. As a result a single shift is enough to get the carry - */ - u = *tmpc >> (MP_SIZEOF_BITS(mp_digit) - 1u); - /* Clear carry from T[i] */ - *tmpc++ &= MP_MASK; - } + c->used = max; - /* now copy higher words if any, e.g. if A has more digits than B */ - for (; i < max; i++) { - /* T[i] = A[i] - U */ - *tmpc = *tmpa++ - u; + /* set carry to zero */ + u = 0; + for (i = 0; i < min; i++) { + /* T[i] = A[i] - B[i] - U */ + c->dp[i] = (a->dp[i] - b->dp[i]) - u; + + /* U = carry bit of T[i] + * Note this saves performing an AND operation since + * if a carry does occur it will propagate all the way to the + * MSB. As a result a single shift is enough to get the carry + */ + u = c->dp[i] >> (MP_SIZEOF_BITS(mp_digit) - 1u); + + /* Clear carry from T[i] */ + c->dp[i] &= MP_MASK; + } - /* U = carry bit of T[i] */ - u = *tmpc >> (MP_SIZEOF_BITS(mp_digit) - 1u); + /* now copy higher words if any, e.g. if A has more digits than B */ + for (; i < max; i++) { + /* T[i] = A[i] - U */ + c->dp[i] = a->dp[i] - u; - /* Clear carry from T[i] */ - *tmpc++ &= MP_MASK; - } + /* U = carry bit of T[i] */ + u = c->dp[i] >> (MP_SIZEOF_BITS(mp_digit) - 1u); - /* clear digits above used (since we may not have grown result above) */ - MP_ZERO_DIGITS(tmpc, olduse - c->used); + /* Clear carry from T[i] */ + c->dp[i] &= MP_MASK; } + /* clear digits above used (since we may not have grown result above) */ + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + mp_clamp(c); return MP_OKAY; } From 7b6c6965bb947a92c9d03d9224dcfa379ae72d39 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:05:30 +0100 Subject: [PATCH 104/304] simplifications: toom and karatsuba --- s_mp_balance_mul.c | 32 +++++++---------- s_mp_karatsuba_mul.c | 81 +++++++++++++++++--------------------------- s_mp_karatsuba_sqr.c | 60 +++++++++++++------------------- s_mp_toom_sqr.c | 12 ++----- 4 files changed, 71 insertions(+), 114 deletions(-) diff --git a/s_mp_balance_mul.c b/s_mp_balance_mul.c index 410883020..77852a427 100644 --- a/s_mp_balance_mul.c +++ b/s_mp_balance_mul.c @@ -6,15 +6,11 @@ /* single-digit multiplication with the smaller number as the single-digit */ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) { - int count, len_a, len_b, nblocks, i, j, bsize; - mp_int a0, tmp, A, B, r; + mp_int a0, tmp, r; mp_err err; - - len_a = a->used; - len_b = b->used; - - nblocks = MP_MAX(a->used, b->used) / MP_MIN(a->used, b->used); - bsize = MP_MIN(a->used, b->used) ; + int i, j, count, + nblocks = MP_MAX(a->used, b->used) / MP_MIN(a->used, b->used), + bsize = MP_MIN(a->used, b->used); if ((err = mp_init_size(&a0, bsize + 2)) != MP_OKAY) { return err; @@ -25,24 +21,20 @@ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) } /* Make sure that A is the larger one*/ - if (len_a < len_b) { - B = *a; - A = *b; - } else { - A = *a; - B = *b; + if (a->used < b->used) { + MP_EXCH(const mp_int *, a, b); } for (i = 0, j=0; i < nblocks; i++) { /* Cut a slice off of a */ a0.used = 0; for (count = 0; count < bsize; count++) { - a0.dp[count] = A.dp[ j++ ]; + a0.dp[count] = a->dp[ j++ ]; a0.used++; } mp_clamp(&a0); /* Multiply with b */ - if ((err = mp_mul(&a0, &B, &tmp)) != MP_OKAY) { + if ((err = mp_mul(&a0, b, &tmp)) != MP_OKAY) { goto LBL_ERR; } /* Shift tmp to the correct position */ @@ -55,14 +47,14 @@ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) } } /* The left-overs; there are always left-overs */ - if (j < A.used) { + if (j < a->used) { a0.used = 0; - for (count = 0; j < A.used; count++) { - a0.dp[count] = A.dp[ j++ ]; + for (count = 0; j < a->used; count++) { + a0.dp[count] = a->dp[ j++ ]; a0.used++; } mp_clamp(&a0); - if ((err = mp_mul(&a0, &B, &tmp)) != MP_OKAY) { + if ((err = mp_mul(&a0, b, &tmp)) != MP_OKAY) { goto LBL_ERR; } if ((err = mp_lshd(&tmp, bsize * i)) != MP_OKAY) { diff --git a/s_mp_karatsuba_mul.c b/s_mp_karatsuba_mul.c index df3daa7ee..762e5e21d 100644 --- a/s_mp_karatsuba_mul.c +++ b/s_mp_karatsuba_mul.c @@ -35,8 +35,8 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x0, x1, y0, y1, t1, x0y0, x1y1; - int B; - mp_err err = MP_MEM; /* default the return code to an error */ + int B, i; + mp_err err; /* min # of digits */ B = MP_MIN(a->used, b->used); @@ -45,27 +45,27 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) B = B >> 1; /* init copy all the temps */ - if (mp_init_size(&x0, B) != MP_OKAY) { + if ((err = mp_init_size(&x0, B)) != MP_OKAY) { goto LBL_ERR; } - if (mp_init_size(&x1, a->used - B) != MP_OKAY) { + if ((err = mp_init_size(&x1, a->used - B)) != MP_OKAY) { goto X0; } - if (mp_init_size(&y0, B) != MP_OKAY) { + if ((err = mp_init_size(&y0, B)) != MP_OKAY) { goto X1; } - if (mp_init_size(&y1, b->used - B) != MP_OKAY) { + if ((err = mp_init_size(&y1, b->used - B)) != MP_OKAY) { goto Y0; } /* init temps */ - if (mp_init_size(&t1, B * 2) != MP_OKAY) { + if ((err = mp_init_size(&t1, B * 2)) != MP_OKAY) { goto Y1; } - if (mp_init_size(&x0y0, B * 2) != MP_OKAY) { + if ((err = mp_init_size(&x0y0, B * 2)) != MP_OKAY) { goto T1; } - if (mp_init_size(&x1y1, B * 2) != MP_OKAY) { + if ((err = mp_init_size(&x1y1, B * 2)) != MP_OKAY) { goto X0Y0; } @@ -74,32 +74,18 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) x1.used = a->used - B; y1.used = b->used - B; - { - int x; - mp_digit *tmpa, *tmpb, *tmpx, *tmpy; - - /* we copy the digits directly instead of using higher level functions - * since we also need to shift the digits - */ - tmpa = a->dp; - tmpb = b->dp; - - tmpx = x0.dp; - tmpy = y0.dp; - for (x = 0; x < B; x++) { - *tmpx++ = *tmpa++; - *tmpy++ = *tmpb++; - } - - tmpx = x1.dp; - for (x = B; x < a->used; x++) { - *tmpx++ = *tmpa++; - } - - tmpy = y1.dp; - for (x = B; x < b->used; x++) { - *tmpy++ = *tmpb++; - } + /* we copy the digits directly instead of using higher level functions + * since we also need to shift the digits + */ + for (i = 0; i < B; i++) { + x0.dp[i] = a->dp[i]; + y0.dp[i] = b->dp[i]; + } + for (i = B; i < a->used; i++) { + x1.dp[i - B] = a->dp[i]; + } + for (i = B; i < b->used; i++) { + y1.dp[i - B] = b->dp[i]; } /* only need to clamp the lower words since by definition the @@ -110,50 +96,47 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) /* now calc the products x0y0 and x1y1 */ /* after this x0 is no longer required, free temp [x0==t2]! */ - if (mp_mul(&x0, &y0, &x0y0) != MP_OKAY) { + if ((err = mp_mul(&x0, &y0, &x0y0)) != MP_OKAY) { goto X1Y1; /* x0y0 = x0*y0 */ } - if (mp_mul(&x1, &y1, &x1y1) != MP_OKAY) { + if ((err = mp_mul(&x1, &y1, &x1y1)) != MP_OKAY) { goto X1Y1; /* x1y1 = x1*y1 */ } /* now calc x1+x0 and y1+y0 */ - if (s_mp_add(&x1, &x0, &t1) != MP_OKAY) { + if ((err = s_mp_add(&x1, &x0, &t1)) != MP_OKAY) { goto X1Y1; /* t1 = x1 - x0 */ } - if (s_mp_add(&y1, &y0, &x0) != MP_OKAY) { + if ((err = s_mp_add(&y1, &y0, &x0)) != MP_OKAY) { goto X1Y1; /* t2 = y1 - y0 */ } - if (mp_mul(&t1, &x0, &t1) != MP_OKAY) { + if ((err = mp_mul(&t1, &x0, &t1)) != MP_OKAY) { goto X1Y1; /* t1 = (x1 + x0) * (y1 + y0) */ } /* add x0y0 */ - if (mp_add(&x0y0, &x1y1, &x0) != MP_OKAY) { + if ((err = mp_add(&x0y0, &x1y1, &x0)) != MP_OKAY) { goto X1Y1; /* t2 = x0y0 + x1y1 */ } - if (s_mp_sub(&t1, &x0, &t1) != MP_OKAY) { + if ((err = s_mp_sub(&t1, &x0, &t1)) != MP_OKAY) { goto X1Y1; /* t1 = (x1+x0)*(y1+y0) - (x1y1 + x0y0) */ } /* shift by B */ - if (mp_lshd(&t1, B) != MP_OKAY) { + if ((err = mp_lshd(&t1, B)) != MP_OKAY) { goto X1Y1; /* t1 = (x0y0 + x1y1 - (x1-x0)*(y1-y0))<used; @@ -23,37 +23,27 @@ mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) B = B >> 1; /* init copy all the temps */ - if (mp_init_size(&x0, B) != MP_OKAY) + if ((err = mp_init_size(&x0, B)) != MP_OKAY) goto LBL_ERR; - if (mp_init_size(&x1, a->used - B) != MP_OKAY) + if ((err = mp_init_size(&x1, a->used - B)) != MP_OKAY) goto X0; /* init temps */ - if (mp_init_size(&t1, a->used * 2) != MP_OKAY) + if ((err = mp_init_size(&t1, a->used * 2)) != MP_OKAY) goto X1; - if (mp_init_size(&t2, a->used * 2) != MP_OKAY) + if ((err = mp_init_size(&t2, a->used * 2)) != MP_OKAY) goto T1; - if (mp_init_size(&x0x0, B * 2) != MP_OKAY) + if ((err = mp_init_size(&x0x0, B * 2)) != MP_OKAY) goto T2; - if (mp_init_size(&x1x1, (a->used - B) * 2) != MP_OKAY) + if ((err = mp_init_size(&x1x1, (a->used - B) * 2)) != MP_OKAY) goto X0X0; - { - int x; - mp_digit *dst, *src; - - src = a->dp; - - /* now shift the digits */ - dst = x0.dp; - for (x = 0; x < B; x++) { - *dst++ = *src++; - } - - dst = x1.dp; - for (x = B; x < a->used; x++) { - *dst++ = *src++; - } + /* now shift the digits */ + for (x = 0; x < B; x++) { + x0.dp[x] = a->dp[x]; + } + for (x = B; x < a->used; x++) { + x1.dp[x - B] = a->dp[x]; } x0.used = B; @@ -62,36 +52,34 @@ mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) mp_clamp(&x0); /* now calc the products x0*x0 and x1*x1 */ - if (mp_sqr(&x0, &x0x0) != MP_OKAY) + if ((err = mp_sqr(&x0, &x0x0)) != MP_OKAY) goto X1X1; /* x0x0 = x0*x0 */ - if (mp_sqr(&x1, &x1x1) != MP_OKAY) + if ((err = mp_sqr(&x1, &x1x1)) != MP_OKAY) goto X1X1; /* x1x1 = x1*x1 */ /* now calc (x1+x0)**2 */ - if (s_mp_add(&x1, &x0, &t1) != MP_OKAY) + if ((err = s_mp_add(&x1, &x0, &t1)) != MP_OKAY) goto X1X1; /* t1 = x1 - x0 */ - if (mp_sqr(&t1, &t1) != MP_OKAY) + if ((err = mp_sqr(&t1, &t1)) != MP_OKAY) goto X1X1; /* t1 = (x1 - x0) * (x1 - x0) */ /* add x0y0 */ - if (s_mp_add(&x0x0, &x1x1, &t2) != MP_OKAY) + if ((err = s_mp_add(&x0x0, &x1x1, &t2)) != MP_OKAY) goto X1X1; /* t2 = x0x0 + x1x1 */ - if (s_mp_sub(&t1, &t2, &t1) != MP_OKAY) + if ((err = s_mp_sub(&t1, &t2, &t1)) != MP_OKAY) goto X1X1; /* t1 = (x1+x0)**2 - (x0x0 + x1x1) */ /* shift by B */ - if (mp_lshd(&t1, B) != MP_OKAY) + if ((err = mp_lshd(&t1, B)) != MP_OKAY) goto X1X1; /* t1 = (x0x0 + x1x1 - (x1-x0)*(x1-x0))<used - (3 * B)))) != MP_OKAY) goto LBL_ERRa2; - tmpa = a->dp; - tmpc = a0.dp; for (count = 0; count < B; count++) { - *tmpc++ = *tmpa++; + a0.dp[count] = a->dp[count]; } - tmpc = a1.dp; for (; count < (2 * B); count++) { - *tmpc++ = *tmpa++; + a1.dp[count - B] = a->dp[count]; } - tmpc = a2.dp; for (; count < a->used; count++) { - *tmpc++ = *tmpa++; + a2.dp[count - 2 * B] = a->dp[count]; a2.used++; } mp_clamp(&a0); From 8ac493512cecd8c2202f0f96bbfb50438f6d6b5c Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:06:20 +0100 Subject: [PATCH 105/304] simplifications: mul/sqr comba --- s_mp_mul_digs.c | 29 ++++++++--------------------- s_mp_mul_digs_fast.c | 32 +++++++++++--------------------- s_mp_mul_high_digs.c | 28 ++++++++-------------------- s_mp_mul_high_digs_fast.c | 29 ++++++++++------------------- s_mp_sqr_fast.c | 32 ++++++++++++-------------------- 5 files changed, 49 insertions(+), 101 deletions(-) diff --git a/s_mp_mul_digs.c b/s_mp_mul_digs.c index ea0985b87..27e51f834 100644 --- a/s_mp_mul_digs.c +++ b/s_mp_mul_digs.c @@ -11,10 +11,7 @@ mp_err s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) { mp_int t; mp_err err; - int pa, pb, ix, iy; - mp_digit u; - mp_word r; - mp_digit tmpx, *tmpt, *tmpy; + int pa, ix; /* can we use the fast multiplier? */ if ((digs < MP_WARRAY) && @@ -30,38 +27,28 @@ mp_err s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* compute the digits of the product directly */ pa = a->used; for (ix = 0; ix < pa; ix++) { - /* set the carry to zero */ - u = 0; + int iy, pb; + mp_digit u = 0; /* limit ourselves to making digs digits of output */ pb = MP_MIN(b->used, digs - ix); - /* setup some aliases */ - /* copy of the digit from a used within the nested loop */ - tmpx = a->dp[ix]; - - /* an alias for the destination shifted ix places */ - tmpt = t.dp + ix; - - /* an alias for the digits of b */ - tmpy = b->dp; - /* compute the columns of the output and propagate the carry */ for (iy = 0; iy < pb; iy++) { /* compute the column as a mp_word */ - r = (mp_word)*tmpt + - ((mp_word)tmpx * (mp_word)*tmpy++) + - (mp_word)u; + mp_word r = (mp_word)t.dp[ix + iy] + + ((mp_word)a->dp[ix] * (mp_word)b->dp[iy]) + + (mp_word)u; /* the new column is the lower part of the result */ - *tmpt++ = (mp_digit)(r & (mp_word)MP_MASK); + t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); /* get the carry word from the result */ u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); } /* set carry if it is placed below digs */ if ((ix + iy) < digs) { - *tmpt = u; + t.dp[ix + pb] = u; } } diff --git a/s_mp_mul_digs_fast.c b/s_mp_mul_digs_fast.c index 8988838fb..44aabd087 100644 --- a/s_mp_mul_digs_fast.c +++ b/s_mp_mul_digs_fast.c @@ -21,7 +21,7 @@ */ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) { - int olduse, pa, ix, iz; + int oldused, pa, ix; mp_err err; mp_digit W[MP_WARRAY]; mp_word _W; @@ -39,18 +39,12 @@ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* clear the carry */ _W = 0; for (ix = 0; ix < pa; ix++) { - int tx, ty; - int iy; - mp_digit *tmpx, *tmpy; + int tx, ty, iy, iz; /* get offsets into the two bignums */ ty = MP_MIN(b->used-1, ix); tx = ix - ty; - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = b->dp + ty; - /* this is the number of times the loop will iterrate, essentially while (tx++ < a->used && ty-- >= 0) { ... } */ @@ -58,8 +52,7 @@ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* execute loop */ for (iz = 0; iz < iy; ++iz) { - _W += (mp_word)*tmpx++ * (mp_word)*tmpy--; - + _W += (mp_word)a->dp[tx + iz] * (mp_word)b->dp[ty - iz]; } /* store term */ @@ -70,20 +63,17 @@ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) } /* setup dest */ - olduse = c->used; + oldused = c->used; c->used = pa; - { - mp_digit *tmpc; - tmpc = c->dp; - for (ix = 0; ix < pa; ix++) { - /* now extract the previous digit [below the carry] */ - *tmpc++ = W[ix]; - } - - /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(tmpc, olduse - ix); + for (ix = 0; ix < pa; ix++) { + /* now extract the previous digit [below the carry] */ + c->dp[ix] = W[ix]; } + + /* clear unused digits [that existed in the old copy of c] */ + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + mp_clamp(c); return MP_OKAY; } diff --git a/s_mp_mul_high_digs.c b/s_mp_mul_high_digs.c index 87cfbe54f..5a8c0731b 100644 --- a/s_mp_mul_high_digs.c +++ b/s_mp_mul_high_digs.c @@ -9,11 +9,8 @@ mp_err s_mp_mul_high_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) { mp_int t; - int pa, pb, ix, iy; + int pa, pb, ix; mp_err err; - mp_digit u; - mp_word r; - mp_digit tmpx, *tmpt, *tmpy; /* can we use the fast multiplier? */ if (MP_HAS(S_MP_MUL_HIGH_DIGS_FAST) @@ -30,31 +27,22 @@ mp_err s_mp_mul_high_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) pa = a->used; pb = b->used; for (ix = 0; ix < pa; ix++) { - /* clear the carry */ - u = 0; - - /* left hand side of A[ix] * B[iy] */ - tmpx = a->dp[ix]; - - /* alias to the address of where the digits will be stored */ - tmpt = &(t.dp[digs]); - - /* alias for where to read the right hand side from */ - tmpy = b->dp + (digs - ix); + int iy; + mp_digit u = 0; for (iy = digs - ix; iy < pb; iy++) { /* calculate the double precision result */ - r = (mp_word)*tmpt + - ((mp_word)tmpx * (mp_word)*tmpy++) + - (mp_word)u; + mp_word r = (mp_word)t.dp[ix + iy] + + ((mp_word)a->dp[ix] * (mp_word)b->dp[iy]) + + (mp_word)u; /* get the lower part */ - *tmpt++ = (mp_digit)(r & (mp_word)MP_MASK); + t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); /* carry the carry */ u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); } - *tmpt = u; + t.dp[ix + pb] = u; } mp_clamp(&t); mp_exch(&t, c); diff --git a/s_mp_mul_high_digs_fast.c b/s_mp_mul_high_digs_fast.c index 1559ebcf4..138476599 100644 --- a/s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_digs_fast.c @@ -14,7 +14,7 @@ */ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) { - int olduse, pa, ix, iz; + int oldused, pa, ix; mp_err err; mp_digit W[MP_WARRAY]; mp_word _W; @@ -31,17 +31,12 @@ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int pa = a->used + b->used; _W = 0; for (ix = digs; ix < pa; ix++) { - int tx, ty, iy; - mp_digit *tmpx, *tmpy; + int tx, ty, iy, iz; /* get offsets into the two bignums */ ty = MP_MIN(b->used-1, ix); tx = ix - ty; - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = b->dp + ty; - /* this is the number of times the loop will iterrate, essentially its while (tx++ < a->used && ty-- >= 0) { ... } */ @@ -49,7 +44,7 @@ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int /* execute loop */ for (iz = 0; iz < iy; iz++) { - _W += (mp_word)*tmpx++ * (mp_word)*tmpy--; + _W += (mp_word)a->dp[tx + iz] * (mp_word)b->dp[ty - iz]; } /* store term */ @@ -60,21 +55,17 @@ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int } /* setup dest */ - olduse = c->used; + oldused = c->used; c->used = pa; - { - mp_digit *tmpc; + for (ix = digs; ix < pa; ix++) { + /* now extract the previous digit [below the carry] */ + c->dp[ix] = W[ix]; + } - tmpc = c->dp + digs; - for (ix = digs; ix < pa; ix++) { - /* now extract the previous digit [below the carry] */ - *tmpc++ = W[ix]; - } + /* clear unused digits [that existed in the old copy of c] */ + MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); - /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(tmpc, olduse - ix); - } mp_clamp(c); return MP_OKAY; } diff --git a/s_mp_sqr_fast.c b/s_mp_sqr_fast.c index bcb1f5e6b..675d75db5 100644 --- a/s_mp_sqr_fast.c +++ b/s_mp_sqr_fast.c @@ -15,14 +15,14 @@ After that loop you do the squares and add them in. mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) { - int olduse, pa, ix, iz; - mp_digit W[MP_WARRAY], *tmpx; + int oldused, pa, ix; + mp_digit W[MP_WARRAY]; mp_word W1; - mp_err err; /* grow the destination as required */ pa = a->used + a->used; if (b->alloc < pa) { + mp_err err; if ((err = mp_grow(b, pa)) != MP_OKAY) { return err; } @@ -31,9 +31,8 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) /* number of output digits to produce */ W1 = 0; for (ix = 0; ix < pa; ix++) { - int tx, ty, iy; + int tx, ty, iy, iz; mp_word _W; - mp_digit *tmpy; /* clear counter */ _W = 0; @@ -42,10 +41,6 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) ty = MP_MIN(a->used-1, ix); tx = ix - ty; - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = a->dp + ty; - /* this is the number of times the loop will iterrate, essentially while (tx++ < a->used && ty-- >= 0) { ... } */ @@ -59,7 +54,7 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) /* execute loop */ for (iz = 0; iz < iy; iz++) { - _W += (mp_word)*tmpx++ * (mp_word)*tmpy--; + _W += (mp_word)a->dp[tx + iz] * (mp_word)a->dp[ty - iz]; } /* double the inner product and add carry */ @@ -78,19 +73,16 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) } /* setup dest */ - olduse = b->used; + oldused = b->used; b->used = a->used+a->used; - { - mp_digit *tmpb; - tmpb = b->dp; - for (ix = 0; ix < pa; ix++) { - *tmpb++ = W[ix] & MP_MASK; - } - - /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(tmpb, olduse - ix); + for (ix = 0; ix < pa; ix++) { + b->dp[ix] = W[ix] & MP_MASK; } + + /* clear unused digits [that existed in the old copy of c] */ + MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); + mp_clamp(b); return MP_OKAY; } From 448f35e2e179460f29713b23179ebb27d1df9fdd Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:07:29 +0100 Subject: [PATCH 106/304] simplifications: prime functions --- mp_prime_fermat.c | 12 ++---- mp_prime_frobenius_underwood.c | 66 ++++++++++++++++--------------- mp_prime_is_prime.c | 14 +++++-- mp_prime_miller_rabin.c | 28 ++++++------- mp_prime_next_prime.c | 27 ++++++------- mp_prime_strong_lucas_selfridge.c | 2 +- s_mp_get_bit.c | 6 +-- s_mp_prime_is_divisible.c | 18 ++++----- tommath_private.h | 2 +- 9 files changed, 85 insertions(+), 90 deletions(-) diff --git a/mp_prime_fermat.c b/mp_prime_fermat.c index 50d2e5ea1..ac8116fef 100644 --- a/mp_prime_fermat.c +++ b/mp_prime_fermat.c @@ -16,9 +16,6 @@ mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, bool *result) mp_int t; mp_err err; - /* default to composite */ - *result = false; - /* ensure b > 1 */ if (mp_cmp_d(b, 1uL) != MP_GT) { return MP_VAL; @@ -31,16 +28,13 @@ mp_err mp_prime_fermat(const mp_int *a, const mp_int *b, bool *result) /* compute t = b**a mod a */ if ((err = mp_exptmod(b, a, a, &t)) != MP_OKAY) { - goto LBL_T; + goto LBL_ERR; } /* is it equal to b? */ - if (mp_cmp(&t, b) == MP_EQ) { - *result = true; - } + *result = mp_cmp(&t, b) == MP_EQ; - err = MP_OKAY; -LBL_T: +LBL_ERR: mp_clear(&t); return err; } diff --git a/mp_prime_frobenius_underwood.c b/mp_prime_frobenius_underwood.c index 543b8b4a2..62d3476a9 100644 --- a/mp_prime_frobenius_underwood.c +++ b/mp_prime_frobenius_underwood.c @@ -23,17 +23,16 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) { mp_int T1z, T2z, Np1z, sz, tz; - - int a, ap2, length, i, j; + int a, ap2, i; mp_err err; - *result = false; - if ((err = mp_init_multi(&T1z, &T2z, &Np1z, &sz, &tz, NULL)) != MP_OKAY) { return err; } for (a = 0; a < LTM_FROBENIUS_UNDERWOOD_A; a++) { + int j; + /* TODO: That's ugly! No, really, it is! */ if ((a==2) || (a==4) || (a==7) || (a==8) || (a==10) || (a==14) || (a==18) || (a==23) || (a==26) || (a==28)) { @@ -42,7 +41,7 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) mp_set_i32(&T1z, (int32_t)((a * a) - 4)); - if ((err = mp_kronecker(&T1z, N, &j)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_kronecker(&T1z, N, &j)) != MP_OKAY) goto LBL_END; if (j == -1) { break; @@ -50,73 +49,76 @@ mp_err mp_prime_frobenius_underwood(const mp_int *N, bool *result) if (j == 0) { /* composite */ - goto LBL_FU_ERR; + *result = false; + goto LBL_END; } } /* Tell it a composite and set return value accordingly */ if (a >= LTM_FROBENIUS_UNDERWOOD_A) { err = MP_ITER; - goto LBL_FU_ERR; + goto LBL_END; } /* Composite if N and (a+4)*(2*a+5) are not coprime */ mp_set_u32(&T1z, (uint32_t)((a+4)*((2*a)+5))); - if ((err = mp_gcd(N, &T1z, &T1z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_gcd(N, &T1z, &T1z)) != MP_OKAY) goto LBL_END; - if (!((T1z.used == 1) && (T1z.dp[0] == 1u))) goto LBL_FU_ERR; + if (!((T1z.used == 1) && (T1z.dp[0] == 1u))) { + /* composite */ + *result = false; + goto LBL_END; + } ap2 = a + 2; - if ((err = mp_add_d(N, 1uL, &Np1z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_add_d(N, 1uL, &Np1z)) != MP_OKAY) goto LBL_END; mp_set(&sz, 1uL); mp_set(&tz, 2uL); - length = mp_count_bits(&Np1z); - for (i = length - 2; i >= 0; i--) { + for (i = mp_count_bits(&Np1z) - 2; i >= 0; i--) { /* * temp = (sz*(a*sz+2*tz))%N; * tz = ((tz-sz)*(tz+sz))%N; * sz = temp; */ - if ((err = mp_mul_2(&tz, &T2z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_mul_2(&tz, &T2z)) != MP_OKAY) goto LBL_END; /* a = 0 at about 50% of the cases (non-square and odd input) */ if (a != 0) { - if ((err = mp_mul_d(&sz, (mp_digit)a, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_add(&T1z, &T2z, &T2z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_mul_d(&sz, (mp_digit)a, &T1z)) != MP_OKAY) goto LBL_END; + if ((err = mp_add(&T1z, &T2z, &T2z)) != MP_OKAY) goto LBL_END; } - if ((err = mp_mul(&T2z, &sz, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_sub(&tz, &sz, &T2z)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_add(&sz, &tz, &sz)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_mul(&sz, &T2z, &tz)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_mod(&tz, N, &tz)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_mod(&T1z, N, &sz)) != MP_OKAY) goto LBL_FU_ERR; - if (s_mp_get_bit(&Np1z, (unsigned int)i)) { + if ((err = mp_mul(&T2z, &sz, &T1z)) != MP_OKAY) goto LBL_END; + if ((err = mp_sub(&tz, &sz, &T2z)) != MP_OKAY) goto LBL_END; + if ((err = mp_add(&sz, &tz, &sz)) != MP_OKAY) goto LBL_END; + if ((err = mp_mul(&sz, &T2z, &tz)) != MP_OKAY) goto LBL_END; + if ((err = mp_mod(&tz, N, &tz)) != MP_OKAY) goto LBL_END; + if ((err = mp_mod(&T1z, N, &sz)) != MP_OKAY) goto LBL_END; + if (s_mp_get_bit(&Np1z, i)) { /* * temp = (a+2) * sz + tz * tz = 2 * tz - sz * sz = temp */ if (a == 0) { - if ((err = mp_mul_2(&sz, &T1z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_mul_2(&sz, &T1z)) != MP_OKAY) goto LBL_END; } else { - if ((err = mp_mul_d(&sz, (mp_digit)ap2, &T1z)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_mul_d(&sz, (mp_digit)ap2, &T1z)) != MP_OKAY) goto LBL_END; } - if ((err = mp_add(&T1z, &tz, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_mul_2(&tz, &T2z)) != MP_OKAY) goto LBL_FU_ERR; - if ((err = mp_sub(&T2z, &sz, &tz)) != MP_OKAY) goto LBL_FU_ERR; + if ((err = mp_add(&T1z, &tz, &T1z)) != MP_OKAY) goto LBL_END; + if ((err = mp_mul_2(&tz, &T2z)) != MP_OKAY) goto LBL_END; + if ((err = mp_sub(&T2z, &sz, &tz)) != MP_OKAY) goto LBL_END; mp_exch(&sz, &T1z); } } mp_set_u32(&T1z, (uint32_t)((2 * a) + 5)); - if ((err = mp_mod(&T1z, N, &T1z)) != MP_OKAY) goto LBL_FU_ERR; - if (mp_iszero(&sz) && (mp_cmp(&tz, &T1z) == MP_EQ)) { - *result = true; - } + if ((err = mp_mod(&T1z, N, &T1z)) != MP_OKAY) goto LBL_END; + + *result = mp_iszero(&sz) && (mp_cmp(&tz, &T1z) == MP_EQ); -LBL_FU_ERR: +LBL_END: mp_clear_multi(&tz, &sz, &Np1z, &T2z, &T1z, NULL); return err; } diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index d0eca2c28..7d73864c7 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -13,14 +13,12 @@ static unsigned int s_floor_ilog2(int value) return r; } - mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) { mp_int b; - int ix, p_max = 0, size_a, len; - bool res; + int ix; + bool res; mp_err err; - unsigned int fips_rand, mask; /* default to no */ *result = false; @@ -133,6 +131,8 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) TODO: can be made a bit finer grained but comparing is not free. */ if (t < 0) { + int p_max = 0; + /* Sorenson, Jonathan; Webster, Jonathan (2015). "Strong Pseudoprimes to Twelve Prime Bases". @@ -174,6 +174,9 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) See Fips 186.4 p. 126ff */ else if (t > 0) { + unsigned int mask; + int size_a; + /* * The mp_digit's have a defined bit-size but the size of the * array a.dp is a simple 'int' and this library can not assume full @@ -219,6 +222,9 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) need to be prime. */ for (ix = 0; ix < t; ix++) { + unsigned int fips_rand; + int len; + /* mp_rand() guarantees the first digit to be non-zero */ if ((err = mp_rand(&b, 1)) != MP_OKAY) { goto LBL_B; diff --git a/mp_prime_miller_rabin.c b/mp_prime_miller_rabin.c index a3af8bc8b..4c23a9f28 100644 --- a/mp_prime_miller_rabin.c +++ b/mp_prime_miller_rabin.c @@ -16,9 +16,6 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) mp_err err; int s, j; - /* default */ - *result = false; - /* ensure b > 1 */ if (mp_cmp_d(b, 1uL) != MP_GT) { return MP_VAL; @@ -29,12 +26,12 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) return err; } if ((err = mp_sub_d(&n1, 1uL, &n1)) != MP_OKAY) { - goto LBL_N1; + goto LBL_ERR1; } /* set 2**s * r = n1 */ if ((err = mp_init_copy(&r, &n1)) != MP_OKAY) { - goto LBL_N1; + goto LBL_ERR1; } /* count the number of least significant bits @@ -44,15 +41,15 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) /* now divide n - 1 by 2**s */ if ((err = mp_div_2d(&r, s, &r, NULL)) != MP_OKAY) { - goto LBL_R; + goto LBL_ERR2; } /* compute y = b**r mod a */ if ((err = mp_init(&y)) != MP_OKAY) { - goto LBL_R; + goto LBL_ERR2; } if ((err = mp_exptmod(b, &r, a, &y)) != MP_OKAY) { - goto LBL_Y; + goto LBL_END; } /* if y != 1 and y != n1 do */ @@ -61,12 +58,13 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) /* while j <= s-1 and y != n1 */ while ((j <= (s - 1)) && (mp_cmp(&y, &n1) != MP_EQ)) { if ((err = mp_sqrmod(&y, a, &y)) != MP_OKAY) { - goto LBL_Y; + goto LBL_END; } /* if y == 1 then composite */ if (mp_cmp_d(&y, 1uL) == MP_EQ) { - goto LBL_Y; + *result = false; + goto LBL_END; } ++j; @@ -74,17 +72,19 @@ mp_err mp_prime_miller_rabin(const mp_int *a, const mp_int *b, bool *result) /* if y != n1 then composite */ if (mp_cmp(&y, &n1) != MP_EQ) { - goto LBL_Y; + *result = false; + goto LBL_END; } } /* probably prime now */ *result = true; -LBL_Y: + +LBL_END: mp_clear(&y); -LBL_R: +LBL_ERR2: mp_clear(&r); -LBL_N1: +LBL_ERR1: mp_clear(&n1); return err; } diff --git a/mp_prime_next_prime.c b/mp_prime_next_prime.c index 40c94a4cf..6faa08de7 100644 --- a/mp_prime_next_prime.c +++ b/mp_prime_next_prime.c @@ -10,11 +10,10 @@ */ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) { - int x, y; - mp_ord cmp; + int x; mp_err err; bool res = false; - mp_digit res_tab[MP_PRIME_TAB_SIZE], step, kstep; + mp_digit res_tab[MP_PRIME_TAB_SIZE], kstep; mp_int b; /* force positive */ @@ -24,7 +23,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) if (mp_cmp_d(a, s_mp_prime_tab[MP_PRIME_TAB_SIZE-1]) == MP_LT) { /* find which prime it is bigger than "a" */ for (x = 0; x < MP_PRIME_TAB_SIZE; x++) { - cmp = mp_cmp_d(a, s_mp_prime_tab[x]); + mp_ord cmp = mp_cmp_d(a, s_mp_prime_tab[x]); if (cmp == MP_EQ) { continue; } @@ -42,11 +41,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) } /* generate a prime congruent to 3 mod 4 or 1/3 mod 4? */ - if (bbs_style) { - kstep = 4; - } else { - kstep = 2; - } + kstep = bbs_style ? 4 : 2; /* at this point we will use a combination of a sieve and Miller-Rabin */ @@ -79,11 +74,12 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) } for (;;) { + mp_digit step = 0; + bool y; /* skip to the next non-trivially divisible candidate */ - step = 0; do { - /* y == 1 if any residue was zero [e.g. cannot be prime] */ - y = 0; + /* y == true if any residue was zero [e.g. cannot be prime] */ + y = false; /* increase step to next candidate */ step += kstep; @@ -100,10 +96,10 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) /* set flag if zero */ if (res_tab[x] == 0u) { - y = 1; + y = true; } } - } while ((y == 1) && (step < (((mp_digit)1 << MP_DIGIT_BIT) - kstep))); + } while (y && (step < (((mp_digit)1 << MP_DIGIT_BIT) - kstep))); /* add the step */ if ((err = mp_add_d(a, step, a)) != MP_OKAY) { @@ -111,7 +107,7 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) } /* if didn't pass sieve and step == MP_MAX then skip test */ - if ((y == 1) && (step >= (((mp_digit)1 << MP_DIGIT_BIT) - kstep))) { + if (y && (step >= (((mp_digit)1 << MP_DIGIT_BIT) - kstep))) { continue; } @@ -123,7 +119,6 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) } } - err = MP_OKAY; LBL_ERR: mp_clear(&b); return err; diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index df5de9637..6262e0714 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -192,7 +192,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) if ((err = mp_mod(&Qmz, a, &Qmz)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mul_2(&Qmz, &Q2mz)) != MP_OKAY) goto LBL_LS_ERR; - if (s_mp_get_bit(&Dz, (unsigned int)u)) { + if (s_mp_get_bit(&Dz, u)) { /* Formulas for addition of indices (carried out mod N); * * U_(m+n) = (U_m*V_n + U_n*V_m)/2 diff --git a/s_mp_get_bit.c b/s_mp_get_bit.c index f077f613c..a509bcecb 100644 --- a/s_mp_get_bit.c +++ b/s_mp_get_bit.c @@ -5,12 +5,12 @@ /* SPDX-License-Identifier: Unlicense */ /* Get bit at position b and return true if the bit is 1, false if it is 0 */ -bool s_mp_get_bit(const mp_int *a, unsigned int b) +bool s_mp_get_bit(const mp_int *a, int b) { mp_digit bit; - int limb = (int)(b / MP_DIGIT_BIT); + int limb = b / MP_DIGIT_BIT; - if (limb >= a->used) { + if (limb < 0 || limb >= a->used) { return false; } diff --git a/s_mp_prime_is_divisible.c b/s_mp_prime_is_divisible.c index 0cca5a6f1..63b2405ab 100644 --- a/s_mp_prime_is_divisible.c +++ b/s_mp_prime_is_divisible.c @@ -10,16 +10,12 @@ */ mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result) { - int ix; - mp_err err; - mp_digit res; - - /* default to not */ - *result = false; - - for (ix = 0; ix < MP_PRIME_TAB_SIZE; ix++) { - /* what is a mod LBL_prime_tab[ix] */ - if ((err = mp_mod_d(a, s_mp_prime_tab[ix], &res)) != MP_OKAY) { + int i; + for (i = 0; i < MP_PRIME_TAB_SIZE; i++) { + /* what is a mod LBL_prime_tab[i] */ + mp_err err; + mp_digit res; + if ((err = mp_mod_d(a, s_mp_prime_tab[i], &res)) != MP_OKAY) { return err; } @@ -30,6 +26,8 @@ mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result) } } + /* default to not */ + *result = false; return MP_OKAY; } #endif diff --git a/tommath_private.h b/tommath_private.h index f2989d42b..aaa3d2307 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -188,7 +188,7 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); /* lowlevel functions, do not call! */ -MP_PRIVATE bool s_mp_get_bit(const mp_int *a, unsigned int b); +MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b); MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; From 56144eed1ea141e2593ac2257a3b3aa69e455816 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:08:42 +0100 Subject: [PATCH 107/304] simplifications: reduce functions --- mp_dr_reduce.c | 56 ++++++++----------- mp_montgomery_reduce.c | 59 ++++++++------------ mp_reduce_2k.c | 35 ++++++------ mp_reduce_2k_l.c | 33 ++++++----- mp_reduce_2k_setup.c | 14 ++--- s_mp_montgomery_reduce_fast.c | 102 +++++++++++----------------------- 6 files changed, 122 insertions(+), 177 deletions(-) diff --git a/mp_dr_reduce.c b/mp_dr_reduce.c index fba0e2110..d63024649 100644 --- a/mp_dr_reduce.c +++ b/mp_dr_reduce.c @@ -19,16 +19,12 @@ */ mp_err mp_dr_reduce(mp_int *x, const mp_int *n, mp_digit k) { - mp_err err; - int i, m; - mp_word r; - mp_digit mu, *tmpx1, *tmpx2; - /* m = digits in modulus */ - m = n->used; + int m = n->used; /* ensure that "x" has at least 2m digits */ if (x->alloc < (m + m)) { + mp_err err; if ((err = mp_grow(x, m + m)) != MP_OKAY) { return err; } @@ -37,41 +33,37 @@ mp_err mp_dr_reduce(mp_int *x, const mp_int *n, mp_digit k) /* top of loop, this is where the code resumes if * another reduction pass is required. */ -top: - /* aliases for digits */ - /* alias for lower half of x */ - tmpx1 = x->dp; - - /* alias for upper half of x, or x/B**m */ - tmpx2 = x->dp + m; + for (;;) { + mp_err err; + int i; + mp_digit mu = 0; - /* set carry to zero */ - mu = 0; + /* compute (x mod B**m) + k * [x/B**m] inline and inplace */ + for (i = 0; i < m; i++) { + mp_word r = ((mp_word)x->dp[i + m] * (mp_word)k) + x->dp[i] + mu; + x->dp[i] = (mp_digit)(r & MP_MASK); + mu = (mp_digit)(r >> ((mp_word)MP_DIGIT_BIT)); + } - /* compute (x mod B**m) + k * [x/B**m] inline and inplace */ - for (i = 0; i < m; i++) { - r = ((mp_word)*tmpx2++ * (mp_word)k) + *tmpx1 + mu; - *tmpx1++ = (mp_digit)(r & MP_MASK); - mu = (mp_digit)(r >> ((mp_word)MP_DIGIT_BIT)); - } + /* set final carry */ + x->dp[i] = mu; - /* set final carry */ - *tmpx1++ = mu; + /* zero words above m */ + MP_ZERO_DIGITS(x->dp + m + 1, (x->used - m) - 1); - /* zero words above m */ - MP_ZERO_DIGITS(tmpx1, (x->used - m) - 1); + /* clamp, sub and return */ + mp_clamp(x); - /* clamp, sub and return */ - mp_clamp(x); + /* if x >= n then subtract and reduce again + * Each successive "recursion" makes the input smaller and smaller. + */ + if (mp_cmp_mag(x, n) == MP_LT) { + break; + } - /* if x >= n then subtract and reduce again - * Each successive "recursion" makes the input smaller and smaller. - */ - if (mp_cmp_mag(x, n) != MP_LT) { if ((err = s_mp_sub(x, n, x)) != MP_OKAY) { return err; } - goto top; } return MP_OKAY; } diff --git a/mp_montgomery_reduce.c b/mp_montgomery_reduce.c index a872aba6b..6a5be2668 100644 --- a/mp_montgomery_reduce.c +++ b/mp_montgomery_reduce.c @@ -6,9 +6,7 @@ /* computes xR**-1 == x (mod N) via Montgomery Reduction */ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) { - int ix, digs; - mp_err err; - mp_digit mu; + int ix, digs; /* can the fast reduction [comba] method be used? * @@ -25,6 +23,7 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) /* grow the input as required */ if (x->alloc < digs) { + mp_err err; if ((err = mp_grow(x, digs)) != MP_OKAY) { return err; } @@ -32,6 +31,9 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) x->used = digs; for (ix = 0; ix < n->used; ix++) { + int iy; + mp_digit u, mu; + /* mu = ai * rho mod b * * The value of rho must be precalculated via @@ -43,41 +45,28 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) mu = (mp_digit)(((mp_word)x->dp[ix] * (mp_word)rho) & MP_MASK); /* a = a + mu * m * b**i */ - { - int iy; - mp_digit *tmpn, *tmpx, u; - mp_word r; - - /* alias for digits of the modulus */ - tmpn = n->dp; - - /* alias for the digits of x [the input] */ - tmpx = x->dp + ix; - - /* set the carry to zero */ - u = 0; - /* Multiply and add in place */ - for (iy = 0; iy < n->used; iy++) { - /* compute product and sum */ - r = ((mp_word)mu * (mp_word)*tmpn++) + - (mp_word)u + (mp_word)*tmpx; + /* Multiply and add in place */ + u = 0; + for (iy = 0; iy < n->used; iy++) { + /* compute product and sum */ + mp_word r = ((mp_word)mu * (mp_word)n->dp[iy]) + + (mp_word)u + (mp_word)x->dp[ix + iy]; - /* get carry */ - u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); + /* get carry */ + u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); - /* fix digit */ - *tmpx++ = (mp_digit)(r & (mp_word)MP_MASK); - } - /* At this point the ix'th digit of x should be zero */ - - - /* propagate carries upwards as required*/ - while (u != 0u) { - *tmpx += u; - u = *tmpx >> MP_DIGIT_BIT; - *tmpx++ &= MP_MASK; - } + /* fix digit */ + x->dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); + } + /* At this point the ix'th digit of x should be zero */ + + /* propagate carries upwards as required*/ + while (u != 0u) { + x->dp[ix + iy] += u; + u = x->dp[ix + iy] >> MP_DIGIT_BIT; + x->dp[ix + iy] &= MP_MASK; + ++iy; } } diff --git a/mp_reduce_2k.c b/mp_reduce_2k.c index 5d3c7f90c..e635f5b90 100644 --- a/mp_reduce_2k.c +++ b/mp_reduce_2k.c @@ -8,36 +8,37 @@ mp_err mp_reduce_2k(mp_int *a, const mp_int *n, mp_digit d) { mp_int q; mp_err err; - int p; + int p; if ((err = mp_init(&q)) != MP_OKAY) { return err; } p = mp_count_bits(n); -top: - /* q = a/2**p, a = a mod 2**p */ - if ((err = mp_div_2d(a, p, &q, a)) != MP_OKAY) { - goto LBL_ERR; - } - - if (d != 1u) { - /* q = q * d */ - if ((err = mp_mul_d(&q, d, &q)) != MP_OKAY) { + for (;;) { + /* q = a/2**p, a = a mod 2**p */ + if ((err = mp_div_2d(a, p, &q, a)) != MP_OKAY) { goto LBL_ERR; } - } - /* a = a + q */ - if ((err = s_mp_add(a, &q, a)) != MP_OKAY) { - goto LBL_ERR; - } + if (d != 1u) { + /* q = q * d */ + if ((err = mp_mul_d(&q, d, &q)) != MP_OKAY) { + goto LBL_ERR; + } + } - if (mp_cmp_mag(a, n) != MP_LT) { + /* a = a + q */ + if ((err = s_mp_add(a, &q, a)) != MP_OKAY) { + goto LBL_ERR; + } + + if (mp_cmp_mag(a, n) == MP_LT) { + break; + } if ((err = s_mp_sub(a, n, a)) != MP_OKAY) { goto LBL_ERR; } - goto top; } LBL_ERR: diff --git a/mp_reduce_2k_l.c b/mp_reduce_2k_l.c index 6328cbc7d..31d9a1882 100644 --- a/mp_reduce_2k_l.c +++ b/mp_reduce_2k_l.c @@ -18,27 +18,30 @@ mp_err mp_reduce_2k_l(mp_int *a, const mp_int *n, const mp_int *d) } p = mp_count_bits(n); -top: - /* q = a/2**p, a = a mod 2**p */ - if ((err = mp_div_2d(a, p, &q, a)) != MP_OKAY) { - goto LBL_ERR; - } - /* q = q * d */ - if ((err = mp_mul(&q, d, &q)) != MP_OKAY) { - goto LBL_ERR; - } + for (;;) { + /* q = a/2**p, a = a mod 2**p */ + if ((err = mp_div_2d(a, p, &q, a)) != MP_OKAY) { + goto LBL_ERR; + } - /* a = a + q */ - if ((err = s_mp_add(a, &q, a)) != MP_OKAY) { - goto LBL_ERR; - } + /* q = q * d */ + if ((err = mp_mul(&q, d, &q)) != MP_OKAY) { + goto LBL_ERR; + } + + /* a = a + q */ + if ((err = s_mp_add(a, &q, a)) != MP_OKAY) { + goto LBL_ERR; + } - if (mp_cmp_mag(a, n) != MP_LT) { + if (mp_cmp_mag(a, n) == MP_LT) { + break; + } if ((err = s_mp_sub(a, n, a)) != MP_OKAY) { goto LBL_ERR; } - goto top; + } LBL_ERR: diff --git a/mp_reduce_2k_setup.c b/mp_reduce_2k_setup.c index 0f3fd291e..51f884134 100644 --- a/mp_reduce_2k_setup.c +++ b/mp_reduce_2k_setup.c @@ -8,25 +8,23 @@ mp_err mp_reduce_2k_setup(const mp_int *a, mp_digit *d) { mp_err err; mp_int tmp; - int p; if ((err = mp_init(&tmp)) != MP_OKAY) { return err; } - p = mp_count_bits(a); - if ((err = mp_2expt(&tmp, p)) != MP_OKAY) { - mp_clear(&tmp); - return err; + if ((err = mp_2expt(&tmp, mp_count_bits(a))) != MP_OKAY) { + goto LBL_ERR; } if ((err = s_mp_sub(&tmp, a, &tmp)) != MP_OKAY) { - mp_clear(&tmp); - return err; + goto LBL_ERR; } *d = tmp.dp[0]; + +LBL_ERR: mp_clear(&tmp); - return MP_OKAY; + return err; } #endif diff --git a/s_mp_montgomery_reduce_fast.c b/s_mp_montgomery_reduce_fast.c index 083e7a4f4..a78c537ee 100644 --- a/s_mp_montgomery_reduce_fast.c +++ b/s_mp_montgomery_reduce_fast.c @@ -13,7 +13,7 @@ */ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) { - int ix, olduse; + int ix, oldused; mp_err err; mp_word W[MP_WARRAY]; @@ -22,7 +22,7 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) } /* get old used count */ - olduse = x->used; + oldused = x->used; /* grow a as required */ if (x->alloc < (n->used + 1)) { @@ -34,38 +34,30 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) /* first we have to get the digits of the input into * an array of double precision words W[...] */ - { - mp_word *_W; - mp_digit *tmpx; - /* alias for the W[] array */ - _W = W; - - /* alias for the digits of x*/ - tmpx = x->dp; - - /* copy the digits of a into W[0..a->used-1] */ - for (ix = 0; ix < x->used; ix++) { - *_W++ = *tmpx++; - } + /* copy the digits of a into W[0..a->used-1] */ + for (ix = 0; ix < x->used; ix++) { + W[ix] = x->dp[ix]; + } - /* zero the high words of W[a->used..m->used*2] */ - if (ix < ((n->used * 2) + 1)) { - MP_ZERO_BUFFER(_W, sizeof(mp_word) * (size_t)(((n->used * 2) + 1) - ix)); - } + /* zero the high words of W[a->used..m->used*2] */ + if (ix < ((n->used * 2) + 1)) { + MP_ZERO_BUFFER(W + x->used, sizeof(mp_word) * (size_t)(((n->used * 2) + 1) - ix)); } /* now we proceed to zero successive digits * from the least significant upwards */ for (ix = 0; ix < n->used; ix++) { + int iy; + mp_digit mu; + /* mu = ai * m' mod b * * We avoid a double precision multiplication (which isn't required) * by casting the value down to a mp_digit. Note this requires * that W[ix-1] have the carry cleared (see after the inner loop) */ - mp_digit mu; mu = ((W[ix] & MP_MASK) * rho) & MP_MASK; /* a = a + mu * m * b**i @@ -82,21 +74,8 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) * carry fixups are done in order so after these loops the * first m->used words of W[] have the carries fixed */ - { - int iy; - mp_digit *tmpn; - mp_word *_W; - - /* alias for the digits of the modulus */ - tmpn = n->dp; - - /* Alias for the columns set by an offset of ix */ - _W = W + ix; - - /* inner loop */ - for (iy = 0; iy < n->used; iy++) { - *_W++ += (mp_word)mu * (mp_word)*tmpn++; - } + for (iy = 0; iy < n->used; iy++) { + W[ix + iy] += (mp_word)mu * (mp_word)n->dp[iy]; } /* now fix carry for next digit, W[ix+1] */ @@ -107,47 +86,30 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) * shift the words downward [all those least * significant digits we zeroed]. */ - { - mp_digit *tmpx; - mp_word *_W, *_W1; - - /* nox fix rest of carries */ - - /* alias for current word */ - _W1 = W + ix; - - /* alias for next word, where the carry goes */ - _W = W + ++ix; - for (; ix < ((n->used * 2) + 1); ix++) { - *_W++ += *_W1++ >> (mp_word)MP_DIGIT_BIT; - } - - /* copy out, A = A/b**n - * - * The result is A/b**n but instead of converting from an - * array of mp_word to mp_digit than calling mp_rshd - * we just copy them in the right order - */ - - /* alias for destination word */ - tmpx = x->dp; - - /* alias for shifted double precision result */ - _W = W + n->used; + for (; ix < (n->used * 2); ix++) { + W[ix + 1] += W[ix] >> (mp_word)MP_DIGIT_BIT; + } - for (ix = 0; ix < (n->used + 1); ix++) { - *tmpx++ = *_W++ & (mp_word)MP_MASK; - } + /* copy out, A = A/b**n + * + * The result is A/b**n but instead of converting from an + * array of mp_word to mp_digit than calling mp_rshd + * we just copy them in the right order + */ - /* zero oldused digits, if the input a was larger than - * m->used+1 we'll have to clear the digits - */ - MP_ZERO_DIGITS(tmpx, olduse - ix); + for (ix = 0; ix < (n->used + 1); ix++) { + x->dp[ix] = W[n->used + ix] & (mp_word)MP_MASK; } - /* set the max used and clamp */ + /* set the max used */ x->used = n->used + 1; + + /* zero oldused digits, if the input a was larger than + * m->used+1 we'll have to clear the digits + */ + MP_ZERO_DIGITS(x->dp + x->used, oldused - x->used); + mp_clamp(x); /* if A >= m then A = A - m */ From b1f9bff192798c83f6de40f5ca067d4036aa0b3e Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:21:22 +0100 Subject: [PATCH 108/304] simplifications: invmod --- s_mp_invmod_fast.c | 74 +++++++++++++++++++------------------- s_mp_invmod_slow.c | 90 +++++++++++++++++++++++----------------------- 2 files changed, 80 insertions(+), 84 deletions(-) diff --git a/s_mp_invmod_fast.c b/s_mp_invmod_fast.c index ed1fc4a7d..46cf0d664 100644 --- a/s_mp_invmod_fast.c +++ b/s_mp_invmod_fast.c @@ -42,51 +42,49 @@ mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) if ((err = mp_copy(&y, &v)) != MP_OKAY) goto LBL_ERR; mp_set(&D, 1uL); -top: - /* 4. while u is even do */ - while (mp_iseven(&u)) { - /* 4.1 u = u/2 */ - if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; - - /* 4.2 if B is odd then */ - if (mp_isodd(&B)) { - if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; + do { + /* 4. while u is even do */ + while (mp_iseven(&u)) { + /* 4.1 u = u/2 */ + if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; + + /* 4.2 if B is odd then */ + if (mp_isodd(&B)) { + if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; + } + /* B = B/2 */ + if ((err = mp_div_2(&B, &B)) != MP_OKAY) goto LBL_ERR; } - /* B = B/2 */ - if ((err = mp_div_2(&B, &B)) != MP_OKAY) goto LBL_ERR; - } - - /* 5. while v is even do */ - while (mp_iseven(&v)) { - /* 5.1 v = v/2 */ - if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; - /* 5.2 if D is odd then */ - if (mp_isodd(&D)) { - /* D = (D-x)/2 */ - if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; + /* 5. while v is even do */ + while (mp_iseven(&v)) { + /* 5.1 v = v/2 */ + if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; + + /* 5.2 if D is odd then */ + if (mp_isodd(&D)) { + /* D = (D-x)/2 */ + if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; + } + /* D = D/2 */ + if ((err = mp_div_2(&D, &D)) != MP_OKAY) goto LBL_ERR; } - /* D = D/2 */ - if ((err = mp_div_2(&D, &D)) != MP_OKAY) goto LBL_ERR; - } - /* 6. if u >= v then */ - if (mp_cmp(&u, &v) != MP_LT) { - /* u = u - v, B = B - D */ - if ((err = mp_sub(&u, &v, &u)) != MP_OKAY) goto LBL_ERR; + /* 6. if u >= v then */ + if (mp_cmp(&u, &v) != MP_LT) { + /* u = u - v, B = B - D */ + if ((err = mp_sub(&u, &v, &u)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&B, &D, &B)) != MP_OKAY) goto LBL_ERR; - } else { - /* v - v - u, D = D - B */ - if ((err = mp_sub(&v, &u, &v)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&B, &D, &B)) != MP_OKAY) goto LBL_ERR; + } else { + /* v - v - u, D = D - B */ + if ((err = mp_sub(&v, &u, &v)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&D, &B, &D)) != MP_OKAY) goto LBL_ERR; - } + if ((err = mp_sub(&D, &B, &D)) != MP_OKAY) goto LBL_ERR; + } - /* if not zero goto step 4 */ - if (!mp_iszero(&u)) { - goto top; - } + /* if not zero goto step 4 */ + } while (!mp_iszero(&u)); /* now a = C, b = D, gcd == g*v */ diff --git a/s_mp_invmod_slow.c b/s_mp_invmod_slow.c index 28cd6cd88..7d07a141a 100644 --- a/s_mp_invmod_slow.c +++ b/s_mp_invmod_slow.c @@ -36,60 +36,58 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) mp_set(&A, 1uL); mp_set(&D, 1uL); -top: - /* 4. while u is even do */ - while (mp_iseven(&u)) { - /* 4.1 u = u/2 */ - if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; - - /* 4.2 if A or B is odd then */ - if (mp_isodd(&A) || mp_isodd(&B)) { - /* A = (A+y)/2, B = (B-x)/2 */ - if ((err = mp_add(&A, &y, &A)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; + do { + /* 4. while u is even do */ + while (mp_iseven(&u)) { + /* 4.1 u = u/2 */ + if ((err = mp_div_2(&u, &u)) != MP_OKAY) goto LBL_ERR; + + /* 4.2 if A or B is odd then */ + if (mp_isodd(&A) || mp_isodd(&B)) { + /* A = (A+y)/2, B = (B-x)/2 */ + if ((err = mp_add(&A, &y, &A)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&B, &x, &B)) != MP_OKAY) goto LBL_ERR; + } + /* A = A/2, B = B/2 */ + if ((err = mp_div_2(&A, &A)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_div_2(&B, &B)) != MP_OKAY) goto LBL_ERR; } - /* A = A/2, B = B/2 */ - if ((err = mp_div_2(&A, &A)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_div_2(&B, &B)) != MP_OKAY) goto LBL_ERR; - } - - /* 5. while v is even do */ - while (mp_iseven(&v)) { - /* 5.1 v = v/2 */ - if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; - /* 5.2 if C or D is odd then */ - if (mp_isodd(&C) || mp_isodd(&D)) { - /* C = (C+y)/2, D = (D-x)/2 */ - if ((err = mp_add(&C, &y, &C)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; + /* 5. while v is even do */ + while (mp_iseven(&v)) { + /* 5.1 v = v/2 */ + if ((err = mp_div_2(&v, &v)) != MP_OKAY) goto LBL_ERR; + + /* 5.2 if C or D is odd then */ + if (mp_isodd(&C) || mp_isodd(&D)) { + /* C = (C+y)/2, D = (D-x)/2 */ + if ((err = mp_add(&C, &y, &C)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&D, &x, &D)) != MP_OKAY) goto LBL_ERR; + } + /* C = C/2, D = D/2 */ + if ((err = mp_div_2(&C, &C)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_div_2(&D, &D)) != MP_OKAY) goto LBL_ERR; } - /* C = C/2, D = D/2 */ - if ((err = mp_div_2(&C, &C)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_div_2(&D, &D)) != MP_OKAY) goto LBL_ERR; - } - /* 6. if u >= v then */ - if (mp_cmp(&u, &v) != MP_LT) { - /* u = u - v, A = A - C, B = B - D */ - if ((err = mp_sub(&u, &v, &u)) != MP_OKAY) goto LBL_ERR; + /* 6. if u >= v then */ + if (mp_cmp(&u, &v) != MP_LT) { + /* u = u - v, A = A - C, B = B - D */ + if ((err = mp_sub(&u, &v, &u)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&A, &C, &A)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&A, &C, &A)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&B, &D, &B)) != MP_OKAY) goto LBL_ERR; - } else { - /* v - v - u, C = C - A, D = D - B */ - if ((err = mp_sub(&v, &u, &v)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&B, &D, &B)) != MP_OKAY) goto LBL_ERR; + } else { + /* v - v - u, C = C - A, D = D - B */ + if ((err = mp_sub(&v, &u, &v)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&C, &A, &C)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_sub(&C, &A, &C)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_sub(&D, &B, &D)) != MP_OKAY) goto LBL_ERR; - } + if ((err = mp_sub(&D, &B, &D)) != MP_OKAY) goto LBL_ERR; + } - /* if not zero goto step 4 */ - if (!mp_iszero(&u)) { - goto top; - } + /* if not zero goto step 4 */ + } while (!mp_iszero(&u)); /* now a = C, b = D, gcd == g*v */ @@ -111,7 +109,7 @@ mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) /* C is now the inverse */ mp_exch(&C, c); - err = MP_OKAY; + LBL_ERR: mp_clear_multi(&x, &y, &u, &v, &A, &B, &C, &D, NULL); return err; From 795cd2013ff9a03a8b9af778e690e9e1fdbd2192 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 21:48:50 +0100 Subject: [PATCH 109/304] simplifications: add s_mp_zero_(digs|buf) and s_mp_copy_digs Originally I made those as macros. However we have many other small functions like mp_clamp, mp_exch which are also not implemented as macros right now. If we would use c99, I would implement them as private static inline functions. And mp_exch would be a public static inline function. But since we are bound to c89, we simply use normal functions. To achieve optimal performance one should either use link time optimization or amalgamation. --- .travis.yml | 1 + etc/tune.c | 2 +- mp_add_d.c | 2 +- mp_clear.c | 2 +- mp_copy.c | 17 +++--------- mp_div_2.c | 2 +- mp_dr_reduce.c | 2 +- mp_fwrite.c | 2 +- mp_grow.c | 2 +- mp_lshd.c | 2 +- mp_mod_2d.c | 2 +- mp_mul_2.c | 2 +- mp_mul_d.c | 2 +- mp_prime_rand.c | 2 +- mp_rshd.c | 2 +- mp_set.c | 2 +- mp_sub_d.c | 2 +- mp_zero.c | 2 +- s_mp_add.c | 2 +- s_mp_balance_mul.c | 20 +++++++------- s_mp_copy_digs.c | 23 ++++++++++++++++ s_mp_karatsuba_mul.c | 16 ++++------- s_mp_karatsuba_sqr.c | 12 +++------ s_mp_montgomery_reduce_fast.c | 4 +-- s_mp_mul_digs_fast.c | 2 +- s_mp_mul_high_digs_fast.c | 2 +- s_mp_sqr_fast.c | 2 +- s_mp_sub.c | 2 +- s_mp_toom_mul.c | 45 +++++++++++-------------------- s_mp_toom_sqr.c | 22 +++++---------- s_mp_zero_buf.c | 22 +++++++++++++++ s_mp_zero_digs.c | 23 ++++++++++++++++ tommath_private.h | 51 +++++++++-------------------------- 33 files changed, 148 insertions(+), 150 deletions(-) create mode 100644 s_mp_copy_digs.c create mode 100644 s_mp_zero_buf.c create mode 100644 s_mp_zero_digs.c diff --git a/.travis.yml b/.travis.yml index 6c7868968..a269c4ec6 100644 --- a/.travis.yml +++ b/.travis.yml @@ -144,6 +144,7 @@ matrix: # clang for x86-64 architecture (64-bit longs and 64-bit pointers) - env: SANITIZER=1 CONV_WARNINGS=relaxed BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_USE_MEMOPS --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --c89 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind --cflags=-DMP_PREC=MP_MIN_PREC' - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-6.0 --with-m64 --with-travis-valgrind' diff --git a/etc/tune.c b/etc/tune.c index be78ce346..383eb4932 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -292,7 +292,7 @@ int main(int argc, char **argv) s_number_of_test_loops = 64; s_stabilization_extra = 3; - MP_ZERO_BUFFER(&args, sizeof(args)); + s_mp_zero_buf(&args, sizeof(args)); args.testmode = 0; args.verbose = 0; diff --git a/mp_add_d.c b/mp_add_d.c index 43d50e879..9ef44754e 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -80,7 +80,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) c->sign = MP_ZPOS; /* now zero to oldused */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/mp_clear.c b/mp_clear.c index 55d76b298..11094b262 100644 --- a/mp_clear.c +++ b/mp_clear.c @@ -9,7 +9,7 @@ void mp_clear(mp_int *a) /* only do anything if a hasn't been freed previously */ if (a->dp != NULL) { /* free ram */ - MP_FREE_DIGITS(a->dp, a->alloc); + MP_FREE_DIGS(a->dp, a->alloc); /* reset members to make debugging easier */ a->dp = NULL; diff --git a/mp_copy.c b/mp_copy.c index cf4d5e0b4..cf93b0490 100644 --- a/mp_copy.c +++ b/mp_copy.c @@ -6,8 +6,6 @@ /* copy, b = a */ mp_err mp_copy(const mp_int *a, mp_int *b) { - int n; - /* if dst == src do nothing */ if (a == b) { return MP_OKAY; @@ -21,19 +19,12 @@ mp_err mp_copy(const mp_int *a, mp_int *b) } } - /* zero b and copy the parameters over */ - - /* copy all the digits */ - for (n = 0; n < a->used; n++) { - b->dp[n] = a->dp[n]; - } - - /* clear high digits */ - MP_ZERO_DIGITS(b->dp + a->used, b->used - a->used); - - /* copy used count and sign */ + /* copy everything over and zero high digits */ + s_mp_copy_digs(b->dp, a->dp, a->used); + s_mp_zero_digs(b->dp + a->used, b->used - a->used); b->used = a->used; b->sign = a->sign; + return MP_OKAY; } #endif diff --git a/mp_div_2.c b/mp_div_2.c index 573570d9d..b15391e6c 100644 --- a/mp_div_2.c +++ b/mp_div_2.c @@ -33,7 +33,7 @@ mp_err mp_div_2(const mp_int *a, mp_int *b) } /* zero excess digits */ - MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); + s_mp_zero_digs(b->dp + b->used, oldused - b->used); b->sign = a->sign; mp_clamp(b); diff --git a/mp_dr_reduce.c b/mp_dr_reduce.c index d63024649..1b97a1d5b 100644 --- a/mp_dr_reduce.c +++ b/mp_dr_reduce.c @@ -49,7 +49,7 @@ mp_err mp_dr_reduce(mp_int *x, const mp_int *n, mp_digit k) x->dp[i] = mu; /* zero words above m */ - MP_ZERO_DIGITS(x->dp + m + 1, (x->used - m) - 1); + s_mp_zero_digs(x->dp + m + 1, (x->used - m) - 1); /* clamp, sub and return */ mp_clamp(x); diff --git a/mp_fwrite.c b/mp_fwrite.c index 42d728778..6b8ea1332 100644 --- a/mp_fwrite.c +++ b/mp_fwrite.c @@ -25,7 +25,7 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) } } - MP_FREE_BUFFER(buf, size); + MP_FREE_BUF(buf, size); return err; } #endif diff --git a/mp_grow.c b/mp_grow.c index 25be5edd2..0de667984 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -26,7 +26,7 @@ mp_err mp_grow(mp_int *a, int size) a->dp = dp; /* zero excess digits */ - MP_ZERO_DIGITS(a->dp + a->alloc, size - a->alloc); + s_mp_zero_digs(a->dp + a->alloc, size - a->alloc); a->alloc = size; } return MP_OKAY; diff --git a/mp_lshd.c b/mp_lshd.c index 6c1440261..2f56e5db7 100644 --- a/mp_lshd.c +++ b/mp_lshd.c @@ -37,7 +37,7 @@ mp_err mp_lshd(mp_int *a, int b) } /* zero the lower digits */ - MP_ZERO_DIGITS(a->dp, b); + s_mp_zero_digs(a->dp, b); return MP_OKAY; } diff --git a/mp_mod_2d.c b/mp_mod_2d.c index a94a314cd..82c64f05f 100644 --- a/mp_mod_2d.c +++ b/mp_mod_2d.c @@ -29,7 +29,7 @@ mp_err mp_mod_2d(const mp_int *a, int b, mp_int *c) /* zero digits above the last digit of the modulus */ x = (b / MP_DIGIT_BIT) + (((b % MP_DIGIT_BIT) == 0) ? 0 : 1); - MP_ZERO_DIGITS(c->dp + x, c->used - x); + s_mp_zero_digs(c->dp + x, c->used - x); /* clear the digit that is not completely outside/inside the modulus */ c->dp[b / MP_DIGIT_BIT] &= diff --git a/mp_mul_2.c b/mp_mul_2.c index 45b6f1cc5..9e549c974 100644 --- a/mp_mul_2.c +++ b/mp_mul_2.c @@ -47,7 +47,7 @@ mp_err mp_mul_2(const mp_int *a, mp_int *b) /* now zero any excess digits on the destination * that we didn't write to */ - MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); + s_mp_zero_digs(b->dp + b->used, oldused - b->used); b->sign = a->sign; return MP_OKAY; diff --git a/mp_mul_d.c b/mp_mul_d.c index 3e5335f42..2be366f15 100644 --- a/mp_mul_d.c +++ b/mp_mul_d.c @@ -45,7 +45,7 @@ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) c->used = a->used + 1; /* now zero digits above the top */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); diff --git a/mp_prime_rand.c b/mp_prime_rand.c index 8476b4f80..c5cebbda7 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -116,7 +116,7 @@ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) err = MP_OKAY; LBL_ERR: - MP_FREE_BUFFER(tmp, (size_t)bsize); + MP_FREE_BUF(tmp, (size_t)bsize); return err; } diff --git a/mp_rshd.c b/mp_rshd.c index d798907a2..3f0a9416e 100644 --- a/mp_rshd.c +++ b/mp_rshd.c @@ -35,7 +35,7 @@ void mp_rshd(mp_int *a, int b) } /* zero the top digits */ - MP_ZERO_DIGITS(a->dp + a->used - b, b); + s_mp_zero_digs(a->dp + a->used - b, b); /* remove excess digits */ a->used -= b; diff --git a/mp_set.c b/mp_set.c index 3ee5f81f7..bc0c4da76 100644 --- a/mp_set.c +++ b/mp_set.c @@ -10,6 +10,6 @@ void mp_set(mp_int *a, mp_digit b) a->dp[0] = b & MP_MASK; a->sign = MP_ZPOS; a->used = (a->dp[0] != 0u) ? 1 : 0; - MP_ZERO_DIGITS(a->dp + a->used, oldused - a->used); + s_mp_zero_digs(a->dp + a->used, oldused - a->used); } #endif diff --git a/mp_sub_d.c b/mp_sub_d.c index c5cf7266b..91437f8b7 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -72,7 +72,7 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) } /* zero excess digits */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/mp_zero.c b/mp_zero.c index b7dddd2f3..48b60e458 100644 --- a/mp_zero.c +++ b/mp_zero.c @@ -7,7 +7,7 @@ void mp_zero(mp_int *a) { a->sign = MP_ZPOS; - MP_ZERO_DIGITS(a->dp, a->used); + s_mp_zero_digs(a->dp, a->used); a->used = 0; } #endif diff --git a/s_mp_add.c b/s_mp_add.c index 1dd09f8ee..1d799b754 100644 --- a/s_mp_add.c +++ b/s_mp_add.c @@ -64,7 +64,7 @@ mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) c->dp[i] = u; /* clear digits above oldused */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_balance_mul.c b/s_mp_balance_mul.c index 77852a427..167a92868 100644 --- a/s_mp_balance_mul.c +++ b/s_mp_balance_mul.c @@ -8,7 +8,7 @@ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_int a0, tmp, r; mp_err err; - int i, j, count, + int i, j, nblocks = MP_MAX(a->used, b->used) / MP_MIN(a->used, b->used), bsize = MP_MIN(a->used, b->used); @@ -27,12 +27,11 @@ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) for (i = 0, j=0; i < nblocks; i++) { /* Cut a slice off of a */ - a0.used = 0; - for (count = 0; count < bsize; count++) { - a0.dp[count] = a->dp[ j++ ]; - a0.used++; - } + a0.used = bsize; + s_mp_copy_digs(a0.dp, a->dp + j, a0.used); + j += a0.used; mp_clamp(&a0); + /* Multiply with b */ if ((err = mp_mul(&a0, b, &tmp)) != MP_OKAY) { goto LBL_ERR; @@ -48,12 +47,11 @@ mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) } /* The left-overs; there are always left-overs */ if (j < a->used) { - a0.used = 0; - for (count = 0; j < a->used; count++) { - a0.dp[count] = a->dp[ j++ ]; - a0.used++; - } + a0.used = a->used - j; + s_mp_copy_digs(a0.dp, a->dp + j, a0.used); + j += a0.used; mp_clamp(&a0); + if ((err = mp_mul(&a0, b, &tmp)) != MP_OKAY) { goto LBL_ERR; } diff --git a/s_mp_copy_digs.c b/s_mp_copy_digs.c new file mode 100644 index 000000000..4079c33a6 --- /dev/null +++ b/s_mp_copy_digs.c @@ -0,0 +1,23 @@ +#include "tommath_private.h" +#ifdef S_MP_COPY_DIGS_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#ifdef MP_USE_MEMOPS +# include +#endif + +void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits) +{ +#ifdef MP_USE_MEMOPS + if (digits > 0) { + memcpy(d, s, (size_t)digits * sizeof(mp_digit)); + } +#else + while (digits-- > 0) { + *d++ = *s++; + } +#endif +} + +#endif diff --git a/s_mp_karatsuba_mul.c b/s_mp_karatsuba_mul.c index 762e5e21d..6d607ea0f 100644 --- a/s_mp_karatsuba_mul.c +++ b/s_mp_karatsuba_mul.c @@ -35,7 +35,7 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x0, x1, y0, y1, t1, x0y0, x1y1; - int B, i; + int B; mp_err err; /* min # of digits */ @@ -77,16 +77,10 @@ mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) /* we copy the digits directly instead of using higher level functions * since we also need to shift the digits */ - for (i = 0; i < B; i++) { - x0.dp[i] = a->dp[i]; - y0.dp[i] = b->dp[i]; - } - for (i = B; i < a->used; i++) { - x1.dp[i - B] = a->dp[i]; - } - for (i = B; i < b->used; i++) { - y1.dp[i - B] = b->dp[i]; - } + s_mp_copy_digs(x0.dp, a->dp, x0.used); + s_mp_copy_digs(y0.dp, b->dp, y0.used); + s_mp_copy_digs(x1.dp, a->dp + B, x1.used); + s_mp_copy_digs(y1.dp, b->dp + B, y1.used); /* only need to clamp the lower words since by definition the * upper words x1/y1 must have a known number of digits diff --git a/s_mp_karatsuba_sqr.c b/s_mp_karatsuba_sqr.c index 824fcdc22..eb92ccb12 100644 --- a/s_mp_karatsuba_sqr.c +++ b/s_mp_karatsuba_sqr.c @@ -13,7 +13,7 @@ mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) { mp_int x0, x1, t1, t2, x0x0, x1x1; - int B, x; + int B; mp_err err; /* min # of digits */ @@ -39,16 +39,10 @@ mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) goto X0X0; /* now shift the digits */ - for (x = 0; x < B; x++) { - x0.dp[x] = a->dp[x]; - } - for (x = B; x < a->used; x++) { - x1.dp[x - B] = a->dp[x]; - } - x0.used = B; x1.used = a->used - B; - + s_mp_copy_digs(x0.dp, a->dp, x0.used); + s_mp_copy_digs(x1.dp, a->dp + B, x1.used); mp_clamp(&x0); /* now calc the products x0*x0 and x1*x1 */ diff --git a/s_mp_montgomery_reduce_fast.c b/s_mp_montgomery_reduce_fast.c index a78c537ee..9b0811561 100644 --- a/s_mp_montgomery_reduce_fast.c +++ b/s_mp_montgomery_reduce_fast.c @@ -42,7 +42,7 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) /* zero the high words of W[a->used..m->used*2] */ if (ix < ((n->used * 2) + 1)) { - MP_ZERO_BUFFER(W + x->used, sizeof(mp_word) * (size_t)(((n->used * 2) + 1) - ix)); + s_mp_zero_buf(W + x->used, sizeof(mp_word) * (size_t)(((n->used * 2) + 1) - ix)); } /* now we proceed to zero successive digits @@ -108,7 +108,7 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) /* zero oldused digits, if the input a was larger than * m->used+1 we'll have to clear the digits */ - MP_ZERO_DIGITS(x->dp + x->used, oldused - x->used); + s_mp_zero_digs(x->dp + x->used, oldused - x->used); mp_clamp(x); diff --git a/s_mp_mul_digs_fast.c b/s_mp_mul_digs_fast.c index 44aabd087..3928d04d3 100644 --- a/s_mp_mul_digs_fast.c +++ b/s_mp_mul_digs_fast.c @@ -72,7 +72,7 @@ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) } /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_mul_high_digs_fast.c b/s_mp_mul_high_digs_fast.c index 138476599..01335a548 100644 --- a/s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_digs_fast.c @@ -64,7 +64,7 @@ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int } /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_sqr_fast.c b/s_mp_sqr_fast.c index 675d75db5..daf4214ce 100644 --- a/s_mp_sqr_fast.c +++ b/s_mp_sqr_fast.c @@ -81,7 +81,7 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) } /* clear unused digits [that existed in the old copy of c] */ - MP_ZERO_DIGITS(b->dp + b->used, oldused - b->used); + s_mp_zero_digs(b->dp + b->used, oldused - b->used); mp_clamp(b); return MP_OKAY; diff --git a/s_mp_sub.c b/s_mp_sub.c index 05386e5f7..ead0b5118 100644 --- a/s_mp_sub.c +++ b/s_mp_sub.c @@ -49,7 +49,7 @@ mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) } /* clear digits above used (since we may not have grown result above) */ - MP_ZERO_DIGITS(c->dp + c->used, oldused - c->used); + s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); return MP_OKAY; diff --git a/s_mp_toom_mul.c b/s_mp_toom_mul.c index 93113b80c..f3dd96a57 100644 --- a/s_mp_toom_mul.c +++ b/s_mp_toom_mul.c @@ -32,7 +32,7 @@ mp_err s_mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) { mp_int S1, S2, T1, a0, a1, a2, b0, b1, b2; - int B, count; + int B; mp_err err; /* init temps */ @@ -45,43 +45,30 @@ mp_err s_mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) /** a = a2 * x^2 + a1 * x + a0; */ if ((err = mp_init_size(&a0, B)) != MP_OKAY) goto LBL_ERRa0; + if ((err = mp_init_size(&a1, B)) != MP_OKAY) goto LBL_ERRa1; + if ((err = mp_init_size(&a2, a->used - 2 * B)) != MP_OKAY) goto LBL_ERRa2; - for (count = 0; count < B; count++) { - a0.dp[count] = a->dp[count]; - a0.used++; - } + a0.used = a1.used = B; + a2.used = a->used - 2 * B; + s_mp_copy_digs(a0.dp, a->dp, a0.used); + s_mp_copy_digs(a1.dp, a->dp + B, a1.used); + s_mp_copy_digs(a2.dp, a->dp + 2 * B, a2.used); mp_clamp(&a0); - if ((err = mp_init_size(&a1, B)) != MP_OKAY) goto LBL_ERRa1; - for (; count < (2 * B); count++) { - a1.dp[count - B] = a->dp[count]; - a1.used++; - } mp_clamp(&a1); - if ((err = mp_init_size(&a2, B + (a->used - (3 * B)))) != MP_OKAY) goto LBL_ERRa2; - for (; count < a->used; count++) { - a2.dp[count - (2 * B)] = a->dp[count]; - a2.used++; - } mp_clamp(&a2); /** b = b2 * x^2 + b1 * x + b0; */ if ((err = mp_init_size(&b0, B)) != MP_OKAY) goto LBL_ERRb0; - for (count = 0; count < B; count++) { - b0.dp[count] = b->dp[count]; - b0.used++; - } - mp_clamp(&b0); if ((err = mp_init_size(&b1, B)) != MP_OKAY) goto LBL_ERRb1; - for (; count < (2 * B); count++) { - b1.dp[count - B] = b->dp[count]; - b1.used++; - } + if ((err = mp_init_size(&b2, b->used - 2 * B)) != MP_OKAY) goto LBL_ERRb2; + + b0.used = b1.used = B; + b2.used = b->used - 2 * B; + s_mp_copy_digs(b0.dp, b->dp, b0.used); + s_mp_copy_digs(b1.dp, b->dp + B, b1.used); + s_mp_copy_digs(b2.dp, b->dp + 2 * B, b2.used); + mp_clamp(&b0); mp_clamp(&b1); - if ((err = mp_init_size(&b2, B + (b->used - (3 * B)))) != MP_OKAY) goto LBL_ERRb2; - for (; count < b->used; count++) { - b2.dp[count - (2 * B)] = b->dp[count]; - b2.used++; - } mp_clamp(&b2); /** \\ S1 = (a2+a1+a0) * (b2+b1+b0); */ diff --git a/s_mp_toom_sqr.c b/s_mp_toom_sqr.c index d8f2f8e0f..1342d5718 100644 --- a/s_mp_toom_sqr.c +++ b/s_mp_toom_sqr.c @@ -21,7 +21,7 @@ mp_err s_mp_toom_sqr(const mp_int *a, mp_int *b) { mp_int S0, a0, a1, a2; - int B, count; + int B; mp_err err; /* init temps */ @@ -34,22 +34,14 @@ mp_err s_mp_toom_sqr(const mp_int *a, mp_int *b) /** a = a2 * x^2 + a1 * x + a0; */ if ((err = mp_init_size(&a0, B)) != MP_OKAY) goto LBL_ERRa0; - - a0.used = B; if ((err = mp_init_size(&a1, B)) != MP_OKAY) goto LBL_ERRa1; - a1.used = B; - if ((err = mp_init_size(&a2, B + (a->used - (3 * B)))) != MP_OKAY) goto LBL_ERRa2; + if ((err = mp_init_size(&a2, a->used - (2 * B))) != MP_OKAY) goto LBL_ERRa2; - for (count = 0; count < B; count++) { - a0.dp[count] = a->dp[count]; - } - for (; count < (2 * B); count++) { - a1.dp[count - B] = a->dp[count]; - } - for (; count < a->used; count++) { - a2.dp[count - 2 * B] = a->dp[count]; - a2.used++; - } + a0.used = a1.used = B; + a2.used = a->used - 2 * B; + s_mp_copy_digs(a0.dp, a->dp, a0.used); + s_mp_copy_digs(a1.dp, a->dp + B, a1.used); + s_mp_copy_digs(a2.dp, a->dp + 2 * B, a2.used); mp_clamp(&a0); mp_clamp(&a1); mp_clamp(&a2); diff --git a/s_mp_zero_buf.c b/s_mp_zero_buf.c new file mode 100644 index 000000000..23a458dcd --- /dev/null +++ b/s_mp_zero_buf.c @@ -0,0 +1,22 @@ +#include "tommath_private.h" +#ifdef S_MP_ZERO_BUF_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#ifdef MP_USE_MEMOPS +# include +#endif + +void s_mp_zero_buf(void *mem, size_t size) +{ +#ifdef MP_USE_MEMOPS + memset(mem, 0, size); +#else + char *m = (char *)mem; + while (size-- > 0u) { + *m++ = '\0'; + } +#endif +} + +#endif diff --git a/s_mp_zero_digs.c b/s_mp_zero_digs.c new file mode 100644 index 000000000..79e837796 --- /dev/null +++ b/s_mp_zero_digs.c @@ -0,0 +1,23 @@ +#include "tommath_private.h" +#ifdef S_MP_ZERO_DIGS_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#ifdef MP_USE_MEMOPS +# include +#endif + +void s_mp_zero_digs(mp_digit *d, int digits) +{ +#ifdef MP_USE_MEMOPS + if (digits > 0) { + memset(d, 0, (size_t)digits * sizeof(mp_digit)); + } +#else + while (digits-- > 0) { + *d++ = 0; + } +#endif +} + +#endif diff --git a/tommath_private.h b/tommath_private.h index aaa3d2307..7aad433a2 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -42,55 +42,25 @@ * define MP_NO_ZERO_ON_FREE during compilation. */ #ifdef MP_NO_ZERO_ON_FREE -# define MP_FREE_BUFFER(mem, size) MP_FREE((mem), (size)) -# define MP_FREE_DIGITS(mem, digits) MP_FREE((mem), sizeof (mp_digit) * (size_t)(digits)) +# define MP_FREE_BUF(mem, size) MP_FREE((mem), (size)) +# define MP_FREE_DIGS(mem, digits) MP_FREE((mem), sizeof (mp_digit) * (size_t)(digits)) #else -# define MP_FREE_BUFFER(mem, size) \ +# define MP_FREE_BUF(mem, size) \ do { \ size_t fs_ = (size); \ void* fm_ = (mem); \ if (fm_ != NULL) { \ - MP_ZERO_BUFFER(fm_, fs_); \ + s_mp_zero_buf(fm_, fs_); \ MP_FREE(fm_, fs_); \ } \ } while (0) -# define MP_FREE_DIGITS(mem, digits) \ +# define MP_FREE_DIGS(mem, digits) \ do { \ int fd_ = (digits); \ - void* fm_ = (mem); \ + mp_digit* fm_ = (mem); \ if (fm_ != NULL) { \ - size_t fs_ = sizeof (mp_digit) * (size_t)fd_; \ - MP_ZERO_BUFFER(fm_, fs_); \ - MP_FREE(fm_, fs_); \ - } \ -} while (0) -#endif - -#ifdef MP_USE_MEMSET -# include -# define MP_ZERO_BUFFER(mem, size) memset((mem), 0, (size)) -# define MP_ZERO_DIGITS(mem, digits) \ -do { \ - int zd_ = (digits); \ - if (zd_ > 0) { \ - memset((mem), 0, sizeof(mp_digit) * (size_t)zd_); \ - } \ -} while (0) -#else -# define MP_ZERO_BUFFER(mem, size) \ -do { \ - size_t zs_ = (size); \ - char* zm_ = (char*)(mem); \ - while (zs_-- > 0u) { \ - *zm_++ = '\0'; \ - } \ -} while (0) -# define MP_ZERO_DIGITS(mem, digits) \ -do { \ - int zd_ = (digits); \ - mp_digit* zm_ = (mem); \ - while (zd_-- > 0) { \ - *zm_++ = 0; \ + s_mp_zero_digs(fm_, fd_); \ + MP_FREE(fm_, sizeof (mp_digit) * (size_t)fd_); \ } \ } while (0) #endif @@ -215,6 +185,9 @@ MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base); MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r); MP_PRIVATE mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); +MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); +MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); +MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); /* TODO: jenkins prng is not thread safe as of now */ MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; @@ -247,7 +220,7 @@ extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; } \ a->used = i; \ a->sign = MP_ZPOS; \ - MP_ZERO_DIGITS(a->dp + a->used, a->alloc - a->used); \ + s_mp_zero_digs(a->dp + a->used, a->alloc - a->used); \ } #define MP_SET_SIGNED(name, uname, type, utype) \ From bcda8fc69678e9e37cdbf4b4c277e3ed6bb00423 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 22:38:49 +0100 Subject: [PATCH 110/304] simplifications: remove unnecessary optimization * these double checks are not necessary * the compiler will move the early return outside of the called function, basically the functions is partially inlined * however lto/amalgamation needed for the optimization --- mp_abs.c | 9 ++++----- mp_add_d.c | 9 +++------ mp_and.c | 6 ++---- mp_copy.c | 9 ++++----- mp_div_2.c | 8 +++----- mp_dr_reduce.c | 10 ++++------ mp_from_ubin.c | 6 ++---- mp_lshd.c | 8 +++----- mp_montgomery_reduce.c | 8 +++----- mp_mul_2.c | 8 +++----- mp_mul_2d.c | 17 ++++++----------- mp_mul_d.c | 6 ++---- mp_neg.c | 8 +++----- mp_or.c | 6 ++---- mp_sub_d.c | 9 +++------ mp_xor.c | 6 ++---- s_mp_add.c | 8 +++----- s_mp_montgomery_reduce_fast.c | 6 ++---- s_mp_mul_digs_fast.c | 6 ++---- s_mp_mul_high_digs_fast.c | 6 ++---- s_mp_sqr_fast.c | 8 +++----- s_mp_sub.c | 8 +++----- 22 files changed, 64 insertions(+), 111 deletions(-) diff --git a/mp_abs.c b/mp_abs.c index 902279e93..a87cc0cb9 100644 --- a/mp_abs.c +++ b/mp_abs.c @@ -9,12 +9,11 @@ */ mp_err mp_abs(const mp_int *a, mp_int *b) { + mp_err err; + /* copy a to b */ - if (a != b) { - mp_err err; - if ((err = mp_copy(a, b)) != MP_OKAY) { - return err; - } + if ((err = mp_copy(a, b)) != MP_OKAY) { + return err; } /* force the sign of b to positive */ diff --git a/mp_add_d.c b/mp_add_d.c index 9ef44754e..de935bbe2 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -6,6 +6,7 @@ /* single digit addition */ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) { + mp_err err; int oldused; /* fast path for a == c */ @@ -24,16 +25,12 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) } /* grow c as required */ - if (c->alloc < (a->used + 1)) { - mp_err err; - if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { + return err; } /* if a is negative and |a| >= b, call c = |a| - b */ if ((a->sign == MP_NEG) && ((a->used > 1) || (a->dp[0] >= b))) { - mp_err err; mp_int a_ = *a; /* temporarily fix sign of a */ a_.sign = MP_ZPOS; diff --git a/mp_and.c b/mp_and.c index 92e6aed4a..a865ae074 100644 --- a/mp_and.c +++ b/mp_and.c @@ -11,10 +11,8 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) mp_digit ac = 1, bc = 1, cc = 1; mp_sign csign = ((a->sign == MP_NEG) && (b->sign == MP_NEG)) ? MP_NEG : MP_ZPOS; - if (c->alloc < used) { - if ((err = mp_grow(c, used)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, used)) != MP_OKAY) { + return err; } for (i = 0; i < used; i++) { diff --git a/mp_copy.c b/mp_copy.c index cf93b0490..d79e2b8bf 100644 --- a/mp_copy.c +++ b/mp_copy.c @@ -6,17 +6,16 @@ /* copy, b = a */ mp_err mp_copy(const mp_int *a, mp_int *b) { + mp_err err; + /* if dst == src do nothing */ if (a == b) { return MP_OKAY; } /* grow dest */ - if (b->alloc < a->used) { - mp_err err; - if ((err = mp_grow(b, a->used)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(b, a->used)) != MP_OKAY) { + return err; } /* copy everything over and zero high digits */ diff --git a/mp_div_2.c b/mp_div_2.c index b15391e6c..8ab9bcb9c 100644 --- a/mp_div_2.c +++ b/mp_div_2.c @@ -6,14 +6,12 @@ /* b = a/2 */ mp_err mp_div_2(const mp_int *a, mp_int *b) { + mp_err err; int x, oldused; mp_digit r; - if (b->alloc < a->used) { - mp_err err; - if ((err = mp_grow(b, a->used)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(b, a->used)) != MP_OKAY) { + return err; } oldused = b->used; diff --git a/mp_dr_reduce.c b/mp_dr_reduce.c index 1b97a1d5b..f0f6f35e6 100644 --- a/mp_dr_reduce.c +++ b/mp_dr_reduce.c @@ -19,22 +19,20 @@ */ mp_err mp_dr_reduce(mp_int *x, const mp_int *n, mp_digit k) { + mp_err err; + /* m = digits in modulus */ int m = n->used; /* ensure that "x" has at least 2m digits */ - if (x->alloc < (m + m)) { - mp_err err; - if ((err = mp_grow(x, m + m)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(x, m + m)) != MP_OKAY) { + return err; } /* top of loop, this is where the code resumes if * another reduction pass is required. */ for (;;) { - mp_err err; int i; mp_digit mu = 0; diff --git a/mp_from_ubin.c b/mp_from_ubin.c index ae79be3cf..8272185b8 100644 --- a/mp_from_ubin.c +++ b/mp_from_ubin.c @@ -9,10 +9,8 @@ mp_err mp_from_ubin(mp_int *a, const uint8_t *buf, size_t size) mp_err err; /* make sure there are at least two digits */ - if (a->alloc < 2) { - if ((err = mp_grow(a, 2)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(a, 2)) != MP_OKAY) { + return err; } /* zero the int */ diff --git a/mp_lshd.c b/mp_lshd.c index 2f56e5db7..bfa8af88b 100644 --- a/mp_lshd.c +++ b/mp_lshd.c @@ -6,6 +6,7 @@ /* shift left a certain amount of digits */ mp_err mp_lshd(mp_int *a, int b) { + mp_err err; int x; /* if its less than zero return */ @@ -18,11 +19,8 @@ mp_err mp_lshd(mp_int *a, int b) } /* grow to fit the new digits */ - if (a->alloc < (a->used + b)) { - mp_err err; - if ((err = mp_grow(a, a->used + b)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(a, a->used + b)) != MP_OKAY) { + return err; } /* increment the used by the shift amount then copy upwards */ diff --git a/mp_montgomery_reduce.c b/mp_montgomery_reduce.c index 6a5be2668..0a8a1a5e6 100644 --- a/mp_montgomery_reduce.c +++ b/mp_montgomery_reduce.c @@ -6,6 +6,7 @@ /* computes xR**-1 == x (mod N) via Montgomery Reduction */ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) { + mp_err err; int ix, digs; /* can the fast reduction [comba] method be used? @@ -22,11 +23,8 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) } /* grow the input as required */ - if (x->alloc < digs) { - mp_err err; - if ((err = mp_grow(x, digs)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(x, digs)) != MP_OKAY) { + return err; } x->used = digs; diff --git a/mp_mul_2.c b/mp_mul_2.c index 9e549c974..7d7084b31 100644 --- a/mp_mul_2.c +++ b/mp_mul_2.c @@ -6,15 +6,13 @@ /* b = a*2 */ mp_err mp_mul_2(const mp_int *a, mp_int *b) { + mp_err err; int x, oldused; mp_digit r; /* grow to accomodate result */ - if (b->alloc < (a->used + 1)) { - mp_err err; - if ((err = mp_grow(b, a->used + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(b, a->used + 1)) != MP_OKAY) { + return err; } oldused = b->used; diff --git a/mp_mul_2d.c b/mp_mul_2d.c index f1016ead5..e4581375b 100644 --- a/mp_mul_2d.c +++ b/mp_mul_2d.c @@ -6,27 +6,22 @@ /* shift left by a certain bit count */ mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c) { + mp_err err; + if (b < 0) { return MP_VAL; } - if (a != c) { - mp_err err; - if ((err = mp_copy(a, c)) != MP_OKAY) { - return err; - } + if ((err = mp_copy(a, c)) != MP_OKAY) { + return err; } - if (c->alloc < (c->used + (b / MP_DIGIT_BIT) + 1)) { - mp_err err; - if ((err = mp_grow(c, c->used + (b / MP_DIGIT_BIT) + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, c->used + (b / MP_DIGIT_BIT) + 1)) != MP_OKAY) { + return err; } /* shift by as many digits in the bit count */ if (b >= MP_DIGIT_BIT) { - mp_err err; if ((err = mp_lshd(c, b / MP_DIGIT_BIT)) != MP_OKAY) { return err; } diff --git a/mp_mul_d.c b/mp_mul_d.c index 2be366f15..30d6c9340 100644 --- a/mp_mul_d.c +++ b/mp_mul_d.c @@ -11,10 +11,8 @@ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) int ix, oldused; /* make sure c is big enough to hold a*b */ - if (c->alloc < (a->used + 1)) { - if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { + return err; } /* get the original destinations used count */ diff --git a/mp_neg.c b/mp_neg.c index f54ef3edd..bfb6eb98e 100644 --- a/mp_neg.c +++ b/mp_neg.c @@ -6,11 +6,9 @@ /* b = -a */ mp_err mp_neg(const mp_int *a, mp_int *b) { - if (a != b) { - mp_err err; - if ((err = mp_copy(a, b)) != MP_OKAY) { - return err; - } + mp_err err; + if ((err = mp_copy(a, b)) != MP_OKAY) { + return err; } b->sign = mp_iszero(b) || b->sign == MP_NEG ? MP_ZPOS : MP_NEG; diff --git a/mp_or.c b/mp_or.c index 7fa13756e..5cf525509 100644 --- a/mp_or.c +++ b/mp_or.c @@ -11,10 +11,8 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) mp_digit ac = 1, bc = 1, cc = 1; mp_sign csign = ((a->sign == MP_NEG) || (b->sign == MP_NEG)) ? MP_NEG : MP_ZPOS; - if (c->alloc < used) { - if ((err = mp_grow(c, used)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, used)) != MP_OKAY) { + return err; } for (i = 0; i < used; i++) { diff --git a/mp_sub_d.c b/mp_sub_d.c index 91437f8b7..e80df3df8 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -6,6 +6,7 @@ /* single digit subtraction */ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) { + mp_err err; int oldused; /* fast path for a == c */ @@ -23,18 +24,14 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) } /* grow c as required */ - if (c->alloc < (a->used + 1)) { - mp_err err; - if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, a->used + 1)) != MP_OKAY) { + return err; } /* if a is negative just do an unsigned * addition [with fudged signs] */ if (a->sign == MP_NEG) { - mp_err err; mp_int a_ = *a; a_.sign = MP_ZPOS; err = mp_add_d(&a_, b, c); diff --git a/mp_xor.c b/mp_xor.c index ca2c2f1e8..2fe8618fd 100644 --- a/mp_xor.c +++ b/mp_xor.c @@ -11,10 +11,8 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) mp_digit ac = 1, bc = 1, cc = 1; mp_sign csign = (a->sign != b->sign) ? MP_NEG : MP_ZPOS; - if (c->alloc < used) { - if ((err = mp_grow(c, used)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, used)) != MP_OKAY) { + return err; } for (i = 0; i < used; i++) { diff --git a/s_mp_add.c b/s_mp_add.c index 1d799b754..2bda2fe1b 100644 --- a/s_mp_add.c +++ b/s_mp_add.c @@ -8,6 +8,7 @@ mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) { int oldused, min, max, i; mp_digit u; + mp_err err; /* find sizes, we let |a| <= |b| which means we have to sort * them. "x" will point to the input with the most digits @@ -20,11 +21,8 @@ mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) max = a->used; /* init result */ - if (c->alloc < (max + 1)) { - mp_err err; - if ((err = mp_grow(c, max + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, max + 1)) != MP_OKAY) { + return err; } /* get old used digit count and set new one */ diff --git a/s_mp_montgomery_reduce_fast.c b/s_mp_montgomery_reduce_fast.c index 9b0811561..751d7fa4b 100644 --- a/s_mp_montgomery_reduce_fast.c +++ b/s_mp_montgomery_reduce_fast.c @@ -25,10 +25,8 @@ mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) oldused = x->used; /* grow a as required */ - if (x->alloc < (n->used + 1)) { - if ((err = mp_grow(x, n->used + 1)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(x, n->used + 1)) != MP_OKAY) { + return err; } /* first we have to get the digits of the input into diff --git a/s_mp_mul_digs_fast.c b/s_mp_mul_digs_fast.c index 3928d04d3..4f882f15f 100644 --- a/s_mp_mul_digs_fast.c +++ b/s_mp_mul_digs_fast.c @@ -27,10 +27,8 @@ mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) mp_word _W; /* grow the destination as required */ - if (c->alloc < digs) { - if ((err = mp_grow(c, digs)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, digs)) != MP_OKAY) { + return err; } /* number of output digits to produce */ diff --git a/s_mp_mul_high_digs_fast.c b/s_mp_mul_high_digs_fast.c index 01335a548..36bc69adf 100644 --- a/s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_digs_fast.c @@ -21,10 +21,8 @@ mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int /* grow the destination as required */ pa = a->used + b->used; - if (c->alloc < pa) { - if ((err = mp_grow(c, pa)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, pa)) != MP_OKAY) { + return err; } /* number of output digits to produce */ diff --git a/s_mp_sqr_fast.c b/s_mp_sqr_fast.c index daf4214ce..aebc61b35 100644 --- a/s_mp_sqr_fast.c +++ b/s_mp_sqr_fast.c @@ -18,14 +18,12 @@ mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) int oldused, pa, ix; mp_digit W[MP_WARRAY]; mp_word W1; + mp_err err; /* grow the destination as required */ pa = a->used + a->used; - if (b->alloc < pa) { - mp_err err; - if ((err = mp_grow(b, pa)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(b, pa)) != MP_OKAY) { + return err; } /* number of output digits to produce */ diff --git a/s_mp_sub.c b/s_mp_sub.c index ead0b5118..b1a749e35 100644 --- a/s_mp_sub.c +++ b/s_mp_sub.c @@ -8,13 +8,11 @@ mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) { int oldused = c->used, min = b->used, max = a->used, i; mp_digit u; + mp_err err; /* init result */ - if (c->alloc < max) { - mp_err err; - if ((err = mp_grow(c, max)) != MP_OKAY) { - return err; - } + if ((err = mp_grow(c, max)) != MP_OKAY) { + return err; } c->used = max; From 3b710fbd7e4d67e4326670019936805c10caadf3 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Sun, 3 Nov 2019 11:00:33 +0100 Subject: [PATCH 111/304] simplify mp_complement --- mp_complement.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/mp_complement.c b/mp_complement.c index ad6bed344..c16e25f9d 100644 --- a/mp_complement.c +++ b/mp_complement.c @@ -6,7 +6,8 @@ /* b = ~a */ mp_err mp_complement(const mp_int *a, mp_int *b) { - mp_err err = mp_neg(a, b); - return (err == MP_OKAY) ? mp_sub_d(b, 1uL, b) : err; + mp_int a_ = *a; + a_.sign = ((a_.sign == MP_ZPOS) && !mp_iszero(a)) ? MP_NEG : MP_ZPOS; + return mp_sub_d(&a_, 1uL, b); } #endif From 5c335f8407dcc7f065b58540b05422ed0289a2ea Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 30 Oct 2019 17:26:27 +0100 Subject: [PATCH 112/304] rename mul/sqr functions for consistency, comba instead of fast suffix --- demo/mtest_opponent.c | 4 +- demo/test.c | 54 +++++++------- demo/timing.c | 12 ++-- etc/tune.c | 72 +++++++++---------- etc/tune_it.sh | 17 +++-- mp_cutoffs.c | 8 +-- mp_div.c | 2 +- mp_invmod.c | 8 +-- mp_montgomery_reduce.c | 2 +- mp_mul.c | 32 ++++----- mp_reduce.c | 10 +-- mp_sqr.c | 16 ++--- s_mp_div_recursive.c | 4 +- s_mp_exptmod_fast.c | 4 +- s_mp_invmod_slow.c => s_mp_invmod.c | 4 +- s_mp_invmod_fast.c => s_mp_invmod_odd.c | 4 +- ...e_fast.c => s_mp_montgomery_reduce_comba.c | 4 +- s_mp_mul_digs.c => s_mp_mul.c | 6 +- s_mp_balance_mul.c => s_mp_mul_balance.c | 4 +- s_mp_mul_digs_fast.c => s_mp_mul_comba.c | 4 +- s_mp_mul_high_digs.c => s_mp_mul_high.c | 8 +-- ..._high_digs_fast.c => s_mp_mul_high_comba.c | 8 +-- s_mp_karatsuba_mul.c => s_mp_mul_karatsuba.c | 4 +- s_mp_toom_mul.c => s_mp_mul_toom.c | 4 +- s_mp_sqr_fast.c => s_mp_sqr_comba.c | 4 +- s_mp_karatsuba_sqr.c => s_mp_sqr_karatsuba.c | 6 +- s_mp_toom_sqr.c => s_mp_sqr_toom.c | 4 +- tommath.h | 10 +-- tommath_cutoffs.h | 8 +-- tommath_private.h | 34 ++++----- tommath_superclass.h | 24 +++---- 31 files changed, 192 insertions(+), 193 deletions(-) rename s_mp_invmod_slow.c => s_mp_invmod.c (97%) rename s_mp_invmod_fast.c => s_mp_invmod_odd.c (97%) rename s_mp_montgomery_reduce_fast.c => s_mp_montgomery_reduce_comba.c (96%) rename s_mp_mul_digs.c => s_mp_mul.c (91%) rename s_mp_balance_mul.c => s_mp_mul_balance.c (95%) rename s_mp_mul_digs_fast.c => s_mp_mul_comba.c (94%) rename s_mp_mul_high_digs.c => s_mp_mul_high.c (86%) rename s_mp_mul_high_digs_fast.c => s_mp_mul_high_comba.c (86%) rename s_mp_karatsuba_mul.c => s_mp_mul_karatsuba.c (97%) rename s_mp_toom_mul.c => s_mp_mul_toom.c (98%) rename s_mp_sqr_fast.c => s_mp_sqr_comba.c (96%) rename s_mp_karatsuba_sqr.c => s_mp_sqr_karatsuba.c (94%) rename s_mp_toom_sqr.c => s_mp_sqr_toom.c (98%) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 1beab5fce..648a65447 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -37,8 +37,8 @@ static int mtest_opponent(void) #ifndef MP_FIXED_CUTOFFS /* force KARA and TOOM to enable despite cutoffs */ - MP_KARATSUBA_SQR_CUTOFF = MP_KARATSUBA_MUL_CUTOFF = 8; - MP_TOOM_SQR_CUTOFF = MP_TOOM_MUL_CUTOFF = 16; + MP_SQR_KARATSUBA_CUTOFF = MP_MUL_KARATSUBA_CUTOFF = 8; + MP_SQR_TOOM_CUTOFF = MP_MUL_TOOM_CUTOFF = 16; #endif for (;;) { diff --git a/demo/test.c b/demo/test.c index 8e37f712a..3b978730a 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1866,7 +1866,7 @@ static int test_mp_root_u32(void) return EXIT_FAILURE; } -static int test_s_mp_balance_mul(void) +static int test_s_mp_mul_balance(void) { mp_int a, b, c; @@ -1881,7 +1881,7 @@ static int test_s_mp_balance_mul(void) DO(mp_read_radix(&a, na, 64)); DO(mp_read_radix(&b, nb, 64)); - DO(s_mp_balance_mul(&a, &b, &c)); + DO(s_mp_mul_balance(&a, &b, &c)); DO(mp_read_radix(&b, nc, 64)); @@ -1896,18 +1896,18 @@ static int test_s_mp_balance_mul(void) return EXIT_FAILURE; } -#define s_mp_mul(a, b, c) s_mp_mul_digs(a, b, c, (a)->used + (b)->used + 1) -static int test_s_mp_karatsuba_mul(void) +#define s_mp_mul_full(a, b, c) s_mp_mul(a, b, c, (a)->used + (b)->used + 1) +static int test_s_mp_mul_karatsuba(void) { mp_int a, b, c, d; int size; DOR(mp_init_multi(&a, &b, &c, &d, NULL)); - for (size = MP_KARATSUBA_MUL_CUTOFF; size < MP_KARATSUBA_MUL_CUTOFF + 20; size++) { + for (size = MP_MUL_KARATSUBA_CUTOFF; size < MP_MUL_KARATSUBA_CUTOFF + 20; size++) { DO(mp_rand(&a, size)); DO(mp_rand(&b, size)); - DO(s_mp_karatsuba_mul(&a, &b, &c)); - DO(s_mp_mul(&a,&b,&d)); + DO(s_mp_mul_karatsuba(&a, &b, &c)); + DO(s_mp_mul_full(&a,&b,&d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Karatsuba multiplication failed at size %d\n", size); goto LBL_ERR; @@ -1921,15 +1921,15 @@ static int test_s_mp_karatsuba_mul(void) return EXIT_FAILURE; } -static int test_s_mp_karatsuba_sqr(void) +static int test_s_mp_sqr_karatsuba(void) { mp_int a, b, c; int size; DOR(mp_init_multi(&a, &b, &c, NULL)); - for (size = MP_KARATSUBA_SQR_CUTOFF; size < MP_KARATSUBA_SQR_CUTOFF + 20; size++) { + for (size = MP_SQR_KARATSUBA_CUTOFF; size < MP_SQR_KARATSUBA_CUTOFF + 20; size++) { DO(mp_rand(&a, size)); - DO(s_mp_karatsuba_sqr(&a, &b)); + DO(s_mp_sqr_karatsuba(&a, &b)); DO(s_mp_sqr(&a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Karatsuba squaring failed at size %d\n", size); @@ -1944,7 +1944,7 @@ static int test_s_mp_karatsuba_sqr(void) return EXIT_FAILURE; } -static int test_s_mp_toom_mul(void) +static int test_s_mp_mul_toom(void) { mp_int a, b, c, d; int size; @@ -1965,10 +1965,10 @@ static int test_s_mp_toom_mul(void) DO(mp_2expt(&c, 99000 - 1000)); DO(mp_add(&b, &c, &b)); - tc_cutoff = MP_TOOM_MUL_CUTOFF; - MP_TOOM_MUL_CUTOFF = INT_MAX; + tc_cutoff = MP_MUL_TOOM_CUTOFF; + MP_MUL_TOOM_CUTOFF = INT_MAX; DO(mp_mul(&a, &b, &c)); - MP_TOOM_MUL_CUTOFF = tc_cutoff; + MP_MUL_TOOM_CUTOFF = tc_cutoff; DO(mp_mul(&a, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed for edgecase f1 * f2\n"); @@ -1976,11 +1976,11 @@ static int test_s_mp_toom_mul(void) } #endif - for (size = MP_TOOM_MUL_CUTOFF; size < MP_TOOM_MUL_CUTOFF + 20; size++) { + for (size = MP_MUL_TOOM_CUTOFF; size < MP_MUL_TOOM_CUTOFF + 20; size++) { DO(mp_rand(&a, size)); DO(mp_rand(&b, size)); - DO(s_mp_toom_mul(&a, &b, &c)); - DO(s_mp_mul(&a,&b,&d)); + DO(s_mp_mul_toom(&a, &b, &c)); + DO(s_mp_mul_full(&a,&b,&d)); if (mp_cmp(&c, &d) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way multiplication failed at size %d\n", size); goto LBL_ERR; @@ -1994,15 +1994,15 @@ static int test_s_mp_toom_mul(void) return EXIT_FAILURE; } -static int test_s_mp_toom_sqr(void) +static int test_s_mp_sqr_toom(void) { mp_int a, b, c; int size; DOR(mp_init_multi(&a, &b, &c, NULL)); - for (size = MP_TOOM_SQR_CUTOFF; size < MP_TOOM_SQR_CUTOFF + 20; size++) { + for (size = MP_SQR_TOOM_CUTOFF; size < MP_SQR_TOOM_CUTOFF + 20; size++) { DO(mp_rand(&a, size)); - DO(s_mp_toom_sqr(&a, &b)); + DO(s_mp_sqr_toom(&a, &b)); DO(s_mp_sqr(&a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { fprintf(stderr, "Toom-Cook 3-way squaring failed at size %d\n", size); @@ -2075,7 +2075,7 @@ static int test_s_mp_div_recursive(void) DOR(mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)); - for (size = MP_KARATSUBA_MUL_CUTOFF; size < 3 * MP_KARATSUBA_MUL_CUTOFF; size += 10) { + for (size = MP_MUL_KARATSUBA_CUTOFF; size < 3 * MP_MUL_KARATSUBA_CUTOFF; size += 10) { printf("\rsizes = %d / %d", 10 * size, size); /* Relation 10:1 */ DO(mp_rand(&a, 10 * size)); @@ -2139,7 +2139,7 @@ static int test_s_mp_div_small(void) int size; DOR(mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)); - for (size = 1; size < MP_KARATSUBA_MUL_CUTOFF; size += 10) { + for (size = 1; size < MP_MUL_KARATSUBA_CUTOFF; size += 10) { printf("\rsizes = %d / %d", 2 * size, size); /* Relation 10:1 */ DO(mp_rand(&a, 2 * size)); @@ -2332,11 +2332,11 @@ static int unit_tests(int argc, char **argv) T1(mp_xor, MP_XOR), T2(s_mp_div_recursive, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), T2(s_mp_div_small, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), - T1(s_mp_balance_mul, S_MP_BALANCE_MUL), - T1(s_mp_karatsuba_mul, S_MP_KARATSUBA_MUL), - T1(s_mp_karatsuba_sqr, S_MP_KARATSUBA_SQR), - T1(s_mp_toom_mul, S_MP_TOOM_MUL), - T1(s_mp_toom_sqr, S_MP_TOOM_SQR) + T1(s_mp_mul_balance, S_MP_MUL_BALANCE), + T1(s_mp_mul_karatsuba, S_MP_MUL_KARATSUBA), + T1(s_mp_sqr_karatsuba, S_MP_SQR_KARATSUBA), + T1(s_mp_mul_toom, S_MP_MUL_TOOM), + T1(s_mp_sqr_toom, S_MP_SQR_TOOM) #undef T2 #undef T1 }; diff --git a/demo/timing.c b/demo/timing.c index bb2d6c488..4385a080d 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -247,18 +247,18 @@ int main(int argc, char **argv) if (should_test("mulsqr", argc, argv) != 0) { /* do mult/square twice, first without karatsuba and second with */ - old_kara_m = MP_KARATSUBA_MUL_CUTOFF; - old_kara_s = MP_KARATSUBA_SQR_CUTOFF; + old_kara_m = MP_MUL_KARATSUBA_CUTOFF; + old_kara_s = MP_SQR_KARATSUBA_CUTOFF; /* currently toom-cook cut-off is too high to kick in, so we just use the karatsuba values */ old_toom_m = old_kara_m; old_toom_s = old_kara_s; for (ix = 0; ix < 3; ix++) { printf("With%s Karatsuba, With%s Toom\n", (ix == 1) ? "" : "out", (ix == 2) ? "" : "out"); - MP_KARATSUBA_MUL_CUTOFF = (ix == 1) ? old_kara_m : 9999; - MP_KARATSUBA_SQR_CUTOFF = (ix == 1) ? old_kara_s : 9999; - MP_TOOM_MUL_CUTOFF = (ix == 2) ? old_toom_m : 9999; - MP_TOOM_SQR_CUTOFF = (ix == 2) ? old_toom_s : 9999; + MP_MUL_KARATSUBA_CUTOFF = (ix == 1) ? old_kara_m : 9999; + MP_SQR_KARATSUBA_CUTOFF = (ix == 1) ? old_kara_s : 9999; + MP_MUL_TOOM_CUTOFF = (ix == 2) ? old_toom_m : 9999; + MP_SQR_TOOM_CUTOFF = (ix == 2) ? old_toom_s : 9999; log = FOPEN((ix == 0) ? "logs/mult" MP_TIMING_VERSION ".log" : (ix == 1) ? "logs/mult_kara" MP_TIMING_VERSION ".log" : "logs/mult_toom" MP_TIMING_VERSION ".log", "w"); diff --git a/etc/tune.c b/etc/tune.c index 383eb4932..9657910ff 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -58,7 +58,7 @@ static int s_number_of_test_loops; static int s_stabilization_extra; static int s_offset = 1; -#define s_mp_mul(a, b, c) s_mp_mul_digs(a, b, c, (a)->used + (b)->used + 1) +#define s_mp_mul_full(a, b, c) s_mp_mul(a, b, c, (a)->used + (b)->used + 1) static uint64_t s_time_mul(int size) { int x; @@ -87,7 +87,7 @@ static uint64_t s_time_mul(int size) goto LBL_ERR; } if (s_check_result == 1) { - if ((e = s_mp_mul(&a,&b,&d)) != MP_OKAY) { + if ((e = s_mp_mul_full(&a,&b,&d)) != MP_OKAY) { t1 = UINT64_MAX; goto LBL_ERR; } @@ -247,8 +247,8 @@ static void s_usage(char *s) } struct cutoffs { - int KARATSUBA_MUL, KARATSUBA_SQR; - int TOOM_MUL, TOOM_SQR; + int MUL_KARATSUBA, SQR_KARATSUBA; + int MUL_TOOM, SQR_TOOM; }; const struct cutoffs max_cutoffs = @@ -256,18 +256,18 @@ const struct cutoffs max_cutoffs = static void set_cutoffs(const struct cutoffs *c) { - MP_KARATSUBA_MUL_CUTOFF = c->KARATSUBA_MUL; - MP_KARATSUBA_SQR_CUTOFF = c->KARATSUBA_SQR; - MP_TOOM_MUL_CUTOFF = c->TOOM_MUL; - MP_TOOM_SQR_CUTOFF = c->TOOM_SQR; + MP_MUL_KARATSUBA_CUTOFF = c->MUL_KARATSUBA; + MP_SQR_KARATSUBA_CUTOFF = c->SQR_KARATSUBA; + MP_MUL_TOOM_CUTOFF = c->MUL_TOOM; + MP_SQR_TOOM_CUTOFF = c->SQR_TOOM; } static void get_cutoffs(struct cutoffs *c) { - c->KARATSUBA_MUL = MP_KARATSUBA_MUL_CUTOFF; - c->KARATSUBA_SQR = MP_KARATSUBA_SQR_CUTOFF; - c->TOOM_MUL = MP_TOOM_MUL_CUTOFF; - c->TOOM_SQR = MP_TOOM_SQR_CUTOFF; + c->MUL_KARATSUBA = MP_MUL_KARATSUBA_CUTOFF; + c->SQR_KARATSUBA = MP_SQR_KARATSUBA_CUTOFF; + c->MUL_TOOM = MP_MUL_TOOM_CUTOFF; + c->SQR_TOOM = MP_SQR_TOOM_CUTOFF; } @@ -414,13 +414,13 @@ int main(int argc, char **argv) s_usage(argv[0]); } str = argv[opt]; - MP_KARATSUBA_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[1/4] No value for MP_KARATSUBA_MUL_CUTOFF given"); + MP_MUL_KARATSUBA_CUTOFF = (int)s_strtol(str, &endptr, "[1/4] No value for MP_MUL_KARATSUBA_CUTOFF given"); str = endptr + 1; - MP_KARATSUBA_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[2/4] No value for MP_KARATSUBA_SQR_CUTOFF given"); + MP_SQR_KARATSUBA_CUTOFF = (int)s_strtol(str, &endptr, "[2/4] No value for MP_SQR_KARATSUBA_CUTOFF given"); str = endptr + 1; - MP_TOOM_MUL_CUTOFF = (int)s_strtol(str, &endptr, "[3/4] No value for MP_TOOM_MUL_CUTOFF given"); + MP_MUL_TOOM_CUTOFF = (int)s_strtol(str, &endptr, "[3/4] No value for MP_MUL_TOOM_CUTOFF given"); str = endptr + 1; - MP_TOOM_SQR_CUTOFF = (int)s_strtol(str, &endptr, "[4/4] No value for MP_TOOM_SQR_CUTOFF given"); + MP_SQR_TOOM_CUTOFF = (int)s_strtol(str, &endptr, "[4/4] No value for MP_SQR_TOOM_CUTOFF given"); break; case 'h': s_exit_code = EXIT_SUCCESS; @@ -455,10 +455,10 @@ int main(int argc, char **argv) of the macro MP_WPARRAY in tommath.h which needs to be changed manually (to 0 (zero)). */ - T_MUL_SQR("Karatsuba multiplication", KARATSUBA_MUL, s_time_mul), - T_MUL_SQR("Karatsuba squaring", KARATSUBA_SQR, s_time_sqr), - T_MUL_SQR("Toom-Cook 3-way multiplying", TOOM_MUL, s_time_mul), - T_MUL_SQR("Toom-Cook 3-way squaring", TOOM_SQR, s_time_sqr), + T_MUL_SQR("Karatsuba multiplication", MUL_KARATSUBA, s_time_mul), + T_MUL_SQR("Karatsuba squaring", SQR_KARATSUBA, s_time_sqr), + T_MUL_SQR("Toom-Cook 3-way multiplying", MUL_TOOM, s_time_mul), + T_MUL_SQR("Toom-Cook 3-way squaring", SQR_TOOM, s_time_sqr), #undef T_MUL_SQR }; /* Turn all limits from bncore.c to the max */ @@ -473,15 +473,15 @@ int main(int argc, char **argv) } if (args.terse == 1) { printf("%d %d %d %d\n", - updated.KARATSUBA_MUL, - updated.KARATSUBA_SQR, - updated.TOOM_MUL, - updated.TOOM_SQR); + updated.MUL_KARATSUBA, + updated.SQR_KARATSUBA, + updated.MUL_TOOM, + updated.SQR_TOOM); } else { - printf("KARATSUBA_MUL_CUTOFF = %d\n", updated.KARATSUBA_MUL); - printf("KARATSUBA_SQR_CUTOFF = %d\n", updated.KARATSUBA_SQR); - printf("TOOM_MUL_CUTOFF = %d\n", updated.TOOM_MUL); - printf("TOOM_SQR_CUTOFF = %d\n", updated.TOOM_SQR); + printf("MUL_KARATSUBA_CUTOFF = %d\n", updated.MUL_KARATSUBA); + printf("SQR_KARATSUBA_CUTOFF = %d\n", updated.SQR_KARATSUBA); + printf("MUL_TOOM_CUTOFF = %d\n", updated.MUL_TOOM); + printf("SQR_TOOM_CUTOFF = %d\n", updated.SQR_TOOM); } if (args.print == 1) { @@ -526,15 +526,15 @@ int main(int argc, char **argv) set_cutoffs(&orig); if (args.terse == 1) { printf("%d %d %d %d\n", - MP_KARATSUBA_MUL_CUTOFF, - MP_KARATSUBA_SQR_CUTOFF, - MP_TOOM_MUL_CUTOFF, - MP_TOOM_SQR_CUTOFF); + MP_MUL_KARATSUBA_CUTOFF, + MP_SQR_KARATSUBA_CUTOFF, + MP_MUL_TOOM_CUTOFF, + MP_SQR_TOOM_CUTOFF); } else { - printf("KARATSUBA_MUL_CUTOFF = %d\n", MP_KARATSUBA_MUL_CUTOFF); - printf("KARATSUBA_SQR_CUTOFF = %d\n", MP_KARATSUBA_SQR_CUTOFF); - printf("TOOM_MUL_CUTOFF = %d\n", MP_TOOM_MUL_CUTOFF); - printf("TOOM_SQR_CUTOFF = %d\n", MP_TOOM_SQR_CUTOFF); + printf("MUL_KARATSUBA_CUTOFF = %d\n", MP_MUL_KARATSUBA_CUTOFF); + printf("SQR_KARATSUBA_CUTOFF = %d\n", MP_SQR_KARATSUBA_CUTOFF); + printf("MUL_TOOM_CUTOFF = %d\n", MP_MUL_TOOM_CUTOFF); + printf("SQR_TOOM_CUTOFF = %d\n", MP_SQR_TOOM_CUTOFF); } } } diff --git a/etc/tune_it.sh b/etc/tune_it.sh index 5e0fe7c3e..dba5b6968 100755 --- a/etc/tune_it.sh +++ b/etc/tune_it.sh @@ -93,15 +93,14 @@ i=$(tail -n +2 $FILE_NAME | wc -l) # our median point will be at $i entries i=$(( (i / 2) + 1 )) TMP=$(median $FILE_NAME 1 $i) -echo "#define MP_DEFAULT_KARATSUBA_MUL_CUTOFF $TMP" -echo "#define MP_DEFAULT_KARATSUBA_MUL_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(km) Appending to $TOMMATH_CUTOFFS_H" $? +echo "#define MP_DEFAULT_MUL_KARATSUBA_CUTOFF $TMP" +echo "#define MP_DEFAULT_MUL_KARATSUBA_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(km) Appending to $TOMMATH_CUTOFFS_H" $? TMP=$(median $FILE_NAME 2 $i) -echo "#define MP_DEFAULT_KARATSUBA_SQR_CUTOFF $TMP" -echo "#define MP_DEFAULT_KARATSUBA_SQR_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(ks) Appending to $TOMMATH_CUTOFFS_H" $? +echo "#define MP_DEFAULT_SQR_KARATSUBA_CUTOFF $TMP" +echo "#define MP_DEFAULT_SQR_KARATSUBA_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(ks) Appending to $TOMMATH_CUTOFFS_H" $? TMP=$(median $FILE_NAME 3 $i) -echo "#define MP_DEFAULT_TOOM_MUL_CUTOFF $TMP" -echo "#define MP_DEFAULT_TOOM_MUL_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(tc3m) Appending to $TOMMATH_CUTOFFS_H" $? +echo "#define MP_DEFAULT_MUL_TOOM_CUTOFF $TMP" +echo "#define MP_DEFAULT_MUL_TOOM_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(tc3m) Appending to $TOMMATH_CUTOFFS_H" $? TMP=$(median $FILE_NAME 4 $i) -echo "#define MP_DEFAULT_TOOM_SQR_CUTOFF $TMP" -echo "#define MP_DEFAULT_TOOM_SQR_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(tc3s) Appending to $TOMMATH_CUTOFFS_H" $? - +echo "#define MP_DEFAULT_SQR_TOOM_CUTOFF $TMP" +echo "#define MP_DEFAULT_SQR_TOOM_CUTOFF $TMP" >> $TOMMATH_CUTOFFS_H || die "(tc3s) Appending to $TOMMATH_CUTOFFS_H" $? diff --git a/mp_cutoffs.c b/mp_cutoffs.c index 46b04ef51..45b0beec1 100644 --- a/mp_cutoffs.c +++ b/mp_cutoffs.c @@ -5,10 +5,10 @@ #ifndef MP_FIXED_CUTOFFS #include "tommath_cutoffs.h" -int MP_KARATSUBA_MUL_CUTOFF = MP_DEFAULT_KARATSUBA_MUL_CUTOFF, - MP_KARATSUBA_SQR_CUTOFF = MP_DEFAULT_KARATSUBA_SQR_CUTOFF, - MP_TOOM_MUL_CUTOFF = MP_DEFAULT_TOOM_MUL_CUTOFF, - MP_TOOM_SQR_CUTOFF = MP_DEFAULT_TOOM_SQR_CUTOFF; +int MP_MUL_KARATSUBA_CUTOFF = MP_DEFAULT_MUL_KARATSUBA_CUTOFF, + MP_SQR_KARATSUBA_CUTOFF = MP_DEFAULT_SQR_KARATSUBA_CUTOFF, + MP_MUL_TOOM_CUTOFF = MP_DEFAULT_MUL_TOOM_CUTOFF, + MP_SQR_TOOM_CUTOFF = MP_DEFAULT_SQR_TOOM_CUTOFF; #endif #endif diff --git a/mp_div.c b/mp_div.c index 05b96dd51..cbc52e8c4 100644 --- a/mp_div.c +++ b/mp_div.c @@ -26,7 +26,7 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) } if (MP_HAS(S_MP_DIV_RECURSIVE) - && (b->used > MP_KARATSUBA_MUL_CUTOFF) + && (b->used > MP_MUL_KARATSUBA_CUTOFF) && (b->used <= ((a->used/3)*2))) { err = s_mp_div_recursive(a, b, c, d); } else if (MP_HAS(S_MP_DIV_SCHOOL)) { diff --git a/mp_invmod.c b/mp_invmod.c index e43eb3ec2..94929ccbe 100644 --- a/mp_invmod.c +++ b/mp_invmod.c @@ -12,12 +12,12 @@ mp_err mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) } /* if the modulus is odd we can use a faster routine instead */ - if (MP_HAS(S_MP_INVMOD_FAST) && mp_isodd(b)) { - return s_mp_invmod_fast(a, b, c); + if (MP_HAS(S_MP_INVMOD_ODD) && mp_isodd(b)) { + return s_mp_invmod_odd(a, b, c); } - return MP_HAS(S_MP_INVMOD_SLOW) - ? s_mp_invmod_slow(a, b, c) + return MP_HAS(S_MP_INVMOD) + ? s_mp_invmod(a, b, c) : MP_VAL; } #endif diff --git a/mp_montgomery_reduce.c b/mp_montgomery_reduce.c index 0a8a1a5e6..de6a90002 100644 --- a/mp_montgomery_reduce.c +++ b/mp_montgomery_reduce.c @@ -19,7 +19,7 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) if ((digs < MP_WARRAY) && (x->used <= MP_WARRAY) && (n->used < MP_MAXFAST)) { - return s_mp_montgomery_reduce_fast(x, n, rho); + return s_mp_montgomery_reduce_comba(x, n, rho); } /* grow the input as required */ diff --git a/mp_mul.c b/mp_mul.c index 1a7091c23..4103535a1 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -12,26 +12,26 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) digs = a->used + b->used + 1; mp_sign neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - if (MP_HAS(S_MP_BALANCE_MUL) && + if (MP_HAS(S_MP_MUL_BALANCE) && /* Check sizes. The smaller one needs to be larger than the Karatsuba cut-off. - * The bigger one needs to be at least about one MP_KARATSUBA_MUL_CUTOFF bigger + * The bigger one needs to be at least about one MP_MUL_KARATSUBA_CUTOFF bigger * to make some sense, but it depends on architecture, OS, position of the * stars... so YMMV. - * Using it to cut the input into slices small enough for s_mp_mul_digs_fast + * Using it to cut the input into slices small enough for s_mp_mul_comba * was actually slower on the author's machine, but YMMV. */ - (min >= MP_KARATSUBA_MUL_CUTOFF) && - ((max / 2) >= MP_KARATSUBA_MUL_CUTOFF) && + (min >= MP_MUL_KARATSUBA_CUTOFF) && + ((max / 2) >= MP_MUL_KARATSUBA_CUTOFF) && /* Not much effect was observed below a ratio of 1:2, but again: YMMV. */ (max >= (2 * min))) { - err = s_mp_balance_mul(a,b,c); - } else if (MP_HAS(S_MP_TOOM_MUL) && - (min >= MP_TOOM_MUL_CUTOFF)) { - err = s_mp_toom_mul(a, b, c); - } else if (MP_HAS(S_MP_KARATSUBA_MUL) && - (min >= MP_KARATSUBA_MUL_CUTOFF)) { - err = s_mp_karatsuba_mul(a, b, c); - } else if (MP_HAS(S_MP_MUL_DIGS_FAST) && + err = s_mp_mul_balance(a,b,c); + } else if (MP_HAS(S_MP_MUL_TOOM) && + (min >= MP_MUL_TOOM_CUTOFF)) { + err = s_mp_mul_toom(a, b, c); + } else if (MP_HAS(S_MP_MUL_KARATSUBA) && + (min >= MP_MUL_KARATSUBA_CUTOFF)) { + err = s_mp_mul_karatsuba(a, b, c); + } else if (MP_HAS(S_MP_MUL_COMBA) && /* can we use the fast multiplier? * * The fast multiplier can be used if the output will @@ -40,9 +40,9 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) */ (digs < MP_WARRAY) && (min <= MP_MAXFAST)) { - err = s_mp_mul_digs_fast(a, b, c, digs); - } else if (MP_HAS(S_MP_MUL_DIGS)) { - err = s_mp_mul_digs(a, b, c, digs); + err = s_mp_mul_comba(a, b, c, digs); + } else if (MP_HAS(S_MP_MUL)) { + err = s_mp_mul(a, b, c, digs); } else { err = MP_VAL; } diff --git a/mp_reduce.c b/mp_reduce.c index 5226fe7d4..b6fae55cc 100644 --- a/mp_reduce.c +++ b/mp_reduce.c @@ -26,12 +26,12 @@ mp_err mp_reduce(mp_int *x, const mp_int *m, const mp_int *mu) if ((err = mp_mul(&q, mu, &q)) != MP_OKAY) { goto LBL_ERR; } - } else if (MP_HAS(S_MP_MUL_HIGH_DIGS)) { - if ((err = s_mp_mul_high_digs(&q, mu, &q, um)) != MP_OKAY) { + } else if (MP_HAS(S_MP_MUL_HIGH)) { + if ((err = s_mp_mul_high(&q, mu, &q, um)) != MP_OKAY) { goto LBL_ERR; } - } else if (MP_HAS(S_MP_MUL_HIGH_DIGS_FAST)) { - if ((err = s_mp_mul_high_digs_fast(&q, mu, &q, um)) != MP_OKAY) { + } else if (MP_HAS(S_MP_MUL_HIGH_COMBA)) { + if ((err = s_mp_mul_high_comba(&q, mu, &q, um)) != MP_OKAY) { goto LBL_ERR; } } else { @@ -48,7 +48,7 @@ mp_err mp_reduce(mp_int *x, const mp_int *m, const mp_int *mu) } /* q = q * m mod b**(k+1), quick (no division) */ - if ((err = s_mp_mul_digs(&q, m, &q, um + 1)) != MP_OKAY) { + if ((err = s_mp_mul(&q, m, &q, um + 1)) != MP_OKAY) { goto LBL_ERR; } diff --git a/mp_sqr.c b/mp_sqr.c index e38130b64..b0da0edeb 100644 --- a/mp_sqr.c +++ b/mp_sqr.c @@ -7,16 +7,16 @@ mp_err mp_sqr(const mp_int *a, mp_int *b) { mp_err err; - if (MP_HAS(S_MP_TOOM_SQR) && /* use Toom-Cook? */ - (a->used >= MP_TOOM_SQR_CUTOFF)) { - err = s_mp_toom_sqr(a, b); - } else if (MP_HAS(S_MP_KARATSUBA_SQR) && /* Karatsuba? */ - (a->used >= MP_KARATSUBA_SQR_CUTOFF)) { - err = s_mp_karatsuba_sqr(a, b); - } else if (MP_HAS(S_MP_SQR_FAST) && /* can we use the fast comba multiplier? */ + if (MP_HAS(S_MP_SQR_TOOM) && /* use Toom-Cook? */ + (a->used >= MP_SQR_TOOM_CUTOFF)) { + err = s_mp_sqr_toom(a, b); + } else if (MP_HAS(S_MP_SQR_KARATSUBA) && /* Karatsuba? */ + (a->used >= MP_SQR_KARATSUBA_CUTOFF)) { + err = s_mp_sqr_karatsuba(a, b); + } else if (MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ (((a->used * 2) + 1) < MP_WARRAY) && (a->used < (MP_MAXFAST / 2))) { - err = s_mp_sqr_fast(a, b); + err = s_mp_sqr_comba(a, b); } else if (MP_HAS(S_MP_SQR)) { err = s_mp_sqr(a, b); } else { diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index 7007aef06..2fbc31210 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -20,7 +20,7 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int mp_int A1, A2, B1, B0, Q1, Q0, R1, R0, t; int m = a->used - b->used, k = m/2; - if (m < MP_KARATSUBA_MUL_CUTOFF) { + if (m < MP_MUL_KARATSUBA_CUTOFF) { return s_mp_div_school(a, b, q, r); } @@ -104,7 +104,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r Vid. section 2.3. */ - m = MP_KARATSUBA_MUL_CUTOFF; + m = MP_MUL_KARATSUBA_CUTOFF; while (m <= b->used) { m <<= 1; } diff --git a/s_mp_exptmod_fast.c b/s_mp_exptmod_fast.c index d58112968..813eef2c3 100644 --- a/s_mp_exptmod_fast.c +++ b/s_mp_exptmod_fast.c @@ -80,10 +80,10 @@ mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_i } /* automatically pick the comba one if available (saves quite a few calls/ifs) */ - if (MP_HAS(S_MP_MONTGOMERY_REDUCE_FAST) && + if (MP_HAS(S_MP_MONTGOMERY_REDUCE_COMBA) && (((P->used * 2) + 1) < MP_WARRAY) && (P->used < MP_MAXFAST)) { - redux = s_mp_montgomery_reduce_fast; + redux = s_mp_montgomery_reduce_comba; } else if (MP_HAS(MP_MONTGOMERY_REDUCE)) { /* use slower baseline Montgomery method */ redux = mp_montgomery_reduce; diff --git a/s_mp_invmod_slow.c b/s_mp_invmod.c similarity index 97% rename from s_mp_invmod_slow.c rename to s_mp_invmod.c index 7d07a141a..f3b3f436f 100644 --- a/s_mp_invmod_slow.c +++ b/s_mp_invmod.c @@ -1,10 +1,10 @@ #include "tommath_private.h" -#ifdef S_MP_INVMOD_SLOW_C +#ifdef S_MP_INVMOD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* hac 14.61, pp608 */ -mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) +mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x, y, u, v, A, B, C, D; mp_err err; diff --git a/s_mp_invmod_fast.c b/s_mp_invmod_odd.c similarity index 97% rename from s_mp_invmod_fast.c rename to s_mp_invmod_odd.c index 46cf0d664..8b55d5b7d 100644 --- a/s_mp_invmod_fast.c +++ b/s_mp_invmod_odd.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_INVMOD_FAST_C +#ifdef S_MP_INVMOD_ODD_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -9,7 +9,7 @@ * Based on slow invmod except this is optimized for the case where b is * odd as per HAC Note 14.64 on pp. 610 */ -mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) +mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x, y, u, v, B, D; mp_sign neg; diff --git a/s_mp_montgomery_reduce_fast.c b/s_mp_montgomery_reduce_comba.c similarity index 96% rename from s_mp_montgomery_reduce_fast.c rename to s_mp_montgomery_reduce_comba.c index 751d7fa4b..6f249c49f 100644 --- a/s_mp_montgomery_reduce_fast.c +++ b/s_mp_montgomery_reduce_comba.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_MONTGOMERY_REDUCE_FAST_C +#ifdef S_MP_MONTGOMERY_REDUCE_COMBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -11,7 +11,7 @@ * * Based on Algorithm 14.32 on pp.601 of HAC. */ -mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) +mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) { int ix, oldused; mp_err err; diff --git a/s_mp_mul_digs.c b/s_mp_mul.c similarity index 91% rename from s_mp_mul_digs.c rename to s_mp_mul.c index 27e51f834..cd17b99ac 100644 --- a/s_mp_mul_digs.c +++ b/s_mp_mul.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_MUL_DIGS_C +#ifdef S_MP_MUL_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -7,7 +7,7 @@ * HAC pp. 595, Algorithm 14.12 Modified so you can control how * many digits of output are created. */ -mp_err s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) +mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) { mp_int t; mp_err err; @@ -16,7 +16,7 @@ mp_err s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* can we use the fast multiplier? */ if ((digs < MP_WARRAY) && (MP_MIN(a->used, b->used) < MP_MAXFAST)) { - return s_mp_mul_digs_fast(a, b, c, digs); + return s_mp_mul_comba(a, b, c, digs); } if ((err = mp_init_size(&t, digs)) != MP_OKAY) { diff --git a/s_mp_balance_mul.c b/s_mp_mul_balance.c similarity index 95% rename from s_mp_balance_mul.c rename to s_mp_mul_balance.c index 167a92868..f36f0d30b 100644 --- a/s_mp_balance_mul.c +++ b/s_mp_mul_balance.c @@ -1,10 +1,10 @@ #include "tommath_private.h" -#ifdef S_MP_BALANCE_MUL_C +#ifdef S_MP_MUL_BALANCE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* single-digit multiplication with the smaller number as the single-digit */ -mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) +mp_err s_mp_mul_balance(const mp_int *a, const mp_int *b, mp_int *c) { mp_int a0, tmp, r; mp_err err; diff --git a/s_mp_mul_digs_fast.c b/s_mp_mul_comba.c similarity index 94% rename from s_mp_mul_digs_fast.c rename to s_mp_mul_comba.c index 4f882f15f..07dd7913d 100644 --- a/s_mp_mul_digs_fast.c +++ b/s_mp_mul_comba.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_MUL_DIGS_FAST_C +#ifdef S_MP_MUL_COMBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -19,7 +19,7 @@ * Based on Algorithm 14.12 on pp.595 of HAC. * */ -mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) +mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) { int oldused, pa, ix; mp_err err; diff --git a/s_mp_mul_high_digs.c b/s_mp_mul_high.c similarity index 86% rename from s_mp_mul_high_digs.c rename to s_mp_mul_high.c index 5a8c0731b..d1d180641 100644 --- a/s_mp_mul_high_digs.c +++ b/s_mp_mul_high.c @@ -1,22 +1,22 @@ #include "tommath_private.h" -#ifdef S_MP_MUL_HIGH_DIGS_C +#ifdef S_MP_MUL_HIGH_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* multiplies |a| * |b| and does not compute the lower digs digits * [meant to get the higher part of the product] */ -mp_err s_mp_mul_high_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) +mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) { mp_int t; int pa, pb, ix; mp_err err; /* can we use the fast multiplier? */ - if (MP_HAS(S_MP_MUL_HIGH_DIGS_FAST) + if (MP_HAS(S_MP_MUL_HIGH_COMBA) && ((a->used + b->used + 1) < MP_WARRAY) && (MP_MIN(a->used, b->used) < MP_MAXFAST)) { - return s_mp_mul_high_digs_fast(a, b, c, digs); + return s_mp_mul_high_comba(a, b, c, digs); } if ((err = mp_init_size(&t, a->used + b->used + 1)) != MP_OKAY) { diff --git a/s_mp_mul_high_digs_fast.c b/s_mp_mul_high_comba.c similarity index 86% rename from s_mp_mul_high_digs_fast.c rename to s_mp_mul_high_comba.c index 36bc69adf..317346dfa 100644 --- a/s_mp_mul_high_digs_fast.c +++ b/s_mp_mul_high_comba.c @@ -1,10 +1,10 @@ #include "tommath_private.h" -#ifdef S_MP_MUL_HIGH_DIGS_FAST_C +#ifdef S_MP_MUL_HIGH_COMBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* this is a modified version of s_mp_mul_digs_fast that only produces - * output digits *above* digs. See the comments for s_mp_mul_digs_fast +/* this is a modified version of s_mp_mul_comba that only produces + * output digits *above* digs. See the comments for s_mp_mul_comba * to see how it works. * * This is used in the Barrett reduction since for one of the multiplications @@ -12,7 +12,7 @@ * * Based on Algorithm 14.12 on pp.595 of HAC. */ -mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) +mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) { int oldused, pa, ix; mp_err err; diff --git a/s_mp_karatsuba_mul.c b/s_mp_mul_karatsuba.c similarity index 97% rename from s_mp_karatsuba_mul.c rename to s_mp_mul_karatsuba.c index 6d607ea0f..bf9271f3b 100644 --- a/s_mp_karatsuba_mul.c +++ b/s_mp_mul_karatsuba.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_KARATSUBA_MUL_C +#ifdef S_MP_MUL_KARATSUBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -32,7 +32,7 @@ * Generally though the overhead of this method doesn't pay off * until a certain size (N ~ 80) is reached. */ -mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) +mp_err s_mp_mul_karatsuba(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x0, x1, y0, y1, t1, x0y0, x1y1; int B; diff --git a/s_mp_toom_mul.c b/s_mp_mul_toom.c similarity index 98% rename from s_mp_toom_mul.c rename to s_mp_mul_toom.c index f3dd96a57..1ed03c83a 100644 --- a/s_mp_toom_mul.c +++ b/s_mp_mul_toom.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_TOOM_MUL_C +#ifdef S_MP_MUL_TOOM_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -29,7 +29,7 @@ Centro Vito Volterra Universita di Roma Tor Vergata (2006) */ -mp_err s_mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) +mp_err s_mp_mul_toom(const mp_int *a, const mp_int *b, mp_int *c) { mp_int S1, S2, T1, a0, a1, a2, b0, b1, b2; int B; diff --git a/s_mp_sqr_fast.c b/s_mp_sqr_comba.c similarity index 96% rename from s_mp_sqr_fast.c rename to s_mp_sqr_comba.c index aebc61b35..cb88dcc9e 100644 --- a/s_mp_sqr_fast.c +++ b/s_mp_sqr_comba.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_SQR_FAST_C +#ifdef S_MP_SQR_COMBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -13,7 +13,7 @@ After that loop you do the squares and add them in. */ -mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) +mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) { int oldused, pa, ix; mp_digit W[MP_WARRAY]; diff --git a/s_mp_karatsuba_sqr.c b/s_mp_sqr_karatsuba.c similarity index 94% rename from s_mp_karatsuba_sqr.c rename to s_mp_sqr_karatsuba.c index eb92ccb12..f064b46a1 100644 --- a/s_mp_karatsuba_sqr.c +++ b/s_mp_sqr_karatsuba.c @@ -1,16 +1,16 @@ #include "tommath_private.h" -#ifdef S_MP_KARATSUBA_SQR_C +#ifdef S_MP_SQR_KARATSUBA_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* Karatsuba squaring, computes b = a*a using three * half size squarings * - * See comments of karatsuba_mul for details. It + * See comments of mul_karatsuba for details. It * is essentially the same algorithm but merely * tuned to perform recursive squarings. */ -mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) +mp_err s_mp_sqr_karatsuba(const mp_int *a, mp_int *b) { mp_int x0, x1, t1, t2, x0x0, x1x1; int B; diff --git a/s_mp_toom_sqr.c b/s_mp_sqr_toom.c similarity index 98% rename from s_mp_toom_sqr.c rename to s_mp_sqr_toom.c index 1342d5718..fd70a3dac 100644 --- a/s_mp_toom_sqr.c +++ b/s_mp_sqr_toom.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef S_MP_TOOM_SQR_C +#ifdef S_MP_SQR_TOOM_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -18,7 +18,7 @@ 18th IEEE Symposium on Computer Arithmetic (ARITH'07). IEEE, 2007. */ -mp_err s_mp_toom_sqr(const mp_int *a, mp_int *b) +mp_err s_mp_sqr_toom(const mp_int *a, mp_int *b) { mp_int S0, a0, a1, a2; int B; diff --git a/tommath.h b/tommath.h index 823154a48..d024a33fe 100644 --- a/tommath.h +++ b/tommath.h @@ -63,7 +63,7 @@ typedef uint32_t mp_digit; # ifdef MP_31BIT /* * This is an extension that uses 31-bit digits. - * Please be aware that not all functions support this size, especially s_mp_mul_digs_fast + * Please be aware that not all functions support this size, especially s_mp_mul_comba * will be reduced to work on small numbers only: * Up to 8 limbs, 248 bits instead of up to 512 limbs, 15872 bits with MP_28BIT. */ @@ -117,10 +117,10 @@ typedef enum { /* tunable cutoffs */ #ifndef MP_FIXED_CUTOFFS extern int -MP_KARATSUBA_MUL_CUTOFF, -MP_KARATSUBA_SQR_CUTOFF, -MP_TOOM_MUL_CUTOFF, -MP_TOOM_SQR_CUTOFF; +MP_MUL_KARATSUBA_CUTOFF, +MP_SQR_KARATSUBA_CUTOFF, +MP_MUL_TOOM_CUTOFF, +MP_SQR_TOOM_CUTOFF; #endif /* define this to use lower memory usage routines (exptmods mostly) */ diff --git a/tommath_cutoffs.h b/tommath_cutoffs.h index a65a9b3e3..fb8416013 100644 --- a/tommath_cutoffs.h +++ b/tommath_cutoffs.h @@ -7,7 +7,7 @@ on the aforementioned machine for example. */ -#define MP_DEFAULT_KARATSUBA_MUL_CUTOFF 80 -#define MP_DEFAULT_KARATSUBA_SQR_CUTOFF 120 -#define MP_DEFAULT_TOOM_MUL_CUTOFF 350 -#define MP_DEFAULT_TOOM_SQR_CUTOFF 400 +#define MP_DEFAULT_MUL_KARATSUBA_CUTOFF 80 +#define MP_DEFAULT_SQR_KARATSUBA_CUTOFF 120 +#define MP_DEFAULT_MUL_TOOM_CUTOFF 350 +#define MP_DEFAULT_SQR_TOOM_CUTOFF 400 diff --git a/tommath_private.h b/tommath_private.h index 7aad433a2..096979634 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -82,10 +82,10 @@ do { \ #ifdef MP_FIXED_CUTOFFS # include "tommath_cutoffs.h" -# define MP_KARATSUBA_MUL_CUTOFF MP_DEFAULT_KARATSUBA_MUL_CUTOFF -# define MP_KARATSUBA_SQR_CUTOFF MP_DEFAULT_KARATSUBA_SQR_CUTOFF -# define MP_TOOM_MUL_CUTOFF MP_DEFAULT_TOOM_MUL_CUTOFF -# define MP_TOOM_SQR_CUTOFF MP_DEFAULT_TOOM_SQR_CUTOFF +# define MP_MUL_KARATSUBA_CUTOFF MP_DEFAULT_MUL_KARATSUBA_CUTOFF +# define MP_SQR_KARATSUBA_CUTOFF MP_DEFAULT_SQR_KARATSUBA_CUTOFF +# define MP_MUL_TOOM_CUTOFF MP_DEFAULT_MUL_TOOM_CUTOFF +# define MP_SQR_TOOM_CUTOFF MP_DEFAULT_SQR_TOOM_CUTOFF #endif /* define heap macros */ @@ -161,20 +161,20 @@ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b); MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_high_digs_fast(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_high_digs(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_sqr_fast(const mp_int *a, mp_int *b) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sqr(const mp_int *a, mp_int *b) MP_WUR; -MP_PRIVATE mp_err s_mp_balance_mul(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_karatsuba_mul(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_toom_mul(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_karatsuba_sqr(const mp_int *a, mp_int *b) MP_WUR; -MP_PRIVATE mp_err s_mp_toom_sqr(const mp_int *a, mp_int *b) MP_WUR; -MP_PRIVATE mp_err s_mp_invmod_fast(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_invmod_slow(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_montgomery_reduce_fast(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_balance(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_karatsuba(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_toom(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_sqr_karatsuba(const mp_int *a, mp_int *b) MP_WUR; +MP_PRIVATE mp_err s_mp_sqr_toom(const mp_int *a, mp_int *b) MP_WUR; +MP_PRIVATE mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; diff --git a/tommath_superclass.h b/tommath_superclass.h index 6961a5968..db927d6cc 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -76,23 +76,23 @@ * like removing support for even moduli, etc... */ # ifdef LTM_LAST +# undef MP_DIV_3_C # undef MP_DR_IS_MODULUS_C -# undef MP_DR_SETUP_C # undef MP_DR_REDUCE_C -# undef MP_DIV_3_C -# undef MP_REDUCE_2K_SETUP_C +# undef MP_DR_SETUP_C # undef MP_REDUCE_2K_C +# undef MP_REDUCE_2K_SETUP_C # undef MP_REDUCE_IS_2K_C # undef MP_REDUCE_SETUP_C -# undef S_MP_BALANCE_MUL_C # undef S_MP_EXPTMOD_C -# undef S_MP_INVMOD_FAST_C -# undef S_MP_KARATSUBA_MUL_C -# undef S_MP_KARATSUBA_SQR_C -# undef S_MP_MUL_HIGH_DIGS_C -# undef S_MP_MUL_HIGH_DIGS_FAST_C -# undef S_MP_TOOM_MUL_C -# undef S_MP_TOOM_SQR_C +# undef S_MP_INVMOD_ODD_C +# undef S_MP_MUL_BALANCE_C +# undef S_MP_MUL_HIGH_C +# undef S_MP_MUL_HIGH_COMBA_C +# undef S_MP_MUL_KARATSUBA_C +# undef S_MP_MUL_TOOM_C +# undef S_MP_SQR_KARATSUBA_C +# undef S_MP_SQR_TOOM_C # ifndef SC_RSA_1_WITH_TESTS # undef MP_REDUCE_C @@ -104,7 +104,7 @@ * trouble. */ # undef MP_MONTGOMERY_REDUCE_C -# undef S_MP_MUL_DIGS_C +# undef S_MP_MUL_C # undef S_MP_SQR_C # endif From 410bf4938571de3b7a6e9ea99d94c68fa00ab110 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:26:50 +0100 Subject: [PATCH 113/304] apply a series of simplifications * this is the final commit of a series of simplifications, containing only the regenerated files and the explanation in the commit message * This is in preparation of the size_t change/a potential representation change to use full width as in tfm, if a (partial?) merge with tfm is desired. These changes have their own merits however. * Remove obfuscating tmpx digit pointers (fewer variables, it is more obvious what is being manipulated) * Reduce scope of variables where possible * Stricter error handling/checking (for example handling in karatsuba was broken) * In some cases the result was written even in the case of an error (e.g. s_mp_is_divisible). This will hide bugs, since the user should check the return value (enforced by MP_WUR). Furthermore if the user accesses the non-initialized result, valgrind will complain for example. Global static analysis like coverity will also detect the issue. Therefore this improves the status quo. * Introduce generic, private MP_EXCH macro which can be used to swap values. * Introduce s_mp_copy_digs/s_mp_zero_digs/s_mp_zero_buf * Some control flow simplifications, e.g, loops instead of goto * Renamings of variables/labels for consistency * Renamings of mul/sqr functions for more consistency, e.g., comba instead of fast suffix * I didn't read through some very complex functions. They are so complex, I am too afraid and lazy to touch them. Maybe someone resposible wants to simplify them if possible. Hint... Hint... - mp_prime_strong_lucas_selfridge.c - s_mp_exptmod.c - s_mp_exptmod_fast.c --- helper.pl | 5 +- libtommath_VS2008.vcproj | 48 +++++---- makefile | 32 +++--- makefile.mingw | 32 +++--- makefile.msvc | 32 +++--- makefile.shared | 32 +++--- makefile.unix | 32 +++--- tommath.def | 1 - tommath_class.h | 228 +++++++++++++++++++++++---------------- 9 files changed, 243 insertions(+), 199 deletions(-) diff --git a/helper.pl b/helper.pl index 223c7ef60..2378ccea8 100755 --- a/helper.pl +++ b/helper.pl @@ -57,9 +57,8 @@ sub check_source { push @{$troubles->{unwanted_calloc}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bcalloc\s*\(/; push @{$troubles->{unwanted_free}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bfree\s*\(/; # and we probably want to also avoid the following - push @{$troubles->{unwanted_memcpy}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcpy\s*\(/; - push @{$troubles->{unwanted_memset}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemset\s*\(/; - push @{$troubles->{unwanted_memcpy}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcpy\s*\(/; + #push @{$troubles->{unwanted_memcpy}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcpy\s*\(/; + #push @{$troubles->{unwanted_memset}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemset\s*\(/; push @{$troubles->{unwanted_memmove}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemmove\s*\(/; push @{$troubles->{unwanted_memcmp}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcmp\s*\(/; push @{$troubles->{unwanted_strcmp}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bstrcmp\s*\(/; diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 116275e8d..07c784bf9 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -576,10 +576,6 @@ RelativePath="mp_mod_2d.c" >
- - @@ -833,7 +829,7 @@ > + + + + + + Date: Tue, 5 Nov 2019 17:53:08 +0100 Subject: [PATCH 114/304] re-enable checks for memcpy&memset [skip ci] --- helper.pl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/helper.pl b/helper.pl index 2378ccea8..93ca40aee 100755 --- a/helper.pl +++ b/helper.pl @@ -57,8 +57,8 @@ sub check_source { push @{$troubles->{unwanted_calloc}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bcalloc\s*\(/; push @{$troubles->{unwanted_free}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bfree\s*\(/; # and we probably want to also avoid the following - #push @{$troubles->{unwanted_memcpy}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcpy\s*\(/; - #push @{$troubles->{unwanted_memset}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemset\s*\(/; + push @{$troubles->{unwanted_memcpy}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcpy\s*\(/ && $file !~ /s_mp_copy_digs.c/; + push @{$troubles->{unwanted_memset}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemset\s*\(/ && $file !~ /s_mp_zero_buf.c/ && $file !~ /s_mp_zero_digs.c/; push @{$troubles->{unwanted_memmove}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemmove\s*\(/; push @{$troubles->{unwanted_memcmp}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bmemcmp\s*\(/; push @{$troubles->{unwanted_strcmp}}, $lineno if $file =~ /^[^\/]+\.c$/ && $l =~ /\bstrcmp\s*\(/; From 146becbd9a73de2356bb38fa19741bf9e0192a3a Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Thu, 31 Oct 2019 19:26:55 +0100 Subject: [PATCH 115/304] literal suffix --- demo/mtest_opponent.c | 2 +- demo/test.c | 78 +++++++++++++++++++++---------------------- etc/tune.c | 2 +- tommath.h | 4 +-- 4 files changed, 43 insertions(+), 43 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 648a65447..edbecc0c1 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -304,7 +304,7 @@ static int mtest_opponent(void) DO(mp_read_radix(&c, buf, 64)); DO(mp_invmod(&a, &b, &d)); DO(mp_mulmod(&d, &a, &b, &e)); - if (mp_cmp_d(&e, 1uL) != MP_EQ) { + if (mp_cmp_d(&e, 1u) != MP_EQ) { printf("inv [wrong value from MPI?!] failure\n"); draw(&a); draw(&b); diff --git a/demo/test.c b/demo/test.c index 3b978730a..4a4170be3 100644 --- a/demo/test.c +++ b/demo/test.c @@ -115,20 +115,20 @@ static int test_trivial_stuff(void) DO(mp_abs(&a, &b)); EXPECT(!mp_isneg(&b)); /* a: -5-> b: -4 */ - DO(mp_add_d(&a, 1uL, &b)); + DO(mp_add_d(&a, 1u, &b)); EXPECT(mp_isneg(&b)); EXPECT(mp_get_i32(&b) == -4); EXPECT(mp_get_u32(&b) == (uint32_t)-4); EXPECT(mp_get_mag_u32(&b) == 4); /* a: -5-> b: 1 */ - DO(mp_add_d(&a, 6uL, &b)); + DO(mp_add_d(&a, 6u, &b)); EXPECT(mp_get_u32(&b) == 1); /* a: -5-> a: 1 */ - DO(mp_add_d(&a, 6uL, &a)); + DO(mp_add_d(&a, 6u, &a)); EXPECT(mp_get_u32(&a) == 1); mp_zero(&a); /* a: 0-> a: 6 */ - DO(mp_add_d(&a, 6uL, &a)); + DO(mp_add_d(&a, 6u, &a)); EXPECT(mp_get_u32(&a) == 6); mp_set(&a, 42u); @@ -223,9 +223,9 @@ static int test_mp_get_set_i64(void) DOR(mp_init(&a)); - check_get_set_i64(&a, 0); - check_get_set_i64(&a, -1); - check_get_set_i64(&a, 1); + check_get_set_i64(&a, 0LL); + check_get_set_i64(&a, -1LL); + check_get_set_i64(&a, 1LL); check_get_set_i64(&a, INT64_MIN); check_get_set_i64(&a, INT64_MAX); @@ -282,7 +282,7 @@ static int test_mp_rand(void) DO(mp_rand(&a, n)); DO(mp_incr(&a)); DO(mp_div_2d(&a, n * MP_DIGIT_BIT, &b, NULL)); - if (mp_cmp_d(&b, 1) != MP_EQ) { + if (mp_cmp_d(&b, 1u) != MP_EQ) { ndraw(&a, "mp_rand() a"); ndraw(&b, "mp_rand() b"); e = MP_ERR; @@ -729,7 +729,7 @@ static int test_mp_sqrt(void) printf("\nmp_sqrt() error!"); goto LBL_ERR; } - DO(mp_root_u32(&a, 2uL, &c)); + DO(mp_root_u32(&a, 2u, &c)); if (mp_cmp_mag(&b, &c) != MP_EQ) { printf("mp_sqrt() bad result!\n"); goto LBL_ERR; @@ -770,7 +770,7 @@ static int test_mp_is_square(void) } /* test for false positives */ - DO(mp_add_d(&a, 1uL, &a)); + DO(mp_add_d(&a, 1u, &a)); if (mp_is_square(&a, &res) != MP_OKAY) { printf("\nfp:mp_is_square() error!"); goto LBL_ERR; @@ -879,9 +879,9 @@ static int test_mp_prime_is_prime(void) } /* About the same size as Arnault's pseudoprime */ printf("\rTesting mp_prime_is_prime() with certified prime 2^1119 + 53 "); - mp_set(&a, 1uL); + mp_set(&a, 1u); DO(mp_mul_2d(&a,1119,&a)); - DO(mp_add_d(&a, 53uL, &a)); + DO(mp_add_d(&a, 53u, &a)); e = mp_prime_is_prime(&a, mp_prime_rabin_miller_trials(mp_count_bits(&a)), &cnt); /* small problem */ if (e != MP_OKAY) { @@ -912,7 +912,7 @@ static int test_mp_prime_is_prime(void) goto LBL_ERR; } /* let's see if it's really a safe prime */ - DO(mp_sub_d(&a, 1uL, &b)); + DO(mp_sub_d(&a, 1u, &b)); DO(mp_div_2(&b, &b)); e = mp_prime_is_prime(&b, mp_prime_rabin_miller_trials(mp_count_bits(&b)), &cnt); /* small problem */ @@ -1010,7 +1010,7 @@ static int test_mp_prime_next_prime(void) putchar('\n'); goto LBL_ERR; } - mp_set(&a, 8); + mp_set(&a, 8u); DO(mp_prime_next_prime(&a, 5, true)); if (mp_cmp_d(&a, 11u) != MP_EQ) { printf("mp_prime_next_prime: output should have been 11 but was: "); @@ -1183,7 +1183,7 @@ static int test_mp_cnt_lsb(void) mp_int a, b; DOR(mp_init_multi(&a, &b, NULL)); - mp_set(&a, 1uL); + mp_set(&a, 1u); for (ix = 0; ix < 1024; ix++) { if (mp_cnt_lsb(&a) != ix) { printf("Failed at %d, %d\n", ix, mp_cnt_lsb(&a)); @@ -1212,7 +1212,7 @@ static int test_mp_reduce_2k(void) mp_digit tmp; DO(mp_2expt(&a, cnt)); - DO(mp_sub_d(&a, 2uL, &a)); /* a = 2**cnt - 2 */ + DO(mp_sub_d(&a, 2u, &a)); /* a = 2**cnt - 2 */ printf("\r %4d bits", cnt); printf("(%d)", mp_reduce_is_2k(&a)); @@ -1226,7 +1226,7 @@ static int test_mp_reduce_2k(void) DO(mp_rand(&b, (cnt / MP_DIGIT_BIT + 1) * 2)); DO(mp_copy(&c, &b)); DO(mp_mod(&c, &a, &c)); - DO(mp_reduce_2k(&b, &a, 2uL)); + DO(mp_reduce_2k(&b, &a, 2u)); if (mp_cmp(&c, &b) != MP_EQ) { printf("FAILED\n"); goto LBL_ERR; @@ -1249,7 +1249,7 @@ static int test_mp_div_3(void) DOR(mp_init_multi(&a, &b, &c, &d, &e, NULL)); /* test mp_div_3 */ - mp_set(&d, 3uL); + mp_set(&d, 3u); for (cnt = 0; cnt < 10000;) { mp_digit r2; @@ -1306,7 +1306,7 @@ static int test_mp_dr_reduce(void) fflush(stdout); } DO(mp_sqr(&b, &b)); - DO(mp_add_d(&b, 1uL, &b)); + DO(mp_add_d(&b, 1u, &b)); DO(mp_copy(&b, &c)); DO(mp_mod(&b, &a, &b)); @@ -1370,10 +1370,10 @@ static int test_mp_reduce_2k_l(void) fflush(stdout); for (cnt = 0; cnt < (int)(1uL << 20); cnt++) { DO(mp_sqr(&b, &b)); - DO(mp_add_d(&b, 1uL, &b)); + DO(mp_add_d(&b, 1u, &b)); DO(mp_reduce_2k_l(&b, &a, &d)); DO(mp_sqr(&c, &c)); - DO(mp_add_d(&c, 1uL, &c)); + DO(mp_add_d(&c, 1u, &c)); DO(mp_mod(&c, &a, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("mp_reduce_2k_l() failed at step %d\n", cnt); @@ -1439,7 +1439,7 @@ static int test_mp_log_u32(void) 0 x MP_VAL 1 x MP_VAL */ - mp_set(&a, 42uL); + mp_set(&a, 42u); base = 0u; if (mp_log_u32(&a, base, &lb) != MP_VAL) { goto LBL_ERR; @@ -1520,8 +1520,8 @@ static int test_mp_log_u32(void) /*Test upper edgecase with base UINT32_MAX and number (UINT32_MAX/2)*UINT32_MAX^10 */ mp_set(&a, max_base); - DO(mp_expt_u32(&a, 10uL, &a)); - DO(mp_add_d(&a, max_base / 2, &a)); + DO(mp_expt_u32(&a, 10u, &a)); + DO(mp_add_d(&a, max_base / 2u, &a)); DO(mp_log_u32(&a, max_base, &lb)); if (lb != 10u) { goto LBL_ERR; @@ -1543,7 +1543,7 @@ static int test_mp_incr(void) /* Does it increment inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); DO(mp_incr(&a)); - if (mp_cmp_d(&a, (MP_MASK/2uL) + 1uL) != MP_EQ) { + if (mp_cmp_d(&a, (MP_MASK/2u) + 1u) != MP_EQ) { goto LBL_ERR; } @@ -1551,22 +1551,22 @@ static int test_mp_incr(void) mp_set(&a, MP_MASK); mp_set(&b, MP_MASK); DO(mp_incr(&a)); - DO(mp_add_d(&b, 1uL, &b)); + DO(mp_add_d(&b, 1u, &b)); if (mp_cmp(&a, &b) != MP_EQ) { goto LBL_ERR; } /* Does it increment from -1 to 0? */ - mp_set(&a, 1uL); + mp_set(&a, 1u); a.sign = MP_NEG; DO(mp_incr(&a)); - if (mp_cmp_d(&a, 0uL) != MP_EQ) { + if (mp_cmp_d(&a, 0u) != MP_EQ) { goto LBL_ERR; } /* Does it increment from -(MP_MASK + 1) to -MP_MASK? */ mp_set(&a, MP_MASK); - DO(mp_add_d(&a, 1uL, &a)); + DO(mp_add_d(&a, 1u, &a)); a.sign = MP_NEG; DO(mp_incr(&a)); if (a.sign != MP_NEG) { @@ -1593,13 +1593,13 @@ static int test_mp_decr(void) /* Does it decrement inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); DO(mp_decr(&a)); - if (mp_cmp_d(&a, (MP_MASK/2uL) - 1uL) != MP_EQ) { + if (mp_cmp_d(&a, (MP_MASK/2u) - 1u) != MP_EQ) { goto LBL_ERR; } /* Does it decrement outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); - DO(mp_add_d(&a, 1uL, &a)); + DO(mp_add_d(&a, 1u, &a)); DO(mp_decr(&a)); if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { goto LBL_ERR; @@ -1610,7 +1610,7 @@ static int test_mp_decr(void) DO(mp_decr(&a)); if (a.sign == MP_NEG) { a.sign = MP_ZPOS; - if (mp_cmp_d(&a, 1uL) != MP_EQ) { + if (mp_cmp_d(&a, 1u) != MP_EQ) { goto LBL_ERR; } } else { @@ -1623,7 +1623,7 @@ static int test_mp_decr(void) a.sign = MP_NEG; mp_set(&b, MP_MASK); b.sign = MP_NEG; - DO(mp_sub_d(&b, 1uL, &b)); + DO(mp_sub_d(&b, 1u, &b)); DO(mp_decr(&a)); if (mp_cmp(&a, &b) != MP_EQ) { goto LBL_ERR; @@ -2038,7 +2038,7 @@ static int test_mp_radix_size(void) DOR(mp_init(&a)); /* number to result in a different size for every base: 67^(4 * 67) */ - mp_set(&a, 67); + mp_set(&a, 67u); DO(mp_expt_u32(&a, 268u, &a)); for (radix = 2; radix < 65; radix++) { @@ -2254,7 +2254,7 @@ static int test_mp_pack_unpack(void) DOR(mp_init_multi(&a, &b, NULL)); DO(mp_rand(&a, 15)); - count = mp_pack_count(&a, 0, 1); + count = mp_pack_count(&a, 0uL, 1uL); buf = malloc(count); if (buf == NULL) { @@ -2262,10 +2262,10 @@ static int test_mp_pack_unpack(void) goto LBL_ERR; } - DO(mp_pack((void *)buf, count, &written, order, 1, - endianess, 0, &a)); - DO(mp_unpack(&b, count, order, 1, - endianess, 0, (const void *)buf)); + DO(mp_pack((void *)buf, count, &written, order, 1uL, + endianess, 0uL, &a)); + DO(mp_unpack(&b, count, order, 1uL, + endianess, 0uL, (const void *)buf)); if (mp_cmp(&a, &b) != MP_EQ) { fprintf(stderr, "pack/unpack cycle failed\n"); diff --git a/etc/tune.c b/etc/tune.c index 9657910ff..0b7373448 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -281,7 +281,7 @@ int main(int argc, char **argv) /*int preset[8];*/ char *endptr, *str; - uint64_t seed = 0xdeadbeef; + uint64_t seed = 0xdeadbeefULL; int opt; struct cutoffs orig, updated; diff --git a/tommath.h b/tommath.h index d024a33fe..68a1592c9 100644 --- a/tommath.h +++ b/tommath.h @@ -375,10 +375,10 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) MP_WUR; mp_err mp_mod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* Increment "a" by one like "a++". Changes input! */ -#define mp_incr(a) mp_add_d((a), 1, (a)) +#define mp_incr(a) mp_add_d((a), 1u, (a)) /* Decrement "a" by one like "a--". Changes input! */ -#define mp_decr(a) mp_sub_d((a), 1, (a)) +#define mp_decr(a) mp_sub_d((a), 1u, (a)) /* ---> single digit functions <--- */ From 40342807dc727d30fbe5e4f9d05a54ec56220467 Mon Sep 17 00:00:00 2001 From: Francois Perrad Date: Fri, 1 Nov 2019 20:08:41 +0100 Subject: [PATCH 116/304] explicit operator precedence --- demo/test.c | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/demo/test.c b/demo/test.c index 4a4170be3..cfe2e5a7d 100644 --- a/demo/test.c +++ b/demo/test.c @@ -43,12 +43,12 @@ static int64_t rand_int64(void) static uint32_t uabs32(int32_t x) { - return x > 0 ? (uint32_t)x : -(uint32_t)x; + return (x > 0) ? (uint32_t)x : -(uint32_t)x; } static uint64_t uabs64(int64_t x) { - return x > 0 ? (uint64_t)x : -(uint64_t)x; + return (x > 0) ? (uint64_t)x : -(uint64_t)x; } /* This function prototype is needed @@ -292,7 +292,7 @@ static int test_mp_rand(void) LBL_ERR: mp_rand_source(s_mp_rand_jenkins); mp_clear_multi(&a, &b, NULL); - return e == MP_OKAY ? EXIT_SUCCESS : EXIT_FAILURE; + return (e == MP_OKAY) ? EXIT_SUCCESS : EXIT_FAILURE; } static int test_mp_kronecker(void) @@ -1092,7 +1092,7 @@ static int test_mp_montgomery_reduce(void) /* now test a random reduction */ for (ix = 0; ix < 100; ix++) { - DO(mp_rand(&c, 1 + abs(rand_int()) % (2*i))); + DO(mp_rand(&c, 1 + (abs(rand_int()) % (2*i)))); DO(mp_copy(&c, &d)); DO(mp_copy(&c, &e)); @@ -1223,7 +1223,7 @@ static int test_mp_reduce_2k(void) printf("."); fflush(stdout); } - DO(mp_rand(&b, (cnt / MP_DIGIT_BIT + 1) * 2)); + DO(mp_rand(&b, ((cnt / MP_DIGIT_BIT) + 1) * 2)); DO(mp_copy(&c, &b)); DO(mp_mod(&c, &a, &c)); DO(mp_reduce_2k(&b, &a, 2u)); @@ -1257,7 +1257,7 @@ static int test_mp_div_3(void) printf("\r %9d", cnt); fflush(stdout); } - DO(mp_rand(&a, abs(rand_int()) % 128 + 1)); + DO(mp_rand(&a, (abs(rand_int()) % 128) + 1)); DO(mp_div(&a, &d, &b, &e)); DO(mp_div_3(&a, &c, &r2)); @@ -1903,7 +1903,7 @@ static int test_s_mp_mul_karatsuba(void) int size; DOR(mp_init_multi(&a, &b, &c, &d, NULL)); - for (size = MP_MUL_KARATSUBA_CUTOFF; size < MP_MUL_KARATSUBA_CUTOFF + 20; size++) { + for (size = MP_MUL_KARATSUBA_CUTOFF; size < (MP_MUL_KARATSUBA_CUTOFF + 20); size++) { DO(mp_rand(&a, size)); DO(mp_rand(&b, size)); DO(s_mp_mul_karatsuba(&a, &b, &c)); @@ -1927,7 +1927,7 @@ static int test_s_mp_sqr_karatsuba(void) int size; DOR(mp_init_multi(&a, &b, &c, NULL)); - for (size = MP_SQR_KARATSUBA_CUTOFF; size < MP_SQR_KARATSUBA_CUTOFF + 20; size++) { + for (size = MP_SQR_KARATSUBA_CUTOFF; size < (MP_SQR_KARATSUBA_CUTOFF + 20); size++) { DO(mp_rand(&a, size)); DO(s_mp_sqr_karatsuba(&a, &b)); DO(s_mp_sqr(&a, &c)); @@ -1976,7 +1976,7 @@ static int test_s_mp_mul_toom(void) } #endif - for (size = MP_MUL_TOOM_CUTOFF; size < MP_MUL_TOOM_CUTOFF + 20; size++) { + for (size = MP_MUL_TOOM_CUTOFF; size < (MP_MUL_TOOM_CUTOFF + 20); size++) { DO(mp_rand(&a, size)); DO(mp_rand(&b, size)); DO(s_mp_mul_toom(&a, &b, &c)); @@ -2000,7 +2000,7 @@ static int test_s_mp_sqr_toom(void) int size; DOR(mp_init_multi(&a, &b, &c, NULL)); - for (size = MP_SQR_TOOM_CUTOFF; size < MP_SQR_TOOM_CUTOFF + 20; size++) { + for (size = MP_SQR_TOOM_CUTOFF; size < (MP_SQR_TOOM_CUTOFF + 20); size++) { DO(mp_rand(&a, size)); DO(s_mp_sqr_toom(&a, &b)); DO(s_mp_sqr(&a, &c)); @@ -2075,7 +2075,7 @@ static int test_s_mp_div_recursive(void) DOR(mp_init_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL)); - for (size = MP_MUL_KARATSUBA_CUTOFF; size < 3 * MP_MUL_KARATSUBA_CUTOFF; size += 10) { + for (size = MP_MUL_KARATSUBA_CUTOFF; size < (3 * MP_MUL_KARATSUBA_CUTOFF); size += 10) { printf("\rsizes = %d / %d", 10 * size, size); /* Relation 10:1 */ DO(mp_rand(&a, 10 * size)); @@ -2289,7 +2289,7 @@ static int unit_tests(int argc, char **argv) } test[] = { #define T0(n) { #n, test_##n } #define T1(n, o) { #n, MP_HAS(o) ? test_##n : NULL } -#define T2(n, o1, o2) { #n, MP_HAS(o1) && MP_HAS(o2) ? test_##n : NULL } +#define T2(n, o1, o2) { #n, (MP_HAS(o1) && MP_HAS(o2)) ? test_##n : NULL } T0(feature_detection), T0(trivial_stuff), T2(mp_get_set_i32, MP_GET_I32, MP_GET_MAG_U32), @@ -2351,7 +2351,7 @@ static int unit_tests(int argc, char **argv) s_mp_rand_jenkins_init(t); mp_rand_source(s_mp_rand_jenkins); - for (i = 0; i < sizeof(test) / sizeof(test[0]); ++i) { + for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { if (argc > 1) { for (j = 1; j < argc; ++j) { if (strstr(test[i].name, argv[j]) != NULL) { From 93f8e7603d727a88519d01418561bc4439b489ae Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 18:04:05 +0100 Subject: [PATCH 117/304] rename MP_MAXFAST to MP_MAX_COMBA --- mp_montgomery_reduce.c | 2 +- mp_mul.c | 2 +- mp_sqr.c | 2 +- s_mp_exptmod_fast.c | 2 +- s_mp_mul.c | 2 +- s_mp_mul_high.c | 2 +- tommath_private.h | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/mp_montgomery_reduce.c b/mp_montgomery_reduce.c index de6a90002..dbf45d3cf 100644 --- a/mp_montgomery_reduce.c +++ b/mp_montgomery_reduce.c @@ -18,7 +18,7 @@ mp_err mp_montgomery_reduce(mp_int *x, const mp_int *n, mp_digit rho) digs = (n->used * 2) + 1; if ((digs < MP_WARRAY) && (x->used <= MP_WARRAY) && - (n->used < MP_MAXFAST)) { + (n->used < MP_MAX_COMBA)) { return s_mp_montgomery_reduce_comba(x, n, rho); } diff --git a/mp_mul.c b/mp_mul.c index 4103535a1..9a83687bf 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -39,7 +39,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) * digits won't affect carry propagation */ (digs < MP_WARRAY) && - (min <= MP_MAXFAST)) { + (min <= MP_MAX_COMBA)) { err = s_mp_mul_comba(a, b, c, digs); } else if (MP_HAS(S_MP_MUL)) { err = s_mp_mul(a, b, c, digs); diff --git a/mp_sqr.c b/mp_sqr.c index b0da0edeb..67a822416 100644 --- a/mp_sqr.c +++ b/mp_sqr.c @@ -15,7 +15,7 @@ mp_err mp_sqr(const mp_int *a, mp_int *b) err = s_mp_sqr_karatsuba(a, b); } else if (MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ (((a->used * 2) + 1) < MP_WARRAY) && - (a->used < (MP_MAXFAST / 2))) { + (a->used < (MP_MAX_COMBA / 2))) { err = s_mp_sqr_comba(a, b); } else if (MP_HAS(S_MP_SQR)) { err = s_mp_sqr(a, b); diff --git a/s_mp_exptmod_fast.c b/s_mp_exptmod_fast.c index 813eef2c3..e7729f49d 100644 --- a/s_mp_exptmod_fast.c +++ b/s_mp_exptmod_fast.c @@ -82,7 +82,7 @@ mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_i /* automatically pick the comba one if available (saves quite a few calls/ifs) */ if (MP_HAS(S_MP_MONTGOMERY_REDUCE_COMBA) && (((P->used * 2) + 1) < MP_WARRAY) && - (P->used < MP_MAXFAST)) { + (P->used < MP_MAX_COMBA)) { redux = s_mp_montgomery_reduce_comba; } else if (MP_HAS(MP_MONTGOMERY_REDUCE)) { /* use slower baseline Montgomery method */ diff --git a/s_mp_mul.c b/s_mp_mul.c index cd17b99ac..fb99d8054 100644 --- a/s_mp_mul.c +++ b/s_mp_mul.c @@ -15,7 +15,7 @@ mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* can we use the fast multiplier? */ if ((digs < MP_WARRAY) && - (MP_MIN(a->used, b->used) < MP_MAXFAST)) { + (MP_MIN(a->used, b->used) < MP_MAX_COMBA)) { return s_mp_mul_comba(a, b, c, digs); } diff --git a/s_mp_mul_high.c b/s_mp_mul_high.c index d1d180641..1bde00aa9 100644 --- a/s_mp_mul_high.c +++ b/s_mp_mul_high.c @@ -15,7 +15,7 @@ mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) /* can we use the fast multiplier? */ if (MP_HAS(S_MP_MUL_HIGH_COMBA) && ((a->used + b->used + 1) < MP_WARRAY) - && (MP_MIN(a->used, b->used) < MP_MAXFAST)) { + && (MP_MIN(a->used, b->used) < MP_MAX_COMBA)) { return s_mp_mul_high_comba(a, b, c, digs); } diff --git a/tommath_private.h b/tommath_private.h index 096979634..9a3e2f8d2 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -124,8 +124,8 @@ extern void MP_FREE(void *mem, size_t size); #define MP_STATIC_ASSERT(msg, cond) typedef char mp_static_assert_##msg[(cond) ? 1 : -1]; #define MP_SIZEOF_BITS(type) ((size_t)CHAR_BIT * sizeof(type)) -#define MP_MAXFAST (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) +#define MP_MAX_COMBA (int)(1uL << (MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT))) #define MP_WARRAY (int)(1uL << ((MP_SIZEOF_BITS(mp_word) - (2u * (size_t)MP_DIGIT_BIT)) + 1u)) #if defined(MP_16BIT) From bbb178089d5bf0b08ff248e26708165588e4a035 Mon Sep 17 00:00:00 2001 From: nijtmans Date: Wed, 30 Oct 2019 14:19:50 +0100 Subject: [PATCH 118/304] mp_radix off-by-one error and other related code-cleanup --- demo/test.c | 13 ++++++------- mp_fread.c | 6 +++--- mp_radix_smap.c | 19 ++++++++----------- mp_read_radix.c | 6 +++--- tommath_private.h | 2 +- 5 files changed, 21 insertions(+), 25 deletions(-) diff --git a/demo/test.c b/demo/test.c index cfe2e5a7d..f2f5800b3 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1138,7 +1138,7 @@ static int test_mp_read_radix(void) DO(mp_read_radix(&a, "123456", 10)); - DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + DO(mp_to_radix(&a, buf, sizeof(buf), &written, 10)); printf(" '123456' a == %s, length = %zu", buf, written); /* See comment in mp_to_radix.c */ @@ -1153,11 +1153,11 @@ static int test_mp_read_radix(void) buf, written, mp_error_to_string(err)); */ DO(mp_read_radix(&a, "-123456", 10)); - DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + DO(mp_to_radix(&a, buf, sizeof(buf), &written, 10)); printf("\r '-123456' a == %s, length = %zu", buf, written); DO(mp_read_radix(&a, "0", 10)); - DO(mp_to_radix(&a, buf, SIZE_MAX, &written, 10)); + DO(mp_to_radix(&a, buf, sizeof(buf), &written, 10)); printf("\r '0' a == %s, length = %zu", buf, written); while (0) { @@ -1335,7 +1335,7 @@ static int test_mp_reduce_2k_l(void) mp_int a, b, c, d; int cnt; char buf[4096]; - size_t length[1]; + size_t length; DOR(mp_init_multi(&a, &b, NULL)); /* test the mp_reduce_2k_l code */ # if LTM_DEMO_TEST_REDUCE_2K_L == 1 @@ -1353,9 +1353,8 @@ static int test_mp_reduce_2k_l(void) # else # error oops # endif - *length = sizeof(buf); - DO(mp_to_radix(&a, buf, length, 10)); - printf("\n\np==%s, length = %zu\n", buf, *length); + DO(mp_to_radix(&a, buf, sizeof(buf), &length, 10)); + printf("\n\np==%s, length = %zu\n", buf, length); /* now mp_reduce_is_2k_l() should return */ if (mp_reduce_is_2k_l(&a) != 1) { printf("mp_reduce_is_2k_l() return 0, should be 1\n"); diff --git a/mp_fread.c b/mp_fread.c index 005c62ae9..bd336ce54 100644 --- a/mp_fread.c +++ b/mp_fread.c @@ -35,14 +35,14 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) uint8_t y; unsigned pos; ch = (radix <= 36) ? MP_TOUPPER(ch) : ch; - pos = (unsigned)(ch - (int)'('); - if (MP_RMAP_REVERSE_SIZE < pos) { + pos = (unsigned)(ch - (int)'+'); + if (MP_RMAP_REVERSE_SIZE <= pos) { break; } y = s_mp_rmap_reverse[pos]; - if ((y == 0xff) || (y >= radix)) { + if (y >= radix) { break; } diff --git a/mp_radix_smap.c b/mp_radix_smap.c index 678e806a7..73fd7cfbe 100644 --- a/mp_radix_smap.c +++ b/mp_radix_smap.c @@ -6,17 +6,14 @@ /* chars used in radix conversions */ const char s_mp_rmap[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; const uint8_t s_mp_rmap_reverse[] = { - 0xff, 0xff, 0xff, 0x3e, 0xff, 0xff, 0xff, 0x3f, /* ()*+,-./ */ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, /* 01234567 */ - 0x08, 0x09, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 89:;<=>? */ - 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, /* @ABCDEFG */ - 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, /* HIJKLMNO */ - 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, /* PQRSTUVW */ - 0x21, 0x22, 0x23, 0xff, 0xff, 0xff, 0xff, 0xff, /* XYZ[\]^_ */ - 0xff, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, /* `abcdefg */ - 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, /* hijklmno */ - 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, /* pqrstuvw */ - 0x3b, 0x3c, 0x3d, 0xff, 0xff, 0xff, 0xff, 0xff, /* xyz{|}~. */ + 0x3e, 0xff, 0xff, 0xff, 0x3f, 0x00, 0x01, 0x02, 0x03, 0x04, /* +,-./01234 */ + 0x05, 0x06, 0x07, 0x08, 0x09, 0xff, 0xff, 0xff, 0xff, 0xff, /* 56789:;<=> */ + 0xff, 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, /* ?@ABCDEFGH */ + 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, /* IJKLMNOPQR */ + 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0xff, 0xff, /* STUVWXYZ[\ */ + 0xff, 0xff, 0xff, 0xff, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, /* ]^_`abcdef */ + 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, /* ghijklmnop */ + 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d /* qrstuvwxyz */ }; MP_STATIC_ASSERT(correct_rmap_reverse_size, sizeof(s_mp_rmap_reverse) == MP_RMAP_REVERSE_SIZE) #endif diff --git a/mp_read_radix.c b/mp_read_radix.c index df8059a55..500f2d9a3 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -33,8 +33,8 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) */ uint8_t y; char ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; - unsigned pos = (unsigned)(ch - '('); - if (MP_RMAP_REVERSE_SIZE < pos) { + unsigned pos = (unsigned)(ch - '+'); + if (MP_RMAP_REVERSE_SIZE <= pos) { break; } y = s_mp_rmap_reverse[pos]; @@ -43,7 +43,7 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) * and is less than the given radix add it * to the number, otherwise exit the loop. */ - if ((y == 0xff) || (y >= radix)) { + if (y >= radix) { break; } if ((err = mp_mul_d(a, (mp_digit)radix, a)) != MP_OKAY) { diff --git a/tommath_private.h b/tommath_private.h index 9a3e2f8d2..90da26923 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -193,7 +193,7 @@ MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); -#define MP_RMAP_REVERSE_SIZE 88u +#define MP_RMAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_rmap[]; extern MP_PRIVATE const uint8_t s_mp_rmap_reverse[]; extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; From e8e65119d10f6c2a54e7404ddc6269d8be62ddbd Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 19:18:32 +0100 Subject: [PATCH 119/304] add COMPILE_LTO to test link time optimization the library performs best with lto since many small functions can be inlined across objects. --- .travis.yml | 4 ++++ demo/shared.c | 2 +- makefile | 2 +- makefile_include.mk | 6 ++++++ testme.sh | 16 ++++++++-------- 5 files changed, 20 insertions(+), 10 deletions(-) diff --git a/.travis.yml b/.travis.yml index a269c4ec6..64ab75ca6 100644 --- a/.travis.yml +++ b/.travis.yml @@ -163,6 +163,10 @@ matrix: packages: - clang-4.0 + # Link time optimization + - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' + # GCC for the x86-64 architecture with restricted limb sizes # formerly started with the option "--with-low-mp" to testme.sh # but testing all three in one run took to long and timed out. diff --git a/demo/shared.c b/demo/shared.c index 5ada4603a..7ef475687 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -3,7 +3,7 @@ void ndraw(const mp_int *a, const char *name) { char *buf; - size_t size; + size_t size = 0; mp_err err; if ((err = mp_radix_size(a, 10, &size)) != MP_OKAY) { diff --git a/makefile b/makefile index 404539084..a04cd4d87 100644 --- a/makefile +++ b/makefile @@ -77,7 +77,7 @@ profiled_single: pre_gen rm -f *.o timing $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o $(AR) $(ARFLAGS) $(LIBNAME) tommath_amalgam.o - ranlib $(LIBNAME) + $(RANLIB) $(LIBNAME) install: $(LIBNAME) install -d $(DESTDIR)$(LIBPATH) diff --git a/makefile_include.mk b/makefile_include.mk index 4b5961c28..aebbc8f94 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -86,6 +86,12 @@ LTM_CFLAGS += -O3 -funroll-loops LTM_CFLAGS += -fomit-frame-pointer endif +ifdef COMPILE_LTO +LTM_CFLAGS += -flto +AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) +RANLIB = $(subst clang,llvm-ranlib,$(subst gcc,gcc-ranlib,$(CC))) +endif + endif # COMPILE_SIZE ifneq ($(findstring clang,$(CC)),) diff --git a/testme.sh b/testme.sh index 6c71ac44f..1a03f55a9 100755 --- a/testme.sh +++ b/testme.sh @@ -107,7 +107,7 @@ _make() { echo -ne " Compile $1 $2" suffix=$(echo ${1}${2} | tr ' ' '_') - CC="$1" CFLAGS="$2 $TEST_CFLAGS" make -j$MAKE_JOBS $3 $MAKE_OPTIONS > /dev/null 2>gcc_errors_${suffix}.log + CC="$1" CFLAGS="$2 $TEST_CFLAGS" make -j$MAKE_JOBS $3 $MAKE_OPTIONS 2>gcc_errors_${suffix}.log errcnt=$(wc -l < gcc_errors_${suffix}.log) if [[ ${errcnt} -gt 1 ]]; then echo " failed" @@ -354,7 +354,7 @@ _banner if [[ "$TEST_VS_MTEST" != "" ]] then make clean > /dev/null - _make "${compilers[0]} ${archflags[0]}" "$CFLAGS" "mtest_opponent" + _make "${compilers[0]}" "${archflags[0]} $CFLAGS" "mtest_opponent" echo _make "gcc" "$MTEST_RAND" "mtest" echo @@ -394,15 +394,15 @@ do fi if [[ "$VALGRIND_BIN" != "" ]] then - _runvalgrind "$i $a" "$CFLAGS" + _runvalgrind "$i" "$a $CFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runvalgrind "$i $a" "-DMP_16BIT $CFLAGS" - _runvalgrind "$i $a" "-DMP_32BIT $CFLAGS" + _runvalgrind "$i" "$a -DMP_16BIT $CFLAGS" + _runvalgrind "$i" "$a -DMP_32BIT $CFLAGS" else - _runtest "$i $a" "$CFLAGS" + _runtest "$i" "$a $CFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runtest "$i $a" "-DMP_16BIT $CFLAGS" - _runtest "$i $a" "-DMP_32BIT $CFLAGS" + _runtest "$i" "$a -DMP_16BIT $CFLAGS" + _runtest "$i" "$a -DMP_32BIT $CFLAGS" fi done done From 74d828d526569c321df37feba2ad810b08d9fa2e Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 20:25:39 +0100 Subject: [PATCH 120/304] don't use ranlib, `ar s` is equivalent --- makefile | 2 -- makefile.mingw | 4 +--- makefile.unix | 4 +--- makefile_include.mk | 2 -- 4 files changed, 2 insertions(+), 10 deletions(-) diff --git a/makefile b/makefile index a04cd4d87..4bb5789f9 100644 --- a/makefile +++ b/makefile @@ -55,7 +55,6 @@ s_mp_zero_buf.o s_mp_zero_digs.o $(LIBNAME): $(OBJECTS) $(AR) $(ARFLAGS) $@ $(OBJECTS) - $(RANLIB) $@ #make a profiled library (takes a while!!!) # @@ -77,7 +76,6 @@ profiled_single: pre_gen rm -f *.o timing $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o $(AR) $(ARFLAGS) $(LIBNAME) tommath_amalgam.o - $(RANLIB) $(LIBNAME) install: $(LIBNAME) install -d $(DESTDIR)$(LIBPATH) diff --git a/makefile.mingw b/makefile.mingw index c597143fc..16d7db374 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -13,8 +13,7 @@ PREFIX = c:\mingw CC = gcc AR = ar -ARFLAGS = r -RANLIB = ranlib +ARFLAGS = rcs STRIP = strip CFLAGS = -O2 LDFLAGS = @@ -69,7 +68,6 @@ $(OBJECTS): $(HEADERS) #Create libtommath.a $(LIBMAIN_S): $(OBJECTS) $(AR) $(ARFLAGS) $@ $(OBJECTS) - $(RANLIB) $@ #Create DLL + import library libtommath.dll.a $(LIBMAIN_D) $(LIBMAIN_I): $(OBJECTS) diff --git a/makefile.unix b/makefile.unix index 33a382926..d093a76df 100644 --- a/makefile.unix +++ b/makefile.unix @@ -16,8 +16,7 @@ LIBPATH = $(PREFIX)/lib INCPATH = $(PREFIX)/include CC = cc AR = ar -ARFLAGS = r -RANLIB = ranlib +ARFLAGS = rcs CFLAGS = -O2 LDFLAGS = @@ -72,7 +71,6 @@ $(OBJECTS): $(HEADERS) #Create libtommath.a $(LIBMAIN_S): $(OBJECTS) $(AR) $(ARFLAGS) $@ $(OBJECTS) - $(RANLIB) $@ #Build test_standalone suite test: demo/shared.o demo/test.o $(LIBMAIN_S) diff --git a/makefile_include.mk b/makefile_include.mk index aebbc8f94..be53ba7b5 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -36,7 +36,6 @@ endif # CROSS_COMPILE non-empty LD=$(CROSS_COMPILE)ld AR=$(CROSS_COMPILE)ar -RANLIB=$(CROSS_COMPILE)ranlib ifndef MAKE # BSDs refer to GNU Make as gmake @@ -89,7 +88,6 @@ endif ifdef COMPILE_LTO LTM_CFLAGS += -flto AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) -RANLIB = $(subst clang,llvm-ranlib,$(subst gcc,gcc-ranlib,$(CC))) endif endif # COMPILE_SIZE From 53a689d08494b9867d22e2a5302b3eb816d398fd Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 20:29:59 +0100 Subject: [PATCH 121/304] travis: install llvm-7 --- .travis.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.travis.yml b/.travis.yml index 64ab75ca6..20299bcea 100644 --- a/.travis.yml +++ b/.travis.yml @@ -166,6 +166,10 @@ matrix: # Link time optimization - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' + addons: + apt: + packages: + - llvm-7 # GCC for the x86-64 architecture with restricted limb sizes # formerly started with the option "--with-low-mp" to testme.sh From 3b98e826278490a3e5a0f578a0513936fa979a91 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 21:01:54 +0100 Subject: [PATCH 122/304] disable lto test for clang for now it works on debian but not on the outdated travis ubuntu --- .travis.yml | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 20299bcea..d8aa8856d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -165,11 +165,7 @@ matrix: # Link time optimization - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' - - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - llvm-7 + #- env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' # GCC for the x86-64 architecture with restricted limb sizes # formerly started with the option "--with-low-mp" to testme.sh From 91d88ce3dbbab05fc4115d2e572619a5afa4df43 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 5 Nov 2019 20:35:19 +0100 Subject: [PATCH 123/304] fix generate_def, rename some internal files --- helper.pl | 2 +- libtommath_VS2008.vcproj | 16 ++++++++-------- makefile | 20 ++++++++++---------- makefile.mingw | 20 ++++++++++---------- makefile.msvc | 20 ++++++++++---------- makefile.shared | 20 ++++++++++---------- makefile.unix | 20 ++++++++++---------- mp_fread.c | 4 ++-- mp_prime_strong_lucas_selfridge.c | 4 ++-- mp_read_radix.c | 4 ++-- mp_to_radix.c | 6 +++--- s_mp_div_recursive.c | 10 +++++----- mp_prime_tab.c => s_mp_prime_tab.c | 2 +- mp_radix_smap.c => s_mp_radix_map.c | 8 ++++---- tommath.def | 2 -- tommath_class.h | 19 ++++++++----------- tommath_private.h | 6 +++--- tommath_superclass.h | 5 ++--- 18 files changed, 91 insertions(+), 97 deletions(-) rename mp_prime_tab.c => s_mp_prime_tab.c (98%) rename mp_radix_smap.c => s_mp_radix_map.c (75%) diff --git a/helper.pl b/helper.pl index 93ca40aee..fb5413cdc 100755 --- a/helper.pl +++ b/helper.pl @@ -425,7 +425,7 @@ sub generate_def { my @files = split /\n/, `git ls-files`; @files = grep(/\.c/, @files); @files = map { my $x = $_; $x =~ s/^bn_|\.c$//g; $x; } @files; - @files = grep(!/mp_radix_smap/, @files); + @files = grep(!/mp_cutoffs/, @files); my $files = join("\n ", sort(grep(/^mp_/, @files))); write_file "tommath.def", "; libtommath diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 07c784bf9..215ab4a09 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -656,18 +656,10 @@ RelativePath="mp_prime_strong_lucas_selfridge.c" > - - - - @@ -912,6 +904,14 @@ RelativePath="s_mp_prime_is_divisible.c" > + + + + diff --git a/makefile b/makefile index 404539084..a976574f5 100644 --- a/makefile +++ b/makefile @@ -38,16 +38,16 @@ mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o m mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o mp_rand.o \ -mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o \ -mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o \ -mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o \ -mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o \ -mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o \ -s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ +mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ +mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.mingw b/makefile.mingw index c597143fc..73199df4e 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -41,16 +41,16 @@ mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o m mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o mp_rand.o \ -mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o \ -mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o \ -mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o \ -mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o \ -mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o \ -s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ +mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ +mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.msvc b/makefile.msvc index 0670b2b1c..7681252a4 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -33,16 +33,16 @@ mp_log_u32.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj mp_montgomery_calc_normaliza mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj \ mp_pack_count.obj mp_prime_fermat.obj mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj \ mp_prime_miller_rabin.obj mp_prime_next_prime.obj mp_prime_rabin_miller_trials.obj mp_prime_rand.obj \ -mp_prime_strong_lucas_selfridge.obj mp_prime_tab.obj mp_radix_size.obj mp_radix_smap.obj mp_rand.obj \ -mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj \ -mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj mp_root_u32.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj \ -mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj \ -mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj mp_sqr.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj \ -mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj \ -s_mp_add.obj s_mp_copy_digs.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj \ -s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_d.obj s_mp_log_pow2.obj \ -s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj \ -s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_rand_jenkins.obj \ +mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj \ +mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj \ +mp_reduce_setup.obj mp_root_u32.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ +mp_set_l.obj mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj \ +mp_sqr.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ +mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_recursive.obj \ +s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj \ +s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_d.obj s_mp_log_pow2.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ +s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ +s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_rand_jenkins.obj \ s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj \ s_mp_zero_buf.obj s_mp_zero_digs.obj diff --git a/makefile.shared b/makefile.shared index 9dd34bb59..62a9343bf 100644 --- a/makefile.shared +++ b/makefile.shared @@ -35,16 +35,16 @@ mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o m mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o mp_rand.o \ -mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o \ -mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o \ -mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o \ -mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o \ -mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o \ -s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ +mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ +mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.unix b/makefile.unix index 33a382926..6d06cabde 100644 --- a/makefile.unix +++ b/makefile.unix @@ -42,16 +42,16 @@ mp_log_u32.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o m mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_prime_tab.o mp_radix_size.o mp_radix_smap.o mp_rand.o \ -mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o \ -mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o \ -mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o \ -mp_set_ull.o mp_shrink.o mp_signed_rsh.o mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o \ -mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o \ -s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_rand_jenkins.o \ +mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ +mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/mp_fread.c b/mp_fread.c index bd336ce54..f1b55d21e 100644 --- a/mp_fread.c +++ b/mp_fread.c @@ -36,11 +36,11 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) unsigned pos; ch = (radix <= 36) ? MP_TOUPPER(ch) : ch; pos = (unsigned)(ch - (int)'+'); - if (MP_RMAP_REVERSE_SIZE <= pos) { + if (MP_RADIX_MAP_REVERSE_SIZE <= pos) { break; } - y = s_mp_rmap_reverse[pos]; + y = s_mp_radix_map_reverse[pos]; if (y >= radix) { break; diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index 6262e0714..e4d06ebd1 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -13,7 +13,7 @@ * multiply bigint a with int d and put the result in c * Like mp_mul_d() but with a signed long as the small input */ -static mp_err s_mp_mul_si(const mp_int *a, int32_t d, mp_int *c) +static mp_err s_mul_si(const mp_int *a, int32_t d, mp_int *c) { mp_int t; mp_err err; @@ -204,7 +204,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) if ((err = mp_mul(&Uz, &V2mz, &T2z)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mul(&V2mz, &Vz, &T3z)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_mul(&U2mz, &Uz, &T4z)) != MP_OKAY) goto LBL_LS_ERR; - if ((err = s_mp_mul_si(&T4z, Ds, &T4z)) != MP_OKAY) goto LBL_LS_ERR; + if ((err = s_mul_si(&T4z, Ds, &T4z)) != MP_OKAY) goto LBL_LS_ERR; if ((err = mp_add(&T1z, &T2z, &Uz)) != MP_OKAY) goto LBL_LS_ERR; if (mp_isodd(&Uz)) { if ((err = mp_add(&Uz, a, &Uz)) != MP_OKAY) goto LBL_LS_ERR; diff --git a/mp_read_radix.c b/mp_read_radix.c index 500f2d9a3..9512fb866 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -34,10 +34,10 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) uint8_t y; char ch = (radix <= 36) ? (char)MP_TOUPPER((int)*str) : *str; unsigned pos = (unsigned)(ch - '+'); - if (MP_RMAP_REVERSE_SIZE <= pos) { + if (MP_RADIX_MAP_REVERSE_SIZE <= pos) { break; } - y = s_mp_rmap_reverse[pos]; + y = s_mp_radix_map_reverse[pos]; /* if the char was found in the map * and is less than the given radix add it diff --git a/mp_to_radix.c b/mp_to_radix.c index 8b7728d87..ebe3f4e35 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* reverse an array, used for radix code */ -static void s_mp_reverse(char *s, size_t len) +static void s_reverse(char *s, size_t len) { size_t ix = 0, iy = len - 1u; while (ix < iy) { @@ -71,13 +71,13 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i if ((err = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { goto LBL_ERR; } - *str++ = s_mp_rmap[d]; + *str++ = s_mp_radix_map[d]; ++digs; } /* reverse the digits of the string. In this case _s points * to the first digit [exluding the sign] of the number */ - s_mp_reverse(_s, digs); + s_reverse(_s, digs); /* append a NULL so the string is properly terminated */ *str = '\0'; diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index 2fbc31210..e2b27cde4 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -14,7 +14,7 @@ pages 19ff. in the above online document. */ -static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) +static mp_err s_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) { mp_err err; mp_int A1, A2, B1, B0, Q1, Q0, R1, R0, t; @@ -33,7 +33,7 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int /* (Q1, R1) = RecursiveDivRem(A / beta^(2k), B1) */ if ((err = mp_div_2d(a, 2*k * MP_DIGIT_BIT, &A1, &t)) != MP_OKAY) goto LBL_ERR; - if ((err = s_mp_recursion(&A1, &B1, &Q1, &R1)) != MP_OKAY) goto LBL_ERR; + if ((err = s_recursion(&A1, &B1, &Q1, &R1)) != MP_OKAY) goto LBL_ERR; /* A1 = (R1 * beta^(2k)) + (A % beta^(2k)) - (Q1 * B0 * beta^k) */ if ((err = mp_lshd(&R1, 2*k)) != MP_OKAY) goto LBL_ERR; @@ -51,7 +51,7 @@ static mp_err s_mp_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int /* (Q0, R0) = RecursiveDivRem(A1 / beta^(k), B1) */ if ((err = mp_div_2d(&A1, k * MP_DIGIT_BIT, &A1, &t)) != MP_OKAY) goto LBL_ERR; - if ((err = s_mp_recursion(&A1, &B1, &Q0, &R0)) != MP_OKAY) goto LBL_ERR; + if ((err = s_recursion(&A1, &B1, &Q0, &R0)) != MP_OKAY) goto LBL_ERR; /* A2 = (R0*beta^k) + (A1 % beta^k) - (Q0*B0) */ if ((err = mp_lshd(&R0, k)) != MP_OKAY) goto LBL_ERR; @@ -142,7 +142,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r /* (q, r) = RecursveDivRem(A / (beta^(m-n)), B) */ j = (m - n) * MP_DIGIT_BIT; if ((err = mp_div_2d(&A, j, &A_div, &A_mod)) != MP_OKAY) goto LBL_ERR; - if ((err = s_mp_recursion(&A_div, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; + if ((err = s_recursion(&A_div, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; /* Q = (Q*beta!(n)) + q */ if ((err = mp_mul_2d(&Q, n * MP_DIGIT_BIT, &Q)) != MP_OKAY) goto LBL_ERR; if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; @@ -153,7 +153,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r m = m - n; } /* (q, r) = RecursveDivRem(A, B) */ - if ((err = s_mp_recursion(&A, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; + if ((err = s_recursion(&A, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; /* Q = (Q * beta^m) + q, R = r */ if ((err = mp_mul_2d(&Q, m * MP_DIGIT_BIT, &Q)) != MP_OKAY) goto LBL_ERR; if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; diff --git a/mp_prime_tab.c b/s_mp_prime_tab.c similarity index 98% rename from mp_prime_tab.c rename to s_mp_prime_tab.c index 24b4016f4..87c07fd95 100644 --- a/mp_prime_tab.c +++ b/s_mp_prime_tab.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef MP_PRIME_TAB_C +#ifdef S_MP_PRIME_TAB_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ diff --git a/mp_radix_smap.c b/s_mp_radix_map.c similarity index 75% rename from mp_radix_smap.c rename to s_mp_radix_map.c index 73fd7cfbe..68e21f32e 100644 --- a/mp_radix_smap.c +++ b/s_mp_radix_map.c @@ -1,11 +1,11 @@ #include "tommath_private.h" -#ifdef MP_RADIX_SMAP_C +#ifdef S_MP_RADIX_MAP_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* chars used in radix conversions */ -const char s_mp_rmap[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; -const uint8_t s_mp_rmap_reverse[] = { +const char s_mp_radix_map[] = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; +const uint8_t s_mp_radix_map_reverse[] = { 0x3e, 0xff, 0xff, 0xff, 0x3f, 0x00, 0x01, 0x02, 0x03, 0x04, /* +,-./01234 */ 0x05, 0x06, 0x07, 0x08, 0x09, 0xff, 0xff, 0xff, 0xff, 0xff, /* 56789:;<=> */ 0xff, 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, /* ?@ABCDEFGH */ @@ -15,5 +15,5 @@ const uint8_t s_mp_rmap_reverse[] = { 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, /* ghijklmnop */ 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d /* qrstuvwxyz */ }; -MP_STATIC_ASSERT(correct_rmap_reverse_size, sizeof(s_mp_rmap_reverse) == MP_RMAP_REVERSE_SIZE) +MP_STATIC_ASSERT(correct_radix_map_reverse_size, sizeof(s_mp_radix_map_reverse) == MP_RADIX_MAP_REVERSE_SIZE) #endif diff --git a/tommath.def b/tommath.def index 4d81e343d..d2509e1f1 100644 --- a/tommath.def +++ b/tommath.def @@ -22,7 +22,6 @@ EXPORTS mp_complement mp_copy mp_count_bits - mp_cutoffs mp_div mp_div_2 mp_div_2d @@ -92,7 +91,6 @@ EXPORTS mp_prime_rabin_miller_trials mp_prime_rand mp_prime_strong_lucas_selfridge - mp_prime_tab mp_radix_size mp_rand mp_read_radix diff --git a/tommath_class.h b/tommath_class.h index 2a5380a32..0f95a9398 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -97,9 +97,7 @@ # define MP_PRIME_RABIN_MILLER_TRIALS_C # define MP_PRIME_RAND_C # define MP_PRIME_STRONG_LUCAS_SELFRIDGE_C -# define MP_PRIME_TAB_C # define MP_RADIX_SIZE_C -# define MP_RADIX_SMAP_C # define MP_RAND_C # define MP_READ_RADIX_C # define MP_REDUCE_C @@ -161,6 +159,8 @@ # define S_MP_MUL_KARATSUBA_C # define S_MP_MUL_TOOM_C # define S_MP_PRIME_IS_DIVISIBLE_C +# define S_MP_PRIME_TAB_C +# define S_MP_RADIX_MAP_C # define S_MP_RAND_JENKINS_C # define S_MP_RAND_PLATFORM_C # define S_MP_SQR_C @@ -714,19 +714,12 @@ # define MP_SUB_C # define MP_SUB_D_C # define S_MP_GET_BIT_C -# define S_MP_MUL_SI_C -#endif - -#if defined(MP_PRIME_TAB_C) #endif #if defined(MP_RADIX_SIZE_C) # define MP_LOG_U32_C #endif -#if defined(MP_RADIX_SMAP_C) -#endif - #if defined(MP_RAND_C) # define MP_GROW_C # define MP_RAND_SOURCE_C @@ -955,7 +948,6 @@ # define MP_CLEAR_C # define MP_DIV_D_C # define MP_INIT_COPY_C -# define S_MP_REVERSE_C #endif #if defined(MP_TO_SBIN_C) @@ -1012,7 +1004,6 @@ # define MP_SUB_D_C # define MP_ZERO_C # define S_MP_DIV_SCHOOL_C -# define S_MP_RECURSION_C #endif #if defined(S_MP_DIV_SCHOOL_C) @@ -1222,6 +1213,12 @@ # define MP_DIV_D_C #endif +#if defined(S_MP_PRIME_TAB_C) +#endif + +#if defined(S_MP_RADIX_MAP_C) +#endif + #if defined(S_MP_RAND_JENKINS_C) # define S_MP_RAND_JENKINS_INIT_C #endif diff --git a/tommath_private.h b/tommath_private.h index 90da26923..17bbb733a 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -193,9 +193,9 @@ MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); -#define MP_RMAP_REVERSE_SIZE 80u -extern MP_PRIVATE const char s_mp_rmap[]; -extern MP_PRIVATE const uint8_t s_mp_rmap_reverse[]; +#define MP_RADIX_MAP_REVERSE_SIZE 80u +extern MP_PRIVATE const char s_mp_radix_map[]; +extern MP_PRIVATE const uint8_t s_mp_radix_map_reverse[]; extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; /* number of primes */ diff --git a/tommath_superclass.h b/tommath_superclass.h index db927d6cc..1d1e0005d 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -59,13 +59,12 @@ # define MP_PRIME_IS_PRIME_C # define MP_PRIME_RABIN_MILLER_TRIALS_C # define MP_PRIME_RAND_C -# define MP_RADIX_SMAP_C # define MP_SET_INT_C # define MP_SHRINK_C # define MP_TO_UNSIGNED_BIN_C # define MP_UNSIGNED_BIN_SIZE_C -# define MP_PRIME_TAB_C -# define S_MP_REVERSE_C +# define S_MP_PRIME_TAB_C +# define S_MP_RADIX_MAP_C /* other modifiers */ From 61ebe7c047dc74297b55c1369c78cc08d73f67c0 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 7 Nov 2019 01:00:13 +0100 Subject: [PATCH 124/304] simplify mod functions --- mp_addmod.c | 16 +++------------- mp_mod.c | 22 +++------------------- mp_mulmod.c | 14 ++------------ mp_sqrmod.c | 16 +++------------- mp_submod.c | 14 ++------------ tommath_class.h | 11 ----------- 6 files changed, 13 insertions(+), 80 deletions(-) diff --git a/mp_addmod.c b/mp_addmod.c index beda87258..91e2087e5 100644 --- a/mp_addmod.c +++ b/mp_addmod.c @@ -6,20 +6,10 @@ /* d = a + b (mod c) */ mp_err mp_addmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d) { - mp_err err; - mp_int t; - - if ((err = mp_init(&t)) != MP_OKAY) { + mp_err err; + if ((err = mp_add(a, b, d)) != MP_OKAY) { return err; } - - if ((err = mp_add(a, b, &t)) != MP_OKAY) { - goto LBL_ERR; - } - err = mp_mod(&t, c, d); - -LBL_ERR: - mp_clear(&t); - return err; + return mp_mod(d, c, d); } #endif diff --git a/mp_mod.c b/mp_mod.c index 3eced35ce..beae13e72 100644 --- a/mp_mod.c +++ b/mp_mod.c @@ -6,26 +6,10 @@ /* c = a mod b, 0 <= c < b if b > 0, b < c <= 0 if b < 0 */ mp_err mp_mod(const mp_int *a, const mp_int *b, mp_int *c) { - mp_int t; - mp_err err; - - if ((err = mp_init_size(&t, b->used)) != MP_OKAY) { + mp_err err; + if ((err = mp_div(a, b, NULL, c)) != MP_OKAY) { return err; } - - if ((err = mp_div(a, b, NULL, &t)) != MP_OKAY) { - goto LBL_ERR; - } - - if (mp_iszero(&t) || (t.sign == b->sign)) { - err = MP_OKAY; - mp_exch(&t, c); - } else { - err = mp_add(b, &t, c); - } - -LBL_ERR: - mp_clear(&t); - return err; + return mp_iszero(c) || (c->sign == b->sign) ? MP_OKAY : mp_add(b, c, c); } #endif diff --git a/mp_mulmod.c b/mp_mulmod.c index 55b635b79..e158693b9 100644 --- a/mp_mulmod.c +++ b/mp_mulmod.c @@ -7,19 +7,9 @@ mp_err mp_mulmod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d) { mp_err err; - mp_int t; - - if ((err = mp_init_size(&t, c->used)) != MP_OKAY) { + if ((err = mp_mul(a, b, d)) != MP_OKAY) { return err; } - - if ((err = mp_mul(a, b, &t)) != MP_OKAY) { - goto LBL_ERR; - } - err = mp_mod(&t, c, d); - -LBL_ERR: - mp_clear(&t); - return err; + return mp_mod(d, c, d); } #endif diff --git a/mp_sqrmod.c b/mp_sqrmod.c index f1a92eff4..bce2af090 100644 --- a/mp_sqrmod.c +++ b/mp_sqrmod.c @@ -6,20 +6,10 @@ /* c = a * a (mod b) */ mp_err mp_sqrmod(const mp_int *a, const mp_int *b, mp_int *c) { - mp_err err; - mp_int t; - - if ((err = mp_init(&t)) != MP_OKAY) { + mp_err err; + if ((err = mp_sqr(a, c)) != MP_OKAY) { return err; } - - if ((err = mp_sqr(a, &t)) != MP_OKAY) { - goto LBL_ERR; - } - err = mp_mod(&t, b, c); - -LBL_ERR: - mp_clear(&t); - return err; + return mp_mod(c, b, c); } #endif diff --git a/mp_submod.c b/mp_submod.c index c5dc40155..6e4d4f712 100644 --- a/mp_submod.c +++ b/mp_submod.c @@ -7,19 +7,9 @@ mp_err mp_submod(const mp_int *a, const mp_int *b, const mp_int *c, mp_int *d) { mp_err err; - mp_int t; - - if ((err = mp_init(&t)) != MP_OKAY) { + if ((err = mp_sub(a, b, d)) != MP_OKAY) { return err; } - - if ((err = mp_sub(a, b, &t)) != MP_OKAY) { - goto LBL_ERR; - } - err = mp_mod(&t, c, d); - -LBL_ERR: - mp_clear(&t); - return err; + return mp_mod(d, c, d); } #endif diff --git a/tommath_class.h b/tommath_class.h index 0f95a9398..b11c57438 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -196,8 +196,6 @@ #if defined(MP_ADDMOD_C) # define MP_ADD_C -# define MP_CLEAR_C -# define MP_INIT_C # define MP_MOD_C #endif @@ -519,10 +517,7 @@ #if defined(MP_MOD_C) # define MP_ADD_C -# define MP_CLEAR_C # define MP_DIV_C -# define MP_EXCH_C -# define MP_INIT_SIZE_C #endif #if defined(MP_MOD_2D_C) @@ -580,8 +575,6 @@ #endif #if defined(MP_MULMOD_C) -# define MP_CLEAR_C -# define MP_INIT_SIZE_C # define MP_MOD_C # define MP_MUL_C #endif @@ -888,8 +881,6 @@ #endif #if defined(MP_SQRMOD_C) -# define MP_CLEAR_C -# define MP_INIT_C # define MP_MOD_C # define MP_SQR_C #endif @@ -938,8 +929,6 @@ #endif #if defined(MP_SUBMOD_C) -# define MP_CLEAR_C -# define MP_INIT_C # define MP_MOD_C # define MP_SUB_C #endif From 0fa802f24b1bbb5b164b64d07cd8a38ed825b5d3 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 16:49:59 +0100 Subject: [PATCH 125/304] make mp_sqr private (optimization of mp_mul) --- mp_mul.c | 40 ++++++++++++++++++++++++++++------------ mp_sqr.c | 28 ---------------------------- tommath.h | 2 +- 3 files changed, 29 insertions(+), 41 deletions(-) delete mode 100644 mp_sqr.c diff --git a/mp_mul.c b/mp_mul.c index 9a83687bf..b2dbf7d72 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -12,18 +12,34 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) digs = a->used + b->used + 1; mp_sign neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - if (MP_HAS(S_MP_MUL_BALANCE) && - /* Check sizes. The smaller one needs to be larger than the Karatsuba cut-off. - * The bigger one needs to be at least about one MP_MUL_KARATSUBA_CUTOFF bigger - * to make some sense, but it depends on architecture, OS, position of the - * stars... so YMMV. - * Using it to cut the input into slices small enough for s_mp_mul_comba - * was actually slower on the author's machine, but YMMV. - */ - (min >= MP_MUL_KARATSUBA_CUTOFF) && - ((max / 2) >= MP_MUL_KARATSUBA_CUTOFF) && - /* Not much effect was observed below a ratio of 1:2, but again: YMMV. */ - (max >= (2 * min))) { + if ((a == b) && + MP_HAS(S_MP_SQR_TOOM) && /* use Toom-Cook? */ + (a->used >= MP_SQR_TOOM_CUTOFF)) { + err = s_mp_sqr_toom(a, c); + } else if ((a == b) && + MP_HAS(S_MP_SQR_KARATSUBA) && /* Karatsuba? */ + (a->used >= MP_SQR_KARATSUBA_CUTOFF)) { + err = s_mp_sqr_karatsuba(a, c); + } else if ((a == b) && + MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ + (((a->used * 2) + 1) < MP_WARRAY) && + (a->used < (MP_MAX_COMBA / 2))) { + err = s_mp_sqr_comba(a, c); + } else if ((a == b) && + MP_HAS(S_MP_SQR)) { + err = s_mp_sqr(a, c); + } else if (MP_HAS(S_MP_MUL_BALANCE) && + /* Check sizes. The smaller one needs to be larger than the Karatsuba cut-off. + * The bigger one needs to be at least about one MP_MUL_KARATSUBA_CUTOFF bigger + * to make some sense, but it depends on architecture, OS, position of the + * stars... so YMMV. + * Using it to cut the input into slices small enough for s_mp_mul_comba + * was actually slower on the author's machine, but YMMV. + */ + (min >= MP_MUL_KARATSUBA_CUTOFF) && + ((max / 2) >= MP_MUL_KARATSUBA_CUTOFF) && + /* Not much effect was observed below a ratio of 1:2, but again: YMMV. */ + (max >= (2 * min))) { err = s_mp_mul_balance(a,b,c); } else if (MP_HAS(S_MP_MUL_TOOM) && (min >= MP_MUL_TOOM_CUTOFF)) { diff --git a/mp_sqr.c b/mp_sqr.c deleted file mode 100644 index 67a822416..000000000 --- a/mp_sqr.c +++ /dev/null @@ -1,28 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_SQR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -/* computes b = a*a */ -mp_err mp_sqr(const mp_int *a, mp_int *b) -{ - mp_err err; - if (MP_HAS(S_MP_SQR_TOOM) && /* use Toom-Cook? */ - (a->used >= MP_SQR_TOOM_CUTOFF)) { - err = s_mp_sqr_toom(a, b); - } else if (MP_HAS(S_MP_SQR_KARATSUBA) && /* Karatsuba? */ - (a->used >= MP_SQR_KARATSUBA_CUTOFF)) { - err = s_mp_sqr_karatsuba(a, b); - } else if (MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ - (((a->used * 2) + 1) < MP_WARRAY) && - (a->used < (MP_MAX_COMBA / 2))) { - err = s_mp_sqr_comba(a, b); - } else if (MP_HAS(S_MP_SQR)) { - err = s_mp_sqr(a, b); - } else { - err = MP_VAL; - } - b->sign = MP_ZPOS; - return err; -} -#endif diff --git a/tommath.h b/tommath.h index 68a1592c9..01a6d3405 100644 --- a/tommath.h +++ b/tommath.h @@ -366,7 +366,7 @@ mp_err mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* b = a*a */ -mp_err mp_sqr(const mp_int *a, mp_int *b) MP_WUR; +#define mp_sqr(a, b) mp_mul((a), (a), (b)) /* a/b => cb + d == a */ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) MP_WUR; From 4f00e75b8fc94889d72eb66d0431158a445c2635 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 16:51:51 +0100 Subject: [PATCH 126/304] make mp_div_3 private --- demo/test.c | 10 ++++----- doc/bn.tex | 8 ------- mp_div_d.c | 4 ++-- mp_div_3.c => s_mp_div_3.c | 4 ++-- s_mp_mul_toom.c | 2 +- tommath.h | 3 --- tommath_private.h | 43 +++++++++++++++++++------------------- tommath_superclass.h | 2 +- 8 files changed, 33 insertions(+), 43 deletions(-) rename mp_div_3.c => s_mp_div_3.c (94%) diff --git a/demo/test.c b/demo/test.c index f2f5800b3..3e432cf0e 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1241,14 +1241,14 @@ static int test_mp_reduce_2k(void) return EXIT_FAILURE; } -static int test_mp_div_3(void) +static int test_s_mp_div_3(void) { int cnt; mp_int a, b, c, d, e; DOR(mp_init_multi(&a, &b, &c, &d, &e, NULL)); - /* test mp_div_3 */ + /* test s_mp_div_3 */ mp_set(&d, 3u); for (cnt = 0; cnt < 10000;) { mp_digit r2; @@ -1259,10 +1259,10 @@ static int test_mp_div_3(void) } DO(mp_rand(&a, (abs(rand_int()) % 128) + 1)); DO(mp_div(&a, &d, &b, &e)); - DO(mp_div_3(&a, &c, &r2)); + DO(s_mp_div_3(&a, &c, &r2)); if (mp_cmp(&b, &c) || mp_cmp_d(&e, r2)) { - printf("\nmp_div_3 => Failure\n"); + printf("\ns_mp_div_3 => Failure\n"); goto LBL_ERR; } } @@ -2297,7 +2297,7 @@ static int unit_tests(int argc, char **argv) T1(mp_cnt_lsb, MP_CNT_LSB), T1(mp_complement, MP_COMPLEMENT), T1(mp_decr, MP_SUB_D), - T1(mp_div_3, MP_DIV_3), + T1(s_mp_div_3, S_MP_DIV_3), T1(mp_dr_reduce, MP_DR_REDUCE), T2(mp_pack_unpack,MP_PACK, MP_UNPACK), T2(mp_fread_fwrite, MP_FREAD, MP_FWRITE), diff --git a/doc/bn.tex b/doc/bn.tex index b8a6404b7..620441401 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2605,14 +2605,6 @@ \section{Single Digit Functions} mp_err mp_decr(mp_int *a); \end{alltt} -The division by three can be made faster by replacing the division with a multiplication by the -multiplicative inverse of three. - -\index{mp\_div\_3} -\begin{alltt} -mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d); -\end{alltt} - \chapter{Little Helpers} It is never wrong to have some useful little shortcuts at hand. \section{Function Macros} diff --git a/mp_div_d.c b/mp_div_d.c index 472ab2796..fc0a5f256 100644 --- a/mp_div_d.c +++ b/mp_div_d.c @@ -43,8 +43,8 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) } /* three? */ - if (MP_HAS(MP_DIV_3) && (b == 3u)) { - return mp_div_3(a, c, d); + if (MP_HAS(S_MP_DIV_3) && (b == 3u)) { + return s_mp_div_3(a, c, d); } /* no easy answer [c'est la vie]. Just division */ diff --git a/mp_div_3.c b/s_mp_div_3.c similarity index 94% rename from mp_div_3.c rename to s_mp_div_3.c index c26692cb2..1cc6d3d8c 100644 --- a/mp_div_3.c +++ b/s_mp_div_3.c @@ -1,10 +1,10 @@ #include "tommath_private.h" -#ifdef MP_DIV_3_C +#ifdef S_MP_DIV_3_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* divide by three (based on routine from MPI and the GMP manual) */ -mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) +mp_err s_mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) { mp_int q; mp_word w; diff --git a/s_mp_mul_toom.c b/s_mp_mul_toom.c index 1ed03c83a..f6c2b103a 100644 --- a/s_mp_mul_toom.c +++ b/s_mp_mul_toom.c @@ -133,7 +133,7 @@ mp_err s_mp_mul_toom(const mp_int *a, const mp_int *b, mp_int *c) if ((err = mp_sub(&S2, &a1, &S2)) != MP_OKAY) goto LBL_ERR; /** S2 = S2 / 3; \\ this is an exact division */ - if ((err = mp_div_3(&S2, &S2, NULL)) != MP_OKAY) goto LBL_ERR; + if ((err = s_mp_div_3(&S2, &S2, NULL)) != MP_OKAY) goto LBL_ERR; /** a1 = S1 - a1; */ if ((err = mp_sub(&S1, &a1, &a1)) != MP_OKAY) goto LBL_ERR; diff --git a/tommath.h b/tommath.h index 01a6d3405..5e75c98b5 100644 --- a/tommath.h +++ b/tommath.h @@ -300,9 +300,6 @@ mp_err mp_div_2d(const mp_int *a, int b, mp_int *c, mp_int *d) MP_WUR; /* b = a/2 */ mp_err mp_div_2(const mp_int *a, mp_int *b) MP_WUR; -/* a/3 => 3c + d == a */ -mp_err mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) MP_WUR; - /* c = a * 2**b, implemented as c = a << b */ mp_err mp_mul_2d(const mp_int *a, int b, mp_int *c) MP_WUR; diff --git a/tommath_private.h b/tommath_private.h index 17bbb733a..f8af53191 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -158,36 +158,37 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); /* lowlevel functions, do not call! */ -MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b); +MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b) MP_WUR; +MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n) MP_WUR; MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) MP_WUR; +MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) MP_WUR; +MP_PRIVATE mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) MP_WUR; +MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) MP_WUR; +MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; +MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; +MP_PRIVATE mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) MP_WUR; +MP_PRIVATE mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; MP_PRIVATE mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; -MP_PRIVATE mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) MP_WUR; -MP_PRIVATE mp_err s_mp_sqr(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_mul_balance(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; +MP_PRIVATE mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; MP_PRIVATE mp_err s_mp_mul_karatsuba(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_mul_toom(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result) MP_WUR; +MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; +MP_PRIVATE mp_err s_mp_sqr(const mp_int *a, mp_int *b) MP_WUR; +MP_PRIVATE mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sqr_karatsuba(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sqr_toom(const mp_int *a, mp_int *b) MP_WUR; -MP_PRIVATE mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; -MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; -MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; -MP_PRIVATE mp_err s_mp_rand_platform(void *p, size_t n) MP_WUR; -MP_PRIVATE mp_err s_mp_prime_is_divisible(const mp_int *a, bool *result); -MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n); -MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c); -MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base); -MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r); -MP_PRIVATE mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); -MP_PRIVATE mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d); +MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base) MP_WUR; +MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); -MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); /* TODO: jenkins prng is not thread safe as of now */ MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; diff --git a/tommath_superclass.h b/tommath_superclass.h index 1d1e0005d..dd83cad92 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -75,7 +75,6 @@ * like removing support for even moduli, etc... */ # ifdef LTM_LAST -# undef MP_DIV_3_C # undef MP_DR_IS_MODULUS_C # undef MP_DR_REDUCE_C # undef MP_DR_SETUP_C @@ -83,6 +82,7 @@ # undef MP_REDUCE_2K_SETUP_C # undef MP_REDUCE_IS_2K_C # undef MP_REDUCE_SETUP_C +# undef S_MP_DIV_3_C # undef S_MP_EXPTMOD_C # undef S_MP_INVMOD_ODD_C # undef S_MP_MUL_BALANCE_C From 6ec36e0b9b24806740e962b3000f657070dead87 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 16:54:07 +0100 Subject: [PATCH 127/304] optimize mp_div_d --- mp_div_d.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/mp_div_d.c b/mp_div_d.c index fc0a5f256..ab8572f42 100644 --- a/mp_div_d.c +++ b/mp_div_d.c @@ -28,7 +28,13 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) } /* power of two ? */ - if ((b & (b - 1u)) == 0u) { + if (MP_HAS(MP_DIV_2) && (b == 2u)) { + if (d != NULL) { + *d = mp_isodd(a) ? 1u : 0u; + } + return (c == NULL) ? MP_OKAY : mp_div_2(a, c); + } + if (MP_HAS(MP_DIV_2D) && (b != 0u) && ((b & (b - 1u)) == 0u)) { ix = 1; while ((ix < MP_DIGIT_BIT) && (b != (((mp_digit)1)<dp[0] & (((mp_digit)1<<(mp_digit)ix) - 1uL); } - if (c != NULL) { - return mp_div_2d(a, ix, c, NULL); - } - return MP_OKAY; + return (c == NULL) ? MP_OKAY : mp_div_2d(a, ix, c, NULL); } /* three? */ From 2e88b571c1911290bfb0c69826f780d8353bad3a Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 16:56:34 +0100 Subject: [PATCH 128/304] optimize mp_mul_d --- mp_mul_d.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/mp_mul_d.c b/mp_mul_d.c index 30d6c9340..c10312a50 100644 --- a/mp_mul_d.c +++ b/mp_mul_d.c @@ -10,6 +10,22 @@ mp_err mp_mul_d(const mp_int *a, mp_digit b, mp_int *c) mp_err err; int ix, oldused; + if (b == 1u) { + return mp_copy(a, c); + } + + /* power of two ? */ + if (MP_HAS(MP_MUL_2) && (b == 2u)) { + return mp_mul_2(a, c); + } + if (MP_HAS(MP_MUL_2D) && (b != 0u) && ((b & (b - 1u)) == 0u)) { + ix = 1; + while ((ix < MP_DIGIT_BIT) && (b != (((mp_digit)1)<used + 1)) != MP_OKAY) { return err; From 6777baaf97c6737bded86c8b7c17c7d280e20057 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 16:59:51 +0100 Subject: [PATCH 129/304] add macro MP_IS_2EXPT --- mp_div_d.c | 2 +- mp_log_u32.c | 2 +- mp_mul_d.c | 2 +- tommath_private.h | 2 ++ 4 files changed, 5 insertions(+), 3 deletions(-) diff --git a/mp_div_d.c b/mp_div_d.c index ab8572f42..5697e545c 100644 --- a/mp_div_d.c +++ b/mp_div_d.c @@ -34,7 +34,7 @@ mp_err mp_div_d(const mp_int *a, mp_digit b, mp_int *c, mp_digit *d) } return (c == NULL) ? MP_OKAY : mp_div_2(a, c); } - if (MP_HAS(MP_DIV_2D) && (b != 0u) && ((b & (b - 1u)) == 0u)) { + if (MP_HAS(MP_DIV_2D) && MP_IS_2EXPT(b)) { ix = 1; while ((ix < MP_DIGIT_BIT) && (b != (((mp_digit)1)< Date: Wed, 6 Nov 2019 16:50:31 +0100 Subject: [PATCH 130/304] regen files --- libtommath_VS2008.vcproj | 12 ++++------ makefile | 12 +++++----- makefile.mingw | 12 +++++----- makefile.msvc | 12 +++++----- makefile.shared | 12 +++++----- makefile.unix | 12 +++++----- tommath.def | 2 -- tommath_class.h | 48 ++++++++++++++++++---------------------- 8 files changed, 55 insertions(+), 67 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 215ab4a09..7e16199e8 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -392,10 +392,6 @@ RelativePath="mp_div_2d.c" > - - @@ -760,10 +756,6 @@ RelativePath="mp_signed_rsh.c" > - - @@ -824,6 +816,10 @@ RelativePath="s_mp_copy_digs.c" > + + diff --git a/makefile b/makefile index a9633f808..88eff7921 100644 --- a/makefile +++ b/makefile @@ -28,7 +28,7 @@ LCOV_ARGS=--directory . #START_INS OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ @@ -42,11 +42,11 @@ mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_r mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ -s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o \ +s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.mingw b/makefile.mingw index 55da599d0..3a3bc631f 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -30,7 +30,7 @@ LIBMAIN_D =libtommath.dll #List of objects to compile (all goes to libtommath.a) OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ @@ -44,11 +44,11 @@ mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_r mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ -s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o \ +s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.msvc b/makefile.msvc index 7681252a4..a22267c4a 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -23,7 +23,7 @@ LIBMAIN_S =tommath.lib #List of objects to compile (all goes to tommath.lib) OBJECTS=mp_2expt.obj mp_abs.obj mp_add.obj mp_add_d.obj mp_addmod.obj mp_and.obj mp_clamp.obj mp_clear.obj mp_clear_multi.obj \ mp_cmp.obj mp_cmp_d.obj mp_cmp_mag.obj mp_cnt_lsb.obj mp_complement.obj mp_copy.obj mp_count_bits.obj mp_cutoffs.obj \ -mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_3.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj mp_dr_setup.obj \ +mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj mp_dr_setup.obj \ mp_error_to_string.obj mp_exch.obj mp_expt_u32.obj mp_exptmod.obj mp_exteuclid.obj mp_fread.obj mp_from_sbin.obj \ mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj mp_get_ll.obj \ mp_get_mag_u32.obj mp_get_mag_u64.obj mp_get_mag_ul.obj mp_get_mag_ull.obj mp_grow.obj mp_init.obj mp_init_copy.obj \ @@ -37,11 +37,11 @@ mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj mp_rand.obj mp_read_radix. mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj \ mp_reduce_setup.obj mp_root_u32.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ mp_set_l.obj mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj \ -mp_sqr.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ -mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_recursive.obj \ -s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj \ -s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_d.obj s_mp_log_pow2.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ -s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ +mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ +mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj \ +s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj \ +s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_d.obj s_mp_log_pow2.obj s_mp_montgomery_reduce_comba.obj \ +s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_rand_jenkins.obj \ s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj \ s_mp_zero_buf.obj s_mp_zero_digs.obj diff --git a/makefile.shared b/makefile.shared index 62a9343bf..ad58e61fe 100644 --- a/makefile.shared +++ b/makefile.shared @@ -25,7 +25,7 @@ LCOV_ARGS=--directory .libs --directory . #START_INS OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ @@ -39,11 +39,11 @@ mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_r mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ -s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o \ +s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/makefile.unix b/makefile.unix index 859eed4bd..1e0da7393 100644 --- a/makefile.unix +++ b/makefile.unix @@ -31,7 +31,7 @@ LIBMAIN_S = libtommath.a OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_clear.o mp_clear_multi.o \ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ -mp_div.o mp_div_2.o mp_div_2d.o mp_div_3.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ +mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_u32.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ @@ -45,11 +45,11 @@ mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_r mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ mp_reduce_setup.o mp_root_u32.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqr.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ -s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ +mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ +s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_d.o s_mp_log_pow2.o s_mp_montgomery_reduce_comba.o \ +s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ s_mp_zero_buf.o s_mp_zero_digs.o diff --git a/tommath.def b/tommath.def index d2509e1f1..8bc6eacfa 100644 --- a/tommath.def +++ b/tommath.def @@ -25,7 +25,6 @@ EXPORTS mp_div mp_div_2 mp_div_2d - mp_div_3 mp_div_d mp_dr_is_modulus mp_dr_reduce @@ -117,7 +116,6 @@ EXPORTS mp_set_ull mp_shrink mp_signed_rsh - mp_sqr mp_sqrmod mp_sqrt mp_sqrtmod_prime diff --git a/tommath_class.h b/tommath_class.h index b11c57438..f5f99074c 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -31,7 +31,6 @@ # define MP_DIV_C # define MP_DIV_2_C # define MP_DIV_2D_C -# define MP_DIV_3_C # define MP_DIV_D_C # define MP_DR_IS_MODULUS_C # define MP_DR_REDUCE_C @@ -123,7 +122,6 @@ # define MP_SET_ULL_C # define MP_SHRINK_C # define MP_SIGNED_RSH_C -# define MP_SQR_C # define MP_SQRMOD_C # define MP_SQRT_C # define MP_SQRTMOD_PRIME_C @@ -139,6 +137,7 @@ # define MP_ZERO_C # define S_MP_ADD_C # define S_MP_COPY_DIGS_C +# define S_MP_DIV_3_C # define S_MP_DIV_RECURSIVE_C # define S_MP_DIV_SCHOOL_C # define S_MP_DIV_SMALL_C @@ -266,21 +265,15 @@ # define MP_RSHD_C #endif -#if defined(MP_DIV_3_C) -# define MP_CLAMP_C -# define MP_CLEAR_C -# define MP_EXCH_C -# define MP_INIT_SIZE_C -#endif - #if defined(MP_DIV_D_C) # define MP_CLAMP_C # define MP_CLEAR_C # define MP_COPY_C # define MP_DIV_2D_C -# define MP_DIV_3_C +# define MP_DIV_2_C # define MP_EXCH_C # define MP_INIT_SIZE_C +# define S_MP_DIV_3_C #endif #if defined(MP_DR_IS_MODULUS_C) @@ -308,7 +301,6 @@ # define MP_INIT_COPY_C # define MP_MUL_C # define MP_SET_C -# define MP_SQR_C #endif #if defined(MP_EXPTMOD_C) @@ -480,8 +472,8 @@ # define MP_GET_I32_C # define MP_INIT_U32_C # define MP_MOD_C +# define MP_MUL_C # define MP_SQRT_C -# define MP_SQR_C #endif #if defined(MP_KRONECKER_C) @@ -554,6 +546,10 @@ # define S_MP_MUL_COMBA_C # define S_MP_MUL_KARATSUBA_C # define S_MP_MUL_TOOM_C +# define S_MP_SQR_C +# define S_MP_SQR_COMBA_C +# define S_MP_SQR_KARATSUBA_C +# define S_MP_SQR_TOOM_C #endif #if defined(MP_MUL_2_C) @@ -570,7 +566,10 @@ #if defined(MP_MUL_D_C) # define MP_CLAMP_C +# define MP_COPY_C # define MP_GROW_C +# define MP_MUL_2D_C +# define MP_MUL_2_C # define S_MP_ZERO_DIGS_C #endif @@ -703,7 +702,6 @@ # define MP_SET_C # define MP_SET_I32_C # define MP_SET_U32_C -# define MP_SQR_C # define MP_SUB_C # define MP_SUB_D_C # define S_MP_GET_BIT_C @@ -873,16 +871,9 @@ # define MP_SUB_D_C #endif -#if defined(MP_SQR_C) -# define S_MP_SQR_C -# define S_MP_SQR_COMBA_C -# define S_MP_SQR_KARATSUBA_C -# define S_MP_SQR_TOOM_C -#endif - #if defined(MP_SQRMOD_C) # define MP_MOD_C -# define MP_SQR_C +# define MP_MUL_C #endif #if defined(MP_SQRT_C) @@ -978,6 +969,13 @@ #if defined(S_MP_COPY_DIGS_C) #endif +#if defined(S_MP_DIV_3_C) +# define MP_CLAMP_C +# define MP_CLEAR_C +# define MP_EXCH_C +# define MP_INIT_SIZE_C +#endif + #if defined(S_MP_DIV_RECURSIVE_C) # define MP_ADD_C # define MP_CLEAR_MULTI_C @@ -1043,7 +1041,6 @@ # define MP_REDUCE_C # define MP_REDUCE_SETUP_C # define MP_SET_C -# define MP_SQR_C #endif #if defined(S_MP_EXPTMOD_FAST_C) @@ -1063,7 +1060,6 @@ # define MP_REDUCE_2K_C # define MP_REDUCE_2K_SETUP_C # define MP_SET_C -# define MP_SQR_C # define S_MP_MONTGOMERY_REDUCE_COMBA_C #endif @@ -1110,7 +1106,6 @@ # define MP_INIT_MULTI_C # define MP_MUL_C # define MP_SET_C -# define MP_SQR_C #endif #if defined(S_MP_LOG_D_C) @@ -1188,7 +1183,6 @@ # define MP_CLEAR_C # define MP_CLEAR_MULTI_C # define MP_DIV_2_C -# define MP_DIV_3_C # define MP_INIT_MULTI_C # define MP_INIT_SIZE_C # define MP_LSHD_C @@ -1196,6 +1190,7 @@ # define MP_MUL_C # define MP_SUB_C # define S_MP_COPY_DIGS_C +# define S_MP_DIV_3_C #endif #if defined(S_MP_PRIME_IS_DIVISIBLE_C) @@ -1234,7 +1229,7 @@ # define MP_CLEAR_C # define MP_INIT_SIZE_C # define MP_LSHD_C -# define MP_SQR_C +# define MP_MUL_C # define S_MP_ADD_C # define S_MP_COPY_DIGS_C # define S_MP_SUB_C @@ -1250,7 +1245,6 @@ # define MP_LSHD_C # define MP_MUL_2_C # define MP_MUL_C -# define MP_SQR_C # define MP_SUB_C # define S_MP_COPY_DIGS_C #endif From 1cc289d2151620de7559960e6b1e5f9ac8a9f84b Mon Sep 17 00:00:00 2001 From: nijtmans Date: Sat, 9 Nov 2019 20:23:03 +0100 Subject: [PATCH 131/304] better use of mp_isneg() and mp_iszero() --- etc/mersenne.c | 2 +- mp_add_d.c | 8 ++++---- mp_and.c | 10 +++++----- mp_clamp.c | 4 ++-- mp_cmp.c | 4 ++-- mp_cmp_d.c | 2 +- mp_exptmod.c | 4 ++-- mp_exteuclid.c | 2 +- mp_fread.c | 6 +++--- mp_from_sbin.c | 2 +- mp_get_double.c | 2 +- mp_invmod.c | 2 +- mp_is_square.c | 2 +- mp_kronecker.c | 6 +++--- mp_log_u32.c | 10 +--------- mp_mul.c | 4 ++-- mp_neg.c | 2 +- mp_or.c | 10 +++++----- mp_prime_strong_lucas_selfridge.c | 4 ++-- mp_radix_size.c | 2 +- mp_read_radix.c | 6 +++--- mp_reduce_is_2k.c | 2 +- mp_reduce_is_2k_l.c | 2 +- mp_root_u32.c | 2 +- mp_signed_rsh.c | 2 +- mp_sqrt.c | 2 +- mp_sub.c | 2 +- mp_sub_d.c | 2 +- mp_to_radix.c | 4 ++-- mp_to_sbin.c | 2 +- mp_xor.c | 10 +++++----- mtest/mpi.c | 14 +++++++------- s_mp_div_recursive.c | 8 ++++---- s_mp_div_school.c | 16 ++++++++-------- s_mp_div_small.c | 8 ++++---- s_mp_invmod_odd.c | 8 ++++---- s_mp_log_d.c | 4 ++-- s_mp_rand_jenkins.c | 6 +++--- tommath_private.h | 2 +- 39 files changed, 91 insertions(+), 99 deletions(-) diff --git a/etc/mersenne.c b/etc/mersenne.c index 54b2360cc..4d3939e35 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -43,7 +43,7 @@ static mp_err is_mersenne(long s, bool *pp) } /* make sure u is positive */ - while (u.sign == MP_NEG) { + while (mp_isneg(&u)) { if ((res = mp_add(&u, &n, &u)) != MP_OKAY) { goto LBL_MU; } diff --git a/mp_add_d.c b/mp_add_d.c index de935bbe2..c57a80db3 100644 --- a/mp_add_d.c +++ b/mp_add_d.c @@ -11,13 +11,13 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) /* fast path for a == c */ if (a == c) { - if ((c->sign == MP_ZPOS) && + if (!mp_isneg(c) && !mp_iszero(c) && ((c->dp[0] + b) < MP_DIGIT_MAX)) { c->dp[0] += b; return MP_OKAY; } - if ((c->sign == MP_NEG) && + if (mp_isneg(c) && (c->dp[0] > b)) { c->dp[0] -= b; return MP_OKAY; @@ -30,7 +30,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) } /* if a is negative and |a| >= b, call c = |a| - b */ - if ((a->sign == MP_NEG) && ((a->used > 1) || (a->dp[0] >= b))) { + if (mp_isneg(a) && ((a->used > 1) || (a->dp[0] >= b))) { mp_int a_ = *a; /* temporarily fix sign of a */ a_.sign = MP_ZPOS; @@ -51,7 +51,7 @@ mp_err mp_add_d(const mp_int *a, mp_digit b, mp_int *c) oldused = c->used; /* if a is positive */ - if (a->sign == MP_ZPOS) { + if (!mp_isneg(a)) { /* add digits, mu is carry */ int i; mp_digit mu = b; diff --git a/mp_and.c b/mp_and.c index a865ae074..b5230c4d1 100644 --- a/mp_and.c +++ b/mp_and.c @@ -9,7 +9,7 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) int used = MP_MAX(a->used, b->used) + 1, i; mp_err err; mp_digit ac = 1, bc = 1, cc = 1; - mp_sign csign = ((a->sign == MP_NEG) && (b->sign == MP_NEG)) ? MP_NEG : MP_ZPOS; + bool neg = (mp_isneg(a) && mp_isneg(b)); if ((err = mp_grow(c, used)) != MP_OKAY) { return err; @@ -19,7 +19,7 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) mp_digit x, y; /* convert to two complement if negative */ - if (a->sign == MP_NEG) { + if (mp_isneg(a)) { ac += (i >= a->used) ? MP_MASK : (~a->dp[i] & MP_MASK); x = ac & MP_MASK; ac >>= MP_DIGIT_BIT; @@ -28,7 +28,7 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) } /* convert to two complement if negative */ - if (b->sign == MP_NEG) { + if (mp_isneg(b)) { bc += (i >= b->used) ? MP_MASK : (~b->dp[i] & MP_MASK); y = bc & MP_MASK; bc >>= MP_DIGIT_BIT; @@ -39,7 +39,7 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) c->dp[i] = x & y; /* convert to to sign-magnitude if negative */ - if (csign == MP_NEG) { + if (neg) { cc += ~c->dp[i] & MP_MASK; c->dp[i] = cc & MP_MASK; cc >>= MP_DIGIT_BIT; @@ -47,7 +47,7 @@ mp_err mp_and(const mp_int *a, const mp_int *b, mp_int *c) } c->used = used; - c->sign = csign; + c->sign = (neg ? MP_NEG : MP_ZPOS); mp_clamp(c); return MP_OKAY; } diff --git a/mp_clamp.c b/mp_clamp.c index 14c18148c..ae59c4016 100644 --- a/mp_clamp.c +++ b/mp_clamp.c @@ -19,8 +19,8 @@ void mp_clamp(mp_int *a) --(a->used); } - /* reset the sign flag if used == 0 */ - if (a->used == 0) { + /* reset the sign flag if zero */ + if (mp_iszero(a)) { a->sign = MP_ZPOS; } } diff --git a/mp_cmp.c b/mp_cmp.c index b9c45920b..9f3847b84 100644 --- a/mp_cmp.c +++ b/mp_cmp.c @@ -8,11 +8,11 @@ mp_ord mp_cmp(const mp_int *a, const mp_int *b) { /* compare based on sign */ if (a->sign != b->sign) { - return a->sign == MP_NEG ? MP_LT : MP_GT; + return mp_isneg(a) ? MP_LT : MP_GT; } /* if negative compare opposite direction */ - if (a->sign == MP_NEG) { + if (mp_isneg(a)) { MP_EXCH(const mp_int *, a, b); } diff --git a/mp_cmp_d.c b/mp_cmp_d.c index 0d98e05a0..42f7b1600 100644 --- a/mp_cmp_d.c +++ b/mp_cmp_d.c @@ -7,7 +7,7 @@ mp_ord mp_cmp_d(const mp_int *a, mp_digit b) { /* compare based on sign */ - if (a->sign == MP_NEG) { + if (mp_isneg(a)) { return MP_LT; } diff --git a/mp_exptmod.c b/mp_exptmod.c index b917c0bb8..b8a5dccc2 100644 --- a/mp_exptmod.c +++ b/mp_exptmod.c @@ -13,12 +13,12 @@ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) int dr; /* modulus P must be positive */ - if (P->sign == MP_NEG) { + if (mp_isneg(P)) { return MP_VAL; } /* if exponent X is negative we have to recurse */ - if (X->sign == MP_NEG) { + if (mp_isneg(X)) { mp_int tmpG, tmpX; mp_err err; diff --git a/mp_exteuclid.c b/mp_exteuclid.c index 0d0bfd339..649c4ca85 100644 --- a/mp_exteuclid.c +++ b/mp_exteuclid.c @@ -48,7 +48,7 @@ mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp } /* make sure U3 >= 0 */ - if (u3.sign == MP_NEG) { + if (mp_isneg(&u3)) { if ((err = mp_neg(&u1, &u1)) != MP_OKAY) goto LBL_ERR; if ((err = mp_neg(&u2, &u2)) != MP_OKAY) goto LBL_ERR; if ((err = mp_neg(&u3, &u3)) != MP_OKAY) goto LBL_ERR; diff --git a/mp_fread.c b/mp_fread.c index f1b55d21e..53c35e822 100644 --- a/mp_fread.c +++ b/mp_fread.c @@ -8,7 +8,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) { mp_err err; - mp_sign neg = MP_ZPOS; + mp_sign sign = MP_ZPOS; int ch; /* make sure the radix is ok */ @@ -19,7 +19,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) /* if first digit is - then set negative */ ch = fgetc(stream); if (ch == (int)'-') { - neg = MP_NEG; + sign = MP_NEG; ch = fgetc(stream); } @@ -56,7 +56,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) } while ((ch = fgetc(stream)) != EOF); if (!mp_iszero(a)) { - a->sign = neg; + a->sign = sign; } return MP_OKAY; diff --git a/mp_from_sbin.c b/mp_from_sbin.c index 3ff7d5d8f..26eb0f120 100644 --- a/mp_from_sbin.c +++ b/mp_from_sbin.c @@ -14,7 +14,7 @@ mp_err mp_from_sbin(mp_int *a, const uint8_t *buf, size_t size) } /* first byte is 0 for positive, non-zero for negative */ - a->sign = (buf[0] == (uint8_t)0) ? MP_ZPOS : MP_NEG; + a->sign = (buf[0] != (uint8_t)0) ? MP_NEG : MP_ZPOS; return MP_OKAY; } diff --git a/mp_get_double.c b/mp_get_double.c index 122b71b03..f462eb8e0 100644 --- a/mp_get_double.c +++ b/mp_get_double.c @@ -13,6 +13,6 @@ double mp_get_double(const mp_int *a) for (i = a->used; i --> 0;) { d = (d * fac) + (double)a->dp[i]; } - return (a->sign == MP_NEG) ? -d : d; + return mp_isneg(a) ? -d : d; } #endif diff --git a/mp_invmod.c b/mp_invmod.c index 94929ccbe..e19c067e2 100644 --- a/mp_invmod.c +++ b/mp_invmod.c @@ -7,7 +7,7 @@ mp_err mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) { /* b cannot be negative and has to be >1 */ - if ((b->sign == MP_NEG) || (mp_cmp_d(b, 1uL) != MP_GT)) { + if (mp_isneg(b) || (mp_cmp_d(b, 1uL) != MP_GT)) { return MP_VAL; } diff --git a/mp_is_square.c b/mp_is_square.c index 47f830015..db1cb3fb3 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -36,7 +36,7 @@ mp_err mp_is_square(const mp_int *arg, bool *ret) /* Default to Non-square :) */ *ret = false; - if (arg->sign == MP_NEG) { + if (mp_isneg(arg)) { return MP_VAL; } diff --git a/mp_kronecker.c b/mp_kronecker.c index b106f7731..e6bedc891 100644 --- a/mp_kronecker.c +++ b/mp_kronecker.c @@ -57,9 +57,9 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) k = table[a->dp[0] & 7u]; } - if (p1.sign == MP_NEG) { + if (mp_isneg(&p1)) { p1.sign = MP_ZPOS; - if (a1.sign == MP_NEG) { + if (mp_isneg(&a1)) { k = -k; } } @@ -88,7 +88,7 @@ mp_err mp_kronecker(const mp_int *a, const mp_int *p, int *c) k = k * table[p1.dp[0] & 7u]; } - if (a1.sign == MP_NEG) { + if (mp_isneg(&a1)) { /* * Compute k = (-1)^((a1)*(p1-1)/4) * k * a1.dp[0] + 1 cannot overflow because the MSB diff --git a/mp_log_u32.c b/mp_log_u32.c index 949ef87b2..1450d3ab3 100644 --- a/mp_log_u32.c +++ b/mp_log_u32.c @@ -5,15 +5,7 @@ mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) { - if (a->sign == MP_NEG) { - return MP_VAL; - } - - if (mp_iszero(a)) { - return MP_VAL; - } - - if (base < 2u) { + if (mp_isneg(a) || mp_iszero(a) || (base < 2u)) { return MP_VAL; } diff --git a/mp_mul.c b/mp_mul.c index b2dbf7d72..d35fa8ef4 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -10,7 +10,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) int min = MP_MIN(a->used, b->used), max = MP_MAX(a->used, b->used), digs = a->used + b->used + 1; - mp_sign neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + bool neg = (a->sign != b->sign); if ((a == b) && MP_HAS(S_MP_SQR_TOOM) && /* use Toom-Cook? */ @@ -62,7 +62,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) } else { err = MP_VAL; } - c->sign = (c->used > 0) ? neg : MP_ZPOS; + c->sign = ((c->used > 0) && neg) ? MP_NEG : MP_ZPOS; return err; } #endif diff --git a/mp_neg.c b/mp_neg.c index bfb6eb98e..b445cd409 100644 --- a/mp_neg.c +++ b/mp_neg.c @@ -11,7 +11,7 @@ mp_err mp_neg(const mp_int *a, mp_int *b) return err; } - b->sign = mp_iszero(b) || b->sign == MP_NEG ? MP_ZPOS : MP_NEG; + b->sign = ((!mp_iszero(b) && !mp_isneg(b)) ? MP_NEG : MP_ZPOS); return MP_OKAY; } diff --git a/mp_or.c b/mp_or.c index 5cf525509..15958524e 100644 --- a/mp_or.c +++ b/mp_or.c @@ -9,7 +9,7 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) int used = MP_MAX(a->used, b->used) + 1, i; mp_err err; mp_digit ac = 1, bc = 1, cc = 1; - mp_sign csign = ((a->sign == MP_NEG) || (b->sign == MP_NEG)) ? MP_NEG : MP_ZPOS; + bool neg = (mp_isneg(a) || mp_isneg(b)); if ((err = mp_grow(c, used)) != MP_OKAY) { return err; @@ -19,7 +19,7 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) mp_digit x, y; /* convert to two complement if negative */ - if (a->sign == MP_NEG) { + if (mp_isneg(a)) { ac += (i >= a->used) ? MP_MASK : (~a->dp[i] & MP_MASK); x = ac & MP_MASK; ac >>= MP_DIGIT_BIT; @@ -28,7 +28,7 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) } /* convert to two complement if negative */ - if (b->sign == MP_NEG) { + if (mp_isneg(b)) { bc += (i >= b->used) ? MP_MASK : (~b->dp[i] & MP_MASK); y = bc & MP_MASK; bc >>= MP_DIGIT_BIT; @@ -39,7 +39,7 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) c->dp[i] = x | y; /* convert to to sign-magnitude if negative */ - if (csign == MP_NEG) { + if (neg) { cc += ~c->dp[i] & MP_MASK; c->dp[i] = cc & MP_MASK; cc >>= MP_DIGIT_BIT; @@ -47,7 +47,7 @@ mp_err mp_or(const mp_int *a, const mp_int *b, mp_int *c) } c->used = used; - c->sign = csign; + c->sign = (neg ? MP_NEG : MP_ZPOS); mp_clamp(c); return MP_OKAY; } diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index e4d06ebd1..ffbd9d34f 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -216,7 +216,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) */ oddness = mp_isodd(&Uz); if ((err = mp_div_2(&Uz, &Uz)) != MP_OKAY) goto LBL_LS_ERR; - if ((Uz.sign == MP_NEG) && oddness) { + if (mp_isneg(&Uz) && oddness) { if ((err = mp_sub_d(&Uz, 1uL, &Uz)) != MP_OKAY) goto LBL_LS_ERR; } if ((err = mp_add(&T3z, &T4z, &Vz)) != MP_OKAY) goto LBL_LS_ERR; @@ -225,7 +225,7 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) } oddness = mp_isodd(&Vz); if ((err = mp_div_2(&Vz, &Vz)) != MP_OKAY) goto LBL_LS_ERR; - if ((Vz.sign == MP_NEG) && oddness) { + if (mp_isneg(&Vz) && oddness) { if ((err = mp_sub_d(&Vz, 1uL, &Vz)) != MP_OKAY) goto LBL_LS_ERR; } if ((err = mp_mod(&Uz, a, &Uz)) != MP_OKAY) goto LBL_LS_ERR; diff --git a/mp_radix_size.c b/mp_radix_size.c index 47f2f68c3..7f7cbc2e2 100644 --- a/mp_radix_size.c +++ b/mp_radix_size.c @@ -27,7 +27,7 @@ mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) } /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ - *size = (size_t)b + 2U + ((a->sign == MP_NEG) ? 1U : 0U); + *size = (size_t)b + 2U + (mp_isneg(a) ? 1U : 0U); LBL_ERR: return err; diff --git a/mp_read_radix.c b/mp_read_radix.c index 9512fb866..28e6eb60a 100644 --- a/mp_read_radix.c +++ b/mp_read_radix.c @@ -7,7 +7,7 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) { mp_err err; - mp_sign neg = MP_ZPOS; + mp_sign sign = MP_ZPOS; /* make sure the radix is ok */ if ((radix < 2) || (radix > 64)) { @@ -19,7 +19,7 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) */ if (*str == '-') { ++str; - neg = MP_NEG; + sign = MP_NEG; } /* set the integer to the default of zero */ @@ -62,7 +62,7 @@ mp_err mp_read_radix(mp_int *a, const char *str, int radix) /* set the sign only if a != 0 */ if (!mp_iszero(a)) { - a->sign = neg; + a->sign = sign; } return MP_OKAY; } diff --git a/mp_reduce_is_2k.c b/mp_reduce_is_2k.c index a5798e62f..9774f96e9 100644 --- a/mp_reduce_is_2k.c +++ b/mp_reduce_is_2k.c @@ -6,7 +6,7 @@ /* determines if mp_reduce_2k can be used */ bool mp_reduce_is_2k(const mp_int *a) { - if (a->used == 0) { + if (mp_iszero(a)) { return false; } else if (a->used == 1) { return true; diff --git a/mp_reduce_is_2k_l.c b/mp_reduce_is_2k_l.c index dca2d7e01..101b4a185 100644 --- a/mp_reduce_is_2k_l.c +++ b/mp_reduce_is_2k_l.c @@ -6,7 +6,7 @@ /* determines if reduce_2k_l can be used */ bool mp_reduce_is_2k_l(const mp_int *a) { - if (a->used == 0) { + if (mp_iszero(a)) { return false; } else if (a->used == 1) { return true; diff --git a/mp_root_u32.c b/mp_root_u32.c index f6827493c..1f972d905 100644 --- a/mp_root_u32.c +++ b/mp_root_u32.c @@ -20,7 +20,7 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) mp_err err; /* input must be positive if b is even */ - if (((b & 1u) == 0u) && (a->sign == MP_NEG)) { + if (((b & 1u) == 0u) && mp_isneg(a)) { return MP_VAL; } diff --git a/mp_signed_rsh.c b/mp_signed_rsh.c index ecaaa2192..3b7e232e5 100644 --- a/mp_signed_rsh.c +++ b/mp_signed_rsh.c @@ -7,7 +7,7 @@ mp_err mp_signed_rsh(const mp_int *a, int b, mp_int *c) { mp_err err; - if (a->sign == MP_ZPOS) { + if (!mp_isneg(a)) { return mp_div_2d(a, b, c, NULL); } diff --git a/mp_sqrt.c b/mp_sqrt.c index e36a81a9c..1a9dca7da 100644 --- a/mp_sqrt.c +++ b/mp_sqrt.c @@ -10,7 +10,7 @@ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) mp_int t1, t2; /* must be positive */ - if (arg->sign == MP_NEG) { + if (mp_isneg(arg)) { return MP_VAL; } diff --git a/mp_sub.c b/mp_sub.c index 810474045..1c95ad544 100644 --- a/mp_sub.c +++ b/mp_sub.c @@ -23,7 +23,7 @@ mp_err mp_sub(const mp_int *a, const mp_int *b, mp_int *c) /* The second has a larger magnitude */ /* The result has the *opposite* sign from */ /* the first number. */ - c->sign = (a->sign == MP_ZPOS) ? MP_NEG : MP_ZPOS; + c->sign = (!mp_isneg(a) ? MP_NEG : MP_ZPOS); MP_EXCH(const mp_int *, a, b); } else { /* The first has a larger or equal magnitude */ diff --git a/mp_sub_d.c b/mp_sub_d.c index e80df3df8..b2b4d723d 100644 --- a/mp_sub_d.c +++ b/mp_sub_d.c @@ -46,7 +46,7 @@ mp_err mp_sub_d(const mp_int *a, mp_digit b, mp_int *c) oldused = c->used; /* if a <= b simply fix the single digit */ - if (((a->used == 1) && (a->dp[0] <= b)) || (a->used == 0)) { + if (((a->used == 1) && (a->dp[0] <= b)) || mp_iszero(a)) { c->dp[0] = (a->used == 1) ? b - a->dp[0] : b; /* negative/1digit */ diff --git a/mp_to_radix.c b/mp_to_radix.c index ebe3f4e35..abf85c067 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -50,7 +50,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i } /* if it is negative output a - */ - if (t.sign == MP_NEG) { + if (mp_isneg(&t)) { /* we have to reverse our digits later... but not the - sign!! */ ++_s; @@ -84,7 +84,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i digs++; if (written != NULL) { - *written = (a->sign == MP_NEG) ? (digs + 1u): digs; + *written = mp_isneg(a) ? (digs + 1u): digs; } LBL_ERR: diff --git a/mp_to_sbin.c b/mp_to_sbin.c index 8225d1306..00884c3be 100644 --- a/mp_to_sbin.c +++ b/mp_to_sbin.c @@ -16,7 +16,7 @@ mp_err mp_to_sbin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) if (written != NULL) { (*written)++; } - buf[0] = (a->sign == MP_ZPOS) ? (uint8_t)0 : (uint8_t)1; + buf[0] = mp_isneg(a) ? (uint8_t)1 : (uint8_t)0; return MP_OKAY; } #endif diff --git a/mp_xor.c b/mp_xor.c index 2fe8618fd..ff264192c 100644 --- a/mp_xor.c +++ b/mp_xor.c @@ -9,7 +9,7 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) int used = MP_MAX(a->used, b->used) + 1, i; mp_err err; mp_digit ac = 1, bc = 1, cc = 1; - mp_sign csign = (a->sign != b->sign) ? MP_NEG : MP_ZPOS; + bool neg = (a->sign != b->sign); if ((err = mp_grow(c, used)) != MP_OKAY) { return err; @@ -19,7 +19,7 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) mp_digit x, y; /* convert to two complement if negative */ - if (a->sign == MP_NEG) { + if (mp_isneg(a)) { ac += (i >= a->used) ? MP_MASK : (~a->dp[i] & MP_MASK); x = ac & MP_MASK; ac >>= MP_DIGIT_BIT; @@ -28,7 +28,7 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) } /* convert to two complement if negative */ - if (b->sign == MP_NEG) { + if (mp_isneg(b)) { bc += (i >= b->used) ? MP_MASK : (~b->dp[i] & MP_MASK); y = bc & MP_MASK; bc >>= MP_DIGIT_BIT; @@ -39,7 +39,7 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) c->dp[i] = x ^ y; /* convert to to sign-magnitude if negative */ - if (csign == MP_NEG) { + if (neg) { cc += ~c->dp[i] & MP_MASK; c->dp[i] = cc & MP_MASK; cc >>= MP_DIGIT_BIT; @@ -47,7 +47,7 @@ mp_err mp_xor(const mp_int *a, const mp_int *b, mp_int *c) } c->used = used; - c->sign = csign; + c->sign = (neg ? MP_NEG : MP_ZPOS); mp_clamp(c); return MP_OKAY; } diff --git a/mtest/mpi.c b/mtest/mpi.c index 7e71ad609..faf09d8df 100644 --- a/mtest/mpi.c +++ b/mtest/mpi.c @@ -846,7 +846,7 @@ mp_err mp_neg(mp_int *a, mp_int *b) if(s_mp_cmp_d(b, 0) == MP_EQ) SIGN(b) = MP_ZPOS; else - SIGN(b) = (SIGN(b) == MP_NEG) ? MP_ZPOS : MP_NEG; + SIGN(b) = (SIGN(b) != MP_NEG) ? MP_NEG : MP_ZPOS; return MP_OKAY; @@ -1055,7 +1055,7 @@ mp_err mp_mul(mp_int *a, mp_int *b, mp_int *c) ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG); - sgn = (SIGN(a) == SIGN(b)) ? MP_ZPOS : MP_NEG; + sgn = (SIGN(a) != SIGN(b)) ? MP_NEG : MP_ZPOS; if(c == b) { if((res = s_mp_mul(c, a)) != MP_OKAY) @@ -1069,7 +1069,7 @@ mp_err mp_mul(mp_int *a, mp_int *b, mp_int *c) return res; } - if(sgn == MP_ZPOS || s_mp_cmp_d(c, 0) == MP_EQ) + if(sgn != MP_NEG || s_mp_cmp_d(c, 0) == MP_EQ) SIGN(c) = MP_ZPOS; else SIGN(c) = sgn; @@ -1821,12 +1821,12 @@ int mp_cmp(mp_int *a, mp_int *b) if((mag = s_mp_cmp(a, b)) == MP_EQ) return MP_EQ; - if(SIGN(a) == MP_ZPOS) + if(SIGN(a) != MP_NEG) return mag; else return -mag; - } else if(SIGN(a) == MP_ZPOS) { + } else if(SIGN(a) != MP_NEG) { return MP_GT; } else { return MP_LT; @@ -1957,7 +1957,7 @@ mp_err mp_gcd(mp_int *a, mp_int *b, mp_int *c) goto CLEANUP; /* t = -v */ - if(SIGN(&v) == MP_ZPOS) + if(SIGN(&v) != MP_NEG) SIGN(&t) = MP_NEG; else SIGN(&t) = MP_ZPOS; @@ -1982,7 +1982,7 @@ mp_err mp_gcd(mp_int *a, mp_int *b, mp_int *c) goto CLEANUP; /* v = -t */ - if(SIGN(&t) == MP_ZPOS) + if(SIGN(&t) != MP_NEG) SIGN(&v) = MP_NEG; else SIGN(&v) = MP_ZPOS; diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index e2b27cde4..5491f225c 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -83,7 +83,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r { int j, m, n, sigma; mp_err err; - mp_sign neg; + bool neg; mp_digit msb_b, msb; mp_int A, B, Q, Q1, R, A_div, A_mod; @@ -126,7 +126,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r } /* fix the sign */ - neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + neg = (a->sign != b->sign); A.sign = B.sign = MP_ZPOS; /* @@ -159,11 +159,11 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; /* get sign before writing to c */ - Q.sign = (Q.used == 0) ? MP_ZPOS : a->sign; + Q.sign = (mp_iszero(&Q) ? MP_ZPOS : a->sign); if (q != NULL) { mp_exch(&Q, q); - q->sign = neg; + q->sign = (neg ? MP_NEG : MP_ZPOS); } if (r != NULL) { /* de-normalize the remainder */ diff --git a/s_mp_div_school.c b/s_mp_div_school.c index cf34cc97b..b6a615d10 100644 --- a/s_mp_div_school.c +++ b/s_mp_div_school.c @@ -18,10 +18,10 @@ */ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) { - mp_int q, x, y, t1, t2; - int n, t, i, norm; - mp_sign neg; - mp_err err; + mp_int q, x, y, t1, t2; + int n, t, i, norm; + bool neg; + mp_err err; if ((err = mp_init_size(&q, a->used + 2)) != MP_OKAY) { return err; @@ -34,7 +34,7 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) if ((err = mp_init_copy(&y, b)) != MP_OKAY) goto LBL_X; /* fix the sign */ - neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + neg = (a->sign != b->sign); x.sign = y.sign = MP_ZPOS; /* normalize both x and y, ensure that y >= b/2, [b == 2**MP_DIGIT_BIT] */ @@ -113,7 +113,7 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) if ((err = mp_sub(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; /* if x < 0 then { x = x + y*b**{i-t-1}; q{i-t-1} -= 1; } */ - if (x.sign == MP_NEG) { + if (mp_isneg(&x)) { if ((err = mp_copy(&y, &t1)) != MP_OKAY) goto LBL_Y; if ((err = mp_lshd(&t1, (i - t) - 1)) != MP_OKAY) goto LBL_Y; if ((err = mp_add(&x, &t1, &x)) != MP_OKAY) goto LBL_Y; @@ -127,12 +127,12 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) */ /* get sign before writing to c */ - x.sign = (x.used == 0) ? MP_ZPOS : a->sign; + x.sign = mp_iszero(&x) ? MP_ZPOS : a->sign; if (c != NULL) { mp_clamp(&q); mp_exch(&q, c); - c->sign = neg; + c->sign = (neg ? MP_NEG : MP_ZPOS); } if (d != NULL) { diff --git a/s_mp_div_small.c b/s_mp_div_small.c index c89023af3..2d951be1c 100644 --- a/s_mp_div_small.c +++ b/s_mp_div_small.c @@ -8,7 +8,7 @@ mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) { mp_int ta, tb, tq, q; int n; - mp_sign sign; + bool neg; mp_err err; /* init our temps */ @@ -34,14 +34,14 @@ mp_err s_mp_div_small(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) /* now q == quotient and ta == remainder */ - sign = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; + neg = (a->sign != b->sign); if (c != NULL) { mp_exch(c, &q); - c->sign = mp_iszero(c) ? MP_ZPOS : sign; + c->sign = ((neg && !mp_iszero(c)) ? MP_NEG : MP_ZPOS); } if (d != NULL) { mp_exch(d, &ta); - d->sign = mp_iszero(d) ? MP_ZPOS : a->sign; + d->sign = (mp_iszero(d) ? MP_ZPOS : a->sign); } LBL_ERR: mp_clear_multi(&ta, &tb, &tq, &q, NULL); diff --git a/s_mp_invmod_odd.c b/s_mp_invmod_odd.c index 8b55d5b7d..e12dfa17f 100644 --- a/s_mp_invmod_odd.c +++ b/s_mp_invmod_odd.c @@ -12,7 +12,7 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x, y, u, v, B, D; - mp_sign neg; + mp_sign sign; mp_err err; /* 2. [modified] b must be odd */ @@ -95,8 +95,8 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) } /* b is now the inverse */ - neg = a->sign; - while (D.sign == MP_NEG) { + sign = a->sign; + while (mp_isneg(&D)) { if ((err = mp_add(&D, b, &D)) != MP_OKAY) goto LBL_ERR; } @@ -106,7 +106,7 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) } mp_exch(&D, c); - c->sign = neg; + c->sign = sign; err = MP_OKAY; LBL_ERR: diff --git a/s_mp_log_d.c b/s_mp_log_d.c index 44edd0755..c9c8df218 100644 --- a/s_mp_log_d.c +++ b/s_mp_log_d.c @@ -5,7 +5,7 @@ static mp_word s_pow(mp_word base, mp_word exponent) { - mp_word result = 1uLL; + mp_word result = 1u; while (exponent != 0u) { if ((exponent & 1u) == 1u) { result *= base; @@ -19,7 +19,7 @@ static mp_word s_pow(mp_word base, mp_word exponent) mp_digit s_mp_log_d(mp_digit base, mp_digit n) { - mp_word bracket_low = 1uLL, bracket_mid, bracket_high, N; + mp_word bracket_low = 1u, bracket_mid, bracket_high, N; mp_digit ret, high = 1uL, low = 0uL, mid; if (n < base) { diff --git a/s_mp_rand_jenkins.c b/s_mp_rand_jenkins.c index cbbe0668b..3a905ba4a 100644 --- a/s_mp_rand_jenkins.c +++ b/s_mp_rand_jenkins.c @@ -27,10 +27,10 @@ static uint64_t s_rand_jenkins_val(void) void s_mp_rand_jenkins_init(uint64_t seed) { - uint64_t i; - jenkins_x.a = 0xf1ea5eedULL; + int i; + jenkins_x.a = 0xF1EA5EEDuLL; jenkins_x.b = jenkins_x.c = jenkins_x.d = seed; - for (i = 0uLL; i < 20uLL; ++i) { + for (i = 0; i < 20; ++i) { (void)s_rand_jenkins_val(); } } diff --git a/tommath_private.h b/tommath_private.h index f6295020f..938865f8d 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -261,7 +261,7 @@ extern MP_PRIVATE const mp_digit s_mp_prime_tab[]; type name(const mp_int* a) \ { \ utype res = mag(a); \ - return (a->sign == MP_NEG) ? (type)-res : (type)res; \ + return mp_isneg(a) ? (type)-res : (type)res; \ } #endif From c47d5e87b23c7520050fce09f3faa23e5e466f69 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 12 Nov 2019 01:11:12 +0100 Subject: [PATCH 132/304] s_mp_rand_platform: add comment regarding MP_HAS requiring dead code elim --- doc/bn.tex | 5 +++++ s_mp_rand_platform.c | 19 +++++++++++++++++++ 2 files changed, 24 insertions(+) diff --git a/doc/bn.tex b/doc/bn.tex index 620441401..64a07ff7a 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -298,6 +298,11 @@ \subsection{Build Depends} includes itself twice). This is to help resolve as many dependencies as possible. In the last pass the symbol \texttt{LTM\_LAST} will be defined. This is useful for ``trims''. +Note that the configuration system relies +on dead code elimination. Unfortunately this can result in linking errors on compilers which +perform insufficient dead code elimination. In particular MSVC with the /Od option enabled shows this issue. +The issue can be resolved by passing the /O option instead to the compiler. + \subsection{Build Trims} A trim is a manner of removing functionality from a function that is not required. For instance, to perform RSA cryptography you only require exponentiation with odd moduli so even moduli support diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 06e92abc1..06b2f1bda 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -117,6 +117,25 @@ mp_err s_read_wincsp(void *p, size_t n); mp_err s_read_getrandom(void *p, size_t n); mp_err s_read_urandom(void *p, size_t n); +/* + * Note: libtommath relies on dead code elimination + * for the configuration system, i.e., the MP_HAS macro. + * + * If you observe linking errors in this functions, + * your compiler does not perform the dead code compilation + * such that the unused functions are still referenced. + * + * This happens for example for MSVC if the /Od compilation + * option is given. The option /Od instructs MSVC to + * not perform any "optimizations", not even removal of + * dead code wrapped in `if (0)` blocks. + * + * If you still insist on compiling with /Od, simply + * comment out the lines which result in linking errors. + * + * We intentionally don't fix this issue in order + * to have a single point of failure for misconfigured compilers. + */ mp_err s_mp_rand_platform(void *p, size_t n) { mp_err err = MP_ERR; From f6a7bedb95f0b0840454fbd7df1c738292017413 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Tue, 29 Oct 2019 20:52:29 +0100 Subject: [PATCH 133/304] suffix _u32 -> _n of mp_(expt|log|root) functions, use int for now --- demo/test.c | 62 ++++++++++++++++++------------------ doc/bn.tex | 26 +++++++-------- mp_expt_u32.c => mp_expt_n.c | 13 +++----- mp_log_n.c | 29 +++++++++++++++++ mp_log_u32.c | 29 ----------------- mp_radix_size.c | 9 +++--- mp_root_u32.c => mp_root_n.c | 28 ++++++++-------- s_mp_log.c | 17 +++++----- s_mp_log_2expt.c | 12 +++++++ s_mp_log_d.c | 19 +++++------ s_mp_log_pow2.c | 12 ------- tommath.h | 14 ++++---- tommath_private.h | 6 ++-- tommath_superclass.h | 4 +-- 14 files changed, 135 insertions(+), 145 deletions(-) rename mp_expt_u32.c => mp_expt_n.c (80%) create mode 100644 mp_log_n.c delete mode 100644 mp_log_u32.c rename mp_root_u32.c => mp_root_n.c (84%) create mode 100644 s_mp_log_2expt.c delete mode 100644 s_mp_log_pow2.c diff --git a/demo/test.c b/demo/test.c index 3e432cf0e..f15350925 100644 --- a/demo/test.c +++ b/demo/test.c @@ -729,7 +729,7 @@ static int test_mp_sqrt(void) printf("\nmp_sqrt() error!"); goto LBL_ERR; } - DO(mp_root_u32(&a, 2u, &c)); + DO(mp_root_n(&a, 2u, &c)); if (mp_cmp_mag(&b, &c) != MP_EQ) { printf("mp_sqrt() bad result!\n"); goto LBL_ERR; @@ -1396,10 +1396,10 @@ static int test_mp_reduce_2k_l(void) /* stripped down version of mp_radix_size. The faster version can be off by up t o +3 */ /* TODO: This function should be removed, replaced by mp_radix_size, mp_radix_size_overestimate in 2.0 */ -static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) +static mp_err s_rs(const mp_int *a, int radix, int *size) { mp_err res; - uint32_t digs = 0u; + int digs = 0u; mp_int t; mp_digit d; *size = 0u; @@ -1408,7 +1408,7 @@ static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) return MP_OKAY; } if (radix == 2) { - *size = (uint32_t)mp_count_bits(a) + 1u; + *size = mp_count_bits(a) + 1; return MP_OKAY; } DOR(mp_init_copy(&t, a)); @@ -1424,12 +1424,12 @@ static mp_err s_rs(const mp_int *a, int radix, uint32_t *size) *size = digs + 1; return MP_OKAY; } -static int test_mp_log_u32(void) +static int test_mp_log_n(void) { mp_int a; mp_digit d; - uint32_t base, lb, size; - const uint32_t max_base = MP_MIN(UINT32_MAX, MP_DIGIT_MAX); + int base, lb, size; + const int max_base = MP_MIN(INT_MAX, MP_DIGIT_MAX); DOR(mp_init(&a)); @@ -1440,11 +1440,11 @@ static int test_mp_log_u32(void) */ mp_set(&a, 42u); base = 0u; - if (mp_log_u32(&a, base, &lb) != MP_VAL) { + if (mp_log_n(&a, base, &lb) != MP_VAL) { goto LBL_ERR; } base = 1u; - if (mp_log_u32(&a, base, &lb) != MP_VAL) { + if (mp_log_n(&a, base, &lb) != MP_VAL) { goto LBL_ERR; } /* @@ -1456,14 +1456,14 @@ static int test_mp_log_u32(void) */ base = 2u; mp_zero(&a); - if (mp_log_u32(&a, base, &lb) != MP_VAL) { + if (mp_log_n(&a, base, &lb) != MP_VAL) { goto LBL_ERR; } for (d = 1; d < 4; d++) { mp_set(&a, d); - DO(mp_log_u32(&a, base, &lb)); - if (lb != ((d == 1)?0uL:1uL)) { + DO(mp_log_n(&a, base, &lb)); + if (lb != ((d == 1)?0:1)) { goto LBL_ERR; } } @@ -1476,13 +1476,13 @@ static int test_mp_log_u32(void) */ base = 3u; mp_zero(&a); - if (mp_log_u32(&a, base, &lb) != MP_VAL) { + if (mp_log_n(&a, base, &lb) != MP_VAL) { goto LBL_ERR; } for (d = 1; d < 4; d++) { mp_set(&a, d); - DO(mp_log_u32(&a, base, &lb)); - if (lb != ((d < base)?0uL:1uL)) { + DO(mp_log_n(&a, base, &lb)); + if (lb != (((int)d < base)?0:1)) { goto LBL_ERR; } } @@ -1493,8 +1493,8 @@ static int test_mp_log_u32(void) radix_size. */ DO(mp_rand(&a, 10)); - for (base = 2u; base < 65u; base++) { - DO(mp_log_u32(&a, base, &lb)); + for (base = 2; base < 65; base++) { + DO(mp_log_n(&a, base, &lb)); DO(s_rs(&a,(int)base, &size)); /* radix_size includes the memory needed for '\0', too*/ size -= 2; @@ -1508,8 +1508,8 @@ static int test_mp_log_u32(void) test the part of mp_ilogb that uses native types. */ DO(mp_rand(&a, 1)); - for (base = 2u; base < 65u; base++) { - DO(mp_log_u32(&a, base, &lb)); + for (base = 2; base < 65; base++) { + DO(mp_log_n(&a, base, &lb)); DO(s_rs(&a,(int)base, &size)); size -= 2; if (lb != size) { @@ -1519,9 +1519,9 @@ static int test_mp_log_u32(void) /*Test upper edgecase with base UINT32_MAX and number (UINT32_MAX/2)*UINT32_MAX^10 */ mp_set(&a, max_base); - DO(mp_expt_u32(&a, 10u, &a)); - DO(mp_add_d(&a, max_base / 2u, &a)); - DO(mp_log_u32(&a, max_base, &lb)); + DO(mp_expt_n(&a, 10uL, &a)); + DO(mp_add_d(&a, max_base / 2, &a)); + DO(mp_log_n(&a, max_base, &lb)); if (lb != 10u) { goto LBL_ERR; } @@ -1636,7 +1636,7 @@ static int test_mp_decr(void) } /* - Cannot test mp_exp(_d) without mp_root and vice versa. + Cannot test mp_exp(_d) without mp_root_n and vice versa. So one of the two has to be tested from scratch. Numbers generated by @@ -1658,7 +1658,7 @@ static int test_mp_decr(void) low-mp branch. */ -static int test_mp_root_u32(void) +static int test_mp_root_n(void) { mp_int a, c, r; int i, j; @@ -1850,10 +1850,10 @@ static int test_mp_root_u32(void) for (i = 0; i < 10; i++) { DO(mp_read_radix(&a, input[i], 64)); for (j = 3; j < 100; j++) { - DO(mp_root_u32(&a, (uint32_t)j, &c)); + DO(mp_root_n(&a, j, &c)); DO(mp_read_radix(&r, root[i][j-3], 10)); if (mp_cmp(&r, &c) != MP_EQ) { - fprintf(stderr, "mp_root_u32 failed at input #%d, root #%d\n", i, j); + fprintf(stderr, "mp_root_n failed at input #%d, root #%d\n", i, j); goto LBL_ERR; } } @@ -2037,8 +2037,8 @@ static int test_mp_radix_size(void) DOR(mp_init(&a)); /* number to result in a different size for every base: 67^(4 * 67) */ - mp_set(&a, 67u); - DO(mp_expt_u32(&a, 268u, &a)); + mp_set(&a, 67); + DO(mp_expt_n(&a, 268, &a)); for (radix = 2; radix < 65; radix++) { DO(mp_radix_size(&a, radix, &size)); @@ -2304,13 +2304,13 @@ static int unit_tests(int argc, char **argv) T1(mp_get_u32, MP_GET_I32), T1(mp_get_u64, MP_GET_I64), T1(mp_get_ul, MP_GET_L), - T1(mp_log_u32, MP_LOG_U32), + T1(mp_log_n, MP_LOG_N), T1(mp_incr, MP_ADD_D), T1(mp_invmod, MP_INVMOD), T1(mp_is_square, MP_IS_SQUARE), T1(mp_kronecker, MP_KRONECKER), T1(mp_montgomery_reduce, MP_MONTGOMERY_REDUCE), - T1(mp_root_u32, MP_ROOT_U32), + T1(mp_root_n, MP_ROOT_N), T1(mp_or, MP_OR), T1(mp_prime_is_prime, MP_PRIME_IS_PRIME), T1(mp_prime_next_prime, MP_PRIME_NEXT_PRIME), @@ -2326,7 +2326,7 @@ static int unit_tests(int argc, char **argv) T1(mp_set_double, MP_SET_DOUBLE), #endif T1(mp_signed_rsh, MP_SIGNED_RSH), - T1(mp_sqrt, MP_SQRT), + T2(mp_sqrt, MP_SQRT, mp_root_n), T1(mp_sqrtmod_prime, MP_SQRTMOD_PRIME), T1(mp_xor, MP_XOR), T2(s_mp_div_recursive, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), diff --git a/doc/bn.tex b/doc/bn.tex index 64a07ff7a..1d6cf835a 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -1911,9 +1911,9 @@ \section{Combined Modular Reduction} \chapter{Exponentiation} \section{Single Digit Exponentiation} -\index{mp\_expt\_u32} +\index{mp\_expt\_n} \begin{alltt} -mp_err mp_expt_u32 (const mp_int *a, uint32_t b, mp_int *c) +mp_err mp_expt_n(const mp_int *a, int b, int *c) \end{alltt} This function computes $c = a^b$. @@ -1940,9 +1940,9 @@ \section{Modulus a Power of Two} It calculates $c = a \mod 2^b$. \section{Root Finding} -\index{mp\_root\_u32} +\index{mp\_root\_n} \begin{alltt} -mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) +mp_err mp_root_n(const mp_int *a, int b, mp_int *c) \end{alltt} This computes $c = a^{1/b}$ such that $c^b \le a$ and $(c+1)^b > a$. Will return a positive root only for even roots and return a root with the sign of the input for odd roots. For example, @@ -1964,9 +1964,9 @@ \section{Integer Logarithm} A logarithm function for positive integer input \texttt{a, base} computing $\floor{\log_bx}$ such that $(\log_b x)^b \le x$. -\index{mp\_log\_u32} +\index{mp\_log\_n} \begin{alltt} -mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) +mp_err mp_log_n(const mp_int *a, int base, int *c) \end{alltt} \subsection{Example} @@ -1981,7 +1981,7 @@ \subsection{Example} int main(int argc, char **argv) { mp_int x, output; - uint32_t base; + int base; mp_err e; if (argc != 3) { @@ -1994,12 +1994,8 @@ \subsection{Example} exit(EXIT_FAILURE); } errno = 0; -#ifdef MP_64BIT - /* Check for overflow skipped */ - base = (uint32_t)strtoull(argv[1], NULL, 10); -#else - base = (uint32_t)strtoul(argv[1], NULL, 10); -#endif + base = (int)strtoul(argv[1], NULL, 10); + if (errno == ERANGE) { fprintf(stderr,"strtoul(l) failed: input out of range\textbackslash{}n"); exit(EXIT_FAILURE); @@ -2009,8 +2005,8 @@ \subsection{Example} mp_error_to_string(e)); exit(EXIT_FAILURE); } - if ((e = mp_log_u32(&x, base, &output)) != MP_OKAY) { - fprintf(stderr,"mp_ilogb failed: \textbackslash{}"%s\textbackslash{}"\textbackslash{}n", + if ((e = mp_log_n(&x, base, &output)) != MP_OKAY) { + fprintf(stderr,"mp_log_n failed: \textbackslash{}"%s\textbackslash{}"\textbackslash{}n", mp_error_to_string(e)); exit(EXIT_FAILURE); } diff --git a/mp_expt_u32.c b/mp_expt_n.c similarity index 80% rename from mp_expt_u32.c rename to mp_expt_n.c index a580fbf0c..93f9249a7 100644 --- a/mp_expt_u32.c +++ b/mp_expt_n.c @@ -1,13 +1,12 @@ #include "tommath_private.h" -#ifdef MP_EXPT_U32_C +#ifdef MP_EXPT_N_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ /* calculate c = a**b using a square-multiply algorithm */ -mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) +mp_err mp_expt_n(const mp_int *a, int b, mp_int *c) { mp_err err; - mp_int g; if ((err = mp_init_copy(&g, a)) != MP_OKAY) { @@ -17,16 +16,16 @@ mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) /* set initial result */ mp_set(c, 1uL); - while (b > 0u) { + while (b > 0) { /* if the bit is set multiply */ - if ((b & 1u) != 0u) { + if ((b & 1) != 0) { if ((err = mp_mul(c, &g, c)) != MP_OKAY) { goto LBL_ERR; } } /* square */ - if (b > 1u) { + if (b > 1) { if ((err = mp_sqr(&g, &g)) != MP_OKAY) { goto LBL_ERR; } @@ -36,8 +35,6 @@ mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) b >>= 1; } - err = MP_OKAY; - LBL_ERR: mp_clear(&g); return err; diff --git a/mp_log_n.c b/mp_log_n.c new file mode 100644 index 000000000..4de1e3993 --- /dev/null +++ b/mp_log_n.c @@ -0,0 +1,29 @@ +#include "tommath_private.h" +#ifdef MP_LOG_N_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_err mp_log_n(const mp_int *a, int base, int *c) +{ + if (mp_isneg(a) || mp_iszero(a) || (base < 2) || (unsigned)base > (unsigned)MP_DIGIT_MAX) { + return MP_VAL; + } + + if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_2EXPT((mp_digit)base)) { + *c = s_mp_log_2expt(a, (mp_digit)base); + return MP_OKAY; + } + + if (MP_HAS(S_MP_LOG_D) && (a->used == 1)) { + *c = s_mp_log_d((mp_digit)base, a->dp[0]); + return MP_OKAY; + } + + if (MP_HAS(S_MP_LOG)) { + return s_mp_log(a, (mp_digit)base, c); + } + + return MP_VAL; +} + +#endif diff --git a/mp_log_u32.c b/mp_log_u32.c deleted file mode 100644 index 1450d3ab3..000000000 --- a/mp_log_u32.c +++ /dev/null @@ -1,29 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_LOG_U32_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) -{ - if (mp_isneg(a) || mp_iszero(a) || (base < 2u)) { - return MP_VAL; - } - - if (MP_HAS(S_MP_LOG_POW2) && MP_IS_2EXPT(base)) { - *c = s_mp_log_pow2(a, base); - return MP_OKAY; - } - - if (MP_HAS(S_MP_LOG_D) && (a->used == 1)) { - *c = (uint32_t)s_mp_log_d(base, a->dp[0]); - return MP_OKAY; - } - - if (MP_HAS(S_MP_LOG)) { - return s_mp_log(a, base, c); - } - - return MP_VAL; -} - -#endif diff --git a/mp_radix_size.c b/mp_radix_size.c index 7f7cbc2e2..ca08438bc 100644 --- a/mp_radix_size.c +++ b/mp_radix_size.c @@ -8,7 +8,7 @@ mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) { mp_err err; mp_int a_; - uint32_t b; + int b; /* make sure the radix is in range */ if ((radix < 2) || (radix > 64)) { @@ -22,14 +22,13 @@ mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) a_ = *a; a_.sign = MP_ZPOS; - if ((err = mp_log_u32(&a_, (uint32_t)radix, &b)) != MP_OKAY) { - goto LBL_ERR; + if ((err = mp_log_n(&a_, radix, &b)) != MP_OKAY) { + return err; } /* mp_ilogb truncates to zero, hence we need one extra put on top and one for `\0`. */ *size = (size_t)b + 2U + (mp_isneg(a) ? 1U : 0U); -LBL_ERR: - return err; + return MP_OKAY; } #endif diff --git a/mp_root_u32.c b/mp_root_n.c similarity index 84% rename from mp_root_u32.c rename to mp_root_n.c index 1f972d905..d904df883 100644 --- a/mp_root_u32.c +++ b/mp_root_n.c @@ -1,5 +1,5 @@ #include "tommath_private.h" -#ifdef MP_ROOT_U32_C +#ifdef MP_ROOT_N_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ @@ -12,15 +12,18 @@ * which will find the root in log(N) time where * each step involves a fair bit. */ -mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) +mp_err mp_root_n(const mp_int *a, int b, mp_int *c) { mp_int t1, t2, t3, a_; - mp_ord cmp; int ilog2; mp_err err; + if (b < 0 || (unsigned)b > (unsigned)MP_DIGIT_MAX) { + return MP_VAL; + } + /* input must be positive if b is even */ - if (((b & 1u) == 0u) && mp_isneg(a)) { + if (((b & 1) == 0) && mp_isneg(a)) { return MP_VAL; } @@ -40,7 +43,7 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) log_2(n) because the bit-length of the "n" is measured with an int and hence the root is always < 2 (two). */ - if (b > (uint32_t)(INT_MAX/2)) { + if (b > INT_MAX/2) { mp_set(c, 1uL); c->sign = a->sign; err = MP_OKAY; @@ -48,13 +51,13 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) } /* "b" is smaller than INT_MAX, we can cast safely */ - if (ilog2 < (int)b) { + if (ilog2 < b) { mp_set(c, 1uL); c->sign = a->sign; err = MP_OKAY; goto LBL_ERR; } - ilog2 = ilog2 / ((int)b); + ilog2 = ilog2 / b; if (ilog2 == 0) { mp_set(c, 1uL); c->sign = a->sign; @@ -71,7 +74,7 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) /* t2 = t1 - ((t1**b - a) / (b * t1**(b-1))) */ /* t3 = t1**(b-1) */ - if ((err = mp_expt_u32(&t1, b - 1u, &t3)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_expt_n(&t1, b - 1, &t3)) != MP_OKAY) goto LBL_ERR; /* numerator */ /* t2 = t1**b */ @@ -82,7 +85,7 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) /* denominator */ /* t3 = t1**(b-1) * b */ - if ((err = mp_mul_d(&t3, b, &t3)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_mul_d(&t3, (mp_digit)b, &t3)) != MP_OKAY) goto LBL_ERR; /* t3 = (t1**b - a)/(b * t1**(b-1)) */ if ((err = mp_div(&t2, &t3, &t3, NULL)) != MP_OKAY) goto LBL_ERR; @@ -101,7 +104,8 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) /* result can be off by a few so check */ /* Loop beneath can overshoot by one if found root is smaller than actual root */ for (;;) { - if ((err = mp_expt_u32(&t1, b, &t2)) != MP_OKAY) goto LBL_ERR; + mp_ord cmp; + if ((err = mp_expt_n(&t1, b, &t2)) != MP_OKAY) goto LBL_ERR; cmp = mp_cmp(&t2, &a_); if (cmp == MP_EQ) { err = MP_OKAY; @@ -115,7 +119,7 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) } /* correct overshoot from above or from recurrence */ for (;;) { - if ((err = mp_expt_u32(&t1, b, &t2)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_expt_n(&t1, b, &t2)) != MP_OKAY) goto LBL_ERR; if (mp_cmp(&t2, &a_) == MP_GT) { if ((err = mp_sub_d(&t1, 1uL, &t1)) != MP_OKAY) goto LBL_ERR; } else { @@ -129,8 +133,6 @@ mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) /* set the sign of the result */ c->sign = a->sign; - err = MP_OKAY; - LBL_ERR: mp_clear_multi(&t1, &t2, &t3, NULL); return err; diff --git a/s_mp_log.c b/s_mp_log.c index eba279ef7..d1ac73b1a 100644 --- a/s_mp_log.c +++ b/s_mp_log.c @@ -3,14 +3,13 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) +mp_err s_mp_log(const mp_int *a, mp_digit base, int *c) { mp_err err; - mp_ord cmp; - uint32_t high, low, mid; + int high, low; mp_int bracket_low, bracket_high, bracket_mid, t, bi_base; - cmp = mp_cmp_d(a, base); + mp_ord cmp = mp_cmp_d(a, base); if ((cmp == MP_LT) || (cmp == MP_EQ)) { *c = cmp == MP_EQ; return MP_OKAY; @@ -22,9 +21,9 @@ mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) return err; } - low = 0u; + low = 0; mp_set(&bracket_low, 1uL); - high = 1u; + high = 1; mp_set(&bracket_high, base); @@ -46,10 +45,10 @@ mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) } mp_set(&bi_base, base); - while ((high - low) > 1u) { - mid = (high + low) >> 1; + while ((high - low) > 1) { + int mid = (high + low) >> 1; - if ((err = mp_expt_u32(&bi_base, (uint32_t)(mid - low), &t)) != MP_OKAY) { + if ((err = mp_expt_n(&bi_base, mid - low, &t)) != MP_OKAY) { goto LBL_END; } if ((err = mp_mul(&bracket_low, &t, &bracket_mid)) != MP_OKAY) { diff --git a/s_mp_log_2expt.c b/s_mp_log_2expt.c new file mode 100644 index 000000000..ec0fda3b7 --- /dev/null +++ b/s_mp_log_2expt.c @@ -0,0 +1,12 @@ +#include "tommath_private.h" +#ifdef S_MP_LOG_2EXPT_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +int s_mp_log_2expt(const mp_int *a, mp_digit base) +{ + int y; + for (y = 0; (base & 1) == 0; y++, base >>= 1) {} + return (mp_count_bits(a) - 1) / y; +} +#endif diff --git a/s_mp_log_d.c b/s_mp_log_d.c index c9c8df218..5ff6c1fba 100644 --- a/s_mp_log_d.c +++ b/s_mp_log_d.c @@ -17,21 +17,18 @@ static mp_word s_pow(mp_word base, mp_word exponent) return result; } -mp_digit s_mp_log_d(mp_digit base, mp_digit n) +int s_mp_log_d(mp_digit base, mp_digit n) { - mp_word bracket_low = 1u, bracket_mid, bracket_high, N; - mp_digit ret, high = 1uL, low = 0uL, mid; + mp_word bracket_low = 1uLL, bracket_high = base, N = n; + int ret, high = 1, low = 0; if (n < base) { - return 0uL; + return 0; } if (n == base) { - return 1uL; + return 1; } - bracket_high = (mp_word) base ; - N = (mp_word) n; - while (bracket_high < N) { low = high; bracket_low = bracket_high; @@ -40,8 +37,8 @@ mp_digit s_mp_log_d(mp_digit base, mp_digit n) } while (((mp_digit)(high - low)) > 1uL) { - mid = (low + high) >> 1; - bracket_mid = bracket_low * s_pow(base, (mp_word)(mid - low)); + int mid = (low + high) >> 1; + mp_word bracket_mid = bracket_low * s_pow(base, (mp_word)(mid - low)); if (N < bracket_mid) { high = mid ; @@ -52,7 +49,7 @@ mp_digit s_mp_log_d(mp_digit base, mp_digit n) bracket_low = bracket_mid ; } if (N == bracket_mid) { - return (mp_digit) mid; + return mid; } } diff --git a/s_mp_log_pow2.c b/s_mp_log_pow2.c deleted file mode 100644 index 74271c68f..000000000 --- a/s_mp_log_pow2.c +++ /dev/null @@ -1,12 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_LOG_POW2_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base) -{ - int y; - for (y = 0; (base & 1u) == 0u; y++, base >>= 1) {} - return (uint32_t)((mp_count_bits(a) - 1) / y); -} -#endif diff --git a/tommath.h b/tommath.h index 5e75c98b5..4b2bc0422 100644 --- a/tommath.h +++ b/tommath.h @@ -423,11 +423,17 @@ mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp /* c = [a, b] or (a*b)/(a, b) */ mp_err mp_lcm(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; +/* Integer logarithm to integer base */ +mp_err mp_log_n(const mp_int *a, int base, int *c) MP_WUR; + +/* c = a**b */ +mp_err mp_expt_n(const mp_int *a, int b, mp_int *c) MP_WUR; + /* finds one of the b'th root of a, such that |c|**b <= |a| * * returns error if a < 0 and b is even */ -mp_err mp_root_u32(const mp_int *a, uint32_t b, mp_int *c) MP_WUR; +mp_err mp_root_n(const mp_int *a, int b, mp_int *c) MP_WUR; /* special sqrt algo */ mp_err mp_sqrt(const mp_int *arg, mp_int *ret) MP_WUR; @@ -557,12 +563,6 @@ mp_err mp_prime_next_prime(mp_int *a, int t, bool bbs_style) MP_WUR; */ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) MP_WUR; -/* Integer logarithm to integer base */ -mp_err mp_log_u32(const mp_int *a, uint32_t base, uint32_t *c) MP_WUR; - -/* c = a**b */ -mp_err mp_expt_u32(const mp_int *a, uint32_t b, mp_int *c) MP_WUR; - /* ---> radix conversion <--- */ int mp_count_bits(const mp_int *a) MP_WUR; diff --git a/tommath_private.h b/tommath_private.h index 938865f8d..60b333684 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -161,7 +161,8 @@ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); /* lowlevel functions, do not call! */ MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b) MP_WUR; -MP_PRIVATE mp_digit s_mp_log_d(mp_digit base, mp_digit n) MP_WUR; +MP_PRIVATE int s_mp_log_2expt(const mp_int *a, mp_digit base) MP_WUR; +MP_PRIVATE int s_mp_log_d(mp_digit base, mp_digit n) MP_WUR; MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) MP_WUR; MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) MP_WUR; @@ -171,7 +172,7 @@ MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_log(const mp_int *a, uint32_t base, uint32_t *c) MP_WUR; +MP_PRIVATE mp_err s_mp_log(const mp_int *a, mp_digit base, int *c) MP_WUR; MP_PRIVATE mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; MP_PRIVATE mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; MP_PRIVATE mp_err s_mp_mul_balance(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; @@ -187,7 +188,6 @@ MP_PRIVATE mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sqr_karatsuba(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sqr_toom(const mp_int *a, mp_int *b) MP_WUR; MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE uint32_t s_mp_log_pow2(const mp_int *a, uint32_t base) MP_WUR; MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); diff --git a/tommath_superclass.h b/tommath_superclass.h index dd83cad92..9e85d9865 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -28,12 +28,12 @@ # define MP_NEG_C # define MP_PRIME_FROBENIUS_UNDERWOOD_C # define MP_RADIX_SIZE_C -# define MP_LOG_U32_C +# define MP_LOG_N_C # define MP_RAND_C # define MP_REDUCE_C # define MP_REDUCE_2K_L_C # define MP_FROM_SBIN_C -# define MP_ROOT_U32_C +# define MP_ROOT_N_C # define MP_SET_L_C # define MP_SET_UL_C # define MP_SBIN_SIZE_C From 41eca3425f424331587a22192260e0920e6cd3b6 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 6 Nov 2019 00:13:39 +0100 Subject: [PATCH 134/304] regen --- libtommath_VS2008.vcproj | 10 +++++----- makefile | 8 ++++---- makefile.mingw | 8 ++++---- makefile.msvc | 8 ++++---- makefile.shared | 8 ++++---- makefile.unix | 8 ++++---- tommath.def | 6 +++--- tommath_class.h | 28 ++++++++++++++-------------- 8 files changed, 42 insertions(+), 42 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 7e16199e8..a9ab86325 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -417,7 +417,7 @@ > Date: Wed, 6 Nov 2019 11:29:17 +0100 Subject: [PATCH 135/304] Fix wrong use of uLL suffix --- demo/test.c | 28 ++++++++++++++-------------- etc/tune.c | 12 ++++++------ makefile | 8 ++++---- mp_set_double.c | 4 ++-- s_mp_rand_jenkins.c | 4 ++-- 5 files changed, 28 insertions(+), 28 deletions(-) diff --git a/demo/test.c b/demo/test.c index f15350925..1c86429ac 100644 --- a/demo/test.c +++ b/demo/test.c @@ -223,9 +223,9 @@ static int test_mp_get_set_i64(void) DOR(mp_init(&a)); - check_get_set_i64(&a, 0LL); - check_get_set_i64(&a, -1LL); - check_get_set_i64(&a, 1LL); + check_get_set_i64(&a, (int64_t)0); + check_get_set_i64(&a, (int64_t)-1); + check_get_set_i64(&a, (int64_t)1); check_get_set_i64(&a, INT64_MIN); check_get_set_i64(&a, INT64_MAX); @@ -683,26 +683,26 @@ static int test_mp_get_ul(void) static int test_mp_get_u64(void) { - unsigned long long q, r; + uint64_t q, r; int i; mp_int a, b; DOR(mp_init_multi(&a, &b, NULL)); - for (i = 0; i < (int)(MP_SIZEOF_BITS(unsigned long long) - 1); ++i) { - r = (1ULL << (i+1)) - 1; + for (i = 0; i < (int)(MP_SIZEOF_BITS(uint64_t) - 1); ++i) { + r = (UINT64_C(1) << (i+1)) - 1; if (!r) - r = ~0ULL; - printf(" r = 0x%llx i = %d\r", r, i); + r = UINT64_MAX; + printf(" r = 0x%" PRIx64 " i = %d\r", r, i); do { mp_set_u64(&a, r); q = mp_get_u64(&a); if (q != r) { - printf("\nmp_get_u64() bad result! 0x%llx != 0x%llx", q, r); + printf("\nmp_get_u64() bad result! 0x%" PRIx64 " != 0x%" PRIx64, q, r); goto LBL_ERR; } r <<= 1; - } while (r != 0uLL); + } while (r != 0u); } mp_clear_multi(&a, &b, NULL); @@ -2177,7 +2177,7 @@ static int test_mp_read_write_ubin(void) size = mp_ubin_size(&a); printf("mp_to_ubin_size %zu - ", size); - buf = malloc(sizeof(*buf) * size); + buf = (unsigned char *)malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (u) failed to allocate %zu bytes\n", sizeof(*buf) * size); @@ -2215,7 +2215,7 @@ static int test_mp_read_write_sbin(void) size = mp_sbin_size(&a); printf("mp_to_sbin_size %zu - ", size); - buf = malloc(sizeof(*buf) * size); + buf = (unsigned char *)malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (s) failed to allocate %zu bytes\n", sizeof(*buf) * size); @@ -2255,7 +2255,7 @@ static int test_mp_pack_unpack(void) count = mp_pack_count(&a, 0uL, 1uL); - buf = malloc(count); + buf = (unsigned char *)malloc(count); if (buf == NULL) { fprintf(stderr, "test_pack_unpack failed to allocate\n"); goto LBL_ERR; @@ -2346,7 +2346,7 @@ static int unit_tests(int argc, char **argv) ok = fail = nop = 0; t = (uint64_t)time(NULL); - printf("SEED: 0x%"PRIx64"\n\n", t); + printf("SEED: 0x%" PRIx64 "\n\n", t); s_mp_rand_jenkins_init(t); mp_rand_source(s_mp_rand_jenkins); diff --git a/etc/tune.c b/etc/tune.c index 0b7373448..9c41e396c 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -93,7 +93,7 @@ static uint64_t s_time_mul(int size) } if (mp_cmp(&c, &d) != MP_EQ) { /* Time of 0 cannot happen (famous last words?) */ - t1 = 0uLL; + t1 = 0u; goto LBL_ERR; } } @@ -134,7 +134,7 @@ static uint64_t s_time_sqr(int size) goto LBL_ERR; } if (mp_cmp(&c, &b) != MP_EQ) { - t1 = 0uLL; + t1 = 0u; goto LBL_ERR; } } @@ -166,16 +166,16 @@ static void s_run(const char *name, uint64_t (*op)(int size), int *cutoff) for (x = 8; x < args.upper_limit_print; x += args.increment_print) { *cutoff = INT_MAX; t1 = op(x); - if ((t1 == 0uLL) || (t1 == UINT64_MAX)) { + if ((t1 == 0u) || (t1 == UINT64_MAX)) { fprintf(stderr,"%s failed at x = INT_MAX (%s)\n", name, - (t1 == 0uLL)?"wrong result":"internal error"); + (t1 == 0u)?"wrong result":"internal error"); exit(EXIT_FAILURE); } *cutoff = x; t2 = op(x); - if ((t2 == 0uLL) || (t2 == UINT64_MAX)) { + if ((t2 == 0u) || (t2 == UINT64_MAX)) { fprintf(stderr,"%s failed (%s)\n", name, - (t2 == 0uLL)?"wrong result":"internal error"); + (t2 == 0u)?"wrong result":"internal error"); exit(EXIT_FAILURE); } if (args.verbose == 1) { diff --git a/makefile b/makefile index 1ce63ee03..f0ff23310 100644 --- a/makefile +++ b/makefile @@ -162,8 +162,8 @@ c89: -e 's/bool/mp_bool/g' \ -e 's/true/MP_YES/g' \ -e 's/false/MP_NO/g' \ - -e 's/UINT32_MAX/0xFFFFFFFFU/g' \ - -e 's/UINT64_MAX/0xFFFFFFFFFFFFFFFFULL/g' \ + -e 's/UINT32_MAX/0xFFFFFFFFu/g' \ + -e 's/UINT64_MAX/0xFFFFFFFFFFFFFFFFuLL/g' \ -e 's/INT32_MAX/2147483647/g' \ -e 's/INT32_MIN/(-2147483647-1)/g' \ -e 's/INT64_MAX/((mp_i64)9223372036854775807LL)/g' \ @@ -184,8 +184,8 @@ c99: -e 's/MP_YES/true/g' \ -e 's/MP_NO/false/g' \ -e 's/false_/MP_NO_/g' \ - -e 's/0xFFFFFFFFU/UINT32_MAX/g' \ - -e 's/0xFFFFFFFFFFFFFFFFULL/UINT64_MAX/g' \ + -e 's/0xFFFFFFFFu/UINT32_MAX/g' \ + -e 's/0xFFFFFFFFFFFFFFFFuLL/UINT64_MAX/g' \ -e 's/(-2147483647-1)/INT32_MIN/g' \ -e 's/2147483647/INT32_MAX/g' \ -e 's/((mp_i64)-9223372036854775807LL-1)/INT64_MIN/g' \ diff --git a/mp_set_double.c b/mp_set_double.c index 467d7fd85..ca4608311 100644 --- a/mp_set_double.c +++ b/mp_set_double.c @@ -16,7 +16,7 @@ mp_err mp_set_double(mp_int *a, double b) cast.dbl = b; exp = (int)((unsigned)(cast.bits >> 52) & 0x7FFu); - frac = (cast.bits & ((1uLL << 52) - 1uLL)) | (1uLL << 52); + frac = (cast.bits & ((UINT64_C(1) << 52) - UINT64_C(1))) | (UINT64_C(1) << 52); if (exp == 0x7FF) { /* +-inf, NaN */ return MP_VAL; @@ -30,7 +30,7 @@ mp_err mp_set_double(mp_int *a, double b) return err; } - if (((cast.bits >> 63) != 0uLL) && !mp_iszero(a)) { + if (((cast.bits >> 63) != 0u) && !mp_iszero(a)) { a->sign = MP_NEG; } diff --git a/s_mp_rand_jenkins.c b/s_mp_rand_jenkins.c index 3a905ba4a..4bb520cd4 100644 --- a/s_mp_rand_jenkins.c +++ b/s_mp_rand_jenkins.c @@ -28,7 +28,7 @@ static uint64_t s_rand_jenkins_val(void) void s_mp_rand_jenkins_init(uint64_t seed) { int i; - jenkins_x.a = 0xF1EA5EEDuLL; + jenkins_x.a = (uint64_t)0xF1EA5EEDuL; jenkins_x.b = jenkins_x.c = jenkins_x.d = seed; for (i = 0; i < 20; ++i) { (void)s_rand_jenkins_val(); @@ -42,7 +42,7 @@ mp_err s_mp_rand_jenkins(void *p, size_t n) int i; uint64_t x = s_rand_jenkins_val(); for (i = 0; (i < 8) && (n > 0u); ++i, --n) { - *q++ = (char)(x & 0xFFuLL); + *q++ = (char)(x & (uint64_t)0xFFu); x >>= 8; } } From 9cfb6c329819871f3ddd2c0ba80f0aa6cb62d3f9 Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Wed, 6 Nov 2019 11:52:42 +0100 Subject: [PATCH 136/304] use type-cast in stead of UINT64_C --- demo/test.c | 2 +- mp_set_double.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 1c86429ac..94a7ca2cb 100644 --- a/demo/test.c +++ b/demo/test.c @@ -690,7 +690,7 @@ static int test_mp_get_u64(void) DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < (int)(MP_SIZEOF_BITS(uint64_t) - 1); ++i) { - r = (UINT64_C(1) << (i+1)) - 1; + r = ((uint64_t)1 << (i+1)) - 1; if (!r) r = UINT64_MAX; printf(" r = 0x%" PRIx64 " i = %d\r", r, i); diff --git a/mp_set_double.c b/mp_set_double.c index ca4608311..78550c8f0 100644 --- a/mp_set_double.c +++ b/mp_set_double.c @@ -16,7 +16,7 @@ mp_err mp_set_double(mp_int *a, double b) cast.dbl = b; exp = (int)((unsigned)(cast.bits >> 52) & 0x7FFu); - frac = (cast.bits & ((UINT64_C(1) << 52) - UINT64_C(1))) | (UINT64_C(1) << 52); + frac = (cast.bits & (((uint64_t)1 << 52) - (uint64_t)1)) | ((uint64_t)1 << 52); if (exp == 0x7FF) { /* +-inf, NaN */ return MP_VAL; From a91eb5a0d9009651a9998db90e5dcb0330833747 Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 14:29:02 +0100 Subject: [PATCH 137/304] fix build (hopefully) --- demo/test.c | 6 +++--- demo/timing.c | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/demo/test.c b/demo/test.c index 94a7ca2cb..1391ee02a 100644 --- a/demo/test.c +++ b/demo/test.c @@ -625,7 +625,7 @@ static int test_mp_get_u32(void) DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < 1000; ++i) { - t = (unsigned long)rand_long() & 0xFFFFFFFFuL; + t = (unsigned long)rand_long() & (unsigned long)UINT32_MAX; mp_set_ul(&a, t); if (t != mp_get_u32(&a)) { printf("\nmp_get_u32() bad result!"); @@ -637,8 +637,8 @@ static int test_mp_get_u32(void) printf("\nmp_get_u32() bad result!"); goto LBL_ERR; } - mp_set_ul(&a, 0xFFFFFFFFuL); - if (mp_get_u32(&a) != 0xFFFFFFFFuL) { + mp_set_ul(&a, (unsigned long)UINT32_MAX); + if (mp_get_u32(&a) != UINT32_MAX) { printf("\nmp_get_u32() bad result!"); goto LBL_ERR; } diff --git a/demo/timing.c b/demo/timing.c index 4385a080d..76ca01fc7 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -47,7 +47,7 @@ static unsigned long lfsr = 0xAAAAAAAAuL; static unsigned int lbit(void) { if ((lfsr & 0x80000000uL) != 0uL) { - lfsr = ((lfsr << 1) ^ 0x8000001BuL) & 0xFFFFFFFFuL; + lfsr = ((lfsr << 1) ^ 0x8000001BuL) & (unsigned long)UINT32_MAX; return 1u; } else { lfsr <<= 1; From e9d54e986787a67d4af3a88261690500be8d1963 Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 14:44:39 +0100 Subject: [PATCH 138/304] remove unnecessary type-casts --- demo/test.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/demo/test.c b/demo/test.c index 1391ee02a..f42c6302c 100644 --- a/demo/test.c +++ b/demo/test.c @@ -223,9 +223,9 @@ static int test_mp_get_set_i64(void) DOR(mp_init(&a)); - check_get_set_i64(&a, (int64_t)0); - check_get_set_i64(&a, (int64_t)-1); - check_get_set_i64(&a, (int64_t)1); + check_get_set_i64(&a, 0); + check_get_set_i64(&a, -1); + check_get_set_i64(&a, 1); check_get_set_i64(&a, INT64_MIN); check_get_set_i64(&a, INT64_MAX); From 9f2cd0430101f7f85a857a05ca9e34c3ca36029b Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 15:30:34 +0100 Subject: [PATCH 139/304] more unnecessary type-casts, correct type-case for malloc --- demo/test.c | 12 ++++++------ demo/timing.c | 2 +- s_mp_rand_jenkins.c | 4 ++-- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/demo/test.c b/demo/test.c index f42c6302c..66a6f0735 100644 --- a/demo/test.c +++ b/demo/test.c @@ -618,14 +618,14 @@ static int test_mp_set_double(void) static int test_mp_get_u32(void) { - unsigned long t; + uint32_t t; int i; mp_int a, b; DOR(mp_init_multi(&a, &b, NULL)); for (i = 0; i < 1000; ++i) { - t = (unsigned long)rand_long() & (unsigned long)UINT32_MAX; + t = (uint32_t)rand_long(); mp_set_ul(&a, t); if (t != mp_get_u32(&a)) { printf("\nmp_get_u32() bad result!"); @@ -637,7 +637,7 @@ static int test_mp_get_u32(void) printf("\nmp_get_u32() bad result!"); goto LBL_ERR; } - mp_set_ul(&a, (unsigned long)UINT32_MAX); + mp_set_ul(&a, UINT32_MAX); if (mp_get_u32(&a) != UINT32_MAX) { printf("\nmp_get_u32() bad result!"); goto LBL_ERR; @@ -2177,7 +2177,7 @@ static int test_mp_read_write_ubin(void) size = mp_ubin_size(&a); printf("mp_to_ubin_size %zu - ", size); - buf = (unsigned char *)malloc(sizeof(*buf) * size); + buf = (uint8_t *)malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (u) failed to allocate %zu bytes\n", sizeof(*buf) * size); @@ -2215,7 +2215,7 @@ static int test_mp_read_write_sbin(void) size = mp_sbin_size(&a); printf("mp_to_sbin_size %zu - ", size); - buf = (unsigned char *)malloc(sizeof(*buf) * size); + buf = (uint8_t *)malloc(sizeof(*buf) * size); if (buf == NULL) { fprintf(stderr, "test_read_write_binaries (s) failed to allocate %zu bytes\n", sizeof(*buf) * size); @@ -2255,7 +2255,7 @@ static int test_mp_pack_unpack(void) count = mp_pack_count(&a, 0uL, 1uL); - buf = (unsigned char *)malloc(count); + buf = (uint8_t *)malloc(count); if (buf == NULL) { fprintf(stderr, "test_pack_unpack failed to allocate\n"); goto LBL_ERR; diff --git a/demo/timing.c b/demo/timing.c index 76ca01fc7..a66ce8505 100644 --- a/demo/timing.c +++ b/demo/timing.c @@ -47,7 +47,7 @@ static unsigned long lfsr = 0xAAAAAAAAuL; static unsigned int lbit(void) { if ((lfsr & 0x80000000uL) != 0uL) { - lfsr = ((lfsr << 1) ^ 0x8000001BuL) & (unsigned long)UINT32_MAX; + lfsr = ((lfsr << 1) ^ 0x8000001BuL) & UINT32_MAX; return 1u; } else { lfsr <<= 1; diff --git a/s_mp_rand_jenkins.c b/s_mp_rand_jenkins.c index 4bb520cd4..6aba0fb2b 100644 --- a/s_mp_rand_jenkins.c +++ b/s_mp_rand_jenkins.c @@ -28,7 +28,7 @@ static uint64_t s_rand_jenkins_val(void) void s_mp_rand_jenkins_init(uint64_t seed) { int i; - jenkins_x.a = (uint64_t)0xF1EA5EEDuL; + jenkins_x.a = 0xF1EA5EEDuL; jenkins_x.b = jenkins_x.c = jenkins_x.d = seed; for (i = 0; i < 20; ++i) { (void)s_rand_jenkins_val(); @@ -42,7 +42,7 @@ mp_err s_mp_rand_jenkins(void *p, size_t n) int i; uint64_t x = s_rand_jenkins_val(); for (i = 0; (i < 8) && (n > 0u); ++i, --n) { - *q++ = (char)(x & (uint64_t)0xFFu); + *q++ = (char)(x & 0xFFu); x >>= 8; } } From 680483518118778d0440fc9ab17403f3625e4d3a Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 15:46:04 +0100 Subject: [PATCH 140/304] more spacing around PRIu64, needed for C++ compatibility --- etc/tune.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/etc/tune.c b/etc/tune.c index 9c41e396c..be0663241 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -179,7 +179,7 @@ static void s_run(const char *name, uint64_t (*op)(int size), int *cutoff) exit(EXIT_FAILURE); } if (args.verbose == 1) { - printf("%d: %9"PRIu64" %9"PRIu64", %9"PRIi64"\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); + printf("%d: %9" PRIu64 " %9" PRIu64 ", %9" PRIi64 "\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); } if (t2 < t1) { if (count == s_stabilization_extra) { @@ -504,20 +504,20 @@ int main(int argc, char **argv) t1 = s_time_mul(x); set_cutoffs(&orig); t2 = s_time_mul(x); - fprintf(multiplying, "%d: %9"PRIu64" %9"PRIu64", %9"PRIi64"\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); + fprintf(multiplying, "%d: %9" PRIu64 " %9" PRIu64 ", %9" PRIi64 "\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); fflush(multiplying); if (args.verbose == 1) { - printf("MUL %d: %9"PRIu64" %9"PRIu64", %9"PRIi64"\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); + printf("MUL %d: %9" PRIu64 " %9" PRIu64 ", %9" PRIi64 "\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); fflush(stdout); } set_cutoffs(&max_cutoffs); t1 = s_time_sqr(x); set_cutoffs(&orig); t2 = s_time_sqr(x); - fprintf(squaring,"%d: %9"PRIu64" %9"PRIu64", %9"PRIi64"\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); + fprintf(squaring,"%d: %9" PRIu64 " %9" PRIu64 ", %9" PRIi64 "\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); fflush(squaring); if (args.verbose == 1) { - printf("SQR %d: %9"PRIu64" %9"PRIu64", %9"PRIi64"\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); + printf("SQR %d: %9" PRIu64 " %9" PRIu64 ", %9" PRIi64 "\n", x, t1, t2, (int64_t)t2 - (int64_t)t1); fflush(stdout); } } From 0730a31ab60da29c71a894e133e0e482d8ca708c Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 16:10:46 +0100 Subject: [PATCH 141/304] Make sure that c89 conversion doesn't produce LL or uLL postfix, since that isn't c89 at all --- makefile | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/makefile b/makefile index f0ff23310..0ce0a481d 100644 --- a/makefile +++ b/makefile @@ -163,11 +163,11 @@ c89: -e 's/true/MP_YES/g' \ -e 's/false/MP_NO/g' \ -e 's/UINT32_MAX/0xFFFFFFFFu/g' \ - -e 's/UINT64_MAX/0xFFFFFFFFFFFFFFFFuLL/g' \ - -e 's/INT32_MAX/2147483647/g' \ + -e 's/UINT64_MAX/(mp_u64)-1/g' \ + -e 's/INT32_MAX/0x7FFFFFFF/g' \ -e 's/INT32_MIN/(-2147483647-1)/g' \ - -e 's/INT64_MAX/((mp_i64)9223372036854775807LL)/g' \ - -e 's/INT64_MIN/((mp_i64)-9223372036854775807LL-1)/g' \ + -e 's/INT64_MAX/(mp_i64)(((mp_u64)1<<63)-1)/g' \ + -e 's/INT64_MIN/(mp_i64)((mp_u64)1<<63)/g' \ -e 's/SIZE_MAX/((size_t)-1)/g' \ -e 's/\(PRI[iux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ @@ -185,11 +185,11 @@ c99: -e 's/MP_NO/false/g' \ -e 's/false_/MP_NO_/g' \ -e 's/0xFFFFFFFFu/UINT32_MAX/g' \ - -e 's/0xFFFFFFFFFFFFFFFFuLL/UINT64_MAX/g' \ + -e 's/(mp_u64)-1/UINT64_MAX/g' \ -e 's/(-2147483647-1)/INT32_MIN/g' \ - -e 's/2147483647/INT32_MAX/g' \ - -e 's/((mp_i64)-9223372036854775807LL-1)/INT64_MIN/g' \ - -e 's/((mp_i64)9223372036854775807LL)/INT64_MAX/g' \ + -e 's/0x7FFFFFFF/INT32_MAX/g' \ + -e 's/(mp_i64)((mp_u64)1<<63)/INT64_MIN/g' \ + -e 's/(mp_i64)(((mp_u64)1<<63)-1)/INT64_MAX/g' \ -e 's/((size_t)-1)/SIZE_MAX/g' \ -e 's/MP_\(PRI[iux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ From bb1e56e775781ee1347fb66b563f83f9ff7cd223 Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Tue, 12 Nov 2019 16:20:07 +0100 Subject: [PATCH 142/304] Fix compilation of demo/test.c using C++ --- demo/test.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/demo/test.c b/demo/test.c index 66a6f0735..281255bab 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1411,7 +1411,7 @@ static mp_err s_rs(const mp_int *a, int radix, int *size) *size = mp_count_bits(a) + 1; return MP_OKAY; } - DOR(mp_init_copy(&t, a)); + DO_WHAT(mp_init_copy(&t, a), return MP_ERR); t.sign = MP_ZPOS; while (!mp_iszero(&t)) { if ((res = mp_div_d(&t, (mp_digit)radix, &t, &d)) != MP_OKAY) { From 642032ddc7ff6189f5768ce02e2431383187cb33 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 22 Nov 2019 02:56:48 +0100 Subject: [PATCH 143/304] wrong sign in mp_div_recursive --- demo/test.c | 41 +++++++++++++++++++++++++++++++++++++++-- s_mp_div_recursive.c | 2 +- 2 files changed, 40 insertions(+), 3 deletions(-) diff --git a/demo/test.c b/demo/test.c index 281255bab..02101aff1 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2082,16 +2082,53 @@ static int test_s_mp_div_recursive(void) DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "1. Recursive division failed at sizes %d / %d, wrong quotient\n", + fprintf(stderr, "1a. Recursive division failed at sizes %d / %d, wrong quotient\n", 10 * size, size); goto LBL_ERR; } if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "1. Recursive division failed at sizes %d / %d, wrong remainder\n", + fprintf(stderr, "1a. Recursive division failed at sizes %d / %d, wrong remainder\n", 10 * size, size); goto LBL_ERR; } printf("\rsizes = %d / %d", 2 * size, size); + + /* Relation 10:1 negative numerator*/ + DO(mp_rand(&a, 10 * size)); + DO(mp_neg(&a, &a)); + DO(mp_rand(&b, size)); + DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "1b. Recursive division failed at sizes %d / %d, wrong quotient\n", + 10 * size, size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "1b. Recursive division failed at sizes %d / %d, wrong remainder\n", + 10 * size, size); + goto LBL_ERR; + } + printf("\rsizes = %d / %d, negative numerator", 2 * size, size); + + /* Relation 10:1 negative denominator*/ + DO(mp_rand(&a, 10 * size)); + DO(mp_rand(&b, size)); + DO(mp_neg(&b, &b)); + DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); + DO(s_mp_div_school(&a, &b, &d_q, &d_r)); + if (mp_cmp(&c_q, &d_q) != MP_EQ) { + fprintf(stderr, "1c. Recursive division failed at sizes %d / %d, wrong quotient\n", + 10 * size, size); + goto LBL_ERR; + } + if (mp_cmp(&c_r, &d_r) != MP_EQ) { + fprintf(stderr, "1c. Recursive division failed at sizes %d / %d, wrong remainder\n", + 10 * size, size); + goto LBL_ERR; + } + printf("\rsizes = %d / %d, negative denominator", 2 * size, size); + /* Relation 2:1 */ DO(mp_rand(&a, 2 * size)); DO(mp_rand(&b, size)); diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index 5491f225c..df9a297be 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -159,7 +159,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r if ((err = mp_add(&Q, &Q1, &Q)) != MP_OKAY) goto LBL_ERR; /* get sign before writing to c */ - Q.sign = (mp_iszero(&Q) ? MP_ZPOS : a->sign); + R.sign = (mp_iszero(&Q) ? MP_ZPOS : a->sign); if (q != NULL) { mp_exch(&Q, q); From 5f3063fb2a396e70f8dab31c17ee1cf494e67d41 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 22 Nov 2019 03:14:59 +0100 Subject: [PATCH 144/304] correction of typo in test.c --- demo/test.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 02101aff1..e1b6f0fa6 100644 --- a/demo/test.c +++ b/demo/test.c @@ -729,7 +729,7 @@ static int test_mp_sqrt(void) printf("\nmp_sqrt() error!"); goto LBL_ERR; } - DO(mp_root_n(&a, 2u, &c)); + DO(mp_root_n(&a, 2, &c)); if (mp_cmp_mag(&b, &c) != MP_EQ) { printf("mp_sqrt() bad result!\n"); goto LBL_ERR; @@ -2363,7 +2363,7 @@ static int unit_tests(int argc, char **argv) T1(mp_set_double, MP_SET_DOUBLE), #endif T1(mp_signed_rsh, MP_SIGNED_RSH), - T2(mp_sqrt, MP_SQRT, mp_root_n), + T2(mp_sqrt, MP_SQRT, MP_ROOT_N), T1(mp_sqrtmod_prime, MP_SQRTMOD_PRIME), T1(mp_xor, MP_XOR), T2(s_mp_div_recursive, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), From 244c698ecd69be18db21d09b58093ec580351855 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 24 Nov 2019 05:37:43 +0100 Subject: [PATCH 145/304] corrected startvalue for sigma and cutoff in mp_div --- mp_div.c | 2 +- s_mp_div_recursive.c | 49 ++++++++++++++------------------------------ 2 files changed, 16 insertions(+), 35 deletions(-) diff --git a/mp_div.c b/mp_div.c index cbc52e8c4..b092d7bb0 100644 --- a/mp_div.c +++ b/mp_div.c @@ -26,7 +26,7 @@ mp_err mp_div(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) } if (MP_HAS(S_MP_DIV_RECURSIVE) - && (b->used > MP_MUL_KARATSUBA_CUTOFF) + && (b->used > (2 * MP_MUL_KARATSUBA_CUTOFF)) && (b->used <= ((a->used/3)*2))) { err = s_mp_div_recursive(a, b, c, d); } else if (MP_HAS(S_MP_DIV_SCHOOL)) { diff --git a/s_mp_div_recursive.c b/s_mp_div_recursive.c index df9a297be..d719c4e28 100644 --- a/s_mp_div_recursive.c +++ b/s_mp_div_recursive.c @@ -20,7 +20,7 @@ static mp_err s_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r mp_int A1, A2, B1, B0, Q1, Q0, R1, R0, t; int m = a->used - b->used, k = m/2; - if (m < MP_MUL_KARATSUBA_CUTOFF) { + if (m < (MP_MUL_KARATSUBA_CUTOFF)) { return s_mp_div_school(a, b, q, r); } @@ -43,15 +43,16 @@ static mp_err s_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r if ((err = mp_sub(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; /* while A1 < 0 do Q1 = Q1 - 1, A1 = A1 + (beta^k * B) */ - if ((err = mp_mul_2d(b, k * MP_DIGIT_BIT, &t)) != MP_OKAY) goto LBL_ERR; - while (mp_cmp_d(&A1, 0uL) == MP_LT) { - if ((err = mp_decr(&Q1)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_add(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; + if (mp_cmp_d(&A1, 0uL) == MP_LT) { + if ((err = mp_mul_2d(b, k * MP_DIGIT_BIT, &t)) != MP_OKAY) goto LBL_ERR; + do { + if ((err = mp_decr(&Q1)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&A1, &t, &A1)) != MP_OKAY) goto LBL_ERR; + } while (mp_cmp_d(&A1, 0uL) == MP_LT); } - /* (Q0, R0) = RecursiveDivRem(A1 / beta^(k), B1) */ if ((err = mp_div_2d(&A1, k * MP_DIGIT_BIT, &A1, &t)) != MP_OKAY) goto LBL_ERR; - if ((err = s_recursion(&A1, &B1, &Q0, &R0)) != MP_OKAY) goto LBL_ERR; + if ((err = s_recursion(&A1, &B1, &Q0, &R0)) != MP_OKAY) goto LBL_ERR; /* A2 = (R0*beta^k) + (A1 % beta^k) - (Q0*B0) */ if ((err = mp_lshd(&R0, k)) != MP_OKAY) goto LBL_ERR; @@ -65,13 +66,10 @@ static mp_err s_recursion(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r if ((err = mp_add(&A2, b, &A2)) != MP_OKAY) goto LBL_ERR; } /* return q = (Q1*beta^k) + Q0, r = A2 */ - if (q != NULL) { - if ((err = mp_lshd(&Q1, k)) != MP_OKAY) goto LBL_ERR; - if ((err = mp_add(&Q1, &Q0, q)) != MP_OKAY) goto LBL_ERR; - } - if (r != NULL) { - if ((err = mp_copy(&A2, r)) != MP_OKAY) goto LBL_ERR; - } + if ((err = mp_lshd(&Q1, k)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_add(&Q1, &Q0, q)) != MP_OKAY) goto LBL_ERR; + + if ((err = mp_copy(&A2, r)) != MP_OKAY) goto LBL_ERR; LBL_ERR: mp_clear_multi(&A1, &A2, &B1, &B0, &Q1, &Q0, &R1, &R0, &t, NULL); @@ -94,24 +92,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r /* most significant bit of a limb */ /* assumes MP_DIGIT_MAX < (sizeof(mp_digit) * CHAR_BIT) */ msb = (MP_DIGIT_MAX + (mp_digit)(1)) >> 1; - - /* - Method to compute sigma shamelessly stolen from - - J. Burnikel and J. Ziegler, "Fast recursive division", Research Report - MPI-I-98-1-022, Max-Planck-Institut fuer Informatik, Saarbruecken, Germany, - October 1998. (available online) - - Vid. section 2.3. - */ - m = MP_MUL_KARATSUBA_CUTOFF; - while (m <= b->used) { - m <<= 1; - } - j = (b->used + m - 1) / m; - n = j * m; - - sigma = MP_DIGIT_BIT * (n - b->used); + sigma = 0; msb_b = b->dp[b->used - 1]; while (msb_b < msb) { sigma++; @@ -139,7 +120,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r /* Q = 0 */ mp_zero(&Q); while (m > n) { - /* (q, r) = RecursveDivRem(A / (beta^(m-n)), B) */ + /* (q, r) = RecursiveDivRem(A / (beta^(m-n)), B) */ j = (m - n) * MP_DIGIT_BIT; if ((err = mp_div_2d(&A, j, &A_div, &A_mod)) != MP_OKAY) goto LBL_ERR; if ((err = s_recursion(&A_div, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; @@ -152,7 +133,7 @@ mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r /* m = m - n */ m = m - n; } - /* (q, r) = RecursveDivRem(A, B) */ + /* (q, r) = RecursiveDivRem(A, B) */ if ((err = s_recursion(&A, &B, &Q1, &R)) != MP_OKAY) goto LBL_ERR; /* Q = (Q * beta^m) + q, R = r */ if ((err = mp_mul_2d(&Q, m * MP_DIGIT_BIT, &Q)) != MP_OKAY) goto LBL_ERR; From 4cbd7d59f21a8362b43a30441939a427c973915f Mon Sep 17 00:00:00 2001 From: Jan Nijtmans Date: Wed, 20 Nov 2019 15:09:22 +0100 Subject: [PATCH 146/304] Don't use long long where not necessary, some platforms lack it --- mtest/mtest.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mtest/mtest.c b/mtest/mtest.c index c8d9e9592..c5a50aef3 100644 --- a/mtest/mtest.c +++ b/mtest/mtest.c @@ -95,7 +95,7 @@ void rand_num2(mp_int *a) int main(int argc, char *argv[]) { int n, tmp; - long long max; + long max; mp_int a, b, c, d, e; #ifdef MTEST_NO_FULLSPEED clock_t t1; From f0ab662ffcb7a08e7e6a14678dff1676c6322098 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Fri, 22 Nov 2019 16:01:42 +0100 Subject: [PATCH 147/304] do not use long long for minimum prec calculation, improve comment --- tommath_private.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/tommath_private.h b/tommath_private.h index 60b333684..eb566dd58 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -151,9 +151,10 @@ MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) /* Minimum number of available digits in mp_int, MP_PREC >= MP_MIN_PREC * - Must be at least 3 for s_mp_div_school. - * - Must be large enough such that uint64_t can be stored in mp_int without growing + * - Must be large enough such that the mp_set_u64 setter can + * store uint64_t in the mp_int without growing */ -#define MP_MIN_PREC MP_MAX(3, (((int)MP_SIZEOF_BITS(long long) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) +#define MP_MIN_PREC MP_MAX(3, (((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) /* random number source */ From b800b7610ad24ea75332a4fac0b477ae6c80082f Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Fri, 22 Nov 2019 16:04:48 +0100 Subject: [PATCH 148/304] remove *_ll* setters/getters * they are non standard * they are incompatible with older compilers * u64/i64 functions should be used instead * these functions should be deprecated again in 1.x --- doc/bn.tex | 28 +--------------------------- mp_get_ll.c | 7 ------- mp_get_mag_ull.c | 7 ------- mp_init_ll.c | 7 ------- mp_init_ull.c | 7 ------- mp_set_ll.c | 7 ------- mp_set_ull.c | 7 ------- tommath.h | 11 ----------- 8 files changed, 1 insertion(+), 80 deletions(-) delete mode 100644 mp_get_ll.c delete mode 100644 mp_get_mag_ull.c delete mode 100644 mp_init_ll.c delete mode 100644 mp_init_ull.c delete mode 100644 mp_set_ll.c delete mode 100644 mp_set_ull.c diff --git a/doc/bn.tex b/doc/bn.tex index 1d6cf835a..711ebf8ff 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -978,30 +978,6 @@ \subsection{Long Constants - platform dependant} This will return the least significant bits of the big integer $a$ that fit into the native data type \texttt{long}. -\subsection{Long Long Constants - platform dependant} - -\index{mp\_set\_ll} \index{mp\_set\_ull} -\begin{alltt} -void mp_set_ll (mp_int *a, long long b); -void mp_set_ull (mp_int *a, unsigned long long b); -\end{alltt} - -This will assign the value of the platform--dependent sized variable $b$ to the big integer $a$. - -To retrieve the value, the following functions can be used. - -\index{mp\_get\_ll} -\index{mp\_get\_ull} -\index{mp\_get\_mag\_ull} -\begin{alltt} -long long mp_get_ll (const mp_int *a); -unsigned long long mp_get_ull (const mp_int *a); -unsigned long long mp_get_mag_ull (const mp_int *a); -\end{alltt} - -This will return the least significant bits of $a$ that fit into the native data type \texttt{long - long}. - \subsection{Floating Point Constants - platform dependant} \index{mp\_set\_double} @@ -1023,7 +999,7 @@ \subsection{Floating Point Constants - platform dependant} \subsection{Initialize and Setting Constants} To both initialize and set small constants the following nine functions are available. \index{mp\_init\_set} \index{mp\_init\_i32} \index{mp\_init\_i64} \index{mp\_init\_u32} \index{mp\_init\_u64} -\index{mp\_init\_l} \index{mp\_init\_ll} \index{mp\_init\_ul} \index{mp\_init\_ull} +\index{mp\_init\_l} \index{mp\_init\_ul} \begin{alltt} mp_err mp_init_set (mp_int *a, mp_digit b); mp_err mp_init_i32 (mp_int *a, int32_t b); @@ -1032,8 +1008,6 @@ \subsection{Initialize and Setting Constants} mp_err mp_init_u64 (mp_int *a, uint64_t b); mp_err mp_init_l (mp_int *a, long b); mp_err mp_init_ul (mp_int *a, unsigned long b); -mp_err mp_init_ll (mp_int *a, long long b); -mp_err mp_init_ull (mp_int *a, unsigned long long b); \end{alltt} Both functions work like the previous counterparts except they first initialize $a$ with the diff --git a/mp_get_ll.c b/mp_get_ll.c deleted file mode 100644 index d31457df7..000000000 --- a/mp_get_ll.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_GET_LL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_GET_SIGNED(mp_get_ll, mp_get_mag_ull, long long, unsigned long long) -#endif diff --git a/mp_get_mag_ull.c b/mp_get_mag_ull.c deleted file mode 100644 index fea1ab117..000000000 --- a/mp_get_mag_ull.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_GET_MAG_ULL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_GET_MAG(mp_get_mag_ull, unsigned long long) -#endif diff --git a/mp_init_ll.c b/mp_init_ll.c deleted file mode 100644 index d8b44a6c3..000000000 --- a/mp_init_ll.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_INIT_LL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_INIT_INT(mp_init_ll, mp_set_ll, long long) -#endif diff --git a/mp_init_ull.c b/mp_init_ull.c deleted file mode 100644 index ef66c6a4b..000000000 --- a/mp_init_ull.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_INIT_ULL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_INIT_INT(mp_init_ull, mp_set_ull, unsigned long long) -#endif diff --git a/mp_set_ll.c b/mp_set_ll.c deleted file mode 100644 index 343012de2..000000000 --- a/mp_set_ll.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_SET_LL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_SET_SIGNED(mp_set_ll, mp_set_ull, long long, unsigned long long) -#endif diff --git a/mp_set_ull.c b/mp_set_ull.c deleted file mode 100644 index cd10b1cd4..000000000 --- a/mp_set_ull.c +++ /dev/null @@ -1,7 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_SET_ULL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -MP_SET_UNSIGNED(mp_set_ull, unsigned long long) -#endif diff --git a/tommath.h b/tommath.h index 4b2bc0422..95f7127b4 100644 --- a/tommath.h +++ b/tommath.h @@ -242,7 +242,6 @@ mp_err mp_init_u64(mp_int *a, uint64_t b) MP_WUR; uint32_t mp_get_mag_u32(const mp_int *a) MP_WUR; uint64_t mp_get_mag_u64(const mp_int *a) MP_WUR; unsigned long mp_get_mag_ul(const mp_int *a) MP_WUR; -unsigned long long mp_get_mag_ull(const mp_int *a) MP_WUR; /* get integer, set integer (long) */ long mp_get_l(const mp_int *a) MP_WUR; @@ -254,16 +253,6 @@ mp_err mp_init_l(mp_int *a, long b) MP_WUR; void mp_set_ul(mp_int *a, unsigned long b); mp_err mp_init_ul(mp_int *a, unsigned long b) MP_WUR; -/* get integer, set integer (long long) */ -long long mp_get_ll(const mp_int *a) MP_WUR; -void mp_set_ll(mp_int *a, long long b); -mp_err mp_init_ll(mp_int *a, long long b) MP_WUR; - -/* get integer, set integer (unsigned long long) */ -#define mp_get_ull(a) ((unsigned long long)mp_get_ll(a)) -void mp_set_ull(mp_int *a, unsigned long long b); -mp_err mp_init_ull(mp_int *a, unsigned long long b) MP_WUR; - /* set to single unsigned digit, up to MP_DIGIT_MAX */ void mp_set(mp_int *a, mp_digit b); mp_err mp_init_set(mp_int *a, mp_digit b) MP_WUR; From cd1bf5e2f0c5b9bddc7b1959a31bc3f99ec8caf3 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Fri, 22 Nov 2019 16:19:11 +0100 Subject: [PATCH 149/304] regen files --- libtommath_VS2008.vcproj | 24 ------------------------ makefile | 39 +++++++++++++++++++-------------------- makefile.mingw | 39 +++++++++++++++++++-------------------- makefile.msvc | 39 +++++++++++++++++++-------------------- makefile.shared | 39 +++++++++++++++++++-------------------- makefile.unix | 39 +++++++++++++++++++-------------------- tommath.def | 6 ------ tommath_class.h | 31 ------------------------------- 8 files changed, 95 insertions(+), 161 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index a9ab86325..6f1a42355 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -464,10 +464,6 @@ RelativePath="mp_get_l.c" > - - @@ -480,10 +476,6 @@ RelativePath="mp_get_mag_ul.c" > - - @@ -508,10 +500,6 @@ RelativePath="mp_init_l.c" > - - @@ -536,10 +524,6 @@ RelativePath="mp_init_ul.c" > - - @@ -728,10 +712,6 @@ RelativePath="mp_set_l.c" > - - @@ -744,10 +724,6 @@ RelativePath="mp_set_ul.c" > - - diff --git a/makefile b/makefile index 0ce0a481d..63930bc97 100644 --- a/makefile +++ b/makefile @@ -30,26 +30,25 @@ OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ -mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ -mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ -mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ -mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ -mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o mp_montgomery_reduce.o \ -mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ -mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ -mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ -mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ -mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ -mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o \ -s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ +mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ +mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ +mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ +mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ +mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ +mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ +mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ +s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 72d54ae1a..ae98a5c86 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -32,26 +32,25 @@ OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ -mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ -mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ -mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ -mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ -mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o mp_montgomery_reduce.o \ -mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ -mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ -mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ -mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ -mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ -mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o \ -s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ +mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ +mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ +mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ +mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ +mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ +mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ +mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ +s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index fe0dc2694..7dcbf3df1 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -25,26 +25,25 @@ OBJECTS=mp_2expt.obj mp_abs.obj mp_add.obj mp_add_d.obj mp_addmod.obj mp_and.obj mp_cmp.obj mp_cmp_d.obj mp_cmp_mag.obj mp_cnt_lsb.obj mp_complement.obj mp_copy.obj mp_count_bits.obj mp_cutoffs.obj \ mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj mp_dr_setup.obj \ mp_error_to_string.obj mp_exch.obj mp_expt_n.obj mp_exptmod.obj mp_exteuclid.obj mp_fread.obj mp_from_sbin.obj \ -mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj mp_get_ll.obj \ -mp_get_mag_u32.obj mp_get_mag_u64.obj mp_get_mag_ul.obj mp_get_mag_ull.obj mp_grow.obj mp_init.obj mp_init_copy.obj \ -mp_init_i32.obj mp_init_i64.obj mp_init_l.obj mp_init_ll.obj mp_init_multi.obj mp_init_set.obj mp_init_size.obj \ -mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj mp_init_ull.obj mp_invmod.obj mp_is_square.obj mp_kronecker.obj mp_lcm.obj \ -mp_log_n.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj \ -mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj \ -mp_pack_count.obj mp_prime_fermat.obj mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj \ -mp_prime_miller_rabin.obj mp_prime_next_prime.obj mp_prime_rabin_miller_trials.obj mp_prime_rand.obj \ -mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj \ -mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj \ -mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ -mp_set_l.obj mp_set_ll.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_set_ull.obj mp_shrink.obj mp_signed_rsh.obj \ -mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj \ -mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj \ -s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj \ -s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_2expt.obj s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj \ -s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ -s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_rand_jenkins.obj \ -s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj \ -s_mp_zero_buf.obj s_mp_zero_digs.obj +mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj mp_get_mag_u32.obj \ +mp_get_mag_u64.obj mp_get_mag_ul.obj mp_grow.obj mp_init.obj mp_init_copy.obj mp_init_i32.obj mp_init_i64.obj mp_init_l.obj \ +mp_init_multi.obj mp_init_set.obj mp_init_size.obj mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj mp_invmod.obj \ +mp_is_square.obj mp_kronecker.obj mp_lcm.obj mp_log_n.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj \ +mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj \ +mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj \ +mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj \ +mp_prime_rabin_miller_trials.obj mp_prime_rand.obj mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj \ +mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj mp_reduce_2k_setup.obj \ +mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj \ +mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj mp_set_u32.obj mp_set_u64.obj \ +mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj \ +mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj \ +s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj \ +s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_2expt.obj \ +s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj \ +s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj \ +s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ +s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 9c6ace005..2e24a43fb 100644 --- a/makefile.shared +++ b/makefile.shared @@ -27,26 +27,25 @@ OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ -mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ -mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ -mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ -mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ -mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o mp_montgomery_reduce.o \ -mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ -mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ -mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ -mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ -mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ -mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o \ -s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ +mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ +mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ +mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ +mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ +mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ +mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ +mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ +s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 8f1ba0760..2b2589c98 100644 --- a/makefile.unix +++ b/makefile.unix @@ -33,26 +33,25 @@ OBJECTS=mp_2expt.o mp_abs.o mp_add.o mp_add_d.o mp_addmod.o mp_and.o mp_clamp.o mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count_bits.o mp_cutoffs.o \ mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ -mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_ll.o \ -mp_get_mag_u32.o mp_get_mag_u64.o mp_get_mag_ul.o mp_get_mag_ull.o mp_grow.o mp_init.o mp_init_copy.o \ -mp_init_i32.o mp_init_i64.o mp_init_l.o mp_init_ll.o mp_init_multi.o mp_init_set.o mp_init_size.o \ -mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_init_ull.o mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o \ -mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o mp_montgomery_calc_normalization.o mp_montgomery_reduce.o \ -mp_montgomery_setup.o mp_mul.o mp_mul_2.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o \ -mp_pack_count.o mp_prime_fermat.o mp_prime_frobenius_underwood.o mp_prime_is_prime.o \ -mp_prime_miller_rabin.o mp_prime_next_prime.o mp_prime_rabin_miller_trials.o mp_prime_rand.o \ -mp_prime_strong_lucas_selfridge.o mp_radix_size.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ -mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ -mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ -mp_set_l.o mp_set_ll.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_set_ull.o mp_shrink.o mp_signed_rsh.o \ -mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o \ -mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ -s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o \ -s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o \ -s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o \ -s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ +mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ +mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ +mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ +mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ +mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ +mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ +mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ +mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ +mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ +mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ +s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/tommath.def b/tommath.def index 52953f93c..88733ca2a 100644 --- a/tommath.def +++ b/tommath.def @@ -43,25 +43,21 @@ EXPORTS mp_get_i32 mp_get_i64 mp_get_l - mp_get_ll mp_get_mag_u32 mp_get_mag_u64 mp_get_mag_ul - mp_get_mag_ull mp_grow mp_init mp_init_copy mp_init_i32 mp_init_i64 mp_init_l - mp_init_ll mp_init_multi mp_init_set mp_init_size mp_init_u32 mp_init_u64 mp_init_ul - mp_init_ull mp_invmod mp_is_square mp_kronecker @@ -109,11 +105,9 @@ EXPORTS mp_set_i32 mp_set_i64 mp_set_l - mp_set_ll mp_set_u32 mp_set_u64 mp_set_ul - mp_set_ull mp_shrink mp_signed_rsh mp_sqrmod diff --git a/tommath_class.h b/tommath_class.h index c8f436719..936a17e46 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -49,25 +49,21 @@ # define MP_GET_I32_C # define MP_GET_I64_C # define MP_GET_L_C -# define MP_GET_LL_C # define MP_GET_MAG_U32_C # define MP_GET_MAG_U64_C # define MP_GET_MAG_UL_C -# define MP_GET_MAG_ULL_C # define MP_GROW_C # define MP_INIT_C # define MP_INIT_COPY_C # define MP_INIT_I32_C # define MP_INIT_I64_C # define MP_INIT_L_C -# define MP_INIT_LL_C # define MP_INIT_MULTI_C # define MP_INIT_SET_C # define MP_INIT_SIZE_C # define MP_INIT_U32_C # define MP_INIT_U64_C # define MP_INIT_UL_C -# define MP_INIT_ULL_C # define MP_INVMOD_C # define MP_IS_SQUARE_C # define MP_KRONECKER_C @@ -115,11 +111,9 @@ # define MP_SET_I32_C # define MP_SET_I64_C # define MP_SET_L_C -# define MP_SET_LL_C # define MP_SET_U32_C # define MP_SET_U64_C # define MP_SET_UL_C -# define MP_SET_ULL_C # define MP_SHRINK_C # define MP_SIGNED_RSH_C # define MP_SQRMOD_C @@ -377,10 +371,6 @@ # define MP_GET_MAG_UL_C #endif -#if defined(MP_GET_LL_C) -# define MP_GET_MAG_ULL_C -#endif - #if defined(MP_GET_MAG_U32_C) #endif @@ -390,9 +380,6 @@ #if defined(MP_GET_MAG_UL_C) #endif -#if defined(MP_GET_MAG_ULL_C) -#endif - #if defined(MP_GROW_C) # define S_MP_ZERO_DIGS_C #endif @@ -421,11 +408,6 @@ # define MP_SET_L_C #endif -#if defined(MP_INIT_LL_C) -# define MP_INIT_C -# define MP_SET_LL_C -#endif - #if defined(MP_INIT_MULTI_C) # define MP_CLEAR_C # define MP_INIT_C @@ -454,11 +436,6 @@ # define MP_SET_UL_C #endif -#if defined(MP_INIT_ULL_C) -# define MP_INIT_C -# define MP_SET_ULL_C -#endif - #if defined(MP_INVMOD_C) # define MP_CMP_D_C # define S_MP_INVMOD_C @@ -842,10 +819,6 @@ # define MP_SET_UL_C #endif -#if defined(MP_SET_LL_C) -# define MP_SET_ULL_C -#endif - #if defined(MP_SET_U32_C) # define S_MP_ZERO_DIGS_C #endif @@ -858,10 +831,6 @@ # define S_MP_ZERO_DIGS_C #endif -#if defined(MP_SET_ULL_C) -# define S_MP_ZERO_DIGS_C -#endif - #if defined(MP_SHRINK_C) #endif From cecfd1f66cc517ef02f92cd8230881ceb874d14a Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 27 Nov 2019 20:55:22 +0100 Subject: [PATCH 150/304] changed generate_def to use the uncommited, raw file list --- helper.pl | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/helper.pl b/helper.pl index fb5413cdc..b3a30a051 100755 --- a/helper.pl +++ b/helper.pl @@ -422,9 +422,8 @@ sub update_dep } sub generate_def { - my @files = split /\n/, `git ls-files`; - @files = grep(/\.c/, @files); - @files = map { my $x = $_; $x =~ s/^bn_|\.c$//g; $x; } @files; + my @files = glob '*mp_*.c'; + @files = map { my $x = $_; $x =~ s/\.c$//g; $x; } @files; @files = grep(!/mp_cutoffs/, @files); my $files = join("\n ", sort(grep(/^mp_/, @files))); From 1e65c0bfe4fd11e7d81dbcd3df78b9d77cf21a65 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 11 Oct 2019 00:06:45 +0200 Subject: [PATCH 151/304] Introduction of a fast but slightly over-estimating radix_size --- demo/shared.c | 4 +- demo/test.c | 104 +++++++++++++++++++++++++++++++++ doc/bn.tex | 16 ++++- libtommath_VS2008.vcproj | 8 +++ makefile | 23 ++++---- makefile.mingw | 23 ++++---- makefile.msvc | 23 ++++---- makefile.shared | 23 ++++---- makefile.unix | 24 ++++---- mp_fwrite.c | 2 +- mp_radix_size_overestimate.c | 17 ++++++ s_mp_radix_size_overestimate.c | 87 +++++++++++++++++++++++++++ tommath.def | 1 + tommath.h | 2 + tommath_class.h | 20 ++++++- tommath_private.h | 1 + tommath_superclass.h | 3 + 17 files changed, 321 insertions(+), 60 deletions(-) create mode 100644 mp_radix_size_overestimate.c create mode 100644 s_mp_radix_size_overestimate.c diff --git a/demo/shared.c b/demo/shared.c index 7ef475687..85c26ed8e 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -6,8 +6,8 @@ void ndraw(const mp_int *a, const char *name) size_t size = 0; mp_err err; - if ((err = mp_radix_size(a, 10, &size)) != MP_OKAY) { - fprintf(stderr, "\nndraw: mp_radix_size(a, 10, %zu) failed - %s\n", size, mp_error_to_string(err)); + if ((err = mp_radix_size_overestimate(a, 10, &size)) != MP_OKAY) { + fprintf(stderr, "\nndraw: mp_radix_size_overestimate(a, 10, %zu) failed - %s\n", size, mp_error_to_string(err)); exit(EXIT_FAILURE); } buf = (char *)malloc(size); diff --git a/demo/test.c b/demo/test.c index e1b6f0fa6..32652d0a2 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2016,6 +2016,7 @@ static int test_s_mp_sqr_toom(void) return EXIT_FAILURE; } + static int test_mp_radix_size(void) { mp_int a; @@ -2201,6 +2202,108 @@ static int test_s_mp_div_small(void) } +static int test_s_mp_radix_size_overestimate(void) +{ + + mp_err err; + mp_int a; + int radix; + size_t size; +/* *INDENT-OFF* */ + size_t results[65] = { + 0u, 0u, 1627u, 1027u, 814u, 702u, 630u, 581u, 543u, + 514u, 491u, 471u, 455u, 441u, 428u, 418u, 408u, 399u, + 391u, 384u, 378u, 372u, 366u, 361u, 356u, 352u, 347u, + 343u, 340u, 336u, 333u, 330u, 327u, 324u, 321u, 318u, + 316u, 314u, 311u, 309u, 307u, 305u, 303u, 301u, 299u, + 298u, 296u, 294u, 293u, 291u, 290u, 288u, 287u, 285u, + 284u, 283u, 281u, 280u, 279u, 278u, 277u, 276u, 275u, + 273u, 272u + }; +#ifdef MP_RADIX_SIZE_OVERESTIMATE_TEST_BIG + size_t big_results[65] = { + 0u, 0u, 0u, 1354911329u, 1073741825u, + 924870867u, 830760078u, 764949110u, 715827883u, 677455665u, + 646456994u, 620761988u, 599025415u, 580332018u, 564035582u, + 549665673u, 536870913u, 525383039u, 514993351u, 505536793u, + 496880930u, 488918137u, 481559946u, 474732892u, 468375401u, + 462435434u, 456868672u, 451637110u, 446707948u, 442052707u, + 437646532u, 433467613u, 429496730u, 425716865u, 422112892u, + 418671312u, 415380039u, 412228213u, 409206043u, 406304679u, + 403516096u, 400833001u, 398248746u, 395757256u, 393352972u, + 391030789u, 388786017u, 386614331u, 384511740u, 382474555u, + 380499357u, 378582973u, 376722456u, 374915062u, 373158233u, + 371449582u, 369786879u, 368168034u, 366591092u, 365054217u, + 363555684u, 362093873u, 360667257u, 359274399u, 357913942 + }; +#endif + +/* *INDENT-ON* */ + if ((err = mp_init(&a)) != MP_OKAY) goto LBL_ERR; + + /* number to result in a different size for every base: 67^(4 * 67) */ + mp_set(&a, 67); + if ((err = mp_expt_n(&a, 268, &a)) != MP_OKAY) { + goto LBL_ERR; + } + + for (radix = 2; radix < 65; radix++) { + if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { + goto LBL_ERR; + } + if (size < results[radix]) { + fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", + radix, size, results[radix]); + goto LBL_ERR; + } + a.sign = MP_NEG; + if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { + goto LBL_ERR; + } + if (size < results[radix]) { + fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", + radix, size, results[radix]); + goto LBL_ERR; + } + a.sign = MP_ZPOS; + } +#ifdef MP_RADIX_SIZE_OVERESTIMATE_TEST_BIG + if ((err = mp_2expt(&a, INT_MAX - 1)) != MP_OKAY) { + goto LBL_ERR; + } + printf("bitcount = %d, alloc = %d\n", mp_count_bits(&a), a.alloc); + /* Start at 3 to avoid integer overflow */ + for (radix = 3; radix < 65; radix++) { + printf("radix = %d, ",radix); + if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { + goto LBL_ERR; + } + printf("size = %zu, diff = %zu\n", size, size - big_results[radix]); + if (size < big_results[radix]) { + fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", + radix, size, results[radix]); + goto LBL_ERR; + } + a.sign = MP_NEG; + if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { + goto LBL_ERR; + } + if (size < big_results[radix]) { + fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", + radix, size, results[radix]); + goto LBL_ERR; + } + a.sign = MP_ZPOS; + } +#endif + mp_clear(&a); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear(&a); + return EXIT_FAILURE; +} + + static int test_mp_read_write_ubin(void) { mp_int a, b, c; @@ -2359,6 +2462,7 @@ static int unit_tests(int argc, char **argv) T1(mp_reduce_2k, MP_REDUCE_2K), T1(mp_reduce_2k_l, MP_REDUCE_2K_L), T1(mp_radix_size, MP_RADIX_SIZE), + T1(s_mp_radix_size_overestimate, S_MP_RADIX_SIZE_OVERESTIMATE), #if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) T1(mp_set_double, MP_SET_DOUBLE), #endif diff --git a/doc/bn.tex b/doc/bn.tex index 711ebf8ff..a0956b302 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2380,7 +2380,21 @@ \subsection{To ASCII} \end{alltt} This stores in \texttt{size} the number of characters (including space for the \texttt{NUL} terminator) required. Upon error this function returns an error code and \texttt{size} will be -zero. +zero. This version of \texttt{mp\_radix\_size} uses \texttt{mp\_log} to calculate the size. It +is exact but slow for larger numbers. + +\index{mp\_radix\_size\_overestimate} +\begin{alltt} +mp_err mp_radix_size_overestimate (const mp_int *a, int radix, int *size) +\end{alltt} +This stores in \texttt{size} the number of characters (including space for the \texttt{NUL} +terminator) required. Upon error this function returns an error code and \texttt{size} will be +zero. This version of \texttt{mp\_radix\_size} is much faster than the exact version above but +introduces the relative error $\approx 10^{-8}$. That would be $22$ for $2^{2^{31}}-1$, the +largest possible number in LibTomMath. Experiments gave no absolute error over $+5$. + +The result is \emph{always} either exact or too large but it is \emph{never} too small. + If \texttt{MP\_NO\_FILE} is not defined a function to write to a file is also available. diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 6f1a42355..192ed0f0d 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -640,6 +640,10 @@ RelativePath="mp_radix_size.c" > + + @@ -884,6 +888,10 @@ RelativePath="s_mp_radix_map.c" > + + diff --git a/makefile b/makefile index 63930bc97..1cd577886 100644 --- a/makefile +++ b/makefile @@ -38,17 +38,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ -mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ -mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ -mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ -mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ -s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ +mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ +mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ +mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ +mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ +mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ +s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ +s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ +s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ +s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ +s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index ae98a5c86..aab267fb3 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -40,17 +40,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ -mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ -mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ -mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ -mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ -s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ +mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ +mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ +mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ +mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ +mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ +s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ +s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ +s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ +s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ +s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 7dcbf3df1..031f1c847 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -33,17 +33,18 @@ mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj mp_montgomery_setu mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj \ mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj \ mp_prime_rabin_miller_trials.obj mp_prime_rand.obj mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj \ -mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj mp_reduce_2k_setup.obj \ -mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj \ -mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj mp_set_u32.obj mp_set_u64.obj \ -mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj \ -mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj \ -s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj \ -s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_2expt.obj \ -s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj \ -s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj \ -s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ -s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +mp_radix_size_overestimate.obj mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj \ +mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj \ +mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj \ +mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj \ +mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj \ +mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj \ +s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj \ +s_mp_log_2expt.obj s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj \ +s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj \ +s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_radix_size_overestimate.obj \ +s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj \ +s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 2e24a43fb..5e19c3bc9 100644 --- a/makefile.shared +++ b/makefile.shared @@ -35,17 +35,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ -mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ -mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ -mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ -mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ -s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ +mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ +mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ +mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ +mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ +mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ +s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ +s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ +s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ +s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ +s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 2b2589c98..f2a918cf5 100644 --- a/makefile.unix +++ b/makefile.unix @@ -41,17 +41,19 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o mp_reduce_2k_setup.o \ -mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o mp_root_n.o mp_rshd.o \ -mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o mp_set_u32.o mp_set_u64.o \ -mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o \ -mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o \ -s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ +mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ +mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ +mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ +mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ +mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ +s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ +s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ +s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ +s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ +s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ +s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o + HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/mp_fwrite.c b/mp_fwrite.c index 6b8ea1332..3d8141f06 100644 --- a/mp_fwrite.c +++ b/mp_fwrite.c @@ -10,7 +10,7 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) mp_err err; size_t size, written; - if ((err = mp_radix_size(a, radix, &size)) != MP_OKAY) { + if ((err = mp_radix_size_overestimate(a, radix, &size)) != MP_OKAY) { return err; } diff --git a/mp_radix_size_overestimate.c b/mp_radix_size_overestimate.c new file mode 100644 index 000000000..3fe81d79d --- /dev/null +++ b/mp_radix_size_overestimate.c @@ -0,0 +1,17 @@ +#include "tommath_private.h" +#ifdef MP_RADIX_SIZE_OVERESTIMATE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_err mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size) +{ + if (MP_HAS(S_MP_RADIX_SIZE_OVERESTIMATE)) { + return s_mp_radix_size_overestimate(a, radix, size); + } + if (MP_HAS(MP_RADIX_SIZE)) { + return mp_radix_size(a, radix, size); + } + return MP_ERR; +} + +#endif diff --git a/s_mp_radix_size_overestimate.c b/s_mp_radix_size_overestimate.c new file mode 100644 index 000000000..35dd1e6b0 --- /dev/null +++ b/s_mp_radix_size_overestimate.c @@ -0,0 +1,87 @@ +#include "tommath_private.h" +#ifdef S_MP_RADIX_SIZE_OVERESTIMATE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* + Overestimate the size needed for the bigint to string conversion by a very small amount. + The error is about 10^-8; it will overestimate the result by at most 11 elements for + a number of the size 2^(2^31)-1 which is currently the largest possible in this library. + Some short tests gave no results larger than 5 (plus 2 for sign and EOS). + */ + +/* + Table of {0, INT(log_2([1..64])*2^p)+1 } where p is the scale + factor defined in MP_RADIX_SIZE_SCALE and INT() extracts the integer part (truncating). + Good for 32 bit "int". Set MP_RADIX_SIZE_SCALE = 61 and recompute values + for 64 bit "int". + */ +/* *INDENT-OFF* */ +#define MP_RADIX_SIZE_SCALE 29 +static const uint32_t s_log_bases[65] = { + 0u, 0u, 0x20000001u, 0x14309399u, 0x10000001u, + 0xdc81a35u, 0xc611924u, 0xb660c9eu, 0xaaaaaabu, 0xa1849cdu, + 0x9a209a9u, 0x94004e1u, 0x8ed19c2u, 0x8a5ca7du, 0x867a000u, + 0x830cee3u, 0x8000001u, 0x7d42d60u, 0x7ac8b32u, 0x7887847u, + 0x7677349u, 0x749131fu, 0x72d0163u, 0x712f657u, 0x6fab5dbu, + 0x6e40d1bu, 0x6ced0d0u, 0x6badbdeu, 0x6a80e3bu, 0x6964c19u, + 0x6857d31u, 0x6758c38u, 0x6666667u, 0x657fb21u, 0x64a3b9fu, + 0x63d1ab4u, 0x6308c92u, 0x624869eu, 0x618ff47u, 0x60dedeau, + 0x6034ab0u, 0x5f90e7bu, 0x5ef32cbu, 0x5e5b1b2u, 0x5dc85c3u, + 0x5d3aa02u, 0x5cb19d9u, 0x5c2d10fu, 0x5bacbbfu, 0x5b3064fu, + 0x5ab7d68u, 0x5a42df0u, 0x59d1506u, 0x5962ffeu, 0x58f7c57u, + 0x588f7bcu, 0x582a000u, 0x57c7319u, 0x5766f1du, 0x5709243u, + 0x56adad9u, 0x565474du, 0x55fd61fu, 0x55a85e8u, 0x5555556u +}; +/* *INDENT-ON* */ + +mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size) +{ + int bit_count; + mp_int bi_bit_count, bi_k; + mp_err err = MP_OKAY; + + if ((radix < 2) || (radix > 64)) { + return MP_VAL; + } + + if (mp_iszero(a)) { + *size = 2U; + return MP_OKAY; + } + + if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_2EXPT((mp_digit)radix)) { + /* floor(log_{2^n}(a)) + 1 + EOS + sign */ + *size = (size_t)(s_mp_log_2expt(a, (mp_digit)radix)); + /* Would overflow with base 2 otherwise */ + if (*size > (INT_MAX - 4)) { + return MP_VAL; + } + *size += 3u; + return MP_OKAY; + } + + if ((err = mp_init_multi(&bi_bit_count, &bi_k, NULL)) != MP_OKAY) { + return err; + } + + /* la = floor(log_2(a)) + 1 */ + bit_count = mp_count_bits(a); + + mp_set_u32(&bi_bit_count, (uint32_t)bit_count); + /* k = floor(2^29/log_2(radix)) + 1 */ + mp_set_u32(&bi_k, s_log_bases[radix]); + /* n = floor((la * k) / 2^29) + 1 */ + if ((err = mp_mul(&bi_bit_count, &bi_k, &bi_bit_count)) != MP_OKAY) goto LBL_ERR; + if ((err = mp_div_2d(&bi_bit_count, MP_RADIX_SIZE_SCALE, &bi_bit_count, NULL)) != MP_OKAY) goto LBL_ERR; + + /* The "+1" here is the "+1" in "floor((la * k) / 2^29) + 1" */ + /* n = n + 1 + EOS + sign */ + *size = (size_t)(mp_get_u64(&bi_bit_count) + 3U); + +LBL_ERR: + mp_clear_multi(&bi_bit_count, &bi_k, NULL); + return err; +} + +#endif diff --git a/tommath.def b/tommath.def index 88733ca2a..7d53508a4 100644 --- a/tommath.def +++ b/tommath.def @@ -87,6 +87,7 @@ EXPORTS mp_prime_rand mp_prime_strong_lucas_selfridge mp_radix_size + mp_radix_size_overestimate mp_rand mp_read_radix mp_reduce diff --git a/tommath.h b/tommath.h index 95f7127b4..a2e758541 100644 --- a/tommath.h +++ b/tommath.h @@ -565,7 +565,9 @@ mp_err mp_to_sbin(const mp_int *a, uint8_t *buf, size_t maxlen, size_t *written) mp_err mp_read_radix(mp_int *a, const char *str, int radix) MP_WUR; mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, int radix) MP_WUR; + mp_err mp_radix_size(const mp_int *a, int radix, size_t *size) MP_WUR; +mp_err mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size) MP_WUR; #ifndef MP_NO_FILE mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; diff --git a/tommath_class.h b/tommath_class.h index 936a17e46..5e76e6a8f 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -93,6 +93,7 @@ # define MP_PRIME_RAND_C # define MP_PRIME_STRONG_LUCAS_SELFRIDGE_C # define MP_RADIX_SIZE_C +# define MP_RADIX_SIZE_OVERESTIMATE_C # define MP_RAND_C # define MP_READ_RADIX_C # define MP_REDUCE_C @@ -154,6 +155,7 @@ # define S_MP_PRIME_IS_DIVISIBLE_C # define S_MP_PRIME_TAB_C # define S_MP_RADIX_MAP_C +# define S_MP_RADIX_SIZE_OVERESTIMATE_C # define S_MP_RAND_JENKINS_C # define S_MP_RAND_PLATFORM_C # define S_MP_SQR_C @@ -339,7 +341,7 @@ #endif #if defined(MP_FWRITE_C) -# define MP_RADIX_SIZE_C +# define MP_RADIX_SIZE_OVERESTIMATE_C # define MP_TO_RADIX_C # define S_MP_ZERO_BUF_C #endif @@ -688,6 +690,11 @@ # define MP_LOG_N_C #endif +#if defined(MP_RADIX_SIZE_OVERESTIMATE_C) +# define MP_RADIX_SIZE_C +# define S_MP_RADIX_SIZE_OVERESTIMATE_C +#endif + #if defined(MP_RAND_C) # define MP_GROW_C # define MP_RAND_SOURCE_C @@ -1172,6 +1179,17 @@ #if defined(S_MP_RADIX_MAP_C) #endif +#if defined(S_MP_RADIX_SIZE_OVERESTIMATE_C) +# define MP_CLEAR_MULTI_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_GET_I64_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_SET_U32_C +# define S_MP_LOG_2EXPT_C +#endif + #if defined(S_MP_RAND_JENKINS_C) # define S_MP_RAND_JENKINS_INIT_C #endif diff --git a/tommath_private.h b/tommath_private.h index eb566dd58..24e778145 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -192,6 +192,7 @@ MP_PRIVATE mp_err s_mp_sub(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE void s_mp_copy_digs(mp_digit *d, const mp_digit *s, int digits); MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); +MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size); /* TODO: jenkins prng is not thread safe as of now */ MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; diff --git a/tommath_superclass.h b/tommath_superclass.h index 9e85d9865..9245e0020 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -28,6 +28,7 @@ # define MP_NEG_C # define MP_PRIME_FROBENIUS_UNDERWOOD_C # define MP_RADIX_SIZE_C +# define MP_RADIX_SIZE_OVERESTIMATE_C # define MP_LOG_N_C # define MP_RAND_C # define MP_REDUCE_C @@ -36,6 +37,8 @@ # define MP_ROOT_N_C # define MP_SET_L_C # define MP_SET_UL_C +# define MP_SET_U64_C +# define MP_SET_I64_C # define MP_SBIN_SIZE_C # define MP_TO_RADIX_C # define MP_TO_SBIN_C From 9d0bdc7efbfdef01b65a06110f4332a233ad77c6 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Wed, 4 Dec 2019 22:23:24 +0100 Subject: [PATCH 152/304] run the test always --- demo/test.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/demo/test.c b/demo/test.c index 32652d0a2..731c3982e 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2220,7 +2220,6 @@ static int test_s_mp_radix_size_overestimate(void) 284u, 283u, 281u, 280u, 279u, 278u, 277u, 276u, 275u, 273u, 272u }; -#ifdef MP_RADIX_SIZE_OVERESTIMATE_TEST_BIG size_t big_results[65] = { 0u, 0u, 0u, 1354911329u, 1073741825u, 924870867u, 830760078u, 764949110u, 715827883u, 677455665u, @@ -2236,7 +2235,6 @@ static int test_s_mp_radix_size_overestimate(void) 371449582u, 369786879u, 368168034u, 366591092u, 365054217u, 363555684u, 362093873u, 360667257u, 359274399u, 357913942 }; -#endif /* *INDENT-ON* */ if ((err = mp_init(&a)) != MP_OKAY) goto LBL_ERR; @@ -2267,7 +2265,6 @@ static int test_s_mp_radix_size_overestimate(void) } a.sign = MP_ZPOS; } -#ifdef MP_RADIX_SIZE_OVERESTIMATE_TEST_BIG if ((err = mp_2expt(&a, INT_MAX - 1)) != MP_OKAY) { goto LBL_ERR; } @@ -2295,7 +2292,6 @@ static int test_s_mp_radix_size_overestimate(void) } a.sign = MP_ZPOS; } -#endif mp_clear(&a); return EXIT_SUCCESS; LBL_ERR: From 3a744dc46d3b9afd265c4a3a1f444f01a08772c0 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 5 Dec 2019 00:33:53 +0100 Subject: [PATCH 153/304] s_mp_radix_size_overestimate: remove overflow check --- mp_grow.c | 1 + mp_init_size.c | 1 + s_mp_radix_size_overestimate.c | 7 +------ 3 files changed, 3 insertions(+), 6 deletions(-) diff --git a/mp_grow.c b/mp_grow.c index 0de667984..344a5a876 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -8,6 +8,7 @@ mp_err mp_grow(mp_int *a, int size) { /* if the alloc size is smaller alloc more ram */ if (a->alloc < size) { + /* TODO */ /* reallocate the array a->dp * * We store the return in a temporary variable diff --git a/mp_init_size.c b/mp_init_size.c index 9aa98b970..fb7a37d51 100644 --- a/mp_init_size.c +++ b/mp_init_size.c @@ -8,6 +8,7 @@ mp_err mp_init_size(mp_int *a, int size) { size = MP_MAX(MP_MIN_PREC, size); + /*TODO*/ /* alloc mem */ a->dp = (mp_digit *) MP_CALLOC((size_t)size, sizeof(mp_digit)); if (a->dp == NULL) { diff --git a/s_mp_radix_size_overestimate.c b/s_mp_radix_size_overestimate.c index 35dd1e6b0..4f0599732 100644 --- a/s_mp_radix_size_overestimate.c +++ b/s_mp_radix_size_overestimate.c @@ -52,12 +52,7 @@ mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *si if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_2EXPT((mp_digit)radix)) { /* floor(log_{2^n}(a)) + 1 + EOS + sign */ - *size = (size_t)(s_mp_log_2expt(a, (mp_digit)radix)); - /* Would overflow with base 2 otherwise */ - if (*size > (INT_MAX - 4)) { - return MP_VAL; - } - *size += 3u; + *size = (size_t)(s_mp_log_2expt(a, (mp_digit)radix) + 3); return MP_OKAY; } From 08d281c46218ef6ff30a512470813c785403897b Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 5 Dec 2019 00:48:25 +0100 Subject: [PATCH 154/304] introduce MP_MAX_DIGIT_COUNT to prevent overflow --- demo/shared.c | 2 +- demo/test.c | 7 +++++++ mp_grow.c | 13 +++++++++---- mp_init.c | 4 ++-- mp_init_size.c | 7 +++++-- mp_shrink.c | 2 +- tommath_private.h | 21 ++++++++++++++------- 7 files changed, 39 insertions(+), 17 deletions(-) diff --git a/demo/shared.c b/demo/shared.c index 85c26ed8e..536a1de22 100644 --- a/demo/shared.c +++ b/demo/shared.c @@ -45,5 +45,5 @@ void print_header(void) printf("Size of mp_digit: %u\n", (unsigned int)sizeof(mp_digit)); printf("Size of mp_word: %u\n", (unsigned int)sizeof(mp_word)); printf("MP_DIGIT_BIT: %d\n", MP_DIGIT_BIT); - printf("MP_PREC: %d\n", MP_PREC); + printf("MP_DEFAULT_DIGIT_COUNT: %d\n", MP_DEFAULT_DIGIT_COUNT); } diff --git a/demo/test.c b/demo/test.c index 731c3982e..5009a8dc5 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2220,6 +2220,8 @@ static int test_s_mp_radix_size_overestimate(void) 284u, 283u, 281u, 280u, 279u, 278u, 277u, 276u, 275u, 273u, 272u }; + +#if 0 size_t big_results[65] = { 0u, 0u, 0u, 1354911329u, 1073741825u, 924870867u, 830760078u, 764949110u, 715827883u, 677455665u, @@ -2235,6 +2237,7 @@ static int test_s_mp_radix_size_overestimate(void) 371449582u, 369786879u, 368168034u, 366591092u, 365054217u, 363555684u, 362093873u, 360667257u, 359274399u, 357913942 }; +#endif /* *INDENT-ON* */ if ((err = mp_init(&a)) != MP_OKAY) goto LBL_ERR; @@ -2265,6 +2268,8 @@ static int test_s_mp_radix_size_overestimate(void) } a.sign = MP_ZPOS; } + +#if 0 if ((err = mp_2expt(&a, INT_MAX - 1)) != MP_OKAY) { goto LBL_ERR; } @@ -2292,6 +2297,8 @@ static int test_s_mp_radix_size_overestimate(void) } a.sign = MP_ZPOS; } +#endif + mp_clear(&a); return EXIT_SUCCESS; LBL_ERR: diff --git a/mp_grow.c b/mp_grow.c index 344a5a876..ff3b96d1e 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -8,16 +8,21 @@ mp_err mp_grow(mp_int *a, int size) { /* if the alloc size is smaller alloc more ram */ if (a->alloc < size) { - /* TODO */ + mp_digit *dp; + + if (size > MP_MAX_DIGIT_COUNT) { + return MP_MEM; + } + /* reallocate the array a->dp * * We store the return in a temporary variable * in case the operation failed we don't want * to overwrite the dp member of a. */ - mp_digit *dp = (mp_digit *) MP_REALLOC(a->dp, - (size_t)a->alloc * sizeof(mp_digit), - (size_t)size * sizeof(mp_digit)); + dp = (mp_digit *) MP_REALLOC(a->dp, + (size_t)a->alloc * sizeof(mp_digit), + (size_t)size * sizeof(mp_digit)); if (dp == NULL) { /* reallocation failed but "a" is still valid [can be freed] */ return MP_MEM; diff --git a/mp_init.c b/mp_init.c index 9b8228262..af1674481 100644 --- a/mp_init.c +++ b/mp_init.c @@ -7,7 +7,7 @@ mp_err mp_init(mp_int *a) { /* allocate memory required and clear it */ - a->dp = (mp_digit *) MP_CALLOC((size_t)MP_PREC, sizeof(mp_digit)); + a->dp = (mp_digit *) MP_CALLOC((size_t)MP_DEFAULT_DIGIT_COUNT, sizeof(mp_digit)); if (a->dp == NULL) { return MP_MEM; } @@ -15,7 +15,7 @@ mp_err mp_init(mp_int *a) /* set the used to zero, allocated digits to the default precision * and sign to positive */ a->used = 0; - a->alloc = MP_PREC; + a->alloc = MP_DEFAULT_DIGIT_COUNT; a->sign = MP_ZPOS; return MP_OKAY; diff --git a/mp_init_size.c b/mp_init_size.c index fb7a37d51..979a0b7d0 100644 --- a/mp_init_size.c +++ b/mp_init_size.c @@ -6,9 +6,12 @@ /* init an mp_init for a given size */ mp_err mp_init_size(mp_int *a, int size) { - size = MP_MAX(MP_MIN_PREC, size); + size = MP_MAX(MP_MIN_DIGIT_COUNT, size); + + if (size > MP_MAX_DIGIT_COUNT) { + return MP_MEM; + } - /*TODO*/ /* alloc mem */ a->dp = (mp_digit *) MP_CALLOC((size_t)size, sizeof(mp_digit)); if (a->dp == NULL) { diff --git a/mp_shrink.c b/mp_shrink.c index e5814cbdf..3d9b1626d 100644 --- a/mp_shrink.c +++ b/mp_shrink.c @@ -6,7 +6,7 @@ /* shrink a bignum */ mp_err mp_shrink(mp_int *a) { - int alloc = MP_MAX(MP_MIN_PREC, a->used); + int alloc = MP_MAX(MP_MIN_DIGIT_COUNT, a->used); if (a->alloc != alloc) { mp_digit *dp = (mp_digit *) MP_REALLOC(a->dp, (size_t)a->alloc * sizeof(mp_digit), diff --git a/tommath_private.h b/tommath_private.h index 24e778145..0096479ec 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -140,22 +140,29 @@ typedef uint64_t mp_word; MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) -/* default precision */ -#ifndef MP_PREC +/* default number of digits */ +#ifndef MP_DEFAULT_DIGIT_COUNT # ifndef MP_LOW_MEM -# define MP_PREC 32 /* default digits of precision */ +# define MP_DEFAULT_DIGIT_COUNT 32 # else -# define MP_PREC 8 /* default digits of precision */ +# define MP_DEFAULT_DIGIT_COUNT 8 # endif #endif -/* Minimum number of available digits in mp_int, MP_PREC >= MP_MIN_PREC +/* Minimum number of available digits in mp_int, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT * - Must be at least 3 for s_mp_div_school. * - Must be large enough such that the mp_set_u64 setter can * store uint64_t in the mp_int without growing */ -#define MP_MIN_PREC MP_MAX(3, (((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) -MP_STATIC_ASSERT(prec_geq_min_prec, MP_PREC >= MP_MIN_PREC) +#define MP_MIN_DIGIT_COUNT MP_MAX(3, (((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) +MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT) + +/* Maximum number of digits. + * - Must be small enough such that mp_bit_count does not overflow. + * - Must be small enough such that mp_radix_size for base 2 does not overflow. + * mp_radix_size needs two additional bytes for zero termination and sign. + */ +#define MP_MAX_DIGIT_COUNT ((INT_MAX - 2) / MP_DIGIT_BIT) /* random number source */ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); From c375b038191f49118be806649f17d0bc2a30c12e Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 5 Dec 2019 11:09:39 +0100 Subject: [PATCH 155/304] test cleanup; add randomized radix_size test --- demo/test.c | 530 +++++++++++----------------------------------------- 1 file changed, 114 insertions(+), 416 deletions(-) diff --git a/demo/test.c b/demo/test.c index 5009a8dc5..998f14b35 100644 --- a/demo/test.c +++ b/demo/test.c @@ -334,10 +334,7 @@ static int test_mp_kronecker(void) mp_set_ul(&a, 0uL); mp_set_ul(&b, 1uL); DO(mp_kronecker(&a, &b, &i)); - if (i != 1) { - printf("Failed trivial mp_kronecker(0 | 1) %d != 1\n", i); - goto LBL_ERR; - } + EXPECT(i == 1); for (cnt = 0; cnt < (int)(sizeof(kronecker)/sizeof(kronecker[0])); ++cnt) { k = kronecker[cnt].n; mp_set_l(&a, k); @@ -345,10 +342,7 @@ static int test_mp_kronecker(void) for (m = -10; m <= 10; m++) { mp_set_l(&b, m); DO(mp_kronecker(&a, &b, &i)); - if (i != kronecker[cnt].c[m + 10]) { - printf("Failed trivial mp_kronecker(%ld | %ld) %d != %d\n", kronecker[cnt].n, m, i, kronecker[cnt].c[m + 10]); - goto LBL_ERR; - } + EXPECT(i == kronecker[cnt].c[m + 10]); } } @@ -374,10 +368,7 @@ static int test_mp_complement(void) l = ~l; mp_set_l(&c, l); - if (mp_cmp(&b, &c) != MP_EQ) { - printf("\nmp_complement() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &c) == MP_EQ); } mp_clear_multi(&a, &b, &c, NULL); @@ -406,10 +397,7 @@ static int test_mp_signed_rsh(void) mp_set_l(&d, l >> em); DO(mp_signed_rsh(&a, em, &b)); - if (mp_cmp(&b, &d) != MP_EQ) { - printf("\nmp_signed_rsh() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &d) == MP_EQ); } mp_clear_multi(&a, &b, &d, NULL); @@ -439,10 +427,7 @@ static int test_mp_xor(void) mp_set_l(&d, l ^ em); DO(mp_xor(&a, &b, &c)); - if (mp_cmp(&c, &d) != MP_EQ) { - printf("\nmp_xor() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -472,10 +457,7 @@ static int test_mp_or(void) mp_set_l(&d, l | em); DO(mp_or(&a, &b, &c)); - if (mp_cmp(&c, &d) != MP_EQ) { - printf("\nmp_or() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -504,10 +486,7 @@ static int test_mp_and(void) mp_set_l(&d, l & em); DO(mp_and(&a, &b, &c)); - if (mp_cmp(&c, &d) != MP_EQ) { - printf("\nmp_and() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -528,28 +507,11 @@ static int test_mp_invmod(void) const char *b_ = "FFFFFFFEFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF00000000FFFFFFFFFFFFFFFF"; const char *should_ = "0521A82E10376F8E4FDEF9A32A427AC2A0FFF686E00290D39E3E4B5522409596"; - if (mp_read_radix(&a, a_, 16) != MP_OKAY) { - printf("\nmp_read_radix(a) failed!"); - goto LBL_ERR; - } - if (mp_read_radix(&b, b_, 16) != MP_OKAY) { - printf("\nmp_read_radix(b) failed!"); - goto LBL_ERR; - } - if (mp_read_radix(&c, should_, 16) != MP_OKAY) { - printf("\nmp_read_radix(should) failed!"); - goto LBL_ERR; - } - - if (mp_invmod(&a, &b, &d) != MP_OKAY) { - printf("\nmp_invmod() failed!"); - goto LBL_ERR; - } - - if (mp_cmp(&c, &d) != MP_EQ) { - printf("\nmp_invmod() bad result!"); - goto LBL_ERR; - } + DO(mp_read_radix(&a, a_, 16)); + DO(mp_read_radix(&b, b_, 16)); + DO(mp_read_radix(&c, should_, 16)); + DO(mp_invmod(&a, &b, &d)); + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -569,42 +531,18 @@ static int test_mp_set_double(void) DOR(mp_init_multi(&a, &b, NULL)); /* test mp_get_double/mp_set_double */ - if (mp_set_double(&a, +1.0/0.0) != MP_VAL) { - printf("\nmp_set_double should return MP_VAL for +inf"); - goto LBL_ERR; - } - if (mp_set_double(&a, -1.0/0.0) != MP_VAL) { - printf("\nmp_set_double should return MP_VAL for -inf"); - goto LBL_ERR; - } - if (mp_set_double(&a, +0.0/0.0) != MP_VAL) { - printf("\nmp_set_double should return MP_VAL for NaN"); - goto LBL_ERR; - } - if (mp_set_double(&a, -0.0/0.0) != MP_VAL) { - printf("\nmp_set_double should return MP_VAL for NaN"); - goto LBL_ERR; - } + EXPECT(mp_set_double(&a, +1.0/0.0) == MP_VAL); + EXPECT(mp_set_double(&a, -1.0/0.0) == MP_VAL); + EXPECT(mp_set_double(&a, +0.0/0.0) == MP_VAL); + EXPECT(mp_set_double(&a, -0.0/0.0) == MP_VAL); for (i = 0; i < 1000; ++i) { int tmp = rand_int(); double dbl = (double)tmp * rand_int() + 1; - if (mp_set_double(&a, dbl) != MP_OKAY) { - printf("\nmp_set_double() failed"); - goto LBL_ERR; - } - if (dbl != mp_get_double(&a)) { - printf("\nmp_get_double() bad result!"); - goto LBL_ERR; - } - if (mp_set_double(&a, -dbl) != MP_OKAY) { - printf("\nmp_set_double() failed"); - goto LBL_ERR; - } - if (-dbl != mp_get_double(&a)) { - printf("\nmp_get_double() bad result!"); - goto LBL_ERR; - } + DO(mp_set_double(&a, dbl)); + EXPECT(dbl == mp_get_double(&a)); + DO(mp_set_double(&a, -dbl)); + EXPECT(-dbl == mp_get_double(&a)); } mp_clear_multi(&a, &b, NULL); @@ -627,21 +565,12 @@ static int test_mp_get_u32(void) for (i = 0; i < 1000; ++i) { t = (uint32_t)rand_long(); mp_set_ul(&a, t); - if (t != mp_get_u32(&a)) { - printf("\nmp_get_u32() bad result!"); - goto LBL_ERR; - } + EXPECT(t == mp_get_u32(&a)); } mp_set_ul(&a, 0uL); - if (mp_get_u32(&a) != 0) { - printf("\nmp_get_u32() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_get_u32(&a) == 0); mp_set_ul(&a, UINT32_MAX); - if (mp_get_u32(&a) != UINT32_MAX) { - printf("\nmp_get_u32() bad result!"); - goto LBL_ERR; - } + EXPECT(mp_get_u32(&a) == UINT32_MAX); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -666,10 +595,7 @@ static int test_mp_get_ul(void) do { mp_set_ul(&a, t); s = mp_get_ul(&a); - if (s != t) { - printf("\nmp_get_ul() bad result! 0x%lx != 0x%lx", s, t); - goto LBL_ERR; - } + EXPECT(s == t); t <<= 1; } while (t != 0uL); } @@ -697,10 +623,7 @@ static int test_mp_get_u64(void) do { mp_set_u64(&a, r); q = mp_get_u64(&a); - if (q != r) { - printf("\nmp_get_u64() bad result! 0x%" PRIx64 " != 0x%" PRIx64, q, r); - goto LBL_ERR; - } + EXPECT(q == r); r <<= 1; } while (r != 0u); } @@ -725,15 +648,9 @@ static int test_mp_sqrt(void) fflush(stdout); n = (rand_int() & 15) + 1; DO(mp_rand(&a, n)); - if (mp_sqrt(&a, &b) != MP_OKAY) { - printf("\nmp_sqrt() error!"); - goto LBL_ERR; - } + DO(mp_sqrt(&a, &b)); DO(mp_root_n(&a, 2, &c)); - if (mp_cmp_mag(&b, &c) != MP_EQ) { - printf("mp_sqrt() bad result!\n"); - goto LBL_ERR; - } + EXPECT(mp_cmp_mag(&b, &c) == MP_EQ); } mp_clear_multi(&a, &b, &c, NULL); @@ -760,26 +677,13 @@ static int test_mp_is_square(void) n = (rand_int() & 7) + 1; DO(mp_rand(&a, n)); DO(mp_sqr(&a, &a)); - if (mp_is_square(&a, &res) != MP_OKAY) { - printf("\nfn:mp_is_square() error!"); - goto LBL_ERR; - } - if (!res) { - printf("\nfn:mp_is_square() bad result!"); - goto LBL_ERR; - } + DO(mp_is_square(&a, &res)); + EXPECT(res); /* test for false positives */ DO(mp_add_d(&a, 1u, &a)); - if (mp_is_square(&a, &res) != MP_OKAY) { - printf("\nfp:mp_is_square() error!"); - goto LBL_ERR; - } - if (res) { - printf("\nfp:mp_is_square() bad result!"); - goto LBL_ERR; - } - + DO(mp_is_square(&a, &res)); + EXPECT(!res); } mp_clear_multi(&a, &b, NULL); @@ -811,15 +715,8 @@ static int test_mp_sqrtmod_prime(void) for (i = 0; i < (int)(sizeof(sqrtmod_prime)/sizeof(sqrtmod_prime[0])); ++i) { mp_set_ul(&a, sqrtmod_prime[i].p); mp_set_ul(&b, sqrtmod_prime[i].n); - if (mp_sqrtmod_prime(&b, &a, &c) != MP_OKAY) { - printf("Failed executing %d. mp_sqrtmod_prime\n", (i+1)); - goto LBL_ERR; - } - if (mp_cmp_d(&c, sqrtmod_prime[i].r) != MP_EQ) { - printf("Failed %d. trivial mp_sqrtmod_prime\n", (i+1)); - ndraw(&c, "r"); - goto LBL_ERR; - } + DO(mp_sqrtmod_prime(&b, &a, &c)); + EXPECT(mp_cmp_d(&c, sqrtmod_prime[i].r) == MP_EQ); } mp_clear_multi(&a, &b, &c, NULL); @@ -832,23 +729,15 @@ static int test_mp_sqrtmod_prime(void) static int test_mp_prime_rand(void) { int ix; - mp_err e; mp_int a, b; DOR(mp_init_multi(&a, &b, NULL)); /* test for size */ for (ix = 10; ix < 128; ix++) { - printf("Testing (not safe-prime): %9d bits \r", ix); + printf("Testing (not safe-prime): %9d bits \n", ix); fflush(stdout); - e = mp_prime_rand(&a, 8, ix, (rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON); - if (e != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(e)); - goto LBL_ERR; - } - if (mp_count_bits(&a) != ix) { - printf("Prime is %d not %d bits!!!\n", mp_count_bits(&a), ix); - goto LBL_ERR; - } + DO(mp_prime_rand(&a, 8, ix, (rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON)); + EXPECT(mp_count_bits(&a) == ix); } mp_clear_multi(&a, &b, NULL); @@ -902,31 +791,16 @@ static int test_mp_prime_is_prime(void) for (ix = 16; ix < 128; ix++) { printf("\rTesting ( safe-prime): %9d bits ", ix); fflush(stdout); - e = mp_prime_rand(&a, 8, ix, ((rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON) | MP_PRIME_SAFE); - if (e != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(e)); - goto LBL_ERR; - } - if (mp_count_bits(&a) != ix) { - printf("Prime is %d not %d bits!!!\n", mp_count_bits(&a), ix); - goto LBL_ERR; - } + DO(mp_prime_rand(&a, 8, ix, ((rand_int() & 1) ? 0 : MP_PRIME_2MSB_ON) | MP_PRIME_SAFE)); + EXPECT(mp_count_bits(&a) == ix); /* let's see if it's really a safe prime */ DO(mp_sub_d(&a, 1u, &b)); DO(mp_div_2(&b, &b)); - e = mp_prime_is_prime(&b, mp_prime_rabin_miller_trials(mp_count_bits(&b)), &cnt); - /* small problem */ - if (e != MP_OKAY) { - printf("\nfailed with error: %s\n", mp_error_to_string(e)); - } + DO(mp_prime_is_prime(&b, mp_prime_rabin_miller_trials(mp_count_bits(&b)), &cnt)); /* large problem */ - if (!cnt) { - printf("\nsub is not prime!\n"); - } + EXPECT(cnt); DO(mp_prime_frobenius_underwood(&b, &fu)); - if (!fu) { - printf("\nfrobenius-underwood says sub is not prime!\n"); - } + EXPECT(fu); if ((e != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); DO(mp_fwrite(&a,16,stdout)); @@ -942,15 +816,9 @@ static int test_mp_prime_is_prime(void) DO(mp_read_radix(&a, "FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A63A3620FFFFFFFFFFFFFFFF", 16)); - e = mp_prime_strong_lucas_selfridge(&a, &cnt); - /* small problem */ - if (e != MP_OKAY) { - printf("\nmp_prime_strong_lucas_selfridge failed with error: %s\n", mp_error_to_string(e)); - } + DO(mp_prime_strong_lucas_selfridge(&a, &cnt)); /* large problem */ - if (!cnt) { - printf("\n\nissue #143 - mp_prime_strong_lucas_selfridge FAILED!\n"); - } + EXPECT(cnt); if ((e != MP_OKAY) || !cnt) { printf("prime tested was: 0x"); DO(mp_fwrite(&a,16,stdout)); @@ -1185,10 +1053,7 @@ static int test_mp_cnt_lsb(void) mp_set(&a, 1u); for (ix = 0; ix < 1024; ix++) { - if (mp_cnt_lsb(&a) != ix) { - printf("Failed at %d, %d\n", ix, mp_cnt_lsb(&a)); - goto LBL_ERR; - } + EXPECT(mp_cnt_lsb(&a) == ix); DO(mp_mul_2(&a, &a)); } @@ -1227,10 +1092,7 @@ static int test_mp_reduce_2k(void) DO(mp_copy(&c, &b)); DO(mp_mod(&c, &a, &c)); DO(mp_reduce_2k(&b, &a, 2u)); - if (mp_cmp(&c, &b) != MP_EQ) { - printf("FAILED\n"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &b) == MP_EQ); } } @@ -1261,10 +1123,7 @@ static int test_s_mp_div_3(void) DO(mp_div(&a, &d, &b, &e)); DO(s_mp_div_3(&a, &c, &r2)); - if (mp_cmp(&b, &c) || mp_cmp_d(&e, r2)) { - printf("\ns_mp_div_3 => Failure\n"); - goto LBL_ERR; - } + EXPECT(!mp_cmp(&b, &c) && !mp_cmp_d(&e, r2)); } printf("... passed!"); @@ -1313,10 +1172,7 @@ static int test_mp_dr_reduce(void) mp_dr_setup(&a, &mp); DO(mp_dr_reduce(&c, &a, mp)); - if (mp_cmp(&b, &c) != MP_EQ) { - printf("Failed on trial %u\n", rr); - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &c) == MP_EQ); } while (++rr < 500); printf(" passed"); fflush(stdout); @@ -1356,10 +1212,7 @@ static int test_mp_reduce_2k_l(void) DO(mp_to_radix(&a, buf, sizeof(buf), &length, 10)); printf("\n\np==%s, length = %zu\n", buf, length); /* now mp_reduce_is_2k_l() should return */ - if (mp_reduce_is_2k_l(&a) != 1) { - printf("mp_reduce_is_2k_l() return 0, should be 1\n"); - goto LBL_ERR; - } + EXPECT(mp_reduce_is_2k_l(&a) == 1); DO(mp_reduce_2k_setup_l(&a, &d)); /* now do a million square+1 to see if it varies */ DO(mp_rand(&b, 64)); @@ -1395,7 +1248,6 @@ static int test_mp_reduce_2k_l(void) } /* stripped down version of mp_radix_size. The faster version can be off by up t o +3 */ -/* TODO: This function should be removed, replaced by mp_radix_size, mp_radix_size_overestimate in 2.0 */ static mp_err s_rs(const mp_int *a, int radix, int *size) { mp_err res; @@ -1440,13 +1292,9 @@ static int test_mp_log_n(void) */ mp_set(&a, 42u); base = 0u; - if (mp_log_n(&a, base, &lb) != MP_VAL) { - goto LBL_ERR; - } + EXPECT(mp_log_n(&a, base, &lb) == MP_VAL); base = 1u; - if (mp_log_n(&a, base, &lb) != MP_VAL) { - goto LBL_ERR; - } + EXPECT(mp_log_n(&a, base, &lb) == MP_VAL); /* base a result 2 0 MP_VAL @@ -1456,16 +1304,12 @@ static int test_mp_log_n(void) */ base = 2u; mp_zero(&a); - if (mp_log_n(&a, base, &lb) != MP_VAL) { - goto LBL_ERR; - } + EXPECT(mp_log_n(&a, base, &lb) == MP_VAL); for (d = 1; d < 4; d++) { mp_set(&a, d); DO(mp_log_n(&a, base, &lb)); - if (lb != ((d == 1)?0:1)) { - goto LBL_ERR; - } + EXPECT(lb == ((d == 1)?0:1)); } /* base a result @@ -1476,15 +1320,11 @@ static int test_mp_log_n(void) */ base = 3u; mp_zero(&a); - if (mp_log_n(&a, base, &lb) != MP_VAL) { - goto LBL_ERR; - } + EXPECT(mp_log_n(&a, base, &lb) == MP_VAL); for (d = 1; d < 4; d++) { mp_set(&a, d); DO(mp_log_n(&a, base, &lb)); - if (lb != (((int)d < base)?0:1)) { - goto LBL_ERR; - } + EXPECT(lb == (((int)d < base)?0:1)); } /* @@ -1498,9 +1338,7 @@ static int test_mp_log_n(void) DO(s_rs(&a,(int)base, &size)); /* radix_size includes the memory needed for '\0', too*/ size -= 2; - if (lb != size) { - goto LBL_ERR; - } + EXPECT(lb == size); } /* @@ -1512,9 +1350,7 @@ static int test_mp_log_n(void) DO(mp_log_n(&a, base, &lb)); DO(s_rs(&a,(int)base, &size)); size -= 2; - if (lb != size) { - goto LBL_ERR; - } + EXPECT(lb == size); } /*Test upper edgecase with base UINT32_MAX and number (UINT32_MAX/2)*UINT32_MAX^10 */ @@ -1522,9 +1358,7 @@ static int test_mp_log_n(void) DO(mp_expt_n(&a, 10uL, &a)); DO(mp_add_d(&a, max_base / 2, &a)); DO(mp_log_n(&a, max_base, &lb)); - if (lb != 10u) { - goto LBL_ERR; - } + EXPECT(lb == 10u); mp_clear(&a); return EXIT_SUCCESS; @@ -1542,39 +1376,30 @@ static int test_mp_incr(void) /* Does it increment inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); DO(mp_incr(&a)); - if (mp_cmp_d(&a, (MP_MASK/2u) + 1u) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, (MP_MASK/2u) + 1u) == MP_EQ); /* Does it increment outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); mp_set(&b, MP_MASK); DO(mp_incr(&a)); DO(mp_add_d(&b, 1u, &b)); - if (mp_cmp(&a, &b) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp(&a, &b) == MP_EQ); /* Does it increment from -1 to 0? */ mp_set(&a, 1u); a.sign = MP_NEG; DO(mp_incr(&a)); - if (mp_cmp_d(&a, 0u) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, 0u) == MP_EQ); /* Does it increment from -(MP_MASK + 1) to -MP_MASK? */ mp_set(&a, MP_MASK); DO(mp_add_d(&a, 1u, &a)); a.sign = MP_NEG; DO(mp_incr(&a)); - if (a.sign != MP_NEG) { - goto LBL_ERR; - } + EXPECT(a.sign == MP_NEG); + a.sign = MP_ZPOS; - if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, MP_MASK) == MP_EQ); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -1592,26 +1417,20 @@ static int test_mp_decr(void) /* Does it decrement inside the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK/2); DO(mp_decr(&a)); - if (mp_cmp_d(&a, (MP_MASK/2u) - 1u) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, (MP_MASK/2u) - 1u) == MP_EQ); /* Does it decrement outside of the limits of a MP_xBIT limb? */ mp_set(&a, MP_MASK); DO(mp_add_d(&a, 1u, &a)); DO(mp_decr(&a)); - if (mp_cmp_d(&a, MP_MASK) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, MP_MASK) == MP_EQ); /* Does it decrement from 0 to -1? */ mp_zero(&a); DO(mp_decr(&a)); if (a.sign == MP_NEG) { a.sign = MP_ZPOS; - if (mp_cmp_d(&a, 1u) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp_d(&a, 1u) == MP_EQ); } else { goto LBL_ERR; } @@ -1624,9 +1443,7 @@ static int test_mp_decr(void) b.sign = MP_NEG; DO(mp_sub_d(&b, 1u, &b)); DO(mp_decr(&a)); - if (mp_cmp(&a, &b) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp(&a, &b) == MP_EQ); mp_clear_multi(&a, &b, NULL); return EXIT_SUCCESS; @@ -1852,10 +1669,7 @@ static int test_mp_root_n(void) for (j = 3; j < 100; j++) { DO(mp_root_n(&a, j, &c)); DO(mp_read_radix(&r, root[i][j-3], 10)); - if (mp_cmp(&r, &c) != MP_EQ) { - fprintf(stderr, "mp_root_n failed at input #%d, root #%d\n", i, j); - goto LBL_ERR; - } + EXPECT(mp_cmp(&r, &c) == MP_EQ); } } mp_clear_multi(&a, &c, &r, NULL); @@ -1884,9 +1698,7 @@ static int test_s_mp_mul_balance(void) DO(mp_read_radix(&b, nc, 64)); - if (mp_cmp(&b, &c) != MP_EQ) { - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &c) == MP_EQ); mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; @@ -1907,10 +1719,7 @@ static int test_s_mp_mul_karatsuba(void) DO(mp_rand(&b, size)); DO(s_mp_mul_karatsuba(&a, &b, &c)); DO(s_mp_mul_full(&a,&b,&d)); - if (mp_cmp(&c, &d) != MP_EQ) { - fprintf(stderr, "Karatsuba multiplication failed at size %d\n", size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -1930,10 +1739,7 @@ static int test_s_mp_sqr_karatsuba(void) DO(mp_rand(&a, size)); DO(s_mp_sqr_karatsuba(&a, &b)); DO(s_mp_sqr(&a, &c)); - if (mp_cmp(&b, &c) != MP_EQ) { - fprintf(stderr, "Karatsuba squaring failed at size %d\n", size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &c) == MP_EQ); } mp_clear_multi(&a, &b, &c, NULL); @@ -1969,10 +1775,7 @@ static int test_s_mp_mul_toom(void) DO(mp_mul(&a, &b, &c)); MP_MUL_TOOM_CUTOFF = tc_cutoff; DO(mp_mul(&a, &b, &d)); - if (mp_cmp(&c, &d) != MP_EQ) { - fprintf(stderr, "Toom-Cook 3-way multiplication failed for edgecase f1 * f2\n"); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); #endif for (size = MP_MUL_TOOM_CUTOFF; size < (MP_MUL_TOOM_CUTOFF + 20); size++) { @@ -1980,10 +1783,7 @@ static int test_s_mp_mul_toom(void) DO(mp_rand(&b, size)); DO(s_mp_mul_toom(&a, &b, &c)); DO(s_mp_mul_full(&a,&b,&d)); - if (mp_cmp(&c, &d) != MP_EQ) { - fprintf(stderr, "Toom-Cook 3-way multiplication failed at size %d\n", size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c, &d) == MP_EQ); } mp_clear_multi(&a, &b, &c, &d, NULL); @@ -2003,10 +1803,7 @@ static int test_s_mp_sqr_toom(void) DO(mp_rand(&a, size)); DO(s_mp_sqr_toom(&a, &b)); DO(s_mp_sqr(&a, &c)); - if (mp_cmp(&b, &c) != MP_EQ) { - fprintf(stderr, "Toom-Cook 3-way squaring failed at size %d\n", size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&b, &c) == MP_EQ); } mp_clear_multi(&a, &b, &c, NULL); @@ -2043,18 +1840,10 @@ static int test_mp_radix_size(void) for (radix = 2; radix < 65; radix++) { DO(mp_radix_size(&a, radix, &size)); - if (size != results[radix]) { - fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; - } + EXPECT(size == results[radix]); a.sign = MP_NEG; DO(mp_radix_size(&a, radix, &size)); - if (size != (results[radix] + 1)) { - fprintf(stderr, "mp_radix_size: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; - } + EXPECT(size == (results[radix] + 1)); a.sign = MP_ZPOS; } @@ -2082,16 +1871,8 @@ static int test_s_mp_div_recursive(void) DO(mp_rand(&b, size)); DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "1a. Recursive division failed at sizes %d / %d, wrong quotient\n", - 10 * size, size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "1a. Recursive division failed at sizes %d / %d, wrong remainder\n", - 10 * size, size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); printf("\rsizes = %d / %d", 2 * size, size); /* Relation 10:1 negative numerator*/ @@ -2100,16 +1881,8 @@ static int test_s_mp_div_recursive(void) DO(mp_rand(&b, size)); DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "1b. Recursive division failed at sizes %d / %d, wrong quotient\n", - 10 * size, size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "1b. Recursive division failed at sizes %d / %d, wrong remainder\n", - 10 * size, size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); printf("\rsizes = %d / %d, negative numerator", 2 * size, size); /* Relation 10:1 negative denominator*/ @@ -2118,16 +1891,8 @@ static int test_s_mp_div_recursive(void) DO(mp_neg(&b, &b)); DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "1c. Recursive division failed at sizes %d / %d, wrong quotient\n", - 10 * size, size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "1c. Recursive division failed at sizes %d / %d, wrong remainder\n", - 10 * size, size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); printf("\rsizes = %d / %d, negative denominator", 2 * size, size); /* Relation 2:1 */ @@ -2135,32 +1900,16 @@ static int test_s_mp_div_recursive(void) DO(mp_rand(&b, size)); DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "2. Recursive division failed at sizes %d / %d, wrong quotient\n", - 2 * size, size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "2. Recursive division failed at sizes %d / %d, wrong remainder\n", - 2 * size, size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); printf("\rsizes = %d / %d", 3 * size, 2 * size); /* Upper limit 3:2 */ DO(mp_rand(&a, 3 * size)); DO(mp_rand(&b, 2 * size)); DO(s_mp_div_recursive(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "3. Recursive division failed at sizes %d / %d, wrong quotient\n", - 3 * size, 2 * size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "3. Recursive division failed at sizes %d / %d, wrong remainder\n", - 3 * size, 2 * size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); } mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); @@ -2183,16 +1932,8 @@ static int test_s_mp_div_small(void) DO(mp_rand(&b, size)); DO(s_mp_div_small(&a, &b, &c_q, &c_r)); DO(s_mp_div_school(&a, &b, &d_q, &d_r)); - if (mp_cmp(&c_q, &d_q) != MP_EQ) { - fprintf(stderr, "1. Small division failed at sizes %d / %d, wrong quotient\n", - 2 * size, size); - goto LBL_ERR; - } - if (mp_cmp(&c_r, &d_r) != MP_EQ) { - fprintf(stderr, "1. Small division failed at sizes %d / %d, wrong remainder\n", - 2 * size, size); - goto LBL_ERR; - } + EXPECT(mp_cmp(&c_q, &d_q) == MP_EQ); + EXPECT(mp_cmp(&c_r, &d_r) == MP_EQ); } mp_clear_multi(&a, &b, &c_q, &c_r, &d_q, &d_r, NULL); return EXIT_SUCCESS; @@ -2205,10 +1946,9 @@ static int test_s_mp_div_small(void) static int test_s_mp_radix_size_overestimate(void) { - mp_err err; mp_int a; - int radix; - size_t size; + int radix, n; + size_t size, size2; /* *INDENT-OFF* */ size_t results[65] = { 0u, 0u, 1627u, 1027u, 814u, 702u, 630u, 581u, 543u, @@ -2220,84 +1960,42 @@ static int test_s_mp_radix_size_overestimate(void) 284u, 283u, 281u, 280u, 279u, 278u, 277u, 276u, 275u, 273u, 272u }; - -#if 0 - size_t big_results[65] = { - 0u, 0u, 0u, 1354911329u, 1073741825u, - 924870867u, 830760078u, 764949110u, 715827883u, 677455665u, - 646456994u, 620761988u, 599025415u, 580332018u, 564035582u, - 549665673u, 536870913u, 525383039u, 514993351u, 505536793u, - 496880930u, 488918137u, 481559946u, 474732892u, 468375401u, - 462435434u, 456868672u, 451637110u, 446707948u, 442052707u, - 437646532u, 433467613u, 429496730u, 425716865u, 422112892u, - 418671312u, 415380039u, 412228213u, 409206043u, 406304679u, - 403516096u, 400833001u, 398248746u, 395757256u, 393352972u, - 391030789u, 388786017u, 386614331u, 384511740u, 382474555u, - 380499357u, 378582973u, 376722456u, 374915062u, 373158233u, - 371449582u, 369786879u, 368168034u, 366591092u, 365054217u, - 363555684u, 362093873u, 360667257u, 359274399u, 357913942 - }; -#endif - /* *INDENT-ON* */ - if ((err = mp_init(&a)) != MP_OKAY) goto LBL_ERR; + + DO(mp_init(&a)); /* number to result in a different size for every base: 67^(4 * 67) */ mp_set(&a, 67); - if ((err = mp_expt_n(&a, 268, &a)) != MP_OKAY) { - goto LBL_ERR; - } + DO(mp_expt_n(&a, 268, &a)); for (radix = 2; radix < 65; radix++) { - if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } - if (size < results[radix]) { - fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; - } + DO(s_mp_radix_size_overestimate(&a, radix, &size)); + EXPECT(size >= results[radix]); + EXPECT(size < results[radix] + 20); /* some error bound */ a.sign = MP_NEG; - if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } - if (size < results[radix]) { - fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; - } + DO(s_mp_radix_size_overestimate(&a, radix, &size)); + EXPECT(size >= results[radix]); + EXPECT(size < results[radix] + 20); /* some error bound */ a.sign = MP_ZPOS; } -#if 0 - if ((err = mp_2expt(&a, INT_MAX - 1)) != MP_OKAY) { - goto LBL_ERR; - } - printf("bitcount = %d, alloc = %d\n", mp_count_bits(&a), a.alloc); - /* Start at 3 to avoid integer overflow */ - for (radix = 3; radix < 65; radix++) { - printf("radix = %d, ",radix); - if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } - printf("size = %zu, diff = %zu\n", size, size - big_results[radix]); - if (size < big_results[radix]) { - fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; - } - a.sign = MP_NEG; - if ((err = s_mp_radix_size_overestimate(&a, radix, &size)) != MP_OKAY) { - goto LBL_ERR; - } - if (size < big_results[radix]) { - fprintf(stderr, "s_mp_radix_size_overestimate: result for base %d was %zu instead of %zu\n", - radix, size, results[radix]); - goto LBL_ERR; + /* randomized test */ + for (n = 1; n < 1024; n += 1234) { + DO(mp_rand(&a, n)); + + for (radix = 2; radix < 65; radix++) { + DO(s_mp_radix_size_overestimate(&a, radix, &size)); + DO(mp_radix_size(&a, radix, &size2)); + EXPECT(size >= size2); + EXPECT(size < size2 + 20); /* some error bound */ + a.sign = MP_NEG; + DO(s_mp_radix_size_overestimate(&a, radix, &size)); + DO(mp_radix_size(&a, radix, &size2)); + EXPECT(size >= size2); + EXPECT(size < size2 + 20); /* some error bound */ + a.sign = MP_ZPOS; } - a.sign = MP_ZPOS; } -#endif mp_clear(&a); return EXIT_SUCCESS; From 40177e18e5c7f7b741a65048c6e75c1b92998265 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 5 Dec 2019 11:47:36 +0100 Subject: [PATCH 156/304] test: print __func__ --- demo/shared.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/shared.h b/demo/shared.h index 5eae9732c..2a1ab3c9d 100644 --- a/demo/shared.h +++ b/demo/shared.h @@ -17,8 +17,8 @@ #include "tommath_private.h" -#define EXPECT(a) do { if (!(a)) { fprintf(stderr, "%d: EXPECT(%s) failed\n", __LINE__, #a); goto LBL_ERR; } } while(0) -#define DO_WHAT(a, what) do { mp_err err; if ((err = (a)) != MP_OKAY) { fprintf(stderr, "%d: DO(%s) failed: %s\n", __LINE__, #a, mp_error_to_string(err)); what; } } while(0) +#define EXPECT(a) do { if (!(a)) { fprintf(stderr, "%s, line %d: EXPECT(%s) failed\n", __func__, __LINE__, #a); goto LBL_ERR; } } while(0) +#define DO_WHAT(a, what) do { mp_err err; if ((err = (a)) != MP_OKAY) { fprintf(stderr, "%s, line %d: DO(%s) failed: %s\n", __func__, __LINE__, #a, mp_error_to_string(err)); what; } } while(0) #define DO(a) DO_WHAT(a, goto LBL_ERR) #define DOR(a) DO_WHAT(a, return EXIT_FAILURE) From 876c5fc3f6c6f100d85973eb185d961a2f8f8444 Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Thu, 5 Dec 2019 11:47:36 +0100 Subject: [PATCH 157/304] disable __func__ in c89 compilers --- makefile | 2 ++ tommath_c89.h | 2 ++ 2 files changed, 4 insertions(+) diff --git a/makefile b/makefile index 1cd577886..b24fe85c0 100644 --- a/makefile +++ b/makefile @@ -172,6 +172,7 @@ c89: -e 's/\(PRI[iux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ + -e 's/__func__/MP_FUNCTION_NAME/g' \ *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c c99: @@ -194,6 +195,7 @@ c99: -e 's/MP_\(PRI[iux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ + -e 's/MP_FUNCTION_NAME/__func__/g' \ *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c astyle: diff --git a/tommath_c89.h b/tommath_c89.h index 35fb828c4..e7b87f105 100644 --- a/tommath_c89.h +++ b/tommath_c89.h @@ -36,3 +36,5 @@ typedef __UINT64_TYPE__ mp_u64; #define MP_PRIi64 MP_PRI64_PREFIX "i" #define MP_PRIu64 MP_PRI64_PREFIX "u" #define MP_PRIx64 MP_PRI64_PREFIX "x" + +#define MP_FUNCTION_NAME __func__ From ca6924b7e64f862ffe2140493cfa9bd736366bbb Mon Sep 17 00:00:00 2001 From: Daniel Mendler Date: Mon, 23 Dec 2019 11:12:42 +0100 Subject: [PATCH 158/304] add error code MP_OVF for integer overflow (too many digits) --- mp_error_to_string.c | 2 ++ mp_grow.c | 2 +- mp_init_multi.c | 8 ++++---- mp_init_size.c | 2 +- tommath.h | 3 ++- 5 files changed, 10 insertions(+), 7 deletions(-) diff --git a/mp_error_to_string.c b/mp_error_to_string.c index 1b34d02ed..39adcd124 100644 --- a/mp_error_to_string.c +++ b/mp_error_to_string.c @@ -19,6 +19,8 @@ const char *mp_error_to_string(mp_err code) return "Max. iterations reached"; case MP_BUF: return "Buffer overflow"; + case MP_OVF: + return "Integer overflow"; default: return "Invalid error code"; } diff --git a/mp_grow.c b/mp_grow.c index ff3b96d1e..5bca1b5ff 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -11,7 +11,7 @@ mp_err mp_grow(mp_int *a, int size) mp_digit *dp; if (size > MP_MAX_DIGIT_COUNT) { - return MP_MEM; + return MP_OVF; } /* reallocate the array a->dp diff --git a/mp_init_multi.c b/mp_init_multi.c index 6567cf1f2..908b4df45 100644 --- a/mp_init_multi.c +++ b/mp_init_multi.c @@ -7,14 +7,15 @@ mp_err mp_init_multi(mp_int *mp, ...) { - mp_err err = MP_OKAY; /* Assume ok until proven otherwise */ + mp_err err = MP_OKAY; int n = 0; /* Number of ok inits */ mp_int *cur_arg = mp; va_list args; va_start(args, mp); /* init args to next argument from caller */ while (cur_arg != NULL) { - if (mp_init(cur_arg) != MP_OKAY) { + err = mp_init(cur_arg); + if (err != MP_OKAY) { /* Oops - error! Back-track and mp_clear what we already succeeded in init-ing, then return error. */ @@ -28,14 +29,13 @@ mp_err mp_init_multi(mp_int *mp, ...) cur_arg = va_arg(clean_args, mp_int *); } va_end(clean_args); - err = MP_MEM; break; } n++; cur_arg = va_arg(args, mp_int *); } va_end(args); - return err; /* Assumed ok, if error flagged above. */ + return err; } #endif diff --git a/mp_init_size.c b/mp_init_size.c index 979a0b7d0..e28a3cd49 100644 --- a/mp_init_size.c +++ b/mp_init_size.c @@ -9,7 +9,7 @@ mp_err mp_init_size(mp_int *a, int size) size = MP_MAX(MP_MIN_DIGIT_COUNT, size); if (size > MP_MAX_DIGIT_COUNT) { - return MP_MEM; + return MP_OVF; } /* alloc mem */ diff --git a/tommath.h b/tommath.h index a2e758541..25a166e77 100644 --- a/tommath.h +++ b/tommath.h @@ -100,7 +100,8 @@ typedef enum { MP_MEM = -2, /* out of mem */ MP_VAL = -3, /* invalid input */ MP_ITER = -4, /* maximum iterations reached */ - MP_BUF = -5 /* buffer overflow, supplied buffer too small */ + MP_BUF = -5, /* buffer overflow, supplied buffer too small */ + MP_OVF = -6 /* mp_int overflow, too many digits */ } mp_err; typedef enum { From 4e90f3185aea9160c28f3eaec5625b67fc0f67db Mon Sep 17 00:00:00 2001 From: Daniel Green Date: Sun, 9 Feb 2020 11:06:53 -0500 Subject: [PATCH 159/304] Build+test bn_mp_set_double.c on more platforms Not all platforms/environments/architectures that support enough of IEEE 754 for the purposes of mp_set_double() actually support enough to legitimately define __STDC_IEC_559__, so only relying on that is too strict. Fixes https://github.com/libtom/libtommath/issues/159 --- demo/test.c | 2 +- mp_set_double.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 998f14b35..f719709dc 100644 --- a/demo/test.c +++ b/demo/test.c @@ -522,7 +522,7 @@ static int test_mp_invmod(void) } -#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) +#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) || defined(__i386__) || defined(_M_X86) || defined(__aarch64__) || defined(__arm__) static int test_mp_set_double(void) { int i; diff --git a/mp_set_double.c b/mp_set_double.c index 78550c8f0..cdc644d90 100644 --- a/mp_set_double.c +++ b/mp_set_double.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) +#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) || defined(__i386__) || defined(_M_X86) || defined(__aarch64__) || defined(__arm__) mp_err mp_set_double(mp_int *a, double b) { uint64_t frac; From c5cb0c6f620d28ecb0297253673973defc9aff34 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 5 Mar 2020 13:48:27 +0100 Subject: [PATCH 160/304] fix compile error on MSVC --- demo/test.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-) diff --git a/demo/test.c b/demo/test.c index f719709dc..279e44eba 100644 --- a/demo/test.c +++ b/demo/test.c @@ -523,18 +523,23 @@ static int test_mp_invmod(void) } #if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) || defined(__i386__) || defined(_M_X86) || defined(__aarch64__) || defined(__arm__) + +#ifdef _MSC_VER +#pragma warning(push) +#pragma warning(disable: 4723) /* potential divide by 0 */ +#endif static int test_mp_set_double(void) { int i; + double dbl_zero = 0.0; mp_int a, b; DOR(mp_init_multi(&a, &b, NULL)); - /* test mp_get_double/mp_set_double */ - EXPECT(mp_set_double(&a, +1.0/0.0) == MP_VAL); - EXPECT(mp_set_double(&a, -1.0/0.0) == MP_VAL); - EXPECT(mp_set_double(&a, +0.0/0.0) == MP_VAL); - EXPECT(mp_set_double(&a, -0.0/0.0) == MP_VAL); + EXPECT(mp_set_double(&a, +1.0/dbl_zero) == MP_VAL); + EXPECT(mp_set_double(&a, -1.0/dbl_zero) == MP_VAL); + EXPECT(mp_set_double(&a, +0.0/dbl_zero) == MP_VAL); + EXPECT(mp_set_double(&a, -0.0/dbl_zero) == MP_VAL); for (i = 0; i < 1000; ++i) { int tmp = rand_int(); @@ -552,6 +557,9 @@ static int test_mp_set_double(void) return EXIT_FAILURE; } +#ifdef _MSC_VER +#pragma warning(pop) +#endif #endif static int test_mp_get_u32(void) From c1cf80738219dbd70cba0c0c1244698aad842ec7 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 5 Mar 2020 13:57:07 +0100 Subject: [PATCH 161/304] introduce MP_HAS_SET_DOUBLE --- demo/test.c | 4 ++-- mp_set_double.c | 2 +- tommath_private.h | 7 +++++++ 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/demo/test.c b/demo/test.c index 279e44eba..98a8499fc 100644 --- a/demo/test.c +++ b/demo/test.c @@ -522,7 +522,7 @@ static int test_mp_invmod(void) } -#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) || defined(__i386__) || defined(_M_X86) || defined(__aarch64__) || defined(__arm__) +#if defined(MP_HAS_SET_DOUBLE) #ifdef _MSC_VER #pragma warning(push) @@ -2172,7 +2172,7 @@ static int unit_tests(int argc, char **argv) T1(mp_reduce_2k_l, MP_REDUCE_2K_L), T1(mp_radix_size, MP_RADIX_SIZE), T1(s_mp_radix_size_overestimate, S_MP_RADIX_SIZE_OVERESTIMATE), -#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) +#if defined(MP_HAS_SET_DOUBLE) T1(mp_set_double, MP_SET_DOUBLE), #endif T1(mp_signed_rsh, MP_SIGNED_RSH), diff --git a/mp_set_double.c b/mp_set_double.c index cdc644d90..0ede359c6 100644 --- a/mp_set_double.c +++ b/mp_set_double.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) || defined(__i386__) || defined(_M_X86) || defined(__aarch64__) || defined(__arm__) +#if defined(MP_HAS_SET_DOUBLE) mp_err mp_set_double(mp_int *a, double b) { uint64_t frac; diff --git a/tommath_private.h b/tommath_private.h index 0096479ec..0c94831f8 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -164,6 +164,13 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT */ #define MP_MAX_DIGIT_COUNT ((INT_MAX - 2) / MP_DIGIT_BIT) +#if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) \ + || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) \ + || defined(__i386__) || defined(_M_X86) \ + || defined(__aarch64__) || defined(__arm__) +#define MP_HAS_SET_DOUBLE +#endif + /* random number source */ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); From ea654566071da61ccfdbc548ba294e5268ad8795 Mon Sep 17 00:00:00 2001 From: Daniel Green Date: Sun, 23 Feb 2020 09:46:12 -0500 Subject: [PATCH 162/304] Give correct values for invmod with modulus of 1 --- demo/test.c | 5 +---- mp_invmod.c | 6 ++++++ tommath_class.h | 1 + 3 files changed, 8 insertions(+), 4 deletions(-) diff --git a/demo/test.c b/demo/test.c index 98a8499fc..2d1d774b7 100644 --- a/demo/test.c +++ b/demo/test.c @@ -135,10 +135,7 @@ static int test_trivial_stuff(void) mp_set(&b, 1u); DO(mp_neg(&b, &b)); mp_set(&c, 1u); - /* I expected this works, but somehow the computer sez no - * DO(mp_exptmod(&a, &b, &c, &d)); - */ - EXPECT(mp_exptmod(&a, &b, &c, &d) != MP_OKAY); + DO(mp_exptmod(&a, &b, &c, &d)); mp_set(&c, 7u); /* same here */ diff --git a/mp_invmod.c b/mp_invmod.c index e19c067e2..2494acbf6 100644 --- a/mp_invmod.c +++ b/mp_invmod.c @@ -6,6 +6,12 @@ /* hac 14.61, pp608 */ mp_err mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) { + /* for all n in N and n > 0, n = 0 mod 1 */ + if (!mp_isneg(a) && mp_cmp_d(b, 1uL) == MP_EQ) { + mp_zero(c); + return MP_OKAY; + } + /* b cannot be negative and has to be >1 */ if (mp_isneg(b) || (mp_cmp_d(b, 1uL) != MP_GT)) { return MP_VAL; diff --git a/tommath_class.h b/tommath_class.h index 5e76e6a8f..0fe046f34 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -440,6 +440,7 @@ #if defined(MP_INVMOD_C) # define MP_CMP_D_C +# define MP_ZERO_C # define S_MP_INVMOD_C # define S_MP_INVMOD_ODD_C #endif From f01cc5d266b888405fd4a0c3c080871044c42715 Mon Sep 17 00:00:00 2001 From: J08nY Date: Fri, 21 Feb 2020 11:44:15 +0100 Subject: [PATCH 163/304] Fix clang detection when cross-compiling. `echo` needs -e to output newlines, without the switch make complains: :1:17: warning: extra tokens at end of #ifdef directive :1: error: unterminated #ifdef and does not detect clang properly when cross-compiling. --- makefile_include.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/makefile_include.mk b/makefile_include.mk index be53ba7b5..0266da123 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -26,7 +26,7 @@ ifeq ($(PLATFORM),FreeBSD) # XXX: FreeBSD needs extra escaping for some reason CSTR := $$$(CSTR) endif -ifneq (,$(shell echo $(CSTR) | $(CC) -E - | grep CLANG)) +ifneq (,$(shell printf $(CSTR) | $(CC) -E - | grep CLANG)) CC := $(CROSS_COMPILE)clang else CC := $(CROSS_COMPILE)gcc From 56dc9df1a68eb911b818b048c0278bbda02a225b Mon Sep 17 00:00:00 2001 From: Sizhe Zhao Date: Sun, 26 Apr 2020 11:36:28 +0800 Subject: [PATCH 164/304] Add _M_IX86 for testing for MSVC x86 --- tommath_private.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tommath_private.h b/tommath_private.h index 0c94831f8..624ba0a47 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -166,7 +166,7 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT #if defined(__STDC_IEC_559__) || defined(__GCC_IEC_559) \ || defined(__x86_64__) || defined(_M_X64) || defined(_M_AMD64) \ - || defined(__i386__) || defined(_M_X86) \ + || defined(__i386__) || defined(_M_X86) || defined(_M_IX86) \ || defined(__aarch64__) || defined(__arm__) #define MP_HAS_SET_DOUBLE #endif From fb305e093d9f6ee80757f6dc106b229136f7a1bf Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 5 Aug 2020 15:18:59 +0200 Subject: [PATCH 165/304] Additional input checks and a test for b \cong 0 (mod a) in test_mp_sqrtmod_prime to go along with it. --- demo/test.c | 14 +++++++++++--- mp_sqrtmod_prime.c | 47 ++++++++++++++++++++++++++++++---------------- tommath_class.h | 2 +- 3 files changed, 43 insertions(+), 20 deletions(-) diff --git a/demo/test.c b/demo/test.c index 2d1d774b7..f6b3c36eb 100644 --- a/demo/test.c +++ b/demo/test.c @@ -707,9 +707,9 @@ static int test_mp_sqrtmod_prime(void) }; static struct mp_sqrtmod_prime_st sqrtmod_prime[] = { - { 5, 14, 3 }, - { 7, 9, 4 }, - { 113, 2, 62 } + { 5, 14, 3 }, /* 5 \cong 1 (mod 4) */ + { 7, 9, 4 }, /* 7 \cong 3 (mod 4) */ + { 113, 2, 62 } /* 113 \cong 1 (mod 4) */ }; int i; @@ -723,6 +723,14 @@ static int test_mp_sqrtmod_prime(void) DO(mp_sqrtmod_prime(&b, &a, &c)); EXPECT(mp_cmp_d(&c, sqrtmod_prime[i].r) == MP_EQ); } + /* Check handling of wrong input (here: modulus is square and cong. 1 mod 4,24 ) */ + mp_set_ul(&a, 25); + mp_set_ul(&b, 2); + EXPECT(mp_sqrtmod_prime(&b, &a, &c) == MP_VAL); + /* b \cong 0 (mod a) */ + mp_set_ul(&a, 45); + mp_set_ul(&b, 3); + EXPECT(mp_sqrtmod_prime(&b, &a, &c) == MP_VAL); mp_clear_multi(&a, &b, &c, NULL); return EXIT_SUCCESS; diff --git a/mp_sqrtmod_prime.c b/mp_sqrtmod_prime.c index 893018498..0fae1d02a 100644 --- a/mp_sqrtmod_prime.c +++ b/mp_sqrtmod_prime.c @@ -13,19 +13,23 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) { mp_err err; int legendre; - mp_int t1, C, Q, S, Z, M, T, R, two; - mp_digit i; + /* The type is "int" because of the types in the mp_int struct. + Don't forget to change them here when you change them there! */ + int S, M, i; + mp_int t1, C, Q, Z, T, R, two; /* first handle the simple cases */ if (mp_cmp_d(n, 0uL) == MP_EQ) { mp_zero(ret); return MP_OKAY; } - if (mp_cmp_d(prime, 2uL) == MP_EQ) return MP_VAL; /* prime must be odd */ - if ((err = mp_kronecker(n, prime, &legendre)) != MP_OKAY) return err; - if (legendre == -1) return MP_VAL; /* quadratic non-residue mod prime */ + /* "prime" must be odd and > 2 */ + if (mp_iseven(prime) || (mp_cmp_d(prime, 3uL) == MP_LT)) return MP_VAL; + if ((err = mp_kronecker(n, prime, &legendre)) != MP_OKAY) return err; + /* n \not\cong 0 (mod p) and n \cong r^2 (mod p) for some r \in N^+ */ + if (legendre != 1) return MP_VAL; - if ((err = mp_init_multi(&t1, &C, &Q, &S, &Z, &M, &T, &R, &two, NULL)) != MP_OKAY) { + if ((err = mp_init_multi(&t1, &C, &Q, &Z, &T, &R, &two, NULL)) != MP_OKAY) { return err; } @@ -33,8 +37,8 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) * compute directly: err = n^(prime+1)/4 mod prime * Handbook of Applied Cryptography algorithm 3.36 */ - if ((err = mp_mod_d(prime, 4uL, &i)) != MP_OKAY) goto LBL_END; - if (i == 3u) { + /* x%4 == x&3 for x in N and x>0 */ + if ((prime->dp[0] & 3u) == 3u) { if ((err = mp_add_d(prime, 1uL, &t1)) != MP_OKAY) goto LBL_END; if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto LBL_END; if ((err = mp_div_2(&t1, &t1)) != MP_OKAY) goto LBL_END; @@ -49,12 +53,12 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) if ((err = mp_copy(prime, &Q)) != MP_OKAY) goto LBL_END; if ((err = mp_sub_d(&Q, 1uL, &Q)) != MP_OKAY) goto LBL_END; /* Q = prime - 1 */ - mp_zero(&S); + S = 0; /* S = 0 */ while (mp_iseven(&Q)) { if ((err = mp_div_2(&Q, &Q)) != MP_OKAY) goto LBL_END; /* Q = Q / 2 */ - if ((err = mp_add_d(&S, 1uL, &S)) != MP_OKAY) goto LBL_END; + S++; /* S = S + 1 */ } @@ -63,6 +67,12 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* Z = 2 */ for (;;) { if ((err = mp_kronecker(&Z, prime, &legendre)) != MP_OKAY) goto LBL_END; + /* If "prime" (p) is an odd prime Jacobi(k|p) = 0 for k \cong 0 (mod p) */ + /* but there is at least one non-quadratic residue before k>=p if p is an odd prime. */ + if (legendre == 0) { + err = MP_VAL; + goto LBL_END; + } if (legendre == -1) break; if ((err = mp_add_d(&Z, 1uL, &Z)) != MP_OKAY) goto LBL_END; /* Z = Z + 1 */ @@ -77,7 +87,7 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* R = n ^ ((Q + 1) / 2) mod prime */ if ((err = mp_exptmod(n, &Q, prime, &T)) != MP_OKAY) goto LBL_END; /* T = n ^ Q mod prime */ - if ((err = mp_copy(&S, &M)) != MP_OKAY) goto LBL_END; + M = S; /* M = S */ mp_set(&two, 2uL); @@ -86,16 +96,21 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) i = 0; for (;;) { if (mp_cmp_d(&t1, 1uL) == MP_EQ) break; + /* No exponent in the range 0 < i < M found + (M is at least 1 in the first round because "prime" > 2) */ + if (M == i) { + err = MP_VAL; + goto LBL_END; + } if ((err = mp_exptmod(&t1, &two, prime, &t1)) != MP_OKAY) goto LBL_END; i++; } - if (i == 0u) { + if (i == 0) { if ((err = mp_copy(&R, ret)) != MP_OKAY) goto LBL_END; err = MP_OKAY; goto LBL_END; } - if ((err = mp_sub_d(&M, i, &t1)) != MP_OKAY) goto LBL_END; - if ((err = mp_sub_d(&t1, 1uL, &t1)) != MP_OKAY) goto LBL_END; + mp_set_i32(&t1, M - i - 1); if ((err = mp_exptmod(&two, &t1, prime, &t1)) != MP_OKAY) goto LBL_END; /* t1 = 2 ^ (M - i - 1) */ if ((err = mp_exptmod(&C, &t1, prime, &t1)) != MP_OKAY) goto LBL_END; @@ -106,12 +121,12 @@ mp_err mp_sqrtmod_prime(const mp_int *n, const mp_int *prime, mp_int *ret) /* R = (R * t1) mod prime */ if ((err = mp_mulmod(&T, &C, prime, &T)) != MP_OKAY) goto LBL_END; /* T = (T * C) mod prime */ - mp_set(&M, i); + M = i; /* M = i */ } LBL_END: - mp_clear_multi(&t1, &C, &Q, &S, &Z, &M, &T, &R, &two, NULL); + mp_clear_multi(&t1, &C, &Q, &Z, &T, &R, &two, NULL); return err; } diff --git a/tommath_class.h b/tommath_class.h index 0fe046f34..68055cce2 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -872,12 +872,12 @@ # define MP_CMP_D_C # define MP_COPY_C # define MP_DIV_2_C -# define MP_DIV_D_C # define MP_EXPTMOD_C # define MP_INIT_MULTI_C # define MP_KRONECKER_C # define MP_MULMOD_C # define MP_SET_C +# define MP_SET_I32_C # define MP_SQRMOD_C # define MP_SUB_D_C # define MP_ZERO_C From 3ba04963f51161a589740f755cb47684aabb5944 Mon Sep 17 00:00:00 2001 From: Anonymous Maarten Date: Fri, 11 Sep 2020 16:04:19 +0200 Subject: [PATCH 166/304] enable building dll's using makefile.msvc --- .gitignore | 3 +++ makefile.msvc | 19 ++++++++++++++----- s_mp_rand_platform.c | 23 +++++++++++++++++++++++ tommath.def | 5 +++++ 4 files changed, 45 insertions(+), 5 deletions(-) diff --git a/.gitignore b/.gitignore index 61495ec6f..696e0ec95 100644 --- a/.gitignore +++ b/.gitignore @@ -5,6 +5,9 @@ *.gcda *.gcno *.gcov +*.dll +*.exp +*.pdb *.lib *.tmp [Dd]ebug/ diff --git a/makefile.msvc b/makefile.msvc index 031f1c847..43e2bd2fb 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -12,13 +12,16 @@ #The following can be overridden from command line e.g. make -f makefile.msvc CC=gcc ARFLAGS=rcs PREFIX = c:\devel CFLAGS = /Ox +LDFLAGS = #Compilation flags LTM_CFLAGS = /nologo /I./ /D_CRT_SECURE_NO_WARNINGS /D_CRT_NONSTDC_NO_DEPRECATE /D__STDC_WANT_SECURE_LIB__=1 /D_CRT_HAS_CXX17=0 /Wall /wd4146 /wd4127 /wd4668 /wd4710 /wd4711 /wd4820 /wd5045 /WX $(CFLAGS) -LTM_LDFLAGS = advapi32.lib +LTM_LDFLAGS = $(LDFLAGS) advapi32.lib -#Libraries to be created (this makefile builds only static libraries) -LIBMAIN_S =tommath.lib +#Libraries to be created +LIBMAIN_S = tommath.lib +LIBMAIN_I = tommath.dll.lib +LIBMAIN_D = tommath.dll #List of objects to compile (all goes to tommath.lib) OBJECTS=mp_2expt.obj mp_abs.obj mp_add.obj mp_add_d.obj mp_addmod.obj mp_and.obj mp_clamp.obj mp_clear.obj mp_clear_multi.obj \ @@ -62,12 +65,16 @@ $(OBJECTS): $(HEADERS) $(LIBMAIN_S): $(OBJECTS) lib /out:$(LIBMAIN_S) $(OBJECTS) +#Create DLL + import library tommath.dll.lib +$(LIBMAIN_D) $(LIBMAIN_I): $(OBJECTS) tommath.def + link /dll /out:$(LIBMAIN_D) /implib:$(LIBMAIN_I) /def:tommath.def $(LTM_LDFLAGS) $(OBJECTS) + #Build test suite test.exe: $(LIBMAIN_S) demo/shared.obj demo/test.obj cl $(LTM_CFLAGS) $(TOBJECTS) $(LIBMAIN_S) $(LTM_LDFLAGS) demo/shared.c demo/test.c /Fe$@ @echo NOTICE: start the tests by launching test.exe -all: $(LIBMAIN_S) test.exe +all: $(LIBMAIN_S) test.exe $(LIBMAIN_D) tune: $(LIBMAIN_S) $(MAKE) -C etc tune @@ -77,9 +84,11 @@ clean: @-cmd /c del /Q /S *.OBJ *.LIB *.EXE *.DLL 2>nul #Install the library + headers -install: $(LIBMAIN_S) +install: $(LIBMAIN_S) $(LIBMAIN_I) $(LIBMAIN_D) cmd /c if not exist "$(PREFIX)\bin" mkdir "$(PREFIX)\bin" cmd /c if not exist "$(PREFIX)\lib" mkdir "$(PREFIX)\lib" cmd /c if not exist "$(PREFIX)\include" mkdir "$(PREFIX)\include" copy /Y $(LIBMAIN_S) "$(PREFIX)\lib" + copy /Y $(LIBMAIN_I) "$(PREFIX)\lib" + copy /Y $(LIBMAIN_D) "$(PREFIX)\bin" copy /Y tommath*.h "$(PREFIX)\include" diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 06b2f1bda..f4d6812e1 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -14,6 +14,13 @@ static mp_err s_read_arc4random(void *p, size_t n) arc4random_buf(p, n); return MP_OKAY; } +#else +static mp_err s_read_arc4random(void *p, size_t n) +{ + (void)p; + (void)n; + return MP_ERR; +} #endif #if defined(_WIN32) @@ -72,6 +79,15 @@ static mp_err s_read_getrandom(void *p, size_t n) #endif #endif +#ifndef S_READ_GETRANDOM_C +static mp_err s_read_getrandom(void *p, size_t n) +{ + (void)p; + (void)n; + return MP_ERR; +} +#endif + /* We assume all platforms besides windows provide "/dev/urandom". * In case yours doesn't, define MP_NO_DEV_URANDOM at compile-time. */ @@ -110,6 +126,13 @@ static mp_err s_read_urandom(void *p, size_t n) close(fd); return MP_OKAY; } +#else +static mp_err s_read_urandom(void *p, size_t n) +{ + (void)p; + (void)n; + return MP_ERR; +} #endif mp_err s_read_arc4random(void *p, size_t n); diff --git a/tommath.def b/tommath.def index 7d53508a4..f0a9703f0 100644 --- a/tommath.def +++ b/tommath.def @@ -89,6 +89,7 @@ EXPORTS mp_radix_size mp_radix_size_overestimate mp_rand + mp_rand_source mp_read_radix mp_reduce mp_reduce_2k @@ -124,3 +125,7 @@ EXPORTS mp_unpack mp_xor mp_zero + MP_MUL_KARATSUBA_CUTOFF + MP_SQR_KARATSUBA_CUTOFF + MP_MUL_TOOM_CUTOFF + MP_SQR_TOOM_CUTOFF From d138abc3a36073d1f19aa52f810e8692846e180e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 13 Sep 2020 14:19:10 +0200 Subject: [PATCH 167/304] split-up mp_rand.c --- libtommath_VS2008.vcproj | 4 ++++ makefile | 24 ++++++++++++------------ makefile.mingw | 24 ++++++++++++------------ makefile.msvc | 24 ++++++++++++------------ makefile.shared | 24 ++++++++++++------------ makefile.unix | 24 ++++++++++++------------ mp_rand.c | 7 ------- mp_rand_source.c | 12 ++++++++++++ tommath_class.h | 7 +++++-- 9 files changed, 81 insertions(+), 69 deletions(-) create mode 100644 mp_rand_source.c diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 192ed0f0d..6b0924dcd 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -648,6 +648,10 @@ RelativePath="mp_rand.c" > + + diff --git a/makefile b/makefile index b24fe85c0..100f99ab8 100644 --- a/makefile +++ b/makefile @@ -38,18 +38,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ -mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ -mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ -s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ -s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ -s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ -s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ -s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_rand_source.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index aab267fb3..fde087ac3 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -40,18 +40,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ -mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ -mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ -s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ -s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ -s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ -s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ -s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_rand_source.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 43e2bd2fb..a03245599 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -36,18 +36,18 @@ mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj mp_montgomery_setu mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj \ mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj \ mp_prime_rabin_miller_trials.obj mp_prime_rand.obj mp_prime_strong_lucas_selfridge.obj mp_radix_size.obj \ -mp_radix_size_overestimate.obj mp_rand.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj mp_reduce_2k_l.obj \ -mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj mp_reduce_setup.obj \ -mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj mp_set_l.obj \ -mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj mp_sqrtmod_prime.obj \ -mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj mp_unpack.obj mp_xor.obj \ -mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj \ -s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log.obj \ -s_mp_log_2expt.obj s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj \ -s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj \ -s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_radix_size_overestimate.obj \ -s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj \ -s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +mp_radix_size_overestimate.obj mp_rand.obj mp_rand_source.obj mp_read_radix.obj mp_reduce.obj mp_reduce_2k.obj \ +mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_2k.obj mp_reduce_is_2k_l.obj \ +mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ +mp_set_l.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj \ +mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ +mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj \ +s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_get_bit.obj s_mp_invmod.obj \ +s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_2expt.obj s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ +s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ +s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj \ +s_mp_radix_size_overestimate.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ +s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 5e19c3bc9..2d8b32c7d 100644 --- a/makefile.shared +++ b/makefile.shared @@ -35,18 +35,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ -mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ -mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ -s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ -s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ -s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ -s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ -s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_rand_source.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index f2a918cf5..3304e7f07 100644 --- a/makefile.unix +++ b/makefile.unix @@ -41,18 +41,18 @@ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ mp_prime_rabin_miller_trials.o mp_prime_rand.o mp_prime_strong_lucas_selfridge.o mp_radix_size.o \ -mp_radix_size_overestimate.o mp_rand.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o mp_reduce_2k_l.o \ -mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o mp_reduce_setup.o \ -mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o mp_set_l.o \ -mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o mp_sqrtmod_prime.o \ -mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o mp_unpack.o mp_xor.o \ -mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o \ -s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log.o \ -s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o \ -s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o \ -s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o \ -s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o \ -s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_radix_size_overestimate.o mp_rand.o mp_rand_source.o mp_read_radix.o mp_reduce.o mp_reduce_2k.o \ +mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o mp_reduce_is_2k_l.o \ +mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ +mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ +mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ +mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_bit.o s_mp_invmod.o \ +s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/mp_rand.c b/mp_rand.c index df665b7ba..19364755a 100644 --- a/mp_rand.c +++ b/mp_rand.c @@ -3,13 +3,6 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -mp_err(*s_mp_rand_source)(void *out, size_t size) = s_mp_rand_platform; - -void mp_rand_source(mp_err(*source)(void *out, size_t size)) -{ - s_mp_rand_source = (source == NULL) ? s_mp_rand_platform : source; -} - mp_err mp_rand(mp_int *a, int digits) { int i; diff --git a/mp_rand_source.c b/mp_rand_source.c new file mode 100644 index 000000000..e9e876948 --- /dev/null +++ b/mp_rand_source.c @@ -0,0 +1,12 @@ +#include "tommath_private.h" +#ifdef MP_RAND_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_err(*s_mp_rand_source)(void *out, size_t size) = s_mp_rand_platform; + +void mp_rand_source(mp_err(*source)(void *out, size_t size)) +{ + s_mp_rand_source = (source == NULL) ? s_mp_rand_platform : source; +} +#endif diff --git a/tommath_class.h b/tommath_class.h index 68055cce2..d6f7e7a51 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -95,6 +95,7 @@ # define MP_RADIX_SIZE_C # define MP_RADIX_SIZE_OVERESTIMATE_C # define MP_RAND_C +# define MP_RAND_SOURCE_C # define MP_READ_RADIX_C # define MP_REDUCE_C # define MP_REDUCE_2K_C @@ -698,12 +699,14 @@ #if defined(MP_RAND_C) # define MP_GROW_C -# define MP_RAND_SOURCE_C # define MP_ZERO_C -# define S_MP_RAND_PLATFORM_C # define S_MP_RAND_SOURCE_C #endif +#if defined(MP_RAND_SOURCE_C) +# define S_MP_RAND_PLATFORM_C +#endif + #if defined(MP_READ_RADIX_C) # define MP_ADD_D_C # define MP_MUL_D_C From 646523e699940746223af237d3e52dae233a1c95 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 13 Sep 2020 14:19:30 +0200 Subject: [PATCH 168/304] add cutoff's to exported symbols --- helper.pl | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/helper.pl b/helper.pl index b3a30a051..20b0dc91d 100755 --- a/helper.pl +++ b/helper.pl @@ -436,6 +436,10 @@ sub generate_def { ; EXPORTS $files + MP_MUL_KARATSUBA_CUTOFF + MP_SQR_KARATSUBA_CUTOFF + MP_MUL_TOOM_CUTOFF + MP_SQR_TOOM_CUTOFF "; return 0; } From 301e2c4173f2d8bc8f02fd8a136896e237b0a037 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 13 Sep 2020 14:59:39 +0200 Subject: [PATCH 169/304] Partially revert "enable building dll's using makefile.msvc" This partially reverts commit b206dde88e4affae07970782498afe9e3664ae30. --- s_mp_rand_platform.c | 23 ----------------------- 1 file changed, 23 deletions(-) diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index f4d6812e1..06b2f1bda 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -14,13 +14,6 @@ static mp_err s_read_arc4random(void *p, size_t n) arc4random_buf(p, n); return MP_OKAY; } -#else -static mp_err s_read_arc4random(void *p, size_t n) -{ - (void)p; - (void)n; - return MP_ERR; -} #endif #if defined(_WIN32) @@ -79,15 +72,6 @@ static mp_err s_read_getrandom(void *p, size_t n) #endif #endif -#ifndef S_READ_GETRANDOM_C -static mp_err s_read_getrandom(void *p, size_t n) -{ - (void)p; - (void)n; - return MP_ERR; -} -#endif - /* We assume all platforms besides windows provide "/dev/urandom". * In case yours doesn't, define MP_NO_DEV_URANDOM at compile-time. */ @@ -126,13 +110,6 @@ static mp_err s_read_urandom(void *p, size_t n) close(fd); return MP_OKAY; } -#else -static mp_err s_read_urandom(void *p, size_t n) -{ - (void)p; - (void)n; - return MP_ERR; -} #endif mp_err s_read_arc4random(void *p, size_t n); From fa94aa2044c2f709a09c15c552dd6b6c8ac8db11 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 13 Sep 2020 15:26:42 +0200 Subject: [PATCH 170/304] add travis job to compare symbols of dynamic libraries --- .travis.yml | 7 +++++++ testme.sh | 23 +++++++++++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/.travis.yml b/.travis.yml index d8aa8856d..4c6e557b8 100644 --- a/.travis.yml +++ b/.travis.yml @@ -72,6 +72,13 @@ matrix: packages: - astyle + # Check public symbols of dynamic libraries + - env: BUILDOPTIONS='--symbols' + addons: + apt: + packages: + - libtool-bin + # Run always with valgrind (no sanitizer, but debug info) - env: COMPILE_DEBUG=1 BUILDOPTIONS='--with-cc=gcc-4.9 --with-m64 --with-valgrind' addons: diff --git a/testme.sh b/testme.sh index 1a03f55a9..41a165bcd 100755 --- a/testme.sh +++ b/testme.sh @@ -195,6 +195,7 @@ VALGRIND_OPTS=" --leak-check=full --show-leak-kinds=all --error-exitcode=1 " #VALGRIND_OPTS="" VALGRIND_BIN="" CHECK_FORMAT="" +CHECK_SYMBOLS="" C89="" C89_C99_ROUNDTRIP="" TUNE_CMD="./etc/tune -t -r 10 -L 3" @@ -276,6 +277,9 @@ do --format) CHECK_FORMAT="1" ;; + --symbols) + CHECK_SYMBOLS="1" + ;; --all) COMPILERS="gcc clang" ARCHFLAGS="-m64 -m32 -mx32" @@ -309,6 +313,25 @@ then exit $? fi +if [[ "$CHECK_SYMBOLS" == "1" ]] +then + make -f makefile.shared + cat << EOF + + +The following list shows the discrepancy between +the shared library and the Windows dynamic library. +To fix this error, one of the following things +has to be done: +* the script which generates tommath.def has to be modified + (function generate_def() in helper.pl). +* The exported symbols are really different for some reason + This has to be manually investigated. + +EOF + exit $(comm -3 <(nm -D --defined-only .libs/libtommath.so | cut -d' ' -f3 | grep -v '^_' | sort) <(tail -n+9 tommath.def | tr -d ' ' | sort) | tee /dev/tty | wc -l) +fi + if [[ "$CHECK_FORMAT" == "1" ]] then make astyle From 34e16d3c550e98cbd3222987e4d95649cac9bc20 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 13 Sep 2020 19:06:43 +0200 Subject: [PATCH 171/304] allow testing of shared library * move jenkins' prng out of the library into the demo's. * add CI test for shared library --- .travis.yml | 7 ++++ .../s_mp_rand_jenkins.c | 7 +++- demo/test.c | 41 +++++++++++-------- etc/makefile | 17 ++++---- etc/tune.c | 6 ++- libtommath_VS2008.vcproj | 4 -- makefile | 6 +-- makefile.mingw | 4 +- makefile.msvc | 4 +- makefile.shared | 6 +-- makefile.unix | 4 +- testme.sh | 2 +- tommath_class.h | 5 --- tommath_private.h | 4 -- 14 files changed, 62 insertions(+), 55 deletions(-) rename s_mp_rand_jenkins.c => demo/s_mp_rand_jenkins.c (87%) diff --git a/.travis.yml b/.travis.yml index 4c6e557b8..0f3e7fb65 100644 --- a/.travis.yml +++ b/.travis.yml @@ -86,6 +86,13 @@ matrix: packages: - gcc-4.9 + # Shared library build + - env: COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc --make-option=-f --make-option=makefile.shared' + addons: + apt: + packages: + - libtool-bin + # GCC for the 32-bit architecture (no valgrind) - env: BUILDOPTIONS='--with-cc=gcc-5 --with-m32' addons: diff --git a/s_mp_rand_jenkins.c b/demo/s_mp_rand_jenkins.c similarity index 87% rename from s_mp_rand_jenkins.c rename to demo/s_mp_rand_jenkins.c index 6aba0fb2b..9c77142ad 100644 --- a/s_mp_rand_jenkins.c +++ b/demo/s_mp_rand_jenkins.c @@ -5,6 +5,9 @@ /* Bob Jenkins' http://burtleburtle.net/bob/rand/smallprng.html */ /* Chosen for speed and a good "mix" */ + +/* TODO: jenkins prng is not thread safe as of now */ + typedef struct { uint64_t a; uint64_t b; @@ -25,7 +28,7 @@ static uint64_t s_rand_jenkins_val(void) return jenkins_x.d; } -void s_mp_rand_jenkins_init(uint64_t seed) +static void s_mp_rand_jenkins_init(uint64_t seed) { int i; jenkins_x.a = 0xF1EA5EEDuL; @@ -35,7 +38,7 @@ void s_mp_rand_jenkins_init(uint64_t seed) } } -mp_err s_mp_rand_jenkins(void *p, size_t n) +static mp_err s_mp_rand_jenkins(void *p, size_t n) { char *q = (char *)p; while (n > 0u) { diff --git a/demo/test.c b/demo/test.c index f6b3c36eb..4ce813140 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1,10 +1,13 @@ #include #include "shared.h" +#define S_MP_RAND_JENKINS_C +#include "s_mp_rand_jenkins.c" + static long rand_long(void) { long x; - if (s_mp_rand_source(&x, sizeof(x)) != MP_OKAY) { + if (s_mp_rand_jenkins(&x, sizeof(x)) != MP_OKAY) { fprintf(stderr, "s_mp_rand_source failed\n"); exit(EXIT_FAILURE); } @@ -14,7 +17,7 @@ static long rand_long(void) static int rand_int(void) { int x; - if (s_mp_rand_source(&x, sizeof(x)) != MP_OKAY) { + if (s_mp_rand_jenkins(&x, sizeof(x)) != MP_OKAY) { fprintf(stderr, "s_mp_rand_source failed\n"); exit(EXIT_FAILURE); } @@ -24,7 +27,7 @@ static int rand_int(void) static int32_t rand_int32(void) { int32_t x; - if (s_mp_rand_source(&x, sizeof(x)) != MP_OKAY) { + if (s_mp_rand_jenkins(&x, sizeof(x)) != MP_OKAY) { fprintf(stderr, "s_mp_rand_source failed\n"); exit(EXIT_FAILURE); } @@ -34,7 +37,7 @@ static int32_t rand_int32(void) static int64_t rand_int64(void) { int64_t x; - if (s_mp_rand_source(&x, sizeof(x)) != MP_OKAY) { + if (s_mp_rand_jenkins(&x, sizeof(x)) != MP_OKAY) { fprintf(stderr, "s_mp_rand_source failed\n"); exit(EXIT_FAILURE); } @@ -2134,15 +2137,20 @@ static int test_mp_pack_unpack(void) return EXIT_FAILURE; } +#ifndef LTM_TEST_DYNAMIC +#define ONLY_PUBLIC_API_C +#endif + static int unit_tests(int argc, char **argv) { static const struct { const char *name; int (*fn)(void); } test[] = { -#define T0(n) { #n, test_##n } -#define T1(n, o) { #n, MP_HAS(o) ? test_##n : NULL } -#define T2(n, o1, o2) { #n, (MP_HAS(o1) && MP_HAS(o2)) ? test_##n : NULL } +#define T0(n) { #n, test_##n } +#define T1(n, o) { #n, MP_HAS(o) ? test_##n : NULL } +#define T2(n, o1, o2) { #n, (MP_HAS(o1) && MP_HAS(o2)) ? test_##n : NULL } +#define T3(n, o1, o2, o3) { #n, (MP_HAS(o1) && MP_HAS(o2) && MP_HAS(o3)) ? test_##n : NULL } T0(feature_detection), T0(trivial_stuff), T2(mp_get_set_i32, MP_GET_I32, MP_GET_MAG_U32), @@ -2151,7 +2159,7 @@ static int unit_tests(int argc, char **argv) T1(mp_cnt_lsb, MP_CNT_LSB), T1(mp_complement, MP_COMPLEMENT), T1(mp_decr, MP_SUB_D), - T1(s_mp_div_3, S_MP_DIV_3), + T2(s_mp_div_3, ONLY_PUBLIC_API, S_MP_DIV_3), T1(mp_dr_reduce, MP_DR_REDUCE), T2(mp_pack_unpack,MP_PACK, MP_UNPACK), T2(mp_fread_fwrite, MP_FREAD, MP_FWRITE), @@ -2176,7 +2184,7 @@ static int unit_tests(int argc, char **argv) T1(mp_reduce_2k, MP_REDUCE_2K), T1(mp_reduce_2k_l, MP_REDUCE_2K_L), T1(mp_radix_size, MP_RADIX_SIZE), - T1(s_mp_radix_size_overestimate, S_MP_RADIX_SIZE_OVERESTIMATE), + T2(s_mp_radix_size_overestimate, ONLY_PUBLIC_API, S_MP_RADIX_SIZE_OVERESTIMATE), #if defined(MP_HAS_SET_DOUBLE) T1(mp_set_double, MP_SET_DOUBLE), #endif @@ -2184,13 +2192,14 @@ static int unit_tests(int argc, char **argv) T2(mp_sqrt, MP_SQRT, MP_ROOT_N), T1(mp_sqrtmod_prime, MP_SQRTMOD_PRIME), T1(mp_xor, MP_XOR), - T2(s_mp_div_recursive, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), - T2(s_mp_div_small, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), - T1(s_mp_mul_balance, S_MP_MUL_BALANCE), - T1(s_mp_mul_karatsuba, S_MP_MUL_KARATSUBA), - T1(s_mp_sqr_karatsuba, S_MP_SQR_KARATSUBA), - T1(s_mp_mul_toom, S_MP_MUL_TOOM), - T1(s_mp_sqr_toom, S_MP_SQR_TOOM) + T3(s_mp_div_recursive, ONLY_PUBLIC_API, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), + T3(s_mp_div_small, ONLY_PUBLIC_API, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), + T2(s_mp_mul_balance, ONLY_PUBLIC_API, S_MP_MUL_BALANCE), + T2(s_mp_mul_karatsuba, ONLY_PUBLIC_API, S_MP_MUL_KARATSUBA), + T2(s_mp_sqr_karatsuba, ONLY_PUBLIC_API, S_MP_SQR_KARATSUBA), + T2(s_mp_mul_toom, ONLY_PUBLIC_API, S_MP_MUL_TOOM), + T2(s_mp_sqr_toom, ONLY_PUBLIC_API, S_MP_SQR_TOOM) +#undef T3 #undef T2 #undef T1 }; diff --git a/etc/makefile b/etc/makefile index 85bb09efc..52ad47533 100644 --- a/etc/makefile +++ b/etc/makefile @@ -1,5 +1,4 @@ -LTM_CFLAGS += -Wall -W -Wextra -Wshadow -O3 -I../ -LTM_CFLAGS += $(CFLAGS) +LTM_TUNE_CFLAGS = $(CFLAGS) $(LTM_CFLAGS) -Wall -W -Wextra -Wshadow -O3 -I../ # default lib name (requires install with root) # LIBNAME=-ltommath @@ -9,31 +8,31 @@ LIBNAME=../libtommath.a #provable primes pprime: pprime.o - $(CC) $(LTM_CFLAGS) pprime.o $(LIBNAME) -o pprime + $(CC) $(LTM_TUNE_CFLAGS) pprime.o $(LIBNAME) -o pprime # portable [well requires clock()] tuning app tune: tune.o - $(CC) $(LTM_CFLAGS) tune.o $(LIBNAME) -o tune + $(CC) $(LTM_TUNE_CFLAGS) tune.o $(LIBNAME) -o tune ./tune_it.sh test_standalone: tune.o # The benchmark program works as a testtool, too - $(CC) $(LTM_CFLAGS) tune.o $(LIBNAME) -o test + $(CC) $(LTM_TUNE_CFLAGS) tune.o $(LIBNAME) -o test # spits out mersenne primes mersenne: mersenne.o - $(CC) $(LTM_CFLAGS) mersenne.o $(LIBNAME) -o mersenne + $(CC) $(LTM_TUNE_CFLAGS) mersenne.o $(LIBNAME) -o mersenne # finds DR safe primes for the given config drprime: drprime.o - $(CC) $(LTM_CFLAGS) drprime.o $(LIBNAME) -o drprime + $(CC) $(LTM_TUNE_CFLAGS) drprime.o $(LIBNAME) -o drprime # finds 2k safe primes for the given config 2kprime: 2kprime.o - $(CC) $(LTM_CFLAGS) 2kprime.o $(LIBNAME) -o 2kprime + $(CC) $(LTM_TUNE_CFLAGS) 2kprime.o $(LIBNAME) -o 2kprime mont: mont.o - $(CC) $(LTM_CFLAGS) mont.o $(LIBNAME) -o mont + $(CC) $(LTM_TUNE_CFLAGS) mont.o $(LIBNAME) -o mont clean: diff --git a/etc/tune.c b/etc/tune.c index be0663241..8ad202890 100644 --- a/etc/tune.c +++ b/etc/tune.c @@ -2,12 +2,14 @@ * * Tom St Denis, tstdenis82@gmail.com */ -#include "../tommath.h" -#include "../tommath_private.h" +#include "tommath_private.h" #include #include #include +#define S_MP_RAND_JENKINS_C +#include "../demo/s_mp_rand_jenkins.c" + /* Please take in mind that both multiplicands are of the same size. The balancing mechanism in mp_balance works well but has some overhead itself. You can test diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 6b0924dcd..1bf2f6ba4 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -896,10 +896,6 @@ RelativePath="s_mp_radix_size_overestimate.c" > - - diff --git a/makefile b/makefile index 100f99ab8..a5e5bf173 100644 --- a/makefile +++ b/makefile @@ -48,8 +48,8 @@ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_b s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS @@ -104,7 +104,7 @@ timing: demo/timing.c $(LIBNAME) $(CC) $(LTM_CFLAGS) $^ $(LTM_LFLAGS) -o timing tune: $(LIBNAME) - $(MAKE) -C etc tune CFLAGS="$(LTM_CFLAGS)" + $(MAKE) -C etc tune CFLAGS="$(LTM_CFLAGS) -I../" $(MAKE) # You have to create a file .coveralls.yml with the content "repo_token: " diff --git a/makefile.mingw b/makefile.mingw index fde087ac3..a0192d642 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -50,8 +50,8 @@ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_b s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index a03245599..e3d6e23f6 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -46,8 +46,8 @@ s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_ s_mp_invmod_odd.obj s_mp_log.obj s_mp_log_2expt.obj s_mp_log_d.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj \ -s_mp_radix_size_overestimate.obj s_mp_rand_jenkins.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ -s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj \ +s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 2d8b32c7d..70543c1a6 100644 --- a/makefile.shared +++ b/makefile.shared @@ -45,8 +45,8 @@ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_b s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS @@ -75,7 +75,7 @@ uninstall: rm $(DESTDIR)$(LIBPATH)/pkgconfig/libtommath.pc test mtest_opponent: demo/shared.o $(LIBNAME) | demo/test.o demo/mtest_opponent.o - $(LTLINK) $(LTM_LDFLAGS) demo/$@.o $^ -o $@ + $(LTLINK) $(LTM_LDFLAGS) -DLTM_TEST_DYNAMIC demo/$@.o $^ -o $@ .PHONY: mtest mtest: diff --git a/makefile.unix b/makefile.unix index 3304e7f07..64fb5806e 100644 --- a/makefile.unix +++ b/makefile.unix @@ -51,8 +51,8 @@ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_get_b s_mp_invmod_odd.o s_mp_log.o s_mp_log_2expt.o s_mp_log_d.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_jenkins.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/testme.sh b/testme.sh index 41a165bcd..2d09d0455 100755 --- a/testme.sh +++ b/testme.sh @@ -348,7 +348,7 @@ fi # default to CC environment variable if no compiler is defined but some other options if [[ "$COMPILERS" == "" ]] && [[ "$ARCHFLAGS$MAKE_OPTIONS$CFLAGS" != "" ]] then - COMPILERS="$CC" + COMPILERS="${CC:-cc}" # default to CC environment variable and run only default config if no option is given elif [[ "$COMPILERS" == "" ]] then diff --git a/tommath_class.h b/tommath_class.h index d6f7e7a51..da9c5ea72 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -157,7 +157,6 @@ # define S_MP_PRIME_TAB_C # define S_MP_RADIX_MAP_C # define S_MP_RADIX_SIZE_OVERESTIMATE_C -# define S_MP_RAND_JENKINS_C # define S_MP_RAND_PLATFORM_C # define S_MP_SQR_C # define S_MP_SQR_COMBA_C @@ -1194,10 +1193,6 @@ # define S_MP_LOG_2EXPT_C #endif -#if defined(S_MP_RAND_JENKINS_C) -# define S_MP_RAND_JENKINS_INIT_C -#endif - #if defined(S_MP_RAND_PLATFORM_C) #endif diff --git a/tommath_private.h b/tommath_private.h index 624ba0a47..42920519c 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -208,10 +208,6 @@ MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size); -/* TODO: jenkins prng is not thread safe as of now */ -MP_PRIVATE mp_err s_mp_rand_jenkins(void *p, size_t n) MP_WUR; -MP_PRIVATE void s_mp_rand_jenkins_init(uint64_t seed); - #define MP_RADIX_MAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_radix_map[]; extern MP_PRIVATE const uint8_t s_mp_radix_map_reverse[]; From fa289f9d2b4d400a5d25e89bccc68d26c1ee3c4a Mon Sep 17 00:00:00 2001 From: Anonymous Maarten Date: Mon, 14 Sep 2020 23:28:01 +0200 Subject: [PATCH 172/304] build and test with dll on MSVC --- appveyor.yml | 3 ++- makefile.msvc | 9 +++++++-- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index 02c343057..b7907024d 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -16,6 +16,7 @@ build_script: if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 - nmake -f makefile.msvc all + nmake -f makefile.msvc all CFLAGS="/Ox /MD" test_script: - cmd: test.exe +- cmd: test_dll.exe diff --git a/makefile.msvc b/makefile.msvc index e3d6e23f6..1e5029f1a 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -71,10 +71,15 @@ $(LIBMAIN_D) $(LIBMAIN_I): $(OBJECTS) tommath.def #Build test suite test.exe: $(LIBMAIN_S) demo/shared.obj demo/test.obj - cl $(LTM_CFLAGS) $(TOBJECTS) $(LIBMAIN_S) $(LTM_LDFLAGS) demo/shared.c demo/test.c /Fe$@ + link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ @echo NOTICE: start the tests by launching test.exe -all: $(LIBMAIN_S) test.exe $(LIBMAIN_D) +#Build test suite for dll +test_dll.exe: $(LIBMAIN_I) demo/shared.obj demo/test.obj + link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ + @echo NOTICE: start the tests by launching test_dll.exe + +all: $(LIBMAIN_S) test.exe $(LIBMAIN_D) test_dll.exe tune: $(LIBMAIN_S) $(MAKE) -C etc tune From 9fa740096b779d1567f4a9c02a07cdd6af3f44ac Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 15 Sep 2020 19:05:20 +0200 Subject: [PATCH 173/304] separate static and dynamic builds --- appveyor.yml | 4 +++- makefile.msvc | 13 ++++++++----- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index b7907024d..3e9ba4a16 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -16,7 +16,9 @@ build_script: if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 - nmake -f makefile.msvc all CFLAGS="/Ox /MD" + nmake -f makefile.msvc test.exe + nmake -f makefile.msvc clean-obj + nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /MD /DLTM_TEST_DYNAMIC" test_script: - cmd: test.exe - cmd: test_dll.exe diff --git a/makefile.msvc b/makefile.msvc index 1e5029f1a..df886e902 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -71,13 +71,13 @@ $(LIBMAIN_D) $(LIBMAIN_I): $(OBJECTS) tommath.def #Build test suite test.exe: $(LIBMAIN_S) demo/shared.obj demo/test.obj - link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ + link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ @echo NOTICE: start the tests by launching test.exe #Build test suite for dll test_dll.exe: $(LIBMAIN_I) demo/shared.obj demo/test.obj - link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ - @echo NOTICE: start the tests by launching test_dll.exe + link $(TOBJECTS) $(LTM_LDFLAGS) $? /out:$@ + @echo NOTICE: start the tests by launching test_dll.exe all: $(LIBMAIN_S) test.exe $(LIBMAIN_D) test_dll.exe @@ -85,8 +85,11 @@ tune: $(LIBMAIN_S) $(MAKE) -C etc tune $(MAKE) -clean: - @-cmd /c del /Q /S *.OBJ *.LIB *.EXE *.DLL 2>nul +clean-obj: + @-cmd /c del /Q /S *.OBJ 2>nul + +clean: clean-obj + @-cmd /c del /Q /S *.LIB *.EXE *.DLL 2>nul #Install the library + headers install: $(LIBMAIN_S) $(LIBMAIN_I) $(LIBMAIN_D) From 34540acb4a41a758034a61feea7c84d3d30d8468 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 29 Nov 2020 15:03:41 +0100 Subject: [PATCH 174/304] fix building demos from makefile.shared --- makefile.shared | 18 +++++++++++++----- makefile_include.mk | 1 + 2 files changed, 14 insertions(+), 5 deletions(-) diff --git a/makefile.shared b/makefile.shared index 70543c1a6..9319e658f 100644 --- a/makefile.shared +++ b/makefile.shared @@ -74,16 +74,24 @@ uninstall: rm $(HEADERS_PUB:%=$(DESTDIR)$(INCPATH)/%) rm $(DESTDIR)$(LIBPATH)/pkgconfig/libtommath.pc -test mtest_opponent: demo/shared.o $(LIBNAME) | demo/test.o demo/mtest_opponent.o - $(LTLINK) $(LTM_LDFLAGS) -DLTM_TEST_DYNAMIC demo/$@.o $^ -o $@ +DEMOS=mtest_opponent test timing +test: LTM_LDFLAGS+=-DLTM_TEST_DYNAMIC + +# build the demos from a template +define DEMO_template +$(1): $(call print-help,$(1),Builds the library and the '$(1)' demo) demo/$(1).o demo/shared.o $$(LIBNAME) +ifneq ($V,1) + @echo " * $${CC} $$@" ${silent_echo} +endif + $(LTLINK) $(LTM_CFLAGS) $(LTM_LDFLAGS) $$^ -o $(1) +endef + +$(foreach demo, $(strip $(DEMOS)), $(eval $(call DEMO_template,$(demo)))) .PHONY: mtest mtest: cd mtest ; $(CC) $(LTM_CFLAGS) -O0 mtest.c $(LTM_LDFLAGS) -o mtest -timing: $(LIBNAME) demo/timing.c - $(LTLINK) $(LTM_CFLAGS) $(LTM_LDFLAGS) -DTIMER demo/timing.c $(LIBNAME) -o timing - tune: $(LIBNAME) $(LTCOMPILE) $(LTM_CFLAGS) -c etc/tune.c -o etc/tune.o $(LTLINK) $(LTM_LDFLAGS) -o etc/tune etc/tune.o $(LIBNAME) diff --git a/makefile_include.mk b/makefile_include.mk index 0266da123..9a152d733 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -87,6 +87,7 @@ endif ifdef COMPILE_LTO LTM_CFLAGS += -flto +LTM_LDFLAGS += -flto AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) endif From bee1e9959299e908a52718f297961dc414bb974d Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 29 Nov 2020 15:06:42 +0100 Subject: [PATCH 175/304] use heredoc instead of all those echo's --- testme.sh | 132 +++++++++++++++++++++++++++--------------------------- 1 file changed, 67 insertions(+), 65 deletions(-) diff --git a/testme.sh b/testme.sh index 2d09d0455..9ff242a2c 100755 --- a/testme.sh +++ b/testme.sh @@ -20,71 +20,73 @@ TEST_CFLAGS="" _help() { - echo "Usage options for $(basename $0) [--with-cc=arg [other options]]" - echo - echo "Executing this script without any parameter will only run the default" - echo "configuration that has automatically been determined for the" - echo "architecture you're running." - echo - echo " --with-cc=* The compiler(s) to use for the tests" - echo " This is an option that will be iterated." - echo - echo " --test-vs-mtest=* Run test vs. mtest for '*' operations." - echo " Only the first of each options will be" - echo " taken into account." - echo - echo "To be able to specify options a compiler has to be given with" - echo "the option --with-cc=compilername" - echo "All other options will be tested with all MP_xBIT configurations." - echo - echo " --with-{m64,m32,mx32} The architecture(s) to build and test" - echo " for, e.g. --with-mx32." - echo " This is an option that will be iterated," - echo " multiple selections are possible." - echo " The mx32 architecture is not supported" - echo " by clang and will not be executed." - echo - echo " --cflags=* Give an option to the compiler," - echo " e.g. --cflags=-g" - echo " This is an option that will always be" - echo " passed as parameter to CC." - echo - echo " --make-option=* Give an option to make," - echo " e.g. --make-option=\"-f makefile.shared\"" - echo " This is an option that will always be" - echo " passed as parameter to make." - echo - echo " --with-low-mp Also build&run tests with -DMP_{8,16,32}BIT." - echo - echo " --mtest-real-rand Use real random data when running mtest." - echo - echo " --with-valgrind" - echo " --with-valgrind=* Run in valgrind (slow!)." - echo - echo " --with-travis-valgrind Run with valgrind on Travis on specific branches." - echo - echo " --valgrind-options Additional Valgrind options" - echo " Some of the options like e.g.:" - echo " --track-origins=yes add a lot of extra" - echo " runtime and may trigger the 30 minutes" - echo " timeout." - echo - echo "Godmode:" - echo - echo " --all Choose all architectures and gcc and clang" - echo " as compilers but does not run valgrind." - echo - echo " --format Runs the various source-code formatters" - echo " and generators and checks if the sources" - echo " are clean." - echo - echo " -h" - echo " --help This message" - echo - echo " -v" - echo " --version Prints the version. It is just the number" - echo " of git commits to this file, no deeper" - echo " meaning attached" + cat << EOF +Usage options for $(basename $0) [--with-cc=arg [other options]] + +Executing this script without any parameter will only run the default +configuration that has automatically been determined for the +architecture you're running. + + --with-cc=* The compiler(s) to use for the tests + This is an option that will be iterated. + + --test-vs-mtest=* Run test vs. mtest for '*' operations. + Only the first of each options will be + taken into account. + +To be able to specify options a compiler has to be given with +the option --with-cc=compilername +All other options will be tested with all MP_xBIT configurations. + + --with-{m64,m32,mx32} The architecture(s) to build and test + for, e.g. --with-mx32. + This is an option that will be iterated, + multiple selections are possible. + The mx32 architecture is not supported + by clang and will not be executed. + + --cflags=* Give an option to the compiler, + e.g. --cflags=-g + This is an option that will always be + passed as parameter to CC. + + --make-option=* Give an option to make, + e.g. --make-option="-f makefile.shared" + This is an option that will always be + passed as parameter to make. + + --with-low-mp Also build&run tests with -DMP_{8,16,32}BIT. + + --mtest-real-rand Use real random data when running mtest. + + --with-valgrind + --with-valgrind=* Run in valgrind (slow!). + + --with-travis-valgrind Run with valgrind on Travis on specific branches. + + --valgrind-options Additional Valgrind options + Some of the options like e.g.: + --track-origins=yes add a lot of extra + runtime and may trigger the 30 minutes + timeout. + +Godmode: + + --all Choose all architectures and gcc and clang + as compilers but does not run valgrind. + + --format Runs the various source-code formatters + and generators and checks if the sources + are clean. + + -h + --help This message + + -v + --version Prints the version. It is just the number + of git commits to this file, no deeper + meaning attached +EOF exit 0 } From 5d744e43eb55712f23f1cf07e98a403308dd82d9 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 20 Sep 2020 18:07:28 +0200 Subject: [PATCH 176/304] update CI to bionic --- .travis.yml | 50 +++++++++++++++++++++++++++++++------------------- 1 file changed, 31 insertions(+), 19 deletions(-) diff --git a/.travis.yml b/.travis.yml index 0f3e7fb65..b97912ed6 100644 --- a/.travis.yml +++ b/.travis.yml @@ -5,8 +5,8 @@ # # ############################################################################# -# Run the tests based on Ubuntu 16.04 -dist: xenial +# The Ubuntu version we're going to use to run the tests +dist: bionic # Compilation failures are in gcc_errors_*.log # Failed tests in test_*.log @@ -80,21 +80,18 @@ matrix: - libtool-bin # Run always with valgrind (no sanitizer, but debug info) - - env: COMPILE_DEBUG=1 BUILDOPTIONS='--with-cc=gcc-4.9 --with-m64 --with-valgrind' - addons: - apt: - packages: - - gcc-4.9 + - env: COMPILE_DEBUG=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-valgrind' # Shared library build - env: COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc --make-option=-f --make-option=makefile.shared' addons: apt: packages: + - gcc-8 - libtool-bin # GCC for the 32-bit architecture (no valgrind) - - env: BUILDOPTIONS='--with-cc=gcc-5 --with-m32' + - env: BUILDOPTIONS='--with-cc=gcc --with-m32' addons: apt: packages: @@ -122,9 +119,9 @@ matrix: # GCC for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs. - #- env: BUILDOPTIONS='--with-cc=gcc-5 --test-vs-mtest=333333 --with-travis-valgrind' + #- env: BUILDOPTIONS='--with-cc=gcc --test-vs-mtest=333333 --with-travis-valgrind' # ... and a better random source. - - env: BUILDOPTIONS='--with-cc=gcc-5 --test-vs-mtest=333333 --mtest-real-rand --with-travis-valgrind' + - env: BUILDOPTIONS='--with-cc=gcc --test-vs-mtest=333333 --mtest-real-rand --with-travis-valgrind' # clang for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs @@ -135,7 +132,7 @@ matrix: # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) # TODO: Probably not possible to run anything in x32 in Travis # but needs to be checked to be sure. - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --with-mx32' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --with-mx32' addons: apt: packages: @@ -143,12 +140,12 @@ matrix: - gcc-multilib # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' - - env: BUILDOPTIONS='--with-cc=gcc-4.7 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-travis-valgrind' + - env: BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' addons: apt: packages: - - gcc-4.7 + - gcc-5 - env: BUILDOPTIONS='--with-cc=gcc-4.8 --with-m64 --with-travis-valgrind' addons: apt: @@ -161,6 +158,21 @@ matrix: - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_USE_MEMOPS --with-m64 --with-travis-valgrind' - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --c89 --with-m64 --with-travis-valgrind' - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind --cflags=-DMP_PREC=MP_MIN_PREC' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-10 --with-m64 --with-travis-valgrind' + addons: + apt: + packages: + - clang-10 + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-9 --with-m64 --with-travis-valgrind' + addons: + apt: + packages: + - clang-9 + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-8 --with-m64 --with-travis-valgrind' + addons: + apt: + packages: + - clang-8 - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-6.0 --with-m64 --with-travis-valgrind' addons: apt: @@ -178,18 +190,18 @@ matrix: - clang-4.0 # Link time optimization - - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' + - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-travis-valgrind' #- env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' # GCC for the x86-64 architecture with restricted limb sizes # formerly started with the option "--with-low-mp" to testme.sh # but testing all three in one run took to long and timed out. - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --with-travis-valgrind' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_32BIT --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --cflags=-DMP_16BIT --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --cflags=-DMP_32BIT --with-travis-valgrind' # clang for the x86-64 architecture with restricted limb sizes - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_16BIT --with-travis-valgrind' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_32BIT --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang --cflags=-DMP_16BIT --with-travis-valgrind' + - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang --cflags=-DMP_32BIT --with-travis-valgrind' # Notifications go to # An email address is also possible. From 8d9df12800d7fbc6e03616180866de4d21e78639 Mon Sep 17 00:00:00 2001 From: Tim Gates Date: Sat, 19 Dec 2020 19:09:57 +1100 Subject: [PATCH 177/304] docs: fix simple typo, exluding -> excluding There is a small typo in mp_to_radix.c. Should read `excluding` rather than `exluding`. --- mp_to_radix.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mp_to_radix.c b/mp_to_radix.c index abf85c067..1e5e67110 100644 --- a/mp_to_radix.c +++ b/mp_to_radix.c @@ -75,7 +75,7 @@ mp_err mp_to_radix(const mp_int *a, char *str, size_t maxlen, size_t *written, i ++digs; } /* reverse the digits of the string. In this case _s points - * to the first digit [exluding the sign] of the number + * to the first digit [excluding the sign] of the number */ s_reverse(_s, digs); From ae29a38ca587ff60faf6041dab87c22bb061fea6 Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Sat, 19 Dec 2020 12:46:16 -0300 Subject: [PATCH 178/304] Documentation: Fix an exponent Signed-off-by: Horst H. von Brand --- doc/bn.tex | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/bn.tex b/doc/bn.tex index a0956b302..1494b2d0e 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2272,7 +2272,7 @@ \section{Primality Testing} If $t$ is set to a negative value the test will run the deterministic Miller--Rabin test for the primes up to $3\,317\,044\,064\,679\,887\ 385\,961\,981$\footnote{The semiprime $1287836182261\cdot - 2575672364521$ with both factors smaller than $2^64$. An alternative with all factors smaller + 2575672364521$ with both factors smaller than $2^{64}$. An alternative with all factors smaller than $2^32$ is $4290067842\cdot 262853\cdot 1206721\cdot 2134439 + 3$}. That limit has to be checked by From a1a057b5df9e52cf34b0a490e044f5bf0d6e2ed1 Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Sat, 19 Dec 2020 12:47:56 -0300 Subject: [PATCH 179/304] Documentation: Fix /dev/urandom Signed-off-by: Horst H. von Brand --- doc/bn.tex | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/bn.tex b/doc/bn.tex index 1494b2d0e..b79d13738 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2343,7 +2343,7 @@ \section{PRNG} The random number generated with these two functions is cryptographically secure if the source of random numbers the operating systems offers is cryptographically secure. It will use -\texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev urandom} on +\texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev/urandom} on all operating systems that have it. If you have a custom random source you might find the function \texttt(mp\_rand\_source) useful. From 64bb3aa2fe4db8ba0bf867ba478d4b4bf619e34a Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Sat, 19 Dec 2020 12:49:03 -0300 Subject: [PATCH 180/304] Documentation: Fix Format mp_rand_source Signed-off-by: Horst H. von Brand --- doc/bn.tex | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/bn.tex b/doc/bn.tex index b79d13738..c15637890 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2346,7 +2346,7 @@ \section{PRNG} \texttt{arc4random()} if the OS is a BSD flavor, Wincrypt on Windows, or \texttt{/dev/urandom} on all operating systems that have it. -If you have a custom random source you might find the function \texttt(mp\_rand\_source) useful. +If you have a custom random source you might find the function \texttt{mp\_rand\_source()} useful. \index{mp\_rand\_source} \begin{alltt} void mp_rand_source(mp_err(*source)(void *out, size_t size)); From eb7520213ce7c332aeccc3f4ecaab4b733b12696 Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Sat, 19 Dec 2020 13:01:28 -0300 Subject: [PATCH 181/304] Documentation: Grammo Signed-off-by: Horst H. von Brand --- doc/bn.tex | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/bn.tex b/doc/bn.tex index c15637890..5119901cb 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2581,7 +2581,7 @@ \section{Single Digit Functions} \end{alltt} These work like the full \texttt{mp\_int} capable variants except the second parameter $b$ is a -\texttt{mp\_digit}. These functions fairly handy if you have to work with relatively small numbers +\texttt{mp\_digit}. These functions come fairly handy if you have to work with relatively small numbers since you will not have to allocate an entire \texttt{mp\_int} to store a number like $1$ or $2$. The functions \texttt{mp\_incr} and \texttt{mp\_decr} mimic the postfix operators \texttt{++} and From 96bfafae7c8c44dcc7535d71d3dabda55e606804 Mon Sep 17 00:00:00 2001 From: "Horst H. von Brand" Date: Sat, 19 Dec 2020 13:08:51 -0300 Subject: [PATCH 182/304] Documentation: Kludge for decent "mod" operation [skip ci] Signed-off-by: Horst H. von Brand --- doc/bn.tex | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 5119901cb..6f1cb8cd4 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2604,13 +2604,13 @@ \section{Function Macros} \begin{alltt} bool mp_iseven(const mp_int *a) \end{alltt} -Checks if $a = 0 mod 2$ +Checks if $a = 0 \;\mathrm{mod}\; 2$ \index{mp\_isodd} \begin{alltt} bool mp_isodd(const mp_int *a) \end{alltt} -Checks if $a = 1 mod 2$ +Checks if $a = 1 \;\mathrm{mod}\; 2$ \index{mp\_isneg} \begin{alltt} From 24ac0de688c6396696eab34be8f8ae27e319b2b0 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sat, 26 Dec 2020 10:28:08 +0100 Subject: [PATCH 183/304] Replaced "fgets" with a "get_token" function in demo/mtest_opponent.c --- demo/mtest_opponent.c | 136 +++++++++++++++++++++++++++--------------- doc/bn.tex | 22 ++++++- 2 files changed, 106 insertions(+), 52 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index edbecc0c1..7cdad2c46 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -11,10 +11,49 @@ static void draw(const mp_int *a) ndraw(a, ""); } -#define FGETS(str, size, stream) \ +/* + Get tokens. It is just a very(!) simple fgets(3) that does not keep line endings. + + Implementation follows along "man 3 fgets", some of which is quoted. + */ +static char *s_mp_get_token(char *s, int size, FILE *stream) +{ + char *s_bar = s; + int c; + bool eol_hit = false; + + /* "fgets [...] reads in at most one less than size characters from stream" */ + while (--size) { + /* "Reading stops after an EOF or a newline." We stop only for EOF here */ + if ((c = fgetc(stream)) == EOF) { + /* "Returns [...] NULL on error or when end of file occurs while no characters have been read" */ + if ((s_bar == s) || (ferror(stream) != 0)) { + return NULL; + } + break; + } + /* Ignore line-breaks but keep reading to get them out of the stream-buffer */ + if ((c == '\n') || (c == '\r')) { + eol_hit = true; + continue; + } + /* Stop reading after linebreak */ + if (eol_hit) { + /* We already read the character after the linebreak, put it back */ + ungetc(c, stream); + break; + } + *s_bar++ = c; + } + /* "A terminating null byte ('\0') is stored after the last character in the buffer" */ + *s_bar = '\0'; + return s; +} + +#define GET_TOKEN(str, size, stream) \ { \ - char *ret = fgets(str, size, stream); \ - if (!ret) { fprintf(stderr, "\n%d: fgets failed\n", __LINE__); goto LBL_ERR; } \ + char *ret = s_mp_get_token((str), (size), (stream)); \ + if (!ret) { fprintf(stderr, "\n%d: s_mp_get_token failed\n", __LINE__); goto LBL_ERR; } \ } static int mtest_opponent(void) @@ -76,17 +115,16 @@ static int mtest_opponent(void) printf("%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu ", add_n, sub_n, mul_n, div_n, sqr_n, mul2d_n, div2d_n, gcd_n, lcm_n, expt_n, inv_n, div2_n, mul2_n, add_d_n, sub_d_n); - FGETS(cmd, 4095, stdin); - cmd[strlen(cmd) - 1u] = '\0'; + GET_TOKEN(cmd, 4095, stdin); printf("%-6s ]\r", cmd); fflush(stdout); if (strcmp(cmd, "mul2d") == 0) { ++mul2d_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); sscanf(buf, "%u", &rr); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_mul_2d(&a, (int)rr, &a)); @@ -99,11 +137,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "div2d") == 0) { ++div2d_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); sscanf(buf, "%u", &rr); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_div_2d(&a, (int)rr, &a, &e)); @@ -119,11 +157,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "add") == 0) { ++add_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_add(&d, &b, &d)); @@ -162,11 +200,11 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "sub") == 0) { ++sub_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_sub(&d, &b, &d)); @@ -180,11 +218,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "mul") == 0) { ++mul_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_mul(&d, &b, &d)); @@ -198,13 +236,13 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "div") == 0) { ++div_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&d, buf, 64)); DO(mp_div(&a, &b, &e, &f)); @@ -222,9 +260,9 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "sqr") == 0) { ++sqr_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_copy(&a, &c)); DO(mp_sqr(&c, &c)); @@ -237,11 +275,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "gcd") == 0) { ++gcd_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_gcd(&d, &b, &d)); @@ -256,11 +294,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "lcm") == 0) { ++lcm_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_lcm(&d, &b, &d)); @@ -275,13 +313,13 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "expt") == 0) { ++expt_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&d, buf, 64)); DO(mp_copy(&a, &e)); DO(mp_exptmod(&e, &b, &c, &e)); @@ -296,11 +334,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "invmod") == 0) { ++inv_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_invmod(&a, &b, &d)); DO(mp_mulmod(&d, &a, &b, &e)); @@ -318,9 +356,9 @@ static int mtest_opponent(void) } else if (strcmp(cmd, "div2") == 0) { ++div2_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_div_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { @@ -332,9 +370,9 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "mul2") == 0) { ++mul2_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_mul_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { @@ -346,11 +384,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "add_d") == 0) { ++add_d_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); sscanf(buf, "%d", &ix); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_add_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { @@ -363,11 +401,11 @@ static int mtest_opponent(void) } } else if (strcmp(cmd, "sub_d") == 0) { ++sub_d_n; - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&a, buf, 64)); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); sscanf(buf, "%d", &ix); - FGETS(buf, 4095, stdin); + GET_TOKEN(buf, 4095, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_sub_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { diff --git a/doc/bn.tex b/doc/bn.tex index 6f1cb8cd4..1dfb34d55 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2409,9 +2409,25 @@ \subsection{From ASCII} mp_err mp_read_radix (mp_int *a, const char *str, int radix); \end{alltt} This will read a \texttt{NUL} terminated string in base \texttt{radix} from \texttt{str} into $a$. -It will stop reading when it reads a character it does not recognize (which happens to include the -\texttt{NUL} char\dots imagine that\dots). A single leading $-$ (ASCII \texttt{0x20}) sign can be -used to denote a negative number. The input encoding is currently restricted to ASCII only. +Valid values of \texttt{radix} are in the range $[2, 64]$. +%It will stop reading when it reads a character it does not recognize (which happens to include the +%\texttt{NUL} char\dots imagine that\dots). + +It returns \texttt{MP\_VAL} for any character {\em not} in the range allowed for the given base. +The list of characters is the same as for base-64 and also in the same order. +\begin{alltt} +0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/ +\end{alltt} + +A single leading $-$ (ASCII \texttt{0x20}) sign can be used to denote a negative number. The +plus sign $+$ (ASCII \texttt{0x2b}) is already in use (bases 63 and 64) and cannot be used +to denote positivity, no matter how good the mood of the number is. + +For all bases smaller than 37 the list is case-insensitive, e.g.:~the two hexadecimal numbers +$123abc_{16} = 1194684_{10}$ and $123ABC_{16} = 1194684_{10}$ are equivalent but the two base +64 numbers $123abc_{64} = 1108232550_{10}$ and $123ABC_{64} = 1108124364_{10}$ are not. + +The input encoding is currently restricted to ASCII only. If \texttt{MP\_NO\_FILE} is not defined a function to read from a file is also available. \index{mp\_fread} From 813b1569f4f211f5a8b5402cbaea4488a1c85285 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 3 Jan 2021 17:44:10 +0100 Subject: [PATCH 184/304] improve error handling * handle buffer full case * display error reason of `s_mp_get_token()` * display name of variables when `draw()`ing on error --- demo/mtest_opponent.c | 235 +++++++++++++++++++++--------------------- 1 file changed, 118 insertions(+), 117 deletions(-) diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 7cdad2c46..25d9b5b90 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -6,17 +6,14 @@ #define LTM_MTEST_RAND_SEED 23 #endif -static void draw(const mp_int *a) -{ - ndraw(a, ""); -} +#define DRAW(a) do{ ndraw(&(a), #a); }while(0) /* Get tokens. It is just a very(!) simple fgets(3) that does not keep line endings. Implementation follows along "man 3 fgets", some of which is quoted. */ -static char *s_mp_get_token(char *s, int size, FILE *stream) +static int s_mp_get_token(char *s, int size, FILE *stream) { char *s_bar = s; int c; @@ -28,7 +25,7 @@ static char *s_mp_get_token(char *s, int size, FILE *stream) if ((c = fgetc(stream)) == EOF) { /* "Returns [...] NULL on error or when end of file occurs while no characters have been read" */ if ((s_bar == s) || (ferror(stream) != 0)) { - return NULL; + return -1; } break; } @@ -45,16 +42,20 @@ static char *s_mp_get_token(char *s, int size, FILE *stream) } *s_bar++ = c; } + if (size == 0) return -2; /* "A terminating null byte ('\0') is stored after the last character in the buffer" */ *s_bar = '\0'; - return s; + return 0; } -#define GET_TOKEN(str, size, stream) \ - { \ - char *ret = s_mp_get_token((str), (size), (stream)); \ - if (!ret) { fprintf(stderr, "\n%d: s_mp_get_token failed\n", __LINE__); goto LBL_ERR; } \ - } +#define TMP_(r,l) r ## _ ## l +#define TMP(r,l) TMP_(r,l) + +#define GET_TOKEN(str, stream) \ + do { \ + int TMP(ret,__LINE__) = s_mp_get_token((str), sizeof(str), (stream)); \ + if (TMP(ret,__LINE__) < 0) { fprintf(stderr, "\n%d: s_mp_get_token failed with error %d\n", __LINE__, TMP(ret,__LINE__)); goto LBL_ERR; } \ + } while(0) static int mtest_opponent(void) { @@ -115,33 +116,33 @@ static int mtest_opponent(void) printf("%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu/%4lu ", add_n, sub_n, mul_n, div_n, sqr_n, mul2d_n, div2d_n, gcd_n, lcm_n, expt_n, inv_n, div2_n, mul2_n, add_d_n, sub_d_n); - GET_TOKEN(cmd, 4095, stdin); + GET_TOKEN(cmd, stdin); printf("%-6s ]\r", cmd); fflush(stdout); if (strcmp(cmd, "mul2d") == 0) { ++mul2d_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); sscanf(buf, "%u", &rr); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_mul_2d(&a, (int)rr, &a)); a.sign = b.sign; if (mp_cmp(&a, &b) != MP_EQ) { printf("mul2d failed, rr == %u\n", rr); - draw(&a); - draw(&b); + DRAW(a); + DRAW(b); goto LBL_ERR; } } else if (strcmp(cmd, "div2d") == 0) { ++div2d_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); sscanf(buf, "%u", &rr); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_div_2d(&a, (int)rr, &a, &e)); @@ -151,26 +152,26 @@ static int mtest_opponent(void) } if (mp_cmp(&a, &b) != MP_EQ) { printf("div2d failed, rr == %u\n", rr); - draw(&a); - draw(&b); + DRAW(a); + DRAW(b); goto LBL_ERR; } } else if (strcmp(cmd, "add") == 0) { ++add_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_add(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("add %lu failure!\n", add_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); goto LBL_ERR; } @@ -182,8 +183,8 @@ static int mtest_opponent(void) DO(mp_from_sbin(&d, (uint8_t *) cmd, (size_t)rr)); if (mp_cmp(&c, &d) != MP_EQ) { printf("mp_signed_bin failure!\n"); - draw(&c); - draw(&d); + DRAW(c); + DRAW(d); goto LBL_ERR; } @@ -193,226 +194,226 @@ static int mtest_opponent(void) DO(mp_from_ubin(&d, (uint8_t *) cmd, (size_t)rr)); if (mp_cmp_mag(&c, &d) != MP_EQ) { printf("mp_unsigned_bin failure!\n"); - draw(&c); - draw(&d); + DRAW(c); + DRAW(d); goto LBL_ERR; } } else if (strcmp(cmd, "sub") == 0) { ++sub_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_sub(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("sub %lu failure!\n", sub_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); goto LBL_ERR; } } else if (strcmp(cmd, "mul") == 0) { ++mul_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_mul(&d, &b, &d)); if (mp_cmp(&c, &d) != MP_EQ) { printf("mul %lu failure!\n", mul_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); goto LBL_ERR; } } else if (strcmp(cmd, "div") == 0) { ++div_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&d, buf, 64)); DO(mp_div(&a, &b, &e, &f)); if ((mp_cmp(&c, &e) != MP_EQ) || (mp_cmp(&d, &f) != MP_EQ)) { printf("div %lu %d, %d, failure!\n", div_n, mp_cmp(&c, &e), mp_cmp(&d, &f)); - draw(&a); - draw(&b); - draw(&c); - draw(&d); - draw(&e); - draw(&f); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); + DRAW(e); + DRAW(f); goto LBL_ERR; } } else if (strcmp(cmd, "sqr") == 0) { ++sqr_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_copy(&a, &c)); DO(mp_sqr(&c, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("sqr %lu failure!\n", sqr_n); - draw(&a); - draw(&b); - draw(&c); + DRAW(a); + DRAW(b); + DRAW(c); goto LBL_ERR; } } else if (strcmp(cmd, "gcd") == 0) { ++gcd_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_gcd(&d, &b, &d)); d.sign = c.sign; if (mp_cmp(&c, &d) != MP_EQ) { printf("gcd %lu failure!\n", gcd_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); goto LBL_ERR; } } else if (strcmp(cmd, "lcm") == 0) { ++lcm_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_copy(&a, &d)); DO(mp_lcm(&d, &b, &d)); d.sign = c.sign; if (mp_cmp(&c, &d) != MP_EQ) { printf("lcm %lu failure!\n", lcm_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); goto LBL_ERR; } } else if (strcmp(cmd, "expt") == 0) { ++expt_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&d, buf, 64)); DO(mp_copy(&a, &e)); DO(mp_exptmod(&e, &b, &c, &e)); if (mp_cmp(&d, &e) != MP_EQ) { printf("expt %lu failure!\n", expt_n); - draw(&a); - draw(&b); - draw(&c); - draw(&d); - draw(&e); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); + DRAW(e); goto LBL_ERR; } } else if (strcmp(cmd, "invmod") == 0) { ++inv_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&c, buf, 64)); DO(mp_invmod(&a, &b, &d)); DO(mp_mulmod(&d, &a, &b, &e)); if (mp_cmp_d(&e, 1u) != MP_EQ) { printf("inv [wrong value from MPI?!] failure\n"); - draw(&a); - draw(&b); - draw(&c); - draw(&d); - draw(&e); + DRAW(a); + DRAW(b); + DRAW(c); + DRAW(d); + DRAW(e); DO(mp_gcd(&a, &b, &e)); - draw(&e); + DRAW(e); goto LBL_ERR; } } else if (strcmp(cmd, "div2") == 0) { ++div2_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_div_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { printf("div_2 %lu failure\n", div2_n); - draw(&a); - draw(&b); - draw(&c); + DRAW(a); + DRAW(b); + DRAW(c); goto LBL_ERR; } } else if (strcmp(cmd, "mul2") == 0) { ++mul2_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_mul_2(&a, &c)); if (mp_cmp(&c, &b) != MP_EQ) { printf("mul_2 %lu failure\n", mul2_n); - draw(&a); - draw(&b); - draw(&c); + DRAW(a); + DRAW(b); + DRAW(c); goto LBL_ERR; } } else if (strcmp(cmd, "add_d") == 0) { ++add_d_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); sscanf(buf, "%d", &ix); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_add_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("add_d %lu failure\n", add_d_n); - draw(&a); - draw(&b); - draw(&c); + DRAW(a); + DRAW(b); + DRAW(c); printf("d == %d\n", ix); goto LBL_ERR; } } else if (strcmp(cmd, "sub_d") == 0) { ++sub_d_n; - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&a, buf, 64)); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); sscanf(buf, "%d", &ix); - GET_TOKEN(buf, 4095, stdin); + GET_TOKEN(buf, stdin); DO(mp_read_radix(&b, buf, 64)); DO(mp_sub_d(&a, (mp_digit)ix, &c)); if (mp_cmp(&b, &c) != MP_EQ) { printf("sub_d %lu failure\n", sub_d_n); - draw(&a); - draw(&b); - draw(&c); + DRAW(a); + DRAW(b); + DRAW(c); printf("d == %d\n", ix); goto LBL_ERR; } From 528fdb04d6deb060c9117dc4a84ebd5c0889b970 Mon Sep 17 00:00:00 2001 From: arnout Date: Tue, 21 Sep 2021 14:37:52 +0200 Subject: [PATCH 185/304] s_mp_rand_platform.c: s_read_urandom: correctly handle split read s_read_urandom has a while loop to handle read() that returns less than the full buffer (either due to EINTR or because more than the atomic guarantee from urandom was requested). However, the target of the read was always the base pointer p instead of the updated pointer q, so in the end less than the requested randomness is returned. Use q instead of p in the read() call. Signed-off-by: Arnout Vandecappelle --- s_mp_rand_platform.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 06b2f1bda..0a6982a55 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -95,7 +95,7 @@ static mp_err s_read_urandom(void *p, size_t n) if (fd == -1) return MP_ERR; while (n > 0u) { - ssize_t ret = read(fd, p, n); + ssize_t ret = read(fd, q, n); if (ret < 0) { if (errno == EINTR) { continue; From 65b6ff69fd980a3f5ea8a595193c169022c57a7f Mon Sep 17 00:00:00 2001 From: "Lvv.me" Date: Thu, 25 Nov 2021 13:37:24 +0800 Subject: [PATCH 186/304] Add Swift Package Manager support --- Package.swift | 36 ++++++++++++++++++++++++++++++++++++ modulemap/module.modulemap | 4 ++++ 2 files changed, 40 insertions(+) create mode 100644 Package.swift create mode 100644 modulemap/module.modulemap diff --git a/Package.swift b/Package.swift new file mode 100644 index 000000000..738bb7fda --- /dev/null +++ b/Package.swift @@ -0,0 +1,36 @@ +// swift-tools-version:5.0 +// The swift-tools-version declares the minimum version of Swift required to build this package. + +import PackageDescription + +let package = Package( + name: "tommath", + platforms: [ + .macOS(.v10_10), .iOS(.v9), .tvOS(.v9) + ], + products: [ + // Products define the executables and libraries a package produces, and make them visible to other packages. + .library( + name: "libtommath", + targets: ["libtommath"]) + ], + dependencies: [ + // Dependencies declare other packages that this package depends on. + // .package(url: /* package url */, from: "1.0.0"), + ], + targets: [ + // Targets are the basic building blocks of a package. A target can define a module or a test suite. + // Targets can depend on other targets in this package, and on products in packages this package depends on. + .target( + name: "libtommath", + path: ".", + exclude: ["demo", "doc", "etc", "logs", "mtest"], + sources: ["."], + publicHeadersPath: "modulemap", + cSettings: [ + .headerSearchPath(".") + ]) + ], + cLanguageStandard: .gnu11, + cxxLanguageStandard: .gnucxx14 +) diff --git a/modulemap/module.modulemap b/modulemap/module.modulemap new file mode 100644 index 000000000..7280be7e0 --- /dev/null +++ b/modulemap/module.modulemap @@ -0,0 +1,4 @@ +module libtommath [extern_c] { + header "../tommath.h" + export * +} From 8422235d2f7dddfebd3f5b5123030aebcc7a7479 Mon Sep 17 00:00:00 2001 From: "Lvv.me" Date: Thu, 25 Nov 2021 13:58:21 +0800 Subject: [PATCH 187/304] Add ThinLTO flags --- Package.swift | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Package.swift b/Package.swift index 738bb7fda..60a7d1ec3 100644 --- a/Package.swift +++ b/Package.swift @@ -28,7 +28,8 @@ let package = Package( sources: ["."], publicHeadersPath: "modulemap", cSettings: [ - .headerSearchPath(".") + .headerSearchPath("."), + .unsafeFlags(["-flto=thin"]) ]) ], cLanguageStandard: .gnu11, From 3d282f2ff2d7d7c13306a33a69571799cf342ed0 Mon Sep 17 00:00:00 2001 From: "Lvv.me" Date: Thu, 25 Nov 2021 14:12:24 +0800 Subject: [PATCH 188/304] Add comment for ThinLTO flags --- Package.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Package.swift b/Package.swift index 60a7d1ec3..1ed4dd3f7 100644 --- a/Package.swift +++ b/Package.swift @@ -29,7 +29,7 @@ let package = Package( publicHeadersPath: "modulemap", cSettings: [ .headerSearchPath("."), - .unsafeFlags(["-flto=thin"]) + .unsafeFlags(["-flto=thin"]) // for Dead Code Elimination ]) ], cLanguageStandard: .gnu11, From 9b6d7d5cac1af3217599e9fbd23fc83a9e536f76 Mon Sep 17 00:00:00 2001 From: "Lvv.me" Date: Wed, 1 Dec 2021 22:10:29 +0800 Subject: [PATCH 189/304] Add Swift Test case for libtommath --- demo/tommath_tests.swift | 94 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 94 insertions(+) create mode 100644 demo/tommath_tests.swift diff --git a/demo/tommath_tests.swift b/demo/tommath_tests.swift new file mode 100644 index 000000000..fd254da31 --- /dev/null +++ b/demo/tommath_tests.swift @@ -0,0 +1,94 @@ +import XCTest +import libtommath + +/* ---> Basic Manipulations <--- */ + +extension mp_int { + var isZero: Bool { used == 0 } + var isNeg: Bool { sign == MP_NEG } + var isEven: Bool { used == 0 || (dp[0] & 1) == 0 } + var isOdd: Bool { !isEven } +} + +func mp_get_u32(_ a: UnsafePointer) -> UInt32 { + return UInt32(bitPattern: mp_get_i32(a)) +} + +class LibTommathTests: XCTestCase { + + override func setUpWithError() throws { + // Put setup code here. This method is called before the invocation of each test method in the class. + } + + override func tearDownWithError() throws { + // Put teardown code here. This method is called after the invocation of each test method in the class. + } + + func testTrivialStuff() throws { + var a = mp_int() + var b = mp_int() + var c = mp_int() + var d = mp_int() + + XCTAssertEqual(mp_init(&a), MP_OKAY) + XCTAssertEqual(mp_init(&b), MP_OKAY) + XCTAssertEqual(mp_init(&c), MP_OKAY) + XCTAssertEqual(mp_init(&d), MP_OKAY) + + defer { + mp_clear(&a) + mp_clear(&b) + mp_clear(&c) + mp_clear(&d) + } + + XCTAssert(mp_error_to_string(MP_OKAY) != nil) + + /* a: 0->5 */ + mp_set(&a, 5) + /* a: 5-> b: -5 */ + XCTAssertEqual(mp_neg(&a, &b), MP_OKAY) + XCTAssertEqual(mp_cmp(&a, &b), MP_GT) + XCTAssertEqual(mp_cmp(&b, &a), MP_LT) + XCTAssertTrue(b.isNeg) + /* a: 5-> a: -5 */ + var t = a // Fix compiler error: Overlapping accesses to 'a', but modification requires exclusive access; consider copying to a local variable + XCTAssertEqual(mp_neg(&t, &a), MP_OKAY) + XCTAssertEqual(mp_cmp(&b, &a), MP_EQ) + XCTAssertTrue(a.isNeg) + /* a: -5-> b: 5 */ + XCTAssertEqual(mp_abs(&a, &b), MP_OKAY) + XCTAssertTrue(!b.isNeg) + /* a: -5-> b: -4 */ + XCTAssertEqual(mp_add_d(&a, 1, &b), MP_OKAY) + XCTAssertTrue(b.isNeg) + XCTAssertEqual(mp_get_i32(&b), -4) + XCTAssertEqual(mp_get_u32(&b), UInt32(bitPattern: -4)) + XCTAssertEqual(mp_get_mag_u32(&b), 4) + /* a: -5-> b: 1 */ + XCTAssertEqual(mp_add_d(&a, 6, &b), MP_OKAY) + XCTAssertEqual(mp_get_u32(&b), 1) + /* a: -5-> a: 1 */ + t = a + XCTAssertEqual(mp_add_d(&t, 6, &a), MP_OKAY) + XCTAssertEqual(mp_get_u32(&a), 1) + mp_zero(&a); + /* a: 0-> a: 6 */ + t = a + XCTAssertEqual(mp_add_d(&t, 6, &a), MP_OKAY) + XCTAssertEqual(mp_get_u32(&a), 6) + + mp_set(&a, 42) + mp_set(&b, 1) + t = b + XCTAssertEqual(mp_neg(&t, &b), MP_OKAY) + mp_set(&c, 1) + XCTAssertEqual(mp_exptmod(&a, &b, &c, &d), MP_OKAY) + + mp_set(&c, 7) + /* same here */ + XCTAssertTrue(mp_exptmod(&a, &b, &c, &d) != MP_OKAY) + + XCTAssertTrue(a.isEven != a.isOdd) + } +} From ac10f9da0df086df6531450284aa652ea03ad5b5 Mon Sep 17 00:00:00 2001 From: "Lvv.me" Date: Wed, 1 Dec 2021 22:43:45 +0800 Subject: [PATCH 190/304] Add testTarget for SwiftPM Run swift test case: ``` $ swift test ``` --- Package.swift | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/Package.swift b/Package.swift index 1ed4dd3f7..54a195b75 100644 --- a/Package.swift +++ b/Package.swift @@ -28,9 +28,12 @@ let package = Package( sources: ["."], publicHeadersPath: "modulemap", cSettings: [ - .headerSearchPath("."), .unsafeFlags(["-flto=thin"]) // for Dead Code Elimination - ]) + ]), + .testTarget(name: "TommathTests", + dependencies: ["libtommath"], + path: "demo", + sources: ["tommath_tests.swift"]) ], cLanguageStandard: .gnu11, cxxLanguageStandard: .gnucxx14 From ab7bcec57becb83d7c55b92ad94a4d7b289aa545 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 13 Dec 2021 21:08:49 +0100 Subject: [PATCH 191/304] Introduced 0 (zero) to mp_is_square as a perfect square --- demo/test.c | 11 +++++++++++ mp_is_square.c | 1 + 2 files changed, 12 insertions(+) diff --git a/demo/test.c b/demo/test.c index 4ce813140..b9ef5090e 100644 --- a/demo/test.c +++ b/demo/test.c @@ -677,6 +677,17 @@ static int test_mp_is_square(void) DOR(mp_init_multi(&a, &b, NULL)); + + /* Domain is {x \in \mathbb{Z} : x \le 0} */ + mp_set_l(&a, -1); + EXPECT(mp_is_square(&a, &res) == MP_VAL); + EXPECT(!res); + + /* Zero is a perfect square, too */ + mp_zero(&a); + DO(mp_is_square(&a, &res)); + EXPECT(res); + for (i = 0; i < 1000; ++i) { printf("%6d\r", i); fflush(stdout); diff --git a/mp_is_square.c b/mp_is_square.c index db1cb3fb3..d2856e255 100644 --- a/mp_is_square.c +++ b/mp_is_square.c @@ -41,6 +41,7 @@ mp_err mp_is_square(const mp_int *arg, bool *ret) } if (mp_iszero(arg)) { + *ret = true; return MP_OKAY; } From 17b0fd2a160904fa42f1e9d0fd1359e06c67ae7d Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 14 Feb 2022 14:32:04 +0100 Subject: [PATCH 192/304] migrate from travis to GitHub actions Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 148 +++++++++++++++++++++++++ .travis.yml | 217 ------------------------------------- makefile_include.mk | 2 +- testme.sh | 6 +- 4 files changed, 152 insertions(+), 221 deletions(-) create mode 100644 .github/workflows/main.yml delete mode 100644 .travis.yml diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml new file mode 100644 index 000000000..9e4cee07a --- /dev/null +++ b/.github/workflows/main.yml @@ -0,0 +1,148 @@ +############################################################################# +# # +# GitHub Actions test-suite for LibTomMath # +# (https://github.com/libtom/libtommath.git) # +# # +############################################################################# + +name: CI + +# Tests restricted to the following branches of LTM. +on: + push: + branches: + - master + - develop + - /^release\/.*$/ + - /^support\/.*$/ + - /^ci\/.*$/ + pull_request: + branches: + - master + - develop + - /^release\/.*$/ + - /^support\/.*$/ + - /^ci\/.*$/ + +jobs: + Build: + runs-on: ${{ matrix.os }} + strategy: + matrix: + os: [ ubuntu-18.04 ] + # The environment given to the programs in the build + # We have only one program and the variable $BUILDOPTIONS + # has only the options to that program: testme.sh + + config: + # Check c89 <-> c99 roundtrip + - { BUILDOPTIONS: '--c89-c99-roundtrip', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # Check source code format + - { BUILDOPTIONS: '--format', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'astyle' } + # Check public symbols of dynamic libraries + - { BUILDOPTIONS: '--symbols', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libtool-bin' } + # Run always with valgrind (no sanitizer, but debug info) + - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --with-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # Shared library build + - { BUILDOPTIONS: '--with-cc=gcc --make-option=-f --make-option=makefile.shared', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: 'gcc-8 libtool-bin' } + # GCC for the 32-bit architecture (no valgrind) + - { BUILDOPTIONS: '--with-cc=gcc --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } + # clang for the 32-bit architecture (no valgrind) + - { BUILDOPTIONS: '--with-cc=clang-7 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7 gcc-multilib' } + # RSA superclass with tests (no sanitizer, but debug info) + - { BUILDOPTIONS: '--with-cc=gcc-5 --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-5' } + + # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. + #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' + #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_32BIT --limit-valgrind --make-option=tune' + #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --limit-valgrind --make-option=tune' + #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' + #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_32BIT --limit-valgrind --make-option=tune' + - { BUILDOPTIONS: '--with-cc=clang-7 --limit-valgrind --make-option=tune', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + + # GCC for the x86-64 architecture testing against a different Bigint-implementation + # with 333333 different inputs. + #- env: BUILDOPTIONS='--with-cc=gcc --test-vs-mtest=333333 --limit-valgrind' + # ... and a better random source. + - { BUILDOPTIONS: '--with-cc=gcc --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + + # clang for the x86-64 architecture testing against a different Bigint-implementation + # with 333333 different inputs + - { BUILDOPTIONS: '--with-cc=clang-7 --test-vs-mtest=333333 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + # ... and a better random source. + - { BUILDOPTIONS: '--with-cc=clang-7 --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + + # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) + # TODO: Probably not possible to run anything in x32 in GH actions + # but needs to be checked to be sure. + - { BUILDOPTIONS: '--with-cc=gcc --with-mx32', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-x32 gcc-multilib' } + + # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) + - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + - { BUILDOPTIONS: '--with-cc=gcc-5 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-5' } + - { BUILDOPTIONS: '--with-cc=gcc-4.8 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-4.8' } + + # clang for x86-64 architecture (64-bit longs and 64-bit pointers) + - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'relaxed', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-7 --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-7 --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-9 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-9 llvm-9' } + - { BUILDOPTIONS: '--with-cc=clang-8 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-8 llvm-8' } + - { BUILDOPTIONS: '--with-cc=clang-6.0 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-6.0 llvm-6.0' } + - { BUILDOPTIONS: '--with-cc=clang-5.0 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-5.0 llvm-5.0' } + - { BUILDOPTIONS: '--with-cc=clang-4.0 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-4.0 llvm-4.0' } + # Link time optimization + - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } + #- { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } + + # GCC for the x86-64 architecture with restricted limb sizes + # formerly started with the option "--with-low-mp" to testme.sh + # but testing all three in one run took to long and timed out. + - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # clang for the x86-64 architecture with restricted limb sizes + - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } + steps: + - uses: actions/checkout@v2 + - name: install dependencies + run: | + sudo apt-get update -qq + sudo apt-get install -y valgrind ${{ matrix.config.OTHERDEPS }} + sudo apt-cache search gcc | grep '^gcc-[0-9\.]* ' + sudo apt-cache search clang | grep compiler + - name: run tests + env: + SANITIZER: ${{ matrix.config.SANITIZER }} + COMPILE_DEBUG: ${{ matrix.config.COMPILE_DEBUG }} + COMPILE_LTO: ${{ matrix.config.COMPILE_LTO }} + CONV_WARNINGS: ${{ matrix.config.CONV_WARNINGS }} + COMMIT_MESSAGE: ${{ github.event.commits[0].message }} + PR_NUMBER: ${{ github.event.number }} + # The actual script the jobs run. + run: | + ./testme.sh ${{ matrix.config.BUILDOPTIONS }} + # In case of a CI error a success might get signaled + # even without any test run. This file also keeps any notes + # printed from the tests which might come handy from time + # to time. + # Valgrid will print its output to stderr which will not show up + # in test_*.log. testme.sh accepts one additional option to + # valgrind and "--valgrind-options=--log-fd=1" sends the output + # of Valgrind to stdout instead. + - name: regular logs + if: ${{ !failure() }} + run: | + cat test_*.log || true + # Compilation failures are in gcc_errors_*.log + # Failed tests in test_*.log + # Files do not exist in case of success + - name: error logs + if: ${{ failure() }} + run: | + cat test_*.log || true + cat valgrind_test.log || true + cat gcc_errors_*.log || true diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index b97912ed6..000000000 --- a/.travis.yml +++ /dev/null @@ -1,217 +0,0 @@ -############################################################################# -# # -# Travis-ci test-suite for LibTomMath # -# (https://github.com/libtom/libtommath.git) # -# # -############################################################################# - -# The Ubuntu version we're going to use to run the tests -dist: bionic - -# Compilation failures are in gcc_errors_*.log -# Failed tests in test_*.log -# Files do not exist in case of success -after_failure: - - cat test_*.log - - cat valgrind_test.log - - cat gcc_errors_*.log - -# In case of a Travis error a success might get signaled -# even without any test run. This file also keeps any notes -# printed from the tests which might come handy from time -# to time. -# Valgrid will print its output to stderr which will not show up -# in test_*.log. testme.sh accepts one additional option to -# valgrind and "--valgrind-options=--log-fd=1" sends the output -# of Valgrind to stdout instead. -after_success: - - cat test_*.log - -# Tests restricted to the following branches of LTM. -branches: - only: - - master - - develop - - /^release/ - - /^support/ - - /^travis/ - -# Additional installs: Valgrind for memory tests. -install: - - sudo apt-get update -qq - - sudo apt-get install valgrind - - apt-cache search gcc | grep '^gcc-[0-9\.]* ' - - apt-cache search clang | grep compiler - -# The language is C and it will load the respective dependencies -language: c - -# The actual workspace. Will run the individual jobs in parallel -# which also means that the jobs must be able to run in parallel. -# Either specify sets which will be combined or, as in this case, -# specify all builds individually. The number of jobs is currently -# restricted to 200 jobs at most. -matrix: - # Will mark as finished if all of the remaining tests are allowed to fail - # or one test has failed already. - fast_finish: true - - # The individual jobs - include: - # The environment given to the programs in the build - # We have only one program and the variable $BUILDOPTIONS - # has only the options to that program: testme.sh - - # Check c89 <-> c99 roundtrip - - env: BUILDOPTIONS='--c89-c99-roundtrip' - - # Check source code format - - env: BUILDOPTIONS='--format' - addons: - apt: - packages: - - astyle - - # Check public symbols of dynamic libraries - - env: BUILDOPTIONS='--symbols' - addons: - apt: - packages: - - libtool-bin - - # Run always with valgrind (no sanitizer, but debug info) - - env: COMPILE_DEBUG=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-valgrind' - - # Shared library build - - env: COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc --make-option=-f --make-option=makefile.shared' - addons: - apt: - packages: - - gcc-8 - - libtool-bin - - # GCC for the 32-bit architecture (no valgrind) - - env: BUILDOPTIONS='--with-cc=gcc --with-m32' - addons: - apt: - packages: - - libc6-dev-i386 - - gcc-multilib - - # clang for the 32-bit architecture (no valgrind) - - env: BUILDOPTIONS='--with-cc=clang-7 --with-m32' - addons: - apt: - packages: - - libc6-dev-i386 - - gcc-multilib - - # RSA superclass with tests (no sanitizer, but debug info) - - env: COMPILE_DEBUG=1 BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --with-travis-valgrind' - - # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. - #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --with-travis-valgrind --make-option=tune' - #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_32BIT --with-travis-valgrind --make-option=tune' - #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --with-travis-valgrind --make-option=tune' - #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_16BIT --with-travis-valgrind --make-option=tune' - #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_32BIT --with-travis-valgrind --make-option=tune' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --with-travis-valgrind --make-option=tune' - - # GCC for the x86-64 architecture testing against a different Bigint-implementation - # with 333333 different inputs. - #- env: BUILDOPTIONS='--with-cc=gcc --test-vs-mtest=333333 --with-travis-valgrind' - # ... and a better random source. - - env: BUILDOPTIONS='--with-cc=gcc --test-vs-mtest=333333 --mtest-real-rand --with-travis-valgrind' - - # clang for the x86-64 architecture testing against a different Bigint-implementation - # with 333333 different inputs - - env: BUILDOPTIONS='--with-cc=clang-7 --test-vs-mtest=333333 --with-travis-valgrind' - # ... and a better random source. - #- env: BUILDOPTIONS='--with-cc=clang-7 --test-vs-mtest=333333 --mtest-real-rand --with-travis-valgrind' - - # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) - # TODO: Probably not possible to run anything in x32 in Travis - # but needs to be checked to be sure. - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --with-mx32' - addons: - apt: - packages: - - libc6-dev-x32 - - gcc-multilib - - # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-travis-valgrind' - - env: BUILDOPTIONS='--with-cc=gcc-5 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - gcc-5 - - env: BUILDOPTIONS='--with-cc=gcc-4.8 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - gcc-4.8 - - # clang for x86-64 architecture (64-bit longs and 64-bit pointers) - - env: SANITIZER=1 CONV_WARNINGS=relaxed BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_USE_MEMOPS --with-m64 --with-travis-valgrind' - - env: SANITIZER=1 CONV_WARNINGS=strict BUILDOPTIONS='--with-cc=clang-7 --c89 --with-m64 --with-travis-valgrind' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind --cflags=-DMP_PREC=MP_MIN_PREC' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-10 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-10 - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-9 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-9 - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-8 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-8 - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-6.0 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-6.0 - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-5.0 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-5.0 - - env: BUILDOPTIONS='--with-cc=clang-4.0 --with-m64 --with-travis-valgrind' - addons: - apt: - packages: - - clang-4.0 - - # Link time optimization - - env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=gcc --with-m64 --with-travis-valgrind' - #- env: SANITIZER=1 COMPILE_LTO=1 BUILDOPTIONS='--with-cc=clang-7 --with-m64 --with-travis-valgrind' - - # GCC for the x86-64 architecture with restricted limb sizes - # formerly started with the option "--with-low-mp" to testme.sh - # but testing all three in one run took to long and timed out. - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --cflags=-DMP_16BIT --with-travis-valgrind' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc --cflags=-DMP_32BIT --with-travis-valgrind' - - # clang for the x86-64 architecture with restricted limb sizes - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang --cflags=-DMP_16BIT --with-travis-valgrind' - - env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang --cflags=-DMP_32BIT --with-travis-valgrind' - -# Notifications go to -# An email address is also possible. -notifications: - irc: "chat.freenode.net#libtom-notifications" - -# The actual script the jobs run. -# Because of a default timeout of 10 minutes it was necessary to use -# a Travis tool to extend that timeout to 40 minutes. 50 minutes -# seem to be the max and 20 the default if travis_wait is called without -# any options. -script: - - ./testme.sh ${BUILDOPTIONS} diff --git a/makefile_include.mk b/makefile_include.mk index 9a152d733..0d17cec8f 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -48,7 +48,7 @@ endif LTM_CFLAGS += -I./ -Wall -Wsign-compare -Wextra -Wshadow -ifdef SANITIZER +ifneq (,$(SANITIZER)) LTM_CFLAGS += -fsanitize=undefined -fno-sanitize-recover=all -fno-sanitize=float-divide-by-zero endif diff --git a/testme.sh b/testme.sh index 9ff242a2c..80f967a34 100755 --- a/testme.sh +++ b/testme.sh @@ -62,7 +62,7 @@ All other options will be tested with all MP_xBIT configurations. --with-valgrind --with-valgrind=* Run in valgrind (slow!). - --with-travis-valgrind Run with valgrind on Travis on specific branches. + --limit-valgrind Run with valgrind on CI only on specific branches. --valgrind-options Additional Valgrind options Some of the options like e.g.: @@ -246,8 +246,8 @@ do fi start_alive_printing ;; - --with-travis-valgrind*) - if [[ ("$TRAVIS_BRANCH" == "develop" && "$TRAVIS_PULL_REQUEST" == "false") || "$TRAVIS_BRANCH" == *"valgrind"* || "$TRAVIS_COMMIT_MESSAGE" == *"valgrind"* ]] + --limit-valgrind*) + if [[ ("$GITHUB_BASE_REF" == "develop" && "$PR_NUMBER" == "") || "$GITHUB_REF_NAME" == *"valgrind"* || "$COMMIT_MESSAGE" == *"valgrind"* ]] then if [[ ${1#*d} != "" ]] then From f12c2ab51727709fd3132fe50689012b898ed35a Mon Sep 17 00:00:00 2001 From: Dilshod Urazov Date: Fri, 26 Mar 2021 10:47:25 +0300 Subject: [PATCH 193/304] Add FNV-1a hash function This allows to compute non-cryptographic hash of mp_int which can be used as a key in a hash table. --- demo/test.c | 51 ++++++++++++++++++++++++++++++++++++++++ libtommath_VS2008.vcproj | 4 ++++ makefile | 6 ++--- makefile.mingw | 6 ++--- makefile.msvc | 6 ++--- makefile.shared | 6 ++--- makefile.unix | 6 ++--- mp_hash.c | 36 ++++++++++++++++++++++++++++ tommath.def | 1 + tommath.h | 9 +++++++ tommath_class.h | 4 ++++ 11 files changed, 120 insertions(+), 15 deletions(-) create mode 100644 mp_hash.c diff --git a/demo/test.c b/demo/test.c index b9ef5090e..c87f97c00 100644 --- a/demo/test.c +++ b/demo/test.c @@ -153,6 +153,56 @@ static int test_trivial_stuff(void) return EXIT_FAILURE; } +static int test_mp_hash(void) +{ + mp_int a; + mp_hval hash; + int i; + int len = 5; + + const char *input[] = { + "0", + "///////////////////////////////////////////////////////////////////", + "4n9cbk886QtLQmofprid3l2Q0GD8Yv979Lh8BdZkFE8g2pDUUSMBET/+M/YFyVZ3mBp", + "5NlgzHhmIX05O5YoW5yW5reAlVNtRAlIcN2dfoATnNdc1Cw5lHZUTwNthmK6/ZLKfY6", + "3gweiHDX+ji5utraSe46IJX+uuh7iggs63xIpMP5MriU4Np+LpHI5are8RzS9pKh9xP" + }; + const mp_hval hvals[] = { +#if (MP_DIGIT_BIT == 15) + 0x50c5d1f, + 0x51b3ba04, + 0xf83febd7, + 0x2dc8624c, + 0xf5c2996b +#elif (MP_DIGIT_BIT == 60) + 0xaf63bd4c8601b7df, + 0xdb090f8a5cd75210, + 0xabae35c7872c107d, + 0xfec74888bcef5fcd, + 0x27ba96030abceda5 +#else + 0xaf63bd4c8601b7df, + 0x7e868fbf541faf44, + 0x420cca3a4cb623bb, + 0x16636d996304ee7f, + 0x33afc9f1b274fa67 +#endif + }; + + DOR(mp_init(&a)); + for (i = 0; i < len; ++i) { + DO(mp_read_radix(&a, input[i], 64)); + DO(mp_hash(&a, &hash)); + EXPECT(hash == hvals[i]); + } + + mp_clear(&a); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear(&a); + return EXIT_FAILURE; +} + static int check_get_set_i32(mp_int *a, int32_t b) { mp_clear(a); @@ -2164,6 +2214,7 @@ static int unit_tests(int argc, char **argv) #define T3(n, o1, o2, o3) { #n, (MP_HAS(o1) && MP_HAS(o2) && MP_HAS(o3)) ? test_##n : NULL } T0(feature_detection), T0(trivial_stuff), + T1(mp_hash, MP_HASH), T2(mp_get_set_i32, MP_GET_I32, MP_GET_MAG_U32), T2(mp_get_set_i64, MP_GET_I64, MP_GET_MAG_U64), T1(mp_and, MP_AND), diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 1bf2f6ba4..e27aa9860 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -480,6 +480,10 @@ RelativePath="mp_grow.c" > + + diff --git a/makefile b/makefile index a5e5bf173..7fa04d2ca 100644 --- a/makefile +++ b/makefile @@ -31,9 +31,9 @@ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ -mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ -mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ -mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_hash.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o \ +mp_init_l.o mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o \ +mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ diff --git a/makefile.mingw b/makefile.mingw index a0192d642..7aeb564e7 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -33,9 +33,9 @@ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ -mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ -mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ -mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_hash.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o \ +mp_init_l.o mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o \ +mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ diff --git a/makefile.msvc b/makefile.msvc index df886e902..59a365e1c 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -29,9 +29,9 @@ mp_cmp.obj mp_cmp_d.obj mp_cmp_mag.obj mp_cnt_lsb.obj mp_complement.obj mp_copy. mp_div.obj mp_div_2.obj mp_div_2d.obj mp_div_d.obj mp_dr_is_modulus.obj mp_dr_reduce.obj mp_dr_setup.obj \ mp_error_to_string.obj mp_exch.obj mp_expt_n.obj mp_exptmod.obj mp_exteuclid.obj mp_fread.obj mp_from_sbin.obj \ mp_from_ubin.obj mp_fwrite.obj mp_gcd.obj mp_get_double.obj mp_get_i32.obj mp_get_i64.obj mp_get_l.obj mp_get_mag_u32.obj \ -mp_get_mag_u64.obj mp_get_mag_ul.obj mp_grow.obj mp_init.obj mp_init_copy.obj mp_init_i32.obj mp_init_i64.obj mp_init_l.obj \ -mp_init_multi.obj mp_init_set.obj mp_init_size.obj mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj mp_invmod.obj \ -mp_is_square.obj mp_kronecker.obj mp_lcm.obj mp_log_n.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj \ +mp_get_mag_u64.obj mp_get_mag_ul.obj mp_grow.obj mp_hash.obj mp_init.obj mp_init_copy.obj mp_init_i32.obj mp_init_i64.obj \ +mp_init_l.obj mp_init_multi.obj mp_init_set.obj mp_init_size.obj mp_init_u32.obj mp_init_u64.obj mp_init_ul.obj \ +mp_invmod.obj mp_is_square.obj mp_kronecker.obj mp_lcm.obj mp_log_n.obj mp_lshd.obj mp_mod.obj mp_mod_2d.obj \ mp_montgomery_calc_normalization.obj mp_montgomery_reduce.obj mp_montgomery_setup.obj mp_mul.obj mp_mul_2.obj \ mp_mul_2d.obj mp_mul_d.obj mp_mulmod.obj mp_neg.obj mp_or.obj mp_pack.obj mp_pack_count.obj mp_prime_fermat.obj \ mp_prime_frobenius_underwood.obj mp_prime_is_prime.obj mp_prime_miller_rabin.obj mp_prime_next_prime.obj \ diff --git a/makefile.shared b/makefile.shared index 9319e658f..41a0cd200 100644 --- a/makefile.shared +++ b/makefile.shared @@ -28,9 +28,9 @@ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ -mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ -mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ -mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_hash.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o \ +mp_init_l.o mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o \ +mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ diff --git a/makefile.unix b/makefile.unix index 64fb5806e..be0467480 100644 --- a/makefile.unix +++ b/makefile.unix @@ -34,9 +34,9 @@ mp_cmp.o mp_cmp_d.o mp_cmp_mag.o mp_cnt_lsb.o mp_complement.o mp_copy.o mp_count mp_div.o mp_div_2.o mp_div_2d.o mp_div_d.o mp_dr_is_modulus.o mp_dr_reduce.o mp_dr_setup.o \ mp_error_to_string.o mp_exch.o mp_expt_n.o mp_exptmod.o mp_exteuclid.o mp_fread.o mp_from_sbin.o \ mp_from_ubin.o mp_fwrite.o mp_gcd.o mp_get_double.o mp_get_i32.o mp_get_i64.o mp_get_l.o mp_get_mag_u32.o \ -mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o mp_init_l.o \ -mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o mp_invmod.o \ -mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ +mp_get_mag_u64.o mp_get_mag_ul.o mp_grow.o mp_hash.o mp_init.o mp_init_copy.o mp_init_i32.o mp_init_i64.o \ +mp_init_l.o mp_init_multi.o mp_init_set.o mp_init_size.o mp_init_u32.o mp_init_u64.o mp_init_ul.o \ +mp_invmod.o mp_is_square.o mp_kronecker.o mp_lcm.o mp_log_n.o mp_lshd.o mp_mod.o mp_mod_2d.o \ mp_montgomery_calc_normalization.o mp_montgomery_reduce.o mp_montgomery_setup.o mp_mul.o mp_mul_2.o \ mp_mul_2d.o mp_mul_d.o mp_mulmod.o mp_neg.o mp_or.o mp_pack.o mp_pack_count.o mp_prime_fermat.o \ mp_prime_frobenius_underwood.o mp_prime_is_prime.o mp_prime_miller_rabin.o mp_prime_next_prime.o \ diff --git a/mp_hash.c b/mp_hash.c new file mode 100644 index 000000000..2add7578b --- /dev/null +++ b/mp_hash.c @@ -0,0 +1,36 @@ +#include "tommath_private.h" +#ifdef MP_HASH_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#if defined(MP_16BIT) +#define FNV_1A_INIT ((uint32_t)0x811c9dc5) +#define FNV_1A_PRIME ((uint32_t)0x01000193) +#else +#define FNV_1A_INIT ((uint64_t)0xcbf29ce484222325ULL) +#define FNV_1A_PRIME ((uint64_t)0x100000001b3ULL) +#endif + +/* computes hash of mp_int. */ +mp_err mp_hash(mp_int *a, mp_hval *hash) +{ + int x; + mp_hval hval = FNV_1A_INIT; + mp_digit r, mask, shift; + + /* FNV-1a algorithm */ + mask = ((mp_digit)1 << 8) - 1uL; + shift = (mp_digit)(MP_DIGIT_BIT - 8); + r = 0; + for (x = a->used; x --> 0;) { + mp_digit rr = a->dp[x] & mask; + hval ^= (mp_hval)(a->dp[x] >> 8) | (r << shift); + hval *= FNV_1A_PRIME; + r = rr; + } + hval ^= mp_isneg(a) ? (mp_hval)1 : (mp_hval)0; + *hash = hval * FNV_1A_PRIME; + + return MP_OKAY; +} +#endif diff --git a/tommath.def b/tommath.def index f0a9703f0..1af4e9e79 100644 --- a/tommath.def +++ b/tommath.def @@ -47,6 +47,7 @@ EXPORTS mp_get_mag_u64 mp_get_mag_ul mp_grow + mp_hash mp_init mp_init_copy mp_init_i32 diff --git a/tommath.h b/tommath.h index 25a166e77..44c92b22a 100644 --- a/tommath.h +++ b/tommath.h @@ -488,6 +488,15 @@ mp_err mp_reduce_2k_l(mp_int *a, const mp_int *n, const mp_int *d) MP_WUR; /* Y = G**X (mod P) */ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) MP_WUR; +#if defined(MP_16BIT) +typedef uint32_t mp_hval; +#else +typedef uint64_t mp_hval; +#endif + +/* computes hash */ +mp_err mp_hash(mp_int *a, mp_hval *hash) MP_WUR; + /* ---> Primes <--- */ /* performs one Fermat test of "a" using base "b". diff --git a/tommath_class.h b/tommath_class.h index da9c5ea72..becbcb193 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -53,6 +53,7 @@ # define MP_GET_MAG_U64_C # define MP_GET_MAG_UL_C # define MP_GROW_C +# define MP_HASH_C # define MP_INIT_C # define MP_INIT_COPY_C # define MP_INIT_I32_C @@ -386,6 +387,9 @@ # define S_MP_ZERO_DIGS_C #endif +#if defined(MP_HASH_C) +#endif + #if defined(MP_INIT_C) #endif From f37f6205986193ae903d4919bb271694eb6a70af Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 16 Feb 2022 12:38:15 +0100 Subject: [PATCH 194/304] add mp_hash doc Signed-off-by: Steffen Jaeckel --- doc/bn.tex | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/doc/bn.tex b/doc/bn.tex index 1dfb34d55..3e01e32df 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -1444,6 +1444,20 @@ \section{Integer Division and Remainder} such that $bc + d = a$. Note that either of $c$ or $d$ can be set to \texttt{NULL} if their value is not required. If $b$ is zero the function returns \texttt{MP\_VAL}. +\section{Hashing} +To get a non-cryptographic hash of an \texttt{mp\_int} use the following function. + +\index{mp\_hash} +\begin{alltt} +mp_err mp_hash (mp_int *a, mp_hval *hash); +\end{alltt} + +This will create the hash of $a$ following the \mbox{FNV-1a} algorithm as described on +\url{http://www.isthe.com/chongo/tech/comp/fnv/index.html#FNV-1a}. With the +help of this function one can use an \texttt{mp\_int} as a key in a hash table. + +NB: The hashing is not stable over different widths of an \texttt{mp\_digit}. + \chapter{Multiplication and Squaring} \section{Multiplication} A full signed integer multiplication can be performed with the following. From f993147b0ea0bdc6d80a3e043a7bdfd03f86f83e Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 13:48:43 +0100 Subject: [PATCH 195/304] git: ignore cmake build directories --- .gitignore | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.gitignore b/.gitignore index 696e0ec95..519e92772 100644 --- a/.gitignore +++ b/.gitignore @@ -104,3 +104,7 @@ logs/*.png logs/*-*.dem callgraph.txt + +# cmake build directories +build*/ + From 44b6517bcae2092b4cf1fcdedb19542dff796bb0 Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 13:49:10 +0100 Subject: [PATCH 196/304] git: ignore kdevelop generated files --- .gitignore | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.gitignore b/.gitignore index 519e92772..36fd9dd9b 100644 --- a/.gitignore +++ b/.gitignore @@ -108,3 +108,6 @@ callgraph.txt # cmake build directories build*/ +# kdevelop section +.kdev4/ +*.kdev4 From 019c3dcc128af3ace0ea7501cd285e2dfbb36535 Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 13:51:43 +0100 Subject: [PATCH 197/304] cmake: add cmake lists file --- CMakeLists.txt | 97 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 97 insertions(+) create mode 100644 CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 000000000..d9235995e --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,97 @@ +# +# LibTomMath, a free open source portable number theoretic multiple-precision +# integer (MPI) library written entirely in C. +# + +cmake_minimum_required(VERSION 3.7) +project(tommath VERSION 1.2.0) + +#----------------------------------------------------------------------------- +# Include cmake modules +#----------------------------------------------------------------------------- +include(GNUInstallDirs) +include(CMakePackageConfigHelpers) +include(sources.cmake) + +#----------------------------------------------------------------------------- +# library target +#----------------------------------------------------------------------------- +add_library(${PROJECT_NAME} + ${SOURCES} +) + +target_include_directories(${PROJECT_NAME} PUBLIC + $ + $ +) + +set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION}) +set_target_properties(${PROJECT_NAME} PROPERTIES SOVERSION ${PROJECT_VERSION_MAJOR}) + +#----------------------------------------------------------------------------- +# demo target +#----------------------------------------------------------------------------- +add_executable(test EXCLUDE_FROM_ALL + ${CMAKE_CURRENT_SOURCE_DIR}/demo/shared.c + ${CMAKE_CURRENT_SOURCE_DIR}/demo/test.c +) + +target_include_directories(test PRIVATE + ${CMAKE_CURRENT_SOURCE_DIR} +) + +target_link_libraries(test PRIVATE + ${PROJECT_NAME} +) + +#----------------------------------------------------------------------------- +# demo target +#----------------------------------------------------------------------------- +add_custom_target(check + COMMAND ${CMAKE_CURRENT_BINARY_DIR}/test +) + +add_dependencies(check test) + +#----------------------------------------------------------------------------- +# Install/export targets and files +#----------------------------------------------------------------------------- +set(CONFIG_INSTALL_DIR "${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}") +set(PROJECT_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}-config-version.cmake") +set(PROJECT_CONFIG_FILE "${PROJECT_NAME}-config.cmake") +set(TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") + +install(TARGETS ${PROJECT_NAME} + EXPORT ${TARGETS_EXPORT_NAME} + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} +) + +install(FILES ${HEADERS} + DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} +) + +# generate package version file +write_basic_package_version_file( + ${PROJECT_VERSION_FILE} + VERSION ${PROJECT_VERSION} + COMPATIBILITY SameMajorVersion +) + +# install version file +install(FILES ${PROJECT_VERSION_FILE} + DESTINATION ${CONFIG_INSTALL_DIR} +) + +# build directory package config +export(EXPORT ${TARGETS_EXPORT_NAME} + FILE ${PROJECT_CONFIG_FILE} +) + +# installed package config +install(EXPORT ${TARGETS_EXPORT_NAME} + DESTINATION ${CONFIG_INSTALL_DIR} + FILE ${PROJECT_CONFIG_FILE} +) + +# add to CMake registry +export(PACKAGE ${PROJECT_NAME}) From 8fd791d8365b4871f7cd061f3626416708231107 Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 13:52:40 +0100 Subject: [PATCH 198/304] cmake: have the sources/headers variables defined in a separated file --- sources.cmake | 165 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 165 insertions(+) create mode 100644 sources.cmake diff --git a/sources.cmake b/sources.cmake new file mode 100644 index 000000000..503a13c92 --- /dev/null +++ b/sources.cmake @@ -0,0 +1,165 @@ +set(SOURCES +mp_2expt.c +mp_abs.c +mp_add.c +mp_add_d.c +mp_addmod.c +mp_and.c +mp_clamp.c +mp_clear.c +mp_clear_multi.c +mp_cmp.c +mp_cmp_d.c +mp_cmp_mag.c +mp_cnt_lsb.c +mp_complement.c +mp_copy.c +mp_count_bits.c +mp_cutoffs.c +mp_div_2.c +mp_div_2d.c +mp_div_3.c +mp_div.c +mp_div_d.c +mp_dr_is_modulus.c +mp_dr_reduce.c +mp_dr_setup.c +mp_error_to_string.c +mp_exch.c +mp_exptmod.c +mp_expt_u32.c +mp_exteuclid.c +mp_fread.c +mp_from_sbin.c +mp_from_ubin.c +mp_fwrite.c +mp_gcd.c +mp_get_double.c +mp_get_i32.c +mp_get_i64.c +mp_get_l.c +mp_get_ll.c +mp_get_mag_u32.c +mp_get_mag_u64.c +mp_get_mag_ul.c +mp_get_mag_ull.c +mp_grow.c +mp_init.c +mp_init_copy.c +mp_init_i32.c +mp_init_i64.c +mp_init_l.c +mp_init_ll.c +mp_init_multi.c +mp_init_set.c +mp_init_size.c +mp_init_u32.c +mp_init_u64.c +mp_init_ul.c +mp_init_ull.c +mp_invmod.c +mp_is_square.c +mp_kronecker.c +mp_lcm.c +mp_log_u32.c +mp_lshd.c +mp_mod_2d.c +mp_mod.c +mp_montgomery_calc_normalization.c +mp_montgomery_reduce.c +mp_montgomery_setup.c +mp_mul_2.c +mp_mul_2d.c +mp_mul.c +mp_mul_d.c +mp_mulmod.c +mp_neg.c +mp_or.c +mp_pack.c +mp_pack_count.c +mp_prime_fermat.c +mp_prime_frobenius_underwood.c +mp_prime_is_prime.c +mp_prime_miller_rabin.c +mp_prime_next_prime.c +mp_prime_rabin_miller_trials.c +mp_prime_rand.c +mp_prime_strong_lucas_selfridge.c +mp_radix_size.c +mp_rand.c +mp_read_radix.c +mp_reduce_2k.c +mp_reduce_2k_l.c +mp_reduce_2k_setup.c +mp_reduce_2k_setup_l.c +mp_reduce.c +mp_reduce_is_2k.c +mp_reduce_is_2k_l.c +mp_reduce_setup.c +mp_root_u32.c +mp_rshd.c +mp_sbin_size.c +mp_set.c +mp_set_double.c +mp_set_i32.c +mp_set_i64.c +mp_set_l.c +mp_set_ll.c +mp_set_u32.c +mp_set_u64.c +mp_set_ul.c +mp_set_ull.c +mp_shrink.c +mp_signed_rsh.c +mp_sqr.c +mp_sqrmod.c +mp_sqrt.c +mp_sqrtmod_prime.c +mp_sub.c +mp_sub_d.c +mp_submod.c +mp_to_radix.c +mp_to_sbin.c +mp_to_ubin.c +mp_ubin_size.c +mp_unpack.c +mp_xor.c +mp_zero.c +s_mp_add.c +s_mp_copy_digs.c +s_mp_div_recursive.c +s_mp_div_school.c +s_mp_div_small.c +s_mp_exptmod.c +s_mp_exptmod_fast.c +s_mp_get_bit.c +s_mp_invmod.c +s_mp_invmod_odd.c +s_mp_log.c +s_mp_log_d.c +s_mp_log_pow2.c +s_mp_montgomery_reduce_comba.c +s_mp_mul_balance.c +s_mp_mul.c +s_mp_mul_comba.c +s_mp_mul_high.c +s_mp_mul_high_comba.c +s_mp_mul_karatsuba.c +s_mp_mul_toom.c +s_mp_prime_is_divisible.c +s_mp_prime_tab.c +s_mp_radix_map.c +s_mp_rand_jenkins.c +s_mp_rand_platform.c +s_mp_sqr.c +s_mp_sqr_comba.c +s_mp_sqr_karatsuba.c +s_mp_sqr_toom.c +s_mp_sub.c +s_mp_zero_buf.c +s_mp_zero_digs.c +) + +set(HEADERS +tommath.h +) From 6da9d1a970e9f83800d66e606e7281c6b2c8fd3b Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 16:08:59 +0100 Subject: [PATCH 199/304] cmake: rename test target fixes cmake (v3.10.2) error under ubuntu 18.04 due to reserved target name --- CMakeLists.txt | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index d9235995e..5a0d84907 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -31,16 +31,16 @@ set_target_properties(${PROJECT_NAME} PROPERTIES SOVERSION ${PROJECT_VERSION_MAJ #----------------------------------------------------------------------------- # demo target #----------------------------------------------------------------------------- -add_executable(test EXCLUDE_FROM_ALL +add_executable(test-target EXCLUDE_FROM_ALL ${CMAKE_CURRENT_SOURCE_DIR}/demo/shared.c ${CMAKE_CURRENT_SOURCE_DIR}/demo/test.c ) -target_include_directories(test PRIVATE +target_include_directories(test-target PRIVATE ${CMAKE_CURRENT_SOURCE_DIR} ) -target_link_libraries(test PRIVATE +target_link_libraries(test-target PRIVATE ${PROJECT_NAME} ) @@ -48,10 +48,10 @@ target_link_libraries(test PRIVATE # demo target #----------------------------------------------------------------------------- add_custom_target(check - COMMAND ${CMAKE_CURRENT_BINARY_DIR}/test + COMMAND ${CMAKE_CURRENT_BINARY_DIR}/test-target ) -add_dependencies(check test) +add_dependencies(check test-target) #----------------------------------------------------------------------------- # Install/export targets and files From 3c94017d7be3a8adb6fd9225ac5af19fb59f4f04 Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Mon, 9 Dec 2019 16:12:38 +0100 Subject: [PATCH 200/304] cmake: add cpack for generating packages --- CMakeLists.txt | 57 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 5a0d84907..de68266d6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -95,3 +95,60 @@ install(EXPORT ${TARGETS_EXPORT_NAME} # add to CMake registry export(PACKAGE ${PROJECT_NAME}) + +#--------------------------------------------------------------------------------------- +# Create release packages +#--------------------------------------------------------------------------------------- +# package release version +set(PACKAGE_RELEASE_VERSION 1) + +# determine distribution and architecture +find_program(LSB_RELEASE lsb_release) + +execute_process(COMMAND uname -m OUTPUT_VARIABLE MACHINE_ARCH OUTPUT_STRIP_TRAILING_WHITESPACE) + +if(LSB_RELEASE) + execute_process(COMMAND lsb_release -sr OUTPUT_VARIABLE LINUX_DISTRO_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND lsb_release -si OUTPUT_VARIABLE LINUX_DISTRO OUTPUT_STRIP_TRAILING_WHITESPACE) + + string(TOLOWER ${LINUX_DISTRO} LINUX_DISTRO) +endif() + +# default CPack generators +set(CPACK_GENERATOR TGZ STGZ) + +# extra CPack generators +if(LINUX_DISTRO STREQUAL "debian" OR LINUX_DISTRO STREQUAL "ubuntu" OR LINUX_DISTRO STREQUAL "linuxmint") + list(APPEND CPACK_GENERATOR DEB) +elseif(LINUX_DISTRO STREQUAL "fedora" OR LINUX_DISTRO STREQUAL "opensuse" OR LINUX_DISTRO STREQUAL "centos") + list(APPEND CPACK_GENERATOR RPM) +endif() + +# general CPack config +set(CPACK_PACKAGE_DIRECTORY ${CMAKE_BINARY_DIR}/packages) +message(STATUS "CPack: packages will be generated under ${CPACK_PACKAGE_DIRECTORY}") +set(CPACK_PACKAGE_NAME "lib${PROJECT_NAME}") +set(CPACK_PACKAGE_VERSION ${PROJECT_VERSION}) +set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "LibTomMath") +set(CPACK_PACKAGE_VENDOR "LibTomMath") +set(CPACK_PACKAGE_CONTACT "libtom@googlegroups.com") +set(CPACK_RESOURCE_FILE_LICENSE "${PROJECT_SOURCE_DIR}/LICENSE") +set(CPACK_PACKAGE_FILE_NAME ${CPACK_PACKAGE_NAME}-${CPACK_PACKAGE_VERSION}-${PACKAGE_RELEASE_VERSION}_${LINUX_DISTRO}-${LINUX_DISTRO_VERSION}_${MACHINE_ARCH}) +set(CPACK_STRIP_FILES ON) + +# deb specific CPack config +set(CPACK_DEBIAN_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) +set(CPACK_DEBIAN_FILE_NAME DEB-DEFAULT) +set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) +set(CPACK_DEBIAN_PACKAGE_HOMEPAGE "https://www.libtom.net/LibTomMath") +set(CPACK_DEBIAN_PACKAGE_SECTION "devel") + +# rpm specific CPack config +set(CPACK_RPM_PACKAGE_URL "https://www.libtom.net/LibTomMath") +set(CPACK_RPM_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) +set(CPACK_RPM_PACKAGE_ARCHITECTURE ${MACHINE_ARCH}) +set(CPACK_RPM_PACKAGE_NAME "lib${PROJECT_NAME}-${PROJECT_VERSION}") +set(CPACK_RPM_FILE_NAME "lib${PROJECT_NAME}_${PROJECT_VERSION}-${CPACK_RPM_PACKAGE_RELEASE}_${LINUX_DISTRO}-${LINUX_DISTRO_VERSION}_${CPACK_RPM_PACKAGE_ARCHITECTURE}.rpm") +set(CPACK_RPM_PACKAGE_LICENSE "WTFPL") + +include(CPack) From 7f9fbb648bbd41ad617b0a8df586c0a7e4e56247 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 16 Jan 2020 15:21:30 +0100 Subject: [PATCH 201/304] helper.pl: add support to update sources.cmake --- helper.pl | 16 ++++++++++++++-- sources.cmake | 29 ++++++++++++----------------- 2 files changed, 26 insertions(+), 19 deletions(-) diff --git a/helper.pl b/helper.pl index 20b0dc91d..ac87556b1 100755 --- a/helper.pl +++ b/helper.pl @@ -221,6 +221,16 @@ sub patch_file { return $content; } +sub make_sources_cmake { + my @list = @_; + my $output = "set(SOURCES\n"; + foreach my $obj (sort @list) { + $output .= $obj . "\n"; + } + $output .= ")\n\nset(HEADERS\ntommath.h\n)\n"; + return $output; +} + sub process_makefiles { my $write = shift; my $changed_count = 0; @@ -244,10 +254,12 @@ sub process_makefiles { } # update OBJECTS + HEADERS in makefile* - for my $m (qw/ makefile makefile.shared makefile_include.mk makefile.msvc makefile.unix makefile.mingw /) { + for my $m (qw/ makefile makefile.shared makefile_include.mk makefile.msvc makefile.unix makefile.mingw sources.cmake /) { my $old = read_file($m); my $new = $m eq 'makefile.msvc' ? patch_file($old, $var_obj) - : patch_file($old, $var_o); + : $m eq 'sources.cmake' ? make_sources_cmake(bsd_glob("*.c")) + : patch_file($old, $var_o); + if ($old ne $new) { write_file($m, $new) if $write; warn "changed: $m\n"; diff --git a/sources.cmake b/sources.cmake index 503a13c92..fd353c00a 100644 --- a/sources.cmake +++ b/sources.cmake @@ -16,18 +16,17 @@ mp_complement.c mp_copy.c mp_count_bits.c mp_cutoffs.c +mp_div.c mp_div_2.c mp_div_2d.c -mp_div_3.c -mp_div.c mp_div_d.c mp_dr_is_modulus.c mp_dr_reduce.c mp_dr_setup.c mp_error_to_string.c mp_exch.c +mp_expt_n.c mp_exptmod.c -mp_expt_u32.c mp_exteuclid.c mp_fread.c mp_from_sbin.c @@ -38,39 +37,35 @@ mp_get_double.c mp_get_i32.c mp_get_i64.c mp_get_l.c -mp_get_ll.c mp_get_mag_u32.c mp_get_mag_u64.c mp_get_mag_ul.c -mp_get_mag_ull.c mp_grow.c mp_init.c mp_init_copy.c mp_init_i32.c mp_init_i64.c mp_init_l.c -mp_init_ll.c mp_init_multi.c mp_init_set.c mp_init_size.c mp_init_u32.c mp_init_u64.c mp_init_ul.c -mp_init_ull.c mp_invmod.c mp_is_square.c mp_kronecker.c mp_lcm.c -mp_log_u32.c +mp_log_n.c mp_lshd.c -mp_mod_2d.c mp_mod.c +mp_mod_2d.c mp_montgomery_calc_normalization.c mp_montgomery_reduce.c mp_montgomery_setup.c +mp_mul.c mp_mul_2.c mp_mul_2d.c -mp_mul.c mp_mul_d.c mp_mulmod.c mp_neg.c @@ -86,17 +81,18 @@ mp_prime_rabin_miller_trials.c mp_prime_rand.c mp_prime_strong_lucas_selfridge.c mp_radix_size.c +mp_radix_size_overestimate.c mp_rand.c mp_read_radix.c +mp_reduce.c mp_reduce_2k.c mp_reduce_2k_l.c mp_reduce_2k_setup.c mp_reduce_2k_setup_l.c -mp_reduce.c mp_reduce_is_2k.c mp_reduce_is_2k_l.c mp_reduce_setup.c -mp_root_u32.c +mp_root_n.c mp_rshd.c mp_sbin_size.c mp_set.c @@ -104,14 +100,11 @@ mp_set_double.c mp_set_i32.c mp_set_i64.c mp_set_l.c -mp_set_ll.c mp_set_u32.c mp_set_u64.c mp_set_ul.c -mp_set_ull.c mp_shrink.c mp_signed_rsh.c -mp_sqr.c mp_sqrmod.c mp_sqrt.c mp_sqrtmod_prime.c @@ -127,6 +120,7 @@ mp_xor.c mp_zero.c s_mp_add.c s_mp_copy_digs.c +s_mp_div_3.c s_mp_div_recursive.c s_mp_div_school.c s_mp_div_small.c @@ -136,11 +130,11 @@ s_mp_get_bit.c s_mp_invmod.c s_mp_invmod_odd.c s_mp_log.c +s_mp_log_2expt.c s_mp_log_d.c -s_mp_log_pow2.c s_mp_montgomery_reduce_comba.c -s_mp_mul_balance.c s_mp_mul.c +s_mp_mul_balance.c s_mp_mul_comba.c s_mp_mul_high.c s_mp_mul_high_comba.c @@ -149,6 +143,7 @@ s_mp_mul_toom.c s_mp_prime_is_divisible.c s_mp_prime_tab.c s_mp_radix_map.c +s_mp_radix_size_overestimate.c s_mp_rand_jenkins.c s_mp_rand_platform.c s_mp_sqr.c From 97ba3e15d2bd08d38a21b9f0f2bfcbef935d28c6 Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Sun, 13 Feb 2022 12:47:40 +0100 Subject: [PATCH 202/304] cmake: update cmake sources file --- sources.cmake | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/sources.cmake b/sources.cmake index fd353c00a..7f395c952 100644 --- a/sources.cmake +++ b/sources.cmake @@ -41,6 +41,7 @@ mp_get_mag_u32.c mp_get_mag_u64.c mp_get_mag_ul.c mp_grow.c +mp_hash.c mp_init.c mp_init_copy.c mp_init_i32.c @@ -83,6 +84,7 @@ mp_prime_strong_lucas_selfridge.c mp_radix_size.c mp_radix_size_overestimate.c mp_rand.c +mp_rand_source.c mp_read_radix.c mp_reduce.c mp_reduce_2k.c @@ -144,7 +146,6 @@ s_mp_prime_is_divisible.c s_mp_prime_tab.c s_mp_radix_map.c s_mp_radix_size_overestimate.c -s_mp_rand_jenkins.c s_mp_rand_platform.c s_mp_sqr.c s_mp_sqr_comba.c From cc8614abee1c08c31cecd3f2c5ad4ffef76c2f3a Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Sat, 19 Feb 2022 12:18:20 +0100 Subject: [PATCH 203/304] cmake: define BUILD_SHARED_LIBS option... in addition to be able to pass it on cmake invokation tools like ccmake et al. will show it as a configurable option --- CMakeLists.txt | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index de68266d6..33e923e65 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -13,6 +13,11 @@ include(GNUInstallDirs) include(CMakePackageConfigHelpers) include(sources.cmake) +#----------------------------------------------------------------------------- +# Options +#----------------------------------------------------------------------------- +option(BUILD_SHARED_LIBS "Build shared library" FALSE) + #----------------------------------------------------------------------------- # library target #----------------------------------------------------------------------------- From 0a370845043f1c73bc0789d5baf7bb97d5170d2b Mon Sep 17 00:00:00 2001 From: Adrian Antonana Date: Sat, 19 Feb 2022 14:37:06 +0100 Subject: [PATCH 204/304] cmake: add missing LIBRARY DESTINATION in install targets --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 33e923e65..8394d1ff1 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -68,6 +68,7 @@ set(TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") install(TARGETS ${PROJECT_NAME} EXPORT ${TARGETS_EXPORT_NAME} + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) From 9412d1a63d137778cc690c4d8b9ba506d83f92de Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 17 Feb 2022 17:18:40 +0100 Subject: [PATCH 205/304] update README Signed-off-by: Steffen Jaeckel --- README.md | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index be5b20783..7ee58bbc0 100644 --- a/README.md +++ b/README.md @@ -6,9 +6,9 @@ This is the git repository for [LibTomMath](http://www.libtom.net/LibTomMath/), ### Travis CI -master: [![Build Status](https://api.travis-ci.org/libtom/libtommath.png?branch=master)](https://travis-ci.org/libtom/libtommath) +master: [![Build Status](https://github.com/libtom/libtommath/actions/workflows/main.yml/badge.svg?branch=master)](https://github.com/libtom/libtommath/actions/workflows/main.yml?query=branch%3Amaster+++) -develop: [![Build Status](https://api.travis-ci.org/libtom/libtommath.png?branch=develop)](https://travis-ci.org/libtom/libtommath) +develop: [![Build Status](https://github.com/libtom/libtommath/actions/workflows/main.yml/badge.svg?branch=develop)](https://github.com/libtom/libtommath/actions/workflows/main.yml?query=branch%3Adevelop+++) ### AppVeyor @@ -42,3 +42,17 @@ Tests are located in `demo/` and can be built in two flavors. ## Building and Installing Building is straightforward for GNU Linux only, the section "Building LibTomMath" in the documentation in `doc/bn.pdf` has the details. + +### CMake support + +The project provides support for the CMake build system. + +``` +git clone https://github.com/libtom/libtommath.git +mkdir -p libtommath/build +cd libtommath/build +cmake .. +make -j$(nproc) +``` + +A shared library build can be done by setting `-DBUILD_SHARED_LIBS=On` when invoking the `cmake` command. From e1788a822de827a5f869321f6a90b5ad31b420ca Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 17 Feb 2022 18:06:19 +0100 Subject: [PATCH 206/304] allow unit tests in shared library builds The test sources must be compiled with a special define and require optimisation in order to be able to run. Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 8394d1ff1..be652dd38 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -49,6 +49,19 @@ target_link_libraries(test-target PRIVATE ${PROJECT_NAME} ) +# for the SHARED_LIBRARY build we need some special flags enabled +# We also allow our users to override our selection by defining their own +# `CMAKE_C_FLAGS` on generation-phase. CMake itself doesn't allow a user +# to override settings defined in the CMakeLists.txt so we append it manually +# again even though CMake prepended it already. +target_compile_options(test-target BEFORE PRIVATE + $<$,SHARED_LIBRARY>:-O1 -DLTM_TEST_DYNAMIC> + ${CMAKE_C_FLAGS} +) +target_link_options(test-target BEFORE PRIVATE + $<$,SHARED_LIBRARY>:-O1> +) + #----------------------------------------------------------------------------- # demo target #----------------------------------------------------------------------------- From 7cacdedc874fc4463ef2a15c4038369a9106083b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 17 Feb 2022 18:06:43 +0100 Subject: [PATCH 207/304] add cmake tests to CI Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 25 ++++++++++++++++++++++++- 1 file changed, 24 insertions(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 9e4cee07a..015afe130 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -25,7 +25,7 @@ on: - /^ci\/.*$/ jobs: - Build: + Testme: runs-on: ${{ matrix.os }} strategy: matrix: @@ -146,3 +146,26 @@ jobs: cat test_*.log || true cat valgrind_test.log || true cat gcc_errors_*.log || true + + CMake: + runs-on: ${{ matrix.os }} + strategy: + matrix: + os: [ ubuntu-18.04, ubuntu-20.04 ] + config: + # Static library build + - { CMAKEOPTIONS: '', TARGET: 'check' } + # Shared library build + - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=On', TARGET: 'check'} + steps: + - uses: actions/checkout@v2 + - name: install dependencies + run: | + sudo apt-get update -qq + sudo apt-get install cmake + - name: build + run: | + mkdir build + cd build + cmake ${{ matrix.config.CMAKEOPTIONS }} .. + make -j$(nproc) ${{ matrix.config.TARGET }} From 391e47d1fb1f8a2f85e3ef02d343e9e745985ee9 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 20 Feb 2022 08:28:34 +0100 Subject: [PATCH 208/304] Made "test" work with shared lib, started gathering environment variables for CFLAGS --- CMakeLists.txt | 119 ++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 114 insertions(+), 5 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index be652dd38..972321c3b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -13,16 +13,124 @@ include(GNUInstallDirs) include(CMakePackageConfigHelpers) include(sources.cmake) +# The only direct cmake argument for now +option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \"ON\", default is static" OFF) + #----------------------------------------------------------------------------- -# Options +# Compose CFLAGS #----------------------------------------------------------------------------- -option(BUILD_SHARED_LIBS "Build shared library" FALSE) + +# check if there was one already set. +if(DEFINED ENV{LTM_CFLAGS}) + set(LTM_C_FLAGS $ENV{LTM_CFLAGS}) +endif() +if(DEFINED ENV{LTM_LDFLAGS}) + set(LTM_LD_FLAGS $ENV{LTM_LDFLAGS}) +endif() + +# Some information copied from makefile_include.mk + +# Basic set +set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wall -Wsign-compare -Wextra -Wshadow") + +# Do we run the sanitizer? +if(DEFINED ENV{SANITIZER}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all -fno-sanitize=float-divide-by-zero") +endif() + +if(NOT DEFINED ENV{NO_ADDTL_WARNINGS}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align") + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith") +endif() + +if(DEFINED ENV{CONV_WARNINGS}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -std=c89 -Wconversion -Wsign-conversion") + if($ENV{CONV_WARNINGS} EQUAL "strict") + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wc++-compat") + endif() +else() + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wsystem-headers") +endif() + +if(DEFINED ENV{COMPILE_DEBUG}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -g3") +endif() + +if(DEFINED ENV{COMPILE_SIZE}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Os") +else() + if(NOT DEFINED ENV{IGNORE_SPEED}) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -O3 -funroll-loops") + #x86 optimizations [should be valid for any GCC install though] + set(LTM_C_FLAGS "${LTM_C_FLAGS} -fomit-frame-pointer") + endif() + # TODO: + # if(DEFINED ENV{COMPILE_LTO}) + # set(LTM_C_FLAGS "${LTM_C_FLAGS} -flto") + # set(LTM_LD_FLAGS "${LTM_LD_FLAGS} -flto") + # #AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) + # endif() +endif() + +# What compiler do we have and what are their...uhm... peculiarities +# TODO: is the check for a C++ compiler necessary? +if( (CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") OR (CMAKE_CXX_COMPILER_ID MATCHES "(C|c?)lang")) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header") +endif() + +if( (CMAKE_C_COMPILER_ID MATCHES "mingw") OR (CMAKE_CXX_COMPILER_ID MATCHES "mingw")) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-shadow") +endif() + +if(DEFINED ENV{PLATFORM}) + if($ENV{PLATFORM} MATCHES "Darwin") + set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-nullability-completeness") + endif() + if($ENV{PLATFORM} MATCHES "CYGWIN") + set(LTM_C_FLAGS "${LTM_C_FLAGS} -no-undefined") + endif() +endif() + +# TODO: coverage (lgcov) + +# We have several private functions in the library and the "demo/test" programm +# needs a littkle note to be able to switch them off. Please use the static build +# to get a full test. +if(BUILD_SHARED_LIBS) + set(LTM_C_FLAGS "${LTM_C_FLAGS} -DLTM_TEST_DYNAMIC") +endif() + +# Bring it home +set(CMAKE_C_FLAGS "${LTM_C_FLAGS}") +set(CMAKE_C_FLAGS_DEBUG "${LTM_C_FLAGS}") +set(CMAKE_C_FLAGS_RELEASE "${LTM_C_FLAGS}") #----------------------------------------------------------------------------- # library target #----------------------------------------------------------------------------- -add_library(${PROJECT_NAME} - ${SOURCES} + +# TODO: There may be a way but I found none to build both at once without complication. +# It is possible with e.g. Linux where the static library is named libtommath.a +# and the dynamic library libtommath.so*, two different names. +# That is not the case with e.g. Windows where both types have the same name. +# See also: +# https://stackoverflow.com/questions/2152077/is-it-possible-to-get-cmake-to-build-both-a-static-and-shared-library-at-the-sam +if(BUILD_SHARED_LIBS) + add_library(${PROJECT_NAME} SHARED + ${SOURCES} + ) +else() + add_library(${PROJECT_NAME} STATIC + ${SOURCES} + ) +endif() + +# Clear cache manually +unset(BUILD_SHARED_LIBS CACHE) + +target_include_directories(${PROJECT_NAME} PUBLIC + $ + $ ) target_include_directories(${PROJECT_NAME} PUBLIC @@ -36,6 +144,8 @@ set_target_properties(${PROJECT_NAME} PROPERTIES SOVERSION ${PROJECT_VERSION_MAJ #----------------------------------------------------------------------------- # demo target #----------------------------------------------------------------------------- + + add_executable(test-target EXCLUDE_FROM_ALL ${CMAKE_CURRENT_SOURCE_DIR}/demo/shared.c ${CMAKE_CURRENT_SOURCE_DIR}/demo/test.c @@ -81,7 +191,6 @@ set(TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") install(TARGETS ${PROJECT_NAME} EXPORT ${TARGETS_EXPORT_NAME} - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) From 41574fab61ae47665ea3fd010363a8744aa97439 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 21 Feb 2022 10:51:14 +0100 Subject: [PATCH 209/304] simplify what was ported from the makefiles * remove some of the complicated logic. The additional warnings always make sense. CMake uses the state of `BUILD_SHARED_LIBS` to determine the library target type. Also remove the comment regarding building shared and static at the same time, as usually that's done as necessary by the user. * append user-defined {C,LD}FLAGS instead of preprending - we expect them to know what they do, so they can override our defaults * use target_{compile,link}_options() instead of setting variables Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 100 ++++++++++++++++++------------------------------- 1 file changed, 36 insertions(+), 64 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 972321c3b..3efd9535e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -20,49 +20,38 @@ option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \" # Compose CFLAGS #----------------------------------------------------------------------------- -# check if there was one already set. -if(DEFINED ENV{LTM_CFLAGS}) - set(LTM_C_FLAGS $ENV{LTM_CFLAGS}) -endif() -if(DEFINED ENV{LTM_LDFLAGS}) - set(LTM_LD_FLAGS $ENV{LTM_LDFLAGS}) -endif() - # Some information copied from makefile_include.mk # Basic set -set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wall -Wsign-compare -Wextra -Wshadow") +set(LTM_C_FLAGS -Wall -Wsign-compare -Wextra -Wshadow) +set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align) +set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith) # Do we run the sanitizer? if(DEFINED ENV{SANITIZER}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all -fno-sanitize=float-divide-by-zero") -endif() - -if(NOT DEFINED ENV{NO_ADDTL_WARNINGS}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align") - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all -fno-sanitize=float-divide-by-zero) endif() if(DEFINED ENV{CONV_WARNINGS}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -std=c89 -Wconversion -Wsign-conversion") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -std=c89 -Wconversion -Wsign-conversion) if($ENV{CONV_WARNINGS} EQUAL "strict") - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wc++-compat") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wc++-compat) endif() else() - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wsystem-headers") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wsystem-headers) endif() if(DEFINED ENV{COMPILE_DEBUG}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -g3") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -g3) endif() if(DEFINED ENV{COMPILE_SIZE}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Os") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Os) else() if(NOT DEFINED ENV{IGNORE_SPEED}) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -O3 -funroll-loops") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -O3 -funroll-loops) #x86 optimizations [should be valid for any GCC install though] - set(LTM_C_FLAGS "${LTM_C_FLAGS} -fomit-frame-pointer") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -fomit-frame-pointer) endif() # TODO: # if(DEFINED ENV{COMPILE_LTO}) @@ -72,70 +61,56 @@ else() # endif() endif() +# TODO +# Are the coming three checks really the best way? + # What compiler do we have and what are their...uhm... peculiarities # TODO: is the check for a C++ compiler necessary? if( (CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") OR (CMAKE_CXX_COMPILER_ID MATCHES "(C|c?)lang")) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header) endif() if( (CMAKE_C_COMPILER_ID MATCHES "mingw") OR (CMAKE_CXX_COMPILER_ID MATCHES "mingw")) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-shadow") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-shadow) endif() if(DEFINED ENV{PLATFORM}) if($ENV{PLATFORM} MATCHES "Darwin") - set(LTM_C_FLAGS "${LTM_C_FLAGS} -Wno-nullability-completeness") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-nullability-completeness) endif() if($ENV{PLATFORM} MATCHES "CYGWIN") - set(LTM_C_FLAGS "${LTM_C_FLAGS} -no-undefined") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -no-undefined) endif() endif() # TODO: coverage (lgcov) -# We have several private functions in the library and the "demo/test" programm -# needs a littkle note to be able to switch them off. Please use the static build -# to get a full test. -if(BUILD_SHARED_LIBS) - set(LTM_C_FLAGS "${LTM_C_FLAGS} -DLTM_TEST_DYNAMIC") +# If the user set the environment variables at generate-time, append them +# in order to allow overriding our defaults. +if(DEFINED ENV{LTM_CFLAGS}) + set(LTM_C_FLAGS ${LTM_C_FLAGS} $ENV{LTM_CFLAGS}) +endif() +if(DEFINED ENV{LTM_LDFLAGS}) + set(LTM_LD_FLAGS ${LTM_LD_FLAGS} $ENV{LTM_LDFLAGS}) endif() - -# Bring it home -set(CMAKE_C_FLAGS "${LTM_C_FLAGS}") -set(CMAKE_C_FLAGS_DEBUG "${LTM_C_FLAGS}") -set(CMAKE_C_FLAGS_RELEASE "${LTM_C_FLAGS}") #----------------------------------------------------------------------------- # library target #----------------------------------------------------------------------------- - -# TODO: There may be a way but I found none to build both at once without complication. -# It is possible with e.g. Linux where the static library is named libtommath.a -# and the dynamic library libtommath.so*, two different names. -# That is not the case with e.g. Windows where both types have the same name. -# See also: -# https://stackoverflow.com/questions/2152077/is-it-possible-to-get-cmake-to-build-both-a-static-and-shared-library-at-the-sam -if(BUILD_SHARED_LIBS) - add_library(${PROJECT_NAME} SHARED - ${SOURCES} - ) -else() - add_library(${PROJECT_NAME} STATIC - ${SOURCES} - ) -endif() - -# Clear cache manually -unset(BUILD_SHARED_LIBS CACHE) +add_library(${PROJECT_NAME} + ${SOURCES} +) target_include_directories(${PROJECT_NAME} PUBLIC $ $ ) -target_include_directories(${PROJECT_NAME} PUBLIC - $ - $ +target_compile_options(${PROJECT_NAME} BEFORE PRIVATE + ${LTM_C_FLAGS} +) +target_link_options(${PROJECT_NAME} BEFORE PRIVATE + ${LTM_LD_FLAGS} ) set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION}) @@ -159,17 +134,13 @@ target_link_libraries(test-target PRIVATE ${PROJECT_NAME} ) -# for the SHARED_LIBRARY build we need some special flags enabled -# We also allow our users to override our selection by defining their own -# `CMAKE_C_FLAGS` on generation-phase. CMake itself doesn't allow a user -# to override settings defined in the CMakeLists.txt so we append it manually -# again even though CMake prepended it already. target_compile_options(test-target BEFORE PRIVATE $<$,SHARED_LIBRARY>:-O1 -DLTM_TEST_DYNAMIC> - ${CMAKE_C_FLAGS} + ${LTM_C_FLAGS} ) target_link_options(test-target BEFORE PRIVATE $<$,SHARED_LIBRARY>:-O1> + ${LTM_LD_FLAGS} ) #----------------------------------------------------------------------------- @@ -191,6 +162,7 @@ set(TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") install(TARGETS ${PROJECT_NAME} EXPORT ${TARGETS_EXPORT_NAME} + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) From cb8f2128a19ab04bf34e82a00841e1bff6dda88c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 21 Feb 2022 11:18:52 +0100 Subject: [PATCH 210/304] add SPDX identifiers Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 1 + helper.pl | 5 ++++- sources.cmake | 3 +++ 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 3efd9535e..d74e86643 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,3 +1,4 @@ +# SPDX-License-Identifier: Unlicense # # LibTomMath, a free open source portable number theoretic multiple-precision # integer (MPI) library written entirely in C. diff --git a/helper.pl b/helper.pl index ac87556b1..3701799fe 100755 --- a/helper.pl +++ b/helper.pl @@ -223,7 +223,10 @@ sub patch_file { sub make_sources_cmake { my @list = @_; - my $output = "set(SOURCES\n"; + my $output = "# SPDX-License-Identifier: Unlicense +# Autogenerated File! Do not edit. + +set(SOURCES\n"; foreach my $obj (sort @list) { $output .= $obj . "\n"; } diff --git a/sources.cmake b/sources.cmake index 7f395c952..2bc891139 100644 --- a/sources.cmake +++ b/sources.cmake @@ -1,3 +1,6 @@ +# SPDX-License-Identifier: Unlicense +# Autogenerated File! Do not edit. + set(SOURCES mp_2expt.c mp_abs.c From ba74457fb46aa4def2978b713eb0ea0f182ff6f0 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 2 Mar 2022 22:28:49 +0100 Subject: [PATCH 211/304] Build and install libtommath.pc --- CMakeLists.txt | 13 +++++++++++++ libtommath.pc.in | 9 ++++----- 2 files changed, 17 insertions(+), 5 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index d74e86643..474ae691c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -171,6 +171,19 @@ install(FILES ${HEADERS} DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} ) +# Install libtommath.pc for pkg-config if we build a shared library +if(BUILD_SHARED_LIBS) + configure_file( + ${CMAKE_CURRENT_SOURCE_DIR}/lib${PROJECT_NAME}.pc.in + ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc + @ONLY + ) + + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc + DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/pkgconfig + ) +endif() + # generate package version file write_basic_package_version_file( ${PROJECT_VERSION_FILE} diff --git a/libtommath.pc.in b/libtommath.pc.in index 099b1cd74..ad8f5c3bb 100644 --- a/libtommath.pc.in +++ b/libtommath.pc.in @@ -1,10 +1,9 @@ -prefix=@to-be-replaced@ -exec_prefix=${prefix} -libdir=${exec_prefix}/lib -includedir=${prefix}/include +prefix=@CMAKE_INSTALL_PREFIX@ +libdir=${prefix}/@CMAKE_INSTALL_LIBDIR@ +includedir=${prefix}/@CMAKE_INSTALL_INCLUDEDIR@/@PROJECT_NAME@ Name: LibTomMath Description: public domain library for manipulating large integer numbers -Version: @to-be-replaced@ +Version: @PROJECT_VERSION@ Libs: -L${libdir} -ltommath Cflags: -I${includedir} From 22dfda7ea085d51c00dcbe841c94a61819c5dc39 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 27 Feb 2022 12:56:09 +0100 Subject: [PATCH 212/304] further simplifications/improvements * bump to CMake 3.10 * only support the CMake standard way to define variables via `-DFOO=On` and not via the environment * clean-up switches only used for unit tests * mingw's ID is "GNU", so we match on the full compiler name instead * use CMake variables instead of environment variables via `$ENV{}` * unconditionally set {C,LD}FLAGS passed by user * clean-up duplicate CPack keys + add FreeBSD config * store pack files in distro-specific paths * use default names where possible * use `CMAKE_BUILD_TYPE`-style variables instead of our own flags * set default `CMAKE_BUILD_TYPE` to "Release" Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 138 +++++++++++++++++++++++++------------------------ 1 file changed, 70 insertions(+), 68 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 474ae691c..a4bdac3e9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -4,8 +4,18 @@ # integer (MPI) library written entirely in C. # -cmake_minimum_required(VERSION 3.7) -project(tommath VERSION 1.2.0) +cmake_minimum_required(VERSION 3.10) + +project(tommath + VERSION 1.2.0 + DESCRIPTION "A free open source portable number theoretic multiple-precision integer (MPI) library written entirely in C." + HOMEPAGE_URL "https://www.libtom.net/LibTomMath" + LANGUAGES C) + +# package release version +# bump if re-releasing the same VERSION + patches +# set to 1 if releasing a new VERSION +set(PACKAGE_RELEASE_VERSION 1) #----------------------------------------------------------------------------- # Include cmake modules @@ -26,74 +36,47 @@ option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \" # Basic set set(LTM_C_FLAGS -Wall -Wsign-compare -Wextra -Wshadow) set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align) -set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith) +set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith -Wsystem-headers) -# Do we run the sanitizer? -if(DEFINED ENV{SANITIZER}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all -fno-sanitize=float-divide-by-zero) +if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) + message(STATUS "Setting build type to 'Release' as none was specified.") + set(CMAKE_BUILD_TYPE "Release") endif() -if(DEFINED ENV{CONV_WARNINGS}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -std=c89 -Wconversion -Wsign-conversion) - if($ENV{CONV_WARNINGS} EQUAL "strict") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wc++-compat) - endif() -else() - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wsystem-headers) -endif() +set(CMAKE_C_FLAGS_DEBUG "-g3") +set(CMAKE_C_FLAGS_RELEASE "-O3 -funroll-loops -fomit-frame-pointer") +set(CMAKE_C_FLAGS_RELWITHDEBINFO "-g3 -O2") +set(CMAKE_C_FLAGS_MINSIZEREL "-Os") -if(DEFINED ENV{COMPILE_DEBUG}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -g3) +if(COMPILE_LTO) + set(LTM_C_FLAGS ${LTM_C_FLAGS} -flto) + set(LTM_LD_FLAGS ${LTM_LD_FLAGS} -flto) endif() -if(DEFINED ENV{COMPILE_SIZE}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Os) -else() - if(NOT DEFINED ENV{IGNORE_SPEED}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -O3 -funroll-loops) - #x86 optimizations [should be valid for any GCC install though] - set(LTM_C_FLAGS ${LTM_C_FLAGS} -fomit-frame-pointer) - endif() - # TODO: - # if(DEFINED ENV{COMPILE_LTO}) - # set(LTM_C_FLAGS "${LTM_C_FLAGS} -flto") - # set(LTM_LD_FLAGS "${LTM_LD_FLAGS} -flto") - # #AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) - # endif() -endif() - -# TODO -# Are the coming three checks really the best way? - # What compiler do we have and what are their...uhm... peculiarities -# TODO: is the check for a C++ compiler necessary? -if( (CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") OR (CMAKE_CXX_COMPILER_ID MATCHES "(C|c?)lang")) +if(CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header) + # Clang requires at least '-O1' for dead code eliminiation + set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -O1") endif() - -if( (CMAKE_C_COMPILER_ID MATCHES "mingw") OR (CMAKE_CXX_COMPILER_ID MATCHES "mingw")) +if(CMAKE_C_COMPILER MATCHES "mingw") set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-shadow) endif() - -if(DEFINED ENV{PLATFORM}) - if($ENV{PLATFORM} MATCHES "Darwin") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-nullability-completeness) - endif() - if($ENV{PLATFORM} MATCHES "CYGWIN") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -no-undefined) - endif() +if(CMAKE_SYSTEM_NAME MATCHES "Darwin") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-nullability-completeness) +endif() +if(CMAKE_SYSTEM_NAME MATCHES "CYGWIN") + set(LTM_C_FLAGS ${LTM_C_FLAGS} -no-undefined) endif() # TODO: coverage (lgcov) # If the user set the environment variables at generate-time, append them # in order to allow overriding our defaults. -if(DEFINED ENV{LTM_CFLAGS}) - set(LTM_C_FLAGS ${LTM_C_FLAGS} $ENV{LTM_CFLAGS}) -endif() -if(DEFINED ENV{LTM_LDFLAGS}) - set(LTM_LD_FLAGS ${LTM_LD_FLAGS} $ENV{LTM_LDFLAGS}) -endif() +# ${LTM_CFLAGS} means the user passed it via sth like: +# $ cmake -DLTM_CFLAGS="foo" +set(LTM_C_FLAGS ${LTM_C_FLAGS} ${LTM_CFLAGS}) +set(LTM_LD_FLAGS ${LTM_LD_FLAGS} ${LTM_LDFLAGS}) #----------------------------------------------------------------------------- # library target @@ -114,8 +97,10 @@ target_link_options(${PROJECT_NAME} BEFORE PRIVATE ${LTM_LD_FLAGS} ) -set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION}) -set_target_properties(${PROJECT_NAME} PROPERTIES SOVERSION ${PROJECT_VERSION_MAJOR}) +set_target_properties(${PROJECT_NAME} PROPERTIES + VERSION ${PROJECT_VERSION} + SOVERSION ${PROJECT_VERSION_MAJOR} +) #----------------------------------------------------------------------------- # demo target @@ -213,8 +198,6 @@ export(PACKAGE ${PROJECT_NAME}) #--------------------------------------------------------------------------------------- # Create release packages #--------------------------------------------------------------------------------------- -# package release version -set(PACKAGE_RELEASE_VERSION 1) # determine distribution and architecture find_program(LSB_RELEASE lsb_release) @@ -222,10 +205,18 @@ find_program(LSB_RELEASE lsb_release) execute_process(COMMAND uname -m OUTPUT_VARIABLE MACHINE_ARCH OUTPUT_STRIP_TRAILING_WHITESPACE) if(LSB_RELEASE) - execute_process(COMMAND lsb_release -sr OUTPUT_VARIABLE LINUX_DISTRO_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) execute_process(COMMAND lsb_release -si OUTPUT_VARIABLE LINUX_DISTRO OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND lsb_release -sc OUTPUT_VARIABLE LINUX_DISTRO_CODENAME OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND lsb_release -sr OUTPUT_VARIABLE LINUX_DISTRO_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) string(TOLOWER ${LINUX_DISTRO} LINUX_DISTRO) + if(LINUX_DISTRO_CODENAME STREQUAL "n/a") + set(DISTRO_PACK_PATH ${LINUX_DISTRO}/${LINUX_DISTRO_VERSION}/) + else() + set(DISTRO_PACK_PATH ${LINUX_DISTRO}/${LINUX_DISTRO_CODENAME}/) + endif() +else() + set(DISTRO_PACK_PATH ${CMAKE_SYSTEM_NAME}/) endif() # default CPack generators @@ -236,33 +227,44 @@ if(LINUX_DISTRO STREQUAL "debian" OR LINUX_DISTRO STREQUAL "ubuntu" OR LINUX_DIS list(APPEND CPACK_GENERATOR DEB) elseif(LINUX_DISTRO STREQUAL "fedora" OR LINUX_DISTRO STREQUAL "opensuse" OR LINUX_DISTRO STREQUAL "centos") list(APPEND CPACK_GENERATOR RPM) +elseif(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD") + list(APPEND CPACK_GENERATOR FREEBSD) endif() # general CPack config -set(CPACK_PACKAGE_DIRECTORY ${CMAKE_BINARY_DIR}/packages) +set(CPACK_PACKAGE_DIRECTORY ${CMAKE_BINARY_DIR}/packages/${DISTRO_PACK_PATH}) message(STATUS "CPack: packages will be generated under ${CPACK_PACKAGE_DIRECTORY}") set(CPACK_PACKAGE_NAME "lib${PROJECT_NAME}") set(CPACK_PACKAGE_VERSION ${PROJECT_VERSION}) set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "LibTomMath") -set(CPACK_PACKAGE_VENDOR "LibTomMath") +set(CPACK_PACKAGE_VENDOR "libtom projects") set(CPACK_PACKAGE_CONTACT "libtom@googlegroups.com") set(CPACK_RESOURCE_FILE_LICENSE "${PROJECT_SOURCE_DIR}/LICENSE") -set(CPACK_PACKAGE_FILE_NAME ${CPACK_PACKAGE_NAME}-${CPACK_PACKAGE_VERSION}-${PACKAGE_RELEASE_VERSION}_${LINUX_DISTRO}-${LINUX_DISTRO_VERSION}_${MACHINE_ARCH}) +set(PACKAGE_NAME_TRAILER ${CPACK_PACKAGE_VERSION}-${PACKAGE_RELEASE_VERSION}_${MACHINE_ARCH}) +set(CPACK_PACKAGE_FILE_NAME ${CPACK_PACKAGE_NAME}-${PACKAGE_NAME_TRAILER}) set(CPACK_STRIP_FILES ON) # deb specific CPack config -set(CPACK_DEBIAN_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) set(CPACK_DEBIAN_FILE_NAME DEB-DEFAULT) set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) -set(CPACK_DEBIAN_PACKAGE_HOMEPAGE "https://www.libtom.net/LibTomMath") -set(CPACK_DEBIAN_PACKAGE_SECTION "devel") +set(CPACK_DEBIAN_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) +if(BUILD_SHARED_LIBS) + set(CPACK_DEBIAN_PACKAGE_NAME "${CPACK_PACKAGE_NAME}1") + set(CPACK_DEBIAN_PACKAGE_SECTION "libs") +else() + set(CPACK_DEBIAN_PACKAGE_NAME "${CPACK_PACKAGE_NAME}-dev") + set(CPACK_DEBIAN_PACKAGE_SECTION "devel") +endif() # rpm specific CPack config -set(CPACK_RPM_PACKAGE_URL "https://www.libtom.net/LibTomMath") set(CPACK_RPM_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) set(CPACK_RPM_PACKAGE_ARCHITECTURE ${MACHINE_ARCH}) -set(CPACK_RPM_PACKAGE_NAME "lib${PROJECT_NAME}-${PROJECT_VERSION}") -set(CPACK_RPM_FILE_NAME "lib${PROJECT_NAME}_${PROJECT_VERSION}-${CPACK_RPM_PACKAGE_RELEASE}_${LINUX_DISTRO}-${LINUX_DISTRO_VERSION}_${CPACK_RPM_PACKAGE_ARCHITECTURE}.rpm") -set(CPACK_RPM_PACKAGE_LICENSE "WTFPL") +set(CPACK_RPM_PACKAGE_NAME "${CPACK_PACKAGE_NAME}-${PROJECT_VERSION}") +set(CPACK_RPM_PACKAGE_LICENSE "The Unlicense") + +# FreeBSD specific CPack config +set(CPACK_FREEBSD_PACKAGE_MAINTAINER "gahr@FreeBSD.org") +set(CPACK_FREEBSD_PACKAGE_ORIGIN "math/libtommath") +set(CPACK_FREEBSD_PACKAGE_CATEGORIES "math") include(CPack) From ed6ad7d9abaf92204ad9e5f7cf1261bbe72b1fc4 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 15 Mar 2022 14:12:09 +0100 Subject: [PATCH 213/304] extend CI matrix for different cmake options Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 015afe130..bfda74b7c 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -152,6 +152,8 @@ jobs: strategy: matrix: os: [ ubuntu-18.04, ubuntu-20.04 ] + build_type: [ '', -DCMAKE_BUILD_TYPE=Debug, -DCMAKE_BUILD_TYPE=Release, -DCMAKE_BUILD_TYPE=RelWithDebInfo, -DCMAKE_BUILD_TYPE=MinSizeRel ] + cc: [ clang, gcc ] config: # Static library build - { CMAKEOPTIONS: '', TARGET: 'check' } @@ -162,10 +164,10 @@ jobs: - name: install dependencies run: | sudo apt-get update -qq - sudo apt-get install cmake + sudo apt-get install -y cmake gcc clang llvm - name: build run: | mkdir build cd build - cmake ${{ matrix.config.CMAKEOPTIONS }} .. + CC=${{ matrix.cc }} cmake ${{ matrix.config.CMAKEOPTIONS }} ${{ matrix.build_type }} .. make -j$(nproc) ${{ matrix.config.TARGET }} From ab9ba06d4deb5e50d8efb43c9b18f4c1e99626b3 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Mar 2022 13:49:02 +0100 Subject: [PATCH 214/304] fix `pkgconfig` creation in `makefile.shared` Signed-off-by: Steffen Jaeckel --- makefile.shared | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/makefile.shared b/makefile.shared index 41a0cd200..4938da820 100644 --- a/makefile.shared +++ b/makefile.shared @@ -65,7 +65,8 @@ install: $(LIBNAME) install -d $(DESTDIR)$(INCPATH) $(LIBTOOL) --mode=install install -m 644 $(LIBNAME) $(DESTDIR)$(LIBPATH)/$(LIBNAME) install -m 644 $(HEADERS_PUB) $(DESTDIR)$(INCPATH) - sed -e 's,^prefix=.*,prefix=$(PREFIX),' -e 's,^Version:.*,Version: $(VERSION_PC),' libtommath.pc.in > libtommath.pc + sed -e 's,^prefix=.*,prefix=$(PREFIX),' -e 's,^Version:.*,Version: $(VERSION_PC),' -e 's,@CMAKE_INSTALL_LIBDIR@,lib,' \ + -e 's,@CMAKE_INSTALL_INCLUDEDIR@/@PROJECT_NAME@,include/tommath,' libtommath.pc.in > libtommath.pc install -d $(DESTDIR)$(LIBPATH)/pkgconfig install -m 644 libtommath.pc $(DESTDIR)$(LIBPATH)/pkgconfig/ From a107eafd84d55faf2612ccd352dd088db69fee10 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Mar 2022 13:49:36 +0100 Subject: [PATCH 215/304] include all headers in sources.cmake Signed-off-by: Steffen Jaeckel --- helper.pl | 22 +++++++++++++++------- sources.cmake | 5 +++++ 2 files changed, 20 insertions(+), 7 deletions(-) diff --git a/helper.pl b/helper.pl index 3701799fe..e5ad27ac5 100755 --- a/helper.pl +++ b/helper.pl @@ -222,23 +222,31 @@ sub patch_file { } sub make_sources_cmake { - my @list = @_; + my ($src_ref, $hdr_ref) = @_; + my @sources = @{ $src_ref }; + my @headers = @{ $hdr_ref }; my $output = "# SPDX-License-Identifier: Unlicense # Autogenerated File! Do not edit. set(SOURCES\n"; - foreach my $obj (sort @list) { - $output .= $obj . "\n"; + foreach my $sobj (sort @sources) { + $output .= $sobj . "\n"; + } + $output .= ")\n\nset(HEADERS\n"; + foreach my $hobj (sort @headers) { + $output .= $hobj . "\n"; } - $output .= ")\n\nset(HEADERS\ntommath.h\n)\n"; + $output .= ")\n"; return $output; } sub process_makefiles { my $write = shift; my $changed_count = 0; - my @o = map { my $x = $_; $x =~ s/\.c$/.o/; $x } bsd_glob("*.c"); - my @all = bsd_glob("*.{c,h}"); + my @headers = bsd_glob("*.h"); + my @sources = bsd_glob("*.c"); + my @o = map { my $x = $_; $x =~ s/\.c$/.o/; $x } @sources; + my @all = sort(@sources, @headers); my $var_o = prepare_variable("OBJECTS", @o); (my $var_obj = $var_o) =~ s/\.o\b/.obj/sg; @@ -260,7 +268,7 @@ sub process_makefiles { for my $m (qw/ makefile makefile.shared makefile_include.mk makefile.msvc makefile.unix makefile.mingw sources.cmake /) { my $old = read_file($m); my $new = $m eq 'makefile.msvc' ? patch_file($old, $var_obj) - : $m eq 'sources.cmake' ? make_sources_cmake(bsd_glob("*.c")) + : $m eq 'sources.cmake' ? make_sources_cmake(\@sources, \@headers) : patch_file($old, $var_o); if ($old ne $new) { diff --git a/sources.cmake b/sources.cmake index 2bc891139..797d461e2 100644 --- a/sources.cmake +++ b/sources.cmake @@ -161,4 +161,9 @@ s_mp_zero_digs.c set(HEADERS tommath.h +tommath_c89.h +tommath_class.h +tommath_cutoffs.h +tommath_private.h +tommath_superclass.h ) From 0b98bc717f48ff16d859c4bdef9f0300c92348e8 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Mar 2022 15:35:55 +0100 Subject: [PATCH 216/304] split up into two CMakeLists.txt one for the library, one for the demo Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 32 +---------------------- demo/CMakeLists.txt | 63 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 64 insertions(+), 31 deletions(-) create mode 100644 demo/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt index a4bdac3e9..b36718c8f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -102,41 +102,11 @@ set_target_properties(${PROJECT_NAME} PROPERTIES SOVERSION ${PROJECT_VERSION_MAJOR} ) -#----------------------------------------------------------------------------- -# demo target -#----------------------------------------------------------------------------- - - -add_executable(test-target EXCLUDE_FROM_ALL - ${CMAKE_CURRENT_SOURCE_DIR}/demo/shared.c - ${CMAKE_CURRENT_SOURCE_DIR}/demo/test.c -) - -target_include_directories(test-target PRIVATE - ${CMAKE_CURRENT_SOURCE_DIR} -) - -target_link_libraries(test-target PRIVATE - ${PROJECT_NAME} -) - -target_compile_options(test-target BEFORE PRIVATE - $<$,SHARED_LIBRARY>:-O1 -DLTM_TEST_DYNAMIC> - ${LTM_C_FLAGS} -) -target_link_options(test-target BEFORE PRIVATE - $<$,SHARED_LIBRARY>:-O1> - ${LTM_LD_FLAGS} -) #----------------------------------------------------------------------------- # demo target #----------------------------------------------------------------------------- -add_custom_target(check - COMMAND ${CMAKE_CURRENT_BINARY_DIR}/test-target -) - -add_dependencies(check test-target) +add_subdirectory(demo) #----------------------------------------------------------------------------- # Install/export targets and files diff --git a/demo/CMakeLists.txt b/demo/CMakeLists.txt new file mode 100644 index 000000000..f8cfef25a --- /dev/null +++ b/demo/CMakeLists.txt @@ -0,0 +1,63 @@ +# SPDX-License-Identifier: Unlicense +# +# LibTomMath, a free open source portable number theoretic multiple-precision +# integer (MPI) library written entirely in C. +# + +cmake_minimum_required(VERSION 3.10) + +set(LTM_TEST test-ltm) + +# This file can be included from the top level or used stand-alone +if(PROJECT_NAME) + set(LIBRARY_NAME ${PROJECT_NAME}) +else() + # Define an independent project and all the necessary stuff around + project(${LTM_TEST} + LANGUAGES C) + set(LIBRARY_NAME tommath) + find_package(${LIBRARY_NAME}) + include(CTest) + if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) + set(CMAKE_BUILD_TYPE "Release") + endif() +endif() + +#----------------------------------------------------------------------------- +# Compose CFLAGS etc. +#----------------------------------------------------------------------------- + +if(NOT MSVC) + set(CMAKE_C_FLAGS_DEBUG "-g3 -O1") +endif() + +#----------------------------------------------------------------------------- +# demo target +#----------------------------------------------------------------------------- + +add_executable(${LTM_TEST} + ${CMAKE_CURRENT_SOURCE_DIR}/shared.c + ${CMAKE_CURRENT_SOURCE_DIR}/test.c +) + +target_include_directories(${LTM_TEST} PRIVATE + ${CMAKE_CURRENT_SOURCE_DIR} + $<$:${CMAKE_CURRENT_SOURCE_DIR}/..> +) + +target_link_libraries(${LTM_TEST} PRIVATE + ${LIBRARY_NAME} +) + +target_compile_options(${LTM_TEST} PRIVATE + $<$,SHARED_LIBRARY>:-DLTM_TEST_DYNAMIC> + ${LTM_C_FLAGS} +) +target_link_options(${LTM_TEST} BEFORE PUBLIC + ${LTM_LD_FLAGS} +) + +#----------------------------------------------------------------------------- +# CTest +#----------------------------------------------------------------------------- +add_test(NAME ${LTM_TEST} COMMAND ${LTM_TEST}) From 0f80b46a6d53d4e1861793d14de08cd43ca73491 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Mar 2022 19:56:27 +0100 Subject: [PATCH 217/304] adjust CI builds * split up build and test process * build and run tests twice - once from regular build folder - once from demo Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 21 +++++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index bfda74b7c..06eb58add 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -156,9 +156,9 @@ jobs: cc: [ clang, gcc ] config: # Static library build - - { CMAKEOPTIONS: '', TARGET: 'check' } + - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=Off' } # Shared library build - - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=On', TARGET: 'check'} + - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=On' } steps: - uses: actions/checkout@v2 - name: install dependencies @@ -169,5 +169,18 @@ jobs: run: | mkdir build cd build - CC=${{ matrix.cc }} cmake ${{ matrix.config.CMAKEOPTIONS }} ${{ matrix.build_type }} .. - make -j$(nproc) ${{ matrix.config.TARGET }} + CC=${{ matrix.cc }} cmake ${{ matrix.config.CMAKEOPTIONS }} ${{ matrix.build_type }} .. + make -j$(nproc) + - name: test + run: | + cd build + CC=${{ matrix.cc }} cmake ${{ matrix.config.CMAKEOPTIONS }} ${{ matrix.build_type }} -DBUILD_TESTING=On .. + make -j$(nproc) + ctest + - name: test (in demo folder) + run: | + mkdir -p demo/build + cd demo/build + CC=${{ matrix.cc }} cmake ${{ matrix.config.CMAKEOPTIONS }} ${{ matrix.build_type }} .. + make -j$(nproc) + ctest From d31801fe03ba93d184586c91060344ed36b14534 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 22 Mar 2022 15:39:00 +0100 Subject: [PATCH 218/304] take review comments into account * protect GCC-specific stuff * use `list(APPEND...)` * use CMake-style way to choose whether LTO should/can be done or not * only install public header, not all * add correct `install` option for DLL's on Windows * use correct folder for .pc files * check if `uname` exists & add support for FreeBSD Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 81 +++++++++++++++++++++++++++++++++----------------- 1 file changed, 54 insertions(+), 27 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index b36718c8f..1b9877604 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -21,7 +21,11 @@ set(PACKAGE_RELEASE_VERSION 1) # Include cmake modules #----------------------------------------------------------------------------- include(GNUInstallDirs) +include(CheckIPOSupported) include(CMakePackageConfigHelpers) +# default is "No tests" +option(BUILD_TESTING "" OFF) +include(CTest) include(sources.cmake) # The only direct cmake argument for now @@ -31,42 +35,41 @@ option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \" # Compose CFLAGS #----------------------------------------------------------------------------- -# Some information copied from makefile_include.mk +# Some information ported from makefile_include.mk -# Basic set -set(LTM_C_FLAGS -Wall -Wsign-compare -Wextra -Wshadow) -set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align) -set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wstrict-prototypes -Wpointer-arith -Wsystem-headers) if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) message(STATUS "Setting build type to 'Release' as none was specified.") set(CMAKE_BUILD_TYPE "Release") endif() -set(CMAKE_C_FLAGS_DEBUG "-g3") -set(CMAKE_C_FLAGS_RELEASE "-O3 -funroll-loops -fomit-frame-pointer") -set(CMAKE_C_FLAGS_RELWITHDEBINFO "-g3 -O2") -set(CMAKE_C_FLAGS_MINSIZEREL "-Os") - -if(COMPILE_LTO) - set(LTM_C_FLAGS ${LTM_C_FLAGS} -flto) - set(LTM_LD_FLAGS ${LTM_LD_FLAGS} -flto) +# We only differentiate between MSVC and GCC-compatible compilers +if(MSVC) + set(LTM_C_FLAGS -W3) +else() + set(LTM_C_FLAGS -Wall -Wsign-compare -Wextra -Wshadow + -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align + -Wstrict-prototypes -Wpointer-arith -Wsystem-headers) + set(CMAKE_C_FLAGS_DEBUG "-g3") + set(CMAKE_C_FLAGS_RELEASE "-O3 -funroll-loops -fomit-frame-pointer") + set(CMAKE_C_FLAGS_RELWITHDEBINFO "-g3 -O2") + set(CMAKE_C_FLAGS_MINSIZEREL "-Os") endif() # What compiler do we have and what are their...uhm... peculiarities if(CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header) + list(APPEND LTM_C_FLAGS -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header) # Clang requires at least '-O1' for dead code eliminiation - set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -O1") + set(CMAKE_C_FLAGS_DEBUG "-O1 ${CMAKE_C_FLAGS_DEBUG}") endif() if(CMAKE_C_COMPILER MATCHES "mingw") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-shadow) + list(APPEND LTM_C_FLAGS -Wno-shadow -Wno-expansion-to-defined -Wno-declaration-after-statement -Wno-bad-function-cast) endif() if(CMAKE_SYSTEM_NAME MATCHES "Darwin") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -Wno-nullability-completeness) + list(APPEND LTM_C_FLAGS -Wno-nullability-completeness) endif() if(CMAKE_SYSTEM_NAME MATCHES "CYGWIN") - set(LTM_C_FLAGS ${LTM_C_FLAGS} -no-undefined) + list(APPEND LTM_C_FLAGS -no-undefined) endif() # TODO: coverage (lgcov) @@ -75,14 +78,15 @@ endif() # in order to allow overriding our defaults. # ${LTM_CFLAGS} means the user passed it via sth like: # $ cmake -DLTM_CFLAGS="foo" -set(LTM_C_FLAGS ${LTM_C_FLAGS} ${LTM_CFLAGS}) -set(LTM_LD_FLAGS ${LTM_LD_FLAGS} ${LTM_LDFLAGS}) +list(APPEND LTM_C_FLAGS ${LTM_CFLAGS}) +list(APPEND LTM_LD_FLAGS ${LTM_LDFLAGS}) #----------------------------------------------------------------------------- # library target #----------------------------------------------------------------------------- add_library(${PROJECT_NAME} ${SOURCES} + ${HEADERS} ) target_include_directories(${PROJECT_NAME} PUBLIC @@ -100,13 +104,27 @@ target_link_options(${PROJECT_NAME} BEFORE PRIVATE set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION} SOVERSION ${PROJECT_VERSION_MAJOR} + PUBLIC_HEADER tommath.h ) +option(COMPILE_LTO "Build with LTO enabled") +if(COMPILE_LTO) + check_ipo_supported(RESULT COMPILER_SUPPORTS_LTO) + if(COMPILER_SUPPORTS_LTO) + set_property(TARGET ${PROJECT_NAME} PROPERTY INTERPROCEDURAL_OPTIMIZATION TRUE) + else() + message(SEND_ERROR "This compiler does not support LTO. Reconfigure ${PROJECT_NAME} with -DCOMPILE_LTO=OFF.") + endif() +endif() #----------------------------------------------------------------------------- # demo target #----------------------------------------------------------------------------- -add_subdirectory(demo) + +if(BUILD_TESTING) + enable_testing() + add_subdirectory(demo) +endif() #----------------------------------------------------------------------------- # Install/export targets and files @@ -120,14 +138,15 @@ install(TARGETS ${PROJECT_NAME} EXPORT ${TARGETS_EXPORT_NAME} LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} -) - -install(FILES ${HEADERS} - DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} + PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} ) # Install libtommath.pc for pkg-config if we build a shared library if(BUILD_SHARED_LIBS) + # Let the user override the default directory of the pkg-config file (usually this shouldn't be required to be changed) + set(CMAKE_INSTALL_PKGCONFIGDIR "${CMAKE_INSTALL_LIBDIR}/pkgconfig" CACHE PATH "Folder where to install .pc files") + configure_file( ${CMAKE_CURRENT_SOURCE_DIR}/lib${PROJECT_NAME}.pc.in ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc @@ -135,7 +154,7 @@ if(BUILD_SHARED_LIBS) ) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc - DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/pkgconfig + DESTINATION ${CMAKE_INSTALL_PKGCONFIGDIR} ) endif() @@ -171,8 +190,16 @@ export(PACKAGE ${PROJECT_NAME}) # determine distribution and architecture find_program(LSB_RELEASE lsb_release) +find_program(SYSCTL sysctl) +find_program(UNAME uname) -execute_process(COMMAND uname -m OUTPUT_VARIABLE MACHINE_ARCH OUTPUT_STRIP_TRAILING_WHITESPACE) +if(UNAME) + execute_process(COMMAND uname -m OUTPUT_VARIABLE MACHINE_ARCH OUTPUT_STRIP_TRAILING_WHITESPACE) +elseif(SYSCTL) + execute_process(COMMAND sysctl -b hw.machine_arch OUTPUT_VARIABLE MACHINE_ARCH OUTPUT_STRIP_TRAILING_WHITESPACE) +else() + string(TOLOWER ${CMAKE_SYSTEM_NAME} MACHINE_ARCH) +endif() if(LSB_RELEASE) execute_process(COMMAND lsb_release -si OUTPUT_VARIABLE LINUX_DISTRO OUTPUT_STRIP_TRAILING_WHITESPACE) From 72ce1e53731dc0a4d42d7568280b063789205db3 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 23 Mar 2022 12:21:27 +0100 Subject: [PATCH 219/304] rename cmake project to `libtommath` Instead of prepending multiple times 'lib', change the target-properties `OUTPUT_NAME` once. This also improves cpack package names to be more distro-style. Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 18 +++++++++++------- demo/CMakeLists.txt | 2 +- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 1b9877604..bca46ea57 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -6,7 +6,7 @@ cmake_minimum_required(VERSION 3.10) -project(tommath +project(libtommath VERSION 1.2.0 DESCRIPTION "A free open source portable number theoretic multiple-precision integer (MPI) library written entirely in C." HOMEPAGE_URL "https://www.libtom.net/LibTomMath" @@ -102,6 +102,7 @@ target_link_options(${PROJECT_NAME} BEFORE PRIVATE ) set_target_properties(${PROJECT_NAME} PROPERTIES + OUTPUT_NAME tommath VERSION ${PROJECT_VERSION} SOVERSION ${PROJECT_VERSION_MAJOR} PUBLIC_HEADER tommath.h @@ -148,12 +149,12 @@ if(BUILD_SHARED_LIBS) set(CMAKE_INSTALL_PKGCONFIGDIR "${CMAKE_INSTALL_LIBDIR}/pkgconfig" CACHE PATH "Folder where to install .pc files") configure_file( - ${CMAKE_CURRENT_SOURCE_DIR}/lib${PROJECT_NAME}.pc.in - ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc + ${CMAKE_CURRENT_SOURCE_DIR}/${PROJECT_NAME}.pc.in + ${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}.pc @ONLY ) - install(FILES ${CMAKE_CURRENT_BINARY_DIR}/lib${PROJECT_NAME}.pc + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}.pc DESTINATION ${CMAKE_INSTALL_PKGCONFIGDIR} ) endif() @@ -231,7 +232,11 @@ endif() # general CPack config set(CPACK_PACKAGE_DIRECTORY ${CMAKE_BINARY_DIR}/packages/${DISTRO_PACK_PATH}) message(STATUS "CPack: packages will be generated under ${CPACK_PACKAGE_DIRECTORY}") -set(CPACK_PACKAGE_NAME "lib${PROJECT_NAME}") +if(BUILD_SHARED_LIBS) + set(CPACK_PACKAGE_NAME "${PROJECT_NAME}${PROJECT_VERSION_MAJOR}") +else() + set(CPACK_PACKAGE_NAME "${PROJECT_NAME}-devel") +endif() set(CPACK_PACKAGE_VERSION ${PROJECT_VERSION}) set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "LibTomMath") set(CPACK_PACKAGE_VENDOR "libtom projects") @@ -246,10 +251,9 @@ set(CPACK_DEBIAN_FILE_NAME DEB-DEFAULT) set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) set(CPACK_DEBIAN_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) if(BUILD_SHARED_LIBS) - set(CPACK_DEBIAN_PACKAGE_NAME "${CPACK_PACKAGE_NAME}1") set(CPACK_DEBIAN_PACKAGE_SECTION "libs") else() - set(CPACK_DEBIAN_PACKAGE_NAME "${CPACK_PACKAGE_NAME}-dev") + set(CPACK_DEBIAN_PACKAGE_NAME "${PROJECT_NAME}-dev") set(CPACK_DEBIAN_PACKAGE_SECTION "devel") endif() diff --git a/demo/CMakeLists.txt b/demo/CMakeLists.txt index f8cfef25a..06ff898b4 100644 --- a/demo/CMakeLists.txt +++ b/demo/CMakeLists.txt @@ -15,7 +15,7 @@ else() # Define an independent project and all the necessary stuff around project(${LTM_TEST} LANGUAGES C) - set(LIBRARY_NAME tommath) + set(LIBRARY_NAME libtommath) find_package(${LIBRARY_NAME}) include(CTest) if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES) From ade13cfcccd6ddb2e65dd48ce4331c04cfd2e931 Mon Sep 17 00:00:00 2001 From: Didiet Date: Sun, 17 Apr 2022 05:02:40 +0700 Subject: [PATCH 220/304] Add Support For WATCOM compiler flags --- CMakeLists.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index bca46ea57..63b62ac9b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -46,6 +46,8 @@ endif() # We only differentiate between MSVC and GCC-compatible compilers if(MSVC) set(LTM_C_FLAGS -W3) +elseif(WATCOM) + set(LTM_C_FLAGS -fo=.obj -oaxt -3r -w3) else() set(LTM_C_FLAGS -Wall -Wsign-compare -Wextra -Wshadow -Wdeclaration-after-statement -Wbad-function-cast -Wcast-align From 6d66501137967badc6f646d92ad62432ab8b296f Mon Sep 17 00:00:00 2001 From: Biswapriyo Nath Date: Sun, 28 Mar 2021 21:24:41 +0530 Subject: [PATCH 221/304] Makefile: Fix shared library build in MinGW. This enables -no-undefined linker flag in mingw toolchain. Previous related commit 4b850954056943be03452c9a2b4bb621d663e40b --- makefile_include.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/makefile_include.mk b/makefile_include.mk index 0d17cec8f..dca5c3bc9 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -102,7 +102,7 @@ endif ifeq ($(PLATFORM), Darwin) LTM_CFLAGS += -Wno-nullability-completeness endif -ifeq ($(PLATFORM), CYGWIN) +ifneq ($(findstring $(PLATFORM),CYGWIN MINGW32 MINGW64 MSYS),) LIBTOOLFLAGS += -no-undefined endif From 6929c1364c39b41fba63e68260a40bbf48dec93e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 23 Mar 2022 17:50:22 +0100 Subject: [PATCH 222/304] add C89 support for CMake Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 8 +++++++- makefile | 6 ++++-- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 63b62ac9b..525ba1c95 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -103,11 +103,17 @@ target_link_options(${PROJECT_NAME} BEFORE PRIVATE ${LTM_LD_FLAGS} ) +set(PUBLIC_HEADERS tommath.h) +set(C89 False CACHE BOOL "(Usually maintained automatically) Enable when the library is in c89 mode to package the correct header files on install") +if(C89) + list(APPEND PUBLIC_HEADERS tommath_c89.h) +endif() + set_target_properties(${PROJECT_NAME} PROPERTIES OUTPUT_NAME tommath VERSION ${PROJECT_VERSION} SOVERSION ${PROJECT_VERSION_MAJOR} - PUBLIC_HEADER tommath.h + PUBLIC_HEADER "${PUBLIC_HEADERS}" ) option(COMPILE_LTO "Build with LTO enabled") diff --git a/makefile b/makefile index 7fa04d2ca..7fe933fa3 100644 --- a/makefile +++ b/makefile @@ -173,7 +173,8 @@ c89: -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ -e 's/__func__/MP_FUNCTION_NAME/g' \ - *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c + -e 's/set(C89 False/set(C89 True/g' \ + *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c CMakeLists.txt c99: @echo "Applying substitutions for c99 compatibility..." @@ -196,7 +197,8 @@ c99: -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ -e 's/MP_FUNCTION_NAME/__func__/g' \ - *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c + -e 's/set(C89 True/set(C89 False/g' \ + *.c tommath.h tommath_private.h demo/*.c demo/*.h etc/*.c CMakeLists.txt astyle: @echo " * run astyle on all sources" From 7c10db3d15e81049fc098271ba7cc46a6edfbe69 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 28 Apr 2022 11:41:40 +0200 Subject: [PATCH 223/304] support Valgrind for tests when using CMake Signed-off-by: Steffen Jaeckel --- demo/CMakeLists.txt | 3 +++ 1 file changed, 3 insertions(+) diff --git a/demo/CMakeLists.txt b/demo/CMakeLists.txt index 06ff898b4..c44b7c23e 100644 --- a/demo/CMakeLists.txt +++ b/demo/CMakeLists.txt @@ -61,3 +61,6 @@ target_link_options(${LTM_TEST} BEFORE PUBLIC # CTest #----------------------------------------------------------------------------- add_test(NAME ${LTM_TEST} COMMAND ${LTM_TEST}) + +find_program(MEMORYCHECK_COMMAND valgrind) +set(MEMORYCHECK_COMMAND_OPTIONS "--trace-children=yes --leak-check=full") From e03e52d26e5d06435e8e033283317aa35b65ca35 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 28 Apr 2022 11:44:00 +0200 Subject: [PATCH 224/304] ensure compilation with Clang succeeds Signed-off-by: Steffen Jaeckel --- makefile_include.mk | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/makefile_include.mk b/makefile_include.mk index dca5c3bc9..f88d18be1 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -95,6 +95,10 @@ endif # COMPILE_SIZE ifneq ($(findstring clang,$(CC)),) LTM_CFLAGS += -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header +ifdef IGNORE_SPEED +#for dead code eliminiation +LTM_CFLAGS += -O1 +endif endif ifneq ($(findstring mingw,$(CC)),) LTM_CFLAGS += -Wno-shadow From ae0c9cb208e9ab576d7d0a6689ccf0cf39a06253 Mon Sep 17 00:00:00 2001 From: spaette Date: Sun, 2 Oct 2022 12:53:57 +0200 Subject: [PATCH 225/304] Add typos.sh script --- typos.sh | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100755 typos.sh diff --git a/typos.sh b/typos.sh new file mode 100755 index 000000000..7ac609845 --- /dev/null +++ b/typos.sh @@ -0,0 +1,35 @@ +#!/bin/sh + +sed -i "s/Dimminished/Diminished/g" libtommath/logs/before_after.dem +sed -i "s/Dimminished/Diminished/g" libtommath/logs/graphs.dem +sed -i "s/accomodate/accommodate/g" libtommath/mp_mul_2.c +sed -i "s/accomodate/accommodate/g" libtommath/mp_2expt.c +sed -i "s/addtional/additional/g" libtommath/mp_prime_is_prime.c +sed -i "s/alot/a lot/g" libtommath/changes.txt +sed -i "s/alot/a lot/g" libtommath/mp_exptmod.c +sed -i "s/alot/a lot/g" libtommath/mp_montgomery_calc_normalization.c +sed -i "s/annonying/annoying/g" libtommath/astylerc +sed -i "s/asymptopically/asymptotically/g" libtommath/s_mp_mul_karatsuba.c +sed -i "s/calulates/calculates/g" libtommath/mp_reduce_setup.c +sed -i "s/configuraion/configuration/g" libtommath/doc/makefile +sed -i "s/eliminiation/elimination/g" libtommath/CMakeLists.txt +sed -i "s/embeded/embedded/g" libtommath/mp_prime_is_prime.c +sed -i "s/endianess/endianness/g" libtommath/demo/test.c +sed -i "s/iterrate/iterate/g" libtommath/s_mp_sqr_comba.c +sed -i "s/iterrate/iterate/g" libtommath/s_mp_mul_high_comba.c +sed -i "s/iterrate/iterate/g" libtommath/s_mp_mul_comba.c +sed -i "s/maginitude/magnitude/g" libtommath/mp_cmp_mag.c +sed -i "s/offseting/offsetting/g" libtommath/s_mp_montgomery_reduce_comba.c +sed -i "s/ofthe/of the/g" libtommath/doc/bn.tex +sed -i "s/otherway/other way/g" libtommath/mp_lshd.c +sed -i "s/packagage/package/g" libtommath/changes.txt +sed -i "s/preemptivly/preemptively/g" libtommath/mp_prime_is_prime.c +sed -i "s/probabilty/probability/g" libtommath/doc/bn.tex +sed -i "s/programms/programs/g" libtommath/doc/bn.tex +sed -i "s/seperate/separate/g" libtommath/changes.txt +sed -i "s/simplifiy/simplify/g" libtommath/demo/test.c +sed -i "s/tollchocked/tolchocked/g" libtommath/mtest/mpi.c +sed -i "s/trimed/trimmed/g" libtommath/mp_clamp.c +sed -i "s/triming/trimming/g" libtommath/demo/mtest_opponent.c +sed -i "s/uncommited/uncommitted/g" libtommath/makefile +sed -i "s/unsused/unused/g" libtommath/changes.txt From c7686f2467a1926db13f9c6ce5480942c8ccd4a4 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 2 Oct 2022 12:58:53 +0200 Subject: [PATCH 226/304] slightly edit, update and run typos.sh Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 2 +- astylerc | 2 +- changes.txt | 8 ++-- demo/mtest_opponent.c | 2 +- demo/test.c | 8 ++-- doc/bn.tex | 6 +-- doc/makefile | 2 +- logs/before_after.dem | 4 +- logs/graphs.dem | 2 +- makefile | 2 +- mp_2expt.c | 2 +- mp_clamp.c | 2 +- mp_cmp_mag.c | 2 +- mp_exptmod.c | 2 +- mp_lshd.c | 2 +- mp_montgomery_calc_normalization.c | 2 +- mp_mul_2.c | 2 +- mp_prime_is_prime.c | 6 +-- mp_reduce_setup.c | 2 +- mtest/mpi.c | 2 +- s_mp_montgomery_reduce_comba.c | 2 +- s_mp_mul_comba.c | 2 +- s_mp_mul_high_comba.c | 2 +- s_mp_mul_karatsuba.c | 2 +- s_mp_sqr_comba.c | 2 +- typos.sh | 67 +++++++++++++++--------------- 26 files changed, 70 insertions(+), 69 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 525ba1c95..8f8524912 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -61,7 +61,7 @@ endif() # What compiler do we have and what are their...uhm... peculiarities if(CMAKE_C_COMPILER_ID MATCHES "(C|c?)lang") list(APPEND LTM_C_FLAGS -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header) - # Clang requires at least '-O1' for dead code eliminiation + # Clang requires at least '-O1' for dead code elimination set(CMAKE_C_FLAGS_DEBUG "-O1 ${CMAKE_C_FLAGS_DEBUG}") endif() if(CMAKE_C_COMPILER MATCHES "mingw") diff --git a/astylerc b/astylerc index c5ff77940..029f35849 100644 --- a/astylerc +++ b/astylerc @@ -4,7 +4,7 @@ # usage: # astyle --options=astylerc *.[ch] -# Do not create backup, annonying in the times of git +# Do not create backup, annoying in the times of git suffix=none ## Bracket Style Options diff --git a/changes.txt b/changes.txt index 1b3a7a3a4..565500b51 100644 --- a/changes.txt +++ b/changes.txt @@ -19,7 +19,7 @@ v1.2.0 -- Unified, safer and improved API's -- Less magic numbers - return values (where appropriate) and most flags are now enums, this was implemented in a backwards compatible way where return values were int. - -- API's with return values are now by default marked as "warn on unsused result", this + -- API's with return values are now by default marked as "warn on unused result", this can be disabled if required (which will most likely hide bugs), c.f. MP_WUR in tommath.h -- Provide a whole set of setters&getters for different primitive types (long, uint32_t, etc.) -- All those primitive setters are now optimized. @@ -412,8 +412,8 @@ v0.13 -- tons of minor speed-ups in low level add, sub, mul_2 and div_2 which p Jan 17th, 2003 v0.12 -- re-wrote the majority of the makefile so its more portable and will install via "make install" on most *nix platforms - -- Re-packaged all the source as seperate files. Means the library a single - file packagage any more. Instead of just adding "bn.c" you have to add + -- Re-packaged all the source as separate files. Means the library a single + file package any more. Instead of just adding "bn.c" you have to add libtommath.a -- Renamed "bn.h" to "tommath.h" -- Changes to the manual to reflect all of this @@ -444,7 +444,7 @@ v0.08 -- Sped up the multipliers by moving the inner loop variables into a smal -- add etc/pprime.c program which makes numbers which are provably prime. Jan 1st, 2003 -v0.07 -- Removed alot of heap operations from core functions to speed them up +v0.07 -- Removed a lot of heap operations from core functions to speed them up -- Added a root finding function [and mp_sqrt macro like from MPI] -- Added more to manual diff --git a/demo/mtest_opponent.c b/demo/mtest_opponent.c index 25d9b5b90..abd7c1614 100644 --- a/demo/mtest_opponent.c +++ b/demo/mtest_opponent.c @@ -82,7 +82,7 @@ static int mtest_opponent(void) #endif for (;;) { - /* randomly clear and re-init one variable, this has the affect of triming the alloc space */ + /* randomly clear and re-init one variable, this has the effect of trimming the alloc space */ switch (abs(rand()) % 7) { case 0: mp_clear(&a); diff --git a/demo/test.c b/demo/test.c index c87f97c00..16fef5570 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1548,7 +1548,7 @@ static int test_mp_decr(void) default(realprecision,1000); for(n=3,100,r = floor(a^(1/n));printf("\"" r "\", ")) - All numbers as strings to simplifiy things, especially for the + All numbers as strings to simplify things, especially for the low-mp branch. */ @@ -2166,7 +2166,7 @@ static int test_mp_pack_unpack(void) uint8_t *buf = NULL; mp_order order = MP_LSB_FIRST; - mp_endian endianess = MP_NATIVE_ENDIAN; + mp_endian endianness = MP_NATIVE_ENDIAN; DOR(mp_init_multi(&a, &b, NULL)); DO(mp_rand(&a, 15)); @@ -2180,9 +2180,9 @@ static int test_mp_pack_unpack(void) } DO(mp_pack((void *)buf, count, &written, order, 1uL, - endianess, 0uL, &a)); + endianness, 0uL, &a)); DO(mp_unpack(&b, count, order, 1uL, - endianess, 0uL, (const void *)buf)); + endianness, 0uL, (const void *)buf)); if (mp_cmp(&a, &b) != MP_EQ) { fprintf(stderr, "pack/unpack cycle failed\n"); diff --git a/doc/bn.tex b/doc/bn.tex index 3e01e32df..566b3be32 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -210,7 +210,7 @@ \subsubsection{OpenBSD} At this time two versions of \texttt{libtool} are installed and both are named \texttt{libtool}, unfortunately but GNU \texttt{libtool} has been placed in \texttt{/usr/local/bin/} and the native version in \texttt{/usr/bin/}. The path might be different in other versions of OpenBSD but both -programms differ in the output of \texttt{libtool --version} +programs differ in the output of \texttt{libtool --version} \begin{alltt} $ /usr/local/bin/libtool --version libtool (GNU libtool) 2.4.2 @@ -519,7 +519,7 @@ \subsection{Single Initialization} \end{alltt} This function expects a pointer to an \texttt{mp\_int} structure and will initialize the members -ofthe structure so the \texttt{mp\_int} represents the default integer which is zero. If the +of the structure so the \texttt{mp\_int} represents the default integer which is zero. If the functions returns \texttt{MP\_OKAY} then the \texttt{mp\_int} is ready to be used by the other LibTomMath functions. @@ -2213,7 +2213,7 @@ \subsection{Required Number of Tests} Determining the probability needed to pick the right column is a bit harder. Fips 186.4, for example has $2^{-80}$ for $512$ bit large numbers, $2^{-112}$ for $1024$ bits, and $2^{128}$ for $1536$ bits. It can be seen in table \ref{table:millerrabinrunsp1} that those combinations follow -the diagonal from $(512,2^{-80})$ downwards and to the right to gain a lower probabilty of getting +the diagonal from $(512,2^{-80})$ downwards and to the right to gain a lower probability of getting a composite declared a pseudoprime for the same amount of work or less. If this version of the library has the strong Lucas--Selfridge and/or the Frobenius--Underwood test diff --git a/doc/makefile b/doc/makefile index 84c48e4b2..a8c6a6539 100644 --- a/doc/makefile +++ b/doc/makefile @@ -40,7 +40,7 @@ manual: mandvi # The file latexindent.pl is in several LaTeX distributions, if not: # https://ctan.org/pkg/latexindent -# Its configuraion is well documented +# Its configuration is well documented # http://mirrors.ctan.org/support/latexindent/documentation/latexindent.pdf pretty: latexindent -s -w -m -l=.latexindent.yaml bn.tex diff --git a/logs/before_after.dem b/logs/before_after.dem index edb59da49..33721ad20 100644 --- a/logs/before_after.dem +++ b/logs/before_after.dem @@ -23,8 +23,8 @@ plot 'sqr-before.log' smooth bezier title "Squaring (without Karatsuba) (before) set output "expt-ba.png" plot 'expt-before.log' smooth bezier title "Exptmod (Montgomery) (before)", \ 'expt-after.log' smooth bezier title "Exptmod (Montgomery) (after)", \ - 'expt_dr-before.log' smooth bezier title "Exptmod (Dimminished Radix) (before)", \ - 'expt_dr-after.log' smooth bezier title "Exptmod (Dimminished Radix) (after)", \ + 'expt_dr-before.log' smooth bezier title "Exptmod (Diminished Radix) (before)", \ + 'expt_dr-after.log' smooth bezier title "Exptmod (Diminished Radix) (after)", \ 'expt_2k-before.log' smooth bezier title "Exptmod (2k Reduction) (before)", \ 'expt_2k-after.log' smooth bezier title "Exptmod (2k Reduction) (after)", \ 'expt_2kl-before.log' smooth bezier title "Exptmod (2k-l Reduction) (before)", \ diff --git a/logs/graphs.dem b/logs/graphs.dem index 538e5c075..fc8ef1bc9 100644 --- a/logs/graphs.dem +++ b/logs/graphs.dem @@ -9,7 +9,7 @@ set output "mult.png" plot 'sqr.log' smooth bezier title "Squaring (without Karatsuba)", 'sqr_kara.log' smooth bezier title "Squaring (Karatsuba)", 'mult.log' smooth bezier title "Multiplication (without Karatsuba)", 'mult_kara.log' smooth bezier title "Multiplication (Karatsuba)" set output "expt.png" -plot 'expt.log' smooth bezier title "Exptmod (Montgomery)", 'expt_dr.log' smooth bezier title "Exptmod (Dimminished Radix)", 'expt_2k.log' smooth bezier title "Exptmod (2k Reduction)" +plot 'expt.log' smooth bezier title "Exptmod (Montgomery)", 'expt_dr.log' smooth bezier title "Exptmod (Diminished Radix)", 'expt_2k.log' smooth bezier title "Exptmod (2k Reduction)" set output "invmod.png" plot 'invmod.log' smooth bezier title "Modular Inverse" diff --git a/makefile b/makefile index 7fe933fa3..666274378 100644 --- a/makefile +++ b/makefile @@ -130,7 +130,7 @@ zipup: clean astyle new_file docs @# As the pdf creation modifies the tex files, git sometimes detects the @# modified files, but misses that it's put back to its original version. @git update-index --refresh - @git diff-index --quiet HEAD -- || ( echo "FAILURE: uncommited changes or not a git" && exit 1 ) + @git diff-index --quiet HEAD -- || ( echo "FAILURE: uncommitted changes or not a git" && exit 1 ) rm -rf libtommath-$(VERSION) ltm-$(VERSION).* @# files/dirs excluded from "git archive" are defined in .gitattributes git archive --format=tar --prefix=libtommath-$(VERSION)/ HEAD | tar x diff --git a/mp_2expt.c b/mp_2expt.c index 66e857478..4a5fc0063 100644 --- a/mp_2expt.c +++ b/mp_2expt.c @@ -15,7 +15,7 @@ mp_err mp_2expt(mp_int *a, int b) /* zero a as per default */ mp_zero(a); - /* grow a to accomodate the single bit */ + /* grow a to accommodate the single bit */ if ((err = mp_grow(a, (b / MP_DIGIT_BIT) + 1)) != MP_OKAY) { return err; } diff --git a/mp_clamp.c b/mp_clamp.c index ae59c4016..463f22dc0 100644 --- a/mp_clamp.c +++ b/mp_clamp.c @@ -6,7 +6,7 @@ /* trim unused digits * * This is used to ensure that leading zero digits are - * trimed and the leading "used" digit will be non-zero + * trimmed and the leading "used" digit will be non-zero * Typically very fast. Also fixes the sign if there * are no more leading digits */ diff --git a/mp_cmp_mag.c b/mp_cmp_mag.c index e5e502b8c..06f22e7ce 100644 --- a/mp_cmp_mag.c +++ b/mp_cmp_mag.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -/* compare maginitude of two ints (unsigned) */ +/* compare magnitude of two ints (unsigned) */ mp_ord mp_cmp_mag(const mp_int *a, const mp_int *b) { int n; diff --git a/mp_exptmod.c b/mp_exptmod.c index b8a5dccc2..eaab861eb 100644 --- a/mp_exptmod.c +++ b/mp_exptmod.c @@ -5,7 +5,7 @@ /* this is a shell function that calls either the normal or Montgomery * exptmod functions. Originally the call to the montgomery code was - * embedded in the normal function but that wasted alot of stack space + * embedded in the normal function but that wasted a lot of stack space * for nothing (since 99% of the time the Montgomery code would be called) */ mp_err mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y) diff --git a/mp_lshd.c b/mp_lshd.c index bfa8af88b..90014e480 100644 --- a/mp_lshd.c +++ b/mp_lshd.c @@ -27,7 +27,7 @@ mp_err mp_lshd(mp_int *a, int b) a->used += b; /* much like mp_rshd this is implemented using a sliding window - * except the window goes the otherway around. Copying from + * except the window goes the other way around. Copying from * the bottom to the top. see mp_rshd.c for more info. */ for (x = a->used; x --> b;) { diff --git a/mp_montgomery_calc_normalization.c b/mp_montgomery_calc_normalization.c index cc07799dc..bbb3adbc1 100644 --- a/mp_montgomery_calc_normalization.c +++ b/mp_montgomery_calc_normalization.c @@ -7,7 +7,7 @@ * shifts with subtractions when the result is greater than b. * * The method is slightly modified to shift B unconditionally upto just under - * the leading bit of b. This saves alot of multiple precision shifting. + * the leading bit of b. This saves a lot of multiple precision shifting. */ mp_err mp_montgomery_calc_normalization(mp_int *a, const mp_int *b) { diff --git a/mp_mul_2.c b/mp_mul_2.c index 7d7084b31..459fbd29d 100644 --- a/mp_mul_2.c +++ b/mp_mul_2.c @@ -10,7 +10,7 @@ mp_err mp_mul_2(const mp_int *a, mp_int *b) int x, oldused; mp_digit r; - /* grow to accomodate result */ + /* grow to accommodate result */ if ((err = mp_grow(b, a->used + 1)) != MP_OKAY) { return err; } diff --git a/mp_prime_is_prime.c b/mp_prime_is_prime.c index 7d73864c7..bb24f5944 100644 --- a/mp_prime_is_prime.c +++ b/mp_prime_is_prime.c @@ -181,7 +181,7 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) * The mp_digit's have a defined bit-size but the size of the * array a.dp is a simple 'int' and this library can not assume full * compliance to the current C-standard (ISO/IEC 9899:2011) because - * it gets used for small embeded processors, too. Some of those MCUs + * it gets used for small embedded processors, too. Some of those MCUs * have compilers that one cannot call standard compliant by any means. * Hence the ugly type-fiddling in the following code. */ @@ -213,12 +213,12 @@ mp_err mp_prime_is_prime(const mp_int *a, int t, bool *result) The function mp_rand() goes to some length to use a cryptographically good PRNG. That also means that the chance to always get the same base in the loop is non-zero, although very low. - If the BPSW test and/or the addtional Frobenious test have been + If the BPSW test and/or the additional Frobenious test have been performed instead of just the Miller-Rabin test with the bases 2 and 3, a single extra test should suffice, so such a very unlikely event will not do much harm. - To preemptivly answer the dangling question: no, a witness does not + To preemptively answer the dangling question: no, a witness does not need to be prime. */ for (ix = 0; ix < t; ix++) { diff --git a/mp_reduce_setup.c b/mp_reduce_setup.c index e12056e1e..2ce5b96f0 100644 --- a/mp_reduce_setup.c +++ b/mp_reduce_setup.c @@ -4,7 +4,7 @@ /* SPDX-License-Identifier: Unlicense */ /* pre-calculate the value required for Barrett reduction - * For a given modulus "b" it calulates the value required in "a" + * For a given modulus "b" it calculates the value required in "a" */ mp_err mp_reduce_setup(mp_int *a, const mp_int *b) { diff --git a/mtest/mpi.c b/mtest/mpi.c index faf09d8df..f9cc4290d 100644 --- a/mtest/mpi.c +++ b/mtest/mpi.c @@ -418,7 +418,7 @@ void mp_exch(mp_int *mp1, mp_int *mp2) Release the storage used by an mp_int, and void its fields so that if someone calls mp_clear() again for the same int later, we won't - get tollchocked. + get tolchocked. */ void mp_clear(mp_int *mp) diff --git a/s_mp_montgomery_reduce_comba.c b/s_mp_montgomery_reduce_comba.c index 6f249c49f..7472caf34 100644 --- a/s_mp_montgomery_reduce_comba.c +++ b/s_mp_montgomery_reduce_comba.c @@ -61,7 +61,7 @@ mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) /* a = a + mu * m * b**i * * This is computed in place and on the fly. The multiplication - * by b**i is handled by offseting which columns the results + * by b**i is handled by offsetting which columns the results * are added to. * * Note the comba method normally doesn't handle carries in the diff --git a/s_mp_mul_comba.c b/s_mp_mul_comba.c index 07dd7913d..1afa1fc68 100644 --- a/s_mp_mul_comba.c +++ b/s_mp_mul_comba.c @@ -43,7 +43,7 @@ mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) ty = MP_MIN(b->used-1, ix); tx = ix - ty; - /* this is the number of times the loop will iterrate, essentially + /* this is the number of times the loop will iterate, essentially while (tx++ < a->used && ty-- >= 0) { ... } */ iy = MP_MIN(a->used-tx, ty+1); diff --git a/s_mp_mul_high_comba.c b/s_mp_mul_high_comba.c index 317346dfa..74960aca6 100644 --- a/s_mp_mul_high_comba.c +++ b/s_mp_mul_high_comba.c @@ -35,7 +35,7 @@ mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs ty = MP_MIN(b->used-1, ix); tx = ix - ty; - /* this is the number of times the loop will iterrate, essentially its + /* this is the number of times the loop will iterate, essentially its while (tx++ < a->used && ty-- >= 0) { ... } */ iy = MP_MIN(a->used-tx, ty+1); diff --git a/s_mp_mul_karatsuba.c b/s_mp_mul_karatsuba.c index bf9271f3b..b46529837 100644 --- a/s_mp_mul_karatsuba.c +++ b/s_mp_mul_karatsuba.c @@ -27,7 +27,7 @@ * are saved. Note also that the call to mp_mul can end up back * in this function if the a0, a1, b0, or b1 are above the threshold. * This is known as divide-and-conquer and leads to the famous - * O(N**lg(3)) or O(N**1.584) work which is asymptopically lower than + * O(N**lg(3)) or O(N**1.584) work which is asymptotically lower than * the standard O(N**2) that the baseline/comba methods use. * Generally though the overhead of this method doesn't pay off * until a certain size (N ~ 80) is reached. diff --git a/s_mp_sqr_comba.c b/s_mp_sqr_comba.c index cb88dcc9e..1bcc1f93f 100644 --- a/s_mp_sqr_comba.c +++ b/s_mp_sqr_comba.c @@ -39,7 +39,7 @@ mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) ty = MP_MIN(a->used-1, ix); tx = ix - ty; - /* this is the number of times the loop will iterrate, essentially + /* this is the number of times the loop will iterate, essentially while (tx++ < a->used && ty-- >= 0) { ... } */ iy = MP_MIN(a->used-tx, ty+1); diff --git a/typos.sh b/typos.sh index 7ac609845..cc2aa954a 100755 --- a/typos.sh +++ b/typos.sh @@ -1,35 +1,36 @@ #!/bin/sh -sed -i "s/Dimminished/Diminished/g" libtommath/logs/before_after.dem -sed -i "s/Dimminished/Diminished/g" libtommath/logs/graphs.dem -sed -i "s/accomodate/accommodate/g" libtommath/mp_mul_2.c -sed -i "s/accomodate/accommodate/g" libtommath/mp_2expt.c -sed -i "s/addtional/additional/g" libtommath/mp_prime_is_prime.c -sed -i "s/alot/a lot/g" libtommath/changes.txt -sed -i "s/alot/a lot/g" libtommath/mp_exptmod.c -sed -i "s/alot/a lot/g" libtommath/mp_montgomery_calc_normalization.c -sed -i "s/annonying/annoying/g" libtommath/astylerc -sed -i "s/asymptopically/asymptotically/g" libtommath/s_mp_mul_karatsuba.c -sed -i "s/calulates/calculates/g" libtommath/mp_reduce_setup.c -sed -i "s/configuraion/configuration/g" libtommath/doc/makefile -sed -i "s/eliminiation/elimination/g" libtommath/CMakeLists.txt -sed -i "s/embeded/embedded/g" libtommath/mp_prime_is_prime.c -sed -i "s/endianess/endianness/g" libtommath/demo/test.c -sed -i "s/iterrate/iterate/g" libtommath/s_mp_sqr_comba.c -sed -i "s/iterrate/iterate/g" libtommath/s_mp_mul_high_comba.c -sed -i "s/iterrate/iterate/g" libtommath/s_mp_mul_comba.c -sed -i "s/maginitude/magnitude/g" libtommath/mp_cmp_mag.c -sed -i "s/offseting/offsetting/g" libtommath/s_mp_montgomery_reduce_comba.c -sed -i "s/ofthe/of the/g" libtommath/doc/bn.tex -sed -i "s/otherway/other way/g" libtommath/mp_lshd.c -sed -i "s/packagage/package/g" libtommath/changes.txt -sed -i "s/preemptivly/preemptively/g" libtommath/mp_prime_is_prime.c -sed -i "s/probabilty/probability/g" libtommath/doc/bn.tex -sed -i "s/programms/programs/g" libtommath/doc/bn.tex -sed -i "s/seperate/separate/g" libtommath/changes.txt -sed -i "s/simplifiy/simplify/g" libtommath/demo/test.c -sed -i "s/tollchocked/tolchocked/g" libtommath/mtest/mpi.c -sed -i "s/trimed/trimmed/g" libtommath/mp_clamp.c -sed -i "s/triming/trimming/g" libtommath/demo/mtest_opponent.c -sed -i "s/uncommited/uncommitted/g" libtommath/makefile -sed -i "s/unsused/unused/g" libtommath/changes.txt +sed -i "s/Dimminished/Diminished/g" logs/before_after.dem +sed -i "s/Dimminished/Diminished/g" logs/graphs.dem +sed -i "s/accomodate/accommodate/g" mp_mul_2.c +sed -i "s/accomodate/accommodate/g" mp_2expt.c +sed -i "s/addtional/additional/g" mp_prime_is_prime.c +sed -i "s/affect/effect/g" demo/mtest_opponent.c +sed -i "s/alot/a lot/g" changes.txt +sed -i "s/alot/a lot/g" mp_exptmod.c +sed -i "s/alot/a lot/g" mp_montgomery_calc_normalization.c +sed -i "s/annonying/annoying/g" astylerc +sed -i "s/asymptopically/asymptotically/g" s_mp_mul_karatsuba.c +sed -i "s/calulates/calculates/g" mp_reduce_setup.c +sed -i "s/configuraion/configuration/g" doc/makefile +sed -i "s/eliminiation/elimination/g" CMakeLists.txt +sed -i "s/embeded/embedded/g" mp_prime_is_prime.c +sed -i "s/endianess/endianness/g" demo/test.c +sed -i "s/iterrate/iterate/g" s_mp_sqr_comba.c +sed -i "s/iterrate/iterate/g" s_mp_mul_high_comba.c +sed -i "s/iterrate/iterate/g" s_mp_mul_comba.c +sed -i "s/maginitude/magnitude/g" mp_cmp_mag.c +sed -i "s/offseting/offsetting/g" s_mp_montgomery_reduce_comba.c +sed -i "s/ofthe/of the/g" doc/bn.tex +sed -i "s/otherway/other way/g" mp_lshd.c +sed -i "s/packagage/package/g" changes.txt +sed -i "s/preemptivly/preemptively/g" mp_prime_is_prime.c +sed -i "s/probabilty/probability/g" doc/bn.tex +sed -i "s/programms/programs/g" doc/bn.tex +sed -i "s/seperate/separate/g" changes.txt +sed -i "s/simplifiy/simplify/g" demo/test.c +sed -i "s/tollchocked/tolchocked/g" mtest/mpi.c +sed -i "s/trimed/trimmed/g" mp_clamp.c +sed -i "s/triming/trimming/g" demo/mtest_opponent.c +sed -i "s/uncommited/uncommitted/g" makefile +sed -i "s/unsused/unused/g" changes.txt From 4de4e4f1473df4bf30afd250ba1dbbaf1043ed54 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 2 Oct 2022 13:03:40 +0200 Subject: [PATCH 227/304] delete typos.sh again you did a good job :) This closes #533 Signed-off-by: Steffen Jaeckel --- typos.sh | 36 ------------------------------------ 1 file changed, 36 deletions(-) delete mode 100755 typos.sh diff --git a/typos.sh b/typos.sh deleted file mode 100755 index cc2aa954a..000000000 --- a/typos.sh +++ /dev/null @@ -1,36 +0,0 @@ -#!/bin/sh - -sed -i "s/Dimminished/Diminished/g" logs/before_after.dem -sed -i "s/Dimminished/Diminished/g" logs/graphs.dem -sed -i "s/accomodate/accommodate/g" mp_mul_2.c -sed -i "s/accomodate/accommodate/g" mp_2expt.c -sed -i "s/addtional/additional/g" mp_prime_is_prime.c -sed -i "s/affect/effect/g" demo/mtest_opponent.c -sed -i "s/alot/a lot/g" changes.txt -sed -i "s/alot/a lot/g" mp_exptmod.c -sed -i "s/alot/a lot/g" mp_montgomery_calc_normalization.c -sed -i "s/annonying/annoying/g" astylerc -sed -i "s/asymptopically/asymptotically/g" s_mp_mul_karatsuba.c -sed -i "s/calulates/calculates/g" mp_reduce_setup.c -sed -i "s/configuraion/configuration/g" doc/makefile -sed -i "s/eliminiation/elimination/g" CMakeLists.txt -sed -i "s/embeded/embedded/g" mp_prime_is_prime.c -sed -i "s/endianess/endianness/g" demo/test.c -sed -i "s/iterrate/iterate/g" s_mp_sqr_comba.c -sed -i "s/iterrate/iterate/g" s_mp_mul_high_comba.c -sed -i "s/iterrate/iterate/g" s_mp_mul_comba.c -sed -i "s/maginitude/magnitude/g" mp_cmp_mag.c -sed -i "s/offseting/offsetting/g" s_mp_montgomery_reduce_comba.c -sed -i "s/ofthe/of the/g" doc/bn.tex -sed -i "s/otherway/other way/g" mp_lshd.c -sed -i "s/packagage/package/g" changes.txt -sed -i "s/preemptivly/preemptively/g" mp_prime_is_prime.c -sed -i "s/probabilty/probability/g" doc/bn.tex -sed -i "s/programms/programs/g" doc/bn.tex -sed -i "s/seperate/separate/g" changes.txt -sed -i "s/simplifiy/simplify/g" demo/test.c -sed -i "s/tollchocked/tolchocked/g" mtest/mpi.c -sed -i "s/trimed/trimmed/g" mp_clamp.c -sed -i "s/triming/trimming/g" demo/mtest_opponent.c -sed -i "s/uncommited/uncommitted/g" makefile -sed -i "s/unsused/unused/g" changes.txt From 908e098cb3ee37fa5b18d650104cacb8d2854422 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 7 Sep 2022 23:03:13 +0200 Subject: [PATCH 228/304] Fix: removed sign operation in s_mp_invmod_odd Changed a check for <0 with mp_isneg() in s_mp_invmod Additional tests for mp_invmod() in demo/test.c --- demo/test.c | 72 +++++++++++++++++++++++++++++++++++++++++++++++ s_mp_invmod.c | 2 +- s_mp_invmod_odd.c | 5 +--- 3 files changed, 74 insertions(+), 5 deletions(-) diff --git a/demo/test.c b/demo/test.c index 16fef5570..0ebcfd07f 100644 --- a/demo/test.c +++ b/demo/test.c @@ -549,6 +549,54 @@ static int test_mp_and(void) static int test_mp_invmod(void) { mp_int a, b, c, d; + int i, j, k; + int e; + + int results[21][21] = + /* Table generated with Pari/GP + + for(i=-10,10, + k=0; + d=0; + printf(" {"); + for(j=-10,10, + iferr( + printf(lift(Mod(1/i, j)) ", "), + k, + printf("-1, ")) + ); + print("},") + ) + + Changes to the output: replaced j < 1 with -1 for now and added the result of 0^(-1) mod (1) + + j = -10, -9, -8, -7, -6, -5, -4, -3, -2, -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 */ + + { + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 2, -1, -1, -1, 2, -1, 8, -1 }, /* i = -10 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, -1, 3, 1, -1, 3, 7, -1, 1 }, /* -9 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, -1, 3, -1, 6, -1, 1, -1 }, /* -8 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, 2, 1, 2, 5, -1, 1, 5, 7 }, /* -7 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 4, -1, 1, -1, -1, -1 }, /* -6 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, 1, 3, -1, 1, 4, 3, 7, -1 }, /* -5 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 2, -1, 1, -1, 5, -1, 2, -1 }, /* -4 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, -1, 1, 3, -1, 2, 5, -1, 3 }, /* -3 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, -1, 2, -1, 3, -1, 4, -1 }, /* -2 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 1, 2, 3, 4, 5, 6, 7, 8, 9 }, /* -1 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, -1, -1, -1, -1, -1, -1, -1, -1 }, /* 0 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, /* 1 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, 2, -1, 3, -1, 4, -1, 5, -1 }, /* 2 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, -1, 3, 2, -1, 5, 3, -1, 7 }, /* 3 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, 1, -1, 4, -1, 2, -1, 7, -1 }, /* 4 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, 2, 1, -1, 5, 3, 5, 2, -1 }, /* 5 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, -1, -1, 1, -1, 6, -1, -1, -1 }, /* 6 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, 1, 3, 3, 1, -1, 7, 4, 3 }, /* 7 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, 2, -1, 2, -1, 1, -1, 8, -1 }, /* 8 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, 1, -1, 1, 4, -1, 4, 1, -1, 9 }, /* 9 */ + {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 0, -1, 1, -1, -1, -1, 5, -1, 1, -1 } /* 10 */ + }; + + DOR(mp_init_multi(&a, &b, &c, &d, NULL)); /* mp_invmod corner-case of https://github.com/libtom/libtommath/issues/118 */ @@ -564,6 +612,30 @@ static int test_mp_invmod(void) EXPECT(mp_cmp(&c, &d) == MP_EQ); } + /* Some small general tests https://github.com/libtom/libtommath/issues/534 */ + for (i = -10; i < 11; i++) { + for (j = -10; j < 11; j++) { + mp_set_i32(&a, i); + mp_set_i32(&b, j); + e = mp_invmod(&a, &b, &c); + if (e != MP_OKAY) { + if (results[i+10][j+10] != -1) { + printf("error = %s from ", mp_error_to_string(e)); + printf("error at i = %d, j =%d should be an error but gave ",i,j); + e = mp_fwrite(&c,10,stdout); + printf("\n"); + goto LBL_ERR; + } + } else { + k = mp_get_i32(&c); + if (k != results[i+10][j+10]) { + printf("result at i = %d, j =%d is %d but should be %d \n", i,j,k,results[i+10][j+10]); + goto LBL_ERR; + } + } + } + } + mp_clear_multi(&a, &b, &c, &d, NULL); return EXIT_SUCCESS; LBL_ERR: diff --git a/s_mp_invmod.c b/s_mp_invmod.c index f3b3f436f..b2fb21dee 100644 --- a/s_mp_invmod.c +++ b/s_mp_invmod.c @@ -98,7 +98,7 @@ mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) } /* if its too low */ - while (mp_cmp_d(&C, 0uL) == MP_LT) { + while (mp_isneg(&C)) { if ((err = mp_add(&C, b, &C)) != MP_OKAY) goto LBL_ERR; } diff --git a/s_mp_invmod_odd.c b/s_mp_invmod_odd.c index e12dfa17f..11fc357dc 100644 --- a/s_mp_invmod_odd.c +++ b/s_mp_invmod_odd.c @@ -12,7 +12,6 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) { mp_int x, y, u, v, B, D; - mp_sign sign; mp_err err; /* 2. [modified] b must be odd */ @@ -28,7 +27,7 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) /* x == modulus, y == value to invert */ if ((err = mp_copy(b, &x)) != MP_OKAY) goto LBL_ERR; - /* we need y = |a| */ + /* y needs to be positive but the remainder d of mp_div(a,b,c,d) might be negative */ if ((err = mp_mod(a, b, &y)) != MP_OKAY) goto LBL_ERR; /* if one of x,y is zero return an error! */ @@ -95,7 +94,6 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) } /* b is now the inverse */ - sign = a->sign; while (mp_isneg(&D)) { if ((err = mp_add(&D, b, &D)) != MP_OKAY) goto LBL_ERR; } @@ -106,7 +104,6 @@ mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) } mp_exch(&D, c); - c->sign = sign; err = MP_OKAY; LBL_ERR: From 6fc9ba65d8c6fcb51ff93d5f1397d7d4c782dcba Mon Sep 17 00:00:00 2001 From: czurnieden Date: Tue, 21 Mar 2023 01:26:21 +0100 Subject: [PATCH 229/304] Removed trailing zero from mp_fwrite output --- mp_fwrite.c | 1 + 1 file changed, 1 insertion(+) diff --git a/mp_fwrite.c b/mp_fwrite.c index 3d8141f06..8ea9d327e 100644 --- a/mp_fwrite.c +++ b/mp_fwrite.c @@ -20,6 +20,7 @@ mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) } if ((err = mp_to_radix(a, buf, size, &written, radix)) == MP_OKAY) { + written--; if (fwrite(buf, written, 1uL, stream) != 1uL) { err = MP_ERR; } From a4a9447447dfd98a72b2ccb6b0a6996032faa9c1 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 15 Jan 2023 01:53:45 +0100 Subject: [PATCH 230/304] Do not assume that more than enough memory is automatically allocated and set to '0' --- s_mp_div_school.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/s_mp_div_school.c b/s_mp_div_school.c index b6a615d10..304c7a9ff 100644 --- a/s_mp_div_school.c +++ b/s_mp_div_school.c @@ -19,6 +19,7 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) { mp_int q, x, y, t1, t2; + mp_digit xdpi; int n, t, i, norm; bool neg; mp_err err; @@ -68,14 +69,16 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) if (i > x.used) { continue; } + /* Do not assume that more than enough memory is automatically allocated and set to '0' */ + xdpi = (i == x.used) ? 0u : x.dp[i]; /* step 3.1 if xi == yt then set q{i-t-1} to b-1, * otherwise set q{i-t-1} to (xi*b + x{i-1})/yt */ - if (x.dp[i] == y.dp[t]) { + if (xdpi == y.dp[t]) { q.dp[(i - t) - 1] = ((mp_digit)1 << (mp_digit)MP_DIGIT_BIT) - (mp_digit)1; } else { mp_word tmp; - tmp = (mp_word)x.dp[i] << (mp_word)MP_DIGIT_BIT; + tmp = (mp_word)xdpi << (mp_word)MP_DIGIT_BIT; tmp |= (mp_word)x.dp[i - 1]; tmp /= (mp_word)y.dp[t]; if (tmp > (mp_word)MP_MASK) { @@ -103,7 +106,7 @@ mp_err s_mp_div_school(const mp_int *a, const mp_int *b, mp_int *c, mp_int *d) /* find right hand */ t2.dp[0] = ((i - 2) < 0) ? 0u : x.dp[i - 2]; t2.dp[1] = x.dp[i - 1]; /* i >= 1 always holds */ - t2.dp[2] = x.dp[i]; + t2.dp[2] = xdpi; t2.used = 3; } while (mp_cmp_mag(&t1, &t2) == MP_GT); From 9e0c049df90c3f92ce51151503401cc6015a1511 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 31 Mar 2023 20:57:47 +0200 Subject: [PATCH 231/304] appveyor: also build against VS2022 Signed-off-by: Steffen Jaeckel --- appveyor.yml | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index 3e9ba4a16..8ed504276 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -5,20 +5,22 @@ branches: - develop - /^release/ - /^support/ - - /^travis/ + - /^build-ci/ image: +- Visual Studio 2022 - Visual Studio 2019 - Visual Studio 2017 - Visual Studio 2015 build_script: - cmd: >- - if "Visual Studio 2019"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\vcvars64.bat" - if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" - if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 - if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 - nmake -f makefile.msvc test.exe - nmake -f makefile.msvc clean-obj - nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /MD /DLTM_TEST_DYNAMIC" + if "Visual Studio 2022"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Auxiliary\Build\vcvars64.bat" + if "Visual Studio 2019"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\vcvars64.bat" + if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" + if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 + if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 + nmake -f makefile.msvc test.exe + nmake -f makefile.msvc clean-obj + nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /MD /DLTM_TEST_DYNAMIC" test_script: - cmd: test.exe - cmd: test_dll.exe From db836bab5a41325b233a08614cd5aea703abad47 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 31 Mar 2023 20:57:59 +0200 Subject: [PATCH 232/304] bump CI base versions & update compiler versions Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 06eb58add..13f2039f5 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -29,7 +29,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [ ubuntu-18.04 ] + os: [ ubuntu-20.04 ] # The environment given to the programs in the build # We have only one program and the variable $BUILDOPTIONS # has only the options to that program: testme.sh @@ -44,13 +44,13 @@ jobs: # Run always with valgrind (no sanitizer, but debug info) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --with-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } # Shared library build - - { BUILDOPTIONS: '--with-cc=gcc --make-option=-f --make-option=makefile.shared', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: 'gcc-8 libtool-bin' } + - { BUILDOPTIONS: '--with-cc=gcc --make-option=-f --make-option=makefile.shared', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: 'libtool-bin' } # GCC for the 32-bit architecture (no valgrind) - { BUILDOPTIONS: '--with-cc=gcc --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } # clang for the 32-bit architecture (no valgrind) - - { BUILDOPTIONS: '--with-cc=clang-7 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } # RSA superclass with tests (no sanitizer, but debug info) - - { BUILDOPTIONS: '--with-cc=gcc-5 --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-5' } + - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' @@ -58,7 +58,7 @@ jobs: #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --limit-valgrind --make-option=tune' #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_32BIT --limit-valgrind --make-option=tune' - - { BUILDOPTIONS: '--with-cc=clang-7 --limit-valgrind --make-option=tune', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-10 --limit-valgrind --make-option=tune', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } # GCC for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs. @@ -68,9 +68,9 @@ jobs: # clang for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs - - { BUILDOPTIONS: '--with-cc=clang-7 --test-vs-mtest=333333 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-10 --test-vs-mtest=333333 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } # ... and a better random source. - - { BUILDOPTIONS: '--with-cc=clang-7 --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } + - { BUILDOPTIONS: '--with-cc=clang-10 --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) # TODO: Probably not possible to run anything in x32 in GH actions @@ -79,21 +79,21 @@ jobs: # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } - - { BUILDOPTIONS: '--with-cc=gcc-5 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-5' } - - { BUILDOPTIONS: '--with-cc=gcc-4.8 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-4.8' } + - { BUILDOPTIONS: '--with-cc=gcc-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-10' } + - { BUILDOPTIONS: '--with-cc=gcc-8 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-8' } + - { BUILDOPTIONS: '--with-cc=gcc-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-7' } # clang for x86-64 architecture (64-bit longs and 64-bit pointers) - - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'relaxed', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-7 --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-7 --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'relaxed', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-10 --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-10 --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-12 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-12 llvm-12' } - { BUILDOPTIONS: '--with-cc=clang-9 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-9 llvm-9' } - { BUILDOPTIONS: '--with-cc=clang-8 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-8 llvm-8' } + - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } - { BUILDOPTIONS: '--with-cc=clang-6.0 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-6.0 llvm-6.0' } - - { BUILDOPTIONS: '--with-cc=clang-5.0 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-5.0 llvm-5.0' } - - { BUILDOPTIONS: '--with-cc=clang-4.0 --with-m64 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-4.0 llvm-4.0' } # Link time optimization - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } #- { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } @@ -151,7 +151,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [ ubuntu-18.04, ubuntu-20.04 ] + os: [ ubuntu-20.04, ubuntu-22.04 ] build_type: [ '', -DCMAKE_BUILD_TYPE=Debug, -DCMAKE_BUILD_TYPE=Release, -DCMAKE_BUILD_TYPE=RelWithDebInfo, -DCMAKE_BUILD_TYPE=MinSizeRel ] cc: [ clang, gcc ] config: From 369107711a6d090f709b7d91c574fa94287eb09c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sat, 1 Apr 2023 12:53:38 +0200 Subject: [PATCH 233/304] silence compiler warnings Signed-off-by: Steffen Jaeckel --- testme.sh | 28 +++++++++++++++++++--------- 1 file changed, 19 insertions(+), 9 deletions(-) diff --git a/testme.sh b/testme.sh index 80f967a34..089e42a70 100755 --- a/testme.sh +++ b/testme.sh @@ -105,10 +105,29 @@ _die() fi } +_fixup_cflags() { + compiler_version=$(echo "$1="$($1 -dumpversion)) + case "$compiler_version" in + clang*=4.2.1) + # one of my versions of clang complains about some stuff in stdio.h and stdarg.h ... + TEST_CFLAGS="-Wno-typedef-redefinition" + ;; + gcc*=9) + # gcc 9 seems to sometimes think that variables are uninitialized, but they are. + TEST_CFLAGS="-Wno-maybe-uninitialized" + ;; + *) + TEST_CFLAGS="" + ;; + esac + echo $compiler_version +} + _make() { echo -ne " Compile $1 $2" suffix=$(echo ${1}${2} | tr ' ' '_') + _fixup_cflags "$1" CC="$1" CFLAGS="$2 $TEST_CFLAGS" make -j$MAKE_JOBS $3 $MAKE_OPTIONS 2>gcc_errors_${suffix}.log errcnt=$(wc -l < gcc_errors_${suffix}.log) if [[ ${errcnt} -gt 1 ]]; then @@ -400,15 +419,6 @@ do echo "Skipped compiler $i, file not found" continue fi - compiler_version=$(echo "$i="$($i -dumpversion)) - if [ "$compiler_version" == "clang=4.2.1" ] - then - # one of my versions of clang complains about some stuff in stdio.h and stdarg.h ... - TEST_CFLAGS="-Wno-typedef-redefinition" - else - TEST_CFLAGS="" - fi - echo $compiler_version for a in "${archflags[@]}" do From b1e1ea53408d1ad4bebd769597e58551a69179cd Mon Sep 17 00:00:00 2001 From: czurnieden Date: Thu, 7 Jan 2021 07:41:46 +0100 Subject: [PATCH 234/304] Raised upper limit for Comba squaring --- mp_mul.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mp_mul.c b/mp_mul.c index d35fa8ef4..1f9bed297 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -23,7 +23,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) } else if ((a == b) && MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ (((a->used * 2) + 1) < MP_WARRAY) && - (a->used < (MP_MAX_COMBA / 2))) { + (a->used < (MP_MAX_COMBA))) { err = s_mp_sqr_comba(a, c); } else if ((a == b) && MP_HAS(S_MP_SQR)) { From 3d79350460dbbc58c2645115259e3a5e0044733a Mon Sep 17 00:00:00 2001 From: czurnieden Date: Thu, 7 Jan 2021 22:16:04 +0100 Subject: [PATCH 235/304] Addition of extensive tests for s_mp_sqr_comba --- demo/test.c | 47 +++++++++++++++++++++++++++++++++++++++++++++++ mp_mul.c | 2 +- 2 files changed, 48 insertions(+), 1 deletion(-) diff --git a/demo/test.c b/demo/test.c index 0ebcfd07f..3ea16bf61 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1828,6 +1828,51 @@ static int test_mp_root_n(void) return EXIT_FAILURE; } +/* Less error-prone than -1 + 2^n with mp_2expt */ +static mp_err s_fill_with_ones(mp_int *a, int size) +{ + int i; + mp_err err = MP_OKAY; + + mp_zero(a); + + if ((err = mp_grow(a, size)) != MP_OKAY) goto LTM_ERR; + for (i = 0; i < size; i++) { + a->dp[i] = (mp_digit)MP_MASK; + a->used++; + } + +LTM_ERR: + return err; +} + +static int test_s_mp_sqr_comba(void) +{ + mp_int a, r1, r2; + int i, j; + + DOR(mp_init_multi(&a, &r1, &r2, NULL)); + + for (i = 1; i <= MP_MAX_COMBA; i++) { + DO(s_fill_with_ones(&a, i)); + DO(s_mp_sqr_comba(&a, &r1)); + DO(s_mp_sqr(&a, &r2)); + EXPECT(mp_cmp(&r1, &r2) == MP_EQ); + for (j = 0; j < 20; j++) { + DO(mp_rand(&a, i)); + DO(s_mp_sqr_comba(&a, &r1)); + DO(s_mp_sqr(&a, &r2)); + EXPECT(mp_cmp(&r1, &r2) == MP_EQ); + } + } + + mp_clear_multi(&a, &r1, &r2, NULL); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear_multi(&a, &r1, &r2, NULL); + return EXIT_FAILURE; +} + static int test_s_mp_mul_balance(void) { mp_int a, b, c; @@ -2328,6 +2373,8 @@ static int unit_tests(int argc, char **argv) T1(mp_xor, MP_XOR), T3(s_mp_div_recursive, ONLY_PUBLIC_API, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), T3(s_mp_div_small, ONLY_PUBLIC_API, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), + /* s_mp_mul_comba not (yet) testable because s_mp_mul branches to s_mp_mul_comba automatically */ + T2(s_mp_sqr_comba, ONLY_PUBLIC_API, S_MP_SQR_COMBA), T2(s_mp_mul_balance, ONLY_PUBLIC_API, S_MP_MUL_BALANCE), T2(s_mp_mul_karatsuba, ONLY_PUBLIC_API, S_MP_MUL_KARATSUBA), T2(s_mp_sqr_karatsuba, ONLY_PUBLIC_API, S_MP_SQR_KARATSUBA), diff --git a/mp_mul.c b/mp_mul.c index 1f9bed297..81807406e 100644 --- a/mp_mul.c +++ b/mp_mul.c @@ -23,7 +23,7 @@ mp_err mp_mul(const mp_int *a, const mp_int *b, mp_int *c) } else if ((a == b) && MP_HAS(S_MP_SQR_COMBA) && /* can we use the fast comba multiplier? */ (((a->used * 2) + 1) < MP_WARRAY) && - (a->used < (MP_MAX_COMBA))) { + (a->used <= MP_MAX_COMBA)) { err = s_mp_sqr_comba(a, c); } else if ((a == b) && MP_HAS(S_MP_SQR)) { From b7d905744c7b360e961ce4a9ad9e7e3b6624958c Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sat, 9 Jan 2021 06:03:14 +0100 Subject: [PATCH 236/304] optimized s_mp_sqr --- demo/test.c | 28 ++++++++++++++++++++++++++++ s_mp_sqr.c | 23 ++++++++++++++++++----- 2 files changed, 46 insertions(+), 5 deletions(-) diff --git a/demo/test.c b/demo/test.c index 3ea16bf61..0a9bfc317 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1846,6 +1846,33 @@ static mp_err s_fill_with_ones(mp_int *a, int size) return err; } +static int test_s_mp_sqr(void) +{ + mp_int a, b, c; + int i; + + DOR(mp_init_multi(&a, &b, &c, NULL)); + + /* s_mp_mul() has a hardcoded branch to s_mul_comba if s_mul_comba is available, + so test another 10 just in case. */ + for (i = 1; i < MP_MAX_COMBA + 10; i++) { + DO(s_fill_with_ones(&a, i)); + DO(s_mp_sqr(&a, &b)); + DO(s_mp_mul(&a, &a, &c, 2*i + 1)); + EXPECT(mp_cmp(&b, &c) == MP_EQ); + DO(mp_rand(&a, i)); + DO(s_mp_sqr(&a, &b)); + DO(s_mp_mul(&a, &a, &c, 2*i + 1)); + EXPECT(mp_cmp(&b, &c) == MP_EQ); + } + + mp_clear_multi(&a, &b, &c, NULL); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear_multi(&a, &b, &c, NULL); + return EXIT_FAILURE; +} + static int test_s_mp_sqr_comba(void) { mp_int a, r1, r2; @@ -2373,6 +2400,7 @@ static int unit_tests(int argc, char **argv) T1(mp_xor, MP_XOR), T3(s_mp_div_recursive, ONLY_PUBLIC_API, S_MP_DIV_RECURSIVE, S_MP_DIV_SCHOOL), T3(s_mp_div_small, ONLY_PUBLIC_API, S_MP_DIV_SMALL, S_MP_DIV_SCHOOL), + T2(s_mp_sqr, ONLY_PUBLIC_API, S_MP_SQR), /* s_mp_mul_comba not (yet) testable because s_mp_mul branches to s_mp_mul_comba automatically */ T2(s_mp_sqr_comba, ONLY_PUBLIC_API, S_MP_SQR_COMBA), T2(s_mp_mul_balance, ONLY_PUBLIC_API, S_MP_MUL_BALANCE), diff --git a/s_mp_sqr.c b/s_mp_sqr.c index 4a2030638..da9aa69ce 100644 --- a/s_mp_sqr.c +++ b/s_mp_sqr.c @@ -38,9 +38,10 @@ mp_err s_mp_sqr(const mp_int *a, mp_int *b) r = (mp_word)a->dp[ix] * (mp_word)a->dp[iy]; /* now calculate the double precision result, note we use - * addition instead of *2 since it's easier to optimize + * addition instead of *2 since it's easier to optimize. */ - r = (mp_word)t.dp[ix + iy] + r + r + (mp_word)u; + /* Some architectures and/or compilers seem to prefer a bit-shift nowadays */ + r = (mp_word)t.dp[ix + iy] + (r<<1) + (mp_word)u; /* store lower part */ t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); @@ -50,9 +51,21 @@ mp_err s_mp_sqr(const mp_int *a, mp_int *b) } /* propagate upwards */ while (u != 0uL) { - r = (mp_word)t.dp[ix + iy] + (mp_word)u; - t.dp[ix + iy] = (mp_digit)(r & (mp_word)MP_MASK); - u = (mp_digit)(r >> (mp_word)MP_DIGIT_BIT); + mp_digit tmp; + /* + "u" can get bigger than MP_DIGIT_MAX and would need a bigger type + for the sum (mp_word). That is costly if mp_word is not a native + integer but a bigint from the compiler library. We do a manual + multiword addition instead. + */ + /* t.dp[ix + iy] has been masked off by MP_MASK and is hence of the correct size + and we can just add the lower part of "u". Carry is guaranteed to fit into + the type used for mp_digit, too, so we can extract it later. */ + tmp = t.dp[ix + iy] + (u & MP_MASK); + /* t.dp[ix + iy] is set to the result minus the carry, carry is still in "tmp" */ + t.dp[ix + iy] = tmp & MP_MASK; + /* Add high part of "u" and the carry from "tmp" to get the next "u" */ + u = (u >> MP_DIGIT_BIT) + (tmp >> MP_DIGIT_BIT); ++iy; } } From eb7fe2d5f8392ec5d1ed3fae4b7c44c5ff69e314 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sat, 10 Jul 2021 23:10:48 +0200 Subject: [PATCH 237/304] Added check for __SIZEOF_INT128__ to avoid some problems with a 64-bit arch. and 32-bit userspace --- tommath.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tommath.h b/tommath.h index 44c92b22a..fbc025ef9 100644 --- a/tommath.h +++ b/tommath.h @@ -29,7 +29,7 @@ extern "C" { defined(__ia64) || defined(__ia64__) || defined(__itanium__) || defined(_M_IA64) || \ defined(__LP64__) || defined(_LP64) || defined(__64BIT__) # if !(defined(MP_64BIT) || defined(MP_32BIT) || defined(MP_16BIT)) -# if defined(__GNUC__) && !defined(__hppa) +# if defined(__GNUC__) && defined(__SIZEOF_INT128__) && !defined(__hppa) /* we support 128bit integers only via: __attribute__((mode(TI))) */ # define MP_64BIT # else From 3be34b15c5c6396be2cf866a0a4c00d75ffa3873 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 20 Dec 2020 22:55:22 +0100 Subject: [PATCH 238/304] Expansion of mp_log to the full range together with the extension of mp_log to bigint bases. --- .gitignore | 10 ++ demo/test.c | 65 ++++++++++ doc/bn.tex | 30 +++-- libtommath_VS2008.vcproj | 16 ++- makefile | 6 +- makefile.mingw | 6 +- makefile.msvc | 6 +- makefile.shared | 6 +- makefile.unix | 6 +- mp_log.c | 251 +++++++++++++++++++++++++++++++++++++++ mp_log_n.c | 24 ++-- s_mp_flog2_mp_word.c | 15 +++ s_mp_fp_log.c | 169 ++++++++++++++++++++++++++ s_mp_log.c | 81 ------------- s_mp_log_d.c | 65 ---------- sources.cmake | 5 +- tommath.def | 1 + tommath.h | 3 + tommath_class.h | 54 +++++---- tommath_private.h | 21 +++- 20 files changed, 619 insertions(+), 221 deletions(-) create mode 100644 mp_log.c create mode 100644 s_mp_flog2_mp_word.c create mode 100644 s_mp_fp_log.c delete mode 100644 s_mp_log.c delete mode 100644 s_mp_log_d.c diff --git a/.gitignore b/.gitignore index 36fd9dd9b..d2f01329f 100644 --- a/.gitignore +++ b/.gitignore @@ -85,6 +85,16 @@ etc/tune tommath.tex libtommath.pc +# ignore files generated by bibtex/biber +83aea75e0c59d1de027747003151d53dcb2a51c9.bib +*.bbl +*.bcf +*.blg +*.loa +*.lol +*.run.xml + + # ignore files generated by testme.sh gcc_errors_*.txt test_*.txt diff --git a/demo/test.c b/demo/test.c index 0a9bfc317..5a7b5db9f 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1516,6 +1516,70 @@ static int test_mp_log_n(void) return EXIT_FAILURE; } +static int test_mp_log(void) +{ + mp_int a, base, bn, t; + int lb, lb2, i, j; + + DOR(mp_init_multi(&a, &base, &bn, &t, NULL)); + + /* + The small values got tested above for mp_log_n already, leaving the big stuff + with bases larger than INT_MAX. + */ + + /* Edgecases a^b and -1+a^b (floor(log_2(256^129)) = 1032) */ + for (i = 2; i < 256; i++) { + mp_set_i32(&a,i); + for (j = 2; j < ((i/2)+1); j++) { + DO(mp_expt_n(&a, j, &bn)); + mp_set_i32(&base,j); + /* i^j a perfect power */ + DO(mp_log(&bn, &a, &lb)); + DO(mp_expt_n(&a, lb, &t)); + if (mp_cmp(&t, &bn) != MP_EQ) { + fprintf(stderr,"FAILURE mp_log for perf. power at i = %d, j = %d\n", i, j); + goto LBL_ERR; + } + /* -1 + i^j */ + DO(mp_decr(&bn)); + DO(mp_log(&bn, &a, &lb2)); + if (lb != (lb2+1)) { + fprintf(stderr,"FAILURE mp_log for -1 + i^j at i = %d, j = %d\n", i, j); + goto LBL_ERR; + } + } + } + + /* Random a, base */ + for (i = 1; i < 256; i++) { + DO(mp_rand(&a, i)); + for (j = 1; j < ((i/2)+1); j++) { + DO(mp_rand(&base, j)); + DO(mp_log(&a, &base, &lb)); + DO(mp_expt_n(&base, lb, &bn)); + /* "bn" must be smaller than or equal to "a" at this point. */ + if (mp_cmp(&bn, &a) == MP_GT) { + fprintf(stderr,"FAILURE mp_log random in GT check"); + goto LBL_ERR; + } + DO(mp_mul(&bn, &base, &bn)); + /* "bn" must be bigger than "a" at this point. */ + if (mp_cmp(&bn, &a) != MP_GT) { + fprintf(stderr,"FAILURE mp_log random in NOT GT check"); + goto LBL_ERR; + } + } + } + + mp_clear_multi(&a, &base, &bn, &t, NULL); + return EXIT_SUCCESS; +LBL_ERR: + mp_clear_multi(&a, &base, &bn, &t, NULL); + return EXIT_FAILURE; +} + + static int test_mp_incr(void) { mp_int a, b; @@ -2373,6 +2437,7 @@ static int unit_tests(int argc, char **argv) T1(mp_get_u64, MP_GET_I64), T1(mp_get_ul, MP_GET_L), T1(mp_log_n, MP_LOG_N), + T1(mp_log, MP_LOG), T1(mp_incr, MP_ADD_D), T1(mp_invmod, MP_INVMOD), T1(mp_is_square, MP_IS_SQUARE), diff --git a/doc/bn.tex b/doc/bn.tex index 566b3be32..711ad0e58 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -1946,11 +1946,16 @@ \section{Root Finding} \begin{alltt} mp_err mp_sqrt(const mp_int *arg, mp_int *ret) \end{alltt} - \chapter{Logarithm} \section{Integer Logarithm} A logarithm function for positive integer input \texttt{a, base} computing $\floor{\log_bx}$ such -that $(\log_b x)^b \le x$. +that $(\log_b x)^b \le x$. The function \texttt{mp\_log\_n} is just a wrapper that converts \texttt{base} +to a bigint and calls \texttt{mp\_log}. + +\index{mp\_log} +\begin{alltt} +mp_err mp_log(const mp_int *a, const mp_int *base, int *c) +\end{alltt} \index{mp\_log\_n} \begin{alltt} @@ -1958,6 +1963,7 @@ \section{Integer Logarithm} \end{alltt} \subsection{Example} +Example given for \texttt{mp\_log\_n} only because the single difference is the type of \texttt{base}. \begin{small} \begin{alltt} #include @@ -1968,15 +1974,15 @@ \subsection{Example} int main(int argc, char **argv) { - mp_int x, output; - int base; + mp_int x; + int base, output; mp_err e; if (argc != 3) { fprintf(stderr,"Usage %s base x\textbackslash{}n", argv[0]); exit(EXIT_FAILURE); } - if ((e = mp_init_multi(&x, &output, NULL)) != MP_OKAY) { + if ((e = mp_init(&x)) != MP_OKAY) { fprintf(stderr,"mp_init failed: \textbackslash{}"%s\textbackslash{}"\textbackslash{}n", mp_error_to_string(e)); exit(EXIT_FAILURE); @@ -1998,20 +2004,18 @@ \subsection{Example} mp_error_to_string(e)); exit(EXIT_FAILURE); } + printf("%d\n",output); - if ((e = mp_fwrite(&output, 10, stdout)) != MP_OKAY) { - fprintf(stderr,"mp_fwrite failed: \textbackslash{}"%s\textbackslash{}"\textbackslash{}n", - mp_error_to_string(e)); - exit(EXIT_FAILURE); - } - putchar('\textbackslash{}n'); - - mp_clear_multi(&x, &output, NULL); + mp_clear(&x); exit(EXIT_SUCCESS); } \end{alltt} \end{small} + + + + \chapter{Prime Numbers} \section{Fermat Test} diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index e27aa9860..2215683f7 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -544,6 +544,10 @@ RelativePath="mp_lcm.c" > + + @@ -829,27 +833,27 @@ > 4 ) ) \ + ||\ + ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) + +mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +{ + mp_int bn, La, Lb; + int n, fla, flb; + mp_word la_word, lb_word; + + mp_err err; + mp_ord cmp; + + if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { + return MP_VAL; + } + + if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_POWER_OF_TWO(b)) { + *lb = MP_LOG2_EXPT(a, b); + return MP_OKAY; + } + + /* floor(log_2(x)) for cut-off */ + fla = mp_count_bits(a) - 1; + flb = mp_count_bits(b) - 1; + + cmp = mp_cmp(a, b); + + /* "a < b -> 0" and "(b == a) -> 1" */ + if ((cmp == MP_LT) || (cmp == MP_EQ)) { + *lb = (cmp == MP_EQ); + return MP_OKAY; + } + + /* "a < b^2 -> 1" (bit-count is sufficient, doesn't need to be exact) */ + if (((2 * flb)-1) > fla) { + *lb = 1; + return MP_OKAY; + } + + if ((err = mp_init_multi(&La, &Lb, &bn, NULL)) != MP_OKAY) { + return err; + } + + /* Approximation of the individual logarithms with low precision */ + if ((err = s_mp_fp_log(a, &la_word)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log(b, &lb_word)) != MP_OKAY) goto LTM_ERR; + + /* Approximation of log_b(a) with low precision. */ + n = (int)(((la_word - (lb_word + 1)/2) / lb_word) + 1); + /* TODO: just floor it instead? Multiplication is cheaper than division. */ + /* n = (int)(la_word / lb_word); */ + + /* Check result. Result is wrong by 2(two) at most. */ + if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) { + /* If the approximation overshot we can give it another try */ + if (err == MP_OVF) { + n--; + /* But only one */ + if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; + } else { + goto LTM_ERR; + } + } + + cmp = mp_cmp(&bn, a); + + /* The rare case of a perfect power makes a perfect shortcut, too. */ + if (cmp == MP_EQ) { + *lb = n; + goto LTM_OUT; + } + + /* We have to make at least one multiplication because it could still be a perfect power. */ + if (cmp == MP_LT) { + do { + /* Full big-integer operations are to be avoided if possible */ + if (b->used == 1) { + if ((err = mp_mul_d(&bn, b->dp[0], &bn)) != MP_OKAY) { + if (err == MP_OVF) { + goto LTM_OUT; + } + goto LTM_ERR; + } + } else { + if ((err = mp_mul(&bn, b, &bn)) != MP_OKAY) { + if (err == MP_OVF) { + goto LTM_OUT; + } + goto LTM_ERR; + } + } + n++; + } while ((cmp = mp_cmp(&bn, a)) == MP_LT); + /* Overshot, take it back. */ + if (cmp == MP_GT) { + n--; + } + goto LTM_OUT; + } + + /* But it can overestimate, too, for example if "a" is closely below some "b^k" */ + if (cmp == MP_GT) { + do { + if (b->used == 1) { + /* These are cheaper exact divisions, but that function is not available in LTM */ + if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; + + } else { + if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; + } + n--; + } while ((cmp = mp_cmp(&bn, a)) == MP_GT); + } + +LTM_OUT: + *lb = n; + err = MP_OKAY; +LTM_ERR: + mp_clear_multi(&La, &Lb, &bn, NULL); + return err; +} + + +#else +/* Bigint version. A bit slower but not _that_ much */ +mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +{ + mp_int bn, La, Lb, t; + + int n, fla, flb; + + mp_err err; + mp_ord cmp; + + if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { + return MP_VAL; + } + + if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_POWER_OF_TWO(b)) { + *lb = MP_LOG2_EXPT(a, b); + return MP_OKAY; + } + + fla = mp_count_bits(a) - 1; + flb = mp_count_bits(b) - 1; + + cmp = mp_cmp(a, b); + + if ((cmp == MP_LT) || (cmp == MP_EQ)) { + *lb = (cmp == MP_EQ); + return MP_OKAY; + } + + if ((2 * flb) > fla) { + *lb = 1; + return MP_OKAY; + } + + if ((err = mp_init_multi(&La, &Lb, &bn, &t, NULL)) != MP_OKAY) { + return err; + } + + if ((err = s_mp_fp_log(a, &La)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log(b, &Lb)) != MP_OKAY) goto LTM_ERR; + + if ((err = mp_add_d(&Lb, 1u, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2(&t, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_sub(&La, &t, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div(&t, &Lb, &t, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add_d(&t, 1u, &t)) != MP_OKAY) goto LTM_ERR; + + n = mp_get_i32(&t); + + if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) { + if (err == MP_OVF) { + n--; + if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; + } else { + goto LTM_ERR; + } + } + cmp = mp_cmp(&bn, a); + + if (cmp == MP_EQ) { + *lb = n; + goto LTM_OUT; + } + + if (cmp == MP_LT) { + do { + if (b->used == 1) { + if ((err = mp_mul_d(&bn, b->dp[0], &bn)) != MP_OKAY) { + if (err == MP_OVF) { + goto LTM_OUT; + } + goto LTM_ERR; + } + } else { + if ((err = mp_mul(&bn, b, &bn)) != MP_OKAY) { + if (err == MP_OVF) { + goto LTM_OUT; + } + goto LTM_ERR; + } + } + n++; + } while ((cmp = mp_cmp(&bn, a)) == MP_LT); + if (cmp == MP_GT) { + n--; + } + goto LTM_OUT; + } + + if (cmp == MP_GT) { + do { + if (b->used == 1) { + if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; + + } else { + if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; + } + n--; + } while ((cmp = mp_cmp(&bn, a)) == MP_GT); + } + +LTM_OUT: + *lb = n; + err = MP_OKAY; +LTM_ERR: + mp_clear_multi(&La, &Lb, &bn, &t, NULL); + return err; +} +#endif + + + +#endif diff --git a/mp_log_n.c b/mp_log_n.c index 4de1e3993..364e28a4b 100644 --- a/mp_log_n.c +++ b/mp_log_n.c @@ -5,25 +5,15 @@ mp_err mp_log_n(const mp_int *a, int base, int *c) { - if (mp_isneg(a) || mp_iszero(a) || (base < 2) || (unsigned)base > (unsigned)MP_DIGIT_MAX) { - return MP_VAL; - } + mp_int b; + mp_err err; - if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_2EXPT((mp_digit)base)) { - *c = s_mp_log_2expt(a, (mp_digit)base); - return MP_OKAY; - } + if ((err = mp_init_i32(&b, base)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_log(a, &b, c)) != MP_OKAY) goto LTM_ERR; - if (MP_HAS(S_MP_LOG_D) && (a->used == 1)) { - *c = s_mp_log_d((mp_digit)base, a->dp[0]); - return MP_OKAY; - } - - if (MP_HAS(S_MP_LOG)) { - return s_mp_log(a, (mp_digit)base, c); - } - - return MP_VAL; +LTM_ERR: + mp_clear(&b); + return err; } #endif diff --git a/s_mp_flog2_mp_word.c b/s_mp_flog2_mp_word.c new file mode 100644 index 000000000..24b21e19f --- /dev/null +++ b/s_mp_flog2_mp_word.c @@ -0,0 +1,15 @@ +#include "tommath_private.h" +#ifdef S_FLOG2_MP_WORD_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_word s_flog2_mp_word(mp_word value) +{ + mp_word r = 0u; + while ((value >>= 1) != 0u) { + r++; + } + return r; +} + +#endif diff --git a/s_mp_fp_log.c b/s_mp_fp_log.c new file mode 100644 index 000000000..e7db14aab --- /dev/null +++ b/s_mp_fp_log.c @@ -0,0 +1,169 @@ +#include "tommath_private.h" +#ifdef S_MP_FP_LOG_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#define MP_PRECISION_FIXED_LOG ( (int) (((sizeof(mp_word) * CHAR_BIT) / 2) - 1)) +#define MP_UPPER_LIMIT_FIXED_LOG ( (int) ( (sizeof(mp_word) * CHAR_BIT) - 1)) + +/* Fixed point binary logarithm with small precision (half the bitsize of a mp_digit)*/ +#if ( (UINT_MAX == UINT32_MAX) && ( MP_WORD_SIZE > 4 ) ) \ + ||\ + ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) + +static mp_word s_mp_flog2_mp_word(mp_word value) +{ + mp_word r = 0u; + while ((value >>= 1) != 0u) { + r++; + } + return r; +} + +/* Fixed point bitwise logarithm base two of "x" with precision "p" */ +static mp_err s_mp_fp_log_fraction(mp_word x, int p, mp_word *c) +{ + mp_word b, L_out, L, a_bar, twoep; + int i; + + L = s_mp_flog2_mp_word(x); + + if ((L + (mp_word)p) > MP_UPPER_LIMIT_FIXED_LOG) { + return MP_VAL; + } + + a_bar = ((mp_word)p < L) ? x << (L - (mp_word)p) : x << ((mp_word)p - L); + b = (mp_word)(1u) << (p - 1); + L_out = L << p; + + twoep = (mp_word)(1u) << (p + 1); + + for (i = 0; i < p; i++) { + a_bar = (a_bar * a_bar) >> p; + if (a_bar >= twoep) { + a_bar >>= 1u; + L_out += b; + } + b >>= 1u; + } + *c = L_out; + return MP_OKAY; +} + +/* Approximate the base two logarithm of "a" */ +mp_err s_mp_fp_log(const mp_int *a, mp_word *c) +{ + mp_err err; + int la; + int prec = MP_PRECISION_FIXED_LOG; + mp_word tmp, la_word; + mp_int t; + + la = mp_count_bits(a) - 1; + + /* We don't use the whole number, just the most significant "prec" bits */ + if (la > prec) { + if ((err = mp_init(&t)) != MP_OKAY) goto LTM_ERR; + /* Get enough msb-bits for the chosen precision */ + if ((err = mp_div_2d(a, la - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; + tmp = mp_get_u64(&t); + /* Compute the low precision approximation for the fractional part */ + if ((err = s_mp_fp_log_fraction(tmp, prec, &la_word)) != MP_OKAY) goto LTM_ERR; + /* Compute the integer part and add it */ + tmp = ((mp_word)(la - prec))< prec) { + if ((err = mp_div_2d(a, fla - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_fraction(&t, prec, + &La)) != MP_OKAY) goto LTM_ERR; + mp_set_i32(&t,fla - prec); + if ((err = mp_mul_2d(&t,prec, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add(&La, &t, &La)) != MP_OKAY) goto LTM_ERR; + } else { + if ((err = s_mp_fp_log_fraction(a, prec, + &La)) != MP_OKAY) goto LTM_ERR; + } + + mp_exch(&La, c); + +LTM_ERR: + mp_clear_multi(&La, &t, NULL); + return err; +} + +#endif +#endif diff --git a/s_mp_log.c b/s_mp_log.c deleted file mode 100644 index d1ac73b1a..000000000 --- a/s_mp_log.c +++ /dev/null @@ -1,81 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_LOG_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_err s_mp_log(const mp_int *a, mp_digit base, int *c) -{ - mp_err err; - int high, low; - mp_int bracket_low, bracket_high, bracket_mid, t, bi_base; - - mp_ord cmp = mp_cmp_d(a, base); - if ((cmp == MP_LT) || (cmp == MP_EQ)) { - *c = cmp == MP_EQ; - return MP_OKAY; - } - - if ((err = - mp_init_multi(&bracket_low, &bracket_high, - &bracket_mid, &t, &bi_base, NULL)) != MP_OKAY) { - return err; - } - - low = 0; - mp_set(&bracket_low, 1uL); - high = 1; - - mp_set(&bracket_high, base); - - /* - A kind of Giant-step/baby-step algorithm. - Idea shamelessly stolen from https://programmingpraxis.com/2010/05/07/integer-logarithms/2/ - The effect is asymptotic, hence needs benchmarks to test if the Giant-step should be skipped - for small n. - */ - while (mp_cmp(&bracket_high, a) == MP_LT) { - low = high; - if ((err = mp_copy(&bracket_high, &bracket_low)) != MP_OKAY) { - goto LBL_END; - } - high <<= 1; - if ((err = mp_sqr(&bracket_high, &bracket_high)) != MP_OKAY) { - goto LBL_END; - } - } - mp_set(&bi_base, base); - - while ((high - low) > 1) { - int mid = (high + low) >> 1; - - if ((err = mp_expt_n(&bi_base, mid - low, &t)) != MP_OKAY) { - goto LBL_END; - } - if ((err = mp_mul(&bracket_low, &t, &bracket_mid)) != MP_OKAY) { - goto LBL_END; - } - cmp = mp_cmp(a, &bracket_mid); - if (cmp == MP_LT) { - high = mid; - mp_exch(&bracket_mid, &bracket_high); - } - if (cmp == MP_GT) { - low = mid; - mp_exch(&bracket_mid, &bracket_low); - } - if (cmp == MP_EQ) { - *c = mid; - goto LBL_END; - } - } - - *c = (mp_cmp(&bracket_high, a) == MP_EQ) ? high : low; - -LBL_END: - mp_clear_multi(&bracket_low, &bracket_high, &bracket_mid, - &t, &bi_base, NULL); - return err; -} - - -#endif diff --git a/s_mp_log_d.c b/s_mp_log_d.c deleted file mode 100644 index 5ff6c1fba..000000000 --- a/s_mp_log_d.c +++ /dev/null @@ -1,65 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_LOG_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -static mp_word s_pow(mp_word base, mp_word exponent) -{ - mp_word result = 1u; - while (exponent != 0u) { - if ((exponent & 1u) == 1u) { - result *= base; - } - exponent >>= 1; - base *= base; - } - - return result; -} - -int s_mp_log_d(mp_digit base, mp_digit n) -{ - mp_word bracket_low = 1uLL, bracket_high = base, N = n; - int ret, high = 1, low = 0; - - if (n < base) { - return 0; - } - if (n == base) { - return 1; - } - - while (bracket_high < N) { - low = high; - bracket_low = bracket_high; - high <<= 1; - bracket_high *= bracket_high; - } - - while (((mp_digit)(high - low)) > 1uL) { - int mid = (low + high) >> 1; - mp_word bracket_mid = bracket_low * s_pow(base, (mp_word)(mid - low)); - - if (N < bracket_mid) { - high = mid ; - bracket_high = bracket_mid ; - } - if (N > bracket_mid) { - low = mid ; - bracket_low = bracket_mid ; - } - if (N == bracket_mid) { - return mid; - } - } - - if (bracket_high == N) { - ret = high; - } else { - ret = low; - } - - return ret; -} - -#endif diff --git a/sources.cmake b/sources.cmake index 797d461e2..e3eeab12d 100644 --- a/sources.cmake +++ b/sources.cmake @@ -60,6 +60,7 @@ mp_invmod.c mp_is_square.c mp_kronecker.c mp_lcm.c +mp_log.c mp_log_n.c mp_lshd.c mp_mod.c @@ -131,12 +132,12 @@ s_mp_div_school.c s_mp_div_small.c s_mp_exptmod.c s_mp_exptmod_fast.c +s_mp_flog2_mp_word.c +s_mp_fp_log.c s_mp_get_bit.c s_mp_invmod.c s_mp_invmod_odd.c -s_mp_log.c s_mp_log_2expt.c -s_mp_log_d.c s_mp_montgomery_reduce_comba.c s_mp_mul.c s_mp_mul_balance.c diff --git a/tommath.def b/tommath.def index 1af4e9e79..86f348727 100644 --- a/tommath.def +++ b/tommath.def @@ -63,6 +63,7 @@ EXPORTS mp_is_square mp_kronecker mp_lcm + mp_log mp_log_n mp_lshd mp_mod diff --git a/tommath.h b/tommath.h index fbc025ef9..7994b6e1a 100644 --- a/tommath.h +++ b/tommath.h @@ -416,6 +416,9 @@ mp_err mp_lcm(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; /* Integer logarithm to integer base */ mp_err mp_log_n(const mp_int *a, int base, int *c) MP_WUR; +/* Integer logarithm to bigint base */ +mp_err mp_log(const mp_int *a, const mp_int *base, int *c) MP_WUR; + /* c = a**b */ mp_err mp_expt_n(const mp_int *a, int b, mp_int *c) MP_WUR; diff --git a/tommath_class.h b/tommath_class.h index becbcb193..8aaa94d20 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -69,6 +69,7 @@ # define MP_IS_SQUARE_C # define MP_KRONECKER_C # define MP_LCM_C +# define MP_LOG_C # define MP_LOG_N_C # define MP_LSHD_C # define MP_MOD_C @@ -140,12 +141,12 @@ # define S_MP_DIV_SMALL_C # define S_MP_EXPTMOD_C # define S_MP_EXPTMOD_FAST_C +# define S_MP_FLOG2_MP_WORD_C +# define S_MP_FP_LOG_C # define S_MP_GET_BIT_C # define S_MP_INVMOD_C # define S_MP_INVMOD_ODD_C -# define S_MP_LOG_C # define S_MP_LOG_2EXPT_C -# define S_MP_LOG_D_C # define S_MP_MONTGOMERY_REDUCE_COMBA_C # define S_MP_MUL_C # define S_MP_MUL_BALANCE_C @@ -480,10 +481,25 @@ # define MP_MUL_C #endif +#if defined(MP_LOG_C) +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_CMP_D_C +# define MP_CNT_LSB_C +# define MP_COUNT_BITS_C +# define MP_DIV_C +# define MP_DIV_D_C +# define MP_EXPT_N_C +# define MP_INIT_MULTI_C +# define MP_MUL_C +# define MP_MUL_D_C +# define S_MP_FP_LOG_C +#endif + #if defined(MP_LOG_N_C) -# define S_MP_LOG_2EXPT_C -# define S_MP_LOG_C -# define S_MP_LOG_D_C +# define MP_CLEAR_C +# define MP_INIT_I32_C +# define MP_LOG_C #endif #if defined(MP_LSHD_C) @@ -1046,6 +1062,19 @@ # define S_MP_MONTGOMERY_REDUCE_COMBA_C #endif +#if defined(S_MP_FLOG2_MP_WORD_C) +#endif + +#if defined(S_MP_FP_LOG_C) +# define MP_CLEAR_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_GET_I64_C +# define MP_INIT_C +# define S_MP_FLOG2_MP_WORD_C +# define S_MP_FP_LOG_FRACTION_C +#endif + #if defined(S_MP_GET_BIT_C) #endif @@ -1079,25 +1108,10 @@ # define MP_SUB_C #endif -#if defined(S_MP_LOG_C) -# define MP_CLEAR_MULTI_C -# define MP_CMP_C -# define MP_CMP_D_C -# define MP_COPY_C -# define MP_EXCH_C -# define MP_EXPT_N_C -# define MP_INIT_MULTI_C -# define MP_MUL_C -# define MP_SET_C -#endif - #if defined(S_MP_LOG_2EXPT_C) # define MP_COUNT_BITS_C #endif -#if defined(S_MP_LOG_D_C) -#endif - #if defined(S_MP_MONTGOMERY_REDUCE_COMBA_C) # define MP_CLAMP_C # define MP_CMP_MAG_C diff --git a/tommath_private.h b/tommath_private.h index 42920519c..4dbe0ef8c 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -122,6 +122,9 @@ extern void MP_FREE(void *mem, size_t size); #define MP_IS_2EXPT(x) (((x) != 0u) && (((x) & ((x) - 1u)) == 0u)) +/* TODO: same as above for bigint, merge (is it used elsewhere?) or change name */ +#define MP_IS_POWER_OF_TWO(a) (((mp_count_bits((a)) - 1) == mp_cnt_lsb((a))) ) + /* Static assertion */ #define MP_STATIC_ASSERT(msg, cond) typedef char mp_static_assert_##msg[(cond) ? 1 : -1]; @@ -132,10 +135,13 @@ extern void MP_FREE(void *mem, size_t size); #if defined(MP_16BIT) typedef uint32_t mp_word; +#define MP_WORD_SIZE 4 #elif defined(MP_64BIT) typedef unsigned long mp_word __attribute__((mode(TI))); +#define MP_WORD_SIZE 16 #else typedef uint64_t mp_word; +#define MP_WORD_SIZE 8 #endif MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) @@ -177,7 +183,7 @@ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); /* lowlevel functions, do not call! */ MP_PRIVATE bool s_mp_get_bit(const mp_int *a, int b) MP_WUR; MP_PRIVATE int s_mp_log_2expt(const mp_int *a, mp_digit base) MP_WUR; -MP_PRIVATE int s_mp_log_d(mp_digit base, mp_digit n) MP_WUR; + MP_PRIVATE mp_err s_mp_add(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_div_3(const mp_int *a, mp_int *c, mp_digit *d) MP_WUR; MP_PRIVATE mp_err s_mp_div_recursive(const mp_int *a, const mp_int *b, mp_int *q, mp_int *r) MP_WUR; @@ -187,7 +193,7 @@ MP_PRIVATE mp_err s_mp_exptmod(const mp_int *G, const mp_int *X, const mp_int *P MP_PRIVATE mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) MP_WUR; MP_PRIVATE mp_err s_mp_invmod(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_invmod_odd(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -MP_PRIVATE mp_err s_mp_log(const mp_int *a, mp_digit base, int *c) MP_WUR; + MP_PRIVATE mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) MP_WUR; MP_PRIVATE mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) MP_WUR; MP_PRIVATE mp_err s_mp_mul_balance(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; @@ -208,6 +214,17 @@ MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size); +/* Bigint version for the unexpected */ +#if ( (UINT_MAX == UINT32_MAX) && ( MP_WORD_SIZE > 4 ) ) \ + ||\ + ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) +MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_word *c) MP_WUR; +#else +MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; +#endif + + + #define MP_RADIX_MAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_radix_map[]; extern MP_PRIVATE const uint8_t s_mp_radix_map_reverse[]; From 548b1f0dec925f4ae7b0d69e57463aa24fee44a7 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 9 Apr 2023 03:18:55 +0200 Subject: [PATCH 239/304] Refactored --- libtommath_VS2008.vcproj | 4 ++ makefile | 10 +-- makefile.mingw | 10 +-- makefile.msvc | 10 +-- makefile.shared | 10 +-- makefile.unix | 10 +-- mp_log.c | 135 ++++++++++++++++----------------------- s_mp_fp_log.c | 98 ++-------------------------- s_mp_fp_log_d.c | 83 ++++++++++++++++++++++++ sources.cmake | 1 + tommath.h | 11 ++++ tommath_class.h | 22 +++++++ tommath_private.h | 11 ++-- 13 files changed, 210 insertions(+), 205 deletions(-) create mode 100644 s_mp_fp_log_d.c diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 2215683f7..3569332a3 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -840,6 +840,10 @@ RelativePath="s_mp_fp_log.c" > + + diff --git a/makefile b/makefile index 58b4c2db7..b55a3cc4c 100644 --- a/makefile +++ b/makefile @@ -45,11 +45,11 @@ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 45b4b3fb0..10923d76b 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -47,11 +47,11 @@ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index f25167663..c1f9abf46 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -43,11 +43,11 @@ mp_set_l.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj \ s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_flog2_mp_word.obj s_mp_fp_log.obj \ -s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ -s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ -s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj \ -s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj \ -s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj \ +s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj \ +s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj \ +s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ +s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 9168a48df..212c489c1 100644 --- a/makefile.shared +++ b/makefile.shared @@ -42,11 +42,11 @@ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 6eb5cf89a..4dc303b1e 100644 --- a/makefile.unix +++ b/makefile.unix @@ -48,11 +48,11 @@ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/mp_log.c b/mp_log.c index 3921d5b03..0a85b595d 100644 --- a/mp_log.c +++ b/mp_log.c @@ -3,61 +3,24 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ - #define MP_LOG2_EXPT(a,b) ((mp_count_bits((a)) - 1) / mp_cnt_lsb((b))) -/* - This functions rely on the size of mp_word being larger than INT_MAX and in case - there is a really weird architecture we try to check for it. Not a 100% reliable - test but it has a safe fallback. - */ -#if ( (UINT_MAX == UINT32_MAX) && ( MP_WORD_SIZE > 4 ) ) \ - ||\ - ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) - -mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +static mp_err s_approx_log_d(const mp_int *a, const mp_int *b, int *lb) { mp_int bn, La, Lb; - int n, fla, flb; + int n; mp_word la_word, lb_word; mp_err err; mp_ord cmp; - if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { - return MP_VAL; - } - - if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_POWER_OF_TWO(b)) { - *lb = MP_LOG2_EXPT(a, b); - return MP_OKAY; - } - - /* floor(log_2(x)) for cut-off */ - fla = mp_count_bits(a) - 1; - flb = mp_count_bits(b) - 1; - - cmp = mp_cmp(a, b); - - /* "a < b -> 0" and "(b == a) -> 1" */ - if ((cmp == MP_LT) || (cmp == MP_EQ)) { - *lb = (cmp == MP_EQ); - return MP_OKAY; - } - - /* "a < b^2 -> 1" (bit-count is sufficient, doesn't need to be exact) */ - if (((2 * flb)-1) > fla) { - *lb = 1; - return MP_OKAY; - } - if ((err = mp_init_multi(&La, &Lb, &bn, NULL)) != MP_OKAY) { return err; } /* Approximation of the individual logarithms with low precision */ - if ((err = s_mp_fp_log(a, &la_word)) != MP_OKAY) goto LTM_ERR; - if ((err = s_mp_fp_log(b, &lb_word)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_d(a, &la_word)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_d(b, &lb_word)) != MP_OKAY) goto LTM_ERR; /* Approximation of log_b(a) with low precision. */ n = (int)(((la_word - (lb_word + 1)/2) / lb_word) + 1); @@ -117,10 +80,10 @@ mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) do { if (b->used == 1) { /* These are cheaper exact divisions, but that function is not available in LTM */ - if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; } else { - if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; } n--; } while ((cmp = mp_cmp(&bn, a)) == MP_GT); @@ -134,61 +97,34 @@ mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) return err; } - -#else -/* Bigint version. A bit slower but not _that_ much */ -mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) { mp_int bn, La, Lb, t; - int n, fla, flb; + int n; mp_err err; mp_ord cmp; - if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { - return MP_VAL; - } - - if (MP_HAS(S_MP_LOG_2EXPT) && MP_IS_POWER_OF_TWO(b)) { - *lb = MP_LOG2_EXPT(a, b); - return MP_OKAY; - } - - fla = mp_count_bits(a) - 1; - flb = mp_count_bits(b) - 1; - - cmp = mp_cmp(a, b); - - if ((cmp == MP_LT) || (cmp == MP_EQ)) { - *lb = (cmp == MP_EQ); - return MP_OKAY; - } - - if ((2 * flb) > fla) { - *lb = 1; - return MP_OKAY; - } - if ((err = mp_init_multi(&La, &Lb, &bn, &t, NULL)) != MP_OKAY) { return err; } - if ((err = s_mp_fp_log(a, &La)) != MP_OKAY) goto LTM_ERR; - if ((err = s_mp_fp_log(b, &Lb)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log(a, &La)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log(b, &Lb)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_add_d(&Lb, 1u, &t)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_div_2(&t, &t)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_sub(&La, &t, &t)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_div(&t, &Lb, &t, NULL)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_add_d(&t, 1u, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add_d(&Lb, 1u, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2(&t, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_sub(&La, &t, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div(&t, &Lb, &t, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add_d(&t, 1u, &t)) != MP_OKAY) goto LTM_ERR; n = mp_get_i32(&t); if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) { if (err == MP_OVF) { n--; - if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; } else { goto LTM_ERR; } @@ -244,8 +180,45 @@ mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) mp_clear_multi(&La, &Lb, &bn, &t, NULL); return err; } -#endif +mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +{ + int fla, flb; + mp_ord cmp; + + if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { + return MP_VAL; + } + + if (MP_IS_POWER_OF_TWO(b)) { + *lb = MP_LOG2_EXPT(a, b); + return MP_OKAY; + } + + /* floor(log_2(x)) for cut-off */ + fla = mp_count_bits(a) - 1; + flb = mp_count_bits(b) - 1; + + cmp = mp_cmp(a, b); + + /* "a < b -> 0" and "(b == a) -> 1" */ + if ((cmp == MP_LT) || (cmp == MP_EQ)) { + *lb = (cmp == MP_EQ); + return MP_OKAY; + } + + /* "a < b^2 -> 1" (bit-count is sufficient, doesn't need to be exact) */ + if (((2 * flb)-1) > fla) { + *lb = 1; + return MP_OKAY; + } + + + if (MP_HAS(S_MP_LOG_D_POSSIBLE)) { + return s_approx_log_d(a, b, lb); + } + return s_approx_log(a, b, lb); +} #endif diff --git a/s_mp_fp_log.c b/s_mp_fp_log.c index e7db14aab..90a89abdf 100644 --- a/s_mp_fp_log.c +++ b/s_mp_fp_log.c @@ -3,92 +3,6 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -#define MP_PRECISION_FIXED_LOG ( (int) (((sizeof(mp_word) * CHAR_BIT) / 2) - 1)) -#define MP_UPPER_LIMIT_FIXED_LOG ( (int) ( (sizeof(mp_word) * CHAR_BIT) - 1)) - -/* Fixed point binary logarithm with small precision (half the bitsize of a mp_digit)*/ -#if ( (UINT_MAX == UINT32_MAX) && ( MP_WORD_SIZE > 4 ) ) \ - ||\ - ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) - -static mp_word s_mp_flog2_mp_word(mp_word value) -{ - mp_word r = 0u; - while ((value >>= 1) != 0u) { - r++; - } - return r; -} - -/* Fixed point bitwise logarithm base two of "x" with precision "p" */ -static mp_err s_mp_fp_log_fraction(mp_word x, int p, mp_word *c) -{ - mp_word b, L_out, L, a_bar, twoep; - int i; - - L = s_mp_flog2_mp_word(x); - - if ((L + (mp_word)p) > MP_UPPER_LIMIT_FIXED_LOG) { - return MP_VAL; - } - - a_bar = ((mp_word)p < L) ? x << (L - (mp_word)p) : x << ((mp_word)p - L); - b = (mp_word)(1u) << (p - 1); - L_out = L << p; - - twoep = (mp_word)(1u) << (p + 1); - - for (i = 0; i < p; i++) { - a_bar = (a_bar * a_bar) >> p; - if (a_bar >= twoep) { - a_bar >>= 1u; - L_out += b; - } - b >>= 1u; - } - *c = L_out; - return MP_OKAY; -} - -/* Approximate the base two logarithm of "a" */ -mp_err s_mp_fp_log(const mp_int *a, mp_word *c) -{ - mp_err err; - int la; - int prec = MP_PRECISION_FIXED_LOG; - mp_word tmp, la_word; - mp_int t; - - la = mp_count_bits(a) - 1; - - /* We don't use the whole number, just the most significant "prec" bits */ - if (la > prec) { - if ((err = mp_init(&t)) != MP_OKAY) goto LTM_ERR; - /* Get enough msb-bits for the chosen precision */ - if ((err = mp_div_2d(a, la - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; - tmp = mp_get_u64(&t); - /* Compute the low precision approximation for the fractional part */ - if ((err = s_mp_fp_log_fraction(tmp, prec, &la_word)) != MP_OKAY) goto LTM_ERR; - /* Compute the integer part and add it */ - tmp = ((mp_word)(la - prec))< prec) { - if ((err = mp_div_2d(a, fla - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2d(a, fla - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; if ((err = s_mp_fp_log_fraction(&t, prec, - &La)) != MP_OKAY) goto LTM_ERR; + &La)) != MP_OKAY) goto LTM_ERR; mp_set_i32(&t,fla - prec); - if ((err = mp_mul_2d(&t,prec, &t)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_add(&La, &t, &La)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_mul_2d(&t,prec, &t)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add(&La, &t, &La)) != MP_OKAY) goto LTM_ERR; } else { if ((err = s_mp_fp_log_fraction(a, prec, - &La)) != MP_OKAY) goto LTM_ERR; + &La)) != MP_OKAY) goto LTM_ERR; } mp_exch(&La, c); @@ -165,5 +79,5 @@ mp_err s_mp_fp_log(const mp_int *a, mp_int *c) return err; } -#endif + #endif diff --git a/s_mp_fp_log_d.c b/s_mp_fp_log_d.c new file mode 100644 index 000000000..cbe3b0728 --- /dev/null +++ b/s_mp_fp_log_d.c @@ -0,0 +1,83 @@ +#include "tommath_private.h" +#ifdef S_MP_FP_LOG_D_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +static mp_word s_mp_flog2_mp_word(mp_word value) +{ + mp_word r = 0u; + while ((value >>= 1) != 0u) { + r++; + } + return r; +} + +/* Fixed point bitwise logarithm base two of "x" with precision "p" */ +static mp_err s_mp_fp_log_fraction(mp_word x, int p, mp_word *c) +{ + mp_word b, L_out, L, a_bar, twoep; + int i; + + L = s_mp_flog2_mp_word(x); + + if ((L + (mp_word)p) > MP_UPPER_LIMIT_FIXED_LOG) { + return MP_VAL; + } + + a_bar = ((mp_word)p < L) ? x << (L - (mp_word)p) : x << ((mp_word)p - L); + b = (mp_word)(1u) << (p - 1); + L_out = L << p; + + twoep = (mp_word)(1u) << (p + 1); + + for (i = 0; i < p; i++) { + a_bar = (a_bar * a_bar) >> p; + if (a_bar >= twoep) { + a_bar >>= 1u; + L_out += b; + } + b >>= 1u; + } + *c = L_out; + return MP_OKAY; +} + +/* Approximate the base two logarithm of "a" */ +mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) +{ + mp_err err; + int la; + int prec = MP_PRECISION_FIXED_LOG; + mp_word tmp, la_word; + mp_int t; + + la = mp_count_bits(a) - 1; + + /* We don't use the whole number, just the most significant "prec" bits */ + if (la > prec) { + if ((err = mp_init(&t)) != MP_OKAY) goto LTM_ERR; + /* Get enough msb-bits for the chosen precision */ + if ((err = mp_div_2d(a, la - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; + tmp = mp_get_u64(&t); + /* Compute the low precision approximation for the fractional part */ + if ((err = s_mp_fp_log_fraction(tmp, prec, &la_word)) != MP_OKAY) goto LTM_ERR; + /* Compute the integer part and add it */ + tmp = ((mp_word)(la - prec))< 4)) \ + || ((UINT_MAX == UINT16_MAX) && (MP_WORD_SIZE > 2)) +#define S_MP_FP_LOG_D_POSSIBLE_C +#endif + /* Integer logarithm to integer base */ mp_err mp_log_n(const mp_int *a, int base, int *c) MP_WUR; diff --git a/tommath_class.h b/tommath_class.h index 8aaa94d20..e2c261457 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -143,6 +143,7 @@ # define S_MP_EXPTMOD_FAST_C # define S_MP_FLOG2_MP_WORD_C # define S_MP_FP_LOG_C +# define S_MP_FP_LOG_D_C # define S_MP_GET_BIT_C # define S_MP_INVMOD_C # define S_MP_INVMOD_ODD_C @@ -482,18 +483,23 @@ #endif #if defined(MP_LOG_C) +# define MP_ADD_D_C # define MP_CLEAR_MULTI_C # define MP_CMP_C # define MP_CMP_D_C # define MP_CNT_LSB_C # define MP_COUNT_BITS_C +# define MP_DIV_2_C # define MP_DIV_C # define MP_DIV_D_C # define MP_EXPT_N_C +# define MP_GET_I32_C # define MP_INIT_MULTI_C # define MP_MUL_C # define MP_MUL_D_C +# define MP_SUB_C # define S_MP_FP_LOG_C +# define S_MP_FP_LOG_D_C #endif #if defined(MP_LOG_N_C) @@ -1066,6 +1072,22 @@ #endif #if defined(S_MP_FP_LOG_C) +# define MP_2EXPT_C +# define MP_ADD_C +# define MP_CLEAR_MULTI_C +# define MP_CMP_C +# define MP_COUNT_BITS_C +# define MP_DIV_2D_C +# define MP_DIV_2_C +# define MP_EXCH_C +# define MP_INIT_MULTI_C +# define MP_MUL_2D_C +# define MP_MUL_C +# define MP_SET_I32_C +# define S_MP_FP_LOG_FRACTION_C +#endif + +#if defined(S_MP_FP_LOG_D_C) # define MP_CLEAR_C # define MP_COUNT_BITS_C # define MP_DIV_2D_C diff --git a/tommath_private.h b/tommath_private.h index 4dbe0ef8c..0915464da 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -214,14 +214,11 @@ MP_PRIVATE void s_mp_zero_buf(void *mem, size_t size); MP_PRIVATE void s_mp_zero_digs(mp_digit *d, int digits); MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, size_t *size); -/* Bigint version for the unexpected */ -#if ( (UINT_MAX == UINT32_MAX) && ( MP_WORD_SIZE > 4 ) ) \ - ||\ - ( (UINT_MAX == UINT16_MAX) && ( MP_WORD_SIZE > 2 ) ) -MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_word *c) MP_WUR; -#else +#define MP_PRECISION_FIXED_LOG ( (int) (((sizeof(mp_word) * CHAR_BIT) / 2) - 1)) +#define MP_UPPER_LIMIT_FIXED_LOG ( (int) ( (sizeof(mp_word) * CHAR_BIT) - 1)) MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; -#endif +MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; + From 8bbb11a69724371af431f01c7715500ee5d1761e Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 9 Apr 2023 05:44:41 +0200 Subject: [PATCH 240/304] Set outlines fo the new tests --- demo/test.c | 31 +++++++++++++++++++++++++++++-- 1 file changed, 29 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 5a7b5db9f..9d5ea35a4 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1395,8 +1395,7 @@ static int test_mp_reduce_2k_l(void) return EXIT_SUCCESS; # endif /* LTM_DEMO_TEST_REDUCE_2K_L */ } -/* stripped down version of mp_radix_size. The faster version can be off by up t -o +3 */ +/* stripped down version of mp_radix_size. The faster version can be off by up to +3 */ static mp_err s_rs(const mp_int *a, int radix, int *size) { mp_err res; @@ -1425,6 +1424,32 @@ static mp_err s_rs(const mp_int *a, int radix, int *size) *size = digs + 1; return MP_OKAY; } + +/* The internal functions that compute the logarithm base two with MP_PRECISION_FIXED_LOG */ +static int test_s_mp_fp_log(void) +{ + // s_mp_fp_log(const mp_int *a, mp_int *c) + + + /* + "a" some large constants. + No random values because it would be quite involved to check the results + + Some checks are made earlier so no tests with "a" a power of two are needed. + */ + + + return MP_OKAY; +} +static int test_s_mp_fp_log_d(void) +{ + // s_mp_fp_log_d(const mp_int *a, mp_word *c) + /* See test_s_mp_fp_log() for details */ + return MP_OKAY; +} + + +/* TODO: Cleanup (not everything is still needed) and construct (find) testvalues for each correction loop */ static int test_mp_log_n(void) { mp_int a; @@ -2436,6 +2461,8 @@ static int unit_tests(int argc, char **argv) T1(mp_get_u32, MP_GET_I32), T1(mp_get_u64, MP_GET_I64), T1(mp_get_ul, MP_GET_L), + T1(s_mp_fp_log_d, S_MP_FP_LOG_D), + T1(s_mp_fp_log, S_MP_FP_LOG), T1(mp_log_n, MP_LOG_N), T1(mp_log, MP_LOG), T1(mp_incr, MP_ADD_D), From 6bc7d154500a70faa6127a01be2e0fd5cc0f0ab1 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Sun, 9 Apr 2023 06:12:35 +0200 Subject: [PATCH 241/304] corrected formatting of comment --- demo/test.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 9d5ea35a4..b124b7cc4 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1428,7 +1428,7 @@ static mp_err s_rs(const mp_int *a, int radix, int *size) /* The internal functions that compute the logarithm base two with MP_PRECISION_FIXED_LOG */ static int test_s_mp_fp_log(void) { - // s_mp_fp_log(const mp_int *a, mp_int *c) + /* s_mp_fp_log(const mp_int *a, mp_int *c) */ /* @@ -1443,7 +1443,7 @@ static int test_s_mp_fp_log(void) } static int test_s_mp_fp_log_d(void) { - // s_mp_fp_log_d(const mp_int *a, mp_word *c) + /* s_mp_fp_log_d(const mp_int *a, mp_word *c) */ /* See test_s_mp_fp_log() for details */ return MP_OKAY; } From 563af5fb12495563f56a3f87723f8ca9043b750f Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 9 Apr 2023 10:18:41 +0200 Subject: [PATCH 242/304] also refactor 'check result' part into `mp_log()` This code was duplicated as well. Signed-off-by: Steffen Jaeckel --- mp_log.c | 204 ++++++++++++++++++++----------------------------------- 1 file changed, 75 insertions(+), 129 deletions(-) diff --git a/mp_log.c b/mp_log.c index 0a85b595d..38aa9dee3 100644 --- a/mp_log.c +++ b/mp_log.c @@ -7,106 +7,28 @@ static mp_err s_approx_log_d(const mp_int *a, const mp_int *b, int *lb) { - mp_int bn, La, Lb; - int n; - mp_word la_word, lb_word; - + mp_word La, Lb; mp_err err; - mp_ord cmp; - - if ((err = mp_init_multi(&La, &Lb, &bn, NULL)) != MP_OKAY) { - return err; - } /* Approximation of the individual logarithms with low precision */ - if ((err = s_mp_fp_log_d(a, &la_word)) != MP_OKAY) goto LTM_ERR; - if ((err = s_mp_fp_log_d(b, &lb_word)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_d(a, &La)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_d(b, &Lb)) != MP_OKAY) goto LTM_ERR; /* Approximation of log_b(a) with low precision. */ - n = (int)(((la_word - (lb_word + 1)/2) / lb_word) + 1); + *lb = (int)(((La - (Lb + 1)/2) / Lb) + 1); /* TODO: just floor it instead? Multiplication is cheaper than division. */ - /* n = (int)(la_word / lb_word); */ - - /* Check result. Result is wrong by 2(two) at most. */ - if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) { - /* If the approximation overshot we can give it another try */ - if (err == MP_OVF) { - n--; - /* But only one */ - if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; - } else { - goto LTM_ERR; - } - } - - cmp = mp_cmp(&bn, a); - - /* The rare case of a perfect power makes a perfect shortcut, too. */ - if (cmp == MP_EQ) { - *lb = n; - goto LTM_OUT; - } - - /* We have to make at least one multiplication because it could still be a perfect power. */ - if (cmp == MP_LT) { - do { - /* Full big-integer operations are to be avoided if possible */ - if (b->used == 1) { - if ((err = mp_mul_d(&bn, b->dp[0], &bn)) != MP_OKAY) { - if (err == MP_OVF) { - goto LTM_OUT; - } - goto LTM_ERR; - } - } else { - if ((err = mp_mul(&bn, b, &bn)) != MP_OKAY) { - if (err == MP_OVF) { - goto LTM_OUT; - } - goto LTM_ERR; - } - } - n++; - } while ((cmp = mp_cmp(&bn, a)) == MP_LT); - /* Overshot, take it back. */ - if (cmp == MP_GT) { - n--; - } - goto LTM_OUT; - } - - /* But it can overestimate, too, for example if "a" is closely below some "b^k" */ - if (cmp == MP_GT) { - do { - if (b->used == 1) { - /* These are cheaper exact divisions, but that function is not available in LTM */ - if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; - - } else { - if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; - } - n--; - } while ((cmp = mp_cmp(&bn, a)) == MP_GT); - } - -LTM_OUT: - *lb = n; + /* *lb = (int)(la_word / lb_word); */ err = MP_OKAY; LTM_ERR: - mp_clear_multi(&La, &Lb, &bn, NULL); return err; } static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) { - mp_int bn, La, Lb, t; - - int n; - + mp_int La, Lb, t; mp_err err; - mp_ord cmp; - if ((err = mp_init_multi(&La, &Lb, &bn, &t, NULL)) != MP_OKAY) { + if ((err = mp_init_multi(&La, &Lb, &t, NULL)) != MP_OKAY) { return err; } @@ -119,25 +41,86 @@ static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) if ((err = mp_div(&t, &Lb, &t, NULL)) != MP_OKAY) goto LTM_ERR; if ((err = mp_add_d(&t, 1u, &t)) != MP_OKAY) goto LTM_ERR; - n = mp_get_i32(&t); + *lb = mp_get_i32(&t); + err = MP_OKAY; +LTM_ERR: + mp_clear_multi(&t, &Lb, &La, NULL); + return err; +} + + +mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) +{ + mp_int bn; + int n, fla, flb; + mp_err err; + mp_ord cmp; + + if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { + return MP_VAL; + } + + if (MP_IS_POWER_OF_TWO(b)) { + *lb = MP_LOG2_EXPT(a, b); + return MP_OKAY; + } + + /* floor(log_2(x)) for cut-off */ + fla = mp_count_bits(a) - 1; + flb = mp_count_bits(b) - 1; + + cmp = mp_cmp(a, b); + + /* "a < b -> 0" and "(b == a) -> 1" */ + if ((cmp == MP_LT) || (cmp == MP_EQ)) { + *lb = (cmp == MP_EQ); + return MP_OKAY; + } + + /* "a < b^2 -> 1" (bit-count is sufficient, doesn't need to be exact) */ + if (((2 * flb)-1) > fla) { + *lb = 1; + return MP_OKAY; + } + + + if (MP_HAS(S_MP_LOG_D_POSSIBLE)) { + err = s_approx_log_d(a, b, &n); + } else { + err = s_approx_log(a, b, &n); + } + if (err != MP_OKAY) { + return err; + } + if ((err = mp_init(&bn)) != MP_OKAY) { + return err; + } + + /* Check result. Result is wrong by 2(two) at most. */ if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) { + /* If the approximation overshot we can give it another try */ if (err == MP_OVF) { n--; + /* But only one */ if ((err = mp_expt_n(b, n, &bn)) != MP_OKAY) goto LTM_ERR; } else { goto LTM_ERR; } } + cmp = mp_cmp(&bn, a); + /* The rare case of a perfect power makes a perfect shortcut, too. */ if (cmp == MP_EQ) { *lb = n; goto LTM_OUT; } + /* We have to make at least one multiplication because it could still be a perfect power. */ if (cmp == MP_LT) { do { + /* Full big-integer operations are to be avoided if possible */ if (b->used == 1) { if ((err = mp_mul_d(&bn, b->dp[0], &bn)) != MP_OKAY) { if (err == MP_OVF) { @@ -155,19 +138,22 @@ static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) } n++; } while ((cmp = mp_cmp(&bn, a)) == MP_LT); + /* Overshot, take it back. */ if (cmp == MP_GT) { n--; } goto LTM_OUT; } + /* But it can overestimate, too, for example if "a" is closely below some "b^k" */ if (cmp == MP_GT) { do { if (b->used == 1) { - if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; + /* These are cheaper exact divisions, but that function is not available in LTM */ + if ((err = mp_div_d(&bn, b->dp[0], &bn, NULL)) != MP_OKAY) goto LTM_ERR; } else { - if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div(&bn, b, &bn, NULL)) != MP_OKAY) goto LTM_ERR; } n--; } while ((cmp = mp_cmp(&bn, a)) == MP_GT); @@ -177,48 +163,8 @@ static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) *lb = n; err = MP_OKAY; LTM_ERR: - mp_clear_multi(&La, &Lb, &bn, &t, NULL); + mp_clear(&bn); return err; } - -mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) -{ - int fla, flb; - mp_ord cmp; - - if (mp_isneg(a) || mp_iszero(a) || (mp_cmp_d(b, 2u) == MP_LT)) { - return MP_VAL; - } - - if (MP_IS_POWER_OF_TWO(b)) { - *lb = MP_LOG2_EXPT(a, b); - return MP_OKAY; - } - - /* floor(log_2(x)) for cut-off */ - fla = mp_count_bits(a) - 1; - flb = mp_count_bits(b) - 1; - - cmp = mp_cmp(a, b); - - /* "a < b -> 0" and "(b == a) -> 1" */ - if ((cmp == MP_LT) || (cmp == MP_EQ)) { - *lb = (cmp == MP_EQ); - return MP_OKAY; - } - - /* "a < b^2 -> 1" (bit-count is sufficient, doesn't need to be exact) */ - if (((2 * flb)-1) > fla) { - *lb = 1; - return MP_OKAY; - } - - - if (MP_HAS(S_MP_LOG_D_POSSIBLE)) { - return s_approx_log_d(a, b, lb); - } - return s_approx_log(a, b, lb); -} - #endif From a3e404c5815ab1df160f0f0faa00a86cf0c8273f Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 9 Apr 2023 10:20:27 +0200 Subject: [PATCH 243/304] remove s_flog2_mp_word.c it's not used Signed-off-by: Steffen Jaeckel --- s_mp_flog2_mp_word.c | 15 --------------- 1 file changed, 15 deletions(-) delete mode 100644 s_mp_flog2_mp_word.c diff --git a/s_mp_flog2_mp_word.c b/s_mp_flog2_mp_word.c deleted file mode 100644 index 24b21e19f..000000000 --- a/s_mp_flog2_mp_word.c +++ /dev/null @@ -1,15 +0,0 @@ -#include "tommath_private.h" -#ifdef S_FLOG2_MP_WORD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -mp_word s_flog2_mp_word(mp_word value) -{ - mp_word r = 0u; - while ((value >>= 1) != 0u) { - r++; - } - return r; -} - -#endif From 6da2101cafd1c2e640df2c459b2971fcdfa8246b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 9 Apr 2023 10:20:48 +0200 Subject: [PATCH 244/304] update makefiles Signed-off-by: Steffen Jaeckel --- libtommath_VS2008.vcproj | 4 ---- makefile | 12 ++++++------ makefile.mingw | 12 ++++++------ makefile.msvc | 12 ++++++------ makefile.shared | 12 ++++++------ makefile.unix | 12 ++++++------ sources.cmake | 1 - tommath_class.h | 6 ++---- 8 files changed, 32 insertions(+), 39 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 3569332a3..13158a09d 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -832,10 +832,6 @@ RelativePath="s_mp_exptmod_fast.c" > - - diff --git a/makefile b/makefile index b55a3cc4c..e92e0e66a 100644 --- a/makefile +++ b/makefile @@ -44,12 +44,12 @@ mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ +s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 10923d76b..532747be0 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -46,12 +46,12 @@ mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ +s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index c1f9abf46..5d1285490 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -42,12 +42,12 @@ mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set mp_set_l.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj \ mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj \ -s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_flog2_mp_word.obj s_mp_fp_log.obj \ -s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj \ -s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj \ -s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj \ -s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ -s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_fp_log.obj s_mp_fp_log_d.obj \ +s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ +s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ +s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj \ +s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj \ +s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 212c489c1..fe077fc8b 100644 --- a/makefile.shared +++ b/makefile.shared @@ -41,12 +41,12 @@ mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ +s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 4dc303b1e..9fe939f04 100644 --- a/makefile.unix +++ b/makefile.unix @@ -47,12 +47,12 @@ mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_flog2_mp_word.o s_mp_fp_log.o \ -s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ -s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ -s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ +s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ +s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ +s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ +s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ +s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/sources.cmake b/sources.cmake index aaee13fc3..bbb2aeab6 100644 --- a/sources.cmake +++ b/sources.cmake @@ -132,7 +132,6 @@ s_mp_div_school.c s_mp_div_small.c s_mp_exptmod.c s_mp_exptmod_fast.c -s_mp_flog2_mp_word.c s_mp_fp_log.c s_mp_fp_log_d.c s_mp_get_bit.c diff --git a/tommath_class.h b/tommath_class.h index e2c261457..911cdcb2d 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -141,7 +141,6 @@ # define S_MP_DIV_SMALL_C # define S_MP_EXPTMOD_C # define S_MP_EXPTMOD_FAST_C -# define S_MP_FLOG2_MP_WORD_C # define S_MP_FP_LOG_C # define S_MP_FP_LOG_D_C # define S_MP_GET_BIT_C @@ -484,6 +483,7 @@ #if defined(MP_LOG_C) # define MP_ADD_D_C +# define MP_CLEAR_C # define MP_CLEAR_MULTI_C # define MP_CMP_C # define MP_CMP_D_C @@ -494,6 +494,7 @@ # define MP_DIV_D_C # define MP_EXPT_N_C # define MP_GET_I32_C +# define MP_INIT_C # define MP_INIT_MULTI_C # define MP_MUL_C # define MP_MUL_D_C @@ -1068,9 +1069,6 @@ # define S_MP_MONTGOMERY_REDUCE_COMBA_C #endif -#if defined(S_MP_FLOG2_MP_WORD_C) -#endif - #if defined(S_MP_FP_LOG_C) # define MP_2EXPT_C # define MP_ADD_C From ac3df4f2a928d33ac27de60ef6ddb9b503f4ba4c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 9 Apr 2023 11:04:04 +0200 Subject: [PATCH 245/304] move define to tommath_private.h it's not required in the public header Signed-off-by: Steffen Jaeckel --- tommath.h | 11 ----------- tommath_private.h | 10 ++++++++++ 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/tommath.h b/tommath.h index 12de40cab..7994b6e1a 100644 --- a/tommath.h +++ b/tommath.h @@ -413,17 +413,6 @@ mp_err mp_exteuclid(const mp_int *a, const mp_int *b, mp_int *U1, mp_int *U2, mp /* c = [a, b] or (a*b)/(a, b) */ mp_err mp_lcm(const mp_int *a, const mp_int *b, mp_int *c) MP_WUR; -/* - The mp_log functions rely on the size of mp_word being larger than INT_MAX and in case - there is a really weird architecture we try to check for it. Not a 100% reliable - test but it has a safe fallback. - */ - -#if ((UINT_MAX == UINT32_MAX) && (MP_WORD_SIZE > 4)) \ - || ((UINT_MAX == UINT16_MAX) && (MP_WORD_SIZE > 2)) -#define S_MP_FP_LOG_D_POSSIBLE_C -#endif - /* Integer logarithm to integer base */ mp_err mp_log_n(const mp_int *a, int base, int *c) MP_WUR; diff --git a/tommath_private.h b/tommath_private.h index 0915464da..9eacbdd89 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -177,6 +177,16 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT #define MP_HAS_SET_DOUBLE #endif +/* + The mp_log functions rely on the size of mp_word being larger than INT_MAX and in case + there is a really weird architecture we try to check for it. Not a 100% reliable + test but it has a safe fallback. + */ +#if ((UINT_MAX == UINT32_MAX) && (MP_WORD_SIZE > 4)) \ + || ((UINT_MAX == UINT16_MAX) && (MP_WORD_SIZE > 2)) +#define S_MP_FP_LOG_D_POSSIBLE_C +#endif + /* random number source */ extern MP_PRIVATE mp_err(*s_mp_rand_source)(void *out, size_t size); From 8781b2415c46c4d4b9d15fb47f0a7a48613253bc Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 10 Apr 2023 03:36:45 +0200 Subject: [PATCH 246/304] make both `mp_log()` variants testable and add CI jobs --- .github/workflows/main.yml | 8 +++++ demo/test.c | 65 +++++++++++++++++--------------------- mp_log.c | 8 ++--- tommath_private.h | 6 ++-- 4 files changed, 43 insertions(+), 44 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 13f2039f5..b42462b13 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -43,10 +43,14 @@ jobs: - { BUILDOPTIONS: '--symbols', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libtool-bin' } # Run always with valgrind (no sanitizer, but debug info) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --with-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # Alternative big-int version of mp_log(_n) + - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --cflags=-DS_MP_WORD_TOO_SMALL_C="" --with-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } # Shared library build - { BUILDOPTIONS: '--with-cc=gcc --make-option=-f --make-option=makefile.shared', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: 'libtool-bin' } # GCC for the 32-bit architecture (no valgrind) - { BUILDOPTIONS: '--with-cc=gcc --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } + # Alternative big-int version of mp_log(_n) for the 32-bit architecture (no valgrind) + - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --cflags=-DS_MP_WORD_TOO_SMALL_C="" ', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } # clang for the 32-bit architecture (no valgrind) - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } # RSA superclass with tests (no sanitizer, but debug info) @@ -103,6 +107,10 @@ jobs: # but testing all three in one run took to long and timed out. - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # Alternative big-int version of mp_log(_n) + - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_16BIT --cflags=-DS_MP_WORD_TOO_SMALL_C="" --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + - { BUILDOPTIONS: '--with-cc=gcc --cflags=-DMP_32BIT --cflags=-DS_MP_WORD_TOO_SMALL_C="" --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # clang for the x86-64 architecture with restricted limb sizes - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } diff --git a/demo/test.c b/demo/test.c index b124b7cc4..939fcc0ed 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1425,38 +1425,20 @@ static mp_err s_rs(const mp_int *a, int radix, int *size) return MP_OKAY; } -/* The internal functions that compute the logarithm base two with MP_PRECISION_FIXED_LOG */ -static int test_s_mp_fp_log(void) -{ - /* s_mp_fp_log(const mp_int *a, mp_int *c) */ - - - /* - "a" some large constants. - No random values because it would be quite involved to check the results - - Some checks are made earlier so no tests with "a" a power of two are needed. - */ - - - return MP_OKAY; -} -static int test_s_mp_fp_log_d(void) -{ - /* s_mp_fp_log_d(const mp_int *a, mp_word *c) */ - /* See test_s_mp_fp_log() for details */ - return MP_OKAY; -} - -/* TODO: Cleanup (not everything is still needed) and construct (find) testvalues for each correction loop */ static int test_mp_log_n(void) { mp_int a; mp_digit d; - int base, lb, size; + int base, lb, size, i; const int max_base = MP_MIN(INT_MAX, MP_DIGIT_MAX); + if (MP_HAS(S_MP_WORD_TOO_SMALL)) { + fprintf(stderr, "Testing mp_log_n with restricted size of mp_word.\n"); + } else { + fprintf(stderr, "Testing mp_log_n with normal size of mp_word.\n"); + } + DOR(mp_init(&a)); /* @@ -1509,25 +1491,32 @@ static int test_mp_log_n(void) DO(mp_rand(&a, 10)); for (base = 2; base < 65; base++) { DO(mp_log_n(&a, base, &lb)); - DO(s_rs(&a,(int)base, &size)); + DO(s_rs(&a,base, &size)); /* radix_size includes the memory needed for '\0', too*/ size -= 2; EXPECT(lb == size); } /* - bases 2..64 with "a" a random small constant to - test the part of mp_ilogb that uses native types. + bases 2..64 with "a" a small constant and a small exponent "n" to test + in the range a^n - 10 .. a^n + 10. That will check the correction loops + and the test for perfect power. + For simplicity a = base and n = 23 (64^23 == 2^138 > 2^128) */ - DO(mp_rand(&a, 1)); for (base = 2; base < 65; base++) { - DO(mp_log_n(&a, base, &lb)); - DO(s_rs(&a,(int)base, &size)); - size -= 2; - EXPECT(lb == size); + mp_set(&a,(mp_digit)base); + DO(mp_expt_n(&a, 23, &a)); + DO(mp_sub_d(&a, 10u, &a)); + for (i = 0; i < 20; i++) { + DO(mp_log_n(&a, base, &lb)); + DO(s_rs(&a, base, &size)); + size -= 2; + EXPECT(lb == size); + DO(mp_add_d(&a, 1u, &a)); + } } - /*Test upper edgecase with base UINT32_MAX and number (UINT32_MAX/2)*UINT32_MAX^10 */ + /*Test base upper edgecase with base = UINT32_MAX and number = (UINT32_MAX/2)*UINT32_MAX^10 */ mp_set(&a, max_base); DO(mp_expt_n(&a, 10uL, &a)); DO(mp_add_d(&a, max_base / 2, &a)); @@ -1546,6 +1535,12 @@ static int test_mp_log(void) mp_int a, base, bn, t; int lb, lb2, i, j; + if (MP_HAS(S_MP_WORD_TOO_SMALL)) { + fprintf(stdout, "Testing mp_log with restricted size of mp_word.\n"); + } else { + fprintf(stdout, "Testing mp_log with normal size of mp_word.\n"); + } + DOR(mp_init_multi(&a, &base, &bn, &t, NULL)); /* @@ -2461,8 +2456,6 @@ static int unit_tests(int argc, char **argv) T1(mp_get_u32, MP_GET_I32), T1(mp_get_u64, MP_GET_I64), T1(mp_get_ul, MP_GET_L), - T1(s_mp_fp_log_d, S_MP_FP_LOG_D), - T1(s_mp_fp_log, S_MP_FP_LOG), T1(mp_log_n, MP_LOG_N), T1(mp_log, MP_LOG), T1(mp_incr, MP_ADD_D), diff --git a/mp_log.c b/mp_log.c index 38aa9dee3..0d5d893ad 100644 --- a/mp_log.c +++ b/mp_log.c @@ -48,7 +48,6 @@ static mp_err s_approx_log(const mp_int *a, const mp_int *b, int *lb) return err; } - mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) { mp_int bn; @@ -83,11 +82,10 @@ mp_err mp_log(const mp_int *a, const mp_int *b, int *lb) return MP_OKAY; } - - if (MP_HAS(S_MP_LOG_D_POSSIBLE)) { - err = s_approx_log_d(a, b, &n); - } else { + if (MP_HAS(S_MP_WORD_TOO_SMALL)) { err = s_approx_log(a, b, &n); + } else { + err = s_approx_log_d(a, b, &n); } if (err != MP_OKAY) { return err; diff --git a/tommath_private.h b/tommath_private.h index 9eacbdd89..d88d263f7 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -182,9 +182,9 @@ MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT there is a really weird architecture we try to check for it. Not a 100% reliable test but it has a safe fallback. */ -#if ((UINT_MAX == UINT32_MAX) && (MP_WORD_SIZE > 4)) \ - || ((UINT_MAX == UINT16_MAX) && (MP_WORD_SIZE > 2)) -#define S_MP_FP_LOG_D_POSSIBLE_C +#if !(((UINT_MAX == UINT32_MAX) && (MP_WORD_SIZE > 4)) \ + || ((UINT_MAX == UINT16_MAX) && (MP_WORD_SIZE > 2))) +#define S_MP_WORD_TOO_SMALL_C #endif /* random number source */ From 02cf798a6910ef2460936c6c032358b6f7699ce0 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 11 Apr 2023 14:53:05 +0200 Subject: [PATCH 247/304] add CI job that tests whether the amalgamated library builds Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 8 ++++++++ makefile | 4 +++- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index b42462b13..457216a7e 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -155,6 +155,14 @@ jobs: cat valgrind_test.log || true cat gcc_errors_*.log || true + amalgam: + runs-on: ubuntu-22.04 + steps: + - uses: actions/checkout@v2 + - name: install dependencies + run: | + make amalgamated_timing + CMake: runs-on: ${{ matrix.os }} strategy: diff --git a/makefile b/makefile index e92e0e66a..b2cb16a3e 100644 --- a/makefile +++ b/makefile @@ -69,9 +69,11 @@ profiled: make CFLAGS="$(CFLAGS) -fbranch-probabilities" #make a single object profiled library -profiled_single: pre_gen +amalgamated_timing: pre_gen $(CC) $(LTM_CFLAGS) -fprofile-arcs -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o $(CC) $(LTM_CFLAGS) -DMP_VERSION=\"before\" demo/timing.c tommath_amalgam.o -lgcov -o timing + +profiled_single: amalgamated_timing ./timing rm -f *.o timing $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o From 66a4a245c93d679e024f84b827643a6943a80d5e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 11 Apr 2023 14:53:43 +0200 Subject: [PATCH 248/304] fix build of amalgamated library Signed-off-by: Steffen Jaeckel --- s_mp_fp_log_d.c | 10 +++++----- tommath_class.h | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/s_mp_fp_log_d.c b/s_mp_fp_log_d.c index cbe3b0728..71d82dc41 100644 --- a/s_mp_fp_log_d.c +++ b/s_mp_fp_log_d.c @@ -3,7 +3,7 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -static mp_word s_mp_flog2_mp_word(mp_word value) +static mp_word s_mp_flog2_mp_word_d(mp_word value) { mp_word r = 0u; while ((value >>= 1) != 0u) { @@ -13,12 +13,12 @@ static mp_word s_mp_flog2_mp_word(mp_word value) } /* Fixed point bitwise logarithm base two of "x" with precision "p" */ -static mp_err s_mp_fp_log_fraction(mp_word x, int p, mp_word *c) +static mp_err s_mp_fp_log_fraction_d(mp_word x, int p, mp_word *c) { mp_word b, L_out, L, a_bar, twoep; int i; - L = s_mp_flog2_mp_word(x); + L = s_mp_flog2_mp_word_d(x); if ((L + (mp_word)p) > MP_UPPER_LIMIT_FIXED_LOG) { return MP_VAL; @@ -60,14 +60,14 @@ mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) if ((err = mp_div_2d(a, la - prec, &t, NULL)) != MP_OKAY) goto LTM_ERR; tmp = mp_get_u64(&t); /* Compute the low precision approximation for the fractional part */ - if ((err = s_mp_fp_log_fraction(tmp, prec, &la_word)) != MP_OKAY) goto LTM_ERR; + if ((err = s_mp_fp_log_fraction_d(tmp, prec, &la_word)) != MP_OKAY) goto LTM_ERR; /* Compute the integer part and add it */ tmp = ((mp_word)(la - prec))< Date: Tue, 30 May 2023 02:59:27 +0200 Subject: [PATCH 249/304] Added checks for PRNG generated values --- demo/test.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index 939fcc0ed..ebf46198a 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1573,9 +1573,13 @@ static int test_mp_log(void) /* Random a, base */ for (i = 1; i < 256; i++) { - DO(mp_rand(&a, i)); + do { + DO(mp_rand(&a, i)); + } while (mp_cmp_d(&a,2u) == MP_LT); for (j = 1; j < ((i/2)+1); j++) { - DO(mp_rand(&base, j)); + do { + DO(mp_rand(&base, j)); + } while (mp_cmp_d(&base,2u) == MP_LT); DO(mp_log(&a, &base, &lb)); DO(mp_expt_n(&base, lb, &bn)); /* "bn" must be smaller than or equal to "a" at this point. */ From 40d97bebc243fdb3bd9db1d6163c5ddc42636b16 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 31 May 2023 15:06:52 +0200 Subject: [PATCH 250/304] Addition of PRIoXX to make c89 --- makefile | 4 ++-- tommath_c89.h | 1 + 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/makefile b/makefile index b2cb16a3e..25eda9c3b 100644 --- a/makefile +++ b/makefile @@ -171,7 +171,7 @@ c89: -e 's/INT64_MAX/(mp_i64)(((mp_u64)1<<63)-1)/g' \ -e 's/INT64_MIN/(mp_i64)((mp_u64)1<<63)/g' \ -e 's/SIZE_MAX/((size_t)-1)/g' \ - -e 's/\(PRI[iux]64\)/MP_\1/g' \ + -e 's/\(PRI[ioux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ -e 's/int\([0-9][0-9]*\)_t/mp_i\1/g' \ -e 's/__func__/MP_FUNCTION_NAME/g' \ @@ -195,7 +195,7 @@ c99: -e 's/(mp_i64)((mp_u64)1<<63)/INT64_MIN/g' \ -e 's/(mp_i64)(((mp_u64)1<<63)-1)/INT64_MAX/g' \ -e 's/((size_t)-1)/SIZE_MAX/g' \ - -e 's/MP_\(PRI[iux]64\)/\1/g' \ + -e 's/MP_\(PRI[ioux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ -e 's/mp_i\([0-9][0-9]*\)/int\1_t/g' \ -e 's/MP_FUNCTION_NAME/__func__/g' \ diff --git a/tommath_c89.h b/tommath_c89.h index e7b87f105..49400a131 100644 --- a/tommath_c89.h +++ b/tommath_c89.h @@ -36,5 +36,6 @@ typedef __UINT64_TYPE__ mp_u64; #define MP_PRIi64 MP_PRI64_PREFIX "i" #define MP_PRIu64 MP_PRI64_PREFIX "u" #define MP_PRIx64 MP_PRI64_PREFIX "x" +#define MP_PRIo64 MP_PRI64_PREFIX "o" #define MP_FUNCTION_NAME __func__ From 13e6bafabcf031abd75f6b5a332162a90b8c6367 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Mon, 29 May 2023 00:15:56 +0200 Subject: [PATCH 251/304] made MP_31BIT working --- demo/test.c | 6 ++++++ tommath.h | 2 +- tommath_private.h | 5 +---- 3 files changed, 8 insertions(+), 5 deletions(-) diff --git a/demo/test.c b/demo/test.c index ebf46198a..f86853644 100644 --- a/demo/test.c +++ b/demo/test.c @@ -180,6 +180,12 @@ static int test_mp_hash(void) 0xabae35c7872c107d, 0xfec74888bcef5fcd, 0x27ba96030abceda5 +#elif (MP_DIGIT_BIT == 31) + 0xaf63bd4c8601b7df, + 0xec1be1c4749a7b86, + 0x138ac13639116f2e, + 0xdd317b32ac9dd90f, + 0x6f87eaac03140738 #else 0xaf63bd4c8601b7df, 0x7e868fbf541faf44, diff --git a/tommath.h b/tommath.h index 7994b6e1a..33aa5dfd7 100644 --- a/tommath.h +++ b/tommath.h @@ -55,7 +55,7 @@ extern "C" { #if defined(MP_16BIT) typedef uint16_t mp_digit; # define MP_DIGIT_BIT 15 -#elif defined(MP_64BIT) +#elif ((defined (MP_64BIT)) && !(defined(MP_31BIT)) ) typedef uint64_t mp_digit; # define MP_DIGIT_BIT 60 #else diff --git a/tommath_private.h b/tommath_private.h index d88d263f7..d319a1db0 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -136,7 +136,7 @@ extern void MP_FREE(void *mem, size_t size); #if defined(MP_16BIT) typedef uint32_t mp_word; #define MP_WORD_SIZE 4 -#elif defined(MP_64BIT) +#elif ((defined (MP_64BIT)) && !(defined(MP_31BIT)) ) typedef unsigned long mp_word __attribute__((mode(TI))); #define MP_WORD_SIZE 16 #else @@ -229,9 +229,6 @@ MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; - - - #define MP_RADIX_MAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_radix_map[]; extern MP_PRIVATE const uint8_t s_mp_radix_map_reverse[]; From 2a5e0b629ce53ba7e8f23338c41b8da20f26b741 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 15 Jun 2023 16:26:07 +0200 Subject: [PATCH 252/304] add deploy script Let's add a manual step to deploy to packagecloud. Signed-off-by: Steffen Jaeckel --- .github/workflows/deploy.yml | 47 ++++++++++++++++++++++++++++++++++++ 1 file changed, 47 insertions(+) create mode 100644 .github/workflows/deploy.yml diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml new file mode 100644 index 000000000..3789236e9 --- /dev/null +++ b/.github/workflows/deploy.yml @@ -0,0 +1,47 @@ +############################################################################# +# # +# Packagecloud deployment via GH actions for LibTomMath # +# (https://github.com/libtom/libtommath.git) # +# # +############################################################################# + +name: Deploy + +on: + workflow_dispatch + +jobs: + deploy-to-packagecloud: + runs-on: ${{ matrix.os }} + strategy: + matrix: + os: [ ubuntu-20.04, ubuntu-22.04 ] + steps: + - uses: actions/checkout@v2 + - name: set Ubuntu codename + run: | + echo "ubuntu_codename="$(lsb_release -sc) >> "$GITHUB_ENV" + - name: install dependencies + run: | + wget -O - https://apt.kitware.com/keys/kitware-archive-latest.asc 2>/dev/null | gpg --dearmor - | sudo tee /usr/share/keyrings/kitware-archive-keyring.gpg >/dev/null + echo "deb [signed-by=/usr/share/keyrings/kitware-archive-keyring.gpg] https://apt.kitware.com/ubuntu/ ${{ env.ubuntu_codename }} main" | sudo tee /etc/apt/sources.list.d/kitware.list >/dev/null + sudo apt-get update -qq + sudo apt-get install -y cmake gcc + - name: build static + run: | + mkdir -p build + cd build + cmake -DBUILD_SHARED_LIBS=Off -DCMAKE_BUILD_TYPE=RelWithDebInfo .. + make -j$(nproc) + cpack -G DEB + cmake -DBUILD_SHARED_LIBS=On -DCMAKE_BUILD_TYPE=RelWithDebInfo .. + make -j$(nproc) + cpack -G DEB + - name: push package to packagecloud.io + uses: computology/packagecloud-github-action@v0.6 + with: + PACKAGE-NAME: packages/ubuntu/${{ env.ubuntu_codename }}/*.deb + PACKAGECLOUD-USERNAME: libtom + PACKAGECLOUD-REPONAME: libtom + PACKAGECLOUD-DISTRO: ubuntu/${{ env.ubuntu_codename }} + PACKAGECLOUD-TOKEN: ${{ secrets.PACKAGECLOUD_TOKEN }} From 9de2c2268baf3d53970ff6c739a00b7b463f69e6 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 15 Jun 2023 16:44:12 +0200 Subject: [PATCH 253/304] Make sure untagged versions get a different package name Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 8f8524912..8321c642f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -225,6 +225,14 @@ else() set(DISTRO_PACK_PATH ${CMAKE_SYSTEM_NAME}/) endif() +# make sure untagged versions get a different package name +execute_process(COMMAND git describe --exact-match --tags RESULT_VARIABLE REPO_HAS_TAG) +if(REPO_HAS_TAG EQUAL 0) + set(PACKAGE_NAME_SUFFIX "") +else() + set(PACKAGE_NAME_SUFFIX "-git") +endif() + # default CPack generators set(CPACK_GENERATOR TGZ STGZ) @@ -245,6 +253,7 @@ if(BUILD_SHARED_LIBS) else() set(CPACK_PACKAGE_NAME "${PROJECT_NAME}-devel") endif() +set(CPACK_PACKAGE_NAME "${CPACK_PACKAGE_NAME}${PACKAGE_NAME_SUFFIX}") set(CPACK_PACKAGE_VERSION ${PROJECT_VERSION}) set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "LibTomMath") set(CPACK_PACKAGE_VENDOR "libtom projects") From 7585a6a0c525b0f6b0b8f4ac31077904e8d7e410 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 15 Jun 2023 17:33:33 +0200 Subject: [PATCH 254/304] Fix packagecloud deploy script Signed-off-by: Steffen Jaeckel --- .github/workflows/deploy.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 3789236e9..381f1f158 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -27,7 +27,7 @@ jobs: echo "deb [signed-by=/usr/share/keyrings/kitware-archive-keyring.gpg] https://apt.kitware.com/ubuntu/ ${{ env.ubuntu_codename }} main" | sudo tee /etc/apt/sources.list.d/kitware.list >/dev/null sudo apt-get update -qq sudo apt-get install -y cmake gcc - - name: build static + - name: build packages run: | mkdir -p build cd build @@ -40,8 +40,8 @@ jobs: - name: push package to packagecloud.io uses: computology/packagecloud-github-action@v0.6 with: - PACKAGE-NAME: packages/ubuntu/${{ env.ubuntu_codename }}/*.deb + PACKAGE-NAME: build/packages/ubuntu/${{ env.ubuntu_codename }}/*.deb PACKAGECLOUD-USERNAME: libtom - PACKAGECLOUD-REPONAME: libtom + PACKAGECLOUD-REPONAME: packages PACKAGECLOUD-DISTRO: ubuntu/${{ env.ubuntu_codename }} PACKAGECLOUD-TOKEN: ${{ secrets.PACKAGECLOUD_TOKEN }} From a45511232d203cf2827f3b49dba0a15f678d677c Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 15 Jun 2023 18:01:55 +0200 Subject: [PATCH 255/304] cmake: Fix naming scheme for debian packages Those are only used in case we're building on develop. Signed-off-by: Steffen Jaeckel --- .github/workflows/deploy.yml | 2 +- CMakeLists.txt | 19 +++++++++++++------ README.md | 6 ++++++ 3 files changed, 20 insertions(+), 7 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 381f1f158..8cd1307de 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -37,7 +37,7 @@ jobs: cmake -DBUILD_SHARED_LIBS=On -DCMAKE_BUILD_TYPE=RelWithDebInfo .. make -j$(nproc) cpack -G DEB - - name: push package to packagecloud.io + - name: push deb packages to packagecloud.io uses: computology/packagecloud-github-action@v0.6 with: PACKAGE-NAME: build/packages/ubuntu/${{ env.ubuntu_codename }}/*.deb diff --git a/CMakeLists.txt b/CMakeLists.txt index 8321c642f..7282823c0 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -146,7 +146,7 @@ set(TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") install(TARGETS ${PROJECT_NAME} EXPORT ${TARGETS_EXPORT_NAME} LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT Libraries RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} ) @@ -226,11 +226,12 @@ else() endif() # make sure untagged versions get a different package name -execute_process(COMMAND git describe --exact-match --tags RESULT_VARIABLE REPO_HAS_TAG) +execute_process(COMMAND git describe --exact-match --tags ERROR_QUIET RESULT_VARIABLE REPO_HAS_TAG) if(REPO_HAS_TAG EQUAL 0) set(PACKAGE_NAME_SUFFIX "") else() set(PACKAGE_NAME_SUFFIX "-git") + message(STATUS "Use -git suffix") endif() # default CPack generators @@ -245,15 +246,18 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "FreeBSD") list(APPEND CPACK_GENERATOR FREEBSD) endif() +set(LTM_DEBIAN_SHARED_PACKAGE_NAME "${PROJECT_NAME}${PACKAGE_NAME_SUFFIX}${PROJECT_VERSION_MAJOR}") + # general CPack config set(CPACK_PACKAGE_DIRECTORY ${CMAKE_BINARY_DIR}/packages/${DISTRO_PACK_PATH}) message(STATUS "CPack: packages will be generated under ${CPACK_PACKAGE_DIRECTORY}") if(BUILD_SHARED_LIBS) set(CPACK_PACKAGE_NAME "${PROJECT_NAME}${PROJECT_VERSION_MAJOR}") + set(CPACK_DEBIAN_PACKAGE_NAME "${LTM_DEBIAN_SHARED_PACKAGE_NAME}") else() set(CPACK_PACKAGE_NAME "${PROJECT_NAME}-devel") + set(CPACK_DEBIAN_LIBRARIES_PACKAGE_NAME "${PROJECT_NAME}${PACKAGE_NAME_SUFFIX}-dev") endif() -set(CPACK_PACKAGE_NAME "${CPACK_PACKAGE_NAME}${PACKAGE_NAME_SUFFIX}") set(CPACK_PACKAGE_VERSION ${PROJECT_VERSION}) set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "LibTomMath") set(CPACK_PACKAGE_VENDOR "libtom projects") @@ -261,17 +265,20 @@ set(CPACK_PACKAGE_CONTACT "libtom@googlegroups.com") set(CPACK_RESOURCE_FILE_LICENSE "${PROJECT_SOURCE_DIR}/LICENSE") set(PACKAGE_NAME_TRAILER ${CPACK_PACKAGE_VERSION}-${PACKAGE_RELEASE_VERSION}_${MACHINE_ARCH}) set(CPACK_PACKAGE_FILE_NAME ${CPACK_PACKAGE_NAME}-${PACKAGE_NAME_TRAILER}) -set(CPACK_STRIP_FILES ON) # deb specific CPack config set(CPACK_DEBIAN_FILE_NAME DEB-DEFAULT) -set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) +set(CPACK_DEBIAN_DEBUGINFO_PACKAGE ON) set(CPACK_DEBIAN_PACKAGE_RELEASE ${PACKAGE_RELEASE_VERSION}) +set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) if(BUILD_SHARED_LIBS) set(CPACK_DEBIAN_PACKAGE_SECTION "libs") else() - set(CPACK_DEBIAN_PACKAGE_NAME "${PROJECT_NAME}-dev") set(CPACK_DEBIAN_PACKAGE_SECTION "devel") + set(CPACK_DEBIAN_PACKAGE_DEPENDS ${LTM_DEBIAN_SHARED_PACKAGE_NAME}) + set(CPACK_DEB_COMPONENT_INSTALL ON) + set(CPACK_ARCHIVE_COMPONENT_INSTALL ON) + set(CPACK_COMPONENTS_ALL Libraries) endif() # rpm specific CPack config diff --git a/README.md b/README.md index 7ee58bbc0..29e077f2b 100644 --- a/README.md +++ b/README.md @@ -20,6 +20,12 @@ develop: [![Build status](https://ci.appveyor.com/api/projects/status/b80lpolw3i API/ABI changes: [check here](https://abi-laboratory.pro/tracker/timeline/libtommath/) +### Pre-built packages + +We sometimes upload `deb` packages of the latest state from the develop branch to [packagecloud.io](https://packagecloud.io/libtom/packages). + +Use those packages with caution and at your own discretion. + ## Summary The `develop` branch contains the in-development version. Stable releases are tagged. From 070946ad4abb78d1dcc91e157b2e3d91dd97ae31 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 19 Jun 2023 16:59:56 +0200 Subject: [PATCH 256/304] Fix `CMAKE_INSTALL_PREFIX` for deploy Signed-off-by: Steffen Jaeckel --- .github/workflows/deploy.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 8cd1307de..a06ac73c5 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -31,10 +31,10 @@ jobs: run: | mkdir -p build cd build - cmake -DBUILD_SHARED_LIBS=Off -DCMAKE_BUILD_TYPE=RelWithDebInfo .. + cmake -DBUILD_SHARED_LIBS=Off -DCMAKE_BUILD_TYPE=RelWithDebInfo -DCMAKE_INSTALL_PREFIX="/usr" .. make -j$(nproc) cpack -G DEB - cmake -DBUILD_SHARED_LIBS=On -DCMAKE_BUILD_TYPE=RelWithDebInfo .. + cmake -DBUILD_SHARED_LIBS=On -DCMAKE_BUILD_TYPE=RelWithDebInfo -DCMAKE_INSTALL_PREFIX="/usr" .. make -j$(nproc) cpack -G DEB - name: push deb packages to packagecloud.io From 5c4f5d9c0c3c5d9666ed1ba4e5d658abb3adc9fb Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 21 Jun 2023 14:10:44 +0200 Subject: [PATCH 257/304] added macro mp_isone --- doc/bn.tex | 6 ++++++ tommath.h | 1 + 2 files changed, 7 insertions(+) diff --git a/doc/bn.tex b/doc/bn.tex index 711ad0e58..0642263e8 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2658,6 +2658,12 @@ \section{Function Macros} \end{alltt} Checks if $a = 0$. It does not check if the amount of memory allocated for $a$ is also minimal. +\index{mp\_isone} +\begin{alltt} +bool mp_isone(mp_int *a) +\end{alltt} +Checks if $a = 1$. + Other macros which are either shortcuts to normal functions or just other names for them do have their place in a programmer's life, too! diff --git a/tommath.h b/tommath.h index 33aa5dfd7..db005081b 100644 --- a/tommath.h +++ b/tommath.h @@ -208,6 +208,7 @@ mp_err mp_init_size(mp_int *a, int size) MP_WUR; /* ---> Basic Manipulations <--- */ #define mp_iszero(a) ((a)->used == 0) +#define mp_isone(a) ( ((a)->sign == MP_ZPOS) && ((a)->used == 1u) && ((a)->dp[0] == 1u) ) #define mp_isneg(a) ((a)->sign == MP_NEG) #define mp_iseven(a) (((a)->used == 0) || (((a)->dp[0] & 1u) == 0u)) #define mp_isodd(a) (!mp_iseven(a)) From 72a0907166918727dd3991995864cb30fa251492 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Tue, 23 May 2023 23:32:45 +0200 Subject: [PATCH 258/304] addition of a man-page --- CMakeLists.txt | 8 + doc/tommath.3 | 1697 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 1705 insertions(+) create mode 100644 doc/tommath.3 diff --git a/CMakeLists.txt b/CMakeLists.txt index 7282823c0..dfbcb0f26 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -174,6 +174,14 @@ write_basic_package_version_file( COMPATIBILITY SameMajorVersion ) +# Windows uses a different help sytem. +if((NOT WIN32) AND (NOT CMAKE_HOST_WIN32)) +# install manpage (not gzipped, some BSD's do not want it compressed?) +install(FILES ${CMAKE_SOURCE_DIR}/doc/tommath.3 + DESTINATION ${CMAKE_INSTALL_MANDIR}/man3/ +) +endif() + # install version file install(FILES ${PROJECT_VERSION_FILE} DESTINATION ${CONFIG_INSTALL_DIR} diff --git a/doc/tommath.3 b/doc/tommath.3 new file mode 100644 index 000000000..120a399bb --- /dev/null +++ b/doc/tommath.3 @@ -0,0 +1,1697 @@ +.TH LIBTOMMATH 3 "2023-04-26" +.SH NAME +libtommath - a big integer library +.SH SYNOPSIS +.sp +.ft B +.nf +#include +.fi +.ft +.SH DESCRIPTION +.I LibTomMath +provides a series of efficient and carefully written functions +for manipulating large integer numbers. +.br +Functions are in alphabetical order. +.LP +\fBNOTE:\fP The errors listed are not the only ones possible, just the interesting ones. + +.LP +.BI "mp_err mp_2expt(mp_int * " a ", int " b ")" +.in 1i +Computes 2^b with b >= 0 and puts the result in \fIa\fP. This functions uses a faster method than \fBmp_mul_2\fP. +.br +Returns \fBMP_OVF\fP if the result would be larger than a \fBmp_int\fP can hold. The macro \fBMP_MAX_DIGIT_COUNT\fP holds +the maximal number of limbs: ((INT_MAX - 2) / MP_DIGIT_BIT). +.br +Returns \fBMP_VAL\fP if b < 0 +.in -1i + + +.LP +.BI "mp_err mp_abs (const mp_int *" a ", mp_int *" b ")" +.in 1i +Computes the absolute value of \fBa\fP and puts the result in \fBb\fP. +.in -1i + +.LP +.BI "mp_err mp_add (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Computes \fBa + b = c\fP. +.in -1i + +.LP +.BI "mp_err mp_add_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" +.in 1i +Computes \fBa + b = c\fP where \fBb\fP is of type \fBmp_digit\fP. +.in -1i + +.LP +.BI "mp_err mp_addmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" +.in 1i +Computes \fB(a + b) % c = d\fP. No optimizations. +.in -1i + +.LP +.BI "mp_err mp_and (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" +.in 1i +Computes bitwise or \fBa & b = c\fP. Negative numbers +are treated as if they are in two-complement representation. +.in -1i + +.LP +.BI "void mp_clamp(mp_int *" a "); +.in 1i +This is used to ensure that leading zero digits are trimmed and the leading \fBused\fP digit will be +non-zero. It also fixes the sign if there are no more leading digits. +.in -1i + +.LP +.BI "void mp_clear (mp_int *" a ")" +.in 1i +Frees the heap memory of \fBa\fP. +.in -1i + +.LP +.BI "int mp_cnt_lsb(const mp_int *" a ")" +.in 1i +Returns the position of the lowest bit set. +.in -1i + +.LP +.BI "mp_err mp_complement(const mp_int *" a ", mp_int *" b ")" +.in 1i +Computes the 2-complement \fIb = ~a\fP. +.in -1i + +.LP +.BI "mp_err mp_copy (const mp_int *" a ", mp_int *" b ")" +.in 1i +Makes a deep copy of \fBa\fP into \fBb\fP. +.in -1i + +.LP +.BI "int mp_count_bits(const mp_int *" a ")" +.in 1i +Returns the position of the highest bit set. +.in -1i + +.LP +.BI "mp_err mp_decr(mp_int *" a ")" +.in 1i +Computes \fBa--\fP. +.in -1i + +.LP +.BI "mp_err mp_div_2(const mp_int *" a ", mp_int *" b "); +.in 1i +Computes \fBa >> 1 = b\fP. +.in -1i + +.LP +.BI "mp_err mp_div_2d (const mp_int *" a ", int " b ", mp_int *" c ", mp_int *" d "); +.in 1i +Computes \fBa >> b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. +.br +Set the argument for quotient and/or remainder to \fBNULL\fP to ignore the respective output. +.br +Returns \fBMP_VAL\fP if \fBb < 0\fP +.in -1i + +.LP +.BI "mp_err mp_div (const mp_int *" a ", const mp_int *" b ", mp_int *" c ", mp_int *" d ")" +.in 1i +Computes \fBa / b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. +.br +Set the argument for quotient and/or remainder to \fBNULL\fP to ignore the respective output. +.br +This function calls one of either: \fBs_mp_div_recursive\fP, \fBs_mp_div_school\fP, or +\fBs_mp_div_small\fP. +.br +Returns \fBMP_VAL\fP if \fBb = 0\fP +.in -1i + +.LP +.BI "mp_err mp_div_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ", mp_digit *" d ")" +.in 1i +Computes \fBa / b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. +.br +Set the argument for quotient and/or remainder to \fBNULL\fP to ignore the respective output. +Returns \fBMP_VAL\fP if \fBb = 0\fP. +.in -1i + +.LP +.BI "bool mp_dr_is_modulus(const mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if the modulus \fBa\fP is of the form below that allows for a diminished radix reduction, \fBfalse\fP otherwise. +.br +\fB\[*b]^k - p\fP for some \fBk >= 0\fP and \fB0 < p < \[*b]\fP where \fB\[*b]\fP is the radix. +.in -1i + +.LP +.BI "mp_err mp_dr_reduce(mp_int *" a ", const mp_int *" b ", mp_digit " mp ")" +.in 1i +This reduces \fBa\fP in place modulo \fBb\fP with the pre-computed value \fBmp\fP. \fBb\fP must be of a restricted +diminished radix form and \fBa\fP must be in the range \fB0 <= a < b^2\fP +.in -1i + +.LP +.BI "void mp_dr_setup(const mp_int *" a ", mp_digit *" d ")" +.in 1i +This computes the value required for the modulus \fBa\fP and stores it in \fBd\fP. +.in -1i + +.LP +.BI "void mp_exch (mp_int *" a ", mp_int *" b ")" +.in 1i +Swaps, but just the pointers. +.in -1i + +.LP +.BI "const char *mp_error_to_string(mp_err " code ")" +.in 1i +Returns a short ASCII message describing the error code given in \fBcode\fP. +.in -1i + +.LP +.BI "mp_err mp_exptmod (const mp_int *" G ", const mp_int *" X ", const mp_int *" P ", mp_int *" Y ")" +.in 1i +This computes \fBY \[==] G^X (mod P)\fP using a variable width sliding window +algorithm. This function will automatically detect the fastest modular reduction technique to use +during the operation. For negative values of \fBX\fP the operation is performed as \fBY \[==] (G^-1 mod P)^(|X| (mod P))\fP +provided that \fBgcd(G, P) = 1\fP. +.br +This function is actually a shell around the two internal exponentiation functions. This routine +will automatically detect when Barrett, Montgomery, Restricted and Unrestricted Diminished Radix +based exponentiation can be used. Generally moduli of the a "restricted diminished radix" form +lead to the fastest modular exponentiations. Followed by Montgomery and the other two algorithms. +.br +Returns \fBMP_VAL\fP if \fBP < 0\fP. +.br +Returns \fBMP_VAL\fP if none of the underlying internal functions have been compiled in. +.in -1i + +.LP +.BI "mp_err mp_expt_n(const mp_int *" a ", int " b ", int *" c ")" +.in 1i +Computes \fBa^b = c\fP. Simple binary exponentiation, no further optimizations. +.br +\fBb\fP must be positive. +.in -1i + +.LP +.BI "mp_err mp_exteuclid(const mp_int *" a ", const mp_int *" b ", mp_int *" U1 ", mp_int *" U2 ", mp_int *" U3 ")" +.in 1i +Computes the extended Euclidean algorithm: \fBa * U1 + b * U2 = U3\fP +.br +Set the argument for \fBU1, U2, U3\fP to \fBNULL\fP to ignore the respective output. +.in -1i + +.LP +.BI "mp_err mp_fread(mp_int *" a ", int " radix ", FILE *" stream ")" +.in 1i +Reads a number in radix \fBradix\fP from file \fBstream\fP and converts it into the big integer \fBa\fP. +.br +Returns \fBMP_VAL\fP if radix is not in the range \fB2 <= radix <= 64\fP. +.br +Returns \fBMP_ERR\fP if no digits were found in \fBstream\fP. +.in -1i + +.LP +.BI "mp_err mp_from_sbin(mp_int *" a ", const uint8_t *" b ", size_t " size ")" +.in 1i +This will read in an big-endian array of octets from \fBb\fP of length +\fBsize\fP into \fBa\fP. +.br +If the first octet of the data is zero, the sign of the big-integer will be \fBMP_NEG\fP and \fBMP_ZPOS\fP otherwise. +.in -1i + +.LP +.BI "mp_err mp_from_ubin(mp_int *" a ", uint8_t *" b ", size_t " size ")" +.in 1i +This will read in an big-endian array of octets from \fBb\fP of length +\fBsize\fP into \fBa\fP. The resulting big-integer \fBa\fP will always be positive. +.in -1i + +.LP +.BI "mp_err mp_fwrite(const mp_int *" a ", int " radix ", FILE *" stream ")" +.in 1i +Writes \fBa\fP as a string representing the big integer in radix \fBradix\fP to file \fBstream\fP. +.br +Returns \fBMP_MEM\fP if the functions fails to allocate memory for the buffer. +.br +Returns \fBMP_ERR\fP if there was a problem writing to the file. +.br +Returns \fBMP_VAL\fP if radix is not in the range \fB2 <= radix <= 64\fP. +.in -1i + +.LP +.BI "mp_err mp_gcd (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Compute the greatest common divisor of \fBa\fP and \fBb\fP and store it in \fBc\fP. +.in -1i + +.LP +.BI "double mp_get_double(const mp_int *" a ")" +.in 1i +Returns a float of type \fBdouble\fP (binary64). +.br +Will overflow if the big integer is too big. +.br +\fBNOTE:\fP rounding mode is not set just taken. Use e.g.: \fBfesetround(3)\fP in \fBfenv.h\fP to +change the rounding mode. +.in -1i + +.LP +.BI "int32_t mp_get_i32 (const mp_int *" a ")" +.in 1i +Returns a signed 32-bit integer from big-integer \fBa\fP. +.br +\fBNOTE:\fP This group of functions is truncating. Example: +.br +.TS +tab(;), allbox; +l r. +Input;123456789101112131415161718192021222324252627282930 +mp_get_i32;-1073632270 +mp_get_i64;5543444065158278130 +mp_get_mag_u32;3221335026 +mp_get_mag_u64;5543444065158278130 +mp_get_l;5543444065158278130 +mp_get_mag_ul;5543444065158278130 +.TE +.in -1i + +.LP +.BI "int64_t mp_get_i64 (const mp_int *" a ")" +.in 1i +Returns a signed 64-bit integer from big-integer \fBa\fP. +.br +\fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. +.in -1i + +.LP +.BI "long mp_get_l (const mp_int *" a ")" +.in 1i +Returns a signed \fBlong\fP from big-integer \fBa\fP. +.br +\fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. +.in -1i + +.LP +.BI "uint32_t mp_get_mag_u32 (const mp_int *" a ")" +.in 1i +Returns an unsigned 32 bit integer from big-integer \fBa\fP. +.br +\fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. +.in -1i + +.LP +.BI "uint64_t mp_get_mag_u64 (const mp_int *" a ")" +.in 1i +Returns an unsigned 64 bit integer from big-integer \fBa\fP. +.br +\fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. +.in -1i + +.LP +.BI "uint32_t mp_get_u32 (const mp_int *" a ")" +.in 1i +Convenience macro for \fBmp_get_mag_u32()\fP. +.in -1i + +.LP +.BI "uint64_t mp_get_u64 (const mp_int *" a ")" +.in 1i +Convenience macro for \fBmp_get_mag_u64()\fP. +.in -1i + +.LP +.BI "mp_err mp_grow (mp_int *" a ", int " size ")" +.in 1i +This will grow the array of digits of \fBa\fP to \fBsize\fP. +.br +Returns \fBMP_MEM\fP if the functions fails to allocate enough memory. +.in -1i + +.LP +.BI "mp_err mp_hash (mp_int *" a ", mp_hval *" hash ")" +.in 1i +This will create the hash of \fBa\fP following the \fIFNV-1a\fP algorithm as described on +\fIhttp://www.isthe.com/chongo/tech/comp/fnv/index.html#FNV-1a\fP. With the +help of this function one can use an \fBmp_int\fP as a key in a hash table. +.br +\fBNOTE:\fP The hashing is not stable over different widths of a \fBmp_digit\fP. +.in -1i + +.LP +.BI "mp_err mp_incr(mp_int *" a ")" +.in 1i +Computes \fBa++\fP. +.br +Returns \fBMP_MEM\fP if the reallocation of memory in \fBmp_grow\fP failed. +.in -1i + +.LP +.BI "mp_err mp_init_copy (mp_int *" a ", mp_int *" b ")" +.in 1i +Initializes \fBa\fP and copies \fBb\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init_i32 (mp_int *" a ", int32_t " b "); +.in 1i +Initializes \fBa\fP and copies the signed 32 bit integer \fBb\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init_i64 (mp_int *" a ", int64_t " b ")" +.in 1i +Initializes \fBa\fP and copies the signed 64 bit integer \fBb\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init_l (mp_int *" a ", long " b ")" +.in 1i +Initializes \fBa\fP and copies the signed integer \fBb\fP of type \fBlong\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init (mp_int *" a ")" +.in 1i +Initializes \fBa\fP. +.br +It allocates a certain amount of memory such that the \fBmp_set_u64\fP setter can +store an \fBuint64_t\fP in the \fBmp_int\fP. To be able to take advantage of the algorithm used for +\fBmp_school_div\fP the \fBmp_int\fP must have at least three limbs. +.br +It actively sets all limbs to zero, overwriting what was there before, sets the \fBa.sign\fP to \fBMP_ZPOS\fP, +and \fBa.used\fP to zero. +.in -1i + +.LP +.BI "mp_err mp_init_multi(mp_int *" mp ", " ... ")" +.in 1i +Initialize a \fBNULL\fP terminated series of \fBmp_int\fPs. +.in -1i + +.LP +.BI "mp_err mp_init_set (mp_int *" a ", mp_digit " b ")" +.in 1i +Initializes \fBa\fP and sets it to the \fBmp_digit\fP \fBb\fP +.in -1i + +.LP +.BI "mp_err mp_init_size (mp_int *" a ", int " size ")" +.in 1i +Initializes \fBa\fP with pre-grown to a \fBsize\fP number of limbs. +.br +If \fBsize\fP is smaller than the minimum (see \fBmp_init\fP for details) \fBsize\fP will be increased to that minimum. +.br +Returns \fBMP_OVF\fP if \fBsize\fP is larger than an \fBmp_int\fP is able to hold. +.in -1i + +.LP +.BI "mp_err mp_init_u32 (mp_int *" a ", uint32_t " b ")" +.in 1i +Initializes \fBa\fP and copies the unsigned 32 bit integer \fBb\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init_u64 (mp_int *" a ", uint64_t " b ")" +.in 1i +Initializes \fBa\fP and copies the unsigned 64 bit integer \fBb\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_init_ul (mp_int *" a ", unsigned long " b ")" +.in 1i +Initializes \fBa\fP and copies the unsigned integer \fBb\fP of type \fBunsigned long\fP into \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_invmod (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Computes the multiplicative inverse of \fBa\fP modulo \fBb\fP and stores the result in \fBv\fP such that +\fBac \[==] 1 (mod b)\fP. +.br +Does use a faster algorithm if the modulus \fBb\fP is odd. +.br +Returns \fBMP_VAL\fP if \fBb <= 1\fP +.in -1i + +.LP +.BI "bool mp_iseven(const mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if \fBa\fP is even, \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "bool mp_isneg(mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if \fBa < 0\fP, \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "bool mp_isodd(const mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if \fBa\fP is odd, \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "mp_err mp_is_square(const mp_int *" arg ", bool *" ret ")" +.in 1i +Sets \fBret\fP to \fBtrue\fP if \fBarg\fP is a square, \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "bool mp_iszero(mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if \fBa = 0\fP, \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "mp_err mp_kronecker (const mp_int *" a ", const mp_int *" p ", int *" c ")" +.in 1i +Computes the Kronecker symbol (an extension of the Jacobi symbol) for \fBa\fP with respect to +\fBp\fP with \fB(a, p) in Z\fP. If \fBp\fP is prime this essentially computes the +Legendre symbol. The result is stored in \fBc\fP and can take on one of three values \fB{-1, 0, 1}\fP. +.TS +tab(;); +r l. +-1 ;if \fBa\fP is not a quadratic residue modulo \fBp\fP and \fBp\fP is prime. +0 ;if \fBa\fP divides \fBp\fP +1 ;if \fBa\fP is a quadratic residue modulo \fBp\fP. +.TE +.in -1i + +.LP +.BI "mp_err mp_lcm (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Computes the least common multiple as \fB|a * b|/gcd(a, b)\fP. +.in -1i + +.LP +.BI "mp_err mp_log(const mp_int *" a ", const mp_int *" base ", int *" c ")" +.in 1i +Computes \fBlog_b(a)\fP such that \fB(log_b a)^b <= a\fP. +.br +Returns \fBMP_VAL\fP if \fBa <= 0\fP or \fBb < 2\fP. +.in -1i + +.LP +.BI "mp_err mp_log_n(const mp_int *" a ", int " base ", int *" c ")" +.in 1i +Computes \fBlog_b(a)\fP such that \fB(log_b a)^b <= a\fP. +.br +Convenience function that is a wrapper for \fBmp_log\fP doing the conversion of \fBb\fP +to a big integer. +.in -1i + +.LP +.BI "mp_err mp_lshd (mp_int *" a ", int " b ")" +.in 1i +Shift \fBa\fP left by \fBb\fP limbs: \fBa * 2^(b*MP_DIGIT_BIT)\fP. +.in -1i + +.LP +.BI "mp_err mp_mod_2d(const mp_int *" a ", int " b ", mp_int *" c ")" +.in 1i +Compute \fBa % 2^b\fP. +.br + +.in -1i + +.LP +.BI "mp_err mp_mod(const mp_int *" a ",const mp_int *" b ", mp_int *" c ")" +.in 1i +Compute \fBa \[==] c mod b\fP. +.br +\fB0 <= c < b\fP if \fBb > 0\fP and \fBb < c <= 0\fP if \fBb < 0\fP. +.in -1i + +.LP +.BI "mp_err mp_mod_d(const mp_int *" a ", mp_digit " b ", mp_digit *" c ")" +.in 1i +Computes the remainder of \fBa / b\fP. +.in -1i + +.LP +.BI "mp_err mp_montgomery_calc_normalization(mp_int *" a ", mp_int *" b ")" +.in 1i +Computes \fBR = r^n\fP for Montgomery reduction where \fBn\fP is size of \fBa\fP in bits and +\fBr\fP is the radix (\fBMP_DIGIT_MAX + 1\fP). +.br +See \fBmp_montgomery_reduce\fP for some example code. +.in -1i + +.LP +.BI "mp_err mp_montgomery_reduce(mp_int *" a ", mp_int *" m ", mp_digit " mp ")" +.in 1i +Reduces \fBa\fP in place modulo \fBm\fP with the pre-computed value \fBmp\fP (\fBa*mp^(-1) \[==] x (mod m) \fP). +Pre-computation of \fBmp\fP can be done with \fBmp_montgomery_setup\fP. Example: + +.nf +int main(void) +{ + mp_int a, b, c, R; + mp_digit mp; + mp_err result; + + /* initialize a,b to desired values, + * mp_init R, c and set c to 1.... + */ + + /* get normalization */ + if ((result = mp_montgomery_calc_normalization(&R, b)) != MP_OKAY) { + printf("Error getting norm. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + /* get mp value */ + if ((result = mp_montgomery_setup(&c, &mp)) != MP_OKAY) { + printf("Error setting up montgomery. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* normalize `a' so now a is equal to aR */ + if ((result = mp_mulmod(&a, &R, &b, &a)) != MP_OKAY) { + printf("Error computing aR. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* square a to get c = a^2R^2 */ + if ((result = mp_sqr(&a, &c)) != MP_OKAY) { + printf("Error squaring. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + /* now reduce `c' back down to c = a^2R^2 * R^-1 == a^2R */ + if ((result = mp_montgomery_reduce(&c, &b, mp)) != MP_OKAY) { + printf("Error reducing. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* multiply a to get c = a^3R^2 */ + if ((result = mp_mul(&a, &c, &c)) != MP_OKAY) { + printf("Error reducing. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* now reduce `c' back down to c = a^3R^2 * R^-1 == a^3R */ + if ((result = mp_montgomery_reduce(&c, &b, mp)) != MP_OKAY) { + printf("Error reducing. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* now reduce (again) `c' back down to c = a^3R * R^-1 == a^3 */ + if ((result = mp_montgomery_reduce(&c, &b, mp)) != MP_OKAY) { + printf("Error reducing. %s", + mp_error_to_string(result)); + return EXIT_FAILURE; + } + + /* c now equals a^3 mod b */ + + return EXIT_SUCCESS; +\} +.in -1i + +.LP +.BI "mp_err mp_montgomery_setup(const mp_int *" a ", mp_digit *" mp ")" +.in 1i +For the given odd modulus \fBa\fP the pre-computation value is placed in \fBmp\fP. +.br +\fBmp = 1/a mod 2^k\fP with \fBk\fP the number of bits in the underlying native type used for \fBmp_digit\fP. +.br +See \fBmp_montgomery_reduce\fP for some example code. +.in -1i + +.LP +.BI "mp_err mp_mul_2(const mp_int *" a ", mp_int *" b ")" +.in 1i +Computes \fBb = 2 * a\fP. +.in -1i + +.LP +.BI "mp_err mp_mul_2d(const mp_int *" a ", int " b ", mp_int *" c ")" +.in 1i +Shifts \fBa\fP left by \fBb\fP bits \fBb = a * 2^b\fP. +.br +Condition: \fBb >= 0\fP +.in -1i + +.LP +.BI "mp_err mp_mul (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Computes \fBc = a * b\fP. +.in -1i + +.LP +.BI "mp_err mp_mul_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" +.in 1i +Computes \fBc = a * b\fP with \fBb\fP and \fBmp_digit\fP. +.in -1i + +.LP +.BI "mp_err mp_mulmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" +.in 1i +Computes \fBd = a * b (mod c)\fP. No optimizations. +.br +For special forms of the input libtommath offers other, optimized algorithms. See for example +\fBmp_montgomery_reduce\fP for some example code with Montgomery reduction. There is also Barret +reduction, which is more generic (\fBmp_reduce\fP), diminished radix reduction (\fBmp_dr_reduce\fP) and +unrestricted diminished radix reduction (\fBmp_reduce_2k\fP) +.br +.in -1i + +.LP +.BI "mp_err mp_neg (const mp_int *" a ", mp_int *" b ")" +.in 1i +Computes \fBb = -a\fP. +.in -1i + +.LP +.BI "mp_err mp_or (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" +.in 1i +Computes bit-wise or \fBa | b = c\fP. Negative numbers +are treated as if they are in two-complement representation. +.in -1i + +.LP +.BI "size_t mp_pack_count(const mp_int *" a ", size_t " nails ", size_t " size ")" +.in 1i +Returns the size in bytes necessary to be put in \fBmp_pack\fP's \fBmaxsize\fP. See \fBmp_pack\fP for details. +.in -1i + +.LP +.BI "mp_err mp_pack(void *" rop ", size_t *" countp ", mp_order " order ", size_t " size ", mp_endian " endian ", size_t " nails ", const mp_int *" op ")" +.in 1i +Export binary data. +.br +Implements the similarly working GMP functions as described at \fIhttp://gmplib.org/manual/Integer-Import-and-Export.html\fP with +the exception that \fBmp_pack\fP will not allocate memory if \fBrop\fP is \fBNULL\fP. +.br +To make things a bit more comfortable libtommath offers two \fBenum\fPs: + +.br +.in 1.5i +typedef enum { + MP_LSB_FIRST = -1, + MP_MSB_FIRST = 1 +} mp_order; + +.br + +typedef enum { + MP_LITTLE_ENDIAN = -1, + MP_NATIVE_ENDIAN = 0, + MP_BIG_ENDIAN = 1 +} mp_ndian; +.in -1.5i +.in -1i + +.LP +.BI "mp_err mp_prime_strong_lucas_selfridge(const mp_int *" a ", bool *" result ")" +.in 1i +Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a strong Lucas-Selfridge pseudoprime, \fBfalse\fP otherwise. +.br +It has been verified that this function together with one round of Miller-Rabin to the base 2 (two) is +deterministic up to 2^64. +.in -1i + +.LP +.BI "mp_err mp_prime_frobenius_underwood(const mp_int *" N ", bool *" result ")" +.in 1i +Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a Frobenius-Underwood pseudoprime, \fBfalse\fP otherwise. +.br +It has been verified that this function (as a stand-alone) is deterministic up to at least 2^50. +.in -1i + +.LP +.BI "mp_err mp_prime_is_prime(const mp_int *" a ", int " t ", bool *" result ")" +.in 1i +Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a pseudoprime, \fBfalse\fP otherwise. +.br +The argument \fBt\fP holds the number of random Miller-Rabin tests to be executed. +.br +.nr step 1 1 +Uses a stack of different tests to detect composites: +.RS +.IP \n[step] 0.3i +Direct test: checks if input is one of the values 0, 1, 2. +.IP \n+[step] +The only even prime has been handled, reject even input from now on +.IP \n+[step] +Check if input is a square. (some of the algorithms used later do not like square input) +.IP \n+[step] +Check if input is equal to one of the primes in the table \fBs_mp_prime_tab\fP +.IP \n+[step] +Check if input is divisible by one of the primes in the table \fBs_mp_prime_tab\fP +.IP \n+[step] +Run a Miller-Rabin test with base 2 +.IP \n+[step] +Run a Miller-Rabin test with base 3 +.IP \n+[step] +If \fBt <= 0\fP and the macro \fBLTM_USE_ONLY_MR\fP is not defined we run either a Frobenius-Underwood +test if the macro \fBLTM_USE_FROBENIUS_TEST\fP is defined or a Lucas-Selfridge test. +.br +The Lucas-Selfridge test together with the two Miller-Rabin tests earlier is deterministic up to at least 2^64. +.br +The Frobenius-Underwood test as a stand-alone is deterministic up to at least 2^50. But it is different from +the Lucas-Selfridge test so the additional cost (about two times the time a Lucas-Selfridge test would need) might be worthwhile. +.IP \n+[step] +Even if \fBt = 0\fP we run at least one Miler-Rabin test with a random base. +.IP \n+[step] +If \fBt < 0\fP and input smaller than 3,317,044,064,679,887,385,961,981 (< 82 bits) several Miller-Rabin tests +are run with bases according to Sorenson, Jonathan; Webster, Jonathan (2015) "Strong Pseudoprimes to Twelve Prime Bases". +.br +Here ends the deterministic part of this function. +.IP \n+[step] +If \fBt > 0\fP: run the given number of Miller-Rabin tests with random bases. +.RE +.in -1i + +.LP +.BI "mp_err mp_prime_miller_rabin (const mp_int *" a ", const mp_int *" b ", int *" result ")" +.in 1i +Run the Miller-Rabin pseudoprime test of \fBa\fP with base \fBb\fP and set \fBresult\fP to \fBtrue\fP +if \fBa\fP is a strong pseudprime for base \fBb\fP and \fBfalse\fP otherwise. +.in -1i + +.LP +.BI "mp_err mp_prime_next_prime(mp_int *" a ", int " t ", bool " bbs_style ")" +.in 1i +Sets \fBa\fP to the next prime, even if \fBa\fP is prime itself. +.br +Argument \fBt\fP holds the number of Miller-Rabin tests to random bases and can also be used to steer +\fBmp_prime_is_prime\fP as described there. +.br +Argument \fBbbs_style\fP returns only primes \fBa \[==] 3 (mod 4)\fP if set to \fBtrue\fP. +.in -1i + +.LP +.BI "mp_err mp_prime_rabin_miller_trials(int " size ")" +.in 1i +Returns the number of Miller-Rabin tests to random bases necessary for RSA according to +FIPS 186-4. +.br +\fBsize\fP is the size of the prime in bits. +.br +The entries are pre-computed: +.br +.TS +tab(;), allbox; +c c c +r r l. +\fB<=size\fP;\fB#tests\fP ;\fBError\fP +.SP + 80;-1;Use deterministic algorithm for size <= 80 bits + 81;37;2^(-96) + 96;32;2^(-96) + 128;40;2^(-112) + 160;35;2^(-112) + 256;27;2^(-128) + 384;16;2^(-128) + 512;18;2^(-160) + 768;11;2^(-160) + 896;10;2^(-160) + 1024;12;2^(-192) + 1536;8;2^(-192) + 2048;6;2^(-192) + 3072;4;2^(-192) + 4096;5;2^(-256) + 5120;4;2^(-256) + 6144;4;2^(-256) + 8192;3;2^(-256) + 9216;3;2^(-256) + 10240;2;For bigger keysizes use always at least 2 Rounds +.TE +.in -1i + +.LP +.BI "mp_err mp_prime_rand(mp_int *" a ", int " t ", int " size ", int " flags ")" +.in 1i +Generates a random big prime \fBa\fP with \fBsize\fP bits. +.br +Argument \fBt\fP holds the number of Miller-Rabin tests to random bases and can also be used to steer +\fBmp_prime_is_prime\fP as described there. +.br +Argument \fBflags\fP determines the kind of prime: +.br +.TS +tab(;), allbox; +c c +l l. +\fBFlag\fP;\fBCondition\fP +MP_PRIME_BBS;make prime congruent to 3 mod 4 +MP_PRIME_SAFE;make sure (p-1)/2 is prime as well (implies MP_PRIME_BBS) +MP_PRIME_2MSB_ON;make the 2nd highest bit one +.TE +.in -1i + +.LP +.BI "mp_err mp_radix_size (const mp_int *" a ", int " radix ", int *" size ")" +.in 1i +Sets \fBsize\fP to the length of the ASCII string of the representation of big integer \fBa\fP in radix \fBradix\fP. +This includes the sign and the terminatong \fBNUL\fP. +.br +Returns \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP +.in -1i + +.LP +.BI "mp_err mp_radix_size_overestimate (const mp_int *" a ", int " radix ", int *" size ")" +.in 1i +Same as \fBmp_radix_size\fP but uses a rough, table based approximation instead of calling \fBmp_log_n\fP. +.br +Overestimates the result by some units: relative error is about \fB10^(-8)\fP. Experiments showed that +the absolute error should not go pass \fB5\fP. +.in -1i + +.LP +.BI "mp_err mp_rand(mp_int *" a ", int " digits ")" +.in 1i +Generates a random big integer \fBa\fP with a \fBdigits\fP number of limbs. +.br +\fBNOTE:\fP This function uses the same (P)RNG as the prime generating/testing functions. If that entropy +is precious see \fBmp_rand_source\fP to set another (P)RNG. +.in -1i + +.LP +.BI "void mp_rand_source(mp_err(*" source ")(void *" out ", size_t " size ")); +.in 1i +Sets the (P)RNG used for \fIall\fP functions in Libtommath, that need some random bytes. +.br +Set \fBsource\fP to \fBNULL\fP to get the original (Libtommath) source back. +.br +Example: +.br +.in +.5i +.nf +uint32_t prng_state = 0xdeadbeef; +uint32_t bad_prng(void) { + prng_state = (1103515245ul * prng_state + 12345ul) % 2147483648ul; + return prng_state; +} +mp_err myprng(void *p, size_t n) +{ + char *q = (char *)p; + while (n > 0u) { + int i; + uint32_t x = bad_prng(); + for (i = 0; (i < 4) && (n > 0u); ++i, --n) { + *q++ = (char)(x & 0xFFu); + x >>= 8; + } + } + return MP_OKAY; +} +mp_err some_monte_carlo_function(...) +{ + /* Use the the bad but fast P(R)NG */ + mp_rand_source(myprng); + ... + while(big_number--) { + mp_rand(a_bigint, n_bits); + ... + } + /* Reset and use (P)RNG provided by the platform */ + mp_rand_source(NULL); + ... +} +.in -.5i +.in -1i + +.LP +.BI "mp_err mp_read_radix (mp_int *" a ", const char *" str ", int " radix ")" +.in 1i +This will read a \fBNUL\fP terminated string in base \fBradix\fP from \fBstr\fP into \fBa\fP. +.br +Returns \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP. +.in -1i + +.LP +.BI "mp_err mp_reduce_2k_l(mp_int *" a ", const mp_int *" n ", const mp_int *" d ")" +.in 1i +Reduces \fBa\fP modulo \fBn\fP where \fBn\fP is of the form \fB2^p - d\fP where \fBd\fP +is a big integer. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "mp_err mp_reduce_2k(mp_int *" a ", const mp_int *" n ", mp_digit " d ")" +.in 1i +Reduces \fBa\fP modulo \fBn\fP where \fBn\fP is of the form \fB2^p - d\fP where \fBd\fP +is a \fBmp_digit\fP. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "mp_err mp_reduce_2k_setup(const mp_int *" a ", mp_digit *" d ")" +.in 1i +This will compute the required \fBd\fP value in \fB2^p - d\fP for the given moduli \fBa\fP where \fBd\fP +is a \fBmp_digit\fP. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "mp_err mp_reduce_2k_setup_l(const mp_int *" a ", mp_int *" d ")" +.in 1i +This will compute the required \fBd\fP value in \fB2^p - d\fP for the given moduli \fBa\fP where \fBd\fP +is a big integer. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "mp_err mp_reduce(const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +This will reduce \fBa\fP in place modulo \fBb\fP with the precomputed \fBmu\fP value in \fBc\fP. \fBa\fPmust be in +the range \fB0 <= a < b^2\fP. +.br +Belongs to the "Barrett reduction" method. +.in -1i + +.LP +.BI "bool mp_reduce_is_2k(const mp_int *" a ")" +.in 1i +Determines if \fBmp_reduce_2k\fP can be used with a \fBmp_digit\fP. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "bool mp_reduce_is_2k_l(const mp_int *" a ")" +.in 1i +Determines if \fBmp_reduce_2k\fP can be used with a big integer. +.br +Belongs to the "unrestricted diminished radix reduction" method. +.in -1i + +.LP +.BI "mp_err mp_reduce_setup(const mp_int *" a ", mp_int *" b ")" +.in 1i +Compute \fBmu\fP for Barrett reduction. +.in -1i + +.LP +.BI "mp_err mp_root_n(const mp_int *" a ", int " b ", mp_int *" c ")" +.in 1i +This computes \fBc = a^(1/b)\fP such that \fBc^b <= a\fP and \fB(c+1)^b > a\fP. Will return a positive root +only for even roots and return a root with the sign of the input for odd roots. For example, +performing \fB4^(1/2)\fP will return \fB2\fP whereas \fB(-8)^(1/3)\fP will return \fB-2\fP. +.br +Returns \fBMP_VAL\fP if \fBb < 0\fP or \fBb > MP_DIGIT_MAX\fP or when \fBb\fP is even and \fBa < 0\fP. +.in -1i + +.LP +.BI "void mp_rshd (mp_int *" a ", int " b ")" +.in 1i +Shift \fBa\fP right by \fBb\fP limbs: \fBa / 2^(b*MP_DIGIT_BIT)\fP. +.in -1i + +.LP +.BI "size_t mp_sbin_size(const mp_int *" a ")" +.in 1i +Returns the number of bytes (octets) required to store the signed copy of the integer \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_set_double(mp_int *" a ", double " b ")" +.in 1i +If the platform supports the floating point data type \fBdouble\fP (binary64) this function will +assign the integer part of \fBb\fP to the big integer \fBa\fP. +.br +Returns \fBMP_VAL\fP if \fBb\fP is \fB+/-infinity\fP or \fBNaN\fP +.in -1i + +.LP +.BI "void mp_set_i32 (mp_int *" a ", int32_t " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the signed 32 bit integer \fBb\fP. +.in -1i + +.LP +.BI "void mp_set_i64 (mp_int *" a ", int64_t " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the signed 64 bit integer \fBb\fP. +.in -1i + +.LP +.BI "void mp_set_l (mp_int *" a ", long " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fIsigned long\fP. +.in -1i + +.LP +.BI "void mp_set (mp_int *" a ", mp_digit " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fImp_digit\fP. +.in -1i + +.LP +.BI "void mp_set_u32 (mp_int *" a ", uint32_t " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the unsigned 32 bit integer \fBb\fP. +.in -1i + +.LP +.BI "void mp_set_u64 (mp_int *" a ", uint64_t " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the unsigned 64 bit integer \fBb\fP. +.in -1i + +.LP +.BI "void mp_set_ul (mp_int *" a ", unsigned long " b ")" +.in 1i +Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fIunsigned long\fP. +.in -1i + +.LP +.BI "mp_err mp_shrink (mp_int *" a ")" +.in 1i +This will remove excess digits of the \fImp_int\fP \fBa\fP. +.br +This method uses \fBrealloc\fP with all its problems, use with caution. +.in -1i + +.LP +.BI "mp_err mp_signed_rsh(const mp_int *" a ", int " b ", mp_int *" c ")" +.in 1i +Shifts right \fBa\fP by \fBb\fP bits with sign extension. +.in -1i + +.LP +.BI "mp_err mp_sqr (const mp_int *" a ", mp_int *" b ")" +.in 1i +Computes \fBa^2 = b\fP +.in -1i + +.LP +.BI "mp_err mp_sqrmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ")" +.in 1i +Computes \fBa^2 % b = c\fP. No optimization. +.in -1i + +.LP +.BI "mp_err mp_sqrt(const mp_int *" arg ", mp_int *" ret ")" +.in 1i +Computes \fBa^(1/2) = b\fP such that \fBb^2 <= a\fP. +.in -1i + +.LP +.BI "mp_err mp_sqrtmod_prime(const mp_int *" n ", const mp_int *" p ", mp_int *" r ")" +.in 1i +Computes\fBa^(1/2) % p = r\fP with \fBp\fP prime. Uses the Tonelli-Shanks algorithm. +.br +Does do some checks for \fBp\fP but no actual primality test. +.br +The prime \fBp\fP must be odd. +.in -1i + +.LP +.BI "mp_err mp_sub (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" +.in 1i +Computes \fBa - b = c\fP with \fBb\fP a big integer. +.in -1i + +.LP +.BI "mp_err mp_sub_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" +.in 1i +Computes \fBa - b = c\fP with \fBb\fP of type \fImp_digit\fP. +.in -1i + +.LP +.BI "mp_err mp_submod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" +.in 1i +Computes \fB(a - b) % c = d\fP. No optimization. +.in -1i + +.LP +.BI "mp_to_binary(" M ", " S ", " N ")" +.in 1i +Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 2\fP. +.in -1i + +.LP +.BI "mp_to_decimal(" M ", " S ", " N ")" +.in 1i +Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 10\fP. +.in -1i + +.LP +.BI "mp_to_hex(" M ", " S ", " N ")" +.in 1i +Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 16\fP. +.in -1i + +.LP +.BI "mp_to_octal(" M ", " S ", " N ")" +.in 1i +Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 8\fP. +.in -1i + +.LP +.BI "mp_err mp_to_radix (const mp_int *" a ", char *" str ", size_t " maxlen ", size_t *" written ", int " radix ")" +.in 1i +Stores upto \fBsize - 1\fP chars and always a \fBNULL\fP byte in \fBstr\fP and puts the number of characters written, +including \fBNUL\fP, in \fBwritten\fP. +.br +The caller is responsible to allocate a sufficient amount of memory for the buffer \fBstr\fP. Use \fBmp_radix_size\fP or +\fBmp_radix_size_overestimate\fP to have that number computed. +.br +Returns \fBMP_BUF\fP if \fBmaxlen < 2\fP +.br +Return \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP. +.in -1i + +.LP +.BI "mp_err mp_to_sbin(const mp_int *" a ", uint8_t *" b ", size_t " maxsize ", size_t *" len ")" +.in 1i +Store a \fBmaxlen\fP amount of the big integer in buffer \fBb\fP and puts the number of bytes written in \fBlen\fP. +.br +If \fBa\fP is negative \fBb0] = 1\fP and \fBb[0] = 0\fP otherwise. +.br +Returns \fBMP_BUF\fP if \fBmaxlen\fP is too small. Use \fBmp_sbin_size\fP to have that number computed. +.in -1i + +.LP +.BI "mp_err mp_to_ubin(const mp_int *" a ", uint8_t *" buf ", size_t " maxlen ", size_t *" written ")" +.in 1i +Store a \fBmaxlen\fP amount of the big integer in buffer \fBb\fP and puts the number of bytes written in \fBlen\fP. +.br +Returns \fBMP_BUF\fP if \fBmaxlen\fP is too small. Use \fBmp_sbin_size\fP to have that number computed. +.in -1i + +.LP +.BI "size_t mp_ubin_size(const mp_int *" a ")" +.in 1i +Returns the number of bytes (octets) required to store the unsigned copy of the big integer \fBa\fP. +.in -1i + +.LP +.BI "mp_err mp_unpack(mp_int *" rop ", size_t " count ", mp_order " order ", size_t " size ", mp_endian " endian ", size_t " nails ", const void *" op ")" +.in 1i +Implements the similarly working GMP functions as described at \fIhttp://gmplib.org/manual/Integer-Import-and-Export.html\fP. +See also: \fBmp_pack\fP for more details. +.in -1i + +.LP +.BI "mp_err mp_xor (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" +.in 1i +Computes bit-wise xor \fBa ^ b = c\fP. Negative numbers are treated as if they are in two-complement representation. +.br +Returns \fBMP_MEM\fP if the reallocation of memory in \fBmp_grow\fP failed. +.in -1i + +.LP +.BI "void mp_zero(mp_int *" a ")" +.in 1i +Sets \fBa\fP to zero. +.in -1i + +.LP +.SS "TYPES" +.\"TODO: sort alphabetically +.BI mp_digit +.in 1i +An unsigned machine integer able to hold \fBMP_DIGIT_BIT + 1\fP bits. +.br +This type is defined in \fBtommath.h\fP +.in -1i +.LP +.BI mp_word +.in 1i +An unsigned integer able to hold a value of size \fB2 * MP_DIGIT_MAX + 1\fP. +This type is defined in \fBtommath_private.h\fP +.in -1i +.LP +.BI mp_int +.in 1i +The internal structure of Libtommath's big integer type \fBmp_int\fP. + +.in 1.5i +.nf +typedef struct { + int used, alloc; + mp_sign sign; + mp_digit *dp; +} mp_int; +.in -1.5i +.in -1i +.LP +.BI mp_sign +.in 1i +The sign of Libtommath's big integer type \fBmp_int\fP + +.in 1.5i +.nf +typedef enum { + MP_ZPOS = 0, /* positive */ + MP_NEG = 1 /* negative */ +} mp_sign; +.in -1.5i +.in -1i + +.LP +.BI mp_ord +.in 1i +Results of comparing with the functions \fBmp_cmp()\fP and \fBmp_cmp_d()\fP. + +.in 1.5i +.nf +typedef enum { + MP_LT = -1, /* less than */ + MP_EQ = 0, /* equal */ + MP_GT = 1 /* greater than */ +} mp_ord; +.in -1.5i +.in -1i + +.LP +.BI mp_err +.in 1i +The handful of different errors Libtommath can throw. + +.in 1.5i +.nf +typedef enum { + MP_OKAY = 0, /* no error */ + MP_ERR = -1, /* unknown error */ + MP_MEM = -2, /* out of mem */ + MP_VAL = -3, /* invalid input */ + MP_ITER = -4, /* maximum iterations reached */ + MP_BUF = -5, /* buffer overflow, supplied buffer too small */ + MP_OVF = -6 /* mp_int overflow, too many digits */ +} mp_err; +.in -1.5i +.in -1i + +.LP +.BI mp_order +.in 1i +Bit order. If the most signifcant bit comes first or the least significant one. +.br +Not to be mistaken for \fBmp_ord\fP. + +.in 1.5i +.nf +typedef enum { + MP_LSB_FIRST = -1, + MP_MSB_FIRST = 1 +} mp_order; +.in -1.5i +.in -1i + +.LP +.BI mp_endian +.in 1i +Byte order. Only big and little endian are supported. \fBMP_NATIVE_ENDIAN\fP refers to the local (detected) +endianess. + +.in 1.5i +.nf +typedef enum { + MP_LITTLE_ENDIAN = -1, + MP_NATIVE_ENDIAN = 0, + MP_BIG_ENDIAN = 1 +} mp_endian; +.in -1.5i +.in -1i + +.LP +.BI hval +.in 1i +Type holding the hash produced by \fBmp_hash\fP. Either a 32 bit or a 64 bit unsigned type. +.in -1i + +.LP +.SS "MACROS" +.LP +.BI MP_DIGIT_BIT +.in 1i +The size in bits of a limb. +.br +The value depends on the size of the biggest available native integer type. +.TS +tab(;) allbox; +c c c +c l l. +\fBarch bits\fP;\fBMP_DIGIT_BIT\fP;\fBMACRO\fP +16;15;MP_16BIT +32;28, (31);MP_32BIT, (MP_31BIT) (1) +64;60, (28);MP_64BIT, (MP_64BIT) (2) +32/64;28;MP_28BIT (3) +.TE + +(1) The size 31 bit reduces some of the optimizations, especially COMBA. +.br +(2) Some C-compilers do not offer 16 byte integers. One of them is very famous. +.br +(3) Default when all tests to search for something better fail. + +.br +\fBNOTE:\fP ISO C 23 introduced \fB_BitInt(n)\fP which would allow 16 byte integers even +on non 64 bit architectures. Not much support as of the time of this writing (LLVM does, for example). +.in -1i + +.LP +.BI MP_PRIME_BBS +.in 1i +Generate a BBS style prime. (See: mp_prime_rand) +.in -1i + +.LP +.BI MP_PRIME_SAFE +.in 1i +Generate a safe prime such that (p-1)/2 == prime. (See: mp_prime_rand) +.in -1i + +.LP +.BI MP_PRIME_2MSB_ON +.in 1i +Force 2nd most siginficant bit to be 1 (one). when generating primes. (See: mp_prime_rand) +.in -1i + +.LP +.BI MP_DIGIT_MAX +.in 1i +Largest value a \fBmp_digit\fP can hold: \fB-1 + 2^MP_DIGIT_BIT\fP. +.in -1i + +.LP +.BI MP_MASK +.in 1i +Holds the same value as \fBMP_DIGIT_MAX\fP. +.br +\fBNOTE:\fP this macro computes the value, \fBMP_DIGIT_MAX\fP is a copy. +.in -1i + + +.LP +.SS "GLOBAL VARIABLES" +.\" TODO: change if COMBA gets its heap alternative +Libtommath uses no global variables, it is threadsafe. +.br +But some global variables are there to allow for e.g.: tuning and can hence be abused. But shouldn't. + +.LP +.BI "extern int MP_MUL_KARATSUBA_CUTOFF" +.in 1i +Sets the cutoff value when Karatsuba multiplication comes in if the macro \fBMP_FIXED_CUTOFFS\fP is not defined. +.in -1i + + +.LP +.BI "extern int MP_SQR_KARATSUBA_CUTOFF" +.in 1i +Sets the cutoff value when Karatsuba squaring comes in if the macro \fBMP_FIXED_CUTOFFS\fP is not defined. +.in -1i + + +.LP +.BI "extern int MP_MUL_TOOM_CUTOFF" +.in 1i +Sets the cutoff value when Toom-Cook 3-way multiplication comes in if the macro \fBMP_FIXED_CUTOFFS\fP is not defined. +.in -1i + + +.LP +.BI "extern int MP_SQR_TOOM_CUTOFF" +.in 1i +Sets the cutoff value when Toom-Cook 3-way squaring comes in if the macro \fBMP_FIXED_CUTOFFS\fP is not defined. +.in -1i + +.LP +.SH "EXAMPLES" +.\" TODO: does it even make sense to have examples? +.LP +.SS "Is \fIn\fP a Perfect Power" +A function that uses a mix of libtommath's functions. + +.nf +static mp_err mp_is_perfect_power(const mp_int *n, bool *result, + mp_int *rootout, mp_int *exponent) +{ + mp_int root, power, prime, max; + int highbit, lowbit, p; + mp_err err = MP_OKAY; + + *result = false; + + /* No negative numbers. For now. */ + if (mp_cmp_d(n, 4) == MP_LT) { + err = MP_VAL; + goto LTM_OUT; + } + + /* Compute floor(log_2(n)) */ + highbit = mp_count_bits(n) - 1; + + /* MP_IS_POWER_OF_TWO(n) is a macro in tommath_private.h */ + if (MP_IS_POWER_OF_TWO(n)) { + *result = true; + if (exponent != NULL) { + if ((err = mp_set_l(exponent, (long)highbit)) != MP_OKAY) { + return err; + } + } + if (rootout != NULL) { + if ((err = mp_set_l(rootout, 2l)) != MP_OKAY) { + return err; + } + } + return err; + } + /* Initialize the needed variables all at once */ + if ((err = mp_init_multi(&root, &power, &prime, &max, NULL)) != MP_OKAY) { + return err; + } + /* a long is at least as big as an int */ + if( (err = mp_set_l(&max, (long)highbit) ) != MP_OKAY) goto LTM_ERR; + + /* mp_prime_next_prime() returns the next prime, so start with a preceding value */ + mp_set(&prime, 2u); + + while (mp_cmp(&prime, &max) != MP_GT) { + /* Deterministic up to 2^82 but the largest value possible is < INT_MAX */ + if ((err = mp_prime_next_prime(&prime, -1, false)) != MP_OKAY) goto LTM_ERR; + p = (int)mp_get_l(&prime); + if ((err = mp_root_n(n, p, &root)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_expt_n(&root, p, &power)) != MP_OKAY) goto LTM_ERR; + + if (mp_cmp(n, &power) == MP_EQ) { + *result = true; + if (rootout != NULL) { + mp_exch(&root, rootout); + } + if (exponent != NULL) { + if ((e = mp_set_l(exponent, (long)p)) != MP_OKAY) goto LTM_ERR; + } + } + } + +LTM_OUT: + if (rootout != NULL) { + if ((err = mp_set(rootout, 0u)) != MP_OKAY) goto LTM_ERR; + } + if (exponent != NULL) { + if ((err = mp_set(exponent, 0u)) != MP_OKAY) goto LTM_ERR; + } +LTM_ERR: + mp_clear_multi(&root, &power,&prime, NULL); + return err; +} +.LP +.SS "Pi by Binary Splitting" +Compute digits of pi using Manchin's formula from 1706. A classic. + +.nf +#include +#include +#include +#include +#include +#include + +static int mp_acot_binary_splitting( + mp_int * q, mp_int * a, mp_int * b, mp_int * P, + mp_int * Q, mp_int * R, int * idx) +{ + mp_err err; + mp_int p1, q1, r1, p2, q2, r2, t1, t2, one; + if ((err = mp_init_multi( + &p1, &q1, &r1, &p2, &q2, + &r2, &t1, &t2, &one, NULL)) != MP_OKAY) { + return err; + } + + err = MP_OKAY; + mp_set(&one, 1); + + if ((err = mp_sub(b, a, &t1)) != MP_OKAY) goto LTM_ERR; + if (mp_cmp(&t1, &one) == MP_EQ) { + if ((err = mp_mul_2d(a, 1, &t1)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add_d(&t1, 3, &t1)) != MP_OKAY) goto LTM_ERR; + mp_set(P, 1); + if ( ((*idx) & 1) == 0 ) { + P->sign = MP_NEG; + } + (*idx)++; + if ((err = mp_mul(&t1, q, Q)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_copy(&t1, R)) != MP_OKAY) goto LTM_ERR; + /* Done */ + goto LTM_ERR; + } + + if ((err = mp_add(a, b, &t1)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2d(&t1, 1, &t1, NULL)) != MP_OKAY) goto LTM_ERR; + + + if ((err = mp_acot_binary_splitting( + q, a, &t1, &p1, &q1, &r1, idx)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_acot_binary_splitting( + q, &t1, b, &p2, &q2, &r2, idx)) != MP_OKAY) goto LTM_ERR; + + /* P = q2*p1 + r1*p2 */ + if ((err = mp_mul(&q2, &p1, &t1)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_mul(&r1, &p2, &t2)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add(&t1, &t2, P)) != MP_OKAY) goto LTM_ERR; + /* Q = q1*q2 */ + if ((err = mp_mul(&q1, &q2, Q)) != MP_OKAY) goto LTM_ERR; + /* R = r1*r2 */ + if ((err = mp_mul(&r1, &r2, R)) != MP_OKAY) goto LTM_ERR; + + LTM_ERR: + mp_clear_multi(&p1, &q1, &r1, &p2, &q2, &r2, &t1, &t2, &one, NULL); + return err; +} + + +int main(int argc, char **argv) +{ + mp_int N, P, Q, R, zero, EPS, t1, t2, t5, t239; + mp_err err = MP_OKAY; + int idx = 0; + long eps, dec; + + if(argc != 2) { + fprintf(stderr, "Usage %s bits of precision", argv[0]); + exit(EXIT_FAILURE); + } + + errno = 0; + eps = strtol(argv[1],NULL,10); + if ((errno == ERANGE && (eps == LONG_MAX || eps == LONG_MIN)) + || (errno != 0 && eps == 0)) { + fprintf(stderr,"Error reading precision. Reason: %s\n", + strerror(errno)); + exit(EXIT_FAILURE); + } + + if( (err = mp_init_multi( + &N, &P, &Q, &R, &zero, &EPS, &t1, &t2, &t5, &t239, NULL) ) != MP_OKAY) { + fprintf(stderr,"Error initializing mp_ints. Reason: %s\n", + mp_error_to_string(err)); + exit(EXIT_FAILURE); + } + + /* Machin's 1706 */ + mp_set(&t5, 5u); + mp_set(&t239, 239u); + mp_set_l(&EPS, eps); + + if( (err = mp_sqr(&t5, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_acot_binary_splitting( + &t1, &zero, &EPS, &P, &Q, &R, &idx) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_add(&P, &Q, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul_2d(&t1, (int)eps, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul(&Q, &t5, &t2) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_div(&t1, &t2, &t5, NULL) ) != MP_OKAY) goto LTM_ERR; + + if( (err = mp_sqr(&t239, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_acot_binary_splitting( + &t1, &zero, &EPS, &P, &Q, &R, &idx) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_add(&P, &Q, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul_2d(&t1, (int)eps, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul(&Q, &t239, &t2) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_div(&t1, &t2, &t239, NULL) ) != MP_OKAY) goto LTM_ERR; + + if( (err = mp_mul_2d(&t5, 2, &t5) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_sub(&t5, &t239, &t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul_2d(&t1, 2, &t1) ) != MP_OKAY) goto LTM_ERR; + + /* 146/485 ~ 1/log_2(10) for about 7 decimal digits */ + dec = (eps * 146) / 485; + mp_set(&t2, 10); + if( (err = mp_expt_n(&t2, (int)dec, &t2) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_mul(&t1,&t2,&t1) ) != MP_OKAY) goto LTM_ERR; + if( (err = mp_div_2d(&t1, (int)eps, &t1, NULL) ) != MP_OKAY) goto LTM_ERR; + + if( (err = mp_fwrite(&t1,10,stdout) ) != MP_OKAY) goto LTM_ERR; + + mp_clear_multi(&N, &P, &Q, &R, &zero, &EPS, &t1, &t2, &t5, &t239, NULL); + exit(EXIT_SUCCESS); +LTM_ERR: + mp_clear_multi(&N, &P, &Q, &R, &zero, &EPS, &t1, &t2, &t5, &t239, NULL); + exit(EXIT_FAILURE); +} + + + +.LP +.SH "SEE ALSO" + +.IR https://github.com/libtom/libtommath + +.SH BUGS + +Please report all bugs and other incommodities at +.IR https://github.com/libtom/libtommath/issues + +.SH AUTHORS AND LICENSE +Version 1.2.0 +.LP +Copyright (C) 2002 Tom St Denis + +.ad c + +The LibTom license + +.ad n +.LP +This is free and unencumbered software released into the public domain. +.LP +Anyone is free to copy, modify, publish, use, compile, sell, or +distribute this software, either in source code form or as a compiled +binary, for any purpose, commercial or non-commercial, and by any +means. +.LP +In jurisdictions that recognize copyright laws, the author or authors +of this software dedicate any and all copyright interest in the +software to the public domain. We make this dedication for the benefit +of the public at large and to the detriment of our heirs and +successors. We intend this dedication to be an overt act of +relinquishment in perpetuity of all present and future rights to this +software under copyright law. +.LP +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR +OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +OTHER DEALINGS IN THE SOFTWARE. +.LP +For more information, please refer to + +." end of man page From f63fce110e86f06a5d4012594f2d4dfefb9c1afd Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 16:33:22 +0200 Subject: [PATCH 259/304] Check whether all API's are included in manpage Signed-off-by: Steffen Jaeckel --- helper.pl | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/helper.pl b/helper.pl index e5ad27ac5..53658614c 100755 --- a/helper.pl +++ b/helper.pl @@ -105,6 +105,7 @@ sub check_comments { sub check_doc { my $fails = 0; + my $man = read_file('doc/tommath.3'); my $tex = read_file('doc/bn.tex'); my $tmh = read_file('tommath.h'); my @functions = $tmh =~ /\n\s*[a-zA-Z0-9_* ]+?(mp_[a-z0-9_]+)\s*\([^\)]+\)\s*[MP_WUR]+?;/sg; @@ -123,6 +124,18 @@ sub check_doc { $fails++ } } + for my $n (sort @functions) { + if ($man !~ /.BI.*$n/) { + warn "[missing_man_entry_for_function] $n\n"; + $fails++ + } + } + for my $n (sort @macros) { + if ($man !~ /.BI.*$n/) { + warn "[missing_man_entry_for_macro] $n\n"; + $fails++ + } + } warn( $fails > 0 ? "check_doc: FAIL $fails\n" : "check-doc: PASS\n" ); return $fails; } From c166d760949d880b6b85a99fdd4aa417b11264a3 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 16:57:05 +0200 Subject: [PATCH 260/304] Trim trailing spaces Signed-off-by: Steffen Jaeckel --- doc/tommath.3 | 262 +++++++++++++++++++++++++------------------------- 1 file changed, 131 insertions(+), 131 deletions(-) diff --git a/doc/tommath.3 b/doc/tommath.3 index 120a399bb..e0eeae2b4 100644 --- a/doc/tommath.3 +++ b/doc/tommath.3 @@ -9,7 +9,7 @@ libtommath - a big integer library .fi .ft .SH DESCRIPTION -.I LibTomMath +.I LibTomMath provides a series of efficient and carefully written functions for manipulating large integer numbers. .br @@ -29,87 +29,87 @@ Returns \fBMP_VAL\fP if b < 0 .in -1i -.LP +.LP .BI "mp_err mp_abs (const mp_int *" a ", mp_int *" b ")" .in 1i Computes the absolute value of \fBa\fP and puts the result in \fBb\fP. .in -1i -.LP +.LP .BI "mp_err mp_add (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Computes \fBa + b = c\fP. .in -1i -.LP +.LP .BI "mp_err mp_add_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" .in 1i Computes \fBa + b = c\fP where \fBb\fP is of type \fBmp_digit\fP. .in -1i -.LP +.LP .BI "mp_err mp_addmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" .in 1i Computes \fB(a + b) % c = d\fP. No optimizations. .in -1i -.LP +.LP .BI "mp_err mp_and (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" .in 1i Computes bitwise or \fBa & b = c\fP. Negative numbers are treated as if they are in two-complement representation. .in -1i -.LP +.LP .BI "void mp_clamp(mp_int *" a "); .in 1i This is used to ensure that leading zero digits are trimmed and the leading \fBused\fP digit will be non-zero. It also fixes the sign if there are no more leading digits. .in -1i -.LP +.LP .BI "void mp_clear (mp_int *" a ")" .in 1i Frees the heap memory of \fBa\fP. .in -1i -.LP +.LP .BI "int mp_cnt_lsb(const mp_int *" a ")" .in 1i Returns the position of the lowest bit set. .in -1i -.LP +.LP .BI "mp_err mp_complement(const mp_int *" a ", mp_int *" b ")" .in 1i Computes the 2-complement \fIb = ~a\fP. .in -1i -.LP +.LP .BI "mp_err mp_copy (const mp_int *" a ", mp_int *" b ")" .in 1i Makes a deep copy of \fBa\fP into \fBb\fP. .in -1i -.LP +.LP .BI "int mp_count_bits(const mp_int *" a ")" .in 1i Returns the position of the highest bit set. .in -1i -.LP +.LP .BI "mp_err mp_decr(mp_int *" a ")" .in 1i Computes \fBa--\fP. .in -1i -.LP +.LP .BI "mp_err mp_div_2(const mp_int *" a ", mp_int *" b "); .in 1i Computes \fBa >> 1 = b\fP. .in -1i -.LP +.LP .BI "mp_err mp_div_2d (const mp_int *" a ", int " b ", mp_int *" c ", mp_int *" d "); .in 1i Computes \fBa >> b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. @@ -119,7 +119,7 @@ Set the argument for quotient and/or remainder to \fBNULL\fP to ignore the respe Returns \fBMP_VAL\fP if \fBb < 0\fP .in -1i -.LP +.LP .BI "mp_err mp_div (const mp_int *" a ", const mp_int *" b ", mp_int *" c ", mp_int *" d ")" .in 1i Computes \fBa / b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. @@ -132,7 +132,7 @@ This function calls one of either: \fBs_mp_div_recursive\fP, \fBs_mp_div_school\ Returns \fBMP_VAL\fP if \fBb = 0\fP .in -1i -.LP +.LP .BI "mp_err mp_div_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ", mp_digit *" d ")" .in 1i Computes \fBa / b = c + d\fP with \fBc\fP the optional quotient and \fBd\fP the optional remainder. @@ -141,7 +141,7 @@ Set the argument for quotient and/or remainder to \fBNULL\fP to ignore the respe Returns \fBMP_VAL\fP if \fBb = 0\fP. .in -1i -.LP +.LP .BI "bool mp_dr_is_modulus(const mp_int *" a ")" .in 1i Returns \fBtrue\fP if the modulus \fBa\fP is of the form below that allows for a diminished radix reduction, \fBfalse\fP otherwise. @@ -149,32 +149,32 @@ Returns \fBtrue\fP if the modulus \fBa\fP is of the form below that allows for a \fB\[*b]^k - p\fP for some \fBk >= 0\fP and \fB0 < p < \[*b]\fP where \fB\[*b]\fP is the radix. .in -1i -.LP +.LP .BI "mp_err mp_dr_reduce(mp_int *" a ", const mp_int *" b ", mp_digit " mp ")" .in 1i This reduces \fBa\fP in place modulo \fBb\fP with the pre-computed value \fBmp\fP. \fBb\fP must be of a restricted diminished radix form and \fBa\fP must be in the range \fB0 <= a < b^2\fP .in -1i -.LP +.LP .BI "void mp_dr_setup(const mp_int *" a ", mp_digit *" d ")" .in 1i This computes the value required for the modulus \fBa\fP and stores it in \fBd\fP. .in -1i -.LP +.LP .BI "void mp_exch (mp_int *" a ", mp_int *" b ")" .in 1i Swaps, but just the pointers. .in -1i -.LP +.LP .BI "const char *mp_error_to_string(mp_err " code ")" .in 1i Returns a short ASCII message describing the error code given in \fBcode\fP. .in -1i -.LP +.LP .BI "mp_err mp_exptmod (const mp_int *" G ", const mp_int *" X ", const mp_int *" P ", mp_int *" Y ")" .in 1i This computes \fBY \[==] G^X (mod P)\fP using a variable width sliding window @@ -192,7 +192,7 @@ Returns \fBMP_VAL\fP if \fBP < 0\fP. Returns \fBMP_VAL\fP if none of the underlying internal functions have been compiled in. .in -1i -.LP +.LP .BI "mp_err mp_expt_n(const mp_int *" a ", int " b ", int *" c ")" .in 1i Computes \fBa^b = c\fP. Simple binary exponentiation, no further optimizations. @@ -200,7 +200,7 @@ Computes \fBa^b = c\fP. Simple binary exponentiation, no further optimizations. \fBb\fP must be positive. .in -1i -.LP +.LP .BI "mp_err mp_exteuclid(const mp_int *" a ", const mp_int *" b ", mp_int *" U1 ", mp_int *" U2 ", mp_int *" U3 ")" .in 1i Computes the extended Euclidean algorithm: \fBa * U1 + b * U2 = U3\fP @@ -208,7 +208,7 @@ Computes the extended Euclidean algorithm: \fBa * U1 + b * U2 = U3\fP Set the argument for \fBU1, U2, U3\fP to \fBNULL\fP to ignore the respective output. .in -1i -.LP +.LP .BI "mp_err mp_fread(mp_int *" a ", int " radix ", FILE *" stream ")" .in 1i Reads a number in radix \fBradix\fP from file \fBstream\fP and converts it into the big integer \fBa\fP. @@ -218,7 +218,7 @@ Returns \fBMP_VAL\fP if radix is not in the range \fB2 <= radix <= 64\fP. Returns \fBMP_ERR\fP if no digits were found in \fBstream\fP. .in -1i -.LP +.LP .BI "mp_err mp_from_sbin(mp_int *" a ", const uint8_t *" b ", size_t " size ")" .in 1i This will read in an big-endian array of octets from \fBb\fP of length @@ -227,14 +227,14 @@ This will read in an big-endian array of octets from \fBb\fP of length If the first octet of the data is zero, the sign of the big-integer will be \fBMP_NEG\fP and \fBMP_ZPOS\fP otherwise. .in -1i -.LP +.LP .BI "mp_err mp_from_ubin(mp_int *" a ", uint8_t *" b ", size_t " size ")" .in 1i This will read in an big-endian array of octets from \fBb\fP of length \fBsize\fP into \fBa\fP. The resulting big-integer \fBa\fP will always be positive. .in -1i -.LP +.LP .BI "mp_err mp_fwrite(const mp_int *" a ", int " radix ", FILE *" stream ")" .in 1i Writes \fBa\fP as a string representing the big integer in radix \fBradix\fP to file \fBstream\fP. @@ -246,13 +246,13 @@ Returns \fBMP_ERR\fP if there was a problem writing to the file. Returns \fBMP_VAL\fP if radix is not in the range \fB2 <= radix <= 64\fP. .in -1i -.LP +.LP .BI "mp_err mp_gcd (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Compute the greatest common divisor of \fBa\fP and \fBb\fP and store it in \fBc\fP. .in -1i -.LP +.LP .BI "double mp_get_double(const mp_int *" a ")" .in 1i Returns a float of type \fBdouble\fP (binary64). @@ -263,7 +263,7 @@ Will overflow if the big integer is too big. change the rounding mode. .in -1i -.LP +.LP .BI "int32_t mp_get_i32 (const mp_int *" a ")" .in 1i Returns a signed 32-bit integer from big-integer \fBa\fP. @@ -283,7 +283,7 @@ mp_get_mag_ul;5543444065158278130 .TE .in -1i -.LP +.LP .BI "int64_t mp_get_i64 (const mp_int *" a ")" .in 1i Returns a signed 64-bit integer from big-integer \fBa\fP. @@ -291,7 +291,7 @@ Returns a signed 64-bit integer from big-integer \fBa\fP. \fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. .in -1i -.LP +.LP .BI "long mp_get_l (const mp_int *" a ")" .in 1i Returns a signed \fBlong\fP from big-integer \fBa\fP. @@ -299,7 +299,7 @@ Returns a signed \fBlong\fP from big-integer \fBa\fP. \fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. .in -1i -.LP +.LP .BI "uint32_t mp_get_mag_u32 (const mp_int *" a ")" .in 1i Returns an unsigned 32 bit integer from big-integer \fBa\fP. @@ -307,7 +307,7 @@ Returns an unsigned 32 bit integer from big-integer \fBa\fP. \fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. .in -1i -.LP +.LP .BI "uint64_t mp_get_mag_u64 (const mp_int *" a ")" .in 1i Returns an unsigned 64 bit integer from big-integer \fBa\fP. @@ -315,19 +315,19 @@ Returns an unsigned 64 bit integer from big-integer \fBa\fP. \fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. .in -1i -.LP +.LP .BI "uint32_t mp_get_u32 (const mp_int *" a ")" .in 1i Convenience macro for \fBmp_get_mag_u32()\fP. .in -1i -.LP +.LP .BI "uint64_t mp_get_u64 (const mp_int *" a ")" .in 1i Convenience macro for \fBmp_get_mag_u64()\fP. .in -1i -.LP +.LP .BI "mp_err mp_grow (mp_int *" a ", int " size ")" .in 1i This will grow the array of digits of \fBa\fP to \fBsize\fP. @@ -335,7 +335,7 @@ This will grow the array of digits of \fBa\fP to \fBsize\fP. Returns \fBMP_MEM\fP if the functions fails to allocate enough memory. .in -1i -.LP +.LP .BI "mp_err mp_hash (mp_int *" a ", mp_hval *" hash ")" .in 1i This will create the hash of \fBa\fP following the \fIFNV-1a\fP algorithm as described on @@ -345,7 +345,7 @@ help of this function one can use an \fBmp_int\fP as a key in a hash table. \fBNOTE:\fP The hashing is not stable over different widths of a \fBmp_digit\fP. .in -1i -.LP +.LP .BI "mp_err mp_incr(mp_int *" a ")" .in 1i Computes \fBa++\fP. @@ -353,31 +353,31 @@ Computes \fBa++\fP. Returns \fBMP_MEM\fP if the reallocation of memory in \fBmp_grow\fP failed. .in -1i -.LP +.LP .BI "mp_err mp_init_copy (mp_int *" a ", mp_int *" b ")" .in 1i Initializes \fBa\fP and copies \fBb\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init_i32 (mp_int *" a ", int32_t " b "); .in 1i Initializes \fBa\fP and copies the signed 32 bit integer \fBb\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init_i64 (mp_int *" a ", int64_t " b ")" .in 1i Initializes \fBa\fP and copies the signed 64 bit integer \fBb\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init_l (mp_int *" a ", long " b ")" .in 1i Initializes \fBa\fP and copies the signed integer \fBb\fP of type \fBlong\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init (mp_int *" a ")" .in 1i Initializes \fBa\fP. @@ -390,19 +390,19 @@ It actively sets all limbs to zero, overwriting what was there before, sets the and \fBa.used\fP to zero. .in -1i -.LP +.LP .BI "mp_err mp_init_multi(mp_int *" mp ", " ... ")" .in 1i Initialize a \fBNULL\fP terminated series of \fBmp_int\fPs. .in -1i -.LP +.LP .BI "mp_err mp_init_set (mp_int *" a ", mp_digit " b ")" .in 1i Initializes \fBa\fP and sets it to the \fBmp_digit\fP \fBb\fP .in -1i -.LP +.LP .BI "mp_err mp_init_size (mp_int *" a ", int " size ")" .in 1i Initializes \fBa\fP with pre-grown to a \fBsize\fP number of limbs. @@ -412,25 +412,25 @@ If \fBsize\fP is smaller than the minimum (see \fBmp_init\fP for details) \fBsi Returns \fBMP_OVF\fP if \fBsize\fP is larger than an \fBmp_int\fP is able to hold. .in -1i -.LP +.LP .BI "mp_err mp_init_u32 (mp_int *" a ", uint32_t " b ")" .in 1i Initializes \fBa\fP and copies the unsigned 32 bit integer \fBb\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init_u64 (mp_int *" a ", uint64_t " b ")" .in 1i Initializes \fBa\fP and copies the unsigned 64 bit integer \fBb\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_init_ul (mp_int *" a ", unsigned long " b ")" .in 1i Initializes \fBa\fP and copies the unsigned integer \fBb\fP of type \fBunsigned long\fP into \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_invmod (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Computes the multiplicative inverse of \fBa\fP modulo \fBb\fP and stores the result in \fBv\fP such that @@ -447,36 +447,36 @@ Returns \fBMP_VAL\fP if \fBb <= 1\fP Returns \fBtrue\fP if \fBa\fP is even, \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "bool mp_isneg(mp_int *" a ")" .in 1i Returns \fBtrue\fP if \fBa < 0\fP, \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "bool mp_isodd(const mp_int *" a ")" .in 1i Returns \fBtrue\fP if \fBa\fP is odd, \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "mp_err mp_is_square(const mp_int *" arg ", bool *" ret ")" .in 1i Sets \fBret\fP to \fBtrue\fP if \fBarg\fP is a square, \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "bool mp_iszero(mp_int *" a ")" .in 1i Returns \fBtrue\fP if \fBa = 0\fP, \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "mp_err mp_kronecker (const mp_int *" a ", const mp_int *" p ", int *" c ")" .in 1i Computes the Kronecker symbol (an extension of the Jacobi symbol) for \fBa\fP with respect to \fBp\fP with \fB(a, p) in Z\fP. If \fBp\fP is prime this essentially computes the -Legendre symbol. The result is stored in \fBc\fP and can take on one of three values \fB{-1, 0, 1}\fP. +Legendre symbol. The result is stored in \fBc\fP and can take on one of three values \fB{-1, 0, 1}\fP. .TS tab(;); r l. @@ -486,13 +486,13 @@ r l. .TE .in -1i -.LP +.LP .BI "mp_err mp_lcm (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Computes the least common multiple as \fB|a * b|/gcd(a, b)\fP. .in -1i -.LP +.LP .BI "mp_err mp_log(const mp_int *" a ", const mp_int *" base ", int *" c ")" .in 1i Computes \fBlog_b(a)\fP such that \fB(log_b a)^b <= a\fP. @@ -500,7 +500,7 @@ Computes \fBlog_b(a)\fP such that \fB(log_b a)^b <= a\fP. Returns \fBMP_VAL\fP if \fBa <= 0\fP or \fBb < 2\fP. .in -1i -.LP +.LP .BI "mp_err mp_log_n(const mp_int *" a ", int " base ", int *" c ")" .in 1i Computes \fBlog_b(a)\fP such that \fB(log_b a)^b <= a\fP. @@ -509,13 +509,13 @@ Convenience function that is a wrapper for \fBmp_log\fP doing the conversion of to a big integer. .in -1i -.LP +.LP .BI "mp_err mp_lshd (mp_int *" a ", int " b ")" .in 1i Shift \fBa\fP left by \fBb\fP limbs: \fBa * 2^(b*MP_DIGIT_BIT)\fP. .in -1i -.LP +.LP .BI "mp_err mp_mod_2d(const mp_int *" a ", int " b ", mp_int *" c ")" .in 1i Compute \fBa % 2^b\fP. @@ -523,7 +523,7 @@ Compute \fBa % 2^b\fP. .in -1i -.LP +.LP .BI "mp_err mp_mod(const mp_int *" a ",const mp_int *" b ", mp_int *" c ")" .in 1i Compute \fBa \[==] c mod b\fP. @@ -531,13 +531,13 @@ Compute \fBa \[==] c mod b\fP. \fB0 <= c < b\fP if \fBb > 0\fP and \fBb < c <= 0\fP if \fBb < 0\fP. .in -1i -.LP +.LP .BI "mp_err mp_mod_d(const mp_int *" a ", mp_digit " b ", mp_digit *" c ")" .in 1i Computes the remainder of \fBa / b\fP. .in -1i -.LP +.LP .BI "mp_err mp_montgomery_calc_normalization(mp_int *" a ", mp_int *" b ")" .in 1i Computes \fBR = r^n\fP for Montgomery reduction where \fBn\fP is size of \fBa\fP in bits and @@ -546,7 +546,7 @@ Computes \fBR = r^n\fP for Montgomery reduction where \fBn\fP is size of \fBa\fP See \fBmp_montgomery_reduce\fP for some example code. .in -1i -.LP +.LP .BI "mp_err mp_montgomery_reduce(mp_int *" a ", mp_int *" m ", mp_digit " mp ")" .in 1i Reduces \fBa\fP in place modulo \fBm\fP with the pre-computed value \fBmp\fP (\fBa*mp^(-1) \[==] x (mod m) \fP). @@ -623,7 +623,7 @@ int main(void) \} .in -1i -.LP +.LP .BI "mp_err mp_montgomery_setup(const mp_int *" a ", mp_digit *" mp ")" .in 1i For the given odd modulus \fBa\fP the pre-computation value is placed in \fBmp\fP. @@ -633,13 +633,13 @@ For the given odd modulus \fBa\fP the pre-computation value is placed in \fBmp\f See \fBmp_montgomery_reduce\fP for some example code. .in -1i -.LP +.LP .BI "mp_err mp_mul_2(const mp_int *" a ", mp_int *" b ")" .in 1i Computes \fBb = 2 * a\fP. .in -1i -.LP +.LP .BI "mp_err mp_mul_2d(const mp_int *" a ", int " b ", mp_int *" c ")" .in 1i Shifts \fBa\fP left by \fBb\fP bits \fBb = a * 2^b\fP. @@ -647,19 +647,19 @@ Shifts \fBa\fP left by \fBb\fP bits \fBb = a * 2^b\fP. Condition: \fBb >= 0\fP .in -1i -.LP +.LP .BI "mp_err mp_mul (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Computes \fBc = a * b\fP. .in -1i -.LP +.LP .BI "mp_err mp_mul_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" .in 1i Computes \fBc = a * b\fP with \fBb\fP and \fBmp_digit\fP. .in -1i -.LP +.LP .BI "mp_err mp_mulmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" .in 1i Computes \fBd = a * b (mod c)\fP. No optimizations. @@ -671,26 +671,26 @@ unrestricted diminished radix reduction (\fBmp_reduce_2k\fP) .br .in -1i -.LP +.LP .BI "mp_err mp_neg (const mp_int *" a ", mp_int *" b ")" .in 1i Computes \fBb = -a\fP. .in -1i -.LP +.LP .BI "mp_err mp_or (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" .in 1i Computes bit-wise or \fBa | b = c\fP. Negative numbers are treated as if they are in two-complement representation. .in -1i -.LP +.LP .BI "size_t mp_pack_count(const mp_int *" a ", size_t " nails ", size_t " size ")" .in 1i Returns the size in bytes necessary to be put in \fBmp_pack\fP's \fBmaxsize\fP. See \fBmp_pack\fP for details. .in -1i -.LP +.LP .BI "mp_err mp_pack(void *" rop ", size_t *" countp ", mp_order " order ", size_t " size ", mp_endian " endian ", size_t " nails ", const mp_int *" op ")" .in 1i Export binary data. @@ -717,7 +717,7 @@ typedef enum { .in -1.5i .in -1i -.LP +.LP .BI "mp_err mp_prime_strong_lucas_selfridge(const mp_int *" a ", bool *" result ")" .in 1i Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a strong Lucas-Selfridge pseudoprime, \fBfalse\fP otherwise. @@ -726,7 +726,7 @@ It has been verified that this function together with one round of Miller-Rabin deterministic up to 2^64. .in -1i -.LP +.LP .BI "mp_err mp_prime_frobenius_underwood(const mp_int *" N ", bool *" result ")" .in 1i Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a Frobenius-Underwood pseudoprime, \fBfalse\fP otherwise. @@ -734,7 +734,7 @@ Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a Frobenius-Underwood pseudoprime, It has been verified that this function (as a stand-alone) is deterministic up to at least 2^50. .in -1i -.LP +.LP .BI "mp_err mp_prime_is_prime(const mp_int *" a ", int " t ", bool *" result ")" .in 1i Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is a pseudoprime, \fBfalse\fP otherwise. @@ -778,14 +778,14 @@ If \fBt > 0\fP: run the given number of Miller-Rabin tests with random bases. .RE .in -1i -.LP +.LP .BI "mp_err mp_prime_miller_rabin (const mp_int *" a ", const mp_int *" b ", int *" result ")" .in 1i Run the Miller-Rabin pseudoprime test of \fBa\fP with base \fBb\fP and set \fBresult\fP to \fBtrue\fP if \fBa\fP is a strong pseudprime for base \fBb\fP and \fBfalse\fP otherwise. .in -1i -.LP +.LP .BI "mp_err mp_prime_next_prime(mp_int *" a ", int " t ", bool " bbs_style ")" .in 1i Sets \fBa\fP to the next prime, even if \fBa\fP is prime itself. @@ -796,10 +796,10 @@ Argument \fBt\fP holds the number of Miller-Rabin tests to random bases and can Argument \fBbbs_style\fP returns only primes \fBa \[==] 3 (mod 4)\fP if set to \fBtrue\fP. .in -1i -.LP +.LP .BI "mp_err mp_prime_rabin_miller_trials(int " size ")" .in 1i -Returns the number of Miller-Rabin tests to random bases necessary for RSA according to +Returns the number of Miller-Rabin tests to random bases necessary for RSA according to FIPS 186-4. .br \fBsize\fP is the size of the prime in bits. @@ -835,7 +835,7 @@ r r l. .TE .in -1i -.LP +.LP .BI "mp_err mp_prime_rand(mp_int *" a ", int " t ", int " size ", int " flags ")" .in 1i Generates a random big prime \fBa\fP with \fBsize\fP bits. @@ -856,7 +856,7 @@ MP_PRIME_2MSB_ON;make the 2nd highest bit one .TE .in -1i -.LP +.LP .BI "mp_err mp_radix_size (const mp_int *" a ", int " radix ", int *" size ")" .in 1i Sets \fBsize\fP to the length of the ASCII string of the representation of big integer \fBa\fP in radix \fBradix\fP. @@ -865,7 +865,7 @@ This includes the sign and the terminatong \fBNUL\fP. Returns \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP .in -1i -.LP +.LP .BI "mp_err mp_radix_size_overestimate (const mp_int *" a ", int " radix ", int *" size ")" .in 1i Same as \fBmp_radix_size\fP but uses a rough, table based approximation instead of calling \fBmp_log_n\fP. @@ -874,7 +874,7 @@ Overestimates the result by some units: relative error is about \fB10^(-8)\fP. E the absolute error should not go pass \fB5\fP. .in -1i -.LP +.LP .BI "mp_err mp_rand(mp_int *" a ", int " digits ")" .in 1i Generates a random big integer \fBa\fP with a \fBdigits\fP number of limbs. @@ -883,7 +883,7 @@ Generates a random big integer \fBa\fP with a \fBdigits\fP number of limbs. is precious see \fBmp_rand_source\fP to set another (P)RNG. .in -1i -.LP +.LP .BI "void mp_rand_source(mp_err(*" source ")(void *" out ", size_t " size ")); .in 1i Sets the (P)RNG used for \fIall\fP functions in Libtommath, that need some random bytes. @@ -928,7 +928,7 @@ mp_err some_monte_carlo_function(...) .in -.5i .in -1i -.LP +.LP .BI "mp_err mp_read_radix (mp_int *" a ", const char *" str ", int " radix ")" .in 1i This will read a \fBNUL\fP terminated string in base \fBradix\fP from \fBstr\fP into \fBa\fP. @@ -936,7 +936,7 @@ This will read a \fBNUL\fP terminated string in base \fBradix\fP from \fBstr\fP Returns \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP. .in -1i -.LP +.LP .BI "mp_err mp_reduce_2k_l(mp_int *" a ", const mp_int *" n ", const mp_int *" d ")" .in 1i Reduces \fBa\fP modulo \fBn\fP where \fBn\fP is of the form \fB2^p - d\fP where \fBd\fP @@ -945,7 +945,7 @@ is a big integer. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "mp_err mp_reduce_2k(mp_int *" a ", const mp_int *" n ", mp_digit " d ")" .in 1i Reduces \fBa\fP modulo \fBn\fP where \fBn\fP is of the form \fB2^p - d\fP where \fBd\fP @@ -954,7 +954,7 @@ is a \fBmp_digit\fP. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "mp_err mp_reduce_2k_setup(const mp_int *" a ", mp_digit *" d ")" .in 1i This will compute the required \fBd\fP value in \fB2^p - d\fP for the given moduli \fBa\fP where \fBd\fP @@ -963,7 +963,7 @@ is a \fBmp_digit\fP. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "mp_err mp_reduce_2k_setup_l(const mp_int *" a ", mp_int *" d ")" .in 1i This will compute the required \fBd\fP value in \fB2^p - d\fP for the given moduli \fBa\fP where \fBd\fP @@ -972,7 +972,7 @@ is a big integer. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "mp_err mp_reduce(const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i This will reduce \fBa\fP in place modulo \fBb\fP with the precomputed \fBmu\fP value in \fBc\fP. \fBa\fPmust be in @@ -981,7 +981,7 @@ the range \fB0 <= a < b^2\fP. Belongs to the "Barrett reduction" method. .in -1i -.LP +.LP .BI "bool mp_reduce_is_2k(const mp_int *" a ")" .in 1i Determines if \fBmp_reduce_2k\fP can be used with a \fBmp_digit\fP. @@ -989,7 +989,7 @@ Determines if \fBmp_reduce_2k\fP can be used with a \fBmp_digit\fP. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "bool mp_reduce_is_2k_l(const mp_int *" a ")" .in 1i Determines if \fBmp_reduce_2k\fP can be used with a big integer. @@ -997,13 +997,13 @@ Determines if \fBmp_reduce_2k\fP can be used with a big integer. Belongs to the "unrestricted diminished radix reduction" method. .in -1i -.LP +.LP .BI "mp_err mp_reduce_setup(const mp_int *" a ", mp_int *" b ")" .in 1i Compute \fBmu\fP for Barrett reduction. .in -1i -.LP +.LP .BI "mp_err mp_root_n(const mp_int *" a ", int " b ", mp_int *" c ")" .in 1i This computes \fBc = a^(1/b)\fP such that \fBc^b <= a\fP and \fB(c+1)^b > a\fP. Will return a positive root @@ -1013,19 +1013,19 @@ performing \fB4^(1/2)\fP will return \fB2\fP whereas \fB(-8)^(1/3)\fP will retur Returns \fBMP_VAL\fP if \fBb < 0\fP or \fBb > MP_DIGIT_MAX\fP or when \fBb\fP is even and \fBa < 0\fP. .in -1i -.LP +.LP .BI "void mp_rshd (mp_int *" a ", int " b ")" .in 1i Shift \fBa\fP right by \fBb\fP limbs: \fBa / 2^(b*MP_DIGIT_BIT)\fP. .in -1i -.LP +.LP .BI "size_t mp_sbin_size(const mp_int *" a ")" .in 1i Returns the number of bytes (octets) required to store the signed copy of the integer \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_set_double(mp_int *" a ", double " b ")" .in 1i If the platform supports the floating point data type \fBdouble\fP (binary64) this function will @@ -1034,49 +1034,49 @@ assign the integer part of \fBb\fP to the big integer \fBa\fP. Returns \fBMP_VAL\fP if \fBb\fP is \fB+/-infinity\fP or \fBNaN\fP .in -1i -.LP +.LP .BI "void mp_set_i32 (mp_int *" a ", int32_t " b ")" .in 1i Sets big integer \fBa\fP to the value of the signed 32 bit integer \fBb\fP. .in -1i -.LP +.LP .BI "void mp_set_i64 (mp_int *" a ", int64_t " b ")" .in 1i Sets big integer \fBa\fP to the value of the signed 64 bit integer \fBb\fP. .in -1i -.LP +.LP .BI "void mp_set_l (mp_int *" a ", long " b ")" .in 1i Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fIsigned long\fP. .in -1i -.LP +.LP .BI "void mp_set (mp_int *" a ", mp_digit " b ")" .in 1i Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fImp_digit\fP. .in -1i -.LP +.LP .BI "void mp_set_u32 (mp_int *" a ", uint32_t " b ")" .in 1i Sets big integer \fBa\fP to the value of the unsigned 32 bit integer \fBb\fP. .in -1i -.LP +.LP .BI "void mp_set_u64 (mp_int *" a ", uint64_t " b ")" .in 1i Sets big integer \fBa\fP to the value of the unsigned 64 bit integer \fBb\fP. .in -1i -.LP +.LP .BI "void mp_set_ul (mp_int *" a ", unsigned long " b ")" .in 1i Sets big integer \fBa\fP to the value of the integer \fBb\fP of type \fIunsigned long\fP. .in -1i -.LP +.LP .BI "mp_err mp_shrink (mp_int *" a ")" .in 1i This will remove excess digits of the \fImp_int\fP \fBa\fP. @@ -1084,31 +1084,31 @@ This will remove excess digits of the \fImp_int\fP \fBa\fP. This method uses \fBrealloc\fP with all its problems, use with caution. .in -1i -.LP +.LP .BI "mp_err mp_signed_rsh(const mp_int *" a ", int " b ", mp_int *" c ")" .in 1i Shifts right \fBa\fP by \fBb\fP bits with sign extension. .in -1i -.LP +.LP .BI "mp_err mp_sqr (const mp_int *" a ", mp_int *" b ")" .in 1i Computes \fBa^2 = b\fP .in -1i -.LP +.LP .BI "mp_err mp_sqrmod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ")" .in 1i Computes \fBa^2 % b = c\fP. No optimization. .in -1i -.LP +.LP .BI "mp_err mp_sqrt(const mp_int *" arg ", mp_int *" ret ")" .in 1i Computes \fBa^(1/2) = b\fP such that \fBb^2 <= a\fP. .in -1i -.LP +.LP .BI "mp_err mp_sqrtmod_prime(const mp_int *" n ", const mp_int *" p ", mp_int *" r ")" .in 1i Computes\fBa^(1/2) % p = r\fP with \fBp\fP prime. Uses the Tonelli-Shanks algorithm. @@ -1118,49 +1118,49 @@ Does do some checks for \fBp\fP but no actual primality test. The prime \fBp\fP must be odd. .in -1i -.LP +.LP .BI "mp_err mp_sub (const mp_int *" a ", const mp_int *" b ", mp_int *" c ")" .in 1i Computes \fBa - b = c\fP with \fBb\fP a big integer. .in -1i -.LP +.LP .BI "mp_err mp_sub_d(const mp_int *" a ", mp_digit " b ", mp_int *" c ")" .in 1i Computes \fBa - b = c\fP with \fBb\fP of type \fImp_digit\fP. .in -1i -.LP +.LP .BI "mp_err mp_submod(const mp_int *" a ", const mp_int *" b ", const mp_int *" c ", mp_int *" d ")" .in 1i Computes \fB(a - b) % c = d\fP. No optimization. .in -1i -.LP +.LP .BI "mp_to_binary(" M ", " S ", " N ")" .in 1i Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 2\fP. .in -1i -.LP +.LP .BI "mp_to_decimal(" M ", " S ", " N ")" .in 1i Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 10\fP. .in -1i -.LP +.LP .BI "mp_to_hex(" M ", " S ", " N ")" .in 1i Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 16\fP. .in -1i -.LP +.LP .BI "mp_to_octal(" M ", " S ", " N ")" .in 1i Macro that calls \fBmp_to_radix\fP with fixed \fBradix = 8\fP. .in -1i -.LP +.LP .BI "mp_err mp_to_radix (const mp_int *" a ", char *" str ", size_t " maxlen ", size_t *" written ", int " radix ")" .in 1i Stores upto \fBsize - 1\fP chars and always a \fBNULL\fP byte in \fBstr\fP and puts the number of characters written, @@ -1174,7 +1174,7 @@ Returns \fBMP_BUF\fP if \fBmaxlen < 2\fP Return \fBMP_VAL\fP if \fBradix\fP is not in the range \fB2 <= radix <= 64\fP. .in -1i -.LP +.LP .BI "mp_err mp_to_sbin(const mp_int *" a ", uint8_t *" b ", size_t " maxsize ", size_t *" len ")" .in 1i Store a \fBmaxlen\fP amount of the big integer in buffer \fBb\fP and puts the number of bytes written in \fBlen\fP. @@ -1184,7 +1184,7 @@ If \fBa\fP is negative \fBb0] = 1\fP and \fBb[0] = 0\fP otherwise. Returns \fBMP_BUF\fP if \fBmaxlen\fP is too small. Use \fBmp_sbin_size\fP to have that number computed. .in -1i -.LP +.LP .BI "mp_err mp_to_ubin(const mp_int *" a ", uint8_t *" buf ", size_t " maxlen ", size_t *" written ")" .in 1i Store a \fBmaxlen\fP amount of the big integer in buffer \fBb\fP and puts the number of bytes written in \fBlen\fP. @@ -1192,20 +1192,20 @@ Store a \fBmaxlen\fP amount of the big integer in buffer \fBb\fP and puts the nu Returns \fBMP_BUF\fP if \fBmaxlen\fP is too small. Use \fBmp_sbin_size\fP to have that number computed. .in -1i -.LP +.LP .BI "size_t mp_ubin_size(const mp_int *" a ")" .in 1i Returns the number of bytes (octets) required to store the unsigned copy of the big integer \fBa\fP. .in -1i -.LP +.LP .BI "mp_err mp_unpack(mp_int *" rop ", size_t " count ", mp_order " order ", size_t " size ", mp_endian " endian ", size_t " nails ", const void *" op ")" .in 1i Implements the similarly working GMP functions as described at \fIhttp://gmplib.org/manual/Integer-Import-and-Export.html\fP. See also: \fBmp_pack\fP for more details. .in -1i -.LP +.LP .BI "mp_err mp_xor (const mp_int *" a ", mp_int *" b ", mp_int *" c ")" .in 1i Computes bit-wise xor \fBa ^ b = c\fP. Negative numbers are treated as if they are in two-complement representation. @@ -1213,7 +1213,7 @@ Computes bit-wise xor \fBa ^ b = c\fP. Negative numbers are treated as if they a Returns \fBMP_MEM\fP if the reallocation of memory in \fBmp_grow\fP failed. .in -1i -.LP +.LP .BI "void mp_zero(mp_int *" a ")" .in 1i Sets \fBa\fP to zero. @@ -1638,7 +1638,7 @@ int main(int argc, char **argv) if( (err = mp_div_2d(&t1, (int)eps, &t1, NULL) ) != MP_OKAY) goto LTM_ERR; if( (err = mp_fwrite(&t1,10,stdout) ) != MP_OKAY) goto LTM_ERR; - + mp_clear_multi(&N, &P, &Q, &R, &zero, &EPS, &t1, &t2, &t5, &t239, NULL); exit(EXIT_SUCCESS); LTM_ERR: From 733cb22e31866c44b1f4feb5c617fe765297d843 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 16:57:27 +0200 Subject: [PATCH 261/304] Add missing APIs&Macros to manpage Signed-off-by: Steffen Jaeckel --- doc/tommath.3 | 47 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 47 insertions(+) diff --git a/doc/tommath.3 b/doc/tommath.3 index e0eeae2b4..0b72c242f 100644 --- a/doc/tommath.3 +++ b/doc/tommath.3 @@ -79,6 +79,24 @@ Frees the heap memory of \fBa\fP. Returns the position of the lowest bit set. .in -1i +.LP +.BI "mp_ord mp_cmp(const mp_int *" a ", const mp_int *" b ")" +.in 1i +Compare \fBa\fP to \fBb\fP. +.in -1i + +.LP +.BI "mp_ord mp_cmp_d(const mp_int *" a ", mp_digit " b ")" +.in 1i +Compare \fBa\fP to a single digit \fBb\fP. +.in -1i + +.LP +.BI "mp_ord mp_cmp_mag(const mp_int *" a ", const mp_int *" b ")" +.in 1i +Compares the absolute values of \fBa\fP and \fBb\fP. +.in -1i + .LP .BI "mp_err mp_complement(const mp_int *" a ", mp_int *" b ")" .in 1i @@ -279,6 +297,7 @@ mp_get_i64;5543444065158278130 mp_get_mag_u32;3221335026 mp_get_mag_u64;5543444065158278130 mp_get_l;5543444065158278130 +mp_get_ul;5543444065158278130 mp_get_mag_ul;5543444065158278130 .TE .in -1i @@ -315,6 +334,14 @@ Returns an unsigned 64 bit integer from big-integer \fBa\fP. \fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. .in -1i +.LP +.BI "unsigned long mp_get_mag_ul (const mp_int *" a ")" +.in 1i +Returns an unsigned long from big-integer \fBa\fP. +.br +\fBNOTE:\fP This function is truncating. See \fBmp_get_i32\fP for details. +.in -1i + .LP .BI "uint32_t mp_get_u32 (const mp_int *" a ")" .in 1i @@ -327,6 +354,12 @@ Convenience macro for \fBmp_get_mag_u32()\fP. Convenience macro for \fBmp_get_mag_u64()\fP. .in -1i +.LP +.BI "unsigned long mp_get_ul (const mp_int *" a ")" +.in 1i +Convenience macro for \fBmp_get_mag_ul()\fP. +.in -1i + .LP .BI "mp_err mp_grow (mp_int *" a ", int " size ")" .in 1i @@ -471,6 +504,12 @@ Sets \fBret\fP to \fBtrue\fP if \fBarg\fP is a square, \fBfalse\fP otherwise. Returns \fBtrue\fP if \fBa = 0\fP, \fBfalse\fP otherwise. .in -1i +.LP +.BI "bool mp_isone(mp_int *" a ")" +.in 1i +Returns \fBtrue\fP if \fBa = 1\fP, \fBfalse\fP otherwise. +.in -1i + .LP .BI "mp_err mp_kronecker (const mp_int *" a ", const mp_int *" p ", int *" c ")" .in 1i @@ -717,6 +756,14 @@ typedef enum { .in -1.5i .in -1i +.LP +.BI "mp_err mp_prime_fermat(const mp_int *" a ", const mp_int *" b ", bool *" result ")" +.in 1i +Performs one Fermat test of \fBa\fP using base \fBb\fP. +.br +Sets \fBresult\fP to \fBtrue\fP if \fBa\fP is probably prime, \fBfalse\fP if composite. +.in -1i + .LP .BI "mp_err mp_prime_strong_lucas_selfridge(const mp_int *" a ", bool *" result ")" .in 1i From e76244976d4b352441018c3fa8dd328303755bc9 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 19:36:38 +0200 Subject: [PATCH 262/304] Install manpage and add it to the release tarball Signed-off-by: Steffen Jaeckel --- doc/tommath.3 | 2 +- makefile | 9 +++------ makefile.shared | 4 +--- makefile_include.mk | 16 ++++++++++++++++ 4 files changed, 21 insertions(+), 10 deletions(-) diff --git a/doc/tommath.3 b/doc/tommath.3 index 0b72c242f..ad9c4d063 100644 --- a/doc/tommath.3 +++ b/doc/tommath.3 @@ -1,4 +1,4 @@ -.TH LIBTOMMATH 3 "2023-04-26" +.TH LIBTOMMATH 3 "2003-28-02" .SH NAME libtommath - a big integer library .SH SYNOPSIS diff --git a/makefile b/makefile index 25eda9c3b..f8feff7cc 100644 --- a/makefile +++ b/makefile @@ -79,9 +79,7 @@ profiled_single: amalgamated_timing $(CC) $(LTM_CFLAGS) -fbranch-probabilities -c pre_gen/tommath_amalgam.c -o tommath_amalgam.o $(AR) $(ARFLAGS) $(LIBNAME) tommath_amalgam.o -install: $(LIBNAME) - install -d $(DESTDIR)$(LIBPATH) - install -d $(DESTDIR)$(INCPATH) +install: $(LIBNAME) .install_common install -m 644 $(LIBNAME) $(DESTDIR)$(LIBPATH) install -m 644 $(HEADERS_PUB) $(DESTDIR)$(INCPATH) @@ -114,9 +112,6 @@ tune: $(LIBNAME) coveralls: lcov coveralls-lcov -docs manual: - $(MAKE) -C doc/ $@ V=$(V) - .PHONY: pre_gen cmp pre_gen: mkdir -p pre_gen @@ -127,6 +122,7 @@ cmp: profiled_single ./timing $(MAKE) -C logs/ cmp +TODAY=$(shell date -I) zipup: clean astyle new_file docs @# Update the index, so diff-index won't fail in case the pdf has been created. @# As the pdf creation modifies the tex files, git sometimes detects the @@ -140,6 +136,7 @@ zipup: clean astyle new_file docs -@(find libtommath-$(VERSION)/ -type f | xargs grep 'FIXM[E]') && echo '############## BEWARE: the "fixme" marker was found !!! ##############' || true mkdir -p libtommath-$(VERSION)/doc cp doc/bn.pdf libtommath-$(VERSION)/doc/ + sed -e "s,^Version.*,Version $(VERSION)," -e "s,2003-28-02,$(TODAY)," doc/tommath.3 > libtommath-$(VERSION)/doc/tommath.3 $(MAKE) -C libtommath-$(VERSION)/ pre_gen tar -c libtommath-$(VERSION)/ | xz -6e -c - > ltm-$(VERSION).tar.xz zip -9rq ltm-$(VERSION).zip libtommath-$(VERSION) diff --git a/makefile.shared b/makefile.shared index fe077fc8b..c9b933513 100644 --- a/makefile.shared +++ b/makefile.shared @@ -60,9 +60,7 @@ LOBJECTS = $(OBJECTS:.o=.lo) $(LIBNAME): $(OBJECTS) $(LTLINK) $(LTM_LDFLAGS) $(LOBJECTS) -o $(LIBNAME) -rpath $(LIBPATH) -version-info $(VERSION_SO) $(LTM_LIBTOOLFLAGS) -install: $(LIBNAME) - install -d $(DESTDIR)$(LIBPATH) - install -d $(DESTDIR)$(INCPATH) +install: $(LIBNAME) .install_common $(LIBTOOL) --mode=install install -m 644 $(LIBNAME) $(DESTDIR)$(LIBPATH)/$(LIBNAME) install -m 644 $(HEADERS_PUB) $(DESTDIR)$(INCPATH) sed -e 's,^prefix=.*,prefix=$(PREFIX),' -e 's,^Version:.*,Version: $(VERSION_PC),' -e 's,@CMAKE_INSTALL_LIBDIR@,lib,' \ diff --git a/makefile_include.mk b/makefile_include.mk index f88d18be1..00e1e7572 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -138,11 +138,27 @@ HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h #LIBPATH The directory for libtommath to be installed to. #INCPATH The directory to install the header files for libtommath. #DATAPATH The directory to install the pdf docs. +#MANPATH The directory to install the manfile. DESTDIR ?= PREFIX ?= /usr/local LIBPATH ?= $(PREFIX)/lib INCPATH ?= $(PREFIX)/include DATAPATH ?= $(PREFIX)/share/doc/libtommath/pdf +MANPATH ?= $(PREFIX)/share/man + +.install_common: + install -d $(DESTDIR)$(LIBPATH) + install -d $(DESTDIR)$(INCPATH) + +install_docs: manual + install -d $(DESTDIR)$(DATAPATH) + install -p -m 644 doc/bn.pdf $(DESTDIR)$(DATAPATH) + install -d $(DESTDIR)$(MANPATH) + install -p -m 644 doc/tommath.3 $(DESTDIR)$(MANPATH)/man3 + + +docs manual: + $(MAKE) -C doc/ $@ V=$(V) # build & run test-suite check: test From 96927a9cb5b1bd188b513785ae34738689fcc322 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 19:37:16 +0200 Subject: [PATCH 263/304] Add CI job to build docs Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 457216a7e..2f0ef4e75 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -25,6 +25,20 @@ on: - /^ci\/.*$/ jobs: + Docs: + runs-on: ubuntu-20.04 + container: texlive/texlive:latest-full + steps: + - uses: actions/checkout@v2 + - name: generate PDF + run: | + make docs V=1 + cp doc/bn.pdf bn-${{ github.run_id }}.pdf + - name: upload PDF + uses: actions/upload-artifact@v3 + with: + name: bn-${{ github.run_id }}.pdf + path: bn-${{ github.run_id }}.pdf Testme: runs-on: ${{ matrix.os }} strategy: From 1dbad380389c14cb24c26fda9d73a9693a24e3db Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 19:37:26 +0200 Subject: [PATCH 264/304] Fix building docs Signed-off-by: Steffen Jaeckel --- doc/bn.tex | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/bn.tex b/doc/bn.tex index 0642263e8..015818738 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -2004,7 +2004,7 @@ \subsection{Example} mp_error_to_string(e)); exit(EXIT_FAILURE); } - printf("%d\n",output); + printf("%d\textbackslash{}n",output); mp_clear(&x); exit(EXIT_SUCCESS); From 4c118b47ffef9c82aa44833321f3a2fd4da212c5 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 21 Jun 2023 19:44:26 +0200 Subject: [PATCH 265/304] Update content of tarball Signed-off-by: Steffen Jaeckel --- .gitattributes | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/.gitattributes b/.gitattributes index b5227298c..307473ca1 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,5 +1,7 @@ -/.gitattributes export-ignore -/.gitignore export-ignore -/.travis.yml export-ignore +/.gitattributes export-ignore +/.gitignore export-ignore +/.github/* export-ignore +/appveyor.yml export-ignore +/doc/.latexindent.yaml export-ignore /** export-subst From 6d65a8f1741f87fb7a388a2bc38f5a3ad708208f Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sat, 26 Aug 2023 12:22:33 +0200 Subject: [PATCH 266/304] Newer GCC requires `-flto=auto` GCC changed something internally [0] and emits now a warning in case there's no `=n` parameter given to force parallelization. This patch tells the lto process to select the number of parallel jobs automatically. Clang doesn't support the `=auto` parameter, so only set it for GCC. [0] https://www.mail-archive.com/gcc-patches@gcc.gnu.org/msg258325.html Signed-off-by: Steffen Jaeckel --- makefile_include.mk | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/makefile_include.mk b/makefile_include.mk index 00e1e7572..ef8e85e9d 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -86,8 +86,11 @@ LTM_CFLAGS += -fomit-frame-pointer endif ifdef COMPILE_LTO -LTM_CFLAGS += -flto -LTM_LDFLAGS += -flto +ifeq ($(findstring clang,$(CC)),) +LTO_ARG = "=auto" +endif +LTM_CFLAGS += -flto$(LTO_ARG) +LTM_LDFLAGS += -flto$(LTO_ARG) AR = $(subst clang,llvm-ar,$(subst gcc,gcc-ar,$(CC))) endif From 31a936cc9490eedfbd2c35090b3c17d1b870d8df Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=AE=87=E6=96=87?= Date: Fri, 11 Aug 2023 17:16:43 +0800 Subject: [PATCH 267/304] Make the arg of mp_hash() const --- mp_hash.c | 2 +- tommath.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/mp_hash.c b/mp_hash.c index 2add7578b..9607c806d 100644 --- a/mp_hash.c +++ b/mp_hash.c @@ -12,7 +12,7 @@ #endif /* computes hash of mp_int. */ -mp_err mp_hash(mp_int *a, mp_hval *hash) +mp_err mp_hash(const mp_int *a, mp_hval *hash) { int x; mp_hval hval = FNV_1A_INIT; diff --git a/tommath.h b/tommath.h index db005081b..84bb0909d 100644 --- a/tommath.h +++ b/tommath.h @@ -499,7 +499,7 @@ typedef uint64_t mp_hval; #endif /* computes hash */ -mp_err mp_hash(mp_int *a, mp_hval *hash) MP_WUR; +mp_err mp_hash(const mp_int *a, mp_hval *hash) MP_WUR; /* ---> Primes <--- */ From a2c6b09dfed38d8a703b7d8903800fb416952d97 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=AE=87=E6=96=87?= Date: Thu, 17 Aug 2023 10:53:50 +0800 Subject: [PATCH 268/304] update docs --- doc/bn.tex | 2 +- doc/tommath.3 | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/bn.tex b/doc/bn.tex index 015818738..2e71f84cc 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -1449,7 +1449,7 @@ \section{Hashing} \index{mp\_hash} \begin{alltt} -mp_err mp_hash (mp_int *a, mp_hval *hash); +mp_err mp_hash (const mp_int *a, mp_hval *hash); \end{alltt} This will create the hash of $a$ following the \mbox{FNV-1a} algorithm as described on diff --git a/doc/tommath.3 b/doc/tommath.3 index ad9c4d063..fabaaf5d5 100644 --- a/doc/tommath.3 +++ b/doc/tommath.3 @@ -369,7 +369,7 @@ Returns \fBMP_MEM\fP if the functions fails to allocate enough memory. .in -1i .LP -.BI "mp_err mp_hash (mp_int *" a ", mp_hval *" hash ")" +.BI "mp_err mp_hash (const mp_int *" a ", mp_hval *" hash ")" .in 1i This will create the hash of \fBa\fP following the \fIFNV-1a\fP algorithm as described on \fIhttp://www.isthe.com/chongo/tech/comp/fnv/index.html#FNV-1a\fP. With the From be78ab95084ed22bac386865f74d7ebbe622feeb Mon Sep 17 00:00:00 2001 From: czurnieden Date: Tue, 9 May 2023 17:17:12 +0200 Subject: [PATCH 269/304] Fix possible integer overflow (cherry picked from commit beba892bc0d4e4ded4d667ab1d2a94f4d75109a9) --- mp_2expt.c | 4 ++++ mp_grow.c | 4 ++++ mp_init_size.c | 4 ++++ s_mp_mul.c | 4 ++++ s_mp_mul_comba.c | 4 ++++ s_mp_mul_high.c | 4 ++++ s_mp_mul_high_comba.c | 4 ++++ 7 files changed, 28 insertions(+) diff --git a/mp_2expt.c b/mp_2expt.c index 4a5fc0063..c11fe4cb3 100644 --- a/mp_2expt.c +++ b/mp_2expt.c @@ -12,6 +12,10 @@ mp_err mp_2expt(mp_int *a, int b) { mp_err err; + if (b < 0) { + return MP_VAL; + } + /* zero a as per default */ mp_zero(a); diff --git a/mp_grow.c b/mp_grow.c index 5bca1b5ff..551d1a3bc 100644 --- a/mp_grow.c +++ b/mp_grow.c @@ -6,6 +6,10 @@ /* grow as required */ mp_err mp_grow(mp_int *a, int size) { + if (size < 0) { + return MP_VAL; + } + /* if the alloc size is smaller alloc more ram */ if (a->alloc < size) { mp_digit *dp; diff --git a/mp_init_size.c b/mp_init_size.c index e28a3cd49..87a4256e8 100644 --- a/mp_init_size.c +++ b/mp_init_size.c @@ -6,6 +6,10 @@ /* init an mp_init for a given size */ mp_err mp_init_size(mp_int *a, int size) { + if (size < 0) { + return MP_VAL; + } + size = MP_MAX(MP_MIN_DIGIT_COUNT, size); if (size > MP_MAX_DIGIT_COUNT) { diff --git a/s_mp_mul.c b/s_mp_mul.c index fb99d8054..3394c142e 100644 --- a/s_mp_mul.c +++ b/s_mp_mul.c @@ -13,6 +13,10 @@ mp_err s_mp_mul(const mp_int *a, const mp_int *b, mp_int *c, int digs) mp_err err; int pa, ix; + if (digs < 0) { + return MP_VAL; + } + /* can we use the fast multiplier? */ if ((digs < MP_WARRAY) && (MP_MIN(a->used, b->used) < MP_MAX_COMBA)) { diff --git a/s_mp_mul_comba.c b/s_mp_mul_comba.c index 1afa1fc68..ca89ff9dd 100644 --- a/s_mp_mul_comba.c +++ b/s_mp_mul_comba.c @@ -26,6 +26,10 @@ mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) mp_digit W[MP_WARRAY]; mp_word _W; + if (digs < 0) { + return MP_VAL; + } + /* grow the destination as required */ if ((err = mp_grow(c, digs)) != MP_OKAY) { return err; diff --git a/s_mp_mul_high.c b/s_mp_mul_high.c index 1bde00aa9..fd532ebd8 100644 --- a/s_mp_mul_high.c +++ b/s_mp_mul_high.c @@ -12,6 +12,10 @@ mp_err s_mp_mul_high(const mp_int *a, const mp_int *b, mp_int *c, int digs) int pa, pb, ix; mp_err err; + if (digs < 0) { + return MP_VAL; + } + /* can we use the fast multiplier? */ if (MP_HAS(S_MP_MUL_HIGH_COMBA) && ((a->used + b->used + 1) < MP_WARRAY) diff --git a/s_mp_mul_high_comba.c b/s_mp_mul_high_comba.c index 74960aca6..b5ac06d74 100644 --- a/s_mp_mul_high_comba.c +++ b/s_mp_mul_high_comba.c @@ -19,6 +19,10 @@ mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs mp_digit W[MP_WARRAY]; mp_word _W; + if (digs < 0) { + return MP_VAL; + } + /* grow the destination as required */ pa = a->used + b->used; if ((err = mp_grow(c, pa)) != MP_OKAY) { From 6175cca524822b2b7fd4fa263ef6ee76be5cd77a Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 5 Sep 2023 07:33:46 +0200 Subject: [PATCH 270/304] Prevent potential runtime-error in tests `abs()` can only convert `INT_MIN-1 .. -1` to a positive `int`. Nothing prevents the PRNG to create `INT_MIN` which then leads to a failure of the call to `abs()` as seen in [0]. Instead add an unsigned version of the function reading from the PRNG, so we also don't need to make an absolute value from it. [0] https://github.com/libtom/libtommath/pull/555#issuecomment-1572004663 ``` demo/test.c:1112:13: runtime error: negation of -2147483648 cannot be represented in type 'int'; cast to an unsigned type to negate this value to itself ``` Signed-off-by: Steffen Jaeckel --- demo/test.c | 20 +++++++++++++------- 1 file changed, 13 insertions(+), 7 deletions(-) diff --git a/demo/test.c b/demo/test.c index f86853644..c5141ef7f 100644 --- a/demo/test.c +++ b/demo/test.c @@ -14,9 +14,9 @@ static long rand_long(void) return x; } -static int rand_int(void) +static unsigned int rand_uint(void) { - int x; + unsigned int x; if (s_mp_rand_jenkins(&x, sizeof(x)) != MP_OKAY) { fprintf(stderr, "s_mp_rand_source failed\n"); exit(EXIT_FAILURE); @@ -24,6 +24,11 @@ static int rand_int(void) return x; } +static int rand_int(void) +{ + return (int)rand_uint(); +} + static int32_t rand_int32(void) { int32_t x; @@ -448,7 +453,7 @@ static int test_mp_signed_rsh(void) l = rand_long(); mp_set_l(&a, l); - em = abs(rand_int()) % 32; + em = rand_uint() % 32; mp_set_l(&d, l >> em); @@ -1091,7 +1096,8 @@ static int test_mp_prime_next_prime(void) static int test_mp_montgomery_reduce(void) { mp_digit mp; - int ix, i, n; + int ix, n; + unsigned int i; char buf[4096]; /* size_t written; */ @@ -1106,7 +1112,7 @@ static int test_mp_montgomery_reduce(void) printf(" digit size: %2d\r", i); fflush(stdout); for (n = 0; n < 1000; n++) { - DO(mp_rand(&a, i)); + DO(mp_rand(&a, (int)i)); a.dp[0] |= 1; /* let's see if R is right */ @@ -1115,7 +1121,7 @@ static int test_mp_montgomery_reduce(void) /* now test a random reduction */ for (ix = 0; ix < 100; ix++) { - DO(mp_rand(&c, 1 + (abs(rand_int()) % (2*i)))); + DO(mp_rand(&c, 1 + (int)(rand_uint() % (2*i)))); DO(mp_copy(&c, &d)); DO(mp_copy(&c, &e)); @@ -1274,7 +1280,7 @@ static int test_s_mp_div_3(void) printf("\r %9d", cnt); fflush(stdout); } - DO(mp_rand(&a, (abs(rand_int()) % 128) + 1)); + DO(mp_rand(&a, (int)(rand_uint() % 128) + 1)); DO(mp_div(&a, &d, &b, &e)); DO(s_mp_div_3(&a, &c, &r2)); From 8314bde5e5c8e5d9331460130a9d1066e324f091 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 5 Sep 2023 16:32:29 +0200 Subject: [PATCH 271/304] Update version Signed-off-by: Steffen Jaeckel --- makefile_include.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/makefile_include.mk b/makefile_include.mk index e10f91d70..777083059 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -3,7 +3,7 @@ # #version of library -VERSION=1.2.1 +VERSION=1.2.1-develop VERSION_PC=1.2.1 VERSION_SO=3:1:2 From fa8f3cf9e4d170c61bd3b7f74c23b4f7290af3d0 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Fri, 14 Jul 2023 02:28:38 +0200 Subject: [PATCH 272/304] Deny 2k-reduce if lsd is zero --- demo/test.c | 9 +++++++++ mp_reduce_is_2k.c | 11 +++++++++-- 2 files changed, 18 insertions(+), 2 deletions(-) diff --git a/demo/test.c b/demo/test.c index c5141ef7f..f290dbf21 100644 --- a/demo/test.c +++ b/demo/test.c @@ -1229,11 +1229,20 @@ static int test_mp_cnt_lsb(void) static int test_mp_reduce_2k(void) { int ix, cnt; + bool is2k; mp_int a, b, c, d; DOR(mp_init_multi(&a, &b, &c, &d, NULL)); /* test mp_reduce_2k */ + + /* Algorithm as implemented does not work if the least significant digit is zero */ + DO(mp_2expt(&a, 100)); + DO(mp_sub_d(&a, 1, &a)); + DO(mp_sub_d(&a, MP_MASK, &a)); + is2k = mp_reduce_is_2k(&a); + EXPECT(!is2k); + for (cnt = 3; cnt <= 128; ++cnt) { mp_digit tmp; diff --git a/mp_reduce_is_2k.c b/mp_reduce_is_2k.c index 9774f96e9..d54963383 100644 --- a/mp_reduce_is_2k.c +++ b/mp_reduce_is_2k.c @@ -11,9 +11,16 @@ bool mp_reduce_is_2k(const mp_int *a) } else if (a->used == 1) { return true; } else if (a->used > 1) { - int ix, iy = mp_count_bits(a), iw = 1; - mp_digit iz = 1; + int ix, iy, iw = 1; + mp_digit iz; + /* Algorithm as implemented does not work if the least significant digit is zero */ + iz = a->dp[0] & MP_MASK; + if (iz == 0u) { + return false; + } + iy = mp_count_bits(a); + iz = 1; /* Test every bit from the second digit up, must be 1 */ for (ix = MP_DIGIT_BIT; ix < iy; ix++) { if ((a->dp[iw] & iz) == 0u) { From 782cda79bf1cc150b258f63c974799b909ae01ad Mon Sep 17 00:00:00 2001 From: czurnieden Date: Wed, 21 Jun 2023 22:15:21 +0200 Subject: [PATCH 273/304] Update of examples in directory "etc" --- .gitignore | 15 +- etc/2kprime.c | 23 +-- etc/drprime.c | 20 +-- etc/drprimes.txt | 9 -- etc/makefile | 2 + etc/mersenne.c | 4 +- etc/mont.c | 18 ++- etc/pprime.c | 363 ++++++++++------------------------------------- makefile | 4 + 9 files changed, 134 insertions(+), 324 deletions(-) delete mode 100644 etc/drprimes.txt diff --git a/.gitignore b/.gitignore index d2f01329f..51f3eee22 100644 --- a/.gitignore +++ b/.gitignore @@ -29,6 +29,17 @@ mtest.exe mtest_opponent mtest_opponent.exe +2kprime +2kprime.exe +drprime +drprime.exe +mersenne +mersenne.exe +mont +mont.exe +pprime +pprime.exe + # ignore eclipse project files .cproject .project @@ -66,9 +77,11 @@ perf.data.old # ignore tommath_amalgam.c generated by make tommath_amalgam.c -# ignore file generated by make tune +# ignore file generated by make 'tune and friends' tuning_list etc/tune +2kprime.1 +drprimes.txt # ignore stuff generated by "make manual" and "make poster" *.aux diff --git a/etc/2kprime.c b/etc/2kprime.c index 3a3e28307..5aa83abd0 100644 --- a/etc/2kprime.c +++ b/etc/2kprime.c @@ -10,23 +10,24 @@ int main(void) size_t x; bool y; mp_int q, p; + mp_err err; FILE *out; clock_t t1; mp_digit z; - mp_init_multi(&q, &p, NULL); + if ((err = mp_init_multi(&q, &p, NULL)) != MP_OKAY) goto LTM_ERR; out = fopen("2kprime.1", "w"); if (out != NULL) { for (x = 0; x < (sizeof(sizes) / sizeof(sizes[0])); x++) { top: - mp_2expt(&q, sizes[x]); - mp_add_d(&q, 3uL, &q); + if ((err = mp_2expt(&q, sizes[x])) != MP_OKAY) goto LTM_ERR; + if ((err = mp_add_d(&q, 3uL, &q)) != MP_OKAY) goto LTM_ERR; z = -3; t1 = clock(); for (;;) { - mp_sub_d(&q, 4uL, &q); + if ((err = mp_sub_d(&q, 4uL, &q)) != MP_OKAY) goto LTM_ERR; z += 4uL; if (z > MP_MASK) { @@ -42,21 +43,21 @@ int main(void) } /* quick test on q */ - mp_prime_is_prime(&q, 1, &y); + if ((err = mp_prime_is_prime(&q, 1, &y)) != MP_OKAY) goto LTM_ERR; if (!y) { continue; } /* find (q-1)/2 */ - mp_sub_d(&q, 1uL, &p); - mp_div_2(&p, &p); - mp_prime_is_prime(&p, 3, &y); + if ((err = mp_sub_d(&q, 1uL, &p)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2(&p, &p)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_prime_is_prime(&p, 3, &y)) != MP_OKAY) goto LTM_ERR; if (!y) { continue; } /* test on q */ - mp_prime_is_prime(&q, 3, &y); + if ((err = mp_prime_is_prime(&q, 3, &y)) != MP_OKAY) goto LTM_ERR; if (!y) { continue; } @@ -69,13 +70,13 @@ int main(void) goto top; } - mp_to_decimal(&q, buf, sizeof(buf)); + if ((err = mp_to_decimal(&q, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("\n\n%d-bits (k = %lu) = %s\n", sizes[x], z, buf); fprintf(out, "%d-bits (k = %lu) = %s\n", sizes[x], z, buf); fflush(out); } fclose(out); } - +LTM_ERR: return 0; } diff --git a/etc/drprime.c b/etc/drprime.c index 31dff4e99..e2e709b99 100644 --- a/etc/drprime.c +++ b/etc/drprime.c @@ -10,16 +10,17 @@ int main(void) char buf[4096]; FILE *out; mp_int a, b; + mp_err err; - mp_init(&a); - mp_init(&b); + if ((err = mp_init(&a)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_init(&b)) != MP_OKAY) goto LTM_ERR; out = fopen("drprimes.txt", "w"); if (out != NULL) { for (x = 0; x < (int)(sizeof(sizes)/sizeof(sizes[0])); x++) { top: printf("Seeking a %d-bit safe prime\n", sizes[x] * MP_DIGIT_BIT); - mp_grow(&a, sizes[x]); + if ((err = mp_grow(&a, sizes[x])) != MP_OKAY) goto LTM_ERR; mp_zero(&a); for (y = 1; y < sizes[x]; y++) { a.dp[y] = MP_MASK; @@ -34,15 +35,15 @@ int main(void) for (;;) { a.dp[0] += 4uL; if (a.dp[0] >= MP_MASK) break; - mp_prime_is_prime(&a, 1, &res); + if ((err = mp_prime_is_prime(&a, 1, &res)) != MP_OKAY) goto LTM_ERR; if (!res) continue; printf("."); fflush(stdout); - mp_sub_d(&a, 1uL, &b); - mp_div_2(&b, &b); - mp_prime_is_prime(&b, 3, &res); + if ((err = mp_sub_d(&a, 1uL, &b)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2(&b, &b)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_prime_is_prime(&b, 3, &res)) != MP_OKAY) goto LTM_ERR; if (!res) continue; - mp_prime_is_prime(&a, 3, &res); + if ((err = mp_prime_is_prime(&a, 3, &res)) != MP_OKAY) goto LTM_ERR; if (res) break; } @@ -51,7 +52,7 @@ int main(void) sizes[x] += 1; goto top; } else { - mp_to_decimal(&a, buf, sizeof(buf)); + if ((err = mp_to_decimal(&a, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("\n\np == %s\n\n", buf); fprintf(out, "%d-bit prime:\np == %s\n\n", mp_count_bits(&a), buf); fflush(out); @@ -60,6 +61,7 @@ int main(void) fclose(out); } +LTM_ERR: mp_clear(&a); mp_clear(&b); diff --git a/etc/drprimes.txt b/etc/drprimes.txt deleted file mode 100644 index 7c97f67b9..000000000 --- a/etc/drprimes.txt +++ /dev/null @@ -1,9 +0,0 @@ -300-bit prime: -p == 2037035976334486086268445688409378161051468393665936250636140449354381298610415201576637819 - -540-bit prime: -p == 3599131035634557106248430806148785487095757694641533306480604458089470064537190296255232548883112685719936728506816716098566612844395439751206810991770626477344739 - -780-bit prime: -p == 6359114106063703798370219984742410466332205126109989319225557147754704702203399726411277962562135973685197744935448875852478791860694279747355800678568677946181447581781401213133886609947027230004277244697462656003655947791725966271167 - diff --git a/etc/makefile b/etc/makefile index 52ad47533..0e178396f 100644 --- a/etc/makefile +++ b/etc/makefile @@ -6,6 +6,8 @@ LTM_TUNE_CFLAGS = $(CFLAGS) $(LTM_CFLAGS) -Wall -W -Wextra -Wshadow -O3 -I../ # libname when you can't install the lib with install LIBNAME=../libtommath.a +all: pprime tune test_standalone mersenne drprime 2kprime mont + #provable primes pprime: pprime.o $(CC) $(LTM_TUNE_CFLAGS) pprime.o $(LIBNAME) -o pprime diff --git a/etc/mersenne.c b/etc/mersenne.c index 4d3939e35..f7487ecd0 100644 --- a/etc/mersenne.c +++ b/etc/mersenne.c @@ -57,7 +57,9 @@ static mp_err is_mersenne(long s, bool *pp) /* if u == 0 then its prime */ if (mp_iszero(&u)) { - mp_prime_is_prime(&n, 8, pp); + if ((res = mp_prime_is_prime(&n, 8, pp)) != MP_OKAY) { + goto LBL_MU; + } if (!*pp) printf("FAILURE\n"); } diff --git a/etc/mont.c b/etc/mont.c index 4652410d0..3d844496e 100644 --- a/etc/mont.c +++ b/etc/mont.c @@ -7,10 +7,11 @@ int main(void) { mp_int modulus, R, p, pp; mp_digit mp; + mp_err err; int x, y; srand(time(NULL)); - mp_init_multi(&modulus, &R, &p, &pp, NULL); + if ((err = mp_init_multi(&modulus, &R, &p, &pp, NULL)) != MP_OKAY) goto LTM_ERR; /* loop through various sizes */ for (x = 4; x < 256; x++) { @@ -18,18 +19,20 @@ int main(void) fflush(stdout); /* make up the odd modulus */ - mp_rand(&modulus, x); + if ((err = mp_rand(&modulus, x)) != MP_OKAY) goto LTM_ERR; modulus.dp[0] |= 1uL; /* now find the R value */ - mp_montgomery_calc_normalization(&R, &modulus); - mp_montgomery_setup(&modulus, &mp); + if ((err = mp_montgomery_calc_normalization(&R, &modulus)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_montgomery_setup(&modulus, &mp)) != MP_OKAY) goto LTM_ERR; /* now run through a bunch tests */ for (y = 0; y < 1000; y++) { - mp_rand(&p, x/2); /* p = random */ - mp_mul(&p, &R, &pp); /* pp = R * p */ - mp_montgomery_reduce(&pp, &modulus, mp); + /* p = random */ + if ((err = mp_rand(&p, x/2)) != MP_OKAY) goto LTM_ERR; + /* pp = R * p */ + if ((err = mp_mul(&p, &R, &pp)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_montgomery_reduce(&pp, &modulus, mp)) != MP_OKAY) goto LTM_ERR; /* should be equal to p */ if (mp_cmp(&pp, &p) != MP_EQ) { @@ -40,5 +43,6 @@ int main(void) printf("PASSED\n"); } +LTM_ERR: return 0; } diff --git a/etc/pprime.c b/etc/pprime.c index 1d59cab7f..7edbca09e 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -1,179 +1,31 @@ -/* Generates provable primes - * - * See http://gmail.com:8080/papers/pp.pdf for more info. +/* + * Generates provable primes * * Tom St Denis, tomstdenis@gmail.com, http://tom.gmail.com + * */ #include #include -#include "tommath_private.h" - -static int n_prime; -static FILE *primes; - -/* fast square root */ -static mp_digit i_sqrt(mp_word x) -{ - mp_word x1, x2; - - x2 = x; - do { - x1 = x2; - x2 = x1 - ((x1 * x1) - x) / (2u * x1); - } while (x1 != x2); - - if ((x1 * x1) > x) { - --x1; - } - - return x1; -} - - -/* generates a prime digit */ -static void gen_prime(void) -{ - mp_digit r, x, y, next; - FILE *out; - - out = fopen("pprime.dat", "wb"); - if (out != NULL) { - - /* write first set of primes */ - /* *INDENT-OFF* */ - r = 3uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 5uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 7uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 11uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 13uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 17uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 19uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 23uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 29uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - r = 31uL; fwrite(&r, 1uL, sizeof(mp_digit), out); - /* *INDENT-ON* */ - - /* get square root, since if 'r' is composite its factors must be < than this */ - y = i_sqrt(r); - next = (y + 1uL) * (y + 1uL); - - for (;;) { - do { - r += 2uL; /* next candidate */ - r &= MP_MASK; - if (r < 31uL) break; - - /* update sqrt ? */ - if (next <= r) { - ++y; - next = (y + 1uL) * (y + 1uL); - } - - /* loop if divisible by 3,5,7,11,13,17,19,23,29 */ - if ((r % 3uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 5uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 7uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 11uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 13uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 17uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 19uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 23uL) == 0uL) { - x = 0uL; - continue; - } - if ((r % 29uL) == 0uL) { - x = 0uL; - continue; - } - - /* now check if r is divisible by x + k={1,7,11,13,17,19,23,29} */ - for (x = 30uL; x <= y; x += 30uL) { - if ((r % (x + 1uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 7uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 11uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 13uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 17uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 19uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 23uL)) == 0uL) { - x = 0uL; - break; - } - if ((r % (x + 29uL)) == 0uL) { - x = 0uL; - break; - } - } - } while (x == 0uL); - if (r > 31uL) { - fwrite(&r, 1uL, sizeof(mp_digit), out); - printf("%9lu\r", r); - fflush(stdout); - } - if (r < 31uL) break; - } - - fclose(out); - } -} - -static void load_tab(void) -{ - primes = fopen("pprime.dat", "rb"); - if (primes == NULL) { - gen_prime(); - primes = fopen("pprime.dat", "rb"); - } - fseek(primes, 0L, SEEK_END); - n_prime = ftell(primes) / sizeof(mp_digit); -} +#include "../tommath_private.h" static mp_digit prime_digit(void) { int n; - mp_digit d; + mp_digit d = 0; + mp_int a; + mp_err err; + + n = abs(rand()) % MP_MASK; + if ((err = mp_init_ul(&a, (unsigned long)n)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_prime_next_prime(&a, -1, false)) != MP_OKAY) goto LTM_ERR; + while (a.used > 1) { + if ((err = mp_div_2(&a, &a)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_prime_next_prime(&a, -1, false)) != MP_OKAY) goto LTM_ERR; + } + d = a.dp[0]; - n = abs(rand()) % n_prime; - fseek(primes, n * sizeof(mp_digit), SEEK_SET); - fread(&d, 1uL, sizeof(mp_digit), primes); +LTM_ERR: + mp_clear(&a); return d; } @@ -182,7 +34,7 @@ static mp_digit prime_digit(void) static mp_err pprime(int k, int li, mp_int *p, mp_int *q) { mp_int a, b, c, n, x, y, z, v; - mp_err res; + mp_err err = MP_OKAY; int ii; static const mp_digit bases[] = { 2, 3, 5, 7, 11, 13, 17, 19 }; @@ -192,49 +44,18 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) return MP_OKAY; } - if ((res = mp_init(&c)) != MP_OKAY) { - return res; - } - - if ((res = mp_init(&v)) != MP_OKAY) { - goto LBL_C; + if ((err = mp_init_multi(&a, &b, &c, &n, &x, &y, &z, &v, NULL)) != MP_OKAY) { + return err; } /* product of first 50 primes */ - if ((res = - mp_read_radix(&v, - "19078266889580195013601891820992757757219839668357012055907516904309700014933909014729740190", - 10)) != MP_OKAY) { - goto LBL_V; - } - - if ((res = mp_init(&a)) != MP_OKAY) { - goto LBL_V; + if ((err = mp_read_radix(&v, "9NPvy2By/eZ0N6s68ky5K/8UTD0Q7fInhDK9BHnueH92HfzU4+U", 64)) != MP_OKAY) { + goto LTM_ERR; } /* set the prime */ mp_set(&a, prime_digit()); - if ((res = mp_init(&b)) != MP_OKAY) { - goto LBL_A; - } - - if ((res = mp_init(&n)) != MP_OKAY) { - goto LBL_B; - } - - if ((res = mp_init(&x)) != MP_OKAY) { - goto LBL_N; - } - - if ((res = mp_init(&y)) != MP_OKAY) { - goto LBL_X; - } - - if ((res = mp_init(&z)) != MP_OKAY) { - goto LBL_Y; - } - /* now loop making the single digit */ while (mp_count_bits(&a) < k) { fprintf(stderr, "prime has %4d bits left\r", k - mp_count_bits(&a)); @@ -243,146 +64,113 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) mp_set(&b, prime_digit()); /* now compute z = a * b * 2 */ - if ((res = mp_mul(&a, &b, &z)) != MP_OKAY) { /* z = a * b */ - goto LBL_Z; - } - - if ((res = mp_copy(&z, &c)) != MP_OKAY) { /* c = a * b */ - goto LBL_Z; - } - - if ((res = mp_mul_2(&z, &z)) != MP_OKAY) { /* z = 2 * a * b */ - goto LBL_Z; - } - + /* z = a * b */ + if ((err = mp_mul(&a, &b, &z)) != MP_OKAY) goto LTM_ERR; + /* c = a * b */ + if ((err = mp_copy(&z, &c)) != MP_OKAY) goto LTM_ERR; + /* z = 2 * a * b */ + if ((err = mp_mul_2(&z, &z)) != MP_OKAY) goto LTM_ERR; /* n = z + 1 */ - if ((res = mp_add_d(&z, 1uL, &n)) != MP_OKAY) { /* n = z + 1 */ - goto LBL_Z; - } + if ((err = mp_add_d(&z, 1uL, &n)) != MP_OKAY) goto LTM_ERR; + /* check (n, v) == 1; y = (n, v) */ + if ((err = mp_gcd(&n, &v, &y)) != MP_OKAY) goto LTM_ERR; - /* check (n, v) == 1 */ - if ((res = mp_gcd(&n, &v, &y)) != MP_OKAY) { /* y = (n, v) */ - goto LBL_Z; - } - - if (mp_cmp_d(&y, 1uL) != MP_EQ) + if (mp_cmp_d(&y, 1uL) != MP_EQ) { goto top; + } /* now try base x=bases[ii] */ for (ii = 0; ii < li; ii++) { mp_set(&x, bases[ii]); - /* compute x^a mod n */ - if ((res = mp_exptmod(&x, &a, &n, &y)) != MP_OKAY) { /* y = x^a mod n */ - goto LBL_Z; - } - + /* compute x^a mod n; y = x^a mod n */ + if ((err = mp_exptmod(&x, &a, &n, &y)) != MP_OKAY) goto LTM_ERR; /* if y == 1 loop */ - if (mp_cmp_d(&y, 1uL) == MP_EQ) + if (mp_cmp_d(&y, 1uL) == MP_EQ) { continue; - - /* now x^2a mod n */ - if ((res = mp_sqrmod(&y, &n, &y)) != MP_OKAY) { /* y = x^2a mod n */ - goto LBL_Z; } + /* now x^2a mod n ; y = x^2a mod n*/ + if ((err = mp_sqrmod(&y, &n, &y)) != MP_OKAY) goto LTM_ERR; - if (mp_cmp_d(&y, 1uL) == MP_EQ) + if (mp_cmp_d(&y, 1uL) == MP_EQ) { continue; - - /* compute x^b mod n */ - if ((res = mp_exptmod(&x, &b, &n, &y)) != MP_OKAY) { /* y = x^b mod n */ - goto LBL_Z; } + /* compute x^b mod n ; y = x^b mod n*/ + if ((err = mp_exptmod(&x, &b, &n, &y)) != MP_OKAY) goto LTM_ERR; + /* if y == 1 loop */ - if (mp_cmp_d(&y, 1uL) == MP_EQ) + if (mp_cmp_d(&y, 1uL) == MP_EQ) { continue; - - /* now x^2b mod n */ - if ((res = mp_sqrmod(&y, &n, &y)) != MP_OKAY) { /* y = x^2b mod n */ - goto LBL_Z; } - if (mp_cmp_d(&y, 1uL) == MP_EQ) - continue; + /* now x^2b mod n; y = x^2b mod n */ + if ((err = mp_sqrmod(&y, &n, &y)) != MP_OKAY) goto LTM_ERR; - /* compute x^c mod n == x^ab mod n */ - if ((res = mp_exptmod(&x, &c, &n, &y)) != MP_OKAY) { /* y = x^ab mod n */ - goto LBL_Z; + if (mp_cmp_d(&y, 1uL) == MP_EQ) { + continue; } + /* compute x^c mod n == x^ab mod n ; y = x^ab mod n */ + if ((err = mp_exptmod(&x, &c, &n, &y)) != MP_OKAY) goto LTM_ERR; /* if y == 1 loop */ - if (mp_cmp_d(&y, 1uL) == MP_EQ) + if (mp_cmp_d(&y, 1uL) == MP_EQ) { continue; - - /* now compute (x^c mod n)^2 */ - if ((res = mp_sqrmod(&y, &n, &y)) != MP_OKAY) { /* y = x^2ab mod n */ - goto LBL_Z; } + /* now compute (x^c mod n)^2 ; y = x^2ab mod n */ + if ((err = mp_sqrmod(&y, &n, &y)) != MP_OKAY) goto LTM_ERR; /* y should be 1 */ - if (mp_cmp_d(&y, 1uL) != MP_EQ) + if (mp_cmp_d(&y, 1uL) != MP_EQ) { continue; + } break; } /* no bases worked? */ - if (ii == li) + if (ii == li) { goto top; + } { char buf[4096]; - mp_to_decimal(&n, buf, sizeof(buf)); + if ((err = mp_to_decimal(&n, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("Certificate of primality for:\n%s\n\n", buf); - mp_to_decimal(&a, buf, sizeof(buf)); + if ((err = mp_to_decimal(&a, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("A == \n%s\n\n", buf); - mp_to_decimal(&b, buf, sizeof(buf)); + if ((err = mp_to_decimal(&b, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("B == \n%s\n\nG == %lu\n", buf, bases[ii]); printf("----------------------------------------------------------------\n"); } /* a = n */ - mp_copy(&n, &a); + if ((err = mp_copy(&n, &a)) != MP_OKAY) goto LTM_ERR; } /* get q to be the order of the large prime subgroup */ - mp_sub_d(&n, 1uL, q); - mp_div_2(q, q); - mp_div(q, &b, q, NULL); + if ((err = mp_sub_d(&n, 1uL, q)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div_2(q, q)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_div(q, &b, q, NULL)) != MP_OKAY) goto LTM_ERR; mp_exch(&n, p); - res = MP_OKAY; -LBL_Z: - mp_clear(&z); -LBL_Y: - mp_clear(&y); -LBL_X: - mp_clear(&x); -LBL_N: - mp_clear(&n); -LBL_B: - mp_clear(&b); -LBL_A: - mp_clear(&a); -LBL_V: - mp_clear(&v); -LBL_C: - mp_clear(&c); - return res; + err = MP_OKAY; +LTM_ERR: + mp_clear_multi(&a, &b, &c, &n, &x, &y, &z, &v, NULL); + return err; } int main(void) { mp_int p, q; + mp_err err; char buf[4096]; int k, li; clock_t t1; srand(time(NULL)); - load_tab(); printf("Enter # of bits: \n"); fgets(buf, sizeof(buf), stdin); @@ -393,8 +181,7 @@ int main(void) sscanf(buf, "%d", &li); - mp_init(&p); - mp_init(&q); + if ((err = mp_init_multi(&p, &q, NULL)) != MP_OKAY) goto LTM_ERR; t1 = clock(); pprime(k, li, &p, &q); @@ -402,10 +189,14 @@ int main(void) printf("\n\nTook %lu ticks, %d bits\n", t1, mp_count_bits(&p)); - mp_to_decimal(&p, buf, sizeof(buf)); + if ((err = mp_to_decimal(&p, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("P == %s\n", buf); - mp_to_decimal(&q, buf, sizeof(buf)); + if ((err = mp_to_decimal(&q, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; printf("Q == %s\n", buf); - return 0; + mp_clear_multi(&p, &q, NULL); + exit(EXIT_SUCCESS); +LTM_ERR: + mp_clear_multi(&p, &q, NULL); + exit(EXIT_FAILURE); } diff --git a/makefile b/makefile index f8feff7cc..27b44d7c6 100644 --- a/makefile +++ b/makefile @@ -107,6 +107,10 @@ tune: $(LIBNAME) $(MAKE) -C etc tune CFLAGS="$(LTM_CFLAGS) -I../" $(MAKE) +etc-all: $(LIBNAME) + $(MAKE) -C etc all CFLAGS="$(LTM_CFLAGS) -I../" + $(MAKE) + # You have to create a file .coveralls.yml with the content "repo_token: " # in the base folder to be able to submit to coveralls coveralls: lcov From 942b8b4317a84d9f472f0fdd3341f65e9ccaaf61 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Thu, 22 Jun 2023 03:02:29 +0200 Subject: [PATCH 274/304] Use cryptographic RNG --- etc/pprime.c | 91 +++++++++++++++++++++++++++++++--------------------- 1 file changed, 54 insertions(+), 37 deletions(-) diff --git a/etc/pprime.c b/etc/pprime.c index 7edbca09e..7533a6099 100644 --- a/etc/pprime.c +++ b/etc/pprime.c @@ -8,20 +8,29 @@ #include #include "../tommath_private.h" -static mp_digit prime_digit(void) +static void mp_print(const char *s, const mp_int *a, int radix, FILE *stream) +{ + mp_err err; + fputs(s, stream); + err = mp_fwrite(a, radix, stream); + if (err != MP_OKAY) { + fprintf(stderr,"mp_fwrite in mp_print failed. error = %s\n", mp_error_to_string(err)); + exit(EXIT_FAILURE); + } + fputc('\n',stream); +} + +static mp_digit prime_digit(int bits) { - int n; mp_digit d = 0; mp_int a; mp_err err; - n = abs(rand()) % MP_MASK; - if ((err = mp_init_ul(&a, (unsigned long)n)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_prime_next_prime(&a, -1, false)) != MP_OKAY) goto LTM_ERR; - while (a.used > 1) { - if ((err = mp_div_2(&a, &a)) != MP_OKAY) goto LTM_ERR; - if ((err = mp_prime_next_prime(&a, -1, false)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_init(&a)) != MP_OKAY) { + return 0; } + + if ((err = mp_prime_rand(&a, 1, bits, false)) != MP_OKAY) goto LTM_ERR; d = a.dp[0]; LTM_ERR: @@ -35,12 +44,14 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) { mp_int a, b, c, n, x, y, z, v; mp_err err = MP_OKAY; - int ii; - static const mp_digit bases[] = { 2, 3, 5, 7, 11, 13, 17, 19 }; + int ii, bits; /* single digit ? */ - if (k <= (int) MP_DIGIT_BIT) { - mp_set(p, prime_digit()); + if (k < (int) MP_DIGIT_BIT) { + mp_set(p, prime_digit(k)); + if (mp_iszero(p)) { + return MP_VAL; + } return MP_OKAY; } @@ -54,14 +65,27 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) } /* set the prime */ - mp_set(&a, prime_digit()); + mp_set(&a, prime_digit(MP_DIGIT_BIT)); + if (mp_iszero(&a)) { + err = MP_VAL; + goto LTM_ERR; + } /* now loop making the single digit */ while (mp_count_bits(&a) < k) { - fprintf(stderr, "prime has %4d bits left\r", k - mp_count_bits(&a)); + bits = k - mp_count_bits(&a); + fprintf(stderr, "prime has %4d bits left\r", bits); fflush(stderr); top: - mp_set(&b, prime_digit()); + if (bits < MP_DIGIT_BIT) { + mp_set(&b, prime_digit(bits)); + } else { + mp_set(&b, prime_digit(MP_DIGIT_BIT)); + } + if (mp_iszero(&b)) { + err = MP_VAL; + goto LTM_ERR; + } /* now compute z = a * b * 2 */ /* z = a * b */ @@ -78,10 +102,10 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) if (mp_cmp_d(&y, 1uL) != MP_EQ) { goto top; } - + mp_set(&x, 2u); /* now try base x=bases[ii] */ for (ii = 0; ii < li; ii++) { - mp_set(&x, bases[ii]); + if ((err = mp_prime_next_prime(&x, -1, false)) != MP_OKAY) goto LTM_ERR; /* compute x^a mod n; y = x^a mod n */ if ((err = mp_exptmod(&x, &a, &n, &y)) != MP_OKAY) goto LTM_ERR; @@ -132,17 +156,11 @@ static mp_err pprime(int k, int li, mp_int *p, mp_int *q) goto top; } - { - char buf[4096]; - - if ((err = mp_to_decimal(&n, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; - printf("Certificate of primality for:\n%s\n\n", buf); - if ((err = mp_to_decimal(&a, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; - printf("A == \n%s\n\n", buf); - if ((err = mp_to_decimal(&b, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; - printf("B == \n%s\n\nG == %lu\n", buf, bases[ii]); - printf("----------------------------------------------------------------\n"); - } + mp_print("Certificate of primality for:\n ", &n, 10, stdout); + mp_print("A == ", &a, 10, stdout); + mp_print("B == ", &b, 10, stdout); + mp_print("G == ", &x, 10, stdout); + printf("----------------------------------------------------------------\n"); /* a = n */ if ((err = mp_copy(&n, &a)) != MP_OKAY) goto LTM_ERR; @@ -170,29 +188,28 @@ int main(void) int k, li; clock_t t1; - srand(time(NULL)); - printf("Enter # of bits: \n"); fgets(buf, sizeof(buf), stdin); sscanf(buf, "%d", &k); - printf("Enter number of bases to try (1 to 8):\n"); + printf("Enter number of bases to try\n"); fgets(buf, sizeof(buf), stdin); sscanf(buf, "%d", &li); - if ((err = mp_init_multi(&p, &q, NULL)) != MP_OKAY) goto LTM_ERR; + if ((err = mp_init_multi(&p, &q, NULL)) != MP_OKAY) goto LTM_ERR; t1 = clock(); - pprime(k, li, &p, &q); + if ((err = pprime(k, li, &p, &q)) != MP_OKAY) { + fprintf(stderr, "Something went wrong in function pprime: %s\n", mp_error_to_string(err)); + goto LTM_ERR; + } t1 = clock() - t1; printf("\n\nTook %lu ticks, %d bits\n", t1, mp_count_bits(&p)); - if ((err = mp_to_decimal(&p, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; - printf("P == %s\n", buf); - if ((err = mp_to_decimal(&q, buf, sizeof(buf))) != MP_OKAY) goto LTM_ERR; - printf("Q == %s\n", buf); + mp_print("P == ", &p, 10, stdout); + mp_print("Q == ", &q, 10, stdout); mp_clear_multi(&p, &q, NULL); exit(EXIT_SUCCESS); From f108889a9a2a07cdc8f4d74723f0c7ff7094cfb7 Mon Sep 17 00:00:00 2001 From: czurnieden Date: Tue, 23 May 2023 23:35:39 +0200 Subject: [PATCH 275/304] Correct sanitation of mp_prime_rand --- mp_prime_rand.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mp_prime_rand.c b/mp_prime_rand.c index c5cebbda7..5351aefe4 100644 --- a/mp_prime_rand.c +++ b/mp_prime_rand.c @@ -26,7 +26,7 @@ mp_err mp_prime_rand(mp_int *a, int t, int size, int flags) mp_err err; /* sanity check the input */ - if ((size <= 1) || (t <= 0)) { + if (size <= 1) { return MP_VAL; } From a8d61b555d9f408ccc5ca3eac275864b2983f7f6 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 10 Mar 2024 22:36:11 +0100 Subject: [PATCH 276/304] Use ccache if available Signed-off-by: Steffen Jaeckel --- CMakeLists.txt | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index dfbcb0f26..4077189fa 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -28,9 +28,25 @@ option(BUILD_TESTING "" OFF) include(CTest) include(sources.cmake) -# The only direct cmake argument for now +#----------------------------------------------------------------------------- +# Options +#----------------------------------------------------------------------------- option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \"ON\", default is static" OFF) +#----------------------------------------------------------------------------- +# Add support for ccache if desired +#----------------------------------------------------------------------------- +find_program(CCACHE ccache) + +if(CCACHE) + option(ENABLE_CCACHE "Enable ccache." ON) +endif() + +# use ccache if installed +if(CCACHE AND ENABLE_CCACHE) + set(CMAKE_C_COMPILER_LAUNCHER ${CCACHE}) +endif() + #----------------------------------------------------------------------------- # Compose CFLAGS #----------------------------------------------------------------------------- From 40a73f3db952f6dfd2f50aa908ccb7efc67e87a1 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Sun, 10 Mar 2024 22:51:24 +0100 Subject: [PATCH 277/304] Clarify what happened to `tommath.pdf` This fixes #570 Signed-off-by: Steffen Jaeckel --- README.md | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 29e077f2b..8ebdab70b 100644 --- a/README.md +++ b/README.md @@ -30,8 +30,14 @@ Use those packages with caution and at your own discretion. The `develop` branch contains the in-development version. Stable releases are tagged. -Documentation is built from the LaTeX file `bn.tex`. There is also limited documentation in `tommath.h`. -There is also a document, `tommath.pdf`, which describes the goals of the project and many of the algorithms used. +Documentation is built from the LaTeX file `doc/bn.tex` and available as PDF for each release. +This PDF is also created as build artifact on each CI run. + +There is also limited documentation in `tommath.h`. + +Originally the library contained a document, `tommath.pdf`, which describes the goals of the project and many of the algorithms used at the time. +This document has been removed since it can't be built anymore and nobody spent the time to fix and update it. +The latest valid update to that document was done in version [`0.39`](https://github.com/libtom/libtommath/releases/tag/0.39) of the library and it is contained within that tarball. The project can be build by using `make`. Along with the usual `make`, `make clean` and `make install`, there are several other build targets, see the makefile for details. From 92e9f32b9f5448bae66180d2cab57408fabc4db8 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 11 Mar 2024 10:16:35 +0100 Subject: [PATCH 278/304] Use actions/checkout@v3 Hopefully we have less warnings in the action logs then ... Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 2f0ef4e75..24f881f3d 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -29,7 +29,7 @@ jobs: runs-on: ubuntu-20.04 container: texlive/texlive:latest-full steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 - name: generate PDF run: | make docs V=1 @@ -129,7 +129,7 @@ jobs: - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 - name: install dependencies run: | sudo apt-get update -qq @@ -172,7 +172,7 @@ jobs: amalgam: runs-on: ubuntu-22.04 steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 - name: install dependencies run: | make amalgamated_timing @@ -190,7 +190,7 @@ jobs: # Shared library build - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=On' } steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 - name: install dependencies run: | sudo apt-get update -qq From 6dbb6fe63db704305231ffae1025e70dc63a9b6c Mon Sep 17 00:00:00 2001 From: J08nY Date: Tue, 28 Nov 2023 15:04:38 +0100 Subject: [PATCH 279/304] Allow to define custom MP_MIN_DIGIT_COUNT. --- tommath_private.h | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/tommath_private.h b/tommath_private.h index d319a1db0..c1fa95a04 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -160,8 +160,13 @@ MP_STATIC_ASSERT(correct_word_size, sizeof(mp_word) == (2u * sizeof(mp_digit))) * - Must be large enough such that the mp_set_u64 setter can * store uint64_t in the mp_int without growing */ -#define MP_MIN_DIGIT_COUNT MP_MAX(3, (((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) +#ifndef MP_MIN_DIGIT_COUNT +# define MP_MIN_DIGIT_COUNT MP_MAX(3, (((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT) +#endif MP_STATIC_ASSERT(prec_geq_min_prec, MP_DEFAULT_DIGIT_COUNT >= MP_MIN_DIGIT_COUNT) +MP_STATIC_ASSERT(min_prec_geq_3, MP_MIN_DIGIT_COUNT >= 3) +MP_STATIC_ASSERT(min_prec_geq_uint64size, + MP_MIN_DIGIT_COUNT >= ((((int)MP_SIZEOF_BITS(uint64_t) + MP_DIGIT_BIT) - 1) / MP_DIGIT_BIT)) /* Maximum number of digits. * - Must be small enough such that mp_bit_count does not overflow. From 4929f09f4304d3a131c11d4e17915db51dfc71d5 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 27 Mar 2024 14:41:51 +0100 Subject: [PATCH 280/304] Update version Signed-off-by: Steffen Jaeckel --- makefile_include.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/makefile_include.mk b/makefile_include.mk index 29ed58234..da897396b 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -3,7 +3,7 @@ # #version of library -VERSION=1.3.0 +VERSION=1.3.0-develop VERSION_PC=1.3.0 VERSION_SO=4:0:3 From bd66fccee4bddfb9334fd419444665abeaea6034 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 12 Apr 2022 15:03:47 +0200 Subject: [PATCH 281/304] add `MP_SMALL_STACK_SIZE` option This adds an option to use a heap-buffer for the usually stack-based `MP_WARRAY`-sized temporary buffers. Per default it will reserve a single buffer, which can be modified * at compile-time via the `MP_WARRAY_NUM` define * at run-time by calling `mp_warray_init()` The internal structure can only be created once. If one wants to modify the maximum number of elements, the entire structure has to be free'd by calling `mp_warray_free()`. In case one wants to use this option with multiple threads, one shall use the `mp_warray_init()` function and pass appropriate locking functions. Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 6 ++++ CMakeLists.txt | 2 +- demo/test.c | 31 ++++++++++++++-- doc/bn.tex | 64 +++++++++++++++++++++++++++++++++- helper.pl | 2 +- mp_warray_free.c | 36 +++++++++++++++++++ mp_warray_init.c | 55 +++++++++++++++++++++++++++++ s_mp_montgomery_reduce_comba.c | 7 +++- s_mp_mul_comba.c | 7 +++- s_mp_mul_high_comba.c | 7 +++- s_mp_sqr_comba.c | 6 +++- s_mp_warray.c | 8 +++++ s_mp_warray_free.c | 17 +++++++++ s_mp_warray_get.c | 33 ++++++++++++++++++ s_mp_warray_put.c | 20 +++++++++++ tommath.def | 2 ++ tommath.h | 28 +++++++++++++++ tommath_class.h | 36 +++++++++++++++++++ tommath_private.h | 36 +++++++++++++++++++ tommath_superclass.h | 2 ++ 20 files changed, 396 insertions(+), 9 deletions(-) create mode 100644 mp_warray_free.c create mode 100644 mp_warray_init.c create mode 100644 s_mp_warray.c create mode 100644 s_mp_warray_free.c create mode 100644 s_mp_warray_get.c create mode 100644 s_mp_warray_put.c diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 24f881f3d..6fcd5d466 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -70,6 +70,12 @@ jobs: # RSA superclass with tests (no sanitizer, but debug info) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + # Build with small stack-size + - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --cflags=-DMP_NO_LOCKING', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --cflags=-DMP_TEST_LOCKING', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_32BIT --limit-valgrind --make-option=tune' diff --git a/CMakeLists.txt b/CMakeLists.txt index d60632777..2f59d32e8 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -138,7 +138,7 @@ if(COMPILE_LTO) if(COMPILER_SUPPORTS_LTO) set_property(TARGET ${PROJECT_NAME} PROPERTY INTERPROCEDURAL_OPTIMIZATION TRUE) else() - message(SEND_ERROR "This compiler does not support LTO. Reconfigure ${PROJECT_NAME} with -DCOMPILE_LTO=OFF.") + message(FATAL_ERROR "This compiler does not support LTO. Reconfigure ${PROJECT_NAME} with -DCOMPILE_LTO=OFF.") endif() endif() diff --git a/demo/test.c b/demo/test.c index f290dbf21..4b1d30f86 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2451,6 +2451,21 @@ static int test_mp_pack_unpack(void) return EXIT_FAILURE; } + +#ifdef MP_TEST_LOCKING +#ifdef MP_NO_LOCKING +#error "Can't test locking when locking is disabled" +#endif +static mp_lock lock_ctx; +static int noop_lock_unlock(void *ctx) +{ + EXPECT(ctx == &lock_ctx); + return 0; +LBL_ERR: + return -1; +} +#endif + #ifndef LTM_TEST_DYNAMIC #define ONLY_PUBLIC_API_C #endif @@ -2525,7 +2540,14 @@ static int unit_tests(int argc, char **argv) unsigned long i, ok, fail, nop; uint64_t t; int j; +#ifdef MP_TEST_LOCKING + lock_ctx.lock = noop_lock_unlock; + lock_ctx.unlock = noop_lock_unlock; + lock_ctx.ctx = &lock_ctx; + if (mp_warray_init(MP_WARRAY_NUM, true, &lock_ctx) != MP_OKAY) + return EXIT_FAILURE; +#endif ok = fail = nop = 0; t = (uint64_t)time(NULL); @@ -2533,6 +2555,7 @@ static int unit_tests(int argc, char **argv) s_mp_rand_jenkins_init(t); mp_rand_source(s_mp_rand_jenkins); + for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { if (argc > 1) { for (j = 1; j < argc; ++j) { @@ -2556,8 +2579,12 @@ static int unit_tests(int argc, char **argv) } fprintf(fail?stderr:stdout, "Tests OK/NOP/FAIL: %lu/%lu/%lu\n", ok, nop, fail); - if (fail != 0) return EXIT_FAILURE; - else return EXIT_SUCCESS; + EXPECT(mp_warray_free() != -2); + + if (fail == 0) + return EXIT_SUCCESS; +LBL_ERR: + return EXIT_FAILURE; } int main(int argc, char **argv) diff --git a/doc/bn.tex b/doc/bn.tex index 22ae5f3eb..185876335 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -352,6 +352,20 @@ \subsubsection{Operand Size Related} \end{center} \end{small} +\subsection{Small-Stack option} +\label{ch:SMALL_STACK_INTRO} +The library can be compiled with the symbol \texttt{MP\_SMALL\_STACK\_SIZE} defined, which results in +the temporary \texttt{MP\_WARRAY}-sized stack buffers being put on the heap. +This comes with one problem, namely: formerly promised thread-safety isn't given anymore. +Therefore if the Small-Stack option is enabled while doing multi threading, the provided locking +mechanism shall be used. +For some use cases it can be desired to use the Small-Stack option, but there are no threads and +therefore we provide the possibility to disable locking by defining the symbol \texttt{MP\_NO\_LOCKING}. + +In case one already knows how many threads must be supported, the symbol \texttt{MP\_WARRAY\_NUM} can +be useful. It can be pre-defined at compile time to the number of heap buffers created on automatic +initialisation. C.f. \ref{ch:SMALL_STACK_API} for the dynamic API and further details. + \section{Purpose of LibTomMath} Unlike GNU MP (GMP) Library, LIP, OpenSSL or various other commercial kits (Miracl), LibTomMath was not written with bleeding edge performance in mind. First and foremost LibTomMath was written @@ -428,7 +442,9 @@ \chapter{Getting Started with LibTomMath} \section{Building Programs} In order to use LibTomMath you must include ``tommath.h'' and link against the appropriate library file (typically -libtommath.a). There is no library initialization required and the entire library is thread safe. +libtommath.a). There is no library initialization required and the entire library is thread safe +if it is used in its default configuration. Locking is recommended if the small-stack option +is enabled and multiple threads are used, c.f. \ref{ch:SMALL_STACK_INTRO} resp. \ref{ch:SMALL_STACK_API} \section{Return Codes} There are five possible return codes a function may return. @@ -813,6 +829,52 @@ \subsection{Adding additional digits} \end{alltt} \end{small} +\section{Small-Stack option} +\label{ch:SMALL_STACK_API} + +In case the \texttt{MP\_SMALL\_STACK\_SIZE} symbol is defined the following functions +can be useful. + +To initialize the internal structure the following function shall be called. + +\index{mp\_warray\_init} +\begin{alltt} +mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock); +\end{alltt} + +The flag \texttt{preallocate} controls whether the internal buffers -- +\texttt{n\_alloc} buffers of size \texttt{MP\_WARRAY} -- will be allocated when +\texttt{mp\_warray\_init()} is called, or whether they will be allocated when required. +The \texttt{mp\_lock} struct looks as follows and shall be used to protect the +internal structure when using the library in a multi-threaded application. + +\index{mp\_lock} +\begin{alltt} +typedef struct { + int (*lock)(void *ctx); + int (*unlock)(void *ctx); + void *ctx; +} mp_lock; +\end{alltt} + +The \texttt{mp\_lock.lock} resp. \texttt{mp\_lock.unlock} functions will be called before resp. +after modifying the internal struct. +The \texttt{mp\_lock.ctx} element will be passed to those functions. + +To free the internally allocated memory the following function shall be called. + +\index{mp\_warray\_free} +\begin{alltt} +int mp_warray_free(void); +\end{alltt} + + +Those two API functions are always available, even if the \texttt{MP\_SMALL\_STACK\_SIZE} option +has been disabled at compile time. +In that case \texttt{mp\_warray\_init()} will return \texttt{MP\_ERR} and \texttt{mp\_warray\_free()} +will return $-1$. + + \chapter{Basic Operations} \section{Copying} diff --git a/helper.pl b/helper.pl index 53658614c..ffc592a7c 100755 --- a/helper.pl +++ b/helper.pl @@ -394,7 +394,7 @@ sub update_dep foreach my $filename (glob '*mp_*.c') { my $content; my $cc = $ENV{'CC'} || 'gcc'; - $content = `$cc -E -x c -DLTM_ALL $filename`; + $content = `$cc -E -x c -DLTM_ALL -DMP_SMALL_STACK_SIZE $filename`; $content =~ s/^# 1 "$filename".*?^# 2 "$filename"//ms; # convert filename to upper case so we can use it as a define diff --git a/mp_warray_free.c b/mp_warray_free.c new file mode 100644 index 000000000..4b01282a0 --- /dev/null +++ b/mp_warray_free.c @@ -0,0 +1,36 @@ +#include "tommath_private.h" +#ifdef MP_WARRAY_FREE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +/* static check that the multiplication won't overflow */ +MP_STATIC_ASSERT(warray_free_sz_does_not_overflow, (sizeof(mp_word) * MP_WARRAY) >= MP_WARRAY) + +static int s_warray_free(void) +{ + int ret = 0; + size_t n; + S_MP_WARRAY_LOCK(); + for (n = 0; n < s_mp_warray.allocated; ++n) { + if (s_mp_warray.l_used[n].warray) { + ret = -2; + goto ERR_OUT; + } + } + for (n = 0; n < s_mp_warray.allocated; ++n) { + MP_FREE(s_mp_warray.l_free[n].warray, sizeof(mp_word) * MP_WARRAY); + s_mp_warray.l_free[n].warray = NULL; + } + s_mp_warray_free(s_mp_warray.usable); +ERR_OUT: + S_MP_WARRAY_UNLOCK(); + return ret; +} + +int mp_warray_free(void) +{ + if (MP_HAS(MP_SMALL_STACK_SIZE)) return s_warray_free(); + return -1; +} + +#endif diff --git a/mp_warray_init.c b/mp_warray_init.c new file mode 100644 index 000000000..0ff93aa53 --- /dev/null +++ b/mp_warray_init.c @@ -0,0 +1,55 @@ +#include "tommath_private.h" +#ifdef MP_WARRAY_INIT_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +static mp_err s_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock) +{ + size_t n; + if (s_mp_warray.l_free != NULL || s_mp_warray.l_used != NULL) { + return MP_VAL; + } + + if (MP_HAS(MP_USE_LOCKING) && (lock != NULL)) { + if (lock->lock == NULL || lock->unlock == NULL) + return MP_VAL; + s_mp_warray.lock = *lock; + s_mp_warray.locking_enabled = true; + } else { + s_mp_zero_buf(&s_mp_warray.lock, sizeof(s_mp_warray.lock)); + } + + s_mp_warray.l_free = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_free))); + s_mp_warray.l_used = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_used))); + if (s_mp_warray.l_free == NULL || s_mp_warray.l_used == NULL) { + s_mp_warray_free(n_alloc); + return MP_MEM; + } + + if (preallocate) { + for (n = 0; n < n_alloc; ++n) { + s_mp_warray.l_free[n].warray = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); + if (s_mp_warray.l_free[n].warray == NULL) { + while (n > 0) { + n--; + MP_FREE(s_mp_warray.l_free[n].warray, MP_WARRAY * sizeof(mp_word)); + s_mp_warray.l_free[n].warray = NULL; + } + s_mp_warray_free(n_alloc); + return MP_MEM; + } + } + s_mp_warray.allocated = n_alloc; + } + + s_mp_warray.usable = n_alloc; + return MP_OKAY; +} + +mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock) +{ + if (MP_HAS(MP_SMALL_STACK_SIZE)) return s_warray_init(n_alloc, preallocate, lock); + return MP_ERR; +} + +#endif diff --git a/s_mp_montgomery_reduce_comba.c b/s_mp_montgomery_reduce_comba.c index 7472caf34..3858f75a0 100644 --- a/s_mp_montgomery_reduce_comba.c +++ b/s_mp_montgomery_reduce_comba.c @@ -15,9 +15,12 @@ mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) { int ix, oldused; mp_err err; - mp_word W[MP_WARRAY]; + mp_word MP_ALLOC_WARRAY(W); + + MP_CHECK_WARRAY(W); if (x->used > MP_WARRAY) { + MP_FREE_WARRAY(W); return MP_VAL; } @@ -26,6 +29,7 @@ mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) /* grow a as required */ if ((err = mp_grow(x, n->used + 1)) != MP_OKAY) { + MP_FREE_WARRAY(W); return err; } @@ -110,6 +114,7 @@ mp_err s_mp_montgomery_reduce_comba(mp_int *x, const mp_int *n, mp_digit rho) mp_clamp(x); + MP_FREE_WARRAY(W); /* if A >= m then A = A - m */ if (mp_cmp_mag(x, n) != MP_LT) { return s_mp_sub(x, n, x); diff --git a/s_mp_mul_comba.c b/s_mp_mul_comba.c index ca89ff9dd..5b37035ea 100644 --- a/s_mp_mul_comba.c +++ b/s_mp_mul_comba.c @@ -23,15 +23,19 @@ mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) { int oldused, pa, ix; mp_err err; - mp_digit W[MP_WARRAY]; + mp_digit MP_ALLOC_WARRAY(W); mp_word _W; + MP_CHECK_WARRAY(W); + if (digs < 0) { + MP_FREE_WARRAY(W); return MP_VAL; } /* grow the destination as required */ if ((err = mp_grow(c, digs)) != MP_OKAY) { + MP_FREE_WARRAY(W); return err; } @@ -77,6 +81,7 @@ mp_err s_mp_mul_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs) s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); + MP_FREE_WARRAY(W); return MP_OKAY; } #endif diff --git a/s_mp_mul_high_comba.c b/s_mp_mul_high_comba.c index b5ac06d74..b0096d4e6 100644 --- a/s_mp_mul_high_comba.c +++ b/s_mp_mul_high_comba.c @@ -16,16 +16,20 @@ mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs { int oldused, pa, ix; mp_err err; - mp_digit W[MP_WARRAY]; + mp_digit MP_ALLOC_WARRAY(W); mp_word _W; + MP_CHECK_WARRAY(W); + if (digs < 0) { + MP_FREE_WARRAY(W); return MP_VAL; } /* grow the destination as required */ pa = a->used + b->used; if ((err = mp_grow(c, pa)) != MP_OKAY) { + MP_FREE_WARRAY(W); return err; } @@ -69,6 +73,7 @@ mp_err s_mp_mul_high_comba(const mp_int *a, const mp_int *b, mp_int *c, int digs s_mp_zero_digs(c->dp + c->used, oldused - c->used); mp_clamp(c); + MP_FREE_WARRAY(W); return MP_OKAY; } #endif diff --git a/s_mp_sqr_comba.c b/s_mp_sqr_comba.c index 1bcc1f93f..336a0a082 100644 --- a/s_mp_sqr_comba.c +++ b/s_mp_sqr_comba.c @@ -16,13 +16,16 @@ After that loop you do the squares and add them in. mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) { int oldused, pa, ix; - mp_digit W[MP_WARRAY]; + mp_digit MP_ALLOC_WARRAY(W); mp_word W1; mp_err err; + MP_CHECK_WARRAY(W); + /* grow the destination as required */ pa = a->used + a->used; if ((err = mp_grow(b, pa)) != MP_OKAY) { + MP_FREE_WARRAY(W); return err; } @@ -82,6 +85,7 @@ mp_err s_mp_sqr_comba(const mp_int *a, mp_int *b) s_mp_zero_digs(b->dp + b->used, oldused - b->used); mp_clamp(b); + MP_FREE_WARRAY(W); return MP_OKAY; } #endif diff --git a/s_mp_warray.c b/s_mp_warray.c new file mode 100644 index 000000000..d181057cb --- /dev/null +++ b/s_mp_warray.c @@ -0,0 +1,8 @@ +#include "tommath_private.h" +#ifdef S_MP_WARRAY_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +st_warray s_mp_warray; + +#endif diff --git a/s_mp_warray_free.c b/s_mp_warray_free.c new file mode 100644 index 000000000..9d8b75eb1 --- /dev/null +++ b/s_mp_warray_free.c @@ -0,0 +1,17 @@ +#include "tommath_private.h" +#ifdef S_MP_WARRAY_FREE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +void s_mp_warray_free(size_t n) +{ + (void)n; + MP_FREE(s_mp_warray.l_free, n * sizeof(*(s_mp_warray.l_free))); + MP_FREE(s_mp_warray.l_used, n * sizeof(*(s_mp_warray.l_used))); + s_mp_warray.l_free = NULL; + s_mp_warray.l_used = NULL; + s_mp_warray.allocated = 0; + s_mp_warray.usable = 0; +} + +#endif diff --git a/s_mp_warray_get.c b/s_mp_warray_get.c new file mode 100644 index 000000000..69b2b72dd --- /dev/null +++ b/s_mp_warray_get.c @@ -0,0 +1,33 @@ +#include "tommath_private.h" +#ifdef S_MP_WARRAY_GET_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +void *s_mp_warray_get(void) +{ + void *ret = NULL; + size_t n; + S_MP_WARRAY_LOCK(); + if (s_mp_warray.usable == 0) { + if (mp_warray_init(MP_WARRAY_NUM, false, NULL) != MP_OKAY) + return NULL; + } + for (n = 0; n < s_mp_warray.allocated; ++n) { + if (s_mp_warray.l_free[n].warray) { + s_mp_warray.l_used[n] = s_mp_warray.l_free[n]; + s_mp_warray.l_free[n].warray = NULL; + ret = s_mp_warray.l_used[n].warray; + goto LBL_OUT; + } + } + if (s_mp_warray.allocated + 1 > s_mp_warray.usable) + goto LBL_OUT; + ret = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); + s_mp_warray.l_used[s_mp_warray.allocated++].warray = ret; + +LBL_OUT: + S_MP_WARRAY_UNLOCK(); + return ret; +} + +#endif diff --git a/s_mp_warray_put.c b/s_mp_warray_put.c new file mode 100644 index 000000000..5d84bea86 --- /dev/null +++ b/s_mp_warray_put.c @@ -0,0 +1,20 @@ +#include "tommath_private.h" +#ifdef S_MP_WARRAY_PUT_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +void s_mp_warray_put(void *w) +{ + size_t n; + S_MP_WARRAY_LOCK(); + for (n = 0; n < s_mp_warray.allocated; ++n) { + if (s_mp_warray.l_used[n].warray == w) { + s_mp_warray.l_free[n] = s_mp_warray.l_used[n]; + s_mp_warray.l_used[n].warray = NULL; + break; + } + } + S_MP_WARRAY_UNLOCK(); +} + +#endif diff --git a/tommath.def b/tommath.def index 86f348727..7aa5860f7 100644 --- a/tommath.def +++ b/tommath.def @@ -125,6 +125,8 @@ EXPORTS mp_to_ubin mp_ubin_size mp_unpack + mp_warray_free + mp_warray_init mp_xor mp_zero MP_MUL_KARATSUBA_CUTOFF diff --git a/tommath.h b/tommath.h index 84bb0909d..d36753dec 100644 --- a/tommath.h +++ b/tommath.h @@ -78,6 +78,25 @@ typedef uint32_t mp_digit; #define MP_MASK ((((mp_digit)1)<<((mp_digit)MP_DIGIT_BIT))-((mp_digit)1)) #define MP_DIGIT_MAX MP_MASK +/* In case the stack size has to be limited, use a WARRAY from the heap */ +#ifdef MP_SMALL_STACK_SIZE +/* Per default we enable the locking mechanism. + * Please disable by defining `MP_NO_LOCKING` if you really know what you do. + */ +#ifndef MP_NO_LOCKING +#define MP_USE_LOCKING +#endif +#endif /* MP_SMALL_STACK_SIZE */ + +/* The user can define how many WARRAY instances are allocated, + * usually this should equal the number of parallel threads that + * use LTM functionality. + * This has no effect if `MP_SMALL_STACK_SIZE` is not defined. + */ +#ifndef MP_WARRAY_NUM +#define MP_WARRAY_NUM 1 +#endif + /* Primality generation flags */ #define MP_PRIME_BBS 0x0001 /* BBS style prime */ #define MP_PRIME_SAFE 0x0002 /* Safe prime (p-1)/2 == prime */ @@ -588,6 +607,15 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) MP_WUR; #endif +typedef struct { + int (*lock)(void *ctx); + int (*unlock)(void *ctx); + void *ctx; +} mp_lock; + +mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock); +int mp_warray_free(void); + #define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), NULL, 2) #define mp_to_octal(M, S, N) mp_to_radix((M), (S), (N), NULL, 8) #define mp_to_decimal(M, S, N) mp_to_radix((M), (S), (N), NULL, 10) diff --git a/tommath_class.h b/tommath_class.h index e08bc5f3c..e1a254fed 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -131,6 +131,8 @@ # define MP_TO_UBIN_C # define MP_UBIN_SIZE_C # define MP_UNPACK_C +# define MP_WARRAY_FREE_C +# define MP_WARRAY_INIT_C # define MP_XOR_C # define MP_ZERO_C # define S_MP_ADD_C @@ -165,6 +167,10 @@ # define S_MP_SQR_KARATSUBA_C # define S_MP_SQR_TOOM_C # define S_MP_SUB_C +# define S_MP_WARRAY_C +# define S_MP_WARRAY_FREE_C +# define S_MP_WARRAY_GET_C +# define S_MP_WARRAY_PUT_C # define S_MP_ZERO_BUF_C # define S_MP_ZERO_DIGS_C #endif @@ -957,6 +963,15 @@ # define MP_ZERO_C #endif +#if defined(MP_WARRAY_FREE_C) +# define S_MP_WARRAY_FREE_C +#endif + +#if defined(MP_WARRAY_INIT_C) +# define S_MP_WARRAY_FREE_C +# define S_MP_ZERO_BUF_C +#endif + #if defined(MP_XOR_C) # define MP_CLAMP_C # define MP_GROW_C @@ -1137,6 +1152,8 @@ # define MP_CMP_MAG_C # define MP_GROW_C # define S_MP_SUB_C +# define S_MP_WARRAY_GET_C +# define S_MP_WARRAY_PUT_C # define S_MP_ZERO_BUF_C # define S_MP_ZERO_DIGS_C #endif @@ -1165,6 +1182,8 @@ #if defined(S_MP_MUL_COMBA_C) # define MP_CLAMP_C # define MP_GROW_C +# define S_MP_WARRAY_GET_C +# define S_MP_WARRAY_PUT_C # define S_MP_ZERO_DIGS_C #endif @@ -1179,6 +1198,8 @@ #if defined(S_MP_MUL_HIGH_COMBA_C) # define MP_CLAMP_C # define MP_GROW_C +# define S_MP_WARRAY_GET_C +# define S_MP_WARRAY_PUT_C # define S_MP_ZERO_DIGS_C #endif @@ -1244,6 +1265,8 @@ #if defined(S_MP_SQR_COMBA_C) # define MP_CLAMP_C # define MP_GROW_C +# define S_MP_WARRAY_GET_C +# define S_MP_WARRAY_PUT_C # define S_MP_ZERO_DIGS_C #endif @@ -1279,6 +1302,19 @@ # define S_MP_ZERO_DIGS_C #endif +#if defined(S_MP_WARRAY_C) +#endif + +#if defined(S_MP_WARRAY_FREE_C) +#endif + +#if defined(S_MP_WARRAY_GET_C) +# define MP_WARRAY_INIT_C +#endif + +#if defined(S_MP_WARRAY_PUT_C) +#endif + #if defined(S_MP_ZERO_BUF_C) #endif diff --git a/tommath_private.h b/tommath_private.h index c1fa95a04..6ccf8f0dd 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -234,6 +234,42 @@ MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; +#ifdef MP_SMALL_STACK_SIZE +#define MP_SMALL_STACK_SIZE_C +#define MP_ALLOC_WARRAY(name) *name = s_mp_warray_get() +#define MP_FREE_WARRAY(name) s_mp_warray_put(name) +#define MP_CHECK_WARRAY(name) do { if ((name) == NULL) { return MP_MEM; } } while(0) +#else +#define MP_ALLOC_WARRAY(name) name[MP_WARRAY] +#define MP_FREE_WARRAY(name) +#define MP_CHECK_WARRAY(name) +#endif + +#ifdef MP_USE_LOCKING +#define MP_USE_LOCKING_C +#define S_MP_WARRAY_LOCK() do { if (s_mp_warray.locking_enabled) { s_mp_warray.lock.lock(s_mp_warray.lock.ctx); } } while(0) +#define S_MP_WARRAY_UNLOCK() do { if (s_mp_warray.locking_enabled) { s_mp_warray.lock.unlock(s_mp_warray.lock.ctx); } } while(0) +#else +#define S_MP_WARRAY_LOCK() +#define S_MP_WARRAY_UNLOCK() +#endif + +struct warray { + void *warray; +}; +typedef struct { + struct warray *l_free, *l_used; + size_t allocated, usable; + bool locking_enabled; + mp_lock lock; +} st_warray; + +extern MP_PRIVATE st_warray s_mp_warray; + +MP_PRIVATE void *s_mp_warray_get(void); +MP_PRIVATE void s_mp_warray_put(void *w); +MP_PRIVATE void s_mp_warray_free(size_t n); + #define MP_RADIX_MAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_radix_map[]; extern MP_PRIVATE const uint8_t s_mp_radix_map_reverse[]; diff --git a/tommath_superclass.h b/tommath_superclass.h index 9245e0020..10c7f12a2 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -42,6 +42,8 @@ # define MP_SBIN_SIZE_C # define MP_TO_RADIX_C # define MP_TO_SBIN_C +# define MP_WARRAY_FREE_C +# define MP_WARRAY_INIT_C # define S_MP_RAND_JENKINS_C # define S_MP_RAND_PLATFORM_C #endif From 18e67e1888a801d550b3a9e3e21943fca0d45875 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 14 Mar 2024 11:42:34 +0100 Subject: [PATCH 282/304] Replace locking by atomic operations `s_warray_init()` and `s_warray_free()` are not safe and MUST NOT be called from multiple threads. This also removes `MP_WARRAY_NUM`, since automatic initialization will not be safe for more than one thread. Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 2 -- demo/test.c | 23 ----------------------- doc/bn.tex | 33 ++++++++------------------------- mp_warray_free.c | 2 -- mp_warray_init.c | 15 +++------------ s_mp_warray_get.c | 17 +++++++++-------- s_mp_warray_put.c | 8 +++----- tommath.h | 27 +-------------------------- tommath_class.h | 1 - tommath_private.h | 15 ++++----------- 10 files changed, 28 insertions(+), 115 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 6fcd5d466..664cfcaf7 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -72,9 +72,7 @@ jobs: # Build with small stack-size - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --cflags=-DMP_NO_LOCKING', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --cflags=-DMP_TEST_LOCKING', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' diff --git a/demo/test.c b/demo/test.c index 4b1d30f86..c4eb1f8a8 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2451,21 +2451,6 @@ static int test_mp_pack_unpack(void) return EXIT_FAILURE; } - -#ifdef MP_TEST_LOCKING -#ifdef MP_NO_LOCKING -#error "Can't test locking when locking is disabled" -#endif -static mp_lock lock_ctx; -static int noop_lock_unlock(void *ctx) -{ - EXPECT(ctx == &lock_ctx); - return 0; -LBL_ERR: - return -1; -} -#endif - #ifndef LTM_TEST_DYNAMIC #define ONLY_PUBLIC_API_C #endif @@ -2540,14 +2525,6 @@ static int unit_tests(int argc, char **argv) unsigned long i, ok, fail, nop; uint64_t t; int j; -#ifdef MP_TEST_LOCKING - lock_ctx.lock = noop_lock_unlock; - lock_ctx.unlock = noop_lock_unlock; - lock_ctx.ctx = &lock_ctx; - - if (mp_warray_init(MP_WARRAY_NUM, true, &lock_ctx) != MP_OKAY) - return EXIT_FAILURE; -#endif ok = fail = nop = 0; t = (uint64_t)time(NULL); diff --git a/doc/bn.tex b/doc/bn.tex index 185876335..63e71633b 100644 --- a/doc/bn.tex +++ b/doc/bn.tex @@ -357,14 +357,10 @@ \subsection{Small-Stack option} The library can be compiled with the symbol \texttt{MP\_SMALL\_STACK\_SIZE} defined, which results in the temporary \texttt{MP\_WARRAY}-sized stack buffers being put on the heap. This comes with one problem, namely: formerly promised thread-safety isn't given anymore. -Therefore if the Small-Stack option is enabled while doing multi threading, the provided locking -mechanism shall be used. -For some use cases it can be desired to use the Small-Stack option, but there are no threads and -therefore we provide the possibility to disable locking by defining the symbol \texttt{MP\_NO\_LOCKING}. +Therefore if the Small-Stack option is enabled while doing multi threading, one shall always initialize +the library by calling \texttt{mp\_warray\_init()} once with the correct number of threads. -In case one already knows how many threads must be supported, the symbol \texttt{MP\_WARRAY\_NUM} can -be useful. It can be pre-defined at compile time to the number of heap buffers created on automatic -initialisation. C.f. \ref{ch:SMALL_STACK_API} for the dynamic API and further details. +C.f. \ref{ch:SMALL_STACK_API} for the API description and further details. \section{Purpose of LibTomMath} Unlike GNU MP (GMP) Library, LIP, OpenSSL or various other commercial kits (Miracl), LibTomMath @@ -443,8 +439,10 @@ \section{Building Programs} In order to use LibTomMath you must include ``tommath.h'' and link against the appropriate library file (typically libtommath.a). There is no library initialization required and the entire library is thread safe -if it is used in its default configuration. Locking is recommended if the small-stack option -is enabled and multiple threads are used, c.f. \ref{ch:SMALL_STACK_INTRO} resp. \ref{ch:SMALL_STACK_API} +if it is used in its default configuration. The small-stack option makes use of atomic operations +to maintain its internal state and therefore does not require locking, but it MUST be initialized +if used from multiple threads. For further information see \ref{ch:SMALL_STACK_INTRO} resp. +\ref{ch:SMALL_STACK_API}. \section{Return Codes} There are five possible return codes a function may return. @@ -839,27 +837,12 @@ \section{Small-Stack option} \index{mp\_warray\_init} \begin{alltt} -mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock); +mp_err mp_warray_init(size_t n_alloc, bool preallocate); \end{alltt} The flag \texttt{preallocate} controls whether the internal buffers -- \texttt{n\_alloc} buffers of size \texttt{MP\_WARRAY} -- will be allocated when \texttt{mp\_warray\_init()} is called, or whether they will be allocated when required. -The \texttt{mp\_lock} struct looks as follows and shall be used to protect the -internal structure when using the library in a multi-threaded application. - -\index{mp\_lock} -\begin{alltt} -typedef struct { - int (*lock)(void *ctx); - int (*unlock)(void *ctx); - void *ctx; -} mp_lock; -\end{alltt} - -The \texttt{mp\_lock.lock} resp. \texttt{mp\_lock.unlock} functions will be called before resp. -after modifying the internal struct. -The \texttt{mp\_lock.ctx} element will be passed to those functions. To free the internally allocated memory the following function shall be called. diff --git a/mp_warray_free.c b/mp_warray_free.c index 4b01282a0..088efefc4 100644 --- a/mp_warray_free.c +++ b/mp_warray_free.c @@ -10,7 +10,6 @@ static int s_warray_free(void) { int ret = 0; size_t n; - S_MP_WARRAY_LOCK(); for (n = 0; n < s_mp_warray.allocated; ++n) { if (s_mp_warray.l_used[n].warray) { ret = -2; @@ -23,7 +22,6 @@ static int s_warray_free(void) } s_mp_warray_free(s_mp_warray.usable); ERR_OUT: - S_MP_WARRAY_UNLOCK(); return ret; } diff --git a/mp_warray_init.c b/mp_warray_init.c index 0ff93aa53..c25098861 100644 --- a/mp_warray_init.c +++ b/mp_warray_init.c @@ -3,22 +3,13 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -static mp_err s_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock) +static mp_err s_warray_init(size_t n_alloc, bool preallocate) { size_t n; if (s_mp_warray.l_free != NULL || s_mp_warray.l_used != NULL) { return MP_VAL; } - if (MP_HAS(MP_USE_LOCKING) && (lock != NULL)) { - if (lock->lock == NULL || lock->unlock == NULL) - return MP_VAL; - s_mp_warray.lock = *lock; - s_mp_warray.locking_enabled = true; - } else { - s_mp_zero_buf(&s_mp_warray.lock, sizeof(s_mp_warray.lock)); - } - s_mp_warray.l_free = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_free))); s_mp_warray.l_used = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_used))); if (s_mp_warray.l_free == NULL || s_mp_warray.l_used == NULL) { @@ -46,9 +37,9 @@ static mp_err s_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock) return MP_OKAY; } -mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock) +mp_err mp_warray_init(size_t n_alloc, bool preallocate) { - if (MP_HAS(MP_SMALL_STACK_SIZE)) return s_warray_init(n_alloc, preallocate, lock); + if (MP_HAS(MP_SMALL_STACK_SIZE)) return s_warray_init(n_alloc, preallocate); return MP_ERR; } diff --git a/s_mp_warray_get.c b/s_mp_warray_get.c index 69b2b72dd..013e83322 100644 --- a/s_mp_warray_get.c +++ b/s_mp_warray_get.c @@ -7,26 +7,27 @@ void *s_mp_warray_get(void) { void *ret = NULL; size_t n; - S_MP_WARRAY_LOCK(); if (s_mp_warray.usable == 0) { - if (mp_warray_init(MP_WARRAY_NUM, false, NULL) != MP_OKAY) + if (mp_warray_init(1, false) != MP_OKAY) return NULL; } for (n = 0; n < s_mp_warray.allocated; ++n) { - if (s_mp_warray.l_free[n].warray) { - s_mp_warray.l_used[n] = s_mp_warray.l_free[n]; - s_mp_warray.l_free[n].warray = NULL; - ret = s_mp_warray.l_used[n].warray; + if (s_mp_warray.l_free[n].warray == NULL) + continue; + ret = s_mp_warray.l_free[n].warray; + if (MP_CMPEXCH(&s_mp_warray.l_free[n].warray, &ret, NULL)) { + s_mp_warray.l_used[n].warray = ret; goto LBL_OUT; } } + ret = NULL; if (s_mp_warray.allocated + 1 > s_mp_warray.usable) goto LBL_OUT; ret = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); - s_mp_warray.l_used[s_mp_warray.allocated++].warray = ret; + if (ret != NULL) + s_mp_warray.l_used[s_mp_warray.allocated++].warray = ret; LBL_OUT: - S_MP_WARRAY_UNLOCK(); return ret; } diff --git a/s_mp_warray_put.c b/s_mp_warray_put.c index 5d84bea86..4cf413d62 100644 --- a/s_mp_warray_put.c +++ b/s_mp_warray_put.c @@ -5,16 +5,14 @@ void s_mp_warray_put(void *w) { - size_t n; - S_MP_WARRAY_LOCK(); - for (n = 0; n < s_mp_warray.allocated; ++n) { + size_t n, allocated = s_mp_warray.allocated; + for (n = 0; n < allocated; ++n) { if (s_mp_warray.l_used[n].warray == w) { - s_mp_warray.l_free[n] = s_mp_warray.l_used[n]; s_mp_warray.l_used[n].warray = NULL; + s_mp_warray.l_free[n].warray = w; break; } } - S_MP_WARRAY_UNLOCK(); } #endif diff --git a/tommath.h b/tommath.h index d36753dec..7da36d0e9 100644 --- a/tommath.h +++ b/tommath.h @@ -78,25 +78,6 @@ typedef uint32_t mp_digit; #define MP_MASK ((((mp_digit)1)<<((mp_digit)MP_DIGIT_BIT))-((mp_digit)1)) #define MP_DIGIT_MAX MP_MASK -/* In case the stack size has to be limited, use a WARRAY from the heap */ -#ifdef MP_SMALL_STACK_SIZE -/* Per default we enable the locking mechanism. - * Please disable by defining `MP_NO_LOCKING` if you really know what you do. - */ -#ifndef MP_NO_LOCKING -#define MP_USE_LOCKING -#endif -#endif /* MP_SMALL_STACK_SIZE */ - -/* The user can define how many WARRAY instances are allocated, - * usually this should equal the number of parallel threads that - * use LTM functionality. - * This has no effect if `MP_SMALL_STACK_SIZE` is not defined. - */ -#ifndef MP_WARRAY_NUM -#define MP_WARRAY_NUM 1 -#endif - /* Primality generation flags */ #define MP_PRIME_BBS 0x0001 /* BBS style prime */ #define MP_PRIME_SAFE 0x0002 /* Safe prime (p-1)/2 == prime */ @@ -607,13 +588,7 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) MP_WUR; #endif -typedef struct { - int (*lock)(void *ctx); - int (*unlock)(void *ctx); - void *ctx; -} mp_lock; - -mp_err mp_warray_init(size_t n_alloc, bool preallocate, mp_lock *lock); +mp_err mp_warray_init(size_t n_alloc, bool preallocate); int mp_warray_free(void); #define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), NULL, 2) diff --git a/tommath_class.h b/tommath_class.h index e1a254fed..8841413cf 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -969,7 +969,6 @@ #if defined(MP_WARRAY_INIT_C) # define S_MP_WARRAY_FREE_C -# define S_MP_ZERO_BUF_C #endif #if defined(MP_XOR_C) diff --git a/tommath_private.h b/tommath_private.h index 6ccf8f0dd..46c3afe2e 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -104,6 +104,10 @@ extern void *MP_CALLOC(size_t nmemb, size_t size); extern void MP_FREE(void *mem, size_t size); #endif +#ifndef MP_CMPEXCH +#define MP_CMPEXCH(ptr, expected, desired) __atomic_compare_exchange_n(ptr, expected, desired, true, __ATOMIC_ACQ_REL, __ATOMIC_ACQUIRE) +#endif + /* feature detection macro */ #ifdef _MSC_VER /* Prevent false positive: not enough arguments for function-like macro invocation */ @@ -245,23 +249,12 @@ MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; #define MP_CHECK_WARRAY(name) #endif -#ifdef MP_USE_LOCKING -#define MP_USE_LOCKING_C -#define S_MP_WARRAY_LOCK() do { if (s_mp_warray.locking_enabled) { s_mp_warray.lock.lock(s_mp_warray.lock.ctx); } } while(0) -#define S_MP_WARRAY_UNLOCK() do { if (s_mp_warray.locking_enabled) { s_mp_warray.lock.unlock(s_mp_warray.lock.ctx); } } while(0) -#else -#define S_MP_WARRAY_LOCK() -#define S_MP_WARRAY_UNLOCK() -#endif - struct warray { void *warray; }; typedef struct { struct warray *l_free, *l_used; size_t allocated, usable; - bool locking_enabled; - mp_lock lock; } st_warray; extern MP_PRIVATE st_warray s_mp_warray; From 795f7ba5f5064e8f9bffc0691c5052e9e7a7b140 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 14 Mar 2024 13:16:01 +0100 Subject: [PATCH 283/304] Add `s_mp_cmpexch_n()` To be able to support this for MSVC as well, we have to move this into a separate private API function. Signed-off-by: Steffen Jaeckel --- s_mp_cmpexch_n.c | 44 ++++++++++++++++++++++++++++++++++++++++++++ s_mp_warray_get.c | 2 +- tommath_class.h | 5 +++++ tommath_private.h | 6 ++---- 4 files changed, 52 insertions(+), 5 deletions(-) create mode 100644 s_mp_cmpexch_n.c diff --git a/s_mp_cmpexch_n.c b/s_mp_cmpexch_n.c new file mode 100644 index 000000000..6334d9d4b --- /dev/null +++ b/s_mp_cmpexch_n.c @@ -0,0 +1,44 @@ +#include "tommath_private.h" +#ifdef S_MP_CMPEXCH_N_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +#ifdef __GNUC__ +#define S_CMPEXCH_N_GCC_C +static bool s_cmpexch_n_gcc(void **ptr, void **expected, void *desired) +{ + return __atomic_compare_exchange_n(ptr, expected, desired, true, __ATOMIC_ACQ_REL, __ATOMIC_ACQUIRE); +} +#endif + +#ifdef _MSC_VER +#define S_CMPEXCH_N_MSVC_C + +#ifndef _WIN32_WINNT +#define _WIN32_WINNT 0x0501 +#endif +#ifndef WINVER +#define WINVER 0x0501 +#endif + +#define WIN32_LEAN_AND_MEAN +#include + +static bool s_cmpexch_n_msvc(void **ptr, void **expected, void *desired) +{ + InterlockedCompareExchangePointer(ptr, desired, *(expected)); + return *ptr == desired; +} +#endif + +bool s_cmpexch_n_gcc(void **ptr, void **expected, void *desired); +bool s_cmpexch_n_msvc(void **ptr, void **expected, void *desired); + +bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired) +{ + if (MP_HAS(S_CMPEXCH_N_GCC)) return s_cmpexch_n_gcc(ptr, expected, desired); + if (MP_HAS(S_CMPEXCH_N_MSVC)) return s_cmpexch_n_msvc(ptr, expected, desired); + return false; +} + +#endif diff --git a/s_mp_warray_get.c b/s_mp_warray_get.c index 013e83322..068e8145d 100644 --- a/s_mp_warray_get.c +++ b/s_mp_warray_get.c @@ -15,7 +15,7 @@ void *s_mp_warray_get(void) if (s_mp_warray.l_free[n].warray == NULL) continue; ret = s_mp_warray.l_free[n].warray; - if (MP_CMPEXCH(&s_mp_warray.l_free[n].warray, &ret, NULL)) { + if (s_mp_cmpexch_n(&s_mp_warray.l_free[n].warray, &ret, NULL)) { s_mp_warray.l_used[n].warray = ret; goto LBL_OUT; } diff --git a/tommath_class.h b/tommath_class.h index 8841413cf..bb89cc237 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -136,6 +136,7 @@ # define MP_XOR_C # define MP_ZERO_C # define S_MP_ADD_C +# define S_MP_CMPEXCH_N_C # define S_MP_COPY_DIGS_C # define S_MP_DIV_3_C # define S_MP_DIV_RECURSIVE_C @@ -986,6 +987,9 @@ # define S_MP_ZERO_DIGS_C #endif +#if defined(S_MP_CMPEXCH_N_C) +#endif + #if defined(S_MP_COPY_DIGS_C) #endif @@ -1309,6 +1313,7 @@ #if defined(S_MP_WARRAY_GET_C) # define MP_WARRAY_INIT_C +# define S_MP_CMPEXCH_N_C #endif #if defined(S_MP_WARRAY_PUT_C) diff --git a/tommath_private.h b/tommath_private.h index 46c3afe2e..36291a061 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -104,10 +104,6 @@ extern void *MP_CALLOC(size_t nmemb, size_t size); extern void MP_FREE(void *mem, size_t size); #endif -#ifndef MP_CMPEXCH -#define MP_CMPEXCH(ptr, expected, desired) __atomic_compare_exchange_n(ptr, expected, desired, true, __ATOMIC_ACQ_REL, __ATOMIC_ACQUIRE) -#endif - /* feature detection macro */ #ifdef _MSC_VER /* Prevent false positive: not enough arguments for function-like macro invocation */ @@ -238,6 +234,8 @@ MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; +MP_PRIVATE bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired); + #ifdef MP_SMALL_STACK_SIZE #define MP_SMALL_STACK_SIZE_C #define MP_ALLOC_WARRAY(name) *name = s_mp_warray_get() From 98655a8e3c7249ce08a30a0b064c874aa5316c60 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 14 Mar 2024 13:49:53 +0100 Subject: [PATCH 284/304] Add multi-threaded tests Output gets garbeled a bit, but we only care for the result which is `Tests OK/NOP/FAIL: 50/0/0`. Add `-Wno-incomplete-setjmp-declaration` since `clang-10` shipping with Ubuntu 20.04 seems broken... and `-Wno-unknown-warning-option` since `clang-8` doesn't know about this warning... Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 2 ++ demo/test.c | 68 ++++++++++++++++++++++++++++++++------ makefile_include.mk | 2 +- testme.sh | 37 ++++++++++++--------- 4 files changed, 82 insertions(+), 27 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 664cfcaf7..fd8e34cf5 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -73,6 +73,8 @@ jobs: # Build with small stack-size - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' diff --git a/demo/test.c b/demo/test.c index c4eb1f8a8..306a9c28a 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2455,12 +2455,39 @@ static int test_mp_pack_unpack(void) #define ONLY_PUBLIC_API_C #endif +#if !defined(LTM_TEST_MULTITHREAD) || !defined(MP_SMALL_STACK_SIZE) +#define SINGLE_THREADED_C +typedef unsigned long int pthread_t; +extern int pthread_create(pthread_t *, const void *, void *(*)(void *), void *); +extern int pthread_join(pthread_t, void **); +#else +#define MULTI_THREADED_C +#include +#endif + +struct test_fn { + const char *name; + int (*fn)(void); +}; + +struct thread_info { + pthread_t thread_id; + const struct test_fn *t; + int ret; +}; + +static void *run(void *arg) +{ + struct thread_info *tinfo = arg; + + tinfo->ret = tinfo->t->fn(); + + return arg; +} + static int unit_tests(int argc, char **argv) { - static const struct { - const char *name; - int (*fn)(void); - } test[] = { + static const struct test_fn test[] = { #define T0(n) { #n, test_##n } #define T1(n, o) { #n, MP_HAS(o) ? test_##n : NULL } #define T2(n, o1, o2) { #n, (MP_HAS(o1) && MP_HAS(o2)) ? test_##n : NULL } @@ -2522,9 +2549,10 @@ static int unit_tests(int argc, char **argv) #undef T2 #undef T1 }; + struct thread_info test_threads[sizeof(test)/sizeof(test[0])], *res; unsigned long i, ok, fail, nop; uint64_t t; - int j; + int j = -1; ok = fail = nop = 0; t = (uint64_t)time(NULL); @@ -2532,21 +2560,39 @@ static int unit_tests(int argc, char **argv) s_mp_rand_jenkins_init(t); mp_rand_source(s_mp_rand_jenkins); + if (MP_HAS(MULTI_THREADED)) { + printf("Multi-threading enabled\n\n"); + DO(mp_warray_init(sizeof(test) / sizeof(test[0]), 1)); + /* we ignore the fact that jenkings is not thread safe */ + for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { + test_threads[i].t = &test[i]; + EXPECT(pthread_create(&test_threads[i].thread_id, NULL, run, &test_threads[i]) == 0); + } + } for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { - if (argc > 1) { - for (j = 1; j < argc; ++j) { - if (strstr(test[i].name, argv[j]) != NULL) { - break; + if (MP_HAS(SINGLE_THREADED)) { + if (argc > 1) { + for (j = 1; j < argc; ++j) { + if (strstr(test[i].name, argv[j]) != NULL) { + break; + } } + if (j == argc) continue; } - if (j == argc) continue; + + if (test[i].fn) + j = test[i].fn(); + } else if (MP_HAS(MULTI_THREADED)) { + EXPECT(pthread_join(test_threads[i].thread_id, (void **)&res) == 0); + j = res->ret; } printf("TEST %s\n", test[i].name); + if (test[i].fn == NULL) { nop++; printf("NOP %s\n\n", test[i].name); - } else if (test[i].fn() == EXIT_SUCCESS) { + } else if (j == EXIT_SUCCESS) { ok++; printf("\n"); } else { diff --git a/makefile_include.mk b/makefile_include.mk index da897396b..d47ea2ba2 100644 --- a/makefile_include.mk +++ b/makefile_include.mk @@ -97,7 +97,7 @@ endif endif # COMPILE_SIZE ifneq ($(findstring clang,$(CC)),) -LTM_CFLAGS += -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header +LTM_CFLAGS += -Wno-unknown-warning-option -Wno-typedef-redefinition -Wno-tautological-compare -Wno-builtin-requires-header -Wno-incomplete-setjmp-declaration ifdef IGNORE_SPEED #for dead code eliminiation LTM_CFLAGS += -O1 diff --git a/testme.sh b/testme.sh index 089e42a70..92997a041 100755 --- a/testme.sh +++ b/testme.sh @@ -70,6 +70,8 @@ All other options will be tested with all MP_xBIT configurations. runtime and may trigger the 30 minutes timeout. + --multithread Run tests in multi-threaded mode (via pthread). + Godmode: --all Choose all architectures and gcc and clang @@ -128,7 +130,7 @@ _make() echo -ne " Compile $1 $2" suffix=$(echo ${1}${2} | tr ' ' '_') _fixup_cflags "$1" - CC="$1" CFLAGS="$2 $TEST_CFLAGS" make -j$MAKE_JOBS $3 $MAKE_OPTIONS 2>gcc_errors_${suffix}.log + CC="$1" CFLAGS="$2 $TEST_CFLAGS" LFLAGS="$4" LDFLAGS="$5" make -j$MAKE_JOBS $3 $MAKE_OPTIONS 2>gcc_errors_${suffix}.log errcnt=$(wc -l < gcc_errors_${suffix}.log) if [[ ${errcnt} -gt 1 ]]; then echo " failed" @@ -148,10 +150,10 @@ _runtest() # "make tune" will run "tune_it.sh" automatically, hence "autotune", but it cannot # get switched off without some effort, so we just let it run twice for testing purposes echo -e "\rRun autotune $1 $2" - _make "$1" "$2" "" + _make "$1" "$2" "" "$3" "$4" $_timeout $TUNE_CMD > test_${suffix}.log || _die "running autotune" $? else - _make "$1" "$2" "test" + _make "$1" "$2" "test" "$3" "$4" echo -e "\rRun test $1 $2" $_timeout ./test > test_${suffix}.log || _die "running tests" $? fi @@ -171,13 +173,13 @@ echo "MAKE_OPTIONS = \"$MAKE_OPTIONS\"" if [[ "$MAKE_OPTIONS" =~ "tune" ]] then echo "autotune branch" - _make "$1" "$2" "" + _make "$1" "$2" "" "$3" "$4" # The shell used for /bin/sh is DASH 0.5.7-4ubuntu1 on the author's machine which fails valgrind, so # we just run on instance of etc/tune with the same options as in etc/tune_it.sh echo -e "\rRun etc/tune $1 $2 once inside valgrind" $_timeout $VALGRIND_BIN $VALGRIND_OPTS $TUNE_CMD > test_${suffix}.log || _die "running etc/tune" $? else - _make "$1" "$2" "test" + _make "$1" "$2" "test" "$3" "$4" echo -e "\rRun test $1 $2 inside valgrind" $_timeout $VALGRIND_BIN $VALGRIND_OPTS ./test > test_${suffix}.log || _die "running tests" $? fi @@ -301,6 +303,11 @@ do --symbols) CHECK_SYMBOLS="1" ;; + --multithread) + CFLAGS="$CFLAGS -DLTM_TEST_MULTITHREAD" + LFLAGS="$LFLAGS -pthread" + LDFLAGS="$LDFLAGS -pthread" + ;; --all) COMPILERS="gcc clang" ARCHFLAGS="-m64 -m32 -mx32" @@ -376,9 +383,9 @@ then _banner "$CC" if [[ "$VALGRIND_BIN" != "" ]] then - _runvalgrind "$CC" "" + _runvalgrind "$CC" "" "$LFLAGS" "$LDFLAGS" else - _runtest "$CC" "" + _runtest "$CC" "" "$LFLAGS" "$LDFLAGS" fi _exit fi @@ -398,9 +405,9 @@ _banner if [[ "$TEST_VS_MTEST" != "" ]] then make clean > /dev/null - _make "${compilers[0]}" "${archflags[0]} $CFLAGS" "mtest_opponent" + _make "${compilers[0]}" "${archflags[0]} $CFLAGS" "mtest_opponent" "$LFLAGS" "$LDFLAGS" echo - _make "gcc" "$MTEST_RAND" "mtest" + _make "gcc" "$MTEST_RAND" "mtest" "$LFLAGS" "$LDFLAGS" echo echo "Run test vs. mtest for $TEST_VS_MTEST iterations" _timeout="" @@ -429,15 +436,15 @@ do fi if [[ "$VALGRIND_BIN" != "" ]] then - _runvalgrind "$i" "$a $CFLAGS" + _runvalgrind "$i" "$a $CFLAGS" "$LFLAGS" "$LDFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runvalgrind "$i" "$a -DMP_16BIT $CFLAGS" - _runvalgrind "$i" "$a -DMP_32BIT $CFLAGS" + _runvalgrind "$i" "$a -DMP_16BIT $CFLAGS" "$LFLAGS" "$LDFLAGS" + _runvalgrind "$i" "$a -DMP_32BIT $CFLAGS" "$LFLAGS" "$LDFLAGS" else - _runtest "$i" "$a $CFLAGS" + _runtest "$i" "$a $CFLAGS" "$LFLAGS" "$LDFLAGS" [ "$WITH_LOW_MP" != "1" ] && continue - _runtest "$i" "$a -DMP_16BIT $CFLAGS" - _runtest "$i" "$a -DMP_32BIT $CFLAGS" + _runtest "$i" "$a -DMP_16BIT $CFLAGS" "$LFLAGS" "$LDFLAGS" + _runtest "$i" "$a -DMP_32BIT $CFLAGS" "$LFLAGS" "$LDFLAGS" fi done done From fae9aa56457a8cba2f1ca93270ee167d319f7ddc Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 25 Mar 2024 11:57:42 +0100 Subject: [PATCH 285/304] Add tests for MSVC multi-threading ... and fix some MSVC related (and other) things. Signed-off-by: Steffen Jaeckel --- appveyor.yml | 10 +++++- demo/test.c | 86 +++++++++++++++++++++++++++++++++++++++++------ makefile | 6 ++-- makefile.msvc | 2 +- s_mp_cmpexch_n.c | 3 +- s_mp_warray_get.c | 8 +++-- tommath_c89.h | 5 +++ 7 files changed, 101 insertions(+), 19 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index 30d9ee757..5606d9abd 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -18,9 +18,17 @@ build_script: if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 + nmake -f makefile.msvc test.exe CFLAGS="/Ox /Oi /DMP_SMALL_STACK_SIZE" + copy /Y test.exe test_small_stack.exe + nmake -f makefile.msvc clean-obj + nmake -f makefile.msvc test.exe CFLAGS="/Ox /Oi /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD" + copy /Y test.exe test_small_stack_multithreaded.exe + nmake -f makefile.msvc clean-obj nmake -f makefile.msvc test.exe nmake -f makefile.msvc clean-obj - nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /MD /DLTM_TEST_DYNAMIC" + nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /Oi /MD /DLTM_TEST_DYNAMIC" test_script: +- cmd: test_small_stack.exe +- cmd: test_small_stack_multithreaded.exe - cmd: test.exe - cmd: test_dll.exe diff --git a/demo/test.c b/demo/test.c index 306a9c28a..5ab9686c3 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2455,14 +2455,40 @@ static int test_mp_pack_unpack(void) #define ONLY_PUBLIC_API_C #endif -#if !defined(LTM_TEST_MULTITHREAD) || !defined(MP_SMALL_STACK_SIZE) +#if !defined(LTM_TEST_MULTITHREAD) #define SINGLE_THREADED_C -typedef unsigned long int pthread_t; -extern int pthread_create(pthread_t *, const void *, void *(*)(void *), void *); -extern int pthread_join(pthread_t, void **); +typedef uintptr_t thread_id_t; #else #define MULTI_THREADED_C +#if !defined(_WIN32) +#define MULTI_THREADED_PTHREAD_C #include +typedef pthread_t thread_id_t; +#else +#define MULTI_THREADED_MSVC_C + +#ifndef _WIN32_WINNT +#define _WIN32_WINNT 0x0501 +#endif +#ifndef WINVER +#define WINVER 0x0501 +#endif + +#define WIN32_LEAN_AND_MEAN +#include +typedef HANDLE thread_id_t; +#endif +#endif + +#if !defined(MULTI_THREADED_PTHREAD_C) +extern int pthread_create(thread_id_t *, const void *, void *(*)(void *), void *); +extern int pthread_join(thread_id_t, void **); +#endif + +#if !defined(MULTI_THREADED_MSVC_C) +extern thread_id_t CreateThread(void *, size_t, unsigned long (*)(void *), void *, unsigned long, void *); +extern unsigned long WaitForSingleObject(thread_id_t hHandle, unsigned long dwMilliseconds); +#define INFINITE ((unsigned long)-1) #endif struct test_fn { @@ -2471,12 +2497,12 @@ struct test_fn { }; struct thread_info { - pthread_t thread_id; + thread_id_t thread_id; const struct test_fn *t; int ret; }; -static void *run(void *arg) +static void *run_pthread(void *arg) { struct thread_info *tinfo = arg; @@ -2485,6 +2511,38 @@ static void *run(void *arg) return arg; } +static unsigned long run_msvc(void *arg) +{ + struct thread_info *tinfo = arg; + + tinfo->ret = tinfo->t->fn(); + + return 0; +} + +static int thread_start(struct thread_info *info) +{ + if (MP_HAS(MULTI_THREADED_PTHREAD)) + return pthread_create(&info->thread_id, NULL, run_pthread, info); + if (MP_HAS(MULTI_THREADED_MSVC)) { + info->thread_id = CreateThread(NULL, 0, run_msvc, info, 0, NULL); + return info->thread_id == (thread_id_t)NULL ? -1 : 0; + } + return -1; +} + +static int thread_join(struct thread_info *info, struct thread_info **res) +{ + if (MP_HAS(MULTI_THREADED_PTHREAD)) + return pthread_join(info->thread_id, (void **)res); + if (MP_HAS(MULTI_THREADED_MSVC)) { + WaitForSingleObject(info->thread_id, INFINITE); + *res = info; + return 0; + } + return -1; +} + static int unit_tests(int argc, char **argv) { static const struct test_fn test[] = { @@ -2551,8 +2609,9 @@ static int unit_tests(int argc, char **argv) }; struct thread_info test_threads[sizeof(test)/sizeof(test[0])], *res; unsigned long i, ok, fail, nop; + size_t n_threads = MP_HAS(MULTI_THREADED) ? sizeof(test) / sizeof(test[0]) : 1; uint64_t t; - int j = -1; + int j; ok = fail = nop = 0; t = (uint64_t)time(NULL); @@ -2560,17 +2619,22 @@ static int unit_tests(int argc, char **argv) s_mp_rand_jenkins_init(t); mp_rand_source(s_mp_rand_jenkins); + if (MP_HAS(MP_SMALL_STACK_SIZE)) { + printf("Small-stack enabled with %zu warray buffers\n\n", n_threads); + DO(mp_warray_init(n_threads, 1)); + } + if (MP_HAS(MULTI_THREADED)) { printf("Multi-threading enabled\n\n"); - DO(mp_warray_init(sizeof(test) / sizeof(test[0]), 1)); - /* we ignore the fact that jenkings is not thread safe */ + /* we ignore the fact that jenkins is not thread safe */ for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { test_threads[i].t = &test[i]; - EXPECT(pthread_create(&test_threads[i].thread_id, NULL, run, &test_threads[i]) == 0); + EXPECT(thread_start(&test_threads[i]) == 0); } } for (i = 0; i < (sizeof(test) / sizeof(test[0])); ++i) { + j = -1; if (MP_HAS(SINGLE_THREADED)) { if (argc > 1) { for (j = 1; j < argc; ++j) { @@ -2584,7 +2648,7 @@ static int unit_tests(int argc, char **argv) if (test[i].fn) j = test[i].fn(); } else if (MP_HAS(MULTI_THREADED)) { - EXPECT(pthread_join(test_threads[i].thread_id, (void **)&res) == 0); + EXPECT(thread_join(&test_threads[i], &res) == 0); j = res->ret; } printf("TEST %s\n", test[i].name); diff --git a/makefile b/makefile index ec32ecd09..437e3d4e9 100644 --- a/makefile +++ b/makefile @@ -172,9 +172,10 @@ c89: -e 's/UINT32_MAX/0xFFFFFFFFu/g' \ -e 's/UINT64_MAX/(mp_u64)-1/g' \ -e 's/INT32_MAX/0x7FFFFFFF/g' \ - -e 's/INT32_MIN/(-2147483647-1)/g' \ + -e 's/INT32_MIN/(-2147483647-1)/g' \ -e 's/INT64_MAX/(mp_i64)(((mp_u64)1<<63)-1)/g' \ -e 's/INT64_MIN/(mp_i64)((mp_u64)1<<63)/g' \ + -e 's/uintptr_t/mp_uintptr/g' \ -e 's/SIZE_MAX/((size_t)-1)/g' \ -e 's/\(PRI[ioux]64\)/MP_\1/g' \ -e 's/uint\([0-9][0-9]*\)_t/mp_u\1/g' \ @@ -195,10 +196,11 @@ c99: -e 's/false_/MP_NO_/g' \ -e 's/0xFFFFFFFFu/UINT32_MAX/g' \ -e 's/(mp_u64)-1/UINT64_MAX/g' \ - -e 's/(-2147483647-1)/INT32_MIN/g' \ + -e 's/(-2147483647-1)/INT32_MIN/g' \ -e 's/0x7FFFFFFF/INT32_MAX/g' \ -e 's/(mp_i64)((mp_u64)1<<63)/INT64_MIN/g' \ -e 's/(mp_i64)(((mp_u64)1<<63)-1)/INT64_MAX/g' \ + -e 's/mp_uintptr/uintptr_t/g' \ -e 's/((size_t)-1)/SIZE_MAX/g' \ -e 's/MP_\(PRI[ioux]64\)/\1/g' \ -e 's/mp_u\([0-9][0-9]*\)/uint\1_t/g' \ diff --git a/makefile.msvc b/makefile.msvc index 5d1285490..da5e2fd62 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -11,7 +11,7 @@ #The following can be overridden from command line e.g. make -f makefile.msvc CC=gcc ARFLAGS=rcs PREFIX = c:\devel -CFLAGS = /Ox +CFLAGS = /Ox /Oi LDFLAGS = #Compilation flags diff --git a/s_mp_cmpexch_n.c b/s_mp_cmpexch_n.c index 6334d9d4b..e8ef969c2 100644 --- a/s_mp_cmpexch_n.c +++ b/s_mp_cmpexch_n.c @@ -26,8 +26,7 @@ static bool s_cmpexch_n_gcc(void **ptr, void **expected, void *desired) static bool s_cmpexch_n_msvc(void **ptr, void **expected, void *desired) { - InterlockedCompareExchangePointer(ptr, desired, *(expected)); - return *ptr == desired; + return InterlockedCompareExchangePointer(ptr, desired, *(expected)); } #endif diff --git a/s_mp_warray_get.c b/s_mp_warray_get.c index 068e8145d..39176eb2c 100644 --- a/s_mp_warray_get.c +++ b/s_mp_warray_get.c @@ -11,14 +11,18 @@ void *s_mp_warray_get(void) if (mp_warray_init(1, false) != MP_OKAY) return NULL; } - for (n = 0; n < s_mp_warray.allocated; ++n) { - if (s_mp_warray.l_free[n].warray == NULL) + for (n = 0; n < s_mp_warray.allocated;) { + if (s_mp_warray.l_free[n].warray == NULL) { + n++; continue; + } ret = s_mp_warray.l_free[n].warray; if (s_mp_cmpexch_n(&s_mp_warray.l_free[n].warray, &ret, NULL)) { s_mp_warray.l_used[n].warray = ret; goto LBL_OUT; } + /* restart from the beginning if we missed a potential slot */ + n = 0; } ret = NULL; if (s_mp_warray.allocated + 1 > s_mp_warray.usable) diff --git a/tommath_c89.h b/tommath_c89.h index 49400a131..22436366b 100644 --- a/tommath_c89.h +++ b/tommath_c89.h @@ -26,6 +26,11 @@ typedef __UINT8_TYPE__ mp_u8; typedef __UINT16_TYPE__ mp_u16; typedef __UINT32_TYPE__ mp_u32; typedef __UINT64_TYPE__ mp_u64; +# if __WORDSIZE == 64 +typedef __UINT64_TYPE__ mp_uintptr; +# else +typedef __UINT32_TYPE__ mp_uintptr; +# endif /* inttypes.h replacement, printf format specifier */ # if __WORDSIZE == 64 From 334465dd1773832d224175fdb252c741e479d32e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 27 Mar 2024 14:49:09 +0100 Subject: [PATCH 286/304] Update makefiles Signed-off-by: Steffen Jaeckel --- libtommath_VS2008.vcproj | 28 ++++++++++++++++++++++++++++ makefile | 15 ++++++++------- makefile.mingw | 15 ++++++++------- makefile.msvc | 15 ++++++++------- makefile.shared | 15 ++++++++------- makefile.unix | 15 ++++++++------- sources.cmake | 7 +++++++ 7 files changed, 75 insertions(+), 35 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 13158a09d..816217e8d 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -792,6 +792,14 @@ RelativePath="mp_unpack.c" > + + + + @@ -804,6 +812,10 @@ RelativePath="s_mp_add.c" > + + @@ -928,6 +940,22 @@ RelativePath="s_mp_sub.c" > + + + + + + + + diff --git a/makefile b/makefile index 437e3d4e9..a1729d7f0 100644 --- a/makefile +++ b/makefile @@ -43,13 +43,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ +s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ +s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 532747be0..7597ba6df 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -45,13 +45,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ +s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ +s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index da5e2fd62..e6e8db7fe 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -41,13 +41,14 @@ mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_ mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ mp_set_l.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj \ mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ -mp_unpack.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj \ -s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_fp_log.obj s_mp_fp_log_d.obj \ -s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj \ -s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj \ -s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj s_mp_radix_map.obj \ -s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj \ -s_mp_sqr_toom.obj s_mp_sub.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +mp_unpack.obj mp_warray_free.obj mp_warray_init.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_cmpexch_n.obj \ +s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj \ +s_mp_exptmod_fast.obj s_mp_fp_log.obj s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj \ +s_mp_log_2expt.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj \ +s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj \ +s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj \ +s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_warray.obj s_mp_warray_free.obj \ +s_mp_warray_get.obj s_mp_warray_put.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index c9b933513..315252f35 100644 --- a/makefile.shared +++ b/makefile.shared @@ -40,13 +40,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ +s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ +s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 34ebd1a86..c74ec5d7b 100644 --- a/makefile.unix +++ b/makefile.unix @@ -46,13 +46,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o \ -s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o \ -s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o \ -s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o \ -s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o s_mp_radix_map.o \ -s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o s_mp_sqr_karatsuba.o \ -s_mp_sqr_toom.o s_mp_sub.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ +s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ +s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ +s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ +s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ +s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ +s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/sources.cmake b/sources.cmake index bbb2aeab6..a23dbd451 100644 --- a/sources.cmake +++ b/sources.cmake @@ -122,9 +122,12 @@ mp_to_sbin.c mp_to_ubin.c mp_ubin_size.c mp_unpack.c +mp_warray_free.c +mp_warray_init.c mp_xor.c mp_zero.c s_mp_add.c +s_mp_cmpexch_n.c s_mp_copy_digs.c s_mp_div_3.c s_mp_div_recursive.c @@ -156,6 +159,10 @@ s_mp_sqr_comba.c s_mp_sqr_karatsuba.c s_mp_sqr_toom.c s_mp_sub.c +s_mp_warray.c +s_mp_warray_free.c +s_mp_warray_get.c +s_mp_warray_put.c s_mp_zero_buf.c s_mp_zero_digs.c ) From 33a9d0d5959abda6cca4fcc0fa9cd71aa653088d Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 29 Mar 2024 10:50:28 +0100 Subject: [PATCH 287/304] Use Thread Local Storage for `warray` buffer Signed-off-by: Steffen Jaeckel --- demo/test.c | 20 +++++++++++--------- mp_warray_free.c | 18 ++++++------------ mp_warray_init.c | 46 ---------------------------------------------- s_mp_cmpexch_n.c | 43 ------------------------------------------- s_mp_warray.c | 2 +- s_mp_warray_free.c | 17 ----------------- s_mp_warray_get.c | 34 +++++++--------------------------- s_mp_warray_put.c | 12 ++++-------- tommath.h | 1 - tommath_private.h | 17 ++++++++--------- 10 files changed, 37 insertions(+), 173 deletions(-) delete mode 100644 mp_warray_init.c delete mode 100644 s_mp_cmpexch_n.c delete mode 100644 s_mp_warray_free.c diff --git a/demo/test.c b/demo/test.c index 5ab9686c3..2fa6e08db 100644 --- a/demo/test.c +++ b/demo/test.c @@ -2502,20 +2502,24 @@ struct thread_info { int ret; }; -static void *run_pthread(void *arg) +static void run(struct thread_info *tinfo) { - struct thread_info *tinfo = arg; - tinfo->ret = tinfo->t->fn(); + if (mp_warray_free() == -2) + tinfo->ret = EXIT_FAILURE; +} + +static void *run_pthread(void *arg) +{ + run(arg); + return arg; } static unsigned long run_msvc(void *arg) { - struct thread_info *tinfo = arg; - - tinfo->ret = tinfo->t->fn(); + run(arg); return 0; } @@ -2609,7 +2613,6 @@ static int unit_tests(int argc, char **argv) }; struct thread_info test_threads[sizeof(test)/sizeof(test[0])], *res; unsigned long i, ok, fail, nop; - size_t n_threads = MP_HAS(MULTI_THREADED) ? sizeof(test) / sizeof(test[0]) : 1; uint64_t t; int j; ok = fail = nop = 0; @@ -2620,8 +2623,7 @@ static int unit_tests(int argc, char **argv) mp_rand_source(s_mp_rand_jenkins); if (MP_HAS(MP_SMALL_STACK_SIZE)) { - printf("Small-stack enabled with %zu warray buffers\n\n", n_threads); - DO(mp_warray_init(n_threads, 1)); + printf("Small-stack enabled\n\n"); } if (MP_HAS(MULTI_THREADED)) { diff --git a/mp_warray_free.c b/mp_warray_free.c index 088efefc4..f7470f818 100644 --- a/mp_warray_free.c +++ b/mp_warray_free.c @@ -9,19 +9,13 @@ MP_STATIC_ASSERT(warray_free_sz_does_not_overflow, (sizeof(mp_word) * MP_WARRAY) static int s_warray_free(void) { int ret = 0; - size_t n; - for (n = 0; n < s_mp_warray.allocated; ++n) { - if (s_mp_warray.l_used[n].warray) { - ret = -2; - goto ERR_OUT; - } + if (s_mp_warray.w_used) + return -2; + if (s_mp_warray.w_free) { + s_mp_zero_buf(s_mp_warray.w_free, sizeof(mp_word) * MP_WARRAY); + MP_FREE(s_mp_warray.w_free, sizeof(mp_word) * MP_WARRAY); + s_mp_warray.w_free = NULL; } - for (n = 0; n < s_mp_warray.allocated; ++n) { - MP_FREE(s_mp_warray.l_free[n].warray, sizeof(mp_word) * MP_WARRAY); - s_mp_warray.l_free[n].warray = NULL; - } - s_mp_warray_free(s_mp_warray.usable); -ERR_OUT: return ret; } diff --git a/mp_warray_init.c b/mp_warray_init.c deleted file mode 100644 index c25098861..000000000 --- a/mp_warray_init.c +++ /dev/null @@ -1,46 +0,0 @@ -#include "tommath_private.h" -#ifdef MP_WARRAY_INIT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -static mp_err s_warray_init(size_t n_alloc, bool preallocate) -{ - size_t n; - if (s_mp_warray.l_free != NULL || s_mp_warray.l_used != NULL) { - return MP_VAL; - } - - s_mp_warray.l_free = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_free))); - s_mp_warray.l_used = MP_CALLOC(n_alloc, sizeof(*(s_mp_warray.l_used))); - if (s_mp_warray.l_free == NULL || s_mp_warray.l_used == NULL) { - s_mp_warray_free(n_alloc); - return MP_MEM; - } - - if (preallocate) { - for (n = 0; n < n_alloc; ++n) { - s_mp_warray.l_free[n].warray = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); - if (s_mp_warray.l_free[n].warray == NULL) { - while (n > 0) { - n--; - MP_FREE(s_mp_warray.l_free[n].warray, MP_WARRAY * sizeof(mp_word)); - s_mp_warray.l_free[n].warray = NULL; - } - s_mp_warray_free(n_alloc); - return MP_MEM; - } - } - s_mp_warray.allocated = n_alloc; - } - - s_mp_warray.usable = n_alloc; - return MP_OKAY; -} - -mp_err mp_warray_init(size_t n_alloc, bool preallocate) -{ - if (MP_HAS(MP_SMALL_STACK_SIZE)) return s_warray_init(n_alloc, preallocate); - return MP_ERR; -} - -#endif diff --git a/s_mp_cmpexch_n.c b/s_mp_cmpexch_n.c deleted file mode 100644 index e8ef969c2..000000000 --- a/s_mp_cmpexch_n.c +++ /dev/null @@ -1,43 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_CMPEXCH_N_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -#ifdef __GNUC__ -#define S_CMPEXCH_N_GCC_C -static bool s_cmpexch_n_gcc(void **ptr, void **expected, void *desired) -{ - return __atomic_compare_exchange_n(ptr, expected, desired, true, __ATOMIC_ACQ_REL, __ATOMIC_ACQUIRE); -} -#endif - -#ifdef _MSC_VER -#define S_CMPEXCH_N_MSVC_C - -#ifndef _WIN32_WINNT -#define _WIN32_WINNT 0x0501 -#endif -#ifndef WINVER -#define WINVER 0x0501 -#endif - -#define WIN32_LEAN_AND_MEAN -#include - -static bool s_cmpexch_n_msvc(void **ptr, void **expected, void *desired) -{ - return InterlockedCompareExchangePointer(ptr, desired, *(expected)); -} -#endif - -bool s_cmpexch_n_gcc(void **ptr, void **expected, void *desired); -bool s_cmpexch_n_msvc(void **ptr, void **expected, void *desired); - -bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired) -{ - if (MP_HAS(S_CMPEXCH_N_GCC)) return s_cmpexch_n_gcc(ptr, expected, desired); - if (MP_HAS(S_CMPEXCH_N_MSVC)) return s_cmpexch_n_msvc(ptr, expected, desired); - return false; -} - -#endif diff --git a/s_mp_warray.c b/s_mp_warray.c index d181057cb..1b8b068b7 100644 --- a/s_mp_warray.c +++ b/s_mp_warray.c @@ -3,6 +3,6 @@ /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ -st_warray s_mp_warray; +mp_thread st_warray s_mp_warray = { 0 }; #endif diff --git a/s_mp_warray_free.c b/s_mp_warray_free.c deleted file mode 100644 index 9d8b75eb1..000000000 --- a/s_mp_warray_free.c +++ /dev/null @@ -1,17 +0,0 @@ -#include "tommath_private.h" -#ifdef S_MP_WARRAY_FREE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis */ -/* SPDX-License-Identifier: Unlicense */ - -void s_mp_warray_free(size_t n) -{ - (void)n; - MP_FREE(s_mp_warray.l_free, n * sizeof(*(s_mp_warray.l_free))); - MP_FREE(s_mp_warray.l_used, n * sizeof(*(s_mp_warray.l_used))); - s_mp_warray.l_free = NULL; - s_mp_warray.l_used = NULL; - s_mp_warray.allocated = 0; - s_mp_warray.usable = 0; -} - -#endif diff --git a/s_mp_warray_get.c b/s_mp_warray_get.c index 39176eb2c..26b0d7c10 100644 --- a/s_mp_warray_get.c +++ b/s_mp_warray_get.c @@ -5,34 +5,14 @@ void *s_mp_warray_get(void) { - void *ret = NULL; - size_t n; - if (s_mp_warray.usable == 0) { - if (mp_warray_init(1, false) != MP_OKAY) - return NULL; + if (s_mp_warray.w_used) + return NULL; + if (s_mp_warray.w_free == NULL) { + s_mp_warray.w_free = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); } - for (n = 0; n < s_mp_warray.allocated;) { - if (s_mp_warray.l_free[n].warray == NULL) { - n++; - continue; - } - ret = s_mp_warray.l_free[n].warray; - if (s_mp_cmpexch_n(&s_mp_warray.l_free[n].warray, &ret, NULL)) { - s_mp_warray.l_used[n].warray = ret; - goto LBL_OUT; - } - /* restart from the beginning if we missed a potential slot */ - n = 0; - } - ret = NULL; - if (s_mp_warray.allocated + 1 > s_mp_warray.usable) - goto LBL_OUT; - ret = MP_CALLOC(MP_WARRAY, sizeof(mp_word)); - if (ret != NULL) - s_mp_warray.l_used[s_mp_warray.allocated++].warray = ret; - -LBL_OUT: - return ret; + s_mp_warray.w_used = s_mp_warray.w_free; + s_mp_warray.w_free = NULL; + return s_mp_warray.w_used; } #endif diff --git a/s_mp_warray_put.c b/s_mp_warray_put.c index 4cf413d62..79e014acd 100644 --- a/s_mp_warray_put.c +++ b/s_mp_warray_put.c @@ -5,14 +5,10 @@ void s_mp_warray_put(void *w) { - size_t n, allocated = s_mp_warray.allocated; - for (n = 0; n < allocated; ++n) { - if (s_mp_warray.l_used[n].warray == w) { - s_mp_warray.l_used[n].warray = NULL; - s_mp_warray.l_free[n].warray = w; - break; - } - } + if (s_mp_warray.w_free || s_mp_warray.w_used != w) + return; + s_mp_warray.w_free = w; + s_mp_warray.w_used = NULL; } #endif diff --git a/tommath.h b/tommath.h index 7da36d0e9..1820d2436 100644 --- a/tommath.h +++ b/tommath.h @@ -588,7 +588,6 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR; mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) MP_WUR; #endif -mp_err mp_warray_init(size_t n_alloc, bool preallocate); int mp_warray_free(void); #define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), NULL, 2) diff --git a/tommath_private.h b/tommath_private.h index 36291a061..9c25f330f 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -234,8 +234,6 @@ MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix, MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; -MP_PRIVATE bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired); - #ifdef MP_SMALL_STACK_SIZE #define MP_SMALL_STACK_SIZE_C #define MP_ALLOC_WARRAY(name) *name = s_mp_warray_get() @@ -247,19 +245,20 @@ MP_PRIVATE bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired); #define MP_CHECK_WARRAY(name) #endif -struct warray { - void *warray; -}; +#if defined(_MSC_VER) +#define mp_thread __declspec(thread) +#elif defined(__GNUC__) +#define mp_thread __thread +#endif + typedef struct { - struct warray *l_free, *l_used; - size_t allocated, usable; + void *w_free, *w_used; } st_warray; -extern MP_PRIVATE st_warray s_mp_warray; +extern MP_PRIVATE mp_thread st_warray s_mp_warray; MP_PRIVATE void *s_mp_warray_get(void); MP_PRIVATE void s_mp_warray_put(void *w); -MP_PRIVATE void s_mp_warray_free(size_t n); #define MP_RADIX_MAP_REVERSE_SIZE 80u extern MP_PRIVATE const char s_mp_radix_map[]; From 513d48d404c77f6886297828e33c4002541aac10 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 29 Mar 2024 10:50:45 +0100 Subject: [PATCH 288/304] regen Signed-off-by: Steffen Jaeckel --- libtommath_VS2008.vcproj | 12 ------------ makefile | 16 ++++++++-------- makefile.mingw | 16 ++++++++-------- makefile.msvc | 16 ++++++++-------- makefile.shared | 16 ++++++++-------- makefile.unix | 16 ++++++++-------- sources.cmake | 3 --- tommath.def | 1 - tommath_class.h | 17 +---------------- 9 files changed, 41 insertions(+), 72 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 816217e8d..71dd3807f 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -796,10 +796,6 @@ RelativePath="mp_warray_free.c" > - - @@ -812,10 +808,6 @@ RelativePath="s_mp_add.c" > - - @@ -944,10 +936,6 @@ RelativePath="s_mp_warray.c" > - - diff --git a/makefile b/makefile index a1729d7f0..8f211f5f2 100644 --- a/makefile +++ b/makefile @@ -43,14 +43,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ -s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ -s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ -s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o \ +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ +s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index 7597ba6df..e2445e8a0 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -45,14 +45,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ -s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ -s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ -s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o \ +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ +s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index e6e8db7fe..8540ca33d 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -41,14 +41,14 @@ mp_reduce_2k_l.obj mp_reduce_2k_setup.obj mp_reduce_2k_setup_l.obj mp_reduce_is_ mp_reduce_setup.obj mp_root_n.obj mp_rshd.obj mp_sbin_size.obj mp_set.obj mp_set_double.obj mp_set_i32.obj mp_set_i64.obj \ mp_set_l.obj mp_set_u32.obj mp_set_u64.obj mp_set_ul.obj mp_shrink.obj mp_signed_rsh.obj mp_sqrmod.obj mp_sqrt.obj \ mp_sqrtmod_prime.obj mp_sub.obj mp_sub_d.obj mp_submod.obj mp_to_radix.obj mp_to_sbin.obj mp_to_ubin.obj mp_ubin_size.obj \ -mp_unpack.obj mp_warray_free.obj mp_warray_init.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_cmpexch_n.obj \ -s_mp_copy_digs.obj s_mp_div_3.obj s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj \ -s_mp_exptmod_fast.obj s_mp_fp_log.obj s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj \ -s_mp_log_2expt.obj s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj \ -s_mp_mul_high.obj s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj \ -s_mp_prime_tab.obj s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj \ -s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_warray.obj s_mp_warray_free.obj \ -s_mp_warray_get.obj s_mp_warray_put.obj s_mp_zero_buf.obj s_mp_zero_digs.obj +mp_unpack.obj mp_warray_free.obj mp_xor.obj mp_zero.obj s_mp_add.obj s_mp_copy_digs.obj s_mp_div_3.obj \ +s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s_mp_exptmod_fast.obj s_mp_fp_log.obj \ +s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj \ +s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj \ +s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj \ +s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ +s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_warray.obj s_mp_warray_get.obj s_mp_warray_put.obj \ +s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 315252f35..50c335269 100644 --- a/makefile.shared +++ b/makefile.shared @@ -40,14 +40,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ -s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ -s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ -s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o \ +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ +s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index c74ec5d7b..58642098d 100644 --- a/makefile.unix +++ b/makefile.unix @@ -46,14 +46,14 @@ mp_reduce_2k_l.o mp_reduce_2k_setup.o mp_reduce_2k_setup_l.o mp_reduce_is_2k.o m mp_reduce_setup.o mp_root_n.o mp_rshd.o mp_sbin_size.o mp_set.o mp_set_double.o mp_set_i32.o mp_set_i64.o \ mp_set_l.o mp_set_u32.o mp_set_u64.o mp_set_ul.o mp_shrink.o mp_signed_rsh.o mp_sqrmod.o mp_sqrt.o \ mp_sqrtmod_prime.o mp_sub.o mp_sub_d.o mp_submod.o mp_to_radix.o mp_to_sbin.o mp_to_ubin.o mp_ubin_size.o \ -mp_unpack.o mp_warray_free.o mp_warray_init.o mp_xor.o mp_zero.o s_mp_add.o s_mp_cmpexch_n.o \ -s_mp_copy_digs.o s_mp_div_3.o s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o \ -s_mp_exptmod_fast.o s_mp_fp_log.o s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o \ -s_mp_log_2expt.o s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o \ -s_mp_mul_high.o s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o \ -s_mp_prime_tab.o s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o \ -s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_free.o \ -s_mp_warray_get.o s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o +mp_unpack.o mp_warray_free.o mp_xor.o mp_zero.o s_mp_add.o s_mp_copy_digs.o s_mp_div_3.o \ +s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_exptmod_fast.o s_mp_fp_log.o \ +s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ +s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ +s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ +s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ +s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/sources.cmake b/sources.cmake index a23dbd451..103e9c099 100644 --- a/sources.cmake +++ b/sources.cmake @@ -123,11 +123,9 @@ mp_to_ubin.c mp_ubin_size.c mp_unpack.c mp_warray_free.c -mp_warray_init.c mp_xor.c mp_zero.c s_mp_add.c -s_mp_cmpexch_n.c s_mp_copy_digs.c s_mp_div_3.c s_mp_div_recursive.c @@ -160,7 +158,6 @@ s_mp_sqr_karatsuba.c s_mp_sqr_toom.c s_mp_sub.c s_mp_warray.c -s_mp_warray_free.c s_mp_warray_get.c s_mp_warray_put.c s_mp_zero_buf.c diff --git a/tommath.def b/tommath.def index 7aa5860f7..ed5aa8b0c 100644 --- a/tommath.def +++ b/tommath.def @@ -126,7 +126,6 @@ EXPORTS mp_ubin_size mp_unpack mp_warray_free - mp_warray_init mp_xor mp_zero MP_MUL_KARATSUBA_CUTOFF diff --git a/tommath_class.h b/tommath_class.h index bb89cc237..09bb3ea63 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -132,11 +132,9 @@ # define MP_UBIN_SIZE_C # define MP_UNPACK_C # define MP_WARRAY_FREE_C -# define MP_WARRAY_INIT_C # define MP_XOR_C # define MP_ZERO_C # define S_MP_ADD_C -# define S_MP_CMPEXCH_N_C # define S_MP_COPY_DIGS_C # define S_MP_DIV_3_C # define S_MP_DIV_RECURSIVE_C @@ -169,7 +167,6 @@ # define S_MP_SQR_TOOM_C # define S_MP_SUB_C # define S_MP_WARRAY_C -# define S_MP_WARRAY_FREE_C # define S_MP_WARRAY_GET_C # define S_MP_WARRAY_PUT_C # define S_MP_ZERO_BUF_C @@ -965,11 +962,7 @@ #endif #if defined(MP_WARRAY_FREE_C) -# define S_MP_WARRAY_FREE_C -#endif - -#if defined(MP_WARRAY_INIT_C) -# define S_MP_WARRAY_FREE_C +# define S_MP_ZERO_BUF_C #endif #if defined(MP_XOR_C) @@ -987,9 +980,6 @@ # define S_MP_ZERO_DIGS_C #endif -#if defined(S_MP_CMPEXCH_N_C) -#endif - #if defined(S_MP_COPY_DIGS_C) #endif @@ -1308,12 +1298,7 @@ #if defined(S_MP_WARRAY_C) #endif -#if defined(S_MP_WARRAY_FREE_C) -#endif - #if defined(S_MP_WARRAY_GET_C) -# define MP_WARRAY_INIT_C -# define S_MP_CMPEXCH_N_C #endif #if defined(S_MP_WARRAY_PUT_C) From 4c2e17793856bb3f5280a379079144b3f3fc2af5 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 29 Mar 2024 11:10:19 +0100 Subject: [PATCH 289/304] Use appveyor build matrix Signed-off-by: Steffen Jaeckel --- appveyor.yml | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index 5606d9abd..b2e2d3907 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -11,6 +11,16 @@ image: - Visual Studio 2019 - Visual Studio 2017 - Visual Studio 2015 +environment: + matrix: + - CFLAGS_VAR: "" + CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC\"" + + - CFLAGS_VAR: "CFLAGS=\"/Ox /Oi /DMP_SMALL_STACK_SIZE\"" + CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC /DMP_SMALL_STACK_SIZE\"" + + - CFLAGS_VAR: "CFLAGS=\"/Ox /Oi /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD\"" + CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD\"" build_script: - cmd: >- if "Visual Studio 2022"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Auxiliary\Build\vcvars64.bat" @@ -18,17 +28,9 @@ build_script: if "Visual Studio 2017"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvars64.bat" if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 if "Visual Studio 2015"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" x86_amd64 - nmake -f makefile.msvc test.exe CFLAGS="/Ox /Oi /DMP_SMALL_STACK_SIZE" - copy /Y test.exe test_small_stack.exe + nmake -f makefile.msvc test.exe %CFLAGS_VAR% nmake -f makefile.msvc clean-obj - nmake -f makefile.msvc test.exe CFLAGS="/Ox /Oi /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD" - copy /Y test.exe test_small_stack_multithreaded.exe - nmake -f makefile.msvc clean-obj - nmake -f makefile.msvc test.exe - nmake -f makefile.msvc clean-obj - nmake -f makefile.msvc test_dll.exe CFLAGS="/Ox /Oi /MD /DLTM_TEST_DYNAMIC" + nmake -f makefile.msvc test_dll.exe %CFLAGS_VAR_DLL% test_script: -- cmd: test_small_stack.exe -- cmd: test_small_stack_multithreaded.exe - cmd: test.exe - cmd: test_dll.exe From 6c70ef1cec6fe26f4e9d316f72b0b2134268634b Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Fri, 29 Mar 2024 12:15:32 +0100 Subject: [PATCH 290/304] Run small-stack tests with valgrind Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index fd8e34cf5..18a832bbe 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -72,9 +72,9 @@ jobs: # Build with small stack-size - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 libc6-dev-i386 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' From 3570e12884d54e1503fda03569517530c01f5ddd Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Wed, 3 Apr 2024 15:48:23 +0200 Subject: [PATCH 291/304] Disable MP_SMALL_STACK_SIZE on MSVC Signed-off-by: Steffen Jaeckel --- appveyor.yml | 8 +------- makefile.msvc | 2 +- tommath_private.h | 23 +++++++++++++++++++---- 3 files changed, 21 insertions(+), 12 deletions(-) diff --git a/appveyor.yml b/appveyor.yml index b2e2d3907..2134f2ddf 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -14,13 +14,7 @@ image: environment: matrix: - CFLAGS_VAR: "" - CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC\"" - - - CFLAGS_VAR: "CFLAGS=\"/Ox /Oi /DMP_SMALL_STACK_SIZE\"" - CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC /DMP_SMALL_STACK_SIZE\"" - - - CFLAGS_VAR: "CFLAGS=\"/Ox /Oi /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD\"" - CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /Oi /MD /DLTM_TEST_DYNAMIC /DMP_SMALL_STACK_SIZE /DLTM_TEST_MULTITHREAD\"" + CFLAGS_VAR_DLL: "CFLAGS=\"/Ox /MD /DLTM_TEST_DYNAMIC\"" build_script: - cmd: >- if "Visual Studio 2022"=="%APPVEYOR_BUILD_WORKER_IMAGE%" call "C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Auxiliary\Build\vcvars64.bat" diff --git a/makefile.msvc b/makefile.msvc index 8540ca33d..8feb425c4 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -11,7 +11,7 @@ #The following can be overridden from command line e.g. make -f makefile.msvc CC=gcc ARFLAGS=rcs PREFIX = c:\devel -CFLAGS = /Ox /Oi +CFLAGS = /Ox LDFLAGS = #Compilation flags diff --git a/tommath_private.h b/tommath_private.h index 9c25f330f..be620dbc9 100644 --- a/tommath_private.h +++ b/tommath_private.h @@ -235,6 +235,23 @@ MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR; MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; #ifdef MP_SMALL_STACK_SIZE + +#if defined(__GNUC__) +/* We use TLS (Thread Local Storage) to manage the instance of the WARRAY + * per thread. + * The compilers we're usually looking at are GCC, Clang and MSVC. + * Both GCC and Clang are straight-forward with TLS, so it's enabled there. + * Using MSVC the tests were OK with the static library, but failed when + * the library was built as a DLL. As a result we completely disable + * support for MSVC. + * If your compiler can handle TLS properly without too much hocus pocus, + * feel free to open a PR to add support for it. + */ +#define mp_thread __thread +#else +#error "MP_SMALL_STACK_SIZE not supported with your compiler" +#endif + #define MP_SMALL_STACK_SIZE_C #define MP_ALLOC_WARRAY(name) *name = s_mp_warray_get() #define MP_FREE_WARRAY(name) s_mp_warray_put(name) @@ -245,10 +262,8 @@ MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR; #define MP_CHECK_WARRAY(name) #endif -#if defined(_MSC_VER) -#define mp_thread __declspec(thread) -#elif defined(__GNUC__) -#define mp_thread __thread +#ifndef mp_thread +#define mp_thread #endif typedef struct { From a2fe83f8052929a63c4300c8e16350bb84da6426 Mon Sep 17 00:00:00 2001 From: Daniel Engberg Date: Fri, 5 Apr 2024 18:57:30 +0200 Subject: [PATCH 292/304] cmake: Remove unnecessary ccache logic Rely on CMAKE_C_COMPILER_LAUNCHER instead of homegrown logic See CMake's documentation for more information https://cmake.org/cmake/help/latest/variable/CMAKE_LANG_COMPILER_LAUNCHER.html --- CMakeLists.txt | 14 -------------- 1 file changed, 14 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 2f59d32e8..014fb1883 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -33,20 +33,6 @@ include(sources.cmake) #----------------------------------------------------------------------------- option(BUILD_SHARED_LIBS "Build shared library and only the shared library if \"ON\", default is static" OFF) -#----------------------------------------------------------------------------- -# Add support for ccache if desired -#----------------------------------------------------------------------------- -find_program(CCACHE ccache) - -if(CCACHE) - option(ENABLE_CCACHE "Enable ccache." ON) -endif() - -# use ccache if installed -if(CCACHE AND ENABLE_CCACHE) - set(CMAKE_C_COMPILER_LAUNCHER ${CCACHE}) -endif() - #----------------------------------------------------------------------------- # Compose CFLAGS #----------------------------------------------------------------------------- From aea4912f1ce488b3acf553077dd3fd0331bc9a27 Mon Sep 17 00:00:00 2001 From: Jukka Laitinen Date: Tue, 7 Sep 2021 14:03:10 +0300 Subject: [PATCH 293/304] Fix compilation of mp_prime_strong_lucas_selfridge Wrong datatype of argument J passed to mp_kronecker Signed-off-by: Jukka Laitinen --- mp_prime_strong_lucas_selfridge.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/mp_prime_strong_lucas_selfridge.c b/mp_prime_strong_lucas_selfridge.c index ffbd9d34f..23486e3a6 100644 --- a/mp_prime_strong_lucas_selfridge.c +++ b/mp_prime_strong_lucas_selfridge.c @@ -52,7 +52,8 @@ mp_err mp_prime_strong_lucas_selfridge(const mp_int *a, bool *result) { /* CZ TODO: choose better variable names! */ mp_int Dz, gcd, Np1, Uz, Vz, U2mz, V2mz, Qmz, Q2mz, Qkdz, T1z, T2z, T3z, T4z, Q2kdz; - int32_t D, Ds, J, sign, P, Q, r, s, u, Nbits; + int J; + int32_t D, Ds, sign, P, Q, r, s, u, Nbits; mp_err err; bool oddness; From 2065e4c270dd2fca9f9e9435513cf243eb85581b Mon Sep 17 00:00:00 2001 From: paperchalice Date: Wed, 29 Jan 2025 16:26:23 +0800 Subject: [PATCH 294/304] Use bcrypt.h on Windows --- CMakeLists.txt | 12 ++++++++++++ s_mp_rand_platform.c | 12 ++++++++++++ 2 files changed, 24 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 014fb1883..3df3a201b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -23,6 +23,8 @@ set(PACKAGE_RELEASE_VERSION 1) include(GNUInstallDirs) include(CheckIPOSupported) include(CMakePackageConfigHelpers) +include(CMakePushCheckState) +include(CheckSymbolExists) # default is "No tests" option(BUILD_TESTING "" OFF) include(CTest) @@ -104,6 +106,16 @@ target_compile_options(${PROJECT_NAME} BEFORE PRIVATE target_link_options(${PROJECT_NAME} BEFORE PRIVATE ${LTM_LD_FLAGS} ) +if(MSVC) + cmake_push_check_state() + set(CMAKE_REQUIRED_LIBRARIES bcrypt) + check_symbol_exists(BCryptGenRandom "Windows.h;bcrypt.h" BCRYPT_AVAILABLE) + cmake_pop_check_state() + if(BCRYPT_AVAILABLE) + target_compile_definitions(${PROJECT_NAME} PRIVATE LTM_WIN32_BCRYPT) + target_link_libraries(${PROJECT_NAME} PRIVATE bcrypt) + endif() +endif() set(PUBLIC_HEADERS tommath.h) set(C89 False CACHE BOOL "(Usually maintained automatically) Enable when the library is in c89 mode to package the correct header files on install") diff --git a/s_mp_rand_platform.c b/s_mp_rand_platform.c index 0a6982a55..f294c832e 100644 --- a/s_mp_rand_platform.c +++ b/s_mp_rand_platform.c @@ -28,6 +28,17 @@ static mp_err s_read_arc4random(void *p, size_t n) #define WIN32_LEAN_AND_MEAN #include + +#ifdef LTM_WIN32_BCRYPT +#include +#pragma comment(lib, "bcrypt") + +static mp_err s_read_wincsp(void *p, size_t n) +{ + return BCRYPT_SUCCESS(BCryptGenRandom(NULL, (PUCHAR)p, (ULONG)n, + BCRYPT_USE_SYSTEM_PREFERRED_RNG)) ? MP_OKAY : MP_ERR; +} +#else #include static mp_err s_read_wincsp(void *p, size_t n) @@ -45,6 +56,7 @@ static mp_err s_read_wincsp(void *p, size_t n) } return CryptGenRandom(hProv, (DWORD)n, (BYTE *)p) == TRUE ? MP_OKAY : MP_ERR; } +#endif #endif /* WIN32 */ #if !defined(S_READ_WINCSP_C) && defined(__linux__) && defined(__GLIBC_PREREQ) From 48a356883d5b59cec1641191d17690ac991a9d3f Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 19 Nov 2024 12:56:36 +0100 Subject: [PATCH 295/304] Split up mp_rand_source.c In order to make `helper.pl` happy, change the ternary operator to an if-else statement, otherwise it won't properly generate `tommath_class.h`. This fixes #582 This closes #583 Signed-off-by: Steffen Jaeckel --- mp_rand_source.c | 10 +++++----- s_mp_rand_source.c | 7 +++++++ tommath_superclass.h | 1 + 3 files changed, 13 insertions(+), 5 deletions(-) create mode 100644 s_mp_rand_source.c diff --git a/mp_rand_source.c b/mp_rand_source.c index e9e876948..25600c274 100644 --- a/mp_rand_source.c +++ b/mp_rand_source.c @@ -1,12 +1,12 @@ #include "tommath_private.h" -#ifdef MP_RAND_C +#ifdef MP_RAND_SOURCE_C /* LibTomMath, multiple-precision integer library -- Tom St Denis */ /* SPDX-License-Identifier: Unlicense */ - -mp_err(*s_mp_rand_source)(void *out, size_t size) = s_mp_rand_platform; - void mp_rand_source(mp_err(*source)(void *out, size_t size)) { - s_mp_rand_source = (source == NULL) ? s_mp_rand_platform : source; + if (source == NULL) + s_mp_rand_source = s_mp_rand_platform; + else + s_mp_rand_source = source; } #endif diff --git a/s_mp_rand_source.c b/s_mp_rand_source.c new file mode 100644 index 000000000..1e35f07bd --- /dev/null +++ b/s_mp_rand_source.c @@ -0,0 +1,7 @@ +#include "tommath_private.h" +#ifdef S_MP_RAND_SOURCE_C +/* LibTomMath, multiple-precision integer library -- Tom St Denis */ +/* SPDX-License-Identifier: Unlicense */ + +mp_err(*s_mp_rand_source)(void *out, size_t size) = s_mp_rand_platform; +#endif diff --git a/tommath_superclass.h b/tommath_superclass.h index 10c7f12a2..432055a97 100644 --- a/tommath_superclass.h +++ b/tommath_superclass.h @@ -31,6 +31,7 @@ # define MP_RADIX_SIZE_OVERESTIMATE_C # define MP_LOG_N_C # define MP_RAND_C +# define MP_RAND_SOURCE_C # define MP_REDUCE_C # define MP_REDUCE_2K_L_C # define MP_FROM_SBIN_C From 162462765263585443fd5dfeb211f42676a68adf Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Tue, 19 Nov 2024 12:56:51 +0100 Subject: [PATCH 296/304] regen Signed-off-by: Steffen Jaeckel --- libtommath_VS2008.vcproj | 4 ++++ makefile | 6 +++--- makefile.mingw | 6 +++--- makefile.msvc | 6 +++--- makefile.shared | 6 +++--- makefile.unix | 6 +++--- sources.cmake | 1 + tommath_class.h | 5 +++++ 8 files changed, 25 insertions(+), 15 deletions(-) diff --git a/libtommath_VS2008.vcproj b/libtommath_VS2008.vcproj index 71dd3807f..080b7e0de 100644 --- a/libtommath_VS2008.vcproj +++ b/libtommath_VS2008.vcproj @@ -912,6 +912,10 @@ RelativePath="s_mp_rand_platform.c" > + + diff --git a/makefile b/makefile index 8f211f5f2..6daa522be 100644 --- a/makefile +++ b/makefile @@ -48,9 +48,9 @@ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_expt s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_rand_source.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o \ +s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.mingw b/makefile.mingw index e2445e8a0..10f2bd59d 100644 --- a/makefile.mingw +++ b/makefile.mingw @@ -50,9 +50,9 @@ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_expt s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_rand_source.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o \ +s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.msvc b/makefile.msvc index 8feb425c4..f160f2ccd 100644 --- a/makefile.msvc +++ b/makefile.msvc @@ -46,9 +46,9 @@ s_mp_div_recursive.obj s_mp_div_school.obj s_mp_div_small.obj s_mp_exptmod.obj s s_mp_fp_log_d.obj s_mp_get_bit.obj s_mp_invmod.obj s_mp_invmod_odd.obj s_mp_log_2expt.obj \ s_mp_montgomery_reduce_comba.obj s_mp_mul.obj s_mp_mul_balance.obj s_mp_mul_comba.obj s_mp_mul_high.obj \ s_mp_mul_high_comba.obj s_mp_mul_karatsuba.obj s_mp_mul_toom.obj s_mp_prime_is_divisible.obj s_mp_prime_tab.obj \ -s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_sqr.obj s_mp_sqr_comba.obj \ -s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_warray.obj s_mp_warray_get.obj s_mp_warray_put.obj \ -s_mp_zero_buf.obj s_mp_zero_digs.obj +s_mp_radix_map.obj s_mp_radix_size_overestimate.obj s_mp_rand_platform.obj s_mp_rand_source.obj s_mp_sqr.obj \ +s_mp_sqr_comba.obj s_mp_sqr_karatsuba.obj s_mp_sqr_toom.obj s_mp_sub.obj s_mp_warray.obj s_mp_warray_get.obj \ +s_mp_warray_put.obj s_mp_zero_buf.obj s_mp_zero_digs.obj HEADERS_PUB=tommath.h HEADERS=tommath_private.h tommath_class.h tommath_superclass.h tommath_cutoffs.h $(HEADERS_PUB) diff --git a/makefile.shared b/makefile.shared index 50c335269..20bd8e03a 100644 --- a/makefile.shared +++ b/makefile.shared @@ -45,9 +45,9 @@ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_expt s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_rand_source.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o \ +s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o #END_INS diff --git a/makefile.unix b/makefile.unix index 58642098d..06dadddb4 100644 --- a/makefile.unix +++ b/makefile.unix @@ -51,9 +51,9 @@ s_mp_div_recursive.o s_mp_div_school.o s_mp_div_small.o s_mp_exptmod.o s_mp_expt s_mp_fp_log_d.o s_mp_get_bit.o s_mp_invmod.o s_mp_invmod_odd.o s_mp_log_2expt.o \ s_mp_montgomery_reduce_comba.o s_mp_mul.o s_mp_mul_balance.o s_mp_mul_comba.o s_mp_mul_high.o \ s_mp_mul_high_comba.o s_mp_mul_karatsuba.o s_mp_mul_toom.o s_mp_prime_is_divisible.o s_mp_prime_tab.o \ -s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_sqr.o s_mp_sqr_comba.o \ -s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o s_mp_warray_put.o \ -s_mp_zero_buf.o s_mp_zero_digs.o +s_mp_radix_map.o s_mp_radix_size_overestimate.o s_mp_rand_platform.o s_mp_rand_source.o s_mp_sqr.o \ +s_mp_sqr_comba.o s_mp_sqr_karatsuba.o s_mp_sqr_toom.o s_mp_sub.o s_mp_warray.o s_mp_warray_get.o \ +s_mp_warray_put.o s_mp_zero_buf.o s_mp_zero_digs.o HEADERS_PUB=tommath.h diff --git a/sources.cmake b/sources.cmake index 103e9c099..e3c12433b 100644 --- a/sources.cmake +++ b/sources.cmake @@ -152,6 +152,7 @@ s_mp_prime_tab.c s_mp_radix_map.c s_mp_radix_size_overestimate.c s_mp_rand_platform.c +s_mp_rand_source.c s_mp_sqr.c s_mp_sqr_comba.c s_mp_sqr_karatsuba.c diff --git a/tommath_class.h b/tommath_class.h index 09bb3ea63..40ddfd4b4 100644 --- a/tommath_class.h +++ b/tommath_class.h @@ -161,6 +161,7 @@ # define S_MP_RADIX_MAP_C # define S_MP_RADIX_SIZE_OVERESTIMATE_C # define S_MP_RAND_PLATFORM_C +# define S_MP_RAND_SOURCE_C # define S_MP_SQR_C # define S_MP_SQR_COMBA_C # define S_MP_SQR_KARATSUBA_C @@ -1248,6 +1249,10 @@ #if defined(S_MP_RAND_PLATFORM_C) #endif +#if defined(S_MP_RAND_SOURCE_C) +# define S_MP_RAND_PLATFORM_C +#endif + #if defined(S_MP_SQR_C) # define MP_CLAMP_C # define MP_CLEAR_C From 5938524c60a7168ba5babb3e47b5cd4ee6eadb46 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Thu, 30 Jan 2025 16:25:57 +0100 Subject: [PATCH 297/304] Bump actions/upload-artifacts version Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 18a832bbe..7f0e1ced7 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -35,7 +35,7 @@ jobs: make docs V=1 cp doc/bn.pdf bn-${{ github.run_id }}.pdf - name: upload PDF - uses: actions/upload-artifact@v3 + uses: actions/upload-artifact@v4 with: name: bn-${{ github.run_id }}.pdf path: bn-${{ github.run_id }}.pdf From afc14115e5a8a4a3d84d71cc208f1cc1be5c7051 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 17 Feb 2025 15:21:50 +0100 Subject: [PATCH 298/304] Make it possible to deploy for Ubuntu 24.04 Signed-off-by: Steffen Jaeckel --- .github/workflows/deploy.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index a06ac73c5..47cfb66db 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -15,7 +15,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [ ubuntu-20.04, ubuntu-22.04 ] + os: [ ubuntu-22.04, ubuntu-24.04 ] steps: - uses: actions/checkout@v2 - name: set Ubuntu codename From b2cdf651524424f6f6cb91e21da1ba33e2595e3a Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 13:15:45 +0100 Subject: [PATCH 299/304] Cancel running CI job if PR is updated. Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7f0e1ced7..b4b79b266 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -24,6 +24,10 @@ on: - /^support\/.*$/ - /^ci\/.*$/ +concurrency: + group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }} + cancel-in-progress: true + jobs: Docs: runs-on: ubuntu-20.04 From 4e22dcbf2e56dcc76ce4c01102e4b27a68a58171 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 13:16:08 +0100 Subject: [PATCH 300/304] Ubuntu 20.04 is no longer supported for CI Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 49 +++++++++++++++++++------------------- 1 file changed, 24 insertions(+), 25 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index b4b79b266..c56b13898 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -30,10 +30,10 @@ concurrency: jobs: Docs: - runs-on: ubuntu-20.04 + runs-on: ubuntu-22.04 container: texlive/texlive:latest-full steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 - name: generate PDF run: | make docs V=1 @@ -47,7 +47,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [ ubuntu-20.04 ] + os: [ ubuntu-22.04 ] # The environment given to the programs in the build # We have only one program and the variable $BUILDOPTIONS # has only the options to that program: testme.sh @@ -70,15 +70,15 @@ jobs: # Alternative big-int version of mp_log(_n) for the 32-bit architecture (no valgrind) - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --cflags=-DS_MP_WORD_TOO_SMALL_C="" ', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } # clang for the 32-bit architecture (no valgrind) - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-14 --with-m32', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14 gcc-multilib' } # RSA superclass with tests (no sanitizer, but debug info) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --cflags=-DLTM_NOTHING --cflags=-DSC_RSA_1_WITH_TESTS --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '1', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } # Build with small stack-size - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 libc6-dev-i386 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-14 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14 libc6-dev-i386 gcc-multilib' } - { BUILDOPTIONS: '--with-cc=gcc --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-i386 gcc-multilib' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10 gcc-multilib' } + - { BUILDOPTIONS: '--with-cc=clang-14 --with-m32 --with-m64 --cflags=-DMP_SMALL_STACK_SIZE --multithread', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14 gcc-multilib' } # Test "autotuning", the automatic evaluation and setting of the Toom-Cook cut-offs. #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' @@ -86,7 +86,7 @@ jobs: #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=gcc-5 --limit-valgrind --make-option=tune' #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_16BIT --limit-valgrind --make-option=tune' #- env: SANITIZER=1 BUILDOPTIONS='--with-cc=clang-7 --cflags=-DMP_32BIT --limit-valgrind --make-option=tune' - - { BUILDOPTIONS: '--with-cc=clang-10 --limit-valgrind --make-option=tune', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-14 --limit-valgrind --make-option=tune', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14' } # GCC for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs. @@ -96,9 +96,9 @@ jobs: # clang for the x86-64 architecture testing against a different Bigint-implementation # with 333333 different inputs - - { BUILDOPTIONS: '--with-cc=clang-10 --test-vs-mtest=333333 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-14 --test-vs-mtest=333333 --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14' } # ... and a better random source. - - { BUILDOPTIONS: '--with-cc=clang-10 --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang-14 --test-vs-mtest=333333 --mtest-real-rand --limit-valgrind', SANITIZER: '', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-14 llvm-14' } # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) # TODO: Probably not possible to run anything in x32 in GH actions @@ -107,21 +107,20 @@ jobs: # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } + - { BUILDOPTIONS: '--with-cc=gcc-9 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-9' } - { BUILDOPTIONS: '--with-cc=gcc-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-10' } - - { BUILDOPTIONS: '--with-cc=gcc-8 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-8' } - - { BUILDOPTIONS: '--with-cc=gcc-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-7' } + - { BUILDOPTIONS: '--with-cc=gcc-12 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'gcc-12' } # clang for x86-64 architecture (64-bit longs and 64-bit pointers) - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'relaxed', OTHERDEPS: 'clang-10 llvm-10' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } - - { BUILDOPTIONS: '--with-cc=clang-10 --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } - - { BUILDOPTIONS: '--with-cc=clang-10 --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang-10 llvm-10' } - - { BUILDOPTIONS: '--with-cc=clang-10 --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-10 llvm-10' } + - { BUILDOPTIONS: '--with-cc=clang --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'relaxed', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } + - { BUILDOPTIONS: '--with-cc=clang-11 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-11 llvm-11' } - { BUILDOPTIONS: '--with-cc=clang-12 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-12 llvm-12' } - - { BUILDOPTIONS: '--with-cc=clang-9 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-9 llvm-9' } - - { BUILDOPTIONS: '--with-cc=clang-8 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-8 llvm-8' } - - { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-7 llvm-7' } - - { BUILDOPTIONS: '--with-cc=clang-6.0 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-6.0 llvm-6.0' } + - { BUILDOPTIONS: '--with-cc=clang-13 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-13 llvm-13' } + - { BUILDOPTIONS: '--with-cc=clang-15 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-15 llvm-15' } # Link time optimization - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } #- { BUILDOPTIONS: '--with-cc=clang-7 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '1', CONV_WARNINGS: '', OTHERDEPS: '' } @@ -139,7 +138,7 @@ jobs: - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_16BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_32BIT --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 - name: install dependencies run: | sudo apt-get update -qq @@ -180,9 +179,9 @@ jobs: cat gcc_errors_*.log || true amalgam: - runs-on: ubuntu-22.04 + runs-on: ubuntu-24.04 steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 - name: install dependencies run: | make amalgamated_timing @@ -191,7 +190,7 @@ jobs: runs-on: ${{ matrix.os }} strategy: matrix: - os: [ ubuntu-20.04, ubuntu-22.04 ] + os: [ ubuntu-22.04, ubuntu-24.04 ] build_type: [ '', -DCMAKE_BUILD_TYPE=Debug, -DCMAKE_BUILD_TYPE=Release, -DCMAKE_BUILD_TYPE=RelWithDebInfo, -DCMAKE_BUILD_TYPE=MinSizeRel ] cc: [ clang, gcc ] config: @@ -200,7 +199,7 @@ jobs: # Shared library build - { CMAKEOPTIONS: '-DBUILD_SHARED_LIBS=On' } steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 - name: install dependencies run: | sudo apt-get update -qq From 68c1463af2e067372de9e7e5632ddfaf74b08358 Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 13:28:51 +0100 Subject: [PATCH 301/304] Fix wrongly ordered cleanup. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Warning was: ``` In function ‘mp_clear’, inlined from ‘mp_gcd.part.0’ at mp_gcd.c:89:4: mp_clear.c:10:9: warning: ‘v.dp’ may be used uninitialized [-Wmaybe-uninitialized] 10 | if (a->dp != NULL) { | ^ ``` Fixes: aab1b3d99f2 ("split label & statement") Signed-off-by: Steffen Jaeckel --- mp_gcd.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mp_gcd.c b/mp_gcd.c index 4f6b6cc29..be77b34a1 100644 --- a/mp_gcd.c +++ b/mp_gcd.c @@ -84,9 +84,9 @@ mp_err mp_gcd(const mp_int *a, const mp_int *b, mp_int *c) c->sign = MP_ZPOS; err = MP_OKAY; LBL_V: - mp_clear(&u); -LBL_U: mp_clear(&v); +LBL_U: + mp_clear(&u); return err; } #endif From 8ce7850e8987ff7e5c23ccb7625f56c973d2f73a Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 13:39:00 +0100 Subject: [PATCH 302/304] Work around false-positive warning. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The warning was: ``` s_mp_exptmod_fast.c: In function ‘s_mp_exptmod_fast’: s_mp_exptmod_fast.c:188:21: warning: ‘mp’ may be used uninitialized in this function [-Wmaybe-uninitialized] 188 | if ((err = redux(&res, P, mp)) != MP_OKAY) goto LBL_RES; | ^ s_mp_exptmod_fast.c:25:18: note: ‘mp’ was declared here 25 | mp_digit buf, mp; | ^ ``` Signed-off-by: Steffen Jaeckel --- s_mp_exptmod_fast.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/s_mp_exptmod_fast.c b/s_mp_exptmod_fast.c index e7729f49d..338fd9a5d 100644 --- a/s_mp_exptmod_fast.c +++ b/s_mp_exptmod_fast.c @@ -22,7 +22,7 @@ mp_err s_mp_exptmod_fast(const mp_int *G, const mp_int *X, const mp_int *P, mp_int *Y, int redmode) { mp_int M[TAB_SIZE], res; - mp_digit buf, mp; + mp_digit buf, mp = 0; int bitbuf, bitcpy, bitcnt, mode, digidx, x, y, winsize; mp_err err; From bbf4dff571bd4f22e75eadfe903c6860fbb574ec Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 13:52:08 +0100 Subject: [PATCH 303/304] x32 ABI is no longer supported on Ubuntu 22.04. c.f. [0] for details. [0] https://github.com/actions/runner-images/issues/8397 Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index c56b13898..58b5aaa89 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -103,7 +103,7 @@ jobs: # GCC for the x64_32 architecture (32-bit longs and 32-bit pointers) # TODO: Probably not possible to run anything in x32 in GH actions # but needs to be checked to be sure. - - { BUILDOPTIONS: '--with-cc=gcc --with-mx32', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-x32 gcc-multilib' } + # - { BUILDOPTIONS: '--with-cc=gcc --with-mx32', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'libc6-dev-x32 gcc-multilib' } # GCC for the x86-64 architecture (64-bit longs and 64-bit pointers) - { BUILDOPTIONS: '--with-cc=gcc --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: '' } From b59524cdfd4855c1b8a1029430347c8946b7694e Mon Sep 17 00:00:00 2001 From: Steffen Jaeckel Date: Mon, 24 Feb 2025 14:02:37 +0100 Subject: [PATCH 304/304] Clang-11 sanitizer seems to be broken. It terminates with the following error message: ``` ==2028==ERROR: UndefinedBehaviorSanitizer failed to allocate 0x0 (0) bytes of SetAlternateSignalStack (error code: 22) ==2028==Process memory map follows: [memory map] ==2028==End of process memory map. ==2028==Sanitizer CHECK failed: /build/llvm-toolchain-11-mnvtwk/llvm-toolchain-11-11.1.0/compiler-rt/lib/sanitizer_common/sanitizer_common.cpp:54 ((0 && "unable to mmap")) != (0) (0, 0) ``` Signed-off-by: Steffen Jaeckel --- .github/workflows/main.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 58b5aaa89..2ca3adcfe 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -117,7 +117,7 @@ jobs: - { BUILDOPTIONS: '--with-cc=clang --cflags=-DMP_USE_MEMOPS --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang llvm' } - { BUILDOPTIONS: '--with-cc=clang --c89 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: 'strict', OTHERDEPS: 'clang llvm' } - { BUILDOPTIONS: '--with-cc=clang --with-m64 --limit-valgrind --cflags=-DMP_PREC=MP_MIN_PREC', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang llvm' } - - { BUILDOPTIONS: '--with-cc=clang-11 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-11 llvm-11' } + # - { BUILDOPTIONS: '--with-cc=clang-11 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-11 llvm-11' } - { BUILDOPTIONS: '--with-cc=clang-12 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-12 llvm-12' } - { BUILDOPTIONS: '--with-cc=clang-13 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-13 llvm-13' } - { BUILDOPTIONS: '--with-cc=clang-15 --with-m64 --limit-valgrind', SANITIZER: '1', COMPILE_DEBUG: '0', COMPILE_LTO: '0', CONV_WARNINGS: '', OTHERDEPS: 'clang-15 llvm-15' }