1 /* Header file for dfp-bit.c.
2 Copyright (C) 2005, 2006 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 2, or (at your option) any later
11 In addition to the permissions in the GNU General Public License, the
12 Free Software Foundation gives you unlimited permission to link the
13 compiled version of this file into combinations with other programs,
14 and to distribute those combinations without any restriction coming
15 from the use of this file. (The General Public License restrictions
16 do apply in other respects; for example, they cover modification of
17 the file, and distribution when not linked into a combine
20 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
21 WARRANTY; without even the implied warranty of MERCHANTABILITY or
22 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
25 You should have received a copy of the GNU General Public License
26 along with GCC; see the file COPYING. If not, write to the Free
27 Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
35 #include <decExcept.h>
37 #include "coretypes.h"
40 #ifndef LIBGCC2_WORDS_BIG_ENDIAN
41 #define LIBGCC2_WORDS_BIG_ENDIAN WORDS_BIG_ENDIAN
44 #ifndef LIBGCC2_FLOAT_WORDS_BIG_ENDIAN
45 #define LIBGCC2_FLOAT_WORDS_BIG_ENDIAN LIBGCC2_WORDS_BIG_ENDIAN
48 #ifndef LIBGCC2_LONG_DOUBLE_TYPE_SIZE
49 #define LIBGCC2_LONG_DOUBLE_TYPE_SIZE LONG_DOUBLE_TYPE_SIZE
52 #ifndef LIBGCC2_HAS_XF_MODE
53 #define LIBGCC2_HAS_XF_MODE \
54 (BITS_PER_UNIT == 8 && LIBGCC2_LONG_DOUBLE_TYPE_SIZE == 80)
57 /* Depending on WIDTH, define a number of macros:
59 DFP_C_TYPE: type of the arguments to the libgcc functions;
62 IEEE_TYPE: the corresponding (encoded) IEEE754R type;
65 TO_INTERNAL: the name of the decNumber function to convert an
66 encoded value into the decNumber internal representation;
68 TO_ENCODED: the name of the decNumber function to convert an
69 internally represented decNumber into the encoded
72 FROM_STRING: the name of the decNumber function to read an
73 encoded value from a string.
75 TO_STRING: the name of the decNumber function to write an
76 encoded value to a string. */
79 #define DFP_C_TYPE _Decimal32
80 #define IEEE_TYPE decimal32
81 #define HOST_TO_IEEE __host_to_ieee_32
82 #define IEEE_TO_HOST __ieee_to_host_32
83 #define TO_INTERNAL __decimal32ToNumber
84 #define TO_ENCODED __decimal32FromNumber
85 #define FROM_STRING __decimal32FromString
86 #define TO_STRING __decimal32ToString
88 #define DFP_C_TYPE _Decimal64
89 #define IEEE_TYPE decimal64
90 #define HOST_TO_IEEE __host_to_ieee_64
91 #define IEEE_TO_HOST __ieee_to_host_64
92 #define TO_INTERNAL __decimal64ToNumber
93 #define TO_ENCODED __decimal64FromNumber
94 #define FROM_STRING __decimal64FromString
95 #define TO_STRING __decimal64ToString
97 #define DFP_C_TYPE _Decimal128
98 #define IEEE_TYPE decimal128
99 #define HOST_TO_IEEE __host_to_ieee_128
100 #define IEEE_TO_HOST __ieee_to_host_128
101 #define TO_INTERNAL __decimal128ToNumber
102 #define TO_ENCODED __decimal128FromNumber
103 #define FROM_STRING __decimal128FromString
104 #define TO_STRING __decimal128ToString
106 #error invalid decimal float word width
109 /* We define __DEC_EVAL_METHOD__ to 2, saying that we evaluate all
110 operations and constants to the range and precision of the _Decimal128
113 #define CONTEXT_INIT DEC_INIT_DECIMAL32
115 #define CONTEXT_INIT DEC_INIT_DECIMAL64
117 #define CONTEXT_INIT DEC_INIT_DECIMAL128
120 #ifndef DFP_INIT_ROUNDMODE
121 #define DFP_INIT_ROUNDMODE(A) A = DEC_ROUND_HALF_EVEN
124 #ifdef DFP_EXCEPTIONS_ENABLED
125 /* Return IEEE exception flags based on decNumber status flags. */
126 #define DFP_IEEE_FLAGS(DEC_FLAGS) __extension__ \
127 ({int _fe_flags = 0; \
128 if ((dec_flags & DEC_IEEE_854_Division_by_zero) != 0) \
129 _fe_flags |= FE_DIVBYZERO; \
130 if ((dec_flags & DEC_IEEE_854_Inexact) != 0) \
131 _fe_flags |= FE_INEXACT; \
132 if ((dec_flags & DEC_IEEE_854_Invalid_operation) != 0) \
133 _fe_flags |= FE_INVALID; \
134 if ((dec_flags & DEC_IEEE_854_Overflow) != 0) \
135 _fe_flags |= FE_OVERFLOW; \
136 if ((dec_flags & DEC_IEEE_854_Underflow) != 0) \
137 _fe_flags |= FE_UNDERFLOW; \
140 #define DFP_EXCEPTIONS_ENABLED 0
141 #define DFP_IEEE_FLAGS(A) 0
142 #define DFP_HANDLE_EXCEPTIONS(A) do {} while (0)
145 /* Conversions between different decimal float types use WIDTH_TO to
146 determine additional macros to define. */
148 #if defined (L_dd_to_sd) || defined (L_td_to_sd)
150 #elif defined (L_sd_to_dd) || defined (L_td_to_dd)
152 #elif defined (L_sd_to_td) || defined (L_dd_to_td)
156 /* If WIDTH_TO is defined, define additional macros:
158 DFP_C_TYPE_TO: type of the result of dfp to dfp conversion.
160 IEEE_TYPE_TO: the corresponding (encoded) IEEE754R type.
162 TO_ENCODED_TO: the name of the decNumber function to convert an
163 internally represented decNumber into the encoded representation
164 for the destination. */
167 #define DFP_C_TYPE_TO _Decimal32
168 #define IEEE_TYPE_TO decimal32
169 #define TO_ENCODED_TO __decimal32FromNumber
170 #define IEEE_TO_HOST_TO __ieee_to_host_32
172 #define DFP_C_TYPE_TO _Decimal64
173 #define IEEE_TYPE_TO decimal64
174 #define TO_ENCODED_TO __decimal64FromNumber
175 #define IEEE_TO_HOST_TO __ieee_to_host_64
176 #elif WIDTH_TO == 128
177 #define DFP_C_TYPE_TO _Decimal128
178 #define IEEE_TYPE_TO decimal128
179 #define TO_ENCODED_TO __decimal128FromNumber
180 #define IEEE_TO_HOST_TO __ieee_to_host_128
183 /* Conversions between decimal float types and integral types use INT_KIND
184 to determine the data type and C functions to use. */
186 #if defined (L_sd_to_si) || defined (L_dd_to_si) || defined (L_td_to_si) \
187 || defined (L_si_to_sd) || defined (L_si_to_dd) || defined (L_si_to_td)
189 #elif defined (L_sd_to_di) || defined (L_dd_to_di) || defined (L_td_to_di) \
190 || defined (L_di_to_sd) || defined (L_di_to_dd) || defined (L_di_to_td)
192 #elif defined (L_sd_to_usi) || defined (L_dd_to_usi) || defined (L_td_to_usi) \
193 || defined (L_usi_to_sd) || defined (L_usi_to_dd) || defined (L_usi_to_td)
195 #elif defined (L_sd_to_udi) || defined (L_dd_to_udi) || defined (L_td_to_udi) \
196 || defined (L_udi_to_sd) || defined (L_udi_to_dd) || defined (L_udi_to_td)
200 /* If INT_KIND is defined, define additional macros:
202 INT_TYPE: The integer data type.
204 INT_FMT: The format string for writing the integer to a string.
206 CAST_FOR_FMT: Cast variable of INT_KIND to C type for sprintf.
207 This works for ILP32 and LP64, won't for other type size systems.
209 STR_TO_INT: The function to read the integer from a string. */
212 #define INT_TYPE SItype
214 #define CAST_FOR_FMT(A) (int)A
215 #define STR_TO_INT strtol
217 #define INT_TYPE DItype
218 #define INT_FMT "%lld"
219 #define CAST_FOR_FMT(A) (long long)A
220 #define STR_TO_INT strtoll
222 #define INT_TYPE USItype
224 #define CAST_FOR_FMT(A) (unsigned int)A
225 #define STR_TO_INT strtoul
227 #define INT_TYPE UDItype
228 #define INT_FMT "%llu"
229 #define CAST_FOR_FMT(A) (unsigned long long)A
230 #define STR_TO_INT strtoull
233 /* Conversions between decimal float types and binary float types use
234 BFP_KIND to determine the data type and C functions to use. */
236 #if defined (L_sd_to_sf) || defined (L_dd_to_sf) || defined (L_td_to_sf) \
237 || defined (L_sf_to_sd) || defined (L_sf_to_dd) || defined (L_sf_to_td)
239 #elif defined (L_sd_to_df) || defined (L_dd_to_df ) || defined (L_td_to_df) \
240 || defined (L_df_to_sd) || defined (L_df_to_dd) || defined (L_df_to_td)
242 #elif defined (L_sd_to_xf) || defined (L_dd_to_xf ) || defined (L_td_to_xf) \
243 || defined (L_xf_to_sd) || defined (L_xf_to_dd) || defined (L_xf_to_td)
247 /* If BFP_KIND is defined, define additional macros:
249 BFP_TYPE: The binary floating point data type.
251 BFP_FMT: The format string for writing the value to a string.
253 STR_TO_BFP: The function to read the value from a string. */
256 /* strtof is declared in <stdlib.h> only for C99. */
257 extern float strtof (const char *, char **);
258 #define BFP_TYPE SFtype
260 #define STR_TO_BFP strtof
263 #define BFP_TYPE DFtype
265 #define STR_TO_BFP strtod
268 #if LIBGCC2_HAS_XF_MODE
269 /* These aren't used if XF mode is not supported. */
270 #define BFP_TYPE XFtype
272 #define BFP_VIA_TYPE double
273 #define STR_TO_BFP strtod
276 #endif /* BFP_KIND */
278 #if WIDTH == 128 || WIDTH_TO == 128
279 #include "decimal128.h"
281 #if WIDTH == 64 || WIDTH_TO == 64
282 #include "decimal64.h"
284 #if WIDTH == 32 || WIDTH_TO == 32
285 #include "decimal32.h"
287 #include "decNumber.h"
289 /* Names of arithmetic functions. */
292 #define DFP_ADD __addsd3
293 #define DFP_SUB __subsd3
294 #define DFP_MULTIPLY __mulsd3
295 #define DFP_DIVIDE __divsd3
296 #define DFP_EQ __eqsd2
297 #define DFP_NE __nesd2
298 #define DFP_LT __ltsd2
299 #define DFP_GT __gtsd2
300 #define DFP_LE __lesd2
301 #define DFP_GE __gesd2
302 #define DFP_UNORD __unordsd2
304 #define DFP_ADD __adddd3
305 #define DFP_SUB __subdd3
306 #define DFP_MULTIPLY __muldd3
307 #define DFP_DIVIDE __divdd3
308 #define DFP_EQ __eqdd2
309 #define DFP_NE __nedd2
310 #define DFP_LT __ltdd2
311 #define DFP_GT __gtdd2
312 #define DFP_LE __ledd2
313 #define DFP_GE __gedd2
314 #define DFP_UNORD __unorddd2
316 #define DFP_ADD __addtd3
317 #define DFP_SUB __subtd3
318 #define DFP_MULTIPLY __multd3
319 #define DFP_DIVIDE __divtd3
320 #define DFP_EQ __eqtd2
321 #define DFP_NE __netd2
322 #define DFP_LT __lttd2
323 #define DFP_GT __gttd2
324 #define DFP_LE __letd2
325 #define DFP_GE __getd2
326 #define DFP_UNORD __unordtd2
329 /* Names of functions to convert between different decimal float types. */
333 #define DFP_TO_DFP __extendsddd2
334 #elif WIDTH_TO == 128
335 #define DFP_TO_DFP __extendsdtd2
339 #define DFP_TO_DFP __truncddsd2
340 #elif WIDTH_TO == 128
341 #define DFP_TO_DFP __extendddtd2
345 #define DFP_TO_DFP __trunctdsd2
347 #define DFP_TO_DFP __trunctddd2
351 /* Names of functions to convert between decimal float and integers. */
355 #define INT_TO_DFP __floatsisd
356 #define DFP_TO_INT __fixsdsi
358 #define INT_TO_DFP __floatdisd
359 #define DFP_TO_INT __fixsddi
361 #define INT_TO_DFP __floatunssisd
362 #define DFP_TO_INT __fixunssdsi
364 #define INT_TO_DFP __floatunsdisd
365 #define DFP_TO_INT __fixunssddi
369 #define INT_TO_DFP __floatsidd
370 #define DFP_TO_INT __fixddsi
372 #define INT_TO_DFP __floatdidd
373 #define DFP_TO_INT __fixdddi
375 #define INT_TO_DFP __floatunssidd
376 #define DFP_TO_INT __fixunsddsi
378 #define INT_TO_DFP __floatunsdidd
379 #define DFP_TO_INT __fixunsdddi
383 #define INT_TO_DFP __floatsitd
384 #define DFP_TO_INT __fixtdsi
386 #define INT_TO_DFP __floatditd
387 #define DFP_TO_INT __fixtddi
389 #define INT_TO_DFP __floatunssitd
390 #define DFP_TO_INT __fixunstdsi
392 #define INT_TO_DFP __floatunsditd
393 #define DFP_TO_INT __fixunstddi
397 /* Names of functions to convert between decimal float and binary float. */
401 #define BFP_TO_DFP __extendsfsd
402 #define DFP_TO_BFP __truncsdsf
404 #define BFP_TO_DFP __truncdfsd
405 #define DFP_TO_BFP __extendsddf
407 #define BFP_TO_DFP __truncxfsd
408 #define DFP_TO_BFP __extendsdxf
409 #endif /* BFP_KIND */
413 #define BFP_TO_DFP __extendsfdd
414 #define DFP_TO_BFP __truncddsf
416 #define BFP_TO_DFP __extenddfdd
417 #define DFP_TO_BFP __truncdddf
419 #define BFP_TO_DFP __truncxfdd
420 #define DFP_TO_BFP __extendddxf
421 #endif /* BFP_KIND */
425 #define BFP_TO_DFP __extendsftd
426 #define DFP_TO_BFP __trunctdsf
428 #define BFP_TO_DFP __extenddftd
429 #define DFP_TO_BFP __trunctddf
431 #define BFP_TO_DFP __extendxftd
432 #define DFP_TO_BFP __trunctdxf
433 #endif /* BFP_KIND */
437 /* Some handy typedefs. */
439 typedef float SFtype __attribute__ ((mode (SF)));
440 typedef float DFtype __attribute__ ((mode (DF)));
441 #if LIBGCC2_HAS_XF_MODE
442 typedef float XFtype __attribute__ ((mode (XF)));
443 #endif /* LIBGCC2_HAS_XF_MODE */
445 typedef int SItype __attribute__ ((mode (SI)));
446 typedef int DItype __attribute__ ((mode (DI)));
447 typedef unsigned int USItype __attribute__ ((mode (SI)));
448 typedef unsigned int UDItype __attribute__ ((mode (DI)));
450 /* The type of the result of a decimal float comparison. This must
451 match `word_mode' in GCC for the target. */
453 typedef int CMPtype __attribute__ ((mode (word)));
457 #if defined (L_mul_sd) || defined (L_mul_dd) || defined (L_mul_td)
458 extern DFP_C_TYPE DFP_MULTIPLY (DFP_C_TYPE, DFP_C_TYPE);
461 #if defined (L_div_sd) || defined (L_div_dd) || defined (L_div_td)
462 extern DFP_C_TYPE DFP_DIVIDE (DFP_C_TYPE, DFP_C_TYPE);
465 #if defined (L_addsub_sd) || defined (L_addsub_dd) || defined (L_addsub_td)
466 extern DFP_C_TYPE DFP_ADD (DFP_C_TYPE, DFP_C_TYPE);
467 extern DFP_C_TYPE DFP_SUB (DFP_C_TYPE, DFP_C_TYPE);
470 #if defined (L_eq_sd) || defined (L_eq_dd) || defined (L_eq_td)
471 extern CMPtype DFP_EQ (DFP_C_TYPE, DFP_C_TYPE);
474 #if defined (L_ne_sd) || defined (L_ne_dd) || defined (L_ne_td)
475 extern CMPtype DFP_NE (DFP_C_TYPE, DFP_C_TYPE);
478 #if defined (L_lt_sd) || defined (L_lt_dd) || defined (L_lt_td)
479 extern CMPtype DFP_LT (DFP_C_TYPE, DFP_C_TYPE);
482 #if defined (L_gt_sd) || defined (L_gt_dd) || defined (L_gt_td)
483 extern CMPtype DFP_GT (DFP_C_TYPE, DFP_C_TYPE);
486 #if defined (L_le_sd) || defined (L_le_dd) || defined (L_le_td)
487 extern CMPtype DFP_LE (DFP_C_TYPE, DFP_C_TYPE);
490 #if defined (L_ge_sd) || defined (L_ge_dd) || defined (L_ge_td)
491 extern CMPtype DFP_GE (DFP_C_TYPE, DFP_C_TYPE);
494 #if defined (L_unord_sd) || defined (L_unord_dd) || defined (L_unord_td)
495 extern CMPtype DFP_UNORD (DFP_C_TYPE, DFP_C_TYPE);
498 #if defined (L_sd_to_dd) || defined (L_sd_to_td) || defined (L_dd_to_sd) \
499 || defined (L_dd_to_td) || defined (L_td_to_sd) || defined (L_td_to_dd)
500 extern DFP_C_TYPE_TO DFP_TO_DFP (DFP_C_TYPE);
503 #if defined (L_sd_to_si) || defined (L_dd_to_si) || defined (L_td_to_si) \
504 || defined (L_sd_to_di) || defined (L_dd_to_di) || defined (L_td_to_di) \
505 || defined (L_sd_to_usi) || defined (L_dd_to_usi) || defined (L_td_to_usi) \
506 || defined (L_sd_to_udi) || defined (L_dd_to_udi) || defined (L_td_to_udi)
507 extern INT_TYPE DFP_TO_INT (DFP_C_TYPE);
510 #if defined (L_si_to_sd) || defined (L_si_to_dd) || defined (L_si_to_td) \
511 || defined (L_di_to_sd) || defined (L_di_to_dd) || defined (L_di_to_td) \
512 || defined (L_usi_to_sd) || defined (L_usi_to_dd) || defined (L_usi_to_td) \
513 || defined (L_udi_to_sd) || defined (L_udi_to_dd) || defined (L_udi_to_td)
514 extern DFP_C_TYPE INT_TO_DFP (INT_TYPE);
517 #if defined (L_sd_to_sf) || defined (L_dd_to_sf) || defined (L_td_to_sf) \
518 || defined (L_sd_to_df) || defined (L_dd_to_df) || defined (L_td_to_df) \
519 || ((defined (L_sd_to_xf) || defined (L_dd_to_xf) || defined (L_td_to_xf)) \
520 && LIBGCC2_HAS_XF_MODE)
521 extern BFP_TYPE DFP_TO_BFP (DFP_C_TYPE);
524 #if defined (L_sf_to_sd) || defined (L_sf_to_dd) || defined (L_sf_to_td) \
525 || defined (L_df_to_sd) || defined (L_df_to_dd) || defined (L_df_to_td) \
526 || ((defined (L_xf_to_sd) || defined (L_xf_to_dd) || defined (L_xf_to_td)) \
527 && LIBGCC2_HAS_XF_MODE)
528 extern DFP_C_TYPE BFP_TO_DFP (BFP_TYPE);
531 #endif /* _DFPBIT_H */