mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2026-04-20 16:17:38 +00:00
Handle '.' correctly in hex float literal parsing.
There were a couple of different loops that were not handling '.' correctly in APFloat::convertFromHexadecimalString; these mistakes could lead to assertion failures and incorrect rounding for overlong hex float literals. Fixes PR16643. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@186539 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
+20
-30
@@ -319,8 +319,8 @@ trailingHexadecimalFraction(StringRef::iterator p, StringRef::iterator end,
|
||||
else if (digitValue < 8 && digitValue > 0)
|
||||
return lfLessThanHalf;
|
||||
|
||||
/* Otherwise we need to find the first non-zero digit. */
|
||||
while (*p == '0')
|
||||
// Otherwise we need to find the first non-zero digit.
|
||||
while (p != end && (*p == '0' || *p == '.'))
|
||||
p++;
|
||||
|
||||
assert(p != end && "Invalid trailing hexadecimal fraction!");
|
||||
@@ -2300,56 +2300,46 @@ APFloat::opStatus
|
||||
APFloat::convertFromHexadecimalString(StringRef s, roundingMode rounding_mode)
|
||||
{
|
||||
lostFraction lost_fraction = lfExactlyZero;
|
||||
integerPart *significand;
|
||||
unsigned int bitPos, partsCount;
|
||||
StringRef::iterator dot, firstSignificantDigit;
|
||||
|
||||
zeroSignificand();
|
||||
exponent = 0;
|
||||
category = fcNormal;
|
||||
|
||||
significand = significandParts();
|
||||
partsCount = partCount();
|
||||
bitPos = partsCount * integerPartWidth;
|
||||
integerPart *significand = significandParts();
|
||||
unsigned partsCount = partCount();
|
||||
unsigned bitPos = partsCount * integerPartWidth;
|
||||
bool computedTrailingFraction = false;
|
||||
|
||||
/* Skip leading zeroes and any (hexa)decimal point. */
|
||||
// Skip leading zeroes and any (hexa)decimal point.
|
||||
StringRef::iterator begin = s.begin();
|
||||
StringRef::iterator end = s.end();
|
||||
StringRef::iterator dot;
|
||||
StringRef::iterator p = skipLeadingZeroesAndAnyDot(begin, end, &dot);
|
||||
firstSignificantDigit = p;
|
||||
StringRef::iterator firstSignificantDigit = p;
|
||||
|
||||
for (; p != end;) {
|
||||
while (p != end) {
|
||||
integerPart hex_value;
|
||||
|
||||
if (*p == '.') {
|
||||
assert(dot == end && "String contains multiple dots");
|
||||
dot = p++;
|
||||
if (p == end) {
|
||||
break;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
hex_value = hexDigitValue(*p);
|
||||
if (hex_value == -1U) {
|
||||
if (hex_value == -1U)
|
||||
break;
|
||||
}
|
||||
|
||||
p++;
|
||||
|
||||
if (p == end) {
|
||||
break;
|
||||
} else {
|
||||
/* Store the number whilst 4-bit nibbles remain. */
|
||||
if (bitPos) {
|
||||
bitPos -= 4;
|
||||
hex_value <<= bitPos % integerPartWidth;
|
||||
significand[bitPos / integerPartWidth] |= hex_value;
|
||||
} else {
|
||||
lost_fraction = trailingHexadecimalFraction(p, end, hex_value);
|
||||
while (p != end && hexDigitValue(*p) != -1U)
|
||||
p++;
|
||||
break;
|
||||
}
|
||||
// Store the number while we have space.
|
||||
if (bitPos) {
|
||||
bitPos -= 4;
|
||||
hex_value <<= bitPos % integerPartWidth;
|
||||
significand[bitPos / integerPartWidth] |= hex_value;
|
||||
} else if (!computedTrailingFraction) {
|
||||
lost_fraction = trailingHexadecimalFraction(p, end, hex_value);
|
||||
computedTrailingFraction = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user