|
|
1.1.1.10 root 1: /*
2: * QEMU float support
3: *
4: * Derived from SoftFloat.
5: */
6:
1.1 root 7: /*============================================================================
8:
9: This C header file is part of the SoftFloat IEC/IEEE Floating-point Arithmetic
10: Package, Release 2b.
11:
12: Written by John R. Hauser. This work was made possible in part by the
13: International Computer Science Institute, located at Suite 600, 1947 Center
14: Street, Berkeley, California 94704. Funding was partially provided by the
15: National Science Foundation under grant MIP-9311980. The original version
16: of this code was written as part of a project to build a fixed-point vector
17: processor in collaboration with the University of California at Berkeley,
18: overseen by Profs. Nelson Morgan and John Wawrzynek. More information
19: is available through the Web page `http://www.cs.berkeley.edu/~jhauser/
20: arithmetic/SoftFloat.html'.
21:
22: THIS SOFTWARE IS DISTRIBUTED AS IS, FOR FREE. Although reasonable effort has
23: been made to avoid it, THIS SOFTWARE MAY CONTAIN FAULTS THAT WILL AT TIMES
24: RESULT IN INCORRECT BEHAVIOR. USE OF THIS SOFTWARE IS RESTRICTED TO PERSONS
25: AND ORGANIZATIONS WHO CAN AND WILL TAKE FULL RESPONSIBILITY FOR ALL LOSSES,
26: COSTS, OR OTHER PROBLEMS THEY INCUR DUE TO THE SOFTWARE, AND WHO FURTHERMORE
27: EFFECTIVELY INDEMNIFY JOHN HAUSER AND THE INTERNATIONAL COMPUTER SCIENCE
28: INSTITUTE (possibly via similar legal warning) AGAINST ALL LOSSES, COSTS, OR
29: OTHER PROBLEMS INCURRED BY THEIR CUSTOMERS AND CLIENTS DUE TO THE SOFTWARE.
30:
31: Derivative works are acceptable, even for commercial purposes, so long as
32: (1) the source code for the derivative work includes prominent notice that
33: the work is derivative, and (2) the source code includes prominent notice with
34: these four paragraphs for those parts of this code that are retained.
35:
36: =============================================================================*/
37:
38: #ifndef SOFTFLOAT_H
39: #define SOFTFLOAT_H
40:
1.1.1.7 root 41: #if defined(CONFIG_SOLARIS) && defined(CONFIG_NEEDS_LIBSUNMATH)
1.1.1.4 root 42: #include <sunmath.h>
43: #endif
44:
1.1 root 45: #include <inttypes.h>
1.1.1.11! root 46: #include "config-host.h"
1.1 root 47:
48: /*----------------------------------------------------------------------------
49: | Each of the following `typedef's defines the most convenient type that holds
50: | integers of at least as many bits as specified. For example, `uint8' should
51: | be the most convenient type that can hold unsigned integers of as many as
52: | 8 bits. The `flag' type must be able to hold either a 0 or 1. For most
53: | implementations of C, `flag', `uint8', and `int8' should all be `typedef'ed
54: | to the same as `int'.
55: *----------------------------------------------------------------------------*/
1.1.1.3 root 56: typedef uint8_t flag;
1.1 root 57: typedef uint8_t uint8;
58: typedef int8_t int8;
1.1.1.5 root 59: #ifndef _AIX
1.1 root 60: typedef int uint16;
61: typedef int int16;
1.1.1.5 root 62: #endif
1.1 root 63: typedef unsigned int uint32;
64: typedef signed int int32;
65: typedef uint64_t uint64;
66: typedef int64_t int64;
67:
68: #define LIT64( a ) a##LL
69: #define INLINE static inline
70:
71: #define STATUS_PARAM , float_status *status
72: #define STATUS(field) status->field
73: #define STATUS_VAR , status
74:
75: /*----------------------------------------------------------------------------
76: | Software IEC/IEEE floating-point ordering relations
77: *----------------------------------------------------------------------------*/
78: enum {
79: float_relation_less = -1,
80: float_relation_equal = 0,
81: float_relation_greater = 1,
82: float_relation_unordered = 2
83: };
84:
85: /*----------------------------------------------------------------------------
86: | Software IEC/IEEE floating-point types.
87: *----------------------------------------------------------------------------*/
1.1.1.4 root 88: /* Use structures for soft-float types. This prevents accidentally mixing
89: them with native int/float types. A sufficiently clever compiler and
90: sane ABI should be able to see though these structs. However
91: x86/gcc 3.x seems to struggle a bit, so leave them disabled by default. */
92: //#define USE_SOFTFLOAT_STRUCT_TYPES
93: #ifdef USE_SOFTFLOAT_STRUCT_TYPES
94: typedef struct {
1.1.1.10 root 95: uint16_t v;
96: } float16;
97: #define float16_val(x) (((float16)(x)).v)
98: #define make_float16(x) __extension__ ({ float16 f16_val = {x}; f16_val; })
99: #define const_float16(x) { x }
100: typedef struct {
1.1.1.4 root 101: uint32_t v;
102: } float32;
103: /* The cast ensures an error if the wrong type is passed. */
104: #define float32_val(x) (((float32)(x)).v)
105: #define make_float32(x) __extension__ ({ float32 f32_val = {x}; f32_val; })
1.1.1.10 root 106: #define const_float32(x) { x }
1.1.1.4 root 107: typedef struct {
108: uint64_t v;
109: } float64;
110: #define float64_val(x) (((float64)(x)).v)
111: #define make_float64(x) __extension__ ({ float64 f64_val = {x}; f64_val; })
1.1.1.10 root 112: #define const_float64(x) { x }
1.1.1.4 root 113: #else
1.1.1.10 root 114: typedef uint16_t float16;
1.1 root 115: typedef uint32_t float32;
116: typedef uint64_t float64;
1.1.1.10 root 117: #define float16_val(x) (x)
1.1.1.4 root 118: #define float32_val(x) (x)
119: #define float64_val(x) (x)
1.1.1.10 root 120: #define make_float16(x) (x)
1.1.1.4 root 121: #define make_float32(x) (x)
122: #define make_float64(x) (x)
1.1.1.10 root 123: #define const_float16(x) (x)
124: #define const_float32(x) (x)
125: #define const_float64(x) (x)
1.1.1.4 root 126: #endif
1.1 root 127: typedef struct {
128: uint64_t low;
129: uint16_t high;
130: } floatx80;
1.1.1.10 root 131: #define make_floatx80(exp, mant) ((floatx80) { mant, exp })
1.1 root 132: typedef struct {
1.1.1.7 root 133: #ifdef HOST_WORDS_BIGENDIAN
1.1 root 134: uint64_t high, low;
135: #else
136: uint64_t low, high;
137: #endif
138: } float128;
1.1.1.11! root 139: #define make_float128(high_, low_) ((float128) { .high = high_, .low = low_ })
1.1 root 140:
141: /*----------------------------------------------------------------------------
142: | Software IEC/IEEE floating-point underflow tininess-detection mode.
143: *----------------------------------------------------------------------------*/
144: enum {
145: float_tininess_after_rounding = 0,
146: float_tininess_before_rounding = 1
147: };
148:
149: /*----------------------------------------------------------------------------
150: | Software IEC/IEEE floating-point rounding mode.
151: *----------------------------------------------------------------------------*/
152: enum {
153: float_round_nearest_even = 0,
154: float_round_down = 1,
155: float_round_up = 2,
156: float_round_to_zero = 3
157: };
158:
159: /*----------------------------------------------------------------------------
160: | Software IEC/IEEE floating-point exception flags.
161: *----------------------------------------------------------------------------*/
162: enum {
163: float_flag_invalid = 1,
164: float_flag_divbyzero = 4,
165: float_flag_overflow = 8,
166: float_flag_underflow = 16,
1.1.1.9 root 167: float_flag_inexact = 32,
1.1.1.10 root 168: float_flag_input_denormal = 64,
169: float_flag_output_denormal = 128
1.1 root 170: };
171:
172: typedef struct float_status {
173: signed char float_detect_tininess;
174: signed char float_rounding_mode;
175: signed char float_exception_flags;
176: signed char floatx80_rounding_precision;
1.1.1.9 root 177: /* should denormalised results go to zero and set the inexact flag? */
1.1.1.5 root 178: flag flush_to_zero;
1.1.1.9 root 179: /* should denormalised inputs go to zero and set the input_denormal flag? */
180: flag flush_inputs_to_zero;
1.1.1.5 root 181: flag default_nan_mode;
1.1 root 182: } float_status;
183:
184: void set_float_rounding_mode(int val STATUS_PARAM);
185: void set_float_exception_flags(int val STATUS_PARAM);
1.1.1.10 root 186: INLINE void set_float_detect_tininess(int val STATUS_PARAM)
187: {
188: STATUS(float_detect_tininess) = val;
189: }
1.1.1.5 root 190: INLINE void set_flush_to_zero(flag val STATUS_PARAM)
191: {
192: STATUS(flush_to_zero) = val;
193: }
1.1.1.9 root 194: INLINE void set_flush_inputs_to_zero(flag val STATUS_PARAM)
195: {
196: STATUS(flush_inputs_to_zero) = val;
197: }
1.1.1.5 root 198: INLINE void set_default_nan_mode(flag val STATUS_PARAM)
199: {
200: STATUS(default_nan_mode) = val;
201: }
1.1 root 202: INLINE int get_float_exception_flags(float_status *status)
203: {
204: return STATUS(float_exception_flags);
205: }
206: void set_floatx80_rounding_precision(int val STATUS_PARAM);
207:
208: /*----------------------------------------------------------------------------
209: | Routine to raise any or all of the software IEC/IEEE floating-point
210: | exception flags.
211: *----------------------------------------------------------------------------*/
1.1.1.2 root 212: void float_raise( int8 flags STATUS_PARAM);
1.1 root 213:
214: /*----------------------------------------------------------------------------
1.1.1.11! root 215: | Options to indicate which negations to perform in float*_muladd()
! 216: | Using these differs from negating an input or output before calling
! 217: | the muladd function in that this means that a NaN doesn't have its
! 218: | sign bit inverted before it is propagated.
! 219: *----------------------------------------------------------------------------*/
! 220: enum {
! 221: float_muladd_negate_c = 1,
! 222: float_muladd_negate_product = 2,
! 223: float_muladd_negate_result = 3,
! 224: };
! 225:
! 226: /*----------------------------------------------------------------------------
1.1 root 227: | Software IEC/IEEE integer-to-floating-point conversion routines.
228: *----------------------------------------------------------------------------*/
1.1.1.10 root 229: float32 int32_to_float32( int32 STATUS_PARAM );
230: float64 int32_to_float64( int32 STATUS_PARAM );
1.1.1.11! root 231: float32 uint32_to_float32( uint32 STATUS_PARAM );
! 232: float64 uint32_to_float64( uint32 STATUS_PARAM );
1.1.1.10 root 233: floatx80 int32_to_floatx80( int32 STATUS_PARAM );
234: float128 int32_to_float128( int32 STATUS_PARAM );
235: float32 int64_to_float32( int64 STATUS_PARAM );
236: float32 uint64_to_float32( uint64 STATUS_PARAM );
237: float64 int64_to_float64( int64 STATUS_PARAM );
238: float64 uint64_to_float64( uint64 STATUS_PARAM );
239: floatx80 int64_to_floatx80( int64 STATUS_PARAM );
240: float128 int64_to_float128( int64 STATUS_PARAM );
1.1 root 241:
242: /*----------------------------------------------------------------------------
1.1.1.7 root 243: | Software half-precision conversion routines.
244: *----------------------------------------------------------------------------*/
1.1.1.10 root 245: float16 float32_to_float16( float32, flag STATUS_PARAM );
246: float32 float16_to_float32( float16, flag STATUS_PARAM );
247:
248: /*----------------------------------------------------------------------------
249: | Software half-precision operations.
250: *----------------------------------------------------------------------------*/
251: int float16_is_quiet_nan( float16 );
252: int float16_is_signaling_nan( float16 );
253: float16 float16_maybe_silence_nan( float16 );
254:
255: /*----------------------------------------------------------------------------
256: | The pattern for a default generated half-precision NaN.
257: *----------------------------------------------------------------------------*/
1.1.1.11! root 258: extern const float16 float16_default_nan;
1.1.1.7 root 259:
260: /*----------------------------------------------------------------------------
1.1 root 261: | Software IEC/IEEE single-precision conversion routines.
262: *----------------------------------------------------------------------------*/
1.1.1.10 root 263: int16 float32_to_int16_round_to_zero( float32 STATUS_PARAM );
1.1.1.11! root 264: uint16 float32_to_uint16_round_to_zero( float32 STATUS_PARAM );
1.1.1.10 root 265: int32 float32_to_int32( float32 STATUS_PARAM );
266: int32 float32_to_int32_round_to_zero( float32 STATUS_PARAM );
267: uint32 float32_to_uint32( float32 STATUS_PARAM );
268: uint32 float32_to_uint32_round_to_zero( float32 STATUS_PARAM );
269: int64 float32_to_int64( float32 STATUS_PARAM );
270: int64 float32_to_int64_round_to_zero( float32 STATUS_PARAM );
1.1 root 271: float64 float32_to_float64( float32 STATUS_PARAM );
272: floatx80 float32_to_floatx80( float32 STATUS_PARAM );
273: float128 float32_to_float128( float32 STATUS_PARAM );
274:
275: /*----------------------------------------------------------------------------
276: | Software IEC/IEEE single-precision operations.
277: *----------------------------------------------------------------------------*/
278: float32 float32_round_to_int( float32 STATUS_PARAM );
279: float32 float32_add( float32, float32 STATUS_PARAM );
280: float32 float32_sub( float32, float32 STATUS_PARAM );
281: float32 float32_mul( float32, float32 STATUS_PARAM );
282: float32 float32_div( float32, float32 STATUS_PARAM );
283: float32 float32_rem( float32, float32 STATUS_PARAM );
1.1.1.11! root 284: float32 float32_muladd(float32, float32, float32, int STATUS_PARAM);
1.1 root 285: float32 float32_sqrt( float32 STATUS_PARAM );
1.1.1.8 root 286: float32 float32_exp2( float32 STATUS_PARAM );
1.1.1.5 root 287: float32 float32_log2( float32 STATUS_PARAM );
1.1.1.3 root 288: int float32_eq( float32, float32 STATUS_PARAM );
289: int float32_le( float32, float32 STATUS_PARAM );
290: int float32_lt( float32, float32 STATUS_PARAM );
1.1.1.10 root 291: int float32_unordered( float32, float32 STATUS_PARAM );
292: int float32_eq_quiet( float32, float32 STATUS_PARAM );
1.1.1.3 root 293: int float32_le_quiet( float32, float32 STATUS_PARAM );
294: int float32_lt_quiet( float32, float32 STATUS_PARAM );
1.1.1.10 root 295: int float32_unordered_quiet( float32, float32 STATUS_PARAM );
1.1.1.3 root 296: int float32_compare( float32, float32 STATUS_PARAM );
297: int float32_compare_quiet( float32, float32 STATUS_PARAM );
1.1.1.10 root 298: float32 float32_min(float32, float32 STATUS_PARAM);
299: float32 float32_max(float32, float32 STATUS_PARAM);
1.1.1.9 root 300: int float32_is_quiet_nan( float32 );
1.1.1.3 root 301: int float32_is_signaling_nan( float32 );
1.1.1.9 root 302: float32 float32_maybe_silence_nan( float32 );
1.1.1.4 root 303: float32 float32_scalbn( float32, int STATUS_PARAM );
1.1 root 304:
305: INLINE float32 float32_abs(float32 a)
306: {
1.1.1.9 root 307: /* Note that abs does *not* handle NaN specially, nor does
308: * it flush denormal inputs to zero.
309: */
1.1.1.4 root 310: return make_float32(float32_val(a) & 0x7fffffff);
1.1 root 311: }
312:
313: INLINE float32 float32_chs(float32 a)
314: {
1.1.1.9 root 315: /* Note that chs does *not* handle NaN specially, nor does
316: * it flush denormal inputs to zero.
317: */
1.1.1.4 root 318: return make_float32(float32_val(a) ^ 0x80000000);
1.1 root 319: }
320:
1.1.1.5 root 321: INLINE int float32_is_infinity(float32 a)
322: {
323: return (float32_val(a) & 0x7fffffff) == 0x7f800000;
324: }
325:
326: INLINE int float32_is_neg(float32 a)
327: {
328: return float32_val(a) >> 31;
329: }
330:
331: INLINE int float32_is_zero(float32 a)
332: {
333: return (float32_val(a) & 0x7fffffff) == 0;
334: }
335:
1.1.1.9 root 336: INLINE int float32_is_any_nan(float32 a)
337: {
338: return ((float32_val(a) & ~(1 << 31)) > 0x7f800000UL);
339: }
340:
341: INLINE int float32_is_zero_or_denormal(float32 a)
342: {
343: return (float32_val(a) & 0x7f800000) == 0;
344: }
345:
1.1.1.10 root 346: INLINE float32 float32_set_sign(float32 a, int sign)
347: {
348: return make_float32((float32_val(a) & 0x7fffffff) | (sign << 31));
349: }
350:
1.1.1.4 root 351: #define float32_zero make_float32(0)
1.1.1.5 root 352: #define float32_one make_float32(0x3f800000)
1.1.1.8 root 353: #define float32_ln2 make_float32(0x3f317218)
1.1.1.10 root 354: #define float32_pi make_float32(0x40490fdb)
355: #define float32_half make_float32(0x3f000000)
356: #define float32_infinity make_float32(0x7f800000)
357:
358:
359: /*----------------------------------------------------------------------------
360: | The pattern for a default generated single-precision NaN.
361: *----------------------------------------------------------------------------*/
1.1.1.11! root 362: extern const float32 float32_default_nan;
1.1.1.4 root 363:
1.1 root 364: /*----------------------------------------------------------------------------
365: | Software IEC/IEEE double-precision conversion routines.
366: *----------------------------------------------------------------------------*/
1.1.1.10 root 367: int16 float64_to_int16_round_to_zero( float64 STATUS_PARAM );
1.1.1.11! root 368: uint16 float64_to_uint16_round_to_zero( float64 STATUS_PARAM );
1.1.1.10 root 369: int32 float64_to_int32( float64 STATUS_PARAM );
370: int32 float64_to_int32_round_to_zero( float64 STATUS_PARAM );
371: uint32 float64_to_uint32( float64 STATUS_PARAM );
372: uint32 float64_to_uint32_round_to_zero( float64 STATUS_PARAM );
373: int64 float64_to_int64( float64 STATUS_PARAM );
374: int64 float64_to_int64_round_to_zero( float64 STATUS_PARAM );
375: uint64 float64_to_uint64 (float64 a STATUS_PARAM);
376: uint64 float64_to_uint64_round_to_zero (float64 a STATUS_PARAM);
1.1 root 377: float32 float64_to_float32( float64 STATUS_PARAM );
378: floatx80 float64_to_floatx80( float64 STATUS_PARAM );
379: float128 float64_to_float128( float64 STATUS_PARAM );
380:
381: /*----------------------------------------------------------------------------
382: | Software IEC/IEEE double-precision operations.
383: *----------------------------------------------------------------------------*/
384: float64 float64_round_to_int( float64 STATUS_PARAM );
1.1.1.3 root 385: float64 float64_trunc_to_int( float64 STATUS_PARAM );
1.1 root 386: float64 float64_add( float64, float64 STATUS_PARAM );
387: float64 float64_sub( float64, float64 STATUS_PARAM );
388: float64 float64_mul( float64, float64 STATUS_PARAM );
389: float64 float64_div( float64, float64 STATUS_PARAM );
390: float64 float64_rem( float64, float64 STATUS_PARAM );
1.1.1.11! root 391: float64 float64_muladd(float64, float64, float64, int STATUS_PARAM);
1.1 root 392: float64 float64_sqrt( float64 STATUS_PARAM );
1.1.1.5 root 393: float64 float64_log2( float64 STATUS_PARAM );
1.1.1.3 root 394: int float64_eq( float64, float64 STATUS_PARAM );
395: int float64_le( float64, float64 STATUS_PARAM );
396: int float64_lt( float64, float64 STATUS_PARAM );
1.1.1.10 root 397: int float64_unordered( float64, float64 STATUS_PARAM );
398: int float64_eq_quiet( float64, float64 STATUS_PARAM );
1.1.1.3 root 399: int float64_le_quiet( float64, float64 STATUS_PARAM );
400: int float64_lt_quiet( float64, float64 STATUS_PARAM );
1.1.1.10 root 401: int float64_unordered_quiet( float64, float64 STATUS_PARAM );
1.1.1.3 root 402: int float64_compare( float64, float64 STATUS_PARAM );
403: int float64_compare_quiet( float64, float64 STATUS_PARAM );
1.1.1.10 root 404: float64 float64_min(float64, float64 STATUS_PARAM);
405: float64 float64_max(float64, float64 STATUS_PARAM);
1.1.1.9 root 406: int float64_is_quiet_nan( float64 a );
1.1.1.3 root 407: int float64_is_signaling_nan( float64 );
1.1.1.9 root 408: float64 float64_maybe_silence_nan( float64 );
1.1.1.4 root 409: float64 float64_scalbn( float64, int STATUS_PARAM );
1.1 root 410:
411: INLINE float64 float64_abs(float64 a)
412: {
1.1.1.9 root 413: /* Note that abs does *not* handle NaN specially, nor does
414: * it flush denormal inputs to zero.
415: */
1.1.1.4 root 416: return make_float64(float64_val(a) & 0x7fffffffffffffffLL);
1.1 root 417: }
418:
419: INLINE float64 float64_chs(float64 a)
420: {
1.1.1.9 root 421: /* Note that chs does *not* handle NaN specially, nor does
422: * it flush denormal inputs to zero.
423: */
1.1.1.4 root 424: return make_float64(float64_val(a) ^ 0x8000000000000000LL);
1.1 root 425: }
426:
1.1.1.5 root 427: INLINE int float64_is_infinity(float64 a)
428: {
429: return (float64_val(a) & 0x7fffffffffffffffLL ) == 0x7ff0000000000000LL;
430: }
431:
432: INLINE int float64_is_neg(float64 a)
433: {
434: return float64_val(a) >> 63;
435: }
436:
437: INLINE int float64_is_zero(float64 a)
438: {
439: return (float64_val(a) & 0x7fffffffffffffffLL) == 0;
440: }
441:
1.1.1.9 root 442: INLINE int float64_is_any_nan(float64 a)
443: {
444: return ((float64_val(a) & ~(1ULL << 63)) > 0x7ff0000000000000ULL);
445: }
446:
1.1.1.10 root 447: INLINE int float64_is_zero_or_denormal(float64 a)
448: {
449: return (float64_val(a) & 0x7ff0000000000000LL) == 0;
450: }
451:
452: INLINE float64 float64_set_sign(float64 a, int sign)
453: {
454: return make_float64((float64_val(a) & 0x7fffffffffffffffULL)
455: | ((int64_t)sign << 63));
456: }
457:
1.1.1.4 root 458: #define float64_zero make_float64(0)
1.1.1.5 root 459: #define float64_one make_float64(0x3ff0000000000000LL)
1.1.1.8 root 460: #define float64_ln2 make_float64(0x3fe62e42fefa39efLL)
1.1.1.10 root 461: #define float64_pi make_float64(0x400921fb54442d18LL)
462: #define float64_half make_float64(0x3fe0000000000000LL)
463: #define float64_infinity make_float64(0x7ff0000000000000LL)
1.1.1.4 root 464:
1.1.1.10 root 465: /*----------------------------------------------------------------------------
466: | The pattern for a default generated double-precision NaN.
467: *----------------------------------------------------------------------------*/
1.1.1.11! root 468: extern const float64 float64_default_nan;
1.1 root 469:
470: /*----------------------------------------------------------------------------
471: | Software IEC/IEEE extended double-precision conversion routines.
472: *----------------------------------------------------------------------------*/
1.1.1.10 root 473: int32 floatx80_to_int32( floatx80 STATUS_PARAM );
474: int32 floatx80_to_int32_round_to_zero( floatx80 STATUS_PARAM );
475: int64 floatx80_to_int64( floatx80 STATUS_PARAM );
476: int64 floatx80_to_int64_round_to_zero( floatx80 STATUS_PARAM );
1.1 root 477: float32 floatx80_to_float32( floatx80 STATUS_PARAM );
478: float64 floatx80_to_float64( floatx80 STATUS_PARAM );
479: float128 floatx80_to_float128( floatx80 STATUS_PARAM );
480:
481: /*----------------------------------------------------------------------------
482: | Software IEC/IEEE extended double-precision operations.
483: *----------------------------------------------------------------------------*/
484: floatx80 floatx80_round_to_int( floatx80 STATUS_PARAM );
485: floatx80 floatx80_add( floatx80, floatx80 STATUS_PARAM );
486: floatx80 floatx80_sub( floatx80, floatx80 STATUS_PARAM );
487: floatx80 floatx80_mul( floatx80, floatx80 STATUS_PARAM );
488: floatx80 floatx80_div( floatx80, floatx80 STATUS_PARAM );
489: floatx80 floatx80_rem( floatx80, floatx80 STATUS_PARAM );
490: floatx80 floatx80_sqrt( floatx80 STATUS_PARAM );
1.1.1.3 root 491: int floatx80_eq( floatx80, floatx80 STATUS_PARAM );
492: int floatx80_le( floatx80, floatx80 STATUS_PARAM );
493: int floatx80_lt( floatx80, floatx80 STATUS_PARAM );
1.1.1.10 root 494: int floatx80_unordered( floatx80, floatx80 STATUS_PARAM );
495: int floatx80_eq_quiet( floatx80, floatx80 STATUS_PARAM );
1.1.1.3 root 496: int floatx80_le_quiet( floatx80, floatx80 STATUS_PARAM );
497: int floatx80_lt_quiet( floatx80, floatx80 STATUS_PARAM );
1.1.1.10 root 498: int floatx80_unordered_quiet( floatx80, floatx80 STATUS_PARAM );
499: int floatx80_compare( floatx80, floatx80 STATUS_PARAM );
500: int floatx80_compare_quiet( floatx80, floatx80 STATUS_PARAM );
1.1.1.9 root 501: int floatx80_is_quiet_nan( floatx80 );
1.1.1.3 root 502: int floatx80_is_signaling_nan( floatx80 );
1.1.1.9 root 503: floatx80 floatx80_maybe_silence_nan( floatx80 );
1.1.1.4 root 504: floatx80 floatx80_scalbn( floatx80, int STATUS_PARAM );
1.1 root 505:
506: INLINE floatx80 floatx80_abs(floatx80 a)
507: {
508: a.high &= 0x7fff;
509: return a;
510: }
511:
512: INLINE floatx80 floatx80_chs(floatx80 a)
513: {
514: a.high ^= 0x8000;
515: return a;
516: }
517:
1.1.1.5 root 518: INLINE int floatx80_is_infinity(floatx80 a)
519: {
1.1.1.10 root 520: return (a.high & 0x7fff) == 0x7fff && a.low == 0x8000000000000000LL;
1.1.1.5 root 521: }
522:
523: INLINE int floatx80_is_neg(floatx80 a)
524: {
525: return a.high >> 15;
526: }
527:
528: INLINE int floatx80_is_zero(floatx80 a)
529: {
530: return (a.high & 0x7fff) == 0 && a.low == 0;
531: }
532:
1.1.1.10 root 533: INLINE int floatx80_is_zero_or_denormal(floatx80 a)
534: {
535: return (a.high & 0x7fff) == 0;
536: }
537:
1.1.1.9 root 538: INLINE int floatx80_is_any_nan(floatx80 a)
539: {
540: return ((a.high & 0x7fff) == 0x7fff) && (a.low<<1);
541: }
542:
1.1.1.10 root 543: #define floatx80_zero make_floatx80(0x0000, 0x0000000000000000LL)
544: #define floatx80_one make_floatx80(0x3fff, 0x8000000000000000LL)
545: #define floatx80_ln2 make_floatx80(0x3ffe, 0xb17217f7d1cf79acLL)
546: #define floatx80_pi make_floatx80(0x4000, 0xc90fdaa22168c235LL)
547: #define floatx80_half make_floatx80(0x3ffe, 0x8000000000000000LL)
548: #define floatx80_infinity make_floatx80(0x7fff, 0x8000000000000000LL)
1.1 root 549:
1.1.1.10 root 550: /*----------------------------------------------------------------------------
1.1.1.11! root 551: | The pattern for a default generated extended double-precision NaN.
! 552: *----------------------------------------------------------------------------*/
! 553: extern const floatx80 floatx80_default_nan;
1.1 root 554:
555: /*----------------------------------------------------------------------------
556: | Software IEC/IEEE quadruple-precision conversion routines.
557: *----------------------------------------------------------------------------*/
1.1.1.10 root 558: int32 float128_to_int32( float128 STATUS_PARAM );
559: int32 float128_to_int32_round_to_zero( float128 STATUS_PARAM );
560: int64 float128_to_int64( float128 STATUS_PARAM );
561: int64 float128_to_int64_round_to_zero( float128 STATUS_PARAM );
1.1 root 562: float32 float128_to_float32( float128 STATUS_PARAM );
563: float64 float128_to_float64( float128 STATUS_PARAM );
564: floatx80 float128_to_floatx80( float128 STATUS_PARAM );
565:
566: /*----------------------------------------------------------------------------
567: | Software IEC/IEEE quadruple-precision operations.
568: *----------------------------------------------------------------------------*/
569: float128 float128_round_to_int( float128 STATUS_PARAM );
570: float128 float128_add( float128, float128 STATUS_PARAM );
571: float128 float128_sub( float128, float128 STATUS_PARAM );
572: float128 float128_mul( float128, float128 STATUS_PARAM );
573: float128 float128_div( float128, float128 STATUS_PARAM );
574: float128 float128_rem( float128, float128 STATUS_PARAM );
575: float128 float128_sqrt( float128 STATUS_PARAM );
1.1.1.3 root 576: int float128_eq( float128, float128 STATUS_PARAM );
577: int float128_le( float128, float128 STATUS_PARAM );
578: int float128_lt( float128, float128 STATUS_PARAM );
1.1.1.10 root 579: int float128_unordered( float128, float128 STATUS_PARAM );
580: int float128_eq_quiet( float128, float128 STATUS_PARAM );
1.1.1.3 root 581: int float128_le_quiet( float128, float128 STATUS_PARAM );
582: int float128_lt_quiet( float128, float128 STATUS_PARAM );
1.1.1.10 root 583: int float128_unordered_quiet( float128, float128 STATUS_PARAM );
1.1.1.4 root 584: int float128_compare( float128, float128 STATUS_PARAM );
585: int float128_compare_quiet( float128, float128 STATUS_PARAM );
1.1.1.9 root 586: int float128_is_quiet_nan( float128 );
1.1.1.3 root 587: int float128_is_signaling_nan( float128 );
1.1.1.9 root 588: float128 float128_maybe_silence_nan( float128 );
1.1.1.4 root 589: float128 float128_scalbn( float128, int STATUS_PARAM );
1.1 root 590:
591: INLINE float128 float128_abs(float128 a)
592: {
593: a.high &= 0x7fffffffffffffffLL;
594: return a;
595: }
596:
597: INLINE float128 float128_chs(float128 a)
598: {
599: a.high ^= 0x8000000000000000LL;
600: return a;
601: }
602:
1.1.1.5 root 603: INLINE int float128_is_infinity(float128 a)
604: {
605: return (a.high & 0x7fffffffffffffffLL) == 0x7fff000000000000LL && a.low == 0;
606: }
607:
608: INLINE int float128_is_neg(float128 a)
609: {
610: return a.high >> 63;
611: }
612:
613: INLINE int float128_is_zero(float128 a)
614: {
615: return (a.high & 0x7fffffffffffffffLL) == 0 && a.low == 0;
616: }
617:
1.1.1.10 root 618: INLINE int float128_is_zero_or_denormal(float128 a)
619: {
620: return (a.high & 0x7fff000000000000LL) == 0;
621: }
622:
1.1.1.9 root 623: INLINE int float128_is_any_nan(float128 a)
624: {
625: return ((a.high >> 48) & 0x7fff) == 0x7fff &&
626: ((a.low != 0) || ((a.high & 0xffffffffffffLL) != 0));
627: }
628:
1.1.1.10 root 629: /*----------------------------------------------------------------------------
1.1.1.11! root 630: | The pattern for a default generated quadruple-precision NaN.
1.1.1.10 root 631: *----------------------------------------------------------------------------*/
1.1.1.11! root 632: extern const float128 float128_default_nan;
1.1 root 633:
634: #endif /* !SOFTFLOAT_H */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.