diff -Naur gmp-4.1.1/ChangeLog gmp-4.1.2/ChangeLog --- gmp-4.1.1/ChangeLog Mon Nov 25 10:44:49 2002 +++ gmp-4.1.2/ChangeLog Mon Dec 23 21:21:56 2002 @@ -19,6 +19,99 @@ MA 02111-1307, USA. +2002-12-24 Kevin Ryde + + * Version 4.1.2 released. + + * tests/devel/try.c (mprotect_maybe, malloc_region): Don't use + strerror, need to check it exists first. + +2002-12-22 Torbjorn Granlund + + * configure.in (hppa2.0*-*-*): Pass +O2 instead of +O3 to work around + compiler bug with mpfr/tests/tdiv. + + * gmp-impl.h (union ieee_double_extract): Test for __sparc_v9 and + __sparc_v9__. + +2002-12-20 Torbjorn Granlund + + * mpn/generic/rootrem.c: In Newton loop, pad qp with leading zero. + +2002-12-19 Torbjorn Granlund + + * mpn/generic/rootrem.c: Allocate 1.585 (log2(3)) times more space + for pp temporary to allow for worst case overestimate of root. + Add some asserts. + + * tests/mpz/t-root.c: Generalize and speed up. + +2002-12-19 Kevin Ryde + + * gmp.texi (Build Options): Mention MS Interix, reported by Paul + Leyland. + (Notes for Particular Systems): Compaq C++ must be used in "standard" + iostream mode. Add Sparc app regs. + (Debugging): Note gcc -fstack options to detect overflow. + (Formatted Output Strings, Formatted Input Strings): Format strings + are not multibyte. + +2002-12-18 Kevin Ryde + + * gmp-h.in (__GNU_MP_VERSION_PATCHLEVEL): Bump to 4.1.2. + * Makefile.am (LIBGMP_LT_REVISION, LIBGMPXX_LT_REVISION, + LIBMP_LT_REVISION): Increment. + +2002-12-18 Paul Zimmermann + + * mpfr/pow.c: Fixed bug (infinite loop) for exact powers. + + * mpfr/sub.c: Fixed wrong inexact flag for a - b where a and b are of + different signs and EXP(a) < EXP(b). + +2002-12-17 Torbjorn Granlund + + * printf/printffuns.c (gmp_fprintf_reps): Make it actually work + for padding > 256. + +2002-12-17 Kevin Ryde + + * gmp.texi (Formatted Output Strings): %a and %A are C99 not glibc. + (Formatted Input Strings): Type "l" is for double too. + +2002-12-13 Kevin Ryde + + * gmp.texi (Debugging): Add maximum debuggability config options. + (Language Bindings): Add Arithmos, reported by Johan Vervloet. + (Formatted Output Strings): 128 bits is about 40 digits, ll is only + for long long not long double. + (Formatted Input Strings): ll is only for long long not long double. + +2002-12-08 Torbjorn Granlund + + * gmp-impl.h (USE_LEADING_REGPARM): Disable for PIC code generation. + +2002-12-04 Torbjorn Granlund + + * gmp-impl.h (union ieee_double_extract): Amend test for ia64 with hpux + test. + +2002-12-04 Kevin Ryde + + * gmp.texi (Floating-point Functions): Note the mantissa is binary and + decimal fractions cannot be represented exactly. Suggested by Serge + Winitzki. + (Known Build Problems): Note libtool stripping options when linking. + Reported by Vincent Lefevre. + +2002-12-03 Kevin Ryde + + * INSTALL: Use return rather than exit in the example programs. + Suggested by Richard Dawe. + + * longlong.h (count_leading_zeros, count_trailing_zeros) [ev67, ev68]: + Restrict __asm__ ctlz and cttz to __GNUC__. + 2002-11-25 Kevin Ryde * Version 4.1.1 released. diff -Naur gmp-4.1.1/INSTALL gmp-4.1.2/INSTALL --- gmp-4.1.1/INSTALL Tue Oct 9 01:21:41 2001 +++ gmp-4.1.2/INSTALL Wed Dec 18 23:41:55 2002 @@ -1,4 +1,4 @@ -Copyright 1996, 1997, 1999, 2000, 2001 Free Software Foundation, Inc. +Copyright 1996, 1997, 1999, 2000, 2001, 2002 Free Software Foundation, Inc. This file is part of the GNU MP Library. @@ -68,7 +68,7 @@ if (argc != 3) { printf ("Usage: %s \n", argv[0]); - exit (1); + return 1; } /* Initialize variables */ @@ -90,7 +90,7 @@ mpz_clear (a); mpz_clear (b); mpz_clear (p); - exit (0); + return 0; } @@ -109,7 +109,7 @@ if (argc != 3) { printf ("Usage: %s \n", argv[0]); - exit (1); + return 1; } /* Initialize and assign a and b from base 10 strings in argv */ @@ -125,7 +125,7 @@ gmp_printf ("%Zd\n", p); /* Since we're about to exit, no need to clear out variables */ - exit (0); + return 0; } diff -Naur gmp-4.1.1/Makefile.am gmp-4.1.2/Makefile.am --- gmp-4.1.1/Makefile.am Wed Nov 13 22:45:04 2002 +++ gmp-4.1.2/Makefile.am Tue Dec 17 23:08:35 2002 @@ -46,6 +46,7 @@ # 4.0.1 5:1:2 3:1:0 4:3:1 # 4.1 6:0:3 3:2:0 4:4:1 # 4.1.1 6:1:3 3:3:0 4:5:1 +# 4.1.2 6:2:3 3:4:0 4:6:1 # # Starting at 3:0:0 is a slight abuse of the versioning system, but it # ensures we're past soname libgmp.so.2, which was used on Debian GNU/Linux @@ -53,15 +54,15 @@ # gmp 3 mean 3:0:0 is right. LIBGMP_LT_CURRENT = 6 -LIBGMP_LT_REVISION = 1 +LIBGMP_LT_REVISION = 2 LIBGMP_LT_AGE = 3 LIBGMPXX_LT_CURRENT = 3 -LIBGMPXX_LT_REVISION = 3 +LIBGMPXX_LT_REVISION = 4 LIBGMPXX_LT_AGE = 0 LIBMP_LT_CURRENT = 4 -LIBMP_LT_REVISION = 5 +LIBMP_LT_REVISION = 6 LIBMP_LT_AGE = 1 diff -Naur gmp-4.1.1/Makefile.in gmp-4.1.2/Makefile.in --- gmp-4.1.1/Makefile.in Wed Nov 27 23:33:58 2002 +++ gmp-4.1.2/Makefile.in Sat Dec 28 00:30:22 2002 @@ -57,6 +57,7 @@ # 4.0.1 5:1:2 3:1:0 4:3:1 # 4.1 6:0:3 3:2:0 4:4:1 # 4.1.1 6:1:3 3:3:0 4:5:1 +# 4.1.2 6:2:3 3:4:0 4:6:1 # # Starting at 3:0:0 is a slight abuse of the versioning system, but it # ensures we're past soname libgmp.so.2, which was used on Debian GNU/Linux @@ -167,15 +168,15 @@ mpn_objs_in_libmp = @mpn_objs_in_libmp@ LIBGMP_LT_CURRENT = 6 -LIBGMP_LT_REVISION = 1 +LIBGMP_LT_REVISION = 2 LIBGMP_LT_AGE = 3 LIBGMPXX_LT_CURRENT = 3 -LIBGMPXX_LT_REVISION = 3 +LIBGMPXX_LT_REVISION = 4 LIBGMPXX_LT_AGE = 0 LIBMP_LT_CURRENT = 4 -LIBMP_LT_REVISION = 5 +LIBMP_LT_REVISION = 6 LIBMP_LT_AGE = 1 AUTOMAKE_OPTIONS = gnu no-dependencies ansi2knr diff -Naur gmp-4.1.1/NEWS gmp-4.1.2/NEWS --- gmp-4.1.1/NEWS Tue Nov 12 00:05:19 2002 +++ gmp-4.1.2/NEWS Tue Dec 17 23:30:54 2002 @@ -18,6 +18,10 @@ 02111-1307, USA. +Changes between MP version 4.1.1 and 4.1.2 + +* Bug fixes. + Changes between MP version 4.1 and 4.1.1 * Bug fixes. diff -Naur gmp-4.1.1/configure gmp-4.1.2/configure --- gmp-4.1.1/configure Wed Nov 27 23:34:02 2002 +++ gmp-4.1.2/configure Sat Dec 28 00:30:26 2002 @@ -1,5 +1,5 @@ #! /bin/sh -# From configure.in Revision: 1.425.2.15 . +# From configure.in Revision: 1.425.2.17 . # # # @@ -1580,7 +1580,7 @@ # Define the identity of the package. PACKAGE=gmp -VERSION=4.1.1 +VERSION=4.1.2 cat >>confdefs.h <: Float Arithmetic. -* Arithmetic functions <2>: Rational Arithmetic. -* Arithmetic functions: Integer Arithmetic. +* Arithmetic functions <1>: Rational Arithmetic. +* Arithmetic functions <2>: Integer Arithmetic. +* Arithmetic functions: Float Arithmetic. * Assignment functions <1>: Assigning Floats. * Assignment functions: Assigning Integers. * Autoconf detections: Autoconf. @@ -441,9 +441,9 @@ * C++ Interface: C++ Class Interface. * C++ istream input: C++ Formatted Input. * C++ ostream output: C++ Formatted Output. -* Comparison functions <1>: Float Comparison. +* Comparison functions <1>: Comparing Rationals. * Comparison functions <2>: Integer Comparisons. -* Comparison functions: Comparing Rationals. +* Comparison functions: Float Comparison. * Compatibility with older versions: Compatibility with older versions. * Conditions for copying GNU MP: Copying. * Configuring GMP: Installing GMP. @@ -452,8 +452,8 @@ * Conventions for parameters: Parameter Conventions. * Conventions for variables: Variable Conventions. * Conversion functions <1>: Converting Integers. -* Conversion functions <2>: Rational Conversions. -* Conversion functions: Converting Floats. +* Conversion functions <2>: Converting Floats. +* Conversion functions: Rational Conversions. * Copying conditions: Copying. * CPUs supported: Introduction to GMP. * Custom allocation: Custom Allocation. @@ -461,8 +461,8 @@ * Demonstration programs: Demonstration Programs. * DESTDIR: Known Build Problems. * Division algorithms: Division Algorithms. -* Division functions <1>: Rational Arithmetic. -* Division functions <2>: Integer Division. +* Division functions <1>: Integer Division. +* Division functions <2>: Rational Arithmetic. * Division functions: Float Arithmetic. * Efficiency: Efficiency. * Emacs: Emacs. @@ -504,13 +504,13 @@ * I/O functions: I/O of Rationals. * Import: Integer Import and Export. * Initialization and assignment functions <1>: Initializing Rationals. -* Initialization and assignment functions <2>: Simultaneous Float Init & Assign. -* Initialization and assignment functions: Simultaneous Integer Init & Assign. +* Initialization and assignment functions <2>: Simultaneous Integer Init & Assign. +* Initialization and assignment functions: Simultaneous Float Init & Assign. * Initialization functions <1>: Initializing Integers. * Initialization functions: Initializing Floats. * Input functions <1>: I/O of Floats. -* Input functions <2>: I/O of Integers. -* Input functions: I/O of Rationals. +* Input functions <2>: I/O of Rationals. +* Input functions: I/O of Integers. * Installing GMP: Installing GMP. * Instruction Set Architecture: ABI and ISA. * Integer: Nomenclature and Types. @@ -563,8 +563,8 @@ * Number theoretic functions: Number Theoretic Functions. * Numerator and denominator: Applying Integer Functions. * ostream output: C++ Formatted Output. -* Output functions <1>: I/O of Floats. -* Output functions <2>: I/O of Integers. +* Output functions <1>: I/O of Integers. +* Output functions <2>: I/O of Floats. * Output functions: I/O of Rationals. * Packaged builds: Notes for Package Builds. * Parameter conventions: Parameter Conventions. @@ -595,14 +595,15 @@ * References: References. * Reporting bugs: Reporting Bugs. * Root extraction algorithms: Root Extraction Algorithms. -* Root extraction functions <1>: Float Arithmetic. -* Root extraction functions: Integer Roots. +* Root extraction functions <1>: Integer Roots. +* Root extraction functions: Float Arithmetic. * Sample programs: Demonstration Programs. * scanf formatted input: Formatted Input. * Shared library versioning: Notes for Package Builds. -* Sign tests <1>: Integer Comparisons. -* Sign tests <2>: Comparing Rationals. -* Sign tests: Float Comparison. +* Sign tests <1>: Comparing Rationals. +* Sign tests <2>: Float Comparison. +* Sign tests: Integer Comparisons. +* Sparc: Notes for Particular Systems. * Stack overflow segfaults: Build Options. * Stripped libraries: Known Build Problems. * Systems: Notes for Particular Systems. diff -Naur gmp-4.1.1/gmp.info-9 gmp-4.1.2/gmp.info-9 --- gmp-4.1.1/gmp.info-9 Wed Nov 27 23:34:33 2002 +++ gmp-4.1.2/gmp.info-9 Sat Dec 28 00:31:09 2002 @@ -1,7 +1,7 @@ This is gmp.info, produced by makeinfo version 4.2 from gmp.texi. This manual describes how to install and use the GNU multiple precision -arithmetic library, version 4.1.1. +arithmetic library, version 4.1.2. Copyright 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc. diff -Naur gmp-4.1.1/gmp.texi gmp-4.1.2/gmp.texi --- gmp-4.1.1/gmp.texi Fri Nov 15 22:16:01 2002 +++ gmp-4.1.2/gmp.texi Fri Dec 20 23:44:02 2002 @@ -553,6 +553,10 @@ @uref{http://www.mingw.org} @end display +Microsoft also publishes an Interix ``Services for Unix'' which can be used to +build GMP on Windows (with a normal @samp{./configure}), but it's not free +software. + The @file{macos} directory contains an unsupported port to MacOS 9 on Power Macintosh, see @file{macos/README}. Note that MacOS X ``Darwin'' should use the normal Unix-style @samp{./configure}. @@ -1261,6 +1265,16 @@ bug in unsigned division, giving wrong results for some operands. GMP @samp{./configure} will demand GCC 2.95.4 or later. +@item Compaq C++ +Compaq C++ on OSF 5.1 has two flavours of @code{iostream}, a standard one and +an old pre-standard one (see @samp{man iostream_intro}). GMP can only use the +standard one, which unfortunately is not the default but must be selected by +defining @code{__USE_STD_IOSTREAM}. Configure with for instance + +@example +./configure --enable-cxx CPPFLAGS=-D__USE_STD_IOSTREAM +@end example + @item Microsoft Windows On systems @samp{*-*-cygwin*}, @samp{*-*-mingw*} and @samp{*-*-pw32*} by default GMP builds only a static library, but a DLL can be built instead using @@ -1322,6 +1336,19 @@ @samp{sparcv8} or @samp{supersparc} on relevant systems will give a significant performance increase over the V7 code. +@item Sparc App Regs +@cindex Sparc +The GMP assembler code for both 32-bit and 64-bit Sparc clobbers the +``application registers'' @code{g2}, @code{g3} and @code{g4}, the same way +that the GCC default @samp{-mapp-regs} does (@pxref{SPARC Options,,, gcc, +Using the GNU Compiler Collection (GCC)}). + +This makes that code unsuitable for use with the special V9 +@samp{-mcmodel=embmedany} (which uses @code{g4} as a data segment pointer), +and for applications wanting to use those registers for special purposes. In +these cases the only suggestion currently is to build GMP with CPU @samp{none} +to avoid the assembler code. + @item SunOS 4 @command{/usr/bin/m4} lacks various features needed to process @file{.asm} @@ -1371,8 +1398,17 @@ You might find more up-to-date information at @uref{http://swox.com/gmp/}. @table @asis -@item DJGPP +@item Compiler link options +The version of libtool currently in use rather aggressively strips compiler +options when linking a shared library. This will hopefully be relaxed in the +future, but for now if this is a problem the suggestion is to create a little +script to hide them, and for instance configure with +@example +./configure CC=gcc-with-my-options +@end example + +@item DJGPP The DJGPP port of @command{bash} 2.03 is unable to run the @samp{configure} script, it exits silently, having died writing a preamble to @file{config.log}. Use @command{bash} 2.04 or higher. @@ -2149,6 +2185,16 @@ only indication of stack overflow. See @samp{--enable-alloca} choices in @ref{Build Options}, for how to address this. +In new enough versions of GCC, @samp{-fstack-check} may be able to ensure an +overflow is recognised by the system before too much damage is done, or +@samp{-fstack-limit-symbol} or @samp{-fstack-limit-register} may be able to +add checking if the system itself doesn't do any (@pxref{Code Gen Options,, +Options for Code Generation, gcc, Using the GNU Compiler Collection (GCC)}). +These options must be added to the @samp{CFLAGS} used in the GMP build +(@pxref{Build Options}), adding them just to an application will have no +effect. Note also they're a slowdown, adding overhead to each function call +and each stack allocation. + @item Heap Problems The most likely cause of application problems with GMP is heap corruption. Failing to @code{init} GMP variables will have unpredictable effects, and @@ -2229,6 +2275,16 @@ or may be allocated with a compiler builtin @code{alloca} which will go nowhere near any malloc debugger hooks. +@item Maximum Debuggability +To summarize the above, a GMP build for maximum debuggability would be + +@example +./configure --disable-shared --enable-assert \ + --enable-alloca=debug --host=none CFLAGS=-g +@end example + +For C++, add @samp{--enable-cxx CXXFLAGS=-g}. + @item Checker The checker program (@uref{http://savannah.gnu.org/projects/checker}) can be used with GMP. It contains a stub library which means GMP applications @@ -3876,6 +3932,14 @@ depending on the high limb of the mantissa. But applications shouldn't be concerned by such details. +The mantissa in stored in binary, as might be imagined from the fact +precisions are expressed in bits. One consequence of this is that decimal +fractions like @math{0.1} cannot be represented exactly. The same is true of +plain IEEE @code{double} floats. This makes both highly unsuitable for +calculations involving money or other values that should be exact decimal +fractions. (Suitably scaled integers, or perhaps rationals, are better +choices.) + @code{mpf} functions and variables have no special notion of infinity or not-a-number, and applications must take care not to overflow the exponent or results will be unpredictable. This might change in a future release. @@ -5043,8 +5107,8 @@ @item @nicode{hh} @tab @nicode{char} @item @nicode{j} @tab @nicode{intmax_t} or @nicode{uintmax_t} @item @nicode{l} @tab @nicode{long} or @nicode{wchar_t} -@item @nicode{ll} @tab same as @nicode{L} -@item @nicode{L} @tab @nicode{long long} or @nicode{long double} +@item @nicode{ll} @tab @nicode{long long} +@item @nicode{L} @tab @nicode{long double} @item @nicode{q} @tab @nicode{quad_t} or @nicode{u_quad_t} @item @nicode{t} @tab @nicode{ptrdiff_t} @item @nicode{z} @tab @nicode{size_t} @@ -5069,7 +5133,7 @@ @quotation @multitable {(space)} {MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM} -@item @nicode{a} @nicode{A} @tab hex floats, GLIBC style +@item @nicode{a} @nicode{A} @tab hex floats, C99 style @item @nicode{c} @tab character @item @nicode{d} @tab decimal integer @item @nicode{e} @nicode{E} @tab scientific format float @@ -5107,7 +5171,7 @@ Zeros will be used if necessary to pad to the requested precision. This happens even for an @samp{f} conversion of an @code{mpf_t} which is an integer, for instance @math{2^@W{1024}} in an @code{mpf_t} of 128 bits -precision will only produce about 20 digits, then pad with zeros to the +precision will only produce about 40 digits, then pad with zeros to the decimal point. An empty precision field like @samp{%.Fe} or @samp{%.Ff} can be used to specifically request just the significant digits. @@ -5116,6 +5180,9 @@ and Internationalization,libc,The GNU C Library Reference Manual}). The C library will normally do the same for standard float output. +The format string is only interpreted as plain @code{char}s, multibyte +characters are not recognised. Perhaps this will change in the future. + @node Formatted Output Functions, C++ Formatted Output, Formatted Output Strings, Formatted Output @section Functions @@ -5341,9 +5408,9 @@ @item @nicode{h} @tab @nicode{short} @item @nicode{hh} @tab @nicode{char} @item @nicode{j} @tab @nicode{intmax_t} or @nicode{uintmax_t} -@item @nicode{l} @tab @nicode{long} or @nicode{wchar_t} -@item @nicode{ll} @tab same as @nicode{L} -@item @nicode{L} @tab @nicode{long long} or @nicode{long double} +@item @nicode{l} @tab @nicode{long int}, @nicode{double} or @nicode{wchar_t} +@item @nicode{ll} @tab @nicode{long long} +@item @nicode{L} @tab @nicode{long double} @item @nicode{q} @tab @nicode{quad_t} or @nicode{u_quad_t} @item @nicode{t} @tab @nicode{ptrdiff_t} @item @nicode{z} @tab @nicode{size_t} @@ -5420,6 +5487,9 @@ GNU C Library Reference Manual}). The C library will normally do the same for standard float input. +The format string is only interpreted as plain @code{char}s, multibyte +characters are not recognised. Perhaps this will change in the future. + @node Formatted Input Functions, C++ Formatted Input, Formatted Input Strings, Formatted Input @section Formatted Input Functions @@ -6290,6 +6360,9 @@ @item ALP @spaceuref{http://www.inria.fr/saga/logiciels/ALP} @* Linear algebra and polynomials using templates. +@item +Arithmos @spaceuref{http://win-www.uia.ac.be/u/cant/arithmos} @* Rationals +with infinities and square roots. @item CLN @spaceuref{http://clisp.cons.org/~haible/packages-cln.html} @* High level classes for arithmetic. diff -Naur gmp-4.1.1/longlong.h gmp-4.1.2/longlong.h --- gmp-4.1.1/longlong.h Sat Nov 2 00:49:20 2002 +++ gmp-4.1.2/longlong.h Tue Dec 17 22:57:20 2002 @@ -139,7 +139,7 @@ /* clz_tab is required by mpn/alpha/cntlz.asm, and that file is built for all alphas, even though ev67 and ev68 don't need it. */ #define COUNT_LEADING_ZEROS_NEED_CLZ_TAB -#if HAVE_HOST_CPU_alphaev67 || HAVE_HOST_CPU_alphaev68 +#if defined (__GNUC__) && (HAVE_HOST_CPU_alphaev67 || HAVE_HOST_CPU_alphaev68) #define count_leading_zeros(COUNT,X) \ __asm__("ctlz %1,%0" : "=r"(COUNT) : "r"(X)) #define count_trailing_zeros(COUNT,X) \ diff -Naur gmp-4.1.1/mpfr/pow.c gmp-4.1.2/mpfr/pow.c --- gmp-4.1.1/mpfr/pow.c Mon Apr 15 23:55:48 2002 +++ gmp-4.1.2/mpfr/pow.c Tue Dec 17 23:23:25 2002 @@ -21,12 +21,71 @@ #include "gmp.h" #include "gmp-impl.h" +#include "longlong.h" #include "mpfr.h" #include "mpfr-impl.h" +static int mpfr_pow_is_exact _PROTO((mpfr_srcptr, mpfr_srcptr)); + +/* return non zero iff x^y is exact. + Assumes x and y are ordinary numbers (neither NaN nor Inf), + and y is not zero. +*/ +int +mpfr_pow_is_exact (mpfr_srcptr x, mpfr_srcptr y) +{ + mp_exp_t d; + unsigned long i, c; + mp_limb_t *yp; + + if ((mpfr_sgn (x) < 0) && (mpfr_isinteger (y) == 0)) + return 0; + + if (mpfr_sgn (y) < 0) + return mpfr_cmp_si_2exp (x, MPFR_SIGN(x), MPFR_EXP(x) - 1) == 0; + + /* compute d such that y = c*2^d with c odd integer */ + d = MPFR_EXP(y) - MPFR_PREC(y); + /* since y is not zero, necessarily one of the mantissa limbs is not zero, + thus we can simply loop until we find a non zero limb */ + yp = MPFR_MANT(y); + for (i = 0; yp[i] == 0; i++, d += BITS_PER_MP_LIMB); + /* now yp[i] is not zero */ + count_trailing_zeros (c, yp[i]); + d += c; + + if (d < 0) + { + mpz_t a; + mp_exp_t b; + + mpz_init (a); + b = mpfr_get_z_exp (a, x); /* x = a * 2^b */ + c = mpz_scan1 (a, 0); + mpz_div_2exp (a, a, c); + b += c; + /* now a is odd */ + while (d != 0) + { + if (mpz_perfect_square_p (a)) + { + d++; + mpz_sqrt (a, a); + } + else + { + mpz_clear (a); + return 0; + } + } + mpz_clear (a); + } + + return 1; +} + /* The computation of z = pow(x,y) is done by z = exp(y * log(x)) = x^y */ - int mpfr_pow (mpfr_ptr z, mpfr_srcptr x, mpfr_srcptr y, mp_rnd_t rnd_mode) { @@ -129,10 +188,10 @@ if (MPFR_IS_ZERO(y)) { - return mpfr_set_ui(z,1,GMP_RNDN); + return mpfr_set_ui (z, 1, GMP_RNDN); } - if(mpfr_isinteger(y)) + if (mpfr_isinteger (y)) { mpz_t zi; long int zii; @@ -149,7 +208,7 @@ zii=mpz_get_ui(zi); mpz_clear(zi); - return mpfr_pow_si(z,x,zii,rnd_mode); + return mpfr_pow_si (z, x, zii, rnd_mode); } if (MPFR_IS_INF(x)) @@ -191,6 +250,7 @@ { /* Declaration of the intermediary variable */ mpfr_t t, te, ti; + int loop = 0, ok; /* Declaration of the size variable */ mp_prec_t Nx = MPFR_PREC(x); /* Precision of input variable */ @@ -209,29 +269,41 @@ mpfr_init(ti); mpfr_init(te); - do { + do + { + + loop ++; - /* reactualisation of the precision */ - mpfr_set_prec(t,Nt); - mpfr_set_prec(ti,Nt); - mpfr_set_prec(te,Nt); - - /* compute exp(y*ln(x))*/ - mpfr_log(ti,x,GMP_RNDU); /* ln(n) */ - mpfr_mul(te,y,ti,GMP_RNDU); /* y*ln(n) */ - mpfr_exp(t,te,GMP_RNDN); /* exp(x*ln(n))*/ + /* reactualisation of the precision */ + mpfr_set_prec (t, Nt); + mpfr_set_prec (ti, Nt); + mpfr_set_prec (te, Nt); + + /* compute exp(y*ln(x)) */ + mpfr_log (ti, x, GMP_RNDU); /* ln(n) */ + mpfr_mul (te, y, ti, GMP_RNDU); /* y*ln(n) */ + mpfr_exp (t, te, GMP_RNDN); /* exp(x*ln(n))*/ /* estimation of the error -- see pow function in algorithms.ps*/ - err = Nt - (MPFR_EXP(te)+3); + err = Nt - (MPFR_EXP(te) + 3); /* actualisation of the precision */ - Nt += 10; + Nt += 10; + + ok = mpfr_can_round (t, err, GMP_RNDN, rnd_mode, Ny); - } while (err<0 || !mpfr_can_round(t,err,GMP_RNDN,rnd_mode,Ny)); - inexact = mpfr_set(z,t,rnd_mode); - mpfr_clear(t); - mpfr_clear(ti); - mpfr_clear(te); + /* check exact power */ + if (ok == 0 && loop == 1) + ok = mpfr_pow_is_exact (x, y); + + } + while (err < 0 || ok == 0); + + inexact = mpfr_set (z, t, rnd_mode); + + mpfr_clear (t); + mpfr_clear (ti); + mpfr_clear (te); } return inexact; } diff -Naur gmp-4.1.1/mpfr/sub.c gmp-4.1.2/mpfr/sub.c --- gmp-4.1.1/mpfr/sub.c Mon Apr 15 23:55:49 2002 +++ gmp-4.1.2/mpfr/sub.c Tue Dec 17 23:21:25 2002 @@ -100,7 +100,7 @@ inexact = mpfr_add1(a, c, b, rnd_mode, (mp_exp_unsigned_t) MPFR_EXP(c) - MPFR_EXP(b)); MPFR_CHANGE_SIGN(a); - return inexact; + return -inexact; } else { diff -Naur gmp-4.1.1/mpn/generic/rootrem.c gmp-4.1.2/mpn/generic/rootrem.c --- gmp-4.1.1/mpn/generic/rootrem.c Sat Oct 19 00:20:54 2002 +++ gmp-4.1.2/mpn/generic/rootrem.c Fri Dec 20 14:14:42 2002 @@ -65,7 +65,17 @@ TMP_DECL (marker); TMP_MARK (marker); - pp = TMP_ALLOC_LIMBS (un + 2); + + /* The extra factor 1.585 = log(3)/log(2) here is for the worst case + overestimate of the root, i.e., when the code rounds a root that is + 2+epsilon to 3, and the powers this to a potentially huge power. We + could generalize the code for detecting root=1 a few lines below to deal + with xnb <= k, for some small k. For example, when xnb <= 2, meaning + the root should be 1, 2, or 3, we could replace this factor by the much + smaller log(5)/log(4). */ + +#define PP_ALLOC (2 + (mp_size_t) (un*1.585)) + pp = TMP_ALLOC_LIMBS (PP_ALLOC); count_leading_zeros (cnt, up[un - 1]); unb = un * GMP_NUMB_BITS - cnt + GMP_NAIL_BITS; @@ -102,6 +112,7 @@ mp_limb_t xl = xp[bit / GMP_NUMB_BITS]; xp[bit / GMP_NUMB_BITS] = xl ^ (mp_limb_t) 1 << bit % GMP_NUMB_BITS; pn = mpn_pow_1 (pp, xp, xn, nth, qp); + ASSERT_ALWAYS (pn < PP_ALLOC); /* If the new root approximation is too small, restore old value. */ if (! (un < pn || (un == pn && mpn_cmp (up, pp, pn) < 0))) xp[bit / GMP_NUMB_BITS] = xl; /* restore old value */ @@ -121,10 +132,11 @@ mp_limb_t cy; pn = mpn_pow_1 (pp, xp, xn, nth - 1, qp); + ASSERT_ALWAYS (pn < PP_ALLOC); + qp[xn - 1] = 0; /* pad quotient to make it always xn limbs */ mpn_tdiv_qr (qp, pp, (mp_size_t) 0, up, un, pp, pn); /* junk remainder */ - qn = un - pn + 1; cy = mpn_addmul_1 (qp, xp, xn, nth - 1); - if (qn == xn + 1) + if (un - pn == xn) { cy += qp[xn]; if (cy == nth) @@ -145,10 +157,12 @@ /* The computed result might be one unit too large. Adjust as necessary. */ done: pn = mpn_pow_1 (pp, xp, xn, nth, qp); + ASSERT_ALWAYS (pn < PP_ALLOC); if (un < pn || (un == pn && mpn_cmp (up, pp, pn) < 0)) { mpn_decr_u (xp, 1); pn = mpn_pow_1 (pp, xp, xn, nth, qp); + ASSERT_ALWAYS (pn < PP_ALLOC); ASSERT_ALWAYS (! (un < pn || (un == pn && mpn_cmp (up, pp, pn) < 0))); } diff -Naur gmp-4.1.1/printf/printffuns.c gmp-4.1.2/printf/printffuns.c --- gmp-4.1.1/printf/printffuns.c Wed Jul 25 01:41:52 2001 +++ gmp-4.1.2/printf/printffuns.c Wed Dec 18 00:10:11 2002 @@ -59,9 +59,9 @@ ASSERT (reps >= 0); memset (buf, c, MIN (reps, sizeof (buf))); - for (i = reps; i > 0; i -= piece) + for (i = reps; i > 0; i -= sizeof (buf)) { - piece = MIN (reps, sizeof (buf)); + piece = MIN (i, sizeof (buf)); ret = fwrite (buf, 1, piece, fp); if (ret == -1) return ret; diff -Naur gmp-4.1.1/stamp-vti gmp-4.1.2/stamp-vti --- gmp-4.1.1/stamp-vti Wed Nov 27 23:34:09 2002 +++ gmp-4.1.2/stamp-vti Sat Dec 28 00:30:38 2002 @@ -1,4 +1,4 @@ -@set UPDATED 15 November 2002 -@set UPDATED-MONTH November 2002 -@set EDITION 4.1.1 -@set VERSION 4.1.1 +@set UPDATED 20 December 2002 +@set UPDATED-MONTH December 2002 +@set EDITION 4.1.2 +@set VERSION 4.1.2 diff -Naur gmp-4.1.1/tests/devel/try.c gmp-4.1.2/tests/devel/try.c --- gmp-4.1.1/tests/devel/try.c Tue Apr 16 02:07:56 2002 +++ gmp-4.1.2/tests/devel/try.c Mon Dec 23 21:10:07 2002 @@ -1324,8 +1324,7 @@ #if HAVE_MPROTECT if (mprotect (addr, len, prot) != 0) { - fprintf (stderr, "Cannot mprotect %p 0x%X 0x%X: %s\n", - addr, len, prot, strerror (errno)); + fprintf (stderr, "Cannot mprotect %p 0x%X 0x%X\n", addr, len, prot); exit (1); } #else @@ -1384,8 +1383,7 @@ p = mmap (NULL, nbytes, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANON, -1, 0); if (p == (void *) -1) { - fprintf (stderr, "Cannot mmap %#x anon bytes: %s\n", - nbytes, strerror (errno)); + fprintf (stderr, "Cannot mmap %#x anon bytes\n", nbytes); exit (1); } #else diff -Naur gmp-4.1.1/tests/mpz/t-root.c gmp-4.1.2/tests/mpz/t-root.c --- gmp-4.1.1/tests/mpz/t-root.c Fri Mar 2 21:07:20 2001 +++ gmp-4.1.2/tests/mpz/t-root.c Thu Dec 19 11:53:38 2002 @@ -1,6 +1,6 @@ /* Test mpz_add, mpz_add_ui, mpz_cmp, mpz_cmp, mpz_mul, mpz_sqrtrem. -Copyright 1991, 1993, 1994, 1996, 2000, 2001 Free Software Foundation, Inc. +Copyright 1991, 1993, 1994, 1996, 2000, 2001, 2002 Free Software Foundation, Inc. This file is part of the GNU MP Library. @@ -36,7 +36,7 @@ mpz_t temp, temp2; mp_size_t x2_size; int i; - int reps = 5000; + int reps = 1000; unsigned long nth; gmp_randstate_ptr rands; mpz_t bs; @@ -64,23 +64,29 @@ x2_size = mpz_get_ui (bs) + 10; mpz_rrandomb (x2, rands, x2_size); - mpz_urandomb (bs, rands, 5L); - nth = mpz_getlimbn (bs, 0) % mpz_sizeinbase (x2, 2) + 1; + mpz_urandomb (bs, rands, 15); + nth = mpz_getlimbn (bs, 0) % mpz_sizeinbase (x2, 2) + 2; - mpz_urandomb (bs, rands, 2); + mpz_root (x, x2, nth); + + mpz_urandomb (bs, rands, 4); bsi = mpz_get_ui (bs); if ((bsi & 1) != 0) { - /* With 50% probability, set x2 just below a perfect power. */ - mpz_root (x, x2, nth); + /* With 50% probability, set x2 near a perfect power. */ mpz_pow_ui (x2, x, nth); - if (mpz_sgn (x2) != 0) - mpz_sub_ui (x2, x2, 1L); + if ((bsi & 2) != 0) + { + mpz_sub_ui (x2, x2, bsi >> 2); + mpz_abs (x2, x2); + } + else + mpz_add_ui (x2, x2, bsi >> 2); + mpz_root (x, x2, nth); } /* printf ("%ld %lu\n", SIZ (x2), nth); */ - mpz_root (x, x2, nth); mpz_pow_ui (temp, x, nth); /* Is power of result > argument? */ diff -Naur gmp-4.1.1/version.texi gmp-4.1.2/version.texi --- gmp-4.1.1/version.texi Wed Nov 27 23:34:09 2002 +++ gmp-4.1.2/version.texi Sat Dec 28 00:30:38 2002 @@ -1,4 +1,4 @@ -@set UPDATED 15 November 2002 -@set UPDATED-MONTH November 2002 -@set EDITION 4.1.1 -@set VERSION 4.1.1 +@set UPDATED 20 December 2002 +@set UPDATED-MONTH December 2002 +@set EDITION 4.1.2 +@set VERSION 4.1.2