This is the mail archive of the libc-alpha@sources.redhat.com mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

patch for e_remainder.c



The patch below is derived from a repaired version of urem.c communicated
by Moshe Olshansky <OLSHANSK@il.ibm.com>, one of the authors.
To create the patch I merged his change into the glibc version of the file.

        Moshe Olshansky <OLSHANSK@il.ibm.com>
	* sysdeps/ieee754/dbl-64/e_remainder.c (__ieee754_remainder):
	 Fix overflow problem.

*** e_remainder.c	2001/05/12 14:31:44	1.1
--- e_remainder.c	2001/12/02 20:10:08
*************** double __ieee754_remainder(double x, dou
*** 55,62 ****
    kx=u.i[HIGH_HALF]&0x7fffffff; /* no sign  for x*/
    t.i[HIGH_HALF]&=0x7fffffff;   /*no sign for y */
    ky=t.i[HIGH_HALF];
!   /*------ |x| < 2^1024  and   2^-970 < |y| < 2^1024 ------------------*/
!   if (kx<0x7ff00000 && ky<0x7ff00000 && ky>=0x03500000) {
      if (kx+0x00100000<ky) return x;
      if ((kx-0x01500000)<ky) {
        z=x/t.x;
--- 55,62 ----
    kx=u.i[HIGH_HALF]&0x7fffffff; /* no sign  for x*/
    t.i[HIGH_HALF]&=0x7fffffff;   /*no sign for y */
    ky=t.i[HIGH_HALF];
!   /*------ |x| < 2^1023  and   2^-970 < |y| < 2^1024 ------------------*/
!   if (kx<0x7fe00000 && ky<0x7ff00000 && ky>=0x03500000) {
      if (kx+0x00100000<ky) return x;
      if ((kx-0x01500000)<ky) {
        z=x/t.x;
*************** double __ieee754_remainder(double x, dou
*** 100,113 ****
          {z=u.x/t.x; d=(z+big.x)-big.x; return ((u.x-d*w.x)-d*ww.x);}
      }
  
!   }   /*   (kx<0x7ff00000&&ky<0x7ff00000&&ky>=0x03500000)     */
    else {
!     if (kx<0x7ff00000&&ky<0x7ff00000&&(ky>0||t.i[LOW_HALF]!=0)) {
        y=ABS(y)*t128.x;
        z=__ieee754_remainder(x,y)*t128.x;
        z=__ieee754_remainder(z,y)*tm128.x;
        return z;
      }
      else { /* if x is too big */
        if (kx == 0x7ff00000 && u.i[LOW_HALF] == 0 && y == 1.0)
  	return x / x;
--- 100,121 ----
          {z=u.x/t.x; d=(z+big.x)-big.x; return ((u.x-d*w.x)-d*ww.x);}
      }
  
!   }   /*   (kx<0x7fe00000&&ky<0x7ff00000&&ky>=0x03500000)     */
    else {
!     if (kx<0x7fe00000&&ky<0x7ff00000&&(ky>0||t.i[LOW_HALF]!=0)) {
        y=ABS(y)*t128.x;
        z=__ieee754_remainder(x,y)*t128.x;
        z=__ieee754_remainder(z,y)*tm128.x;
        return z;
      }
+   else {
+     if ((kx&0x7ff00000)==0x7fe00000&&ky<0x7ff00000&&(ky>0||t.i[LOW_HALF]!=0)) {
+       y=ABS(y);
+       z=2.0*__ieee754_remainder(0.5*x,y);
+       d = ABS(z);
+       if (d <= ABS(d-y)) return z;
+       else return (z>0)?z-y:z+y;
+     }
      else { /* if x is too big */
        if (kx == 0x7ff00000 && u.i[LOW_HALF] == 0 && y == 1.0)
  	return x / x;
*************** double __ieee754_remainder(double x, dou
*** 116,120 ****
--- 124,129 ----
  	return (u.i[HIGH_HALF]&0x80000000)?nNAN.x:NAN.x;
        else return x;
      }
+    }
    }
  }


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]