patches/gmp/4.2.4/100-mpf_eq.patch
author "Yann E. MORIN" <yann.morin.1998@anciens.enib.fr>
Mon May 25 19:48:42 2009 +0000 (2009-05-25)
branchgcc-4.4
changeset 1387 a52504ffac55
permissions -rw-r--r--
/devel/gcc-4.4:
- TODO: remove completed items

-------- diffstat follows --------
/devel/gcc-4.4/TODO | 1 0 1 0 -
1 file changed, 1 deletion(-)
     1 Original patch from: mpf_eq.diff
     2 
     3 -= BEGIN original header =-
     4 -= END original header =-
     5 
     6 diff -durN gmp-4.2.4.orig/doc/gmp.texi gmp-4.2.4/doc/gmp.texi
     7 --- gmp-4.2.4.orig/doc/gmp.texi	2008-09-18 17:36:14.000000000 +0200
     8 +++ gmp-4.2.4/doc/gmp.texi	2009-03-08 18:36:16.000000000 +0100
     9 @@ -4849,9 +4849,12 @@
    10  equal, zero otherwise.  I.e., test if @var{op1} and @var{op2} are approximately
    11  equal.
    12  
    13 -Caution: Currently only whole limbs are compared, and only in an exact
    14 -fashion.  In the future values like 1000 and 0111 may be considered the same
    15 -to 3 bits (on the basis that their difference is that small).
    16 +Caution 1: All version of GMP up to version 4.2.4 compared just whole limbs,
    17 +meaning sometimes more than @var{op3} bits, sometimes fewer.
    18 +
    19 +Caution 2: This function will consider XXX11...111 and XX100...000 different,
    20 +even if ... is replaced by a semi-infinite number of bits.  Such numbers are
    21 +really just one ulp off, and should be considered equal.
    22  @end deftypefun
    23  
    24  @deftypefun void mpf_reldiff (mpf_t @var{rop}, mpf_t @var{op1}, mpf_t @var{op2})
    25 diff -durN gmp-4.2.4.orig/mpf/eq.c gmp-4.2.4/mpf/eq.c
    26 --- gmp-4.2.4.orig/mpf/eq.c	2007-08-30 20:31:40.000000000 +0200
    27 +++ gmp-4.2.4/mpf/eq.c	2009-03-08 18:36:16.000000000 +0100
    28 @@ -1,6 +1,6 @@
    29  /* mpf_eq -- Compare two floats up to a specified bit #.
    30  
    31 -Copyright 1993, 1995, 1996, 2001, 2002 Free Software Foundation, Inc.
    32 +Copyright 1993, 1995, 1996, 2001, 2002, 2008 Free Software Foundation, Inc.
    33  
    34  This file is part of the GNU MP Library.
    35  
    36 @@ -19,6 +19,7 @@
    37  
    38  #include "gmp.h"
    39  #include "gmp-impl.h"
    40 +#include "longlong.h"
    41  
    42  int
    43  mpf_eq (mpf_srcptr u, mpf_srcptr v, unsigned long int n_bits)
    44 @@ -26,6 +27,8 @@
    45    mp_srcptr up, vp;
    46    mp_size_t usize, vsize, size, i;
    47    mp_exp_t uexp, vexp;
    48 +  mp_limb_t diff;
    49 +  int cnt;
    50  
    51    uexp = u->_mp_exp;
    52    vexp = v->_mp_exp;
    53 @@ -53,10 +56,8 @@
    54    /* U and V have the same sign and are both non-zero.  */
    55  
    56    /* 2. Are the exponents different?  */
    57 -  if (uexp > vexp)
    58 -    return 0;			/* ??? handle (uexp = vexp + 1)   */
    59 -  if (vexp > uexp)
    60 -    return 0;			/* ??? handle (vexp = uexp + 1)   */
    61 +  if (uexp != vexp)
    62 +    return 0;
    63  
    64    usize = ABS (usize);
    65    vsize = ABS (vsize);
    66 @@ -93,17 +94,26 @@
    67        size = usize;
    68      }
    69  
    70 -  if (size > (n_bits + GMP_NUMB_BITS - 1) / GMP_NUMB_BITS)
    71 -    size = (n_bits + GMP_NUMB_BITS - 1) / GMP_NUMB_BITS;
    72 +  up += usize;			/* point just above most significant limb */
    73 +  vp += vsize;			/* point just above most significant limb */
    74  
    75 -  up += usize - size;
    76 -  vp += vsize - size;
    77 +  count_leading_zeros (cnt, up[-1]);
    78 +  if ((vp[-1] >> (GMP_LIMB_BITS - 1 - cnt)) != 1)
    79 +    return 0;			/* msb positions different */
    80  
    81 -  for (i = size - 1; i >= 0; i--)
    82 +  n_bits += cnt - GMP_NAIL_BITS;
    83 +
    84 +  size = MIN (size, (n_bits + GMP_NUMB_BITS - 1) / GMP_NUMB_BITS);
    85 +
    86 +  up -= size;			/* point at least significant relevant limb */
    87 +  vp -= size;			/* point at least significant relevant limb */
    88 +
    89 +  for (i = size - 1; i > 0; i--)
    90      {
    91        if (up[i] != vp[i])
    92  	return 0;
    93      }
    94  
    95 -  return 1;
    96 +  diff = (up[0] ^ vp[0]) >> GMP_NUMB_BITS - 1 - (n_bits - 1) % GMP_NUMB_BITS;
    97 +  return diff == 0;
    98  }
    99 diff -durN gmp-4.2.4.orig/tests/cxx/t-prec.cc gmp-4.2.4/tests/cxx/t-prec.cc
   100 --- gmp-4.2.4.orig/tests/cxx/t-prec.cc	2007-09-01 12:09:03.000000000 +0200
   101 +++ gmp-4.2.4/tests/cxx/t-prec.cc	2009-03-08 18:36:16.000000000 +0100
   102 @@ -1,6 +1,6 @@
   103  /* Test precision of mpf_class expressions.
   104  
   105 -Copyright 2001, 2002, 2003 Free Software Foundation, Inc.
   106 +Copyright 2001, 2002, 2003, 2008 Free Software Foundation, Inc.
   107  
   108  This file is part of the GNU MP Library.
   109  
   110 @@ -61,7 +61,7 @@
   111      g = 1 / f;
   112      ASSERT_ALWAYS_PREC
   113        (g, "0.11111 11111 11111 11111 11111 11111 11111 11111 11111 11111"
   114 -       "     11111 11111 11111 11111 11111 11", very_large_prec);
   115 +       "     11111 11111 11111 11111 11111 111", very_large_prec);
   116    }
   117    {
   118      mpf_class f(15.0, large_prec);
   119 @@ -69,7 +69,7 @@
   120      g = 1 / f;
   121      ASSERT_ALWAYS_PREC
   122        (g, "0.06666 66666 66666 66666 66666 66666 66666 66666 66666 66666"
   123 -       "     66666 66666 66666 66666 66666 67", very_large_prec);
   124 +       "     66666 66666 66666 66666 66666 667", very_large_prec);
   125    }
   126  
   127    // compound expressions
   128 @@ -94,14 +94,14 @@
   129      i = f / g + h;
   130      ASSERT_ALWAYS_PREC
   131        (i, "15.33333 33333 33333 33333 33333 33333 33333 33333 33333 33333"
   132 -       "      33333 33333 33333 333", very_large_prec);
   133 +       "      33333 33333 33333 33333 33333 3", very_large_prec);
   134    }
   135    {
   136      mpf_class f(3.0, small_prec);
   137      mpf_class g(-(1 + f) / 3, very_large_prec);
   138      ASSERT_ALWAYS_PREC
   139        (g, "-1.33333 33333 33333 33333 33333 33333 33333 33333 33333 33333"
   140 -       "      33333 33333 33333 333", very_large_prec);
   141 +       "      33333 33333 33333 33333 33333 33", very_large_prec);
   142    }
   143    {
   144      mpf_class f(9.0, medium_prec);
   145 @@ -117,7 +117,7 @@
   146      g = hypot(1 + 5 / f, 1.0);
   147      ASSERT_ALWAYS_PREC
   148        (g, "1.66666 66666 66666 66666 66666 66666 66666 66666 66666 66666"
   149 -       "     66666 66666 66666 667", very_large_prec);
   150 +       "     66666 66666 66666 66666 66666 67", very_large_prec);
   151    }
   152  
   153    // compound assignments
   154 @@ -142,7 +142,7 @@
   155      mpf_class g(0.0, very_large_prec);
   156      g = mpf_class(1 / f);
   157      ASSERT_ALWAYS_PREC
   158 -      (g, "0.11111 11111 11111 11111 11111 11111 11111 111", medium_prec);
   159 +      (g, "0.11111 11111 11111 11111 11111 11111 11111 1111", medium_prec);
   160    }
   161    {
   162      mpf_class f(15.0, large_prec);
   163 @@ -150,7 +150,7 @@
   164      g = mpf_class(1 / f);
   165      ASSERT_ALWAYS_PREC
   166        (g, "0.06666 66666 66666 66666 66666 66666 66666 66666 66666 66666"
   167 -       "     66666 667", large_prec);
   168 +       "     66666 6667", large_prec);
   169    }
   170  
   171    {
   172 @@ -158,7 +158,8 @@
   173      mpf_class h(0.0, very_large_prec);
   174      h = mpf_class(f / g + 1, large_prec);
   175      ASSERT_ALWAYS_PREC
   176 -      (h, "1.33333 33333 33333 33333 33333 33333 33333 33333 33333 3333",
   177 +      (h, "1.33333 33333 33333 33333 33333 33333 33333 33333 33333 33333"
   178 +       "     33333 333",
   179         large_prec);
   180    }
   181  
   182 @@ -170,7 +171,7 @@
   183      g = f - q;
   184      ASSERT_ALWAYS_PREC
   185        (g, "2.66666 66666 66666 66666 66666 66666 66666 66666 66666 66666"
   186 -       "     66666 66666 66666 667", very_large_prec);
   187 +       "     66666 66666 66666 66666 66666 67", very_large_prec);
   188    }
   189  
   190    {
   191 @@ -179,7 +180,8 @@
   192      mpf_class g(0.0, very_large_prec);
   193      g = mpf_class(f - q, large_prec);
   194      ASSERT_ALWAYS_PREC
   195 -      (g, "2.66666 66666 66666 66666 66666 66666 66666 66666 66666 6667",
   196 +      (g, "2.66666 66666 66666 66666 66666 66666 66666 66666 66666 66666"
   197 +       "     66666 667",
   198         large_prec);
   199    }
   200    {
   201 @@ -188,7 +190,7 @@
   202      mpf_class g(0.0, very_large_prec);
   203      g = mpf_class(f - q);
   204      ASSERT_ALWAYS_PREC
   205 -      (g, "2.66666 66666 66666 66666 66666 6667", medium_prec);
   206 +      (g, "2.66666 66666 66666 66666 66666 66666 66666 667", medium_prec);
   207    }
   208    {
   209      mpf_class f(15.0, large_prec);
   210 @@ -196,7 +198,8 @@
   211      mpf_class g(0.0, very_large_prec);
   212      g = mpf_class(f + q);
   213      ASSERT_ALWAYS_PREC
   214 -      (g, "15.33333 33333 33333 33333 33333 33333 33333 33333 33333 3333",
   215 +      (g, "15.33333 33333 33333 33333 33333 33333 33333 33333 33333 33333"
   216 +       "      33333 33",
   217         large_prec);
   218    }
   219  }