Warning: This file is not a C or C++ file. It does not have highlighting.

1/*===-- include/flang/Decimal/decimal.h ---------------------------*- C++ -*-===
2 *
3 * Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 * See https://llvm.org/LICENSE.txt for license information.
5 * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 *
7 * ===-----------------------------------------------------------------------===
8 */
9
10/* C and C++ API for binary-to/from-decimal conversion package. */
11
12#ifndef FORTRAN_DECIMAL_DECIMAL_H_
13#define FORTRAN_DECIMAL_DECIMAL_H_
14
15#include "flang/Common/api-attrs.h"
16#include <stddef.h>
17
18#ifdef __cplusplus
19// Binary-to-decimal conversions (formatting) produce a sequence of decimal
20// digit characters in a NUL-terminated user-supplied buffer that constitute
21// a decimal fraction (or zero), accompanied by a decimal exponent that
22// you'll get to adjust and format yourself. There can be a leading sign
23// character.
24// Negative zero is "-0". The result can also be "NaN", "Inf", "+Inf",
25// or "-Inf".
26// If the conversion can't fit in the user-supplied buffer, a null pointer
27// is returned.
28
29#include "binary-floating-point.h"
30namespace Fortran::decimal {
31#endif /* C++ */
32
33enum ConversionResultFlags {
34 Exact = 0,
35 Overflow = 1,
36 Inexact = 2,
37 Invalid = 4,
38 Underflow = 8,
39};
40
41struct ConversionToDecimalResult {
42 const char *str; /* may not be original buffer pointer; null if overflow */
43 size_t length; /* does not include NUL terminator */
44 int decimalExponent; /* assuming decimal point to the left of first digit */
45 enum ConversionResultFlags flags;
46};
47
48/* The "minimize" flag causes the fewest number of output digits
49 * to be emitted such that reading them back into the same binary
50 * floating-point format with RoundNearest will return the same
51 * value.
52 */
53enum DecimalConversionFlags {
54 Minimize = 1, /* Minimize # of digits */
55 AlwaysSign = 2, /* emit leading '+' if not negative */
56};
57
58/*
59 * When allocating decimal conversion output buffers, use the maximum
60 * number of significant decimal digits in the representation of the
61 * least nonzero value, and add this extra space for a sign, a NUL, and
62 * some extra due to the library working internally in base 10**16
63 * and computing its output size in multiples of 16.
64 */
65#define EXTRA_DECIMAL_CONVERSION_SPACE (1 + 1 + 2 * 16 - 1)
66
67#ifdef __cplusplus
68template <int PREC>
69RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal(char *, size_t,
70 DecimalConversionFlags, int digits, enum FortranRounding rounding,
71 BinaryFloatingPointNumber<PREC> x);
72
73extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<8>(
74 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
75 BinaryFloatingPointNumber<8>);
76extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<11>(
77 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
78 BinaryFloatingPointNumber<11>);
79extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<24>(
80 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
81 BinaryFloatingPointNumber<24>);
82extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<53>(
83 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
84 BinaryFloatingPointNumber<53>);
85extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<64>(
86 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
87 BinaryFloatingPointNumber<64>);
88extern template RT_API_ATTRS ConversionToDecimalResult ConvertToDecimal<113>(
89 char *, size_t, enum DecimalConversionFlags, int, enum FortranRounding,
90 BinaryFloatingPointNumber<113>);
91
92template <int PREC> struct ConversionToBinaryResult {
93 BinaryFloatingPointNumber<PREC> binary;
94 enum ConversionResultFlags flags { Exact };
95};
96
97template <int PREC>
98RT_API_ATTRS ConversionToBinaryResult<PREC> ConvertToBinary(const char *&,
99 enum FortranRounding = RoundNearest, const char *end = nullptr);
100
101extern template RT_API_ATTRS ConversionToBinaryResult<8> ConvertToBinary<8>(
102 const char *&, enum FortranRounding, const char *end);
103extern template RT_API_ATTRS ConversionToBinaryResult<11> ConvertToBinary<11>(
104 const char *&, enum FortranRounding, const char *end);
105extern template RT_API_ATTRS ConversionToBinaryResult<24> ConvertToBinary<24>(
106 const char *&, enum FortranRounding, const char *end);
107extern template RT_API_ATTRS ConversionToBinaryResult<53> ConvertToBinary<53>(
108 const char *&, enum FortranRounding, const char *end);
109extern template RT_API_ATTRS ConversionToBinaryResult<64> ConvertToBinary<64>(
110 const char *&, enum FortranRounding, const char *end);
111extern template RT_API_ATTRS ConversionToBinaryResult<113> ConvertToBinary<113>(
112 const char *&, enum FortranRounding, const char *end);
113} // namespace Fortran::decimal
114extern "C" {
115#define NS(x) Fortran::decimal::x
116#else /* C++ */
117#define NS(x) x
118#endif /* C++ */
119
120RT_API_ATTRS struct NS(ConversionToDecimalResult)
121 ConvertFloatToDecimal(char *, size_t, enum NS(DecimalConversionFlags),
122 int digits, enum NS(FortranRounding), float);
123RT_API_ATTRS struct NS(ConversionToDecimalResult)
124 ConvertDoubleToDecimal(char *, size_t, enum NS(DecimalConversionFlags),
125 int digits, enum NS(FortranRounding), double);
126RT_API_ATTRS struct NS(ConversionToDecimalResult)
127 ConvertLongDoubleToDecimal(char *, size_t, enum NS(DecimalConversionFlags),
128 int digits, enum NS(FortranRounding), long double);
129
130RT_API_ATTRS enum NS(ConversionResultFlags)
131 ConvertDecimalToFloat(const char **, float *, enum NS(FortranRounding));
132RT_API_ATTRS enum NS(ConversionResultFlags)
133 ConvertDecimalToDouble(const char **, double *, enum NS(FortranRounding));
134RT_API_ATTRS enum NS(ConversionResultFlags) ConvertDecimalToLongDouble(
135 const char **, long double *, enum NS(FortranRounding));
136#undef NS
137#ifdef __cplusplus
138} // extern "C"
139#endif
140#endif
141

Warning: This file is not a C or C++ file. It does not have highlighting.

source code of flang/include/flang/Decimal/decimal.h