Exemplo n.º 1
0
long double __fabsl(long double x)
{
	uint64_t hx, lx;
	double xhi, xlo;

	ldbl_unpack (x, &xhi, &xlo);
	EXTRACT_WORDS64 (hx, xhi);
	EXTRACT_WORDS64 (lx, xlo);
	lx = lx ^ ( hx & 0x8000000000000000LL );
	hx = hx & 0x7fffffffffffffffLL;
	INSERT_WORDS64 (xhi, hx);
	INSERT_WORDS64 (xlo, lx);
	x = ldbl_pack (xhi, xlo);
	return x;
}
Exemplo n.º 2
0
double
__ieee754_log10 (double x)
{
    double y, z;
    int64_t i, hx;
    int32_t k;

    EXTRACT_WORDS64 (hx, x);

    k = 0;
    if (hx < INT64_C(0x0010000000000000))
    {   /* x < 2**-1022  */
        if (__builtin_expect ((hx & UINT64_C(0x7fffffffffffffff)) == 0, 0))
            return -two54 / (x - x);	/* log(+-0)=-inf */
        if (__builtin_expect (hx < 0, 0))
            return (x - x) / (x - x);	/* log(-#) = NaN */
        k -= 54;
        x *= two54;		/* subnormal number, scale up x */
        EXTRACT_WORDS64 (hx, x);
    }
    /* scale up resulted in a NaN number  */
    if (__builtin_expect (hx >= UINT64_C(0x7ff0000000000000), 0))
        return x + x;
    k += (hx >> 52) - 1023;
    i = ((uint64_t) k & UINT64_C(0x8000000000000000)) >> 63;
    hx = (hx & UINT64_C(0x000fffffffffffff)) | ((0x3ff - i) << 52);
    y = (double) (k + i);
    INSERT_WORDS64 (x, hx);
    z = y * log10_2lo + ivln10 * __ieee754_log (x);
    return z + y * log10_2hi;
}
Exemplo n.º 3
0
double
__roundeven (double x)
{
  uint64_t ix, ux;
  EXTRACT_WORDS64 (ix, x);
  ux = ix & 0x7fffffffffffffffULL;
  int exponent = ux >> (MANT_DIG - 1);
  if (exponent >= BIAS + MANT_DIG - 1)
    {
      /* Integer, infinity or NaN.  */
      if (exponent == MAX_EXP)
	/* Infinity or NaN; quiet signaling NaNs.  */
	return x + x;
      else
	return x;
    }
  else if (exponent >= BIAS)
    {
      /* At least 1; not necessarily an integer.  Locate the bits with
	 exponents 0 and -1 (when the unbiased exponent is 0, the bit
	 with exponent 0 is implicit, but as the bias is odd it is OK
	 to take it from the low bit of the exponent).  */
      int int_pos = (BIAS + MANT_DIG - 1) - exponent;
      int half_pos = int_pos - 1;
      uint64_t half_bit = 1ULL << half_pos;
      uint64_t int_bit = 1ULL << int_pos;
      if ((ix & (int_bit | (half_bit - 1))) != 0)
	/* Carry into the exponent works correctly.  No need to test
	   whether HALF_BIT is set.  */
	ix += half_bit;
      ix &= ~(int_bit - 1);
    }
  else if (exponent == BIAS - 1 && ux > 0x3fe0000000000000ULL)
    /* Interval (0.5, 1).  */
    ix = (ix & 0x8000000000000000ULL) | 0x3ff0000000000000ULL;
  else
    /* Rounds to 0.  */
    ix &= 0x8000000000000000ULL;
  INSERT_WORDS64 (x, ix);
  return x;
}
Exemplo n.º 4
0
double
__remquo (double x, double y, int *quo)
{
  int64_t hx, hy;
  uint64_t sx, qs;
  int cquo;

  EXTRACT_WORDS64 (hx, x);
  EXTRACT_WORDS64 (hy, y);
  sx = hx & UINT64_C(0x8000000000000000);
  qs = sx ^ (hy & UINT64_C(0x8000000000000000));
  hy &= UINT64_C(0x7fffffffffffffff);
  hx &= UINT64_C(0x7fffffffffffffff);

  /* Purge off exception values.  */
  if (__glibc_unlikely (hy == 0))
    return (x * y) / (x * y);			/* y = 0 */
  if (__builtin_expect (hx >= UINT64_C(0x7ff0000000000000) /* x not finite */
			|| hy > UINT64_C(0x7ff0000000000000), 0))/* y is NaN */
    return (x * y) / (x * y);

  if (hy <= UINT64_C(0x7fbfffffffffffff))
    x = __ieee754_fmod (x, 8 * y);		/* now x < 8y */

  if (__glibc_unlikely (hx == hy))
    {
      *quo = qs ? -1 : 1;
      return zero * x;
    }

  x = fabs (x);
  INSERT_WORDS64 (y, hy);
  cquo = 0;

  if (hy <= UINT64_C(0x7fcfffffffffffff) && x >= 4 * y)
    {
      x -= 4 * y;
      cquo += 4;
    }
  if (hy <= UINT64_C(0x7fdfffffffffffff) && x >= 2 * y)
    {
      x -= 2 * y;
      cquo += 2;
    }

  if (hy < UINT64_C(0x0020000000000000))
    {
      if (x + x > y)
	{
	  x -= y;
	  ++cquo;
	  if (x + x >= y)
	    {
	      x -= y;
	      ++cquo;
	    }
	}
    }
  else
    {
      double y_half = 0.5 * y;
      if (x > y_half)
	{
	  x -= y;
	  ++cquo;
	  if (x >= y_half)
	    {
	      x -= y;
	      ++cquo;
	    }
	}
    }

  *quo = qs ? -cquo : cquo;

  /* Ensure correct sign of zero result in round-downward mode.  */
  if (x == 0.0)
    x = 0.0;
  if (sx)
    x = -x;
  return x;
}