92.28% Lines (1410/1528) 100.00% Functions (32/32)
TLA Baseline Branch
Line Hits Code Line Hits Code
1   // 1   //
2   // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com) 2   // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
3   // Copyright (c) 2020 Krystian Stasiowski (sdkrystian@gmail.com) 3   // Copyright (c) 2020 Krystian Stasiowski (sdkrystian@gmail.com)
4   // 4   //
5   // Distributed under the Boost Software License, Version 1.0. (See accompanying 5   // Distributed under the Boost Software License, Version 1.0. (See accompanying
6   // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 6   // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7   // 7   //
8   // Official repository: https://github.com/boostorg/json 8   // Official repository: https://github.com/boostorg/json
9   // 9   //
10   10  
11   #ifndef BOOST_JSON_BASIC_PARSER_IMPL_HPP 11   #ifndef BOOST_JSON_BASIC_PARSER_IMPL_HPP
12   #define BOOST_JSON_BASIC_PARSER_IMPL_HPP 12   #define BOOST_JSON_BASIC_PARSER_IMPL_HPP
13   13  
14   #include <boost/json/detail/config.hpp> 14   #include <boost/json/detail/config.hpp>
15   #include <boost/json/detail/literals.hpp> 15   #include <boost/json/detail/literals.hpp>
16   #include <boost/json/basic_parser.hpp> 16   #include <boost/json/basic_parser.hpp>
17   #include <boost/json/error.hpp> 17   #include <boost/json/error.hpp>
18   #include <boost/json/detail/buffer.hpp> 18   #include <boost/json/detail/buffer.hpp>
19   #include <boost/json/detail/charconv/from_chars.hpp> 19   #include <boost/json/detail/charconv/from_chars.hpp>
20   #include <boost/json/detail/sse2.hpp> 20   #include <boost/json/detail/sse2.hpp>
21   #include <boost/mp11/algorithm.hpp> 21   #include <boost/mp11/algorithm.hpp>
22   #include <boost/mp11/integral.hpp> 22   #include <boost/mp11/integral.hpp>
23   #include <cmath> 23   #include <cmath>
24   #include <limits> 24   #include <limits>
25   #include <cstring> 25   #include <cstring>
26   26  
27   #ifdef _MSC_VER 27   #ifdef _MSC_VER
28   #pragma warning(push) 28   #pragma warning(push)
29   #pragma warning(disable: 4702) // unreachable code 29   #pragma warning(disable: 4702) // unreachable code
30   #pragma warning(disable: 4127) // conditional expression is constant 30   #pragma warning(disable: 4127) // conditional expression is constant
31   #endif 31   #endif
32   32  
33   /* This file must be manually included to get the 33   /* This file must be manually included to get the
34   function template definitions for basic_parser. 34   function template definitions for basic_parser.
35   */ 35   */
36   36  
37   /* Reference: 37   /* Reference:
38   38  
39   https://www.json.org/ 39   https://www.json.org/
40   40  
41   RFC 7159: The JavaScript Object Notation (JSON) Data Interchange Format 41   RFC 7159: The JavaScript Object Notation (JSON) Data Interchange Format
42   https://tools.ietf.org/html/rfc7159 42   https://tools.ietf.org/html/rfc7159
43   43  
44   https://ampl.com/netlib/fp/dtoa.c 44   https://ampl.com/netlib/fp/dtoa.c
45   */ 45   */
46   46  
47   #ifndef BOOST_JSON_DOCS 47   #ifndef BOOST_JSON_DOCS
48   48  
49   namespace boost { 49   namespace boost {
50   namespace json { 50   namespace json {
51   namespace detail { 51   namespace detail {
52   52  
53   inline 53   inline
54   double 54   double
HITCBC 55   1042951 pow10(int exp) noexcept 55   1042951 pow10(int exp) noexcept
56   { 56   {
57   static double const tab[618] = { 57   static double const tab[618] = {
58   1e-308, 1e-307, 1e-306, 1e-305, 1e-304, 1e-303, 1e-302, 1e-301, 58   1e-308, 1e-307, 1e-306, 1e-305, 1e-304, 1e-303, 1e-302, 1e-301,
59   59  
60   1e-300, 1e-299, 1e-298, 1e-297, 1e-296, 1e-295, 1e-294, 1e-293, 1e-292, 1e-291, 60   1e-300, 1e-299, 1e-298, 1e-297, 1e-296, 1e-295, 1e-294, 1e-293, 1e-292, 1e-291,
61   1e-290, 1e-289, 1e-288, 1e-287, 1e-286, 1e-285, 1e-284, 1e-283, 1e-282, 1e-281, 61   1e-290, 1e-289, 1e-288, 1e-287, 1e-286, 1e-285, 1e-284, 1e-283, 1e-282, 1e-281,
62   1e-280, 1e-279, 1e-278, 1e-277, 1e-276, 1e-275, 1e-274, 1e-273, 1e-272, 1e-271, 62   1e-280, 1e-279, 1e-278, 1e-277, 1e-276, 1e-275, 1e-274, 1e-273, 1e-272, 1e-271,
63   1e-270, 1e-269, 1e-268, 1e-267, 1e-266, 1e-265, 1e-264, 1e-263, 1e-262, 1e-261, 63   1e-270, 1e-269, 1e-268, 1e-267, 1e-266, 1e-265, 1e-264, 1e-263, 1e-262, 1e-261,
64   1e-260, 1e-259, 1e-258, 1e-257, 1e-256, 1e-255, 1e-254, 1e-253, 1e-252, 1e-251, 64   1e-260, 1e-259, 1e-258, 1e-257, 1e-256, 1e-255, 1e-254, 1e-253, 1e-252, 1e-251,
65   1e-250, 1e-249, 1e-248, 1e-247, 1e-246, 1e-245, 1e-244, 1e-243, 1e-242, 1e-241, 65   1e-250, 1e-249, 1e-248, 1e-247, 1e-246, 1e-245, 1e-244, 1e-243, 1e-242, 1e-241,
66   1e-240, 1e-239, 1e-238, 1e-237, 1e-236, 1e-235, 1e-234, 1e-233, 1e-232, 1e-231, 66   1e-240, 1e-239, 1e-238, 1e-237, 1e-236, 1e-235, 1e-234, 1e-233, 1e-232, 1e-231,
67   1e-230, 1e-229, 1e-228, 1e-227, 1e-226, 1e-225, 1e-224, 1e-223, 1e-222, 1e-221, 67   1e-230, 1e-229, 1e-228, 1e-227, 1e-226, 1e-225, 1e-224, 1e-223, 1e-222, 1e-221,
68   1e-220, 1e-219, 1e-218, 1e-217, 1e-216, 1e-215, 1e-214, 1e-213, 1e-212, 1e-211, 68   1e-220, 1e-219, 1e-218, 1e-217, 1e-216, 1e-215, 1e-214, 1e-213, 1e-212, 1e-211,
69   1e-210, 1e-209, 1e-208, 1e-207, 1e-206, 1e-205, 1e-204, 1e-203, 1e-202, 1e-201, 69   1e-210, 1e-209, 1e-208, 1e-207, 1e-206, 1e-205, 1e-204, 1e-203, 1e-202, 1e-201,
70   70  
71   1e-200, 1e-199, 1e-198, 1e-197, 1e-196, 1e-195, 1e-194, 1e-193, 1e-192, 1e-191, 71   1e-200, 1e-199, 1e-198, 1e-197, 1e-196, 1e-195, 1e-194, 1e-193, 1e-192, 1e-191,
72   1e-190, 1e-189, 1e-188, 1e-187, 1e-186, 1e-185, 1e-184, 1e-183, 1e-182, 1e-181, 72   1e-190, 1e-189, 1e-188, 1e-187, 1e-186, 1e-185, 1e-184, 1e-183, 1e-182, 1e-181,
73   1e-180, 1e-179, 1e-178, 1e-177, 1e-176, 1e-175, 1e-174, 1e-173, 1e-172, 1e-171, 73   1e-180, 1e-179, 1e-178, 1e-177, 1e-176, 1e-175, 1e-174, 1e-173, 1e-172, 1e-171,
74   1e-170, 1e-169, 1e-168, 1e-167, 1e-166, 1e-165, 1e-164, 1e-163, 1e-162, 1e-161, 74   1e-170, 1e-169, 1e-168, 1e-167, 1e-166, 1e-165, 1e-164, 1e-163, 1e-162, 1e-161,
75   1e-160, 1e-159, 1e-158, 1e-157, 1e-156, 1e-155, 1e-154, 1e-153, 1e-152, 1e-151, 75   1e-160, 1e-159, 1e-158, 1e-157, 1e-156, 1e-155, 1e-154, 1e-153, 1e-152, 1e-151,
76   1e-150, 1e-149, 1e-148, 1e-147, 1e-146, 1e-145, 1e-144, 1e-143, 1e-142, 1e-141, 76   1e-150, 1e-149, 1e-148, 1e-147, 1e-146, 1e-145, 1e-144, 1e-143, 1e-142, 1e-141,
77   1e-140, 1e-139, 1e-138, 1e-137, 1e-136, 1e-135, 1e-134, 1e-133, 1e-132, 1e-131, 77   1e-140, 1e-139, 1e-138, 1e-137, 1e-136, 1e-135, 1e-134, 1e-133, 1e-132, 1e-131,
78   1e-130, 1e-129, 1e-128, 1e-127, 1e-126, 1e-125, 1e-124, 1e-123, 1e-122, 1e-121, 78   1e-130, 1e-129, 1e-128, 1e-127, 1e-126, 1e-125, 1e-124, 1e-123, 1e-122, 1e-121,
79   1e-120, 1e-119, 1e-118, 1e-117, 1e-116, 1e-115, 1e-114, 1e-113, 1e-112, 1e-111, 79   1e-120, 1e-119, 1e-118, 1e-117, 1e-116, 1e-115, 1e-114, 1e-113, 1e-112, 1e-111,
80   1e-110, 1e-109, 1e-108, 1e-107, 1e-106, 1e-105, 1e-104, 1e-103, 1e-102, 1e-101, 80   1e-110, 1e-109, 1e-108, 1e-107, 1e-106, 1e-105, 1e-104, 1e-103, 1e-102, 1e-101,
81   81  
82   1e-100, 1e-099, 1e-098, 1e-097, 1e-096, 1e-095, 1e-094, 1e-093, 1e-092, 1e-091, 82   1e-100, 1e-099, 1e-098, 1e-097, 1e-096, 1e-095, 1e-094, 1e-093, 1e-092, 1e-091,
83   1e-090, 1e-089, 1e-088, 1e-087, 1e-086, 1e-085, 1e-084, 1e-083, 1e-082, 1e-081, 83   1e-090, 1e-089, 1e-088, 1e-087, 1e-086, 1e-085, 1e-084, 1e-083, 1e-082, 1e-081,
84   1e-080, 1e-079, 1e-078, 1e-077, 1e-076, 1e-075, 1e-074, 1e-073, 1e-072, 1e-071, 84   1e-080, 1e-079, 1e-078, 1e-077, 1e-076, 1e-075, 1e-074, 1e-073, 1e-072, 1e-071,
85   1e-070, 1e-069, 1e-068, 1e-067, 1e-066, 1e-065, 1e-064, 1e-063, 1e-062, 1e-061, 85   1e-070, 1e-069, 1e-068, 1e-067, 1e-066, 1e-065, 1e-064, 1e-063, 1e-062, 1e-061,
86   1e-060, 1e-059, 1e-058, 1e-057, 1e-056, 1e-055, 1e-054, 1e-053, 1e-052, 1e-051, 86   1e-060, 1e-059, 1e-058, 1e-057, 1e-056, 1e-055, 1e-054, 1e-053, 1e-052, 1e-051,
87   1e-050, 1e-049, 1e-048, 1e-047, 1e-046, 1e-045, 1e-044, 1e-043, 1e-042, 1e-041, 87   1e-050, 1e-049, 1e-048, 1e-047, 1e-046, 1e-045, 1e-044, 1e-043, 1e-042, 1e-041,
88   1e-040, 1e-039, 1e-038, 1e-037, 1e-036, 1e-035, 1e-034, 1e-033, 1e-032, 1e-031, 88   1e-040, 1e-039, 1e-038, 1e-037, 1e-036, 1e-035, 1e-034, 1e-033, 1e-032, 1e-031,
89   1e-030, 1e-029, 1e-028, 1e-027, 1e-026, 1e-025, 1e-024, 1e-023, 1e-022, 1e-021, 89   1e-030, 1e-029, 1e-028, 1e-027, 1e-026, 1e-025, 1e-024, 1e-023, 1e-022, 1e-021,
90   1e-020, 1e-019, 1e-018, 1e-017, 1e-016, 1e-015, 1e-014, 1e-013, 1e-012, 1e-011, 90   1e-020, 1e-019, 1e-018, 1e-017, 1e-016, 1e-015, 1e-014, 1e-013, 1e-012, 1e-011,
91   1e-010, 1e-009, 1e-008, 1e-007, 1e-006, 1e-005, 1e-004, 1e-003, 1e-002, 1e-001, 91   1e-010, 1e-009, 1e-008, 1e-007, 1e-006, 1e-005, 1e-004, 1e-003, 1e-002, 1e-001,
92   92  
93   1e+000, 1e+001, 1e+002, 1e+003, 1e+004, 1e+005, 1e+006, 1e+007, 1e+008, 1e+009, 93   1e+000, 1e+001, 1e+002, 1e+003, 1e+004, 1e+005, 1e+006, 1e+007, 1e+008, 1e+009,
94   1e+010, 1e+011, 1e+012, 1e+013, 1e+014, 1e+015, 1e+016, 1e+017, 1e+018, 1e+019, 94   1e+010, 1e+011, 1e+012, 1e+013, 1e+014, 1e+015, 1e+016, 1e+017, 1e+018, 1e+019,
95   1e+020, 1e+021, 1e+022, 1e+023, 1e+024, 1e+025, 1e+026, 1e+027, 1e+028, 1e+029, 95   1e+020, 1e+021, 1e+022, 1e+023, 1e+024, 1e+025, 1e+026, 1e+027, 1e+028, 1e+029,
96   1e+030, 1e+031, 1e+032, 1e+033, 1e+034, 1e+035, 1e+036, 1e+037, 1e+038, 1e+039, 96   1e+030, 1e+031, 1e+032, 1e+033, 1e+034, 1e+035, 1e+036, 1e+037, 1e+038, 1e+039,
97   1e+040, 1e+041, 1e+042, 1e+043, 1e+044, 1e+045, 1e+046, 1e+047, 1e+048, 1e+049, 97   1e+040, 1e+041, 1e+042, 1e+043, 1e+044, 1e+045, 1e+046, 1e+047, 1e+048, 1e+049,
98   1e+050, 1e+051, 1e+052, 1e+053, 1e+054, 1e+055, 1e+056, 1e+057, 1e+058, 1e+059, 98   1e+050, 1e+051, 1e+052, 1e+053, 1e+054, 1e+055, 1e+056, 1e+057, 1e+058, 1e+059,
99   1e+060, 1e+061, 1e+062, 1e+063, 1e+064, 1e+065, 1e+066, 1e+067, 1e+068, 1e+069, 99   1e+060, 1e+061, 1e+062, 1e+063, 1e+064, 1e+065, 1e+066, 1e+067, 1e+068, 1e+069,
100   1e+070, 1e+071, 1e+072, 1e+073, 1e+074, 1e+075, 1e+076, 1e+077, 1e+078, 1e+079, 100   1e+070, 1e+071, 1e+072, 1e+073, 1e+074, 1e+075, 1e+076, 1e+077, 1e+078, 1e+079,
101   1e+080, 1e+081, 1e+082, 1e+083, 1e+084, 1e+085, 1e+086, 1e+087, 1e+088, 1e+089, 101   1e+080, 1e+081, 1e+082, 1e+083, 1e+084, 1e+085, 1e+086, 1e+087, 1e+088, 1e+089,
102   1e+090, 1e+091, 1e+092, 1e+093, 1e+094, 1e+095, 1e+096, 1e+097, 1e+098, 1e+099, 102   1e+090, 1e+091, 1e+092, 1e+093, 1e+094, 1e+095, 1e+096, 1e+097, 1e+098, 1e+099,
103   103  
104   1e+100, 1e+101, 1e+102, 1e+103, 1e+104, 1e+105, 1e+106, 1e+107, 1e+108, 1e+109, 104   1e+100, 1e+101, 1e+102, 1e+103, 1e+104, 1e+105, 1e+106, 1e+107, 1e+108, 1e+109,
105   1e+110, 1e+111, 1e+112, 1e+113, 1e+114, 1e+115, 1e+116, 1e+117, 1e+118, 1e+119, 105   1e+110, 1e+111, 1e+112, 1e+113, 1e+114, 1e+115, 1e+116, 1e+117, 1e+118, 1e+119,
106   1e+120, 1e+121, 1e+122, 1e+123, 1e+124, 1e+125, 1e+126, 1e+127, 1e+128, 1e+129, 106   1e+120, 1e+121, 1e+122, 1e+123, 1e+124, 1e+125, 1e+126, 1e+127, 1e+128, 1e+129,
107   1e+130, 1e+131, 1e+132, 1e+133, 1e+134, 1e+135, 1e+136, 1e+137, 1e+138, 1e+139, 107   1e+130, 1e+131, 1e+132, 1e+133, 1e+134, 1e+135, 1e+136, 1e+137, 1e+138, 1e+139,
108   1e+140, 1e+141, 1e+142, 1e+143, 1e+144, 1e+145, 1e+146, 1e+147, 1e+148, 1e+149, 108   1e+140, 1e+141, 1e+142, 1e+143, 1e+144, 1e+145, 1e+146, 1e+147, 1e+148, 1e+149,
109   1e+150, 1e+151, 1e+152, 1e+153, 1e+154, 1e+155, 1e+156, 1e+157, 1e+158, 1e+159, 109   1e+150, 1e+151, 1e+152, 1e+153, 1e+154, 1e+155, 1e+156, 1e+157, 1e+158, 1e+159,
110   1e+160, 1e+161, 1e+162, 1e+163, 1e+164, 1e+165, 1e+166, 1e+167, 1e+168, 1e+169, 110   1e+160, 1e+161, 1e+162, 1e+163, 1e+164, 1e+165, 1e+166, 1e+167, 1e+168, 1e+169,
111   1e+170, 1e+171, 1e+172, 1e+173, 1e+174, 1e+175, 1e+176, 1e+177, 1e+178, 1e+179, 111   1e+170, 1e+171, 1e+172, 1e+173, 1e+174, 1e+175, 1e+176, 1e+177, 1e+178, 1e+179,
112   1e+180, 1e+181, 1e+182, 1e+183, 1e+184, 1e+185, 1e+186, 1e+187, 1e+188, 1e+189, 112   1e+180, 1e+181, 1e+182, 1e+183, 1e+184, 1e+185, 1e+186, 1e+187, 1e+188, 1e+189,
113   1e+190, 1e+191, 1e+192, 1e+193, 1e+194, 1e+195, 1e+196, 1e+197, 1e+198, 1e+199, 113   1e+190, 1e+191, 1e+192, 1e+193, 1e+194, 1e+195, 1e+196, 1e+197, 1e+198, 1e+199,
114   114  
115   1e+200, 1e+201, 1e+202, 1e+203, 1e+204, 1e+205, 1e+206, 1e+207, 1e+208, 1e+209, 115   1e+200, 1e+201, 1e+202, 1e+203, 1e+204, 1e+205, 1e+206, 1e+207, 1e+208, 1e+209,
116   1e+210, 1e+211, 1e+212, 1e+213, 1e+214, 1e+215, 1e+216, 1e+217, 1e+218, 1e+219, 116   1e+210, 1e+211, 1e+212, 1e+213, 1e+214, 1e+215, 1e+216, 1e+217, 1e+218, 1e+219,
117   1e+220, 1e+221, 1e+222, 1e+223, 1e+224, 1e+225, 1e+226, 1e+227, 1e+228, 1e+229, 117   1e+220, 1e+221, 1e+222, 1e+223, 1e+224, 1e+225, 1e+226, 1e+227, 1e+228, 1e+229,
118   1e+230, 1e+231, 1e+232, 1e+233, 1e+234, 1e+235, 1e+236, 1e+237, 1e+238, 1e+239, 118   1e+230, 1e+231, 1e+232, 1e+233, 1e+234, 1e+235, 1e+236, 1e+237, 1e+238, 1e+239,
119   1e+240, 1e+241, 1e+242, 1e+243, 1e+244, 1e+245, 1e+246, 1e+247, 1e+248, 1e+249, 119   1e+240, 1e+241, 1e+242, 1e+243, 1e+244, 1e+245, 1e+246, 1e+247, 1e+248, 1e+249,
120   1e+250, 1e+251, 1e+252, 1e+253, 1e+254, 1e+255, 1e+256, 1e+257, 1e+258, 1e+259, 120   1e+250, 1e+251, 1e+252, 1e+253, 1e+254, 1e+255, 1e+256, 1e+257, 1e+258, 1e+259,
121   1e+260, 1e+261, 1e+262, 1e+263, 1e+264, 1e+265, 1e+266, 1e+267, 1e+268, 1e+269, 121   1e+260, 1e+261, 1e+262, 1e+263, 1e+264, 1e+265, 1e+266, 1e+267, 1e+268, 1e+269,
122   1e+270, 1e+271, 1e+272, 1e+273, 1e+274, 1e+275, 1e+276, 1e+277, 1e+278, 1e+279, 122   1e+270, 1e+271, 1e+272, 1e+273, 1e+274, 1e+275, 1e+276, 1e+277, 1e+278, 1e+279,
123   1e+280, 1e+281, 1e+282, 1e+283, 1e+284, 1e+285, 1e+286, 1e+287, 1e+288, 1e+289, 123   1e+280, 1e+281, 1e+282, 1e+283, 1e+284, 1e+285, 1e+286, 1e+287, 1e+288, 1e+289,
124   1e+290, 1e+291, 1e+292, 1e+293, 1e+294, 1e+295, 1e+296, 1e+297, 1e+298, 1e+299, 124   1e+290, 1e+291, 1e+292, 1e+293, 1e+294, 1e+295, 1e+296, 1e+297, 1e+298, 1e+299,
125   125  
126   1e+300, 1e+301, 1e+302, 1e+303, 1e+304, 1e+305, 1e+306, 1e+307, 1e+308 }; 126   1e+300, 1e+301, 1e+302, 1e+303, 1e+304, 1e+305, 1e+306, 1e+307, 1e+308 };
127   127  
HITCBC 128   1042951 if( exp > 308 ) 128   1042951 if( exp > 308 )
129   { 129   {
HITCBC 130   341 return std::numeric_limits<double>::infinity(); 130   341 return std::numeric_limits<double>::infinity();
131   } 131   }
HITCBC 132   1042610 else if( exp < -308 ) 132   1042610 else if( exp < -308 )
133   { 133   {
134   // due to the way pow10 is used by dec_to_float, 134   // due to the way pow10 is used by dec_to_float,
135   // we can afford to return 0.0 here 135   // we can afford to return 0.0 here
HITCBC 136   151 return 0.0; 136   151 return 0.0;
137   } 137   }
138   else 138   else
139   { 139   {
HITCBC 140   1042459 exp += 308; 140   1042459 exp += 308;
HITCBC 141   1042459 BOOST_ASSERT(exp >= 0 && exp < 618); 141   1042459 BOOST_ASSERT(exp >= 0 && exp < 618);
HITCBC 142   1042459 return tab[exp]; 142   1042459 return tab[exp];
143   } 143   }
144   } 144   }
145   145  
146   inline 146   inline
147   double 147   double
HITCBC 148   1042951 dec_to_float( 148   1042951 dec_to_float(
149   std::uint64_t m, 149   std::uint64_t m,
150   std::int32_t e, 150   std::int32_t e,
151   bool neg) noexcept 151   bool neg) noexcept
152   { 152   {
153   // convert to double explicitly to silence warnings 153   // convert to double explicitly to silence warnings
HITCBC 154   1042951 double x = static_cast<double>(m); 154   1042951 double x = static_cast<double>(m);
HITCBC 155   1042951 if(neg) 155   1042951 if(neg)
HITCBC 156   17062 x = -x; 156   17062 x = -x;
157   157  
HITCBC 158   1042951 if(e < -305) 158   1042951 if(e < -305)
159   { 159   {
HITCBC 160   5269 x *= 1e-305 ; 160   5269 x *= 1e-305 ;
HITCBC 161   5269 e += 305; 161   5269 e += 305;
162   } 162   }
163   163  
HITCBC 164   1042951 if(e >= -22 && e < 0) 164   1042951 if(e >= -22 && e < 0)
HITCBC 165   59279 return x / pow10(-e); 165   59279 return x / pow10(-e);
166   166  
HITCBC 167   983672 return x * pow10(e); 167   983672 return x * pow10(e);
168   } 168   }
169   169  
170   inline 170   inline
171   bool 171   bool
172   is_control(char c) noexcept 172   is_control(char c) noexcept
173   { 173   {
174   return static_cast<unsigned char>(c) < 32; 174   return static_cast<unsigned char>(c) < 32;
175   } 175   }
176   176  
177   inline 177   inline
178   int 178   int
HITCBC 179   66931 hex_digit(unsigned char c) noexcept 179   66931 hex_digit(unsigned char c) noexcept
180   { 180   {
181   // by Peter Dimov 181   // by Peter Dimov
HITCBC 182   66931 if( c >= '0' && c <= '9' ) 182   66931 if( c >= '0' && c <= '9' )
HITCBC 183   35759 return c - '0'; 183   35759 return c - '0';
HITCBC 184   31172 c &= ~0x20; 184   31172 c &= ~0x20;
HITCBC 185   31172 if( c >= 'A' && c <= 'F' ) 185   31172 if( c >= 'A' && c <= 'F' )
HITCBC 186   30562 return 10 + c - 'A'; 186   30562 return 10 + c - 'A';
HITCBC 187   610 return -1; 187   610 return -1;
188   } 188   }
189   189  
190   } // detail 190   } // detail
191   191  
192   //---------------------------------------------------------- 192   //----------------------------------------------------------
193   193  
194   template< class Handler > 194   template< class Handler >
195   template< bool StackEmpty_, char First_ > 195   template< bool StackEmpty_, char First_ >
196   struct basic_parser<Handler>:: 196   struct basic_parser<Handler>::
197   parse_number_helper 197   parse_number_helper
198   { 198   {
199   basic_parser* parser; 199   basic_parser* parser;
200   char const* p; 200   char const* p;
201   201  
202   template< std::size_t N > 202   template< std::size_t N >
203   char const* 203   char const*
HITCBC 204   2126888 operator()( mp11::mp_size_t<N> ) const 204   2110611 operator()( mp11::mp_size_t<N> ) const
205   { 205   {
HITCBC 206   4248335 return parser->parse_number( 206   4215781 return parser->parse_number(
HITCBC 207   2126888 p, 207   2110611 p,
208   std::integral_constant<bool, StackEmpty_>(), 208   std::integral_constant<bool, StackEmpty_>(),
209   std::integral_constant<char, First_>(), 209   std::integral_constant<char, First_>(),
210   std::integral_constant< 210   std::integral_constant<
HITCBC 211   2121448 number_precision, static_cast<number_precision>(N)>() ); 211   2105171 number_precision, static_cast<number_precision>(N)>() );
212   } 212   }
  213 +
  214 + char const*
HITGNC   215 + 16277 operator()(
  216 + mp11::mp_size_t<static_cast<std::size_t>(number_precision::none)> )
  217 + const
  218 + {
HITGNC   219 + 32554 return parser->skip_number(
HITGNC   220 + 16277 p,
  221 + std::integral_constant<bool, StackEmpty_>(),
HITGNC   222 + 16277 std::integral_constant<char, First_>() );
  223 + }
213   }; 224   };
214   225  
215   //---------------------------------------------------------- 226   //----------------------------------------------------------
216   227  
217   template<class Handler> 228   template<class Handler>
218   void 229   void
HITCBC 219   210572 basic_parser<Handler>:: 230   210572 basic_parser<Handler>::
220   reserve() 231   reserve()
221   { 232   {
HITCBC 222   210572 if(BOOST_JSON_LIKELY( 233   210572 if(BOOST_JSON_LIKELY(
223   ! st_.empty())) 234   ! st_.empty()))
HITCBC 224   37469 return; 235   37469 return;
225   // Reserve the largest stack we need, 236   // Reserve the largest stack we need,
226   // to avoid reallocation during suspend. 237   // to avoid reallocation during suspend.
HITCBC 227   346206 st_.reserve( 238   346206 st_.reserve(
228   sizeof(state) + // document parsing state 239   sizeof(state) + // document parsing state
229   (sizeof(state) + 240   (sizeof(state) +
HITCBC 230   173103 sizeof(std::size_t)) * depth() + // array and object state + size 241   173103 sizeof(std::size_t)) * depth() + // array and object state + size
231   sizeof(state) + // value parsing state 242   sizeof(state) + // value parsing state
232   sizeof(std::size_t) + // string size 243   sizeof(std::size_t) + // string size
233   sizeof(state)); // comment state 244   sizeof(state)); // comment state
234   } 245   }
235   246  
236   //---------------------------------------------------------- 247   //----------------------------------------------------------
237   // 248   //
238   // The sentinel value is returned by parse functions 249   // The sentinel value is returned by parse functions
239   // to indicate that the parser failed, or suspended. 250   // to indicate that the parser failed, or suspended.
240   // this is used as it is distinct from all valid values 251   // this is used as it is distinct from all valid values
241   // for data in write 252   // for data in write
242   253  
243   template<class Handler> 254   template<class Handler>
244   const char* 255   const char*
HITCBC 245   5341073 basic_parser<Handler>:: 256   5341073 basic_parser<Handler>::
246   sentinel() 257   sentinel()
247   { 258   {
248   // the "+1" ensures that the returned pointer is unique even if 259   // the "+1" ensures that the returned pointer is unique even if
249   // the given input buffer borders on this object 260   // the given input buffer borders on this object
250   return reinterpret_cast< 261   return reinterpret_cast<
HITCBC 251   5341073 const char*>(this) + 1; 262   5341073 const char*>(this) + 1;
252   } 263   }
253   264  
254   template<class Handler> 265   template<class Handler>
255   bool 266   bool
HITCBC 256   2459881 basic_parser<Handler>:: 267   2459881 basic_parser<Handler>::
257   incomplete( 268   incomplete(
258   const detail::const_stream_wrapper& cs) 269   const detail::const_stream_wrapper& cs)
259   { 270   {
HITCBC 260   2459881 return cs.begin() == sentinel(); 271   2459881 return cs.begin() == sentinel();
261   } 272   }
262   273  
263   //---------------------------------------------------------- 274   //----------------------------------------------------------
264   // 275   //
265   // These functions are declared with the BOOST_NOINLINE 276   // These functions are declared with the BOOST_NOINLINE
266   // attribute to avoid polluting the parsers hot-path. 277   // attribute to avoid polluting the parsers hot-path.
267   // They return the canary value to indicate suspension 278   // They return the canary value to indicate suspension
268   // or failure. 279   // or failure.
269   280  
270   template<class Handler> 281   template<class Handler>
271   const char* 282   const char*
272   basic_parser<Handler>:: 283   basic_parser<Handler>::
273   suspend_or_fail(state st) 284   suspend_or_fail(state st)
274   { 285   {
275   if(BOOST_JSON_LIKELY( 286   if(BOOST_JSON_LIKELY(
276   ! ec_ && more_)) 287   ! ec_ && more_))
277   { 288   {
278   // suspend 289   // suspend
279   reserve(); 290   reserve();
280   st_.push_unchecked(st); 291   st_.push_unchecked(st);
281   } 292   }
282   return sentinel(); 293   return sentinel();
283   } 294   }
284   295  
285   template<class Handler> 296   template<class Handler>
286   const char* 297   const char*
HITCBC 287   56176 basic_parser<Handler>:: 298   56176 basic_parser<Handler>::
288   suspend_or_fail( 299   suspend_or_fail(
289   state st, 300   state st,
290   std::size_t n) 301   std::size_t n)
291   { 302   {
HITCBC 292   56176 if(BOOST_JSON_LIKELY( 303   56176 if(BOOST_JSON_LIKELY(
293   ! ec_ && more_)) 304   ! ec_ && more_))
294   { 305   {
295   // suspend 306   // suspend
HITCBC 296   35861 reserve(); 307   35861 reserve();
HITCBC 297   35861 st_.push_unchecked(n); 308   35861 st_.push_unchecked(n);
HITCBC 298   35861 st_.push_unchecked(st); 309   35861 st_.push_unchecked(st);
299   } 310   }
HITCBC 300   56176 return sentinel(); 311   56176 return sentinel();
301   } 312   }
302   313  
303   314  
304   template<class Handler> 315   template<class Handler>
305   const char* 316   const char*
HITCBC 306   19005 basic_parser<Handler>:: 317   19005 basic_parser<Handler>::
307   fail(const char* p) noexcept 318   fail(const char* p) noexcept
308   { 319   {
HITCBC 309   19005 BOOST_ASSERT( p != sentinel() ); 320   19005 BOOST_ASSERT( p != sentinel() );
HITCBC 310   19005 end_ = p; 321   19005 end_ = p;
HITCBC 311   19005 return sentinel(); 322   19005 return sentinel();
312   } 323   }
313   324  
314   template<class Handler> 325   template<class Handler>
315   const char* 326   const char*
HITCBC 316   7774 basic_parser<Handler>:: 327   7774 basic_parser<Handler>::
317   fail( 328   fail(
318   const char* p, 329   const char* p,
319   error ev, 330   error ev,
320   source_location const* loc) noexcept 331   source_location const* loc) noexcept
321   { 332   {
HITCBC 322   7774 BOOST_ASSERT( p != sentinel() ); 333   7774 BOOST_ASSERT( p != sentinel() );
HITCBC 323   7774 end_ = p; 334   7774 end_ = p;
HITCBC 324   7774 ec_.assign(ev, loc); 335   7774 ec_.assign(ev, loc);
HITCBC 325   7774 return sentinel(); 336   7774 return sentinel();
326   } 337   }
327   338  
328   template<class Handler> 339   template<class Handler>
329   const char* 340   const char*
HITCBC 330   11289 basic_parser<Handler>:: 341   11289 basic_parser<Handler>::
331   maybe_suspend( 342   maybe_suspend(
332   const char* p, 343   const char* p,
333   state st) 344   state st)
334   { 345   {
HITCBC 335   11289 if( p != sentinel() ) 346   11289 if( p != sentinel() )
HITCBC 336   9424 end_ = p; 347   9424 end_ = p;
HITCBC 337   11289 if(BOOST_JSON_LIKELY(more_)) 348   11289 if(BOOST_JSON_LIKELY(more_))
338   { 349   {
339   // suspend 350   // suspend
HITCBC 340   11027 reserve(); 351   11027 reserve();
HITCBC 341   11027 st_.push_unchecked(st); 352   11027 st_.push_unchecked(st);
342   } 353   }
HITCBC 343   11289 return sentinel(); 354   11289 return sentinel();
344   } 355   }
345   356  
346   template<class Handler> 357   template<class Handler>
347   const char* 358   const char*
HITCBC 348   38234 basic_parser<Handler>:: 359   38234 basic_parser<Handler>::
349   maybe_suspend( 360   maybe_suspend(
350   const char* p, 361   const char* p,
351   state st, 362   state st,
352   std::size_t n) 363   std::size_t n)
353   { 364   {
HITCBC 354   38234 BOOST_ASSERT( p != sentinel() ); 365   38234 BOOST_ASSERT( p != sentinel() );
HITCBC 355   38234 end_ = p; 366   38234 end_ = p;
HITCBC 356   38234 if(BOOST_JSON_LIKELY(more_)) 367   38234 if(BOOST_JSON_LIKELY(more_))
357   { 368   {
358   // suspend 369   // suspend
HITCBC 359   37833 reserve(); 370   37833 reserve();
HITCBC 360   37833 st_.push_unchecked(n); 371   37833 st_.push_unchecked(n);
HITCBC 361   37833 st_.push_unchecked(st); 372   37833 st_.push_unchecked(st);
362   } 373   }
HITCBC 363   38234 return sentinel(); 374   38234 return sentinel();
364   } 375   }
365   376  
366   template<class Handler> 377   template<class Handler>
367   const char* 378   const char*
HITCBC 368   1123 basic_parser<Handler>:: 379   1123 basic_parser<Handler>::
369   maybe_suspend( 380   maybe_suspend(
370   const char* p, 381   const char* p,
371   state st, 382   state st,
372   const number& num) 383   const number& num)
373   { 384   {
HITCBC 374   1123 BOOST_ASSERT( p != sentinel() ); 385   1123 BOOST_ASSERT( p != sentinel() );
HITCBC 375   1123 end_ = p; 386   1123 end_ = p;
HITCBC 376   1123 if(BOOST_JSON_LIKELY(more_)) 387   1123 if(BOOST_JSON_LIKELY(more_))
377   { 388   {
378   // suspend 389   // suspend
HITCBC 379   1123 num_ = num; 390   1123 num_ = num;
HITCBC 380   1123 reserve(); 391   1123 reserve();
HITCBC 381   1123 st_.push_unchecked(st);; 392   1123 st_.push_unchecked(st);;
382   } 393   }
HITCBC 383   1123 return sentinel(); 394   1123 return sentinel();
384   } 395   }
385   396  
386   template<class Handler> 397   template<class Handler>
387   const char* 398   const char*
HITCBC 388   88657 basic_parser<Handler>:: 399   88657 basic_parser<Handler>::
389   suspend( 400   suspend(
390   const char* p, 401   const char* p,
391   state st) 402   state st)
392   { 403   {
HITCBC 393   88657 BOOST_ASSERT( p != sentinel() ); 404   88657 BOOST_ASSERT( p != sentinel() );
HITCBC 394   88657 end_ = p; 405   88657 end_ = p;
395   // suspend 406   // suspend
HITCBC 396   88657 reserve(); 407   88657 reserve();
HITCBC 397   88657 st_.push_unchecked(st); 408   88657 st_.push_unchecked(st);
HITCBC 398   88657 return sentinel(); 409   88657 return sentinel();
399   } 410   }
400   411  
401   template<class Handler> 412   template<class Handler>
402   const char* 413   const char*
HITCBC 403   36071 basic_parser<Handler>:: 414   36071 basic_parser<Handler>::
404   suspend( 415   suspend(
405   const char* p, 416   const char* p,
406   state st, 417   state st,
407   const number& num) 418   const number& num)
408   { 419   {
HITCBC 409   36071 BOOST_ASSERT( p != sentinel() ); 420   36071 BOOST_ASSERT( p != sentinel() );
HITCBC 410   36071 end_ = p; 421   36071 end_ = p;
411   // suspend 422   // suspend
HITCBC 412   36071 num_ = num; 423   36071 num_ = num;
HITCBC 413   36071 reserve(); 424   36071 reserve();
HITCBC 414   36071 st_.push_unchecked(st); 425   36071 st_.push_unchecked(st);
HITCBC 415   36071 return sentinel(); 426   36071 return sentinel();
416   } 427   }
417   428  
418   template<class Handler> 429   template<class Handler>
419   template< 430   template<
420   bool StackEmpty_/*, 431   bool StackEmpty_/*,
421   bool Terminal_*/> 432   bool Terminal_*/>
422   const char* 433   const char*
HITCBC 423   21737 basic_parser<Handler>:: 434   21737 basic_parser<Handler>::
424   parse_comment(const char* p, 435   parse_comment(const char* p,
425   std::integral_constant<bool, StackEmpty_> stack_empty, 436   std::integral_constant<bool, StackEmpty_> stack_empty,
426   /*std::integral_constant<bool, Terminal_>*/ bool terminal) 437   /*std::integral_constant<bool, Terminal_>*/ bool terminal)
427   { 438   {
HITCBC 428   21737 detail::const_stream_wrapper cs(p, end_); 439   21737 detail::const_stream_wrapper cs(p, end_);
HITCBC 429   21737 const char* start = cs.begin(); 440   21737 const char* start = cs.begin();
430   std::size_t remain; 441   std::size_t remain;
HITCBC 431   21737 if(! stack_empty && ! st_.empty()) 442   21737 if(! stack_empty && ! st_.empty())
432   { 443   {
433   state st; 444   state st;
HITCBC 434   3507 st_.pop(st); 445   3507 st_.pop(st);
HITCBC 435   3507 switch(st) 446   3507 switch(st)
436   { 447   {
MISUBC 437   ✗ default: BOOST_JSON_UNREACHABLE(); 448   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 438   534 case state::com1: goto do_com1; 449   534 case state::com1: goto do_com1;
HITCBC 439   2319 case state::com2: goto do_com2; 450   2319 case state::com2: goto do_com2;
HITCBC 440   438 case state::com3: goto do_com3; 451   438 case state::com3: goto do_com3;
HITCBC 441   216 case state::com4: goto do_com4; 452   216 case state::com4: goto do_com4;
442   } 453   }
443   } 454   }
HITCBC 444   18230 BOOST_ASSERT(*cs == '/'); 455   18230 BOOST_ASSERT(*cs == '/');
HITCBC 445   18230 ++cs; 456   18230 ++cs;
HITCBC 446   18764 do_com1: 457   18764 do_com1:
HITCBC 447   18764 if(BOOST_JSON_UNLIKELY(! cs)) 458   18764 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 448   551 return maybe_suspend(cs.begin(), state::com1); 459   551 return maybe_suspend(cs.begin(), state::com1);
HITCBC 449   18213 switch(*cs) 460   18213 switch(*cs)
450   { 461   {
HITCBC 451   5 default: 462   5 default:
452   { 463   {
453   BOOST_STATIC_CONSTEXPR source_location loc 464   BOOST_STATIC_CONSTEXPR source_location loc
454   = BOOST_CURRENT_LOCATION; 465   = BOOST_CURRENT_LOCATION;
HITCBC 455   5 return fail(cs.begin(), error::syntax, &loc); 466   5 return fail(cs.begin(), error::syntax, &loc);
456   } 467   }
HITCBC 457   10524 case '/': 468   10524 case '/':
HITCBC 458   10524 ++cs; 469   10524 ++cs;
HITCBC 459   12843 do_com2: 470   12843 do_com2:
460   // KRYSTIAN TODO: this is a mess, we have to fix this 471   // KRYSTIAN TODO: this is a mess, we have to fix this
HITCBC 461   12843 remain = cs.remain(); 472   12843 remain = cs.remain();
HITCBC 462   25686 cs = remain ? static_cast<const char*>( 473   25686 cs = remain ? static_cast<const char*>(
HITCBC 463   12843 std::memchr(cs.begin(), '\n', remain)) : sentinel(); 474   12843 std::memchr(cs.begin(), '\n', remain)) : sentinel();
HITCBC 464   12843 if(! cs.begin()) 475   12843 if(! cs.begin())
HITCBC 465   2143 cs = sentinel(); 476   2143 cs = sentinel();
HITCBC 466   12843 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 477   12843 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
467   { 478   {
468   // if the doc does not terminate 479   // if the doc does not terminate
469   // with a newline, treat it as the 480   // with a newline, treat it as the
470   // end of the comment 481   // end of the comment
HITCBC 471   2568 if(terminal && ! more_) 482   2568 if(terminal && ! more_)
472   { 483   {
HITCBC 473   39 if(BOOST_JSON_UNLIKELY(! h_.on_comment( 484   39 if(BOOST_JSON_UNLIKELY(! h_.on_comment(
474   {start, cs.remain(start)}, ec_))) 485   {start, cs.remain(start)}, ec_)))
HITCBC 475   2 return fail(cs.end()); 486   2 return fail(cs.end());
HITCBC 476   35 return cs.end(); 487   35 return cs.end();
477   } 488   }
HITCBC 478   2529 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part( 489   2529 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part(
479   {start, cs.remain(start)}, ec_))) 490   {start, cs.remain(start)}, ec_)))
HITCBC 480   95 return fail(cs.end()); 491   95 return fail(cs.end());
HITCBC 481   2339 if(terminal) 492   2339 if(terminal)
HITCBC 482   106 return suspend(cs.end(), state::com2); 493   106 return suspend(cs.end(), state::com2);
HITCBC 483   2233 return maybe_suspend(cs.end(), state::com2); 494   2233 return maybe_suspend(cs.end(), state::com2);
484   } 495   }
HITCBC 485   10275 break; 496   10275 break;
HITCBC 486   1684 case '*': 497   1684 case '*':
487   do 498   do
488   { 499   {
HITCBC 489   9368 ++cs; 500   9368 ++cs;
HITCBC 490   9806 do_com3: 501   9806 do_com3:
491   // KRYSTIAN TODO: this is a mess, we have to fix this 502   // KRYSTIAN TODO: this is a mess, we have to fix this
HITCBC 492   9806 remain = cs.remain(); 503   9806 remain = cs.remain();
HITCBC 493   19612 cs = remain ? static_cast<const char*>( 504   19612 cs = remain ? static_cast<const char*>(
HITCBC 494   9806 std::memchr(cs.begin(), '*', remain)) : sentinel(); 505   9806 std::memchr(cs.begin(), '*', remain)) : sentinel();
HITCBC 495   9806 if(! cs.begin()) 506   9806 if(! cs.begin())
HITCBC 496   242 cs = sentinel(); 507   242 cs = sentinel();
497   // stopped inside a c comment 508   // stopped inside a c comment
HITCBC 498   9806 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 509   9806 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
499   { 510   {
HITCBC 500   503 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part( 511   503 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part(
501   {start, cs.remain(start)}, ec_))) 512   {start, cs.remain(start)}, ec_)))
HITCBC 502   30 return fail(cs.end()); 513   30 return fail(cs.end());
HITCBC 503   443 return maybe_suspend(cs.end(), state::com3); 514   443 return maybe_suspend(cs.end(), state::com3);
504   } 515   }
505   // found a asterisk, check if the next char is a slash 516   // found a asterisk, check if the next char is a slash
HITCBC 506   9303 ++cs; 517   9303 ++cs;
HITCBC 507   9519 do_com4: 518   9519 do_com4:
HITCBC 508   9519 if(BOOST_JSON_UNLIKELY(! cs)) 519   9519 if(BOOST_JSON_UNLIKELY(! cs))
509   { 520   {
HITCBC 510   259 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part( 521   259 if(BOOST_JSON_UNLIKELY(! h_.on_comment_part(
511   {start, cs.used(start)}, ec_))) 522   {start, cs.used(start)}, ec_)))
HITCBC 512   18 return fail(cs.begin()); 523   18 return fail(cs.begin());
HITCBC 513   223 return maybe_suspend(cs.begin(), state::com4); 524   223 return maybe_suspend(cs.begin(), state::com4);
514   } 525   }
515   } 526   }
HITCBC 516   9260 while(*cs != '/'); 527   9260 while(*cs != '/');
517   } 528   }
HITCBC 518   17851 ++cs; 529   17851 ++cs;
HITCBC 519   17851 if(BOOST_JSON_UNLIKELY(! h_.on_comment( 530   17851 if(BOOST_JSON_UNLIKELY(! h_.on_comment(
520   {start, cs.used(start)}, ec_))) 531   {start, cs.used(start)}, ec_)))
HITCBC 521   964 return fail(cs.begin()); 532   964 return fail(cs.begin());
HITCBC 522   15923 return cs.begin(); 533   15923 return cs.begin();
523   } 534   }
524   535  
525   template<class Handler> 536   template<class Handler>
526   template<bool StackEmpty_> 537   template<bool StackEmpty_>
527   const char* 538   const char*
HITCBC 528   2318439 basic_parser<Handler>:: 539   2318439 basic_parser<Handler>::
529   parse_document(const char* p, 540   parse_document(const char* p,
530   std::integral_constant<bool, StackEmpty_> stack_empty) 541   std::integral_constant<bool, StackEmpty_> stack_empty)
531   { 542   {
HITCBC 532   2318439 detail::const_stream_wrapper cs(p, end_); 543   2318439 detail::const_stream_wrapper cs(p, end_);
HITCBC 533   2318439 if(! stack_empty && ! st_.empty()) 544   2318439 if(! stack_empty && ! st_.empty())
534   { 545   {
535   state st; 546   state st;
HITCBC 536   169624 st_.peek(st); 547   169624 st_.peek(st);
HITCBC 537   169624 switch(st) 548   169624 switch(st)
538   { 549   {
HITCBC 539   83559 default: goto do_doc2; 550   83559 default: goto do_doc2;
HITCBC 540   601 case state::doc1: 551   601 case state::doc1:
HITCBC 541   601 st_.pop(st); 552   601 st_.pop(st);
HITCBC 542   601 goto do_doc1; 553   601 goto do_doc1;
HITCBC 543   85244 case state::doc3: 554   85244 case state::doc3:
HITCBC 544   85244 st_.pop(st); 555   85244 st_.pop(st);
HITCBC 545   85244 goto do_doc3; 556   85244 goto do_doc3;
HITCBC 546   220 case state::com1: case state::com2: 557   220 case state::com1: case state::com2:
547   case state::com3: case state::com4: 558   case state::com3: case state::com4:
HITCBC 548   220 goto do_doc4; 559   220 goto do_doc4;
549   } 560   }
550   } 561   }
HITCBC 551   2148815 do_doc1: 562   2148815 do_doc1:
HITCBC 552   2149416 cs = detail::count_whitespace(cs.begin(), cs.end()); 563   2149416 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 553   2149416 if(BOOST_JSON_UNLIKELY(! cs)) 564   2149416 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 554   633 return maybe_suspend(cs.begin(), state::doc1); 565   633 return maybe_suspend(cs.begin(), state::doc1);
HITCBC 555   2148783 do_doc2: 566   2148783 do_doc2:
HITCBC 556   2232342 switch(+opt_.allow_comments | 567   2232342 switch(+opt_.allow_comments |
HITCBC 557   2232342 (opt_.allow_trailing_commas << 1) | 568   2232342 (opt_.allow_trailing_commas << 1) |
HITCBC 558   2232342 (opt_.allow_invalid_utf8 << 2)) 569   2232342 (opt_.allow_invalid_utf8 << 2))
559   { 570   {
560   // no extensions 571   // no extensions
HITCBC 561   2208660 default: 572   2208660 default:
HITCBC 562   2208660 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::false_type(), std::false_type(), opt_.allow_invalid_utf16); 573   2208660 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::false_type(), std::false_type(), opt_.allow_invalid_utf16);
HITCBC 563   2193502 break; 574   2193502 break;
564   // comments 575   // comments
HITCBC 565   13551 case 1: 576   13551 case 1:
HITCBC 566   13551 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::false_type(), std::false_type(), opt_.allow_invalid_utf16); 577   13551 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::false_type(), std::false_type(), opt_.allow_invalid_utf16);
HITCBC 567   11288 break; 578   11288 break;
568   // trailing 579   // trailing
HITCBC 569   6710 case 2: 580   6710 case 2:
HITCBC 570   6710 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::true_type(), std::false_type(), opt_.allow_invalid_utf16); 581   6710 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::true_type(), std::false_type(), opt_.allow_invalid_utf16);
HITCBC 571   5117 break; 582   5117 break;
572   // comments & trailing 583   // comments & trailing
HITCBC 573   761 case 3: 584   761 case 3:
HITCBC 574   761 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::true_type(), std::false_type(), opt_.allow_invalid_utf16); 585   761 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::true_type(), std::false_type(), opt_.allow_invalid_utf16);
HITCBC 575   761 break; 586   761 break;
576   // skip validation 587   // skip validation
HITCBC 577   760 case 4: 588   760 case 4:
HITCBC 578   760 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::false_type(), std::true_type(), opt_.allow_invalid_utf16); 589   760 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::false_type(), std::true_type(), opt_.allow_invalid_utf16);
HITCBC 579   760 break; 590   760 break;
580   // comments & skip validation 591   // comments & skip validation
HITCBC 581   760 case 5: 592   760 case 5:
HITCBC 582   760 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::false_type(), std::true_type(), opt_.allow_invalid_utf16); 593   760 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::false_type(), std::true_type(), opt_.allow_invalid_utf16);
HITCBC 583   760 break; 594   760 break;
584   // trailing & skip validation 595   // trailing & skip validation
HITCBC 585   760 case 6: 596   760 case 6:
HITCBC 586   760 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::true_type(), std::true_type(), opt_.allow_invalid_utf16); 597   760 cs = parse_value(cs.begin(), stack_empty, std::false_type(), std::true_type(), std::true_type(), opt_.allow_invalid_utf16);
HITCBC 587   760 break; 598   760 break;
588   // comments & trailing & skip validation 599   // comments & trailing & skip validation
HITCBC 589   380 case 7: 600   380 case 7:
HITCBC 590   380 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::true_type(), std::true_type(), opt_.allow_invalid_utf16); 601   380 cs = parse_value(cs.begin(), stack_empty, std::true_type(), std::true_type(), std::true_type(), opt_.allow_invalid_utf16);
HITCBC 591   380 break; 602   380 break;
592   } 603   }
HITCBC 593   2213328 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 604   2213328 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
594   // the appropriate state has already been pushed into stack 605   // the appropriate state has already been pushed into stack
HITCBC 595   110765 return sentinel(); 606   110765 return sentinel();
HITCBC 596   2102563 do_doc3: 607   2102563 do_doc3:
HITCBC 597   2188139 cs = detail::count_whitespace(cs.begin(), cs.end()); 608   2188139 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 598   2188139 if(BOOST_JSON_UNLIKELY(! cs)) 609   2188139 if(BOOST_JSON_UNLIKELY(! cs))
599   { 610   {
HITCBC 600   2185541 if(more_) 611   2185541 if(more_)
HITCBC 601   88551 return suspend(cs.begin(), state::doc3); 612   88551 return suspend(cs.begin(), state::doc3);
602   } 613   }
HITCBC 603   2598 else if(opt_.allow_comments && *cs == '/') 614   2598 else if(opt_.allow_comments && *cs == '/')
604   { 615   {
HITCBC 605   536 do_doc4: 616   536 do_doc4:
HITCBC 606   756 cs = parse_comment(cs.begin(), stack_empty, std::true_type()); 617   756 cs = parse_comment(cs.begin(), stack_empty, std::true_type());
HITCBC 607   671 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 618   671 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 608   339 return sentinel(); 619   339 return sentinel();
HITCBC 609   332 goto do_doc3; 620   332 goto do_doc3;
610   } 621   }
HITCBC 611   2099052 return cs.begin(); 622   2099052 return cs.begin();
612   } 623   }
613   624  
614   template<class Handler> 625   template<class Handler>
615   template< 626   template<
616   bool StackEmpty_, 627   bool StackEmpty_,
617   bool AllowComments_/*, 628   bool AllowComments_/*,
618   bool AllowTrailing_, 629   bool AllowTrailing_,
619   bool AllowBadUTF8_*/> 630   bool AllowBadUTF8_*/>
620   const char* 631   const char*
HITCBC 621   2349972 basic_parser<Handler>:: 632   2349972 basic_parser<Handler>::
622   parse_value(const char* p, 633   parse_value(const char* p,
623   std::integral_constant<bool, StackEmpty_> stack_empty, 634   std::integral_constant<bool, StackEmpty_> stack_empty,
624   std::integral_constant<bool, AllowComments_> allow_comments, 635   std::integral_constant<bool, AllowComments_> allow_comments,
625   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing, 636   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing,
626   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8, 637   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8,
627   bool allow_bad_utf16) 638   bool allow_bad_utf16)
628   { 639   {
HITCBC 629   2349972 if(stack_empty || st_.empty()) 640   2349972 if(stack_empty || st_.empty())
630   { 641   {
HITCBC 631   2248027 loop: 642   2248027 loop:
HITCBC 632   2252943 switch(*p) 643   2252943 switch(*p)
633   { 644   {
HITCBC 634   22753 case '0': 645   22753 case '0':
HITCBC 635   22753 return mp11::mp_with_index<3>( 646   22753 return mp11::mp_with_index<3>(
HITCBC 636   22753 static_cast<unsigned char>(opt_.numbers), 647   22753 static_cast<unsigned char>(opt_.numbers),
HITCBC 637   22092 parse_number_helper<true, '0'>{ this, p }); 648   22092 parse_number_helper<true, '0'>{ this, p });
HITCBC 638   25178 case '-': 649   25178 case '-':
HITCBC 639   25178 return mp11::mp_with_index<3>( 650   25178 return mp11::mp_with_index<3>(
HITCBC 640   25178 static_cast<unsigned char>(opt_.numbers), 651   25178 static_cast<unsigned char>(opt_.numbers),
HITCBC 641   24066 parse_number_helper<true, '-'>{ this, p }); 652   24066 parse_number_helper<true, '-'>{ this, p });
HITCBC 642   2041766 case '1': case '2': case '3': 653   2041766 case '1': case '2': case '3':
643   case '4': case '5': case '6': 654   case '4': case '5': case '6':
644   case '7': case '8': case '9': 655   case '7': case '8': case '9':
HITCBC 645   2041766 return mp11::mp_with_index<3>( 656   2041766 return mp11::mp_with_index<3>(
HITCBC 646   2041766 static_cast<unsigned char>(opt_.numbers), 657   2041766 static_cast<unsigned char>(opt_.numbers),
HITCBC 647   2038922 parse_number_helper<true, '+'>{ this, p }); 658   2038922 parse_number_helper<true, '+'>{ this, p });
HITCBC 648   11380 case 'n': 659   11380 case 'n':
HITCBC 649   11380 return parse_literal( p, detail::literals_c<detail::literals::null>() ); 660   11380 return parse_literal( p, detail::literals_c<detail::literals::null>() );
HITCBC 650   664 case 't': 661   664 case 't':
HITCBC 651   664 return parse_literal( p, detail::literals_c<detail::literals::true_>() ); 662   664 return parse_literal( p, detail::literals_c<detail::literals::true_>() );
HITCBC 652   722 case 'f': 663   722 case 'f':
HITCBC 653   722 return parse_literal( p, detail::literals_c<detail::literals::false_>() ); 664   722 return parse_literal( p, detail::literals_c<detail::literals::false_>() );
HITCBC 654   681 case 'I': 665   681 case 'I':
HITCBC 655   681 if( !opt_.allow_infinity_and_nan ) 666   681 if( !opt_.allow_infinity_and_nan )
656   { 667   {
657   BOOST_STATIC_CONSTEXPR source_location loc 668   BOOST_STATIC_CONSTEXPR source_location loc
658   = BOOST_CURRENT_LOCATION; 669   = BOOST_CURRENT_LOCATION;
HITCBC 659   24 return fail(p, error::syntax, &loc); 670   24 return fail(p, error::syntax, &loc);
660   } 671   }
HITCBC 661   657 return parse_literal( p, detail::literals_c<detail::literals::infinity>() ); 672   657 return parse_literal( p, detail::literals_c<detail::literals::infinity>() );
HITCBC 662   231 case 'N': 673   231 case 'N':
HITCBC 663   231 if( !opt_.allow_infinity_and_nan ) 674   231 if( !opt_.allow_infinity_and_nan )
664   { 675   {
665   BOOST_STATIC_CONSTEXPR source_location loc 676   BOOST_STATIC_CONSTEXPR source_location loc
666   = BOOST_CURRENT_LOCATION; 677   = BOOST_CURRENT_LOCATION;
HITCBC 667   30 return fail(p, error::syntax, &loc); 678   30 return fail(p, error::syntax, &loc);
668   } 679   }
HITCBC 669   201 return parse_literal(p, detail::literals_c<detail::literals::nan>() ); 680   201 return parse_literal(p, detail::literals_c<detail::literals::nan>() );
HITCBC 670   47577 case '"': 681   47577 case '"':
HITCBC 671   47577 return parse_string(p, std::true_type(), std::false_type(), allow_bad_utf8, allow_bad_utf16); 682   47577 return parse_string(p, std::true_type(), std::false_type(), allow_bad_utf8, allow_bad_utf16);
HITCBC 672   20618 case '[': 683   20618 case '[':
HITCBC 673   20618 return parse_array(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 684   20618 return parse_array(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
HITCBC 674   74131 case '{': 685   74131 case '{':
HITCBC 675   74131 return parse_object(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 686   74131 return parse_object(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
HITCBC 676   6125 case '/': 687   6125 case '/':
HITCBC 677   6125 if(! allow_comments) 688   6125 if(! allow_comments)
678   { 689   {
679   BOOST_STATIC_CONSTEXPR source_location loc 690   BOOST_STATIC_CONSTEXPR source_location loc
680   = BOOST_CURRENT_LOCATION; 691   = BOOST_CURRENT_LOCATION;
HITCBC 681   284 return fail(p, error::syntax, &loc); 692   284 return fail(p, error::syntax, &loc);
682   } 693   }
HITCBC 683   5841 p = parse_comment(p, stack_empty, std::false_type()); 694   5841 p = parse_comment(p, stack_empty, std::false_type());
684   // KRYSTIAN NOTE: incomplete takes const_stream, we either 695   // KRYSTIAN NOTE: incomplete takes const_stream, we either
685   // can add an overload, change the existing one to take a pointer, 696   // can add an overload, change the existing one to take a pointer,
686   // or just leave it as is 697   // or just leave it as is
HITCBC 687   5605 if(BOOST_JSON_UNLIKELY(p == sentinel())) 698   5605 if(BOOST_JSON_UNLIKELY(p == sentinel()))
HITCBC 688   591 return maybe_suspend(p, state::val2); 699   591 return maybe_suspend(p, state::val2);
689   BOOST_FALLTHROUGH; 700   BOOST_FALLTHROUGH;
690   case ' ': 701   case ' ':
691   case '\t': 702   case '\t':
692   case '\n': 703   case '\n':
693   case '\r': 704   case '\r':
HITCBC 694   5026 p = detail::count_whitespace(p, end_); 705   5026 p = detail::count_whitespace(p, end_);
HITCBC 695   5026 if(BOOST_JSON_UNLIKELY(p == end_)) 706   5026 if(BOOST_JSON_UNLIKELY(p == end_))
HITCBC 696   110 return maybe_suspend(p, state::val1); 707   110 return maybe_suspend(p, state::val1);
HITCBC 697   4916 goto loop; 708   4916 goto loop;
HITCBC 698   1105 default: 709   1105 default:
699   { 710   {
700   BOOST_STATIC_CONSTEXPR source_location loc 711   BOOST_STATIC_CONSTEXPR source_location loc
701   = BOOST_CURRENT_LOCATION; 712   = BOOST_CURRENT_LOCATION;
HITCBC 702   1105 return fail(p, error::syntax, &loc); 713   1105 return fail(p, error::syntax, &loc);
703   } 714   }
704   } 715   }
705   } 716   }
HITCBC 706   101945 return resume_value(p, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 717   101945 return resume_value(p, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
707   } 718   }
708   719  
709   template<class Handler> 720   template<class Handler>
710   template< 721   template<
711   bool AllowComments_/*, 722   bool AllowComments_/*,
712   bool AllowTrailing_, 723   bool AllowTrailing_,
713   bool AllowBadUTF8_*/> 724   bool AllowBadUTF8_*/>
714   const char* 725   const char*
HITCBC 715   101945 basic_parser<Handler>:: 726   101945 basic_parser<Handler>::
716   resume_value(const char* p, 727   resume_value(const char* p,
717   std::integral_constant<bool, AllowComments_> allow_comments, 728   std::integral_constant<bool, AllowComments_> allow_comments,
718   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing, 729   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing,
719   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8, 730   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8,
720   bool allow_bad_utf16) 731   bool allow_bad_utf16)
721   { 732   {
722   state st; 733   state st;
HITCBC 723   101945 st_.peek(st); 734   101945 st_.peek(st);
HITCBC 724   101945 switch(st) 735   101945 switch(st)
725   { 736   {
MISUBC 726   ✗ default: BOOST_JSON_UNREACHABLE(); 737   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 727   1924 case state::lit1: 738   1924 case state::lit1:
HITCBC 728   1924 return parse_literal(p, detail::literals_c<detail::literals::resume>() ); 739   1924 return parse_literal(p, detail::literals_c<detail::literals::resume>() );
729   740  
HITCBC 730   20259 case state::str1: case state::str2: 741   20259 case state::str1: case state::str2:
731   case state::str8: 742   case state::str8:
HITCBC 732   20259 return parse_string(p, std::false_type(), std::false_type(), allow_bad_utf8, allow_bad_utf16); 743   20259 return parse_string(p, std::false_type(), std::false_type(), allow_bad_utf8, allow_bad_utf16);
733   744  
HITCBC 734   5730 case state::arr1: case state::arr2: 745   5730 case state::arr1: case state::arr2:
735   case state::arr3: case state::arr4: 746   case state::arr3: case state::arr4:
736   case state::arr5: case state::arr6: 747   case state::arr5: case state::arr6:
HITCBC 737   5730 return parse_array(p, std::false_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 748   5730 return parse_array(p, std::false_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
738   749  
HITCBC 739   35058 case state::obj1: case state::obj2: 750   35058 case state::obj1: case state::obj2:
740   case state::obj3: case state::obj4: 751   case state::obj3: case state::obj4:
741   case state::obj5: case state::obj6: 752   case state::obj5: case state::obj6:
742   case state::obj7: case state::obj8: 753   case state::obj7: case state::obj8:
743   case state::obj9: case state::obj10: 754   case state::obj9: case state::obj10:
744   case state::obj11: 755   case state::obj11:
HITCBC 745   35058 return parse_object(p, std::false_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 756   35058 return parse_object(p, std::false_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
746   757  
HITCBC 747   37191 case state::num1: case state::num2: 758   37191 case state::num1: case state::num2:
748   case state::num3: case state::num4: 759   case state::num3: case state::num4:
749   case state::num5: case state::num6: 760   case state::num5: case state::num6:
750   case state::num7: case state::num8: 761   case state::num7: case state::num8:
751   case state::exp1: case state::exp2: 762   case state::exp1: case state::exp2:
752   case state::exp3: 763   case state::exp3:
HITCBC 753   37191 return mp11::mp_with_index<3>( 764   37191 return mp11::mp_with_index<3>(
HITCBC 754   37191 static_cast<unsigned char>(opt_.numbers), 765   37191 static_cast<unsigned char>(opt_.numbers),
HITCBC 755   36368 parse_number_helper<false, 0>{ this, p }); 766   36368 parse_number_helper<false, 0>{ this, p });
756   767  
757   // KRYSTIAN NOTE: these are special cases 768   // KRYSTIAN NOTE: these are special cases
HITCBC 758   108 case state::val1: 769   108 case state::val1:
759   { 770   {
HITCBC 760   108 st_.pop(st); 771   108 st_.pop(st);
HITCBC 761   108 BOOST_ASSERT(st_.empty()); 772   108 BOOST_ASSERT(st_.empty());
HITCBC 762   108 p = detail::count_whitespace(p, end_); 773   108 p = detail::count_whitespace(p, end_);
HITCBC 763   108 if(BOOST_JSON_UNLIKELY(p == end_)) 774   108 if(BOOST_JSON_UNLIKELY(p == end_))
MISUBC 764   ✗ return maybe_suspend(p, state::val1); 775   ✗ return maybe_suspend(p, state::val1);
HITCBC 765   108 return parse_value(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 776   108 return parse_value(p, std::true_type(), allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
766   } 777   }
767   778  
HITCBC 768   1608 case state::val2: 779   1608 case state::val2:
769   { 780   {
HITCBC 770   1608 st_.pop(st); 781   1608 st_.pop(st);
HITCBC 771   1608 p = parse_comment(p, std::false_type(), std::false_type()); 782   1608 p = parse_comment(p, std::false_type(), std::false_type());
HITCBC 772   1590 if(BOOST_JSON_UNLIKELY(p == sentinel())) 783   1590 if(BOOST_JSON_UNLIKELY(p == sentinel()))
HITCBC 773   1274 return maybe_suspend(p, state::val2); 784   1274 return maybe_suspend(p, state::val2);
HITCBC 774   316 if(BOOST_JSON_UNLIKELY( p == end_ )) 785   316 if(BOOST_JSON_UNLIKELY( p == end_ ))
HITCBC 775   77 return maybe_suspend(p, state::val3); 786   77 return maybe_suspend(p, state::val3);
HITCBC 776   239 BOOST_ASSERT(st_.empty()); 787   239 BOOST_ASSERT(st_.empty());
HITCBC 777   239 return parse_value(p, std::true_type(), std::true_type(), allow_trailing, allow_bad_utf8, allow_bad_utf16); 788   239 return parse_value(p, std::true_type(), std::true_type(), allow_trailing, allow_bad_utf8, allow_bad_utf16);
778   } 789   }
779   790  
HITCBC 780   67 case state::val3: 791   67 case state::val3:
781   { 792   {
HITCBC 782   67 st_.pop(st); 793   67 st_.pop(st);
HITCBC 783   67 return parse_value(p, std::true_type(), std::true_type(), allow_trailing, allow_bad_utf8, allow_bad_utf16); 794   67 return parse_value(p, std::true_type(), std::true_type(), allow_trailing, allow_bad_utf8, allow_bad_utf16);
784   } 795   }
785   } 796   }
786   } 797   }
787   798  
788   template<class Handler> 799   template<class Handler>
789   template<class Literal> 800   template<class Literal>
790   const char* 801   const char*
HITCBC 791   16564 basic_parser<Handler>:: 802   16564 basic_parser<Handler>::
792   parse_literal(const char* p, Literal) 803   parse_literal(const char* p, Literal)
793   { 804   {
794   using L = detail::literals; 805   using L = detail::literals;
795   806  
796   std::size_t cur_lit; 807   std::size_t cur_lit;
797   std::size_t offset; 808   std::size_t offset;
798   809  
HITCBC 799   16564 detail::const_stream_wrapper cs(p, end_); 810   16564 detail::const_stream_wrapper cs(p, end_);
800   BOOST_IF_CONSTEXPR( Literal::value != L::resume ) 811   BOOST_IF_CONSTEXPR( Literal::value != L::resume )
801   { 812   {
HITCBC 802   13633 constexpr std::size_t index = literal_index(Literal::value); 813   13633 constexpr std::size_t index = literal_index(Literal::value);
HITCBC 803   13633 constexpr char const* literal = detail::literal_strings[index]; 814   13633 constexpr char const* literal = detail::literal_strings[index];
HITCBC 804   13633 constexpr std::size_t sz = detail::literal_sizes[index]; 815   13633 constexpr std::size_t sz = detail::literal_sizes[index];
805   816  
HITCBC 806   13633 if(BOOST_JSON_LIKELY( cs.remain() >= sz )) 817   13633 if(BOOST_JSON_LIKELY( cs.remain() >= sz ))
807   { 818   {
HITCBC 808   11983 int const cmp = std::memcmp(cs.begin(), literal, sz); 819   11983 int const cmp = std::memcmp(cs.begin(), literal, sz);
HITCBC 809   11983 if( cmp != 0 ) 820   11983 if( cmp != 0 )
810   { 821   {
811   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 822   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 812   197 return fail(cs.begin(), error::syntax, &loc); 823   197 return fail(cs.begin(), error::syntax, &loc);
813   } 824   }
814   825  
815   BOOST_IF_CONSTEXPR( Literal::value == L::null ) 826   BOOST_IF_CONSTEXPR( Literal::value == L::null )
816   { 827   {
HITCBC 817   10788 if(BOOST_JSON_UNLIKELY( 828   10788 if(BOOST_JSON_UNLIKELY(
818   ! h_.on_null(ec_))) 829   ! h_.on_null(ec_)))
HITCBC 819   161 return fail(cs.begin()); 830   161 return fail(cs.begin());
820   } 831   }
821   else BOOST_IF_CONSTEXPR( Literal::value == L::true_ ) 832   else BOOST_IF_CONSTEXPR( Literal::value == L::true_ )
822   { 833   {
HITCBC 823   384 if(BOOST_JSON_UNLIKELY( 834   384 if(BOOST_JSON_UNLIKELY(
824   ! h_.on_bool(true, ec_))) 835   ! h_.on_bool(true, ec_)))
HITCBC 825   14 return fail(cs.begin()); 836   14 return fail(cs.begin());
826   } 837   }
827   else BOOST_IF_CONSTEXPR( Literal::value == L::false_ ) 838   else BOOST_IF_CONSTEXPR( Literal::value == L::false_ )
828   { 839   {
HITCBC 829   406 if(BOOST_JSON_UNLIKELY( 840   406 if(BOOST_JSON_UNLIKELY(
830   ! h_.on_bool(false, ec_))) 841   ! h_.on_bool(false, ec_)))
HITCBC 831   13 return fail(cs.begin()); 842   13 return fail(cs.begin());
832   } 843   }
833   else BOOST_IF_CONSTEXPR( Literal::value == L::infinity ) 844   else BOOST_IF_CONSTEXPR( Literal::value == L::infinity )
834   { 845   {
HITCBC 835   103 if(BOOST_JSON_UNLIKELY( 846   103 if(BOOST_JSON_UNLIKELY(
836   ! h_.on_double( 847   ! h_.on_double(
837   std::numeric_limits<double>::infinity(), 848   std::numeric_limits<double>::infinity(),
838   string_view(literal, sz), 849   string_view(literal, sz),
839   ec_))) 850   ec_)))
HITCBC 840   13 return fail(cs.begin()); 851   13 return fail(cs.begin());
841   } 852   }
842   else BOOST_IF_CONSTEXPR( Literal::value == L::neg_infinity ) 853   else BOOST_IF_CONSTEXPR( Literal::value == L::neg_infinity )
843   { 854   {
HITCBC 844   9 if(BOOST_JSON_UNLIKELY( 855   9 if(BOOST_JSON_UNLIKELY(
845   ! h_.on_double( 856   ! h_.on_double(
846   -std::numeric_limits<double>::infinity(), 857   -std::numeric_limits<double>::infinity(),
847   string_view(literal, sz), 858   string_view(literal, sz),
848   ec_))) 859   ec_)))
HITCBC 849   1 return fail(cs.begin()); 860   1 return fail(cs.begin());
850   } 861   }
851   else BOOST_IF_CONSTEXPR( Literal::value == L::nan ) 862   else BOOST_IF_CONSTEXPR( Literal::value == L::nan )
852   { 863   {
HITCBC 853   96 if(BOOST_JSON_UNLIKELY( 864   96 if(BOOST_JSON_UNLIKELY(
854   ! h_.on_double( 865   ! h_.on_double(
855   std::numeric_limits<double>::quiet_NaN(), 866   std::numeric_limits<double>::quiet_NaN(),
856   string_view(literal, sz), 867   string_view(literal, sz),
857   ec_))) 868   ec_)))
HITCBC 858   12 return fail(cs.begin()); 869   12 return fail(cs.begin());
859   } 870   }
860   else 871   else
861   { 872   {
862   BOOST_JSON_UNREACHABLE(); 873   BOOST_JSON_UNREACHABLE();
863   } 874   }
864   875  
HITCBC 865   11362 cs += sz; 876   11362 cs += sz;
HITCBC 866   11362 return cs.begin(); 877   11362 return cs.begin();
867   } 878   }
868   879  
HITCBC 869   1650 offset = 0; 880   1650 offset = 0;
HITCBC 870   1650 cur_lit = index; 881   1650 cur_lit = index;
871   } 882   }
872   else 883   else
873   { 884   {
874   state st; 885   state st;
HITCBC 875   2931 st_.pop(st); 886   2931 st_.pop(st);
HITCBC 876   2931 BOOST_ASSERT( st == state::lit1 ); 887   2931 BOOST_ASSERT( st == state::lit1 );
877   888  
HITCBC 878   2931 cur_lit = cur_lit_; 889   2931 cur_lit = cur_lit_;
HITCBC 879   2931 offset = lit_offset_; 890   2931 offset = lit_offset_;
880   } 891   }
881   892  
HITCBC 882   4581 std::size_t const lit_size = detail::literal_sizes[cur_lit]; 893   4581 std::size_t const lit_size = detail::literal_sizes[cur_lit];
HITCBC 883   4581 std::size_t const size = (std::min)( lit_size - offset, cs.remain() ); 894   4581 std::size_t const size = (std::min)( lit_size - offset, cs.remain() );
HITCBC 884   4581 int cmp = 0; 895   4581 int cmp = 0;
HITCBC 885   4581 if(BOOST_JSON_LIKELY( cs.begin() )) 896   4581 if(BOOST_JSON_LIKELY( cs.begin() ))
HITCBC 886   4580 cmp = std::memcmp( 897   4580 cmp = std::memcmp(
HITCBC 887   4580 cs.begin(), detail::literal_strings[cur_lit] + offset, size ); 898   4580 cs.begin(), detail::literal_strings[cur_lit] + offset, size );
HITCBC 888   4581 if( cmp != 0 ) 899   4581 if( cmp != 0 )
889   { 900   {
890   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 901   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 891   699 return fail(cs.begin(), error::syntax, &loc); 902   699 return fail(cs.begin(), error::syntax, &loc);
892   } 903   }
893   904  
HITCBC 894   3882 if(BOOST_JSON_UNLIKELY( offset + size < lit_size )) 905   3882 if(BOOST_JSON_UNLIKELY( offset + size < lit_size ))
895   { 906   {
HITCBC 896   1990 BOOST_ASSERT( cur_lit < 256 ); 907   1990 BOOST_ASSERT( cur_lit < 256 );
HITCBC 897   1990 cur_lit_ = static_cast<unsigned char>( cur_lit ); 908   1990 cur_lit_ = static_cast<unsigned char>( cur_lit );
HITCBC 898   1990 BOOST_ASSERT( offset + size < 256 ); 909   1990 BOOST_ASSERT( offset + size < 256 );
HITCBC 899   1990 lit_offset_ = static_cast<unsigned char>( offset + size ); 910   1990 lit_offset_ = static_cast<unsigned char>( offset + size );
HITCBC 900   1990 return maybe_suspend(cs.begin() + size, state::lit1); 911   1990 return maybe_suspend(cs.begin() + size, state::lit1);
901   } 912   }
902   913  
HITCBC 903   1892 switch( static_cast<L>(cur_lit) ) 914   1892 switch( static_cast<L>(cur_lit) )
904   { 915   {
HITCBC 905   472 case L::null: 916   472 case L::null:
HITCBC 906   472 if(BOOST_JSON_UNLIKELY( 917   472 if(BOOST_JSON_UNLIKELY(
907   ! h_.on_null(ec_))) 918   ! h_.on_null(ec_)))
HITCBC 908   61 return fail(cs.begin()); 919   61 return fail(cs.begin());
HITCBC 909   351 break; 920   351 break;
HITCBC 910   152 case L::true_: 921   152 case L::true_:
HITCBC 911   152 if(BOOST_JSON_UNLIKELY( 922   152 if(BOOST_JSON_UNLIKELY(
912   ! h_.on_bool(true, ec_))) 923   ! h_.on_bool(true, ec_)))
HITCBC 913   22 return fail(cs.begin()); 924   22 return fail(cs.begin());
HITCBC 914   109 break; 925   109 break;
HITCBC 915   198 case L::false_: 926   198 case L::false_:
HITCBC 916   198 if(BOOST_JSON_UNLIKELY( 927   198 if(BOOST_JSON_UNLIKELY(
917   ! h_.on_bool(false, ec_))) 928   ! h_.on_bool(false, ec_)))
HITCBC 918   28 return fail(cs.begin()); 929   28 return fail(cs.begin());
HITCBC 919   142 break; 930   142 break;
HITCBC 920   308 case L::infinity: 931   308 case L::infinity:
HITCBC 921   308 if(BOOST_JSON_UNLIKELY( 932   308 if(BOOST_JSON_UNLIKELY(
922   ! h_.on_double( 933   ! h_.on_double(
923   std::numeric_limits<double>::infinity(), 934   std::numeric_limits<double>::infinity(),
924   string_view( 935   string_view(
925   detail::literal_strings[ literal_index(L::infinity) ], 936   detail::literal_strings[ literal_index(L::infinity) ],
926   detail::literal_sizes[ literal_index(L::infinity) ]), 937   detail::literal_sizes[ literal_index(L::infinity) ]),
927   ec_))) 938   ec_)))
HITCBC 928   49 return fail(cs.begin()); 939   49 return fail(cs.begin());
HITCBC 929   210 break; 940   210 break;
HITCBC 930   686 case L::neg_infinity: 941   686 case L::neg_infinity:
HITCBC 931   686 if(BOOST_JSON_UNLIKELY( 942   686 if(BOOST_JSON_UNLIKELY(
932   ! h_.on_double( 943   ! h_.on_double(
933   -std::numeric_limits<double>::infinity(), 944   -std::numeric_limits<double>::infinity(),
934   string_view( 945   string_view(
935   detail::literal_strings[ literal_index(L::neg_infinity) ], 946   detail::literal_strings[ literal_index(L::neg_infinity) ],
936   detail::literal_sizes[ literal_index(L::neg_infinity) ]), 947   detail::literal_sizes[ literal_index(L::neg_infinity) ]),
937   ec_))) 948   ec_)))
HITCBC 938   102 return fail(cs.begin()); 949   102 return fail(cs.begin());
HITCBC 939   482 break; 950   482 break;
HITCBC 940   76 case L::nan: 951   76 case L::nan:
HITCBC 941   76 if(BOOST_JSON_UNLIKELY( 952   76 if(BOOST_JSON_UNLIKELY(
942   ! h_.on_double( 953   ! h_.on_double(
943   std::numeric_limits<double>::quiet_NaN(), 954   std::numeric_limits<double>::quiet_NaN(),
944   string_view( 955   string_view(
945   detail::literal_strings[ literal_index(L::nan) ], 956   detail::literal_strings[ literal_index(L::nan) ],
946   detail::literal_sizes[ literal_index(L::nan) ]), 957   detail::literal_sizes[ literal_index(L::nan) ]),
947   ec_))) 958   ec_)))
HITCBC 948   12 return fail(cs.begin()); 959   12 return fail(cs.begin());
HITCBC 949   52 break; 960   52 break;
MISUBC 950   ✗ default: BOOST_JSON_UNREACHABLE(); 961   ✗ default: BOOST_JSON_UNREACHABLE();
951   } 962   }
952   963  
HITCBC 953   1346 cs += size; 964   1346 cs += size;
HITCBC 954   1346 return cs.begin(); 965   1346 return cs.begin();
955   } 966   }
956   967  
957   //---------------------------------------------------------- 968   //----------------------------------------------------------
958   969  
959   template<class Handler> 970   template<class Handler>
960   template<bool StackEmpty_, bool IsKey_> 971   template<bool StackEmpty_, bool IsKey_>
961   const char* 972   const char*
HITCBC 962   161311 basic_parser<Handler>:: 973   161311 basic_parser<Handler>::
963   parse_string(const char* p, 974   parse_string(const char* p,
964   std::integral_constant<bool, StackEmpty_> stack_empty, 975   std::integral_constant<bool, StackEmpty_> stack_empty,
965   std::integral_constant<bool, IsKey_> is_key, 976   std::integral_constant<bool, IsKey_> is_key,
966   bool allow_bad_utf8, 977   bool allow_bad_utf8,
967   bool allow_bad_utf16) 978   bool allow_bad_utf16)
968   { 979   {
HITCBC 969   161311 detail::const_stream_wrapper cs(p, end_); 980   161311 detail::const_stream_wrapper cs(p, end_);
970   std::size_t total; 981   std::size_t total;
971   char const* start; 982   char const* start;
972   std::size_t size; 983   std::size_t size;
HITCBC 973   161311 if(! stack_empty && ! st_.empty()) 984   161311 if(! stack_empty && ! st_.empty())
974   { 985   {
975   state st; 986   state st;
HITCBC 976   32906 st_.pop(st); 987   32906 st_.pop(st);
HITCBC 977   32906 st_.pop(total); 988   32906 st_.pop(total);
HITCBC 978   32906 switch(st) 989   32906 switch(st)
979   { 990   {
MISUBC 980   ✗ default: BOOST_JSON_UNREACHABLE(); 991   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 981   3149 case state::str2: goto do_str2; 992   3149 case state::str2: goto do_str2;
HITCBC 982   1864 case state::str8: goto do_str8; 993   1864 case state::str8: goto do_str8;
HITCBC 983   27893 case state::str1: break; 994   27893 case state::str1: break;
984   } 995   }
985   } 996   }
986   else 997   else
987   { 998   {
HITCBC 988   128405 BOOST_ASSERT(*cs == '\x22'); // '"' 999   128405 BOOST_ASSERT(*cs == '\x22'); // '"'
HITCBC 989   128405 ++cs; 1000   128405 ++cs;
HITCBC 990   128405 total = 0; 1001   128405 total = 0;
991   } 1002   }
992   1003  
HITCBC 993   164791 do_str1: 1004   164791 do_str1:
HITCBC 994   164791 start = cs.begin(); 1005   164791 start = cs.begin();
HITCBC 995   329582 cs = allow_bad_utf8? 1006   329582 cs = allow_bad_utf8?
HITCBC 996   2177 detail::count_valid<true>(cs.begin(), cs.end()): 1007   2177 detail::count_valid<true>(cs.begin(), cs.end()):
HITCBC 997   162614 detail::count_valid<false>(cs.begin(), cs.end()); 1008   162614 detail::count_valid<false>(cs.begin(), cs.end());
HITCBC 998   164791 size = cs.used(start); 1009   164791 size = cs.used(start);
HITCBC 999   164791 if(is_key) 1010   164791 if(is_key)
1000   { 1011   {
HITCBC 1001   46694 BOOST_ASSERT(total <= Handler::max_key_size); 1012   46694 BOOST_ASSERT(total <= Handler::max_key_size);
HITCBC 1002   94005 if(BOOST_JSON_UNLIKELY(size > 1013   94005 if(BOOST_JSON_UNLIKELY(size >
1003   Handler::max_key_size - total)) 1014   Handler::max_key_size - total))
1004   { 1015   {
1005   BOOST_STATIC_CONSTEXPR source_location loc 1016   BOOST_STATIC_CONSTEXPR source_location loc
1006   = BOOST_CURRENT_LOCATION; 1017   = BOOST_CURRENT_LOCATION;
HITCBC 1007   3 return fail(cs.begin(), error::key_too_large, &loc); 1018   3 return fail(cs.begin(), error::key_too_large, &loc);
1008   } 1019   }
1009   } 1020   }
1010   else 1021   else
1011   { 1022   {
HITCBC 1012   35324 BOOST_ASSERT(total <= Handler::max_string_size); 1023   35324 BOOST_ASSERT(total <= Handler::max_string_size);
HITCBC 1013   70786 if(BOOST_JSON_UNLIKELY(size > 1024   70786 if(BOOST_JSON_UNLIKELY(size >
1014   Handler::max_string_size - total)) 1025   Handler::max_string_size - total))
1015   { 1026   {
1016   BOOST_STATIC_CONSTEXPR source_location loc 1027   BOOST_STATIC_CONSTEXPR source_location loc
1017   = BOOST_CURRENT_LOCATION; 1028   = BOOST_CURRENT_LOCATION;
HITCBC 1018   3 return fail(cs.begin(), error::string_too_large, &loc); 1029   3 return fail(cs.begin(), error::string_too_large, &loc);
1019   } 1030   }
1020   } 1031   }
HITCBC 1021   164785 total += size; 1032   164785 total += size;
HITCBC 1022   164785 if(BOOST_JSON_UNLIKELY(! cs)) 1033   164785 if(BOOST_JSON_UNLIKELY(! cs))
1023   { 1034   {
1024   // call handler if the string isn't empty 1035   // call handler if the string isn't empty
HITCBC 1025   30227 if(BOOST_JSON_LIKELY(size)) 1036   30227 if(BOOST_JSON_LIKELY(size))
1026   { 1037   {
1027   { 1038   {
HITCBC 1028   27066 bool r = is_key? 1039   27066 bool r = is_key?
HITCBC 1029   12404 h_.on_key_part( {start, size}, total, ec_ ): 1040   12404 h_.on_key_part( {start, size}, total, ec_ ):
HITCBC 1030   15996 h_.on_string_part( {start, size}, total, ec_ ); 1041   15996 h_.on_string_part( {start, size}, total, ec_ );
1031   1042  
HITCBC 1032   25958 if(BOOST_JSON_UNLIKELY(!r)) 1043   25958 if(BOOST_JSON_UNLIKELY(!r))
1033   { 1044   {
HITCBC 1034   1110 return fail(cs.begin()); 1045   1110 return fail(cs.begin());
1035   } 1046   }
1036   } 1047   }
1037   } 1048   }
HITCBC 1038   28009 return maybe_suspend(cs.begin(), state::str1, total); 1049   28009 return maybe_suspend(cs.begin(), state::str1, total);
1039   } 1050   }
1040   // at this point all valid characters have been skipped, so any remaining 1051   // at this point all valid characters have been skipped, so any remaining
1041   // if there are any more characters, they are either escaped, or incomplete 1052   // if there are any more characters, they are either escaped, or incomplete
1042   // utf8, or invalid utf8 1053   // utf8, or invalid utf8
HITCBC 1043   134558 if(BOOST_JSON_UNLIKELY(*cs != '\x22')) // '"' 1054   134558 if(BOOST_JSON_UNLIKELY(*cs != '\x22')) // '"'
1044   { 1055   {
1045   // sequence is invalid or incomplete 1056   // sequence is invalid or incomplete
HITCBC 1046   15071 if((*cs & 0x80) && !allow_bad_utf8) 1057   15071 if((*cs & 0x80) && !allow_bad_utf8)
1047   { 1058   {
HITCBC 1048   3465 seq_.save(cs.begin(), cs.remain()); 1059   3465 seq_.save(cs.begin(), cs.remain());
HITCBC 1049   3465 if(BOOST_JSON_UNLIKELY(seq_.complete())) 1060   3465 if(BOOST_JSON_UNLIKELY(seq_.complete()))
1050   { 1061   {
1051   BOOST_STATIC_CONSTEXPR source_location loc 1062   BOOST_STATIC_CONSTEXPR source_location loc
1052   = BOOST_CURRENT_LOCATION; 1063   = BOOST_CURRENT_LOCATION;
HITCBC 1053   1557 return fail(cs.begin(), error::syntax, &loc); 1064   1557 return fail(cs.begin(), error::syntax, &loc);
1054   } 1065   }
HITCBC 1055   1908 if(BOOST_JSON_LIKELY(size)) 1066   1908 if(BOOST_JSON_LIKELY(size))
1056   { 1067   {
HITCBC 1057   245 bool const r = is_key? 1068   245 bool const r = is_key?
HITCBC 1058   22 h_.on_key_part( {start, size}, total, ec_ ): 1069   22 h_.on_key_part( {start, size}, total, ec_ ):
HITCBC 1059   245 h_.on_string_part( {start, size}, total, ec_ ); 1070   245 h_.on_string_part( {start, size}, total, ec_ );
HITCBC 1060   223 if(BOOST_JSON_UNLIKELY( !r )) 1071   223 if(BOOST_JSON_UNLIKELY( !r ))
HITCBC 1061   22 return fail( cs.begin() ); 1072   22 return fail( cs.begin() );
1062   } 1073   }
HITCBC 1063   1864 return maybe_suspend(cs.end(), state::str8, total); 1074   1864 return maybe_suspend(cs.end(), state::str8, total);
1064   } 1075   }
HITCBC 1065   11606 else if(BOOST_JSON_LIKELY(*cs == '\\')) 1076   11606 else if(BOOST_JSON_LIKELY(*cs == '\\'))
1066   { 1077   {
1067   // flush unescaped run from input 1078   // flush unescaped run from input
HITCBC 1068   11497 if(BOOST_JSON_LIKELY(size)) 1079   11497 if(BOOST_JSON_LIKELY(size))
1069   { 1080   {
HITCBC 1070   4250 bool const r = is_key? 1081   4250 bool const r = is_key?
HITCBC 1071   1226 h_.on_key_part( {start, size}, total, ec_ ): 1082   1226 h_.on_key_part( {start, size}, total, ec_ ):
HITCBC 1072   3554 h_.on_string_part( {start, size}, total, ec_ ); 1083   3554 h_.on_string_part( {start, size}, total, ec_ );
HITCBC 1073   3766 if(BOOST_JSON_UNLIKELY( !r )) 1084   3766 if(BOOST_JSON_UNLIKELY( !r ))
HITCBC 1074   484 return fail( cs.begin() ); 1085   484 return fail( cs.begin() );
1075   } 1086   }
HITCBC 1076   7247 do_str2: 1087   7247 do_str2:
HITCBC 1077   13678 cs = parse_escaped(cs.begin(), total, stack_empty, is_key, allow_bad_utf16); 1088   13678 cs = parse_escaped(cs.begin(), total, stack_empty, is_key, allow_bad_utf16);
HITCBC 1078   12716 if(BOOST_JSON_UNLIKELY( incomplete(cs) )) 1089   12716 if(BOOST_JSON_UNLIKELY( incomplete(cs) ))
HITCBC 1079   5473 return suspend_or_fail(state::str2, total); 1090   5473 return suspend_or_fail(state::str2, total);
1080   1091  
HITCBC 1081   7243 goto do_str1; 1092   7243 goto do_str1;
1082   } 1093   }
1083   // illegal control 1094   // illegal control
1084   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 1095   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 1085   109 return fail(cs.begin(), error::syntax, &loc); 1096   109 return fail(cs.begin(), error::syntax, &loc);
1086   } 1097   }
1087   1098  
1088   { 1099   {
HITCBC 1089   119487 bool r = is_key? 1100   119487 bool r = is_key?
HITCBC 1090   84511 h_.on_key( {start, size}, total, ec_ ): 1101   84511 h_.on_key( {start, size}, total, ec_ ):
HITCBC 1091   41985 h_.on_string( {start, size}, total, ec_ ); 1102   41985 h_.on_string( {start, size}, total, ec_ );
1092   1103  
HITCBC 1093   115113 if(BOOST_JSON_UNLIKELY(!r)) 1104   115113 if(BOOST_JSON_UNLIKELY(!r))
1094   { 1105   {
HITCBC 1095   4318 return fail(cs.begin()); 1106   4318 return fail(cs.begin());
1096   } 1107   }
1097   } 1108   }
1098   1109  
HITCBC 1099   110795 ++cs; 1110   110795 ++cs;
HITCBC 1100   110795 return cs.begin(); 1111   110795 return cs.begin();
1101   1112  
HITCBC 1102   1864 do_str8: 1113   1864 do_str8:
HITCBC 1103   1864 uint8_t needed = seq_.needed(); 1114   1864 uint8_t needed = seq_.needed();
HITCBC 1104   1864 if(BOOST_JSON_UNLIKELY( !seq_.append(cs.begin(), cs.remain()) )) 1115   1864 if(BOOST_JSON_UNLIKELY( !seq_.append(cs.begin(), cs.remain()) ))
MISUBC 1105   ✗ return maybe_suspend(cs.end(), state::str8, total); 1116   ✗ return maybe_suspend(cs.end(), state::str8, total);
HITCBC 1106   1864 if(BOOST_JSON_UNLIKELY( !seq_.valid() )) 1117   1864 if(BOOST_JSON_UNLIKELY( !seq_.valid() ))
1107   { 1118   {
1108   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 1119   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 1109   210 return fail(cs.begin(), error::syntax, &loc); 1120   210 return fail(cs.begin(), error::syntax, &loc);
1110   } 1121   }
1111   { 1122   {
HITCBC 1112   1654 std::size_t const n = seq_.length(); 1123   1654 std::size_t const n = seq_.length();
1113   bool r; 1124   bool r;
HITCBC 1114   1654 if(is_key) 1125   1654 if(is_key)
1115   { 1126   {
HITCBC 1116   2 BOOST_ASSERT(total <= Handler::max_key_size); 1127   2 BOOST_ASSERT(total <= Handler::max_key_size);
HITCBC 1117   2 if(BOOST_JSON_UNLIKELY(n > 1128   2 if(BOOST_JSON_UNLIKELY(n >
1118   Handler::max_key_size - total)) 1129   Handler::max_key_size - total))
1119   { 1130   {
1120   BOOST_STATIC_CONSTEXPR source_location loc 1131   BOOST_STATIC_CONSTEXPR source_location loc
1121   = BOOST_CURRENT_LOCATION; 1132   = BOOST_CURRENT_LOCATION;
HITCBC 1122   1 return fail(cs.begin(), error::key_too_large, &loc); 1133   1 return fail(cs.begin(), error::key_too_large, &loc);
1123   } 1134   }
HITCBC 1124   1 total += n; 1135   1 total += n;
HITCBC 1125   1 r = h_.on_key_part( {seq_.data(), n}, total, ec_ ); 1136   1 r = h_.on_key_part( {seq_.data(), n}, total, ec_ );
1126   } 1137   }
1127   else 1138   else
1128   { 1139   {
HITCBC 1129   1 BOOST_ASSERT(total <= Handler::max_string_size); 1140   1 BOOST_ASSERT(total <= Handler::max_string_size);
HITCBC 1130   1652 if(BOOST_JSON_UNLIKELY(n > 1141   1652 if(BOOST_JSON_UNLIKELY(n >
1131   Handler::max_string_size - total)) 1142   Handler::max_string_size - total))
1132   { 1143   {
1133   BOOST_STATIC_CONSTEXPR source_location loc 1144   BOOST_STATIC_CONSTEXPR source_location loc
1134   = BOOST_CURRENT_LOCATION; 1145   = BOOST_CURRENT_LOCATION;
HITCBC 1135   1 return fail(cs.begin(), error::string_too_large, &loc); 1146   1 return fail(cs.begin(), error::string_too_large, &loc);
1136   } 1147   }
HITCBC 1137   1651 total += n; 1148   1651 total += n;
HITCBC 1138   1651 r = h_.on_string_part( {seq_.data(), n}, total, ec_ ); 1149   1651 r = h_.on_string_part( {seq_.data(), n}, total, ec_ );
1139   } 1150   }
HITCBC 1140   1451 if(BOOST_JSON_UNLIKELY( !r )) 1151   1451 if(BOOST_JSON_UNLIKELY( !r ))
HITCBC 1141   201 return fail( cs.begin() ); 1152   201 return fail( cs.begin() );
1142   } 1153   }
HITCBC 1143   1250 cs += needed; 1154   1250 cs += needed;
HITCBC 1144   1250 goto do_str1; 1155   1250 goto do_str1;
1145   } 1156   }
1146   1157  
1147   template<class Handler> 1158   template<class Handler>
1148   template<bool StackEmpty_> 1159   template<bool StackEmpty_>
1149   const char* 1160   const char*
HITCBC 1150   13678 basic_parser<Handler>:: 1161   13678 basic_parser<Handler>::
1151   parse_escaped( 1162   parse_escaped(
1152   const char* p, 1163   const char* p,
1153   std::size_t& total, 1164   std::size_t& total,
1154   std::integral_constant<bool, StackEmpty_> stack_empty, 1165   std::integral_constant<bool, StackEmpty_> stack_empty,
1155   bool is_key, 1166   bool is_key,
1156   bool allow_bad_utf16) 1167   bool allow_bad_utf16)
1157   { 1168   {
HITCBC 1158   13678 constexpr unsigned urc = 0xFFFD; // Unicode replacement character 1169   13678 constexpr unsigned urc = 0xFFFD; // Unicode replacement character
HITCBC 1159   13678 auto const ev_too_large = is_key? 1170   13678 auto const ev_too_large = is_key?
1160   error::key_too_large : error::string_too_large; 1171   error::key_too_large : error::string_too_large;
HITCBC 1161   13678 auto const max_size = is_key? 1172   13678 auto const max_size = is_key?
1162   Handler::max_key_size : Handler::max_string_size; 1173   Handler::max_key_size : Handler::max_string_size;
1163   int digit; 1174   int digit;
1164   1175  
1165   //--------------------------------------------------------------- 1176   //---------------------------------------------------------------
1166   // 1177   //
1167   // To handle escapes, a local temporary buffer accumulates 1178   // To handle escapes, a local temporary buffer accumulates
1168   // the unescaped result. The algorithm attempts to fill the 1179   // the unescaped result. The algorithm attempts to fill the
1169   // buffer to capacity before invoking the handler. 1180   // buffer to capacity before invoking the handler.
1170   // In some cases the temporary buffer needs to be flushed 1181   // In some cases the temporary buffer needs to be flushed
1171   // before it is full: 1182   // before it is full:
1172   // * When the closing double quote is seen 1183   // * When the closing double quote is seen
1173   // * When there in no more input (and more is expected later) 1184   // * When there in no more input (and more is expected later)
1174   // A goal of the algorithm is to call the handler as few times 1185   // A goal of the algorithm is to call the handler as few times
1175   // as possible. Thus, when the first escape is encountered, 1186   // as possible. Thus, when the first escape is encountered,
1176   // the algorithm attempts to fill the temporary buffer first. 1187   // the algorithm attempts to fill the temporary buffer first.
1177   // 1188   //
HITCBC 1178   13678 detail::buffer<BOOST_JSON_STACK_BUFFER_SIZE> temp; 1189   13678 detail::buffer<BOOST_JSON_STACK_BUFFER_SIZE> temp;
1179   1190  
1180   // Unescaped JSON is never larger than its escaped version. 1191   // Unescaped JSON is never larger than its escaped version.
1181   // To efficiently process only what will fit in the temporary buffer, 1192   // To efficiently process only what will fit in the temporary buffer,
1182   // the size of the input stream is temporarily "clipped" to the size 1193   // the size of the input stream is temporarily "clipped" to the size
1183   // of the temporary buffer. 1194   // of the temporary buffer.
1184   // handle escaped character 1195   // handle escaped character
HITCBC 1185   13678 detail::clipped_const_stream cs(p, end_); 1196   13678 detail::clipped_const_stream cs(p, end_);
HITCBC 1186   13678 cs.clip(temp.max_size()); 1197   13678 cs.clip(temp.max_size());
1187   1198  
HITCBC 1188   13678 if(! stack_empty && ! st_.empty()) 1199   13678 if(! stack_empty && ! st_.empty())
1189   { 1200   {
1190   state st; 1201   state st;
HITCBC 1191   3149 st_.pop(st); 1202   3149 st_.pop(st);
HITCBC 1192   3149 switch(st) 1203   3149 switch(st)
1193   { 1204   {
MISUBC 1194   ✗ default: BOOST_JSON_UNREACHABLE(); 1205   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 1195   528 case state::str3: goto do_str3; 1206   528 case state::str3: goto do_str3;
HITCBC 1196   392 case state::str4: goto do_str4; 1207   392 case state::str4: goto do_str4;
HITCBC 1197   390 case state::str5: goto do_str5; 1208   390 case state::str5: goto do_str5;
HITCBC 1198   389 case state::str6: goto do_str6; 1209   389 case state::str6: goto do_str6;
HITCBC 1199   386 case state::str7: goto do_str7; 1210   386 case state::str7: goto do_str7;
HITCBC 1200   232 case state::sur1: goto do_sur1; 1211   232 case state::sur1: goto do_sur1;
HITCBC 1201   188 case state::sur2: goto do_sur2; 1212   188 case state::sur2: goto do_sur2;
HITCBC 1202   164 case state::sur3: goto do_sur3; 1213   164 case state::sur3: goto do_sur3;
HITCBC 1203   162 case state::sur4: goto do_sur4; 1214   162 case state::sur4: goto do_sur4;
HITCBC 1204   160 case state::sur5: goto do_sur5; 1215   160 case state::sur5: goto do_sur5;
HITCBC 1205   158 case state::sur6: goto do_sur6; 1216   158 case state::sur6: goto do_sur6;
1206   } 1217   }
1207   } 1218   }
1208   1219  
HITCBC 1209   3781 while(true) 1220   3781 while(true)
1210   { 1221   {
HITCBC 1211   14310 BOOST_ASSERT( temp.capacity() ); 1222   14310 BOOST_ASSERT( temp.capacity() );
HITCBC 1212   14310 BOOST_ASSERT(*cs == '\\'); 1223   14310 BOOST_ASSERT(*cs == '\\');
HITCBC 1213   14310 ++cs; 1224   14310 ++cs;
HITCBC 1214   15169 do_str3: 1225   15169 do_str3:
HITCBC 1215   15374 if(BOOST_JSON_UNLIKELY(! cs)) 1226   15374 if(BOOST_JSON_UNLIKELY(! cs))
1216   { 1227   {
HITCBC 1217   561 if(BOOST_JSON_LIKELY(! temp.empty())) 1228   561 if(BOOST_JSON_LIKELY(! temp.empty()))
1218   { 1229   {
MISUBC 1219   ✗ BOOST_ASSERT(total <= max_size); 1230   ✗ BOOST_ASSERT(total <= max_size);
HITCBC 1220   100 if(BOOST_JSON_UNLIKELY( 1231   100 if(BOOST_JSON_UNLIKELY(
1221   temp.size() > max_size - total)) 1232   temp.size() > max_size - total))
1222   { 1233   {
1223   BOOST_STATIC_CONSTEXPR source_location loc 1234   BOOST_STATIC_CONSTEXPR source_location loc
1224   = BOOST_CURRENT_LOCATION; 1235   = BOOST_CURRENT_LOCATION;
MISUBC 1225   ✗ return fail(cs.begin(), ev_too_large, &loc); 1236   ✗ return fail(cs.begin(), ev_too_large, &loc);
1226   } 1237   }
HITCBC 1227   100 total += temp.size(); 1238   100 total += temp.size();
1228   { 1239   {
HITCBC 1229   91 bool r = is_key 1240   91 bool r = is_key
HITCBC 1230   100 ? h_.on_key_part(temp.get(), total, ec_) 1241   100 ? h_.on_key_part(temp.get(), total, ec_)
HITCBC 1231   100 : h_.on_string_part(temp.get(), total, ec_); 1242   100 : h_.on_string_part(temp.get(), total, ec_);
1232   1243  
HITCBC 1233   91 if(BOOST_JSON_UNLIKELY(!r)) 1244   91 if(BOOST_JSON_UNLIKELY(!r))
1234   { 1245   {
HITCBC 1235   9 return fail(cs.begin()); 1246   9 return fail(cs.begin());
1236   } 1247   }
1237   } 1248   }
HITCBC 1238   82 temp.clear(); 1249   82 temp.clear();
1239   } 1250   }
HITCBC 1240   543 cs.clip(temp.max_size()); 1251   543 cs.clip(temp.max_size());
HITCBC 1241   543 if(BOOST_JSON_UNLIKELY(! cs)) 1252   543 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1242   543 return maybe_suspend(cs.begin(), state::str3); 1253   543 return maybe_suspend(cs.begin(), state::str3);
1243   } 1254   }
HITCBC 1244   14813 switch(*cs) 1255   14813 switch(*cs)
1245   { 1256   {
HITCBC 1246   191 default: 1257   191 default:
1247   { 1258   {
1248   BOOST_STATIC_CONSTEXPR source_location loc 1259   BOOST_STATIC_CONSTEXPR source_location loc
1249   = BOOST_CURRENT_LOCATION; 1260   = BOOST_CURRENT_LOCATION;
HITCBC 1250   191 return fail(cs.begin(), error::syntax, &loc); 1261   191 return fail(cs.begin(), error::syntax, &loc);
1251   } 1262   }
HITCBC 1252   265 case '\x22': // '"' 1263   265 case '\x22': // '"'
HITCBC 1253   265 temp.push_back('\x22'); 1264   265 temp.push_back('\x22');
HITCBC 1254   265 ++cs; 1265   265 ++cs;
HITCBC 1255   265 break; 1266   265 break;
HITCBC 1256   178 case '\\': 1267   178 case '\\':
HITCBC 1257   178 temp.push_back('\\'); 1268   178 temp.push_back('\\');
HITCBC 1258   178 ++cs; 1269   178 ++cs;
HITCBC 1259   178 break; 1270   178 break;
HITCBC 1260   96 case '/': 1271   96 case '/':
HITCBC 1261   96 temp.push_back('/'); 1272   96 temp.push_back('/');
HITCBC 1262   96 ++cs; 1273   96 ++cs;
HITCBC 1263   96 break; 1274   96 break;
HITCBC 1264   112 case 'b': 1275   112 case 'b':
HITCBC 1265   112 temp.push_back('\x08'); 1276   112 temp.push_back('\x08');
HITCBC 1266   112 ++cs; 1277   112 ++cs;
HITCBC 1267   112 break; 1278   112 break;
HITCBC 1268   108 case 'f': 1279   108 case 'f':
HITCBC 1269   108 temp.push_back('\x0c'); 1280   108 temp.push_back('\x0c');
HITCBC 1270   108 ++cs; 1281   108 ++cs;
HITCBC 1271   108 break; 1282   108 break;
HITCBC 1272   1763 case 'n': 1283   1763 case 'n':
HITCBC 1273   1763 temp.push_back('\x0a'); 1284   1763 temp.push_back('\x0a');
HITCBC 1274   1763 ++cs; 1285   1763 ++cs;
HITCBC 1275   1763 break; 1286   1763 break;
HITCBC 1276   146 case 'r': 1287   146 case 'r':
HITCBC 1277   146 temp.push_back('\x0d'); 1288   146 temp.push_back('\x0d');
HITCBC 1278   146 ++cs; 1289   146 ++cs;
HITCBC 1279   146 break; 1290   146 break;
HITCBC 1280   266 case 't': 1291   266 case 't':
HITCBC 1281   266 temp.push_back('\x09'); 1292   266 temp.push_back('\x09');
HITCBC 1282   266 ++cs; 1293   266 ++cs;
HITCBC 1283   266 break; 1294   266 break;
HITCBC 1284   11688 case 'u': 1295   11688 case 'u':
1285   // utf16 escape 1296   // utf16 escape
1286   // 1297   //
1287   // fast path only when the buffer 1298   // fast path only when the buffer
1288   // is large enough for 2 surrogates 1299   // is large enough for 2 surrogates
HITCBC 1289   11688 if(BOOST_JSON_LIKELY(cs.remain() > 10)) 1300   11688 if(BOOST_JSON_LIKELY(cs.remain() > 10))
1290   { 1301   {
1291   // KRYSTIAN TODO: this could be done 1302   // KRYSTIAN TODO: this could be done
1292   // with fewer instructions 1303   // with fewer instructions
HITCBC 1293   11394 digit = detail::load_little_endian<4>( 1304   11394 digit = detail::load_little_endian<4>(
HITCBC 1294   5697 cs.begin() + 1); 1305   5697 cs.begin() + 1);
HITCBC 1295   5697 int d4 = detail::hex_digit(static_cast< 1306   5697 int d4 = detail::hex_digit(static_cast<
HITCBC 1296   5697 unsigned char>(digit >> 24)); 1307   5697 unsigned char>(digit >> 24));
HITCBC 1297   5697 int d3 = detail::hex_digit(static_cast< 1308   5697 int d3 = detail::hex_digit(static_cast<
HITCBC 1298   5697 unsigned char>(digit >> 16)); 1309   5697 unsigned char>(digit >> 16));
HITCBC 1299   5697 int d2 = detail::hex_digit(static_cast< 1310   5697 int d2 = detail::hex_digit(static_cast<
HITCBC 1300   5697 unsigned char>(digit >> 8)); 1311   5697 unsigned char>(digit >> 8));
HITCBC 1301   5697 int d1 = detail::hex_digit(static_cast< 1312   5697 int d1 = detail::hex_digit(static_cast<
1302   unsigned char>(digit)); 1313   unsigned char>(digit));
HITCBC 1303   5697 if(BOOST_JSON_UNLIKELY( 1314   5697 if(BOOST_JSON_UNLIKELY(
1304   (d1 | d2 | d3 | d4) == -1)) 1315   (d1 | d2 | d3 | d4) == -1))
1305   { 1316   {
HITCBC 1306   60 if(d1 != -1) 1317   60 if(d1 != -1)
HITCBC 1307   45 ++cs; 1318   45 ++cs;
HITCBC 1308   60 if(d2 != -1) 1319   60 if(d2 != -1)
HITCBC 1309   30 ++cs; 1320   30 ++cs;
HITCBC 1310   60 if(d3 != -1) 1321   60 if(d3 != -1)
HITCBC 1311   15 ++cs; 1322   15 ++cs;
1312   BOOST_STATIC_CONSTEXPR source_location loc 1323   BOOST_STATIC_CONSTEXPR source_location loc
1313   = BOOST_CURRENT_LOCATION; 1324   = BOOST_CURRENT_LOCATION;
HITCBC 1314   60 return fail(cs.begin(), error::expected_hex_digit, &loc); 1325   60 return fail(cs.begin(), error::expected_hex_digit, &loc);
1315   } 1326   }
1316   // 32 bit unicode scalar value 1327   // 32 bit unicode scalar value
HITCBC 1317   5637 unsigned u1 = 1328   5637 unsigned u1 =
HITCBC 1318   5637 (d1 << 12) + (d2 << 8) + 1329   5637 (d1 << 12) + (d2 << 8) +
HITCBC 1319   5637 (d3 << 4) + d4; 1330   5637 (d3 << 4) + d4;
1320   // valid unicode scalar values are 1331   // valid unicode scalar values are
1321   // [0, D7FF] and [E000, 10FFFF] 1332   // [0, D7FF] and [E000, 10FFFF]
1322   // values within this range are valid utf-8 1333   // values within this range are valid utf-8
1323   // code points and invalid leading surrogates. 1334   // code points and invalid leading surrogates.
HITCBC 1324   5637 if(BOOST_JSON_LIKELY( 1335   5637 if(BOOST_JSON_LIKELY(
1325   u1 < 0xd800 || u1 > 0xdfff)) 1336   u1 < 0xd800 || u1 > 0xdfff))
1326   { 1337   {
HITCBC 1327   1340 cs += 5; 1338   1340 cs += 5;
HITCBC 1328   1340 temp.append_utf8(u1); 1339   1340 temp.append_utf8(u1);
HITCBC 1329   1340 break; 1340   1340 break;
1330   } 1341   }
HITCBC 1331   4297 if(BOOST_JSON_UNLIKELY(u1 > 0xdbff)) 1342   4297 if(BOOST_JSON_UNLIKELY(u1 > 0xdbff))
1332   { 1343   {
1333   // If it's an illegal leading surrogate and 1344   // If it's an illegal leading surrogate and
1334   // the parser does not allow it, return an error. 1345   // the parser does not allow it, return an error.
HITCBC 1335   707 if(!allow_bad_utf16) 1346   707 if(!allow_bad_utf16)
1336   { 1347   {
1337   BOOST_STATIC_CONSTEXPR source_location loc 1348   BOOST_STATIC_CONSTEXPR source_location loc
1338   = BOOST_CURRENT_LOCATION; 1349   = BOOST_CURRENT_LOCATION;
HITCBC 1339   122 return fail(cs.begin(), error::illegal_leading_surrogate, 1350   122 return fail(cs.begin(), error::illegal_leading_surrogate,
HITCBC 1340   122 &loc); 1351   122 &loc);
1341   } 1352   }
1342   // Otherwise, append the Unicode replacement character 1353   // Otherwise, append the Unicode replacement character
1343   else 1354   else
1344   { 1355   {
HITCBC 1345   585 cs += 5; 1356   585 cs += 5;
HITCBC 1346   585 temp.append_utf8(urc); 1357   585 temp.append_utf8(urc);
HITCBC 1347   585 break; 1358   585 break;
1348   } 1359   }
1349   } 1360   }
HITCBC 1350   3590 cs += 5; 1361   3590 cs += 5;
1351   // KRYSTIAN TODO: this can be a two byte load 1362   // KRYSTIAN TODO: this can be a two byte load
1352   // and a single comparison. We lose error information, 1363   // and a single comparison. We lose error information,
1353   // but it's faster. 1364   // but it's faster.
HITCBC 1354   3590 if(BOOST_JSON_UNLIKELY(*cs != '\\')) 1365   3590 if(BOOST_JSON_UNLIKELY(*cs != '\\'))
1355   { 1366   {
1356   // If the next character is not a backslash and 1367   // If the next character is not a backslash and
1357   // the parser does not allow it, return a syntax error. 1368   // the parser does not allow it, return a syntax error.
HITCBC 1358   156 if(!allow_bad_utf16) 1369   156 if(!allow_bad_utf16)
1359   { 1370   {
1360   BOOST_STATIC_CONSTEXPR source_location loc 1371   BOOST_STATIC_CONSTEXPR source_location loc
1361   = BOOST_CURRENT_LOCATION; 1372   = BOOST_CURRENT_LOCATION;
HITCBC 1362   15 return fail(cs.begin(), error::syntax, &loc); 1373   15 return fail(cs.begin(), error::syntax, &loc);
1363   } 1374   }
1364   // Otherwise, append the Unicode replacement character since 1375   // Otherwise, append the Unicode replacement character since
1365   // the first code point is a valid leading surrogate 1376   // the first code point is a valid leading surrogate
1366   else 1377   else
1367   { 1378   {
HITCBC 1368   141 temp.append_utf8(urc); 1379   141 temp.append_utf8(urc);
HITCBC 1369   141 break; 1380   141 break;
1370   } 1381   }
1371   } 1382   }
HITCBC 1372   3434 ++cs; 1383   3434 ++cs;
HITCBC 1373   3434 if(BOOST_JSON_UNLIKELY(*cs != 'u')) 1384   3434 if(BOOST_JSON_UNLIKELY(*cs != 'u'))
1374   { 1385   {
HITCBC 1375   220 if (!allow_bad_utf16) 1386   220 if (!allow_bad_utf16)
1376   { 1387   {
1377   BOOST_STATIC_CONSTEXPR source_location loc 1388   BOOST_STATIC_CONSTEXPR source_location loc
1378   = BOOST_CURRENT_LOCATION; 1389   = BOOST_CURRENT_LOCATION;
HITCBC 1379   15 return fail(cs.begin(), error::syntax, &loc); 1390   15 return fail(cs.begin(), error::syntax, &loc);
1380   } 1391   }
1381   // Otherwise, append the Unicode replacement character since 1392   // Otherwise, append the Unicode replacement character since
1382   // the first code point is a valid leading surrogate 1393   // the first code point is a valid leading surrogate
1383   else 1394   else
1384   { 1395   {
HITCBC 1385   205 temp.append_utf8(urc); 1396   205 temp.append_utf8(urc);
HITCBC 1386   205 goto do_str3; 1397   205 goto do_str3;
1387   } 1398   }
1388   } 1399   }
HITCBC 1389   3214 ++cs; 1400   3214 ++cs;
HITCBC 1390   3214 digit = detail::load_little_endian<4>(cs.begin()); 1401   3214 digit = detail::load_little_endian<4>(cs.begin());
HITCBC 1391   3214 d4 = detail::hex_digit(static_cast< 1402   3214 d4 = detail::hex_digit(static_cast<
HITCBC 1392   3214 unsigned char>(digit >> 24)); 1403   3214 unsigned char>(digit >> 24));
HITCBC 1393   3214 d3 = detail::hex_digit(static_cast< 1404   3214 d3 = detail::hex_digit(static_cast<
HITCBC 1394   3214 unsigned char>(digit >> 16)); 1405   3214 unsigned char>(digit >> 16));
HITCBC 1395   3214 d2 = detail::hex_digit(static_cast< 1406   3214 d2 = detail::hex_digit(static_cast<
HITCBC 1396   3214 unsigned char>(digit >> 8)); 1407   3214 unsigned char>(digit >> 8));
HITCBC 1397   3214 d1 = detail::hex_digit(static_cast< 1408   3214 d1 = detail::hex_digit(static_cast<
1398   unsigned char>(digit)); 1409   unsigned char>(digit));
HITCBC 1399   3214 if(BOOST_JSON_UNLIKELY( 1410   3214 if(BOOST_JSON_UNLIKELY(
1400   (d1 | d2 | d3 | d4) == -1)) 1411   (d1 | d2 | d3 | d4) == -1))
1401   { 1412   {
HITCBC 1402   90 if(d1 != -1) 1413   90 if(d1 != -1)
HITCBC 1403   75 ++cs; 1414   75 ++cs;
HITCBC 1404   90 if(d2 != -1) 1415   90 if(d2 != -1)
HITCBC 1405   45 ++cs; 1416   45 ++cs;
HITCBC 1406   90 if(d3 != -1) 1417   90 if(d3 != -1)
HITCBC 1407   15 ++cs; 1418   15 ++cs;
1408   BOOST_STATIC_CONSTEXPR source_location loc 1419   BOOST_STATIC_CONSTEXPR source_location loc
1409   = BOOST_CURRENT_LOCATION; 1420   = BOOST_CURRENT_LOCATION;
HITCBC 1410   90 return fail(cs.begin(), error::expected_hex_digit, &loc); 1421   90 return fail(cs.begin(), error::expected_hex_digit, &loc);
1411   } 1422   }
HITCBC 1412   3124 unsigned u2 = 1423   3124 unsigned u2 =
HITCBC 1413   3124 (d1 << 12) + (d2 << 8) + 1424   3124 (d1 << 12) + (d2 << 8) +
HITCBC 1414   3124 (d3 << 4) + d4; 1425   3124 (d3 << 4) + d4;
1415   // Check if the second code point is a valid trailing surrogate. 1426   // Check if the second code point is a valid trailing surrogate.
1416   // Valid trailing surrogates are [DC00, DFFF] 1427   // Valid trailing surrogates are [DC00, DFFF]
HITCBC 1417   3124 if(BOOST_JSON_UNLIKELY( 1428   3124 if(BOOST_JSON_UNLIKELY(
1418   u2 < 0xdc00 || u2 > 0xdfff)) 1429   u2 < 0xdc00 || u2 > 0xdfff))
1419   { 1430   {
1420   // If not valid and the parser does not allow it, return an error. 1431   // If not valid and the parser does not allow it, return an error.
HITCBC 1421   1353 if(!allow_bad_utf16) 1432   1353 if(!allow_bad_utf16)
1422   { 1433   {
1423   BOOST_STATIC_CONSTEXPR source_location loc 1434   BOOST_STATIC_CONSTEXPR source_location loc
1424   = BOOST_CURRENT_LOCATION; 1435   = BOOST_CURRENT_LOCATION;
HITCBC 1425   136 return fail(cs.begin(), error::illegal_trailing_surrogate, 1436   136 return fail(cs.begin(), error::illegal_trailing_surrogate,
HITCBC 1426   136 &loc); 1437   136 &loc);
1427   } 1438   }
1428   // Append the replacement character for the 1439   // Append the replacement character for the
1429   // first leading surrogate. 1440   // first leading surrogate.
HITCBC 1430   1217 cs += 4; 1441   1217 cs += 4;
HITCBC 1431   1217 temp.append_utf8(urc); 1442   1217 temp.append_utf8(urc);
1432   // Check if the second code point is a 1443   // Check if the second code point is a
1433   // valid unicode scalar value (invalid leading 1444   // valid unicode scalar value (invalid leading
1434   // or trailing surrogate) 1445   // or trailing surrogate)
HITCBC 1435   1217 if (u2 < 0xd800 || u2 > 0xdbff) 1446   1217 if (u2 < 0xd800 || u2 > 0xdbff)
1436   { 1447   {
HITCBC 1437   524 temp.append_utf8(u2); 1448   524 temp.append_utf8(u2);
HITCBC 1438   524 break; 1449   524 break;
1439   } 1450   }
1440   // If it is a valid leading surrogate 1451   // If it is a valid leading surrogate
1441   else 1452   else
1442   { 1453   {
HITCBC 1443   693 u1_ = u2; 1454   693 u1_ = u2;
HITCBC 1444   693 goto do_sur1; 1455   693 goto do_sur1;
1445   } 1456   }
1446   } 1457   }
HITCBC 1447   1771 cs += 4; 1458   1771 cs += 4;
1448   // Calculate the Unicode code point from the surrogate pair and 1459   // Calculate the Unicode code point from the surrogate pair and
1449   // append the UTF-8 representation. 1460   // append the UTF-8 representation.
HITCBC 1450   1771 unsigned cp = 1461   1771 unsigned cp =
HITCBC 1451   1771 ((u1 - 0xd800) << 10) + 1462   1771 ((u1 - 0xd800) << 10) +
1452   ((u2 - 0xdc00)) + 1463   ((u2 - 0xdc00)) +
1453   0x10000; 1464   0x10000;
1454   // utf-16 surrogate pair 1465   // utf-16 surrogate pair
HITCBC 1455   1771 temp.append_utf8(cp); 1466   1771 temp.append_utf8(cp);
HITCBC 1456   1771 break; 1467   1771 break;
1457   } 1468   }
1458   // flush 1469   // flush
HITCBC 1459   5991 if(BOOST_JSON_LIKELY(! temp.empty())) 1470   5991 if(BOOST_JSON_LIKELY(! temp.empty()))
1460   { 1471   {
HITCBC 1461   3 BOOST_ASSERT(total <= max_size); 1472   3 BOOST_ASSERT(total <= max_size);
HITCBC 1462   1722 if(BOOST_JSON_UNLIKELY( 1473   1722 if(BOOST_JSON_UNLIKELY(
1463   temp.size() > max_size - total)) 1474   temp.size() > max_size - total))
1464   { 1475   {
1465   BOOST_STATIC_CONSTEXPR source_location loc 1476   BOOST_STATIC_CONSTEXPR source_location loc
1466   = BOOST_CURRENT_LOCATION; 1477   = BOOST_CURRENT_LOCATION;
MISUBC 1467   ✗ return fail(cs.begin(), ev_too_large, &loc); 1478   ✗ return fail(cs.begin(), ev_too_large, &loc);
1468   } 1479   }
HITCBC 1469   1722 total += temp.size(); 1480   1722 total += temp.size();
1470   { 1481   {
HITCBC 1471   1582 bool r = is_key 1482   1582 bool r = is_key
HITCBC 1472   1722 ? h_.on_key_part(temp.get(), total, ec_) 1483   1722 ? h_.on_key_part(temp.get(), total, ec_)
HITCBC 1473   1722 : h_.on_string_part(temp.get(), total, ec_); 1484   1722 : h_.on_string_part(temp.get(), total, ec_);
1474   1485  
HITCBC 1475   1582 if(BOOST_JSON_UNLIKELY(!r)) 1486   1582 if(BOOST_JSON_UNLIKELY(!r))
1476   { 1487   {
HITCBC 1477   140 return fail(cs.begin()); 1488   140 return fail(cs.begin());
1478   } 1489   }
1479   } 1490   }
HITCBC 1480   1442 temp.clear(); 1491   1442 temp.clear();
HITCBC 1481   1442 cs.clip(temp.max_size()); 1492   1442 cs.clip(temp.max_size());
1482   } 1493   }
HITCBC 1483   5711 ++cs; 1494   5711 ++cs;
1484   // utf-16 escape 1495   // utf-16 escape
HITCBC 1485   6103 do_str4: 1496   6103 do_str4:
HITCBC 1486   6103 if(BOOST_JSON_UNLIKELY(! cs)) 1497   6103 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1487   392 return maybe_suspend(cs.begin(), state::str4); 1498   392 return maybe_suspend(cs.begin(), state::str4);
HITCBC 1488   5711 digit = detail::hex_digit(*cs); 1499   5711 digit = detail::hex_digit(*cs);
HITCBC 1489   5711 if(BOOST_JSON_UNLIKELY(digit == -1)) 1500   5711 if(BOOST_JSON_UNLIKELY(digit == -1))
1490   { 1501   {
1491   BOOST_STATIC_CONSTEXPR source_location loc 1502   BOOST_STATIC_CONSTEXPR source_location loc
1492   = BOOST_CURRENT_LOCATION; 1503   = BOOST_CURRENT_LOCATION;
HITCBC 1493   50 return fail(cs.begin(), error::expected_hex_digit, &loc); 1504   50 return fail(cs.begin(), error::expected_hex_digit, &loc);
1494   } 1505   }
HITCBC 1495   5661 ++cs; 1506   5661 ++cs;
HITCBC 1496   5661 u1_ = digit << 12; 1507   5661 u1_ = digit << 12;
HITCBC 1497   6051 do_str5: 1508   6051 do_str5:
HITCBC 1498   6051 if(BOOST_JSON_UNLIKELY(! cs)) 1509   6051 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1499   390 return maybe_suspend(cs.begin(), state::str5); 1510   390 return maybe_suspend(cs.begin(), state::str5);
HITCBC 1500   5661 digit = detail::hex_digit(*cs); 1511   5661 digit = detail::hex_digit(*cs);
HITCBC 1501   5661 if(BOOST_JSON_UNLIKELY(digit == -1)) 1512   5661 if(BOOST_JSON_UNLIKELY(digit == -1))
1502   { 1513   {
1503   BOOST_STATIC_CONSTEXPR source_location loc 1514   BOOST_STATIC_CONSTEXPR source_location loc
1504   = BOOST_CURRENT_LOCATION; 1515   = BOOST_CURRENT_LOCATION;
HITCBC 1505   20 return fail(cs.begin(), error::expected_hex_digit, &loc); 1516   20 return fail(cs.begin(), error::expected_hex_digit, &loc);
1506   } 1517   }
HITCBC 1507   5641 ++cs; 1518   5641 ++cs;
HITCBC 1508   5641 u1_ += digit << 8; 1519   5641 u1_ += digit << 8;
HITCBC 1509   6030 do_str6: 1520   6030 do_str6:
HITCBC 1510   6030 if(BOOST_JSON_UNLIKELY(! cs)) 1521   6030 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1511   389 return maybe_suspend(cs.begin(), state::str6); 1522   389 return maybe_suspend(cs.begin(), state::str6);
HITCBC 1512   5641 digit = detail::hex_digit(*cs); 1523   5641 digit = detail::hex_digit(*cs);
HITCBC 1513   5641 if(BOOST_JSON_UNLIKELY(digit == -1)) 1524   5641 if(BOOST_JSON_UNLIKELY(digit == -1))
1514   { 1525   {
1515   BOOST_STATIC_CONSTEXPR source_location loc 1526   BOOST_STATIC_CONSTEXPR source_location loc
1516   = BOOST_CURRENT_LOCATION; 1527   = BOOST_CURRENT_LOCATION;
HITCBC 1517   20 return fail(cs.begin(), error::expected_hex_digit, &loc); 1528   20 return fail(cs.begin(), error::expected_hex_digit, &loc);
1518   } 1529   }
HITCBC 1519   5621 ++cs; 1530   5621 ++cs;
HITCBC 1520   5621 u1_ += digit << 4; 1531   5621 u1_ += digit << 4;
HITCBC 1521   6007 do_str7: 1532   6007 do_str7:
HITCBC 1522   6007 if(BOOST_JSON_UNLIKELY(! cs)) 1533   6007 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1523   386 return maybe_suspend(cs.begin(), state::str7); 1534   386 return maybe_suspend(cs.begin(), state::str7);
HITCBC 1524   5621 digit = detail::hex_digit(*cs); 1535   5621 digit = detail::hex_digit(*cs);
HITCBC 1525   5621 if(BOOST_JSON_UNLIKELY(digit == -1)) 1536   5621 if(BOOST_JSON_UNLIKELY(digit == -1))
1526   { 1537   {
1527   BOOST_STATIC_CONSTEXPR source_location loc 1538   BOOST_STATIC_CONSTEXPR source_location loc
1528   = BOOST_CURRENT_LOCATION; 1539   = BOOST_CURRENT_LOCATION;
HITCBC 1529   35 return fail(cs.begin(), error::expected_hex_digit, &loc); 1540   35 return fail(cs.begin(), error::expected_hex_digit, &loc);
1530   } 1541   }
HITCBC 1531   5586 ++cs; 1542   5586 ++cs;
HITCBC 1532   5586 u1_ += digit; 1543   5586 u1_ += digit;
HITCBC 1533   5586 if(BOOST_JSON_LIKELY( 1544   5586 if(BOOST_JSON_LIKELY(
1534   u1_ < 0xd800 || u1_ > 0xdfff)) 1545   u1_ < 0xd800 || u1_ > 0xdfff))
1535   { 1546   {
HITCBC 1536   1434 BOOST_ASSERT(temp.empty()); 1547   1434 BOOST_ASSERT(temp.empty());
1537   // utf-8 codepoint 1548   // utf-8 codepoint
HITCBC 1538   1434 temp.append_utf8(u1_); 1549   1434 temp.append_utf8(u1_);
HITCBC 1539   1434 break; 1550   1434 break;
1540   } 1551   }
HITCBC 1541   4152 if(BOOST_JSON_UNLIKELY(u1_ > 0xdbff)) 1552   4152 if(BOOST_JSON_UNLIKELY(u1_ > 0xdbff))
1542   { 1553   {
1543   // If it's an illegal leading surrogate and 1554   // If it's an illegal leading surrogate and
1544   // the parser does not allow it, return an error. 1555   // the parser does not allow it, return an error.
HITCBC 1545   1585 if(!allow_bad_utf16) 1556   1585 if(!allow_bad_utf16)
1546   { 1557   {
1547   BOOST_STATIC_CONSTEXPR source_location loc 1558   BOOST_STATIC_CONSTEXPR source_location loc
1548   = BOOST_CURRENT_LOCATION; 1559   = BOOST_CURRENT_LOCATION;
HITCBC 1549   209 return fail(cs.begin(), error::illegal_leading_surrogate, &loc); 1560   209 return fail(cs.begin(), error::illegal_leading_surrogate, &loc);
1550   } 1561   }
1551   // Otherwise, append the Unicode replacement character 1562   // Otherwise, append the Unicode replacement character
1552   else 1563   else
1553   { 1564   {
HITCBC 1554   1376 BOOST_ASSERT(temp.empty()); 1565   1376 BOOST_ASSERT(temp.empty());
HITCBC 1555   1376 temp.append_utf8(urc); 1566   1376 temp.append_utf8(urc);
HITCBC 1556   1376 break; 1567   1376 break;
1557   } 1568   }
1558   } 1569   }
HITCBC 1559   2567 do_sur1: 1570   2567 do_sur1:
HITCBC 1560   3792 if(BOOST_JSON_UNLIKELY(! cs)) 1571   3792 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1561   232 return maybe_suspend(cs.begin(), state::sur1); 1572   232 return maybe_suspend(cs.begin(), state::sur1);
HITCBC 1562   3560 if(BOOST_JSON_UNLIKELY(*cs != '\\')) 1573   3560 if(BOOST_JSON_UNLIKELY(*cs != '\\'))
1563   { 1574   {
1564   // If the next character is not a backslash and 1575   // If the next character is not a backslash and
1565   // the parser does not allow it, return a syntax error. 1576   // the parser does not allow it, return a syntax error.
HITCBC 1566   952 if(!allow_bad_utf16) 1577   952 if(!allow_bad_utf16)
1567   { 1578   {
1568   BOOST_STATIC_CONSTEXPR source_location loc 1579   BOOST_STATIC_CONSTEXPR source_location loc
1569   = BOOST_CURRENT_LOCATION; 1580   = BOOST_CURRENT_LOCATION;
HITCBC 1570   149 return fail(cs.begin(), error::syntax, &loc); 1581   149 return fail(cs.begin(), error::syntax, &loc);
1571   } 1582   }
1572   // Otherwise, append the Unicode replacement character since 1583   // Otherwise, append the Unicode replacement character since
1573   // the first code point is a valid leading surrogate 1584   // the first code point is a valid leading surrogate
1574   else 1585   else
1575   { 1586   {
HITCBC 1576   803 temp.append_utf8(urc); 1587   803 temp.append_utf8(urc);
HITCBC 1577   803 break; 1588   803 break;
1578   } 1589   }
1579   } 1590   }
HITCBC 1580   2608 ++cs; 1591   2608 ++cs;
HITCBC 1581   2796 do_sur2: 1592   2796 do_sur2:
HITCBC 1582   2796 if(BOOST_JSON_UNLIKELY(! cs)) 1593   2796 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1583   188 return maybe_suspend(cs.begin(), state::sur2); 1594   188 return maybe_suspend(cs.begin(), state::sur2);
HITCBC 1584   2608 if(BOOST_JSON_UNLIKELY(*cs != 'u')) 1595   2608 if(BOOST_JSON_UNLIKELY(*cs != 'u'))
1585   { 1596   {
HITCBC 1586   396 if (!allow_bad_utf16) 1597   396 if (!allow_bad_utf16)
1587   { 1598   {
1588   BOOST_STATIC_CONSTEXPR source_location loc 1599   BOOST_STATIC_CONSTEXPR source_location loc
1589   = BOOST_CURRENT_LOCATION; 1600   = BOOST_CURRENT_LOCATION;
HITCBC 1590   65 return fail(cs.begin(), error::syntax, &loc); 1601   65 return fail(cs.begin(), error::syntax, &loc);
1591   } 1602   }
1592   // Otherwise, append the Unicode replacement character since 1603   // Otherwise, append the Unicode replacement character since
1593   // the first code point is a valid leading surrogate 1604   // the first code point is a valid leading surrogate
1594   else 1605   else
1595   { 1606   {
HITCBC 1596   331 temp.append_utf8(urc); 1607   331 temp.append_utf8(urc);
HITCBC 1597   331 goto do_str3; 1608   331 goto do_str3;
1598   } 1609   }
1599   } 1610   }
HITCBC 1600   2212 ++cs; 1611   2212 ++cs;
HITCBC 1601   2376 do_sur3: 1612   2376 do_sur3:
HITCBC 1602   2376 if(BOOST_JSON_UNLIKELY(! cs)) 1613   2376 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1603   164 return maybe_suspend(cs.begin(), state::sur3); 1614   164 return maybe_suspend(cs.begin(), state::sur3);
HITCBC 1604   2212 digit = detail::hex_digit(*cs); 1615   2212 digit = detail::hex_digit(*cs);
HITCBC 1605   2212 if(BOOST_JSON_UNLIKELY(digit == -1)) 1616   2212 if(BOOST_JSON_UNLIKELY(digit == -1))
1606   { 1617   {
1607   BOOST_STATIC_CONSTEXPR source_location loc 1618   BOOST_STATIC_CONSTEXPR source_location loc
1608   = BOOST_CURRENT_LOCATION; 1619   = BOOST_CURRENT_LOCATION;
HITCBC 1609   35 return fail(cs.begin(), error::expected_hex_digit, &loc); 1620   35 return fail(cs.begin(), error::expected_hex_digit, &loc);
1610   } 1621   }
HITCBC 1611   2177 ++cs; 1622   2177 ++cs;
HITCBC 1612   2177 u2_ = digit << 12; 1623   2177 u2_ = digit << 12;
HITCBC 1613   2339 do_sur4: 1624   2339 do_sur4:
HITCBC 1614   2339 if(BOOST_JSON_UNLIKELY(! cs)) 1625   2339 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1615   162 return maybe_suspend(cs.begin(), state::sur4); 1626   162 return maybe_suspend(cs.begin(), state::sur4);
HITCBC 1616   2177 digit = detail::hex_digit(*cs); 1627   2177 digit = detail::hex_digit(*cs);
HITCBC 1617   2177 if(BOOST_JSON_UNLIKELY(digit == -1)) 1628   2177 if(BOOST_JSON_UNLIKELY(digit == -1))
1618   { 1629   {
1619   BOOST_STATIC_CONSTEXPR source_location loc 1630   BOOST_STATIC_CONSTEXPR source_location loc
1620   = BOOST_CURRENT_LOCATION; 1631   = BOOST_CURRENT_LOCATION;
HITCBC 1621   35 return fail(cs.begin(), error::expected_hex_digit, &loc); 1632   35 return fail(cs.begin(), error::expected_hex_digit, &loc);
1622   } 1633   }
HITCBC 1623   2142 ++cs; 1634   2142 ++cs;
HITCBC 1624   2142 u2_ += digit << 8; 1635   2142 u2_ += digit << 8;
HITCBC 1625   2302 do_sur5: 1636   2302 do_sur5:
HITCBC 1626   2302 if(BOOST_JSON_UNLIKELY(! cs)) 1637   2302 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1627   160 return maybe_suspend(cs.begin(), state::sur5); 1638   160 return maybe_suspend(cs.begin(), state::sur5);
HITCBC 1628   2142 digit = detail::hex_digit(*cs); 1639   2142 digit = detail::hex_digit(*cs);
HITCBC 1629   2142 if(BOOST_JSON_UNLIKELY(digit == -1)) 1640   2142 if(BOOST_JSON_UNLIKELY(digit == -1))
1630   { 1641   {
1631   BOOST_STATIC_CONSTEXPR source_location loc 1642   BOOST_STATIC_CONSTEXPR source_location loc
1632   = BOOST_CURRENT_LOCATION; 1643   = BOOST_CURRENT_LOCATION;
HITCBC 1633   20 return fail(cs.begin(), error::expected_hex_digit, &loc); 1644   20 return fail(cs.begin(), error::expected_hex_digit, &loc);
1634   } 1645   }
HITCBC 1635   2122 ++cs; 1646   2122 ++cs;
HITCBC 1636   2122 u2_ += digit << 4; 1647   2122 u2_ += digit << 4;
HITCBC 1637   2280 do_sur6: 1648   2280 do_sur6:
HITCBC 1638   2280 if(BOOST_JSON_UNLIKELY(! cs)) 1649   2280 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1639   158 return maybe_suspend(cs.begin(), state::sur6); 1650   158 return maybe_suspend(cs.begin(), state::sur6);
HITCBC 1640   2122 digit = detail::hex_digit(*cs); 1651   2122 digit = detail::hex_digit(*cs);
HITCBC 1641   2122 if(BOOST_JSON_UNLIKELY(digit == -1)) 1652   2122 if(BOOST_JSON_UNLIKELY(digit == -1))
1642   { 1653   {
1643   BOOST_STATIC_CONSTEXPR source_location loc 1654   BOOST_STATIC_CONSTEXPR source_location loc
1644   = BOOST_CURRENT_LOCATION; 1655   = BOOST_CURRENT_LOCATION;
HITCBC 1645   20 return fail(cs.begin(), error::expected_hex_digit, &loc); 1656   20 return fail(cs.begin(), error::expected_hex_digit, &loc);
1646   } 1657   }
HITCBC 1647   2102 ++cs; 1658   2102 ++cs;
HITCBC 1648   2102 u2_ += digit; 1659   2102 u2_ += digit;
1649   // Check if the second code point is a valid trailing surrogate. 1660   // Check if the second code point is a valid trailing surrogate.
1650   // Valid trailing surrogates are [DC00, DFFF] 1661   // Valid trailing surrogates are [DC00, DFFF]
HITCBC 1651   2102 if(BOOST_JSON_UNLIKELY( 1662   2102 if(BOOST_JSON_UNLIKELY(
1652   u2_ < 0xdc00 || u2_ > 0xdfff)) 1663   u2_ < 0xdc00 || u2_ > 0xdfff))
1653   { 1664   {
1654   // If not valid and the parser does not allow it, return an error. 1665   // If not valid and the parser does not allow it, return an error.
HITCBC 1655   580 if(!allow_bad_utf16) 1666   580 if(!allow_bad_utf16)
1656   { 1667   {
1657   BOOST_STATIC_CONSTEXPR source_location loc 1668   BOOST_STATIC_CONSTEXPR source_location loc
1658   = BOOST_CURRENT_LOCATION; 1669   = BOOST_CURRENT_LOCATION;
HITCBC 1659   60 return fail(cs.begin(), error::illegal_trailing_surrogate, &loc); 1670   60 return fail(cs.begin(), error::illegal_trailing_surrogate, &loc);
1660   } 1671   }
1661   // Append the replacement character for the 1672   // Append the replacement character for the
1662   // first leading surrogate. 1673   // first leading surrogate.
HITCBC 1663   520 temp.append_utf8(urc); 1674   520 temp.append_utf8(urc);
1664   // Check if the second code point is a 1675   // Check if the second code point is a
1665   // valid unicode scalar value (invalid leading 1676   // valid unicode scalar value (invalid leading
1666   // or trailing surrogate) 1677   // or trailing surrogate)
HITCBC 1667   520 if (u2_ < 0xd800 || u2_ > 0xdbff) 1678   520 if (u2_ < 0xd800 || u2_ > 0xdbff)
1668   { 1679   {
HITCBC 1669   220 temp.append_utf8(u2_); 1680   220 temp.append_utf8(u2_);
HITCBC 1670   220 break; 1681   220 break;
1671   } 1682   }
1672   // If it is a valid leading surrogate 1683   // If it is a valid leading surrogate
1673   else 1684   else
1674   { 1685   {
HITCBC 1675   300 u1_ = u2_; 1686   300 u1_ = u2_;
HITCBC 1676   300 goto do_sur1; 1687   300 goto do_sur1;
1677   } 1688   }
1678   } 1689   }
1679   // Calculate the Unicode code point from the surrogate pair and 1690   // Calculate the Unicode code point from the surrogate pair and
1680   // append the UTF-8 representation. 1691   // append the UTF-8 representation.
HITCBC 1681   1522 unsigned cp = 1692   1522 unsigned cp =
HITCBC 1682   1522 ((u1_ - 0xd800) << 10) + 1693   1522 ((u1_ - 0xd800) << 10) +
HITCBC 1683   1522 ((u2_ - 0xdc00)) + 1694   1522 ((u2_ - 0xdc00)) +
1684   0x10000; 1695   0x10000;
1685   // utf-16 surrogate pair 1696   // utf-16 surrogate pair
HITCBC 1686   1522 temp.append_utf8(cp); 1697   1522 temp.append_utf8(cp);
1687   } 1698   }
1688   1699  
1689   // flush 1700   // flush
HITCBC 1690   12650 if(BOOST_JSON_UNLIKELY( !cs ) || *cs != '\\') 1701   12650 if(BOOST_JSON_UNLIKELY( !cs ) || *cs != '\\')
HITCBC 1691   8869 break; 1702   8869 break;
1692   } 1703   }
1693   1704  
HITCBC 1694   8869 if(BOOST_JSON_LIKELY( temp.size() )) 1705   8869 if(BOOST_JSON_LIKELY( temp.size() ))
1695   { 1706   {
HITCBC 1696   433 BOOST_ASSERT(total <= max_size); 1707   433 BOOST_ASSERT(total <= max_size);
HITCBC 1697   8869 if(BOOST_JSON_UNLIKELY( temp.size() > max_size - total )) 1708   8869 if(BOOST_JSON_UNLIKELY( temp.size() > max_size - total ))
1698   { 1709   {
1699   BOOST_STATIC_CONSTEXPR source_location loc 1710   BOOST_STATIC_CONSTEXPR source_location loc
1700   = BOOST_CURRENT_LOCATION; 1711   = BOOST_CURRENT_LOCATION;
MISUBC 1701   ✗ return fail(cs.begin(), ev_too_large, &loc); 1712   ✗ return fail(cs.begin(), ev_too_large, &loc);
1702   } 1713   }
1703   1714  
HITCBC 1704   8869 total += temp.size(); 1715   8869 total += temp.size();
HITCBC 1705   8056 bool const r = is_key 1716   8056 bool const r = is_key
HITCBC 1706   8869 ? h_.on_key_part(temp.get(), total, ec_) 1717   8869 ? h_.on_key_part(temp.get(), total, ec_)
HITCBC 1707   8152 : h_.on_string_part(temp.get(), total, ec_); 1718   8152 : h_.on_string_part(temp.get(), total, ec_);
HITCBC 1708   8056 if(BOOST_JSON_UNLIKELY( !r )) 1719   8056 if(BOOST_JSON_UNLIKELY( !r ))
HITCBC 1709   813 return fail( cs.begin() ); 1720   813 return fail( cs.begin() );
1710   } 1721   }
1711   1722  
HITCBC 1712   7243 return cs.begin(); 1723   7243 return cs.begin();
1713   } 1724   }
1714   1725  
1715   //---------------------------------------------------------- 1726   //----------------------------------------------------------
1716   1727  
1717   template<class Handler> 1728   template<class Handler>
1718   template< 1729   template<
1719   bool StackEmpty_, 1730   bool StackEmpty_,
1720   bool AllowComments_/*, 1731   bool AllowComments_/*,
1721   bool AllowTrailing_, 1732   bool AllowTrailing_,
1722   bool AllowBadUTF8_*/> 1733   bool AllowBadUTF8_*/>
1723   const char* 1734   const char*
HITCBC 1724   109189 basic_parser<Handler>:: 1735   109189 basic_parser<Handler>::
1725   parse_object(const char* p, 1736   parse_object(const char* p,
1726   std::integral_constant<bool, StackEmpty_> stack_empty, 1737   std::integral_constant<bool, StackEmpty_> stack_empty,
1727   std::integral_constant<bool, AllowComments_> allow_comments, 1738   std::integral_constant<bool, AllowComments_> allow_comments,
1728   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing, 1739   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing,
1729   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8, 1740   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8,
1730   bool allow_bad_utf16) 1741   bool allow_bad_utf16)
1731   { 1742   {
HITCBC 1732   109189 detail::const_stream_wrapper cs(p, end_); 1743   109189 detail::const_stream_wrapper cs(p, end_);
1733   std::size_t size; 1744   std::size_t size;
HITCBC 1734   109189 if(! stack_empty && ! st_.empty()) 1745   109189 if(! stack_empty && ! st_.empty())
1735   { 1746   {
1736   // resume 1747   // resume
1737   state st; 1748   state st;
HITCBC 1738   35058 st_.pop(st); 1749   35058 st_.pop(st);
HITCBC 1739   35058 st_.pop(size); 1750   35058 st_.pop(size);
HITCBC 1740   35058 switch(st) 1751   35058 switch(st)
1741   { 1752   {
MISUBC 1742   ✗ default: BOOST_JSON_UNREACHABLE(); 1753   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 1743   1595 case state::obj1: goto do_obj1; 1754   1595 case state::obj1: goto do_obj1;
HITCBC 1744   235 case state::obj2: goto do_obj2; 1755   235 case state::obj2: goto do_obj2;
HITCBC 1745   12647 case state::obj3: goto do_obj3; 1756   12647 case state::obj3: goto do_obj3;
HITCBC 1746   1690 case state::obj4: goto do_obj4; 1757   1690 case state::obj4: goto do_obj4;
HITCBC 1747   251 case state::obj5: goto do_obj5; 1758   251 case state::obj5: goto do_obj5;
HITCBC 1748   1591 case state::obj6: goto do_obj6; 1759   1591 case state::obj6: goto do_obj6;
HITCBC 1749   15448 case state::obj7: goto do_obj7; 1760   15448 case state::obj7: goto do_obj7;
HITCBC 1750   426 case state::obj8: goto do_obj8; 1761   426 case state::obj8: goto do_obj8;
HITCBC 1751   660 case state::obj9: goto do_obj9; 1762   660 case state::obj9: goto do_obj9;
HITCBC 1752   181 case state::obj10: goto do_obj10; 1763   181 case state::obj10: goto do_obj10;
HITCBC 1753   334 case state::obj11: goto do_obj11; 1764   334 case state::obj11: goto do_obj11;
1754   } 1765   }
1755   } 1766   }
HITCBC 1756   74131 BOOST_ASSERT(*cs == '{'); 1767   74131 BOOST_ASSERT(*cs == '{');
HITCBC 1757   74131 size = 0; 1768   74131 size = 0;
HITCBC 1758   74131 if(BOOST_JSON_UNLIKELY(! depth_)) 1769   74131 if(BOOST_JSON_UNLIKELY(! depth_))
1759   { 1770   {
1760   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 1771   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 1761   3 return fail(cs.begin(), error::too_deep, &loc); 1772   3 return fail(cs.begin(), error::too_deep, &loc);
1762   } 1773   }
HITCBC 1763   74128 --depth_; 1774   74128 --depth_;
HITCBC 1764   74128 if(BOOST_JSON_UNLIKELY( 1775   74128 if(BOOST_JSON_UNLIKELY(
1765   ! h_.on_object_begin(ec_))) 1776   ! h_.on_object_begin(ec_)))
HITCBC 1766   2040 return fail(cs.begin()); 1777   2040 return fail(cs.begin());
HITCBC 1767   70050 ++cs; 1778   70050 ++cs;
1768   // object: 1779   // object:
1769   // '{' *ws '}' 1780   // '{' *ws '}'
1770   // '{' *ws string *ws ':' *ws value *ws *[ ',' *ws string *ws ':' *ws value *ws ] '}' 1781   // '{' *ws string *ws ':' *ws value *ws *[ ',' *ws string *ws ':' *ws value *ws ] '}'
HITCBC 1771   73616 do_obj1: 1782   73616 do_obj1:
HITCBC 1772   73616 cs = detail::count_whitespace(cs.begin(), cs.end()); 1783   73616 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1773   73616 if(BOOST_JSON_UNLIKELY(! cs)) 1784   73616 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1774   1629 return maybe_suspend(cs.begin(), state::obj1, size); 1785   1629 return maybe_suspend(cs.begin(), state::obj1, size);
HITCBC 1775   71987 if(BOOST_JSON_LIKELY(*cs != '}')) 1786   71987 if(BOOST_JSON_LIKELY(*cs != '}'))
1776   { 1787   {
HITCBC 1777   69088 if(BOOST_JSON_UNLIKELY(*cs != '\x22')) 1788   69088 if(BOOST_JSON_UNLIKELY(*cs != '\x22'))
1778   { 1789   {
HITCBC 1779   2411 if(allow_comments && *cs == '/') 1790   2411 if(allow_comments && *cs == '/')
1780   { 1791   {
HITCBC 1781   2139 do_obj2: 1792   2139 do_obj2:
HITCBC 1782   2374 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1793   2374 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1783   2290 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1794   2290 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1784   319 return suspend_or_fail(state::obj2, size); 1795   319 return suspend_or_fail(state::obj2, size);
HITCBC 1785   1971 goto do_obj1; 1796   1971 goto do_obj1;
1786   } 1797   }
1787   BOOST_STATIC_CONSTEXPR source_location loc 1798   BOOST_STATIC_CONSTEXPR source_location loc
1788   = BOOST_CURRENT_LOCATION; 1799   = BOOST_CURRENT_LOCATION;
HITCBC 1789   272 return fail(cs.begin(), error::syntax, &loc); 1800   272 return fail(cs.begin(), error::syntax, &loc);
1790   } 1801   }
HITCBC 1791   66677 loop: 1802   66677 loop:
HITCBC 1792   80829 if(BOOST_JSON_UNLIKELY(++size > 1803   80829 if(BOOST_JSON_UNLIKELY(++size >
1793   Handler::max_object_size)) 1804   Handler::max_object_size))
1794   { 1805   {
1795   BOOST_STATIC_CONSTEXPR source_location loc 1806   BOOST_STATIC_CONSTEXPR source_location loc
1796   = BOOST_CURRENT_LOCATION; 1807   = BOOST_CURRENT_LOCATION;
HITCBC 1797   1 return fail(cs.begin(), error::object_too_large, &loc); 1808   1 return fail(cs.begin(), error::object_too_large, &loc);
1798   } 1809   }
HITCBC 1799   80828 do_obj3: 1810   80828 do_obj3:
HITCBC 1800   93475 cs = parse_string(cs.begin(), stack_empty, std::true_type(), allow_bad_utf8, allow_bad_utf16); 1811   93475 cs = parse_string(cs.begin(), stack_empty, std::true_type(), allow_bad_utf8, allow_bad_utf16);
HITCBC 1801   90519 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1812   90519 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1802   15592 return suspend_or_fail(state::obj3, size); 1813   15592 return suspend_or_fail(state::obj3, size);
HITCBC 1803   74927 do_obj4: 1814   74927 do_obj4:
HITCBC 1804   79088 cs = detail::count_whitespace(cs.begin(), cs.end()); 1815   79088 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1805   79088 if(BOOST_JSON_UNLIKELY(! cs)) 1816   79088 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1806   1705 return maybe_suspend(cs.begin(), state::obj4, size); 1817   1705 return maybe_suspend(cs.begin(), state::obj4, size);
HITCBC 1807   77383 if(BOOST_JSON_UNLIKELY(*cs != ':')) 1818   77383 if(BOOST_JSON_UNLIKELY(*cs != ':'))
1808   { 1819   {
HITCBC 1809   2925 if(allow_comments && *cs == '/') 1820   2925 if(allow_comments && *cs == '/')
1810   { 1821   {
HITCBC 1811   2779 do_obj5: 1822   2779 do_obj5:
HITCBC 1812   3030 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1823   3030 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1813   2876 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1824   2876 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1814   405 return suspend_or_fail(state::obj5, size); 1825   405 return suspend_or_fail(state::obj5, size);
HITCBC 1815   2471 goto do_obj4; 1826   2471 goto do_obj4;
1816   } 1827   }
1817   BOOST_STATIC_CONSTEXPR source_location loc 1828   BOOST_STATIC_CONSTEXPR source_location loc
1818   = BOOST_CURRENT_LOCATION; 1829   = BOOST_CURRENT_LOCATION;
HITCBC 1819   146 return fail(cs.begin(), error::syntax, &loc); 1830   146 return fail(cs.begin(), error::syntax, &loc);
1820   } 1831   }
HITCBC 1821   74458 ++cs; 1832   74458 ++cs;
HITCBC 1822   76049 do_obj6: 1833   76049 do_obj6:
HITCBC 1823   76049 cs = detail::count_whitespace(cs.begin(), cs.end()); 1834   76049 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1824   76049 if(BOOST_JSON_UNLIKELY(! cs)) 1835   76049 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1825   1622 return maybe_suspend(cs.begin(), state::obj6, size); 1836   1622 return maybe_suspend(cs.begin(), state::obj6, size);
HITCBC 1826   74427 do_obj7: 1837   74427 do_obj7:
HITCBC 1827   89875 cs = parse_value(cs.begin(), stack_empty, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 1838   89875 cs = parse_value(cs.begin(), stack_empty, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
HITCBC 1828   82526 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1839   82526 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1829   23593 return suspend_or_fail(state::obj7, size); 1840   23593 return suspend_or_fail(state::obj7, size);
HITCBC 1830   58933 do_obj8: 1841   58933 do_obj8:
HITCBC 1831   61195 cs = detail::count_whitespace(cs.begin(), cs.end()); 1842   61195 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1832   61195 if(BOOST_JSON_UNLIKELY(! cs)) 1843   61195 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1833   441 return maybe_suspend(cs.begin(), state::obj8, size); 1844   441 return maybe_suspend(cs.begin(), state::obj8, size);
HITCBC 1834   60754 if(BOOST_JSON_LIKELY(*cs == ',')) 1845   60754 if(BOOST_JSON_LIKELY(*cs == ','))
1835   { 1846   {
HITCBC 1836   17792 ++cs; 1847   17792 ++cs;
HITCBC 1837   19707 do_obj9: 1848   19707 do_obj9:
HITCBC 1838   19707 cs = detail::count_whitespace(cs.begin(), cs.end()); 1849   19707 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1839   19707 if(BOOST_JSON_UNLIKELY(! cs)) 1850   19707 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1840   690 return maybe_suspend(cs.begin(), state::obj9, size); 1851   690 return maybe_suspend(cs.begin(), state::obj9, size);
1841   1852  
1842   // loop for next element 1853   // loop for next element
HITCBC 1843   19017 if(BOOST_JSON_LIKELY(*cs == '\x22')) 1854   19017 if(BOOST_JSON_LIKELY(*cs == '\x22'))
HITCBC 1844   14152 goto loop; 1855   14152 goto loop;
HITCBC 1845   4865 if(! allow_trailing || *cs != '}') 1856   4865 if(! allow_trailing || *cs != '}')
1846   { 1857   {
HITCBC 1847   1644 if(allow_comments && *cs == '/') 1858   1644 if(allow_comments && *cs == '/')
1848   { 1859   {
HITCBC 1849   1433 do_obj10: 1860   1433 do_obj10:
HITCBC 1850   1614 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1861   1614 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1851   1525 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1862   1525 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1852   270 return suspend_or_fail(state::obj10, size); 1863   270 return suspend_or_fail(state::obj10, size);
HITCBC 1853   1255 goto do_obj9; 1864   1255 goto do_obj9;
1854   } 1865   }
1855   BOOST_STATIC_CONSTEXPR source_location loc 1866   BOOST_STATIC_CONSTEXPR source_location loc
1856   = BOOST_CURRENT_LOCATION; 1867   = BOOST_CURRENT_LOCATION;
HITCBC 1857   211 return fail(cs.begin(), error::syntax, &loc); 1868   211 return fail(cs.begin(), error::syntax, &loc);
1858   } 1869   }
1859   } 1870   }
HITCBC 1860   42962 else if(BOOST_JSON_UNLIKELY(*cs != '}')) 1871   42962 else if(BOOST_JSON_UNLIKELY(*cs != '}'))
1861   { 1872   {
HITCBC 1862   2325 if(allow_comments && *cs == '/') 1873   2325 if(allow_comments && *cs == '/')
1863   { 1874   {
HITCBC 1864   2172 do_obj11: 1875   2172 do_obj11:
HITCBC 1865   2506 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1876   2506 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1866   2338 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1877   2338 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1867   502 return suspend_or_fail(state::obj11, size); 1878   502 return suspend_or_fail(state::obj11, size);
HITCBC 1868   1836 goto do_obj8; 1879   1836 goto do_obj8;
1869   } 1880   }
1870   BOOST_STATIC_CONSTEXPR source_location loc 1881   BOOST_STATIC_CONSTEXPR source_location loc
1871   = BOOST_CURRENT_LOCATION; 1882   = BOOST_CURRENT_LOCATION;
HITCBC 1872   153 return fail(cs.begin(), error::syntax, &loc); 1883   153 return fail(cs.begin(), error::syntax, &loc);
1873   } 1884   }
1874   // got closing brace, fall through 1885   // got closing brace, fall through
1875   } 1886   }
HITCBC 1876   46757 if(BOOST_JSON_UNLIKELY( 1887   46757 if(BOOST_JSON_UNLIKELY(
1877   ! h_.on_object_end(size, ec_))) 1888   ! h_.on_object_end(size, ec_)))
HITCBC 1878   1502 return fail(cs.begin()); 1889   1502 return fail(cs.begin());
HITCBC 1879   43714 ++depth_; 1890   43714 ++depth_;
HITCBC 1880   43714 ++cs; 1891   43714 ++cs;
HITCBC 1881   43714 return cs.begin(); 1892   43714 return cs.begin();
1882   } 1893   }
1883   1894  
1884   //---------------------------------------------------------- 1895   //----------------------------------------------------------
1885   1896  
1886   template<class Handler> 1897   template<class Handler>
1887   template< 1898   template<
1888   bool StackEmpty_, 1899   bool StackEmpty_,
1889   bool AllowComments_/*, 1900   bool AllowComments_/*,
1890   bool AllowTrailing_, 1901   bool AllowTrailing_,
1891   bool AllowBadUTF8_*/> 1902   bool AllowBadUTF8_*/>
1892   const char* 1903   const char*
HITCBC 1893   26348 basic_parser<Handler>:: 1904   26348 basic_parser<Handler>::
1894   parse_array(const char* p, 1905   parse_array(const char* p,
1895   std::integral_constant<bool, StackEmpty_> stack_empty, 1906   std::integral_constant<bool, StackEmpty_> stack_empty,
1896   std::integral_constant<bool, AllowComments_> allow_comments, 1907   std::integral_constant<bool, AllowComments_> allow_comments,
1897   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing, 1908   /*std::integral_constant<bool, AllowTrailing_>*/ bool allow_trailing,
1898   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8, 1909   /*std::integral_constant<bool, AllowBadUTF8_>*/ bool allow_bad_utf8,
1899   bool allow_bad_utf16) 1910   bool allow_bad_utf16)
1900   { 1911   {
HITCBC 1901   26348 detail::const_stream_wrapper cs(p, end_); 1912   26348 detail::const_stream_wrapper cs(p, end_);
1902   std::size_t size; 1913   std::size_t size;
HITCBC 1903   26348 if(! stack_empty && ! st_.empty()) 1914   26348 if(! stack_empty && ! st_.empty())
1904   { 1915   {
1905   // resume 1916   // resume
1906   state st; 1917   state st;
HITCBC 1907   5730 st_.pop(st); 1918   5730 st_.pop(st);
HITCBC 1908   5730 st_.pop(size); 1919   5730 st_.pop(size);
HITCBC 1909   5730 switch(st) 1920   5730 switch(st)
1910   { 1921   {
MISUBC 1911   ✗ default: BOOST_JSON_UNREACHABLE(); 1922   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 1912   1052 case state::arr1: goto do_arr1; 1923   1052 case state::arr1: goto do_arr1;
HITCBC 1913   384 case state::arr2: goto do_arr2; 1924   384 case state::arr2: goto do_arr2;
HITCBC 1914   2938 case state::arr3: goto do_arr3; 1925   2938 case state::arr3: goto do_arr3;
HITCBC 1915   391 case state::arr4: goto do_arr4; 1926   391 case state::arr4: goto do_arr4;
HITCBC 1916   671 case state::arr5: goto do_arr5; 1927   671 case state::arr5: goto do_arr5;
HITCBC 1917   294 case state::arr6: goto do_arr6; 1928   294 case state::arr6: goto do_arr6;
1918   } 1929   }
1919   } 1930   }
HITCBC 1920   20618 BOOST_ASSERT(*cs == '['); 1931   20618 BOOST_ASSERT(*cs == '[');
HITCBC 1921   20618 size = 0; 1932   20618 size = 0;
HITCBC 1922   20618 if(BOOST_JSON_UNLIKELY(! depth_)) 1933   20618 if(BOOST_JSON_UNLIKELY(! depth_))
1923   { 1934   {
1924   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION; 1935   BOOST_STATIC_CONSTEXPR source_location loc = BOOST_CURRENT_LOCATION;
HITCBC 1925   34 return fail(cs.begin(), error::too_deep, &loc); 1936   34 return fail(cs.begin(), error::too_deep, &loc);
1926   } 1937   }
HITCBC 1927   20584 --depth_; 1938   20584 --depth_;
HITCBC 1928   20584 if(BOOST_JSON_UNLIKELY( 1939   20584 if(BOOST_JSON_UNLIKELY(
1929   ! h_.on_array_begin(ec_))) 1940   ! h_.on_array_begin(ec_)))
HITCBC 1930   812 return fail(cs.begin()); 1941   812 return fail(cs.begin());
HITCBC 1931   18966 ++cs; 1942   18966 ++cs;
1932   // array: 1943   // array:
1933   // '[' *ws ']' 1944   // '[' *ws ']'
1934   // '[' *ws value *ws *[ ',' *ws value *ws ] ']' 1945   // '[' *ws value *ws *[ ',' *ws value *ws ] ']'
HITCBC 1935   21551 do_arr1: 1946   21551 do_arr1:
HITCBC 1936   21551 cs = detail::count_whitespace(cs.begin(), cs.end()); 1947   21551 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1937   21551 if(BOOST_JSON_UNLIKELY(! cs)) 1948   21551 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1938   1073 return maybe_suspend(cs.begin(), state::arr1, size); 1949   1073 return maybe_suspend(cs.begin(), state::arr1, size);
HITCBC 1939   20478 if(BOOST_JSON_LIKELY(*cs != ']')) 1950   20478 if(BOOST_JSON_LIKELY(*cs != ']'))
1940   { 1951   {
HITCBC 1941   18730 loop: 1952   18730 loop:
HITCBC 1942   26193 if(allow_comments && *cs == '/') 1953   26193 if(allow_comments && *cs == '/')
1943   { 1954   {
HITCBC 1944   1789 do_arr2: 1955   1789 do_arr2:
HITCBC 1945   2173 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1956   2173 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1946   2045 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1957   2045 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1947   512 return suspend_or_fail(state::arr2, size); 1958   512 return suspend_or_fail(state::arr2, size);
HITCBC 1948   1533 goto do_arr1; 1959   1533 goto do_arr1;
1949   } 1960   }
HITCBC 1950   24404 if(BOOST_JSON_UNLIKELY(++size > 1961   24404 if(BOOST_JSON_UNLIKELY(++size >
1951   Handler::max_array_size)) 1962   Handler::max_array_size))
1952   { 1963   {
1953   BOOST_STATIC_CONSTEXPR source_location loc 1964   BOOST_STATIC_CONSTEXPR source_location loc
1954   = BOOST_CURRENT_LOCATION; 1965   = BOOST_CURRENT_LOCATION;
HITCBC 1955   1 return fail(cs.begin(), error::array_too_large, &loc); 1966   1 return fail(cs.begin(), error::array_too_large, &loc);
1956   } 1967   }
HITCBC 1957   24403 do_arr3: 1968   24403 do_arr3:
1958   // array is not empty, value required 1969   // array is not empty, value required
HITCBC 1959   27341 cs = parse_value(cs.begin(), stack_empty, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16); 1970   27341 cs = parse_value(cs.begin(), stack_empty, allow_comments, allow_trailing, allow_bad_utf8, allow_bad_utf16);
HITCBC 1960   24710 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1971   24710 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1961   9052 return suspend_or_fail(state::arr3, size); 1972   9052 return suspend_or_fail(state::arr3, size);
HITCBC 1962   15658 do_arr4: 1973   15658 do_arr4:
HITCBC 1963   17279 cs = detail::count_whitespace(cs.begin(), cs.end()); 1974   17279 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1964   17279 if(BOOST_JSON_UNLIKELY(! cs)) 1975   17279 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1965   500 return maybe_suspend(cs.begin(), state::arr4, size); 1976   500 return maybe_suspend(cs.begin(), state::arr4, size);
HITCBC 1966   16779 if(BOOST_JSON_LIKELY(*cs == ',')) 1977   16779 if(BOOST_JSON_LIKELY(*cs == ','))
1967   { 1978   {
HITCBC 1968   9176 ++cs; 1979   9176 ++cs;
HITCBC 1969   9847 do_arr5: 1980   9847 do_arr5:
HITCBC 1970   9847 cs = detail::count_whitespace(cs.begin(), cs.end()); 1981   9847 cs = detail::count_whitespace(cs.begin(), cs.end());
HITCBC 1971   9847 if(BOOST_JSON_UNLIKELY(! cs)) 1982   9847 if(BOOST_JSON_UNLIKELY(! cs))
HITCBC 1972   701 return maybe_suspend(cs.begin(), state::arr5, size); 1983   701 return maybe_suspend(cs.begin(), state::arr5, size);
1973   // loop for next element 1984   // loop for next element
HITCBC 1974   9146 if(! allow_trailing || *cs != ']') 1985   9146 if(! allow_trailing || *cs != ']')
HITCBC 1975   7463 goto loop; 1986   7463 goto loop;
1976   } 1987   }
HITCBC 1977   7603 else if(BOOST_JSON_UNLIKELY(*cs != ']')) 1988   7603 else if(BOOST_JSON_UNLIKELY(*cs != ']'))
1978   { 1989   {
HITCBC 1979   1969 if(allow_comments && *cs == '/') 1990   1969 if(allow_comments && *cs == '/')
1980   { 1991   {
HITCBC 1981   1541 do_arr6: 1992   1541 do_arr6:
HITCBC 1982   1835 cs = parse_comment(cs.begin(), stack_empty, std::false_type()); 1993   1835 cs = parse_comment(cs.begin(), stack_empty, std::false_type());
HITCBC 1983   1688 if(BOOST_JSON_UNLIKELY(incomplete(cs))) 1994   1688 if(BOOST_JSON_UNLIKELY(incomplete(cs)))
HITCBC 1984   458 return suspend_or_fail(state::arr6, size); 1995   458 return suspend_or_fail(state::arr6, size);
HITCBC 1985   1230 goto do_arr4; 1996   1230 goto do_arr4;
1986   } 1997   }
1987   BOOST_STATIC_CONSTEXPR source_location loc 1998   BOOST_STATIC_CONSTEXPR source_location loc
1988   = BOOST_CURRENT_LOCATION; 1999   = BOOST_CURRENT_LOCATION;
HITCBC 1989   428 return fail(cs.begin(), error::syntax, &loc); 2000   428 return fail(cs.begin(), error::syntax, &loc);
1990   } 2001   }
1991   // got closing bracket; fall through 2002   // got closing bracket; fall through
1992   } 2003   }
HITCBC 1993   9065 if(BOOST_JSON_UNLIKELY( 2004   9065 if(BOOST_JSON_UNLIKELY(
1994   ! h_.on_array_end(size, ec_))) 2005   ! h_.on_array_end(size, ec_)))
HITCBC 1995   547 return fail(cs.begin()); 2006   547 return fail(cs.begin());
HITCBC 1996   7939 ++depth_; 2007   7939 ++depth_;
HITCBC 1997   7939 ++cs; 2008   7939 ++cs;
HITCBC 1998   7939 return cs.begin(); 2009   7939 return cs.begin();
1999   } 2010   }
2000   2011  
2001   //---------------------------------------------------------- 2012   //----------------------------------------------------------
2002   2013  
2003   template<class Handler> 2014   template<class Handler>
2004   template<bool StackEmpty_, char First_, number_precision Numbers_> 2015   template<bool StackEmpty_, char First_, number_precision Numbers_>
2005 - const char* 2016 + char const*
HITCBC 2006 - 2126888 basic_parser<Handler>:: 2017 + 2110611 basic_parser<Handler>::parse_number(
2007 - parse_number(const char* p, 2018 + char const* p,
2008   std::integral_constant<bool, StackEmpty_> stack_empty, 2019   std::integral_constant<bool, StackEmpty_> stack_empty,
2009   std::integral_constant<char, First_> first, 2020   std::integral_constant<char, First_> first,
2010   std::integral_constant<number_precision, Numbers_> mode) 2021   std::integral_constant<number_precision, Numbers_> mode)
2011   { 2022   {
  2023 + BOOST_CORE_STATIC_ASSERT(Numbers_ != number_precision::none);
DCB 2012 - 2126888 constexpr bool no_parsing = mode == number_precision::none;  
HITCBC 2013   2126888 constexpr bool precise_parsing = mode == number_precision::precise; 2024   2110611 constexpr bool precise_parsing = mode == number_precision::precise;
2014   2025  
2015   // only one of these will be true if we are not resuming 2026   // only one of these will be true if we are not resuming
2016   // if negative then !zero_first && !nonzero_first 2027   // if negative then !zero_first && !nonzero_first
2017   // if zero_first then !nonzero_first && !negative 2028   // if zero_first then !nonzero_first && !negative
2018   // if nonzero_first then !zero_first && !negative 2029   // if nonzero_first then !zero_first && !negative
HITCBC 2019   2126888 bool const negative = first == '-'; 2030   2110611 bool const negative = first == '-';
HITCBC 2020   2126888 bool const zero_first = first == '0'; 2031   2110611 bool const zero_first = first == '0';
HITCBC 2021   2126888 bool const nonzero_first = first == '+'; 2032   2110611 bool const nonzero_first = first == '+';
HITCBC 2022   2126888 detail::const_stream_wrapper cs(p, end_); 2033   2110611 detail::const_stream_wrapper cs(p, end_);
2023   number num; 2034   number num;
HITCBC 2024   2126888 const char* begin = cs.begin(); 2035   2110611 const char* begin = cs.begin();
HITCBC 2025   2126888 if(stack_empty || st_.empty()) 2036   2110611 if(stack_empty || st_.empty())
2026   { 2037   {
HITCBC 2027   2089697 num.bias = 0; 2038   2080439 num.bias = 0;
HITCBC 2028   2089697 num.exp = 0; 2039   2080439 num.exp = 0;
HITCBC 2029   2089697 num.frac = false; 2040   2080439 num.frac = false;
HITCBC 2030   2089697 num_buf_.clear(); 2041   2080439 num_buf_.clear();
2031   2042  
2032   //---------------------------------- 2043   //----------------------------------
2033   // 2044   //
2034   // '-' 2045   // '-'
2035   // leading minus sign 2046   // leading minus sign
2036   // 2047   //
HITCBC 2037   2089697 BOOST_ASSERT(cs); 2048   2080439 BOOST_ASSERT(cs);
2038   if(negative) 2049   if(negative)
HITCBC 2039   25178 ++cs; 2050   21280 ++cs;
2040   2051  
HITCBC 2041   2089697 num.neg = negative; 2052   2080439 num.neg = negative;
HITCBC 2042   2089697 num.frac = false; 2053   2080439 num.frac = false;
HITCBC 2043   2089697 num.exp = 0; 2054   2080439 num.exp = 0;
HITCBC 2044   2089697 num.bias = 0; 2055   2080439 num.bias = 0;
2045   2056  
2046   // fast path 2057   // fast path
HITCBC 2047   2089697 if( cs.remain() >= 16 + 1 + 16 ) // digits . digits 2058   2080439 if( cs.remain() >= 16 + 1 + 16 ) // digits . digits
2048   { 2059   {
2049   int n1; 2060   int n1;
2050   2061  
HITCBC 2051   9989 if( nonzero_first || 2062   7569 if( nonzero_first ||
HITCBC 2052   9989 (negative && *cs != '0') ) 2063   7569 (negative && *cs != '0') )
2053   { 2064   {
HITCBC 2054   2007318 n1 = detail::count_digits( cs.begin() ); 2065   2006470 n1 = detail::count_digits( cs.begin() );
HITCBC 2055   2007318 BOOST_ASSERT(n1 >= 0 && n1 <= 16); 2066   2006470 BOOST_ASSERT(n1 >= 0 && n1 <= 16);
2056   2067  
HITCBC 2057   1837 if( negative && n1 == 0 && opt_.allow_infinity_and_nan ) 2068   1450 if( negative && n1 == 0 && opt_.allow_infinity_and_nan )
2058   { 2069   {
HITCBC 2059   9 return parse_literal( 2070   9 return parse_literal(
2060   p - 1, 2071   p - 1,
HITCBC 2061   8 detail::literals_c<detail::literals::neg_infinity>()); 2072   8 detail::literals_c<detail::literals::neg_infinity>());
2062   } 2073   }
2063   2074  
HITCBC 2064   1828 if( ! nonzero_first && n1 == 0 ) 2075   1441 if( ! nonzero_first && n1 == 0 )
2065   { 2076   {
2066   // digit required 2077   // digit required
2067   BOOST_STATIC_CONSTEXPR source_location loc 2078   BOOST_STATIC_CONSTEXPR source_location loc
2068   = BOOST_CURRENT_LOCATION; 2079   = BOOST_CURRENT_LOCATION;
HITCBC 2069   2 return fail(cs.begin(), error::syntax, &loc); 2080   2 return fail(cs.begin(), error::syntax, &loc);
2070   } 2081   }
2071   2082  
HITGIC 2072 - BOOST_IF_CONSTEXPR( !no_parsing ) 2083 + 2006459 num.mant = detail::parse_unsigned( 0, cs.begin(), n1 );
DCB 2073 - 2006459 num.mant = detail::parse_unsigned( 0, cs.begin(), n1 );  
2074 - else  
DCB 2075 - 848 num.mant = 0;  
2076 -  
HITCBC 2077   2007307 cs += n1; 2084   2006459 cs += n1;
2078   2085  
2079   // integer or floating-point with 2086   // integer or floating-point with
2080   // >= 16 leading digits 2087   // >= 16 leading digits
HITCBC 2081   2007307 if( n1 == 16 ) 2088   2006459 if( n1 == 16 )
2082   { 2089   {
HITCBC 2083   2001424 goto do_num2; 2090   2001197 goto do_num2;
2084   } 2091   }
2085   } 2092   }
2086   else 2093   else
2087   { 2094   {
2088   // 0. floating-point or 0e integer 2095   // 0. floating-point or 0e integer
HITCBC 2089   21187 num.mant = 0; 2096   15960 num.mant = 0;
HITCBC 2090   21187 n1 = 0; 2097   15960 n1 = 0;
HITCBC 2091   21187 ++cs; 2098   15960 ++cs;
2092   } 2099   }
2093   2100  
2094   { 2101   {
HITCBC 2095   27070 const char c = *cs; 2102   21222 const char c = *cs;
HITCBC 2096   27070 if(c != '.') 2103   21222 if(c != '.')
2097   { 2104   {
HITCBC 2098   9871 if((c | 32) == 'e') 2105   8242 if((c | 32) == 'e')
2099   { 2106   {
HITCBC 2100   6576 ++cs; 2107   4947 ++cs;
HITCBC 2101   6576 goto do_exp1; 2108   4947 goto do_exp1;
2102   } 2109   }
2103 - BOOST_IF_CONSTEXPR( negative && !no_parsing ) 2110 + BOOST_IF_CONSTEXPR( negative )
HITCBC 2104   20 num.mant = ~num.mant + 1; 2111   20 num.mant = ~num.mant + 1;
HITCBC 2105   3295 goto finish_signed; 2112   3295 goto finish_signed;
2106   } 2113   }
2107   } 2114   }
2108   2115  
2109   // floating-point number 2116   // floating-point number
2110   2117  
HITCBC 2111   17199 ++cs; 2118   12980 ++cs;
2112   2119  
HITCBC 2113   17199 int n2 = detail::count_digits( cs.begin() ); 2120   12980 int n2 = detail::count_digits( cs.begin() );
HITCBC 2114   17199 BOOST_ASSERT(n2 >= 0 && n2 <= 16); 2121   12980 BOOST_ASSERT(n2 >= 0 && n2 <= 16);
2115   2122  
HITCBC 2116   17199 if( n2 == 0 ) 2123   12980 if( n2 == 0 )
2117   { 2124   {
2118   // digit required 2125   // digit required
2119   BOOST_STATIC_CONSTEXPR source_location loc 2126   BOOST_STATIC_CONSTEXPR source_location loc
2120   = BOOST_CURRENT_LOCATION; 2127   = BOOST_CURRENT_LOCATION;
HITCBC 2121   3 return fail(cs.begin(), error::syntax, &loc); 2128   3 return fail(cs.begin(), error::syntax, &loc);
2122   } 2129   }
2123   2130  
2124   // floating-point mantissa overflow 2131   // floating-point mantissa overflow
HITCBC 2125   17196 if( n1 + n2 >= 19 ) 2132   12977 if( n1 + n2 >= 19 )
2126   { 2133   {
HITCBC 2127   122 goto do_num7; 2134   122 goto do_num7;
2128   } 2135   }
2129   2136  
HITGIC 2130 - BOOST_IF_CONSTEXPR( !no_parsing ) 2137 + 12855 num.mant = detail::parse_unsigned( num.mant, cs.begin(), n2 );
DCB 2131 - 12855 num.mant = detail::parse_unsigned( num.mant, cs.begin(), n2 );  
2132 -  
DCB 2133 - 17074  
HITGIC 2134   BOOST_ASSERT(num.bias == 0); 2138   12855 BOOST_ASSERT(num.bias == 0);
HITCBC 2135   17074 num.bias -= n2; 2139   12855 num.bias -= n2;
2136   2140  
HITCBC 2137   17074 cs += n2; 2141   12855 cs += n2;
2138   2142  
HITCBC 2139   17074 char ch = *cs; 2143   12855 char ch = *cs;
2140   2144  
HITCBC 2141   17074 if( (ch | 32) == 'e' ) 2145   12855 if( (ch | 32) == 'e' )
2142   { 2146   {
HITCBC 2143   110 ++cs; 2147   110 ++cs;
HITCBC 2144   110 goto do_exp1; 2148   110 goto do_exp1;
2145   } 2149   }
HITCBC 2146   16964 else if( ch >= '0' && ch <= '9' ) 2150   12745 else if( ch >= '0' && ch <= '9' )
2147   { 2151   {
HITCBC 2148   10017 goto do_num8; 2152   7517 goto do_num8;
2149   } 2153   }
2150   2154  
HITCBC 2151   6947 goto finish_dub; 2155   5228 goto finish_dub;
2152   } 2156   }
2153   } 2157   }
2154   else 2158   else
2155   { 2159   {
HITCBC 2156   37191 num = num_; 2160   30172 num = num_;
2157   state st; 2161   state st;
HITCBC 2158   37191 st_.pop(st); 2162   30172 st_.pop(st);
HITCBC 2159   37191 switch(st) 2163   30172 switch(st)
2160   { 2164   {
MISUBC 2161   ✗ default: BOOST_JSON_UNREACHABLE(); 2165   ✗ default: BOOST_JSON_UNREACHABLE();
HITCBC 2162   602 case state::num1: goto do_num1; 2166   538 case state::num1: goto do_num1;
HITCBC 2163   6338 case state::num2: goto do_num2; 2167   6120 case state::num2: goto do_num2;
HITCBC 2164   802 case state::num3: goto do_num3; 2168   802 case state::num3: goto do_num3;
HITCBC 2165   52 case state::num4: goto do_num4; 2169   52 case state::num4: goto do_num4;
HITCBC 2166   4537 case state::num5: goto do_num5; 2170   919 case state::num5: goto do_num5;
HITCBC 2167   666 case state::num6: goto do_num6; 2171   570 case state::num6: goto do_num6;
HITCBC 2168   616 case state::num7: goto do_num7; 2172   516 case state::num7: goto do_num7;
HITCBC 2169   10944 case state::num8: goto do_num8; 2173   10944 case state::num8: goto do_num8;
HITCBC 2170   469 case state::exp1: goto do_exp1; 2174   423 case state::exp1: goto do_exp1;
HITCBC 2171   133 case state::exp2: goto do_exp2; 2175   129 case state::exp2: goto do_exp2;
HITCBC 2172   12032 case state::exp3: goto do_exp3; 2176   9159 case state::exp3: goto do_exp3;
2173   } 2177   }
2174   } 2178   }
2175   2179  
2176   //---------------------------------- 2180   //----------------------------------
2177   // 2181   //
2178   // DIGIT 2182   // DIGIT
2179   // first digit 2183   // first digit
2180   // 2184   //
HITCBC 2181   61794 do_num1: 2185   58547 do_num1:
HITCBC 2182   15791 if(zero_first || nonzero_first || 2186   14249 if(zero_first || nonzero_first ||
HITCBC 2183   15791 BOOST_JSON_LIKELY(cs)) 2187   14249 BOOST_JSON_LIKELY(cs))
2184   { 2188   {
HITCBC 2185   61072 char const c = *cs; 2189   57889 char const c = *cs;
2186   if(zero_first) 2190   if(zero_first)
2187   { 2191   {
HITCBC 2188   9718 ++cs; 2192   8474 ++cs;
HITCBC 2189   9718 num.mant = 0; 2193   8474 num.mant = 0;
HITCBC 2190   9718 goto do_num6; 2194   8474 goto do_num6;
2191   } 2195   }
HITCBC 2192   15069 else if(nonzero_first || BOOST_JSON_LIKELY( 2196   13591 else if(nonzero_first || BOOST_JSON_LIKELY(
2193   c >= '1' && c <= '9')) 2197   c >= '1' && c <= '9'))
2194   { 2198   {
HITCBC 2195   42532 ++cs; 2199   41664 ++cs;
HITCBC 2196   42532 num.mant = c - '0'; 2200   41664 num.mant = c - '0';
2197   } 2201   }
HITCBC 2198   8822 else if(BOOST_JSON_UNLIKELY( 2202   7751 else if(BOOST_JSON_UNLIKELY(
2199   c == '0')) 2203   c == '0'))
2200   { 2204   {
HITCBC 2201   7627 ++cs; 2205   6556 ++cs;
HITCBC 2202   7627 num.mant = 0; 2206   6556 num.mant = 0;
HITCBC 2203   7627 goto do_num6; 2207   6556 goto do_num6;
2204   } 2208   }
HITCBC 2205   1195 else if( (negative || num.neg) && opt_.allow_infinity_and_nan ) 2209   1195 else if( (negative || num.neg) && opt_.allow_infinity_and_nan )
2206   { 2210   {
HITCBC 2207   1007 st_.push(state::lit1); 2211   1007 st_.push(state::lit1);
HITCBC 2208   1007 cur_lit_ = literal_index(detail::literals::neg_infinity); 2212   1007 cur_lit_ = literal_index(detail::literals::neg_infinity);
HITCBC 2209   1007 lit_offset_ = 1; 2213   1007 lit_offset_ = 1;
HITCBC 2210   1007 return parse_literal( 2214   1007 return parse_literal(
HITCBC 2211   961 cs.begin(), detail::literals_c<detail::literals::resume>() ); 2215   961 cs.begin(), detail::literals_c<detail::literals::resume>() );
2212   } 2216   }
2213   else 2217   else
2214   { 2218   {
2215   BOOST_STATIC_CONSTEXPR source_location loc 2219   BOOST_STATIC_CONSTEXPR source_location loc
2216   = BOOST_CURRENT_LOCATION; 2220   = BOOST_CURRENT_LOCATION;
HITCBC 2217   188 return fail(cs.begin(), error::syntax, &loc); 2221   188 return fail(cs.begin(), error::syntax, &loc);
2218   } 2222   }
2219   } 2223   }
2220   else 2224   else
2221   { 2225   {
HITCBC 2222   722 if(BOOST_JSON_UNLIKELY( 2226   658 if(BOOST_JSON_UNLIKELY(
2223   ! h_.on_number_part( 2227   ! h_.on_number_part(
2224   {begin, cs.used(begin)}, ec_))) 2228   {begin, cs.used(begin)}, ec_)))
HITCBC 2225   60 return fail(cs.begin()); 2229   60 return fail(cs.begin());
2226   2230  
2227   BOOST_IF_CONSTEXPR( precise_parsing ) 2231   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2228   ✗ num_buf_.append( begin, cs.used(begin) ); 2232   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2229   602 return maybe_suspend( 2233   538 return maybe_suspend(
HITCBC 2230   602 cs.begin(), state::num1, num); 2234   538 cs.begin(), state::num1, num);
2231   } 2235   }
2232   2236  
2233   //---------------------------------- 2237   //----------------------------------
2234   // 2238   //
2235   // 1*DIGIT 2239   // 1*DIGIT
2236   // significant digits left of decimal 2240   // significant digits left of decimal
2237   // 2241   //
HITCBC 2238   2050294 do_num2: 2242   2048981 do_num2:
HITCBC 2239   2044036 if(negative || (!stack_empty && num.neg)) 2243   2043110 if(negative || (!stack_empty && num.neg))
2240   { 2244   {
HITCBC 2241   22400 for(;;) 2245   22141 for(;;)
2242   { 2246   {
HITCBC 2243   30225 if(BOOST_JSON_UNLIKELY(! cs)) 2247   29527 if(BOOST_JSON_UNLIKELY(! cs))
2244   { 2248   {
HITCBC 2245   1921 if(BOOST_JSON_UNLIKELY(more_)) 2249   1889 if(BOOST_JSON_UNLIKELY(more_))
2246   { 2250   {
HITCBC 2247   1469 if(BOOST_JSON_UNLIKELY( 2251   1437 if(BOOST_JSON_UNLIKELY(
2248   ! h_.on_number_part( 2252   ! h_.on_number_part(
2249   {begin, cs.used(begin)}, ec_))) 2253   {begin, cs.used(begin)}, ec_)))
HITCBC 2250   69 return fail(cs.begin()); 2254   69 return fail(cs.begin());
2251   2255  
2252   BOOST_IF_CONSTEXPR( precise_parsing ) 2256   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2253   ✗ num_buf_.append( begin, cs.used(begin) ); 2257   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2254   1331 return suspend(cs.begin(), state::num2, num); 2258   1299 return suspend(cs.begin(), state::num2, num);
2255   } 2259   }
HITCBC 2256   452 goto finish_int; 2260   452 goto finish_int;
2257   } 2261   }
HITCBC 2258   28304 char const c = *cs; 2262   27638 char const c = *cs;
HITCBC 2259   28304 if(BOOST_JSON_LIKELY( 2263   27638 if(BOOST_JSON_LIKELY(
2260   c >= '0' && c <= '9')) 2264   c >= '0' && c <= '9'))
2261   { 2265   {
HITCBC 2262   23223 ++cs; 2266   22964 ++cs;
2263   // 9223372036854775808 INT64_MIN 2267   // 9223372036854775808 INT64_MIN
HITCBC 2264   23223 if( num.mant > 922337203685477580 || ( 2268   22964 if( num.mant > 922337203685477580 || (
HITCBC 2265   22508 num.mant == 922337203685477580 && c > '8')) 2269   22249 num.mant == 922337203685477580 && c > '8'))
2266   break; 2270   break;
HITGIC 2267 - BOOST_IF_CONSTEXPR( !no_parsing ) 2271 + 22141 num.mant = 10 * num.mant + ( c - '0' );
DCB 2268 - 22141 num.mant = 10 * num.mant + ( c - '0' );  
HITCBC 2269   22400 continue; 2272   22141 continue;
2270   } 2273   }
HITCBC 2271   5081 goto do_num6; // [.eE] 2274   4674 goto do_num6; // [.eE]
2272   } 2275   }
2273   } 2276   }
2274   else 2277   else
2275   { 2278   {
HITCBC 2276   6885037 for(;;) 2279   6879439 for(;;)
2277   { 2280   {
HITCBC 2278   8927506 if(BOOST_JSON_UNLIKELY(! cs)) 2281   8921034 if(BOOST_JSON_UNLIKELY(! cs))
2279   { 2282   {
HITCBC 2280   6426 if(BOOST_JSON_UNLIKELY(more_)) 2283   6240 if(BOOST_JSON_UNLIKELY(more_))
2281   { 2284   {
HITCBC 2282   5813 if(BOOST_JSON_UNLIKELY( 2285   5627 if(BOOST_JSON_UNLIKELY(
2283   ! h_.on_number_part( 2286   ! h_.on_number_part(
2284   {begin, cs.used(begin)}, ec_))) 2287   {begin, cs.used(begin)}, ec_)))
HITCBC 2285   406 return fail(cs.begin()); 2288   406 return fail(cs.begin());
2286   2289  
2287   BOOST_IF_CONSTEXPR( precise_parsing ) 2290   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2288   ✗ num_buf_.append( begin, cs.used(begin) ); 2291   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2289   5007 return suspend(cs.begin(), state::num2, num); 2292   4821 return suspend(cs.begin(), state::num2, num);
2290   } 2293   }
HITCBC 2291   613 goto finish_int; 2294   613 goto finish_int;
2292   } 2295   }
HITCBC 2293   8921080 char const c = *cs; 2296   8914794 char const c = *cs;
HITCBC 2294   8921080 if(BOOST_JSON_LIKELY( 2297   8914794 if(BOOST_JSON_LIKELY(
2295   c >= '0' && c <= '9')) 2298   c >= '0' && c <= '9'))
2296   { 2299   {
HITCBC 2297   6888862 ++cs; 2300   6883264 ++cs;
2298   // 18446744073709551615 UINT64_MAX 2301   // 18446744073709551615 UINT64_MAX
HITCBC 2299   6888862 if( num.mant > 1844674407370955161 || ( 2302   6883264 if( num.mant > 1844674407370955161 || (
HITCBC 2300   6885459 num.mant == 1844674407370955161 && c > '5')) 2303   6879861 num.mant == 1844674407370955161 && c > '5'))
2301   break; 2304   break;
HITGIC 2302 - BOOST_IF_CONSTEXPR( !no_parsing ) 2305 + 6879439 num.mant = 10 * num.mant + ( c - '0' );
DCB 2303 - 6879439 num.mant = 10 * num.mant + ( c - '0' );  
2304   } 2306   }
2305   else 2307   else
2306   { 2308   {
HITCBC 2307   2032218 goto do_num6; // [.eE] 2309   2031530 goto do_num6; // [.eE]
2308   } 2310   }
2309   } 2311   }
2310   } 2312   }
HITCBC 2311   4648 ++num.bias; 2313   4648 ++num.bias;
2312   2314  
2313   //---------------------------------- 2315   //----------------------------------
2314   // 2316   //
2315   // 1*DIGIT 2317   // 1*DIGIT
2316   // non-significant digits left of decimal 2318   // non-significant digits left of decimal
2317   // 2319   //
HITCBC 2318   5450 do_num3: 2320   5450 do_num3:
HITCBC 2319   11558 for(;;) 2321   11558 for(;;)
2320   { 2322   {
HITCBC 2321   17008 if(BOOST_JSON_UNLIKELY(! cs)) 2323   17008 if(BOOST_JSON_UNLIKELY(! cs))
2322   { 2324   {
HITCBC 2323   1527 if(BOOST_JSON_UNLIKELY(more_)) 2325   1527 if(BOOST_JSON_UNLIKELY(more_))
2324   { 2326   {
HITCBC 2325   894 if(BOOST_JSON_UNLIKELY( 2327   894 if(BOOST_JSON_UNLIKELY(
2326   ! h_.on_number_part( 2328   ! h_.on_number_part(
2327   {begin, cs.used(begin)}, ec_))) 2329   {begin, cs.used(begin)}, ec_)))
HITCBC 2328   46 return fail(cs.begin()); 2330   46 return fail(cs.begin());
2329   2331  
2330   BOOST_IF_CONSTEXPR( precise_parsing ) 2332   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2331   ✗ num_buf_.append( begin, cs.used(begin) ); 2333   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2332   802 return suspend(cs.begin(), state::num3, num); 2334   802 return suspend(cs.begin(), state::num3, num);
2333   } 2335   }
HITCBC 2334   633 goto finish_dub; 2336   633 goto finish_dub;
2335   } 2337   }
HITCBC 2336   15481 char const c = *cs; 2338   15481 char const c = *cs;
HITCBC 2337   15481 if(BOOST_JSON_UNLIKELY( 2339   15481 if(BOOST_JSON_UNLIKELY(
2338   c >= '0' && c <= '9')) 2340   c >= '0' && c <= '9'))
2339   { 2341   {
HITCBC 2340   11558 if(BOOST_JSON_UNLIKELY( num.bias + 1 == INT_MAX )) 2342   11558 if(BOOST_JSON_UNLIKELY( num.bias + 1 == INT_MAX ))
2341   { 2343   {
2342   BOOST_STATIC_CONSTEXPR source_location loc 2344   BOOST_STATIC_CONSTEXPR source_location loc
2343   = BOOST_CURRENT_LOCATION; 2345   = BOOST_CURRENT_LOCATION;
MISUBC 2344   ✗ return fail(cs.begin(), error::exponent_overflow, &loc); 2346   ✗ return fail(cs.begin(), error::exponent_overflow, &loc);
2345   } 2347   }
HITCBC 2346   11558 ++cs; 2348   11558 ++cs;
HITCBC 2347   11558 ++num.bias; 2349   11558 ++num.bias;
2348   } 2350   }
HITCBC 2349   3923 else if(BOOST_JSON_LIKELY( 2351   3923 else if(BOOST_JSON_LIKELY(
2350   c == '.')) 2352   c == '.'))
2351   { 2353   {
HITCBC 2352   2028 ++cs; 2354   2028 ++cs;
HITCBC 2353   2028 break; 2355   2028 break;
2354   } 2356   }
HITCBC 2355   1895 else if((c | 32) == 'e') 2357   1895 else if((c | 32) == 'e')
2356   { 2358   {
HITCBC 2357   546 ++cs; 2359   546 ++cs;
HITCBC 2358   546 goto do_exp1; 2360   546 goto do_exp1;
2359   } 2361   }
2360   else 2362   else
2361   { 2363   {
HITCBC 2362   1349 goto finish_dub; 2364   1349 goto finish_dub;
2363   } 2365   }
2364   } 2366   }
2365   2367  
2366   //---------------------------------- 2368   //----------------------------------
2367   // 2369   //
2368   // DIGIT 2370   // DIGIT
2369   // first non-significant digit 2371   // first non-significant digit
2370   // to the right of decimal 2372   // to the right of decimal
2371   // 2373   //
HITCBC 2372   2080 do_num4: 2374   2080 do_num4:
2373   { 2375   {
HITCBC 2374   2080 if(BOOST_JSON_UNLIKELY(! cs)) 2376   2080 if(BOOST_JSON_UNLIKELY(! cs))
2375   { 2377   {
HITCBC 2376   64 if(BOOST_JSON_UNLIKELY( 2378   64 if(BOOST_JSON_UNLIKELY(
2377   ! h_.on_number_part( 2379   ! h_.on_number_part(
2378   {begin, cs.used(begin)}, ec_))) 2380   {begin, cs.used(begin)}, ec_)))
HITCBC 2379   6 return fail(cs.begin()); 2381   6 return fail(cs.begin());
2380   2382  
2381   BOOST_IF_CONSTEXPR( precise_parsing ) 2383   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2382   ✗ num_buf_.append( begin, cs.used(begin) ); 2384   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2383   52 return maybe_suspend( 2385   52 return maybe_suspend(
HITCBC 2384   52 cs.begin(), state::num4, num); 2386   52 cs.begin(), state::num4, num);
2385   } 2387   }
HITCBC 2386   2016 char const c = *cs; 2388   2016 char const c = *cs;
HITCBC 2387   2016 if(BOOST_JSON_LIKELY( 2389   2016 if(BOOST_JSON_LIKELY(
2388   //static_cast<unsigned char>(c - '0') < 10)) 2390   //static_cast<unsigned char>(c - '0') < 10))
2389   c >= '0' && c <= '9')) 2391   c >= '0' && c <= '9'))
2390   { 2392   {
HITCBC 2391   1949 ++cs; 2393   1949 ++cs;
2392   } 2394   }
2393   else 2395   else
2394   { 2396   {
2395   // digit required 2397   // digit required
2396   BOOST_STATIC_CONSTEXPR source_location loc 2398   BOOST_STATIC_CONSTEXPR source_location loc
2397   = BOOST_CURRENT_LOCATION; 2399   = BOOST_CURRENT_LOCATION;
HITCBC 2398   67 return fail(cs.begin(), error::syntax, &loc); 2400   67 return fail(cs.begin(), error::syntax, &loc);
2399   } 2401   }
2400   } 2402   }
2401   2403  
2402   //---------------------------------- 2404   //----------------------------------
2403   // 2405   //
2404   // 1*DIGIT 2406   // 1*DIGIT
2405   // non-significant digits 2407   // non-significant digits
2406   // to the right of decimal 2408   // to the right of decimal
2407   // 2409   //
HITCBC 2408   2013470 do_num5: 2410   2004759 do_num5:
HITCBC 2409   37889832 for(;;) 2411   36805410 for(;;)
2410   { 2412   {
HITCBC 2411   39903302 if(BOOST_JSON_UNLIKELY(! cs)) 2413   38810169 if(BOOST_JSON_UNLIKELY(! cs))
2412   { 2414   {
HITCBC 2413   6112 if(BOOST_JSON_UNLIKELY(more_)) 2415   1851 if(BOOST_JSON_UNLIKELY(more_))
2414   { 2416   {
HITCBC 2415   4577 if(BOOST_JSON_UNLIKELY( 2417   959 if(BOOST_JSON_UNLIKELY(
2416   ! h_.on_number_part( 2418   ! h_.on_number_part(
2417   {begin, cs.used(begin)}, ec_))) 2419   {begin, cs.used(begin)}, ec_)))
HITCBC 2418   20 return fail(cs.begin()); 2420   20 return fail(cs.begin());
2419   2421  
2420   BOOST_IF_CONSTEXPR( precise_parsing ) 2422   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2421   ✗ num_buf_.append( begin, cs.used(begin) ); 2423   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2422   4537 return suspend(cs.begin(), state::num5, num); 2424   919 return suspend(cs.begin(), state::num5, num);
2423   } 2425   }
HITCBC 2424   1535 goto finish_dub; 2426   892 goto finish_dub;
2425   } 2427   }
HITCBC 2426   39897190 char const c = *cs; 2428   38808318 char const c = *cs;
HITCBC 2427   39897190 if(BOOST_JSON_LIKELY( 2429   38808318 if(BOOST_JSON_LIKELY(
2428   c >= '0' && c <= '9')) 2430   c >= '0' && c <= '9'))
2429   { 2431   {
HITCBC 2430   37889832 ++cs; 2432   36805410 ++cs;
2431   } 2433   }
HITCBC 2432   2007358 else if((c | 32) == 'e') 2434   2002908 else if((c | 32) == 'e')
2433   { 2435   {
HITCBC 2434   2003236 ++cs; 2436   2000590 ++cs;
HITCBC 2435   2003236 goto do_exp1; 2437   2000590 goto do_exp1;
2436   } 2438   }
2437   else 2439   else
2438   { 2440   {
HITCBC 2439   4122 goto finish_dub; 2441   2318 goto finish_dub;
2440   } 2442   }
2441   } 2443   }
2442   2444  
2443   //---------------------------------- 2445   //----------------------------------
2444   // 2446   //
2445   // [.eE] 2447   // [.eE]
2446   // 2448   //
HITCBC 2447   2055310 do_num6: 2449   2051804 do_num6:
2448   { 2450   {
HITCBC 2449   2055310 if(BOOST_JSON_UNLIKELY(! cs)) 2451   2051804 if(BOOST_JSON_UNLIKELY(! cs))
2450   { 2452   {
HITCBC 2451   798 if(BOOST_JSON_UNLIKELY(more_)) 2453   702 if(BOOST_JSON_UNLIKELY(more_))
2452   { 2454   {
HITCBC 2453   751 if(BOOST_JSON_UNLIKELY( 2455   655 if(BOOST_JSON_UNLIKELY(
2454   ! h_.on_number_part( 2456   ! h_.on_number_part(
2455   {begin, cs.used(begin)}, ec_))) 2457   {begin, cs.used(begin)}, ec_)))
HITCBC 2456   42 return fail(cs.begin()); 2458   42 return fail(cs.begin());
2457   2459  
2458   BOOST_IF_CONSTEXPR( precise_parsing ) 2460   BOOST_IF_CONSTEXPR( precise_parsing )
HITCBC 2459   2 num_buf_.append( begin, cs.used(begin) ); 2461   2 num_buf_.append( begin, cs.used(begin) );
HITCBC 2460   667 return suspend(cs.begin(), state::num6, num); 2462   571 return suspend(cs.begin(), state::num6, num);
2461   } 2463   }
HITCBC 2462   47 goto finish_int; 2464   47 goto finish_int;
2463   } 2465   }
HITCBC 2464   2054512 char const c = *cs; 2466   2051102 char const c = *cs;
HITCBC 2465   2054512 if(BOOST_JSON_LIKELY( 2467   2051102 if(BOOST_JSON_LIKELY(
2466   c == '.')) 2468   c == '.'))
2467   { 2469   {
HITCBC 2468   2016097 ++cs; 2470   2013504 ++cs;
2469   } 2471   }
HITCBC 2470   38415 else if((c | 32) == 'e') 2472   37598 else if((c | 32) == 'e')
2471   { 2473   {
HITCBC 2472   9140 ++cs; 2474   8323 ++cs;
HITCBC 2473   9140 goto do_exp1; 2475   8323 goto do_exp1;
2474   } 2476   }
2475   else 2477   else
2476   { 2478   {
HITCBC 2477   29275 goto finish_int; 2479   29275 goto finish_int;
2478   } 2480   }
2479   } 2481   }
2480   2482  
2481   //---------------------------------- 2483   //----------------------------------
2482   // 2484   //
2483   // DIGIT 2485   // DIGIT
2484   // first significant digit 2486   // first significant digit
2485   // to the right of decimal 2487   // to the right of decimal
2486   // 2488   //
HITCBC 2487   2016835 do_num7: 2489   2014142 do_num7:
2488   { 2490   {
HITCBC 2489   2016835 if(BOOST_JSON_UNLIKELY(! cs)) 2491   2014142 if(BOOST_JSON_UNLIKELY(! cs))
2490   { 2492   {
HITCBC 2491   691 if(BOOST_JSON_UNLIKELY(more_)) 2493   591 if(BOOST_JSON_UNLIKELY(more_))
2492   { 2494   {
HITCBC 2493   687 if(BOOST_JSON_UNLIKELY( 2495   587 if(BOOST_JSON_UNLIKELY(
2494   ! h_.on_number_part( 2496   ! h_.on_number_part(
2495   {begin, cs.used(begin)}, ec_))) 2497   {begin, cs.used(begin)}, ec_)))
HITCBC 2496   35 return fail(cs.begin()); 2498   35 return fail(cs.begin());
2497   2499  
2498   BOOST_IF_CONSTEXPR( precise_parsing ) 2500   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2499   ✗ num_buf_.append( begin, cs.used(begin) ); 2501   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2500   617 return suspend(cs.begin(), state::num7, num); 2502   517 return suspend(cs.begin(), state::num7, num);
2501   } 2503   }
2502   // digit required 2504   // digit required
2503   BOOST_STATIC_CONSTEXPR source_location loc 2505   BOOST_STATIC_CONSTEXPR source_location loc
2504   = BOOST_CURRENT_LOCATION; 2506   = BOOST_CURRENT_LOCATION;
HITCBC 2505   4 return fail(cs.begin(), error::syntax, &loc); 2507   4 return fail(cs.begin(), error::syntax, &loc);
2506   } 2508   }
HITCBC 2507   2016144 char const c = *cs; 2509   2013551 char const c = *cs;
HITCBC 2508   2016144 if(BOOST_JSON_UNLIKELY( 2510   2013551 if(BOOST_JSON_UNLIKELY(
2509   c < '0' || c > '9')) 2511   c < '0' || c > '9'))
2510   { 2512   {
2511   // digit required 2513   // digit required
2512   BOOST_STATIC_CONSTEXPR source_location loc 2514   BOOST_STATIC_CONSTEXPR source_location loc
2513   = BOOST_CURRENT_LOCATION; 2515   = BOOST_CURRENT_LOCATION;
HITCBC 2514   169 return fail(cs.begin(), error::syntax, &loc); 2516   169 return fail(cs.begin(), error::syntax, &loc);
2515   } 2517   }
2516   } 2518   }
2517   2519  
2518   //---------------------------------- 2520   //----------------------------------
2519   // 2521   //
2520   // 1*DIGIT 2522   // 1*DIGIT
2521   // significant digits 2523   // significant digits
2522   // to the right of decimal 2524   // to the right of decimal
2523   // 2525   //
HITCBC 2524   2034436 do_num8: 2526   2031843 do_num8:
HITCBC 2525   3277926 for(;;) 2527   3277926 for(;;)
2526   { 2528   {
HITCBC 2527   5314862 if(BOOST_JSON_UNLIKELY(! cs)) 2529   5309769 if(BOOST_JSON_UNLIKELY(! cs))
2528   { 2530   {
HITCBC 2529   12816 if(BOOST_JSON_UNLIKELY(more_)) 2531   12816 if(BOOST_JSON_UNLIKELY(more_))
2530   { 2532   {
HITCBC 2531   11080 if(BOOST_JSON_UNLIKELY( 2533   11080 if(BOOST_JSON_UNLIKELY(
2532   ! h_.on_number_part( 2534   ! h_.on_number_part(
2533   {begin, cs.used(begin)}, ec_))) 2535   {begin, cs.used(begin)}, ec_)))
HITCBC 2534   67 return fail(cs.begin()); 2536   67 return fail(cs.begin());
2535   2537  
2536   BOOST_IF_CONSTEXPR( precise_parsing ) 2538   BOOST_IF_CONSTEXPR( precise_parsing )
HITCBC 2537   2 num_buf_.append( begin, cs.used(begin) ); 2539   2 num_buf_.append( begin, cs.used(begin) );
HITCBC 2538   10945 return suspend(cs.begin(), state::num8, num); 2540   10945 return suspend(cs.begin(), state::num8, num);
2539   } 2541   }
HITCBC 2540   1736 goto finish_dub; 2542   1736 goto finish_dub;
2541   } 2543   }
HITCBC 2542   5302046 char const c = *cs; 2544   5296953 char const c = *cs;
HITCBC 2543   5302046 if(BOOST_JSON_LIKELY( 2545   5296953 if(BOOST_JSON_LIKELY(
2544   c >= '0' && c <= '9')) 2546   c >= '0' && c <= '9'))
2545   { 2547   {
HITCBC 2546   5284910 ++cs; 2548   5279817 ++cs;
HITCBC 2547 - 5279817 if(!no_parsing && BOOST_JSON_LIKELY( 2549 + 5279817 if(BOOST_JSON_LIKELY( num.mant <= 9007199254740991 )) // 2^53-1
2548 - num.mant <= 9007199254740991)) // 2^53-1  
2549   { 2550   {
HITCBC 2550   3277926 if(BOOST_JSON_UNLIKELY( num.bias - 1 == INT_MIN )) 2551   3277926 if(BOOST_JSON_UNLIKELY( num.bias - 1 == INT_MIN ))
2551   { 2552   {
2552   BOOST_STATIC_CONSTEXPR source_location loc 2553   BOOST_STATIC_CONSTEXPR source_location loc
2553   = BOOST_CURRENT_LOCATION; 2554   = BOOST_CURRENT_LOCATION;
MISUBC 2554   ✗ return fail(cs.begin(), error::exponent_overflow, &loc); 2555   ✗ return fail(cs.begin(), error::exponent_overflow, &loc);
2555   } 2556   }
HITCBC 2556   3277926 --num.bias; 2557   3277926 --num.bias;
HITCBC 2557   3277926 num.mant = 10 * num.mant + ( c - '0' ); 2558   3277926 num.mant = 10 * num.mant + ( c - '0' );
2558   } 2559   }
2559   else 2560   else
2560   { 2561   {
HITCBC 2561   2006984 goto do_num5; 2562   2001891 goto do_num5;
2562   } 2563   }
2563   } 2564   }
HITCBC 2564   17136 else if((c | 32) == 'e') 2565   17136 else if((c | 32) == 'e')
2565   { 2566   {
HITCBC 2566   11133 ++cs; 2567   11133 ++cs;
HITCBC 2567   11133 goto do_exp1; 2568   11133 goto do_exp1;
2568   } 2569   }
2569   else 2570   else
2570   { 2571   {
HITCBC 2571   6003 goto finish_dub; 2572   6003 goto finish_dub;
2572   } 2573   }
2573   } 2574   }
2574   2575  
2575   //---------------------------------- 2576   //----------------------------------
2576   // 2577   //
2577   // *[+-] 2578   // *[+-]
2578   // 2579   //
HITCBC 2579   2031210 do_exp1: 2580   2026072 do_exp1:
HITCBC 2580   2031210 if(BOOST_JSON_UNLIKELY(! cs)) 2581   2026072 if(BOOST_JSON_UNLIKELY(! cs))
2581   { 2582   {
HITCBC 2582   565 if(BOOST_JSON_UNLIKELY( 2583   519 if(BOOST_JSON_UNLIKELY(
2583   ! h_.on_number_part( 2584   ! h_.on_number_part(
2584   {begin, cs.used(begin)}, ec_))) 2585   {begin, cs.used(begin)}, ec_)))
HITCBC 2585   48 return fail(cs.begin()); 2586   48 return fail(cs.begin());
2586   2587  
2587   BOOST_IF_CONSTEXPR( precise_parsing ) 2588   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2588   ✗ num_buf_.append( begin, cs.used(begin) ); 2589   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2589   469 return maybe_suspend( 2590   423 return maybe_suspend(
HITCBC 2590   469 cs.begin(), state::exp1, num); 2591   423 cs.begin(), state::exp1, num);
2591   } 2592   }
HITCBC 2592   2030645 if(*cs == '+') 2593   2025553 if(*cs == '+')
2593   { 2594   {
HITCBC 2594   2150 ++cs; 2595   2150 ++cs;
2595   } 2596   }
HITCBC 2596   2028495 else if(*cs == '-') 2597   2023403 else if(*cs == '-')
2597   { 2598   {
HITCBC 2598   1001935 ++cs; 2599   1001775 ++cs;
HITCBC 2599   1001935 num.frac = true; 2600   1001775 num.frac = true;
2600   } 2601   }
2601   2602  
2602   //---------------------------------- 2603   //----------------------------------
2603   // 2604   //
2604   // DIGIT 2605   // DIGIT
2605   // first digit of the exponent 2606   // first digit of the exponent
2606   // 2607   //
HITCBC 2607   1026560 do_exp2: 2608   1021628 do_exp2:
2608   { 2609   {
HITCBC 2609   2030778 if(BOOST_JSON_UNLIKELY(! cs)) 2610   2025682 if(BOOST_JSON_UNLIKELY(! cs))
2610   { 2611   {
HITCBC 2611   180 if(BOOST_JSON_UNLIKELY(more_)) 2612   176 if(BOOST_JSON_UNLIKELY(more_))
2612   { 2613   {
HITCBC 2613   171 if(BOOST_JSON_UNLIKELY( 2614   167 if(BOOST_JSON_UNLIKELY(
2614   ! h_.on_number_part( 2615   ! h_.on_number_part(
2615   {begin, cs.used(begin)}, ec_))) 2616   {begin, cs.used(begin)}, ec_)))
HITCBC 2616   19 return fail(cs.begin()); 2617   19 return fail(cs.begin());
2617   2618  
2618   BOOST_IF_CONSTEXPR( precise_parsing ) 2619   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2619   ✗ num_buf_.append( begin, cs.used(begin) ); 2620   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2620   133 return suspend(cs.begin(), state::exp2, num); 2621   129 return suspend(cs.begin(), state::exp2, num);
2621   } 2622   }
2622   // digit required 2623   // digit required
2623   BOOST_STATIC_CONSTEXPR source_location loc 2624   BOOST_STATIC_CONSTEXPR source_location loc
2624   = BOOST_CURRENT_LOCATION; 2625   = BOOST_CURRENT_LOCATION;
HITCBC 2625   9 return fail(cs.begin(), error::syntax, &loc); 2626   9 return fail(cs.begin(), error::syntax, &loc);
2626   } 2627   }
HITCBC 2627   2030598 char const c = *cs; 2628   2025506 char const c = *cs;
HITCBC 2628   2030598 if(BOOST_JSON_UNLIKELY( 2629   2025506 if(BOOST_JSON_UNLIKELY(
2629   c < '0' || c > '9')) 2630   c < '0' || c > '9'))
2630   { 2631   {
2631   // digit required 2632   // digit required
2632   BOOST_STATIC_CONSTEXPR source_location loc 2633   BOOST_STATIC_CONSTEXPR source_location loc
2633   = BOOST_CURRENT_LOCATION; 2634   = BOOST_CURRENT_LOCATION;
HITCBC 2634   508 return fail(cs.begin(), error::syntax, &loc); 2635   508 return fail(cs.begin(), error::syntax, &loc);
2635   } 2636   }
HITCBC 2636   2030090 ++cs; 2637   2024998 ++cs;
HITCBC 2637   2030090 num.exp = c - '0'; 2638   2024998 num.exp = c - '0';
2638   } 2639   }
2639   2640  
2640   //---------------------------------- 2641   //----------------------------------
2641   // 2642   //
2642   // 1*DIGIT 2643   // 1*DIGIT
2643   // subsequent digits in the exponent 2644   // subsequent digits in the exponent
2644   // 2645   //
HITCBC 2645   2042122 do_exp3: 2646   2034157 do_exp3:
HITCBC 2646   5466310 for(;;) 2647   4925458 for(;;)
2647   { 2648   {
HITCBC 2648   7508432 if(BOOST_JSON_UNLIKELY(! cs)) 2649   6959615 if(BOOST_JSON_UNLIKELY(! cs))
2649   { 2650   {
HITCBC 2650   2020539 if(BOOST_JSON_UNLIKELY(more_)) 2651   2015856 if(BOOST_JSON_UNLIKELY(more_))
2651   { 2652   {
HITCBC 2652   12186 if(BOOST_JSON_UNLIKELY( 2653   9313 if(BOOST_JSON_UNLIKELY(
2653   ! h_.on_number_part( 2654   ! h_.on_number_part(
2654   {begin, cs.used(begin)}, ec_))) 2655   {begin, cs.used(begin)}, ec_)))
HITCBC 2655   77 return fail(cs.begin()); 2656   77 return fail(cs.begin());
2656   2657  
2657   BOOST_IF_CONSTEXPR( precise_parsing ) 2658   BOOST_IF_CONSTEXPR( precise_parsing )
MISUBC 2658   ✗ num_buf_.append( begin, cs.used(begin) ); 2659   ✗ num_buf_.append( begin, cs.used(begin) );
HITCBC 2659   12032 return suspend(cs.begin(), state::exp3, num); 2660   9159 return suspend(cs.begin(), state::exp3, num);
2660   } 2661   }
2661   } 2662   }
2662   else 2663   else
2663   { 2664   {
HITCBC 2664   5487893 char const c = *cs; 2665   4943759 char const c = *cs;
HITCBC 2665   5487893 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' )) 2666   4943759 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
2666   { 2667   {
HITCBC 2667   5466310 if(BOOST_JSON_UNLIKELY( 2668   4925458 if(BOOST_JSON_UNLIKELY(
2668   // 2147483647 INT_MAX 2669   // 2147483647 INT_MAX
2669   num.exp > 214748364 || 2670   num.exp > 214748364 ||
2670   (num.exp == 214748364 && c > '7') 2671   (num.exp == 214748364 && c > '7')
2671   )) 2672   ))
HITCBC 2672   3855 num.exp = INT_MAX; 2673   3855 num.exp = INT_MAX;
2673 - else BOOST_IF_CONSTEXPR( !no_parsing ) 2674 + else
HITCBC 2674   4921603 num.exp = 10 * num.exp + ( c - '0' ); 2675   4921603 num.exp = 10 * num.exp + ( c - '0' );
2675   2676  
HITCBC 2676   5466310 ++cs; 2677   4925458 ++cs;
HITCBC 2677   5466310 continue; 2678   4925458 continue;
2678   } 2679   }
2679   } 2680   }
HITCBC 2680   2029936 BOOST_ASSERT(num.exp >= 0); 2681   2024844 BOOST_ASSERT(num.exp >= 0);
HITCBC 2681   2029936 if ( num.frac ) 2682   2024844 if ( num.frac )
2682   { 2683   {
HITCBC 2683   1001799 if(BOOST_JSON_UNLIKELY( num.bias < (INT_MIN + num.exp) )) 2684   1001639 if(BOOST_JSON_UNLIKELY( num.bias < (INT_MIN + num.exp) ))
2684   { 2685   {
2685   // if exponent overflowed, bias is a very large negative 2686   // if exponent overflowed, bias is a very large negative
2686   // number, and mantissa isn't zero, then we cannot parse the 2687   // number, and mantissa isn't zero, then we cannot parse the
2687   // number correctly 2688   // number correctly
HITCBC 2688   91 if(BOOST_JSON_UNLIKELY( 2689   91 if(BOOST_JSON_UNLIKELY(
2689   (num.exp == INT_MAX) && 2690   (num.exp == INT_MAX) &&
2690   (num.bias < 0) && 2691   (num.bias < 0) &&
2691   (num.exp + num.bias < 308) && 2692   (num.exp + num.bias < 308) &&
2692   num.mant )) 2693   num.mant ))
2693   { 2694   {
2694   BOOST_STATIC_CONSTEXPR source_location loc 2695   BOOST_STATIC_CONSTEXPR source_location loc
2695   = BOOST_CURRENT_LOCATION; 2696   = BOOST_CURRENT_LOCATION;
MISUBC 2696   ✗ return fail(cs.begin(), error::exponent_overflow, &loc); 2697   ✗ return fail(cs.begin(), error::exponent_overflow, &loc);
2697   } 2698   }
2698   2699  
HITCBC 2699   91 num.bias = 0; 2700   91 num.bias = 0;
HITCBC 2700   91 num.exp = INT_MAX; 2701   91 num.exp = INT_MAX;
2701   } 2702   }
2702   } 2703   }
HITCBC 2703   1028137 else if (BOOST_JSON_UNLIKELY( num.bias > (INT_MAX - num.exp) )) 2704   1023205 else if (BOOST_JSON_UNLIKELY( num.bias > (INT_MAX - num.exp) ))
2704   { 2705   {
2705   // if exponent overflowed, bias is a very large positive number, 2706   // if exponent overflowed, bias is a very large positive number,
2706   // and mantissa isn't zero, then we cannot parse the 2707   // and mantissa isn't zero, then we cannot parse the
2707   // number correctly 2708   // number correctly
MISUBC 2708   ✗ if(BOOST_JSON_UNLIKELY( 2709   ✗ if(BOOST_JSON_UNLIKELY(
2709   (num.exp == INT_MAX) && 2710   (num.exp == INT_MAX) &&
2710   (num.bias > 0) && 2711   (num.bias > 0) &&
2711   (num.exp - num.bias < 308) && 2712   (num.exp - num.bias < 308) &&
2712   num.mant )) 2713   num.mant ))
2713   { 2714   {
2714   BOOST_STATIC_CONSTEXPR source_location loc 2715   BOOST_STATIC_CONSTEXPR source_location loc
2715   = BOOST_CURRENT_LOCATION; 2716   = BOOST_CURRENT_LOCATION;
MISUBC 2716   ✗ return fail(cs.begin(), error::exponent_overflow, &loc); 2717   ✗ return fail(cs.begin(), error::exponent_overflow, &loc);
2717   } 2718   }
2718   2719  
MISUBC 2719   ✗ num.bias = 0; 2720   ✗ num.bias = 0;
MISUBC 2720   ✗ num.exp = INT_MAX; 2721   ✗ num.exp = INT_MAX;
2721   } 2722   }
HITCBC 2722   2029936 goto finish_dub; 2723   2024844 goto finish_dub;
2723   } 2724   }
2724   2725  
HITCBC 2725   30387 finish_int: 2726   30387 finish_int:
HITCBC 2726   28458 if(negative || (!stack_empty && num.neg)) 2727   28458 if(negative || (!stack_empty && num.neg))
2727   { 2728   {
HITCBC 2728   2531 if(BOOST_JSON_UNLIKELY( 2729   2531 if(BOOST_JSON_UNLIKELY(
2729   ! h_.on_int64(static_cast< 2730   ! h_.on_int64(static_cast<
2730   int64_t>(~num.mant + 1), {begin, cs.used(begin)}, ec_))) 2731   int64_t>(~num.mant + 1), {begin, cs.used(begin)}, ec_)))
HITCBC 2731   310 return fail(cs.begin()); 2732   310 return fail(cs.begin());
HITCBC 2732   1913 return cs.begin(); 2733   1913 return cs.begin();
2733   } 2734   }
HITCBC 2734   27856 if(num.mant <= INT64_MAX) 2735   27856 if(num.mant <= INT64_MAX)
2735   { 2736   {
HITCBC 2736   27555 finish_signed: 2737   27555 finish_signed:
HITCBC 2737   30830 if(BOOST_JSON_UNLIKELY( 2738   30830 if(BOOST_JSON_UNLIKELY(
2738   ! h_.on_int64(static_cast< 2739   ! h_.on_int64(static_cast<
2739   int64_t>(num.mant), {begin, cs.used(begin)}, ec_))) 2740   int64_t>(num.mant), {begin, cs.used(begin)}, ec_)))
HITCBC 2740   2267 return fail(cs.begin()); 2741   2267 return fail(cs.begin());
HITCBC 2741   26303 return cs.begin(); 2742   26303 return cs.begin();
2742   } 2743   }
HITCBC 2743   321 if(BOOST_JSON_UNLIKELY( 2744   321 if(BOOST_JSON_UNLIKELY(
2744   ! h_.on_uint64(num.mant, {begin, cs.used(begin)}, ec_))) 2745   ! h_.on_uint64(num.mant, {begin, cs.used(begin)}, ec_)))
HITCBC 2745   35 return fail(cs.begin()); 2746   35 return fail(cs.begin());
HITCBC 2746   254 return cs.begin(); 2747   254 return cs.begin();
HITCBC 2747   2052261 finish_dub: 2748   2043003 finish_dub:
2748   double d; 2749   double d;
HITCBC 2749   2052261 std::size_t const size = cs.used(begin); 2750   2043003 std::size_t const size = cs.used(begin);
HITCBC 2750   2052261 BOOST_ASSERT( !num_buf_.size() || precise_parsing ); 2751   2043003 BOOST_ASSERT( !num_buf_.size() || precise_parsing );
2751   BOOST_IF_CONSTEXPR( precise_parsing ) 2752   BOOST_IF_CONSTEXPR( precise_parsing )
2752   { 2753   {
HITCBC 2753   1000052 char const* data = begin; 2754   1000052 char const* data = begin;
HITCBC 2754   1000052 std::size_t full_size = size; 2755   1000052 std::size_t full_size = size;
2755   // if we previously suspended or if the current input ends with the 2756   // if we previously suspended or if the current input ends with the
2756   // number, we need to copy the current part of the number to the 2757   // number, we need to copy the current part of the number to the
2757   // temporary buffer 2758   // temporary buffer
HITCBC 2758   1000052 if(BOOST_JSON_UNLIKELY( num_buf_.size() )) 2759   1000052 if(BOOST_JSON_UNLIKELY( num_buf_.size() ))
2759   { 2760   {
HITCBC 2760   1 data = num_buf_.append( begin, size ); 2761   1 data = num_buf_.append( begin, size );
HITCBC 2761   1 full_size = num_buf_.size(); 2762   1 full_size = num_buf_.size();
2762   } 2763   }
HITCBC 2763   1000052 auto const err = detail::charconv::from_chars( 2764   1000052 auto const err = detail::charconv::from_chars(
2764   data, data + full_size, d ); 2765   data, data + full_size, d );
HITCBC 2765   1000052 BOOST_ASSERT( err.ec != std::errc::invalid_argument ); 2766   1000052 BOOST_ASSERT( err.ec != std::errc::invalid_argument );
HITCBC 2766   1000052 BOOST_ASSERT( err.ptr == data + full_size ); 2767   1000052 BOOST_ASSERT( err.ptr == data + full_size );
2767   (void)err; 2768   (void)err;
2768 - else BOOST_IF_CONSTEXPR( no_parsing )  
2769 - d = 0;  
ECB 2770   9258 } 2769   }
2771   else 2770   else
HITCBC 2772   1042951 d = detail::dec_to_float( 2771   1042951 d = detail::dec_to_float(
2773   num.mant, 2772   num.mant,
HITCBC 2774   540839 num.bias + (num.frac ? 2773   540839 num.bias + (num.frac ?
HITCBC 2775   502112 -num.exp : num.exp), 2774   502112 -num.exp : num.exp),
HITCBC 2776   1042951 num.neg); 2775   1042951 num.neg);
HITCBC 2777   2052261 if(BOOST_JSON_UNLIKELY( 2776   2043003 if(BOOST_JSON_UNLIKELY(
2778   ! h_.on_double(d, {begin, size}, ec_))) 2777   ! h_.on_double(d, {begin, size}, ec_)))
HITGNC   2778 + 1903 return fail(cs.begin());
HITGNC   2779 + 2039197 return cs.begin();
  2780 + }
  2781 +
  2782 + //----------------------------------------------------------
  2783 +
  2784 + template<class Handler>
  2785 + template<bool StackEmpty_, char First_>
  2786 + char const*
HITGNC   2787 + 16277 basic_parser<Handler>::skip_number(
  2788 + char const* p,
  2789 + std::integral_constant<bool, StackEmpty_> stack_empty,
  2790 + std::integral_constant<char, First_> first)
  2791 + {
  2792 + // only one of these will be true if we are not resuming
  2793 + // if negative then !zero_first && !nonzero_first
  2794 + // if zero_first then !nonzero_first && !negative
  2795 + // if nonzero_first then !zero_first && !negative
HITGNC   2796 + 16277 bool negative = first == '-';
HITGNC   2797 + 16277 bool const zero_first = first == '0';
HITGNC   2798 + 16277 bool const nonzero_first = first == '+';
HITGNC   2799 + 16277 detail::const_stream_wrapper cs(p, end_);
HITGNC   2800 + 16277 const char* begin = cs.begin();
HITGNC   2801 + 16277 if(stack_empty || st_.empty())
  2802 + {
  2803 + //----------------------------------
  2804 + //
  2805 + // '-'
  2806 + // leading minus sign
  2807 + //
HITGNC   2808 + 9258 BOOST_ASSERT(cs);
HITGNC   2809 + 9258 if(negative)
HITGNC   2810 + 3898 ++cs;
  2811 +
  2812 + // fast path
HITGNC   2813 + 9258 if( cs.remain() >= 16 + 1 + 16 ) // digits . digits
  2814 + {
  2815 + int n1;
  2816 +
HITGNC   2817 + 5614 if( nonzero_first || (negative && *cs != '0') )
  2818 + {
HITGNC   2819 + 848 n1 = detail::count_digits( cs.begin() );
HITGNC   2820 + 848 BOOST_ASSERT(n1 >= 0 && n1 <= 16);
  2821 +
HITGNC   2822 + 848 if( negative && n1 == 0 && opt_.allow_infinity_and_nan )
MISUNC   2823 + ✗ return parse_literal(
  2824 + p - 1,
MISUNC   2825 + ✗ detail::literals_c<detail::literals::neg_infinity>());
  2826 +
HITGNC   2827 + 387 if( ! nonzero_first && n1 == 0 )
  2828 + {
  2829 + // digit required
  2830 + BOOST_STATIC_CONSTEXPR source_location loc
  2831 + = BOOST_CURRENT_LOCATION;
MISUNC   2832 + ✗ return fail(cs.begin(), error::syntax, &loc);
  2833 + }
  2834 +
HITGNC   2835 + 848 cs += n1;
  2836 +
  2837 + // integer or floating-point with
  2838 + // >= 16 leading digits
HITGNC   2839 + 848 if( n1 == 16 )
HITGNC   2840 + 227 goto do_num2;
  2841 + }
  2842 + else
  2843 + {
  2844 + // 0. floating-point or 0e integer
HITGNC   2845 + 5227 n1 = 0;
HITGNC   2846 + 5227 ++cs;
  2847 + }
  2848 +
  2849 + {
HITGNC   2850 + 5848 const char c = *cs;
HITGNC   2851 + 5848 if(c != '.')
  2852 + {
HITGNC   2853 + 1629 if((c | 32) == 'e')
  2854 + {
HITGNC   2855 + 1629 ++cs;
HITGNC   2856 + 1629 goto do_exp1;
  2857 + }
MISUNC   2858 + ✗ goto finish_signed;
  2859 + }
  2860 + }
  2861 +
  2862 + // floating-point number
  2863 +
HITGNC   2864 + 4219 ++cs;
  2865 +
HITGNC   2866 + 4219 int n2 = detail::count_digits( cs.begin() );
HITGNC   2867 + 4219 BOOST_ASSERT(n2 >= 0 && n2 <= 16);
  2868 +
HITGNC   2869 + 4219 if( n2 == 0 )
  2870 + {
  2871 + // digit required
  2872 + BOOST_STATIC_CONSTEXPR source_location loc
  2873 + = BOOST_CURRENT_LOCATION;
MISUNC   2874 + ✗ return fail(cs.begin(), error::syntax, &loc);
  2875 + }
  2876 +
  2877 + // floating-point mantissa overflow
HITGNC   2878 + 4219 if( n1 + n2 >= 19 )
MISUNC   2879 + ✗ goto do_num7;
  2880 +
HITGNC   2881 + 4219 cs += n2;
  2882 +
HITGNC   2883 + 4219 char ch = *cs;
HITGNC   2884 + 4219 if( (ch | 32) == 'e' )
  2885 + {
MISUNC   2886 + ✗ ++cs;
MISUNC   2887 + ✗ goto do_exp1;
  2888 + }
HITGNC   2889 + 4219 else if( ch >= '0' && ch <= '9' )
  2890 + {
HITGNC   2891 + 2500 goto do_num8;
  2892 + }
  2893 +
HITGNC   2894 + 1719 goto finish_dub;
  2895 + }
  2896 + }
  2897 + else
  2898 + {
HITGNC   2899 + 7019 negative = num_.neg;
  2900 + state st;
HITGNC   2901 + 7019 st_.pop(st);
HITGNC   2902 + 7019 switch(st)
  2903 + {
MISUNC   2904 + ✗ default: BOOST_JSON_UNREACHABLE();
HITGNC   2905 + 64 case state::num1: goto do_num1;
HITGNC   2906 + 218 case state::num2: goto do_num2;
MISUNC   2907 + ✗ case state::num3: goto do_num3;
MISUNC   2908 + ✗ case state::num4: goto do_num4;
HITGNC   2909 + 3618 case state::num5: goto do_num5;
HITGNC   2910 + 96 case state::num6: goto do_num6;
HITGNC   2911 + 100 case state::num7: goto do_num7;
MISUNC   2912 + ✗ case state::num8: goto do_num8;
HITGNC   2913 + 46 case state::exp1: goto do_exp1;
HITGNC   2914 + 4 case state::exp2: goto do_exp2;
HITGNC   2915 + 2873 case state::exp3: goto do_exp3;
  2916 + }
  2917 + }
  2918 +
  2919 + //----------------------------------
  2920 + //
  2921 + // DIGIT
  2922 + // first digit
  2923 + //
HITGNC   2924 + 3247 do_num1:
HITGNC   2925 + 1542 if( zero_first || nonzero_first || BOOST_JSON_LIKELY(cs) )
  2926 + {
HITGNC   2927 + 3183 char const c = *cs;
  2928 + if(zero_first)
  2929 + {
HITGNC   2930 + 1244 ++cs;
HITGNC   2931 + 1244 goto do_num6;
  2932 + }
HITGNC   2933 + 1478 else if( nonzero_first || BOOST_JSON_LIKELY(c >= '1' && c <= '9') )
  2934 + {
HITGNC   2935 + 868 ++cs;
  2936 + }
HITGNC   2937 + 1071 else if(BOOST_JSON_UNLIKELY( c == '0' ))
  2938 + {
HITGNC   2939 + 1071 ++cs;
HITGNC   2940 + 1071 goto do_num6;
  2941 + }
MISUNC   2942 + ✗ else if( negative && opt_.allow_infinity_and_nan )
  2943 + {
MISUNC   2944 + ✗ st_.push(state::lit1);
MISUNC   2945 + ✗ cur_lit_ = literal_index(detail::literals::neg_infinity);
MISUNC   2946 + ✗ lit_offset_ = 1;
MISUNC   2947 + ✗ return parse_literal(
MISUNC   2948 + ✗ cs.begin(), detail::literals_c<detail::literals::resume>() );
  2949 + }
  2950 + else
  2951 + {
  2952 + BOOST_STATIC_CONSTEXPR source_location loc
  2953 + = BOOST_CURRENT_LOCATION;
MISUNC   2954 + ✗ return fail(cs.begin(), error::syntax, &loc);
  2955 + }
  2956 + }
  2957 + else
  2958 + {
HITGNC   2959 + 64 if(BOOST_JSON_UNLIKELY(
  2960 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   2961 + ✗ return fail(cs.begin());
  2962 +
  2963 + number num;
HITGNC   2964 + 64 num.neg = negative;
HITGNC   2965 + 64 return maybe_suspend(cs.begin(), state::num1, num);
  2966 + }
  2967 +
  2968 + //----------------------------------
  2969 + //
  2970 + // 1*DIGIT
  2971 + // significant digits left of decimal
  2972 + //
HITGNC   2973 + 1313 do_num2:
HITGNC   2974 + 1313 if(negative || (!stack_empty && negative))
  2975 + {
HITGNC   2976 + 259 for(;;)
  2977 + {
HITGNC   2978 + 698 if(BOOST_JSON_UNLIKELY(! cs))
  2979 + {
HITGNC   2980 + 32 if(BOOST_JSON_UNLIKELY(more_))
  2981 + {
HITGNC   2982 + 32 if(BOOST_JSON_UNLIKELY(
  2983 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   2984 + ✗ return fail(cs.begin());
  2985 +
  2986 + number num;
HITGNC   2987 + 32 num.neg = negative;
HITGNC   2988 + 32 return suspend(cs.begin(), state::num2, num);
  2989 + }
MISUNC   2990 + ✗ goto finish_int;
  2991 + }
HITGNC   2992 + 666 char const c = *cs;
HITGNC   2993 + 666 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
  2994 + {
HITGNC   2995 + 259 ++cs;
HITGNC   2996 + 259 continue;
  2997 + }
HITGNC   2998 + 407 goto do_num6; // [.eE]
  2999 + }
  3000 + }
  3001 + else
  3002 + {
HITGNC   3003 + 5598 for(;;)
  3004 + {
HITGNC   3005 + 6472 if(BOOST_JSON_UNLIKELY(! cs))
  3006 + {
HITGNC   3007 + 186 if(BOOST_JSON_UNLIKELY(more_))
  3008 + {
HITGNC   3009 + 186 if(BOOST_JSON_UNLIKELY(
  3010 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3011 + ✗ return fail(cs.begin());
  3012 +
  3013 + number num;
HITGNC   3014 + 186 num.neg = negative;
HITGNC   3015 + 186 return suspend(cs.begin(), state::num2, num);
  3016 + }
MISUNC   3017 + ✗ goto finish_int;
  3018 + }
HITGNC   3019 + 6286 char const c = *cs;
HITGNC   3020 + 6286 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
HITGNC   3021 + 5598 ++cs;
  3022 + else
HITGNC   3023 + 688 goto do_num6; // [.eE]
  3024 + }
  3025 + }
  3026 +
  3027 + //----------------------------------
  3028 + //
  3029 + // 1*DIGIT
  3030 + // non-significant digits left of decimal
  3031 + //
MISUNC   3032 + ✗ do_num3:
MISUNC   3033 + ✗ for(;;)
  3034 + {
MISUNC   3035 + ✗ if(BOOST_JSON_UNLIKELY(! cs))
  3036 + {
MISUNC   3037 + ✗ if(BOOST_JSON_UNLIKELY(more_))
  3038 + {
MISUNC   3039 + ✗ if(BOOST_JSON_UNLIKELY(
  3040 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3041 + ✗ return fail(cs.begin());
  3042 +
  3043 + number num;
MISUNC   3044 + ✗ num.neg = negative;
MISUNC   3045 + ✗ return suspend(cs.begin(), state::num3, num);
  3046 + }
MISUNC   3047 + ✗ goto finish_dub;
  3048 + }
MISUNC   3049 + ✗ char const c = *cs;
MISUNC   3050 + ✗ if(BOOST_JSON_UNLIKELY( c >= '0' && c <= '9' ))
  3051 + {
MISUNC   3052 + ✗ ++cs;
  3053 + }
MISUNC   3054 + ✗ else if(BOOST_JSON_LIKELY( c == '.' ))
  3055 + {
MISUNC   3056 + ✗ ++cs;
MISUNC   3057 + ✗ break;
  3058 + }
MISUNC   3059 + ✗ else if( (c | 32) == 'e' )
  3060 + {
MISUNC   3061 + ✗ ++cs;
MISUNC   3062 + ✗ goto do_exp1;
  3063 + }
  3064 + else
  3065 + {
MISUNC   3066 + ✗ goto finish_dub;
  3067 + }
  3068 + }
  3069 +
  3070 + //----------------------------------
  3071 + //
  3072 + // DIGIT
  3073 + // first non-significant digit
  3074 + // to the right of decimal
  3075 + //
MISUNC   3076 + ✗ do_num4:
  3077 + {
MISUNC   3078 + ✗ if(BOOST_JSON_UNLIKELY(! cs))
  3079 + {
MISUNC   3080 + ✗ if(BOOST_JSON_UNLIKELY(
  3081 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3082 + ✗ return fail(cs.begin());
  3083 +
  3084 + number num;
MISUNC   3085 + ✗ num.neg = negative;
MISUNC   3086 + ✗ return maybe_suspend(cs.begin(), state::num4, num);
  3087 + }
MISUNC   3088 + ✗ char const c = *cs;
MISUNC   3089 + ✗ if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
  3090 + {
MISUNC   3091 + ✗ ++cs;
  3092 + }
  3093 + else
  3094 + {
  3095 + // digit required
  3096 + BOOST_STATIC_CONSTEXPR source_location loc
  3097 + = BOOST_CURRENT_LOCATION;
MISUNC   3098 + ✗ return fail(cs.begin(), error::syntax, &loc);
  3099 + }
  3100 + }
  3101 +
  3102 + //----------------------------------
  3103 + //
  3104 + // 1*DIGIT
  3105 + // non-significant digits
  3106 + // to the right of decimal
  3107 + //
HITGNC   3108 + 8711 do_num5:
HITGNC   3109 + 1084422 for(;;)
  3110 + {
HITGNC   3111 + 1093133 if(BOOST_JSON_UNLIKELY(! cs))
  3112 + {
HITGNC   3113 + 4261 if(BOOST_JSON_UNLIKELY(more_))
  3114 + {
HITGNC   3115 + 3618 if(BOOST_JSON_UNLIKELY(
  3116 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3117 + ✗ return fail(cs.begin());
  3118 +
  3119 + number num;
HITGNC   3120 + 3618 num.neg = negative;
HITGNC   3121 + 3618 return suspend(cs.begin(), state::num5, num);
  3122 + }
HITGNC   3123 + 643 goto finish_dub;
  3124 + }
HITGNC   3125 + 1088872 char const c = *cs;
HITGNC   3126 + 1088872 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
  3127 + {
HITGNC   3128 + 1084422 ++cs;
  3129 + }
HITGNC   3130 + 4450 else if( (c | 32) == 'e' )
  3131 + {
HITGNC   3132 + 2646 ++cs;
HITGNC   3133 + 2646 goto do_exp1;
  3134 + }
  3135 + else
  3136 + {
HITGNC   3137 + 1804 goto finish_dub;
  3138 + }
  3139 + }
  3140 +
  3141 + //----------------------------------
  3142 + //
  3143 + // [.eE]
  3144 + //
HITGNC   3145 + 3506 do_num6:
  3146 + {
HITGNC   3147 + 3506 if(BOOST_JSON_UNLIKELY(! cs))
  3148 + {
HITGNC   3149 + 96 if(BOOST_JSON_UNLIKELY(more_))
  3150 + {
HITGNC   3151 + 96 if(BOOST_JSON_UNLIKELY(
  3152 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3153 + ✗ return fail(cs.begin());
  3154 +
  3155 + number num;
HITGNC   3156 + 96 num.neg = negative;
HITGNC   3157 + 96 return suspend(cs.begin(), state::num6, num);
  3158 + }
MISUNC   3159 + ✗ goto finish_int;
  3160 + }
HITGNC   3161 + 3410 char const c = *cs;
HITGNC   3162 + 3410 if(BOOST_JSON_LIKELY(
  3163 + c == '.'))
  3164 + {
HITGNC   3165 + 2593 ++cs;
  3166 + }
HITGNC   3167 + 817 else if( (c | 32) == 'e' )
  3168 + {
HITGNC   3169 + 817 ++cs;
HITGNC   3170 + 817 goto do_exp1;
  3171 + }
  3172 + else
  3173 + {
MISUNC   3174 + ✗ goto finish_int;
  3175 + }
  3176 + }
  3177 +
  3178 + //----------------------------------
  3179 + //
  3180 + // DIGIT
  3181 + // first significant digit
  3182 + // to the right of decimal
  3183 + //
HITGNC   3184 + 2693 do_num7:
  3185 + {
HITGNC   3186 + 2693 if(BOOST_JSON_UNLIKELY(! cs))
  3187 + {
HITGNC   3188 + 100 if(BOOST_JSON_UNLIKELY(more_))
  3189 + {
HITGNC   3190 + 100 if(BOOST_JSON_UNLIKELY(
  3191 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3192 + ✗ return fail(cs.begin());
  3193 +
  3194 + number num;
HITGNC   3195 + 100 num.neg = negative;
HITGNC   3196 + 100 return suspend(cs.begin(), state::num7, num);
  3197 + }
  3198 + // digit required
  3199 + BOOST_STATIC_CONSTEXPR source_location loc
  3200 + = BOOST_CURRENT_LOCATION;
MISUNC   3201 + ✗ return fail(cs.begin(), error::syntax, &loc);
  3202 + }
HITGNC   3203 + 2593 char const c = *cs;
HITGNC   3204 + 2593 if(BOOST_JSON_UNLIKELY( c < '0' || c > '9' ))
  3205 + {
  3206 + // digit required
  3207 + BOOST_STATIC_CONSTEXPR source_location loc
  3208 + = BOOST_CURRENT_LOCATION;
MISUNC   3209 + ✗ return fail(cs.begin(), error::syntax, &loc);
  3210 + }
  3211 + }
  3212 +
  3213 + //----------------------------------
  3214 + //
  3215 + // 1*DIGIT
  3216 + // significant digits
  3217 + // to the right of decimal
  3218 + //
HITGNC   3219 + 2593 do_num8:
  3220 + for(;;)
  3221 + {
HITGNC   3222 + 5093 if(BOOST_JSON_UNLIKELY(! cs))
  3223 + {
MISUNC   3224 + ✗ if(BOOST_JSON_UNLIKELY(more_))
  3225 + {
MISUNC   3226 + ✗ if(BOOST_JSON_UNLIKELY(
  3227 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3228 + ✗ return fail(cs.begin());
  3229 +
  3230 + number num;
MISUNC   3231 + ✗ num.neg = negative;
MISUNC   3232 + ✗ return suspend(cs.begin(), state::num8, num);
  3233 + }
MISUNC   3234 + ✗ goto finish_dub;
  3235 + }
HITGNC   3236 + 5093 char const c = *cs;
HITGNC   3237 + 5093 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
  3238 + {
HITGNC   3239 + 5093 ++cs;
HITGNC   3240 + 5093 goto do_num5;
  3241 + }
MISUNC   3242 + ✗ else if( (c | 32) == 'e' )
  3243 + {
MISUNC   3244 + ✗ ++cs;
MISUNC   3245 + ✗ goto do_exp1;
  3246 + }
  3247 + else
  3248 + {
MISUNC   3249 + ✗ goto finish_dub;
  3250 + }
  3251 + }
  3252 +
  3253 + //----------------------------------
  3254 + //
  3255 + // *[+-]
  3256 + //
HITGNC   3257 + 5138 do_exp1:
HITGNC   3258 + 5138 if(BOOST_JSON_UNLIKELY(! cs))
  3259 + {
HITGNC   3260 + 46 if(BOOST_JSON_UNLIKELY(
  3261 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3262 + ✗ return fail(cs.begin());
  3263 +
  3264 + number num;
HITGNC   3265 + 46 num.neg = negative;
HITGNC   3266 + 46 return maybe_suspend(cs.begin(), state::exp1, num);
  3267 + }
HITGNC   3268 + 5092 if(*cs == '+')
  3269 + {
MISUNC   3270 + ✗ ++cs;
  3271 + }
HITGNC   3272 + 5092 else if(*cs == '-')
  3273 + {
HITGNC   3274 + 160 ++cs;
  3275 + }
  3276 +
  3277 + //----------------------------------
  3278 + //
  3279 + // DIGIT
  3280 + // first digit of the exponent
  3281 + //
HITGNC   3282 + 4932 do_exp2:
  3283 + {
HITGNC   3284 + 5096 if(BOOST_JSON_UNLIKELY(! cs))
  3285 + {
HITGNC   3286 + 4 if(BOOST_JSON_UNLIKELY(more_))
  3287 + {
HITGNC   3288 + 4 if(BOOST_JSON_UNLIKELY(
  3289 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3290 + ✗ return fail(cs.begin());
  3291 +
  3292 + number num;
HITGNC   3293 + 4 num.neg = negative;
HITGNC   3294 + 4 return suspend(cs.begin(), state::exp2, num);
  3295 + }
  3296 + // digit required
  3297 + BOOST_STATIC_CONSTEXPR source_location loc
  3298 + = BOOST_CURRENT_LOCATION;
MISUNC   3299 + ✗ return fail(cs.begin(), error::syntax, &loc);
  3300 + }
HITGNC   3301 + 5092 char const c = *cs;
HITGNC   3302 + 5092 if(BOOST_JSON_UNLIKELY( c < '0' || c > '9' ))
  3303 + {
  3304 + // digit required
  3305 + BOOST_STATIC_CONSTEXPR source_location loc
  3306 + = BOOST_CURRENT_LOCATION;
MISUNC   3307 + ✗ return fail(cs.begin(), error::syntax, &loc);
  3308 + }
HITGNC   3309 + 5092 ++cs;
  3310 + }
  3311 +
  3312 + //----------------------------------
  3313 + //
  3314 + // 1*DIGIT
  3315 + // subsequent digits in the exponent
  3316 + //
HITGNC   3317 + 7965 do_exp3:
HITGNC   3318 + 540852 for(;;)
  3319 + {
HITGNC   3320 + 548817 if(BOOST_JSON_UNLIKELY(! cs))
  3321 + {
HITGNC   3322 + 4683 if(BOOST_JSON_UNLIKELY(more_))
  3323 + {
HITGNC   3324 + 2873 if(BOOST_JSON_UNLIKELY(
  3325 + ! h_.on_number_part( {begin, cs.used(begin)}, ec_ )))
MISUNC   3326 + ✗ return fail(cs.begin());
  3327 +
  3328 + number num;
HITGNC   3329 + 2873 num.neg = negative;
HITGNC   3330 + 2873 return suspend(cs.begin(), state::exp3, num);
  3331 + }
  3332 + }
  3333 + else
  3334 + {
HITGNC   3335 + 544134 char const c = *cs;
HITGNC   3336 + 544134 if(BOOST_JSON_LIKELY( c >= '0' && c <= '9' ))
  3337 + {
HITGNC   3338 + 540852 ++cs;
HITGNC   3339 + 540852 continue;
  3340 + }
  3341 + }
HITGNC   3342 + 5092 goto finish_dub;
  3343 + }
  3344 +
MISUNC   3345 + ✗ finish_int:
MISUNC   3346 + ✗ if(negative)
  3347 + {
MISUNC   3348 + ✗ if(BOOST_JSON_UNLIKELY(
  3349 + ! h_.on_int64(0, {begin, cs.used(begin)}, ec_)))
MISUNC   3350 + ✗ return fail(cs.begin());
MISUNC   3351 + ✗ return cs.begin();
  3352 + }
MISUNC   3353 + ✗ finish_signed:
MISUNC   3354 + ✗ if(BOOST_JSON_UNLIKELY(
  3355 + ! h_.on_uint64(0, {begin, cs.used(begin)}, ec_)))
MISUNC   3356 + ✗ return fail(cs.begin());
MISUNC   3357 + ✗ return cs.begin();
HITGNC   3358 + 9258 finish_dub:
HITGNC   3359 + 9258 if(BOOST_JSON_UNLIKELY( !h_.on_double(0, {begin, cs.used(begin)}, ec_) ))
MISLBC 2779   1903 return fail(cs.begin()); 3360   ✗ return fail(cs.begin());
HITCBC 2780   2048455 return cs.begin(); 3361   9258 return cs.begin();
2781   } 3362   }
2782   3363  
2783   //---------------------------------------------------------- 3364   //----------------------------------------------------------
2784   3365  
2785   template<class Handler> 3366   template<class Handler>
2786   template<class... Args> 3367   template<class... Args>
HITCBC 2787   2164608 basic_parser<Handler>:: 3368   2164608 basic_parser<Handler>::
2788   basic_parser( 3369   basic_parser(
2789   parse_options const& opt, 3370   parse_options const& opt,
2790   Args&&... args) 3371   Args&&... args)
HITCBC 2791   2164600 : h_(std::forward<Args>(args)...) 3372   2164600 : h_(std::forward<Args>(args)...)
HITCBC 2792   2164608 , opt_(opt) 3373   2164608 , opt_(opt)
2793   { 3374   {
HITCBC 2794   2164608 } 3375   2164608 }
2795   3376  
2796   //---------------------------------------------------------- 3377   //----------------------------------------------------------
2797   3378  
2798   template<class Handler> 3379   template<class Handler>
2799   void 3380   void
HITCBC 2800   4153132 basic_parser<Handler>:: 3381   4153132 basic_parser<Handler>::
2801   reset() noexcept 3382   reset() noexcept
2802   { 3383   {
HITCBC 2803   4153132 ec_ = {}; 3384   4153132 ec_ = {};
HITCBC 2804   4153132 st_.clear(); 3385   4153132 st_.clear();
HITCBC 2805   4153132 more_ = true; 3386   4153132 more_ = true;
HITCBC 2806   4153132 done_ = false; 3387   4153132 done_ = false;
HITCBC 2807   4153132 clean_ = true; 3388   4153132 clean_ = true;
HITCBC 2808   4153132 num_buf_.clear(); 3389   4153132 num_buf_.clear();
HITCBC 2809   4153132 } 3390   4153132 }
2810   3391  
2811   template<class Handler> 3392   template<class Handler>
2812   void 3393   void
HITCBC 2813   16 basic_parser<Handler>:: 3394   16 basic_parser<Handler>::
2814   fail(system::error_code ec) noexcept 3395   fail(system::error_code ec) noexcept
2815   { 3396   {
HITCBC 2816   16 if(! ec) 3397   16 if(! ec)
2817   { 3398   {
2818   // assign an arbitrary 3399   // assign an arbitrary
2819   // error code to prevent UB 3400   // error code to prevent UB
MISUBC 2820   ✗ BOOST_JSON_FAIL(ec_, error::incomplete); 3401   ✗ BOOST_JSON_FAIL(ec_, error::incomplete);
2821   } 3402   }
2822   else 3403   else
2823   { 3404   {
HITCBC 2824   16 ec_ = ec; 3405   16 ec_ = ec;
2825   } 3406   }
HITCBC 2826   16 done_ = false; 3407   16 done_ = false;
HITCBC 2827   16 } 3408   16 }
2828   3409  
2829   //---------------------------------------------------------- 3410   //----------------------------------------------------------
2830   3411  
2831   template<class Handler> 3412   template<class Handler>
2832   std::size_t 3413   std::size_t
HITCBC 2833   2334223 basic_parser<Handler>:: 3414   2334223 basic_parser<Handler>::
2834   write_some( 3415   write_some(
2835   bool more, 3416   bool more,
2836   char const* data, 3417   char const* data,
2837   std::size_t size, 3418   std::size_t size,
2838   system::error_code& ec) 3419   system::error_code& ec)
2839   { 3420   {
2840   // see if we exited via exception 3421   // see if we exited via exception
2841   // on the last call to write_some 3422   // on the last call to write_some
HITCBC 2842   2334223 if(! clean_) 3423   2334223 if(! clean_)
2843   { 3424   {
2844   // prevent UB 3425   // prevent UB
HITCBC 2845   1 if(! ec_) 3426   1 if(! ec_)
2846   { 3427   {
HITCBC 2847   1 BOOST_JSON_FAIL(ec_, error::exception); 3428   1 BOOST_JSON_FAIL(ec_, error::exception);
2848   } 3429   }
2849   } 3430   }
HITCBC 2850   2334223 if(ec_) 3431   2334223 if(ec_)
2851   { 3432   {
2852   // error is sticky 3433   // error is sticky
HITCBC 2853   5 ec = ec_; 3434   5 ec = ec_;
HITCBC 2854   5 return 0; 3435   5 return 0;
2855   } 3436   }
HITCBC 2856   2334218 clean_ = false; 3437   2334218 clean_ = false;
HITCBC 2857   2334218 more_ = more; 3438   2334218 more_ = more;
HITCBC 2858   2334218 end_ = data + size; 3439   2334218 end_ = data + size;
2859   const char* p; 3440   const char* p;
HITCBC 2860   2334218 if(BOOST_JSON_LIKELY(st_.empty())) 3441   2334218 if(BOOST_JSON_LIKELY(st_.empty()))
2861   { 3442   {
2862   // first time 3443   // first time
HITCBC 2863   2164594 depth_ = opt_.max_depth; 3444   2164594 depth_ = opt_.max_depth;
HITCBC 2864   2164594 if(BOOST_JSON_UNLIKELY( 3445   2164594 if(BOOST_JSON_UNLIKELY(
2865   ! h_.on_document_begin(ec_))) 3446   ! h_.on_document_begin(ec_)))
2866   { 3447   {
HITCBC 2867   7889 ec = ec_; 3448   7889 ec = ec_;
HITCBC 2868   7889 return 0; 3449   7889 return 0;
2869   } 3450   }
HITCBC 2870   2148815 p = parse_document(data, std::true_type()); 3451   2148815 p = parse_document(data, std::true_type());
2871   } 3452   }
2872   else 3453   else
2873   { 3454   {
HITCBC 2874   169624 p = parse_document(data, std::false_type()); 3455   169624 p = parse_document(data, std::false_type());
2875   } 3456   }
2876   3457  
HITCBC 2877   2299340 if(BOOST_JSON_LIKELY(p != sentinel())) 3458   2299340 if(BOOST_JSON_LIKELY(p != sentinel()))
2878   { 3459   {
HITCBC 2879   2099052 BOOST_ASSERT(! ec_); 3460   2099052 BOOST_ASSERT(! ec_);
HITCBC 2880   2099052 if(! done_) 3461   2099052 if(! done_)
2881   { 3462   {
HITCBC 2882   2031637 done_ = true; 3463   2031637 done_ = true;
HITCBC 2883   2031637 h_.on_document_end(ec_); 3464   2031637 h_.on_document_end(ec_);
2884   } 3465   }
2885   } 3466   }
2886   else 3467   else
2887   { 3468   {
HITCBC 2888   200288 if(! ec_) 3469   200288 if(! ec_)
2889   { 3470   {
HITCBC 2890   173509 if(! more_) 3471   173509 if(! more_)
2891   { 3472   {
HITCBC 2892   573 BOOST_JSON_FAIL(ec_, error::incomplete); 3473   573 BOOST_JSON_FAIL(ec_, error::incomplete);
2893   } 3474   }
HITCBC 2894   172936 else if(! st_.empty()) 3475   172936 else if(! st_.empty())
2895   { 3476   {
2896   // consume as much trailing whitespace in 3477   // consume as much trailing whitespace in
2897   // the JSON document as possible, but still 3478   // the JSON document as possible, but still
2898   // consider the parse complete 3479   // consider the parse complete
2899   state st; 3480   state st;
HITCBC 2900   172936 st_.peek(st); 3481   172936 st_.peek(st);
HITCBC 2901   172936 if( st == state::doc3 && 3482   172936 if( st == state::doc3 &&
HITCBC 2902   88551 ! done_) 3483   88551 ! done_)
2903   { 3484   {
HITCBC 2904   70724 done_ = true; 3485   70724 done_ = true;
HITCBC 2905   70724 h_.on_document_end(ec_); 3486   70724 h_.on_document_end(ec_);
2906   } 3487   }
2907   } 3488   }
2908   } 3489   }
HITCBC 2909   198644 p = end_; 3490   198644 p = end_;
2910   } 3491   }
HITCBC 2911   2293736 ec = ec_; 3492   2293736 ec = ec_;
HITCBC 2912   2293736 clean_ = true; 3493   2293736 clean_ = true;
HITCBC 2913   2293736 return p - data; 3494   2293736 return p - data;
2914   } 3495   }
2915   3496  
2916   template<class Handler> 3497   template<class Handler>
2917   std::size_t 3498   std::size_t
HITCBC 2918   1 basic_parser<Handler>:: 3499   1 basic_parser<Handler>::
2919   write_some( 3500   write_some(
2920   bool more, 3501   bool more,
2921   char const* data, 3502   char const* data,
2922   std::size_t size, 3503   std::size_t size,
2923   std::error_code& ec) 3504   std::error_code& ec)
2924   { 3505   {
HITCBC 2925   1 system::error_code jec; 3506   1 system::error_code jec;
HITCBC 2926   1 std::size_t const result = write_some(more, data, size, jec); 3507   1 std::size_t const result = write_some(more, data, size, jec);
HITCBC 2927   1 ec = jec; 3508   1 ec = jec;
HITCBC 2928   1 return result; 3509   1 return result;
2929   } 3510   }
2930   3511  
2931   #endif 3512   #endif
2932   3513  
2933   } // namespace json 3514   } // namespace json
2934   } // namespace boost 3515   } // namespace boost
2935   3516  
2936   #ifdef _MSC_VER 3517   #ifdef _MSC_VER
2937   #pragma warning(pop) 3518   #pragma warning(pop)
2938   #endif 3519   #endif
2939   3520  
2940   #endif 3521   #endif