1 // std::from_chars implementation for floating-point types -*- C++ -*- 2 3 // Copyright (C) 2020-2022 Free Software Foundation, Inc. 4 // 5 // This file is part of the GNU ISO C++ Library. This library is free 6 // software; you can redistribute it and/or modify it under the 7 // terms of the GNU General Public License as published by the 8 // Free Software Foundation; either version 3, or (at your option) 9 // any later version. 10 11 // This library is distributed in the hope that it will be useful, 12 // but WITHOUT ANY WARRANTY; without even the implied warranty of 13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 // GNU General Public License for more details. 15 16 // Under Section 7 of GPL version 3, you are granted additional 17 // permissions described in the GCC Runtime Library Exception, version 18 // 3.1, as published by the Free Software Foundation. 19 20 // You should have received a copy of the GNU General Public License and 21 // a copy of the GCC Runtime Library Exception along with this program; 22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 // <http://www.gnu.org/licenses/>. 24 25 // 26 // ISO C++ 14882:2017 27 // 23.2.9 Primitive numeric input conversion [utility.from.chars] 28 // 29 30 // Prefer to use std::pmr::string if possible, which requires the cxx11 ABI. 31 #define _GLIBCXX_USE_CXX11_ABI 1 32 33 #include <algorithm> 34 #include <array> 35 #include <charconv> 36 #include <bit> 37 #include <iterator> 38 #include <limits> 39 #include <string> 40 #include <memory_resource> 41 #include <cfenv> 42 #include <cfloat> 43 #include <cmath> 44 #include <cstdint> 45 #include <cstdlib> 46 #include <cstring> 47 #include <locale.h> 48 #include <bits/functexcept.h> 49 #if _GLIBCXX_HAVE_XLOCALE_H 50 # include <xlocale.h> 51 #endif 52 53 #if _GLIBCXX_HAVE_USELOCALE 54 // FIXME: This should be reimplemented so it doesn't use strtod and newlocale. 55 // That will avoid the need for any memory allocation, meaning that the 56 // non-conforming errc::not_enough_memory result cannot happen. 57 # define USE_STRTOD_FOR_FROM_CHARS 1 58 #endif 59 60 #ifdef _GLIBCXX_LONG_DOUBLE_ALT128_COMPAT 61 #ifndef __LONG_DOUBLE_IBM128__ 62 #error "floating_from_chars.cc must be compiled with -mabi=ibmlongdouble" 63 #endif 64 // strtold for __ieee128 65 extern "C" __ieee128 __strtoieee128(const char*, char**); 66 #endif 67 68 #if _GLIBCXX_FLOAT_IS_IEEE_BINARY32 && _GLIBCXX_DOUBLE_IS_IEEE_BINARY64 \ 69 && __SIZE_WIDTH__ >= 32 70 # define USE_LIB_FAST_FLOAT 1 71 # if __LDBL_MANT_DIG__ == __DBL_MANT_DIG__ 72 // No need to use strtold. 73 # undef USE_STRTOD_FOR_FROM_CHARS 74 # endif 75 #endif 76 77 #if USE_LIB_FAST_FLOAT 78 # define FASTFLOAT_DEBUG_ASSERT __glibcxx_assert 79 namespace 80 { 81 # include "fast_float/fast_float.h" 82 } // anon namespace 83 #endif 84 85 namespace std _GLIBCXX_VISIBILITY(default) 86 { 87 _GLIBCXX_BEGIN_NAMESPACE_VERSION 88 89 namespace 90 { 91 #if USE_STRTOD_FOR_FROM_CHARS 92 // A memory resource with a static buffer that can be used for small 93 // allocations. At most one allocation using the freestore can be done 94 // if the static buffer is insufficient. The callers below only require 95 // a single allocation, so there's no need for anything more complex. 96 struct buffer_resource : pmr::memory_resource 97 { 98 ~buffer_resource() { if (m_ptr) operator delete(m_ptr, m_bytes); } 99 100 void* 101 do_allocate(size_t bytes, size_t alignment [[maybe_unused]]) override 102 { 103 // Allocate from the buffer if it will fit. 104 if (m_bytes < sizeof(m_buf) && (m_bytes + bytes) <= sizeof(m_buf)) 105 return m_buf + std::__exchange(m_bytes, m_bytes + bytes); 106 107 __glibcxx_assert(m_ptr == nullptr); 108 109 m_ptr = operator new(bytes); 110 m_bytes = bytes; 111 return m_ptr; 112 } 113 114 void 115 do_deallocate(void*, size_t, size_t) noexcept override 116 { /* like pmr::monotonic_buffer_resource, do nothing here */ } 117 118 bool 119 do_is_equal(const pmr::memory_resource& other) const noexcept override 120 { return &other == this; } 121 122 static constexpr int guaranteed_capacity() { return sizeof(m_buf); } 123 124 private: 125 char m_buf[512]; 126 size_t m_bytes = 0; 127 void* m_ptr = nullptr; 128 }; 129 130 #if _GLIBCXX_USE_CXX11_ABI 131 using buffered_string = std::pmr::string; 132 #else 133 using buffered_string = std::string; 134 #endif 135 136 inline bool valid_fmt(chars_format fmt) 137 { 138 return fmt != chars_format{} 139 && ((fmt & chars_format::general) == fmt 140 || (fmt & chars_format::hex) == fmt); 141 } 142 143 constexpr char hex_digits[] = "abcdefABCDEF0123456789"; 144 constexpr auto dec_digits = hex_digits + 12; 145 146 // Find initial portion of [first, last) containing a floating-point number. 147 // The string `digits` is either `dec_digits` or `hex_digits` 148 // and `exp` is "eE", "pP" or NULL. 149 const char* 150 find_end_of_float(const char* first, const char* last, const char* digits, 151 const char *exp) 152 { 153 while (first < last && strchr(digits, *first) != nullptr) 154 ++first; 155 if (first < last && *first == '.') 156 { 157 ++first; 158 while (first < last && strchr(digits, *first)) 159 ++first; 160 } 161 if (first < last && exp != nullptr && (*first == exp[0] || *first == exp[1])) 162 { 163 ++first; 164 if (first < last && (*first == '-' || *first == '+')) 165 ++first; 166 while (first < last && strchr(dec_digits, *first) != nullptr) 167 ++first; 168 } 169 return first; 170 } 171 172 // Determine the prefix of [first, last) that matches the pattern 173 // corresponding to `fmt`. 174 // Returns a NTBS containing the pattern, using `buf` to allocate 175 // additional storage if needed. 176 // Returns a nullptr if a valid pattern is not present. 177 const char* 178 pattern(const char* const first, const char* last, 179 chars_format& fmt, buffered_string& buf) 180 { 181 // fmt has the value of one of the enumerators of chars_format. 182 __glibcxx_assert(valid_fmt(fmt)); 183 184 string_view res; 185 186 if (first == last || *first == '+') [[unlikely]] 187 return nullptr; 188 189 const int neg = (*first == '-'); 190 191 if (std::memchr("iInN", (unsigned char)first[neg], 4)) 192 { 193 ptrdiff_t len = last - first; 194 if (len < (3 + neg)) 195 return nullptr; 196 197 // possible infinity or NaN, let strtod decide 198 if (first[neg] == 'i' || first[neg] == 'I') 199 { 200 // Need at most 9 chars for "-INFINITY", ignore anything after it. 201 len = std::min(len, ptrdiff_t(neg + 8)); 202 } 203 else if (len > (neg + 3) && first[neg + 3] == '(') 204 { 205 // Look for end of "NAN(n-char-sequence)" 206 if (void* p = std::memchr(const_cast<char*>(first)+4, ')', len-4)) 207 len = static_cast<char*>(p) + 1 - first; 208 #ifndef __cpp_exceptions 209 if (len > buffer_resource::guaranteed_capacity()) 210 { 211 // The character sequence is too large for the buffer. 212 // Allocation failure could terminate the process, 213 // so just return an error via the fmt parameter. 214 fmt = chars_format{}; 215 return nullptr; 216 } 217 #endif 218 } 219 else // Only need 4 chars for "-NAN" 220 len = neg + 3; 221 222 buf.assign(first, 0, len); 223 // prevent make_result correcting for "0x" 224 fmt = chars_format::general; 225 return buf.c_str(); 226 } 227 228 const char* digits; 229 char* ptr; 230 231 // Assign [first,last) to a std::string to get a NTBS that can be used 232 // with strspn, strtod etc. 233 // If the string would be longer than the fixed buffer inside the 234 // buffer_resource type use find_end_of_float to try to reduce how 235 // much memory is needed, to reduce the chance of std::bad_alloc. 236 237 if (fmt == chars_format::hex) 238 { 239 digits = hex_digits; 240 241 if ((last - first + 2) > buffer_resource::guaranteed_capacity()) 242 { 243 last = find_end_of_float(first + neg, last, digits, "pP"); 244 #ifndef __cpp_exceptions 245 if ((last - first + 2) > buffer_resource::guaranteed_capacity()) 246 { 247 // The character sequence is still too large for the buffer. 248 // Allocation failure could terminate the process, 249 // so just return an error via the fmt parameter. 250 fmt = chars_format{}; 251 return nullptr; 252 } 253 #endif 254 } 255 256 buf = "-0x" + !neg; 257 buf.append(first + neg, last); 258 ptr = buf.data() + neg + 2; 259 } 260 else 261 { 262 digits = dec_digits; 263 264 if ((last - first) > buffer_resource::guaranteed_capacity()) 265 { 266 last = find_end_of_float(first + neg, last, digits, 267 fmt == chars_format::fixed ? nullptr : "eE"); 268 #ifndef __cpp_exceptions 269 if ((last - first) > buffer_resource::guaranteed_capacity()) 270 { 271 // The character sequence is still too large for the buffer. 272 // Allocation failure could terminate the process, 273 // so just return an error via the fmt parameter. 274 fmt = chars_format{}; 275 return nullptr; 276 } 277 #endif 278 } 279 buf.assign(first, last); 280 ptr = buf.data() + neg; 281 } 282 283 // "A non-empty sequence of decimal digits" or 284 // "A non-empty sequence of hexadecimal digits" 285 size_t len = std::strspn(ptr, digits); 286 // "possibly containing a radix character," 287 if (ptr[len] == '.') 288 { 289 const size_t len2 = std::strspn(ptr + len + 1, digits); 290 if (len + len2) 291 ptr += len + 1 + len2; 292 else 293 return nullptr; 294 } 295 else if (len == 0) [[unlikely]] 296 return nullptr; 297 else 298 ptr += len; 299 300 if (fmt == chars_format::fixed) 301 { 302 // Truncate the string to stop strtod parsing past this point. 303 *ptr = '\0'; 304 } 305 else if (fmt == chars_format::scientific) 306 { 307 // Check for required exponent part which starts with 'e' or 'E' 308 if (*ptr != 'e' && *ptr != 'E') 309 return nullptr; 310 // then an optional plus or minus sign 311 const int sign = (ptr[1] == '-' || ptr[1] == '+'); 312 // then a nonempty sequence of decimal digits 313 if (!std::memchr(dec_digits, (unsigned char)ptr[1+sign], 10)) 314 return nullptr; 315 } 316 else if (fmt == chars_format::general) 317 { 318 if (*ptr == 'x' || *ptr == 'X') 319 *ptr = '\0'; 320 } 321 322 return buf.c_str(); 323 } 324 325 // Convert the NTBS `str` to a floating-point value of type `T`. 326 // If `str` cannot be converted, `value` is unchanged and `0` is returned. 327 // Otherwise, let N be the number of characters consumed from `str`. 328 // On success `value` is set to the converted value and N is returned. 329 // If the converted value is out of range, `value` is unchanged and 330 // -N is returned. 331 template<typename T> 332 ptrdiff_t 333 from_chars_impl(const char* str, T& value, errc& ec) noexcept 334 { 335 if (locale_t loc = ::newlocale(LC_ALL_MASK, "C", (locale_t)0)) [[likely]] 336 { 337 locale_t orig = ::uselocale(loc); 338 339 #if _GLIBCXX_USE_C99_FENV_TR1 && defined(FE_TONEAREST) 340 const int rounding = std::fegetround(); 341 if (rounding != FE_TONEAREST) 342 std::fesetround(FE_TONEAREST); 343 #endif 344 345 const int save_errno = errno; 346 errno = 0; 347 char* endptr; 348 T tmpval; 349 #if _GLIBCXX_USE_C99_STDLIB 350 if constexpr (is_same_v<T, float>) 351 tmpval = std::strtof(str, &endptr); 352 else if constexpr (is_same_v<T, double>) 353 tmpval = std::strtod(str, &endptr); 354 else if constexpr (is_same_v<T, long double>) 355 tmpval = std::strtold(str, &endptr); 356 # ifdef _GLIBCXX_LONG_DOUBLE_ALT128_COMPAT 357 else if constexpr (is_same_v<T, __ieee128>) 358 tmpval = __strtoieee128(str, &endptr); 359 # endif 360 #else 361 tmpval = std::strtod(str, &endptr); 362 #endif 363 const int conv_errno = std::__exchange(errno, save_errno); 364 365 #if _GLIBCXX_USE_C99_FENV_TR1 && defined(FE_TONEAREST) 366 if (rounding != FE_TONEAREST) 367 std::fesetround(rounding); 368 #endif 369 370 ::uselocale(orig); 371 ::freelocale(loc); 372 373 const ptrdiff_t n = endptr - str; 374 if (conv_errno == ERANGE) [[unlikely]] 375 { 376 if (__builtin_isinf(tmpval)) // overflow 377 ec = errc::result_out_of_range; 378 else // underflow (LWG 3081 wants to set value = tmpval here) 379 ec = errc::result_out_of_range; 380 } 381 else if (n) 382 { 383 value = tmpval; 384 ec = errc(); 385 } 386 return n; 387 } 388 else if (errno == ENOMEM) 389 ec = errc::not_enough_memory; 390 391 return 0; 392 } 393 394 inline from_chars_result 395 make_result(const char* str, ptrdiff_t n, chars_format fmt, errc ec) noexcept 396 { 397 from_chars_result result = { str, ec }; 398 if (n != 0) 399 { 400 if (fmt == chars_format::hex) 401 n -= 2; // correct for the "0x" inserted into the pattern 402 result.ptr += n; 403 } 404 else if (fmt == chars_format{}) [[unlikely]] 405 { 406 // FIXME: the standard does not allow this result. 407 ec = errc::not_enough_memory; 408 } 409 return result; 410 } 411 412 #if ! _GLIBCXX_USE_CXX11_ABI 413 inline bool 414 reserve_string(std::string& s) noexcept 415 { 416 __try 417 { 418 s.reserve(buffer_resource::guaranteed_capacity()); 419 } 420 __catch (const std::bad_alloc&) 421 { 422 return false; 423 } 424 return true; 425 } 426 #endif 427 428 template<typename T> 429 from_chars_result 430 from_chars_strtod(const char* first, const char* last, T& value, 431 chars_format fmt) noexcept 432 { 433 errc ec = errc::invalid_argument; 434 #if _GLIBCXX_USE_CXX11_ABI 435 buffer_resource mr; 436 pmr::string buf(&mr); 437 #else 438 string buf; 439 if (!reserve_string(buf)) 440 return make_result(first, 0, {}, ec); 441 #endif 442 size_t len = 0; 443 __try 444 { 445 if (const char* pat = pattern(first, last, fmt, buf)) [[likely]] 446 len = from_chars_impl(pat, value, ec); 447 } 448 __catch (const std::bad_alloc&) 449 { 450 fmt = chars_format{}; 451 } 452 return make_result(first, len, fmt, ec); 453 } 454 #endif // USE_STRTOD_FOR_FROM_CHARS 455 456 #if _GLIBCXX_FLOAT_IS_IEEE_BINARY32 && _GLIBCXX_DOUBLE_IS_IEEE_BINARY64 457 // Return true iff [FIRST,LAST) begins with PREFIX, ignoring case. 458 // PREFIX is assumed to not contain any uppercase letters. 459 bool 460 starts_with_ci(const char* first, const char* last, string_view prefix) 461 { 462 __glibcxx_requires_valid_range(first, last); 463 464 // A lookup table that maps uppercase letters to lowercase and 465 // is otherwise the identity mapping. 466 static constexpr auto upper_to_lower_table = [] { 467 constexpr unsigned char lower_letters[27] = "abcdefghijklmnopqrstuvwxyz"; 468 constexpr unsigned char upper_letters[27] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; 469 std::array<unsigned char, (1u << __CHAR_BIT__)> table = {}; 470 for (unsigned i = 0; i < table.size(); ++i) 471 table[i] = i; 472 for (unsigned i = 0; i < 26; ++i) 473 table[upper_letters[i]] = lower_letters[i]; 474 return table; 475 }(); 476 477 if (last - first < static_cast<ptrdiff_t>(prefix.length())) 478 return false; 479 480 for (const unsigned char pch : prefix) 481 { 482 // __glibcxx_assert(pch == upper_to_lower_table[pch]); 483 const unsigned char ch = *first; 484 if (ch != pch && upper_to_lower_table[ch] != pch) 485 return false; 486 ++first; 487 } 488 489 return true; 490 } 491 492 // An implementation of hexadecimal float parsing for binary32/64. 493 template<typename T> 494 from_chars_result 495 __floating_from_chars_hex(const char* first, const char* last, T& value) 496 { 497 static_assert(is_same_v<T, float> || is_same_v<T, double>); 498 499 using uint_t = conditional_t<is_same_v<T, float>, uint32_t, uint64_t>; 500 constexpr int mantissa_bits = is_same_v<T, float> ? 23 : 52; 501 constexpr int exponent_bits = is_same_v<T, float> ? 8 : 11; 502 constexpr int exponent_bias = (1 << (exponent_bits - 1)) - 1; 503 504 __glibcxx_requires_valid_range(first, last); 505 if (first == last) 506 return {first, errc::invalid_argument}; 507 508 // Consume the sign bit. 509 const char* const orig_first = first; 510 bool sign_bit = false; 511 if (*first == '-') 512 { 513 sign_bit = true; 514 ++first; 515 } 516 517 // Handle "inf", "infinity", "NaN" and variants thereof. 518 if (first != last) 519 if (*first == 'i' || *first == 'I' || *first == 'n' || *first == 'N') [[unlikely]] 520 { 521 if (starts_with_ci(first, last, "inf"sv)) 522 { 523 first += strlen("inf"); 524 if (starts_with_ci(first, last, "inity"sv)) 525 first += strlen("inity"); 526 527 uint_t result = 0; 528 result |= sign_bit; 529 result <<= exponent_bits; 530 result |= (1ull << exponent_bits) - 1; 531 result <<= mantissa_bits; 532 memcpy(&value, &result, sizeof(result)); 533 534 return {first, errc{}}; 535 } 536 else if (starts_with_ci(first, last, "nan")) 537 { 538 first += strlen("nan"); 539 540 if (first != last && *first == '(') 541 { 542 // Tentatively consume the '(' as we look for an optional 543 // n-char-sequence followed by a ')'. 544 const char* const fallback_first = first; 545 for (;;) 546 { 547 ++first; 548 if (first == last) 549 { 550 first = fallback_first; 551 break; 552 } 553 554 char ch = *first; 555 if (ch == ')') 556 { 557 ++first; 558 break; 559 } 560 else if (ch == '_' 561 || __detail::__from_chars_alnum_to_val(ch) < 127) 562 continue; 563 else 564 { 565 first = fallback_first; 566 break; 567 } 568 } 569 } 570 571 // We make the implementation-defined decision of ignoring the 572 // sign bit and the n-char-sequence when assembling the NaN. 573 uint_t result = 0; 574 result <<= exponent_bits; 575 result |= (1ull << exponent_bits) - 1; 576 result <<= mantissa_bits; 577 result |= (1ull << (mantissa_bits - 1)) | 1; 578 memcpy(&value, &result, sizeof(result)); 579 580 return {first, errc{}}; 581 } 582 } 583 584 // Consume all insignificant leading zeros in the whole part of the 585 // mantissa. 586 bool seen_hexit = false; 587 while (first != last && *first == '0') 588 { 589 seen_hexit = true; 590 ++first; 591 } 592 593 // Now consume the rest of the written mantissa, populating MANTISSA with 594 // the first MANTISSA_BITS+k significant bits of the written mantissa, where 595 // 1 <= k <= 4 is the bit width of the leading significant written hexit. 596 // 597 // Examples: 598 // After parsing "1.2f3", MANTISSA is 0x12f30000000000 (bit_width=52+1). 599 // After parsing ".0000f0e", MANTISSA is 0xf0e00000000000 (bit_width=52+4). 600 // After parsing ".1234567890abcd8", MANTISSA is 0x1234567890abcd (bit_width=52+1) 601 // and MIDPOINT_BIT is true (and NONZERO_TAIL is false). 602 uint_t mantissa = 0; 603 int mantissa_idx = mantissa_bits; // The current bit index into MANTISSA 604 // into which we'll write the next hexit. 605 int exponent_adjustment = 0; // How much we'd have to adjust the written 606 // exponent in order to represent the mantissa 607 // in scientific form h.hhhhhhhhhhhhh. 608 bool midpoint_bit = false; // Whether the MANTISSA_BITS+k+1 significant 609 // bit is set in the written mantissa. 610 bool nonzero_tail = false; // Whether some bit thereafter is set in the 611 // written mantissa. 612 bool seen_decimal_point = false; 613 for (; first != last; ++first) 614 { 615 char ch = *first; 616 if (ch == '.' && !seen_decimal_point) 617 { 618 seen_decimal_point = true; 619 continue; 620 } 621 622 int hexit = __detail::__from_chars_alnum_to_val(ch); 623 if (hexit >= 16) 624 break; 625 seen_hexit = true; 626 627 if (!seen_decimal_point && mantissa != 0) 628 exponent_adjustment += 4; 629 else if (seen_decimal_point && mantissa == 0) 630 { 631 exponent_adjustment -= 4; 632 if (hexit == 0x0) 633 continue; 634 } 635 636 if (mantissa_idx >= 0) 637 mantissa |= uint_t(hexit) << mantissa_idx; 638 else if (mantissa_idx >= -4) 639 { 640 if constexpr (is_same_v<T, float>) 641 { 642 __glibcxx_assert(mantissa_idx == -1); 643 mantissa |= hexit >> 1; 644 midpoint_bit = (hexit & 0b0001) != 0; 645 } 646 else 647 { 648 __glibcxx_assert(mantissa_idx == -4); 649 midpoint_bit = (hexit & 0b1000) != 0; 650 nonzero_tail = (hexit & 0b0111) != 0; 651 } 652 } 653 else 654 nonzero_tail |= (hexit != 0x0); 655 656 mantissa_idx -= 4; 657 } 658 if (mantissa != 0) 659 __glibcxx_assert(__bit_width(mantissa) >= mantissa_bits + 1 660 && __bit_width(mantissa) <= mantissa_bits + 4); 661 else 662 __glibcxx_assert(!midpoint_bit && !nonzero_tail); 663 664 if (!seen_hexit) 665 // If we haven't seen any hexit at this point, the parse failed. 666 return {orig_first, errc::invalid_argument}; 667 668 // Parse the written exponent. 669 int written_exponent = 0; 670 if (first != last && (*first == 'p' || *first == 'P')) 671 { 672 // Tentatively consume the 'p' and try to parse a decimal number. 673 const char* const fallback_first = first; 674 ++first; 675 if (first != last && *first == '+') 676 ++first; 677 from_chars_result fcr = from_chars(first, last, written_exponent, 10); 678 if (fcr.ptr == first) 679 // The parse failed, so undo consuming the 'p' and carry on as if the 680 // exponent was omitted (i.e. is 0). 681 first = fallback_first; 682 else 683 { 684 first = fcr.ptr; 685 if (mantissa != 0 && fcr.ec == errc::result_out_of_range) 686 // Punt on very large exponents for now. FIXME 687 return {first, errc::result_out_of_range}; 688 } 689 } 690 int biased_exponent = written_exponent + exponent_bias; 691 if (exponent_adjustment != 0) 692 // The mantissa wasn't written in scientific form. Adjust the exponent 693 // so that we may assume scientific form. 694 // 695 // Examples; 696 // For input "a.bcp5", EXPONENT_ADJUSTMENT would be 0 since this 697 // written mantissa is already in scientific form. 698 // For input "ab.cp5", EXPONENT_ADJUSTMENT would be 4 since the 699 // scientific form is "a.bcp9". 700 // For input 0.0abcp5", EXPONENT_ADJUSTMENT would be -8 since the 701 // scientific form is "a.bcp-3". 702 biased_exponent += exponent_adjustment; 703 704 // Shifts the mantissa to the right by AMOUNT while updating 705 // BIASED_EXPONENT, MIDPOINT_BIT and NONZERO_TAIL accordingly. 706 auto shift_mantissa = [&] (int amount) { 707 __glibcxx_assert(amount >= 0); 708 if (amount > mantissa_bits + 1) 709 { 710 // Shifting the mantissa by an amount greater than its precision. 711 nonzero_tail |= midpoint_bit; 712 nonzero_tail |= mantissa != 0; 713 midpoint_bit = false; 714 mantissa = 0; 715 biased_exponent += amount; 716 } 717 else if (amount != 0) 718 { 719 nonzero_tail |= midpoint_bit; 720 nonzero_tail |= (mantissa & ((1ull << (amount - 1)) - 1)) != 0; 721 midpoint_bit = (mantissa & (1ull << (amount - 1))) != 0; 722 mantissa >>= amount; 723 biased_exponent += amount; 724 } 725 }; 726 727 if (mantissa != 0) 728 { 729 // If the leading hexit is not '1', shift MANTISSA to make it so. 730 // This normalizes input like "4.08p0" into "1.02p2". 731 const int leading_hexit = mantissa >> mantissa_bits; 732 const int leading_hexit_width = __bit_width(leading_hexit); // FIXME: optimize? 733 __glibcxx_assert(leading_hexit_width >= 1 && leading_hexit_width <= 4); 734 shift_mantissa(leading_hexit_width - 1); 735 // After this adjustment, we can assume the leading hexit is '1'. 736 __glibcxx_assert((mantissa >> mantissa_bits) == 0x1); 737 } 738 739 if (biased_exponent <= 0) 740 { 741 // This number is too small to be represented as a normal number, so 742 // try for a subnormal number by shifting the mantissa sufficiently. 743 // We need to shift by 1 more than -BIASED_EXPONENT because the leading 744 // mantissa bit is omitted in the representation of a normal number but 745 // not in a subnormal number. 746 shift_mantissa(-biased_exponent + 1); 747 __glibcxx_assert(!(mantissa & (1ull << mantissa_bits))); 748 __glibcxx_assert(biased_exponent == 1); 749 biased_exponent = 0; 750 } 751 752 // Perform round-to-nearest, tie-to-even rounding according to 753 // MIDPOINT_BIT and NONZERO_TAIL. 754 if (midpoint_bit && (nonzero_tail || (mantissa % 2) != 0)) 755 { 756 // Rounding away from zero. 757 ++mantissa; 758 midpoint_bit = false; 759 nonzero_tail = false; 760 761 // Deal with a couple of corner cases after rounding. 762 if (mantissa == (1ull << mantissa_bits)) 763 { 764 // We rounded the subnormal number 1.fffffffffffff...p-1023 765 // up to the normal number 1p-1022. 766 __glibcxx_assert(biased_exponent == 0); 767 ++biased_exponent; 768 } 769 else if (mantissa & (1ull << (mantissa_bits + 1))) 770 { 771 // We rounded the normal number 1.fffffffffffff8pN (with maximal 772 // mantissa) up to to 1p(N+1). 773 mantissa >>= 1; 774 ++biased_exponent; 775 } 776 } 777 else 778 { 779 // Rounding toward zero. 780 781 if (mantissa == 0 && (midpoint_bit || nonzero_tail)) 782 { 783 // A nonzero number that rounds to zero is unrepresentable. 784 __glibcxx_assert(biased_exponent == 0); 785 return {first, errc::result_out_of_range}; 786 } 787 788 midpoint_bit = false; 789 nonzero_tail = false; 790 } 791 792 if (mantissa != 0 && biased_exponent >= (1 << exponent_bits) - 1) 793 // The exponent of this number is too large to be representable. 794 return {first, errc::result_out_of_range}; 795 796 uint_t result = 0; 797 if (mantissa == 0) 798 { 799 // Assemble a (possibly signed) zero. 800 if (sign_bit) 801 result |= 1ull << (exponent_bits + mantissa_bits); 802 } 803 else 804 { 805 // Assemble a nonzero normal or subnormal value. 806 result |= sign_bit; 807 result <<= exponent_bits; 808 result |= biased_exponent; 809 result <<= mantissa_bits; 810 result |= mantissa & ((1ull << mantissa_bits) - 1); 811 // The implicit leading mantissa bit is set iff the number is normal. 812 __glibcxx_assert(((mantissa & (1ull << mantissa_bits)) != 0) 813 == (biased_exponent != 0)); 814 } 815 memcpy(&value, &result, sizeof(result)); 816 817 return {first, errc{}}; 818 } 819 #endif // _GLIBCXX_FLOAT_IS_IEEE_BINARY32 && _GLIBCXX_DOUBLE_IS_IEEE_BINARY64 820 821 } // namespace 822 823 #if USE_LIB_FAST_FLOAT || USE_STRTOD_FOR_FROM_CHARS 824 825 from_chars_result 826 from_chars(const char* first, const char* last, float& value, 827 chars_format fmt) noexcept 828 { 829 #if USE_LIB_FAST_FLOAT 830 if (fmt == chars_format::hex) 831 return __floating_from_chars_hex(first, last, value); 832 else 833 { 834 return fast_float::from_chars(first, last, value, fmt); 835 } 836 #else 837 return from_chars_strtod(first, last, value, fmt); 838 #endif 839 } 840 841 from_chars_result 842 from_chars(const char* first, const char* last, double& value, 843 chars_format fmt) noexcept 844 { 845 #if USE_LIB_FAST_FLOAT 846 if (fmt == chars_format::hex) 847 return __floating_from_chars_hex(first, last, value); 848 else 849 { 850 return fast_float::from_chars(first, last, value, fmt); 851 } 852 #else 853 return from_chars_strtod(first, last, value, fmt); 854 #endif 855 } 856 857 from_chars_result 858 from_chars(const char* first, const char* last, long double& value, 859 chars_format fmt) noexcept 860 { 861 #if ! USE_STRTOD_FOR_FROM_CHARS 862 // Either long double is the same as double, or we can't use strtold. 863 // In the latter case, this might give an incorrect result (e.g. values 864 // out of range of double give an error, even if they fit in long double). 865 double dbl_value; 866 from_chars_result result; 867 if (fmt == chars_format::hex) 868 result = __floating_from_chars_hex(first, last, dbl_value); 869 else 870 { 871 result = fast_float::from_chars(first, last, dbl_value, fmt); 872 } 873 if (result.ec == errc{}) 874 value = dbl_value; 875 return result; 876 #else 877 return from_chars_strtod(first, last, value, fmt); 878 #endif 879 } 880 881 #ifdef _GLIBCXX_LONG_DOUBLE_COMPAT 882 // Make std::from_chars for 64-bit long double an alias for the overload 883 // for double. 884 extern "C" from_chars_result 885 _ZSt10from_charsPKcS0_ReSt12chars_format(const char* first, const char* last, 886 long double& value, 887 chars_format fmt) noexcept 888 __attribute__((alias ("_ZSt10from_charsPKcS0_RdSt12chars_format"))); 889 #endif 890 891 #ifdef _GLIBCXX_LONG_DOUBLE_ALT128_COMPAT 892 from_chars_result 893 from_chars(const char* first, const char* last, __ieee128& value, 894 chars_format fmt) noexcept 895 { 896 // fast_float doesn't support IEEE binary128 format, but we can use strtold. 897 return from_chars_strtod(first, last, value, fmt); 898 } 899 #endif 900 901 #endif // USE_LIB_FAST_FLOAT || USE_STRTOD_FOR_FROM_CHARS 902 903 _GLIBCXX_END_NAMESPACE_VERSION 904 } // namespace std 905