Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
96 changes: 48 additions & 48 deletions stl/inc/xcharconv_ryu.h
Original file line number Diff line number Diff line change
Expand Up @@ -1121,7 +1121,7 @@ _NODISCARD inline __floating_decimal_32 __f2d(const uint32_t __ieeeMantissa, con

// Step 4: Find the shortest decimal representation in the interval of valid representations.
int32_t __removed = 0;
uint32_t __output;
uint32_t _Output;
if (__vmIsTrailingZeros || __vrIsTrailingZeros) {
// General case, which happens rarely (~4.0%).
while (__vp / 10 > __vm / 10) {
Expand Down Expand Up @@ -1152,7 +1152,7 @@ _NODISCARD inline __floating_decimal_32 __f2d(const uint32_t __ieeeMantissa, con
__lastRemovedDigit = 4;
}
// We need to take __vr + 1 if __vr is outside bounds or we need to round up.
__output = __vr + ((__vr == __vm && (!__acceptBounds || !__vmIsTrailingZeros)) || __lastRemovedDigit >= 5);
_Output = __vr + ((__vr == __vm && (!__acceptBounds || !__vmIsTrailingZeros)) || __lastRemovedDigit >= 5);
} else {
// Specialized for the common case (~96.0%). Percentages below are relative to this.
// Loop iterations below (approximately):
Expand All @@ -1165,13 +1165,13 @@ _NODISCARD inline __floating_decimal_32 __f2d(const uint32_t __ieeeMantissa, con
++__removed;
}
// We need to take __vr + 1 if __vr is outside bounds or we need to round up.
__output = __vr + (__vr == __vm || __lastRemovedDigit >= 5);
_Output = __vr + (__vr == __vm || __lastRemovedDigit >= 5);
}
const int32_t __exp = __e10 + __removed;

__floating_decimal_32 __fd;
__fd.__exponent = __exp;
__fd.__mantissa = __output;
__fd.__mantissa = _Output;
return __fd;
}

Expand Down Expand Up @@ -1302,9 +1302,9 @@ _NODISCARD inline to_chars_result _Large_integer_to_chars(char* const _First, ch
_NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _Last, const __floating_decimal_32 __v,
chars_format _Fmt, const uint32_t __ieeeMantissa, const uint32_t __ieeeExponent) {
// Step 5: Print the decimal representation.
uint32_t __output = __v.__mantissa;
uint32_t _Output = __v.__mantissa;
int32_t _Ryu_exponent = __v.__exponent;
const uint32_t __olength = __decimalLength9(__output);
const uint32_t __olength = __decimalLength9(_Output);
int32_t _Scientific_exponent = _Ryu_exponent + static_cast<int32_t>(__olength) - 1;

if (_Fmt == chars_format{}) {
Expand Down Expand Up @@ -1344,7 +1344,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
}

if (_Fmt == chars_format::fixed) {
// Example: __output == 1729, __olength == 4
// Example: _Output == 1729, __olength == 4

// _Ryu_exponent | Printed | _Whole_digits | _Total_fixed_length | Notes
// --------------|----------|---------------|----------------------|---------------------------------------
Expand All @@ -1366,7 +1366,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
uint32_t _Total_fixed_length;
if (_Ryu_exponent >= 0) { // cases "172900" and "1729"
_Total_fixed_length = static_cast<uint32_t>(_Whole_digits);
if (__output == 1) {
if (_Output == 1) {
// Rounding can affect the number of digits.
// For example, 1e11f is exactly "99999997952" which is 11 digits instead of 12.
// We can use a lookup table to detect this and adjust the total length.
Expand Down Expand Up @@ -1439,28 +1439,28 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
_Mid = _First + _Total_fixed_length;
}

while (__output >= 10000) {
while (_Output >= 10000) {
#ifdef __clang__ // TRANSITION, LLVM-38217
const uint32_t __c = __output - 10000 * (__output / 10000);
const uint32_t __c = _Output - 10000 * (_Output / 10000);
#else
const uint32_t __c = __output % 10000;
const uint32_t __c = _Output % 10000;
#endif
__output /= 10000;
_Output /= 10000;
const uint32_t __c0 = (__c % 100) << 1;
const uint32_t __c1 = (__c / 100) << 1;
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __c0, 2);
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __c1, 2);
}
if (__output >= 100) {
const uint32_t __c = (__output % 100) << 1;
__output /= 100;
if (_Output >= 100) {
const uint32_t __c = (_Output % 100) << 1;
_Output /= 100;
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __c, 2);
}
if (__output >= 10) {
const uint32_t __c = __output << 1;
if (_Output >= 10) {
const uint32_t __c = _Output << 1;
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __c, 2);
} else {
*--_Mid = static_cast<char>('0' + __output);
*--_Mid = static_cast<char>('0' + _Output);
}

if (_Ryu_exponent > 0) { // case "172900" with _Can_use_ryu
Expand Down Expand Up @@ -1491,32 +1491,32 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La

// Print the decimal digits.
uint32_t __i = 0;
while (__output >= 10000) {
while (_Output >= 10000) {
#ifdef __clang__ // TRANSITION, LLVM-38217
const uint32_t __c = __output - 10000 * (__output / 10000);
const uint32_t __c = _Output - 10000 * (_Output / 10000);
#else
const uint32_t __c = __output % 10000;
const uint32_t __c = _Output % 10000;
#endif
__output /= 10000;
_Output /= 10000;
const uint32_t __c0 = (__c % 100) << 1;
const uint32_t __c1 = (__c / 100) << 1;
_CSTD memcpy(__result + __olength - __i - 1, __DIGIT_TABLE + __c0, 2);
_CSTD memcpy(__result + __olength - __i - 3, __DIGIT_TABLE + __c1, 2);
__i += 4;
}
if (__output >= 100) {
const uint32_t __c = (__output % 100) << 1;
__output /= 100;
if (_Output >= 100) {
const uint32_t __c = (_Output % 100) << 1;
_Output /= 100;
_CSTD memcpy(__result + __olength - __i - 1, __DIGIT_TABLE + __c, 2);
__i += 2;
}
if (__output >= 10) {
const uint32_t __c = __output << 1;
if (_Output >= 10) {
const uint32_t __c = _Output << 1;
// We can't use memcpy here: the decimal dot goes between these two digits.
__result[2] = __DIGIT_TABLE[__c + 1];
__result[0] = __DIGIT_TABLE[__c];
} else {
__result[0] = static_cast<char>('0' + __output);
__result[0] = static_cast<char>('0' + _Output);
}

// Print decimal point if needed.
Expand Down Expand Up @@ -1809,7 +1809,7 @@ _NODISCARD inline __floating_decimal_64 __d2d(const uint64_t __ieeeMantissa, con
// Step 4: Find the shortest decimal representation in the interval of valid representations.
int32_t __removed = 0;
uint8_t __lastRemovedDigit = 0;
uint64_t __output;
uint64_t _Output;
// On average, we remove ~2 digits.
if (__vmIsTrailingZeros || __vrIsTrailingZeros) {
// General case, which happens rarely (~0.7%).
Expand Down Expand Up @@ -1853,7 +1853,7 @@ _NODISCARD inline __floating_decimal_64 __d2d(const uint64_t __ieeeMantissa, con
__lastRemovedDigit = 4;
}
// We need to take __vr + 1 if __vr is outside bounds or we need to round up.
__output = __vr + ((__vr == __vm && (!__acceptBounds || !__vmIsTrailingZeros)) || __lastRemovedDigit >= 5);
_Output = __vr + ((__vr == __vm && (!__acceptBounds || !__vmIsTrailingZeros)) || __lastRemovedDigit >= 5);
} else {
// Specialized for the common case (~99.3%). Percentages below are relative to this.
bool __roundUp = false;
Expand Down Expand Up @@ -1887,22 +1887,22 @@ _NODISCARD inline __floating_decimal_64 __d2d(const uint64_t __ieeeMantissa, con
++__removed;
}
// We need to take __vr + 1 if __vr is outside bounds or we need to round up.
__output = __vr + (__vr == __vm || __roundUp);
_Output = __vr + (__vr == __vm || __roundUp);
}
const int32_t __exp = __e10 + __removed;

__floating_decimal_64 __fd;
__fd.__exponent = __exp;
__fd.__mantissa = __output;
__fd.__mantissa = _Output;
return __fd;
}

_NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _Last, const __floating_decimal_64 __v,
chars_format _Fmt, const double __f) {
// Step 5: Print the decimal representation.
uint64_t __output = __v.__mantissa;
uint64_t _Output = __v.__mantissa;
int32_t _Ryu_exponent = __v.__exponent;
const uint32_t __olength = __decimalLength17(__output);
const uint32_t __olength = __decimalLength17(_Output);
int32_t _Scientific_exponent = _Ryu_exponent + static_cast<int32_t>(__olength) - 1;

if (_Fmt == chars_format{}) {
Expand Down Expand Up @@ -1942,7 +1942,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
}

if (_Fmt == chars_format::fixed) {
// Example: __output == 1729, __olength == 4
// Example: _Output == 1729, __olength == 4

// _Ryu_exponent | Printed | _Whole_digits | _Total_fixed_length | Notes
// --------------|----------|---------------|----------------------|---------------------------------------
Expand All @@ -1964,7 +1964,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
uint32_t _Total_fixed_length;
if (_Ryu_exponent >= 0) { // cases "172900" and "1729"
_Total_fixed_length = static_cast<uint32_t>(_Whole_digits);
if (__output == 1) {
if (_Output == 1) {
// Rounding can affect the number of digits.
// For example, 1e23 is exactly "99999999999999991611392" which is 23 digits instead of 24.
// We can use a lookup table to detect this and adjust the total length.
Expand Down Expand Up @@ -2056,13 +2056,13 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La

// We prefer 32-bit operations, even on 64-bit platforms.
// We have at most 17 digits, and uint32_t can store 9 digits.
// If __output doesn't fit into uint32_t, we cut off 8 digits,
// If _Output doesn't fit into uint32_t, we cut off 8 digits,
// so the rest will fit into uint32_t.
if ((__output >> 32) != 0) {
if ((_Output >> 32) != 0) {
// Expensive 64-bit division.
const uint64_t __q = __div1e8(__output);
uint32_t __output2 = static_cast<uint32_t>(__output - 100000000 * __q);
__output = __q;
const uint64_t __q = __div1e8(_Output);
uint32_t __output2 = static_cast<uint32_t>(_Output - 100000000 * __q);
_Output = __q;

const uint32_t __c = __output2 % 10000;
__output2 /= 10000;
Expand All @@ -2077,7 +2077,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __d0, 2);
_CSTD memcpy(_Mid -= 2, __DIGIT_TABLE + __d1, 2);
}
uint32_t __output2 = static_cast<uint32_t>(__output);
uint32_t __output2 = static_cast<uint32_t>(_Output);
while (__output2 >= 10000) {
#ifdef __clang__ // TRANSITION, LLVM-38217
const uint32_t __c = __output2 - 10000 * (__output2 / 10000);
Expand Down Expand Up @@ -2132,13 +2132,13 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
uint32_t __i = 0;
// We prefer 32-bit operations, even on 64-bit platforms.
// We have at most 17 digits, and uint32_t can store 9 digits.
// If __output doesn't fit into uint32_t, we cut off 8 digits,
// If _Output doesn't fit into uint32_t, we cut off 8 digits,
// so the rest will fit into uint32_t.
if ((__output >> 32) != 0) {
if ((_Output >> 32) != 0) {
// Expensive 64-bit division.
const uint64_t __q = __div1e8(__output);
uint32_t __output2 = static_cast<uint32_t>(__output) - 100000000 * static_cast<uint32_t>(__q);
__output = __q;
const uint64_t __q = __div1e8(_Output);
uint32_t __output2 = static_cast<uint32_t>(_Output) - 100000000 * static_cast<uint32_t>(__q);
_Output = __q;

const uint32_t __c = __output2 % 10000;
__output2 /= 10000;
Expand All @@ -2153,7 +2153,7 @@ _NODISCARD inline to_chars_result __to_chars(char* const _First, char* const _La
_CSTD memcpy(__result + __olength - __i - 7, __DIGIT_TABLE + __d1, 2);
__i += 8;
}
uint32_t __output2 = static_cast<uint32_t>(__output);
uint32_t __output2 = static_cast<uint32_t>(_Output);
while (__output2 >= 10000) {
#ifdef __clang__ // TRANSITION, LLVM-38217
const uint32_t __c = __output2 - 10000 * (__output2 / 10000);
Expand Down
10 changes: 6 additions & 4 deletions tests/std/tests/P0067R5_charconv/test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,8 @@ void initialize_randomness(mt19937_64& mt64, const int argc, char** const argv)

puts("Successfully seeded mt64. First three values:");
for (int i = 0; i < 3; ++i) {
printf("0x%016llX\n", mt64());
// libc++ uses long for 64-bit values.
Comment thread
StephanTLavavej marked this conversation as resolved.
printf("0x%016llX\n", static_cast<unsigned long long>(mt64()));
}
}

Expand Down Expand Up @@ -575,7 +576,8 @@ void assert_message_bits(const bool b, const char* const msg, const uint32_t bit

void assert_message_bits(const bool b, const char* const msg, const uint64_t bits) {
if (!b) {
fprintf(stderr, "%s failed for 0x%016llX\n", msg, bits);
// libc++ uses long for 64-bit values.
fprintf(stderr, "%s failed for 0x%016llX\n", msg, static_cast<unsigned long long>(bits));
fprintf(stderr, "This is a randomized test.\n");
fprintf(stderr, "DO NOT IGNORE/RERUN THIS FAILURE.\n");
fprintf(stderr, "You must report it to the STL maintainers.\n");
Expand Down Expand Up @@ -1098,8 +1100,8 @@ int main(int argc, char** argv) {
printf("Total time: %lld ms\n", ms);

if (ms < 3'000) {
puts("That was fast. Consider retuning PrefixesToTest and FractionBits.");
puts("That was fast. Consider tuning PrefixesToTest and FractionBits to test more cases.");
} else if (ms > 30'000) {
puts("That was slow. Consider retuning PrefixesToTest and FractionBits.");
puts("That was slow. Consider tuning PrefixesToTest and FractionBits to test fewer cases.");
}
}
2 changes: 1 addition & 1 deletion tests/std/tests/P0220R1_searchers/test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -433,7 +433,7 @@ void test_case_randomized_cases() {

if (elapsed > 10s) {
cout << "test_case_randomized_cases() took " << duration_cast<milliseconds>(elapsed).count() << " ms.\n";
cout << "Consider retuning Needles and Haystacks.\n";
cout << "Consider tuning Needles and Haystacks to test fewer cases.\n";
}
}

Expand Down