diff options
Diffstat (limited to 'vendor/gmp-6.3.0/mini-gmp/tests')
39 files changed, 6716 insertions, 0 deletions
diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/Makefile b/vendor/gmp-6.3.0/mini-gmp/tests/Makefile new file mode 100644 index 0000000..7cc4485 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/Makefile @@ -0,0 +1,65 @@ +# Note: Requires GNU make + +# Copyright 2011, 2012, 2014, 2016, 2018 Free Software Foundation, Inc. +# +# This file is part of the GNU MP Library test suite. +# +# The GNU MP Library test suite is free software; you can redistribute it +# and/or modify it under the terms of the GNU General Public License as +# published by the Free Software Foundation; either version 3 of the License, +# or (at your option) any later version. +# +# The GNU MP Library test suite is distributed in the hope that it will be +# useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +# Public License for more details. +# +# You should have received a copy of the GNU General Public License along with +# the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. + +srcdir=. +MINI_GMP_DIR=.. + +CC = gcc +CFLAGS = -O -Wall -g +CPPFLAGS = +LDFLAGS = + +LIBS = -lgmp -lm -lmcheck + +CHECK_PROGRAMS = t-add t-sub t-mul t-invert t-div t-div_2exp \ + t-double t-cmp_d t-gcd t-lcm t-import t-comb t-signed \ + t-sqrt t-root t-powm t-logops t-bitops t-scan t-str \ + t-reuse t-aorsmul t-limbs t-cong t-pprime_p t-lucm \ + t-mpq_addsub t-mpq_muldiv t-mpq_muldiv_2exp t-mpq_str \ + t-mpq_double +# Default TESTS to all tests, allowing overriding TESTS for building tests +# without running them. +TESTS = $(CHECK_PROGRAMS) + +MISC_OBJS = hex-random.o mini-random.o testutils.o + +all: + +clean: + rm -f *.o $(CHECK_PROGRAMS) + +%: %.c +.c: + +# Keep object files +.PRECIOUS: %.o + +%.o: %.c $(MINI_GMP_DIR)/mini-gmp.h $(MINI_GMP_DIR)/mini-mpq.h hex-random.h mini-random.h + $(CC) $(CFLAGS) $(CPPFLAGS) -c $< -o $@ + +testutils.o: $(MINI_GMP_DIR)/mini-gmp.c $(MINI_GMP_DIR)/mini-mpq.c + +%: %.o $(MISC_OBJS) + $(CC) $(CFLAGS) $(LDFLAGS) $^ $(LIBS) -o $@ + +# Missing tests include: +# mpz_cmp_d, mpz_popcount, mpz_hamdist, mpz_ui_pow_ui + +check: $(CHECK_PROGRAMS) + $(srcdir)/run-tests $(TESTS) diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.c b/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.c new file mode 100644 index 0000000..a5b405b --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.c @@ -0,0 +1,573 @@ +/* + +Copyright 2011, 2016, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdio.h> +#include <stdlib.h> + +#include <time.h> + +#ifdef __unix__ +# include <unistd.h> +# include <sys/time.h> +#endif + +#include "gmp.h" + +#include "hex-random.h" + +/* FIXME: gmp-impl.h included only for mpz_lucas_mod */ +/* #include "gmp-impl.h" */ +#if defined (__cplusplus) +extern "C" { +#endif + +#define mpz_lucas_mod __gmpz_lucas_mod +__GMP_DECLSPEC int mpz_lucas_mod (mpz_ptr, mpz_ptr, long, mp_bitcnt_t, mpz_srcptr, mpz_ptr, mpz_ptr); + +#if defined (__cplusplus) +} +#endif + +static gmp_randstate_t state; + +static void +mkseed (mpz_t seed) +{ + FILE *f = fopen ("/dev/urandom", "rb"); + if (f) + { + unsigned char buf[6]; + size_t res; + + setbuf (f, NULL); + res = fread (buf, sizeof(buf), 1, f); + fclose (f); + + if (res == 1) + { + mpz_import (seed, sizeof(buf), 1, 1, 0, 0, buf); + return; + } + } + +#ifdef __unix__ + { + struct timeval tv; + mpz_t usec; + mpz_init (usec); + + gettimeofday (&tv, NULL); + mpz_set_ui (seed, tv.tv_sec); + mpz_set_ui (usec, tv.tv_usec); + /* usec fits in 20 bits, shift left to make it 48 bits. */ + mpz_mul_2exp (usec, usec, 28); + mpz_xor (seed, seed, usec); + + mpz_clear (usec); + } +#else + mpz_set_ui (seed, time (NULL)); +#endif +} + +void +hex_random_init (void) +{ + mpz_t seed; + char *env_seed; + + mpz_init (seed); + + env_seed = getenv ("GMP_CHECK_RANDOMIZE"); + if (env_seed && env_seed[0]) + { + mpz_set_str (seed, env_seed, 0); + if (mpz_cmp_ui (seed, 0) != 0) + gmp_printf ("Re-seeding with GMP_CHECK_RANDOMIZE=%Zd\n", seed); + else + { + mkseed (seed); + gmp_printf ("Seed GMP_CHECK_RANDOMIZE=%Zd (include this in bug reports)\n", seed); + } + fflush (stdout); + } + else + mpz_set_ui (seed, 4711); + + gmp_randinit_default (state); + gmp_randseed (state, seed); + + mpz_clear (seed); +} + +char * +hex_urandomb (unsigned long bits) +{ + char *res; + mpz_t x; + + mpz_init (x); + mpz_urandomb (x, state, bits); + gmp_asprintf (&res, "%Zx", x); + mpz_clear (x); + return res; +} + +char * +hex_rrandomb (unsigned long bits) +{ + char *res; + mpz_t x; + + mpz_init (x); + mpz_rrandomb (x, state, bits); + gmp_asprintf (&res, "%Zx", x); + mpz_clear (x); + return res; +} + +char * +hex_rrandomb_export (void *dst, size_t *countp, + int order, size_t size, int endian, unsigned long bits) +{ + char *res; + mpz_t x; + mpz_init (x); + mpz_rrandomb (x, state, bits); + gmp_asprintf (&res, "%Zx", x); + mpz_export (dst, countp, order, size, endian, 0, x); + mpz_clear (x); + return res; +} + +void hex_random_op2 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **rp) +{ + mpz_t a, r; + unsigned long abits; + unsigned signs; + + mpz_init (a); + mpz_init (r); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + + mpz_rrandomb (a, state, abits); + + signs = gmp_urandomb_ui (state, 1); + if (signs & 1) + mpz_neg (a, a); + + switch (op) + { + default: + abort (); + case OP_SQR: + mpz_mul (r, a, a); + break; + } + + gmp_asprintf (ap, "%Zx", a); + gmp_asprintf (rp, "%Zx", r); + + mpz_clear (a); + mpz_clear (r); +} + +void +hex_random_op3 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **bp, char **rp) +{ + mpz_t a, b, r; + unsigned long abits, bbits; + unsigned signs; + + mpz_init (a); + mpz_init (b); + mpz_init (r); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + bbits = gmp_urandomb_ui (state, 32) % maxbits; + + mpz_rrandomb (a, state, abits); + mpz_rrandomb (b, state, bbits); + + signs = gmp_urandomb_ui (state, 3); + if (signs & 1) + mpz_neg (a, a); + if (signs & 2) + mpz_neg (b, b); + + switch (op) + { + default: + abort (); + case OP_ADD: + mpz_add (r, a, b); + break; + case OP_SUB: + mpz_sub (r, a, b); + break; + case OP_MUL: + mpz_mul (r, a, b); + break; + case OP_GCD: + if (signs & 4) + { + /* Produce a large gcd */ + unsigned long gbits = gmp_urandomb_ui (state, 32) % maxbits; + mpz_rrandomb (r, state, gbits); + mpz_mul (a, a, r); + mpz_mul (b, b, r); + } + mpz_gcd (r, a, b); + break; + case OP_LCM: + if (signs & 4) + { + /* Produce a large gcd */ + unsigned long gbits = gmp_urandomb_ui (state, 32) % maxbits; + mpz_rrandomb (r, state, gbits); + mpz_mul (a, a, r); + mpz_mul (b, b, r); + } + mpz_lcm (r, a, b); + break; + case OP_AND: + mpz_and (r, a, b); + break; + case OP_IOR: + mpz_ior (r, a, b); + break; + case OP_XOR: + mpz_xor (r, a, b); + break; + } + + gmp_asprintf (ap, "%Zx", a); + gmp_asprintf (bp, "%Zx", b); + gmp_asprintf (rp, "%Zx", r); + + mpz_clear (a); + mpz_clear (b); + mpz_clear (r); +} + +void +hex_random_op4 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **bp, char **cp, char **dp) +{ + mpz_t a, b, c, d; + unsigned long abits, bbits; + unsigned signs; + + mpz_init (a); + mpz_init (b); + mpz_init (c); + mpz_init (d); + + if (op == OP_POWM) + { + unsigned long cbits; + abits = gmp_urandomb_ui (state, 32) % maxbits; + bbits = 1 + gmp_urandomb_ui (state, 32) % maxbits; + cbits = 2 + gmp_urandomb_ui (state, 32) % maxbits; + + mpz_rrandomb (a, state, abits); + mpz_rrandomb (b, state, bbits); + mpz_rrandomb (c, state, cbits); + + signs = gmp_urandomb_ui (state, 3); + if (signs & 1) + mpz_neg (a, a); + if (signs & 2) + { + mpz_t g; + + /* If we negate the exponent, must make sure that gcd(a, c) = 1 */ + if (mpz_sgn (a) == 0) + mpz_set_ui (a, 1); + else + { + mpz_init (g); + + for (;;) + { + mpz_gcd (g, a, c); + if (mpz_cmp_ui (g, 1) == 0) + break; + mpz_divexact (a, a, g); + } + mpz_clear (g); + } + mpz_neg (b, b); + } + if (signs & 4) + mpz_neg (c, c); + + mpz_powm (d, a, b, c); + } + else + { + unsigned long qbits; + bbits = 1 + gmp_urandomb_ui (state, 32) % maxbits; + qbits = gmp_urandomb_ui (state, 32) % maxbits; + abits = bbits + qbits; + if (abits > 30) + abits -= 30; + else + abits = 0; + + mpz_rrandomb (a, state, abits); + mpz_rrandomb (b, state, bbits); + + signs = gmp_urandomb_ui (state, 2); + if (signs & 1) + mpz_neg (a, a); + if (signs & 2) + mpz_neg (b, b); + + switch (op) + { + default: + abort (); + case OP_CDIV: + mpz_cdiv_qr (c, d, a, b); + break; + case OP_FDIV: + mpz_fdiv_qr (c, d, a, b); + break; + case OP_TDIV: + mpz_tdiv_qr (c, d, a, b); + break; + } + } + gmp_asprintf (ap, "%Zx", a); + gmp_asprintf (bp, "%Zx", b); + gmp_asprintf (cp, "%Zx", c); + gmp_asprintf (dp, "%Zx", d); + + mpz_clear (a); + mpz_clear (b); + mpz_clear (c); + mpz_clear (d); +} + +void +hex_random_bit_op (enum hex_random_op op, unsigned long maxbits, + char **ap, unsigned long *b, char **rp) +{ + mpz_t a, r; + unsigned long abits, bbits; + unsigned signs; + + mpz_init (a); + mpz_init (r); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + bbits = gmp_urandomb_ui (state, 32) % (maxbits + 100); + + mpz_rrandomb (a, state, abits); + + signs = gmp_urandomb_ui (state, 1); + if (signs & 1) + mpz_neg (a, a); + + switch (op) + { + default: + abort (); + + case OP_SETBIT: + mpz_set (r, a); + mpz_setbit (r, bbits); + break; + case OP_CLRBIT: + mpz_set (r, a); + mpz_clrbit (r, bbits); + break; + case OP_COMBIT: + mpz_set (r, a); + mpz_combit (r, bbits); + break; + case OP_CDIV_Q_2: + mpz_cdiv_q_2exp (r, a, bbits); + break; + case OP_CDIV_R_2: + mpz_cdiv_r_2exp (r, a, bbits); + break; + case OP_FDIV_Q_2: + mpz_fdiv_q_2exp (r, a, bbits); + break; + case OP_FDIV_R_2: + mpz_fdiv_r_2exp (r, a, bbits); + break; + case OP_TDIV_Q_2: + mpz_tdiv_q_2exp (r, a, bbits); + break; + case OP_TDIV_R_2: + mpz_tdiv_r_2exp (r, a, bbits); + break; + } + + gmp_asprintf (ap, "%Zx", a); + *b = bbits; + gmp_asprintf (rp, "%Zx", r); + + mpz_clear (a); + mpz_clear (r); +} + +void +hex_random_scan_op (enum hex_random_op op, unsigned long maxbits, + char **ap, unsigned long *b, unsigned long *r) +{ + mpz_t a; + unsigned long abits, bbits; + unsigned signs; + + mpz_init (a); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + bbits = gmp_urandomb_ui (state, 32) % (maxbits + 100); + + mpz_rrandomb (a, state, abits); + + signs = gmp_urandomb_ui (state, 1); + if (signs & 1) + mpz_neg (a, a); + + switch (op) + { + default: + abort (); + + case OP_SCAN0: + *r = mpz_scan0 (a, bbits); + break; + case OP_SCAN1: + *r = mpz_scan1 (a, bbits); + break; + } + gmp_asprintf (ap, "%Zx", a); + *b = bbits; + + mpz_clear (a); +} + +void +hex_random_str_op (unsigned long maxbits, + int base, char **ap, char **rp) +{ + mpz_t a; + unsigned long abits; + unsigned signs; + + mpz_init (a); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + + mpz_rrandomb (a, state, abits); + + signs = gmp_urandomb_ui (state, 2); + if (signs & 1) + mpz_neg (a, a); + + *ap = mpz_get_str (NULL, 16, a); + *rp = mpz_get_str (NULL, base, a); + + mpz_clear (a); +} + +void hex_random_lucm_op (unsigned long maxbits, + char **vp, char **qp, char **mp, + long *Q, unsigned long *b0, int *res) +{ + mpz_t m, v, q, t1, t2; + unsigned long mbits; + + mpz_init (m); + mpz_init (v); + mpz_init (q); + mpz_init (t1); + mpz_init (t2); + + *Q = gmp_urandomb_ui (state, 14) + 1; + + do + { + mbits = gmp_urandomb_ui (state, 32) % maxbits + 5; + + mpz_rrandomb (m, state, mbits); + *b0 = gmp_urandomb_ui (state, 32) % (mbits - 3) + 2; + /* The GMP implementation uses the exponent (m >> b0) + 1. */ + /* mini-gmp implementation uses the exponent (m >> b0) | 1. */ + /* They are the same (and are used) only when (m >> b0) is even */ + mpz_clrbit (m, *b0); + /* mini-gmp implementation only works if the modulus is odd. */ + mpz_setbit (m, 0); + } + while (mpz_gcd_ui (NULL, m, *Q) != 1); + + if (*Q == 1 || gmp_urandomb_ui (state, 1)) + *Q = - *Q; + +#if (__GNU_MP_VERSION == 6 && (__GNU_MP_VERSION_MINOR > 1 || __GNU_MP_VERSION_PATCHLEVEL > 9)) + *res = mpz_lucas_mod (v, q, *Q, *b0, m, t1, t2); +#else + *b0 = 0; +#endif + + gmp_asprintf (vp, "%Zx", v); + gmp_asprintf (qp, "%Zx", q); + gmp_asprintf (mp, "%Zx", m); + + mpz_clear (m); + mpz_clear (v); + mpz_clear (q); + mpz_clear (t1); + mpz_clear (t2); +} + +void +hex_mpq_random_str_op (unsigned long maxbits, + int base, char **ap, char **rp) +{ + mpq_t a; + unsigned long abits; + unsigned signs; + + mpq_init (a); + + abits = gmp_urandomb_ui (state, 32) % maxbits; + + mpz_rrandomb (mpq_numref (a), state, abits); + mpz_rrandomb (mpq_denref (a), state, abits); + mpz_add_ui (mpq_denref (a), mpq_denref (a), 1); + + mpq_canonicalize (a); + signs = gmp_urandomb_ui (state, 2); + if (signs & 1) + mpq_neg (a, a); + + *ap = mpq_get_str (NULL, 16, a); + *rp = mpq_get_str (NULL, base, a); + + mpq_clear (a); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.h b/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.h new file mode 100644 index 0000000..da44347 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/hex-random.h @@ -0,0 +1,55 @@ +/* + +Copyright 2011, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +enum hex_random_op + { + OP_ADD, OP_SUB, OP_MUL, OP_SQR, + OP_CDIV, OP_FDIV, OP_TDIV, + OP_CDIV_Q_2, OP_CDIV_R_2, + OP_FDIV_Q_2, OP_FDIV_R_2, + OP_TDIV_Q_2, OP_TDIV_R_2, + OP_GCD, OP_LCM, OP_POWM, OP_AND, OP_IOR, OP_XOR, + OP_SETBIT, OP_CLRBIT, OP_COMBIT, + OP_SCAN0, OP_SCAN1, + }; + +void hex_random_init (void); +char *hex_urandomb (unsigned long bits); +char *hex_rrandomb (unsigned long bits); +char *hex_rrandomb_export (void *dst, size_t *countp, + int order, size_t size, int endian, + unsigned long bits); + +void hex_random_op2 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **rp); +void hex_random_op3 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **bp, char **rp); +void hex_random_op4 (enum hex_random_op op, unsigned long maxbits, + char **ap, char **bp, char **rp, char **qp); +void hex_random_bit_op (enum hex_random_op op, unsigned long maxbits, + char **ap, unsigned long *b, char **rp); +void hex_random_scan_op (enum hex_random_op op, unsigned long maxbits, + char **ap, unsigned long *b, unsigned long *r); +void hex_random_str_op (unsigned long maxbits, + int base, char **ap, char **rp); +void hex_random_lucm_op (unsigned long maxbits, + char **vp, char **qp, char **mp, + long *Q, unsigned long *b0, int *res); +void hex_mpq_random_str_op (unsigned long maxbits, + int base, char **ap, char **rp); diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.c b/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.c new file mode 100644 index 0000000..7504af3 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.c @@ -0,0 +1,160 @@ +/* + +Copyright 2011, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdio.h> +#include <stdlib.h> + +#include "mini-random.h" + +static void +set_str (mpz_t r, const char *s) +{ + if (mpz_set_str (r, s, 16) != 0) + { + fprintf (stderr, "mpz_set_str failed on input %s\n", s); + abort (); + } +} + +void +mini_urandomb (mpz_t r, unsigned long bits) +{ + char *s; + s = hex_urandomb (bits); + set_str (r, s); + free (s); +} + +void +mini_rrandomb (mpz_t r, unsigned long bits) +{ + char *s; + s = hex_rrandomb (bits); + set_str (r, s); + free (s); +} + +void +mini_rrandomb_export (mpz_t r, void *dst, size_t *countp, + int order, size_t size, int endian, unsigned long bits) +{ + char *s; + s = hex_rrandomb_export (dst, countp, order, size, endian, bits); + set_str (r, s); + free (s); +} + +void +mini_random_op2 (enum hex_random_op op, unsigned long maxbits, + mpz_t a, mpz_t r) +{ + char *ap; + char *rp; + + hex_random_op2 (op, maxbits, &ap, &rp); + set_str (a, ap); + set_str (r, rp); + + free (ap); + free (rp); +} + +void +mini_random_op3 (enum hex_random_op op, unsigned long maxbits, + mpz_t a, mpz_t b, mpz_t r) +{ + char *ap; + char *bp; + char *rp; + + hex_random_op3 (op, maxbits, &ap, &bp, &rp); + set_str (a, ap); + set_str (b, bp); + set_str (r, rp); + + free (ap); + free (bp); + free (rp); +} + +void +mini_random_op4 (enum hex_random_op op, unsigned long maxbits, + mpz_t a, mpz_t b, mpz_t c, mpz_t d) +{ + char *ap; + char *bp; + char *cp; + char *dp; + + hex_random_op4 (op, maxbits, &ap, &bp, &cp, &dp); + set_str (a, ap); + set_str (b, bp); + set_str (c, cp); + set_str (d, dp); + + free (ap); + free (bp); + free (cp); + free (dp); +} + +void +mini_random_bit_op (enum hex_random_op op, unsigned long maxbits, + mpz_t a, mp_bitcnt_t *b, mpz_t r) +{ + char *ap; + char *rp; + + hex_random_bit_op (op, maxbits, &ap, b, &rp); + set_str (a, ap); + set_str (r, rp); + + free (ap); + free (rp); +} + +void +mini_random_scan_op (enum hex_random_op op, unsigned long maxbits, + mpz_t a, mp_bitcnt_t *b, mp_bitcnt_t *r) +{ + char *ap; + + hex_random_scan_op (op, maxbits, &ap, b, r); + set_str (a, ap); + + free (ap); +} + +void +mini_random_lucm_op (unsigned long maxbits, mpz_t v, mpz_t q, mpz_t m, + long *Q, unsigned long *b0, int *res) +{ + char *vp; + char *qp; + char *mp; + + hex_random_lucm_op (maxbits, &vp, &qp, &mp, Q, b0, res); + set_str (v, vp); + set_str (q, qp); + set_str (m, mp); + + free (vp); + free (qp); + free (mp); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.h b/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.h new file mode 100644 index 0000000..2f54749 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/mini-random.h @@ -0,0 +1,35 @@ +/* + +Copyright 2011, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include "../mini-gmp.h" +#include "hex-random.h" + +void mini_urandomb (mpz_t, unsigned long); +void mini_rrandomb (mpz_t, unsigned long); +void mini_rrandomb_export (mpz_t r, void *dst, size_t *countp, + int order, size_t size, int endian, + unsigned long bits); + +void mini_random_op2 (enum hex_random_op, unsigned long, mpz_t, mpz_t); +void mini_random_op3 (enum hex_random_op, unsigned long, mpz_t, mpz_t, mpz_t); +void mini_random_op4 (enum hex_random_op, unsigned long, mpz_t, mpz_t, mpz_t, mpz_t); +void mini_random_scan_op (enum hex_random_op, unsigned long, mpz_t, mp_bitcnt_t *, mp_bitcnt_t *); +void mini_random_bit_op (enum hex_random_op, unsigned long, mpz_t, mp_bitcnt_t *, mpz_t); +void mini_random_lucm_op (unsigned long, mpz_t, mpz_t, mpz_t, + long *, unsigned long *, int *); diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/run-tests b/vendor/gmp-6.3.0/mini-gmp/tests/run-tests new file mode 100755 index 0000000..3ebc4ae --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/run-tests @@ -0,0 +1,143 @@ +#! /bin/sh + +# Copyright (C) 2000-2002, 2004, 2005, 2011, 2012, 2016, 2020 Niels Möller +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along +# with this program; if not, write to the Free Software Foundation, Inc., +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + +failed=0 +all=0 + +debug='no' +testflags='' + +if [ -z "$srcdir" ] ; then + srcdir=`pwd` +fi + +export srcdir + +if [ -n "$TEST_SHLIB_DIR" ] ; then + # Prepend to LD_LIBRARY_PATH, if it is alredy set. + LD_LIBRARY_PATH="${TEST_SHLIB_DIR}${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}" + # For MACOS + DYLD_LIBRARY_PATH="$TEST_SHLIB_DIR" + # For Windows + PATH="${TEST_SHLIB_DIR}:${PATH}" + # For Wine + WINEPATH="${TEST_SHLIB_DIR}${WINEPATH:+;$WINEPATH}" + + export LD_LIBRARY_PATH + export DYLD_LIBRARY_PATH + export PATH + export WINEPATH +fi + +# When used in make rules, we sometimes get the filenames VPATH +# expanded, but usually not. +find_program () { + case "$1" in + */*) + echo "$1" + ;; + *) + if [ -x "$1" ] ; then + echo "./$1" + elif [ -x "$1.exe" ] ; then + echo "./$1.exe" + else + echo "$srcdir/$1" + fi + ;; + esac +} + +env_program () { + if [ -x "$1" ] ; then + if "$1"; then : ; else + echo FAIL: $1 + exit 1 + fi + fi +} + +test_program () { + testname=`basename "$1" .exe` + testname=`basename "$testname" -test` + if [ -z "$EMULATOR" ] || head -1 "$1" | grep '^#!' > /dev/null; then + "$1" $testflags + else + $EMULATOR "$1" $testflags + fi + case "$?" in + 0) + echo PASS: $testname + all=`expr $all + 1` + ;; + 77) + echo SKIP: $testname + ;; + *) + echo FAIL: $testname + failed=`expr $failed + 1` + all=`expr $all + 1` + ;; + esac +} + +env_program `find_program setup-env` + +while test $# != 0 +do + case "$1" in + --debug) + debug=yes + ;; + -v) + testflags='-v' + ;; + -*) + echo >&2 'Unknown option `'"$1'" + exit 1 + ;; + *) + break + ;; + esac + shift +done + +# Comment out special handling for zero arguments to support separate +# tests-build/tests-run. +#if [ $# -eq 0 ] ; then +# for f in *-test; do test_program "./$f"; done +#else + for f in "$@" ; do test_program `find_program "$f"`; done +#fi + +if [ $failed -eq 0 ] ; then + banner="All $all tests passed" +else + banner="$failed of $all tests failed" +fi +dashes=`echo "$banner" | sed s/./=/g` +echo "$dashes" +echo "$banner" +echo "$dashes" + +if [ "x$debug" = xno ] ; then + env_program `find_program teardown-env` +fi + +[ "$failed" -eq 0 ] diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-add.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-add.c new file mode 100644 index 0000000..0a093ef --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-add.c @@ -0,0 +1,57 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, res, ref; + + mpz_init (a); + mpz_init (b); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_ADD, MAXBITS, a, b, ref); + mpz_add (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_add failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-aorsmul.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-aorsmul.c new file mode 100644 index 0000000..eb275a8 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-aorsmul.c @@ -0,0 +1,77 @@ +/* + +Copyright 2012, 2014, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) +#define MAXLIMBS ((MAXBITS + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS) + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, res, ref; + + mpz_init (a); + mpz_init (b); + mpz_init_set_ui (res, 5); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_MUL, MAXBITS, a, b, ref); + if (i & 1) { + mpz_add (ref, ref, res); + if (mpz_fits_ulong_p (b)) + mpz_addmul_ui (res, a, mpz_get_ui (b)); + else + mpz_addmul (res, a, b); + } else { + mpz_sub (ref, res, ref); + if (mpz_fits_ulong_p (b)) + mpz_submul_ui (res, a, mpz_get_ui (b)); + else + mpz_submul (res, a, b); + } + if (mpz_cmp (res, ref)) + { + if (i & 1) + fprintf (stderr, "mpz_addmul failed:\n"); + else + fprintf (stderr, "mpz_submul failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-bitops.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-bitops.c new file mode 100644 index 0000000..27d87ca --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-bitops.c @@ -0,0 +1,104 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, res, ref; + mp_bitcnt_t b; + + mpz_init (a); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_bit_op (OP_SETBIT, MAXBITS, a, &b, ref); + mpz_set (res, a); + mpz_setbit (res, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_setbit failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + if (!mpz_tstbit (res, b)) + { + fprintf (stderr, "mpz_tstbit failed (after mpz_setbit):\n"); + dump ("res", a); + fprintf (stderr, "b: %lu\n", b); + abort (); + } + mini_random_bit_op (OP_CLRBIT, MAXBITS, a, &b, ref); + mpz_set (res, a); + mpz_clrbit (res, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_clrbit failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + if (mpz_tstbit (res, b)) + { + fprintf (stderr, "mpz_tstbit failed (after mpz_clrbit):\n"); + dump ("res", a); + fprintf (stderr, "b: %lu\n", b); + abort (); + } + mini_random_bit_op (OP_COMBIT, MAXBITS, a, &b, ref); + mpz_set (res, a); + mpz_com (a, a); + mpz_combit (res, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_combit failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + if (mpz_tstbit (res, b) != mpz_tstbit (a, b)) + { + fprintf (stderr, "mpz_tstbit failed (after mpz_combit):\n"); + dump ("res", a); + fprintf (stderr, "b: %lu\n", b); + abort (); + } + } + mpz_clear (a); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-cmp_d.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-cmp_d.c new file mode 100644 index 0000000..09ca810 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-cmp_d.c @@ -0,0 +1,283 @@ +/* Test mpz_cmp_d and mpz_cmpabs_d. + +Copyright 2001-2003, 2005, 2013 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <math.h> + +#include "testutils.h" + +/* FIXME: Not sure if the tests here are exhaustive. Ought to try to get + each possible exit from mpz_cmp_d (and mpz_cmpabs_d) exercised. */ + + +#define SGN(n) ((n) > 0 ? 1 : (n) < 0 ? -1 : 0) + + +void +check_one (const char *name, mpz_srcptr x, double y, int cmp, int cmpabs) +{ + int got; + + got = mpz_cmp_d (x, y); + if (SGN(got) != cmp) + { + unsigned i; + printf ("mpz_cmp_d wrong (from %s)\n", name); + printf (" got %d\n", got); + printf (" want %d\n", cmp); + fail: + printf (" x="); + mpz_out_str (stdout, 10, x); + printf ("\n y %g\n", y); + printf (" x=0x"); + mpz_out_str (stdout, -16, x); + printf ("\n y %g\n", y); + printf (" y"); + for (i = 0; i < sizeof(y); i++) + printf (" %02X", (unsigned) ((unsigned char *) &y)[i]); + printf ("\n"); + abort (); + } + + got = mpz_cmpabs_d (x, y); + if (SGN(got) != cmpabs) + { + printf ("mpz_cmpabs_d wrong\n"); + printf (" got %d\n", got); + printf (" want %d\n", cmpabs); + goto fail; + } +} + +void +check_data (void) +{ + static const struct { + const char *x; + double y; + int cmp, cmpabs; + + } data[] = { + + { "0", 0.0, 0, 0 }, + + { "1", 0.0, 1, 1 }, + { "-1", 0.0, -1, 1 }, + + { "1", 0.5, 1, 1 }, + { "-1", -0.5, -1, 1 }, + + { "0", 1.0, -1, -1 }, + { "0", -1.0, 1, -1 }, + + { "0x1000000000000000000000000000000000000000000000000", 1.0, 1, 1 }, + { "-0x1000000000000000000000000000000000000000000000000", 1.0, -1, 1 }, + + { "0", 1e100, -1, -1 }, + { "0", -1e100, 1, -1 }, + + { "2", 1.5, 1, 1 }, + { "2", -1.5, 1, 1 }, + { "-2", 1.5, -1, 1 }, + { "-2", -1.5, -1, 1 }, + }; + + mpz_t x; + unsigned i; + + mpz_init (x); + + for (i = 0; i < numberof (data); i++) + { + mpz_set_str_or_abort (x, data[i].x, 0); + check_one ("check_data", x, data[i].y, data[i].cmp, data[i].cmpabs); + } + + mpz_clear (x); +} + + +/* Equality of integers with up to 53 bits */ +void +check_onebits (void) +{ + mpz_t x, x2; + double y; + int i; + + mpz_init_set_ui (x, 0L); + mpz_init (x2); + + for (i = 0; i < 512; i++) + { + mpz_mul_2exp (x, x, 1); + mpz_add_ui (x, x, 1L); + + y = mpz_get_d (x); + mpz_set_d (x2, y); + + /* stop if any truncation is occurring */ + if (mpz_cmp (x, x2) != 0) + break; + + check_one ("check_onebits", x, y, 0, 0); + check_one ("check_onebits", x, -y, 1, 0); + mpz_neg (x, x); + check_one ("check_onebits", x, y, -1, 0); + check_one ("check_onebits", x, -y, 0, 0); + mpz_neg (x, x); + } + + mpz_clear (x); + mpz_clear (x2); +} + + +/* With the mpz differing by 1, in a limb position possibly below the double */ +void +check_low_z_one (void) +{ + mpz_t x; + double y; + unsigned long i; + + mpz_init (x); + + /* FIXME: It'd be better to base this on the float format. */ +#if defined (__vax) || defined (__vax__) +#define LIM 127 /* vax fp numbers have limited range */ +#else +#define LIM 512 +#endif + + for (i = 1; i < LIM; i++) + { + mpz_set_ui (x, 1L); + mpz_mul_2exp (x, x, i); + y = mpz_get_d (x); + + check_one ("check_low_z_one", x, y, 0, 0); + check_one ("check_low_z_one", x, -y, 1, 0); + mpz_neg (x, x); + check_one ("check_low_z_one", x, y, -1, 0); + check_one ("check_low_z_one", x, -y, 0, 0); + mpz_neg (x, x); + + mpz_sub_ui (x, x, 1); + + check_one ("check_low_z_one", x, y, -1, -1); + check_one ("check_low_z_one", x, -y, 1, -1); + mpz_neg (x, x); + check_one ("check_low_z_one", x, y, -1, -1); + check_one ("check_low_z_one", x, -y, 1, -1); + mpz_neg (x, x); + + mpz_add_ui (x, x, 2); + + check_one ("check_low_z_one", x, y, 1, 1); + check_one ("check_low_z_one", x, -y, 1, 1); + mpz_neg (x, x); + check_one ("check_low_z_one", x, y, -1, 1); + check_one ("check_low_z_one", x, -y, -1, 1); + mpz_neg (x, x); + } + + mpz_clear (x); +} + +/* Comparing 1 and 1+2^-n. "y" is volatile to make gcc store and fetch it, + which forces it to a 64-bit double, whereas on x86 it would otherwise + remain on the float stack as an 80-bit long double. */ +void +check_one_2exp (void) +{ + double e; + mpz_t x; + volatile double y; + int i; + + mpz_init (x); + + e = 1.0; + for (i = 0; i < 128; i++) + { + e /= 2.0; + y = 1.0 + e; + if (y == 1.0) + break; + + mpz_set_ui (x, 1L); + check_one ("check_one_2exp", x, y, -1, -1); + check_one ("check_one_2exp", x, -y, 1, -1); + + mpz_set_si (x, -1L); + check_one ("check_one_2exp", x, y, -1, -1); + check_one ("check_one_2exp", x, -y, 1, -1); + } + + mpz_clear (x); +} + +void +check_infinity (void) +{ + mpz_t x; + double y = HUGE_VAL; + if (y != 2*y) + return; + + mpz_init (x); + + /* 0 cmp inf */ + mpz_set_ui (x, 0L); + check_one ("check_infinity", x, y, -1, -1); + check_one ("check_infinity", x, -y, 1, -1); + + /* 123 cmp inf */ + mpz_set_ui (x, 123L); + check_one ("check_infinity", x, y, -1, -1); + check_one ("check_infinity", x, -y, 1, -1); + + /* -123 cmp inf */ + mpz_set_si (x, -123L); + check_one ("check_infinity", x, y, -1, -1); + check_one ("check_infinity", x, -y, 1, -1); + + /* 2^5000 cmp inf */ + mpz_set_ui (x, 1L); + mpz_mul_2exp (x, x, 5000L); + check_one ("check_infinity", x, y, -1, -1); + check_one ("check_infinity", x, -y, 1, -1); + + /* -2^5000 cmp inf */ + mpz_neg (x, x); + check_one ("check_infinity", x, y, -1, -1); + check_one ("check_infinity", x, -y, 1, -1); + + mpz_clear (x); +} + +void +testmain (int argc, char *argv[]) +{ + check_data (); + check_onebits (); + check_low_z_one (); + check_one_2exp (); + check_infinity (); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-comb.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-comb.c new file mode 100644 index 0000000..652bfcb --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-comb.c @@ -0,0 +1,175 @@ +/* Exercise mpz_fac_ui and mpz_bin_uiui. + +Copyright 2000-2002, 2012, 2013, 2017-2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdio.h> +#include <stdlib.h> + +#include "testutils.h" + +/* Usage: t-fac_ui [x|num] + + With no arguments testing goes up to the initial value of "limit" below. + With a number argument tests are carried that far, or with a literal "x" + tests are continued without limit (this being meant only for development + purposes). */ + +void +try_mpz_bin_uiui (mpz_srcptr want, unsigned long n, unsigned long k) +{ + mpz_t got; + + mpz_init (got); + mpz_bin_uiui (got, n, k); + if (mpz_cmp (got, want) != 0) + { + printf ("mpz_bin_uiui wrong\n"); + printf (" n=%lu\n", n); + printf (" k=%lu\n", k); + printf (" got="); mpz_out_str (stdout, 10, got); printf ("\n"); + printf (" want="); mpz_out_str (stdout, 10, want); printf ("\n"); + abort(); + } + mpz_clear (got); +} + +/* Test all bin(n,k) cases, with 0 <= k <= n + 1 <= count. */ +void +bin_smallexaustive (unsigned int count) +{ + mpz_t want; + unsigned long n, k; + + mpz_init (want); + + for (n = 0; n < count; n++) + { + mpz_set_ui (want, 1); + for (k = 0; k <= n; k++) + { + try_mpz_bin_uiui (want, n, k); + mpz_mul_ui (want, want, n - k); + mpz_fdiv_q_ui (want, want, k + 1); + } + try_mpz_bin_uiui (want, n, k); + } + + mpz_clear (want); +} + +/* Test all fac(n) cases, with 0 <= n <= limit. */ +void +fac_smallexaustive (unsigned int limit) +{ + mpz_t f, r; + unsigned long n; + mpz_init_set_si (f, 1); /* 0! = 1 */ + mpz_init (r); + + for (n = 0; n < limit; n++) + { + mpz_fac_ui (r, n); + + if (mpz_cmp (f, r) != 0) + { + printf ("mpz_fac_ui(%lu) wrong\n", n); + printf (" got "); mpz_out_str (stdout, 10, r); printf("\n"); + printf (" want "); mpz_out_str (stdout, 10, f); printf("\n"); + abort (); + } + + mpz_mul_ui (f, f, n+1); /* (n+1)! = n! * (n+1) */ + } + + mpz_clear (f); + mpz_clear (r); +} + +void checkWilson (mpz_t f, unsigned long n) +{ + unsigned long m, a; + + mpz_2fac_ui (f, 2 * n - 1); + + a = mpz_fdiv_q_ui (f, f, n); + m = mpz_fdiv_ui (f, n); + if ((m != n - 1) || (a != 0)) + { + printf ("mpz_2fac_ui(%lu) wrong\n", 2 * n - 1); + printf (" Wilson's theorem not verified: got (%lu, %lu), expected (0, %lu).\n", a, m, n - 1); + abort (); + } + + mpz_fac_ui (f, n - 1); + m = mpz_fdiv_ui (f, n); + if ( m != n - 1) + { + printf ("mpz_fac_ui(%lu) wrong\n", n - 1); + printf (" Wilson's theorem not verified: got %lu, expected %lu.\n",m ,n - 1); + abort (); + } +} + +void +checkprimes (unsigned long p1, unsigned long p2, unsigned long p3) +{ + mpz_t b, f; + + if (p1 - 1 != p2 - 1 + p3 - 1) + { + printf ("checkprimes(%lu, %lu, %lu) wrong\n", p1, p2, p3); + printf (" %lu - 1 != %lu - 1 + %lu - 1 \n", p1, p2, p3); + abort (); + } + + mpz_init (b); + mpz_init (f); + + checkWilson (b, p1); /* b = (p1-1)! */ + checkWilson (f, p2); /* f = (p2-1)! */ + mpz_divexact (b, b, f); + checkWilson (f, p3); /* f = (p3-1)! */ + mpz_divexact (b, b, f); /* b = (p1-1)!/((p2-1)!(p3-1)!) */ + mpz_bin_uiui (f, p1 - 1, p2 - 1); + if (mpz_cmp (f, b) != 0) + { + printf ("checkprimes(%lu, %lu, %lu) wrong\n", p1, p2, p3); + printf (" got "); mpz_out_str (stdout, 10, b); printf("\n"); + printf (" want "); mpz_out_str (stdout, 10, f); printf("\n"); + abort (); + } + + mpz_clear (b); + mpz_clear (f); + +} + +void +testmain (int argc, char *argv[]) +{ + unsigned long limit = 128; + + if (argc > 1 && argv[1][0] == 'x') + limit = ~ limit; + else if (argc > 1) + limit = atoi (argv[1]); + + checkprimes(1009, 733, 277); + fac_smallexaustive (limit); + bin_smallexaustive (limit); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-cong.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-cong.c new file mode 100644 index 0000000..92b6930 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-cong.c @@ -0,0 +1,212 @@ +/* test mpz_congruent_p + +Copyright 2001, 2002, 2012, 2014 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include "testutils.h" + +#define MPZ_SRCPTR_SWAP(x, y) \ + do { \ + mpz_srcptr __mpz_srcptr_swap__tmp = (x); \ + (x) = (y); \ + (y) = __mpz_srcptr_swap__tmp; \ + } while (0) + +void +check_one (mpz_srcptr a, mpz_srcptr c, mpz_srcptr d, int want) +{ + int got; + int swap; + + for (swap = 0; swap <= 1; swap++) + { + got = (mpz_congruent_p (a, c, d) != 0); + if (want != got) + { + printf ("mpz_congruent_p wrong\n"); + printf (" expected %d got %d\n", want, got); + dump (" a", a); + dump (" c", c); + dump (" d", d); + abort (); + } + +#if 0 + if (mpz_fits_ulong_p (c) && mpz_fits_ulong_p (d)) + { + unsigned long uc = mpz_get_ui (c); + unsigned long ud = mpz_get_ui (d); + got = (mpz_congruent_ui_p (a, uc, ud) != 0); + if (want != got) + { + printf ("mpz_congruent_ui_p wrong\n"); + printf (" expected %d got %d\n", want, got); + dump (" a", a); + printf (" c=%lu\n", uc); + printf (" d=%lu\n", ud); + abort (); + } + } +#endif + MPZ_SRCPTR_SWAP (a, c); + } +} + + +void +check_data (void) +{ + static const struct { + const char *a; + const char *c; + const char *d; + int want; + + } data[] = { + + /* strict equality mod 0 */ + { "0", "0", "0", 1 }, + { "11", "11", "0", 1 }, + { "3", "11", "0", 0 }, + + /* anything congruent mod 1 */ + { "0", "0", "1", 1 }, + { "1", "0", "1", 1 }, + { "0", "1", "1", 1 }, + { "123", "456", "1", 1 }, + { "0x123456789123456789", "0x987654321987654321", "1", 1 }, + + /* csize==1, dsize==2 changing to 1 after stripping 2s */ + { "0x3333333333333333", "0x33333333", + "0x180000000", 1 }, + { "0x33333333333333333333333333333333", "0x3333333333333333", + "0x18000000000000000", 1 }, + + /* another dsize==2 becoming 1, with opposite signs this time */ + { "0x444444441", + "-0x22222221F", + "0x333333330", 1 }, + { "0x44444444444444441", + "-0x2222222222222221F", + "0x33333333333333330", 1 }, + }; + + mpz_t a, c, d; + unsigned i; + + mpz_init (a); + mpz_init (c); + mpz_init (d); + + for (i = 0; i < numberof (data); i++) + { + mpz_set_str_or_abort (a, data[i].a, 0); + mpz_set_str_or_abort (c, data[i].c, 0); + mpz_set_str_or_abort (d, data[i].d, 0); + check_one (a, c, d, data[i].want); + } + + mpz_clear (a); + mpz_clear (c); + mpz_clear (d); +} + + +void +check_random (int argc, char *argv[]) +{ + mpz_t a, c, d, ra, rc; + int i; + int want; + int reps = 10000; + mpz_t bs; + unsigned long size_range, size; + + if (argc >= 2) + reps = atoi (argv[1]); + + mpz_init (bs); + + mpz_init (a); + mpz_init (c); + mpz_init (d); + mpz_init (ra); + mpz_init (rc); + + for (i = 0; i < reps; i++) + { + mini_urandomb (bs, 32); + size_range = mpz_get_ui (bs) % 13 + 1; /* 0..8192 bit operands */ + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (a, size); + + mini_urandomb (bs, 32); + size_range = mpz_get_ui (bs) % 13 + 1; /* 0..8192 bit operands */ + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (c, size); + + do + { + mini_urandomb (bs, 32); + size_range = mpz_get_ui (bs) % 13 + 1; /* 0..8192 bit operands */ + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (d, size); + } + while (mpz_sgn(d) == 0); + + mini_urandomb (bs, 3); + if (mpz_tstbit (bs, 0)) + mpz_neg (a, a); + if (mpz_tstbit (bs, 1)) + mpz_neg (c, c); + if (mpz_tstbit (bs, 2)) + mpz_neg (d, d); + + mpz_fdiv_r (ra, a, d); + mpz_fdiv_r (rc, c, d); + + want = (mpz_cmp (ra, rc) == 0); + check_one (a, c, d, want); + + mpz_sub (ra, ra, rc); + mpz_sub (a, a, ra); + check_one (a, c, d, 1); + + } + + mpz_clear (bs); + + mpz_clear (a); + mpz_clear (c); + mpz_clear (d); + mpz_clear (ra); + mpz_clear (rc); +} + + +void +testmain (int argc, char *argv[]) +{ + check_data (); + check_random (argc, argv); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-div.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-div.c new file mode 100644 index 0000000..be2f6b1 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-div.c @@ -0,0 +1,258 @@ +/* + +Copyright 2012, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +typedef void div_qr_func (mpz_t, mpz_t, const mpz_t, const mpz_t); +typedef unsigned long div_qr_ui_func (mpz_t, mpz_t, const mpz_t, unsigned long); +typedef void div_func (mpz_t, const mpz_t, const mpz_t); +typedef unsigned long div_x_ui_func (mpz_t, const mpz_t, unsigned long); +typedef unsigned long div_ui_func (const mpz_t, unsigned long); + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, q, r, rq, rr; + int div_p; + + mpz_init (a); + mpz_init (b); + mpz_init (r); + mpz_init (q); + mpz_init (rr); + mpz_init (rq); + + for (i = 0; i < COUNT; i++) + { + unsigned j; + for (j = 0; j < 3; j++) + { + static const enum hex_random_op ops[3] = { OP_CDIV, OP_FDIV, OP_TDIV }; + static const char name[3] = { 'c', 'f', 't'}; + static div_qr_func * const div_qr [3] = + { + mpz_cdiv_qr, mpz_fdiv_qr, mpz_tdiv_qr + }; + static div_qr_ui_func * const div_qr_ui[3] = + { + mpz_cdiv_qr_ui, mpz_fdiv_qr_ui, mpz_tdiv_qr_ui + }; + static div_func * const div_q [3] = + { + mpz_cdiv_q, mpz_fdiv_q, mpz_tdiv_q + }; + static div_x_ui_func * const div_q_ui[3] = + { + mpz_cdiv_q_ui, mpz_fdiv_q_ui, mpz_tdiv_q_ui + }; + static div_func * const div_r [3] = + { + mpz_cdiv_r, mpz_fdiv_r, mpz_tdiv_r + }; + static div_x_ui_func * const div_r_ui[3] = + { + mpz_cdiv_r_ui, mpz_fdiv_r_ui, mpz_tdiv_r_ui + }; + static div_ui_func * const div_ui[3] = + { + mpz_cdiv_ui, mpz_fdiv_ui, mpz_tdiv_ui + }; + + mini_random_op4 (ops[j], MAXBITS, a, b, rq, rr); + div_qr[j] (q, r, a, b); + if (mpz_cmp (r, rr) || mpz_cmp (q, rq)) + { + fprintf (stderr, "mpz_%cdiv_qr failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + dump ("rref", rr); + dump ("q ", q); + dump ("qref", rq); + abort (); + } + mpz_set_si (q, -5); + div_q[j] (q, a, b); + if (mpz_cmp (q, rq)) + { + fprintf (stderr, "mpz_%cdiv_q failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + dump ("q ", q); + dump ("qref", rq); + abort (); + } + mpz_set_ui (r, ~5); + div_r[j] (r, a, b); + if (mpz_cmp (r, rr)) + { + fprintf (stderr, "mpz_%cdiv_r failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + dump ("rref", rr); + abort (); + } + + if (j == 0) /* do this once, not for all roundings */ + { + div_p = mpz_divisible_p (a, b); + if ((mpz_sgn (r) == 0) ^ (div_p != 0)) + { + fprintf (stderr, "mpz_divisible_p failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + abort (); + } + } + + mpz_set_si (r, -6); + if (j == 0 && mpz_sgn (b) < 0) /* ceil, negative divisor */ + { + mpz_mod (r, a, b); + if (mpz_cmp (r, rr)) + { + fprintf (stderr, "mpz_mod failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + dump ("rref", rr); + abort (); + } + } + + if (j == 1 && mpz_sgn (b) > 0) /* floor, positive divisor */ + { + mpz_mod (r, a, b); + if (mpz_cmp (r, rr)) + { + fprintf (stderr, "mpz_mod failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + dump ("rref", rr); + abort (); + } + } + + if (mpz_fits_ulong_p (b)) + { + unsigned long rl; + + mpz_set_si (r, -7); + mpz_set_ui (q, ~7); + rl = div_qr_ui[j] (q, r, a, mpz_get_ui (b)); + if (rl != mpz_get_ui (rr) + || mpz_cmp (r, rr) || mpz_cmp (q, rq)) + { + fprintf (stderr, "mpz_%cdiv_qr_ui failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + fprintf(stderr, "rl = %lx\n", rl); + dump ("r ", r); + dump ("rref", rr); + dump ("q ", q); + dump ("qref", rq); + abort (); + } + + mpz_set_si (q, 3); + rl = div_q_ui[j] (q, a, mpz_get_ui (b)); + if (rl != mpz_get_ui (rr) || mpz_cmp (q, rq)) + { + fprintf (stderr, "mpz_%cdiv_q_ui failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + fprintf(stderr, "rl = %lx\n", rl); + dump ("rref", rr); + dump ("q ", q); + dump ("qref", rq); + abort (); + } + + mpz_set_ui (r, 7); + rl = div_r_ui[j] (r, a, mpz_get_ui (b)); + if (rl != mpz_get_ui (rr) || mpz_cmp (r, rr)) + { + fprintf (stderr, "mpz_%cdiv_r_ui failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + fprintf(stderr, "rl = %lx\n", rl); + dump ("r ", r); + dump ("rref", rr); + abort (); + } + + rl = div_ui[j] (a, mpz_get_ui (b)); + if (rl != mpz_get_ui (rr)) + { + fprintf (stderr, "mpz_%cdiv_ui failed:\n", name[j]); + dump ("a", a); + dump ("b", b); + fprintf(stderr, "rl = %lx\n", rl); + dump ("rref", rr); + abort (); + } + + if (j == 0) /* do this once, not for all roundings */ + { + div_p = mpz_divisible_ui_p (a, mpz_get_ui (b)); + if ((mpz_sgn (r) == 0) ^ (div_p != 0)) + { + fprintf (stderr, "mpz_divisible_ui_p failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + abort (); + } + } + + if (j == 1) /* floor */ + { + mpz_set_si (r, -2); + mpz_mod_ui (r, a, mpz_get_ui (b)); + if (mpz_cmp (r, rr)) + { + fprintf (stderr, "mpz_mod failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r ", r); + dump ("rref", rr); + abort (); + } + } + } + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (r); + mpz_clear (q); + mpz_clear (rr); + mpz_clear (rq); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-div_2exp.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-div_2exp.c new file mode 100644 index 0000000..53d3f2b --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-div_2exp.c @@ -0,0 +1,82 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +typedef void div_func (mpz_t, const mpz_t, mp_bitcnt_t); + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, res, ref; + mp_bitcnt_t b; + + mpz_init (a); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + unsigned j; + for (j = 0; j < 6; j++) + { + static const enum hex_random_op ops[6] = + { + OP_CDIV_Q_2, OP_CDIV_R_2, + OP_FDIV_Q_2, OP_FDIV_R_2, + OP_TDIV_Q_2, OP_TDIV_R_2 + }; + static const char *name[6] = + { + "cdiv_q", "cdiv_r", + "fdiv_q", "fdiv_r", + "tdiv_q", "tdiv_r" + }; + static div_func * const div [6] = + { + mpz_cdiv_q_2exp, mpz_cdiv_r_2exp, + mpz_fdiv_q_2exp, mpz_fdiv_r_2exp, + mpz_tdiv_q_2exp, mpz_tdiv_r_2exp + }; + + mini_random_bit_op (ops[j], MAXBITS, a, &b, ref); + div[j] (res, a, b); + if (mpz_cmp (ref, res)) + { + fprintf (stderr, "mpz_%s_2exp failed:\n", name[j]); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + } + } + mpz_clear (a); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-double.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-double.c new file mode 100644 index 0000000..48774b3 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-double.c @@ -0,0 +1,232 @@ +/* + +Copyright 2012, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <math.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> +#include <float.h> + +#include "testutils.h" + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) + +mp_bitcnt_t +mpz_mantissasizeinbits (const mpz_t z) +{ + return ! mpz_cmp_ui (z, 0) ? 0 : + mpz_sizeinbase (z, 2) - mpz_scan1 (z, 0); +} + +#if defined(DBL_MANT_DIG) && FLT_RADIX == 2 +int +mpz_get_d_exact_p (const mpz_t z) +{ + return mpz_mantissasizeinbits (z) <= DBL_MANT_DIG; +} +#define HAVE_EXACT_P 1 +#endif + +#define COUNT 10000 + +void +test_matissa (void) +{ + mpz_t x, y; + int i, c; + + mpz_init (x); + mpz_init (y); + + mini_urandomb (y, 4); + c = i = mpz_get_ui (y); + + do { + double d; + int cmp; + + mpz_setbit (x, c); + d = mpz_get_d (x); + mpz_set_d (y, d); + if (mpz_cmp_d (y, d) != 0) + { + fprintf (stderr, "mpz_cmp_d (y, d) failed:\n" + "d = %.20g\n" + "i = %i\n" + "c = %i\n", + d, i, c); + abort (); + } + + cmp = mpz_cmp (x, y); + +#if defined(HAVE_EXACT_P) + if ((mpz_get_d_exact_p (x) != 0) != (cmp == 0)) + { + fprintf (stderr, "Not all bits converted:\n" + "d = %.20g\n" + "i = %i\n" + "c = %i\n", + d, i, c); + abort (); + } +#endif + + if (cmp < 0) + { + fprintf (stderr, "mpz_get_d failed:\n" + "d = %.20g\n" + "i = %i\n" + "c = %i\n", + d, i, c); + abort (); + } + else if (cmp > 0) + { + if (mpz_cmp_d (x, d) <= 0) + { + fprintf (stderr, "mpz_cmp_d (x, d) failed:\n" + "d = %.20g\n" + "i = %i\n" + "c = %i\n", + d, i, c); + abort (); + } + break; + } + ++c; + } while (1); + + mpz_clear (x); + mpz_clear (y); +} + +#ifndef M_PI +#define M_PI 3.141592653589793238462643383279502884 +#endif + +static const struct +{ + double d; + const char *s; +} values[] = { + { 0.0, "0" }, + { 0.3, "0" }, + { -0.3, "0" }, + { M_PI, "3" }, + { M_PI*1e15, "b29430a256d21" }, + { -M_PI*1e15, "-b29430a256d21" }, + /* 17 * 2^{200} = + 27317946752402834684213355569799764242877450894307478200123392 */ + {0.2731794675240283468421335556979976424288e62, + "1100000000000000000000000000000000000000000000000000" }, + { 0.0, NULL } +}; + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t x; + + for (i = 0; values[i].s; i++) + { + char *s; + mpz_init_set_d (x, values[i].d); + s = mpz_get_str (NULL, 16, x); + if (strcmp (s, values[i].s) != 0) + { + fprintf (stderr, "mpz_set_d failed:\n" + "d = %.20g\n" + "s = %s\n" + "r = %s\n", + values[i].d, s, values[i].s); + abort (); + } + testfree (s, strlen(s) + 1); + mpz_clear (x); + } + + mpz_init (x); + + for (i = 0; i < COUNT; i++) + { + /* Use volatile, to avoid extended precision in floating point + registers, e.g., on m68k and 80387. */ + volatile double d, f; + unsigned long m; + int e; + + mini_rrandomb (x, GMP_LIMB_BITS); + m = mpz_get_ui (x); + mini_urandomb (x, 8); + e = mpz_get_ui (x) - 100; + + d = ldexp ((double) m, e); + mpz_set_d (x, d); + f = mpz_get_d (x); + if (f != floor (d)) + { + fprintf (stderr, "mpz_set_d/mpz_get_d failed:\n"); + goto dumperror; + } + if ((f == d) ? (mpz_cmp_d (x, d) != 0) : (mpz_cmp_d (x, d) >= 0)) + { + fprintf (stderr, "mpz_cmp_d (x, d) failed:\n"); + goto dumperror; + } + f = d + 1.0; + if (f > d && ! (mpz_cmp_d (x, f) < 0)) + { + fprintf (stderr, "mpz_cmp_d (x, f) failed:\n"); + goto dumperror; + } + + d = - d; + + mpz_set_d (x, d); + f = mpz_get_d (x); + if (f != ceil (d)) + { + fprintf (stderr, "mpz_set_d/mpz_get_d failed:\n"); + dumperror: + dump ("x", x); + fprintf (stderr, "m = %lx, e = %i\n", m, e); + fprintf (stderr, "d = %.15g\n", d); + fprintf (stderr, "f = %.15g\n", f); + fprintf (stderr, "f - d = %.5g\n", f - d); + abort (); + } + if ((f == d) ? (mpz_cmp_d (x, d) != 0) : (mpz_cmp_d (x, d) <= 0)) + { + fprintf (stderr, "mpz_cmp_d (x, d) failed:\n"); + goto dumperror; + } + f = d - 1.0; + if (f < d && ! (mpz_cmp_d (x, f) > 0)) + { + fprintf (stderr, "mpz_cmp_d (x, f) failed:\n"); + goto dumperror; + } + } + + mpz_clear (x); + test_matissa(); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-gcd.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-gcd.c new file mode 100644 index 0000000..64f90f4 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-gcd.c @@ -0,0 +1,178 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +/* Called when g is supposed to be gcd(a,b), and g = s a + t b. */ +static int +gcdext_valid_p (const mpz_t a, const mpz_t b, + const mpz_t g, const mpz_t s, const mpz_t t) +{ + mpz_t ta, tb, r; + + /* It's not clear that gcd(0,0) is well defined, but we allow it and + require that gcd(0,0) = 0. */ + if (mpz_sgn (g) < 0) + return 0; + + if (mpz_sgn (a) == 0) + { + /* Must have g == abs (b). Any value for s is in some sense "correct", + but it makes sense to require that s == 0, t = sgn (b)*/ + return mpz_cmpabs (g, b) == 0 + && mpz_sgn (s) == 0 && mpz_cmp_si (t, mpz_sgn (b)) == 0; + } + else if (mpz_sgn (b) == 0) + { + /* Must have g == abs (a), s == sign (a), t = 0 */ + return mpz_cmpabs (g, a) == 0 + && mpz_cmp_si (s, mpz_sgn (a)) == 0 && mpz_sgn (t) == 0; + } + + if (mpz_sgn (g) <= 0) + return 0; + + mpz_init (ta); + mpz_init (tb); + mpz_init (r); + + mpz_mul (ta, s, a); + mpz_mul (tb, t, b); + mpz_add (ta, ta, tb); + + if (mpz_cmp (ta, g) != 0) + { + fail: + mpz_clear (ta); + mpz_clear (tb); + mpz_clear (r); + return 0; + } + mpz_tdiv_qr (ta, r, a, g); + if (mpz_sgn (r) != 0) + goto fail; + + mpz_tdiv_qr (tb, r, b, g); + if (mpz_sgn (r) != 0) + goto fail; + + /* Require that 2 |s| < |b/g|, or |s| == 1. */ + if (mpz_cmpabs_ui (s, 1) > 0) + { + mpz_mul_2exp (r, s, 1); + if (mpz_cmpabs (r, tb) > 0) + goto fail; + } + + /* Require that 2 |t| < |a/g| or |t| == 1*/ + if (mpz_cmpabs_ui (t, 1) > 0) + { + mpz_mul_2exp (r, t, 1); + if (mpz_cmpabs (r, ta) > 0) + return 0; + } + + mpz_clear (ta); + mpz_clear (tb); + mpz_clear (r); + + return 1; +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, g, s, t; + + mpz_init (a); + mpz_init (b); + mpz_init (g); + mpz_init (s); + mpz_init (t); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_GCD, MAXBITS, a, b, s); + mpz_gcd (g, a, b); + if (mpz_cmp (g, s)) + { + fprintf (stderr, "mpz_gcd failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", g); + dump ("ref", s); + abort (); + } + } + + for (i = 0; i < COUNT; i++) + { + unsigned flags; + mini_urandomb (a, 32); + flags = mpz_get_ui (a); + mini_rrandomb (a, MAXBITS); + mini_rrandomb (b, MAXBITS); + + if (flags % 37 == 0) + mpz_mul (a, a, b); + if (flags % 37 == 1) + mpz_mul (b, a, b); + + if (flags & 1) + mpz_neg (a, a); + if (flags & 2) + mpz_neg (b, b); + + mpz_gcdext (g, s, t, a, b); + if (!gcdext_valid_p (a, b, g, s, t)) + { + fprintf (stderr, "mpz_gcdext failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("g", g); + dump ("s", s); + dump ("t", t); + abort (); + } + + mpz_gcd (s, a, b); + if (mpz_cmp (g, s)) + { + fprintf (stderr, "mpz_gcd failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", g); + dump ("ref", s); + abort (); + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (g); + mpz_clear (s); + mpz_clear (t); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-import.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-import.c new file mode 100644 index 0000000..66c9d5e --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-import.c @@ -0,0 +1,99 @@ +/* + +Copyright 2013 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAX_WORDS 20 +#define MAX_WORD_SIZE 10 + +static void +dump_bytes (const char *label, const unsigned char *s, size_t n) +{ + size_t i; + fprintf (stderr, "%s:", label); + for (i = 0; i < n; i++) + { + if (i && (i % 16) == 0) + fprintf (stderr, "\n"); + fprintf (stderr, " %02x", s[i]); + } + fprintf (stderr, "\n"); +} + +/* Tests both mpz_import and mpz_export. */ +void +testmain (int argc, char **argv) +{ + unsigned char input[MAX_WORDS * MAX_WORD_SIZE]; + unsigned char output[MAX_WORDS * MAX_WORD_SIZE + 2]; + size_t count, in_count, out_count, size; + int endian, order; + + mpz_t a, res; + + mpz_init (a); + mpz_init (res); + + for (size = 0; size <= MAX_WORD_SIZE; size++) + for (count = 0; count <= MAX_WORDS; count++) + for (endian = -1; endian <= 1; endian++) + for (order = -1; order <= 1; order += 2) + { + mini_rrandomb_export (a, input, &in_count, + order, size, endian, size*count * 8); + mpz_import (res, in_count, order, size, endian, 0, input); + if (mpz_cmp (a, res)) + { + fprintf (stderr, "mpz_import failed:\n" + "in_count %lu, out_count %lu, endian = %d, order = %d\n", + (unsigned long) in_count, (unsigned long) out_count, endian, order); + dump ("a", a); + dump ("res", res); + abort (); + } + output[0] = 17; + output[1+in_count*size] = 17; + + mpz_export (output+1, &out_count, order, size, endian, 0, a); + if (out_count != in_count + || memcmp (output+1, input, in_count * size) + || output[0] != 17 + || output[1+in_count*size] != 17) + { + fprintf (stderr, "mpz_export failed:\n" + "in_count %lu, out_count %lu, endian = %d, order = %d\n", + (unsigned long) in_count, (unsigned long) out_count, endian, order); + dump_bytes ("input", input, in_count * size); + dump_bytes ("output", output+1, out_count * size); + if (output[0] != 17) + fprintf (stderr, "Overwrite at -1, value %02x\n", output[0]); + if (output[1+in_count*size] != 17) + fprintf (stderr, "Overwrite at %lu, value %02x\n", + (unsigned long) (in_count*size), output[1+in_count*size]); + + abort (); + } + } + mpz_clear (a); + mpz_clear (res); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-invert.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-invert.c new file mode 100644 index 0000000..02e1731 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-invert.c @@ -0,0 +1,141 @@ +/* + +Copyright 2012, 2016 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) + +#define COUNT 10000 + +static void +test_2by1(const mpz_t u) +{ + mpz_t m, p, t; + mp_limb_t tl; + + mpz_init (p); + + assert (mpz_size (u) == 1); + + tl = mpn_invert_limb (u->_mp_d[0]); + mpz_roinit_n (t, &tl, 1); + mpz_init_set (m, t); + mpz_setbit (m, GMP_LIMB_BITS); + + mpz_mul (p, m, u); + + mpz_init (t); + mpz_setbit (t, 2* GMP_LIMB_BITS); + mpz_sub (t, t, p); + + /* Should have 0 < B^2 - m u <= u */ + if (mpz_sgn (t) <= 0 || mpz_cmp (t, u) > 0) + { + fprintf (stderr, "mpn_invert_limb failed:\n"); + dump ("u", u); + dump ("m", m); + dump ("p", p); + dump ("t", t); + abort (); + } + mpz_clear (m); + mpz_clear (p); + mpz_clear (t); +} + +static void +test_3by2(const mpz_t u) +{ + mpz_t m, p, t; + mp_limb_t tl; + + mpz_init (p); + + assert (mpz_size (u) == 2); + + tl = mpn_invert_3by2 (u->_mp_d[1], u->_mp_d[0]); + mpz_roinit_n (t, &tl, 1); + mpz_init_set (m, t); + + mpz_setbit (m, GMP_LIMB_BITS); + + mpz_mul (p, m, u); + + mpz_init (t); + mpz_setbit (t, 3 * GMP_LIMB_BITS); + mpz_sub (t, t, p); + + /* Should have 0 < B^3 - m u <= u */ + if (mpz_sgn (t) <= 0 || mpz_cmp (t, u) > 0) + { + fprintf (stderr, "mpn_invert_3by2 failed:\n"); + dump ("u", u); + dump ("m", m); + dump ("p", p); + dump ("t", t); + abort (); + } + mpz_clear (m); + mpz_clear (p); + mpz_clear (t); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t u, m, p, t; + + mpz_init (u); + mpz_init (m); + mpz_init (p); + mpz_init (t); + + /* These values trigger 32-bit overflow of ql in mpn_invert_3by2. */ + if (GMP_LIMB_BITS == 64) + { + mpz_set_str (u, "80007fff3ffe0000", 16); + test_2by1 (u); + mpz_set_str (u, "80007fff3ffe000000000000000003ff", 16); + test_3by2 (u); + } + + for (i = 0; i < COUNT; i++) + { + mini_urandomb (u, GMP_LIMB_BITS); + mpz_setbit (u, GMP_LIMB_BITS -1); + + test_2by1 (u); + } + + for (i = 0; i < COUNT; i++) + { + mini_urandomb (u, 2*GMP_LIMB_BITS); + mpz_setbit (u, 2*GMP_LIMB_BITS -1); + + test_3by2 (u); + } + + mpz_clear (u); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-lcm.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-lcm.c new file mode 100644 index 0000000..f21a39a --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-lcm.c @@ -0,0 +1,73 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, g, s; + + mpz_init (a); + mpz_init (b); + mpz_init (g); + mpz_init (s); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_LCM, MAXBITS, a, b, s); + mpz_lcm (g, a, b); + if (mpz_cmp (g, s)) + { + fprintf (stderr, "mpz_lcm failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", g); + dump ("ref", s); + abort (); + } + if (mpz_fits_ulong_p (b)) + { + mpz_set_si (g, 0); + mpz_lcm_ui (g, a, mpz_get_ui (b)); + if (mpz_cmp (g, s)) + { + fprintf (stderr, "mpz_lcm_ui failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", g); + dump ("ref", s); + abort (); + } + } + } + + mpz_clear (a); + mpz_clear (b); + mpz_clear (g); + mpz_clear (s); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-limbs.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-limbs.c new file mode 100644 index 0000000..f4e57dd --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-limbs.c @@ -0,0 +1,111 @@ +/* + +Copyright 2012, 2014, 2016, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 100 + +void +my_mpz_mul (mpz_t r, mpz_srcptr a, mpz_srcptr b) +{ + mp_limb_t *tp; + mp_size_t tn, an, bn; + + an = mpz_size (a); + bn = mpz_size (b); + + assert (an > 0); + assert (bn > 0); + + tn = an + bn; + tp = mpz_limbs_write (r, tn); + if (an > bn) + mpn_mul (tp, mpz_limbs_read (a), an, mpz_limbs_read (b), bn); + else + mpn_mul (tp, mpz_limbs_read (b), bn, mpz_limbs_read (a), an); + + if (mpz_sgn (a) != mpz_sgn(b)) + tn = - tn; + + mpz_limbs_finish (r, tn); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, res, ref; + + mpz_init (a); + mpz_init (b); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_MUL, MAXBITS, a, b, ref); + if (mpz_sgn(ref) == 0) + /* my_mpz_mul requires a != 0, b != 0 */ + continue; + my_mpz_mul (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "my_mpz_mul failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + /* The following test exploits a side-effect of my_mpz_mul: res + points to a buffer with at least an+bn limbs, and the limbs + above the result are zeroed. */ + if (mpz_size (b) > 0 && mpz_getlimbn (res, mpz_size(a)) != mpz_limbs_read (res) [mpz_size(a)]) + { + fprintf (stderr, "getlimbn - limbs_read differ.\n"); + abort (); + } + if ((i % 4 == 0) && mpz_size (res) > 1) + { + mpz_realloc2 (res, 1); + if (mpz_cmp_ui (res, 0)) + { + fprintf (stderr, "mpz_realloc2 did not clear res.\n"); + abort (); + } + mpz_limbs_finish (ref, 0); + if (mpz_cmp_d (ref, 0)) + { + fprintf (stderr, "mpz_limbs_finish did not clear res.\n"); + abort (); + } + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-logops.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-logops.c new file mode 100644 index 0000000..b4e0239 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-logops.c @@ -0,0 +1,112 @@ +/* + +Copyright 2012, 2013 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testlogops (int count) +{ + int i; + mpz_t a, b, res, ref; + mp_bitcnt_t c; + + mpz_init (a); + mpz_init (b); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < count; i++) + { + mini_random_op3 (OP_AND, MAXBITS, a, b, ref); + mpz_and (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_and failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + + mini_random_op3 (OP_IOR, MAXBITS, a, b, ref); + mpz_ior (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_ior failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + + mini_random_op3 (OP_XOR, MAXBITS, a, b, ref); + mpz_xor (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_xor failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + + if (i % 8) { + c = 0; + mpz_mul_2exp (res, res, i % 8); + } else if (mpz_sgn (res) >= 0) { + c = mpz_odd_p (res) != 0; + mpz_tdiv_q_2exp (res, res, 1); + } else { + c = (~ (mp_bitcnt_t) 0) - 3; + mpz_set_ui (res, 11 << ((i >> 3)%4)); /* set 3 bits */ + } + + if (mpz_popcount (res) + c != mpz_hamdist (a, b)) + { + fprintf (stderr, "mpz_popcount(r) + %lu and mpz_hamdist(a,b) differ:\n", c); + dump ("a", a); + dump ("b", b); + dump ("r", res); + fprintf (stderr, "mpz_popcount(r) = %lu:\n", mpz_popcount (res)); + fprintf (stderr, "mpz_hamdist(a,b) = %lu:\n", mpz_hamdist (a, b)); + abort (); + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (ref); +} + +void +testmain (int argc, char **argv) +{ + testhalves (COUNT*2/3, testlogops); + testlogops (COUNT/3); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-lucm.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-lucm.c new file mode 100644 index 0000000..22ad575 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-lucm.c @@ -0,0 +1,98 @@ +/* Tests the (internal) function mpz_lucas_mod + +Copyright 2018, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAXBITS 100 +#define COUNT 1000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t m, vr, qr, vm, qm, vt; + int resm, resr; + long Q; + unsigned long b0; + + mpz_init (m); + mpz_init (vr); + mpz_init (qr); + mpz_init (vm); + mpz_init (qm); + mpz_init (vt); + + for (i = 0; i < COUNT; i++) + { + mini_random_lucm_op (MAXBITS, vr, qr, m, &Q, &b0, &resr); + if (b0 == 0) + { + fprintf (stderr, "lucas_mod: test disabled (%u tests done).\n", i); + break; + } + resm = mpz_lucas_mod (vm, qm, Q, b0, m); + + if (resr != resm) + { + if (resm != 0 || mpz_cmp_ui (vm, 0) != 0) + { + fprintf (stderr, "mpz_lucas_mod wrong return value (%d != %d):\n", resr, resm); + fprintf (stderr, "Q = %ld , b0 = %lu\n", Q, b0); + dump ("m", m); + dump ("vm", vm); + dump ("qm", qm); + abort (); + } + } + else if (resm == 0) + { + mpz_abs (vr, vr); + mpz_sub (vt, m, vr); + mpz_abs (vm, vm); + mpz_mod (qm, qm, m); + if (mpz_cmp_ui (qr, 0) < 0) + mpz_add (qr, qr, m); + if (mpz_cmp (qm, qr) != 0 || + (mpz_cmp (vm, vr) != 0 && mpz_cmp (vm, vt) != 0)) + { + fprintf (stderr, "mpz_lucas_mod error:\n"); + fprintf (stderr, "Q = %ld , b0 = %lu\n", Q, b0); + dump ("m", m); + dump ("vm", vm); + dump ("vr", vr); + dump ("vt", vt); + dump ("qm", qm); + dump ("qr", qr); + abort (); + } + + } + } + mpz_clear (m); + mpz_clear (vr); + mpz_clear (qr); + mpz_clear (vm); + mpz_clear (qm); + mpz_clear (vt); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_addsub.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_addsub.c new file mode 100644 index 0000000..de1461f --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_addsub.c @@ -0,0 +1,204 @@ +/* + +Copyright 2012, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" +#include "../mini-mpq.h" + +#define MAXBITS 300 +#define COUNT 10000 + +static void +_mpq_set_zz (mpq_t q, mpz_t n, mpz_t d) +{ + if (mpz_fits_ulong_p (d) && mpz_fits_slong_p (n)) + { + mpq_set_si (q, mpz_get_si (n), mpz_get_ui (d)); + } + else if (mpz_fits_ulong_p (d) && mpz_fits_ulong_p (n)) + { + mpq_set_ui (q, mpz_get_ui (n), mpz_get_ui (d)); + } + else + { + mpq_set_num (q, n); + mpq_set_den (q, d); + } + mpq_canonicalize (q); +} + +void +testcmpui () +{ + unsigned d1, d2, n1, n2; + mpq_t q1, q2; + + mpq_init (q1); + mpq_init (q2); + + for (d1 = 1; d1 < 6; d1 += 2) + for (n1 = 1; n1 < 6; n1 *= 2) + { + mpq_set_ui (q1, n1, d1); + for (d2 = 1; d2 < 6; d2 += 2) + for (n2 = 1; n2 < 6; n2 *= 2) + { + int fres = mpq_cmp_ui (q1, n2, d2); + int ref = (d1*n2 < d2*n1) - (d1*n2 > d2*n1); + + mpq_set_ui (q2, n2, d2); + + if ((!ref) != mpq_equal (q1, q2)) + { + fprintf (stderr, "mpz_equal failed: %i / %i = %i / %i ? %i\n", n1, d1, n2, d2, ref); + abort (); + } + + if (ref != fres) + { + fprintf (stderr, "mpz_cmp_ui failed: %i / %i = %i / %i ? %i != %i\n", n1, d1, n2, d2, ref, fres); + abort (); + } + } + } + + mpq_clear (q1); + mpq_clear (q2); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, q, r, c; + mpq_t rr, ii, ff; + int tst; + + testcmpui (); + mpz_init (a); + mpz_init (b); + mpz_init (r); + mpz_init (q); + mpz_init (c); + mpq_init (rr); + mpq_init (ff); + mpq_init (ii); + + for (i = 0; i < COUNT; i++) + { + mini_random_op4 (OP_TDIV, MAXBITS, a, b, q, r); + + _mpq_set_zz (rr, a, b); + _mpq_set_zz (ff, r, b); + + mpq_set_z (ii, q); + + mpz_set_q (c, rr); + if (mpz_cmp (c, q)) + { + fprintf (stderr, "mpz_set_q failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("c", c); + dump ("q", q); + abort (); + } + + if ((mpz_sgn (r) != 0) ^ (mpz_cmp_ui (mpq_denref (rr), 1) != 0)) + { + fprintf (stderr, "mpq_canonicalize failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", r); + dump ("D", mpq_denref (rr)); + abort (); + } + + if (i & 1) + { + if (mpz_fits_slong_p (q)) + tst = mpq_cmp_si (rr, mpz_get_si (q), 1); + else if (mpz_fits_ulong_p (q)) + tst = mpq_cmp_ui (rr, mpz_get_ui (q), 1); + else + tst = mpq_cmp_z (rr, q); + if (mpz_sgn (b) < 0) + tst = - tst; + if ((tst != mpz_sgn (r)) && ((tst < 0 && mpz_sgn (r) >= 0) || (tst > 0 && mpz_sgn (r) <= 0))) + { + fprintf (stderr, "mpq_cmp ii failed: %i %i\n", tst, mpz_sgn (r)); + dump ("a", a); + dump ("b", b); + dump ("r", r); + dump ("q", q); + abort (); + } + } + else + { + if (mpz_fits_ulong_p (b) && mpz_fits_slong_p (r)) + tst = mpq_cmp_si (rr, mpz_get_si (r), mpz_get_ui (b)); + else if (mpz_fits_ulong_p (b) && mpz_fits_ulong_p (r)) + tst = mpq_cmp_ui (rr, mpz_get_ui (r), mpz_get_ui (b)); + else + tst = mpq_cmp (rr, ff); + if ((tst != mpz_sgn (q)) && ((tst < 0 && mpz_sgn (q) >= 0) || (tst > 0 && mpz_sgn (q) <= 0))) + { + fprintf (stderr, "mpq_cmp ff failed: %i %i\n", tst, mpz_sgn (q)); + dump ("a", a); + dump ("b", b); + dump ("r", r); + dump ("q", q); + abort (); + } + } + + if (i & 1) + { + mpq_sub (rr, rr, ff); + } + else + { + mpq_neg (ff, ff); + mpq_add (rr, ff, rr); + } + + if (!mpq_equal (ii, rr)) + { + fprintf (stderr, "mpq_%s failed:\n", (i & 1) ? "sub" : "add"); + dump ("a", a); + dump ("b", b); + dump ("r", r); + dump ("q", q); + abort (); + } + } + + mpz_clear (a); + mpz_clear (b); + mpz_clear (r); + mpz_clear (q); + mpz_clear (c); + mpq_clear (rr); + mpq_clear (ff); + mpq_clear (ii); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_double.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_double.c new file mode 100644 index 0000000..3cfba60 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_double.c @@ -0,0 +1,211 @@ +/* Test mpq_set_d. + +Copyright 2001-2003, 2005, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <math.h> +#include <float.h> +#include <limits.h> + +#include "testutils.h" +#include "../mini-mpq.h" + +#define COUNT 2000 + +mp_bitcnt_t +mpz_mantissasizeinbits (const mpz_t z) +{ + return ! mpz_cmp_ui (z, 0) ? 0 : + mpz_sizeinbase (z, 2) - mpz_scan1 (z, 0); +} + +int +mpz_abspow2_p (const mpz_t z) +{ + return mpz_mantissasizeinbits (z) == 1; +} + +mp_bitcnt_t +mpq_mantissasizeinbits (const mpq_t q) +{ + if (! mpz_abspow2_p (mpq_denref (q))) + return ~ (mp_bitcnt_t) 0; + + return mpz_mantissasizeinbits (mpq_numref (q)); +} + +#if defined(DBL_MANT_DIG) && FLT_RADIX == 2 +int +mpz_get_d_exact_p (const mpz_t z) +{ + return mpz_mantissasizeinbits (z) <= DBL_MANT_DIG; +} + +int +mpq_get_d_exact_p (const mpq_t q) +{ + return mpq_mantissasizeinbits (q) <= DBL_MANT_DIG; +} +#define HAVE_EXACT_P 1 +#endif + +void +check_random (void) +{ + unsigned i; + mpz_t x; + mpq_t y, z; + + mpz_init (x); + mpq_init (y); + mpq_init (z); + + for (i = 0; i < COUNT; i++) + { + /* Use volatile, to avoid extended precision in floating point + registers, e.g., on m68k and 80387. */ + volatile double d, f; + unsigned long m; + int e, c; + + mini_rrandomb (x, CHAR_BIT * sizeof (unsigned long)); + m = mpz_get_ui (x); + mini_urandomb (x, 8); + e = mpz_get_ui (x) - 128; + + d = ldexp ((double) m, e); + mpq_set_d (y, d); + f = mpq_get_d (y); + if (f != d) + { + fprintf (stderr, "mpq_set_d/mpq_get_d failed:\n"); + goto dumperror; + } + + d = - d; + mpq_neg (y, y); + + mpq_set_d (z, d); + f = mpq_get_d (z); + if (f != d || !mpq_equal (y, z)) + { + fprintf (stderr, "mpq_set_d/mpq_get_d failed:\n"); + dumperror: + dump ("ny", mpq_numref (y)); + dump ("dy", mpq_denref (y)); + fprintf (stderr, "m = %lx, e = %i\n", m, e); + fprintf (stderr, "d = %.35g\n", d); + fprintf (stderr, "f = %.35g\n", f); + fprintf (stderr, "f - d = %.35g\n", f - d); + abort (); + } + + mini_rrandomb (x, CHAR_BIT * sizeof (unsigned long)); + m = mpz_get_ui (x); + mini_urandomb (x, 8); + e = mpz_get_ui (x) - 128; + + d = ldexp ((double) m, e); + mpq_set_d (y, d); + + if (i == 0) + mpq_neg (z, y); + + mpq_add (y, y, z); + mpq_set_d (z, mpq_get_d (y)); + f = mpq_get_d (z); + c = mpq_cmp (y, z); + +#if defined(HAVE_EXACT_P) + if (mpq_get_d_exact_p (y) ? c != 0 : (f > 0 ? c <= 0 : c >= 0)) +#else + if (f > 0 ? c < 0 : c > 0) +#endif + { + fprintf (stderr, "mpq_get_d/mpq_set_d failed: %i %i\n", i, c); + goto dumperror; + } + } + + mpz_clear (x); + mpq_clear (y); + mpq_clear (z); +} + + +void +check_data (void) +{ + static const struct { + double y; + long int n; + unsigned long d; + } data[] = { + { 0.0, 0, 1 }, + { 1.0, 1, 1 }, + { -1.0, -1, 1 }, + { -1.5, -3, 2 }, + {-1.25, -5, 4 }, + {0.125, 1, 8 }, + + {24685,24685,1}, + {-9876,-9876,1}, + {463.5, 927,2}, + + {1234.5/8192, 2469, 16384 }, + {-543.0/1024, -543, 1024 }, + {9876.5/ 512, 19753, 1024 }, + {9753.0/ 128, 9753, 128 }, + {-789.0/ 32, -789, 32 }, + {4.580078125, 2345, 512 }, + }; + + mpq_t x, r; + unsigned i; + double d; + + mpq_init (x); + mpq_init (r); + + for (i = 0; i < numberof (data); i++) + { + mpq_set_d (x, data[i].y); + mpq_set_si (r, data[i].n, data[i].d); + mpq_canonicalize (r); + if (!mpq_equal (x, r)) + { + fprintf (stderr, "mpq_set_d failed: %li / %lu != %g\n", data[i].n, data[i].d, data[i].y); + abort (); + } + d = mpq_get_d (r); + if (d != data[i].y) + { + fprintf (stderr, "mpq_get_d failed: %li / %lu != %g\n", data[i].n, data[i].d, data[i].y); + abort (); + } + } + + mpq_clear (x); + mpq_clear (r); +} + +void +testmain (int argc, char *argv[]) +{ + check_data (); + check_random (); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv.c new file mode 100644 index 0000000..8e7de8b --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv.c @@ -0,0 +1,176 @@ +/* + +Copyright 2012, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" +#include "../mini-mpq.h" + +#define MAXBITS 300 +#define COUNT 10000 + +static void +_mpq_set_zz (mpq_t q, mpz_t n, mpz_t d) +{ + if (mpz_fits_ulong_p (d) && mpz_fits_slong_p (n)) + { + mpq_set_si (q, mpz_get_si (n), mpz_get_ui (d)); + } + else if (mpz_fits_ulong_p (d) && mpz_fits_ulong_p (n)) + { + mpq_set_ui (q, mpz_get_ui (n), mpz_get_ui (d)); + } + else + { + mpq_set_num (q, n); + mpq_set_den (q, d); + } + mpq_canonicalize (q); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t an, bn, rn, ad, bd, rd; + mpq_t aq, bq, refq, resq; + + mpz_init (an); + mpz_init (bn); + mpz_init (rn); + mpz_init (ad); + mpz_init (bd); + mpz_init (rd); + mpq_init (aq); + mpq_init (bq); + mpq_init (refq); + mpq_init (resq); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_MUL, MAXBITS, an, bn, rn); + do { + mini_random_op3 (OP_MUL, MAXBITS, ad, bd, rd); + } while (mpz_sgn (rd) == 0); + + _mpq_set_zz (aq, an, ad); + _mpq_set_zz (bq, bn, bd); + _mpq_set_zz (refq, rn, rd); + + mpq_mul (resq, aq, bq); + if (!mpq_equal (resq, refq)) + { + fprintf (stderr, "mpq_mul failed [%i]:\n", i); + dump ("an", an); + dump ("ad", ad); + dump ("bn", bn); + dump ("bd", bd); + dump ("refn", rn); + dump ("refd", rd); + dump ("resn", mpq_numref (resq)); + dump ("resd", mpq_denref (resq)); + abort (); + } + + if (mpq_sgn (refq) != 0) + { + mpq_set_ui (resq, ~6, 8); + mpq_inv (aq, aq); + mpq_div (resq, aq, bq); + mpq_inv (resq, resq); + if (!mpq_equal (resq, refq)) + { + fprintf (stderr, "mpq_div failed [%i]:\n", i); + dump ("an", an); + dump ("ad", ad); + dump ("bn", bn); + dump ("bd", bd); + dump ("refn", rn); + dump ("refd", rd); + dump ("resn", mpq_numref (resq)); + dump ("resd", mpq_denref (resq)); + abort (); + } + + mpq_swap (bq, aq); + mpq_div (resq, aq, bq); + if (!mpq_equal (resq, refq)) + { + fprintf (stderr, "mpq_swap failed [%i]:\n", i); + dump ("an", an); + dump ("ad", ad); + dump ("bn", bn); + dump ("bd", bd); + dump ("refn", rn); + dump ("refd", rd); + dump ("resn", mpq_numref (resq)); + dump ("resd", mpq_denref (resq)); + abort (); + } + } + + mpq_set (resq, aq); + mpq_neg (bq, aq); + mpq_abs (refq, aq); + if (mpq_equal (refq, resq)) + mpq_add (resq, refq, bq); + else + mpq_add (resq, refq, resq); + mpq_set_ui (refq, 0, 1); + if (!mpq_equal (resq, refq)) + { + fprintf (stderr, "mpq_abs failed [%i]:\n", i); + dump ("an", an); + dump ("ad", ad); + dump ("resn", mpq_numref (resq)); + dump ("resd", mpq_denref (resq)); + abort (); + } + + mpq_mul (resq, aq, aq); + mpq_mul (refq, aq, bq); /* now bq = - aq */ + mpq_neg (refq, refq); + if (!mpq_equal (resq, refq)) + { + fprintf (stderr, "mpq_mul(sqr) failed [%i]:\n", i); + dump ("an", an); + dump ("ad", ad); + dump ("bn", bn); + dump ("bd", bd); + dump ("refn", rn); + dump ("refd", rd); + dump ("resn", mpq_numref (resq)); + dump ("resd", mpq_denref (resq)); + abort (); + } + } + + mpz_clear (an); + mpz_clear (bn); + mpz_clear (rn); + mpz_clear (ad); + mpz_clear (bd); + mpz_clear (rd); + mpq_clear (aq); + mpq_clear (bq); + mpq_clear (refq); + mpq_clear (resq); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv_2exp.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv_2exp.c new file mode 100644 index 0000000..46b2c0c --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_muldiv_2exp.c @@ -0,0 +1,138 @@ +/* + +Copyright 2012, 2013, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" +#include "../mini-mpq.h" + +#define MAXBITS 300 +#define COUNT 10000 + +static void +_mpq_set_zz (mpq_t q, mpz_t n, mpz_t d) +{ + if (mpz_fits_ulong_p (d) && mpz_fits_slong_p (n)) + { + mpq_set_si (q, mpz_get_si (n), mpz_get_ui (d)); + } + else if (mpz_fits_ulong_p (d) && mpz_fits_ulong_p (n)) + { + mpq_set_ui (q, mpz_get_ui (n), mpz_get_ui (d)); + } + else + { + mpq_set_num (q, n); + mpq_set_den (q, d); + } + mpq_canonicalize (q); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, t; + mpq_t aq, rq, tq; + mp_bitcnt_t e; + long int e2, t1, t2; + + mpz_init (a); + mpz_init (b); + mpz_init (t); + mpq_init (aq); + mpq_init (rq); + mpq_init (tq); + + for (i = 0; i < COUNT; i++) + { + do { + mini_random_bit_op (OP_COMBIT, MAXBITS, a, &e, b); + } while (mpz_sgn (a) == 0 || mpz_sgn (b) == 0); + + _mpq_set_zz (aq, a, b); + e2 = mpz_scan1 (a, 0); + e2-= mpz_scan1 (b, 0); + + mpq_mul_2exp (rq, aq, e); + t1 = mpz_scan1 (mpq_numref (rq), 0); + t2 = mpz_scan1 (mpq_denref (rq), 0); + mpq_neg (tq, rq); + mpq_div (tq, aq, tq); + mpq_get_den (t, tq); + + if (e2 + e != t1 - t2 || (t2 != 0 && t1 != 0) || mpz_scan1 (t, 0) != e + || mpz_sizeinbase (t, 2) - 1 != e || mpz_cmp_si (mpq_numref (tq), -1) != 0) + { + fprintf (stderr, "mpq_mul_2exp failed: %lu\n", e); + dump ("na", a); + dump ("da", b); + dump ("nr", mpq_numref (rq)); + dump ("dr", mpq_denref (rq)); + abort (); + } + + mpq_div_2exp (rq, aq, e); + t1 = mpz_scan1 (mpq_numref (rq), 0); + t2 = mpz_scan1 (mpq_denref (rq), 0); + mpq_div (aq, aq, rq); + mpq_get_num (t, aq); + + if (e2 != t1 - t2 + e || (t2 != 0 && t1 != 0) || mpz_scan1 (t, 0) != e + || mpz_sizeinbase (t, 2) - 1 != e || mpz_cmp_ui (mpq_denref (aq), 1) != 0) + { + fprintf (stderr, "mpq_div_2exp failed: %lu\n", e); + fprintf (stderr, "%li %li %lu %zu\n", e2, t2, mpz_scan1 (t, 0), mpz_sizeinbase (t, 2)); + dump ("na", a); + dump ("da", b); + dump ("nr", mpq_numref (rq)); + dump ("dr", mpq_denref (rq)); + abort (); + } + + mpq_set_ui (aq, 0, 1); + mpq_set_ui (rq, 6, 7); + mpq_set (tq, aq); + mpq_div_2exp (rq, aq, e); + + if (!mpq_equal (tq, rq)) + { + fprintf (stderr, "mpq_div_2exp failed on zero: %lu\n", e); + abort (); + } + + mpq_set_ui (rq, 7, 6); + mpq_mul_2exp (rq, aq, e); + + if (!mpq_equal (rq, tq)) + { + fprintf (stderr, "mpq_mul_2exp failed on zero: %lu\n", e); + abort (); + } + } + + mpz_clear (a); + mpz_clear (b); + mpz_clear (t); + mpq_clear (aq); + mpq_clear (rq); + mpq_clear (tq); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_str.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_str.c new file mode 100644 index 0000000..e2b740a --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mpq_str.c @@ -0,0 +1,263 @@ +/* + +Copyright 2012-2014, 2016, 2018, 2020 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" +#include "../mini-mpq.h" + +#define MAXBITS 400 +#define COUNT 2000 + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) +#define MAXLIMBS ((MAXBITS + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS) + +static void +test_small (void) +{ + struct { + const char *input; + const char *decimal; + } data[] = { + { "1832407/3", "1832407/3" }, + { " 2763959/6", "2763959/6 " }, + { "4 981 999 / 1 8", "4981999/18" }, + { "10\t73981/30 ", "1073981/30" }, + { "958 544 /1", "00958544/01" }, + { "-0", "0000" }, + { " -000 ", "0/ 1" }, + { "0704436/011", "231710/9" }, + /* Check the case of large number of leading zeros. */ + { "0000000000000000000000000/1", "0/0000000000000000000000001" }, + { "000000000000000704436/000011", "0000000000000000231710/00009" }, + { " 012/ 02503517", "10/689999" }, + { "0b 10/0 1312143", "2/365667" }, + { "-03 274062/0x1", "-882738/1" }, + { "012\t242", "005282" }, + { "9/0b11010111110010001111", "9/883855" }, + { "022/ 0b11001010010100001", "18/103585" }, + { "-0b101010110011101111/0x12", "-175343/18" }, + { "-05/0b 111 1111 0110 1110 0110", "-5/521958" }, + { "0b 011 111 110 111 001 000 011/0b00110", "1044035/6" }, + { " 0x53dfc", "343548" }, + { "-0x00012/0x000fA019", "-18/1024025" }, + { "0x 642d1", "410321" }, + { "0x5 8067/0Xa", "360551/10" }, + { "-0xd6Be6/3", "-879590/3" }, + { "\t0B1110000100000000011", "460803" }, + { "0B\t1111110010010100101", "517285" }, + { "-0x 00 2d/0B1\t010111101101110100", "-45/359284" }, + { "-0B101\t1001101111111001", "-367609" }, + { "0B10001001010111110000/0xf", "562672/15" }, + { "0Xe4B7e/1", "936830" }, + { "0X1E4bf/0X1", "124095" }, + { "-0Xfdb90/05", "-1039248/5" }, + { "0b010/0X7fc47", "2/523335" }, + { "15/0X8167c", "15/530044" }, + /* Some invalid inputs */ + { "", NULL }, + { "0x", NULL }, + { "0b", NULL }, + { "0z", NULL }, + { "-", NULL }, + { "/0x ", NULL }, + { "0|1", NULL }, + { "/", NULL }, + { "0ab", NULL }, + { "10x0", NULL }, + { "1/0xxab", NULL }, + { "0/ab", NULL }, + { "0/#", NULL }, + { "$foo/1", NULL }, + { NULL, NULL } + }; + unsigned i; + mpq_t a, b; + mpq_init (a); + mpq_init (b); + + for (i = 0; data[i].input; i++) + { + int res = mpq_set_str (a, data[i].input, 0); + if (data[i].decimal) + { + if (res != 0) + { + fprintf (stderr, "mpq_set_str returned -1, input: %s\n", + data[i].input); + abort (); + } + if (mpq_set_str (b, data[i].decimal, 10) != 0) + { + fprintf (stderr, "mpq_set_str returned -1, decimal input: %s\n", + data[i].input); + abort (); + } + if (!mpq_equal (a, b)) + { + fprintf (stderr, "mpq_set_str failed for input: %s\n", + data[i].input); + + dump ("got_num", mpq_numref (a)); + dump ("got_den", mpq_denref (a)); + dump ("ref_num", mpq_numref (b)); + dump ("ref_den", mpq_denref (b)); + abort (); + } + } + else if (res != -1) + { + fprintf (stderr, "mpq_set_str returned %d, invalid input: %s\n", + res, data[i].input); + abort (); + } + } + + mpq_clear (a); + mpq_clear (b); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + char *ap; + char *bp; + char *rp; + size_t rn; + + mpq_t a, b; + + FILE *tmp; + + test_small (); + + mpq_init (a); + mpq_init (b); + + tmp = tmpfile (); + if (!tmp) + fprintf (stderr, + "Failed to create temporary file. Skipping mpq_out_str tests.\n"); + + if (mpq_out_str (tmp, 63, a) != 0) + { + printf ("mpq_out_str did not return 0 (error) with base > 62\n"); + abort (); + } + + if (mpq_out_str (tmp, -37, a) != 0) + { + printf ("mpq_out_str did not return 0 (error) with base < -37\n"); + abort (); + } + + for (i = 0; i < COUNT/60; i++) + { + int base; + for (base = 2; base <= 62; ++base) + { + hex_mpq_random_str_op (MAXBITS, (i&1 || base > 36) ? base: -base, &ap, &rp); + if (mpq_set_str (a, ap, 16) != 0) + { + fprintf (stderr, "mpq_set_str failed on input %s\n", ap); + abort (); + } + + rn = strlen (rp); + + bp = mpq_get_str (NULL, (i&1 || base > 36) ? base: -base, a); + if (strcmp (bp, rp)) + { + fprintf (stderr, "mpz_get_str failed:\n"); + dump ("a_num", mpq_numref (a)); + dump ("a_den", mpq_denref (a)); + fprintf (stderr, "b = %s\n", bp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", rp); + abort (); + } + + /* Just a few tests with file i/o. */ + if (tmp && i < 20) + { + size_t tn; + rewind (tmp); + tn = mpq_out_str (tmp, (i&1 || base > 36) ? base: -base, a); + if (tn != rn) + { + fprintf (stderr, "mpq_out_str, bad return value:\n"); + dump ("a_num", mpq_numref (a)); + dump ("a_den", mpq_denref (a)); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base %d, correct size %u, got %u\n", + base, (unsigned) rn, (unsigned)tn); + abort (); + } + rewind (tmp); + memset (bp, 0, rn); + tn = fread (bp, 1, rn, tmp); + if (tn != rn) + { + fprintf (stderr, + "fread failed, expected %lu bytes, got only %lu.\n", + (unsigned long) rn, (unsigned long) tn); + abort (); + } + + if (memcmp (bp, rp, rn) != 0) + { + fprintf (stderr, "mpq_out_str failed:\n"); + dump ("a_num", mpq_numref (a)); + dump ("a_den", mpq_denref (a)); + fprintf (stderr, "b = %s\n", bp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", rp); + abort (); + } + } + + mpq_set_str (b, rp, base); + + if (!mpq_equal (a, b)) + { + fprintf (stderr, "mpq_set_str failed:\n"); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", ap); + fprintf (stderr, " base = 16\n"); + dump ("b_num", mpq_numref (b)); + dump ("b_den", mpq_denref (b)); + dump ("r_num", mpq_numref (a)); + dump ("r_den", mpq_denref (a)); + abort (); + } + + free (ap); + free (rp); + testfree (bp, strlen(bp) + 1); + } + } + mpq_clear (a); + mpq_clear (b); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-mul.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-mul.c new file mode 100644 index 0000000..57ec4ed --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-mul.c @@ -0,0 +1,113 @@ +/* + +Copyright 2012, 2014, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) +#define MAXLIMBS ((MAXBITS + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS) + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, res, res_ui, ref, tz; + mp_limb_t t[2*MAXLIMBS]; + mp_size_t an; + + mpz_init (a); + mpz_init (b); + mpz_init (res); + mpz_init (res_ui); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_MUL, MAXBITS, a, b, ref); + mpz_mul (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_mul failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + if (mpz_size (a) == mpz_size (b)) + { + memset (t, 0x55, sizeof(t)); + an = mpz_size (a); + if (an > 0) + { + mpn_mul_n (t, a->_mp_d, b->_mp_d, an); + + mpz_roinit_n (tz, t, 2*an); + if (mpz_cmpabs (tz, ref)) + { + fprintf (stderr, "mpn_mul_n failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("ref", ref); + abort (); + } + } + } + if (mpz_fits_slong_p (b)) { + mpz_mul_si (res_ui, a, mpz_get_si (b)); + if (mpz_cmp (res_ui, ref)) + { + fprintf (stderr, "mpz_mul_si failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res_ui); + dump ("ref", ref); + abort (); + } + } + mini_random_op2 (OP_SQR, MAXBITS, a, ref); + an = mpz_size (a); + if (an > 0) + { + memset (t, 0x33, sizeof(t)); + mpn_sqr (t, mpz_limbs_read (a), an); + + mpz_roinit_n (tz, t, 2*an); + if (mpz_cmp (tz, ref)) + { + fprintf (stderr, "mpn (squaring) failed:\n"); + dump ("a", a); + dump ("ref", ref); + abort (); + } + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (res_ui); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-powm.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-powm.c new file mode 100644 index 0000000..1cce9b5 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-powm.c @@ -0,0 +1,87 @@ +/* + +Copyright 2012, 2022, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 1000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t b, e, m, res, ref; + + mpz_init (b); + mpz_init (e); + mpz_init (m); + mpz_init (res); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op4 (OP_POWM, MAXBITS, b, e, m, ref); + mpz_powm (res, b, e, m); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_powm failed:\n"); + dump ("b", b); + dump ("e", e); + dump ("m", m); + dump ("r", res); + dump ("ref", ref); + abort (); + } + } + + /* res >= 0, come from the random choices above, */ + if (mpz_cmp_ui (res, 1) <= 0) /* if too small, */ + mpz_add_ui (res, res, 9); /* add an arbitrary value. */ + + mpz_set_ui (e, 0); + /* Test the case m^0 (mod m), expect 1 (m is greater than 1). */ + mpz_powm (res, res, e, res); + if (mpz_cmp_ui (res, 1) != 0) + { + fprintf (stderr, "mpz_powm failed: b=m, e=0; 1 expected,\n"); + dump ("m", res); + dump ("r", res); + abort (); + } + + /* Now res is 1. */ + /* Test the case 1^0 (mod 1), expect 0. */ + mpz_powm (res, res, e, res); + if (mpz_size (res)) + { + fprintf (stderr, "mpz_powm failed: b=1, e=0, m=1; 0 expected,\n"); + dump ("r", res); + abort (); + } + + mpz_clear (b); + mpz_clear (e); + mpz_clear (m); + mpz_clear (res); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-pprime_p.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-pprime_p.c new file mode 100644 index 0000000..6cf9b18 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-pprime_p.c @@ -0,0 +1,183 @@ +/* test mpz_probab_prime_p + +Copyright 2001, 2002, 2004, 2011, 2012, 2014, 2016 Free Software +Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include "testutils.h" + +static int +isprime (unsigned long int t) +{ + unsigned long int q, r, d; + + if (t < 32) + return (0xa08a28acUL >> t) & 1; + if ((t & 1) == 0) + return 0; + + if (t % 3 == 0) + return 0; + if (t % 5 == 0) + return 0; + if (t % 7 == 0) + return 0; + + for (d = 11;;) + { + q = t / d; + r = t - q * d; + if (q < d) + return 1; + if (r == 0) + break; + d += 2; + q = t / d; + r = t - q * d; + if (q < d) + return 1; + if (r == 0) + break; + d += 4; + } + return 0; +} + +static void +check_one (mpz_srcptr n, int want) +{ + int got; + + got = mpz_probab_prime_p (n, 25); + + /* "definitely prime" is fine if we only wanted "probably prime" */ + if (got == 2 && want == 1) + want = 2; + + if (got != want) + { + printf ("mpz_probab_prime_p\n"); + dump (" n ", n); + printf (" got =%d", got); + printf (" want=%d\n", want); + abort (); + } +} + +static void +check_pn (mpz_ptr n, int want) +{ + check_one (n, want); + mpz_neg (n, n); + check_one (n, want); +} + +static void +check_small (void) +{ + mpz_t n; + long i; + + mpz_init (n); + + for (i = 0; i < 1700; i++) + { + mpz_set_si (n, i); + check_pn (n, isprime (i)); + } + + mpz_clear (n); +} + +void +check_composites (void) +{ + int i; + int reps = 1000; + mpz_t a, b, n, bs; + unsigned long size_range, size; + + mpz_init (a); + mpz_init (b); + mpz_init (n); + mpz_init (bs); + + for (i = 0; i < reps; i++) + { + mini_urandomb (bs, 16); + size_range = mpz_get_ui (bs) % 10 + 1; /* 0..1024 bit operands */ + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (a, size); + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (b, size); + + /* Exclude trivial factors */ + if (mpz_cmp_ui (a, 1) == 0) + mpz_set_ui (a, 2); + if (mpz_cmp_ui (b, 1) == 0) + mpz_set_ui (b, 2); + + mpz_mul (n, a, b); + + check_pn (n, 0); + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (n); + mpz_clear (bs); +} + +static void +check_primes (void) +{ + static const char * const primes[] = { + "2", "17", "65537", + /* diffie-hellman-group1-sha1, also "Well known group 2" in RFC + 2412, 2^1024 - 2^960 - 1 + 2^64 * { [2^894 pi] + 129093 } */ + "0xFFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1" + "29024E088A67CC74020BBEA63B139B22514A08798E3404DD" + "EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245" + "E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED" + "EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE65381" + "FFFFFFFFFFFFFFFF", + NULL + }; + + mpz_t n; + int i; + + mpz_init (n); + + for (i = 0; primes[i]; i++) + { + mpz_set_str_or_abort (n, primes[i], 0); + check_one (n, 1); + } + mpz_clear (n); +} + +void +testmain (int argc, char *argv[]) +{ + check_small (); + check_composites (); + check_primes (); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-reuse.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-reuse.c new file mode 100644 index 0000000..09a5440 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-reuse.c @@ -0,0 +1,663 @@ +/* Test that routines allow reusing a source variable as destination. + +Copyright 1996, 1999-2002, 2009, 2012 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define COUNT 100 + +void dump3 (const char *, mpz_t, mpz_t, mpz_t); +void mpz_check_format (const mpz_t); + +typedef void (*dss_func) (mpz_t, const mpz_t, const mpz_t); +typedef void (*dsi_func) (mpz_t, const mpz_t, unsigned long int); +typedef unsigned long int (*dsi_div_func) (mpz_t, const mpz_t, unsigned long int); +typedef unsigned long int (*ddsi_div_func) (mpz_t, mpz_t, const mpz_t, unsigned long int); +typedef void (*ddss_div_func) (mpz_t, mpz_t, const mpz_t, const mpz_t); +typedef void (*ds_func) (mpz_t, const mpz_t); + + +void +mpz_xinvert (mpz_t r, const mpz_t a, const mpz_t b) +{ + int res; + res = mpz_invert (r, a, b); + if (res == 0) + mpz_set_ui (r, 0); +} + +dss_func dss_funcs[] = +{ + mpz_add, mpz_sub, mpz_mul, + mpz_cdiv_q, mpz_cdiv_r, mpz_fdiv_q, mpz_fdiv_r, mpz_tdiv_q, mpz_tdiv_r, + mpz_xinvert, + mpz_gcd, mpz_lcm, mpz_and, mpz_ior, mpz_xor +}; +const char *dss_func_names[] = +{ + "mpz_add", "mpz_sub", "mpz_mul", + "mpz_cdiv_q", "mpz_cdiv_r", "mpz_fdiv_q", "mpz_fdiv_r", "mpz_tdiv_q", "mpz_tdiv_r", + "mpz_xinvert", + "mpz_gcd", "mpz_lcm", "mpz_and", "mpz_ior", "mpz_xor" +}; +char dss_func_division[] = {0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0}; + +dsi_func dsi_funcs[] = +{ + /* Don't change order here without changing the code in main(). */ + mpz_add_ui, mpz_mul_ui, mpz_sub_ui, + mpz_fdiv_q_2exp, mpz_fdiv_r_2exp, + mpz_cdiv_q_2exp, mpz_cdiv_r_2exp, + mpz_tdiv_q_2exp, mpz_tdiv_r_2exp, + mpz_mul_2exp, + mpz_pow_ui +}; +const char *dsi_func_names[] = +{ + "mpz_add_ui", "mpz_mul_ui", "mpz_sub_ui", + "mpz_fdiv_q_2exp", "mpz_fdiv_r_2exp", + "mpz_cdiv_q_2exp", "mpz_cdiv_r_2exp", + "mpz_tdiv_q_2exp", "mpz_tdiv_r_2exp", + "mpz_mul_2exp", + "mpz_pow_ui" +}; + +dsi_div_func dsi_div_funcs[] = +{ + mpz_cdiv_q_ui, mpz_cdiv_r_ui, + mpz_fdiv_q_ui, mpz_fdiv_r_ui, + mpz_tdiv_q_ui, mpz_tdiv_r_ui +}; +const char *dsi_div_func_names[] = +{ + "mpz_cdiv_q_ui", "mpz_cdiv_r_ui", + "mpz_fdiv_q_ui", "mpz_fdiv_r_ui", + "mpz_tdiv_q_ui", "mpz_tdiv_r_ui" +}; + +ddsi_div_func ddsi_div_funcs[] = +{ + mpz_cdiv_qr_ui, + mpz_fdiv_qr_ui, + mpz_tdiv_qr_ui +}; +const char *ddsi_div_func_names[] = +{ + "mpz_cdiv_qr_ui", + "mpz_fdiv_qr_ui", + "mpz_tdiv_qr_ui" +}; + +ddss_div_func ddss_div_funcs[] = +{ + mpz_cdiv_qr, + mpz_fdiv_qr, + mpz_tdiv_qr +}; +const char *ddss_div_func_names[] = +{ + "mpz_cdiv_qr", + "mpz_fdiv_qr", + "mpz_tdiv_qr" +}; + +ds_func ds_funcs[] = +{ + mpz_abs, mpz_com, mpz_neg, mpz_sqrt +}; +const char *ds_func_names[] = +{ + "mpz_abs", "mpz_com", "mpz_neg", "mpz_sqrt" +}; + + +#define FAIL(class,indx,op1,op2,op3) \ + do { \ + class##_funcs[indx] = 0; \ + dump3 (class##_func_names[indx], op1, op2, op3); \ + failures++; \ + } while (0) +#define FAIL2(fname,op1,op2,op3) \ + do { \ + dump3 (#fname, op1, op2, op3); \ + failures++; \ + } while (0) + +void +testmain (int argc, char **argv) +{ + unsigned i; + int pass, reps = COUNT; + mpz_t in1, in2, in3; + unsigned long int in2i; + mp_size_t size; + mpz_t res1, res2, res3; + mpz_t ref1, ref2, ref3; + mpz_t t; + unsigned long int r1, r2; + long failures = 0; + mpz_t bs; + unsigned long bsi, size_range; + + mpz_init (bs); + + mpz_init (in1); + mpz_init (in2); + mpz_init (in3); + mpz_init (ref1); + mpz_init (ref2); + mpz_init (ref3); + mpz_init (res1); + mpz_init (res2); + mpz_init (res3); + mpz_init (t); + + for (pass = 1; pass <= reps; pass++) + { + mini_urandomb (bs, 32); + size_range = mpz_get_ui (bs) % 12 + 2; + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (in1, size); + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (in2, size); + + mini_urandomb (bs, size_range); + size = mpz_get_ui (bs); + mini_rrandomb (in3, size); + + mini_urandomb (bs, 3); + bsi = mpz_get_ui (bs); + if ((bsi & 1) != 0) + mpz_neg (in1, in1); + if ((bsi & 2) != 0) + mpz_neg (in2, in2); + if ((bsi & 4) != 0) + mpz_neg (in3, in3); + + for (i = 0; i < numberof (dss_funcs); i++) + { + if (dss_funcs[i] == 0) + continue; + if (dss_func_division[i] && mpz_sgn (in2) == 0) + continue; + + (dss_funcs[i]) (ref1, in1, in2); + mpz_check_format (ref1); + + mpz_set (res1, in1); + (dss_funcs[i]) (res1, res1, in2); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL (dss, i, in1, in2, NULL); + + mpz_set (res1, in2); + (dss_funcs[i]) (res1, in1, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL (dss, i, in1, in2, NULL); + } + + for (i = 0; i < numberof (ddss_div_funcs); i++) + { + if (ddss_div_funcs[i] == 0) + continue; + if (mpz_sgn (in2) == 0) + continue; + + (ddss_div_funcs[i]) (ref1, ref2, in1, in2); + mpz_check_format (ref1); + mpz_check_format (ref2); + + mpz_set (res1, in1); + (ddss_div_funcs[i]) (res1, res2, res1, in2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL (ddss_div, i, in1, in2, NULL); + + mpz_set (res2, in1); + (ddss_div_funcs[i]) (res1, res2, res2, in2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL (ddss_div, i, in1, in2, NULL); + + mpz_set (res1, in2); + (ddss_div_funcs[i]) (res1, res2, in1, res1); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL (ddss_div, i, in1, in2, NULL); + + mpz_set (res2, in2); + (ddss_div_funcs[i]) (res1, res2, in1, res2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL (ddss_div, i, in1, in2, NULL); + } + + for (i = 0; i < numberof (ds_funcs); i++) + { + if (ds_funcs[i] == 0) + continue; + if (strcmp (ds_func_names[i], "mpz_sqrt") == 0 + && mpz_sgn (in1) < 0) + continue; + + (ds_funcs[i]) (ref1, in1); + mpz_check_format (ref1); + + mpz_set (res1, in1); + (ds_funcs[i]) (res1, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL (ds, i, in1, in2, NULL); + } + + in2i = mpz_get_ui (in2); + + for (i = 0; i < numberof (dsi_funcs); i++) + { + if (dsi_funcs[i] == 0) + continue; + if (strcmp (dsi_func_names[i], "mpz_fdiv_q_2exp") == 0) + /* Limit exponent to something reasonable for the division + functions. Without this, we'd normally shift things off + the end and just generate the trivial values 1, 0, -1. */ + in2i %= 0x1000; + if (strcmp (dsi_func_names[i], "mpz_mul_2exp") == 0) + /* Limit exponent more for mpz_mul_2exp to save time. */ + in2i %= 0x100; + if (strcmp (dsi_func_names[i], "mpz_pow_ui") == 0) + /* Limit exponent yet more for mpz_pow_ui to save time. */ + in2i %= 0x10; + + (dsi_funcs[i]) (ref1, in1, in2i); + mpz_check_format (ref1); + + mpz_set (res1, in1); + (dsi_funcs[i]) (res1, res1, in2i); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL (dsi, i, in1, in2, NULL); + } + + if (in2i != 0) /* Don't divide by 0. */ + { + for (i = 0; i < numberof (dsi_div_funcs); i++) + { + r1 = (dsi_div_funcs[i]) (ref1, in1, in2i); + mpz_check_format (ref1); + + mpz_set (res1, in1); + r2 = (dsi_div_funcs[i]) (res1, res1, in2i); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0 || r1 != r2) + FAIL (dsi_div, i, in1, in2, NULL); + } + + for (i = 0; i < numberof (ddsi_div_funcs); i++) + { + r1 = (ddsi_div_funcs[i]) (ref1, ref2, in1, in2i); + mpz_check_format (ref1); + + mpz_set (res1, in1); + r2 = (ddsi_div_funcs[i]) (res1, res2, res1, in2i); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 || r1 != r2) + FAIL (ddsi_div, i, in1, in2, NULL); + + mpz_set (res2, in1); + (ddsi_div_funcs[i]) (res1, res2, res2, in2i); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 || r1 != r2) + FAIL (ddsi_div, i, in1, in2, NULL); + } + } + + if (mpz_sgn (in1) >= 0) + { + mpz_sqrtrem (ref1, ref2, in1); + mpz_check_format (ref1); + mpz_check_format (ref2); + + mpz_set (res1, in1); + mpz_sqrtrem (res1, res2, res1); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL2 (mpz_sqrtrem, in1, NULL, NULL); + + mpz_set (res2, in1); + mpz_sqrtrem (res1, res2, res2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL2 (mpz_sqrtrem, in1, NULL, NULL); + } + + if (mpz_sgn (in1) >= 0) + { + mpz_root (ref1, in1, in2i % 0x1000 + 1); + mpz_check_format (ref1); + + mpz_set (res1, in1); + mpz_root (res1, res1, in2i % 0x1000 + 1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_root, in1, in2, NULL); + } + + if (mpz_sgn (in1) >= 0) + { + mpz_rootrem (ref1, ref2, in1, in2i % 0x1000 + 1); + mpz_check_format (ref1); + mpz_check_format (ref2); + + mpz_set (res1, in1); + mpz_rootrem (res1, res2, res1, in2i % 0x1000 + 1); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL2 (mpz_rootrem, in1, in2, NULL); + + mpz_set (res2, in1); + mpz_rootrem (res1, res2, res2, in2i % 0x1000 + 1); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0) + FAIL2 (mpz_rootrem, in1, in2, NULL); + } + + if (pass < reps / 2) /* run fewer tests since gcdext lots of time */ + { + mpz_gcdext (ref1, ref2, ref3, in1, in2); + mpz_check_format (ref1); + mpz_check_format (ref2); + mpz_check_format (ref3); + + mpz_set (res1, in1); + mpz_gcdext (res1, res2, res3, res1, in2); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res2, in1); + mpz_gcdext (res1, res2, res3, res2, in2); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res3, in1); + mpz_gcdext (res1, res2, res3, res3, in2); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res1, in2); + mpz_gcdext (res1, res2, res3, in1, res1); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res2, in2); + mpz_gcdext (res1, res2, res3, in1, res2); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res3, in2); + mpz_gcdext (res1, res2, res3, in1, res3); + mpz_check_format (res1); + mpz_check_format (res2); + mpz_check_format (res3); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res1, in1); + mpz_gcdext (res1, res2, NULL, res1, in2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res2, in1); + mpz_gcdext (res1, res2, NULL, res2, in2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res1, in2); + mpz_gcdext (res1, res2, NULL, in1, res1); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + + mpz_set (res2, in2); + mpz_gcdext (res1, res2, NULL, in1, res2); + mpz_check_format (res1); + mpz_check_format (res2); + if (mpz_cmp (ref1, res1) != 0 || mpz_cmp (ref2, res2) != 0 + || mpz_cmp (ref3, res3) != 0) + FAIL2 (mpz_gcdext, in1, in2, NULL); + } + + /* Don't run mpz_powm for huge exponents or when undefined. */ + if (mpz_sizeinbase (in2, 2) < 250 && mpz_sgn (in3) != 0 + && (mpz_sgn (in2) >= 0 || mpz_invert (t, in1, in3))) + { + mpz_powm (ref1, in1, in2, in3); + mpz_check_format (ref1); + + mpz_set (res1, in1); + mpz_powm (res1, res1, in2, in3); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_powm, in1, in2, in3); + + mpz_set (res1, in2); + mpz_powm (res1, in1, res1, in3); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_powm, in1, in2, in3); + + mpz_set (res1, in3); + mpz_powm (res1, in1, in2, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_powm, in1, in2, in3); + } + + /* Don't run mpz_powm_ui when undefined. */ + if (mpz_sgn (in3) != 0) + { + mpz_powm_ui (ref1, in1, in2i, in3); + mpz_check_format (ref1); + + mpz_set (res1, in1); + mpz_powm_ui (res1, res1, in2i, in3); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_powm_ui, in1, in2, in3); + + mpz_set (res1, in3); + mpz_powm_ui (res1, in1, in2i, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_powm_ui, in1, in2, in3); + } + + { + r1 = mpz_gcd_ui (ref1, in1, in2i); + mpz_check_format (ref1); + + mpz_set (res1, in1); + r2 = mpz_gcd_ui (res1, res1, in2i); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_gcd_ui, in1, in2, NULL); + } +#if 0 + if (mpz_cmp_ui (in2, 1L) > 0 && mpz_sgn (in1) != 0) + { + /* Test mpz_remove */ + mpz_remove (ref1, in1, in2); + mpz_check_format (ref1); + + mpz_set (res1, in1); + mpz_remove (res1, res1, in2); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_remove, in1, in2, NULL); + + mpz_set (res1, in2); + mpz_remove (res1, in1, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_remove, in1, in2, NULL); + } +#endif + if (mpz_sgn (in2) != 0) + { + /* Test mpz_divexact */ + mpz_mul (t, in1, in2); + mpz_divexact (ref1, t, in2); + mpz_check_format (ref1); + + mpz_set (res1, t); + mpz_divexact (res1, res1, in2); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_divexact, t, in2, NULL); + + mpz_set (res1, in2); + mpz_divexact (res1, t, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_divexact, t, in2, NULL); + } + +#if 0 + if (mpz_sgn (in2) > 0) + { + /* Test mpz_divexact_gcd, same as mpz_divexact */ + mpz_mul (t, in1, in2); + mpz_divexact_gcd (ref1, t, in2); + mpz_check_format (ref1); + + mpz_set (res1, t); + mpz_divexact_gcd (res1, res1, in2); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_divexact_gcd, t, in2, NULL); + + mpz_set (res1, in2); + mpz_divexact_gcd (res1, t, res1); + mpz_check_format (res1); + if (mpz_cmp (ref1, res1) != 0) + FAIL2 (mpz_divexact_gcd, t, in2, NULL); + } +#endif + } + + if (failures != 0) + { + fprintf (stderr, "mpz/reuse: %ld error%s\n", failures, "s" + (failures == 1)); + exit (1); + } + + mpz_clear (bs); + mpz_clear (in1); + mpz_clear (in2); + mpz_clear (in3); + mpz_clear (ref1); + mpz_clear (ref2); + mpz_clear (ref3); + mpz_clear (res1); + mpz_clear (res2); + mpz_clear (res3); + mpz_clear (t); +} + +void +dump3 (const char *name, mpz_t in1, mpz_t in2, mpz_t in3) +{ + printf ("failure in %s (", name); + mpz_out_str (stdout, -16, in1); + if (in2 != NULL) + { + printf (" "); + mpz_out_str (stdout, -16, in2); + } + if (in3 != NULL) + { + printf (" "); + mpz_out_str (stdout, -16, in3); + } + printf (")\n"); +} + +void +mpz_check_format (const mpz_t x) +{ + mp_size_t n = x ->_mp_size; + if (n < 0) + n = - n; + + if (n > x->_mp_alloc) + { + fprintf (stderr, "mpz_t size exceeds allocation!\n"); + abort (); + } + + if (n > 0 && x->_mp_d[n-1] == 0) + { + fprintf (stderr, "Unnormalized mpz_t!\n"); + abort (); + } +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-root.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-root.c new file mode 100644 index 0000000..1f46c43 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-root.c @@ -0,0 +1,95 @@ +/* + +Copyright 2012, 2013 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +/* Called when s is supposed to be floor(root(u,z)), and r = u - s^z */ +static int +rootrem_valid_p (const mpz_t u, const mpz_t s, const mpz_t r, unsigned long z) +{ + mpz_t t; + + mpz_init (t); + if (mpz_fits_ulong_p (s)) + mpz_ui_pow_ui (t, mpz_get_ui (s), z); + else + mpz_pow_ui (t, s, z); + mpz_sub (t, u, t); + if ((mpz_sgn (t) != mpz_sgn(u) && mpz_sgn (t) != 0) || mpz_cmp (t, r) != 0) + { + mpz_clear (t); + return 0; + } + if (mpz_sgn (s) > 0) + mpz_add_ui (t, s, 1); + else + mpz_sub_ui (t, s, 1); + mpz_pow_ui (t, t, z); + if (mpz_cmpabs (t, u) <= 0) + { + mpz_clear (t); + return 0; + } + + mpz_clear (t); + return 1; +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + unsigned long e; + mpz_t u, s, r, bs; + + mpz_init (u); + mpz_init (s); + mpz_init (r); + mpz_init (bs); + + for (i = 0; i < COUNT; i++) + { + mini_rrandomb (u, MAXBITS); + mini_rrandomb (bs, 12); + e = mpz_getlimbn (bs, 0) % mpz_sizeinbase (u, 2) + 1; + if ((e & 1) && (mpz_getlimbn (bs, 0) & (1L<<10))) + mpz_neg (u, u); + mpz_rootrem (s, r, u, e); + + if (!rootrem_valid_p (u, s, r, e)) + { + fprintf (stderr, "mpz_rootrem(%lu-th) failed:\n", e); + dump ("u", u); + dump ("root", s); + dump ("rem", r); + abort (); + } + } + mpz_clear (bs); + mpz_clear (u); + mpz_clear (s); + mpz_clear (r); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-scan.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-scan.c new file mode 100644 index 0000000..39b1f35 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-scan.c @@ -0,0 +1,90 @@ +/* + +Copyright 2012, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a; + mp_bitcnt_t b, res, ref; + + mpz_init (a); + + for (i = 0; i < COUNT; i++) + { + mini_random_scan_op (OP_SCAN0, MAXBITS, a, &b, &ref); + res = mpz_scan0 (a, b); + if (res != ref) + { + fprintf (stderr, "mpz_scan0 failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + fprintf (stderr, "r: %lu\n", res); + fprintf (stderr, "ref: %lu\n", ref); + abort (); + } + if (mpz_sgn (a) > 0 && ref < mpz_sizeinbase (a, 2)) + { + res = mpn_scan0 (a->_mp_d, b); + if (res != ref) + { + fprintf (stderr, "mpn_scan0 failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + fprintf (stderr, "r: %lu\n", res); + fprintf (stderr, "ref: %lu\n", ref); + abort (); + } + } + mini_random_scan_op (OP_SCAN1, MAXBITS, a, &b, &ref); + res = mpz_scan1 (a, b); + if (res != ref) + { + fprintf (stderr, "mpz_scan1 failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + fprintf (stderr, "r: %lu\n", res); + fprintf (stderr, "ref: %lu\n", ref); + abort (); + } + if (mpz_sgn (a) > 0 && ref != ~ (mp_bitcnt_t) 0) + { + res = mpn_scan1 (a->_mp_d, b); + if (res != ref) + { + fprintf (stderr, "mpn_scan1 failed:\n"); + dump ("a", a); + fprintf (stderr, "b: %lu\n", b); + fprintf (stderr, "r: %lu\n", res); + fprintf (stderr, "ref: %lu\n", ref); + abort (); + } + } + } + mpz_clear (a); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-signed.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-signed.c new file mode 100644 index 0000000..cfa40d7 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-signed.c @@ -0,0 +1,348 @@ +/* Exercise some mpz_..._si functions. + +Copyright 2013, 2016, 2020 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdio.h> +#include <stdlib.h> + +#include "testutils.h" + +/* Always called with sz fitting in a signed long, and si is the + corresponding value. */ +int +check_si (const mpz_t sz, long si) +{ + mpz_t t; + + /* Checks on sz/si */ + if ((mpz_cmp_si (sz, si)) != 0) + { + printf ("mpz_cmp_si (sz, %ld) != 0.\n", si); + return 0; + } + if (mpz_get_si (sz) != si) + { + printf ("mpz_get_si (sz) != %ld.\n", si); + return 0; + } + + mpz_init_set_si (t, si); + + if (mpz_cmp (t, sz) != 0) + { + printf ("mpz_init_set_si (%ld) failed.\n", si); + printf (" got="); mpz_out_str (stdout, 10, t); printf ("\n"); + return 0; + } + + mpz_clear (t); + return 1; +} + +/* Called with mpz_cmp (sz, oz) == c. If sz fits in a signed long, + si is the coresponding value, and similarly for oz and oi. */ +void +check_si_cmp (const mpz_t sz, const mpz_t oz, long si, long oi, int c) +{ + if (mpz_cmp (sz, oz) != c) + { + printf ("mpz_cmp (sz, oz) != %i.\n", c); + goto fail; + } + + if (mpz_fits_slong_p (sz)) + { + if (!check_si (sz, si)) + goto fail; + if (mpz_cmp_si (oz, si) != -c) + { + printf ("mpz_cmp_si (oz, %ld) != %i.\n", si, -c); + goto fail; + } + } + else + { + if (mpz_cmp_si (sz, si) != c) + { + printf ("mpz_cmp_si (sz, %ld) != %i.\n", si, c); + goto fail; + } + if (mpz_cmp_si (sz, -c) != c) + { + printf ("mpz_cmp_si (sz, %i) != %i.\n", -c, c); + goto fail; + } + } + if (mpz_fits_slong_p (oz)) + { + if (!check_si (oz, oi)) + goto fail; + if (mpz_cmp_si (sz, oi) != c) + { + printf ("mpz_cmp_si (sz, %ld) != %i.\n", oi, c); + goto fail; + } + } + return; + + fail: + printf (" sz="); mpz_out_str (stdout, 10, sz); printf ("\n"); + printf (" si=%ld\n", si); + printf (" oz="); mpz_out_str (stdout, 10, oz); printf ("\n"); + printf (" oi=%ld\n", si); + abort (); +} + +void +try_op_si (int c) +{ + long si, oi; + mpz_t sz, oz; + unsigned overflow_count; + + si = c; + mpz_init_set_si (sz, si); + + oi = si; + mpz_init_set (oz, sz); + + /* To get a few tests with operands straddling the border, don't + stop at the very first operand exceeding a signed long. */ + for (overflow_count = 0; overflow_count < 10; ) + { + /* c * 2^k */ + mpz_mul_2exp (sz, sz, 1); + if (mpz_fits_slong_p (sz)) + si *= 2; + else + overflow_count++; + + check_si_cmp (sz, oz, si, oi, c); + + /* c * (2^k + 1) */ + if (c == -1) + mpz_sub_ui (oz, sz, 1); + else + mpz_add_ui (oz, sz, 1); + if (mpz_fits_slong_p (oz)) + oi = si + c; + else + overflow_count++; + check_si_cmp (oz, sz, oi, si, c); + + /* c * (2^K - 1) */ + mpz_mul_si (oz, sz, 2*c); + if (c == -1) + mpz_ui_sub (oz, 1, oz); /* oz = sz * 2 + 1 */ + else + mpz_sub_ui (oz, oz, 1); /* oz = sz * 2 - 1 */ + if (mpz_fits_slong_p (oz)) + oi = (si - c) * 2 + c; + else + overflow_count++; + + check_si_cmp (oz, sz, oi, si, c); + }; + + mpz_clear (sz); + mpz_clear (oz); +} + +void +try_fits_slong_p (void) +{ + mpz_t x; + mpz_init_set_si (x, LONG_MAX); + if (!mpz_fits_slong_p (x)) + { + printf ("mpz_fits_slong_p (LONG_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_slong_p (x)) + { + printf ("mpz_fits_slong_p (LONG_MAX + 1) true!\n"); + abort (); + } + mpz_set_si (x, LONG_MIN); + if (!mpz_fits_slong_p (x)) + { + printf ("mpz_fits_slong_p (LONG_MIN) false!\n"); + abort (); + } + mpz_sub_ui (x, x, 1); + if (mpz_fits_slong_p (x)) + { + printf ("mpz_fits_slong_p (LONG_MIN - 1) true!\n"); + abort (); + } + + mpz_clear (x); +} + +void +try_fits_utype_p (void) +{ + mpz_t x; + mpz_init (x); + if (!mpz_fits_ulong_p (x)) + { + printf ("mpz_fits_ulong_p (0) false!\n"); + abort (); + } + if (!mpz_fits_uint_p (x)) + { + printf ("mpz_fits_uint_p (0) false!\n"); + abort (); + } + if (!mpz_fits_ushort_p (x)) + { + printf ("mpz_fits_udhort_p (0) false!\n"); + abort (); + } + mpz_set_si (x, -1); + if (mpz_fits_ulong_p (x)) + { + printf ("mpz_fits_ulong_p (- 1) true!\n"); + abort (); + } + if (mpz_fits_uint_p (x)) + { + printf ("mpz_fits_uint_p (- 1) true!\n"); + abort (); + } + if (mpz_fits_ushort_p (x)) + { + printf ("mpz_fits_ushort_p (- 1) true!\n"); + abort (); + } + mpz_set_ui (x, ULONG_MAX); + if (!mpz_fits_ulong_p (x)) + { + printf ("mpz_fits_ulong_p (ULONG_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_ulong_p (x)) + { + printf ("mpz_fits_ulong_p (ULONG_MAX + 1) true!\n"); + abort (); + } + mpz_set_ui (x, UINT_MAX); + if (!mpz_fits_uint_p (x)) + { + printf ("mpz_fits_uint_p (UINT_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_uint_p (x)) + { + printf ("mpz_fits_uint_p (UINT_MAX + 1) true!\n"); + abort (); + } + mpz_set_ui (x, USHRT_MAX); + if (!mpz_fits_ushort_p (x)) + { + printf ("mpz_fits_ushort_p (USHRT_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_ushort_p (x)) + { + printf ("mpz_fits_ushort_p (USHRT_MAX + 1) true!\n"); + abort (); + } + + mpz_clear (x); +} + +void +try_fits_sint_p (void) +{ + mpz_t x; + mpz_init_set_si (x, INT_MAX); + if (!mpz_fits_sint_p (x)) + { + printf ("mpz_fits_sint_p (INT_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_sint_p (x)) + { + printf ("mpz_fits_sint_p (INT_MAX + 1) true!\n"); + abort (); + } + mpz_set_si (x, INT_MIN); + if (!mpz_fits_sint_p (x)) + { + printf ("mpz_fits_sint_p (INT_MIN) false!\n"); + abort (); + } + mpz_sub_ui (x, x, 1); + if (mpz_fits_sint_p (x)) + { + printf ("mpz_fits_sint_p (INT_MIN - 1) true!\n"); + abort (); + } + + mpz_clear (x); +} + +void +try_fits_sshort_p (void) +{ + mpz_t x; + mpz_init_set_si (x, SHRT_MAX); + if (!mpz_fits_sshort_p (x)) + { + printf ("mpz_fits_sshort_p (SHRT_MAX) false!\n"); + abort (); + } + mpz_add_ui (x, x, 1); + if (mpz_fits_sshort_p (x)) + { + printf ("mpz_fits_sshort_p (SHRT_MAX + 1) true!\n"); + abort (); + } + mpz_set_si (x, SHRT_MIN); + if (!mpz_fits_sshort_p (x)) + { + printf ("mpz_fits_sshort_p (SHRT_MIN) false!\n"); + abort (); + } + mpz_sub_ui (x, x, 1); + if (mpz_fits_sshort_p (x)) + { + printf ("mpz_fits_sshort_p (SHRT_MIN - 1) true!\n"); + abort (); + } + + mpz_clear (x); +} + +void +testmain (int argc, char *argv[]) +{ + try_fits_slong_p (); + try_fits_sint_p (); + try_fits_sshort_p (); + try_fits_utype_p (); + try_op_si (-1); + try_op_si (1); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-sqrt.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-sqrt.c new file mode 100644 index 0000000..dd4c83a --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-sqrt.c @@ -0,0 +1,181 @@ +/* + +Copyright 2012, 2014, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 9000 + +/* Called when s is supposed to be floor(sqrt(u)), and r = u - s^2 */ +static int +sqrtrem_valid_p (const mpz_t u, const mpz_t s, const mpz_t r) +{ + mpz_t t; + + mpz_init (t); + mpz_mul (t, s, s); + mpz_sub (t, u, t); + if (mpz_sgn (t) < 0 || mpz_cmp (t, r) != 0) + { + mpz_clear (t); + return 0; + } + mpz_add_ui (t, s, 1); + mpz_mul (t, t, t); + if (mpz_cmp (t, u) <= 0) + { + mpz_clear (t); + return 0; + } + + mpz_clear (t); + return 1; +} + +void +mpz_mpn_sqrtrem (mpz_t s, mpz_t r, const mpz_t u) +{ + mp_limb_t *sp, *rp; + mp_size_t un, sn, ret; + + un = mpz_size (u); + + mpz_xor (s, s, u); + sn = (un + 1) / 2; + sp = mpz_limbs_write (s, sn + 1); + sp [sn] = 11; + + if (un & 1) + rp = NULL; /* Exploits the fact that r already is correct. */ + else { + mpz_add (r, u, s); + rp = mpz_limbs_write (r, un + 1); + rp [un] = 19; + } + + ret = mpn_sqrtrem (sp, rp, mpz_limbs_read (u), un); + + if (sp [sn] != 11) + { + fprintf (stderr, "mpn_sqrtrem buffer overrun on sp.\n"); + abort (); + } + if (un & 1) { + if ((ret != 0) != (mpz_size (r) != 0)) { + fprintf (stderr, "mpn_sqrtrem wrong return value with NULL.\n"); + abort (); + } + } else { + mpz_limbs_finish (r, ret); + if ((size_t) ret != mpz_size (r)) { + fprintf (stderr, "mpn_sqrtrem wrong return value.\n"); + abort (); + } + if (rp [un] != 19) + { + fprintf (stderr, "mpn_sqrtrem buffer overrun on rp.\n"); + abort (); + } + } + + mpz_limbs_finish (s, (un + 1) / 2); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t u, s, r; + + mpz_init (s); + mpz_init (r); + + mpz_init_set_si (u, -1); + if (mpz_perfect_square_p (u)) + { + fprintf (stderr, "mpz_perfect_square_p failed on -1.\n"); + abort (); + } + + if (!mpz_perfect_square_p (s)) + { + fprintf (stderr, "mpz_perfect_square_p failed on 0.\n"); + abort (); + } + + for (i = 0; i < COUNT; i++) + { + mini_rrandomb (u, MAXBITS - (i & 0xFF)); + mpz_sqrtrem (s, r, u); + + if (!sqrtrem_valid_p (u, s, r)) + { + fprintf (stderr, "mpz_sqrtrem failed:\n"); + dump ("u", u); + dump ("sqrt", s); + dump ("rem", r); + abort (); + } + + mpz_mpn_sqrtrem (s, r, u); + + if (!sqrtrem_valid_p (u, s, r)) + { + fprintf (stderr, "mpn_sqrtrem failed:\n"); + dump ("u", u); + dump ("sqrt", s); + dump ("rem", r); + abort (); + } + + if (mpz_sgn (r) == 0) { + mpz_neg (u, u); + mpz_sub_ui (u, u, 1); + } + + if ((mpz_sgn (u) <= 0 || (i & 1)) ? + mpz_perfect_square_p (u) : + mpn_perfect_square_p (mpz_limbs_read (u), mpz_size (u))) + { + fprintf (stderr, "mp%s_perfect_square_p failed on non square:\n", + (mpz_sgn (u) <= 0 || (i & 1)) ? "z" : "n"); + dump ("u", u); + abort (); + } + + mpz_mul (u, s, s); + if (!((mpz_sgn (u) <= 0 || (i & 1)) ? + mpz_perfect_square_p (u) : + mpn_perfect_square_p (mpz_limbs_read (u), mpz_size (u)))) + { + fprintf (stderr, "mp%s_perfect_square_p failed on square:\n", + (mpz_sgn (u) <= 0 || (i & 1)) ? "z" : "n"); + dump ("u", u); + abort (); + } + + } + mpz_clear (u); + mpz_clear (s); + mpz_clear (r); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-str.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-str.c new file mode 100644 index 0000000..d4dce1e --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-str.c @@ -0,0 +1,332 @@ +/* + +Copyright 2012-2014, 2016 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <assert.h> +#include <limits.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 2000 + +#define GMP_LIMB_BITS (sizeof(mp_limb_t) * CHAR_BIT) +#define MAXLIMBS ((MAXBITS + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS) + +static void +test_small (void) +{ + struct { + const char *input; + const char *decimal; + } data[] = { + { "183407", "183407" }, + { " 763959", "763959 " }, + { "9 81999", "981999" }, + { "10\t7398 ", "107398" }, + { "-9585 44", "-00958544" }, + { "-0", "0000" }, + { " -000 ", "0" }, + { "0704436", "231710" }, + /* Check the case of large number of leading zeros. */ + { "0000000000000000000000000", "0000000000000000000000000" }, + { "000000000000000000000000704436", "000000000000000000000000231710" }, + { " 02503517", "689999" }, + { "0 1312143", "365667" }, + { "-03 274062", "-882738" }, + { "012\t242", "005282" }, + { "0b11010111110010001111", "883855" }, + { " 0b11001010010100001", "103585" }, + { "-0b101010110011101111", "-175343" }, + { "0b 1111111011011100110", "521958" }, + { "0b1 1111110111001000011", "1044035" }, + { " 0x53dfc", "343548" }, + { "0xfA019", "1024025" }, + { "0x 642d1", "410321" }, + { "0x5 8067", "360551" }, + { "-0xd6Be6", "-879590" }, + { "\t0B1110000100000000011", "460803" }, + { "0B\t1111110010010100101", "517285" }, + { "0B1\t010111101101110100", "359284" }, + { "-0B101\t1001101111111001", "-367609" }, + { "0B10001001010111110000", "562672" }, + { "0Xe4B7e", "936830" }, + { "0X1E4bf", "124095" }, + { "-0Xfdb90", "-1039248" }, + { "0X7fc47", "523335" }, + { "0X8167c", "530044" }, + /* Some invalid inputs */ + { "", NULL }, + { "0x", NULL }, + { "0b", NULL }, + { "0z", NULL }, + { "-", NULL }, + { "-0x ", NULL }, + { "0|1", NULL }, + { "4+4", NULL }, + { "0ab", NULL }, + { "10x0", NULL }, + { "0xxab", NULL }, + { "ab", NULL }, + { "0%#", NULL }, + { "$foo", NULL }, + { NULL, NULL } + }; + unsigned i; + mpz_t a, b; + mpz_init (b); + + for (i = 0; data[i].input; i++) + { + int res = mpz_init_set_str (a, data[i].input, 0); + if (data[i].decimal) + { + if (res != 0) + { + fprintf (stderr, "mpz_set_str returned -1, input: %s\n", + data[i].input); + abort (); + } + if (mpz_set_str (b, data[i].decimal, 10) != 0) + { + fprintf (stderr, "mpz_set_str returned -1, decimal input: %s\n", + data[i].input); + abort (); + } + if (mpz_cmp (a, b) != 0) + { + fprintf (stderr, "mpz_set_str failed for input: %s\n", + data[i].input); + + dump ("got", a); + dump ("ref", b); + abort (); + } + } + else if (res != -1) + { + fprintf (stderr, "mpz_set_str returned %d, invalid input: %s\n", + res, data[i].input); + abort (); + } + mpz_clear (a); + } + + mpz_clear (b); +} + +void +testmain (int argc, char **argv) +{ + unsigned i; + char *ap; + char *bp; + char *rp; + size_t bn, rn, arn, bps; + + mpz_t a, b; + + FILE *tmp; + + test_small (); + + mpz_init (a); + mpz_init (b); + + tmp = tmpfile (); + if (!tmp) + fprintf (stderr, + "Failed to create temporary file. Skipping mpz_out_str tests.\n"); + + if (mpz_out_str (tmp, 63, a) != 0) + { + printf ("mpz_out_str did not return 0 (error) with base > 62\n"); + abort (); + } + + if (mpz_out_str (tmp, -37, a) != 0) + { + printf ("mpz_out_str did not return 0 (error) with base < -37\n"); + abort (); + } + + for (i = 0; i < COUNT; i++) + { + int base; + for (base = 0; base <= 62; base += 1 + (base == 0)) + { + hex_random_str_op (MAXBITS, (i&1 || base > 36) ? base: -base, &ap, &rp); + if (mpz_set_str (a, ap, 16) != 0) + { + fprintf (stderr, "mpz_set_str failed on input %s\n", ap); + abort (); + } + + rn = strlen (rp); + arn = rn - (rp[0] == '-'); + + bn = mpz_sizeinbase (a, base ? base : 10); + if (bn < arn || bn > (arn + 1)) + { + fprintf (stderr, "mpz_sizeinbase failed:\n"); + dump ("a", a); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base %d, correct size %u, got %u\n", + base, (unsigned) arn, (unsigned)bn); + abort (); + } + bp = mpz_get_str (NULL, (i&1 || base > 36) ? base: -base, a); + bps = strlen(bp) + 1; + if (strcmp (bp, rp)) + { + fprintf (stderr, "mpz_get_str failed:\n"); + dump ("a", a); + fprintf (stderr, "b = %s\n", bp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", rp); + abort (); + } + + /* Just a few tests with file i/o. */ + if (tmp && i < 20) + { + size_t tn; + rewind (tmp); + tn = mpz_out_str (tmp, (i&1 || base > 36) ? base: -base, a); + if (tn != rn) + { + fprintf (stderr, "mpz_out_str, bad return value:\n"); + dump ("a", a); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base %d, correct size %u, got %u\n", + base, (unsigned) rn, (unsigned)tn); + abort (); + } + rewind (tmp); + memset (bp, 0, rn); + tn = fread (bp, 1, rn, tmp); + if (tn != rn) + { + fprintf (stderr, + "fread failed, expected %lu bytes, got only %lu.\n", + (unsigned long) rn, (unsigned long) tn); + abort (); + } + + if (memcmp (bp, rp, rn) != 0) + { + fprintf (stderr, "mpz_out_str failed:\n"); + dump ("a", a); + fprintf (stderr, "b = %s\n", bp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", rp); + abort (); + } + } + + mpz_set_str (b, rp, base); + + if (mpz_cmp (a, b)) + { + fprintf (stderr, "mpz_set_str failed:\n"); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", ap); + fprintf (stderr, " base = 16\n"); + dump ("b", b); + dump ("r", a); + abort (); + } + + /* Test mpn interface */ + if (base && mpz_sgn (a)) + { + size_t i; + const char *absr; + mp_limb_t t[MAXLIMBS]; + size_t tn = mpz_size (a); + + assert (tn <= MAXLIMBS); + mpn_copyi (t, a->_mp_d, tn); + + bn = mpn_get_str ((unsigned char *) bp, base, t, tn); + if (bn != arn) + { + fprintf (stderr, "mpn_get_str failed:\n"); + fprintf (stderr, "returned length: %lu (bad)\n", (unsigned long) bn); + fprintf (stderr, "expected: %lu\n", (unsigned long) arn); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", ap); + fprintf (stderr, " base = 16\n"); + dump ("b", b); + dump ("r", a); + abort (); + } + absr = rp + (rp[0] == '-'); + + for (i = 0; i < bn; i++) + { + unsigned char digit = absr[i]; + char value; + if (digit >= '0' && digit <= '9') + value = digit - '0'; + else if (digit >= 'a' && digit <= 'z') + value = digit - 'a' + ((base > 36) ? 36 : 10); + else if (digit >= 'A' && digit <= 'Z') + value = digit - 'A' + 10; + else + { + fprintf (stderr, "Internal error in test.\n"); + abort(); + } + if (bp[i] != value) + { + fprintf (stderr, "mpn_get_str failed:\n"); + fprintf (stderr, "digit %lu: %d (bad)\n", (unsigned long) i, bp[i]); + fprintf (stderr, "expected: %d\n", value); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", ap); + fprintf (stderr, " base = 16\n"); + dump ("b", b); + dump ("r", a); + abort (); + } + } + tn = mpn_set_str (t, (unsigned char *) bp, bn, base); + if (tn != mpz_size (a) || mpn_cmp (t, a->_mp_d, tn)) + { + fprintf (stderr, "mpn_set_str failed:\n"); + fprintf (stderr, "r = %s\n", rp); + fprintf (stderr, " base = %d\n", base); + fprintf (stderr, "r = %s\n", ap); + fprintf (stderr, " base = 16\n"); + dump ("r", a); + abort (); + } + } + free (ap); + free (rp); + testfree (bp, bps); + } + } + mpz_clear (a); + mpz_clear (b); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/t-sub.c b/vendor/gmp-6.3.0/mini-gmp/tests/t-sub.c new file mode 100644 index 0000000..e230fda --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/t-sub.c @@ -0,0 +1,71 @@ +/* + +Copyright 2012, 2013 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdlib.h> +#include <stdio.h> + +#include "testutils.h" + +#define MAXBITS 400 +#define COUNT 10000 + +void +testmain (int argc, char **argv) +{ + unsigned i; + mpz_t a, b, res, res_ui, ref; + + mpz_init (a); + mpz_init (b); + mpz_init (res); + mpz_init (res_ui); + mpz_init (ref); + + for (i = 0; i < COUNT; i++) + { + mini_random_op3 (OP_SUB, MAXBITS, a, b, ref); + mpz_sub (res, a, b); + if (mpz_cmp (res, ref)) + { + fprintf (stderr, "mpz_sub failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res); + dump ("ref", ref); + abort (); + } + if (mpz_fits_ulong_p (a)) { + mpz_ui_sub (res_ui, mpz_get_ui (a), b); + if (mpz_cmp (res_ui, ref)) + { + fprintf (stderr, "mpz_ui_sub failed:\n"); + dump ("a", a); + dump ("b", b); + dump ("r", res_ui); + dump ("ref", ref); + abort (); + } + } + } + mpz_clear (a); + mpz_clear (b); + mpz_clear (res); + mpz_clear (res_ui); + mpz_clear (ref); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/testutils.c b/vendor/gmp-6.3.0/mini-gmp/tests/testutils.c new file mode 100644 index 0000000..46e368a --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/testutils.c @@ -0,0 +1,196 @@ +/* + +Copyright 2013-2015, 2018 Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include "testutils.h" + +/* Include it here, so we we could tweak, e.g., how MPZ_REALLOC + works. */ +#include "../mini-gmp.c" +#include "../mini-mpq.c" + +static size_t total_alloc = 0; + +/* Custom memory allocation to track memory usage, and add a small red + zone. + + About alignment: In general, getting a block from malloc, and + incrementing it by sizeof(size_t), like we do here, might give a + pointer which is not properly aligned for all types. But the + largest type we allocate space for is unsigned long (mp_limb_t), + which shouldn't have stricter alignment requirements than + size_t. */ + +static unsigned char block_end[8] = + { 0x7c, 0x37, 0xd6, 0x12, 0xa8, 0x6c, 0x01, 0xd1 }; + +static void * +block_init (size_t *block, size_t size) +{ + char *p; + *block++ = size; + + p = (char *) block; + memcpy (p + size, block_end, sizeof(block_end)); + + total_alloc += size; + return p; +} + +/* Check small redzone, return pointer to malloced block. */ +static size_t * +block_check (void *p) +{ + size_t *block = (size_t *) p - 1; + size_t size = block[0]; + + if (memcmp ((char *)p + size, block_end, sizeof(block_end)) != 0) + { + fprintf (stderr, "red zone overwritten.\n"); + abort (); + } + total_alloc -= size; + return block; +} + +static void * +tu_alloc (size_t size) +{ + size_t *block = (size_t *) malloc (sizeof(size_t) + size + sizeof(block_end)); + if (!block) + { + fprintf (stderr, "Virtual memory exhausted.\n"); + abort (); + } + + return block_init (block, size); +} + +static void * +tu_realloc (void *p, size_t old_size, size_t new_size) +{ + size_t *block; + size_t *old_block = block_check (p); + if (old_block[0] != old_size) + { + fprintf (stderr, "%s:%d: bad old_size: want %ld, got %ld.\n", __FILE__, __LINE__, + (long)old_block[0], (long)old_size); + abort (); + } + + block = (size_t *) realloc (old_block, sizeof(size_t) + new_size + sizeof(block_end)); + if (!block) + { + fprintf (stderr, "Virtual memory exhausted.\n"); + abort (); + } + + return block_init (block, new_size); +} + +static void +tu_free (void *p, size_t old_size) +{ + size_t *old_block = block_check (p); + if (old_block[0] != old_size && old_size != 0) + { + fprintf (stderr, "%s:%d: bad old_size: want %ld, got %ld.\n", __FILE__, __LINE__, + (long)old_block[0], (long)old_size); + abort (); + } + free (old_block); +} + +/* Free memory allocated via mini-gmp allocation function. */ +void +testfree (void *p, size_t size) +{ + void (*freefunc) (void *, size_t); + mp_get_memory_functions (NULL, NULL, &freefunc); + + freefunc (p, size); +} + +int +main (int argc, char **argv) +{ + hex_random_init (); + + mp_set_memory_functions (tu_alloc, tu_realloc, tu_free); + + /* Currently, t-comb seems to be the only program accepting any + arguments. It might make sense to parse common arguments here. */ + testmain (argc, argv); + + if (total_alloc != 0) + { + fprintf (stderr, "Memory leaked: %lu bytes.\n", + (unsigned long) total_alloc); + abort (); + } + return 0; +} + +void +testhalves (int count, void (*tested_fun) (int)) +{ + void (*freefunc) (void *, size_t); + void *(*reallocfunc) (void *, size_t, size_t); + void *(*allocfunc) (size_t); + size_t initial_alloc; + + mp_get_memory_functions (&allocfunc, &reallocfunc, &freefunc); + initial_alloc = total_alloc; + (*tested_fun) (count / 2); + if (initial_alloc != total_alloc) + { + fprintf (stderr, "First half, memory leaked: %lu bytes.\n", + (unsigned long) total_alloc - initial_alloc); + abort (); + } + mp_set_memory_functions (NULL, NULL, NULL); + (*tested_fun) (count / 2); + mp_set_memory_functions (allocfunc, reallocfunc, freefunc); +} + +void +dump (const char *label, const mpz_t x) +{ + char *buf = mpz_get_str (NULL, 16, x); + fprintf (stderr, "%s: %s\n", label, buf); + testfree (buf, strlen(buf) + 1); +} + +void +mpz_set_str_or_abort (mpz_ptr z, const char *str, int base) +{ + if (mpz_set_str (z, str, base) != 0) + { + fprintf (stderr, "ERROR: mpz_set_str failed\n"); + fprintf (stderr, " str = \"%s\"\n", str); + fprintf (stderr, " base = %d\n", base); + abort(); + } +} + +int +mpz_lucas_mod (mpz_t V, mpz_t Qk, long Q, + mp_bitcnt_t b0, const mpz_t n) +{ + return gmp_lucas_mod (V, Qk, Q, b0, n); +} diff --git a/vendor/gmp-6.3.0/mini-gmp/tests/testutils.h b/vendor/gmp-6.3.0/mini-gmp/tests/testutils.h new file mode 100644 index 0000000..bcc08c5 --- /dev/null +++ b/vendor/gmp-6.3.0/mini-gmp/tests/testutils.h @@ -0,0 +1,42 @@ +/* + +Copyright 2013, 2014, 2018, Free Software Foundation, Inc. + +This file is part of the GNU MP Library test suite. + +The GNU MP Library test suite is free software; you can redistribute it +and/or modify it under the terms of the GNU General Public License as +published by the Free Software Foundation; either version 3 of the License, +or (at your option) any later version. + +The GNU MP Library test suite is distributed in the hope that it will be +useful, but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +Public License for more details. + +You should have received a copy of the GNU General Public License along with +the GNU MP Library test suite. If not, see https://www.gnu.org/licenses/. */ + +#include <stdio.h> +#include <stdlib.h> + +#include "mini-random.h" + +#define numberof(x) (sizeof (x) / sizeof ((x)[0])) + +void testmain (int argc, char **argv); + +void testhalves (int count, void (*tested_fun) (int)); + +void testfree (void *p, size_t size); + +void +dump (const char *label, const mpz_t x); + +void +mpz_set_str_or_abort (mpz_ptr z, const char *str, int base); + +/* Prototype for wrappers to internal functions to be tested. */ +int +mpz_lucas_mod (mpz_t V, mpz_t Qk, long Q, + mp_bitcnt_t b0, const mpz_t n); |