155dfb921Sbrad /* @(#)s_floor.c 5.1 93/09/24 */
255dfb921Sbrad /*
355dfb921Sbrad * ====================================================
455dfb921Sbrad * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
555dfb921Sbrad *
655dfb921Sbrad * Developed at SunPro, a Sun Microsystems, Inc. business.
755dfb921Sbrad * Permission to use, copy, modify, and distribute this
855dfb921Sbrad * software is freely granted, provided that this notice
955dfb921Sbrad * is preserved.
1055dfb921Sbrad * ====================================================
1155dfb921Sbrad */
1255dfb921Sbrad
1355dfb921Sbrad /*
1455dfb921Sbrad * trunc(x)
1555dfb921Sbrad * Return x rounded toward 0 to integral value
1655dfb921Sbrad * Method:
1755dfb921Sbrad * Bit twiddling.
1855dfb921Sbrad * Exception:
1955dfb921Sbrad * Inexact flag raised if x not equal to trunc(x).
2055dfb921Sbrad */
2155dfb921Sbrad
2249393c00Smartynas #include <float.h>
2349393c00Smartynas #include <math.h>
2449393c00Smartynas
2555dfb921Sbrad #include "math_private.h"
2655dfb921Sbrad
2755dfb921Sbrad static const double huge = 1.0e300;
2855dfb921Sbrad
2955dfb921Sbrad double
trunc(double x)3055dfb921Sbrad trunc(double x)
3155dfb921Sbrad {
3255fa043fSotto int32_t i0,i1,jj0;
3371324c4cSotto u_int32_t i;
3455dfb921Sbrad EXTRACT_WORDS(i0,i1,x);
3555fa043fSotto jj0 = ((i0>>20)&0x7ff)-0x3ff;
3655fa043fSotto if(jj0<20) {
3755fa043fSotto if(jj0<0) { /* raise inexact if x != 0 */
3855dfb921Sbrad if(huge+x>0.0) {/* |x|<1, so return 0*sign(x) */
3955dfb921Sbrad i0 &= 0x80000000U;
4055dfb921Sbrad i1 = 0;
4155dfb921Sbrad }
4255dfb921Sbrad } else {
4355fa043fSotto i = (0x000fffff)>>jj0;
4455dfb921Sbrad if(((i0&i)|i1)==0) return x; /* x is integral */
4555dfb921Sbrad if(huge+x>0.0) { /* raise inexact flag */
4655dfb921Sbrad i0 &= (~i); i1=0;
4755dfb921Sbrad }
4855dfb921Sbrad }
4955fa043fSotto } else if (jj0>51) {
5055fa043fSotto if(jj0==0x400) return x+x; /* inf or NaN */
5155dfb921Sbrad else return x; /* x is integral */
5255dfb921Sbrad } else {
5355fa043fSotto i = ((u_int32_t)(0xffffffff))>>(jj0-20);
5455dfb921Sbrad if((i1&i)==0) return x; /* x is integral */
5555dfb921Sbrad if(huge+x>0.0) /* raise inexact flag */
5655dfb921Sbrad i1 &= (~i);
5755dfb921Sbrad }
5855dfb921Sbrad INSERT_WORDS(x,i0,i1);
5955dfb921Sbrad return x;
6055dfb921Sbrad }
61*2f2c0062Sguenther DEF_STD(trunc);
62*2f2c0062Sguenther LDBL_MAYBE_UNUSED_CLONE(trunc);
63