BDE 4.14.0 Production release
Loading...
Searching...
No Matches
bdldfp_decimalimputil.h
Go to the documentation of this file.
1/// @file bdldfp_decimalimputil.h
2///
3/// The content of this file has been pre-processed for Doxygen.
4///
5
6
7// bdldfp_decimalimputil.h -*-C++-*-
8
9#ifndef INCLUDED_BDLDFP_DECIMALIMPUTIL
10#define INCLUDED_BDLDFP_DECIMALIMPUTIL
11
12#include <bsls_ident.h>
13BSLS_IDENT("$Id$")
14
15/// @defgroup bdldfp_decimalimputil bdldfp_decimalimputil
16/// @brief Provide a unified low-level interface for decimal floating point.
17/// @addtogroup bdl
18/// @{
19/// @addtogroup bdldfp
20/// @{
21/// @addtogroup bdldfp_decimalimputil
22/// @{
23///
24/// <h1> Outline </h1>
25/// * <a href="#bdldfp_decimalimputil-purpose"> Purpose</a>
26/// * <a href="#bdldfp_decimalimputil-classes"> Classes </a>
27/// * <a href="#bdldfp_decimalimputil-description"> Description </a>
28/// * <a href="#bdldfp_decimalimputil-usage"> Usage </a>
29/// * <a href="#bdldfp_decimalimputil-example-1-constructing-a-representation-of-a-value-in-decimal"> Example 1: Constructing a Representation of a Value in Decimal </a>
30/// * <a href="#bdldfp_decimalimputil-example-2-adding-two-decimal-floating-point-values"> Example 2: Adding Two Decimal Floating Point Values </a>
31///
32/// # Purpose {#bdldfp_decimalimputil-purpose}
33/// Provide a unified low-level interface for decimal floating point.
34///
35/// # Classes {#bdldfp_decimalimputil-classes}
36///
37/// - bdldfp::DecimalImpUtil: Unified low-level decimal floating point functions.
38///
39/// @see bdldfp_decimalimputil_inteldfp
40///
41/// # Description {#bdldfp_decimalimputil-description}
42/// This component provides a namespace, `bdldfp::DecimalImpUtil`,
43/// containing primitive utilities used in the implementation of a decimal
44/// floating point type (e.g., see @ref bdldfp_decimal ).
45///
46/// ## Usage {#bdldfp_decimalimputil-usage}
47///
48///
49/// This section shows the intended use of this component.
50///
51/// ### Example 1: Constructing a Representation of a Value in Decimal {#bdldfp_decimalimputil-example-1-constructing-a-representation-of-a-value-in-decimal}
52///
53///
54/// A common requirement for decimal floating point types is to be able to
55/// create a value from independent "coefficient" and "exponent" values, where
56/// the resulting decimal has the value `coefficient * 10 ^ exponent`. In the
57/// following example we use such a `coefficient` and `exponent` to create
58/// `Decimal32`, `Decimal64`, and `Decimal128` values.
59///
60/// First we define values representing the `coefficient` and `exponent` (note
61/// the result should be the value 42.5):
62/// @code
63/// int coefficient = 425; // Yet another name for significand
64/// int exponent = -1;
65/// @endcode
66/// Then we call `makeDecimal32`, `makeDecimal64`, and `makeDecimal128` to
67/// construct a `Decimal32`, `Decimal64`, and `Decimal128` respectively.
68/// @code
69/// bdldfp::DecimalImpUtil::ValueType32 d32 =
70/// bdldfp::DecimalImpUtil::makeDecimalRaw32( coefficient, exponent);
71/// bdldfp::DecimalImpUtil::ValueType64 d64 =
72/// bdldfp::DecimalImpUtil::makeDecimalRaw64( coefficient, exponent);
73/// bdldfp::DecimalImpUtil::ValueType128 d128 =
74/// bdldfp::DecimalImpUtil::makeDecimalRaw128(coefficient, exponent);
75///
76/// ASSERT(bdldfp::DecimalImpUtil::equal(
77/// bdldfp::DecimalImpUtil::binaryToDecimal32( 42.5), d32));
78/// ASSERT(bdldfp::DecimalImpUtil::equal(
79/// bdldfp::DecimalImpUtil::binaryToDecimal64( 42.5), d64));
80/// ASSERT(bdldfp::DecimalImpUtil::equal(
81/// bdldfp::DecimalImpUtil::binaryToDecimal128(42.5), d128));
82/// @endcode
83///
84/// ### Example 2: Adding Two Decimal Floating Point Values {#bdldfp_decimalimputil-example-2-adding-two-decimal-floating-point-values}
85///
86///
87/// Decimal floating point values are frequently used in arithmetic computations
88/// where the precise representation of decimal values is of paramount
89/// importance (for example, financial calculations, as currency is typically
90/// denominated in base-10 decimal values). In the following example we
91/// demonstrate computing the sum of a sequence of security prices, where each
92/// price is held in a `DecimalImpUtil::ValueType64` value.
93///
94/// First, we define the signature of a function that computes the sum of an
95/// array of security prices, and returns that sum as a decimal floating point
96/// value:
97/// @code
98/// bdldfp::DecimalImpUtil::ValueType64
99/// totalSecurities(bdldfp::DecimalImpUtil::ValueType64 *prices,
100/// int numPrices)
101/// // Return a Decimal Floating Point number representing the arithmetic
102/// // total of the values specified by 'prices' and 'numPrices'.
103/// {
104/// @endcode
105/// Then, we create a local variable to hold the intermediate sum, and set it to
106/// 0:
107/// @code
108/// bdldfp::DecimalImpUtil::ValueType64 total;
109/// total = bdldfp::DecimalImpUtil::int32ToDecimal64(0);
110/// @endcode
111/// Next, we loop over the array of `prices` and add each price to the
112/// intermediate `total`:
113/// @code
114/// for (int i = 0; i < numPrices; ++i) {
115/// total = bdldfp::DecimalImpUtil::add(total, prices[i]);
116/// }
117/// @endcode
118/// Now, we return the computed total value of the securities:
119/// @code
120/// return total;
121/// }
122/// @endcode
123/// Notice that `add` is called as a function, and is not an operator overload
124/// for `+`; this is because the `bdldfp::DecimalImpUtil` utility is intended to
125/// be used in the implementation of operator overloads on a more full fledged
126/// type.
127///
128/// Finally, we call the function with some sample data, and check the result:
129/// @code
130/// bdldfp::DecimalImpUtil::ValueType64 data[16];
131///
132/// for (int i = 0; i < 16; ++i) {
133/// data[i] = bdldfp::DecimalImpUtil::int32ToDecimal64(i + 1);
134/// }
135///
136/// bdldfp::DecimalImpUtil::ValueType64 result;
137/// result = totalSecurities(data, 16);
138///
139/// bdldfp::DecimalImpUtil::ValueType64 expected;
140///
141/// expected = bdldfp::DecimalImpUtil::int32ToDecimal64(16);
142///
143/// // Totals of values from 1 to 'x' are '(x * x + x) / 2':
144///
145/// expected = bdldfp::DecimalImpUtil::add(
146/// bdldfp::DecimalImpUtil::multiply(expected, expected),
147/// expected);
148/// expected = bdldfp::DecimalImpUtil::divide(
149/// expected,
150/// bdldfp::DecimalImpUtil::int32ToDecimal64(2));
151///
152/// assert(bdldfp::DecimalImpUtil::equal(expected, result));
153/// @endcode
154/// Notice that arithmetic is unwieldy and hard to visualize. This is by
155/// design, as the DecimalImpUtil and subordinate components are not intended
156/// for public consumption, or direct use in decimal arithmetic.
157/// @}
158/** @} */
159/** @} */
160
161/** @addtogroup bdl
162 * @{
163 */
164/** @addtogroup bdldfp
165 * @{
166 */
167/** @addtogroup bdldfp_decimalimputil
168 * @{
169 */
170
171#include <bdlscm_version.h>
172
178#include <bdldfp_uint128.h>
179
180#include <bslmf_assert.h>
181
182#include <bsls_assert.h>
183#include <bsls_keyword.h>
184#include <bsls_types.h>
185
186#include <bsl_algorithm.h>
187#include <bsl_cmath.h>
188#include <bsl_c_errno.h>
189#include <bsl_iostream.h>
190
191#ifndef BDE_DONT_ALLOW_TRANSITIVE_INCLUDES
192#include <bsl_c_signal.h> // Formerly transitively included via decContext.h
193#endif // BDE_DONT_ALLOW_TRANSITIVE_INCLUDES
194
195#ifdef BDLDFP_DECIMALPLATFORM_SOFTWARE
196
197 // DECIMAL FLOATING-POINT LITERAL EMULATION
198
199
200#define BDLDFP_DECIMALIMPUTIL_DF(lit) \
201 BloombergLP::bdldfp::DecimalImpUtil::parse32( \
202 (BloombergLP::bdldfp::DecimalImpUtil::checkLiteral(lit), #lit))
203
204#define BDLDFP_DECIMALIMPUTIL_DD(lit) \
205 BloombergLP::bdldfp::DecimalImpUtil::parse64( \
206 (BloombergLP::bdldfp::DecimalImpUtil::checkLiteral(lit), #lit))
207
208#define BDLDFP_DECIMALIMPUTIL_DL(lit) \
209 BloombergLP::bdldfp::DecimalImpUtil::parse128( \
210 (BloombergLP::bdldfp::DecimalImpUtil::checkLiteral(lit), #lit))
211
212#elif defined(BDLDFP_DECIMALPLATFORM_C99_TR) || defined( __IBM_DFP__ )
213
214#define BDLDFP_DECIMALIMPUTIL_JOIN_(a,b) a##b
215
216 // Portable decimal floating-point literal support
217
218#define BDLDFP_DECIMALIMPUTIL_DF(lit) BDLDFP_DECIMALIMPUTIL_JOIN_(lit,df)
219
220#define BDLDFP_DECIMALIMPUTIL_DD(lit) BDLDFP_DECIMALIMPUTIL_JOIN_(lit,dd)
221
222#define BDLDFP_DECIMALIMPUTIL_DL(lit) BDLDFP_DECIMALIMPUTIL_JOIN_(lit,dl)
223
224#endif
225
226
227
228namespace bdldfp {
229
230 // ====================
231 // class DecimalImpUtil
232 // ====================
233
234/// This `struct` provides a namespace for utility functions that implement
235/// core decimal floating-poing operations.
236///
237/// See @ref bdldfp_decimalimputil
239
240 private:
241#if defined(BDLDFP_DECIMALPLATFORM_INTELDFP)
242 typedef DecimalImpUtil_IntelDfp Imp;
243#else
244 BDLDFP_DECIMALPLATFORM_COMPILER_ERROR;
245#endif
246
247 public:
248 // TYPES
249 typedef Imp::ValueType32 ValueType32;
250 typedef Imp::ValueType64 ValueType64;
251 typedef Imp::ValueType128 ValueType128;
252
253 enum {
254 // Status flag bitmask for numeric operations.
255
256 k_STATUS_INEXACT = Imp::k_STATUS_INEXACT,
257 k_STATUS_UNDERFLOW = Imp::k_STATUS_UNDERFLOW,
258 k_STATUS_OVERFLOW = Imp::k_STATUS_OVERFLOW
259 };
260
261 // CLASS METHODS
262
263 static ValueType64 makeDecimal64( int significand,
264 int exponent);
265 static ValueType64 makeDecimal64(unsigned int significand,
266 int exponent);
267 static ValueType64 makeDecimal64( long long int significand,
268 int exponent);
269 /// Return a `Decimal64` object that has the specified `significand` and
270 /// `exponent`, rounded according to the current decimal rounding mode,
271 /// if necessary. If an overflow condition occurs, store the value of
272 /// the macro `ERANGE` into `errno` and return infinity with the
273 /// appropriate sign.
274 static ValueType64 makeDecimal64(unsigned long long int significand,
275 int exponent);
276
277 /// Return a `ValueType64` representing infinity. Optionally specify
278 /// whether the infinity `isNegative`. If `isNegative` is `false` or is
279 /// is not supplied, the returned value will be infinity, and negative
280 /// infinity otherwise.
281 static ValueType64 makeInfinity64(bool isNegative = false);
282
283#ifdef BDLDFP_DECIMALPLATFORM_SOFTWARE
284
285 // Literal Checking Functions
286
287 /// This `struct` is a helper type used to generate error messages for
288 /// bad literals.
289 struct This_is_not_a_floating_point_literal {};
290
291 /// Generate an error if the specified `t` is bad decimal
292 /// floating-point. Note that this function is intended for use with
293 /// literals
294 template <class TYPE>
295 static void checkLiteral(const TYPE& t);
296
297 /// Overload to avoid an error when the decimal floating-point literal
298 /// (without the suffix) can be interpreted as a `double` literal.
299 static void checkLiteral(double);
300
301#elif defined(BDLDFP_DECIMALPLATFORM_HARDWARE)
302
303#else
304
305#error Improperly configured decimal floating point platform settings
306
307#endif
308 // classify
309
310 /// Return the integer value that respresents the floating point
311 /// classification of the specified `x` value as follows:
312 ///
313 /// * if `x` is NaN, return FP_NAN;
314 /// * otherwise if `x` is positive or negative infinity, return
315 /// `FP_INFINITE`;
316 /// * otherwise if `x` is a subnormal value, return `FP_SUBNORMAL`
317 /// * otherwise if `x` is a zero value, return `FP_ZERO`
318 /// * otherwise return `FP_NORMAL`
319 ///
320 static int classify(ValueType32 x);
321 static int classify(ValueType64 x);
322 /// Note that the mention `FP_XXX` constants are C99 standard macros and
323 /// they are defined in the math.h (cmath) standard header. On systems
324 /// that fail to define those standard macros we define the in this
325 /// component as public macros.
326 static int classify(ValueType128 x);
327
328
329 // normalize
330
331 /// Return a `ValueTypeXX` number having the value as the specified
332 /// 'original, but with the significand, that can not be divided by ten,
333 /// and appropriate exponent.
334 ///
337 /// * Any representations of zero value (either positive or negative)
338 /// are normalized to positive zero having null significand and
339 /// exponent.
340 /// * Any NaN values (either signaling or quiet) are normalized to
341 /// quiet NaN.
342 /// * Normalized non-zero value has the same sign as the original one.
344
345 // Quantum functions
346
347 static ValueType32 quantize(ValueType32 value, ValueType32 exponent);
348 static ValueType64 quantize(ValueType64 value, ValueType64 exponent);
349 /// Return a number equal to the specified `value` (except for possible
350 /// rounding) having the exponent equal to the exponent of the specified
351 /// `exponent`. Rounding may occur when the exponent is greater than
352 /// the quantum of `value`. E.g., `quantize(147e-2_d32, 1e-1_d32)`
353 /// yields `15e-1_d32`. In the opposite direction, if `exponent` is
354 /// sufficiently less than the quantum of `value`, it may not be
355 /// possible to construct the requested result, and if so, `NaN` is
356 /// returned. E.g., `quantize(1234567e0_d32, 1e-1_d32)` returns `NaN`.
357 static ValueType128 quantize(ValueType128 value, ValueType128 exponent);
358
359 static ValueType32 quantize(ValueType32 value, int exponent);
360 static ValueType64 quantize(ValueType64 value, int exponent);
361 /// Return a number equal to the specified `value` (except for possible
362 /// rounding) having the specified `exponent`. Rounding may occur when
363 /// `exponent` is greater than the quantum of `value`. E.g.,
364 /// `quantize(147e-2_d32, -1)` yields `15e-1_d32`. In the opposite
365 /// direction, if `exponent` is sufficiently less than the quantum of
366 /// `value`, it may not be possible to construct the requested result,
367 /// and if so, `NaN` is returned. E.g., `quantize(1234567e0_d32, -1)`
368 /// returns `NaN`. Behavior is undefined unless the `exponent`
369 /// satisfies the following conditions
370 /// * for `Decimal32` type: `-101 <= exponent <= 90`
371 /// * for `Decimal64` type: `-398 <= exponent <= 369`
372 /// * for `Decimal128` type: `-6176 <= exponent <= 6111`
373 static ValueType128 quantize(ValueType128 value, int exponent);
374
375 /// If a floating-point number equal to the specified `y` and having the
376 /// specified `exponent` can be constructed, set that value into the
377 /// specified `x` and return 0. Otherwise, or if `y` is NaN or
378 /// infinity, leave the contents of `x` unchanged and return a non-zero
379 /// value. The behavior is undefined unless `exponent` satisfies the
380 /// following conditions
381 /// * for `Decimal32` type: `-101 <= exponent <= 90`
382 /// * for `Decimal64` type: `-398 <= exponent <= 369`
383 /// * for `Decimal128` type: `-6176 <= exponent <= 6111`
384 ///
385 static int quantizeEqual(ValueType32 *x, ValueType32 y, int exponent);
386 static int quantizeEqual(ValueType64 *x, ValueType64 y, int exponent);
387 /// Example:
388 /// `Decimal32 x;`
389 /// `BSLS_ASSERT(0 == quantizeEqual(&x, 123e+3_d32, 2);`
390 /// `BSLS_ASSERT(1230e+2_d32 == x);`
391 /// `BSLS_ASSERT(0 != quantizeEqual(&x, 123e+3_d32, -2);`
392 /// `BSLS_ASSERT(1230e+2_d32 == x);`
393 static int quantizeEqual(ValueType128 *x, ValueType128 y, int exponent);
394
395 static bool sameQuantum(ValueType32 x, ValueType32 y);
396 static bool sameQuantum(ValueType64 x, ValueType64 y);
397 /// Return `true` if the specified `x` and `y` values have the same
398 /// quantum exponents, and `false` otherwise. If both arguments are NaN
399 /// or both arguments are infinity, they have the same quantum
400 /// exponents. Note that if exactly one operand is NaN or exactly one
401 /// operand is infinity, they do not have the same quantum exponents.
402 static bool sameQuantum(ValueType128 x, ValueType128 y);
403
404 // compose and decompose
405
406 //static ValueType32 composeDecimal32 (DecimalTriple triple);
407 //static ValueType64 composeDecimal64 (DecimalTriple triple);
408 //static ValueType128 composeDecimal128(DecimalTriple triple);
409 // Return a 'ValueTypeXX' number having the value as specified by the
410 // salient attributes of the specified 'triple'. The behavior is
411 // undefined if the 'significand' has too many decimal digits for
412 // 'ValueType', or the 'exponent' is too large for 'ValueType'
413
414 /// Decompose the specified decimal `value` into the components of
415 /// the decimal floating-point format and load the result into the
416 /// specified `sign`, `significand` and `exponent` such that
417 /// `value` is equal to `sign * significand * (10 ** exponent)`.
418 /// The special values infinity and NaNs are decomposed to `sign`,
419 /// `exponent` and `significand` parts, even though they don't have
420 /// their normal meaning (except `sign`). That is those specific values
421 /// cannot be restored using these parts, unlike the finite ones.
422 /// Return the integer value that represents the floating point
423 /// classification of the specified `value` as follows:
424 ///
425 /// * if `value` is NaN, return FP_NAN;
426 /// * if `value` is infinity, return `FP_INFINITE`;
427 /// * if `value` is a subnormal value, return `FP_SUBNORMAL`;
428 /// * if `value` is a zero value, return `FP_ZERO`;
429 /// * otherwise return `FP_NORMAL`.
430 ///
431 static int decompose(int *sign,
432 unsigned int *significand,
433 int *exponent,
434 ValueType32 value);
435 static int decompose(int *sign,
436 bsls::Types::Uint64 *significand,
437 int *exponent,
438 ValueType64 value);
439 /// Note that a decomposed representation may not be unique,
440 /// for example 10 can be represented as either `10 * (10 ** 0)`
441 /// or `1 * (10 ** 1)`. The returned `significand` and `exponent`
442 /// reflect the encoded representation of `value` (i.e., they
443 /// reflect the `quantum` of `value`).
444 static int decompose(int *sign,
445 Uint128 *significand,
446 int *exponent,
447 ValueType128 value);
448
449 // Format functions
450
451 static int format(char *buffer,
452 int length,
453 ValueType32 value,
454 const DecimalFormatConfig& cfg);
455
456 static int format(char *buffer,
457 int length,
458 ValueType64 value,
459 const DecimalFormatConfig& cfg);
460
461 /// Format the specified `value`, according to the parameters in the
462 /// specified `cfg`. Place the output in the buffer designated by the
463 /// specified `buffer` and `length`, and return the length of the
464 /// formatted value. If there is insufficient room in the buffer, its
465 /// contents will be left in an unspecified state, with the returned
466 /// value indicating the necessary size. This function does not write
467 /// a terminating null character. If `length` is not positive, `buffer`
468 /// is permitted to be null. This can be used to determine the
469 /// necessary buffer size. See the Attributes section under
470 /// @DESCRIPTION in the component-level documentation for
471 /// `bdldfp::DecimalFormatConfig` component for information on the
472 /// configuration attributes.
473 ///
474 /// Note that for some combinations of `value` and precision provided by
475 /// `cfg` object, the number being written must first be rounded to
476 /// fewer digits than it initially contains. The number written must be
477 /// as close as possible to the initial value given the constraints on
478 /// precision. The rounding should be done as "round-half-up", i.e.,
479 /// round up in magnitude when the first of the discarded digits is
480 /// between 5 and 9.
481 ///
482 /// Also note that if the configuration format attribute `style` is
483 /// `e_NATURAL` then all significand digits of the `value` are output in
484 /// the buffer regardless of the value specified in configuration's
485 /// `precision` attribute.
486 static int format(char *buffer,
487 int length,
488 ValueType128 value,
489 const DecimalFormatConfig& cfg);
490
491 // Integer construction
492
493 static ValueType32 int32ToDecimal32( int value);
494 static ValueType32 uint32ToDecimal32(unsigned int value);
495 static ValueType32 int64ToDecimal32( long long int value);
496
497 /// Return a `Decimal32` object having the value closest to the
498 /// specified `value` following the conversion rules as defined by
499 /// IEEE-754:
500 ///
501 /// * If `value` is zero then initialize this object to a zero with an
502 /// unspecified sign and an unspecified exponent.
503 /// * Otherwise if `value` has a value that is not exactly
504 /// representable using `std::numeric_limits<Decimal32>::max_digit`
505 /// decimal digits then return a decimal value initialized to the
506 /// value of `value` rounded according to the rounding direction.
507 /// * Otherwise initialize this object to the value of the `value`.
508 ///
509 static ValueType32 uint64ToDecimal32(unsigned long long int value);
510
511 static ValueType64 int32ToDecimal64( int value);
512 static ValueType64 uint32ToDecimal64(unsigned int value);
513 /// The exponent 0 (quantum 1e-6) is preferred during conversion unless
514 /// it would cause unnecessary loss of precision.
515 static ValueType64 int64ToDecimal64( long long int value);
516
517 /// Return a `Decimal64` object having the value closest to the
518 /// specified `value` following the conversion rules as defined by
519 /// IEEE-754:
520 ///
521 /// * If `value` is zero then initialize this object to a zero with an
522 /// unspecified sign and an unspecified exponent.
523 /// * Otherwise if `value` has a value that is not exactly
524 /// representable using `std::numeric_limits<Decimal64>::max_digit`
525 /// decimal digits then return a decimal value initialized to the
526 /// value of `value` rounded according to the rounding direction.
527 /// * Otherwise initialize this object to the value of the `value`.
528 ///
529 static ValueType64 uint64ToDecimal64(unsigned long long int value);
530
531 static ValueType128 int32ToDecimal128( int value);
532 static ValueType128 uint32ToDecimal128(unsigned int value);
533 /// The exponent 0 (quantum 1e-15) is preferred during conversion unless
534 /// it would cause unnecessary loss of precision.
535 static ValueType128 int64ToDecimal128( long long int value);
536
537 /// Return a `Decimal128` object having the value closest to the
538 /// specified `value` subject to the conversion rules as defined by
539 /// IEEE-754:
540 ///
541 /// * If `value` is zero then initialize this object to a zero with an
542 /// unspecified sign and an unspecified exponent.
543 /// * Otherwise if `value` has a value that is not exactly
544 /// representable using `std::numeric_limits<Decimal128>::max_digit`
545 /// decimal digits then return a decimal value initialized to the
546 /// value of `value` rounded according to the rounding direction.
547 /// * Otherwise initialize this object to `value`.
548 ///
549 /// The exponent 0 (quantum 1e-33) is preferred during conversion unless
550 /// it would cause unnecessary loss of precision.
551 static ValueType128 uint64ToDecimal128(unsigned long long int value);
552
553 // Arithmetic
554
555 // Addition functions
556
557 /// Add the value of the specified `rhs` to the value of the specified
558 /// `lhs` as described by IEEE-754 and return the result.
559 ///
560 static ValueType32 add(ValueType32 lhs, ValueType32 rhs);
561 static ValueType64 add(ValueType64 lhs, ValueType64 rhs);
562 /// * If either of `lhs` or `rhs` is signaling NaN, then store the
563 /// value of the macro `EDOM` into `errno` and return a NaN.
564 /// * Otherwise if either of `lhs` or `rhs` is NaN, return a NaN.
565 /// * Otherwise if `lhs` and `rhs` are infinities of differing signs,
566 /// store the value of the macro `EDOM` into `errno` and return a
567 /// NaN.
568 /// * Otherwise if `lhs` and `rhs` are infinities of the same sign then
569 /// return infinity of that sign.
570 /// * Otherwise if `rhs` is zero (positive or negative), return `lhs`.
571 /// * Otherwise if the sum of `lhs` and `rhs` has an absolute value
572 /// that is larger than the maximum value supported by the indicated
573 /// result type then store the value of the macro `ERANGE` into
574 /// `errno` and return infinity with the same sign as that result.
575 /// * Otherwise return the sum of the number represented by `lhs` and
576 /// the number represented by `rhs`.
577 static ValueType128 add(ValueType128 lhs, ValueType128 rhs);
578
579 // Subtraction functions
580
581 /// Subtract the value of the specified `rhs` from the value of the
582 /// specified `lhs` as described by IEEE-754 and return the result.
583 ///
586 /// * If either of `lhs` or `rhs` is signaling NaN, then store the
587 /// value of the macro `EDOM` into `errno` and return a NaN.
588 /// * Otherwise if either of `lhs` or `rhs` is NaN, return a NaN.
589 /// * Otherwise if `lhs` and the `rhs` have infinity values of the same
590 /// sign, store the value of the macro `EDOM` into `errno` and return
591 /// a NaN.
592 /// * Otherwise if `lhs` and the `rhs` have infinity values of
593 /// differing signs, then return `lhs`.
594 /// * Otherwise if `rhs` has a zero value (positive or negative), then
595 /// return `lhs`.
596 /// * Otherwise if the subtracting of `lhs` and `rhs` has an absolute
597 /// value that is larger than the maximum value supported by the
598 /// indicated result type then store the value of the macro `ERANGE`
599 /// into `errno` and return infinity with the same sign as that
600 /// result.
601 /// * Otherwise return the result of subtracting the value of `rhs`
602 /// from the value of `lhs`.
604
605 // Multiplication functions
606
607 /// Multiply the value of the specified `lhs` object by the value of the
608 /// specified `rhs` as described by IEEE-754 and return the result.
609 ///
612 /// * If either of `lhs` or `rhs` is signaling NaN, then store the
613 /// value of the macro `EDOM` into `errno` and return a NaN.
614 /// * Otherwise if either of `lhs` or `rhs` is NaN, return a NaN.
615 /// * Otherwise if one of the operands is infinity (positive or
616 /// negative) and the other is zero (positive or negative), then
617 /// store the value of the macro `EDOM` into `errno` and return a
618 /// NaN.
619 /// * Otherwise if both `lhs` and `rhs` are infinity (positive or
620 /// negative), return infinity. The sign of the returned value will
621 /// be positive if `lhs` and `rhs` have the same sign, and negative
622 /// otherwise.
623 /// * Otherwise, if either `lhs` or `rhs` is zero, return zero. The
624 /// sign of the returned value will be positive if `lhs` and `rhs`
625 /// have the same sign, and negative otherwise.
626 /// * Otherwise if the product of `lhs` and `rhs` has an absolute value
627 /// that is larger than the maximum value of the indicated result
628 /// type then store the value of the macro `ERANGE` into `errno` and
629 /// return infinity with the same sign as that result.
630 /// * Otherwise if the product of `lhs` and `rhs` has an absolute value
631 /// that is smaller than min value of the indicated result type then
632 /// store the value of the macro `ERANGE` into `errno` and return
633 /// zero with the same sign as that result.
634 /// * Otherwise return the product of the value of `rhs` and the number
635 /// represented by `rhs`.
637
638 // Division functions
639
640 /// Divide the value of the specified `lhs` by the value of the
641 /// specified `rhs` as described by IEEE-754, and return the result.
642 ///
643 static ValueType32 divide(ValueType32 lhs, ValueType32 rhs);
644 static ValueType64 divide(ValueType64 lhs, ValueType64 rhs);
645 /// * If either of `lhs` or `rhs` is signaling NaN, then store the
646 /// value of the macro `EDOM` into `errno` and return a NaN.
647 /// * Otherwise if either of `lhs` or `rhs` is NaN, return a NaN.
648 /// * Otherwise if `lhs` and `rhs` are both infinity (positive or
649 /// negative) or both zero (positive or negative) then store the
650 /// value of the macro `EDOM` into `errno` and return a NaN.
651 /// * Otherwise if `lhs` has a normal value and `rhs` has a positive
652 /// zero value, store the value of the macro `ERANGE` into `errno`
653 /// and return infinity with the sign of `lhs`.
654 /// * Otherwise if `lhs` has a normal value and `rhs` has a negative
655 /// zero value, store the value of the macro `ERANGE` into `errno`
656 /// and return infinity with the opposite sign as `lhs`.
657 /// * Otherwise if dividing the value of `lhs` by the value of `rhs`
658 /// results in an absolute value that is larger than the maximum
659 /// value supported by the result type then store the value of the
660 /// macro `ERANGE` into `errno` and return infinity with the same
661 /// sign as that result.
662 /// * Otherwise if dividing the value of `lhs` by the value of `rhs`
663 /// results in an absolute value that is smaller than min value
664 /// supported by the indicated result type then store the value of
665 /// the macro `ERANGE` into `errno`and return zero with the same sign
666 /// as that result.
667 /// * Otherwise return the result of dividing the value of `lhs` by the
668 /// value of `rhs`.
670
671 // Math functions
672
673 /// Return a decimal value with the magnitude of the specifed `x` and
674 /// the sign of the specified `y`. If `x` is NaN, then NaN with the
675 /// sign of `y` is returned.
676 ///
679 /// Examples: `copysign( 5.0, -2.0)` ==> -5.0;
680 /// `copysign(-5.0, -2.0)` ==> -5.0
682
683 /// Return `e` (Euler's number, 2.7182818) raised to the specified power
684 /// `x`.
685 ///
686 static ValueType32 exp(ValueType32 x);
687 static ValueType64 exp(ValueType64 x);
688 /// Special value handling:
689 /// * If `x` is +/-0, 1 is returned.
690 /// * If `x` is negative infinity, +0 is returned.
691 /// * If `x` is +infinity, +infinity is returned.
692 /// * If `x` is quiet NaN, quiet NaN is returned.
693 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
694 /// the macro `EDOM` is stored into `errno`.
695 /// * If `x` is finite, but the result value is outside the range of
696 /// the return type, store the value of the macro `ERANGE` into
697 /// `errno` and +infinity value is returned.
698 static ValueType128 exp(ValueType128 x);
699
700 /// Return the natural (base `e`) logarithm of the specified `x`.
701 ///
702 static ValueType32 log(ValueType32 x);
703 static ValueType64 log(ValueType64 x);
704 /// Special value handling:
705 /// * If `x` is +/-0, -infinity is returned and the value of the macro
706 /// `ERANGE` is stored into `errno`.
707 /// * If `x` is 1, +0 is returned.
708 /// * If `x` is negative, quiet NaN is returned and the value of the
709 /// macro `EDOM` is stored into `errno`.
710 /// * If `x` is +infinity, +infinity is returned.
711 /// * If `x` is quiet NaN, quiet NaN is returned.
712 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
713 /// the macro `EDOM` is stored into `errno`.
714 static ValueType128 log(ValueType128 x);
715
716 /// Return the FLT_RADIX-based logarithm (i.e., base 10) of the absolute
717 /// value of the specified `x`.
718 ///
719 /// Special value handling:
720 /// * If `x` is +/-0, -infinity is returned and the value of the macro
721 /// `ERANGE` is stored into `errno`.
722 /// * If `x` is 1, +0 is returned.
723 /// * If `x` is +/-infinity, +infinity is returned.
724 /// * If `x` is quiet NaN, quiet NaN is returned.
725 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
726 /// the macro `EDOM` is stored into `errno`.
727 ///
728 static ValueType32 logB(ValueType32 x);
729 static ValueType64 logB(ValueType64 x);
730 /// Examples: `logB( 10.0)` ==> 1.0;
731 /// `logB(-100.0)` ==> 2.0
733
734 /// Return the common (base-10) logarithm of the specified `x`.
735 ///
736 static ValueType32 log10(ValueType32 x);
737 static ValueType64 log10(ValueType64 x);
738 /// Special value handling:
739 /// * If `x` is +/-0, -infinity is returned and the value of the macro
740 /// `ERANGE` is stored into `errno`.
741 /// * If `x` is 1, +0 is returned.
742 /// * If `x` is negative, quiet NaN is returned and the value of the
743 /// macro `EDOM` is stored into `errno`.
744 /// * If `x` is +infinity, +infinity is returned.
745 /// * If `x` is quiet NaN, quiet NaN is returned.
746 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
747 /// the macro `EDOM` is stored into `errno`.
749
750 /// Return the remainder of the division of the specified `x` by the
751 /// specified `y`. The returned value has the same sign as `x` and is
752 /// less than `y` in magnitude.
753 ///
756 /// Special value handling:
757 /// * If either argument is quiet NaN, quiet NaN is returned.
758 /// * If either argument is signaling NaN, quiet NaN is returned, and
759 /// the value of the macro `EDOM` is stored into `errno`.
760 /// * If `x` is +/-infnity and `y` is not NaN, quiet NaN is returned
761 /// and the value of the macro `EDOM` is stored into `errno`.
762 /// * If `x` is +/-0 and `y` is not zero, +/-0 is returned.
763 /// * If `y` is +/-0, quite NaN is returned and the value of the macro
764 /// `EDOM` is stored into `errno`.
765 /// * If `x` is finite and `y` is +/-infnity, `x` is returned.
767
768 /// Return the remainder of the division of the specified `x` by the
769 /// specified `y`. The remainder of the division operation `x/y`
770 /// calculated by this function is exactly the value `x - n*y`, where
771 /// `n` s the integral value nearest the exact value `x/y`. When
772 /// `|n - x/y| == 0.5`, the value `n` is chosen to be even. Note that
773 /// in contrast to `DecimalImpUtil::fmod()`, the returned value is not
774 /// guaranteed to have the same sign as `x`.
775 ///
779
780 static long int lrint(ValueType32 x);
781 static long int lrint(ValueType64 x);
782 /// Special value handling:
783 /// * The current rounding mode has no effect.
784 /// * If either argument is quiet NaN, quiet NaN is returned.
785 /// * If either argument is signaling NaN, quiet NaN is returned, and
786 /// the value of the macro `EDOM` is stored into `errno`.
787 /// * If `y` is +/-0, quiet NaN is returned and the value of the macro
788 /// `EDOM` is stored into `errno`.
789 /// * If `x` is +/-infnity and `y` is not NaN, quiet NaN is returned
790 /// and the value of the macro `EDOM` is stored into `errno`.
791 /// * If `x` is finite and `y` is +/-infnity, `x` is returned.
792 static long int lrint(ValueType128 x);
793
794 static long long int llrint(ValueType32 x);
795 static long long int llrint(ValueType64 x);
796 static long long int llrint(ValueType128 x);
797
800 /// Return an integer value nearest to the specified `x`. Round `x`
801 /// using the current rounding mode. If `x` is +/-infnity, NaN (either
802 /// signaling or quiet) or the rounded value is outside the range of the
803 /// return type, store the value of the macro `EDOM` into `errno` and
804 /// return implementation-defined value.
806
807 /// Return the next representable value of the specified `from` in the
808 /// direction of the specified `to`.
809 ///
812 /// Special value handling:
813 /// * If `from` equals `to`, `to` is returned.
814 /// * If either argument is quiet NaN, quiet NaN is returned.
815 /// * If either argument is signaling NaN, quiet NaN is returned and
816 /// the value of the macro `EDOM` is stored into `errno`.
817 /// * If `from` is finite, but the expected result is infinity,
818 /// infinity is returned and the value of the macro `ERANGE` is
819 /// stored into `errno`.
820 /// * If `from` does not equal `to` and the result is subnormal or
821 /// zero, the value of the macro `ERANGE` is stored into `errno`.
823
824 /// Return the value of the specified `base` raised to the power of the
825 /// specified `exp`.
826 ///
827 static ValueType32 pow(ValueType32 base, ValueType32 exp);
828 static ValueType64 pow(ValueType64 base, ValueType64 exp);
829 /// Special value handling:
830 /// * If `base` is finite and negative and `exp` is finite and
831 /// non-integer, quiet NaN is returned and the value of the macro
832 /// `EDOM` is stored into `errno`.
833 /// * If the mathematical result of this function is infinity or
834 /// undefined or a range error due to overflow occurs, infinity is
835 /// returned and the value of the macro `ERANGE` is stored into
836 /// `errno`.
837 /// * If a range error occurs due to underflow, the correct result
838 /// (after rounding) is returned and the value of the macro `ERANGE`
839 /// is stored into `errno`.
840 /// * If either argument is signaling NaN, quiet NaN is returned and
841 /// the value of the macro `EDOM` is stored into `errno`.
842 static ValueType128 pow(ValueType128 base, ValueType128 exp);
843
844 /// Return the smallest integral value that is not less than the
845 /// specified `x`.
846 ///
847 /// Special value handling:
848 /// * if `x` is quiet NaN, quiet NaN is returned.
849 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
850 /// the macro `EDOM` is stored into `errno`.
851 /// * if `x` is +/-infinity or +/-0, it is returned unmodified.
852 ///
853 static ValueType32 ceil(ValueType32 x);
854 static ValueType64 ceil(ValueType64 x);
855 /// Examples: `ceil(0.5)` ==> 1.0; `ceil(-0.5)` ==> 0.0
857
858 /// Return the largest integral value that is not greater than the
859 /// specified `x`.
860 ///
861 /// Special value handling:
862 /// * if `x` is quiet NaN, quiet NaN is returned.
863 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
864 /// the macro `EDOM` is stored into `errno`.
865 /// * if `x` is +/-infinity or +/-0, it is returned unmodified.
866 ///
867 static ValueType32 floor(ValueType32 x);
868 static ValueType64 floor(ValueType64 x);
869 /// Examples: `floor(0.5)` ==> 0.0; `floor(-0.5)` ==> -1.0
871
872 /// Return the integral value nearest to the specified `x`. Round
873 /// halfway cases away from zero, regardless of the current decimal
874 /// floating point rounding mode.
875 ///
876 /// Special value handling:
877 /// * if `x` is quiet NaN, quiet NaN is returned.
878 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
879 /// the macro `EDOM` is stored into `errno`.
880 /// * if `x` is +/-infinity or +/-0, it is returned unmodified.
881 ///
882 static ValueType32 round(ValueType32 x);
883 static ValueType64 round(ValueType64 x);
884 /// Examples: `round(0.5)` ==> 1.0; `round(-0.5)` ==> -1.0
886
887 /// Return the integral value nearest to the specified `x`. Round
888 /// halfway cases away from zero, regardless of the current decimal
889 /// floating point rounding mode.
890 ///
891 /// Special value handling:
892 /// * if `x` is NaN (either quiet or signaling), quiet NaN is returned
893 /// and the value of the macro `EDOM` is stored into `errno`.
894 /// * if `x` is +/-infinity, quite NaN is returned and the value of the
895 /// macro `EDOM` is stored into `errno`.
896 /// * If the result of the rounding is outside the range of the return
897 /// type, the macro `EDOM` is stored into `errno`.
898 ///
899 static long int lround(ValueType32 x);
900 static long int lround(ValueType64 x);
901 /// Examples: `lround(0.5)` ==> 1.0; `lround(-0.5)` ==> -1.0
902 static long int lround(ValueType128 x);
903
904 /// Return the specified `x` value rounded to the specified `precision`.
905 /// Round halfway cases away from zero, regardless of the current
906 /// decimal floating point rounding mode. If `x` is integral, positive
907 /// zero, negative zero, NaN, or infinity then return `x` itself.
908 ///
909 static ValueType32 round(ValueType32 x, unsigned int precision);
910 static ValueType64 round(ValueType64 x, unsigned int precision);
911 /// Examples: `round(3.14159, 3)` ==> 3.142
912 static ValueType128 round(ValueType128 x, unsigned int precision);
913
914
915 /// Return the nearest integral value that is not greater in absolute
916 /// value than the specified `x`.
917 ///
918 /// Special value handling:
919 /// * if `x` is quiet NaN, quiet NaN is returned.
920 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
921 /// the macro `EDOM` is stored into `errno`.
922 /// * if `x` is +/-infinity or +/-0, it is returned unmodified.
923 ///
924 static ValueType32 trunc(ValueType32 x);
925 static ValueType64 trunc(ValueType64 x);
926 /// Examples: `trunc(0.5)` ==> 0.0; `trunc(-0.5)` ==> 0.0
928
929 /// Return, using the specified `x`, `y`, and `z`, the value of the
930 /// expression `x * y + z`, rounded as one ternary operation according
931 /// to the current decimal floating point rounding mode.
932 ///
935 /// Special value handling:
936 /// * If `x` or `y` are quiet NaN, quiet NaN is returned.
937 /// * If any argument is signaling NaN, quiet NaN is returned and the
938 /// value of the macro `EDOM` is stored into `errno`.
939 /// * If `x*y` is an exact infinity and `z` is infinity with the
940 /// opposite sign, quiet NaN is returned and the value of the macro
941 /// `EDOM` is stored into `errno`.
942 /// * If `x` is zero and `y` is infinite or if `x` is infinite and `y`
943 /// is zero, and `z` is not a NaN, then quiet NaN is returned and the
944 /// value of the macro `EDOM` is stored into `errno`.
945 /// * If `x` is zero and `y` is infinite or if `x` is infinite and `y`
946 /// is zero, and `z` is NaN, then quiet NaN is returned.
948
949 /// Return the absolute value of the specified `x`.
950 ///
951 static ValueType32 fabs(ValueType32 x);
952 static ValueType64 fabs(ValueType64 x);
953 /// Special value handling:
954 /// * if `x` is NaN (either signaling or quiet), quiet NaN is returned.
955 /// * if `x` is +/-infinity or +/-0, it is returned unmodified.
957
958 /// Return the square root of the specified `x`.
959 ///
960 static ValueType32 sqrt(ValueType32 x);
961 static ValueType64 sqrt(ValueType64 x);
962 /// Special value handling:
963 /// * If `x` is quiet NaN, quiet NaN is returned.
964 /// * If `x` is signaling NaN, quiet NaN is returned and the value of
965 /// the macro `EDOM` is stored into `errno`.
966 /// * If `x` is less than -0, quiet NaN is returned and the value of
967 /// the macro `EDOM` is stored into `errno`.
968 /// * If `x` is +/-infinity or +/-0, it is returned unmodified.
970
971 // Negation functions
972
973 static ValueType32 negate(ValueType32 value);
974 static ValueType64 negate(ValueType64 value);
975 /// Return the result of applying the unary negation (`-`) operator to
976 /// the specified `value` as described by IEEE-754. Note that decimal
977 /// floating point representations can encode signed zero values, thus
978 /// negating 0 results in -0 and negating -0 results in 0.
979 static ValueType128 negate(ValueType128 value);
980
981 // Comparison functions
982
983 // Less Than functions
984
985 /// Return `true` if the specified `lhs` has a value less than the
986 /// specified `rhs` and `false` otherwise. The value of a `Decimal64`
987 /// object `lhs` is less than that of an object `rhs` if the
988 /// `compareQuietLess` operation (IEEE-754 defined, non-total ordering
989 /// comparison) considers the underlying IEEE representation of `lhs` to
990 /// be less than of that of `rhs`. In other words, `lhs` is less than
991 /// `rhs` if:
992 ///
993 /// * neither `lhs` nor `rhs` are NaN, or
994 /// * `lhs` is zero (positive or negative) and `rhs` is positive, or
995 /// * `rhs` is zero (positive or negative) and `lhs` negative, or
996 /// * `lhs` is not positive infinity, or
997 /// * `lhs` is negative infinity and `rhs` is not, or
998 /// * `lhs` and `rhs` both represent a real number and the real number
999 /// of `lhs` is less than that of `rhs`
1000 ///
1001 static bool less(ValueType32 lhs, ValueType32 rhs);
1002 static bool less(ValueType64 lhs, ValueType64 rhs);
1003 /// If either or both operands are signaling NaN, store the value of the
1004 /// macro `EDOM` into `errno` and return `false`.
1005 static bool less(ValueType128 lhs, ValueType128 rhs);
1006
1007 // Greater Than functions
1008
1009 /// Return `true` if the specified `lhs` has a greater value than the
1010 /// specified `rhs` and `false` otherwise. The value of a `Decimal64`
1011 /// object `lhs` is greater than that of an object `rhs` if the
1012 /// `compareQuietGreater` operation (IEEE-754 defined, non-total
1013 /// ordering comparison) considers the underlying IEEE representation of
1014 /// `lhs` to be greater than of that of `rhs`. In other words, `lhs` is
1015 /// greater than `rhs` if:
1016 ///
1017 /// * neither `lhs` nor `rhs` are NaN, or
1018 /// * `rhs` is zero (positive or negative) and `lhs` positive, or
1019 /// * `lhs` is zero (positive or negative) and `rhs` negative, or
1020 /// * `lhs` is not negative infinity, or
1021 /// * `lhs` is positive infinity and `rhs` is not, or
1022 /// * `lhs` and `rhs` both represent a real number and the real number
1023 /// of `lhs` is greater than that of `rhs`
1024 ///
1025 static bool greater(ValueType32 lhs, ValueType32 rhs);
1026 static bool greater(ValueType64 lhs, ValueType64 rhs);
1027 /// If either or both operands are signaling NaN, store the value of the
1028 /// macro `EDOM` into `errno` and return `false`.
1029 static bool greater(ValueType128 lhs, ValueType128 rhs);
1030
1031 // Less Or Equal functions
1032
1033 /// Return `true` if the specified `lhs` has a value less than or equal
1034 /// the value of the specified `rhs` and `false` otherwise. The value
1035 /// of a `Decimal64` object `lhs` is less than or equal to the value of
1036 /// an object `rhs` if the `compareQuietLessEqual` operation (IEEE-754
1037 /// defined, non-total ordering comparison) considers the underlying
1038 /// IEEE representation of `lhs` to be less or equal to that of `rhs`.
1039 /// In other words, `lhs` is less or equal than `rhs` if:
1040 ///
1041 /// * neither `lhs` nor `rhs` are NaN, or
1042 /// * `lhs` and `rhs` are both zero (positive or negative), or
1043 /// * both `lhs` and `rhs` are positive infinity, or
1044 /// * `lhs` is negative infinity, or
1045 /// * `lhs` and `rhs` both represent a real number and the real number
1046 /// of `lhs` is less or equal to that of `rhs`
1047 ///
1048 static bool lessEqual(ValueType32 lhs, ValueType32 rhs);
1049 static bool lessEqual(ValueType64 lhs, ValueType64 rhs);
1050 /// If either or both operands are signaling NaN, store the value of the
1051 /// macro `EDOM` into `errno` and return `false`.
1052 static bool lessEqual(ValueType128 lhs, ValueType128 rhs);
1053
1054 // Greater Or Equal functions
1055
1056 /// Return `true` if the specified `lhs` has a value greater than or
1057 /// equal to the value of the specified `rhs` and `false` otherwise.
1058 /// The value of a `Decimal64` object `lhs` is greater or equal to a
1059 /// `Decimal64` object `rhs` if the `compareQuietGreaterEqual` operation
1060 /// (IEEE-754 defined, non-total ordering comparison ) considers the
1061 /// underlying IEEE representation of `lhs` to be greater or equal to
1062 /// that of `rhs`. In other words, `lhs` is greater than or equal to
1063 /// `rhs` if:
1064 ///
1065 /// * neither `lhs` nor `rhs` are NaN, or
1066 /// * `lhs` and `rhs` are both zero (positive or negative), or
1067 /// * both `lhs` and `rhs` are negative infinity, or
1068 /// * `lhs` is positive infinity, or
1069 /// * `lhs` and `rhs` both represent a real number and the real number
1070 /// of `lhs` is greater or equal to that of `rhs`
1071 ///
1072 static bool greaterEqual(ValueType32 lhs, ValueType32 rhs);
1073 static bool greaterEqual(ValueType64 lhs, ValueType64 rhs);
1074 /// If either or both operands are signaling NaN, store the value of the
1075 /// macro `EDOM` into `errno` and return `false`.
1076 static bool greaterEqual(ValueType128 lhs, ValueType128 rhs);
1077
1078 // Equality functions
1079
1080 /// Return `true` if the specified `lhs` and `rhs` have the same value,
1081 /// and `false` otherwise. Two decimal objects have the same value if
1082 /// the `compareQuietEqual` operation (IEEE-754 defined, non-total
1083 /// ordering comparison) considers the underlying IEEE representations
1084 /// equal. In other words, two decimal objects have the same value if:
1085 ///
1086 /// * both have a zero value (positive or negative), or
1087 /// * both have the same infinity value (both positive or negative), or
1088 /// * both have the value of a real number that are equal, even if they
1089 /// are represented differently (cohorts have the same value)
1090 ///
1091 static bool equal(ValueType32 lhs, ValueType32 rhs);
1092 static bool equal(ValueType64 lhs, ValueType64 rhs);
1093 /// If either or both operands are signaling NaN, store the value of the
1094 /// macro `EDOM` into `errno` and return `false`.
1095 static bool equal(ValueType128 lhs, ValueType128 rhs);
1096
1097 // Inequality functions
1098
1099 /// Return `false` if the specified `lhs` and `rhs` have the same value,
1100 /// and `true` otherwise. Two decimal objects have the same value if
1101 /// the `compareQuietEqual` operation (IEEE-754 defined, non-total
1102 /// ordering comparison) considers the underlying IEEE representations
1103 /// equal. In other words, two decimal objects have the same value if:
1104 ///
1105 /// * both have a zero value (positive or negative), or
1106 /// * both have the same infinity value (both positive or negative), or
1107 /// * both have the value of a real number that are equal, even if they
1108 /// are represented differently (cohorts have the same value)
1109 ///
1110 static bool notEqual(ValueType32 lhs, ValueType32 rhs);
1111 static bool notEqual(ValueType64 lhs, ValueType64 rhs);
1112 /// If either or both operands are signaling NaN, store the value of the
1113 /// macro `EDOM` into `errno` and return `false`.
1114 static bool notEqual(ValueType128 lhs, ValueType128 rhs);
1115
1116 // Inter-type Conversion functions
1117
1118 static ValueType32 convertToDecimal32 (const ValueType64& input);
1119 static ValueType32 convertToDecimal32 (const ValueType128& input);
1120 static ValueType64 convertToDecimal64 (const ValueType32& input);
1121 static ValueType64 convertToDecimal64 (const ValueType128& input);
1122
1123 /// Convert the specified `input` to the closest value of the indicated
1124 /// result type following the conversion rules as defined by IEEE-754:
1125 ///
1126 static ValueType128 convertToDecimal128(const ValueType32& input);
1127 /// * If `input` is signaling NaN, store the value of the macro `EDOM`
1128 /// into `errno` and return signaling NaN value.
1129 /// * If `input` is NaN, return NaN value.
1130 /// * Otherwise if `input` is infinity (positive or negative), then
1131 /// return infinity with the same sign.
1132 /// * Otherwise if `input` is zero (positive or negative), then
1133 /// return zero with the same sign.
1134 /// * Otherwise if `input` has an absolute value that is larger than
1135 /// maximum or is smaller than minimum value supported by the result
1136 /// type, store the value of the macro `ERANGE` into `errno` and
1137 /// return infinity or zero with the same sign respectively.
1138 /// * Otherwise if `input` has a value that is not exactly
1139 /// representable using maximum digit number supported by the
1140 /// indicated result type then return the `input` rounded according
1141 /// to the rounding direction.
1142 /// * Otherwise return `input` value of the result type.
1143 static ValueType128 convertToDecimal128(const ValueType64& input);
1144
1145 // Binary floating point conversion functions
1146
1147 /// Create a `Decimal32` object having the value closest to the
1148 /// specified `value` following the conversion rules as defined by
1149 /// IEEE-754:
1150 ///
1151 static ValueType32 binaryToDecimal32( float value);
1152 /// * If `value` is signaling NaN, store the value of the macro `EDOM`
1153 /// into `errno` and return signaling NaN value.
1154 /// * Otherwise if `value` is NaN, return a NaN.
1155 /// * Otherwise if `value` is infinity (positive or negative), then
1156 /// return an object equal to infinity with the same sign.
1157 /// * Otherwise if `value` is a zero value, then return an object equal
1158 /// to zero with the same sign.
1159 /// * Otherwise if `value` has an absolute value that is larger than
1160 /// `std::numeric_limits<Decimal32>::max()` then store the value of
1161 /// the macro `ERANGE` into `errno` and return infinity with the same
1162 /// sign as `value`.
1163 /// * Otherwise if `value` has an absolute value that is smaller than
1164 /// `std::numeric_limits<Decimal32>::min()` then store the value of
1165 /// the macro `ERANGE` into `errno` and return a zero with the same
1166 /// sign as `value`.
1167 /// * Otherwise if `value` needs more than
1168 /// `std::numeric_limits<Decimal32>::max_digit` significant decimal
1169 /// digits to represent then return the `value` rounded according to
1170 /// the rounding direction.
1171 /// * Otherwise return a `Decimal32` object representing `value`.
1172 static ValueType32 binaryToDecimal32( double value);
1173
1174 /// Create a `Decimal64` object having the value closest to the
1175 /// specified `value` following the conversion rules as defined by
1176 /// IEEE-754:
1177 ///
1178 static ValueType64 binaryToDecimal64( float value);
1179 /// * If `value` is signaling NaN, store the value of the macro `EDOM`
1180 /// into `errno` and return signaling NaN value.
1181 /// * Otherwise if `value` is NaN, return a NaN.
1182 /// * Otherwise if `value` is infinity (positive or negative), then
1183 /// return an object equal to infinity with the same sign.
1184 /// * Otherwise if `value` is a zero value, then return an object equal
1185 /// to zero with the same sign.
1186 /// * Otherwise if `value` needs more than
1187 /// `std::numeric_limits<Decimal64>::max_digit` significant decimal
1188 /// digits to represent then return the `value` rounded according to
1189 /// the rounding direction.
1190 /// * Otherwise return a `Decimal64` object representing `value`.
1191 static ValueType64 binaryToDecimal64( double value);
1192
1193 /// Create a `Decimal128` object having the value closest to the
1194 /// specified `value` following the conversion rules as defined by
1195 /// IEEE-754:
1196 ///
1197 static ValueType128 binaryToDecimal128( float value);
1198 /// * If `value` is signaling NaN, store the value of the macro `EDOM`
1199 /// into `errno` and return signaling NaN value.
1200 /// * Otherwise if `value` is NaN, return a NaN.
1201 /// * Otherwise if `value` is infinity (positive or negative), then
1202 /// return an object equal to infinity with the same sign.
1203 /// * Otherwise if `value` is a zero value, then return an object equal
1204 /// to zero with the same sign.
1205 /// * Otherwise if `value` has an absolute value that is larger than
1206 /// `std::numeric_limits<Decimal128>::max()` then store the value of
1207 /// the macro `ERANGE` into `errno` and return infinity with the same
1208 /// sign as `value`.
1209 /// * Otherwise if `value` has an absolute value that is smaller than
1210 /// `std::numeric_limits<Decimal128>::min()` then store the value of
1211 /// the macro `ERANGE` into `errno` and return a zero with the same
1212 /// sign as `value`.
1213 /// * Otherwise if `value` needs more than
1214 /// `std::numeric_limits<Decimal128>::max_digit` significant decimal
1215 /// digits to represent then return the `value` rounded according to
1216 /// the rounding direction.
1217 /// * Otherwise return a `Decimal128` object representing `value`.
1218 static ValueType128 binaryToDecimal128( double value);
1219
1220 // makeDecimalRaw functions
1221
1222 /// Create a `ValueType32` object representing a decimal floating point
1223 /// number consisting of the specified `significand` and `exponent`,
1224 /// with the sign given by `significand`. The behavior is undefined
1225 /// unless `abs(significand) <= 9,999,999` and `-101 <= exponent <= 90`.
1226 static ValueType32 makeDecimalRaw32(int significand, int exponent);
1227
1228 static ValueType64 makeDecimalRaw64(unsigned long long int significand,
1229 int exponent);
1230 static ValueType64 makeDecimalRaw64( long long int significand,
1231 int exponent);
1232 static ValueType64 makeDecimalRaw64(unsigned int significand,
1233 int exponent);
1234 /// Create a `ValueType64` object representing a decimal floating point
1235 /// number consisting of the specified `significand` and `exponent`,
1236 /// with the sign given by `significand`. The behavior is undefined
1237 /// unless `abs(significand) <= 9,999,999,999,999,999` and
1238 /// `-398 <= exponent <= 369`.
1239 static ValueType64 makeDecimalRaw64( int significand,
1240 int exponent);
1241
1242 static ValueType128 makeDecimalRaw128(unsigned long long int significand,
1243 int exponent);
1244 static ValueType128 makeDecimalRaw128( long long int significand,
1245 int exponent);
1246 static ValueType128 makeDecimalRaw128(unsigned int significand,
1247 int exponent);
1248 /// Create a `ValueType128` object representing a decimal floating point
1249 /// number consisting of the specified `significand` and `exponent`,
1250 /// with the sign given by `significand`. The behavior is undefined
1251 /// unless `-6176 <= exponent <= 6111`.
1252 static ValueType128 makeDecimalRaw128( int significand,
1253 int exponent);
1254
1255 // ScaleB functions
1256
1257 /// Return the result of multiplying the specified `value` by ten raised
1258 /// to the specified `exponent`. The quantum of `value` is scaled
1259 /// according to IEEE 754's `scaleB` operations.
1260 ///
1261 static ValueType32 scaleB(ValueType32 value, int exponent);
1262 static ValueType64 scaleB(ValueType64 value, int exponent);
1263 /// Special value handling:
1264 /// * If `value` is quiet NaN, quiet NaN is returned.
1265 /// * If `value` is signaling NaN, quiet NaN is returned and the value
1266 /// of the macro `EDOM` is stored into `errno`.
1267 /// * If `x` is infinite, then infinity is returned.
1268 /// * If a range error due to overflow occurs, infinity is returned and
1269 ///: the value of the macro `ERANGE` is stored into `errno`.
1270 static ValueType128 scaleB(ValueType128 value, int exponent);
1271
1272 // Parsing functions
1273
1274 static ValueType32 parse32( const char *input);
1275 static ValueType64 parse64( const char *input);
1276 static ValueType128 parse128(const char *input);
1277 static ValueType32 parse32( const char *input, unsigned int *status);
1278 static ValueType64 parse64( const char *input, unsigned int *status);
1279
1280 /// Produce an object of the indicated return type by parsing the
1281 /// specified `input` string that represents a floating-point number
1282 /// (written in either fixed or scientific notation). Optionally
1283 /// specify `status` in which to load a bit mask of additional status
1284 /// information. The resulting decimal object is initialized as follows:
1285 ///
1286 /// * If `input` does not represent a floating-point value, then return
1287 /// a decimal object of the indicated return type initialized to a
1288 /// NaN.
1289 /// * Otherwise if `input` represents infinity (positive or negative),
1290 /// as case-insensitive "Inf" or "Infinity" string, then return a
1291 /// decimal object of the indicated return type initialized to
1292 /// infinity value with the same sign.
1293 /// * Otherwise if `input` represents zero (positive or negative), then
1294 /// return a decimal object of the indicated return type initialized
1295 /// to zero with the same sign.
1296 /// * Otherwise if `str` represents a value that has an absolute value
1297 /// that is larger than `std::numeric_limits<Decimal32>::max()` then
1298 /// store the value of the macro `ERANGE` into `errno` and return a
1299 /// decimal object of the indicated return type initialized to
1300 /// infinity with the same sign.
1301 /// * Otherwise if `input` represents a value that has an absolute
1302 /// value that is smaller than
1303 /// `std::numeric_limits<Decimal32>::min()`, then store the value of
1304 /// the macro `ERANGE` into `errno` and return a decimal object of
1305 /// the indicated return type initialized to zero with the same sign.
1306 /// * Otherwise if `input` has a value that is not exactly
1307 /// representable using `std::numeric_limits<Decimal32>::max_digit`
1308 /// decimal digits then return a decimal object of the indicated
1309 /// return type initialized to the value represented by `input`
1310 /// rounded according to the rounding direction.
1311 /// * Otherwise return a decimal object of the indicated return type
1312 /// initialized to the decimal value representation of `input`.
1313 ///
1314 /// The `*status`, if supplied, mest be 0, and may be loaded with a bit
1315 /// mask of `k_STATUS_INEXACT`, `k_STATUS_UNDERFLOW`, and
1316 /// `k_STATUS_OVERFLOW` indicating wether the conversion from text was
1317 /// inexact, underflowed, or overflowed (or some combination)
1318 /// respectively. The behavior is undefined unless `*status` (if
1319 /// supplied) is 0.
1320 ///
1321 /// Note that the parsing follows the rules as specified for the
1322 /// `strtod32` function in section 9.6 of the ISO/EIC TR 24732 C Decimal
1323 /// Floating-Point Technical Report.
1324 ///
1325 /// Also note that the quanta of the resultant value is determined by
1326 /// the number of decimal places starting with the most significand
1327 /// digit in `input` string and cannot exceed the maximum number of
1328 /// digits necessary to differentiate all values of the indicated return
1329 /// type, for example:
1330 ///
1331 /// @code
1332 /// 'parse32("0.015") => 15e-3'
1333 /// 'parse32("1.5") => 15e-1'
1334 /// 'parse32("1.500") => 1500e-3'
1335 /// 'parse32("1.2345678) => 1234568e-6'
1336 /// @endcode
1337 static ValueType128 parse128(const char *input, unsigned int *status);
1338
1339 // Densely Packed Conversion Functions
1340
1343 /// Return a `ValueTypeXX` representing the specified `dpd`, which is
1344 /// currently in Densely Packed Decimal (DPD) format. This format is
1345 /// compatible with the IBM compiler's native type.
1347
1348 /// Return a `DecimalStorage::TypeXX` representing the specified `value`
1349 /// in Densely Packed Decimal (DPD) format. This format is compatible
1350 /// with the IBM compiler's native type.
1354
1355 // Binary Integral Conversion Functions
1356
1359 /// Return a `ValueTypeXX` representing the specified `bid`, which is
1360 /// currently in Binary Integral Decimal (BID) format. This format is
1361 /// compatible with the Intel DFP implementation type.
1363
1364 /// Return a `DecimalStorage::TypeXX` representing the specified
1365 /// `value` in Binary Integral Decimal (BID) format. This format is
1366 /// compatible with the Intel DFP implementation type.
1367 static
1369 static
1371 static
1373
1374 // Functions returning special values
1375
1376 /// Return the smallest positive normalized number `ValueType32` can
1377 /// represent (IEEE-754: +1e-95).
1378 static
1380
1381 /// Return the largest number `ValueType32` can represent (IEEE-754:
1382 /// +9.999999e+96).
1383 static
1385
1386 /// Return the difference between the least representable value of type
1387 /// `ValueType32` greater than 1 and 1 (IEEE-754: +1e-6).
1388 static
1390
1391 /// Return the maximum rounding error for the `ValueType32` type. The
1392 /// actual value returned depends on the current decimal floating point
1393 /// rounding setting.
1394 static
1396
1397 /// Return the smallest positive denormalized value for the
1398 /// `ValueType32` type (IEEE-754: +0.000001e-95).
1399 static
1401
1402 /// Return the value that represents positive infinity for the
1403 /// `ValueType32` type.
1404 static
1406
1407 /// Return a value that represents non-signaling NaN for the
1408 /// `ValueType32` type.
1409 static
1411
1412 /// Return a value that represents signaling NaN for the `ValueType32`
1413 /// type.
1414 static
1416
1417 /// Return the smallest positive normalized number `ValueType64` can
1418 /// represent (IEEE-754: +1e-383).
1419 static
1421
1422 /// Return the largest number `ValueType64` can represent (IEEE-754:
1423 /// +9.999999999999999e+384).
1424 static
1426
1427 /// Return the difference between the least representable value of type
1428 /// `ValueType64` greater than 1 and 1 (IEEE-754: +1e-15).
1429 static
1431
1432 /// Return the maximum rounding error for the `ValueType64` type. The
1433 /// actual value returned depends on the current decimal floating point
1434 /// rounding setting.
1435 static
1437
1438 /// Return the smallest positive denormalized value for the
1439 /// `ValueType64` type (IEEE-754: +0.000000000000001e-383).
1440 static
1442
1443 /// Return the value that represents positive infinity for the
1444 /// `ValueType64` type.
1445 static
1447
1448 /// Return a value that represents non-signaling NaN for the
1449 /// `ValueType64` type.
1450 static
1452
1453 /// Return a value that represents signaling NaN for the `ValueType64`
1454 /// type.
1455 static
1457
1458 /// Return the smallest positive normalized number `ValueType128` can
1459 /// represent (IEEE-754: +1e-6143).
1460 static
1462
1463 /// Return the largest number `ValueType128` can represent (IEEE-754:
1464 /// +9.999999999999999999999999999999999e+6144).
1465 static
1467
1468 /// Return the difference between the least representable value of type
1469 /// `ValueType128` greater than 1 and 1 (IEEE-754: +1e-33).
1470 static
1472
1473 /// Return the maximum rounding error for the `ValueType128` type. The
1474 /// actual value returned depends on the current decimal floating point
1475 /// rounding setting.
1476 static
1478
1479 /// Return the smallest positive denormalized value for the
1480 /// `ValueType128` type (IEEE-754:
1481 /// +0.000000000000000000000000000000001e-6143).
1482 static
1484
1485 /// Return the value that represents positive infinity for the
1486 /// `ValueType128` type.
1487 static
1489
1490 /// Return a value that represents non-signaling NaN for the
1491 /// `ValueType128` type.
1492 static
1494
1495 /// Return a value that represents signaling NaN for the `ValueType128`
1496 /// type.
1497 static
1499};
1500
1501// ============================================================================
1502// INLINE DEFINITIONS
1503// ============================================================================
1504
1505 // --------------------
1506 // class DecimalImpUtil
1507 // --------------------
1508
1509#ifdef BDLDFP_DECIMALPLATFORM_SOFTWARE
1510
1511template <class TYPE>
1512inline
1513void DecimalImpUtil::checkLiteral(const TYPE& t)
1514{
1515 (void)static_cast<This_is_not_a_floating_point_literal>(t);
1516}
1517
1518inline
1519void DecimalImpUtil::checkLiteral(double)
1520{
1521}
1522#endif
1523
1524
1525// CLASS METHODS
1526
1527 // Integer construction
1528
1529inline
1531{
1532 return Imp::int32ToDecimal32(value);
1533}
1534
1535inline
1537{
1538 return Imp::int32ToDecimal64(value);
1539}
1540
1541inline
1543{
1544 return Imp::int32ToDecimal128(value);
1545}
1546
1547
1548inline
1551{
1552 return Imp::uint32ToDecimal32(value);
1553}
1554
1555inline
1558{
1559 return Imp::uint32ToDecimal64(value);
1560}
1561
1562inline
1565{
1566 return Imp::uint32ToDecimal128(value);
1567}
1568
1569
1570inline
1573{
1574 return Imp::int64ToDecimal32(value);
1575}
1576
1577inline
1580{
1581 return Imp::int64ToDecimal64(value);
1582}
1583
1584inline
1587{
1588 return Imp::int64ToDecimal128(value);
1589}
1590
1591
1592inline
1594DecimalImpUtil::uint64ToDecimal32(unsigned long long int value)
1595{
1596 return Imp::uint64ToDecimal32(value);
1597}
1598
1599inline
1601DecimalImpUtil::uint64ToDecimal64(unsigned long long int value)
1602{
1603 return Imp::uint64ToDecimal64(value);
1604}
1605
1606inline
1608DecimalImpUtil::uint64ToDecimal128(unsigned long long int value)
1609{
1610 return Imp::uint64ToDecimal128(value);
1611}
1612
1613 // Arithmetic
1614
1615 // Addition Functions
1616
1617inline
1621{
1622 return Imp::add(lhs, rhs);
1623}
1624
1625inline
1629{
1630 return Imp::add(lhs, rhs);
1631}
1632
1636{
1637 return Imp::add(lhs, rhs);
1638}
1639
1640 // Subtraction Functions
1641
1642inline
1646{
1647 return Imp::subtract(lhs, rhs);
1648}
1649
1650inline
1654{
1655 return Imp::subtract(lhs, rhs);
1656}
1657
1658inline
1662{
1663 return Imp::subtract(lhs, rhs);
1664}
1665
1666 // Multiplication Functions
1667
1668inline
1672{
1673 return Imp::multiply(lhs, rhs);
1674}
1675
1676inline
1680{
1681 return Imp::multiply(lhs, rhs);
1682}
1683
1684inline
1688{
1689 return Imp::multiply(lhs, rhs);
1690}
1691
1692 // Division Functions
1693
1694 // Division Functions
1695
1696inline
1700{
1701 return Imp::divide(lhs, rhs);
1702}
1703
1704inline
1708{
1709 return Imp::divide(lhs, rhs);
1710}
1711
1712inline
1716{
1717 return Imp::divide(lhs, rhs);
1718}
1719
1720inline
1722 ValueType32 exponent)
1723{
1725 _IDEC_flags flags(0);
1726 retval.d_raw = __bid32_quantize(value.d_raw,
1727 exponent.d_raw,
1728 &flags);
1729 return retval;
1730}
1731
1732inline
1734 ValueType64 exponent)
1735{
1737 _IDEC_flags flags(0);
1738 retval.d_raw = __bid64_quantize(value.d_raw,
1739 exponent.d_raw,
1740 &flags);
1741 return retval;
1742}
1743
1744inline
1746 ValueType128 exponent)
1747{
1749 _IDEC_flags flags(0);
1750 retval.d_raw = __bid128_quantize(value.d_raw,
1751 exponent.d_raw,
1752 &flags);
1753 return retval;
1754}
1755
1756inline
1758 int exponent)
1759{
1760 BSLS_ASSERT(-101 <= exponent);
1761 BSLS_ASSERT( exponent <= 90);
1762
1765 1,
1766 exponent);
1767 _IDEC_flags flags(0);
1768 retval.d_raw = __bid32_quantize(value.d_raw, exp.d_raw, &flags);
1769 return retval;
1770}
1771
1772inline
1774 int exponent)
1775{
1776 BSLS_ASSERT(-398 <= exponent);
1777 BSLS_ASSERT( exponent <= 369);
1778
1781 1,
1782 exponent);
1783 _IDEC_flags flags(0);
1784 retval.d_raw = __bid64_quantize(value.d_raw, exp.d_raw, &flags);
1785 return retval;
1786}
1787
1788inline
1790 int exponent)
1791{
1792 BSLS_ASSERT(-6176 <= exponent);
1793 BSLS_ASSERT( exponent <= 6111);
1794
1797 1,
1798 exponent);
1799 _IDEC_flags flags(0);
1800 retval.d_raw = __bid128_quantize(value.d_raw, exp.d_raw, &flags);
1801 return retval;
1802}
1803
1804inline
1806{
1807 BSLS_ASSERT(x);
1808 BSLS_ASSERT(-101 <= exponent);
1809 BSLS_ASSERT( exponent <= 90);
1810
1813 1,
1814 exponent);
1815 _IDEC_flags flags(0);
1816 retval.d_raw = __bid32_quantize(y.d_raw, exp.d_raw, &flags);
1817 if (DecimalImpUtil::equal(retval, y)) {
1818 *x = retval;
1819 return 0;
1820 }
1821 return -1;
1822}
1823
1824inline
1826{
1827 BSLS_ASSERT(x);
1828 BSLS_ASSERT(-398 <= exponent);
1829 BSLS_ASSERT( exponent <= 369);
1832 1,
1833 exponent);
1834 _IDEC_flags flags(0);
1835 retval.d_raw = __bid64_quantize(y.d_raw, exp.d_raw, &flags);
1836 if (DecimalImpUtil::equal(retval, y)) {
1837 *x = retval;
1838 return 0;
1839 }
1840 return -1;
1841}
1842
1843inline
1845{
1846 BSLS_ASSERT(x);
1847 BSLS_ASSERT(-6176 <= exponent);
1848 BSLS_ASSERT( exponent <= 6111);
1849
1852 1,
1853 exponent);
1854 _IDEC_flags flags(0);
1855 retval.d_raw = __bid128_quantize(y.d_raw, exp.d_raw, &flags);
1856 if (DecimalImpUtil::equal(retval, y)) {
1857 *x = retval;
1858 return 0;
1859 }
1860 return -1;
1861}
1862
1863inline
1865{
1866 return __bid32_sameQuantum(x.d_raw, y.d_raw);
1867}
1868
1869inline
1871{
1872 return __bid64_sameQuantum(x.d_raw, y.d_raw);
1873}
1874
1875inline
1877{
1878 return __bid128_sameQuantum(x.d_raw, y.d_raw);
1879}
1880
1881
1882 // Math functions
1883
1884inline
1886{
1887 _IDEC_flags flags(0);
1888 long int ret = __bid32_lrint(x.d_raw, &flags);
1889 if (BID_INVALID_EXCEPTION & flags) {
1890 errno = EDOM;
1891 }
1892 return ret;
1893}
1894
1895inline
1897{
1898 _IDEC_flags flags(0);
1899 long int ret = __bid64_lrint(x.d_raw, &flags);
1900 if (BID_INVALID_EXCEPTION & flags) {
1901 errno = EDOM;
1902 }
1903 return ret;
1904}
1905
1906inline
1908{
1909 _IDEC_flags flags(0);
1910 long int ret = __bid128_lrint(x.d_raw, &flags);
1911 if (BID_INVALID_EXCEPTION & flags) {
1912 errno = EDOM;
1913 }
1914 return ret;
1915}
1916
1917inline
1919{
1920 _IDEC_flags flags(0);
1921 long long int ret = __bid32_llrint(x.d_raw, &flags);
1922 if (BID_INVALID_EXCEPTION & flags) {
1923 errno = EDOM;
1924 }
1925 return ret;
1926}
1927
1928inline
1930{
1931 _IDEC_flags flags(0);
1932 long long int ret = __bid64_llrint(x.d_raw, &flags);
1933 if (BID_INVALID_EXCEPTION & flags) {
1934 errno = EDOM;
1935 }
1936 return ret;
1937}
1938
1939inline
1941{
1942 _IDEC_flags flags(0);
1943 long long int ret = __bid128_llrint(x.d_raw, &flags);
1944 if (BID_INVALID_EXCEPTION & flags) {
1945 errno = EDOM;
1946 }
1947 return ret;
1948}
1949
1950inline
1953{
1955 _IDEC_flags flags(0);
1956 retval.d_raw = __bid32_nextafter(x.d_raw, y.d_raw, &flags);
1957 if (BID_OVERFLOW_EXCEPTION & flags ||
1958 BID_UNDERFLOW_EXCEPTION & flags)
1959 {
1960 errno = ERANGE;
1961 }
1962 if (BID_INVALID_EXCEPTION & flags) {
1963 errno = EDOM;
1964 }
1965 return retval;
1966}
1967
1968inline
1971{
1973 _IDEC_flags flags(0);
1974 retval.d_raw = __bid64_nextafter(x.d_raw, y.d_raw, &flags);
1975 if (BID_OVERFLOW_EXCEPTION & flags ||
1976 BID_UNDERFLOW_EXCEPTION & flags)
1977 {
1978 errno = ERANGE;
1979 }
1980 if (BID_INVALID_EXCEPTION & flags) {
1981 errno = EDOM;
1982 }
1983 return retval;
1984}
1985
1986inline
1989{
1991 _IDEC_flags flags(0);
1992 retval.d_raw = __bid128_nextafter(x.d_raw, y.d_raw, &flags);
1993 if (BID_OVERFLOW_EXCEPTION & flags ||
1994 BID_UNDERFLOW_EXCEPTION & flags)
1995 {
1996 errno = ERANGE;
1997 }
1998 if (BID_INVALID_EXCEPTION & flags) {
1999 errno = EDOM;
2000 }
2001 return retval;
2002}
2003
2004inline
2007{
2009 _IDEC_flags flags(0);
2010 retval.d_raw = __bid32_nexttoward(x.d_raw, y.d_raw, &flags);
2011 if (BID_OVERFLOW_EXCEPTION & flags ||
2012 BID_UNDERFLOW_EXCEPTION & flags)
2013 {
2014 errno = ERANGE;
2015 }
2016 if (BID_INVALID_EXCEPTION & flags) {
2017 errno = EDOM;
2018 }
2019 return retval;
2020}
2021
2022inline
2025{
2027 _IDEC_flags flags(0);
2028 retval.d_raw = __bid64_nexttoward(x.d_raw, y.d_raw, &flags);
2029 if (BID_OVERFLOW_EXCEPTION & flags ||
2030 BID_UNDERFLOW_EXCEPTION & flags)
2031 {
2032 errno = ERANGE;
2033 }
2034 if (BID_INVALID_EXCEPTION & flags) {
2035 errno = EDOM;
2036 }
2037 return retval;
2038}
2039
2040inline
2043{
2045 _IDEC_flags flags(0);
2046 retval.d_raw = __bid128_nexttoward(x.d_raw, y.d_raw, &flags);
2047 if (BID_OVERFLOW_EXCEPTION & flags ||
2048 BID_UNDERFLOW_EXCEPTION & flags)
2049 {
2050 errno = ERANGE;
2051 }
2052 if (BID_INVALID_EXCEPTION & flags) {
2053 errno = EDOM;
2054 }
2055 return retval;
2056}
2057
2058inline
2061{
2063 _IDEC_flags flags(0);
2064 retval.d_raw = __bid32_pow(base.d_raw, exp.d_raw, &flags);
2065 if (BID_OVERFLOW_EXCEPTION & flags ||
2066 BID_UNDERFLOW_EXCEPTION & flags ||
2067 BID_ZERO_DIVIDE_EXCEPTION & flags)
2068 {
2069 errno = ERANGE;
2070 }
2071 if (BID_INVALID_EXCEPTION & flags) {
2072 errno = EDOM;
2073 }
2074 return retval;
2075}
2076
2077inline
2080{
2082 _IDEC_flags flags(0);
2083 retval.d_raw = __bid64_pow(base.d_raw, exp.d_raw, &flags);
2084 if (BID_OVERFLOW_EXCEPTION & flags ||
2085 BID_UNDERFLOW_EXCEPTION & flags ||
2086 BID_ZERO_DIVIDE_EXCEPTION & flags)
2087 {
2088 errno = ERANGE;
2089 }
2090 if (BID_INVALID_EXCEPTION & flags) {
2091 errno = EDOM;
2092 }
2093
2094 return retval;
2095}
2096
2097inline
2100{
2102 _IDEC_flags flags(0);
2103 retval.d_raw = __bid128_pow(base.d_raw, exp.d_raw, &flags);
2104 if (BID_OVERFLOW_EXCEPTION & flags ||
2105 BID_UNDERFLOW_EXCEPTION & flags ||
2106 BID_ZERO_DIVIDE_EXCEPTION & flags)
2107 {
2108 errno = ERANGE;
2109 }
2110 if (BID_INVALID_EXCEPTION & flags) {
2111 errno = EDOM;
2112 }
2113 return retval;
2114}
2115
2116inline
2118{
2120 _IDEC_flags flags(0);
2121 retval.d_raw = __bid32_round_integral_positive(x.d_raw, &flags);
2122 if (BID_INVALID_EXCEPTION & flags) {
2123 errno = EDOM;
2124 }
2125 return retval;
2126}
2127
2128inline
2130{
2132 _IDEC_flags flags(0);
2133 retval.d_raw = __bid64_round_integral_positive(x.d_raw, &flags);
2134 if (BID_INVALID_EXCEPTION & flags) {
2135 errno = EDOM;
2136 }
2137 return retval;
2138}
2139
2140inline
2142{
2144 _IDEC_flags flags(0);
2145 retval.d_raw = __bid128_round_integral_positive(x.d_raw, &flags);
2146 if (BID_INVALID_EXCEPTION & flags) {
2147 errno = EDOM;
2148 }
2149 return retval;
2150
2151}
2152
2153inline
2155{
2157 _IDEC_flags flags(0);
2158 retval.d_raw = __bid32_round_integral_negative(x.d_raw, &flags);
2159 if (BID_INVALID_EXCEPTION & flags) {
2160 errno = EDOM;
2161 }
2162 return retval;
2163}
2164
2165inline
2167{
2169 _IDEC_flags flags(0);
2170 retval.d_raw = __bid64_round_integral_negative(x.d_raw, &flags);
2171 if (BID_INVALID_EXCEPTION & flags) {
2172 errno = EDOM;
2173 }
2174 return retval;
2175}
2176
2177inline
2179{
2181 _IDEC_flags flags(0);
2182 retval.d_raw = __bid128_round_integral_negative(x.d_raw, &flags);
2183 if (BID_INVALID_EXCEPTION & flags) {
2184 errno = EDOM;
2185 }
2186 return retval;
2187}
2188
2189inline
2191{
2193 _IDEC_flags flags(0);
2194 retval.d_raw = __bid32_round_integral_nearest_away(x.d_raw, &flags);
2195 if (BID_INVALID_EXCEPTION & flags) {
2196 errno = EDOM;
2197 }
2198 return retval;
2199}
2200
2201inline
2203{
2205 _IDEC_flags flags(0);
2206 retval.d_raw = __bid64_round_integral_nearest_away(x.d_raw, &flags);
2207 if (BID_INVALID_EXCEPTION & flags) {
2208 errno = EDOM;
2209 }
2210 return retval;
2211}
2212
2213inline
2215{
2217 _IDEC_flags flags(0);
2218 retval.d_raw = __bid128_round_integral_nearest_away(x.d_raw, &flags);
2219 if (BID_INVALID_EXCEPTION & flags) {
2220 errno = EDOM;
2221 }
2222 return retval;
2223}
2224
2225inline
2227{
2228 _IDEC_flags flags(0);
2229 long int rv = __bid32_lround(x.d_raw, &flags);
2230 if (BID_INVALID_EXCEPTION & flags) {
2231 errno = EDOM;
2232 }
2233 return rv;
2234}
2235
2236inline
2238{
2239 _IDEC_flags flags(0);
2240 long int rv = __bid64_lround(x.d_raw, &flags);
2241 if (BID_INVALID_EXCEPTION & flags) {
2242 errno = EDOM;
2243 }
2244 return rv;
2245}
2246
2247inline
2249{
2250 _IDEC_flags flags(0);
2251 long int rv = __bid128_lround(x.d_raw, &flags);
2252 if (BID_INVALID_EXCEPTION & flags) {
2253 errno = EDOM;
2254 }
2255 return rv;
2256}
2257
2258inline
2260{
2262 _IDEC_flags flags(0);
2263 retval.d_raw = __bid32_round_integral_zero(x.d_raw, &flags);
2264 if (BID_INVALID_EXCEPTION & flags) {
2265 errno = EDOM;
2266 }
2267 return retval;
2268}
2269
2270inline
2272{
2274 _IDEC_flags flags(0);
2275 retval.d_raw = __bid64_round_integral_zero(x.d_raw, &flags);
2276 if (BID_INVALID_EXCEPTION & flags) {
2277 errno = EDOM;
2278 }
2279 return retval;
2280}
2281
2282inline
2284{
2286 _IDEC_flags flags(0);
2287 retval.d_raw = __bid128_round_integral_zero(x.d_raw, &flags);
2288 if (BID_INVALID_EXCEPTION & flags) {
2289 errno = EDOM;
2290 }
2291 return retval;
2292}
2293
2294
2295inline
2297{
2298 ValueType32 rv;
2299 _IDEC_flags flags(0);
2300 rv.d_raw = __bid32_fma(x.d_raw, y.d_raw, z.d_raw, &flags);
2301 if (BID_INVALID_EXCEPTION & flags) {
2302 errno = EDOM;
2303 }
2304 return rv;
2305}
2306
2307inline
2309{
2310 ValueType64 rv;
2311 _IDEC_flags flags(0);
2312 rv.d_raw = __bid64_fma(x.d_raw, y.d_raw, z.d_raw, &flags);
2313 if (BID_INVALID_EXCEPTION & flags) {
2314 errno = EDOM;
2315 }
2316 return rv;
2317}
2318
2319inline
2321{
2322 ValueType128 rv;
2323 _IDEC_flags flags(0);
2324 rv.d_raw = __bid128_fma(x.d_raw, y.d_raw, z.d_raw, &flags);
2325 if (BID_INVALID_EXCEPTION & flags) {
2326 errno = EDOM;
2327 }
2328 return rv;
2329}
2330 // Selecting, converting functions
2331
2332inline
2334{
2335 ValueType32 rv;
2336 rv.d_raw = __bid32_abs(value.d_raw);
2337 return rv;
2338}
2339
2340inline
2342{
2343 ValueType64 rv;
2344 rv.d_raw = __bid64_abs(value.d_raw);
2345 return rv;
2346}
2347
2348inline
2350{
2351 ValueType128 rv;
2352 rv.d_raw = __bid128_abs(value.d_raw);
2353 return rv;
2354}
2355
2356inline
2358{
2359 ValueType32 rv;
2360 _IDEC_flags flags(0);
2361 rv.d_raw = __bid32_sqrt(value.d_raw, &flags);
2362 if (BID_INVALID_EXCEPTION & flags) {
2363 errno = EDOM;
2364 }
2365 return rv;
2366}
2367
2368inline
2370{
2371 ValueType64 rv;
2372 _IDEC_flags flags(0);
2373 rv.d_raw = __bid64_sqrt(value.d_raw, &flags);
2374 if (BID_INVALID_EXCEPTION & flags) {
2375 errno = EDOM;
2376 }
2377 return rv;
2378}
2379
2380inline
2382{
2383 ValueType128 rv;
2384 _IDEC_flags flags(0);
2385 rv.d_raw = __bid128_sqrt(value.d_raw, &flags);
2386 if (BID_INVALID_EXCEPTION & flags) {
2387 errno = EDOM;
2388 }
2389 return rv;
2390}
2391
2392inline
2394 ValueType32 y)
2395{
2396 ValueType32 rv;
2397 rv.d_raw = __bid32_copySign(x.d_raw, y.d_raw);
2398 return rv;
2399}
2400
2401inline
2403 ValueType64 y)
2404{
2405 ValueType64 rv;
2406 rv.d_raw = __bid64_copySign(x.d_raw, y.d_raw);
2407 return rv;
2408}
2409
2410inline
2412 ValueType128 y)
2413{
2414 ValueType128 rv;
2415 rv.d_raw = __bid128_copySign(x.d_raw, y.d_raw);
2416 return rv;
2417}
2418
2419inline
2421{
2422 ValueType32 rv;
2423 _IDEC_flags flags(0);
2424 rv.d_raw = __bid32_exp(value.d_raw, &flags);
2425 if (BID_INVALID_EXCEPTION & flags) {
2426 errno = EDOM;
2427 }
2428 if (BID_OVERFLOW_EXCEPTION & flags) {
2429 errno = ERANGE;
2430 }
2431 return rv;
2432}
2433
2434inline
2436{
2437 ValueType64 rv;
2438 _IDEC_flags flags(0);
2439 rv.d_raw = __bid64_exp(value.d_raw, &flags);
2440 if (BID_INVALID_EXCEPTION & flags) {
2441 errno = EDOM;
2442 }
2443 if (BID_OVERFLOW_EXCEPTION & flags) {
2444 errno = ERANGE;
2445 }
2446 return rv;
2447}
2448
2449inline
2451{
2452 ValueType128 rv;
2453 _IDEC_flags flags(0);
2454 rv.d_raw = __bid128_exp(value.d_raw, &flags);
2455 if (BID_INVALID_EXCEPTION & flags) {
2456 errno = EDOM;
2457 }
2458 if (BID_OVERFLOW_EXCEPTION & flags) {
2459 errno = ERANGE;
2460 }
2461 return rv;
2462}
2463
2464inline
2466{
2467 ValueType32 rv;
2468 _IDEC_flags flags(0);
2469 rv.d_raw = __bid32_log(value.d_raw, &flags);
2470 if (BID_INVALID_EXCEPTION & flags) {
2471 errno = EDOM;
2472 }
2473 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2474 errno = ERANGE;
2475 }
2476 return rv;
2477}
2478
2479inline
2481{
2482 ValueType64 rv;
2483 _IDEC_flags flags(0);
2484 rv.d_raw = __bid64_log(value.d_raw, &flags);
2485 if (BID_INVALID_EXCEPTION & flags) {
2486 errno = EDOM;
2487 }
2488 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2489 errno = ERANGE;
2490 }
2491 return rv;
2492}
2493
2494inline
2496{
2497 ValueType128 rv;
2498 _IDEC_flags flags(0);
2499 rv.d_raw = __bid128_log(value.d_raw, &flags);
2500 if (BID_INVALID_EXCEPTION & flags) {
2501 errno = EDOM;
2502 }
2503 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2504 errno = ERANGE;
2505 }
2506 return rv;
2507}
2508
2509inline
2511{
2512 ValueType32 rv;
2513 _IDEC_flags flags(0);
2514 rv.d_raw = __bid32_logb(value.d_raw, &flags);
2515 if (BID_INVALID_EXCEPTION & flags) {
2516 errno = EDOM;
2517 }
2518 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2519 errno = ERANGE;
2520 }
2521 return rv;
2522}
2523
2524inline
2526{
2527 ValueType64 rv;
2528 _IDEC_flags flags(0);
2529 rv.d_raw = __bid64_logb(value.d_raw, &flags);
2530 if (BID_INVALID_EXCEPTION & flags) {
2531 errno = EDOM;
2532 }
2533 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2534 errno = ERANGE;
2535 }
2536 return rv;
2537}
2538
2539inline
2541{
2542 ValueType128 rv;
2543 _IDEC_flags flags(0);
2544 rv.d_raw = __bid128_logb(value.d_raw, &flags);
2545 if (BID_INVALID_EXCEPTION & flags) {
2546 errno = EDOM;
2547 }
2548 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2549 errno = ERANGE;
2550 }
2551 return rv;
2552}
2553
2554inline
2556{
2557 ValueType32 rv;
2558 _IDEC_flags flags(0);
2559 rv.d_raw = __bid32_log10(value.d_raw, &flags);
2560 if (BID_INVALID_EXCEPTION & flags) {
2561 errno = EDOM;
2562 }
2563 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2564 errno = ERANGE;
2565 }
2566 return rv;
2567}
2568
2569inline
2571{
2572 ValueType64 rv;
2573 _IDEC_flags flags(0);
2574 rv.d_raw = __bid64_log10(value.d_raw, &flags);
2575 if (BID_INVALID_EXCEPTION & flags) {
2576 errno = EDOM;
2577 }
2578 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2579 errno = ERANGE;
2580 }
2581 return rv;
2582}
2583
2584inline
2586{
2587 ValueType128 rv;
2588 _IDEC_flags flags(0);
2589 rv.d_raw = __bid128_log10(value.d_raw, &flags);
2590 if (BID_INVALID_EXCEPTION & flags) {
2591 errno = EDOM;
2592 }
2593 if (BID_ZERO_DIVIDE_EXCEPTION & flags) {
2594 errno = ERANGE;
2595 }
2596 return rv;
2597}
2598
2599inline
2601 ValueType32 y)
2602{
2603 ValueType32 rv;
2604 _IDEC_flags flags(0);
2605 rv.d_raw = __bid32_fmod(x.d_raw, y.d_raw, &flags);
2606 if (BID_INVALID_EXCEPTION & flags) {
2607 errno = EDOM;
2608 }
2609 return rv;
2610}
2611
2612inline
2614 ValueType64 y)
2615{
2616 ValueType64 rv;
2617 _IDEC_flags flags(0);
2618 rv.d_raw = __bid64_fmod(x.d_raw, y.d_raw, &flags);
2619 if (BID_INVALID_EXCEPTION & flags) {
2620 errno = EDOM;
2621 }
2622 return rv;
2623}
2624
2625inline
2627 ValueType128 y)
2628{
2629 ValueType128 rv;
2630 _IDEC_flags flags(0);
2631 rv.d_raw = __bid128_fmod(x.d_raw, y.d_raw, &flags);
2632 if (BID_INVALID_EXCEPTION & flags) {
2633 errno = EDOM;
2634 }
2635 return rv;
2636}
2637
2638inline
2640 ValueType32 y)
2641{
2642 ValueType32 rv;
2643 _IDEC_flags flags(0);
2644 rv.d_raw = __bid32_rem(x.d_raw, y.d_raw, &flags);
2645 if (BID_INVALID_EXCEPTION & flags) {
2646 errno = EDOM;
2647 }
2648 return rv;
2649}
2650
2651inline
2653 ValueType64 y)
2654{
2655 ValueType64 rv;
2656 _IDEC_flags flags(0);
2657 rv.d_raw = __bid64_rem(x.d_raw, y.d_raw, &flags);
2658 if (BID_INVALID_EXCEPTION & flags) {
2659 errno = EDOM;
2660 }
2661 return rv;
2662}
2663
2664inline
2666 ValueType128 y)
2667{
2668 ValueType128 rv;
2669 _IDEC_flags flags(0);
2670 rv.d_raw = __bid128_rem(x.d_raw, y.d_raw, &flags);
2671 if (BID_INVALID_EXCEPTION & flags) {
2672 errno = EDOM;
2673 }
2674 return rv;
2675}
2676
2677 // Negation Functions
2678
2679inline
2682{
2683 return Imp::negate(value);
2684}
2685
2686inline
2689{
2690 return Imp::negate(value);
2691}
2692
2693inline
2696{
2697 return Imp::negate(value);
2698}
2699
2700 // Comparison
2701
2702 // Less Than Functions
2703
2704inline
2705bool
2708{
2709 return Imp::less(lhs, rhs);
2710}
2711
2712inline
2713bool
2716{
2717 return Imp::less(lhs, rhs);
2718}
2719
2720inline
2721bool
2724{
2725 return Imp::less(lhs, rhs);
2726}
2727
2728 // Greater Than Functions
2729
2730inline
2731bool
2734{
2735 return Imp::greater(lhs, rhs);
2736}
2737
2738inline
2739bool
2742{
2743 return Imp::greater(lhs, rhs);
2744}
2745
2746inline
2747bool
2750{
2751 return Imp::greater(lhs, rhs);
2752}
2753
2754 // Less Or Equal Functions
2755
2756inline
2757bool
2760{
2761 return Imp::lessEqual(lhs, rhs);
2762}
2763
2764inline
2765bool
2768{
2769 return Imp::lessEqual(lhs, rhs);
2770}
2771
2772inline
2773bool
2776{
2777 return Imp::lessEqual(lhs, rhs);
2778}
2779
2780 // Greater Or Equal Functions
2781
2782inline
2783bool
2786{
2787 return Imp::greaterEqual(lhs, rhs);
2788}
2789
2790inline
2791bool
2794{
2795 return Imp::greaterEqual(lhs, rhs);
2796}
2797
2798inline
2799bool
2802{
2803 return Imp::greaterEqual(lhs, rhs);
2804}
2805
2806 // Equality Functions
2807
2808inline
2809bool
2812{
2813 return Imp::equal(lhs, rhs);
2814}
2815
2816inline
2817bool
2820{
2821 return Imp::equal(lhs, rhs);
2822}
2823
2824inline
2825bool
2828{
2829 return Imp::equal(lhs, rhs);
2830}
2831
2832 // Inequality Functions
2833
2834inline
2835bool
2838{
2839 return Imp::notEqual(lhs, rhs);
2840}
2841
2842inline
2843bool
2846{
2847 return Imp::notEqual(lhs, rhs);
2848}
2849
2850inline
2851bool
2854{
2855 return Imp::notEqual(lhs, rhs);
2856}
2857
2858 // Inter-type Conversion functions
2859
2860inline
2863{
2864 return Imp::convertToDecimal32(input);
2865}
2866
2867inline
2870{
2871 return Imp::convertToDecimal32(input);
2872}
2873
2874inline
2877{
2878 return Imp::convertToDecimal64(input);
2879}
2880
2881inline
2884{
2885 return Imp::convertToDecimal64(input);
2886}
2887
2888inline
2891{
2892 return Imp::convertToDecimal128(input);
2893}
2894
2895inline
2898{
2899 return Imp::convertToDecimal128(input);
2900}
2901
2902 // Binary floating point conversion functions
2903
2904inline
2907{
2908 return Imp::binaryToDecimal32(value);
2909}
2910
2911inline
2914{
2915 return Imp::binaryToDecimal32(value);
2916}
2917
2918inline
2921{
2922 return Imp::binaryToDecimal64(value);
2923}
2924
2925inline
2928{
2929 return Imp::binaryToDecimal64(value);
2930}
2931
2932inline
2935{
2936 return Imp::binaryToDecimal128(value);
2937}
2938
2939inline
2942{
2943 return Imp::binaryToDecimal128(value);
2944}
2945
2946 // makeDecimalRaw Functions
2947
2948inline
2950DecimalImpUtil::makeDecimalRaw32(int significand, int exponent)
2951{
2952 BSLS_ASSERT(-101 <= exponent);
2953 BSLS_ASSERT( exponent <= 90);
2954 BSLS_ASSERT(bsl::max(significand, -significand) <= 9999999);
2955 return Imp::makeDecimalRaw32(significand, exponent);
2956}
2957
2958
2959inline
2961DecimalImpUtil::makeDecimalRaw64(unsigned long long significand, int exponent)
2962{
2963 BSLS_ASSERT(-398 <= exponent);
2964 BSLS_ASSERT( exponent <= 369);
2965 BSLS_ASSERT(significand <= 9999999999999999LL);
2966
2967 return Imp::makeDecimalRaw64(significand, exponent);
2968}
2969
2970inline
2972DecimalImpUtil::makeDecimalRaw64(long long significand, int exponent)
2973{
2974 BSLS_ASSERT(-398 <= exponent);
2975 BSLS_ASSERT( exponent <= 369);
2976 BSLS_ASSERT(std::max(significand, -significand) <= 9999999999999999LL);
2977
2978 return Imp::makeDecimalRaw64(significand, exponent);
2979}
2980
2981inline
2983DecimalImpUtil::makeDecimalRaw64(unsigned int significand, int exponent)
2984{
2985 BSLS_ASSERT(-398 <= exponent);
2986 BSLS_ASSERT( exponent <= 369);
2987
2988 return Imp::makeDecimalRaw64(significand, exponent);
2989}
2990
2991inline
2993DecimalImpUtil::makeDecimalRaw64(int significand, int exponent)
2994{
2995 BSLS_ASSERT(-398 <= exponent);
2996 BSLS_ASSERT( exponent <= 369);
2997 return Imp::makeDecimalRaw64(significand, exponent);
2998}
2999
3000
3001inline
3003DecimalImpUtil::makeDecimalRaw128(unsigned long long significand, int exponent)
3004{
3005 BSLS_ASSERT(-6176 <= exponent);
3006 BSLS_ASSERT( exponent <= 6111);
3007
3008 return Imp::makeDecimalRaw128(significand, exponent);
3009}
3010
3011inline
3013DecimalImpUtil::makeDecimalRaw128(long long significand, int exponent)
3014{
3015 BSLS_ASSERT(-6176 <= exponent);
3016 BSLS_ASSERT( exponent <= 6111);
3017
3018 return Imp::makeDecimalRaw128(significand, exponent);
3019}
3020
3021inline
3023DecimalImpUtil::makeDecimalRaw128(unsigned int significand, int exponent)
3024{
3025 BSLS_ASSERT(-6176 <= exponent);
3026 BSLS_ASSERT( exponent <= 6111);
3027
3028 return Imp::makeDecimalRaw128(significand, exponent);
3029}
3030
3031inline
3033DecimalImpUtil::makeDecimalRaw128(int significand, int exponent)
3034{
3035 BSLS_ASSERT(-6176 <= exponent);
3036 BSLS_ASSERT( exponent <= 6111);
3037
3038 return Imp::makeDecimalRaw128(significand, exponent);
3039}
3040
3041 // IEEE Scale B Functions
3042
3043inline
3046{
3047 ValueType32 result;
3048 _IDEC_flags flags(0);
3049 result.d_raw = __bid32_scalbn(value.d_raw, exponent, &flags);
3050 if (BID_INVALID_EXCEPTION & flags) {
3051 errno = EDOM;
3052 }
3053 if (BID_OVERFLOW_EXCEPTION & flags) {
3054 errno = ERANGE;
3055 }
3056 return result;
3057}
3058
3059inline
3062{
3063 ValueType64 result;
3064 _IDEC_flags flags(0);
3065 result.d_raw = __bid64_scalbn(value.d_raw, exponent, &flags);
3066 if (BID_INVALID_EXCEPTION & flags) {
3067 errno = EDOM;
3068 }
3069 if (BID_OVERFLOW_EXCEPTION & flags) {
3070 errno = ERANGE;
3071 }
3072 return result;
3073}
3074
3075inline
3078{
3079 ValueType128 result;
3080 _IDEC_flags flags(0);
3081 result.d_raw = __bid128_scalbn(value.d_raw, exponent, &flags);
3082 if (BID_INVALID_EXCEPTION & flags) {
3083 errno = EDOM;
3084 }
3085 if (BID_OVERFLOW_EXCEPTION & flags) {
3086 errno = ERANGE;
3087 }
3088 return result;
3089}
3090 // Parsing functions
3091
3092inline
3094DecimalImpUtil::parse32(const char *input)
3095{
3096 return Imp::parse32(input);
3097}
3098
3099inline
3101DecimalImpUtil::parse64(const char *input)
3102{
3103 return Imp::parse64(input);
3104}
3105
3106inline
3109{
3110 return Imp::parse128(input);
3111}
3112
3113inline
3115DecimalImpUtil::parse32(const char *input, unsigned int *status)
3116{
3117 BSLS_ASSERT(0 == *status);
3118 return Imp::parse32(input, status);
3119}
3120
3121inline
3123DecimalImpUtil::parse64(const char *input, unsigned int *status)
3124{
3125 BSLS_ASSERT(0 == *status);
3126 return Imp::parse64(input, status);
3127}
3128
3129inline
3131DecimalImpUtil::parse128(const char *input, unsigned int *status)
3132{
3133 BSLS_ASSERT(0 == *status);
3134 return Imp::parse128(input, status);
3135}
3136
3137 // Densely Packed Conversion Functions
3138inline
3141{
3142 return Imp::convertDPDtoBID(dpd);
3143}
3144
3145inline
3148{
3149 return Imp::convertDPDtoBID(dpd);
3150}
3151
3152inline
3155{
3156 return Imp::convertDPDtoBID(dpd);
3157}
3158
3159inline
3162{
3163 return Imp::convertBIDtoDPD(value);
3164}
3165
3166inline
3169{
3170 return Imp::convertBIDtoDPD(value);
3171}
3172
3173inline
3176{
3177 return Imp::convertBIDtoDPD(value);
3178}
3179 // Binary Integral Conversion Functions
3180
3181inline
3184{
3185 return Imp::convertFromBID(bid);
3186}
3187
3188inline
3191{
3192 return Imp::convertFromBID(bid);
3193}
3194
3195inline
3198{
3199 return Imp::convertFromBID(bid);
3200}
3201
3202inline
3205{
3206 return Imp::convertToBID(value);
3207}
3208
3209inline
3212{
3213 return Imp::convertToBID(value);
3214}
3215
3216inline
3219{
3220 return Imp::convertToBID(value);
3221}
3222
3223} // close package namespace
3224
3225
3226#endif
3227
3228// ----------------------------------------------------------------------------
3229// Copyright 2014 Bloomberg Finance L.P.
3230//
3231// Licensed under the Apache License, Version 2.0 (the "License");
3232// you may not use this file except in compliance with the License.
3233// You may obtain a copy of the License at
3234//
3235// http://www.apache.org/licenses/LICENSE-2.0
3236//
3237// Unless required by applicable law or agreed to in writing, software
3238// distributed under the License is distributed on an "AS IS" BASIS,
3239// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
3240// See the License for the specific language governing permissions and
3241// limitations under the License.
3242// ----------------------------- END-OF-FILE ----------------------------------
3243
3244/** @} */
3245/** @} */
3246/** @} */
Definition bdldfp_decimalformatconfig.h:118
Definition bdldfp_decimalimputil.h:238
static ValueType32 min32() BSLS_KEYWORD_NOEXCEPT
static ValueType32 remainder(ValueType32 x, ValueType32 y)
Definition bdldfp_decimalimputil.h:2639
static ValueType32 trunc(ValueType32 x)
Definition bdldfp_decimalimputil.h:2259
static ValueType64 makeDecimal64(long long int significand, int exponent)
static ValueType32 log(ValueType32 x)
Definition bdldfp_decimalimputil.h:2465
static ValueType128 roundError128() BSLS_KEYWORD_NOEXCEPT
static ValueType128 int32ToDecimal128(int value)
Definition bdldfp_decimalimputil.h:1542
static ValueType64 convertToDecimal64(const ValueType32 &input)
Definition bdldfp_decimalimputil.h:2876
static ValueType128 denormMin128() BSLS_KEYWORD_NOEXCEPT
static ValueType32 normalize(ValueType32 original)
static bool lessEqual(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2758
static ValueType128 makeDecimalRaw128(unsigned long long int significand, int exponent)
static ValueType32 fma(ValueType32 x, ValueType32 y, ValueType32 z)
Definition bdldfp_decimalimputil.h:2296
static ValueType64 max64() BSLS_KEYWORD_NOEXCEPT
static ValueType128 convertToDecimal128(const ValueType32 &input)
Definition bdldfp_decimalimputil.h:2890
static ValueType32 scaleB(ValueType32 value, int exponent)
Definition bdldfp_decimalimputil.h:3045
static ValueType32 signalingNaN32() BSLS_KEYWORD_NOEXCEPT
static ValueType64 epsilon64() BSLS_KEYWORD_NOEXCEPT
static ValueType32 pow(ValueType32 base, ValueType32 exp)
Definition bdldfp_decimalimputil.h:2060
static ValueType64 roundError64() BSLS_KEYWORD_NOEXCEPT
static ValueType64 parse64(const char *input)
Definition bdldfp_decimalimputil.h:3101
static ValueType128 max128() BSLS_KEYWORD_NOEXCEPT
static ValueType32 binaryToDecimal32(float value)
Definition bdldfp_decimalimputil.h:2906
static int format(char *buffer, int length, ValueType64 value, const DecimalFormatConfig &cfg)
static int decompose(int *sign, Uint128 *significand, int *exponent, ValueType128 value)
static long long int llrint(ValueType32 x)
Definition bdldfp_decimalimputil.h:1918
static ValueType64 infinity64() BSLS_KEYWORD_NOEXCEPT
static ValueType128 infinity128() BSLS_KEYWORD_NOEXCEPT
static ValueType32 parse32(const char *input)
Definition bdldfp_decimalimputil.h:3094
static bool notEqual(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2836
static ValueType32 floor(ValueType32 x)
Definition bdldfp_decimalimputil.h:2154
static ValueType32 copySign(ValueType32 x, ValueType32 y)
Definition bdldfp_decimalimputil.h:2393
static ValueType32 convertDPDtoBID(DecimalStorage::Type32 dpd)
Definition bdldfp_decimalimputil.h:3140
static bool less(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2706
Imp::ValueType64 ValueType64
Definition bdldfp_decimalimputil.h:250
static ValueType32 round(ValueType32 x)
Definition bdldfp_decimalimputil.h:2190
static ValueType32 uint32ToDecimal32(unsigned int value)
Definition bdldfp_decimalimputil.h:1550
static bool greater(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2732
static ValueType32 fabs(ValueType32 x)
Definition bdldfp_decimalimputil.h:2333
static ValueType32 fmod(ValueType32 x, ValueType32 y)
Definition bdldfp_decimalimputil.h:2600
static ValueType32 log10(ValueType32 x)
Definition bdldfp_decimalimputil.h:2555
static ValueType64 makeDecimalRaw64(long long int significand, int exponent)
static ValueType32 multiply(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:1670
static ValueType32 convertFromBID(DecimalStorage::Type32 bid)
Definition bdldfp_decimalimputil.h:3183
static ValueType32 divide(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:1698
static int decompose(int *sign, bsls::Types::Uint64 *significand, int *exponent, ValueType64 value)
static ValueType64 min64() BSLS_KEYWORD_NOEXCEPT
static ValueType32 epsilon32() BSLS_KEYWORD_NOEXCEPT
static ValueType32 roundError32() BSLS_KEYWORD_NOEXCEPT
static int decompose(int *sign, unsigned int *significand, int *exponent, ValueType32 value)
static ValueType64 normalize(ValueType64 original)
Imp::ValueType128 ValueType128
Definition bdldfp_decimalimputil.h:251
static ValueType32 makeDecimalRaw32(int significand, int exponent)
Definition bdldfp_decimalimputil.h:2950
static ValueType32 logB(ValueType32 x)
Definition bdldfp_decimalimputil.h:2510
static DecimalStorage::Type32 convertToBID(ValueType32 value)
Definition bdldfp_decimalimputil.h:3204
static int format(char *buffer, int length, ValueType32 value, const DecimalFormatConfig &cfg)
static ValueType64 makeDecimal64(int significand, int exponent)
static long int lround(ValueType32 x)
Definition bdldfp_decimalimputil.h:2226
static ValueType32 convertToDecimal32(const ValueType64 &input)
Definition bdldfp_decimalimputil.h:2862
static ValueType128 parse128(const char *input)
Definition bdldfp_decimalimputil.h:3108
static ValueType128 epsilon128() BSLS_KEYWORD_NOEXCEPT
static ValueType64 int64ToDecimal64(long long int value)
Definition bdldfp_decimalimputil.h:1579
static ValueType32 denormMin32() BSLS_KEYWORD_NOEXCEPT
static ValueType64 binaryToDecimal64(float value)
Definition bdldfp_decimalimputil.h:2920
static ValueType32 quantize(ValueType32 value, ValueType32 exponent)
Definition bdldfp_decimalimputil.h:1721
static int classify(ValueType64 x)
static ValueType32 subtract(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:1644
static ValueType128 uint32ToDecimal128(unsigned int value)
Definition bdldfp_decimalimputil.h:1564
static ValueType64 quietNaN64() BSLS_KEYWORD_NOEXCEPT
static ValueType32 sqrt(ValueType32 x)
Definition bdldfp_decimalimputil.h:2357
static ValueType64 round(ValueType64 x, unsigned int precision)
static int quantizeEqual(ValueType32 *x, ValueType32 y, int exponent)
Definition bdldfp_decimalimputil.h:1805
static ValueType128 quietNaN128() BSLS_KEYWORD_NOEXCEPT
static ValueType128 signalingNaN128() BSLS_KEYWORD_NOEXCEPT
static bool equal(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2810
static ValueType32 uint64ToDecimal32(unsigned long long int value)
Definition bdldfp_decimalimputil.h:1594
static ValueType64 makeDecimalRaw64(unsigned long long int significand, int exponent)
static int classify(ValueType32 x)
static ValueType128 binaryToDecimal128(float value)
Definition bdldfp_decimalimputil.h:2934
static ValueType64 uint32ToDecimal64(unsigned int value)
Definition bdldfp_decimalimputil.h:1557
static ValueType128 round(ValueType128 x, unsigned int precision)
Examples: round(3.14159, 3) ==> 3.142.
static ValueType32 round(ValueType32 x, unsigned int precision)
static ValueType32 nexttoward(ValueType32 from, ValueType128 to)
Definition bdldfp_decimalimputil.h:2006
static int classify(ValueType128 x)
static ValueType32 quietNaN32() BSLS_KEYWORD_NOEXCEPT
static ValueType64 makeInfinity64(bool isNegative=false)
static ValueType32 int64ToDecimal32(long long int value)
Definition bdldfp_decimalimputil.h:1572
static ValueType32 nextafter(ValueType32 from, ValueType32 to)
Definition bdldfp_decimalimputil.h:1952
static ValueType32 exp(ValueType32 x)
Definition bdldfp_decimalimputil.h:2420
static ValueType64 int32ToDecimal64(int value)
Definition bdldfp_decimalimputil.h:1536
static ValueType128 normalize(ValueType128 original)
static ValueType32 negate(ValueType32 value)
Definition bdldfp_decimalimputil.h:2681
static ValueType128 makeDecimalRaw128(long long int significand, int exponent)
static ValueType64 makeDecimal64(unsigned int significand, int exponent)
@ k_STATUS_UNDERFLOW
Definition bdldfp_decimalimputil.h:257
@ k_STATUS_INEXACT
Definition bdldfp_decimalimputil.h:256
@ k_STATUS_OVERFLOW
Definition bdldfp_decimalimputil.h:258
static bool greaterEqual(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:2784
static ValueType32 infinity32() BSLS_KEYWORD_NOEXCEPT
static ValueType32 int32ToDecimal32(int value)
Definition bdldfp_decimalimputil.h:1530
static long int lrint(ValueType32 x)
Definition bdldfp_decimalimputil.h:1885
static ValueType32 max32() BSLS_KEYWORD_NOEXCEPT
static ValueType32 add(ValueType32 lhs, ValueType32 rhs)
Definition bdldfp_decimalimputil.h:1619
static ValueType64 uint64ToDecimal64(unsigned long long int value)
Definition bdldfp_decimalimputil.h:1601
static ValueType128 min128() BSLS_KEYWORD_NOEXCEPT
static DecimalStorage::Type32 convertBIDtoDPD(ValueType32 value)
Definition bdldfp_decimalimputil.h:3161
static ValueType128 uint64ToDecimal128(unsigned long long int value)
Definition bdldfp_decimalimputil.h:1608
static int format(char *buffer, int length, ValueType128 value, const DecimalFormatConfig &cfg)
static ValueType128 int64ToDecimal128(long long int value)
Definition bdldfp_decimalimputil.h:1586
Imp::ValueType32 ValueType32
Definition bdldfp_decimalimputil.h:249
static bool sameQuantum(ValueType32 x, ValueType32 y)
Definition bdldfp_decimalimputil.h:1864
static ValueType64 denormMin64() BSLS_KEYWORD_NOEXCEPT
static ValueType32 ceil(ValueType32 x)
Definition bdldfp_decimalimputil.h:2117
static ValueType64 makeDecimal64(unsigned long long int significand, int exponent)
static ValueType64 signalingNaN64() BSLS_KEYWORD_NOEXCEPT
Definition bdldfp_uint128.h:175
#define BSLS_ASSERT(X)
Definition bsls_assert.h:1804
#define BSLS_IDENT(str)
Definition bsls_ident.h:195
#define BSLS_KEYWORD_NOEXCEPT
Definition bsls_keyword.h:632
Definition bdldfp_decimal.h:712
BID_UINT128 Type128
Definition bdldfp_decimalstorage.h:84
BID_UINT64 Type64
Definition bdldfp_decimalstorage.h:83
BID_UINT32 Type32
Definition bdldfp_decimalstorage.h:82
unsigned long long Uint64
Definition bsls_types.h:137