summary refs log tree commit diff
path: root/sysdeps/ieee754/dbl-64/s_scalbn.c
diff options
context:
space:
mode:
Diffstat (limited to 'sysdeps/ieee754/dbl-64/s_scalbn.c')
-rw-r--r--sysdeps/ieee754/dbl-64/s_scalbn.c63
1 files changed, 30 insertions, 33 deletions
diff --git a/sysdeps/ieee754/dbl-64/s_scalbn.c b/sysdeps/ieee754/dbl-64/s_scalbn.c
index cf4d6846ee..4491227f3e 100644
--- a/sysdeps/ieee754/dbl-64/s_scalbn.c
+++ b/sysdeps/ieee754/dbl-64/s_scalbn.c
@@ -20,43 +20,40 @@
 #include <math_private.h>
 
 static const double
-  two54 = 1.80143985094819840000e+16,  /* 0x43500000, 0x00000000 */
-  twom54 = 5.55111512312578270212e-17, /* 0x3C900000, 0x00000000 */
-  huge = 1.0e+300,
-  tiny = 1.0e-300;
+two54   =  1.80143985094819840000e+16, /* 0x43500000, 0x00000000 */
+twom54  =  5.55111512312578270212e-17, /* 0x3C900000, 0x00000000 */
+huge   = 1.0e+300,
+tiny   = 1.0e-300;
 
 double
 __scalbn (double x, int n)
 {
-  int32_t k, hx, lx;
-  EXTRACT_WORDS (hx, lx, x);
-  k = (hx & 0x7ff00000) >> 20;                  /* extract exponent */
-  if (__glibc_unlikely (k == 0))                   /* 0 or subnormal x */
-    {
-      if ((lx | (hx & 0x7fffffff)) == 0)
-	return x;                                  /* +-0 */
-      x *= two54;
-      GET_HIGH_WORD (hx, x);
-      k = ((hx & 0x7ff00000) >> 20) - 54;
-    }
-  if (__glibc_unlikely (k == 0x7ff))
-    return x + x;                                       /* NaN or Inf */
-  if (__glibc_unlikely (n < -50000))
-    return tiny * copysign (tiny, x);   /*underflow*/
-  if (__glibc_unlikely (n > 50000 || k + n > 0x7fe))
-    return huge * copysign (huge, x);   /* overflow  */
-  /* Now k and n are bounded we know that k = k+n does not
-     overflow.  */
-  k = k + n;
-  if (__glibc_likely (k > 0))                    /* normal result */
-    {
-      SET_HIGH_WORD (x, (hx & 0x800fffff) | (k << 20)); return x;
-    }
-  if (k <= -54)
-    return tiny * copysign (tiny, x);         /*underflow*/
-  k += 54;                                      /* subnormal result */
-  SET_HIGH_WORD (x, (hx & 0x800fffff) | (k << 20));
-  return x * twom54;
+	int64_t ix;
+	int64_t k;
+	EXTRACT_WORDS64(ix,x);
+	k = (ix >> 52) & 0x7ff;			/* extract exponent */
+	if (__builtin_expect(k==0, 0)) {	/* 0 or subnormal x */
+	    if ((ix & UINT64_C(0xfffffffffffff))==0) return x; /* +-0 */
+	    x *= two54;
+	    EXTRACT_WORDS64(ix,x);
+	    k = ((ix >> 52) & 0x7ff) - 54;
+	    }
+	if (__builtin_expect(k==0x7ff, 0)) return x+x;	/* NaN or Inf */
+	if (__builtin_expect(n< -50000, 0))
+	  return tiny*copysign(tiny,x); /*underflow*/
+	if (__builtin_expect(n> 50000 || k+n > 0x7fe, 0))
+	  return huge*copysign(huge,x); /* overflow  */
+	/* Now k and n are bounded we know that k = k+n does not
+	   overflow.  */
+	k = k+n;
+	if (__builtin_expect(k > 0, 1))		/* normal result */
+	    {INSERT_WORDS64(x,(ix&UINT64_C(0x800fffffffffffff))|(k<<52));
+	      return x;}
+	if (k <= -54)
+	  return tiny*copysign(tiny,x);	/*underflow*/
+	k += 54;				/* subnormal result */
+	INSERT_WORDS64(x,(ix&INT64_C(0x800fffffffffffff))|(k<<52));
+	return x*twom54;
 }
 #ifdef NO_LONG_DOUBLE
 strong_alias (__scalbn, __scalbnl)