23#include "llvm/Config/llvm-config.h"
31#define APFLOAT_DISPATCH_ON_SEMANTICS(METHOD_CALL) \
33 if (usesLayout<IEEEFloat>(getSemantics())) \
34 return U.IEEE.METHOD_CALL; \
35 if (usesLayout<DoubleAPFloat>(getSemantics())) \
36 return U.Double.METHOD_CALL; \
37 llvm_unreachable("Unexpected semantics"); \
48#define PackCategoriesIntoKey(_lhs, _rhs) ((_lhs) * 4 + (_rhs))
320 if (Src.maxExponent >= Dst.maxExponent || Src.minExponent <= Dst.minExponent)
328 return Dst.precision >= Src.precision;
366static inline unsigned int
380 unsigned int absExponent;
381 const unsigned int overlargeExponent = 24000;
385 if (p == end || ((*p ==
'-' || *p ==
'+') && (p + 1) == end)) {
389 isNegative = (*p ==
'-');
390 if (*p ==
'-' || *p ==
'+') {
397 if (absExponent >= 10U)
398 return createError(
"Invalid character in exponent");
400 for (; p != end; ++p) {
405 return createError(
"Invalid character in exponent");
407 absExponent = absExponent * 10U +
value;
408 if (absExponent >= overlargeExponent) {
409 absExponent = overlargeExponent;
415 return -(int) absExponent;
417 return (
int) absExponent;
424 int exponentAdjustment) {
425 int unsignedExponent;
426 bool negative, overflow;
432 negative = *p ==
'-';
433 if (*p ==
'-' || *p ==
'+') {
439 unsignedExponent = 0;
441 for (; p != end; ++p) {
446 return createError(
"Invalid character in exponent");
448 unsignedExponent = unsignedExponent * 10 +
value;
449 if (unsignedExponent > 32767) {
455 if (exponentAdjustment > 32767 || exponentAdjustment < -32768)
459 exponent = unsignedExponent;
461 exponent = -exponent;
462 exponent += exponentAdjustment;
463 if (exponent > 32767 || exponent < -32768)
468 exponent = negative ? -32768: 32767;
478 while (p != end && *p ==
'0')
481 if (p != end && *p ==
'.') {
484 if (end - begin == 1)
487 while (p != end && *p ==
'0')
520 return PtrOrErr.takeError();
523 D->firstSigDigit = p;
525 D->normalizedExponent = 0;
527 for (; p != end; ++p) {
530 return createError(
"String contains multiple dots");
540 if (*p !=
'e' && *p !=
'E')
541 return createError(
"Invalid character in significand");
544 if (dot != end && p - begin == 1)
550 return ExpOrErr.takeError();
551 D->exponent = *ExpOrErr;
559 if (p !=
D->firstSigDigit) {
565 while (p != begin && *p ==
'0');
566 while (p != begin && *p ==
'.');
571 D->normalizedExponent = (
D->exponent +
573 - (dot >
D->firstSigDigit && dot < p)));
585 unsigned int digitValue) {
586 unsigned int hexDigit;
592 else if (digitValue < 8 && digitValue > 0)
596 while (p != end && (*p ==
'0' || *p ==
'.'))
600 return createError(
"Invalid trailing hexadecimal fraction!");
602 hexDigit = hexDigitValue(*p);
606 if (hexDigit == UINT_MAX)
616 unsigned int partCount,
645 return lost_fraction;
660 return moreSignificant;
671HUerrBound(
bool inexactMultiply,
unsigned int HUerr1,
unsigned int HUerr2)
673 assert(HUerr1 < 2 || HUerr2 < 2 || (HUerr1 + HUerr2 < 8));
675 if (HUerr1 + HUerr2 == 0)
676 return inexactMultiply * 2;
678 return inexactMultiply + 2 * (HUerr1 + HUerr2);
687 unsigned int count, partBits;
704 if (part - boundary <= boundary - part)
705 return part - boundary;
707 return boundary - part;
710 if (part == boundary) {
716 }
else if (part == boundary - 1) {
733 pow5s[0] = 78125 * 5;
735 unsigned int partsCount[16] = { 1 };
743 *p1 = firstEightPowers[power & 7];
749 for (
unsigned int n = 0; power; power >>= 1, n++) {
756 pc = partsCount[n - 1];
759 if (pow5[pc - 1] == 0)
769 if (p2[result - 1] == 0)
794static const char NaNL[] =
"nan";
795static const char NaNU[] =
"NAN";
802 const char *hexDigitChars)
804 unsigned int result =
count;
810 dst[
count] = hexDigitChars[part & 0xf];
850void IEEEFloat::initialize(
const fltSemantics *ourSemantics) {
853 semantics = ourSemantics;
859void IEEEFloat::freeSignificand() {
861 delete [] significand.parts;
864void IEEEFloat::assign(
const IEEEFloat &rhs) {
865 assert(semantics == rhs.semantics);
868 category = rhs.category;
869 exponent = rhs.exponent;
871 copySignificand(rhs);
874void IEEEFloat::copySignificand(
const IEEEFloat &rhs) {
876 assert(rhs.partCount() >= partCount());
888 exponent = exponentNaN();
891 unsigned numParts = partCount();
904 fill = &fill_storage;
915 unsigned bitsToPreserve = semantics->
precision - 1;
916 unsigned part = bitsToPreserve / 64;
917 bitsToPreserve %= 64;
918 significand[part] &= ((1ULL << bitsToPreserve) - 1);
919 for (part++; part != numParts; ++part)
920 significand[part] = 0;
923 unsigned QNaNBit = semantics->
precision - 2;
951 if (semantics != rhs.semantics) {
953 initialize(rhs.semantics);
964 semantics = rhs.semantics;
965 significand = rhs.significand;
966 exponent = rhs.exponent;
967 category = rhs.category;
985 significandMSB() == 0;
990 isSignificandAllZerosExceptMSB();
993bool IEEEFloat::isSignificandAllOnes()
const {
998 for (
unsigned i = 0; i < PartCount - 1; i++)
1003 const unsigned NumHighBits =
1005 assert(NumHighBits <= integerPartWidth && NumHighBits > 0 &&
1006 "Can not have more high bits to fill than integerPartWidth");
1009 if (~(Parts[PartCount - 1] | HighBitFill))
1015bool IEEEFloat::isSignificandAllOnesExceptLSB()
const {
1024 for (
unsigned i = 0; i < PartCount - 1; i++) {
1025 if (~Parts[i] & ~
unsigned{!i})
1030 const unsigned NumHighBits =
1032 assert(NumHighBits <= integerPartWidth && NumHighBits > 0 &&
1033 "Can not have more high bits to fill than integerPartWidth");
1036 if (~(Parts[PartCount - 1] | HighBitFill | 0x1))
1042bool IEEEFloat::isSignificandAllZeros()
const {
1048 for (
unsigned i = 0; i < PartCount - 1; i++)
1053 const unsigned NumHighBits =
1056 "clear than integerPartWidth");
1057 const integerPart HighBitMask = ~integerPart(0) >> NumHighBits;
1059 if (Parts[PartCount - 1] & HighBitMask)
1065bool IEEEFloat::isSignificandAllZerosExceptMSB()
const {
1069 for (
unsigned i = 0; i < PartCount - 1; i++) {
1074 const unsigned NumHighBits =
1087 isSignificandAllOnesExceptLSB();
1092 isSignificandAllOnes();
1107 if (semantics != rhs.semantics ||
1108 category != rhs.category ||
1117 return std::equal(significandParts(), significandParts() + partCount(),
1118 rhs.significandParts());
1122 initialize(&ourSemantics);
1127 significandParts()[0] =
value;
1132 initialize(&ourSemantics);
1142 initialize(rhs.semantics);
1147 *
this = std::move(rhs);
1152unsigned int IEEEFloat::partCount()
const {
1157 return const_cast<IEEEFloat *
>(
this)->significandParts();
1161 if (partCount() > 1)
1162 return significand.parts;
1164 return &significand.part;
1167void IEEEFloat::zeroSignificand() {
1172void IEEEFloat::incrementSignificand() {
1186 parts = significandParts();
1188 assert(semantics == rhs.semantics);
1189 assert(exponent == rhs.exponent);
1191 return APInt::tcAdd(parts, rhs.significandParts(), 0, partCount());
1197 integerPart borrow) {
1200 parts = significandParts();
1202 assert(semantics == rhs.semantics);
1203 assert(exponent == rhs.exponent);
1212lostFraction IEEEFloat::multiplySignificand(
const IEEEFloat &rhs,
1215 unsigned int partsCount, newPartsCount, precision;
1222 assert(semantics == rhs.semantics);
1230 if (newPartsCount > 4)
1233 fullSignificand = scratch;
1235 lhsSignificand = significandParts();
1236 partsCount = partCount();
1239 rhs.significandParts(), partsCount, partsCount);
1242 omsb =
APInt::tcMSB(fullSignificand, newPartsCount) + 1;
1243 exponent += rhs.exponent;
1257 if (addend.isNonZero()) {
1261 Significand savedSignificand = significand;
1265 unsigned int extendedPrecision;
1268 extendedPrecision = 2 * precision + 1;
1269 if (omsb != extendedPrecision - 1) {
1270 assert(extendedPrecision > omsb);
1272 (extendedPrecision - 1) - omsb);
1273 exponent -= (extendedPrecision - 1) - omsb;
1277 extendedSemantics = *semantics;
1278 extendedSemantics.
precision = extendedPrecision;
1280 if (newPartsCount == 1)
1281 significand.part = fullSignificand[0];
1283 significand.parts = fullSignificand;
1284 semantics = &extendedSemantics;
1297 lost_fraction = extendedAddend.shiftSignificandRight(1);
1299 "Lost precision while shifting addend for fused-multiply-add.");
1301 lost_fraction = addOrSubtractSignificand(extendedAddend,
false);
1304 if (newPartsCount == 1)
1305 fullSignificand[0] = significand.part;
1306 significand = savedSignificand;
1307 semantics = savedSemantics;
1309 omsb =
APInt::tcMSB(fullSignificand, newPartsCount) + 1;
1316 exponent -= precision + 1;
1325 if (omsb > precision) {
1326 unsigned int bits, significantParts;
1329 bits = omsb - precision;
1331 lf =
shiftRight(fullSignificand, significantParts, bits);
1338 if (newPartsCount > 4)
1339 delete [] fullSignificand;
1341 return lost_fraction;
1344lostFraction IEEEFloat::multiplySignificand(
const IEEEFloat &rhs) {
1345 return multiplySignificand(rhs,
IEEEFloat(*semantics));
1349lostFraction IEEEFloat::divideSignificand(
const IEEEFloat &rhs) {
1350 unsigned int bit, i, partsCount;
1356 assert(semantics == rhs.semantics);
1358 lhsSignificand = significandParts();
1359 rhsSignificand = rhs.significandParts();
1360 partsCount = partCount();
1367 divisor = dividend + partsCount;
1370 for (i = 0; i < partsCount; i++) {
1371 dividend[i] = lhsSignificand[i];
1372 divisor[i] = rhsSignificand[i];
1373 lhsSignificand[i] = 0;
1376 exponent -= rhs.exponent;
1378 unsigned int precision = semantics->
precision;
1381 bit = precision -
APInt::tcMSB(divisor, partsCount) - 1;
1388 bit = precision -
APInt::tcMSB(dividend, partsCount) - 1;
1404 for (bit = precision; bit; bit -= 1) {
1428 return lost_fraction;
1431unsigned int IEEEFloat::significandMSB()
const {
1435unsigned int IEEEFloat::significandLSB()
const {
1440lostFraction IEEEFloat::shiftSignificandRight(
unsigned int bits) {
1446 return shiftRight(significandParts(), partCount(), bits);
1450void IEEEFloat::shiftSignificandLeft(
unsigned int bits) {
1451 assert(bits < semantics->precision);
1454 unsigned int partsCount = partCount();
1467 assert(semantics == rhs.semantics);
1471 compare = exponent - rhs.exponent;
1536bool IEEEFloat::roundAwayFromZero(roundingMode rounding_mode,
1538 unsigned int bit)
const {
1545 switch (rounding_mode) {
1583 omsb = significandMSB() + 1;
1589 exponentChange = omsb - semantics->
precision;
1593 if (exponent + exponentChange > semantics->
maxExponent)
1594 return handleOverflow(rounding_mode);
1598 if (exponent + exponentChange < semantics->minExponent)
1599 exponentChange = semantics->
minExponent - exponent;
1602 if (exponentChange < 0) {
1605 shiftSignificandLeft(-exponentChange);
1610 if (exponentChange > 0) {
1614 lf = shiftSignificandRight(exponentChange);
1619 if (omsb > (
unsigned) exponentChange)
1620 omsb -= exponentChange;
1630 exponent == semantics->
maxExponent && isSignificandAllOnes())
1631 return handleOverflow(rounding_mode);
1650 if (roundAwayFromZero(rounding_mode, lost_fraction, 0)) {
1654 incrementSignificand();
1655 omsb = significandMSB() + 1;
1658 if (omsb == (
unsigned) semantics->
precision + 1) {
1669 shiftSignificandRight(1);
1678 exponent == semantics->
maxExponent && isSignificandAllOnes())
1679 return handleOverflow(rounding_mode);
1688 assert(omsb < semantics->precision);
1758lostFraction IEEEFloat::addOrSubtractSignificand(
const IEEEFloat &rhs,
1766 subtract ^=
static_cast<bool>(sign ^ rhs.sign);
1769 bits = exponent - rhs.exponent;
1777 else if (bits > 0) {
1778 lost_fraction = temp_rhs.shiftSignificandRight(bits - 1);
1779 shiftSignificandLeft(1);
1781 lost_fraction = shiftSignificandRight(-bits - 1);
1782 temp_rhs.shiftSignificandLeft(1);
1787 carry = temp_rhs.subtractSignificand
1789 copySignificand(temp_rhs);
1792 carry = subtractSignificand
1811 lost_fraction = temp_rhs.shiftSignificandRight(bits);
1812 carry = addSignificand(temp_rhs);
1814 lost_fraction = shiftSignificandRight(-bits);
1815 carry = addSignificand(rhs);
1823 return lost_fraction;
2008 roundingMode rounding_mode,
2012 fs = addOrSubtractSpecials(rhs,
subtract);
2018 lost_fraction = addOrSubtractSignificand(rhs,
subtract);
2019 fs = normalize(rounding_mode, lost_fraction);
2028 if (category ==
fcZero) {
2042 return addOrSubtract(rhs, rounding_mode,
false);
2048 return addOrSubtract(rhs, rounding_mode,
true);
2057 fs = multiplySpecials(rhs);
2063 fs = normalize(rounding_mode, lost_fraction);
2077 fs = divideSpecials(rhs);
2083 fs = normalize(rounding_mode, lost_fraction);
2094 unsigned int origSign = sign;
2097 fs = remainderSpecials(rhs);
2204 fs = modSpecials(rhs);
2205 unsigned int origSign = sign;
2235 sign ^= multiplicand.sign;
2244 lost_fraction = multiplySignificand(multiplicand, addend);
2245 fs = normalize(rounding_mode, lost_fraction);
2258 fs = multiplySpecials(multiplicand);
2268 fs = addOrSubtract(addend, rounding_mode,
false);
2341 MagicConstant.sign = sign;
2347 fs =
add(MagicConstant, rounding_mode);
2351 subtract(MagicConstant, rounding_mode);
2365 assert(semantics == rhs.semantics);
2397 if (sign == rhs.sign)
2412 if (sign != rhs.sign) {
2443 unsigned int newPartCount, oldPartCount;
2451 oldPartCount = partCount();
2454 bool X86SpecialNan =
false;
2457 (!(*significandParts() & 0x8000000000000000ULL) ||
2458 !(*significandParts() & 0x4000000000000000ULL))) {
2461 X86SpecialNan =
true;
2472 int omsb = significandMSB() + 1;
2473 int exponentChange = omsb - fromSemantics.
precision;
2474 if (exponent + exponentChange < toSemantics.
minExponent)
2475 exponentChange = toSemantics.
minExponent - exponent;
2476 if (exponentChange < shift)
2477 exponentChange = shift;
2478 if (exponentChange < 0) {
2479 shift -= exponentChange;
2480 exponent += exponentChange;
2481 }
else if (omsb <= -shift) {
2482 exponentChange = omsb + shift - 1;
2483 shift -= exponentChange;
2484 exponent += exponentChange;
2495 if (newPartCount > oldPartCount) {
2503 significand.parts = newParts;
2504 }
else if (newPartCount == 1 && oldPartCount != 1) {
2508 newPart = significandParts()[0];
2510 significand.part = newPart;
2514 semantics = &toSemantics;
2523 *losesInfo = (fs !=
opOK);
2524 }
else if (category ==
fcNaN) {
2559 }
else if (category ==
fcZero &&
2587 roundingMode rounding_mode,
bool *isExact)
const {
2590 unsigned int dstPartsCount, truncatedBits;
2599 assert(dstPartsCount <= parts.
size() &&
"Integer too big");
2601 if (category ==
fcZero) {
2608 src = significandParts();
2617 truncatedBits = semantics->
precision -1U - exponent;
2621 unsigned int bits = exponent + 1U;
2627 if (bits < semantics->precision) {
2629 truncatedBits = semantics->
precision - bits;
2643 if (truncatedBits) {
2647 roundAwayFromZero(rounding_mode, lost_fraction, truncatedBits)) {
2667 if (omsb == width &&
2704 fs = convertToSignExtendedInteger(parts, width,
isSigned, rounding_mode,
2708 unsigned int bits, dstPartsCount;
2711 assert(dstPartsCount <= parts.
size() &&
"Integer too big");
2713 if (category ==
fcNaN)
2732 const integerPart *src,
unsigned int srcCount, roundingMode rounding_mode) {
2733 unsigned int omsb, precision, dstCount;
2739 dst = significandParts();
2740 dstCount = partCount();
2745 if (precision <= omsb) {
2746 exponent = omsb - 1;
2751 exponent = precision - 1;
2756 return normalize(rounding_mode, lost_fraction);
2770 return convertFromUnsignedParts(api.
getRawData(), partCount, rounding_mode);
2778 unsigned int srcCount,
bool isSigned,
2791 status = convertFromUnsignedParts(
copy, srcCount, rounding_mode);
2795 status = convertFromUnsignedParts(src, srcCount, rounding_mode);
2815 return convertFromUnsignedParts(api.
getRawData(), partCount, rounding_mode);
2819IEEEFloat::convertFromHexadecimalString(
StringRef s,
2820 roundingMode rounding_mode) {
2828 unsigned partsCount = partCount();
2830 bool computedTrailingFraction =
false;
2838 return PtrOrErr.takeError();
2847 return createError(
"String contains multiple dots");
2852 hex_value = hexDigitValue(*p);
2853 if (hex_value == UINT_MAX)
2863 }
else if (!computedTrailingFraction) {
2866 return FractOrErr.takeError();
2867 lost_fraction = *FractOrErr;
2868 computedTrailingFraction =
true;
2874 return createError(
"Hex strings require an exponent");
2875 if (*p !=
'p' && *p !=
'P')
2876 return createError(
"Invalid character in significand");
2879 if (dot != end && p - begin == 1)
2883 if (p != firstSignificantDigit) {
2892 expAdjustment =
static_cast<int>(
dot - firstSignificantDigit);
2893 if (expAdjustment < 0)
2895 expAdjustment = expAdjustment * 4 - 1;
2905 return ExpOrErr.takeError();
2906 exponent = *ExpOrErr;
2909 return normalize(rounding_mode, lost_fraction);
2913IEEEFloat::roundSignificandWithExponent(
const integerPart *decSigParts,
2914 unsigned sigPartCount,
int exp,
2915 roundingMode rounding_mode) {
2916 unsigned int parts, pow5PartCount;
2927 pow5PartCount =
powerOf5(pow5Parts, exp >= 0 ? exp: -exp);
2929 for (;; parts *= 2) {
2931 unsigned int excessPrecision, truncatedBits;
2935 truncatedBits = excessPrecision;
2938 decSig.makeZero(sign);
2941 sigStatus = decSig.convertFromUnsignedParts(decSigParts, sigPartCount,
2943 powStatus = pow5.convertFromUnsignedParts(pow5Parts, pow5PartCount,
2946 decSig.exponent += exp;
2950 unsigned int powHUerr;
2954 calcLostFraction = decSig.multiplySignificand(pow5);
2955 powHUerr = powStatus !=
opOK;
2957 calcLostFraction = decSig.divideSignificand(pow5);
2960 excessPrecision += (semantics->
minExponent - decSig.exponent);
2961 truncatedBits = excessPrecision;
2962 if (excessPrecision > calcSemantics.
precision)
2963 excessPrecision = calcSemantics.
precision;
2972 (decSig.significandParts(), calcSemantics.
precision - 1) == 1);
2977 excessPrecision, isNearest);
2980 if (HUdistance >= HUerr) {
2981 APInt::tcExtract(significandParts(), partCount(), decSig.significandParts(),
2982 calcSemantics.
precision - excessPrecision,
2987 exponent = (decSig.exponent + semantics->
precision
2988 - (calcSemantics.
precision - excessPrecision));
2992 return normalize(rounding_mode, calcLostFraction);
2998IEEEFloat::convertFromDecimalString(
StringRef str, roundingMode rounding_mode) {
3005 return std::move(Err);
3039 }
else if (
D.normalizedExponent - 1 > INT_MAX / 42039) {
3040 fs = handleOverflow(rounding_mode);
3046 }
else if (
D.normalizedExponent - 1 < INT_MIN / 42039 ||
3047 (
D.normalizedExponent + 1) * 28738 <=
3055 }
else if ((
D.normalizedExponent - 1) * 42039
3058 fs = handleOverflow(rounding_mode);
3061 unsigned int partCount;
3067 partCount =
static_cast<unsigned int>(
D.lastSigDigit -
D.firstSigDigit) + 1;
3085 if (p == str.
end()) {
3090 if (decValue >= 10U) {
3091 delete[] decSignificand;
3092 return createError(
"Invalid character in significand");
3095 val = val * 10 + decValue;
3098 }
while (p <=
D.lastSigDigit && multiplier <= (~ (
integerPart) 0 - 9) / 10);
3102 partCount, partCount + 1,
false);
3106 if (decSignificand[partCount])
3108 }
while (p <=
D.lastSigDigit);
3111 fs = roundSignificandWithExponent(decSignificand, partCount,
3112 D.exponent, rounding_mode);
3114 delete [] decSignificand;
3120bool IEEEFloat::convertFromStringSpecials(
StringRef str) {
3121 const size_t MIN_NAME_SIZE = 3;
3123 if (str.
size() < MIN_NAME_SIZE)
3131 bool IsNegative = str.
front() ==
'-';
3134 if (str.
size() < MIN_NAME_SIZE)
3144 bool IsSignaling = str.
front() ==
's' || str.
front() ==
'S';
3147 if (str.
size() < MIN_NAME_SIZE)
3156 makeNaN(IsSignaling, IsNegative);
3161 if (str.
front() ==
'(') {
3163 if (str.
size() <= 2 || str.
back() !=
')')
3170 unsigned Radix = 10;
3171 if (str[0] ==
'0') {
3172 if (str.
size() > 1 && tolower(str[1]) ==
'x') {
3182 makeNaN(IsSignaling, IsNegative, &Payload);
3196 if (convertFromStringSpecials(str))
3201 size_t slen = str.
size();
3202 sign = *p ==
'-' ? 1 : 0;
3203 if (*p ==
'-' || *p ==
'+') {
3210 if (slen >= 2 && p[0] ==
'0' && (p[1] ==
'x' || p[1] ==
'X')) {
3213 return convertFromHexadecimalString(
StringRef(p + 2, slen - 2),
3217 return convertFromDecimalString(
StringRef(p, slen), rounding_mode);
3261 dst +=
sizeof NaNU - 1;
3266 *dst++ = upperCase ?
'X':
'x';
3268 if (hexDigits > 1) {
3270 memset (dst,
'0', hexDigits - 1);
3271 dst += hexDigits - 1;
3273 *dst++ = upperCase ?
'P':
'p';
3278 dst = convertNormalToHexString (dst, hexDigits, upperCase, rounding_mode);
3284 return static_cast<unsigned int>(dst - p);
3291char *IEEEFloat::convertNormalToHexString(
char *dst,
unsigned int hexDigits,
3293 roundingMode rounding_mode)
const {
3294 unsigned int count, valueBits, shift, partsCount, outputDigits;
3295 const char *hexDigitChars;
3301 *dst++ = upperCase ?
'X':
'x';
3306 significand = significandParts();
3307 partsCount = partCount();
3316 outputDigits = (valueBits - significandLSB () + 3) / 4;
3322 if (hexDigits < outputDigits) {
3328 bits = valueBits - hexDigits * 4;
3330 roundUp = roundAwayFromZero(rounding_mode, fraction, bits);
3332 outputDigits = hexDigits;
3342 while (outputDigits &&
count) {
3346 if (--
count == partsCount)
3349 part = significand[
count] << shift;
3357 if (curDigits > outputDigits)
3358 curDigits = outputDigits;
3359 dst +=
partAsHex (dst, part, curDigits, hexDigitChars);
3360 outputDigits -= curDigits;
3369 *
q = hexDigitChars[hexDigitValue (*q) + 1];
3370 }
while (*q ==
'0');
3374 memset (dst,
'0', outputDigits);
3375 dst += outputDigits;
3388 *dst++ = upperCase ?
'P':
'p';
3397 Arg.
isNaN() ? (uint8_t)0 : (uint8_t)Arg.sign,
3401 return hash_combine((uint8_t)Arg.category, (uint8_t)Arg.sign,
3404 Arg.significandParts(),
3405 Arg.significandParts() + Arg.partCount()));
3417APInt IEEEFloat::convertF80LongDoubleAPFloatToAPInt()
const {
3421 uint64_t myexponent, mysignificand;
3424 myexponent = exponent+16383;
3425 mysignificand = significandParts()[0];
3426 if (myexponent==1 && !(mysignificand & 0x8000000000000000ULL))
3428 }
else if (category==
fcZero) {
3432 myexponent = 0x7fff;
3433 mysignificand = 0x8000000000000000ULL;
3436 myexponent = 0x7fff;
3437 mysignificand = significandParts()[0];
3441 words[0] = mysignificand;
3442 words[1] = ((
uint64_t)(sign & 1) << 15) |
3443 (myexponent & 0x7fffLL);
3444 return APInt(80, words);
3447APInt IEEEFloat::convertPPCDoubleDoubleAPFloatToAPInt()
const {
3472 words[0] = *
u.convertDoubleAPFloatToAPInt().getRawData();
3478 if (
u.isFiniteNonZero() && losesInfo) {
3488 words[1] = *
v.convertDoubleAPFloatToAPInt().getRawData();
3493 return APInt(128, words);
3496template <const fltSemantics &S>
3497APInt IEEEFloat::convertIEEEFloatToAPInt()
const {
3500 constexpr int bias = -(S.minExponent - 1);
3501 constexpr unsigned int trailing_significand_bits = S.precision - 1;
3502 constexpr int integer_bit_part = trailing_significand_bits /
integerPartWidth;
3505 constexpr uint64_t significand_mask = integer_bit - 1;
3506 constexpr unsigned int exponent_bits =
3507 S.sizeInBits - 1 - trailing_significand_bits;
3508 static_assert(exponent_bits < 64);
3516 myexponent = exponent + bias;
3517 std::copy_n(significandParts(), mysignificand.size(),
3518 mysignificand.begin());
3519 if (myexponent == 1 &&
3520 !(significandParts()[integer_bit_part] & integer_bit))
3522 }
else if (category ==
fcZero) {
3523 myexponent = ::exponentZero(S) + bias;
3524 mysignificand.fill(0);
3529 myexponent = ::exponentInf(S) + bias;
3530 mysignificand.fill(0);
3533 myexponent = ::exponentNaN(S) + bias;
3534 std::copy_n(significandParts(), mysignificand.size(),
3535 mysignificand.begin());
3537 std::array<
uint64_t, (S.sizeInBits + 63) / 64> words;
3539 std::copy_n(mysignificand.begin(), mysignificand.size(), words.begin());
3540 if constexpr (significand_mask != 0) {
3542 words[mysignificand.size() - 1] &= significand_mask;
3544 std::fill(words_iter, words.end(),
uint64_t{0});
3545 constexpr size_t last_word = words.size() - 1;
3547 << ((S.sizeInBits - 1) % 64);
3548 words[last_word] |= shifted_sign;
3549 uint64_t shifted_exponent = (myexponent & exponent_mask)
3550 << (trailing_significand_bits % 64);
3551 words[last_word] |= shifted_exponent;
3552 if constexpr (last_word == 0) {
3553 return APInt(S.sizeInBits, words[0]);
3555 return APInt(S.sizeInBits, words);
3558APInt IEEEFloat::convertQuadrupleAPFloatToAPInt()
const {
3559 assert(partCount() == 2);
3560 return convertIEEEFloatToAPInt<semIEEEquad>();
3563APInt IEEEFloat::convertDoubleAPFloatToAPInt()
const {
3565 return convertIEEEFloatToAPInt<semIEEEdouble>();
3568APInt IEEEFloat::convertFloatAPFloatToAPInt()
const {
3570 return convertIEEEFloatToAPInt<semIEEEsingle>();
3573APInt IEEEFloat::convertBFloatAPFloatToAPInt()
const {
3574 assert(partCount() == 1);
3575 return convertIEEEFloatToAPInt<semBFloat>();
3578APInt IEEEFloat::convertHalfAPFloatToAPInt()
const {
3580 return convertIEEEFloatToAPInt<semIEEEhalf>();
3583APInt IEEEFloat::convertFloat8E5M2APFloatToAPInt()
const {
3584 assert(partCount() == 1);
3585 return convertIEEEFloatToAPInt<semFloat8E5M2>();
3588APInt IEEEFloat::convertFloat8E5M2FNUZAPFloatToAPInt()
const {
3589 assert(partCount() == 1);
3590 return convertIEEEFloatToAPInt<semFloat8E5M2FNUZ>();
3593APInt IEEEFloat::convertFloat8E4M3FNAPFloatToAPInt()
const {
3594 assert(partCount() == 1);
3595 return convertIEEEFloatToAPInt<semFloat8E4M3FN>();
3598APInt IEEEFloat::convertFloat8E4M3FNUZAPFloatToAPInt()
const {
3599 assert(partCount() == 1);
3600 return convertIEEEFloatToAPInt<semFloat8E4M3FNUZ>();
3603APInt IEEEFloat::convertFloat8E4M3B11FNUZAPFloatToAPInt()
const {
3604 assert(partCount() == 1);
3605 return convertIEEEFloatToAPInt<semFloat8E4M3B11FNUZ>();
3608APInt IEEEFloat::convertFloatTF32APFloatToAPInt()
const {
3609 assert(partCount() == 1);
3610 return convertIEEEFloatToAPInt<semFloatTF32>();
3619 return convertHalfAPFloatToAPInt();
3622 return convertBFloatAPFloatToAPInt();
3625 return convertFloatAPFloatToAPInt();
3628 return convertDoubleAPFloatToAPInt();
3631 return convertQuadrupleAPFloatToAPInt();
3634 return convertPPCDoubleDoubleAPFloatToAPInt();
3637 return convertFloat8E5M2APFloatToAPInt();
3640 return convertFloat8E5M2FNUZAPFloatToAPInt();
3643 return convertFloat8E4M3FNAPFloatToAPInt();
3646 return convertFloat8E4M3FNUZAPFloatToAPInt();
3649 return convertFloat8E4M3B11FNUZAPFloatToAPInt();
3652 return convertFloatTF32APFloatToAPInt();
3656 return convertF80LongDoubleAPFloatToAPInt();
3661 "Float semantics are not IEEEsingle");
3668 "Float semantics are not IEEEdouble");
3680void IEEEFloat::initFromF80LongDoubleAPInt(
const APInt &api) {
3683 uint64_t myexponent = (i2 & 0x7fff);
3685 uint8_t myintegerbit = mysignificand >> 63;
3690 sign =
static_cast<unsigned int>(i2>>15);
3691 if (myexponent == 0 && mysignificand == 0) {
3693 }
else if (myexponent==0x7fff && mysignificand==0x8000000000000000ULL) {
3695 }
else if ((myexponent == 0x7fff && mysignificand != 0x8000000000000000ULL) ||
3696 (myexponent != 0x7fff && myexponent != 0 && myintegerbit == 0)) {
3698 exponent = exponentNaN();
3699 significandParts()[0] = mysignificand;
3700 significandParts()[1] = 0;
3703 exponent = myexponent - 16383;
3704 significandParts()[0] = mysignificand;
3705 significandParts()[1] = 0;
3711void IEEEFloat::initFromPPCDoubleDoubleAPInt(
const APInt &api) {
3718 initFromDoubleAPInt(
APInt(64, i1));
3734template <const fltSemantics &S>
3735void IEEEFloat::initFromIEEEAPInt(
const APInt &api) {
3739 constexpr uint64_t significand_mask = integer_bit - 1;
3740 constexpr unsigned int trailing_significand_bits = S.precision - 1;
3741 constexpr unsigned int stored_significand_parts =
3743 constexpr unsigned int exponent_bits =
3744 S.sizeInBits - 1 - trailing_significand_bits;
3745 static_assert(exponent_bits < 64);
3747 constexpr int bias = -(S.minExponent - 1);
3751 std::array<integerPart, stored_significand_parts> mysignificand;
3752 std::copy_n(api.
getRawData(), mysignificand.size(), mysignificand.begin());
3753 if constexpr (significand_mask != 0) {
3754 mysignificand[mysignificand.size() - 1] &= significand_mask;
3761 (last_word >> (trailing_significand_bits % 64)) & exponent_mask;
3764 assert(partCount() == mysignificand.size());
3766 sign =
static_cast<unsigned int>(last_word >> ((S.sizeInBits - 1) % 64));
3768 bool all_zero_significand =
3771 bool is_zero = myexponent == 0 && all_zero_significand;
3774 if (myexponent - bias == ::exponentInf(S) && all_zero_significand) {
3783 is_nan = myexponent - bias == ::exponentNaN(S) && !all_zero_significand;
3785 bool all_ones_significand =
3786 std::all_of(mysignificand.begin(), mysignificand.end() - 1,
3787 [](
integerPart bits) { return bits == ~integerPart{0}; }) &&
3788 (!significand_mask ||
3789 mysignificand[mysignificand.size() - 1] == significand_mask);
3790 is_nan = myexponent - bias == ::exponentNaN(S) && all_ones_significand;
3798 std::copy_n(mysignificand.begin(), mysignificand.size(),
3799 significandParts());
3809 exponent = myexponent - bias;
3810 std::copy_n(mysignificand.begin(), mysignificand.size(), significandParts());
3811 if (myexponent == 0)
3812 exponent = S.minExponent;
3814 significandParts()[mysignificand.size()-1] |= integer_bit;
3817void IEEEFloat::initFromQuadrupleAPInt(
const APInt &api) {
3818 initFromIEEEAPInt<semIEEEquad>(api);
3821void IEEEFloat::initFromDoubleAPInt(
const APInt &api) {
3822 initFromIEEEAPInt<semIEEEdouble>(api);
3825void IEEEFloat::initFromFloatAPInt(
const APInt &api) {
3826 initFromIEEEAPInt<semIEEEsingle>(api);
3829void IEEEFloat::initFromBFloatAPInt(
const APInt &api) {
3830 initFromIEEEAPInt<semBFloat>(api);
3833void IEEEFloat::initFromHalfAPInt(
const APInt &api) {
3834 initFromIEEEAPInt<semIEEEhalf>(api);
3837void IEEEFloat::initFromFloat8E5M2APInt(
const APInt &api) {
3838 initFromIEEEAPInt<semFloat8E5M2>(api);
3841void IEEEFloat::initFromFloat8E5M2FNUZAPInt(
const APInt &api) {
3842 initFromIEEEAPInt<semFloat8E5M2FNUZ>(api);
3845void IEEEFloat::initFromFloat8E4M3FNAPInt(
const APInt &api) {
3846 initFromIEEEAPInt<semFloat8E4M3FN>(api);
3849void IEEEFloat::initFromFloat8E4M3FNUZAPInt(
const APInt &api) {
3850 initFromIEEEAPInt<semFloat8E4M3FNUZ>(api);
3853void IEEEFloat::initFromFloat8E4M3B11FNUZAPInt(
const APInt &api) {
3854 initFromIEEEAPInt<semFloat8E4M3B11FNUZ>(api);
3857void IEEEFloat::initFromFloatTF32APInt(
const APInt &api) {
3858 initFromIEEEAPInt<semFloatTF32>(api);
3865 return initFromHalfAPInt(api);
3867 return initFromBFloatAPInt(api);
3869 return initFromFloatAPInt(api);
3871 return initFromDoubleAPInt(api);
3873 return initFromF80LongDoubleAPInt(api);
3875 return initFromQuadrupleAPInt(api);
3877 return initFromPPCDoubleDoubleAPInt(api);
3879 return initFromFloat8E5M2APInt(api);
3881 return initFromFloat8E5M2FNUZAPInt(api);
3883 return initFromFloat8E4M3FNAPInt(api);
3885 return initFromFloat8E4M3FNUZAPInt(api);
3887 return initFromFloat8E4M3B11FNUZAPInt(api);
3889 return initFromFloatTF32APInt(api);
3896void IEEEFloat::makeLargest(
bool Negative) {
3903 exponent = semantics->maxExponent;
3907 unsigned PartCount = partCount();
3908 memset(significand, 0xFF,
sizeof(
integerPart)*(PartCount - 1));
3912 const unsigned NumUnusedHighBits =
3913 PartCount*integerPartWidth - semantics->precision;
3914 significand[PartCount - 1] = (NumUnusedHighBits < integerPartWidth)
3925void IEEEFloat::makeSmallest(
bool Negative) {
3932 exponent = semantics->minExponent;
3936void IEEEFloat::makeSmallestNormalized(
bool Negative) {
3945 exponent = semantics->minExponent;
3950 initFromAPInt(&Sem, API);
3953IEEEFloat::IEEEFloat(
float f) {
3957IEEEFloat::IEEEFloat(
double d) {
3963 Buffer.
append(Str.begin(), Str.end());
3968 void AdjustToPrecision(
APInt &significand,
3969 int &exp,
unsigned FormatPrecision) {
3973 unsigned bitsRequired = (FormatPrecision * 196 + 58) / 59;
3975 if (bits <= bitsRequired)
return;
3977 unsigned tensRemovable = (bits - bitsRequired) * 59 / 196;
3978 if (!tensRemovable)
return;
3980 exp += tensRemovable;
3985 if (tensRemovable & 1)
3987 tensRemovable >>= 1;
3988 if (!tensRemovable)
break;
3992 significand = significand.
udiv(divisor);
4000 int &exp,
unsigned FormatPrecision) {
4001 unsigned N = buffer.
size();
4002 if (
N <= FormatPrecision)
return;
4005 unsigned FirstSignificant =
N - FormatPrecision;
4012 if (buffer[FirstSignificant - 1] <
'5') {
4013 while (FirstSignificant <
N && buffer[FirstSignificant] ==
'0')
4016 exp += FirstSignificant;
4017 buffer.
erase(&buffer[0], &buffer[FirstSignificant]);
4023 for (
unsigned I = FirstSignificant;
I !=
N; ++
I) {
4024 if (buffer[
I] ==
'9') {
4033 if (FirstSignificant ==
N) {
4034 exp += FirstSignificant;
4040 exp += FirstSignificant;
4041 buffer.
erase(&buffer[0], &buffer[FirstSignificant]);
4046 unsigned FormatMaxPadding,
bool TruncateZero)
const {
4050 return append(Str,
"-Inf");
4052 return append(Str,
"+Inf");
4054 case fcNaN:
return append(Str,
"NaN");
4060 if (!FormatMaxPadding) {
4062 append(Str,
"0.0E+0");
4065 if (FormatPrecision > 1)
4066 Str.append(FormatPrecision - 1,
'0');
4067 append(Str,
"e+00");
4081 int exp = exponent - ((int) semantics->precision - 1);
4083 semantics->precision,
4088 if (!FormatPrecision) {
4096 FormatPrecision = 2 + semantics->precision * 59 / 196;
4101 exp += trailingZeros;
4107 }
else if (exp > 0) {
4109 significand = significand.
zext(semantics->precision + exp);
4110 significand <<= exp;
4124 unsigned precision = semantics->precision + (137 * texp + 136) / 59;
4128 significand = significand.
zext(precision);
4129 APInt five_to_the_i(precision, 5);
4131 if (texp & 1) significand *= five_to_the_i;
4135 five_to_the_i *= five_to_the_i;
4139 AdjustToPrecision(significand, exp, FormatPrecision);
4145 if (precision < 4) {
4148 significand = significand.
zext(precision);
4150 APInt ten(precision, 10);
4151 APInt digit(precision, 0);
4153 bool inTrail =
true;
4154 while (significand != 0) {
4162 if (inTrail && !d) exp++;
4169 assert(!buffer.
empty() &&
"no characters in buffer!");
4173 AdjustToPrecision(buffer, exp, FormatPrecision);
4175 unsigned NDigits = buffer.
size();
4178 bool FormatScientific;
4179 if (!FormatMaxPadding)
4180 FormatScientific =
true;
4186 FormatScientific = ((
unsigned) exp > FormatMaxPadding ||
4187 NDigits + (
unsigned) exp > FormatPrecision);
4190 int MSD = exp + (int) (NDigits - 1);
4193 FormatScientific =
false;
4197 FormatScientific = ((
unsigned) -MSD) > FormatMaxPadding;
4203 if (FormatScientific) {
4204 exp += (NDigits - 1);
4206 Str.push_back(buffer[NDigits-1]);
4208 if (NDigits == 1 && TruncateZero)
4211 for (
unsigned I = 1;
I != NDigits; ++
I)
4212 Str.push_back(buffer[NDigits-1-
I]);
4214 if (!TruncateZero && FormatPrecision > NDigits - 1)
4215 Str.append(FormatPrecision - NDigits + 1,
'0');
4217 Str.push_back(TruncateZero ?
'E' :
'e');
4219 Str.push_back(exp >= 0 ?
'+' :
'-');
4220 if (exp < 0) exp = -exp;
4223 expbuf.
push_back((
char) (
'0' + (exp % 10)));
4227 if (!TruncateZero && expbuf.
size() < 2)
4229 for (
unsigned I = 0, E = expbuf.
size();
I != E; ++
I)
4230 Str.push_back(expbuf[E-1-
I]);
4236 for (
unsigned I = 0;
I != NDigits; ++
I)
4237 Str.push_back(buffer[NDigits-1-
I]);
4246 int NWholeDigits = exp + (int) NDigits;
4249 if (NWholeDigits > 0) {
4251 Str.push_back(buffer[NDigits-
I-1]);
4254 unsigned NZeros = 1 + (
unsigned) -NWholeDigits;
4258 for (
unsigned Z = 1; Z != NZeros; ++Z)
4262 for (;
I != NDigits; ++
I)
4263 Str.push_back(buffer[NDigits-
I-1]);
4266bool IEEEFloat::getExactInverse(
APFloat *inv)
const {
4268 if (!isFiniteNonZero())
4273 if (significandLSB() != semantics->precision - 1)
4278 if (reciprocal.
divide(*
this, rmNearestTiesToEven) != opOK)
4287 reciprocal.significandLSB() == reciprocal.semantics->
precision - 1);
4290 *inv =
APFloat(reciprocal, *semantics);
4295int IEEEFloat::getExactLog2Abs()
const {
4303 for (
int i = 0; i < PartCount; ++i) {
4309 if (exponent != semantics->minExponent)
4312 int CountrParts = 0;
4313 for (
int i = 0; i < PartCount;
4315 if (Parts[i] != 0) {
4316 return exponent - semantics->precision + CountrParts +
4324bool IEEEFloat::isSignaling()
const {
4360 if (isSignaling()) {
4361 result = opInvalidOp;
4363 makeNaN(
false, isNegative(),
nullptr);
4368 makeSmallest(
false);
4372 if (isSmallest() && isNegative()) {
4381 if (isLargest() && !isNegative()) {
4389 category = fcInfinity;
4390 exponent = semantics->maxExponent + 1;
4404 bool WillCrossBinadeBoundary =
4405 exponent != semantics->minExponent && isSignificandAllZeros();
4423 if (WillCrossBinadeBoundary) {
4439 bool WillCrossBinadeBoundary = !isDenormal() && isSignificandAllOnes();
4441 if (WillCrossBinadeBoundary) {
4445 assert(exponent != semantics->maxExponent &&
4446 "We can not increment an exponent beyond the maxExponent allowed"
4447 " by the given floating point semantics.");
4450 incrementSignificand();
4464 return ::exponentNaN(*semantics);
4468 return ::exponentInf(*semantics);
4472 return ::exponentZero(*semantics);
4475void IEEEFloat::makeInf(
bool Negative) {
4478 makeNaN(
false, Negative);
4481 category = fcInfinity;
4487void IEEEFloat::makeZero(
bool Negative) {
4498void IEEEFloat::makeQuiet() {
4506 return IEEEFloat::IEK_NaN;
4508 return IEEEFloat::IEK_Zero;
4510 return IEEEFloat::IEK_Inf;
4512 return Arg.exponent;
4517 Normalized.exponent += SignificandBits;
4518 Normalized.normalize(IEEEFloat::rmNearestTiesToEven,
lfExactlyZero);
4519 return Normalized.exponent - SignificandBits;
4523 auto MaxExp =
X.getSemantics().maxExponent;
4524 auto MinExp =
X.getSemantics().minExponent;
4532 int SignificandBits =
X.getSemantics().precision - 1;
4533 int MaxIncrement = MaxExp - (MinExp - SignificandBits) + 1;
4536 X.exponent += std::clamp(Exp, -MaxIncrement - 1, MaxIncrement);
4547 if (Exp == IEEEFloat::IEK_NaN) {
4553 if (Exp == IEEEFloat::IEK_Inf)
4558 Exp = Exp == IEEEFloat::IEK_Zero ? 0 : Exp + 1;
4559 return scalbn(Val, -Exp, RM);
4592 Floats(new
APFloat[2]{std::move(
First), std::move(Second)}) {
4614 Floats[0] =
RHS.Floats[0];
4615 Floats[1] =
RHS.Floats[1];
4616 }
else if (
this != &
RHS) {
4634 Floats[0] = std::move(z);
4635 Floats[1].makeZero(
false);
4639 auto AComparedToC = a.compareAbsoluteValue(c);
4652 Floats[0] = std::move(z);
4653 Floats[1].makeZero(
false);
4662 Status |= Floats[1].subtract(z, RM);
4663 Status |= Floats[1].add(c, RM);
4664 Status |= Floats[1].add(zz, RM);
4668 Status |= Floats[1].subtract(z, RM);
4669 Status |= Floats[1].add(a, RM);
4670 Status |= Floats[1].add(zz, RM);
4688 Floats[0] = std::move(z);
4689 Floats[1].makeZero(
false);
4693 Status |= Floats[0].add(zz, RM);
4695 Floats[1].makeZero(
false);
4698 Floats[1] = std::move(z);
4699 Status |= Floats[1].subtract(Floats[0], RM);
4700 Status |= Floats[1].add(zz, RM);
4706 const DoubleAPFloat &RHS,
4726 LHS.isNegative() !=
RHS.isNegative()) {
4727 Out.makeNaN(
false, Out.isNegative(),
nullptr);
4748 return Out.addImpl(
A, AA,
C,
CC, RM);
4753 return addWithSpecial(*
this,
RHS, *
this, RM);
4766 const auto &
LHS = *
this;
4793 Out.makeNaN(
false,
false,
nullptr);
4805 "Special cases not handled exhaustively");
4812 if (!
T.isFiniteNonZero()) {
4814 Floats[1].makeZero(
false);
4836 Status |= U.add(Tau, RM);
4839 if (!U.isFinite()) {
4840 Floats[1].makeZero(
false);
4899 Floats[0].changeSign();
4900 Floats[1].changeSign();
4905 auto Result = Floats[0].compareAbsoluteValue(
RHS.Floats[0]);
4908 Result = Floats[1].compareAbsoluteValue(
RHS.Floats[1]);
4910 auto Against = Floats[0].isNegative() ^ Floats[1].isNegative();
4911 auto RHSAgainst =
RHS.Floats[0].isNegative() ^
RHS.Floats[1].isNegative();
4912 if (Against && !RHSAgainst)
4914 if (!Against && RHSAgainst)
4916 if (!Against && !RHSAgainst)
4918 if (Against && RHSAgainst)
4925 return Floats[0].getCategory();
4931 Floats[0].makeInf(Neg);
4932 Floats[1].makeZero(
false);
4936 Floats[0].makeZero(Neg);
4937 Floats[1].makeZero(
false);
4950 Floats[0].makeSmallest(Neg);
4951 Floats[1].makeZero(
false);
4958 Floats[0].changeSign();
4959 Floats[1].makeZero(
false);
4963 Floats[0].makeNaN(SNaN, Neg, fill);
4964 Floats[1].makeZero(
false);
4968 auto Result = Floats[0].compare(
RHS.Floats[0]);
4971 return Floats[1].compare(
RHS.Floats[1]);
4976 return Floats[0].bitwiseIsEqual(
RHS.Floats[0]) &&
4977 Floats[1].bitwiseIsEqual(
RHS.Floats[1]);
4989 Floats[0].bitcastToAPInt().getRawData()[0],
4990 Floats[1].bitcastToAPInt().getRawData()[0],
5007 auto Ret = Tmp.
next(nextDown);
5014 unsigned int Width,
bool IsSigned,
5033 unsigned int InputSize,
5044 unsigned int InputSize,
5054 unsigned int HexDigits,
5064 (Floats[0].isDenormal() || Floats[1].isDenormal() ||
5066 Floats[0] != Floats[0] + Floats[1]);
5096 return Floats[0].isInteger() && Floats[1].isInteger();
5100 unsigned FormatPrecision,
5101 unsigned FormatMaxPadding,
5102 bool TruncateZero)
const {
5105 .
toString(Str, FormatPrecision, FormatMaxPadding, TruncateZero);
5133 scalbn(Arg.Floats[1], Exp, RM));
5140 APFloat Second = Arg.Floats[1];
5142 Second =
scalbn(Second, -Exp, RM);
5148APFloat::Storage::Storage(IEEEFloat
F,
const fltSemantics &Semantics) {
5149 if (usesLayout<IEEEFloat>(Semantics)) {
5150 new (&
IEEE) IEEEFloat(std::move(
F));
5153 if (usesLayout<DoubleAPFloat>(Semantics)) {
5156 DoubleAPFloat(Semantics,
APFloat(std::move(
F), S),
5169 if (APFloat::usesLayout<detail::IEEEFloat>(Arg.
getSemantics()))
5171 if (APFloat::usesLayout<detail::DoubleAPFloat>(Arg.
getSemantics()))
5179 assert(StatusOrErr &&
"Invalid floating point representation");
5203 usesLayout<IEEEFloat>(ToSemantics))
5204 return U.IEEE.convert(ToSemantics, RM, losesInfo);
5206 usesLayout<DoubleAPFloat>(ToSemantics)) {
5209 *
this =
APFloat(ToSemantics, U.IEEE.bitcastToAPInt());
5213 usesLayout<IEEEFloat>(ToSemantics)) {
5214 auto Ret = getIEEE().
convert(ToSemantics, RM, losesInfo);
5215 *
this =
APFloat(std::move(getIEEE()), ToSemantics);
5228 OS << Buffer <<
"\n";
5231#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
5245 bool *isExact)
const {
5249 rounding_mode, isExact);
5251 result =
APInt(bitWidth, parts);
5259 "Float semantics is not representable by IEEEdouble");
5272 "Float semantics is not representable by IEEEsingle");
5283#undef APFLOAT_DISPATCH_ON_SEMANTICS
#define PackCategoriesIntoKey(_lhs, _rhs)
A macro used to combine two fcCategory enums into one key which can be used in a switch statement to ...
This file declares a class to represent arbitrary precision floating point values and provide a varie...
#define APFLOAT_DISPATCH_ON_SEMANTICS(METHOD_CALL)
This file implements the APSInt class, which is a simple class that represents an arbitrary sized int...
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
#define LLVM_DUMP_METHOD
Mark debug helper function definitions like dump() that should not be stripped from debug builds.
Looks at all the uses of the given value Returns the Liveness deduced from the uses of this value Adds all uses that cause the result to be MaybeLive to MaybeLiveRetUses If the result is MaybeLiveUses might be modified but its content should be ignored(since it might not be complete). DeadArgumentEliminationPass
Given that RA is a live value
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
static bool isSigned(unsigned int Opcode)
Utilities for dealing with flags related to floating point properties and mode controls.
This file defines a hash set that can be used to remove duplication of nodes in a graph.
static bool isZero(Value *V, const DataLayout &DL, DominatorTree *DT, AssumptionCache *AC)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
void Profile(FoldingSetNodeID &NID) const
Used to insert APFloat objects, or objects that contain APFloat objects, into FoldingSets.
opStatus divide(const APFloat &RHS, roundingMode RM)
bool getExactInverse(APFloat *inv) const
opStatus convert(const fltSemantics &ToSemantics, roundingMode RM, bool *losesInfo)
double convertToDouble() const
Converts this APFloat to host double value.
void toString(SmallVectorImpl< char > &Str, unsigned FormatPrecision=0, unsigned FormatMaxPadding=3, bool TruncateZero=true) const
opStatus add(const APFloat &RHS, roundingMode RM)
static APFloat getAllOnesValue(const fltSemantics &Semantics)
Returns a float which is bitcasted from an all one value int.
const fltSemantics & getSemantics() const
opStatus convertFromSignExtendedInteger(const integerPart *Input, unsigned int InputSize, bool IsSigned, roundingMode RM)
opStatus convertFromAPInt(const APInt &Input, bool IsSigned, roundingMode RM)
unsigned int convertToHexString(char *DST, unsigned int HexDigits, bool UpperCase, roundingMode RM) const
float convertToFloat() const
Converts this APFloat to host float value.
opStatus fusedMultiplyAdd(const APFloat &Multiplicand, const APFloat &Addend, roundingMode RM)
opStatus remainder(const APFloat &RHS)
APInt bitcastToAPInt() const
opStatus convertToInteger(MutableArrayRef< integerPart > Input, unsigned int Width, bool IsSigned, roundingMode RM, bool *IsExact) const
opStatus next(bool nextDown)
FPClassTest classify() const
Return the FPClassTest which will return true for the value.
opStatus mod(const APFloat &RHS)
Expected< opStatus > convertFromString(StringRef, roundingMode)
void print(raw_ostream &) const
opStatus roundToIntegral(roundingMode RM)
opStatus convertFromZeroExtendedInteger(const integerPart *Input, unsigned int InputSize, bool IsSigned, roundingMode RM)
Class for arbitrary precision integers.
APInt udiv(const APInt &RHS) const
Unsigned division operation.
static void tcSetBit(WordType *, unsigned bit)
Set the given bit of a bignum. Zero-based.
static APInt getAllOnes(unsigned numBits)
Return an APInt of a specified width with all bits set.
static void tcSet(WordType *, WordType, unsigned)
Sets the least significant part of a bignum to the input value, and zeroes out higher parts.
static void udivrem(const APInt &LHS, const APInt &RHS, APInt &Quotient, APInt &Remainder)
Dual division/remainder interface.
static int tcExtractBit(const WordType *, unsigned bit)
Extract the given bit of a bignum; returns 0 or 1. Zero-based.
APInt zext(unsigned width) const
Zero extend to a new width.
uint64_t getZExtValue() const
Get zero extended value.
static WordType tcAdd(WordType *, const WordType *, WordType carry, unsigned)
DST += RHS + CARRY where CARRY is zero or one. Returns the carry flag.
static void tcExtract(WordType *, unsigned dstCount, const WordType *, unsigned srcBits, unsigned srcLSB)
Copy the bit vector of width srcBITS from SRC, starting at bit srcLSB, to DST, of dstCOUNT parts,...
unsigned getActiveBits() const
Compute the number of active bits in the value.
APInt trunc(unsigned width) const
Truncate to new width.
static int tcCompare(const WordType *, const WordType *, unsigned)
Comparison (unsigned) of two bignums.
static APInt floatToBits(float V)
Converts a float to APInt bits.
static void tcAssign(WordType *, const WordType *, unsigned)
Assign one bignum to another.
unsigned getBitWidth() const
Return the number of bits in the APInt.
static void tcShiftRight(WordType *, unsigned Words, unsigned Count)
Shift a bignum right Count bits.
static void tcFullMultiply(WordType *, const WordType *, const WordType *, unsigned, unsigned)
DST = LHS * RHS, where DST has width the sum of the widths of the operands.
unsigned getNumWords() const
Get the number of words.
bool isNegative() const
Determine sign of this APInt.
@ APINT_BITS_PER_WORD
Bits in a word.
static void tcClearBit(WordType *, unsigned bit)
Clear the given bit of a bignum. Zero-based.
static WordType tcDecrement(WordType *dst, unsigned parts)
Decrement a bignum in-place. Return the borrow flag.
unsigned countr_zero() const
Count the number of trailing zero bits.
static unsigned tcLSB(const WordType *, unsigned n)
Returns the bit number of the least or most significant set bit of a number.
static void tcShiftLeft(WordType *, unsigned Words, unsigned Count)
Shift a bignum left Count bits.
static bool tcIsZero(const WordType *, unsigned)
Returns true if a bignum is zero, false otherwise.
static unsigned tcMSB(const WordType *parts, unsigned n)
Returns the bit number of the most significant set bit of a number.
float bitsToFloat() const
Converts APInt bits to a float.
static int tcMultiplyPart(WordType *dst, const WordType *src, WordType multiplier, WordType carry, unsigned srcParts, unsigned dstParts, bool add)
DST += SRC * MULTIPLIER + PART if add is true DST = SRC * MULTIPLIER + PART if add is false.
static WordType tcSubtract(WordType *, const WordType *, WordType carry, unsigned)
DST -= RHS + CARRY where CARRY is zero or one. Returns the carry flag.
static void tcNegate(WordType *, unsigned)
Negate a bignum in-place.
static APInt doubleToBits(double V)
Converts a double to APInt bits.
static WordType tcIncrement(WordType *dst, unsigned parts)
Increment a bignum in-place. Return the carry flag.
double bitsToDouble() const
Converts APInt bits to a double.
const uint64_t * getRawData() const
This function returns a pointer to the internal storage of the APInt.
static APInt getZero(unsigned numBits)
Get the '0' value for the specified bit-width.
void lshrInPlace(unsigned ShiftAmt)
Logical right-shift this APInt by ShiftAmt in place.
An arbitrary precision integer that knows its signedness.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
size_t size() const
size - Get the array size.
Lightweight error class with error context and mandatory checking.
static ErrorSuccess success()
Create a success value.
Tagged union holding either a T or a Error.
FoldingSetNodeID - This class is used to gather all the unique data bits of a node.
MutableArrayRef - Represent a mutable reference to an array (0 or more elements consecutively in memo...
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
iterator erase(const_iterator CI)
void append(ItTy in_start, ItTy in_end)
Add the specified range to the end of the SmallVector.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
bool getAsInteger(unsigned Radix, T &Result) const
Parse the current string as an integer of the specified radix.
bool starts_with(StringRef Prefix) const
Check if this string starts with the given Prefix.
constexpr bool empty() const
empty - Check if the string is empty.
StringRef drop_front(size_t N=1) const
Return a StringRef equal to 'this' but with the first N elements dropped.
char back() const
back - Get the last character in the string.
StringRef slice(size_t Start, size_t End) const
Return a reference to the substring from [Start, End).
constexpr size_t size() const
size - Get the string size.
char front() const
front - Get the first character in the string.
bool equals(StringRef RHS) const
equals - Check for string equality, this is more efficient than compare() when the relative ordering ...
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
void makeSmallestNormalized(bool Neg)
DoubleAPFloat & operator=(const DoubleAPFloat &RHS)
LLVM_READONLY int getExactLog2() const
opStatus remainder(const DoubleAPFloat &RHS)
opStatus multiply(const DoubleAPFloat &RHS, roundingMode RM)
fltCategory getCategory() const
bool bitwiseIsEqual(const DoubleAPFloat &RHS) const
LLVM_READONLY int getExactLog2Abs() const
opStatus convertFromAPInt(const APInt &Input, bool IsSigned, roundingMode RM)
opStatus convertFromZeroExtendedInteger(const integerPart *Input, unsigned int InputSize, bool IsSigned, roundingMode RM)
APInt bitcastToAPInt() const
bool getExactInverse(APFloat *inv) const
Expected< opStatus > convertFromString(StringRef, roundingMode)
opStatus subtract(const DoubleAPFloat &RHS, roundingMode RM)
cmpResult compareAbsoluteValue(const DoubleAPFloat &RHS) const
opStatus convertToInteger(MutableArrayRef< integerPart > Input, unsigned int Width, bool IsSigned, roundingMode RM, bool *IsExact) const
void makeSmallest(bool Neg)
opStatus next(bool nextDown)
opStatus divide(const DoubleAPFloat &RHS, roundingMode RM)
bool isSmallestNormalized() const
opStatus mod(const DoubleAPFloat &RHS)
DoubleAPFloat(const fltSemantics &S)
void toString(SmallVectorImpl< char > &Str, unsigned FormatPrecision, unsigned FormatMaxPadding, bool TruncateZero=true) const
void makeLargest(bool Neg)
cmpResult compare(const DoubleAPFloat &RHS) const
opStatus roundToIntegral(roundingMode RM)
opStatus convertFromSignExtendedInteger(const integerPart *Input, unsigned int InputSize, bool IsSigned, roundingMode RM)
opStatus fusedMultiplyAdd(const DoubleAPFloat &Multiplicand, const DoubleAPFloat &Addend, roundingMode RM)
unsigned int convertToHexString(char *DST, unsigned int HexDigits, bool UpperCase, roundingMode RM) const
opStatus add(const DoubleAPFloat &RHS, roundingMode RM)
void makeNaN(bool SNaN, bool Neg, const APInt *fill)
unsigned int convertToHexString(char *dst, unsigned int hexDigits, bool upperCase, roundingMode) const
Write out a hexadecimal representation of the floating point value to DST, which must be of sufficien...
fltCategory getCategory() const
bool isFiniteNonZero() const
opStatus add(const IEEEFloat &, roundingMode)
bool needsCleanup() const
Returns whether this instance allocated memory.
APInt bitcastToAPInt() const
bool isNegative() const
IEEE-754R isSignMinus: Returns true if and only if the current value is negative.
opStatus convertFromZeroExtendedInteger(const integerPart *, unsigned int, bool, roundingMode)
bool isNaN() const
Returns true if and only if the float is a quiet or signaling NaN.
opStatus convertFromAPInt(const APInt &, bool, roundingMode)
opStatus roundToIntegral(roundingMode)
double convertToDouble() const
float convertToFloat() const
cmpResult compareAbsoluteValue(const IEEEFloat &) const
opStatus fusedMultiplyAdd(const IEEEFloat &, const IEEEFloat &, roundingMode)
void makeInf(bool Neg=false)
Expected< opStatus > convertFromString(StringRef, roundingMode)
bool isSmallestNormalized() const
Returns true if this is the smallest (by magnitude) normalized finite number in the given semantics.
bool isLargest() const
Returns true if and only if the number has the largest possible finite magnitude in the current seman...
bool isFinite() const
Returns true if and only if the current value is zero, subnormal, or normal.
void makeNaN(bool SNaN=false, bool Neg=false, const APInt *fill=nullptr)
opStatus convertToInteger(MutableArrayRef< integerPart >, unsigned int, bool, roundingMode, bool *) const
friend int ilogb(const IEEEFloat &Arg)
Returns the exponent of the internal representation of the APFloat.
opStatus remainder(const IEEEFloat &)
IEEE remainder.
IEEEFloat & operator=(const IEEEFloat &)
opStatus divide(const IEEEFloat &, roundingMode)
friend IEEEFloat scalbn(IEEEFloat X, int Exp, roundingMode)
Returns: X * 2^Exp for integral exponents.
bool bitwiseIsEqual(const IEEEFloat &) const
Bitwise comparison for equality (QNaNs compare equal, 0!=-0).
bool isInteger() const
Returns true if and only if the number is an exact integer.
IEEEFloat(const fltSemantics &)
cmpResult compare(const IEEEFloat &) const
IEEE comparison with another floating point number (NaNs compare unordered, 0==-0).
opStatus subtract(const IEEEFloat &, roundingMode)
bool isInfinity() const
IEEE-754R isInfinite(): Returns true if and only if the float is infinity.
const fltSemantics & getSemantics() const
bool isZero() const
Returns true if and only if the float is plus or minus zero.
bool isSignaling() const
Returns true if and only if the float is a signaling NaN.
opStatus convertFromSignExtendedInteger(const integerPart *, unsigned int, bool, roundingMode)
opStatus convert(const fltSemantics &, roundingMode, bool *)
IEEEFloat::convert - convert a value of one floating point type to another.
void makeZero(bool Neg=false)
bool isDenormal() const
IEEE-754R isSubnormal(): Returns true if and only if the float is a denormal.
bool isSmallest() const
Returns true if and only if the number has the smallest possible non-zero magnitude in the current se...
opStatus mod(const IEEEFloat &)
C fmod, or llvm frem.
opStatus multiply(const IEEEFloat &, roundingMode)
An opaque object representing a hash code.
This class implements an extremely fast bulk output stream that can only output to a stream.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
IEEEFloat scalbn(IEEEFloat X, int Exp, IEEEFloat::roundingMode)
static void tcSetLeastSignificantBits(APInt::WordType *dst, unsigned parts, unsigned bits)
hash_code hash_value(const IEEEFloat &Arg)
IEEEFloat frexp(const IEEEFloat &Val, int &Exp, IEEEFloat::roundingMode RM)
int ilogb(const IEEEFloat &Arg)
std::error_code status(const Twine &path, file_status &result, bool follow=true)
Get file status as if by POSIX stat().
This is an optimization pass for GlobalISel generic memory operations.
static unsigned int partAsHex(char *dst, APFloatBase::integerPart part, unsigned int count, const char *hexDigitChars)
static constexpr fltSemantics semBogus
static const char infinityL[]
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
hash_code hash_value(const FixedPointSemantics &Val)
int popcount(T Value) noexcept
Count the number of set bits in a value.
static constexpr unsigned int partCountForBits(unsigned int bits)
static unsigned int HUerrBound(bool inexactMultiply, unsigned int HUerr1, unsigned int HUerr2)
static unsigned int powerOf5(APFloatBase::integerPart *dst, unsigned int power)
static constexpr APFloatBase::ExponentType exponentZero(const fltSemantics &semantics)
static Expected< int > totalExponent(StringRef::iterator p, StringRef::iterator end, int exponentAdjustment)
std::error_code inconvertibleErrorCode()
The value returned by this function can be returned from convertToErrorCode for Error values where no...
static constexpr fltSemantics semIEEEquad
const unsigned int maxPowerOfFiveExponent
static char * writeUnsignedDecimal(char *dst, unsigned int n)
static constexpr fltSemantics semFloat8E4M3FNUZ
const unsigned int maxPrecision
static constexpr fltSemantics semIEEEdouble
APFloat frexp(const APFloat &X, int &Exp, APFloat::roundingMode RM)
Equivalent of C standard library function.
int countr_zero(T Val)
Count number of 0's from the least significant bit to the most stopping at the first 1.
static constexpr fltSemantics semFloat8E4M3FN
static const char infinityU[]
lostFraction
Enum that represents what fraction of the LSB truncated bits of an fp number represent.
static constexpr fltSemantics semPPCDoubleDouble
static Error interpretDecimal(StringRef::iterator begin, StringRef::iterator end, decimalInfo *D)
static constexpr fltSemantics semFloat8E5M2FNUZ
bool isFinite(const Loop *L)
Return true if this loop can be assumed to run for a finite number of iterations.
FPClassTest
Floating-point class tests, supported by 'is_fpclass' intrinsic.
const unsigned int maxPowerOfFiveParts
static constexpr fltSemantics semIEEEsingle
APFloat scalbn(APFloat X, int Exp, APFloat::roundingMode RM)
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
static constexpr APFloatBase::ExponentType exponentNaN(const fltSemantics &semantics)
static Error createError(const Twine &Err)
static constexpr fltSemantics semIEEEhalf
static constexpr fltSemantics semPPCDoubleDoubleLegacy
static lostFraction shiftRight(APFloatBase::integerPart *dst, unsigned int parts, unsigned int bits)
static constexpr fltSemantics semFloat8E5M2
@ First
Helpers to iterate all locations in the MemoryEffectsBase class.
static const char hexDigitsUpper[]
const unsigned int maxExponent
static unsigned int decDigitValue(unsigned int c)
static constexpr fltSemantics semFloat8E4M3B11FNUZ
auto count(R &&Range, const E &Element)
Wrapper function around std::count to count the number of times an element Element occurs in the give...
static lostFraction combineLostFractions(lostFraction moreSignificant, lostFraction lessSignificant)
static Expected< StringRef::iterator > skipLeadingZeroesAndAnyDot(StringRef::iterator begin, StringRef::iterator end, StringRef::iterator *dot)
RoundingMode
Rounding mode.
OutputIt copy(R &&Range, OutputIt Out)
static constexpr fltSemantics semX87DoubleExtended
OutputIt move(R &&Range, OutputIt Out)
Provide wrappers to std::move which take ranges instead of having to pass begin/end explicitly.
static constexpr fltSemantics semFloatTF32
static constexpr APFloatBase::ExponentType exponentInf(const fltSemantics &semantics)
static lostFraction lostFractionThroughTruncation(const APFloatBase::integerPart *parts, unsigned int partCount, unsigned int bits)
static APFloatBase::integerPart ulpsFromBoundary(const APFloatBase::integerPart *parts, unsigned int bits, bool isNearest)
static char * writeSignedDecimal(char *dst, int value)
hash_code hash_combine(const Ts &...args)
Combine values into a single hash_code.
static constexpr fltSemantics semBFloat
static Expected< lostFraction > trailingHexadecimalFraction(StringRef::iterator p, StringRef::iterator end, unsigned int digitValue)
void consumeError(Error Err)
Consume a Error without doing anything.
static Expected< int > readExponent(StringRef::iterator begin, StringRef::iterator end)
hash_code hash_combine_range(InputIteratorT first, InputIteratorT last)
Compute a hash_code for a sequence of values.
constexpr uint64_t NextPowerOf2(uint64_t A)
Returns the next power of two (in 64-bits) that is strictly greater than A.
static const char hexDigitsLower[]
Implement std::hash so that hash_code can be used in STL containers.
static const llvm::fltSemantics & EnumToSemantics(Semantics S)
static const fltSemantics & IEEEsingle() LLVM_READNONE
static constexpr roundingMode rmNearestTiesToAway
cmpResult
IEEE-754R 5.11: Floating Point Comparison Relations.
static constexpr roundingMode rmTowardNegative
static ExponentType semanticsMinExponent(const fltSemantics &)
static constexpr roundingMode rmNearestTiesToEven
static unsigned int semanticsSizeInBits(const fltSemantics &)
static unsigned getSizeInBits(const fltSemantics &Sem)
Returns the size of the floating point number (in bits) in the given semantics.
static const fltSemantics & Float8E4M3FN() LLVM_READNONE
static const fltSemantics & PPCDoubleDouble() LLVM_READNONE
static constexpr roundingMode rmTowardZero
static const fltSemantics & x87DoubleExtended() LLVM_READNONE
uninitializedTag
Convenience enum used to construct an uninitialized APFloat.
static const fltSemantics & IEEEquad() LLVM_READNONE
static const fltSemantics & Float8E4M3B11FNUZ() LLVM_READNONE
static const fltSemantics & Bogus() LLVM_READNONE
A Pseudo fltsemantic used to construct APFloats that cannot conflict with anything real.
static ExponentType semanticsMaxExponent(const fltSemantics &)
static unsigned int semanticsPrecision(const fltSemantics &)
static const fltSemantics & IEEEdouble() LLVM_READNONE
static const fltSemantics & Float8E5M2() LLVM_READNONE
static Semantics SemanticsToEnum(const llvm::fltSemantics &Sem)
static constexpr unsigned integerPartWidth
static const fltSemantics & IEEEhalf() LLVM_READNONE
APInt::WordType integerPart
static constexpr roundingMode rmTowardPositive
static bool isRepresentableAsNormalIn(const fltSemantics &Src, const fltSemantics &Dst)
static const fltSemantics & Float8E4M3FNUZ() LLVM_READNONE
static const fltSemantics & BFloat() LLVM_READNONE
static const fltSemantics & FloatTF32() LLVM_READNONE
static const fltSemantics & Float8E5M2FNUZ() LLVM_READNONE
fltCategory
Category of internally-represented number.
opStatus
IEEE-754R 7: Default exception handling.
int32_t ExponentType
A signed type to represent a floating point numbers unbiased exponent.
static unsigned int semanticsIntSizeInBits(const fltSemantics &, bool)
const char * lastSigDigit
const char * firstSigDigit
bool isRepresentableBy(const fltSemantics &S) const
APFloatBase::ExponentType maxExponent
fltNonfiniteBehavior nonFiniteBehavior
APFloatBase::ExponentType minExponent
fltNanEncoding nanEncoding