diff options
author | Jakub Jelinek <jakub@redhat.com> | 2022-11-01 13:34:51 +0100 |
---|---|---|
committer | Jakub Jelinek <jakub@redhat.com> | 2022-11-01 13:34:51 +0100 |
commit | 29ef50b6bc609130a1550cdfc3997d1e501ffb28 (patch) | |
tree | ca94c6eaf682309b1bafd19952ddc56716ac1d82 /libstdc++-v3/include/std/charconv | |
parent | 5cee5f94000ee5eabce9b223c44c7923c1c69f61 (diff) | |
download | gcc-29ef50b6bc609130a1550cdfc3997d1e501ffb28.zip gcc-29ef50b6bc609130a1550cdfc3997d1e501ffb28.tar.gz gcc-29ef50b6bc609130a1550cdfc3997d1e501ffb28.tar.bz2 |
libstdc++-v3: Some std::*float*_t charconv and i/ostream overloads
The following patch adds the easy part of <charconv>, <istream> and
<ostream> changes for extended floats.
In particular, for the first one only overloads where the _Float* has
the same format as float/double/long double and for the latter two
everything but the _GLIBCXX_HAVE_FLOAT128_MATH case.
For charconv, I'm not really familiar with it, I'm pretty sure
we need new libstdc++.so.6 side implementation of from_chars for
{,b}float16_t and for to_chars not really sure but for unspecified precision
if it should emit minimum characters that to_chars then can unambiguously
parse, I think it is less than in the float case. For float128_t
{to,from}_chars I think we even have it on the library side already, just
ifdefed for powerpc64le only.
For i/o stream operator<</>>, not sure what is better, if not providing
anything at all, or doing what we in the end do if user doesn't override
the virtual functions, or use {to,from}_chars under the hood, something
else?
Besides this, the patch adds some further missed
// { dg-options "-std=gnu++2b" }
spots, I've also noticed I got the formatting wrong in some testcases
by not using spaces around VERIFY conditions and elsewhere by having
space before ( for calls.
The testsuite coverage is limited, I've added test for from_chars because
it was easy to port, but not really sure what to do about to_chars, it has
for float/double huge testcases which would be excessive to repeat.
And for i/ostream not really sure what exactly is worth testing.
2022-11-01 Jakub Jelinek <jakub@redhat.com>
* include/std/charconv (from_chars, to_chars): Add _Float{32,64,128}
overloads for cases where those types match {float,double,long double}.
* include/std/istream (basic_istream::operator>>): Add
_Float{16,32,64,128} and __gnu_cxx::__bfloat16_t overloads.
* include/std/ostream (basic_ostream::operator<<): Add
_Float{16,32,64,128} and __gnu_cxx::__bfloat16_t overloads.
* testsuite/20_util/from_chars/8.cc: New test.
* testsuite/26_numerics/headers/cmath/nextafter_c++23.cc (test):
Formatting fixes.
* testsuite/26_numerics/headers/cmath/functions_std_c++23.cc: Add
dg-options "-std=gnu++2b".
(test_functions, main): Formatting fixes.
* testsuite/26_numerics/headers/cmath/c99_classification_macros_c++23.cc:
Add dg-options "-std=gnu++2b".
Diffstat (limited to 'libstdc++-v3/include/std/charconv')
-rw-r--r-- | libstdc++-v3/include/std/charconv | 86 |
1 files changed, 86 insertions, 0 deletions
diff --git a/libstdc++-v3/include/std/charconv b/libstdc++-v3/include/std/charconv index a65fbed..9b9cd83 100644 --- a/libstdc++-v3/include/std/charconv +++ b/libstdc++-v3/include/std/charconv @@ -672,6 +672,45 @@ namespace __detail from_chars_result from_chars(const char* __first, const char* __last, long double& __value, chars_format __fmt = chars_format::general) noexcept; + +#if defined(__STDCPP_FLOAT32_T__) && defined(_GLIBCXX_FLOAT_IS_IEEE_BINARY32) + inline from_chars_result + from_chars(const char* __first, const char* __last, _Float32& __value, + chars_format __fmt = chars_format::general) noexcept + { + float __val; + from_chars_result __res = from_chars(__first, __last, __val, __fmt); + if (__res.ec == errc{}) + __value = __val; + return __res; + } +#endif + +#if defined(__STDCPP_FLOAT64_T__) && defined(_GLIBCXX_DOUBLE_IS_IEEE_BINARY64) + inline from_chars_result + from_chars(const char* __first, const char* __last, _Float64& __value, + chars_format __fmt = chars_format::general) noexcept + { + double __val; + from_chars_result __res = from_chars(__first, __last, __val, __fmt); + if (__res.ec == errc{}) + __value = __val; + return __res; + } +#endif + +#if defined(__STDCPP_FLOAT128_T__) && defined(_GLIBCXX_LDOUBLE_IS_IEEE_BINARY128) + inline from_chars_result + from_chars(const char* __first, const char* __last, _Float128& __value, + chars_format __fmt = chars_format::general) noexcept + { + long double __val; + from_chars_result __res = from_chars(__first, __last, __val, __fmt); + if (__res.ec == errc{}) + __value = __val; + return __res; + } +#endif #endif #if defined __cpp_lib_to_chars @@ -698,6 +737,53 @@ namespace __detail chars_format __fmt) noexcept; to_chars_result to_chars(char* __first, char* __last, long double __value, chars_format __fmt, int __precision) noexcept; + +#if defined(__STDCPP_FLOAT32_T__) && defined(_GLIBCXX_FLOAT_IS_IEEE_BINARY32) + inline to_chars_result + to_chars(char* __first, char* __last, _Float32 __value) noexcept + { return to_chars(__first, __last, float(__value)); } + inline to_chars_result + to_chars(char* __first, char* __last, _Float32 __value, + chars_format __fmt) noexcept + { return to_chars(__first, __last, float(__value), __fmt); } + inline to_chars_result + to_chars(char* __first, char* __last, _Float32 __value, + chars_format __fmt, int __precision) noexcept + { return to_chars(__first, __last, float(__value), __fmt, __precision); } +#endif + +#if defined(__STDCPP_FLOAT64_T__) && defined(_GLIBCXX_DOUBLE_IS_IEEE_BINARY64) + inline to_chars_result + to_chars(char* __first, char* __last, _Float64 __value) noexcept + { return to_chars(__first, __last, double(__value)); } + inline to_chars_result + to_chars(char* __first, char* __last, _Float64 __value, + chars_format __fmt) noexcept + { return to_chars(__first, __last, double(__value), __fmt); } + inline to_chars_result + to_chars(char* __first, char* __last, _Float64 __value, + chars_format __fmt, int __precision) noexcept + { return to_chars(__first, __last, double(__value), __fmt, __precision); } +#endif + +#if defined(__STDCPP_FLOAT128_T__) && defined(_GLIBCXX_LDOUBLE_IS_IEEE_BINARY128) + inline to_chars_result + to_chars(char* __first, char* __last, _Float128 __value) noexcept + { return to_chars(__first, __last, static_cast<long double>(__value)); } + inline to_chars_result + to_chars(char* __first, char* __last, _Float128 __value, + chars_format __fmt) noexcept + { + return to_chars(__first, __last, static_cast<long double>(__value), __fmt); + } + inline to_chars_result + to_chars(char* __first, char* __last, _Float128 __value, + chars_format __fmt, int __precision) noexcept + { + return to_chars(__first, __last, static_cast<long double>(__value), __fmt, + __precision); + } +#endif #endif _GLIBCXX_END_NAMESPACE_VERSION |