patches/glibc/ports-2.10.1/470-alpha-floor_ceil_fix.patch
changeset 1625 fde082da9813
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/patches/glibc/ports-2.10.1/470-alpha-floor_ceil_fix.patch	Fri Nov 13 21:37:18 2009 +0100
     1.3 @@ -0,0 +1,270 @@
     1.4 +http://sources.redhat.com/bugzilla/show_bug.cgi?id=5350
     1.5 +https://bugs.gentoo.org/264335
     1.6 +
     1.7 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceil.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceil.c
     1.8 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceil.c	2009-05-16 10:36:20.000000000 +0200
     1.9 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceil.c	2009-11-13 00:50:59.000000000 +0100
    1.10 +@@ -27,20 +27,25 @@
    1.11 + double
    1.12 + __ceil (double x)
    1.13 + {
    1.14 +-  double two52 = copysign (0x1.0p52, x);
    1.15 +-  double r, tmp;
    1.16 +-  
    1.17 +-  __asm (
    1.18 ++  if (isless (fabs (x), 9007199254740992.0))	/* 1 << DBL_MANT_DIG */
    1.19 ++    {
    1.20 ++      double tmp1, new_x;
    1.21 ++
    1.22 ++      new_x = -x;
    1.23 ++      __asm (
    1.24 + #ifdef _IEEE_FP_INEXACT
    1.25 +-	 "addt/suim %2, %3, %1\n\tsubt/suim %1, %3, %0"
    1.26 ++	     "cvttq/svim %2,%1\n\t"
    1.27 + #else
    1.28 +-	 "addt/sum %2, %3, %1\n\tsubt/sum %1, %3, %0"
    1.29 ++	     "cvttq/svm %2,%1\n\t"
    1.30 + #endif
    1.31 +-	 : "=&f"(r), "=&f"(tmp)
    1.32 +-	 : "f"(-x), "f"(-two52));
    1.33 ++	     "cvtqt/m %1,%0\n\t"
    1.34 ++	     : "=f"(new_x), "=&f"(tmp1)
    1.35 ++	     : "f"(new_x));
    1.36 + 
    1.37 +-  /* Fix up the negation we did above, as well as handling -0 properly. */
    1.38 +-  return copysign (r, x);
    1.39 ++      /* Fix up the negation we did above, as well as handling -0 properly. */
    1.40 ++      x = copysign(new_x, x);
    1.41 ++    }
    1.42 ++  return x;
    1.43 + }
    1.44 + 
    1.45 + weak_alias (__ceil, ceil)
    1.46 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceilf.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceilf.c
    1.47 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceilf.c	2009-05-16 10:36:20.000000000 +0200
    1.48 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_ceilf.c	2009-11-13 00:50:59.000000000 +0100
    1.49 +@@ -26,20 +26,30 @@
    1.50 + float
    1.51 + __ceilf (float x)
    1.52 + {
    1.53 +-  float two23 = copysignf (0x1.0p23, x);
    1.54 +-  float r, tmp;
    1.55 +-  
    1.56 +-  __asm (
    1.57 ++  if (isless (fabsf (x), 16777216.0f))	/* 1 << FLT_MANT_DIG */
    1.58 ++    {
    1.59 ++      /* Note that Alpha S_Floating is stored in registers in a
    1.60 ++	 restricted T_Floating format, so we don't even need to
    1.61 ++	 convert back to S_Floating in the end.  The initial
    1.62 ++	 conversion to T_Floating is needed to handle denormals.  */
    1.63 ++
    1.64 ++      float tmp1, tmp2, new_x;
    1.65 ++
    1.66 ++      new_x = -x;
    1.67 ++      __asm ("cvtst/s %3,%2\n\t"
    1.68 + #ifdef _IEEE_FP_INEXACT
    1.69 +-	 "adds/suim %2, %3, %1\n\tsubs/suim %1, %3, %0"
    1.70 ++	     "cvttq/svim %2,%1\n\t"
    1.71 + #else
    1.72 +-	 "adds/sum %2, %3, %1\n\tsubs/sum %1, %3, %0"
    1.73 ++	     "cvttq/svm %2,%1\n\t"
    1.74 + #endif
    1.75 +-	 : "=&f"(r), "=&f"(tmp)
    1.76 +-	 : "f"(-x), "f"(-two23));
    1.77 ++	     "cvtqt/m %1,%0\n\t"
    1.78 ++	     : "=f"(new_x), "=&f"(tmp1), "=&f"(tmp2)
    1.79 ++	     : "f"(new_x));
    1.80 + 
    1.81 +-  /* Fix up the negation we did above, as well as handling -0 properly. */
    1.82 +-  return copysignf (r, x);
    1.83 ++      /* Fix up the negation we did above, as well as handling -0 properly. */
    1.84 ++      x = copysignf(new_x, x);
    1.85 ++    }
    1.86 ++  return x;
    1.87 + }
    1.88 + 
    1.89 + weak_alias (__ceilf, ceilf)
    1.90 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floor.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floor.c
    1.91 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floor.c	2009-05-16 10:36:20.000000000 +0200
    1.92 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floor.c	2009-11-13 00:50:59.000000000 +0100
    1.93 +@@ -21,26 +21,32 @@
    1.94 + #include <math_ldbl_opt.h>
    1.95 + 
    1.96 + 
    1.97 +-/* Use the -inf rounding mode conversion instructions to implement floor.  */
    1.98 ++/* Use the -inf rounding mode conversion instructions to implement
    1.99 ++   floor.  We note when the exponent is large enough that the value
   1.100 ++   must be integral, as this avoids unpleasant integer overflows.  */
   1.101 + 
   1.102 + double
   1.103 + __floor (double x)
   1.104 + {
   1.105 +-  double two52 = copysign (0x1.0p52, x);
   1.106 +-  double r, tmp;
   1.107 +-  
   1.108 +-  __asm (
   1.109 ++  if (isless (fabs (x), 9007199254740992.0))	/* 1 << DBL_MANT_DIG */
   1.110 ++    {
   1.111 ++      double tmp1, new_x;
   1.112 ++
   1.113 ++      __asm (
   1.114 + #ifdef _IEEE_FP_INEXACT
   1.115 +-	 "addt/suim %2, %3, %1\n\tsubt/suim %1, %3, %0"
   1.116 ++	     "cvttq/svim %2,%1\n\t"
   1.117 + #else
   1.118 +-	 "addt/sum %2, %3, %1\n\tsubt/sum %1, %3, %0"
   1.119 ++	     "cvttq/svm %2,%1\n\t"
   1.120 + #endif
   1.121 +-	 : "=&f"(r), "=&f"(tmp)
   1.122 +-	 : "f"(x), "f"(two52));
   1.123 ++	     "cvtqt/m %1,%0\n\t"
   1.124 ++	     : "=f"(new_x), "=&f"(tmp1)
   1.125 ++	     : "f"(x));
   1.126 + 
   1.127 +-  /* floor(-0) == -0, and in general we'll always have the same
   1.128 +-     sign as our input.  */
   1.129 +-  return copysign (r, x);
   1.130 ++      /* floor(-0) == -0, and in general we'll always have the same
   1.131 ++	 sign as our input.  */
   1.132 ++      x = copysign(new_x, x);
   1.133 ++    }
   1.134 ++  return x;
   1.135 + }
   1.136 + 
   1.137 + weak_alias (__floor, floor)
   1.138 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floorf.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floorf.c
   1.139 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floorf.c	2009-05-16 10:36:20.000000000 +0200
   1.140 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_floorf.c	2009-11-13 00:50:59.000000000 +0100
   1.141 +@@ -20,26 +20,37 @@
   1.142 + #include <math.h>
   1.143 + 
   1.144 + 
   1.145 +-/* Use the -inf rounding mode conversion instructions to implement floor.  */
   1.146 ++/* Use the -inf rounding mode conversion instructions to implement
   1.147 ++   floor.  We note when the exponent is large enough that the value
   1.148 ++   must be integral, as this avoids unpleasant integer overflows.  */
   1.149 + 
   1.150 + float
   1.151 + __floorf (float x)
   1.152 + {
   1.153 +-  float two23 = copysignf (0x1.0p23, x);
   1.154 +-  float r, tmp;
   1.155 +-  
   1.156 +-  __asm (
   1.157 ++  if (isless (fabsf (x), 16777216.0f))	/* 1 << FLT_MANT_DIG */
   1.158 ++    {
   1.159 ++      /* Note that Alpha S_Floating is stored in registers in a
   1.160 ++	 restricted T_Floating format, so we don't even need to
   1.161 ++	 convert back to S_Floating in the end.  The initial
   1.162 ++	 conversion to T_Floating is needed to handle denormals.  */
   1.163 ++
   1.164 ++      float tmp1, tmp2, new_x;
   1.165 ++
   1.166 ++      __asm ("cvtst/s %3,%2\n\t"
   1.167 + #ifdef _IEEE_FP_INEXACT
   1.168 +-	 "adds/suim %2, %3, %1\n\tsubs/suim %1, %3, %0"
   1.169 ++	     "cvttq/svim %2,%1\n\t"
   1.170 + #else
   1.171 +-	 "adds/sum %2, %3, %1\n\tsubs/sum %1, %3, %0"
   1.172 ++	     "cvttq/svm %2,%1\n\t"
   1.173 + #endif
   1.174 +-	 : "=&f"(r), "=&f"(tmp)
   1.175 +-	 : "f"(x), "f"(two23));
   1.176 ++	     "cvtqt/m %1,%0\n\t"
   1.177 ++	     : "=f"(new_x), "=&f"(tmp1), "=&f"(tmp2)
   1.178 ++	     : "f"(x));
   1.179 + 
   1.180 +-  /* floor(-0) == -0, and in general we'll always have the same
   1.181 +-     sign as our input.  */
   1.182 +-  return copysignf (r, x);
   1.183 ++      /* floor(-0) == -0, and in general we'll always have the same
   1.184 ++	 sign as our input.  */
   1.185 ++      x = copysignf(new_x, x);
   1.186 ++    }
   1.187 ++  return x;
   1.188 + }
   1.189 + 
   1.190 + weak_alias (__floorf, floorf)
   1.191 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rint.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rint.c
   1.192 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rint.c	2009-05-16 10:36:20.000000000 +0200
   1.193 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rint.c	2009-11-13 00:50:59.000000000 +0100
   1.194 +@@ -24,15 +24,24 @@
   1.195 + double
   1.196 + __rint (double x)
   1.197 + {
   1.198 +-  double two52 = copysign (0x1.0p52, x);
   1.199 +-  double r;
   1.200 +-  
   1.201 +-  r = x + two52;
   1.202 +-  r = r - two52;
   1.203 ++  if (isless (fabs (x), 9007199254740992.0))	/* 1 << DBL_MANT_DIG */
   1.204 ++    {
   1.205 ++      double tmp1, new_x;
   1.206 ++      __asm (
   1.207 ++#ifdef _IEEE_FP_INEXACT
   1.208 ++	     "cvttq/svid %2,%1\n\t"
   1.209 ++#else
   1.210 ++	     "cvttq/svd %2,%1\n\t"
   1.211 ++#endif
   1.212 ++	     "cvtqt/d %1,%0\n\t"
   1.213 ++	     : "=f"(new_x), "=&f"(tmp1)
   1.214 ++	     : "f"(x));
   1.215 + 
   1.216 +-  /* rint(-0.1) == -0, and in general we'll always have the same sign
   1.217 +-     as our input.  */
   1.218 +-  return copysign (r, x);
   1.219 ++      /* rint(-0.1) == -0, and in general we'll always have the same
   1.220 ++	 sign as our input.  */
   1.221 ++      x = copysign(new_x, x);
   1.222 ++    }
   1.223 ++  return x;
   1.224 + }
   1.225 + 
   1.226 + weak_alias (__rint, rint)
   1.227 +diff -durN glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rintf.c glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rintf.c
   1.228 +--- glibc-2.10.1.orig/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rintf.c	2009-05-16 10:36:20.000000000 +0200
   1.229 ++++ glibc-2.10.1/glibc-ports-2.10.1/sysdeps/alpha/fpu/s_rintf.c	2009-11-13 00:50:59.000000000 +0100
   1.230 +@@ -23,15 +23,30 @@
   1.231 + float
   1.232 + __rintf (float x)
   1.233 + {
   1.234 +-  float two23 = copysignf (0x1.0p23, x);
   1.235 +-  float r;
   1.236 ++  if (isless (fabsf (x), 16777216.0f))	/* 1 << FLT_MANT_DIG */
   1.237 ++    {
   1.238 ++      /* Note that Alpha S_Floating is stored in registers in a
   1.239 ++	 restricted T_Floating format, so we don't even need to
   1.240 ++	 convert back to S_Floating in the end.  The initial
   1.241 ++	 conversion to T_Floating is needed to handle denormals.  */
   1.242 + 
   1.243 +-  r = x + two23;
   1.244 +-  r = r - two23;
   1.245 ++      float tmp1, tmp2, new_x;
   1.246 + 
   1.247 +-  /* rint(-0.1) == -0, and in general we'll always have the same sign
   1.248 +-     as our input.  */
   1.249 +-  return copysign (r, x);
   1.250 ++      __asm ("cvtst/s %3,%2\n\t"
   1.251 ++#ifdef _IEEE_FP_INEXACT
   1.252 ++	     "cvttq/svid %2,%1\n\t"
   1.253 ++#else
   1.254 ++	     "cvttq/svd %2,%1\n\t"
   1.255 ++#endif
   1.256 ++	     "cvtqt/d %1,%0\n\t"
   1.257 ++	     : "=f"(new_x), "=&f"(tmp1), "=&f"(tmp2)
   1.258 ++	     : "f"(x));
   1.259 ++
   1.260 ++      /* rint(-0.1) == -0, and in general we'll always have the same
   1.261 ++	 sign as our input.  */
   1.262 ++      x = copysignf(new_x, x);
   1.263 ++    }
   1.264 ++  return x;
   1.265 + }
   1.266 + 
   1.267 + weak_alias (__rintf, rintf)
   1.268 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_ceil.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_ceil.c
   1.269 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_ceilf.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_ceilf.c
   1.270 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_floor.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_floor.c
   1.271 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_floorf.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_floorf.c
   1.272 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_rint.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_rint.c
   1.273 +diff -durN glibc-2.10.1.orig/ports/sysdeps/alpha/fpu/s_rintf.c glibc-2.10.1/ports/sysdeps/alpha/fpu/s_rintf.c