1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9// UNSUPPORTED: c++03, c++11, c++14
10
11// XFAIL: availability-fp_from_chars-missing
12
13// from_chars_result from_chars(const char* first, const char* last,
14// float& value, chars_format fmt = chars_format::general)
15//
16// from_chars_result from_chars(const char* first, const char* last,
17// double& value, chars_format fmt = chars_format::general)
18
19#include <array>
20#include <charconv>
21#include <cmath>
22#include <cstring>
23#include <limits>
24#include <stdexcept>
25#include <system_error>
26
27#include "charconv_test_helpers.h"
28#include "test_macros.h"
29
30template <class F>
31void test_infinity(std::chars_format fmt) {
32 const char* s = "-InFiNiTyXXX";
33 { // I
34 F value = 0.25;
35 std::from_chars_result result = std::from_chars(s + 1, s + 2, value, fmt);
36
37 assert(result.ec == std::errc::invalid_argument);
38 assert(result.ptr == s + 1);
39 assert(value == F(0.25));
40 }
41 { // In
42 F value = 0.25;
43 std::from_chars_result result = std::from_chars(s + 1, s + 3, value, fmt);
44
45 assert(result.ec == std::errc::invalid_argument);
46 assert(result.ptr == s + 1);
47 assert(value == F(0.25));
48 }
49 { // InF
50 F value = 0.25;
51 std::from_chars_result result = std::from_chars(s + 1, s + 4, value, fmt);
52
53 assert(result.ec == std::errc{});
54 assert(result.ptr == s + 4);
55 assert(value == std::numeric_limits<F>::infinity());
56 }
57 { // -InF
58 F value = 0.25;
59 std::from_chars_result result = std::from_chars(s, s + 4, value, fmt);
60
61 assert(result.ec == std::errc{});
62 assert(result.ptr == s + 4);
63 assert(value == -std::numeric_limits<F>::infinity());
64 }
65 { // InFi
66 F value = 0.25;
67 std::from_chars_result result = std::from_chars(s + 1, s + 5, value, fmt);
68
69 assert(result.ec == std::errc{});
70 assert(result.ptr == s + 4);
71 assert(value == std::numeric_limits<F>::infinity());
72 }
73 { // -InFiN
74 F value = 0.25;
75 std::from_chars_result result = std::from_chars(s, s + 6, value, fmt);
76
77 assert(result.ec == std::errc{});
78 assert(result.ptr == s + 4);
79 assert(value == -std::numeric_limits<F>::infinity());
80 }
81 { // InFiNi
82 F value = 0.25;
83 std::from_chars_result result = std::from_chars(s + 1, s + 7, value, fmt);
84
85 assert(result.ec == std::errc{});
86 assert(result.ptr == s + 4);
87 assert(value == std::numeric_limits<F>::infinity());
88 }
89 { // -InFiNiT
90 F value = 0.25;
91 std::from_chars_result result = std::from_chars(s, s + 8, value, fmt);
92
93 assert(result.ec == std::errc{});
94 assert(result.ptr == s + 4);
95 assert(value == -std::numeric_limits<F>::infinity());
96 }
97 { // InFiNiTy
98 F value = 0.25;
99 std::from_chars_result result = std::from_chars(s + 1, s + 9, value, fmt);
100
101 assert(result.ec == std::errc{});
102 assert(result.ptr == s + 9);
103 assert(value == std::numeric_limits<F>::infinity());
104 }
105 { // -InFiNiTy
106 F value = 0.25;
107 std::from_chars_result result = std::from_chars(s, s + 9, value, fmt);
108
109 assert(result.ec == std::errc{});
110 assert(result.ptr == s + 9);
111 assert(value == -std::numeric_limits<F>::infinity());
112 }
113 { // InFiNiTyXXX
114 F value = 0.25;
115 std::from_chars_result result = std::from_chars(s + 1, s + 12, value, fmt);
116
117 assert(result.ec == std::errc{});
118 assert(result.ptr == s + 9);
119 assert(value == std::numeric_limits<F>::infinity());
120 }
121 { // -InFiNiTyXXX
122 F value = 0.25;
123 std::from_chars_result result = std::from_chars(s, s + 12, value, fmt);
124
125 assert(result.ec == std::errc{});
126 assert(result.ptr == s + 9);
127 assert(value == -std::numeric_limits<F>::infinity());
128 }
129}
130
131template <class F>
132void test_nan(std::chars_format fmt) {
133 {
134 const char* s = "-NaN(1_A)XXX";
135 { // N
136 F value = 0.25;
137 std::from_chars_result result = std::from_chars(s + 1, s + 2, value, fmt);
138
139 assert(result.ec == std::errc::invalid_argument);
140 assert(result.ptr == s + 1);
141 assert(value == F(0.25));
142 }
143 { // Na
144 F value = 0.25;
145 std::from_chars_result result = std::from_chars(s + 1, s + 3, value, fmt);
146
147 assert(result.ec == std::errc::invalid_argument);
148 assert(result.ptr == s + 1);
149 assert(value == F(0.25));
150 }
151 { // NaN
152 F value = 0.25;
153 std::from_chars_result result = std::from_chars(s + 1, s + 4, value, fmt);
154
155 assert(result.ec == std::errc{});
156 assert(result.ptr == s + 4);
157 assert(std::isnan(value));
158 assert(!std::signbit(value));
159 }
160 { // -NaN
161 F value = 0.25;
162 std::from_chars_result result = std::from_chars(s + 0, s + 4, value, fmt);
163
164 assert(result.ec == std::errc{});
165 assert(result.ptr == s + 4);
166 assert(std::isnan(value));
167 assert(std::signbit(value));
168 }
169 { // NaN(
170 F value = 0.25;
171 std::from_chars_result result = std::from_chars(s + 1, s + 5, value, fmt);
172
173 assert(result.ec == std::errc{});
174 assert(result.ptr == s + 4);
175 assert(std::isnan(value));
176 assert(!std::signbit(value));
177 }
178 { // -NaN(1
179 F value = 0.25;
180 std::from_chars_result result = std::from_chars(s, s + 6, value, fmt);
181
182 assert(result.ec == std::errc{});
183 assert(result.ptr == s + 4);
184 assert(std::isnan(value));
185 assert(std::signbit(value));
186 }
187 { // NaN(1_
188 F value = 0.25;
189 std::from_chars_result result = std::from_chars(s + 1, s + 7, value, fmt);
190
191 assert(result.ec == std::errc{});
192 assert(result.ptr == s + 4);
193 assert(std::isnan(value));
194 assert(!std::signbit(value));
195 }
196 { // -NaN(1_A
197 F value = 0.25;
198 std::from_chars_result result = std::from_chars(s, s + 8, value, fmt);
199
200 assert(result.ec == std::errc{});
201 assert(result.ptr == s + 4);
202 assert(std::isnan(value));
203 assert(std::signbit(value));
204 }
205 { // NaN(1_A)
206 F value = 0.25;
207 std::from_chars_result result = std::from_chars(s + 1, s + 9, value, fmt);
208
209 assert(result.ec == std::errc{});
210 assert(result.ptr == s + 9);
211 assert(std::isnan(value));
212 assert(!std::signbit(value));
213 }
214 { // -NaN(1_A)
215 F value = 0.25;
216 std::from_chars_result result = std::from_chars(s, s + 9, value, fmt);
217
218 assert(result.ec == std::errc{});
219 assert(result.ptr == s + 9);
220 assert(std::isnan(value));
221 assert(std::signbit(value));
222 }
223 { // NaN(1_A)XXX
224 F value = 0.25;
225 std::from_chars_result result = std::from_chars(s + 1, s + 12, value, fmt);
226
227 assert(result.ec == std::errc{});
228 assert(result.ptr == s + 9);
229 assert(std::isnan(value));
230 assert(!std::signbit(value));
231 }
232 { // -NaN(1_A)XXX
233 F value = 0.25;
234 std::from_chars_result result = std::from_chars(s, s + 12, value, fmt);
235
236 assert(result.ec == std::errc{});
237 assert(result.ptr == s + 9);
238 assert(std::isnan(value));
239 assert(std::signbit(value));
240 }
241 }
242 {
243 const char* s = "NaN()";
244 F value = 0.25;
245 std::from_chars_result result = std::from_chars(s, s + std::strlen(s: s), value, fmt);
246
247 assert(result.ec == std::errc{});
248 assert(result.ptr == s + 5);
249 assert(std::isnan(value));
250 assert(!std::signbit(value));
251 }
252 { // validates a n-char-sequences with an invalid value
253 std::array s = {'N', 'a', 'N', '(', ' ', ')'};
254 s[4] = 'a';
255 {
256 F value = 0.25;
257 std::from_chars_result result = std::from_chars(s.data(), s.data() + s.size(), value, fmt);
258
259 assert(result.ec == std::errc{});
260 assert(result.ptr == s.data() + s.size());
261 assert(std::isnan(value));
262 assert(!std::signbit(value));
263 }
264 for (auto c : "!@#$%^&*(-=+[]{}|\\;:'\",./<>?~` \t\v\r\n") {
265 F value = 0.25;
266 s[4] = c;
267 std::from_chars_result result = std::from_chars(s.data(), s.data() + s.size(), value, fmt);
268
269 assert(result.ec == std::errc{});
270 assert(result.ptr == s.data() + 3);
271 assert(std::isnan(value));
272 assert(!std::signbit(value));
273 }
274 }
275}
276
277template <class F>
278void test_fmt_independent(std::chars_format fmt) {
279 test_infinity<F>(fmt);
280 test_nan<F>(fmt);
281
282 { // first == last
283 F value = 0.25;
284 std::from_chars_result result = std::from_chars(nullptr, nullptr, value, fmt);
285
286 assert(result.ec == std::errc::invalid_argument);
287 assert(result.ptr == nullptr);
288 assert(value == F(0.25));
289 }
290 { // only a sign
291 F value = 0.25;
292 const char* s = "-";
293 std::from_chars_result result = std::from_chars(s, s + std::strlen(s: s), value, fmt);
294
295 assert(result.ec == std::errc::invalid_argument);
296 assert(result.ptr == s);
297 assert(value == F(0.25));
298 }
299 { // only decimal separator
300 F value = 0.25;
301 const char* s = ".";
302 std::from_chars_result result = std::from_chars(s, s + std::strlen(s: s), value, fmt);
303
304 assert(result.ec == std::errc::invalid_argument);
305 assert(result.ptr == s);
306 assert(value == F(0.25));
307 }
308 { // sign and decimal separator
309 F value = 0.25;
310 const char* s = "-.";
311 std::from_chars_result result = std::from_chars(s, s + std::strlen(s: s), value, fmt);
312
313 assert(result.ec == std::errc::invalid_argument);
314 assert(result.ptr == s);
315 assert(value == F(0.25));
316 }
317 { // + sign is not allowed
318 F value = 0.25;
319 const char* s = "+0.25";
320 std::from_chars_result result = std::from_chars(s, s + std::strlen(s: s), value, fmt);
321
322 assert(result.ec == std::errc::invalid_argument);
323 assert(result.ptr == s);
324 assert(value == F(0.25));
325 }
326}
327
328template <class F>
329struct test_basics {
330 void operator()() {
331 for (auto fmt : {std::chars_format::scientific,
332 std::chars_format::fixed,
333 /*std::chars_format::hex,*/ std::chars_format::general})
334 test_fmt_independent<F>(fmt);
335 }
336};
337
338template <class F>
339struct test_fixed {
340 void operator()() {
341 std::from_chars_result r;
342 F x = 0.25;
343
344 // *** Failures
345
346 { // Starts with invalid character
347 std::array s = {' ', '1'};
348 for (auto c : "abcdefghijklmnopqrstuvwxyz"
349 "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
350 "`~!@#$%^&*()_=[]{}\\|;:'\",/<>? \t\v\r\n") {
351 s[0] = c;
352 r = std::from_chars(s.data(), s.data() + s.size(), x, std::chars_format::fixed);
353
354 assert(r.ec == std::errc::invalid_argument);
355 assert(r.ptr == s.data());
356 assert(x == F(0.25));
357 }
358 }
359
360 // *** Success
361
362 { // number followed by non-numeric values
363 const char* s = "001x";
364
365 // the expected form of the subject sequence is a nonempty sequence of
366 // decimal digits optionally containing a decimal-point character, then
367 // an optional exponent part as defined in 6.4.4.3, excluding any digit
368 // separators (6.4.4.2); (C23 7.24.1.5)
369 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
370 assert(r.ec == std::errc{});
371 assert(r.ptr == s + 3);
372 assert(x == F(1.0));
373 }
374 { // no leading digit
375 const char* s = ".5";
376
377 // the expected form of the subject sequence is a nonempty sequence of
378 // decimal digits optionally containing a decimal-point character, then
379 // an optional exponent part as defined in 6.4.4.3, excluding any digit
380 // separators (6.4.4.2); (C23 7.24.1.5)
381 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
382 assert(r.ec == std::errc{});
383 assert(r.ptr == s + 2);
384 assert(x == F(0.5));
385 }
386 { // negative sign and no leading digit
387 const char* s = "-.5";
388
389 // the expected form of the subject sequence is a nonempty sequence of
390 // decimal digits optionally containing a decimal-point character, then
391 // an optional exponent part as defined in 6.4.4.3, excluding any digit
392 // separators (6.4.4.2); (C23 7.24.1.5)
393 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
394 assert(r.ec == std::errc{});
395 assert(r.ptr == s + 3);
396 assert(x == F(-0.5));
397 }
398
399 { // double deciamal point
400 const char* s = "1.25.78";
401
402 // This number is halfway between two float values.
403 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
404 assert(r.ec == std::errc{});
405 assert(r.ptr == s + 4);
406 assert(x == F(1.25));
407 }
408 { // exponenent no sign
409 const char* s = "1.5e10";
410 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
411
412 assert(r.ec == std::errc{});
413 assert(r.ptr == s + 3);
414 assert(x == F(1.5));
415 }
416 { // exponenent capitalized no sign
417 const char* s = "1.5E10";
418 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
419
420 assert(r.ec == std::errc{});
421 assert(r.ptr == s + 3);
422 assert(x == F(1.5));
423 }
424 { // exponenent + sign
425 const char* s = "1.5e+10";
426 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
427
428 assert(r.ec == std::errc{});
429 assert(r.ptr == s + 3);
430 assert(x == F(1.5));
431 }
432 { // exponenent - sign
433 const char* s = "1.5e-10";
434 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
435
436 assert(r.ec == std::errc{});
437 assert(r.ptr == s + 3);
438 assert(x == F(1.5));
439 }
440 { // Exponent no number
441 const char* s = "1.5e";
442
443 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
444 assert(r.ec == std::errc{});
445 assert(r.ptr == s + 3);
446 assert(x == F(1.5));
447 }
448 { // Exponent sign no number
449 {
450 const char* s = "1.5e+";
451
452 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
453 assert(r.ec == std::errc{});
454 assert(r.ptr == s + 3);
455 assert(x == F(1.5));
456 }
457 {
458 const char* s = "1.5e-";
459
460 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
461 assert(r.ec == std::errc{});
462 assert(r.ptr == s + 3);
463 assert(x == F(1.5));
464 }
465 }
466 { // Exponent with whitespace
467 {
468 const char* s = "1.5e +1";
469
470 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
471 assert(r.ec == std::errc{});
472 assert(r.ptr == s + 3);
473 assert(x == F(1.5));
474 }
475 {
476 const char* s = "1.5e+ 1";
477
478 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
479 assert(r.ec == std::errc{});
480 assert(r.ptr == s + 3);
481 assert(x == F(1.5));
482 }
483 {
484 const char* s = "1.5e -1";
485
486 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
487 assert(r.ec == std::errc{});
488 assert(r.ptr == s + 3);
489 assert(x == F(1.5));
490 }
491 {
492 const char* s = "1.5e- 1";
493
494 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
495 assert(r.ec == std::errc{});
496 assert(r.ptr == s + 3);
497 assert(x == F(1.5));
498 }
499 }
500 { // double exponent
501 const char* s = "1.25e0e12";
502 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
503
504 assert(r.ec == std::errc{});
505 assert(r.ptr == s + 4);
506 assert(x == F(1.25));
507 }
508 { // Exponent double sign
509 {
510 const char* s = "1.25e++12";
511
512 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
513 assert(r.ec == std::errc{});
514 assert(r.ptr == s + 4);
515 assert(x == F(1.25));
516 }
517 {
518 const char* s = "1.25e+-12";
519
520 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
521 assert(r.ec == std::errc{});
522 assert(r.ptr == s + 4);
523 assert(x == F(1.25));
524 }
525 {
526 const char* s = "1.25e-+12";
527
528 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
529 assert(r.ec == std::errc{});
530 assert(r.ptr == s + 4);
531 assert(x == F(1.25));
532 }
533 {
534 const char* s = "1.25e--12";
535
536 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
537 assert(r.ec == std::errc{});
538 assert(r.ptr == s + 4);
539 assert(x == F(1.25));
540 }
541 }
542 { // exponent hex prefix
543 const char* s = "1.25e0x12";
544
545 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
546 assert(r.ec == std::errc{});
547 assert(r.ptr == s + 4);
548 assert(x == F(1.25));
549 }
550 { // This number is halfway between two float values.
551 const char* s = "20040229";
552
553 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
554 assert(r.ec == std::errc{});
555 assert(r.ptr == s + 8);
556 assert(x == F(20040229));
557 }
558 { // Shifting mantissa exponent and no exponent
559 const char* s = "123.456";
560
561 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
562 assert(r.ec == std::errc{});
563 assert(r.ptr == s + 7);
564 assert(x == F(1.23456e2));
565 }
566 { // Shifting mantissa exponent and an exponent
567 const char* s = "123.456e3";
568 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
569
570 assert(r.ec == std::errc{});
571 assert(r.ptr == s + 7);
572 assert(x == F(123.456));
573 }
574 { // Mantissa overflow
575 {
576 const char* s = "0.111111111111111111111111111111111111111111";
577
578 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
579 assert(r.ec == std::errc{});
580 assert(r.ptr == s + std::strlen(s: s));
581 assert(x == F(0.111111111111111111111111111111111111111111));
582 }
583 {
584 const char* s = "111111111111.111111111111111111111111111111111111111111";
585
586 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
587 assert(r.ec == std::errc{});
588 assert(r.ptr == s + std::strlen(s: s));
589 assert(x == F(111111111111.111111111111111111111111111111111111111111));
590 }
591 }
592 { // Negative value
593 const char* s = "-0.25";
594
595 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::fixed);
596 assert(r.ec == std::errc{});
597 assert(r.ptr == s + std::strlen(s: s));
598 assert(x == F(-0.25));
599 }
600 }
601};
602
603template <class F>
604struct test_scientific {
605 void operator()() {
606 std::from_chars_result r;
607 F x = 0.25;
608
609 // *** Failures
610
611 { // Starts with invalid character
612 std::array s = {' ', '1', 'e', '0'};
613 for (auto c : "abcdefghijklmnopqrstuvwxyz"
614 "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
615 "`~!@#$%^&*()_=[]{}\\|;:'\",/<>? \t\v\r\n") {
616 s[0] = c;
617 r = std::from_chars(s.data(), s.data() + s.size(), x, std::chars_format::scientific);
618
619 assert(r.ec == std::errc::invalid_argument);
620 assert(r.ptr == s.data());
621 assert(x == F(0.25));
622 }
623 }
624 { // No exponent
625 const char* s = "1.23";
626 r = std::from_chars(s, s + strlen(s: s), x, std::chars_format::scientific);
627
628 assert(r.ec == std::errc::invalid_argument);
629 assert(r.ptr == s);
630 assert(x == F(0.25));
631 }
632 { // Exponent no number
633 const char* s = "1.23e";
634 r = std::from_chars(s, s + strlen(s: s), x, std::chars_format::scientific);
635
636 assert(r.ec == std::errc::invalid_argument);
637 assert(r.ptr == s);
638 assert(x == F(0.25));
639 }
640 { // Exponent sign no number
641 {
642 const char* s = "1.5e+";
643
644 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
645 assert(r.ec == std::errc::invalid_argument);
646 assert(r.ptr == s);
647 assert(x == F(0.25));
648 }
649 {
650 const char* s = "1.5e-";
651
652 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
653 assert(r.ec == std::errc::invalid_argument);
654 assert(r.ptr == s);
655 assert(x == F(0.25));
656 }
657 }
658 { // Exponent with whitespace
659 {
660 const char* s = "1.5e +1";
661
662 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
663 assert(r.ec == std::errc::invalid_argument);
664 assert(r.ptr == s);
665 assert(x == F(0.25));
666 }
667 {
668 const char* s = "1.5e+ 1";
669
670 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
671 assert(r.ec == std::errc::invalid_argument);
672 assert(r.ptr == s);
673 assert(x == F(0.25));
674 }
675 {
676 const char* s = "1.5e -1";
677
678 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
679 assert(r.ec == std::errc::invalid_argument);
680 assert(r.ptr == s);
681 assert(x == F(0.25));
682 }
683 {
684 const char* s = "1.5e- 1";
685
686 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
687 assert(r.ec == std::errc::invalid_argument);
688 assert(r.ptr == s);
689 assert(x == F(0.25));
690 }
691 }
692 { // exponent double sign
693 {
694 const char* s = "1.25e++12";
695
696 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
697 assert(r.ec == std::errc::invalid_argument);
698 assert(r.ptr == s);
699 assert(x == F(0.25));
700 }
701 {
702 const char* s = "1.25e+-12";
703
704 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
705 assert(r.ec == std::errc::invalid_argument);
706 assert(r.ptr == s);
707 assert(x == F(0.25));
708 }
709 {
710 const char* s = "1.25e-+12";
711
712 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
713 assert(r.ec == std::errc::invalid_argument);
714 assert(r.ptr == s);
715 assert(x == F(0.25));
716 }
717 {
718 const char* s = "1.25e--12";
719
720 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
721 assert(r.ec == std::errc::invalid_argument);
722 assert(r.ptr == s);
723 assert(x == F(0.25));
724 }
725 }
726
727 // *** Success
728
729 { // number followed by non-numeric values
730 const char* s = "001e0x";
731
732 // the expected form of the subject sequence is a nonempty sequence of
733 // decimal digits optionally containing a decimal-point character, then
734 // an optional exponent part as defined in 6.4.4.3, excluding any digit
735 // separators (6.4.4.2); (C23 7.24.1.5)
736 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
737 assert(r.ec == std::errc{});
738 assert(r.ptr == s + 5);
739 assert(x == F(1.0));
740 }
741
742 { // double deciamal point
743 const char* s = "1.25e0.78";
744
745 // This number is halfway between two float values.
746 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
747 assert(r.ec == std::errc{});
748 assert(r.ptr == s + 6);
749 assert(x == F(1.25));
750 }
751
752 { // exponenent no sign
753 const char* s = "1.5e10";
754
755 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
756 assert(r.ec == std::errc{});
757 assert(r.ptr == s + 6);
758 assert(x == F(1.5e10));
759 }
760 { // exponenent capitalized no sign
761 const char* s = "1.5E10";
762
763 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
764 assert(r.ec == std::errc{});
765 assert(r.ptr == s + 6);
766 assert(x == F(1.5e10));
767 }
768 { // exponenent + sign
769 const char* s = "1.5e+10";
770
771 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
772 assert(r.ec == std::errc{});
773 assert(r.ptr == s + 7);
774 assert(x == F(1.5e10));
775 }
776 { // exponenent - sign
777 const char* s = "1.5e-10";
778
779 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
780 assert(r.ec == std::errc{});
781 assert(r.ptr == s + 7);
782 assert(x == F(1.5e-10));
783 }
784 { // exponent hex prefix -> e0
785 const char* s = "1.25e0x12";
786
787 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
788 assert(r.ec == std::errc{});
789 assert(r.ptr == s + 6);
790 assert(x == F(1.25));
791 }
792 { // double exponent
793 const char* s = "1.25e0e12";
794
795 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
796 assert(r.ec == std::errc{});
797 assert(r.ptr == s + 6);
798 assert(x == F(1.25));
799 }
800 { // This number is halfway between two float values.
801 const char* s = "20040229e0";
802
803 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
804 assert(r.ec == std::errc{});
805 assert(r.ptr == s + 10);
806 assert(x == F(20040229));
807 }
808 { // Shifting mantissa exponent and an exponent
809 const char* s = "123.456e3";
810
811 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
812 assert(r.ec == std::errc{});
813 assert(r.ptr == s + 9);
814 assert(x == F(1.23456e5));
815 }
816 { // Mantissa overflow
817 {
818 const char* s = "0.111111111111111111111111111111111111111111e0";
819
820 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
821 assert(r.ec == std::errc{});
822 assert(r.ptr == s + std::strlen(s: s));
823 assert(x == F(0.111111111111111111111111111111111111111111));
824 }
825 {
826 const char* s = "111111111111.111111111111111111111111111111111111111111e0";
827
828 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
829 assert(r.ec == std::errc{});
830 assert(r.ptr == s + std::strlen(s: s));
831 assert(x == F(111111111111.111111111111111111111111111111111111111111));
832 }
833 }
834 { // Negative value
835 const char* s = "-0.25e0";
836
837 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
838 assert(r.ec == std::errc{});
839 assert(r.ptr == s + std::strlen(s: s));
840 assert(x == F(-0.25));
841 }
842 { // value is too big -> +inf
843 const char* s = "1e9999999999999999999999999999999999999999";
844
845 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
846 assert(r.ec == std::errc::result_out_of_range);
847 assert(r.ptr == s + strlen(s: s));
848 assert(x == std::numeric_limits<F>::infinity());
849 }
850 { // negative value is too big -> -inf
851 const char* s = "-1e9999999999999999999999999999999999999999";
852
853 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
854 assert(r.ec == std::errc::result_out_of_range);
855 assert(r.ptr == s + strlen(s: s));
856 assert(x == -std::numeric_limits<F>::infinity());
857 }
858 { // value is too small -> 0
859 const char* s = "1e-9999999999999999999999999999999999999999";
860
861 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
862 assert(r.ec == std::errc::result_out_of_range);
863 assert(r.ptr == s + strlen(s: s));
864 assert(x == F(0.0));
865 }
866 { // negative value is too small -> -0
867 const char* s = "-1e-9999999999999999999999999999999999999999";
868
869 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::scientific);
870 assert(r.ec == std::errc::result_out_of_range);
871 assert(r.ptr == s + strlen(s: s));
872 assert(x == F(-0.0));
873 }
874 }
875};
876
877template <class F>
878struct test_general {
879 void operator()() {
880 std::from_chars_result r;
881 F x = 0.25;
882
883 // *** Failures
884
885 { // Starts with invalid character
886 std::array s = {' ', '1'};
887 for (auto c : "abcdefghijklmnopqrstuvwxyz"
888 "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
889 "`~!@#$%^&*()_=[]{}\\|;:'\",/<>? \t\v\r\n") {
890 s[0] = c;
891 r = std::from_chars(s.data(), s.data() + s.size(), x);
892
893 assert(r.ec == std::errc::invalid_argument);
894 assert(r.ptr == s.data());
895 assert(x == F(0.25));
896 }
897 }
898
899 // *** Success
900
901 { // number followed by non-numeric values
902 const char* s = "001x";
903
904 // the expected form of the subject sequence is a nonempty sequence of
905 // decimal digits optionally containing a decimal-point character, then
906 // an optional exponent part as defined in 6.4.4.3, excluding any digit
907 // separators (6.4.4.2); (C23 7.24.1.5)
908 r = std::from_chars(s, s + std::strlen(s: s), x);
909 assert(r.ec == std::errc{});
910 assert(r.ptr == s + 3);
911 assert(x == F(1.0));
912 }
913 { // no leading digit
914 const char* s = ".5e0";
915
916 // the expected form of the subject sequence is a nonempty sequence of
917 // decimal digits optionally containing a decimal-point character, then
918 // an optional exponent part as defined in 6.4.4.3, excluding any digit
919 // separators (6.4.4.2); (C23 7.24.1.5)
920 r = std::from_chars(s, s + std::strlen(s: s), x);
921 assert(r.ec == std::errc{});
922 assert(r.ptr == s + 4);
923 assert(x == F(0.5));
924 }
925 { // negative sign and no leading digit
926 const char* s = "-.5e0";
927
928 // the expected form of the subject sequence is a nonempty sequence of
929 // decimal digits optionally containing a decimal-point character, then
930 // an optional exponent part as defined in 6.4.4.3, excluding any digit
931 // separators (6.4.4.2); (C23 7.24.1.5)
932 r = std::from_chars(s, s + std::strlen(s: s), x);
933 assert(r.ec == std::errc{});
934 assert(r.ptr == s + 5);
935 assert(x == F(-0.5));
936 }
937 { // no leading digit
938 const char* s = ".5";
939
940 // the expected form of the subject sequence is a nonempty sequence of
941 // decimal digits optionally containing a decimal-point character, then
942 // an optional exponent part as defined in 6.4.4.3, excluding any digit
943 // separators (6.4.4.2); (C23 7.24.1.5)
944 r = std::from_chars(s, s + std::strlen(s: s), x);
945 assert(r.ec == std::errc{});
946 assert(r.ptr == s + 2);
947 assert(x == F(0.5));
948 }
949 { // negative sign and no leading digit
950 const char* s = "-.5";
951
952 // the expected form of the subject sequence is a nonempty sequence of
953 // decimal digits optionally containing a decimal-point character, then
954 // an optional exponent part as defined in 6.4.4.3, excluding any digit
955 // separators (6.4.4.2); (C23 7.24.1.5)
956 r = std::from_chars(s, s + std::strlen(s: s), x);
957 assert(r.ec == std::errc{});
958 assert(r.ptr == s + 3);
959 assert(x == F(-0.5));
960 }
961 { // double deciamal point
962 const char* s = "1.25.78";
963
964 // This number is halfway between two float values.
965 r = std::from_chars(s, s + std::strlen(s: s), x);
966 assert(r.ec == std::errc{});
967 assert(r.ptr == s + 4);
968 assert(x == F(1.25));
969 }
970 { // exponenent no sign
971 const char* s = "1.5e10";
972
973 r = std::from_chars(s, s + std::strlen(s: s), x);
974 assert(r.ec == std::errc{});
975 assert(r.ptr == s + 6);
976 assert(x == F(1.5e10));
977 }
978 { // exponenent capitalized no sign
979 const char* s = "1.5E10";
980
981 r = std::from_chars(s, s + std::strlen(s: s), x);
982 assert(r.ec == std::errc{});
983 assert(r.ptr == s + 6);
984 assert(x == F(1.5e10));
985 }
986 { // exponenent + sign
987 const char* s = "1.5e+10";
988
989 r = std::from_chars(s, s + std::strlen(s: s), x);
990 assert(r.ec == std::errc{});
991 assert(r.ptr == s + 7);
992 assert(x == F(1.5e10));
993 }
994 { // exponenent - sign
995 const char* s = "1.5e-10";
996
997 r = std::from_chars(s, s + std::strlen(s: s), x);
998 assert(r.ec == std::errc{});
999 assert(r.ptr == s + 7);
1000 assert(x == F(1.5e-10));
1001 }
1002 { // Exponent no number
1003 const char* s = "1.5e";
1004
1005 r = std::from_chars(s, s + std::strlen(s: s), x);
1006 assert(r.ec == std::errc{});
1007 assert(r.ptr == s + 3);
1008 assert(x == F(1.5));
1009 }
1010 { // Exponent sign no number
1011 {
1012 const char* s = "1.5e+";
1013
1014 r = std::from_chars(s, s + std::strlen(s: s), x);
1015 assert(r.ec == std::errc{});
1016 assert(r.ptr == s + 3);
1017 assert(x == F(1.5));
1018 }
1019 {
1020 const char* s = "1.5e-";
1021
1022 r = std::from_chars(s, s + std::strlen(s: s), x);
1023 assert(r.ec == std::errc{});
1024 assert(r.ptr == s + 3);
1025 assert(x == F(1.5));
1026 }
1027 }
1028 { // Exponent with whitespace
1029 {
1030 const char* s = "1.5e +1";
1031
1032 r = std::from_chars(s, s + std::strlen(s: s), x);
1033 assert(r.ec == std::errc{});
1034 assert(r.ptr == s + 3);
1035 assert(x == F(1.5));
1036 }
1037 {
1038 const char* s = "1.5e+ 1";
1039
1040 r = std::from_chars(s, s + std::strlen(s: s), x);
1041 assert(r.ec == std::errc{});
1042 assert(r.ptr == s + 3);
1043 assert(x == F(1.5));
1044 }
1045 {
1046 const char* s = "1.5e -1";
1047
1048 r = std::from_chars(s, s + std::strlen(s: s), x);
1049 assert(r.ec == std::errc{});
1050 assert(r.ptr == s + 3);
1051 assert(x == F(1.5));
1052 }
1053 {
1054 const char* s = "1.5e- 1";
1055
1056 r = std::from_chars(s, s + std::strlen(s: s), x);
1057 assert(r.ec == std::errc{});
1058 assert(r.ptr == s + 3);
1059 assert(x == F(1.5));
1060 }
1061 }
1062 { // exponent double sign
1063 {
1064 const char* s = "1.25e++12";
1065
1066 r = std::from_chars(s, s + std::strlen(s: s), x);
1067 assert(r.ec == std::errc{});
1068 assert(r.ptr == s + 4);
1069 assert(x == F(1.25));
1070 }
1071 {
1072 const char* s = "1.25e+-12";
1073
1074 r = std::from_chars(s, s + std::strlen(s: s), x);
1075 assert(r.ec == std::errc{});
1076 assert(r.ptr == s + 4);
1077 assert(x == F(1.25));
1078 }
1079 {
1080 const char* s = "1.25e-+12";
1081
1082 r = std::from_chars(s, s + std::strlen(s: s), x);
1083 assert(r.ec == std::errc{});
1084 assert(r.ptr == s + 4);
1085 assert(x == F(1.25));
1086 }
1087 {
1088 const char* s = "1.25e--12";
1089
1090 r = std::from_chars(s, s + std::strlen(s: s), x);
1091 assert(r.ec == std::errc{});
1092 assert(r.ptr == s + 4);
1093 assert(x == F(1.25));
1094 }
1095 }
1096 { // exponent hex prefix -> e0
1097 const char* s = "1.25e0x12";
1098
1099 r = std::from_chars(s, s + std::strlen(s: s), x);
1100 assert(r.ec == std::errc{});
1101 assert(r.ptr == s + 6);
1102 assert(x == F(1.25));
1103 }
1104 { // double exponent
1105 const char* s = "1.25e0e12";
1106
1107 r = std::from_chars(s, s + std::strlen(s: s), x);
1108 assert(r.ec == std::errc{});
1109 assert(r.ptr == s + 6);
1110 assert(x == F(1.25));
1111 }
1112 { // This number is halfway between two float values.
1113 const char* s = "20040229";
1114
1115 r = std::from_chars(s, s + std::strlen(s: s), x);
1116 assert(r.ec == std::errc{});
1117 assert(r.ptr == s + 8);
1118 assert(x == F(20040229));
1119 }
1120 { // Shifting mantissa exponent and no exponent
1121 const char* s = "123.456";
1122
1123 r = std::from_chars(s, s + std::strlen(s: s), x);
1124 assert(r.ec == std::errc{});
1125 assert(r.ptr == s + 7);
1126 assert(x == F(1.23456e2));
1127 }
1128 { // Shifting mantissa exponent and an exponent
1129 const char* s = "123.456e3";
1130
1131 r = std::from_chars(s, s + std::strlen(s: s), x);
1132 assert(r.ec == std::errc{});
1133 assert(r.ptr == s + 9);
1134 assert(x == F(1.23456e5));
1135 }
1136 { // Mantissa overflow
1137 {
1138 const char* s = "0.111111111111111111111111111111111111111111";
1139
1140 r = std::from_chars(s, s + std::strlen(s: s), x);
1141 assert(r.ec == std::errc{});
1142 assert(r.ptr == s + std::strlen(s: s));
1143 assert(x == F(0.111111111111111111111111111111111111111111));
1144 }
1145 {
1146 const char* s = "111111111111.111111111111111111111111111111111111111111";
1147
1148 r = std::from_chars(s, s + std::strlen(s: s), x);
1149 assert(r.ec == std::errc{});
1150 assert(r.ptr == s + std::strlen(s: s));
1151 assert(x == F(111111111111.111111111111111111111111111111111111111111));
1152 }
1153 }
1154 { // Negative value
1155 const char* s = "-0.25";
1156
1157 r = std::from_chars(s, s + std::strlen(s: s), x);
1158 assert(r.ec == std::errc{});
1159 assert(r.ptr == s + std::strlen(s: s));
1160 assert(x == F(-0.25));
1161 }
1162 { // value is too big -> +inf
1163 const char* s = "1e9999999999999999999999999999999999999999";
1164
1165 r = std::from_chars(s, s + std::strlen(s: s), x);
1166 assert(r.ec == std::errc::result_out_of_range);
1167 assert(r.ptr == s + strlen(s: s));
1168 assert(x == std::numeric_limits<F>::infinity());
1169 }
1170 { // negative value is too big -> -inf
1171 const char* s = "-1e9999999999999999999999999999999999999999";
1172
1173 r = std::from_chars(s, s + std::strlen(s: s), x);
1174 assert(r.ec == std::errc::result_out_of_range);
1175 assert(r.ptr == s + strlen(s: s));
1176 assert(x == -std::numeric_limits<F>::infinity());
1177 }
1178 { // value is too small -> 0
1179 const char* s = "1e-9999999999999999999999999999999999999999";
1180
1181 r = std::from_chars(s, s + std::strlen(s: s), x);
1182 assert(r.ec == std::errc::result_out_of_range);
1183 assert(r.ptr == s + strlen(s: s));
1184 assert(x == F(0.0));
1185 }
1186 { // negative value is too small -> -0
1187 const char* s = "-1e-9999999999999999999999999999999999999999";
1188
1189 r = std::from_chars(s, s + std::strlen(s: s), x);
1190 assert(r.ec == std::errc::result_out_of_range);
1191 assert(r.ptr == s + strlen(s: s));
1192 assert(x == F(-0.0));
1193 }
1194 }
1195};
1196
1197template <class F>
1198struct test_hex {
1199 void operator()() {
1200 std::from_chars_result r;
1201 F x = 0.25;
1202
1203 // *** Failures
1204
1205 { // Starts with invalid character
1206 std::array s = {' ', '1', 'e', '0'};
1207 for (auto c : "ghijklmnopqrstuvwxyz"
1208 "GHIJKLMNOPQRSTUVWXYZ"
1209 "`~!@#$%^&*()_=[]{}\\|;:'\",/<>? \t\v\r\n") {
1210 s[0] = c;
1211 r = std::from_chars(s.data(), s.data() + s.size(), x, std::chars_format::hex);
1212
1213 assert(r.ec == std::errc::invalid_argument);
1214 assert(r.ptr == s.data());
1215 assert(x == F(0.25));
1216 }
1217 }
1218
1219 // *** Success
1220
1221 { // number followed by non-numeric values
1222 const char* s = "001x";
1223
1224 // the expected form of the subject sequence is a nonempty sequence of
1225 // decimal digits optionally containing a decimal-point character, then
1226 // an optional exponent part as defined in 6.4.4.3, excluding any digit
1227 // separators (6.4.4.2); (C23 7.24.1.5)
1228 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1229 assert(r.ec == std::errc{});
1230 assert(r.ptr == s + 3);
1231 assert(x == F(1.0));
1232 }
1233 { // no leading digit
1234 const char* s = ".5p0";
1235
1236 // the expected form of the subject sequence is a nonempty sequence of
1237 // decimal digits optionally containing a decimal-point character, then
1238 // an optional exponent part as defined in 6.4.4.3, excluding any digit
1239 // separators (6.4.4.2); (C23 7.24.1.5)
1240 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1241 assert(r.ec == std::errc{});
1242 assert(r.ptr == s + 4);
1243 assert(x == F(0x0.5p0));
1244 }
1245 { // negative sign and no leading digit
1246 const char* s = "-.5p0";
1247
1248 // the expected form of the subject sequence is a nonempty sequence of
1249 // decimal digits optionally containing a decimal-point character, then
1250 // an optional exponent part as defined in 6.4.4.3, excluding any digit
1251 // separators (6.4.4.2); (C23 7.24.1.5)
1252 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1253 assert(r.ec == std::errc{});
1254 assert(r.ptr == s + 5);
1255 assert(x == F(-0x0.5p0));
1256 }
1257 { // no leading digit
1258 const char* s = ".5";
1259
1260 // the expected form of the subject sequence is a nonempty sequence of
1261 // decimal digits optionally containing a decimal-point character, then
1262 // an optional exponent part as defined in 6.4.4.3, excluding any digit
1263 // separators (6.4.4.2); (C23 7.24.1.5)
1264 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1265 assert(r.ec == std::errc{});
1266 assert(r.ptr == s + 2);
1267 assert(x == F(0x0.5p0));
1268 }
1269 { // negative sign and no leading digit
1270 const char* s = "-.5";
1271
1272 // the expected form of the subject sequence is a nonempty sequence of
1273 // decimal digits optionally containing a decimal-point character, then
1274 // an optional exponent part as defined in 6.4.4.3, excluding any digit
1275 // separators (6.4.4.2); (C23 7.24.1.5)
1276 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1277 assert(r.ec == std::errc{});
1278 assert(r.ptr == s + 3);
1279 assert(x == F(-0x0.5p0));
1280 }
1281 { // double deciamal point
1282 const char* s = "1.25.78";
1283
1284 // This number is halfway between two float values.
1285 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1286 assert(r.ec == std::errc{});
1287 assert(r.ptr == s + 4);
1288 assert(x == F(0x1.25p0));
1289 }
1290 { // exponenent no sign
1291 const char* s = "1.5p10";
1292
1293 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1294 assert(r.ec == std::errc{});
1295 assert(r.ptr == s + 6);
1296 assert(x == F(0x1.5p10));
1297 }
1298 { // exponenent capitalized no sign
1299 const char* s = "1.5P10";
1300
1301 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1302 assert(r.ec == std::errc{});
1303 assert(r.ptr == s + 6);
1304 assert(x == F(0x1.5p10));
1305 }
1306 { // exponenent + sign
1307 const char* s = "1.5p+10";
1308
1309 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1310 assert(r.ec == std::errc{});
1311 assert(r.ptr == s + 7);
1312 assert(x == F(0x1.5p10));
1313 }
1314 { // exponenent - sign
1315 const char* s = "1.5p-10";
1316
1317 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1318 assert(r.ec == std::errc{});
1319 assert(r.ptr == s + 7);
1320 assert(x == F(0x1.5p-10));
1321 }
1322 { // Exponent no number
1323 const char* s = "1.5p";
1324
1325 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1326 assert(r.ec == std::errc{});
1327 assert(r.ptr == s + 3);
1328 assert(x == F(0x1.5p0));
1329 }
1330 { // Exponent sign no number
1331 {
1332 const char* s = "1.5p+";
1333
1334 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1335 assert(r.ec == std::errc{});
1336 assert(r.ptr == s + 3);
1337 assert(x == F(0x1.5p0));
1338 }
1339 {
1340 const char* s = "1.5p-";
1341
1342 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1343 assert(r.ec == std::errc{});
1344 assert(r.ptr == s + 3);
1345 assert(x == F(0x1.5p0));
1346 }
1347 }
1348 { // Exponent with whitespace
1349 {
1350 const char* s = "1.5p +1";
1351
1352 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1353 assert(r.ec == std::errc{});
1354 assert(r.ptr == s + 3);
1355 assert(x == F(0x1.5p0));
1356 }
1357 {
1358 const char* s = "1.5p+ 1";
1359
1360 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1361 assert(r.ec == std::errc{});
1362 assert(r.ptr == s + 3);
1363 assert(x == F(0x1.5p0));
1364 }
1365 {
1366 const char* s = "1.5p -1";
1367
1368 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1369 assert(r.ec == std::errc{});
1370 assert(r.ptr == s + 3);
1371 assert(x == F(0x1.5p0));
1372 }
1373 {
1374 const char* s = "1.5p- 1";
1375
1376 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1377 assert(r.ec == std::errc{});
1378 assert(r.ptr == s + 3);
1379 assert(x == F(0x1.5p0));
1380 }
1381 }
1382 { // Exponent double sign
1383 {
1384 const char* s = "1.25p++12";
1385
1386 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1387 assert(r.ec == std::errc{});
1388 assert(r.ptr == s + 4);
1389 assert(x == F(0x1.25p0));
1390 }
1391 {
1392 const char* s = "1.25p+-12";
1393
1394 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1395 assert(r.ec == std::errc{});
1396 assert(r.ptr == s + 4);
1397 assert(x == F(0x1.25p0));
1398 }
1399 {
1400 const char* s = "1.25p-+12";
1401
1402 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1403 assert(r.ec == std::errc{});
1404 assert(r.ptr == s + 4);
1405 assert(x == F(0x1.25p0));
1406 }
1407 {
1408 const char* s = "1.25p--12";
1409
1410 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1411 assert(r.ec == std::errc{});
1412 assert(r.ptr == s + 4);
1413 assert(x == F(0x1.25p0));
1414 }
1415 }
1416 { // exponent hex prefix -> p0
1417 const char* s = "1.25p0x12";
1418
1419 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1420 assert(r.ec == std::errc{});
1421 assert(r.ptr == s + 6);
1422 assert(x == F(0x1.25p0));
1423 }
1424 { // double exponent
1425 const char* s = "1.25p0p12";
1426
1427 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1428 assert(r.ec == std::errc{});
1429 assert(r.ptr == s + 6);
1430 assert(x == F(0x1.25p0));
1431 }
1432 { // This number is halfway between two float values.
1433 const char* s = "131CA25";
1434
1435 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1436 assert(r.ec == std::errc{});
1437 assert(r.ptr == s + 7);
1438 assert(x == F(0x131CA25p0));
1439 }
1440 { // Shifting mantissa exponent and no exponent
1441 const char* s = "123.456";
1442
1443 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1444 assert(r.ec == std::errc{});
1445 assert(r.ptr == s + 7);
1446 assert(x == F(0x123.456p0));
1447 }
1448 { // Shifting mantissa exponent and an exponent
1449 const char* s = "123.456p3";
1450
1451 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1452 assert(r.ec == std::errc{});
1453 assert(r.ptr == s + 9);
1454 assert(x == F(0x123.456p3));
1455 }
1456 { // Mantissa overflow
1457 {
1458 const char* s = "0.111111111111111111111111111111111111111111";
1459
1460 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1461 assert(r.ec == std::errc{});
1462 assert(r.ptr == s + std::strlen(s: s));
1463 assert(x == F(0x0.111111111111111111111111111111111111111111p0));
1464 }
1465 {
1466 const char* s = "111111111111.111111111111111111111111111111111111111111";
1467
1468 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1469 assert(r.ec == std::errc{});
1470 assert(r.ptr == s + std::strlen(s: s));
1471 assert(x == F(0x111111111111.111111111111111111111111111111111111111111p0));
1472 }
1473 }
1474 { // Negative value
1475 const char* s = "-0.25";
1476
1477 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1478 assert(r.ec == std::errc{});
1479 assert(r.ptr == s + std::strlen(s: s));
1480 assert(x == F(-0x0.25p0));
1481 }
1482 { // value is too big -> +inf
1483 const char* s = "1p9999999999999999999999999999999999999999";
1484
1485 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1486 assert(r.ec == std::errc::result_out_of_range);
1487 assert(r.ptr == s + strlen(s: s));
1488 assert(x == std::numeric_limits<F>::infinity());
1489 }
1490 { // negative value is too big -> -inf
1491 const char* s = "-1p9999999999999999999999999999999999999999";
1492
1493 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1494 assert(r.ec == std::errc::result_out_of_range);
1495 assert(r.ptr == s + strlen(s: s));
1496 assert(x == -std::numeric_limits<F>::infinity());
1497 }
1498 { // value is too small -> 0
1499 const char* s = "1p-9999999999999999999999999999999999999999";
1500
1501 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1502 assert(r.ec == std::errc::result_out_of_range);
1503 assert(r.ptr == s + strlen(s: s));
1504 assert(x == F(0.0));
1505 }
1506 { // negative value is too small -> -0
1507 const char* s = "-1p-9999999999999999999999999999999999999999";
1508
1509 r = std::from_chars(s, s + std::strlen(s: s), x, std::chars_format::hex);
1510 assert(r.ec == std::errc::result_out_of_range);
1511 assert(r.ptr == s + strlen(s: s));
1512 assert(x == F(-0.0));
1513 }
1514 }
1515};
1516
1517// The test
1518// test/std/utilities/charconv/charconv.msvc/test.cpp
1519// uses random values. This tests contains errors found by this test.
1520void test_random_errors() {
1521 {
1522 const char* s = "4.219902180869891e-2788";
1523 const char* last = s + std::strlen(s: s) - 1;
1524
1525 // last + 1 contains a digit. When that value is parsed the exponent is
1526 // e-2788 which returns std::errc::result_out_of_range and the value 0.
1527 // the proper exponent is e-278, which can be represented by a double.
1528
1529 double value = 0.25;
1530 std::from_chars_result result = std::from_chars(first: s, last: last, value&: value);
1531
1532 assert(result.ec == std::errc{});
1533 assert(result.ptr == last);
1534 assert(value == 4.219902180869891e-278);
1535 }
1536 {
1537 const char* s = "7.411412e-39U";
1538 const char* last = s + std::strlen(s: s) - 1;
1539
1540 float value = 0.25;
1541 std::from_chars_result result = std::from_chars(first: s, last: last, value&: value);
1542
1543 assert(result.ec == std::errc{});
1544 assert(result.ptr == last);
1545 assert(value == 7.411412e-39F);
1546 }
1547}
1548
1549int main(int, char**) {
1550 run<test_basics>(all_floats);
1551 run<test_scientific>(all_floats);
1552 run<test_fixed>(all_floats);
1553 run<test_general>(all_floats);
1554
1555 run<test_hex>(all_floats);
1556
1557 test_random_errors();
1558
1559 return 0;
1560}
1561

source code of libcxx/test/std/utilities/charconv/charconv.from.chars/floating_point.pass.cpp