Update contrib.
3 * Portions Copyright (c) 1993-1999 Nokia Corporation and/or its subsidiary(-ies).
8 /* @(#)s_modf.c 5.1 93/09/24 */
10 * ====================================================
11 * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved.
13 * Developed at SunPro, a Sun Microsystems, Inc. business.
14 * Permission to use, copy, modify, and distribute this
15 * software is freely granted, provided that this notice
17 * ====================================================
22 <<modf>>, <<modff>>---split fractional and integer parts
31 double modf(double <[val]>, double *<[ipart]>);
32 float modff(float <[val]>, float *<[ipart]>);
36 double modf(<[val]>, <[ipart]>)
40 float modff(<[val]>, <[ipart]>)
45 <<modf>> splits the double <[val]> apart into an integer part
46 and a fractional part, returning the fractional part and
47 storing the integer part in <<*<[ipart]>>>. No rounding
48 whatsoever is done; the sum of the integer and fractional
49 parts is guaranteed to be exactly equal to <[val]>. That
50 is, if . <[realpart]> = modf(<[val]>, &<[intpart]>); then
51 `<<<[realpart]>+<[intpart]>>>' is the same as <[val]>.
52 <<modff>> is identical, save that it takes and returns
53 <<float>> rather than <<double>> values.
56 The fractional part is returned. Each result has the same
57 sign as the supplied argument <[val]>.
60 <<modf>> is ANSI C. <<modff>> is an extension.
69 * modf(double x, double *iptr)
70 * return fraction part of x, and return x's integral part in *iptr.
80 static const double one = 1.0;
83 Split floating-point value into fractional and integer parts.
84 Breaks x in two parts: the integer (stored in location pointed by iptr)
85 and the fraction (return value).
86 @return Fractional part of x
87 @param x Floating point value.
88 @param iptr Location where the integer part of x will be stored.
90 EXPORT_C double modf(double x, double *iptr) __SOFTFP
94 EXTRACT_WORDS(i0,i1,x);
95 j0 = ((i0>>20)&0x7ff)-0x3ff; /* exponent of x */
96 if(j0<20) { /* integer part in high x */
97 if(j0<0) { /* |x|<1 */
98 INSERT_WORDS(*iptr,i0&0x80000000,0); /* *iptr = +-0 */
101 i = (0x000fffff)>>j0;
102 if(((i0&i)|i1)==0) { /* x is integral */
105 GET_HIGH_WORD(high,x);
106 INSERT_WORDS(x,high&0x80000000,0); /* return +-0 */
109 INSERT_WORDS(*iptr,i0&(~i),0);
113 } else if (j0>51) { /* no fraction part */
116 GET_HIGH_WORD(high,x);
117 INSERT_WORDS(x,high&0x80000000,0); /* return +-0 */
119 } else { /* fraction part in low x */
120 i = ((__uint32_t)(0xffffffff))>>(j0-20);
121 if((i1&i)==0) { /* x is integral */
124 GET_HIGH_WORD(high,x);
125 INSERT_WORDS(x,high&0x80000000,0); /* return +-0 */
128 INSERT_WORDS(*iptr,i0,i1&(~i));