[Gmp-commit] /var/hg/gmp: 5 new changesets
mercurial at gmplib.org
mercurial at gmplib.org
Sun Jul 12 08:20:33 CEST 2026
details: /var/hg/gmp/rev/c14ab54ef5ca
changeset: 18557:c14ab54ef5ca
user: Marco Bodrato <bodrato at mail.dm.unipi.it>
date: Sun Jul 12 08:15:55 2026 +0200
description:
mini-gmp/mini-gmp.[ch]: Add the new function mpz_perfect_square_root
details: /var/hg/gmp/rev/9597e16aee1b
changeset: 18558:9597e16aee1b
user: Marco Bodrato <bodrato at mail.dm.unipi.it>
date: Sun Jul 12 08:16:42 2026 +0200
description:
mini-gmp/tests/t-sqrt.c: Test mpz_perfect_square_root
details: /var/hg/gmp/rev/cf18512fa8ca
changeset: 18559:cf18512fa8ca
user: Marco Bodrato <bodrato at mail.dm.unipi.it>
date: Sun Jul 12 08:17:46 2026 +0200
description:
tests/mpz/t-perfsqr.c: Check the format of return values
details: /var/hg/gmp/rev/27b7b4d951c0
changeset: 18560:27b7b4d951c0
user: Marco Bodrato <bodrato at mail.dm.unipi.it>
date: Sun Jul 12 08:18:36 2026 +0200
description:
mpn/generic/sqrtrem.c (mpn_divappr_q): Return the highest limb instead of writing it
details: /var/hg/gmp/rev/29913bdd5d7c
changeset: 18561:29913bdd5d7c
user: Marco Bodrato <bodrato at mail.dm.unipi.it>
date: Sun Jul 12 08:19:13 2026 +0200
description:
ChangeLog
diffstat:
ChangeLog | 7 +++
mini-gmp/ChangeLog | 7 +++
mini-gmp/mini-gmp.c | 17 +++++++-
mini-gmp/mini-gmp.h | 1 +
mini-gmp/tests/t-sqrt.c | 87 ++++++++++++++++++++++++++++++++++--------------
mpn/generic/sqrtrem.c | 6 +-
tests/mpz/reuse.c | 3 +-
tests/mpz/t-perfsqr.c | 8 ++-
8 files changed, 100 insertions(+), 36 deletions(-)
diffs (truncated from 302 to 300 lines):
diff -r ac62fde50484 -r 29913bdd5d7c ChangeLog
--- a/ChangeLog Sat Jul 04 21:35:55 2026 +0200
+++ b/ChangeLog Sun Jul 12 08:19:13 2026 +0200
@@ -1,3 +1,10 @@
+2026-07-12 Marco Bodrato <marco.bodrato at protonmail.com>
+
+ * tests/mpz/t-perfsqr.c: Check the format of return values.
+
+ * mpn/generic/sqrtrem.c (mpn_divappr_q): Return the highest limb
+ instead of writing it.
+
2026-07-04 Seth Troisi <sethtroisi at google.com>
* mpn/generic/perfsqr.c: New function mpn_probab_perfect_square_p.
diff -r ac62fde50484 -r 29913bdd5d7c mini-gmp/ChangeLog
--- a/mini-gmp/ChangeLog Sat Jul 04 21:35:55 2026 +0200
+++ b/mini-gmp/ChangeLog Sun Jul 12 08:19:13 2026 +0200
@@ -1,3 +1,10 @@
+2026-07-12 Marco Bodrato <marco.bodrato at protonmail.com>
+
+ * mini-gmp.c (mpz_perfect_square_root): New function.
+ (mpz_perfect_square_p): Use it.
+ * mini-gmp.h: Add declaration.
+ * tests/t-sqrt.c: Test the new function.
+
2026-06-26 Marco Bodrato <marco.bodrato at protonmail.com>
* mini-gmp.c (mpz_init_setbit): New function.
diff -r ac62fde50484 -r 29913bdd5d7c mini-gmp/mini-gmp.c
--- a/mini-gmp/mini-gmp.c Sat Jul 04 21:35:55 2026 +0200
+++ b/mini-gmp/mini-gmp.c Sun Jul 12 08:19:13 2026 +0200
@@ -3342,12 +3342,23 @@
}
int
-mpz_perfect_square_p (const mpz_t u)
+mpz_perfect_square_root (mpz_t r, const mpz_t u)
{
if (u->_mp_size <= 0)
- return (u->_mp_size == 0);
+ {
+ int ret = u->_mp_size == 0;
+ if (r != NULL)
+ r->_mp_size = 0;
+ return ret;
+ }
else
- return mpz_root (NULL, u, 2);
+ return mpz_root (r, u, 2);
+}
+
+int
+mpz_perfect_square_p (const mpz_t u)
+{
+ return mpz_perfect_square_root (NULL, u);
}
int
diff -r ac62fde50484 -r 29913bdd5d7c mini-gmp/mini-gmp.h
--- a/mini-gmp/mini-gmp.h Sat Jul 04 21:35:55 2026 +0200
+++ b/mini-gmp/mini-gmp.h Sun Jul 12 08:19:13 2026 +0200
@@ -212,6 +212,7 @@
void mpz_sqrtrem (mpz_t, mpz_t, const mpz_t);
void mpz_sqrt (mpz_t, const mpz_t);
+int mpz_perfect_square_root (mpz_t, const mpz_t);
int mpz_perfect_square_p (const mpz_t);
void mpz_pow_ui (mpz_t, const mpz_t, unsigned long);
diff -r ac62fde50484 -r 29913bdd5d7c mini-gmp/tests/t-sqrt.c
--- a/mini-gmp/tests/t-sqrt.c Sat Jul 04 21:35:55 2026 +0200
+++ b/mini-gmp/tests/t-sqrt.c Sun Jul 12 08:19:13 2026 +0200
@@ -1,6 +1,6 @@
/*
-Copyright 2012, 2014, Free Software Foundation, Inc.
+Copyright 2012, 2014, 2026, Free Software Foundation, Inc.
This file is part of the GNU MP Library test suite.
@@ -31,25 +31,24 @@
sqrtrem_valid_p (const mpz_t u, const mpz_t s, const mpz_t r)
{
mpz_t t;
+ int ret;
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;
+ ret = 0;
}
- mpz_add_ui (t, s, 1);
- mpz_mul (t, t, t);
- if (mpz_cmp (t, u) <= 0)
+ else
{
- mpz_clear (t);
- return 0;
+ mpz_add_ui (t, s, 1);
+ mpz_mul (t, t, t);
+ ret = mpz_cmp (t, u) > 0;
}
mpz_clear (t);
- return 1;
+ return ret;
}
void
@@ -105,6 +104,7 @@
testmain (int argc, char **argv)
{
unsigned i;
+ int res;
mpz_t u, s, r;
mpz_init (s);
@@ -117,12 +117,26 @@
abort ();
}
+ /* FIXME: We should also check that r is still a valid mpz_t */
+ if (mpz_perfect_square_root (r, u))
+ {
+ fprintf (stderr, "mpz_perfect_square_root failed on -1.\n");
+ abort ();
+ }
+
if (!mpz_perfect_square_p (s))
{
fprintf (stderr, "mpz_perfect_square_p failed on 0.\n");
abort ();
}
+ res = mpz_perfect_square_root (r, s);
+ if (!res || mpz_cmp_ui (r, 0) != 0)
+ {
+ fprintf (stderr, "mpz_perfect_square_root failed on 0.\n");
+ abort ();
+ }
+
for (i = 0; i < COUNT; i++)
{
mini_rrandomb (u, MAXBITS - (i & 0xFF));
@@ -153,27 +167,48 @@
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)))
+ if (i & 2)
{
- fprintf (stderr, "mp%s_perfect_square_p failed on non square:\n",
- (mpz_sgn (u) <= 0 || (i & 1)) ? "z" : "n");
- dump ("u", u);
- abort ();
- }
+ 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))))
+ 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 ();
+ }
+ }
+ else
{
- fprintf (stderr, "mp%s_perfect_square_p failed on square:\n",
- (mpz_sgn (u) <= 0 || (i & 1)) ? "z" : "n");
- dump ("u", u);
- abort ();
+ /* FIXME: We should also check that r is still a valid mpz_t */
+ if (mpz_perfect_square_root (r, u))
+ {
+ fprintf (stderr, "mpz_perfect_square_root failed on non square:\n");
+ dump ("u", u);
+ abort ();
+ }
+
+ mpz_mul (u, s, s);
+ res = mpz_perfect_square_root (r, u);
+ if (!res || mpz_cmp (r, s) != 0)
+ {
+ fprintf (stderr, "mpz_perfect_square_root failed on square:\n");
+ dump ("u", u);
+ abort ();
+ }
}
-
}
mpz_clear (u);
mpz_clear (s);
diff -r ac62fde50484 -r 29913bdd5d7c mpn/generic/sqrtrem.c
--- a/mpn/generic/sqrtrem.c Sat Jul 04 21:35:55 2026 +0200
+++ b/mpn/generic/sqrtrem.c Sun Jul 12 08:19:13 2026 +0200
@@ -276,7 +276,7 @@
}
#if USE_DIVAPPR_Q
-static void
+static mp_limb_t
mpn_divappr_q (mp_ptr qp, mp_srcptr np, mp_size_t nn, mp_srcptr dp, mp_size_t dn, mp_ptr scratch)
{
gmp_pi1_t inv;
@@ -300,7 +300,7 @@
qh = mpn_mu_divappr_q (qp, np, nn, dp, dn, TMP_ALLOC_LIMBS (itch));
TMP_FREE;
}
- qp [nn - dn] = qh;
+ return qh;
}
#endif
@@ -344,7 +344,7 @@
qp = tp + n + 1; /* l + 2 */
TRACE(printf("div(appr)_q(,,%u,,%u) -> %u \n", (unsigned) n+1, (unsigned) h, (unsigned) (n + 1 - h + 1)));
#if USE_DIVAPPR_Q
- mpn_divappr_q (qp, tp, n + 1, sp + l, h, scratch);
+ qp [l + 1] = mpn_divappr_q (qp, tp, n + 1, sp + l, h, scratch);
#else
mpn_div_q (qp, tp, n + 1, sp + l, h, scratch);
#endif
diff -r ac62fde50484 -r 29913bdd5d7c tests/mpz/reuse.c
--- a/tests/mpz/reuse.c Sat Jul 04 21:35:55 2026 +0200
+++ b/tests/mpz/reuse.c Sun Jul 12 08:19:13 2026 +0200
@@ -2,7 +2,8 @@
Test all relevant functions except:
mpz_bin_ui
- mpz_nextprime
+ mpz_{next,prev}prime
+ mpz_perfect_square_root
mpz_mul_si
mpz_addmul_ui (should this really allow a+=a*c?)
diff -r ac62fde50484 -r 29913bdd5d7c tests/mpz/t-perfsqr.c
--- a/tests/mpz/t-perfsqr.c Sat Jul 04 21:35:55 2026 +0200
+++ b/tests/mpz/t-perfsqr.c Sun Jul 12 08:19:13 2026 +0200
@@ -1,6 +1,6 @@
/* Test mpz_perfect_square_p and mpz_perfect_square_root.
-Copyright 2000-2002 Free Software Foundation, Inc.
+Copyright 2000-2002, 2026 Free Software Foundation, Inc.
This file is part of the GNU MP Library test suite.
@@ -117,6 +117,7 @@
printf ("mpz_perfect_square_root -4 not a square\n");
abort ();
}
+ MPZ_CHECK_FORMAT (root);
// 0 and 1 are both perfect squares with respective root 0 and 1.
for (unsigned int m = 0; m < 2; m++)
@@ -191,6 +192,7 @@
printf (" mpz_sqrt %d\n", want);
abort ();
}
+ MPZ_CHECK_FORMAT (rop);
if (res && mpz_cmp(x, rop) != 0)
{
printf ("mpz_perfect_square_root and mpz_sqrt differ\n");
@@ -204,6 +206,7 @@
/* Check that same variable as input and output works */
mpz_set(rop, x2);
res = mpz_perfect_square_root (rop, rop);
+ MPZ_CHECK_FORMAT (rop);
if (res != want || (res && mpz_cmp(x, rop) != 0))
{
printf ("mpz_perfect_square_root differ when output == input\n");
@@ -217,8 +220,7 @@
}
if (reps > 1000 && cnt == 0) {
- printf("No perfect squares found in %d reps", reps);
- abort();
+ printf("No perfect squares found in %d reps\n", reps);
}
More information about the gmp-commit
mailing list