13a8617a8SJordan K. Hubbard /* 23a8617a8SJordan K. Hubbard * ==================================================== 33a8617a8SJordan K. Hubbard * Copyright (C) 1993 by Sun Microsystems, Inc. All rights reserved. 43a8617a8SJordan K. Hubbard * 53a8617a8SJordan K. Hubbard * Developed at SunPro, a Sun Microsystems, Inc. business. 63a8617a8SJordan K. Hubbard * Permission to use, copy, modify, and distribute this 73a8617a8SJordan K. Hubbard * software is freely granted, provided that this notice 83a8617a8SJordan K. Hubbard * is preserved. 93a8617a8SJordan K. Hubbard * ==================================================== 103a8617a8SJordan K. Hubbard */ 113a8617a8SJordan K. Hubbard 123a8617a8SJordan K. Hubbard /* 133a8617a8SJordan K. Hubbard * from: @(#)fdlibm.h 5.1 93/09/24 147f3dea24SPeter Wemm * $FreeBSD$ 153a8617a8SJordan K. Hubbard */ 163a8617a8SJordan K. Hubbard 173a8617a8SJordan K. Hubbard #ifndef _MATH_PRIVATE_H_ 183a8617a8SJordan K. Hubbard #define _MATH_PRIVATE_H_ 193a8617a8SJordan K. Hubbard 203a8617a8SJordan K. Hubbard #include <sys/types.h> 21bcfa1759SBrian Somers #include <machine/endian.h> 223a8617a8SJordan K. Hubbard 23ef1ee63eSAlexey Zelkin /* 24ef1ee63eSAlexey Zelkin * The original fdlibm code used statements like: 25ef1ee63eSAlexey Zelkin * n0 = ((*(int*)&one)>>29)^1; * index of high word * 26ef1ee63eSAlexey Zelkin * ix0 = *(n0+(int*)&x); * high word of x * 27ef1ee63eSAlexey Zelkin * ix1 = *((1-n0)+(int*)&x); * low word of x * 28ef1ee63eSAlexey Zelkin * to dig two 32 bit words out of the 64 bit IEEE floating point 29ef1ee63eSAlexey Zelkin * value. That is non-ANSI, and, moreover, the gcc instruction 30ef1ee63eSAlexey Zelkin * scheduler gets it wrong. We instead use the following macros. 31ef1ee63eSAlexey Zelkin * Unlike the original code, we determine the endianness at compile 32ef1ee63eSAlexey Zelkin * time, not at run time; I don't see much benefit to selecting 33ef1ee63eSAlexey Zelkin * endianness at run time. 34ef1ee63eSAlexey Zelkin */ 353a8617a8SJordan K. Hubbard 36ef1ee63eSAlexey Zelkin /* 37ef1ee63eSAlexey Zelkin * A union which permits us to convert between a double and two 32 bit 38ef1ee63eSAlexey Zelkin * ints. 39ef1ee63eSAlexey Zelkin */ 403a8617a8SJordan K. Hubbard 4174aed985SMarcel Moolenaar #ifdef __arm__ 4274aed985SMarcel Moolenaar #if defined(__VFP_FP__) 4374aed985SMarcel Moolenaar #define IEEE_WORD_ORDER BYTE_ORDER 4474aed985SMarcel Moolenaar #else 4574aed985SMarcel Moolenaar #define IEEE_WORD_ORDER BIG_ENDIAN 4674aed985SMarcel Moolenaar #endif 4774aed985SMarcel Moolenaar #else /* __arm__ */ 4874aed985SMarcel Moolenaar #define IEEE_WORD_ORDER BYTE_ORDER 4974aed985SMarcel Moolenaar #endif 5074aed985SMarcel Moolenaar 5174aed985SMarcel Moolenaar #if IEEE_WORD_ORDER == BIG_ENDIAN 523a8617a8SJordan K. Hubbard 533a8617a8SJordan K. Hubbard typedef union 543a8617a8SJordan K. Hubbard { 553a8617a8SJordan K. Hubbard double value; 563a8617a8SJordan K. Hubbard struct 573a8617a8SJordan K. Hubbard { 583a8617a8SJordan K. Hubbard u_int32_t msw; 593a8617a8SJordan K. Hubbard u_int32_t lsw; 603a8617a8SJordan K. Hubbard } parts; 613d4dfde4SDavid Schultz struct 623d4dfde4SDavid Schultz { 633d4dfde4SDavid Schultz u_int64_t w; 643d4dfde4SDavid Schultz } xparts; 653a8617a8SJordan K. Hubbard } ieee_double_shape_type; 663a8617a8SJordan K. Hubbard 673a8617a8SJordan K. Hubbard #endif 683a8617a8SJordan K. Hubbard 6974aed985SMarcel Moolenaar #if IEEE_WORD_ORDER == LITTLE_ENDIAN 703a8617a8SJordan K. Hubbard 713a8617a8SJordan K. Hubbard typedef union 723a8617a8SJordan K. Hubbard { 733a8617a8SJordan K. Hubbard double value; 743a8617a8SJordan K. Hubbard struct 753a8617a8SJordan K. Hubbard { 763a8617a8SJordan K. Hubbard u_int32_t lsw; 773a8617a8SJordan K. Hubbard u_int32_t msw; 783a8617a8SJordan K. Hubbard } parts; 793d4dfde4SDavid Schultz struct 803d4dfde4SDavid Schultz { 813d4dfde4SDavid Schultz u_int64_t w; 823d4dfde4SDavid Schultz } xparts; 833a8617a8SJordan K. Hubbard } ieee_double_shape_type; 843a8617a8SJordan K. Hubbard 853a8617a8SJordan K. Hubbard #endif 863a8617a8SJordan K. Hubbard 873a8617a8SJordan K. Hubbard /* Get two 32 bit ints from a double. */ 883a8617a8SJordan K. Hubbard 893a8617a8SJordan K. Hubbard #define EXTRACT_WORDS(ix0,ix1,d) \ 903a8617a8SJordan K. Hubbard do { \ 913a8617a8SJordan K. Hubbard ieee_double_shape_type ew_u; \ 923a8617a8SJordan K. Hubbard ew_u.value = (d); \ 933a8617a8SJordan K. Hubbard (ix0) = ew_u.parts.msw; \ 943a8617a8SJordan K. Hubbard (ix1) = ew_u.parts.lsw; \ 953a8617a8SJordan K. Hubbard } while (0) 963a8617a8SJordan K. Hubbard 973d4dfde4SDavid Schultz /* Get a 64-bit int from a double. */ 983d4dfde4SDavid Schultz #define EXTRACT_WORD64(ix,d) \ 993d4dfde4SDavid Schultz do { \ 1003d4dfde4SDavid Schultz ieee_double_shape_type ew_u; \ 1013d4dfde4SDavid Schultz ew_u.value = (d); \ 1023d4dfde4SDavid Schultz (ix) = ew_u.xparts.w; \ 1033d4dfde4SDavid Schultz } while (0) 1043d4dfde4SDavid Schultz 1053a8617a8SJordan K. Hubbard /* Get the more significant 32 bit int from a double. */ 1063a8617a8SJordan K. Hubbard 1073a8617a8SJordan K. Hubbard #define GET_HIGH_WORD(i,d) \ 1083a8617a8SJordan K. Hubbard do { \ 1093a8617a8SJordan K. Hubbard ieee_double_shape_type gh_u; \ 1103a8617a8SJordan K. Hubbard gh_u.value = (d); \ 1113a8617a8SJordan K. Hubbard (i) = gh_u.parts.msw; \ 1123a8617a8SJordan K. Hubbard } while (0) 1133a8617a8SJordan K. Hubbard 1143a8617a8SJordan K. Hubbard /* Get the less significant 32 bit int from a double. */ 1153a8617a8SJordan K. Hubbard 1163a8617a8SJordan K. Hubbard #define GET_LOW_WORD(i,d) \ 1173a8617a8SJordan K. Hubbard do { \ 1183a8617a8SJordan K. Hubbard ieee_double_shape_type gl_u; \ 1193a8617a8SJordan K. Hubbard gl_u.value = (d); \ 1203a8617a8SJordan K. Hubbard (i) = gl_u.parts.lsw; \ 1213a8617a8SJordan K. Hubbard } while (0) 1223a8617a8SJordan K. Hubbard 1233a8617a8SJordan K. Hubbard /* Set a double from two 32 bit ints. */ 1243a8617a8SJordan K. Hubbard 1253a8617a8SJordan K. Hubbard #define INSERT_WORDS(d,ix0,ix1) \ 1263a8617a8SJordan K. Hubbard do { \ 1273a8617a8SJordan K. Hubbard ieee_double_shape_type iw_u; \ 1283a8617a8SJordan K. Hubbard iw_u.parts.msw = (ix0); \ 1293a8617a8SJordan K. Hubbard iw_u.parts.lsw = (ix1); \ 1303a8617a8SJordan K. Hubbard (d) = iw_u.value; \ 1313a8617a8SJordan K. Hubbard } while (0) 1323a8617a8SJordan K. Hubbard 1333d4dfde4SDavid Schultz /* Set a double from a 64-bit int. */ 1343d4dfde4SDavid Schultz #define INSERT_WORD64(d,ix) \ 1353d4dfde4SDavid Schultz do { \ 1363d4dfde4SDavid Schultz ieee_double_shape_type iw_u; \ 1373d4dfde4SDavid Schultz iw_u.xparts.w = (ix); \ 1383d4dfde4SDavid Schultz (d) = iw_u.value; \ 1393d4dfde4SDavid Schultz } while (0) 1403d4dfde4SDavid Schultz 1413a8617a8SJordan K. Hubbard /* Set the more significant 32 bits of a double from an int. */ 1423a8617a8SJordan K. Hubbard 1433a8617a8SJordan K. Hubbard #define SET_HIGH_WORD(d,v) \ 1443a8617a8SJordan K. Hubbard do { \ 1453a8617a8SJordan K. Hubbard ieee_double_shape_type sh_u; \ 1463a8617a8SJordan K. Hubbard sh_u.value = (d); \ 1473a8617a8SJordan K. Hubbard sh_u.parts.msw = (v); \ 1483a8617a8SJordan K. Hubbard (d) = sh_u.value; \ 1493a8617a8SJordan K. Hubbard } while (0) 1503a8617a8SJordan K. Hubbard 1513a8617a8SJordan K. Hubbard /* Set the less significant 32 bits of a double from an int. */ 1523a8617a8SJordan K. Hubbard 1533a8617a8SJordan K. Hubbard #define SET_LOW_WORD(d,v) \ 1543a8617a8SJordan K. Hubbard do { \ 1553a8617a8SJordan K. Hubbard ieee_double_shape_type sl_u; \ 1563a8617a8SJordan K. Hubbard sl_u.value = (d); \ 1573a8617a8SJordan K. Hubbard sl_u.parts.lsw = (v); \ 1583a8617a8SJordan K. Hubbard (d) = sl_u.value; \ 1593a8617a8SJordan K. Hubbard } while (0) 1603a8617a8SJordan K. Hubbard 161ef1ee63eSAlexey Zelkin /* 162ef1ee63eSAlexey Zelkin * A union which permits us to convert between a float and a 32 bit 163ef1ee63eSAlexey Zelkin * int. 164ef1ee63eSAlexey Zelkin */ 1653a8617a8SJordan K. Hubbard 1663a8617a8SJordan K. Hubbard typedef union 1673a8617a8SJordan K. Hubbard { 1683a8617a8SJordan K. Hubbard float value; 1693a8617a8SJordan K. Hubbard /* FIXME: Assumes 32 bit int. */ 1703a8617a8SJordan K. Hubbard unsigned int word; 1713a8617a8SJordan K. Hubbard } ieee_float_shape_type; 1723a8617a8SJordan K. Hubbard 1733a8617a8SJordan K. Hubbard /* Get a 32 bit int from a float. */ 1743a8617a8SJordan K. Hubbard 1753a8617a8SJordan K. Hubbard #define GET_FLOAT_WORD(i,d) \ 1763a8617a8SJordan K. Hubbard do { \ 1773a8617a8SJordan K. Hubbard ieee_float_shape_type gf_u; \ 1783a8617a8SJordan K. Hubbard gf_u.value = (d); \ 1793a8617a8SJordan K. Hubbard (i) = gf_u.word; \ 1803a8617a8SJordan K. Hubbard } while (0) 1813a8617a8SJordan K. Hubbard 1823a8617a8SJordan K. Hubbard /* Set a float from a 32 bit int. */ 1833a8617a8SJordan K. Hubbard 1843a8617a8SJordan K. Hubbard #define SET_FLOAT_WORD(d,i) \ 1853a8617a8SJordan K. Hubbard do { \ 1863a8617a8SJordan K. Hubbard ieee_float_shape_type sf_u; \ 1873a8617a8SJordan K. Hubbard sf_u.word = (i); \ 1883a8617a8SJordan K. Hubbard (d) = sf_u.value; \ 1893a8617a8SJordan K. Hubbard } while (0) 1903a8617a8SJordan K. Hubbard 191*25a4d6bfSDavid Schultz /* 192*25a4d6bfSDavid Schultz * Get expsign and mantissa as 16 bit and 64 bit ints from an 80 bit long 193*25a4d6bfSDavid Schultz * double. 194*25a4d6bfSDavid Schultz */ 195*25a4d6bfSDavid Schultz 196*25a4d6bfSDavid Schultz #define EXTRACT_LDBL80_WORDS(ix0,ix1,d) \ 197*25a4d6bfSDavid Schultz do { \ 198*25a4d6bfSDavid Schultz union IEEEl2bits ew_u; \ 199*25a4d6bfSDavid Schultz ew_u.e = (d); \ 200*25a4d6bfSDavid Schultz (ix0) = ew_u.xbits.expsign; \ 201*25a4d6bfSDavid Schultz (ix1) = ew_u.xbits.man; \ 202*25a4d6bfSDavid Schultz } while (0) 203*25a4d6bfSDavid Schultz 204*25a4d6bfSDavid Schultz /* 205*25a4d6bfSDavid Schultz * Get expsign and mantissa as one 16 bit and two 64 bit ints from a 128 bit 206*25a4d6bfSDavid Schultz * long double. 207*25a4d6bfSDavid Schultz */ 208*25a4d6bfSDavid Schultz 209*25a4d6bfSDavid Schultz #define EXTRACT_LDBL128_WORDS(ix0,ix1,ix2,d) \ 210*25a4d6bfSDavid Schultz do { \ 211*25a4d6bfSDavid Schultz union IEEEl2bits ew_u; \ 212*25a4d6bfSDavid Schultz ew_u.e = (d); \ 213*25a4d6bfSDavid Schultz (ix0) = ew_u.xbits.expsign; \ 214*25a4d6bfSDavid Schultz (ix1) = ew_u.xbits.manh; \ 215*25a4d6bfSDavid Schultz (ix2) = ew_u.xbits.manl; \ 216*25a4d6bfSDavid Schultz } while (0) 217*25a4d6bfSDavid Schultz 218e6239486SDavid Schultz /* Get expsign as a 16 bit int from a long double. */ 219e6239486SDavid Schultz 220e6239486SDavid Schultz #define GET_LDBL_EXPSIGN(i,d) \ 221e6239486SDavid Schultz do { \ 222e6239486SDavid Schultz union IEEEl2bits ge_u; \ 223e6239486SDavid Schultz ge_u.e = (d); \ 224e6239486SDavid Schultz (i) = ge_u.xbits.expsign; \ 225e6239486SDavid Schultz } while (0) 226e6239486SDavid Schultz 227*25a4d6bfSDavid Schultz /* 228*25a4d6bfSDavid Schultz * Set an 80 bit long double from a 16 bit int expsign and a 64 bit int 229*25a4d6bfSDavid Schultz * mantissa. 230*25a4d6bfSDavid Schultz */ 231*25a4d6bfSDavid Schultz 232*25a4d6bfSDavid Schultz #define INSERT_LDBL80_WORDS(d,ix0,ix1) \ 233*25a4d6bfSDavid Schultz do { \ 234*25a4d6bfSDavid Schultz union IEEEl2bits iw_u; \ 235*25a4d6bfSDavid Schultz iw_u.xbits.expsign = (ix0); \ 236*25a4d6bfSDavid Schultz iw_u.xbits.man = (ix1); \ 237*25a4d6bfSDavid Schultz (d) = iw_u.e; \ 238*25a4d6bfSDavid Schultz } while (0) 239*25a4d6bfSDavid Schultz 240*25a4d6bfSDavid Schultz /* 241*25a4d6bfSDavid Schultz * Set a 128 bit long double from a 16 bit int expsign and two 64 bit ints 242*25a4d6bfSDavid Schultz * comprising the mantissa. 243*25a4d6bfSDavid Schultz */ 244*25a4d6bfSDavid Schultz 245*25a4d6bfSDavid Schultz #define INSERT_LDBL128_WORDS(d,ix0,ix1,ix2) \ 246*25a4d6bfSDavid Schultz do { \ 247*25a4d6bfSDavid Schultz union IEEEl2bits iw_u; \ 248*25a4d6bfSDavid Schultz iw_u.xbits.expsign = (ix0); \ 249*25a4d6bfSDavid Schultz iw_u.xbits.manh = (ix1); \ 250*25a4d6bfSDavid Schultz iw_u.xbits.manl = (ix2); \ 251*25a4d6bfSDavid Schultz (d) = iw_u.e; \ 252*25a4d6bfSDavid Schultz } while (0) 253*25a4d6bfSDavid Schultz 254e6239486SDavid Schultz /* Set expsign of a long double from a 16 bit int. */ 255e6239486SDavid Schultz 256e6239486SDavid Schultz #define SET_LDBL_EXPSIGN(d,v) \ 257e6239486SDavid Schultz do { \ 258e6239486SDavid Schultz union IEEEl2bits se_u; \ 259e6239486SDavid Schultz se_u.e = (d); \ 260e6239486SDavid Schultz se_u.xbits.expsign = (v); \ 261e6239486SDavid Schultz (d) = se_u.e; \ 262e6239486SDavid Schultz } while (0) 263e6239486SDavid Schultz 264a077586cSSteve Kargl #ifdef __i386__ 265a077586cSSteve Kargl /* Long double constants are broken on i386. */ 266a077586cSSteve Kargl #define LD80C(m, ex, v) { \ 267b83ccea3SSteve Kargl .xbits.man = __CONCAT(m, ULL), \ 268a077586cSSteve Kargl .xbits.expsign = (0x3fff + (ex)) | ((v) < 0 ? 0x8000 : 0), \ 269b83ccea3SSteve Kargl } 270a077586cSSteve Kargl #else 271a077586cSSteve Kargl /* The above works on non-i386 too, but we use this to check v. */ 272a077586cSSteve Kargl #define LD80C(m, ex, v) { .e = (v), } 273a077586cSSteve Kargl #endif 274b83ccea3SSteve Kargl 2751880ccbdSBruce Evans #ifdef FLT_EVAL_METHOD 2761880ccbdSBruce Evans /* 2771880ccbdSBruce Evans * Attempt to get strict C99 semantics for assignment with non-C99 compilers. 2781880ccbdSBruce Evans */ 2791880ccbdSBruce Evans #if FLT_EVAL_METHOD == 0 || __GNUC__ == 0 2801880ccbdSBruce Evans #define STRICT_ASSIGN(type, lval, rval) ((lval) = (rval)) 2811880ccbdSBruce Evans #else 2821880ccbdSBruce Evans #define STRICT_ASSIGN(type, lval, rval) do { \ 2831880ccbdSBruce Evans volatile type __lval; \ 2841880ccbdSBruce Evans \ 285e6f9129aSSteve Kargl if (sizeof(type) >= sizeof(long double)) \ 2865b62c380SBruce Evans (lval) = (rval); \ 2875b62c380SBruce Evans else { \ 2881880ccbdSBruce Evans __lval = (rval); \ 2891880ccbdSBruce Evans (lval) = __lval; \ 2905b62c380SBruce Evans } \ 2911880ccbdSBruce Evans } while (0) 2921880ccbdSBruce Evans #endif 293b83ccea3SSteve Kargl #endif /* FLT_EVAL_METHOD */ 294b83ccea3SSteve Kargl 295b83ccea3SSteve Kargl /* Support switching the mode to FP_PE if necessary. */ 296b83ccea3SSteve Kargl #if defined(__i386__) && !defined(NO_FPSETPREC) 297b83ccea3SSteve Kargl #define ENTERI() \ 298b83ccea3SSteve Kargl long double __retval; \ 299b83ccea3SSteve Kargl fp_prec_t __oprec; \ 300b83ccea3SSteve Kargl \ 301b83ccea3SSteve Kargl if ((__oprec = fpgetprec()) != FP_PE) \ 302e6f9129aSSteve Kargl fpsetprec(FP_PE) 303b83ccea3SSteve Kargl #define RETURNI(x) do { \ 304b83ccea3SSteve Kargl __retval = (x); \ 305b83ccea3SSteve Kargl if (__oprec != FP_PE) \ 306b83ccea3SSteve Kargl fpsetprec(__oprec); \ 307b83ccea3SSteve Kargl RETURNF(__retval); \ 308b83ccea3SSteve Kargl } while (0) 309b83ccea3SSteve Kargl #else 310b83ccea3SSteve Kargl #define ENTERI(x) 311b83ccea3SSteve Kargl #define RETURNI(x) RETURNF(x) 3121880ccbdSBruce Evans #endif 3131880ccbdSBruce Evans 314b83ccea3SSteve Kargl /* Default return statement if hack*_t() is not used. */ 315b83ccea3SSteve Kargl #define RETURNF(v) return (v) 316b83ccea3SSteve Kargl 3177cd4a832SDavid Schultz /* 318*25a4d6bfSDavid Schultz * 2sum gives the same result as 2sumF without requiring |a| >= |b| or 319*25a4d6bfSDavid Schultz * a == 0, but is slower. 320*25a4d6bfSDavid Schultz */ 321*25a4d6bfSDavid Schultz #define _2sum(a, b) do { \ 322*25a4d6bfSDavid Schultz __typeof(a) __s, __w; \ 323*25a4d6bfSDavid Schultz \ 324*25a4d6bfSDavid Schultz __w = (a) + (b); \ 325*25a4d6bfSDavid Schultz __s = __w - (a); \ 326*25a4d6bfSDavid Schultz (b) = ((a) - (__w - __s)) + ((b) - __s); \ 327*25a4d6bfSDavid Schultz (a) = __w; \ 328*25a4d6bfSDavid Schultz } while (0) 329*25a4d6bfSDavid Schultz 330*25a4d6bfSDavid Schultz /* 331*25a4d6bfSDavid Schultz * 2sumF algorithm. 332*25a4d6bfSDavid Schultz * 333*25a4d6bfSDavid Schultz * "Normalize" the terms in the infinite-precision expression a + b for 334*25a4d6bfSDavid Schultz * the sum of 2 floating point values so that b is as small as possible 335*25a4d6bfSDavid Schultz * relative to 'a'. (The resulting 'a' is the value of the expression in 336*25a4d6bfSDavid Schultz * the same precision as 'a' and the resulting b is the rounding error.) 337*25a4d6bfSDavid Schultz * |a| must be >= |b| or 0, b's type must be no larger than 'a's type, and 338*25a4d6bfSDavid Schultz * exponent overflow or underflow must not occur. This uses a Theorem of 339*25a4d6bfSDavid Schultz * Dekker (1971). See Knuth (1981) 4.2.2 Theorem C. The name "TwoSum" 340*25a4d6bfSDavid Schultz * is apparently due to Skewchuk (1997). 341*25a4d6bfSDavid Schultz * 342*25a4d6bfSDavid Schultz * For this to always work, assignment of a + b to 'a' must not retain any 343*25a4d6bfSDavid Schultz * extra precision in a + b. This is required by C standards but broken 344*25a4d6bfSDavid Schultz * in many compilers. The brokenness cannot be worked around using 345*25a4d6bfSDavid Schultz * STRICT_ASSIGN() like we do elsewhere, since the efficiency of this 346*25a4d6bfSDavid Schultz * algorithm would be destroyed by non-null strict assignments. (The 347*25a4d6bfSDavid Schultz * compilers are correct to be broken -- the efficiency of all floating 348*25a4d6bfSDavid Schultz * point code calculations would be destroyed similarly if they forced the 349*25a4d6bfSDavid Schultz * conversions.) 350*25a4d6bfSDavid Schultz * 351*25a4d6bfSDavid Schultz * Fortunately, a case that works well can usually be arranged by building 352*25a4d6bfSDavid Schultz * any extra precision into the type of 'a' -- 'a' should have type float_t, 353*25a4d6bfSDavid Schultz * double_t or long double. b's type should be no larger than 'a's type. 354*25a4d6bfSDavid Schultz * Callers should use these types with scopes as large as possible, to 355*25a4d6bfSDavid Schultz * reduce their own extra-precision and efficiciency problems. In 356*25a4d6bfSDavid Schultz * particular, they shouldn't convert back and forth just to call here. 357*25a4d6bfSDavid Schultz */ 358*25a4d6bfSDavid Schultz #ifdef DEBUG 359*25a4d6bfSDavid Schultz #define _2sumF(a, b) do { \ 360*25a4d6bfSDavid Schultz __typeof(a) __w; \ 361*25a4d6bfSDavid Schultz volatile __typeof(a) __ia, __ib, __r, __vw; \ 362*25a4d6bfSDavid Schultz \ 363*25a4d6bfSDavid Schultz __ia = (a); \ 364*25a4d6bfSDavid Schultz __ib = (b); \ 365*25a4d6bfSDavid Schultz assert(__ia == 0 || fabsl(__ia) >= fabsl(__ib)); \ 366*25a4d6bfSDavid Schultz \ 367*25a4d6bfSDavid Schultz __w = (a) + (b); \ 368*25a4d6bfSDavid Schultz (b) = ((a) - __w) + (b); \ 369*25a4d6bfSDavid Schultz (a) = __w; \ 370*25a4d6bfSDavid Schultz \ 371*25a4d6bfSDavid Schultz /* The next 2 assertions are weak if (a) is already long double. */ \ 372*25a4d6bfSDavid Schultz assert((long double)__ia + __ib == (long double)(a) + (b)); \ 373*25a4d6bfSDavid Schultz __vw = __ia + __ib; \ 374*25a4d6bfSDavid Schultz __r = __ia - __vw; \ 375*25a4d6bfSDavid Schultz __r += __ib; \ 376*25a4d6bfSDavid Schultz assert(__vw == (a) && __r == (b)); \ 377*25a4d6bfSDavid Schultz } while (0) 378*25a4d6bfSDavid Schultz #else /* !DEBUG */ 379*25a4d6bfSDavid Schultz #define _2sumF(a, b) do { \ 380*25a4d6bfSDavid Schultz __typeof(a) __w; \ 381*25a4d6bfSDavid Schultz \ 382*25a4d6bfSDavid Schultz __w = (a) + (b); \ 383*25a4d6bfSDavid Schultz (b) = ((a) - __w) + (b); \ 384*25a4d6bfSDavid Schultz (a) = __w; \ 385*25a4d6bfSDavid Schultz } while (0) 386*25a4d6bfSDavid Schultz #endif /* DEBUG */ 387*25a4d6bfSDavid Schultz 388*25a4d6bfSDavid Schultz /* 389*25a4d6bfSDavid Schultz * Set x += c, where x is represented in extra precision as a + b. 390*25a4d6bfSDavid Schultz * x must be sufficiently normalized and sufficiently larger than c, 391*25a4d6bfSDavid Schultz * and the result is then sufficiently normalized. 392*25a4d6bfSDavid Schultz * 393*25a4d6bfSDavid Schultz * The details of ordering are that |a| must be >= |c| (so that (a, c) 394*25a4d6bfSDavid Schultz * can be normalized without extra work to swap 'a' with c). The details of 395*25a4d6bfSDavid Schultz * the normalization are that b must be small relative to the normalized 'a'. 396*25a4d6bfSDavid Schultz * Normalization of (a, c) makes the normalized c tiny relative to the 397*25a4d6bfSDavid Schultz * normalized a, so b remains small relative to 'a' in the result. However, 398*25a4d6bfSDavid Schultz * b need not ever be tiny relative to 'a'. For example, b might be about 399*25a4d6bfSDavid Schultz * 2**20 times smaller than 'a' to give about 20 extra bits of precision. 400*25a4d6bfSDavid Schultz * That is usually enough, and adding c (which by normalization is about 401*25a4d6bfSDavid Schultz * 2**53 times smaller than a) cannot change b significantly. However, 402*25a4d6bfSDavid Schultz * cancellation of 'a' with c in normalization of (a, c) may reduce 'a' 403*25a4d6bfSDavid Schultz * significantly relative to b. The caller must ensure that significant 404*25a4d6bfSDavid Schultz * cancellation doesn't occur, either by having c of the same sign as 'a', 405*25a4d6bfSDavid Schultz * or by having |c| a few percent smaller than |a|. Pre-normalization of 406*25a4d6bfSDavid Schultz * (a, b) may help. 407*25a4d6bfSDavid Schultz * 408*25a4d6bfSDavid Schultz * This is is a variant of an algorithm of Kahan (see Knuth (1981) 4.2.2 409*25a4d6bfSDavid Schultz * exercise 19). We gain considerable efficiency by requiring the terms to 410*25a4d6bfSDavid Schultz * be sufficiently normalized and sufficiently increasing. 411*25a4d6bfSDavid Schultz */ 412*25a4d6bfSDavid Schultz #define _3sumF(a, b, c) do { \ 413*25a4d6bfSDavid Schultz __typeof(a) __tmp; \ 414*25a4d6bfSDavid Schultz \ 415*25a4d6bfSDavid Schultz __tmp = (c); \ 416*25a4d6bfSDavid Schultz _2sumF(__tmp, (a)); \ 417*25a4d6bfSDavid Schultz (b) += (a); \ 418*25a4d6bfSDavid Schultz (a) = __tmp; \ 419*25a4d6bfSDavid Schultz } while (0) 420*25a4d6bfSDavid Schultz 421*25a4d6bfSDavid Schultz /* 4227cd4a832SDavid Schultz * Common routine to process the arguments to nan(), nanf(), and nanl(). 4237cd4a832SDavid Schultz */ 4247cd4a832SDavid Schultz void _scan_nan(uint32_t *__words, int __num_words, const char *__s); 4257cd4a832SDavid Schultz 42619b114daSBruce Evans #ifdef _COMPLEX_H 42724863729SDavid Schultz 42824863729SDavid Schultz /* 42924863729SDavid Schultz * C99 specifies that complex numbers have the same representation as 43024863729SDavid Schultz * an array of two elements, where the first element is the real part 43124863729SDavid Schultz * and the second element is the imaginary part. 43224863729SDavid Schultz */ 43324863729SDavid Schultz typedef union { 43424863729SDavid Schultz float complex f; 43524863729SDavid Schultz float a[2]; 43624863729SDavid Schultz } float_complex; 43724863729SDavid Schultz typedef union { 43824863729SDavid Schultz double complex f; 43924863729SDavid Schultz double a[2]; 44024863729SDavid Schultz } double_complex; 44124863729SDavid Schultz typedef union { 44224863729SDavid Schultz long double complex f; 44324863729SDavid Schultz long double a[2]; 44424863729SDavid Schultz } long_double_complex; 44524863729SDavid Schultz #define REALPART(z) ((z).a[0]) 44624863729SDavid Schultz #define IMAGPART(z) ((z).a[1]) 44724863729SDavid Schultz 44819b114daSBruce Evans /* 44919b114daSBruce Evans * Inline functions that can be used to construct complex values. 45019b114daSBruce Evans * 45119b114daSBruce Evans * The C99 standard intends x+I*y to be used for this, but x+I*y is 45219b114daSBruce Evans * currently unusable in general since gcc introduces many overflow, 45319b114daSBruce Evans * underflow, sign and efficiency bugs by rewriting I*y as 45419b114daSBruce Evans * (0.0+I)*(y+0.0*I) and laboriously computing the full complex product. 45519b114daSBruce Evans * In particular, I*Inf is corrupted to NaN+I*Inf, and I*-0 is corrupted 45619b114daSBruce Evans * to -0.0+I*0.0. 45719b114daSBruce Evans */ 45819b114daSBruce Evans static __inline float complex 45919b114daSBruce Evans cpackf(float x, float y) 46019b114daSBruce Evans { 46124863729SDavid Schultz float_complex z; 46219b114daSBruce Evans 46324863729SDavid Schultz REALPART(z) = x; 46424863729SDavid Schultz IMAGPART(z) = y; 46524863729SDavid Schultz return (z.f); 46619b114daSBruce Evans } 46719b114daSBruce Evans 46819b114daSBruce Evans static __inline double complex 46919b114daSBruce Evans cpack(double x, double y) 47019b114daSBruce Evans { 47124863729SDavid Schultz double_complex z; 47219b114daSBruce Evans 47324863729SDavid Schultz REALPART(z) = x; 47424863729SDavid Schultz IMAGPART(z) = y; 47524863729SDavid Schultz return (z.f); 47619b114daSBruce Evans } 47719b114daSBruce Evans 47819b114daSBruce Evans static __inline long double complex 47919b114daSBruce Evans cpackl(long double x, long double y) 48019b114daSBruce Evans { 48124863729SDavid Schultz long_double_complex z; 48219b114daSBruce Evans 48324863729SDavid Schultz REALPART(z) = x; 48424863729SDavid Schultz IMAGPART(z) = y; 48524863729SDavid Schultz return (z.f); 48619b114daSBruce Evans } 48719b114daSBruce Evans #endif /* _COMPLEX_H */ 48819b114daSBruce Evans 4890ddfa46bSBruce Evans #ifdef __GNUCLIKE_ASM 4900ddfa46bSBruce Evans 4910ddfa46bSBruce Evans /* Asm versions of some functions. */ 4920ddfa46bSBruce Evans 4930ddfa46bSBruce Evans #ifdef __amd64__ 4940ddfa46bSBruce Evans static __inline int 4950ddfa46bSBruce Evans irint(double x) 4960ddfa46bSBruce Evans { 4970ddfa46bSBruce Evans int n; 4980ddfa46bSBruce Evans 499a4f326ddSEd Schouten asm("cvtsd2si %1,%0" : "=r" (n) : "x" (x)); 5000ddfa46bSBruce Evans return (n); 5010ddfa46bSBruce Evans } 5020ddfa46bSBruce Evans #define HAVE_EFFICIENT_IRINT 5030ddfa46bSBruce Evans #endif 5040ddfa46bSBruce Evans 5050ddfa46bSBruce Evans #ifdef __i386__ 5060ddfa46bSBruce Evans static __inline int 5070ddfa46bSBruce Evans irint(double x) 5080ddfa46bSBruce Evans { 5090ddfa46bSBruce Evans int n; 5100ddfa46bSBruce Evans 5110ddfa46bSBruce Evans asm("fistl %0" : "=m" (n) : "t" (x)); 5120ddfa46bSBruce Evans return (n); 5130ddfa46bSBruce Evans } 5140ddfa46bSBruce Evans #define HAVE_EFFICIENT_IRINT 5150ddfa46bSBruce Evans #endif 5160ddfa46bSBruce Evans 517b83ccea3SSteve Kargl #if defined(__amd64__) || defined(__i386__) 518b83ccea3SSteve Kargl static __inline int 519b83ccea3SSteve Kargl irintl(long double x) 520b83ccea3SSteve Kargl { 521b83ccea3SSteve Kargl int n; 522b83ccea3SSteve Kargl 523b83ccea3SSteve Kargl asm("fistl %0" : "=m" (n) : "t" (x)); 524b83ccea3SSteve Kargl return (n); 525b83ccea3SSteve Kargl } 526b83ccea3SSteve Kargl #define HAVE_EFFICIENT_IRINTL 527b83ccea3SSteve Kargl #endif 528b83ccea3SSteve Kargl 5290ddfa46bSBruce Evans #endif /* __GNUCLIKE_ASM */ 5300ddfa46bSBruce Evans 531*25a4d6bfSDavid Schultz #ifdef DEBUG 532*25a4d6bfSDavid Schultz #if defined(__amd64__) || defined(__i386__) 533*25a4d6bfSDavid Schultz #define breakpoint() asm("int $3") 534*25a4d6bfSDavid Schultz #else 535*25a4d6bfSDavid Schultz #include <signal.h> 536*25a4d6bfSDavid Schultz 537*25a4d6bfSDavid Schultz #define breakpoint() raise(SIGTRAP) 538*25a4d6bfSDavid Schultz #endif 539*25a4d6bfSDavid Schultz #endif 540*25a4d6bfSDavid Schultz 541*25a4d6bfSDavid Schultz /* Write a pari script to test things externally. */ 542*25a4d6bfSDavid Schultz #ifdef DOPRINT 543*25a4d6bfSDavid Schultz #include <stdio.h> 544*25a4d6bfSDavid Schultz 545*25a4d6bfSDavid Schultz #ifndef DOPRINT_SWIZZLE 546*25a4d6bfSDavid Schultz #define DOPRINT_SWIZZLE 0 547*25a4d6bfSDavid Schultz #endif 548*25a4d6bfSDavid Schultz 549*25a4d6bfSDavid Schultz #ifdef DOPRINT_LD80 550*25a4d6bfSDavid Schultz 551*25a4d6bfSDavid Schultz #define DOPRINT_START(xp) do { \ 552*25a4d6bfSDavid Schultz uint64_t __lx; \ 553*25a4d6bfSDavid Schultz uint16_t __hx; \ 554*25a4d6bfSDavid Schultz \ 555*25a4d6bfSDavid Schultz /* Hack to give more-problematic args. */ \ 556*25a4d6bfSDavid Schultz EXTRACT_LDBL80_WORDS(__hx, __lx, *xp); \ 557*25a4d6bfSDavid Schultz __lx ^= DOPRINT_SWIZZLE; \ 558*25a4d6bfSDavid Schultz INSERT_LDBL80_WORDS(*xp, __hx, __lx); \ 559*25a4d6bfSDavid Schultz printf("x = %.21Lg; ", (long double)*xp); \ 560*25a4d6bfSDavid Schultz } while (0) 561*25a4d6bfSDavid Schultz #define DOPRINT_END1(v) \ 562*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = 0; show(x, y, z);\n", (long double)(v)) 563*25a4d6bfSDavid Schultz #define DOPRINT_END2(hi, lo) \ 564*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = %.21Lg; show(x, y, z);\n", \ 565*25a4d6bfSDavid Schultz (long double)(hi), (long double)(lo)) 566*25a4d6bfSDavid Schultz 567*25a4d6bfSDavid Schultz #elif defined(DOPRINT_D64) 568*25a4d6bfSDavid Schultz 569*25a4d6bfSDavid Schultz #define DOPRINT_START(xp) do { \ 570*25a4d6bfSDavid Schultz uint32_t __hx, __lx; \ 571*25a4d6bfSDavid Schultz \ 572*25a4d6bfSDavid Schultz EXTRACT_WORDS(__hx, __lx, *xp); \ 573*25a4d6bfSDavid Schultz __lx ^= DOPRINT_SWIZZLE; \ 574*25a4d6bfSDavid Schultz INSERT_WORDS(*xp, __hx, __lx); \ 575*25a4d6bfSDavid Schultz printf("x = %.21Lg; ", (long double)*xp); \ 576*25a4d6bfSDavid Schultz } while (0) 577*25a4d6bfSDavid Schultz #define DOPRINT_END1(v) \ 578*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = 0; show(x, y, z);\n", (long double)(v)) 579*25a4d6bfSDavid Schultz #define DOPRINT_END2(hi, lo) \ 580*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = %.21Lg; show(x, y, z);\n", \ 581*25a4d6bfSDavid Schultz (long double)(hi), (long double)(lo)) 582*25a4d6bfSDavid Schultz 583*25a4d6bfSDavid Schultz #elif defined(DOPRINT_F32) 584*25a4d6bfSDavid Schultz 585*25a4d6bfSDavid Schultz #define DOPRINT_START(xp) do { \ 586*25a4d6bfSDavid Schultz uint32_t __hx; \ 587*25a4d6bfSDavid Schultz \ 588*25a4d6bfSDavid Schultz GET_FLOAT_WORD(__hx, *xp); \ 589*25a4d6bfSDavid Schultz __hx ^= DOPRINT_SWIZZLE; \ 590*25a4d6bfSDavid Schultz SET_FLOAT_WORD(*xp, __hx); \ 591*25a4d6bfSDavid Schultz printf("x = %.21Lg; ", (long double)*xp); \ 592*25a4d6bfSDavid Schultz } while (0) 593*25a4d6bfSDavid Schultz #define DOPRINT_END1(v) \ 594*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = 0; show(x, y, z);\n", (long double)(v)) 595*25a4d6bfSDavid Schultz #define DOPRINT_END2(hi, lo) \ 596*25a4d6bfSDavid Schultz printf("y = %.21Lg; z = %.21Lg; show(x, y, z);\n", \ 597*25a4d6bfSDavid Schultz (long double)(hi), (long double)(lo)) 598*25a4d6bfSDavid Schultz 599*25a4d6bfSDavid Schultz #else /* !DOPRINT_LD80 && !DOPRINT_D64 (LD128 only) */ 600*25a4d6bfSDavid Schultz 601*25a4d6bfSDavid Schultz #ifndef DOPRINT_SWIZZLE_HIGH 602*25a4d6bfSDavid Schultz #define DOPRINT_SWIZZLE_HIGH 0 603*25a4d6bfSDavid Schultz #endif 604*25a4d6bfSDavid Schultz 605*25a4d6bfSDavid Schultz #define DOPRINT_START(xp) do { \ 606*25a4d6bfSDavid Schultz uint64_t __lx, __llx; \ 607*25a4d6bfSDavid Schultz uint16_t __hx; \ 608*25a4d6bfSDavid Schultz \ 609*25a4d6bfSDavid Schultz EXTRACT_LDBL128_WORDS(__hx, __lx, __llx, *xp); \ 610*25a4d6bfSDavid Schultz __llx ^= DOPRINT_SWIZZLE; \ 611*25a4d6bfSDavid Schultz __lx ^= DOPRINT_SWIZZLE_HIGH; \ 612*25a4d6bfSDavid Schultz INSERT_LDBL128_WORDS(*xp, __hx, __lx, __llx); \ 613*25a4d6bfSDavid Schultz printf("x = %.36Lg; ", (long double)*xp); \ 614*25a4d6bfSDavid Schultz } while (0) 615*25a4d6bfSDavid Schultz #define DOPRINT_END1(v) \ 616*25a4d6bfSDavid Schultz printf("y = %.36Lg; z = 0; show(x, y, z);\n", (long double)(v)) 617*25a4d6bfSDavid Schultz #define DOPRINT_END2(hi, lo) \ 618*25a4d6bfSDavid Schultz printf("y = %.36Lg; z = %.36Lg; show(x, y, z);\n", \ 619*25a4d6bfSDavid Schultz (long double)(hi), (long double)(lo)) 620*25a4d6bfSDavid Schultz 621*25a4d6bfSDavid Schultz #endif /* DOPRINT_LD80 */ 622*25a4d6bfSDavid Schultz 623*25a4d6bfSDavid Schultz #else /* !DOPRINT */ 624*25a4d6bfSDavid Schultz #define DOPRINT_START(xp) 625*25a4d6bfSDavid Schultz #define DOPRINT_END1(v) 626*25a4d6bfSDavid Schultz #define DOPRINT_END2(hi, lo) 627*25a4d6bfSDavid Schultz #endif /* DOPRINT */ 628*25a4d6bfSDavid Schultz 629*25a4d6bfSDavid Schultz #define RETURNP(x) do { \ 630*25a4d6bfSDavid Schultz DOPRINT_END1(x); \ 631*25a4d6bfSDavid Schultz RETURNF(x); \ 632*25a4d6bfSDavid Schultz } while (0) 633*25a4d6bfSDavid Schultz #define RETURNPI(x) do { \ 634*25a4d6bfSDavid Schultz DOPRINT_END1(x); \ 635*25a4d6bfSDavid Schultz RETURNI(x); \ 636*25a4d6bfSDavid Schultz } while (0) 637*25a4d6bfSDavid Schultz #define RETURN2P(x, y) do { \ 638*25a4d6bfSDavid Schultz DOPRINT_END2((x), (y)); \ 639*25a4d6bfSDavid Schultz RETURNF((x) + (y)); \ 640*25a4d6bfSDavid Schultz } while (0) 641*25a4d6bfSDavid Schultz #define RETURN2PI(x, y) do { \ 642*25a4d6bfSDavid Schultz DOPRINT_END2((x), (y)); \ 643*25a4d6bfSDavid Schultz RETURNI((x) + (y)); \ 644*25a4d6bfSDavid Schultz } while (0) 645*25a4d6bfSDavid Schultz #ifdef STRUCT_RETURN 646*25a4d6bfSDavid Schultz #define RETURNSP(rp) do { \ 647*25a4d6bfSDavid Schultz if (!(rp)->lo_set) \ 648*25a4d6bfSDavid Schultz RETURNP((rp)->hi); \ 649*25a4d6bfSDavid Schultz RETURN2P((rp)->hi, (rp)->lo); \ 650*25a4d6bfSDavid Schultz } while (0) 651*25a4d6bfSDavid Schultz #define RETURNSPI(rp) do { \ 652*25a4d6bfSDavid Schultz if (!(rp)->lo_set) \ 653*25a4d6bfSDavid Schultz RETURNPI((rp)->hi); \ 654*25a4d6bfSDavid Schultz RETURN2PI((rp)->hi, (rp)->lo); \ 655*25a4d6bfSDavid Schultz } while (0) 656*25a4d6bfSDavid Schultz #endif 657*25a4d6bfSDavid Schultz #define SUM2P(x, y) ({ \ 658*25a4d6bfSDavid Schultz const __typeof (x) __x = (x); \ 659*25a4d6bfSDavid Schultz const __typeof (y) __y = (y); \ 660*25a4d6bfSDavid Schultz \ 661*25a4d6bfSDavid Schultz DOPRINT_END2(__x, __y); \ 662*25a4d6bfSDavid Schultz __x + __y; \ 663*25a4d6bfSDavid Schultz }) 664*25a4d6bfSDavid Schultz 665e1b61b5bSDavid Schultz /* 666e1b61b5bSDavid Schultz * ieee style elementary functions 667e1b61b5bSDavid Schultz * 668e1b61b5bSDavid Schultz * We rename functions here to improve other sources' diffability 669e1b61b5bSDavid Schultz * against fdlibm. 670e1b61b5bSDavid Schultz */ 671e1b61b5bSDavid Schultz #define __ieee754_sqrt sqrt 672e1b61b5bSDavid Schultz #define __ieee754_acos acos 673e1b61b5bSDavid Schultz #define __ieee754_acosh acosh 674e1b61b5bSDavid Schultz #define __ieee754_log log 675177668d1SDavid Schultz #define __ieee754_log2 log2 676e1b61b5bSDavid Schultz #define __ieee754_atanh atanh 677e1b61b5bSDavid Schultz #define __ieee754_asin asin 678e1b61b5bSDavid Schultz #define __ieee754_atan2 atan2 679e1b61b5bSDavid Schultz #define __ieee754_exp exp 680e1b61b5bSDavid Schultz #define __ieee754_cosh cosh 681e1b61b5bSDavid Schultz #define __ieee754_fmod fmod 682e1b61b5bSDavid Schultz #define __ieee754_pow pow 683e1b61b5bSDavid Schultz #define __ieee754_lgamma lgamma 684e1b61b5bSDavid Schultz #define __ieee754_gamma gamma 685e1b61b5bSDavid Schultz #define __ieee754_lgamma_r lgamma_r 686e1b61b5bSDavid Schultz #define __ieee754_gamma_r gamma_r 687e1b61b5bSDavid Schultz #define __ieee754_log10 log10 688e1b61b5bSDavid Schultz #define __ieee754_sinh sinh 689e1b61b5bSDavid Schultz #define __ieee754_hypot hypot 690e1b61b5bSDavid Schultz #define __ieee754_j0 j0 691e1b61b5bSDavid Schultz #define __ieee754_j1 j1 692e1b61b5bSDavid Schultz #define __ieee754_y0 y0 693e1b61b5bSDavid Schultz #define __ieee754_y1 y1 694e1b61b5bSDavid Schultz #define __ieee754_jn jn 695e1b61b5bSDavid Schultz #define __ieee754_yn yn 696e1b61b5bSDavid Schultz #define __ieee754_remainder remainder 697e1b61b5bSDavid Schultz #define __ieee754_scalb scalb 698e1b61b5bSDavid Schultz #define __ieee754_sqrtf sqrtf 699e1b61b5bSDavid Schultz #define __ieee754_acosf acosf 700e1b61b5bSDavid Schultz #define __ieee754_acoshf acoshf 701e1b61b5bSDavid Schultz #define __ieee754_logf logf 702e1b61b5bSDavid Schultz #define __ieee754_atanhf atanhf 703e1b61b5bSDavid Schultz #define __ieee754_asinf asinf 704e1b61b5bSDavid Schultz #define __ieee754_atan2f atan2f 705e1b61b5bSDavid Schultz #define __ieee754_expf expf 706e1b61b5bSDavid Schultz #define __ieee754_coshf coshf 707e1b61b5bSDavid Schultz #define __ieee754_fmodf fmodf 708e1b61b5bSDavid Schultz #define __ieee754_powf powf 709e1b61b5bSDavid Schultz #define __ieee754_lgammaf lgammaf 710e1b61b5bSDavid Schultz #define __ieee754_gammaf gammaf 711e1b61b5bSDavid Schultz #define __ieee754_lgammaf_r lgammaf_r 712e1b61b5bSDavid Schultz #define __ieee754_gammaf_r gammaf_r 713e1b61b5bSDavid Schultz #define __ieee754_log10f log10f 714177668d1SDavid Schultz #define __ieee754_log2f log2f 715e1b61b5bSDavid Schultz #define __ieee754_sinhf sinhf 716e1b61b5bSDavid Schultz #define __ieee754_hypotf hypotf 717e1b61b5bSDavid Schultz #define __ieee754_j0f j0f 718e1b61b5bSDavid Schultz #define __ieee754_j1f j1f 719e1b61b5bSDavid Schultz #define __ieee754_y0f y0f 720e1b61b5bSDavid Schultz #define __ieee754_y1f y1f 721e1b61b5bSDavid Schultz #define __ieee754_jnf jnf 722e1b61b5bSDavid Schultz #define __ieee754_ynf ynf 723e1b61b5bSDavid Schultz #define __ieee754_remainderf remainderf 724e1b61b5bSDavid Schultz #define __ieee754_scalbf scalbf 7253a8617a8SJordan K. Hubbard 7263a8617a8SJordan K. Hubbard /* fdlibm kernel function */ 727079299f7SDavid Schultz int __kernel_rem_pio2(double*,double*,int,int,int); 728079299f7SDavid Schultz 729079299f7SDavid Schultz /* double precision kernel functions */ 7302b795b29SDimitry Andric #ifndef INLINE_REM_PIO2 731e02846ceSDavid Schultz int __ieee754_rem_pio2(double,double*); 7322b795b29SDimitry Andric #endif 73369160b1eSDavid E. O'Brien double __kernel_sin(double,double,int); 73469160b1eSDavid E. O'Brien double __kernel_cos(double,double); 73569160b1eSDavid E. O'Brien double __kernel_tan(double,double,int); 73612188b77SDavid Schultz double __ldexp_exp(double,int); 73712188b77SDavid Schultz #ifdef _COMPLEX_H 73812188b77SDavid Schultz double complex __ldexp_cexp(double complex,int); 73912188b77SDavid Schultz #endif 7403a8617a8SJordan K. Hubbard 741079299f7SDavid Schultz /* float precision kernel functions */ 7422b795b29SDimitry Andric #ifndef INLINE_REM_PIO2F 74370d818a2SBruce Evans int __ieee754_rem_pio2f(float,double*); 744b492f289SEd Schouten #endif 7452b795b29SDimitry Andric #ifndef INLINE_KERNEL_SINDF 74659aad933SBruce Evans float __kernel_sindf(double); 747b492f289SEd Schouten #endif 7482b795b29SDimitry Andric #ifndef INLINE_KERNEL_COSDF 74959aad933SBruce Evans float __kernel_cosdf(double); 750b492f289SEd Schouten #endif 7512b795b29SDimitry Andric #ifndef INLINE_KERNEL_TANDF 75294a5f9beSBruce Evans float __kernel_tandf(double,int); 7532b795b29SDimitry Andric #endif 75412188b77SDavid Schultz float __ldexp_expf(float,int); 75512188b77SDavid Schultz #ifdef _COMPLEX_H 75612188b77SDavid Schultz float complex __ldexp_cexpf(float complex,int); 75712188b77SDavid Schultz #endif 758079299f7SDavid Schultz 759079299f7SDavid Schultz /* long double precision kernel functions */ 760079299f7SDavid Schultz long double __kernel_sinl(long double, long double, int); 761079299f7SDavid Schultz long double __kernel_cosl(long double, long double); 762079299f7SDavid Schultz long double __kernel_tanl(long double, long double, int); 7633a8617a8SJordan K. Hubbard 764ef1ee63eSAlexey Zelkin #endif /* !_MATH_PRIVATE_H_ */ 765