summaryrefslogtreecommitdiff
path: root/src/mpfr-mini-gmp.c
diff options
context:
space:
mode:
authorzimmerma <zimmerma@280ebfd0-de03-0410-8827-d642c229c3f4>2014-01-16 22:03:40 +0000
committerzimmerma <zimmerma@280ebfd0-de03-0410-8827-d642c229c3f4>2014-01-16 22:03:40 +0000
commitdd36bc8f4acebbc891952073628b895ddd444388 (patch)
tree7deed3e87b9739df1dc773c9915034fbb41c71c9 /src/mpfr-mini-gmp.c
parentb8ef4f9b79a2a989a601bf0fad918541aaada8cd (diff)
downloadmpfr-dd36bc8f4acebbc891952073628b895ddd444388.tar.gz
added two new files for mini-gmp interface
git-svn-id: svn://scm.gforge.inria.fr/svn/mpfr/trunk@8754 280ebfd0-de03-0410-8827-d642c229c3f4
Diffstat (limited to 'src/mpfr-mini-gmp.c')
-rw-r--r--src/mpfr-mini-gmp.c322
1 files changed, 322 insertions, 0 deletions
diff --git a/src/mpfr-mini-gmp.c b/src/mpfr-mini-gmp.c
new file mode 100644
index 000000000..993f0509a
--- /dev/null
+++ b/src/mpfr-mini-gmp.c
@@ -0,0 +1,322 @@
+/* mpfr-mini-gmp.c -- Interface functions for mini-gmp.
+
+Copyright 2014 Free Software Foundation, Inc.
+Contributed by the AriC and Caramel projects, INRIA.
+
+This file is part of the GNU MPFR Library.
+
+The GNU MPFR Library is free software; you can redistribute it and/or modify
+it under the terms of the GNU Lesser 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 MPFR Library 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 Lesser General Public
+License for more details.
+
+You should have received a copy of the GNU Lesser General Public License
+along with the GNU MPFR Library; see the file COPYING.LESSER. If not, see
+http://www.gnu.org/licenses/ or write to the Free Software Foundation, Inc.,
+51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. */
+
+#ifdef WANT_MINI_GMP
+
+#include "mpfr-impl.h"
+#include "mpfr-mini-gmp.h"
+
+#ifndef mp_bits_per_limb
+const int mp_bits_per_limb = GMP_NUMB_BITS;
+#endif
+
+#ifdef WANT_gmp_randinit_default
+void
+gmp_randinit_default (gmp_randstate_t state)
+{
+}
+#endif
+
+#ifdef WANT_gmp_randseed_ui
+void
+gmp_randseed_ui (gmp_randstate_t state, const mpz_t seed)
+{
+ srand48 (mpz_get_ui (seed));
+}
+#endif
+
+#ifdef WANT_gmp_randclear
+void
+gmp_randclear (gmp_randstate_t state)
+{
+}
+#endif
+
+#ifdef WANT_gmp_default_alloc
+void *
+gmp_default_alloc (size_t s)
+{
+ return malloc (s);
+}
+#endif
+
+#ifdef WANT_gmp_default_realloc
+void *
+gmp_default_realloc (void *x, size_t olds, size_t s)
+{
+ return realloc (x, s);
+}
+#endif
+
+#ifdef WANT_gmp_default_free
+void
+gmp_default_free (void *x, size_t s)
+{
+ free (x);
+}
+#endif
+
+#ifdef WANT_mpn_scan1
+mp_bitcnt_t
+mpn_scan1 (const mp_limb_t *s, mp_bitcnt_t n)
+{
+ while (1)
+ {
+ if (s[n / GMP_NUMB_BITS] & ((mp_limb_t) 1 << (n % GMP_NUMB_BITS)))
+ return n;
+ n ++;
+ }
+}
+#endif
+
+#ifdef WANT_mpz_perfect_square_p
+int
+mpz_perfect_square_p (const mpz_t z)
+{
+ mpz_t s, r;
+ int ret;
+
+ if (mpz_sgn (z) < 0)
+ return 0;
+
+ mpz_init (s);
+ mpz_init (r);
+ mpz_sqrtrem (s, r, z);
+ ret = mpz_sgn (r) == 0;
+ mpz_clear (s);
+ mpz_clear (r);
+ return ret;
+}
+#endif
+
+#ifdef WANT_mpz_addmul_ui
+void
+mpz_addmul_ui (mpz_t a, const mpz_t b, unsigned long c)
+{
+ mpz_t t;
+
+ mpz_init (t);
+ mpz_mul_ui (t, b, c);
+ mpz_add (a, a, t);
+ mpz_clear (t);
+}
+#endif
+
+#ifdef WANT_mpn_divrem_1
+mp_limb_t
+mpn_divrem_1 (mp_limb_t *qp, mp_size_t qxn, mp_limb_t *np, mp_size_t nn,
+ mp_limb_t d0)
+{
+ mpz_t q, r, n, d;
+ mp_limb_t ret;
+
+ d->_mp_d = gmp_default_alloc (sizeof (mp_limb_t));
+ d->_mp_d[0] = d0;
+ d->_mp_size = 1;
+ mpz_init (q);
+ mpz_init (r);
+ if (qxn == 0)
+ {
+ n->_mp_d = np;
+ n->_mp_size = nn;
+ }
+ else
+ {
+ mpz_init2 (n, (nn + qxn) * GMP_NUMB_BITS);
+ mpn_copyi (n->_mp_d + qxn, np, nn);
+ mpn_zero (n->_mp_d, qxn);
+ n->_mp_size = nn + qxn;
+ }
+ mpz_tdiv_qr (q, r, n, d);
+ MPFR_ASSERTN(q->_mp_size == nn + qxn);
+ mpn_copyi (qp, q->_mp_d, nn + qxn);
+ MPFR_ASSERTN(r->_mp_size == 1);
+ ret = r->_mp_d[0];
+ mpz_clear (q);
+ mpz_clear (r);
+ if (qxn != 0)
+ mpz_clear (n);
+ return ret;
+}
+#endif
+
+#ifdef WANT_mpz_realloc2
+void
+mpz_realloc2 (mpz_t X, mp_bitcnt_t N)
+{
+ unsigned long n = (N - 1) / GMP_NUMB_BITS + 1;
+
+ if (n > X->_mp_alloc)
+ {
+ X->_mp_d = gmp_default_realloc (X->_mp_d, X->_mp_alloc, n);
+ X->_mp_alloc = n;
+ }
+}
+#endif
+
+#ifdef WANT_mpz_urandomb
+void
+mpz_urandomb (mpz_t ROP, gmp_randstate_t STATE, mp_bitcnt_t N)
+{
+ unsigned long n;
+
+ mpz_realloc2 (ROP, N);
+ n = (N - 1) / GMP_NUMB_BITS + 1; /* number of limbs */
+ while (n--)
+ ROP->_mp_d[n] = lrand48 ();
+}
+#endif
+
+#ifdef WANT_mpn_zero
+void
+mpn_zero (mp_limb_t *RP, mp_size_t N)
+{
+ memset (RP, 0, N * sizeof (mp_limb_t));
+}
+#endif
+
+#ifdef WANT_mpn_popcount
+mp_bitcnt_t
+mpn_popcount (const mp_limb_t *S1P, mp_size_t N)
+{
+ mpz_t t;
+
+ t->_mp_d = (mp_limb_t*) S1P;
+ t->_mp_size = N;
+ return mpz_popcount (t);
+}
+#endif
+
+#ifdef WANT_mpn_divrem
+mp_limb_t
+mpn_divrem (mp_limb_t *qp, mp_size_t qn, mp_limb_t *np,
+ mp_size_t nn, const mp_limb_t *dp, mp_size_t dn)
+{
+ mpz_t q, r, n, d;
+ mp_limb_t ret;
+
+ MPFR_ASSERTN(qn == 0);
+ qn = nn - dn;
+ n->_mp_d = np;
+ n->_mp_size = nn;
+ d->_mp_d = (mp_limb_t*) dp;
+ d->_mp_size = dn;
+ mpz_init (q);
+ mpz_init (r);
+ mpz_tdiv_qr (q, r, n, d);
+ MPFR_ASSERTN(q->_mp_size == qn || q->_mp_size == qn + 1);
+ mpn_copyi (qp, q->_mp_d, qn);
+ ret = (q->_mp_size == qn) ? 0 : q->_mp_d[qn];
+ MPFR_ASSERTN(r->_mp_size == dn);
+ mpn_copyi (np, r->_mp_d, dn);
+ mpz_clear (q);
+ mpz_clear (r);
+ return ret;
+}
+#endif
+
+#ifdef WANT_mpz_submul
+void
+mpz_submul (mpz_t ROP, const mpz_t OP1, const mpz_t OP2)
+{
+ mpz_t t;
+
+ mpz_init (t);
+ mpz_mul (t, OP1, OP2);
+ mpz_sub (ROP, ROP, t);
+ mpz_clear (t);
+}
+#endif
+
+#ifdef WANT_mpz_addmul
+void
+mpz_addmul (mpz_t ROP, const mpz_t OP1, const mpz_t OP2)
+{
+ mpz_t t;
+
+ mpz_init (t);
+ mpz_mul (t, OP1, OP2);
+ mpz_add (ROP, ROP, t);
+ mpz_clear (t);
+}
+#endif
+
+#ifdef WANT_mpn_tdiv_qr
+void
+mpn_tdiv_qr (mp_limb_t *QP, mp_limb_t *RP, mp_size_t QXN,
+ const mp_limb_t *NP, mp_size_t NN,
+ const mp_limb_t *DP, mp_size_t DN)
+{
+ mpz_t q, r, n, d;
+
+ MPFR_ASSERTN(QXN == 0);
+ n->_mp_d = (mp_limb_t*) NP;
+ n->_mp_size = NN;
+ d->_mp_d = (mp_limb_t*) DP;
+ d->_mp_size = DN;
+ mpz_init (q);
+ mpz_init (r);
+ mpz_tdiv_qr (q, r, n, d);
+ MPFR_ASSERTN(q->_mp_size > 0);
+ mpn_copyi (QP, q->_mp_d, q->_mp_size);
+ MPFR_ASSERTN(r->_mp_size > 0);
+ mpn_copyi (RP, r->_mp_d, r->_mp_size);
+ mpz_clear (q);
+ mpz_clear (r);
+}
+#endif
+
+#ifdef WANT_mpn_sqrtrem
+mp_size_t
+mpn_sqrtrem (mp_limb_t *SP, mp_limb_t *RP, const mp_limb_t *NP, mp_size_t N)
+{
+ mpz_t s, r, n;
+ mp_size_t sn = (N + 1) >> 1, ret;
+
+ n->_mp_d = (mp_limb_t*) NP;
+ n->_mp_size = N;
+ mpz_init (s);
+ mpz_init (r);
+ mpz_sqrtrem (s, r, n);
+ if (s->_mp_size > 0)
+ mpn_copyi (SP, s->_mp_d, s->_mp_size);
+ if (s->_mp_size < sn)
+ mpn_zero (SP + s->_mp_size, sn - s->_mp_size);
+ if (r->_mp_size > 0)
+ mpn_copyi (RP, r->_mp_d, r->_mp_size);
+ ret = r->_mp_size;
+ mpz_clear (s);
+ mpz_clear (r);
+ return ret;
+}
+#endif
+
+#ifdef WANT_mpz_dump
+void
+mpz_dump (mpz_t z)
+{
+ mpz_out_str (stdout, 10, z);
+ putchar ('\n');
+}
+#endif
+
+#endif /* WANT_MINI_GMP */