]>
Commit | Line | Data |
---|---|---|
a334319f UD |
1 | // |
2 | // Copyright (C) 2000, 2001, Intel Corporation | |
8da2915d UD |
3 | // All rights reserved. |
4 | // | |
a334319f UD |
5 | // Contributed 2/2/2000 by John Harrison, Ted Kubaska, Bob Norin, Shane Story, |
6 | // and Ping Tak Peter Tang of the Computational Software Lab, Intel Corporation. | |
8da2915d | 7 | // |
aeb25823 AJ |
8 | // Redistribution and use in source and binary forms, with or without |
9 | // modification, are permitted provided that the following conditions are | |
10 | // met: | |
11 | // | |
12 | // * Redistributions of source code must retain the above copyright | |
13 | // notice, this list of conditions and the following disclaimer. | |
14 | // | |
15 | // * Redistributions in binary form must reproduce the above copyright | |
16 | // notice, this list of conditions and the following disclaimer in the | |
17 | // documentation and/or other materials provided with the distribution. | |
18 | // | |
19 | // * The name of Intel Corporation may not be used to endorse or promote | |
20 | // products derived from this software without specific prior written | |
21 | // permission. | |
8da2915d UD |
22 | // |
23 | // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | |
24 | // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | |
25 | // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | |
26 | // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR ITS | |
27 | // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, | |
28 | // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | |
29 | // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR | |
30 | // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY | |
31 | // OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY OR TORT (INCLUDING | |
32 | // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | |
33 | // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
34 | // | |
35 | // Intel Corporation is the author of this code, and requests that all | |
36 | // problem reports or change requests be submitted to it directly at | |
a334319f | 37 | // http://developer.intel.com/opensource. |
8da2915d UD |
38 | // |
39 | ||
40 | // History: 02/02/2000 Initial version | |
41 | // 2/28/2000 added tags for logb and nextafter | |
a334319f | 42 | // 3/22/2000 Changes to support _LIB_VERSION variable |
8da2915d UD |
43 | // and filled some enum gaps. Added support for C99. |
44 | // 5/31/2000 added prototypes for __libm_frexp_4l/8l | |
a334319f | 45 | // 8/10/2000 Changed declaration of _LIB_VERSION to work for library |
8da2915d UD |
46 | // builds and other application builds (precompiler directives). |
47 | // 8/11/2000 Added pointers-to-matherr-functions declarations to allow | |
48 | // for user-defined matherr functions in the dll build. | |
49 | // 12/07/2000 Added scalbn error_types values. | |
50 | // | |
51 | ||
a334319f UD |
52 | #ifndef __ASSEMBLER__ |
53 | #include <math.h> | |
54 | ||
55 | float __libm_frexp_4f( float x, int* exp); | |
56 | float _GI___libm_frexp_4f( float x, int* exp); | |
57 | float __libm_frexp_8f( float x, int* exp); | |
58 | double __libm_frexp_4( double x, int* exp); | |
59 | double _GI___libm_frexp_4( double x, int* exp); | |
60 | double __libm_frexp_8( double x, int* exp); | |
61 | long double __libm_frexp_4l( long double x, int* exp); | |
62 | long double _GI___libm_frexp_4l( long double x, int* exp); | |
63 | long double __libm_frexp_8l( long double x, int* exp); | |
64 | void __libm_sincos_pi4(double,double*,double*,int); | |
65 | void __libm_y0y1(double , double *, double *); | |
66 | void __libm_j0j1(double , double *, double *); | |
67 | double __libm_lgamma_kernel(double,int*,int,int); | |
68 | double __libm_j0(double); | |
69 | double __libm_j1(double); | |
70 | double __libm_jn(int,double); | |
71 | double __libm_y0(double); | |
72 | double __libm_y1(double); | |
73 | double __libm_yn(int,double); | |
74 | ||
75 | extern double rint(double); | |
76 | extern double sqrt(double); | |
77 | extern double fabs(double); | |
78 | extern double log(double); | |
79 | extern double log1p(double); | |
80 | extern double sqrt(double); | |
81 | extern double sin(double); | |
82 | extern double exp(double); | |
83 | extern double modf(double, double *); | |
84 | extern double asinh(double); | |
85 | extern double acosh(double); | |
86 | extern double atanh(double); | |
87 | extern double tanh(double); | |
88 | extern double erf(double); | |
89 | extern double erfc(double); | |
90 | extern double j0(double); | |
91 | extern double j1(double); | |
92 | extern double jn(int, double); | |
93 | extern double y0(double); | |
94 | extern double y1(double); | |
95 | extern double yn(int, double); | |
96 | ||
97 | extern float fabsf(float); | |
98 | extern float asinhf(float); | |
99 | extern float acoshf(float); | |
100 | extern float atanhf(float); | |
101 | extern float tanhf(float); | |
102 | extern float erff(float); | |
103 | extern float erfcf(float); | |
104 | extern float j0f(float); | |
105 | extern float j1f(float); | |
106 | extern float jnf(int, float); | |
107 | extern float y0f(float); | |
108 | extern float y1f(float); | |
109 | extern float ynf(int, float); | |
110 | ||
111 | extern long double log1pl(long double); | |
112 | extern long double logl(long double); | |
113 | extern long double sqrtl(long double); | |
114 | extern long double expl(long double); | |
115 | ||
116 | extern long lround(double); | |
117 | extern long lroundf(float); | |
118 | extern long lroundl(long double); | |
8da2915d | 119 | |
a334319f UD |
120 | #if !(defined(SIZE_INT_32) || defined(SIZE_INT_64)) |
121 | #error integer size not established; define SIZE_INT_32 or SIZE_INT_64 | |
8da2915d UD |
122 | #endif |
123 | ||
a334319f UD |
124 | struct fp64 { /*/ sign:1 exponent:11 significand:52 (implied leading 1)*/ |
125 | unsigned lo_significand:32; | |
126 | unsigned hi_significand:20; | |
127 | unsigned exponent:11; | |
128 | unsigned sign:1; | |
129 | }; | |
8da2915d | 130 | |
a334319f UD |
131 | #define HI_SIGNIFICAND_LESS(X, HI) ((X)->hi_significand < 0x ## HI) |
132 | #define f64abs(x) ((x) < 0.0 ? -(x) : (x)) | |
8da2915d | 133 | |
a334319f UD |
134 | typedef enum |
135 | { | |
136 | logl_zero=0, logl_negative, /* 0, 1 */ | |
137 | log_zero, log_negative, /* 2, 3 */ | |
138 | logf_zero, logf_negative, /* 4, 5 */ | |
139 | log10l_zero, log10l_negative, /* 6, 7 */ | |
140 | log10_zero, log10_negative, /* 8, 9 */ | |
141 | log10f_zero, log10f_negative, /* 10, 11 */ | |
142 | expl_overflow, expl_underflow, /* 12, 13 */ | |
143 | exp_overflow, exp_underflow, /* 14, 15 */ | |
144 | expf_overflow, expf_underflow, /* 16, 17 */ | |
145 | powl_overflow, powl_underflow, /* 18, 19 */ | |
146 | powl_zero_to_zero, /* 20 */ | |
147 | powl_zero_to_negative, /* 21 */ | |
148 | powl_neg_to_non_integer, /* 22 */ | |
149 | powl_nan_to_zero, /* 23 */ | |
150 | pow_overflow, pow_underflow, /* 24, 25 */ | |
151 | pow_zero_to_zero, /* 26 */ | |
152 | pow_zero_to_negative, /* 27 */ | |
153 | pow_neg_to_non_integer, /* 28 */ | |
154 | pow_nan_to_zero, /* 29 */ | |
155 | powf_overflow, powf_underflow, /* 30, 31 */ | |
156 | powf_zero_to_zero, /* 32 */ | |
157 | powf_zero_to_negative, /* 33 */ | |
158 | powf_neg_to_non_integer, /* 34 */ | |
159 | powf_nan_to_zero, /* 35 */ | |
160 | atan2l_zero, /* 36 */ | |
161 | atan2_zero, /* 37 */ | |
162 | atan2f_zero, /* 38 */ | |
163 | expm1l_overflow, /* 39 */ | |
164 | expm1l_underflow, /* 40 */ | |
165 | expm1_overflow, /* 41 */ | |
166 | expm1_underflow, /* 42 */ | |
167 | expm1f_overflow, /* 43 */ | |
168 | expm1f_underflow, /* 44 */ | |
169 | hypotl_overflow, /* 45 */ | |
170 | hypot_overflow, /* 46 */ | |
171 | hypotf_overflow, /* 47 */ | |
172 | sqrtl_negative, /* 48 */ | |
173 | sqrt_negative, /* 49 */ | |
174 | sqrtf_negative, /* 50 */ | |
175 | scalbl_overflow, scalbl_underflow, /* 51, 52 */ | |
176 | scalb_overflow, scalb_underflow, /* 53, 54 */ | |
177 | scalbf_overflow, scalbf_underflow, /* 55, 56 */ | |
178 | acosl_gt_one, acos_gt_one, acosf_gt_one, /* 57, 58, 59 */ | |
179 | asinl_gt_one, asin_gt_one, asinf_gt_one, /* 60, 61, 62 */ | |
180 | coshl_overflow, cosh_overflow, coshf_overflow, /* 63, 64, 65 */ | |
181 | y0l_zero, y0l_negative,y0l_gt_loss, /* 66, 67, 68 */ | |
182 | y0_zero, y0_negative,y0_gt_loss, /* 69, 70, 71 */ | |
183 | y0f_zero, y0f_negative,y0f_gt_loss, /* 72, 73, 74 */ | |
184 | y1l_zero, y1l_negative,y1l_gt_loss, /* 75, 76, 77 */ | |
185 | y1_zero, y1_negative,y1_gt_loss, /* 78, 79, 80 */ | |
186 | y1f_zero, y1f_negative,y1f_gt_loss, /* 81, 82, 83 */ | |
187 | ynl_zero, ynl_negative,ynl_gt_loss, /* 84, 85, 86 */ | |
188 | yn_zero, yn_negative,yn_gt_loss, /* 87, 88, 89 */ | |
189 | ynf_zero, ynf_negative,ynf_gt_loss, /* 90, 91, 92 */ | |
190 | j0l_gt_loss, /* 93 */ | |
191 | j0_gt_loss, /* 94 */ | |
192 | j0f_gt_loss, /* 95 */ | |
193 | j1l_gt_loss, /* 96 */ | |
194 | j1_gt_loss, /* 97 */ | |
195 | j1f_gt_loss, /* 98 */ | |
196 | jnl_gt_loss, /* 99 */ | |
197 | jn_gt_loss, /* 100 */ | |
198 | jnf_gt_loss, /* 101 */ | |
199 | lgammal_overflow, lgammal_negative,lgammal_reserve, /* 102, 103, 104 */ | |
200 | lgamma_overflow, lgamma_negative,lgamma_reserve, /* 105, 106, 107 */ | |
201 | lgammaf_overflow, lgammaf_negative, lgammaf_reserve,/* 108, 109, 110 */ | |
202 | gammal_overflow,gammal_negative, gammal_reserve, /* 111, 112, 113 */ | |
203 | gamma_overflow, gamma_negative, gamma_reserve, /* 114, 115, 116 */ | |
204 | gammaf_overflow,gammaf_negative,gammaf_reserve, /* 117, 118, 119 */ | |
205 | fmodl_by_zero, /* 120 */ | |
206 | fmod_by_zero, /* 121 */ | |
207 | fmodf_by_zero, /* 122 */ | |
208 | remainderl_by_zero, /* 123 */ | |
209 | remainder_by_zero, /* 124 */ | |
210 | remainderf_by_zero, /* 125 */ | |
211 | sinhl_overflow, sinh_overflow, sinhf_overflow, /* 126, 127, 128 */ | |
212 | atanhl_gt_one, atanhl_eq_one, /* 129, 130 */ | |
213 | atanh_gt_one, atanh_eq_one, /* 131, 132 */ | |
214 | atanhf_gt_one, atanhf_eq_one, /* 133, 134 */ | |
215 | acoshl_lt_one, /* 135 */ | |
216 | acosh_lt_one, /* 136 */ | |
217 | acoshf_lt_one, /* 137 */ | |
218 | log1pl_zero, log1pl_negative, /* 138, 139 */ | |
219 | log1p_zero, log1p_negative, /* 140, 141 */ | |
220 | log1pf_zero, log1pf_negative, /* 142, 143 */ | |
221 | ldexpl_overflow, ldexpl_underflow, /* 144, 145 */ | |
222 | ldexp_overflow, ldexp_underflow, /* 146, 147 */ | |
223 | ldexpf_overflow, ldexpf_underflow, /* 148, 149 */ | |
224 | logbl_zero, logb_zero, logbf_zero, /* 150, 151, 152 */ | |
225 | nextafterl_overflow, nextafter_overflow, | |
226 | nextafterf_overflow, /* 153, 154, 155 */ | |
227 | ilogbl_zero, ilogb_zero, ilogbf_zero, /* 156, 157, 158 */ | |
228 | exp2l_overflow, exp2l_underflow, /* 159, 160 */ | |
229 | exp2_overflow, exp2_underflow, /* 161, 162 */ | |
230 | exp2f_overflow, exp2f_underflow, /* 163, 164 */ | |
231 | exp10l_overflow, exp10_overflow, | |
232 | exp10f_overflow, /* 165, 166, 167 */ | |
233 | log2l_zero, log2l_negative, /* 168, 169 */ | |
234 | log2_zero, log2_negative, /* 170, 171 */ | |
235 | log2f_zero, log2f_negative, /* 172, 173 */ | |
236 | scalbnl_overflow, scalbnl_underflow, /* 174, 175 */ | |
237 | scalbn_overflow, scalbn_underflow, /* 176, 177 */ | |
238 | scalbnf_overflow, scalbnf_underflow /* 178, 179 */ | |
239 | } error_types; | |
240 | ||
241 | void __libm_error_support(void*,void*,void*,error_types); | |
242 | libc_hidden_proto(__libm_error_support) | |
243 | ||
244 | #define BIAS_64 1023 | |
245 | #define EXPINF_64 2047 | |
246 | ||
247 | #define DOUBLE_HEX(HI, LO) 0x ## LO, 0x ## HI | |
248 | ||
249 | #if 0 | |
250 | static const unsigned INF[] = { | |
251 | DOUBLE_HEX(7ff00000, 00000000), | |
252 | DOUBLE_HEX(fff00000, 00000000) | |
253 | }; | |
8da2915d | 254 | |
a334319f UD |
255 | static const double _zeroo = 0.0; |
256 | static const double _bigg = 1.0e300; | |
257 | static const double _ponee = 1.0; | |
258 | static const double _nonee = -1.0; | |
8da2915d | 259 | |
a334319f UD |
260 | #define INVALID (_zeroo * *((double*)&INF[0])) |
261 | #define PINF *((double*)&INF[0]) | |
262 | #define NINF -PINF | |
263 | #define PINF_DZ (_ponee/_zeroo) | |
264 | #define X_TLOSS 1.41484755040568800000e+16 | |
8da2915d UD |
265 | #endif |
266 | ||
267 | struct exceptionf | |
268 | { | |
269 | int type; | |
270 | char *name; | |
271 | float arg1, arg2, retval; | |
272 | }; | |
273 | ||
274 | # ifdef __cplusplus | |
275 | struct __exception | |
276 | { | |
277 | int type; | |
278 | char *name; | |
279 | double arg1, arg2, retval; | |
280 | }; | |
281 | # else | |
282 | ||
283 | # ifndef _LIBC | |
284 | struct exception | |
285 | { | |
286 | int type; | |
287 | char *name; | |
288 | double arg1, arg2, retval; | |
289 | }; | |
290 | # endif | |
291 | # endif | |
292 | ||
a334319f UD |
293 | |
294 | ||
8da2915d UD |
295 | struct exceptionl |
296 | { | |
297 | int type; | |
298 | char *name; | |
299 | long double arg1, arg2, retval; | |
300 | }; | |
301 | ||
a334319f UD |
302 | #ifdef _MS_ |
303 | #define MATHERR_F _matherrf | |
304 | #define MATHERR_D _matherr | |
8da2915d | 305 | #else |
a334319f UD |
306 | #define MATHERR_F matherrf |
307 | #define MATHERR_D matherr | |
8da2915d UD |
308 | #endif |
309 | ||
310 | # ifdef __cplusplus | |
a334319f | 311 | #define EXC_DECL_D __exception |
8da2915d UD |
312 | #else |
313 | // exception is a reserved name in C++ | |
a334319f | 314 | #define EXC_DECL_D exception |
8da2915d UD |
315 | #endif |
316 | ||
317 | extern int MATHERR_F(struct exceptionf*); | |
318 | extern int MATHERR_D(struct EXC_DECL_D*); | |
319 | extern int matherrl(struct exceptionl*); | |
320 | ||
a334319f UD |
321 | |
322 | /* Set these appropriately to make thread Safe */ | |
323 | #define ERRNO_RANGE errno = ERANGE | |
324 | #define ERRNO_DOMAIN errno = EDOM | |
325 | ||
326 | ||
327 | // Add code to support _LIB_VERSION | |
8da2915d UD |
328 | #ifndef _LIBC |
329 | typedef enum | |
330 | { | |
331 | _IEEE_ = -1, // IEEE-like behavior | |
332 | _SVID_, // SysV, Rel. 4 behavior | |
333 | _XOPEN_, // Unix98 | |
334 | _POSIX_, // Posix | |
335 | _ISOC_ // ISO C9X | |
336 | } _LIB_VERSION_TYPE; | |
0ecb606c | 337 | |
a334319f | 338 | extern _LIB_VERSION_TYPE _LIB_VERSION; |
0ecb606c JJ |
339 | #endif |
340 | ||
a334319f UD |
341 | // This is a run-time variable and may effect |
342 | // floating point behavior of the libm functions | |
0ecb606c | 343 | |
a334319f | 344 | #elif defined _LIBC |
0ecb606c | 345 | |
a334319f UD |
346 | # if !defined NOT_IN_libc && defined SHARED && defined DO_VERSIONING \ |
347 | && !defined HAVE_BROKEN_ALIAS_ATTRIBUTE && !defined NO_HIDDEN | |
348 | # define __libm_error_support __GI___libm_error_support | |
349 | # endif | |
27b02589 | 350 | |
a334319f | 351 | #endif /* __ASSEMBLER__ */ |
8da2915d | 352 | |
a334319f UD |
353 | /* Support for compatible assembler handling. */ |
354 | #if !defined L && defined _LIBC | |
355 | #define L(name) .L##name | |
8da2915d | 356 | #endif |
a334319f UD |
357 | #ifdef __ELF__ |
358 | #define ASM_SIZE_DIRECTIVE(name) .size name,.-name | |
359 | #define ASM_TYPE_DIRECTIVE(name,T) .type name,T | |
8da2915d | 360 | #else |
a334319f UD |
361 | #define ASM_SIZE_DIRECTIVE(name) |
362 | #define ASM_TYPE_DIRECTIVE(name,T) | |
8da2915d | 363 | #endif |