xref: /netbsd-src/external/gpl3/gcc/dist/libstdc++-v3/src/c++17/floating_from_chars.cc (revision b1e838363e3c6fc78a55519254d99869742dd33c)
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   {
~buffer_resourcestd::__anon70c05ec00211::buffer_resource98     ~buffer_resource() { if (m_ptr) operator delete(m_ptr, m_bytes); }
99 
100     void*
do_allocatestd::__anon70c05ec00211::buffer_resource101     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
do_deallocatestd::__anon70c05ec00211::buffer_resource115     do_deallocate(void*, size_t, size_t) noexcept override
116     { /* like pmr::monotonic_buffer_resource, do nothing here */ }
117 
118     bool
do_is_equalstd::__anon70c05ec00211::buffer_resource119     do_is_equal(const pmr::memory_resource& other) const noexcept override
120     { return &other == this; }
121 
guaranteed_capacitystd::__anon70c05ec00211::buffer_resource122     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 
valid_fmt(chars_format fmt)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*
find_end_of_float(const char * first,const char * last,const char * digits,const char * exp)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*
pattern(const char * const first,const char * last,chars_format & fmt,buffered_string & buf)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
from_chars_impl(const char * str,T & value,errc & ec)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
make_result(const char * str,ptrdiff_t n,chars_format fmt,errc ec)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
reserve_string(std::string & s)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
from_chars_strtod(const char * first,const char * last,T & value,chars_format fmt)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
starts_with_ci(const char * first,const char * last,string_view prefix)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
__floating_from_chars_hex(const char * first,const char * last,T & value)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
from_chars(const char * first,const char * last,float & value,chars_format fmt)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
from_chars(const char * first,const char * last,double & value,chars_format fmt)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
from_chars(const char * first,const char * last,long double & value,chars_format fmt)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
from_chars(const char * first,const char * last,__ieee128 & value,chars_format fmt)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