Line data Source code
1 : //
2 : // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
3 : // Copyright (c) 2020 Krystian Stasiowski (sdkrystian@gmail.com)
4 : //
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)
7 : //
8 : // Official repository: https://github.com/boostorg/json
9 : //
10 :
11 : #ifndef BOOST_JSON_DETAIL_PARSE_INTO_HPP
12 : #define BOOST_JSON_DETAIL_PARSE_INTO_HPP
13 :
14 : #include <boost/json/detail/config.hpp>
15 :
16 : #include <boost/json/error.hpp>
17 : #include <boost/json/conversion.hpp>
18 : #include <boost/describe/enum_from_string.hpp>
19 :
20 : #include <vector>
21 :
22 : /*
23 : * This file contains the majority of parse_into functionality, specifically
24 : * the implementation of dedicated handlers for different generic categories of
25 : * types.
26 : *
27 : * At the core of parse_into is the specialisation basic_parser<
28 : * detail::into_handler<T> >. detail::into_handler<T> is a handler for
29 : * basic_parser. It directly handles events on_comment_part and on_comment (by
30 : * ignoring them), on_document_begin (by enabling the nested dedicated
31 : * handler), and on_document_end (by disabling the nested handler).
32 : *
33 : * Every other event is handled by the nested handler, which has the type
34 : * get_handler< T, into_handler<T> >. The second parameter is the parent
35 : * handler (in this case, it's the top handler, into_handler<T>). The type is
36 : * actually an alias to class template converting_handler, which has a separate
37 : * specialisation for every conversion category from the list of generic
38 : * conversion categories (e.g. sequence_conversion_tag, tuple_conversion_tag,
39 : * etc.) Instantiations of the template store a pointer to the parent handler
40 : * and a pointer to the value T.
41 : *
42 : * The nested handler handles specific parser events by setting error_code to
43 : * an appropriate value, if it receives an event it isn't supposed to handle
44 : * (e.g. a number handler getting an on_string event), and also updates the
45 : * value when appropriate. Note that they never need to handle on_comment_part,
46 : * on_comment, on_document_begin, and on_document_end events, as those are
47 : * always handled by the top handler into_handler<T>.
48 : *
49 : * When the nested handler receives an event that completes the current value,
50 : * it is supposed to call its parent's signal_value member function. This is
51 : * necessary for correct handling of composite types (e.g. sequences).
52 : *
53 : * Finally, nested handlers should always call parent's signal_end member
54 : * function if they don't handle on_array_end themselves. This is necessary
55 : * to correctly handle nested composites (e.g. sequences inside sequences).
56 : * signal_end can return false and set error state when the containing parser
57 : * requires more elements.
58 : *
59 : * converting_handler instantiations for composite categories of types have
60 : * their own nested handlers, to which they themselves delegate events. For
61 : * complex types you will get a tree of handlers with into_handler<T> as the
62 : * root and handlers for scalars as leaves.
63 : *
64 : * To reiterate, only into_handler has to handle on_comment_part, on_comment,
65 : * on_document_begin, and on_document_end; only handlers for composites and
66 : * into_handler has to provide signal_value and signal_end; all handlers
67 : * except for into_handler have to call their parent's signal_end from
68 : * their on_array_begin, if they don't handle it themselves; once a handler
69 : * receives an event that finishes its current value, it should call its
70 : * parent's signal_value.
71 : */
72 :
73 : namespace boost {
74 : namespace json {
75 : namespace detail {
76 :
77 : template< class Impl, class T, class Parent >
78 : class converting_handler;
79 :
80 : // get_handler
81 : template< class V, class P >
82 : using get_handler = converting_handler< generic_conversion_category<V>, V, P >;
83 :
84 : template<error E> class handler_error_base
85 : {
86 : public:
87 :
88 : handler_error_base() = default;
89 :
90 : handler_error_base( handler_error_base const& ) = delete;
91 : handler_error_base& operator=( handler_error_base const& ) = delete;
92 :
93 : public:
94 :
95 2 : bool on_object_begin( system::error_code& ec ) { BOOST_JSON_FAIL( ec, E ); return false; }
96 7 : bool on_array_begin( system::error_code& ec ) { BOOST_JSON_FAIL( ec, E ); return false; }
97 : bool on_array_end( system::error_code& ec ) { BOOST_JSON_FAIL( ec, E ); return false; }
98 1 : bool on_string_part( system::error_code& ec, string_view ) { BOOST_JSON_FAIL( ec, E ); return false; }
99 60 : bool on_string( system::error_code& ec, string_view ) { BOOST_JSON_FAIL( ec, E ); return false; }
100 2 : bool on_number_part( system::error_code& ec ) { BOOST_JSON_FAIL( ec, E ); return false; }
101 8 : bool on_int64( system::error_code& ec, std::int64_t ) { BOOST_JSON_FAIL( ec, E ); return false; }
102 8 : bool on_uint64( system::error_code& ec, std::uint64_t ) { BOOST_JSON_FAIL( ec, E ); return false; }
103 7 : bool on_double( system::error_code& ec, double ) { BOOST_JSON_FAIL( ec, E ); return false; }
104 2 : bool on_bool( system::error_code& ec, bool ) { BOOST_JSON_FAIL( ec, E ); return false; }
105 4 : bool on_null( system::error_code& ec ) { BOOST_JSON_FAIL( ec, E ); return false; }
106 :
107 : // LCOV_EXCL_START
108 : // parses that can't handle this would fail at on_object_begin
109 : bool on_object_end( system::error_code& ) { BOOST_ASSERT( false ); return false; }
110 : bool on_key_part( system::error_code& ec, string_view ) { BOOST_JSON_FAIL( ec, E ); return false; }
111 : bool on_key( system::error_code& ec, string_view ) { BOOST_JSON_FAIL( ec, E ); return false; }
112 : // LCOV_EXCL_STOP
113 : };
114 :
115 : template< class P, error E >
116 : class scalar_handler
117 : : public handler_error_base<E>
118 : {
119 : protected:
120 : P* parent_;
121 :
122 : public:
123 : scalar_handler(scalar_handler const&) = delete;
124 : scalar_handler& operator=(scalar_handler const&) = delete;
125 :
126 816 : scalar_handler(P* p): parent_( p )
127 816 : {}
128 :
129 180 : bool on_array_end( system::error_code& ec )
130 : {
131 180 : return parent_->signal_end(ec);
132 : }
133 : };
134 :
135 : template< class D, class V, class P, error E >
136 : class composite_handler
137 : {
138 : protected:
139 : using inner_handler_type = get_handler<V, D>;
140 :
141 : P* parent_;
142 : #if defined(__GNUC__) && __GNUC__ < 5 && !defined(__clang__)
143 : # pragma GCC diagnostic push
144 : # pragma GCC diagnostic ignored "-Wmissing-field-initializers"
145 : #endif
146 : V next_value_ = {};
147 : inner_handler_type inner_;
148 : bool inner_active_ = false;
149 :
150 : public:
151 : composite_handler( composite_handler const& ) = delete;
152 : composite_handler& operator=( composite_handler const& ) = delete;
153 :
154 413 : composite_handler( P* p )
155 413 : : parent_(p), inner_( &next_value_, static_cast<D*>(this) )
156 413 : {}
157 : #if defined(__GNUC__) && __GNUC__ < 5 && !defined(__clang__)
158 : # pragma GCC diagnostic pop
159 : #endif
160 :
161 272 : bool signal_end(system::error_code& ec)
162 : {
163 272 : inner_active_ = false;
164 272 : return parent_->signal_value(ec);
165 : }
166 :
167 : #define BOOST_JSON_INVOKE_INNER(f) \
168 : if( !inner_active_ ) { \
169 : BOOST_JSON_FAIL(ec, E); \
170 : return false; \
171 : } \
172 : else \
173 : return inner_.f
174 :
175 21 : bool on_object_begin( system::error_code& ec )
176 : {
177 21 : BOOST_JSON_INVOKE_INNER( on_object_begin(ec) );
178 : }
179 :
180 21 : bool on_object_end( system::error_code& ec )
181 : {
182 21 : BOOST_JSON_INVOKE_INNER( on_object_end(ec) );
183 : }
184 :
185 59 : bool on_array_begin( system::error_code& ec )
186 : {
187 59 : BOOST_JSON_INVOKE_INNER( on_array_begin(ec) );
188 : }
189 :
190 : bool on_array_end( system::error_code& ec )
191 : {
192 : BOOST_JSON_INVOKE_INNER( on_array_end(ec) );
193 : }
194 :
195 3 : bool on_key_part( system::error_code& ec, string_view sv )
196 : {
197 3 : BOOST_JSON_INVOKE_INNER( on_key_part(ec, sv) );
198 : }
199 :
200 21 : bool on_key( system::error_code& ec, string_view sv )
201 : {
202 21 : BOOST_JSON_INVOKE_INNER( on_key(ec, sv) );
203 : }
204 :
205 24 : bool on_string_part( system::error_code& ec, string_view sv )
206 : {
207 24 : BOOST_JSON_INVOKE_INNER( on_string_part(ec, sv) );
208 : }
209 :
210 50 : bool on_string( system::error_code& ec, string_view sv )
211 : {
212 50 : BOOST_JSON_INVOKE_INNER( on_string(ec, sv) );
213 : }
214 :
215 229 : bool on_number_part( system::error_code& ec )
216 : {
217 229 : BOOST_JSON_INVOKE_INNER( on_number_part(ec) );
218 : }
219 :
220 894 : bool on_int64( system::error_code& ec, std::int64_t v )
221 : {
222 894 : BOOST_JSON_INVOKE_INNER( on_int64(ec, v) );
223 : }
224 :
225 7 : bool on_uint64( system::error_code& ec, std::uint64_t v )
226 : {
227 7 : BOOST_JSON_INVOKE_INNER( on_uint64(ec, v) );
228 : }
229 :
230 42 : bool on_double( system::error_code& ec, double v )
231 : {
232 42 : BOOST_JSON_INVOKE_INNER( on_double(ec, v) );
233 : }
234 :
235 21 : bool on_bool( system::error_code& ec, bool v )
236 : {
237 21 : BOOST_JSON_INVOKE_INNER( on_bool(ec, v) );
238 : }
239 :
240 14 : bool on_null( system::error_code& ec )
241 : {
242 14 : BOOST_JSON_INVOKE_INNER( on_null(ec) );
243 : }
244 :
245 : #undef BOOST_JSON_INVOKE_INNER
246 : };
247 :
248 : // integral handler
249 : template<class V,
250 : typename std::enable_if<std::is_signed<V>::value, int>::type = 0>
251 680 : bool integral_in_range( std::int64_t v )
252 : {
253 680 : return v >= (std::numeric_limits<V>::min)() && v <= (std::numeric_limits<V>::max)();
254 : }
255 :
256 : template<class V,
257 : typename std::enable_if<!std::is_signed<V>::value, int>::type = 0>
258 35 : bool integral_in_range( std::int64_t v )
259 : {
260 35 : return v >= 0 && static_cast<std::uint64_t>( v ) <= (std::numeric_limits<V>::max)();
261 : }
262 :
263 : template<class V>
264 37 : bool integral_in_range( std::uint64_t v )
265 : {
266 37 : return v <= static_cast<typename std::make_unsigned<V>::type>( (std::numeric_limits<V>::max)() );
267 : }
268 :
269 : template< class V, class P >
270 : class converting_handler<integral_conversion_tag, V, P>
271 : : public scalar_handler<P, error::not_integer>
272 : {
273 : private:
274 : V* value_;
275 :
276 : public:
277 553 : converting_handler( V* v, P* p )
278 : : converting_handler::scalar_handler(p)
279 553 : , value_(v)
280 553 : {}
281 :
282 319 : bool on_number_part( system::error_code& )
283 : {
284 319 : return true;
285 : }
286 :
287 715 : bool on_int64(system::error_code& ec, std::int64_t v)
288 : {
289 715 : if( !integral_in_range<V>( v ) )
290 : {
291 2 : BOOST_JSON_FAIL( ec, error::not_exact );
292 2 : return false;
293 : }
294 :
295 713 : *value_ = static_cast<V>( v );
296 713 : return this->parent_->signal_value(ec);
297 : }
298 :
299 37 : bool on_uint64(system::error_code& ec, std::uint64_t v)
300 : {
301 37 : if( !integral_in_range<V>(v) )
302 : {
303 2 : BOOST_JSON_FAIL( ec, error::not_exact );
304 2 : return false;
305 : }
306 :
307 35 : *value_ = static_cast<V>(v);
308 35 : return this->parent_->signal_value(ec);
309 : }
310 : };
311 :
312 : // floating point handler
313 : template< class V, class P>
314 : class converting_handler<floating_point_conversion_tag, V, P>
315 : : public scalar_handler<P, error::not_double>
316 : {
317 : private:
318 : V* value_;
319 :
320 : public:
321 53 : converting_handler( V* v, P* p )
322 : : converting_handler::scalar_handler(p)
323 53 : , value_(v)
324 53 : {}
325 :
326 99 : bool on_number_part( system::error_code& )
327 : {
328 99 : return true;
329 : }
330 :
331 1 : bool on_int64(system::error_code& ec, std::int64_t v)
332 : {
333 1 : *value_ = static_cast<V>(v);
334 1 : return this->parent_->signal_value(ec);
335 : }
336 :
337 1 : bool on_uint64(system::error_code& ec, std::uint64_t v)
338 : {
339 1 : *value_ = static_cast<V>(v);
340 1 : return this->parent_->signal_value(ec);
341 : }
342 :
343 63 : bool on_double(system::error_code& ec, double v)
344 : {
345 63 : *value_ = static_cast<V>(v);
346 63 : return this->parent_->signal_value(ec);
347 : }
348 : };
349 :
350 : // string handler
351 : template< class V, class P >
352 : class converting_handler<string_like_conversion_tag, V, P>
353 : : public scalar_handler<P, error::not_string>
354 : {
355 : private:
356 : V* value_;
357 : bool cleared_ = false;
358 :
359 : public:
360 95 : converting_handler( V* v, P* p )
361 : : converting_handler::scalar_handler(p)
362 95 : , value_(v)
363 95 : {}
364 :
365 21 : bool on_string_part( system::error_code&, string_view sv )
366 : {
367 21 : if( !cleared_ )
368 : {
369 5 : cleared_ = true;
370 5 : value_->clear();
371 : }
372 :
373 21 : value_->append( sv.begin(), sv.end() );
374 21 : return true;
375 : }
376 :
377 100 : bool on_string(system::error_code& ec, string_view sv)
378 : {
379 100 : if( !cleared_ )
380 95 : value_->clear();
381 : else
382 5 : cleared_ = false;
383 :
384 100 : value_->append( sv.begin(), sv.end() );
385 100 : return this->parent_->signal_value(ec);
386 : }
387 : };
388 :
389 : // bool handler
390 : template< class V, class P >
391 : class converting_handler<bool_conversion_tag, V, P>
392 : : public scalar_handler<P, error::not_bool>
393 : {
394 : private:
395 : V* value_;
396 :
397 : public:
398 60 : converting_handler( V* v, P* p )
399 : : converting_handler::scalar_handler(p)
400 60 : , value_(v)
401 60 : {}
402 :
403 42 : bool on_bool(system::error_code& ec, bool v)
404 : {
405 42 : *value_ = v;
406 42 : return this->parent_->signal_value(ec);
407 : }
408 : };
409 :
410 : // null handler
411 : template< class V, class P >
412 : class converting_handler<null_like_conversion_tag, V, P>
413 : : public scalar_handler<P, error::not_null>
414 : {
415 : private:
416 : V* value_;
417 :
418 : public:
419 55 : converting_handler( V* v, P* p )
420 : : converting_handler::scalar_handler(p)
421 55 : , value_(v)
422 55 : {}
423 :
424 35 : bool on_null(system::error_code& ec)
425 : {
426 35 : *value_ = {};
427 35 : return this->parent_->signal_value(ec);
428 : }
429 : };
430 :
431 : // described enum handler
432 : template< class V, class P >
433 : class converting_handler<described_enum_conversion_tag, V, P>
434 : : public scalar_handler<P, error::not_string>
435 : {
436 : #ifndef BOOST_DESCRIBE_CXX14
437 :
438 : static_assert(
439 : sizeof(V) == 0, "Enum support for parse_into requires C++14" );
440 :
441 : #else
442 :
443 : private:
444 : V* value_;
445 : std::string name_;
446 :
447 : public:
448 : converting_handler( V* v, P* p )
449 : : converting_handler::scalar_handler(p)
450 : , value_(v)
451 : {}
452 :
453 : bool on_string_part( system::error_code&, string_view sv )
454 : {
455 : name_.append( sv.begin(), sv.end() );
456 : return true;
457 : }
458 :
459 : bool on_string(system::error_code& ec, string_view sv)
460 : {
461 : string_view name = sv;
462 : if( !name_.empty() )
463 : {
464 : name_.append( sv.begin(), sv.end() );
465 : name = name_;
466 : }
467 :
468 : if( !describe::enum_from_string(name, *value_) )
469 : {
470 : BOOST_JSON_FAIL(ec, error::unknown_name);
471 : return false;
472 : }
473 :
474 : return this->parent_->signal_value(ec);
475 : }
476 :
477 : #endif // BOOST_DESCRIBE_CXX14
478 : };
479 :
480 : template< class V, class P >
481 : class converting_handler<no_conversion_tag, V, P>
482 : {
483 : static_assert( sizeof(V) == 0, "This type is not supported" );
484 : };
485 :
486 : // sequence handler
487 : template< class It >
488 128 : bool cannot_insert(It i, It e)
489 : {
490 128 : return i == e;
491 : }
492 :
493 : template< class It1, class It2 >
494 507 : std::false_type cannot_insert(It1, It2)
495 : {
496 507 : return {};
497 : }
498 :
499 : template< class It >
500 30 : bool needs_more_elements(It i, It e)
501 : {
502 30 : return i != e;
503 : }
504 :
505 : template< class It1, class It2 >
506 244 : std::false_type needs_more_elements(It1, It2)
507 : {
508 244 : return {};
509 : }
510 :
511 : template<class T>
512 : void
513 32 : clear_container(
514 : T&,
515 : mp11::mp_int<2>)
516 : {
517 32 : }
518 :
519 : template<class T>
520 : void
521 260 : clear_container(
522 : T& target,
523 : mp11::mp_int<1>)
524 : {
525 260 : target.clear();
526 260 : }
527 :
528 : template<class T>
529 : void
530 149 : clear_container(
531 : T& target,
532 : mp11::mp_int<0>)
533 : {
534 149 : target.clear();
535 149 : }
536 :
537 : template< class V, class P >
538 : class converting_handler<sequence_conversion_tag, V, P>
539 : : public composite_handler<
540 : converting_handler<sequence_conversion_tag, V, P>,
541 : detail::value_type<V>,
542 : P,
543 : error::not_array>
544 : {
545 : private:
546 : V* value_;
547 :
548 : using Inserter = decltype(
549 : detail::inserter(*value_, inserter_implementation<V>()) );
550 : Inserter inserter;
551 :
552 : public:
553 276 : converting_handler( V* v, P* p )
554 : : converting_handler::composite_handler(p)
555 276 : , value_(v)
556 276 : , inserter( detail::inserter(*value_, inserter_implementation<V>()) )
557 276 : {}
558 :
559 635 : bool signal_value(system::error_code& ec)
560 : {
561 635 : if(cannot_insert( inserter, value_->end() ))
562 : {
563 2 : BOOST_JSON_FAIL( ec, error::size_mismatch );
564 2 : return false;
565 : }
566 :
567 633 : *inserter++ = std::move(this->next_value_);
568 : #if defined(__GNUC__) && __GNUC__ < 5 && !defined(__clang__)
569 : # pragma GCC diagnostic push
570 : # pragma GCC diagnostic ignored "-Wmissing-field-initializers"
571 : #endif
572 633 : this->next_value_ = {};
573 : #if defined(__GNUC__) && __GNUC__ < 5 && !defined(__clang__)
574 : # pragma GCC diagnostic pop
575 : #endif
576 633 : return true;
577 : }
578 :
579 274 : bool signal_end(system::error_code& ec)
580 : {
581 274 : if(needs_more_elements( inserter, value_->end() ))
582 : {
583 2 : BOOST_JSON_FAIL( ec, error::size_mismatch );
584 2 : return false;
585 : }
586 :
587 272 : inserter = detail::inserter(*value_, inserter_implementation<V>());
588 :
589 272 : return converting_handler::composite_handler::signal_end(ec);
590 : }
591 :
592 474 : bool on_array_begin( system::error_code& ec )
593 : {
594 474 : if( this->inner_active_ )
595 182 : return this->inner_.on_array_begin( ec );
596 :
597 292 : this->inner_active_ = true;
598 292 : clear_container( *value_, inserter_implementation<V>() );
599 292 : return true;
600 : }
601 :
602 498 : bool on_array_end( system::error_code& ec )
603 : {
604 498 : if( this->inner_active_ )
605 456 : return this->inner_.on_array_end( ec );
606 :
607 42 : return this->parent_->signal_end(ec);
608 : }
609 : };
610 :
611 : // map handler
612 : template< class V, class P >
613 : class converting_handler<map_like_conversion_tag, V, P>
614 : : public composite_handler<
615 : converting_handler<map_like_conversion_tag, V, P>,
616 : detail::mapped_type<V>,
617 : P,
618 : error::not_object>
619 : {
620 : private:
621 : V* value_;
622 : std::string key_;
623 :
624 : public:
625 137 : converting_handler( V* v, P* p )
626 137 : : converting_handler::composite_handler(p), value_(v)
627 137 : {}
628 :
629 135 : bool signal_value(system::error_code&)
630 : {
631 135 : value_->emplace( std::move(key_), std::move(this->next_value_) );
632 :
633 135 : key_ = {};
634 135 : this->next_value_ = {};
635 :
636 135 : this->inner_active_ = false;
637 :
638 135 : return true;
639 : }
640 :
641 165 : bool on_object_begin( system::error_code& ec )
642 : {
643 165 : if( this->inner_active_ )
644 16 : return this->inner_.on_object_begin(ec);
645 :
646 149 : clear_container( *value_, inserter_implementation<V>() );
647 149 : return true;
648 : }
649 :
650 154 : bool on_object_end(system::error_code& ec)
651 : {
652 154 : if( this->inner_active_ )
653 16 : return this->inner_.on_object_end(ec);
654 :
655 138 : return this->parent_->signal_value(ec);
656 : }
657 :
658 60 : bool on_array_end( system::error_code& ec )
659 : {
660 60 : if( this->inner_active_ )
661 53 : return this->inner_.on_array_end(ec);
662 :
663 7 : return this->parent_->signal_end(ec);
664 : }
665 :
666 45 : bool on_key_part( system::error_code& ec, string_view sv )
667 : {
668 45 : if( this->inner_active_ )
669 2 : return this->inner_.on_key_part(ec, sv);
670 :
671 43 : key_.append( sv.data(), sv.size() );
672 43 : return true;
673 : }
674 :
675 160 : bool on_key( system::error_code& ec, string_view sv )
676 : {
677 160 : if( this->inner_active_ )
678 14 : return this->inner_.on_key(ec, sv);
679 :
680 146 : key_.append( sv.data(), sv.size() );
681 :
682 146 : this->inner_active_ = true;
683 146 : return true;
684 : }
685 : };
686 :
687 : // tuple handler
688 : template<std::size_t I, class T>
689 : struct handler_tuple_element
690 : {
691 : template< class... Args >
692 286 : handler_tuple_element( Args&& ... args )
693 286 : : t_( static_cast<Args&&>(args)... )
694 286 : {}
695 :
696 : T t_;
697 : };
698 :
699 : template<std::size_t I, class T>
700 : T&
701 516 : get( handler_tuple_element<I, T>& e )
702 : {
703 516 : return e.t_;
704 : }
705 :
706 : template<
707 : class P,
708 : class LV,
709 : class S = mp11::make_index_sequence<mp11::mp_size<LV>::value> >
710 : struct handler_tuple;
711 :
712 : template< class P, template<class...> class L, class... V, std::size_t... I >
713 : struct handler_tuple< P, L<V...>, mp11::index_sequence<I...> >
714 : : handler_tuple_element<I, V>
715 : ...
716 : {
717 : handler_tuple( handler_tuple const& ) = delete;
718 : handler_tuple& operator=( handler_tuple const& ) = delete;
719 :
720 : template< class Access, class T >
721 129 : handler_tuple( Access access, T* pv, P* pp )
722 : : handler_tuple_element<I, V>(
723 6 : access( pv, mp11::mp_size_t<I>() ),
724 : pp )
725 129 : ...
726 129 : {}
727 : };
728 :
729 : #if defined(BOOST_MSVC) && BOOST_MSVC < 1910
730 :
731 : template< class T >
732 : struct tuple_element_list_impl
733 : {
734 : template< class I >
735 : using tuple_element_helper = tuple_element_t<I::value, T>;
736 :
737 : using type = mp11::mp_transform<
738 : tuple_element_helper,
739 : mp11::mp_iota< std::tuple_size<T> > >;
740 : };
741 : template< class T >
742 : using tuple_element_list = typename tuple_element_list_impl<T>::type;
743 :
744 : #else
745 :
746 : template< class I, class T >
747 : using tuple_element_helper = tuple_element_t<I::value, T>;
748 : template< class T >
749 : using tuple_element_list = mp11::mp_transform_q<
750 : mp11::mp_bind_back< tuple_element_helper, T>,
751 : mp11::mp_iota< std::tuple_size<T> > >;
752 :
753 : #endif
754 :
755 : template< class Op, class... Args>
756 : struct handler_op_invoker
757 : {
758 : public:
759 : std::tuple<Args&...> args;
760 :
761 : template< class Handler >
762 : bool
763 466 : operator()( Handler& handler ) const
764 : {
765 466 : return (*this)( handler, mp11::index_sequence_for<Args...>() );
766 : }
767 :
768 : private:
769 : template< class Handler, std::size_t... I >
770 : bool
771 466 : operator()( Handler& handler, mp11::index_sequence<I...> ) const
772 : {
773 466 : return Op()( handler, std::get<I>(args)... );
774 : }
775 : };
776 :
777 : template< class Handlers, class F >
778 : struct tuple_handler_op_invoker
779 : {
780 : Handlers& handlers;
781 : F fn;
782 :
783 : template< class I >
784 : bool
785 466 : operator()( I ) const
786 : {
787 466 : return fn( get<I::value>(handlers) );
788 : }
789 : };
790 :
791 : struct tuple_accessor
792 : {
793 : template< class T, class I >
794 286 : auto operator()( T* t, I ) const -> tuple_element_t<I::value, T>*
795 : {
796 : using std::get;
797 286 : return &get<I::value>(*t);
798 : }
799 : };
800 :
801 : template< class T, class P >
802 : class converting_handler<tuple_conversion_tag, T, P>
803 : {
804 :
805 : private:
806 : using ElementTypes = tuple_element_list<T>;
807 :
808 : template<class V>
809 : using ElementHandler = get_handler<V, converting_handler>;
810 : using InnerHandlers = mp11::mp_transform<ElementHandler, ElementTypes>;
811 : using HandlerTuple = handler_tuple<converting_handler, InnerHandlers>;
812 :
813 : T* value_;
814 : P* parent_;
815 :
816 : HandlerTuple handlers_;
817 : int inner_active_ = -1;
818 :
819 : public:
820 : converting_handler( converting_handler const& ) = delete;
821 : converting_handler& operator=( converting_handler const& ) = delete;
822 :
823 129 : converting_handler( T* v, P* p )
824 129 : : value_(v) , parent_(p) , handlers_(tuple_accessor(), v, this)
825 129 : {}
826 :
827 283 : bool signal_value(system::error_code&)
828 : {
829 283 : ++inner_active_;
830 283 : return true;
831 : }
832 :
833 123 : bool signal_end(system::error_code& ec)
834 : {
835 123 : constexpr int N = std::tuple_size<T>::value;
836 123 : if( inner_active_ < N )
837 : {
838 4 : BOOST_JSON_FAIL( ec, error::size_mismatch );
839 4 : return false;
840 : }
841 :
842 119 : inner_active_ = -1;
843 119 : return parent_->signal_value(ec);
844 : }
845 :
846 : #define BOOST_JSON_HANDLE_EVENT(fn) \
847 : struct do_ ## fn \
848 : { \
849 : template< class H, class... Args > \
850 : bool operator()( H& h, Args& ... args ) const \
851 : { \
852 : return h. fn (args...); \
853 : } \
854 : }; \
855 : \
856 : template< class... Args > \
857 : bool fn( system::error_code& ec, Args&& ... args ) \
858 : { \
859 : if( inner_active_ < 0 ) \
860 : { \
861 : BOOST_JSON_FAIL( ec, error::not_array ); \
862 : return false; \
863 : } \
864 : constexpr int N = std::tuple_size<T>::value; \
865 : if( inner_active_ >= N ) \
866 : { \
867 : BOOST_JSON_FAIL( ec, error::size_mismatch ); \
868 : return false; \
869 : } \
870 : using F = handler_op_invoker< do_ ## fn, system::error_code, Args...>; \
871 : using H = decltype(handlers_); \
872 : return mp11::mp_with_index<N>( \
873 : inner_active_, \
874 : tuple_handler_op_invoker<H, F>{ \
875 : handlers_, \
876 : F{ std::forward_as_tuple(ec, args...) } } ); \
877 : }
878 :
879 56 : BOOST_JSON_HANDLE_EVENT( on_object_begin )
880 42 : BOOST_JSON_HANDLE_EVENT( on_object_end )
881 :
882 : struct do_on_array_begin
883 : {
884 : HandlerTuple& handlers;
885 : system::error_code& ec;
886 :
887 : template< class I >
888 23 : bool operator()( I ) const
889 : {
890 23 : return get<I::value>(handlers).on_array_begin(ec);
891 : }
892 : };
893 159 : bool on_array_begin( system::error_code& ec )
894 : {
895 159 : if( inner_active_ < 0 )
896 : {
897 134 : inner_active_ = 0;
898 134 : return true;
899 : }
900 :
901 25 : constexpr int N = std::tuple_size<T>::value;
902 :
903 25 : if( inner_active_ >= N )
904 : {
905 2 : BOOST_JSON_FAIL( ec, error::size_mismatch );
906 2 : return false;
907 : }
908 :
909 23 : return mp11::mp_with_index<N>(
910 23 : inner_active_, do_on_array_begin{handlers_, ec} );
911 : }
912 :
913 : struct do_on_array_end
914 : {
915 : HandlerTuple& handlers;
916 : system::error_code& ec;
917 :
918 : template< class I >
919 27 : bool operator()( I ) const
920 : {
921 27 : return get<I::value>(handlers).on_array_end(ec);
922 : }
923 : };
924 195 : bool on_array_end( system::error_code& ec )
925 : {
926 195 : if( inner_active_ < 0 )
927 49 : return parent_->signal_end(ec);
928 :
929 146 : constexpr int N = std::tuple_size<T>::value;
930 :
931 146 : if( inner_active_ >= N )
932 119 : return signal_end(ec);
933 :
934 27 : return mp11::mp_with_index<N>(
935 27 : inner_active_, do_on_array_end{handlers_, ec} );
936 : }
937 :
938 6 : BOOST_JSON_HANDLE_EVENT( on_key_part )
939 56 : BOOST_JSON_HANDLE_EVENT( on_key )
940 10 : BOOST_JSON_HANDLE_EVENT( on_string_part )
941 56 : BOOST_JSON_HANDLE_EVENT( on_string )
942 152 : BOOST_JSON_HANDLE_EVENT( on_number_part )
943 432 : BOOST_JSON_HANDLE_EVENT( on_int64 )
944 14 : BOOST_JSON_HANDLE_EVENT( on_uint64 )
945 70 : BOOST_JSON_HANDLE_EVENT( on_double )
946 28 : BOOST_JSON_HANDLE_EVENT( on_bool )
947 14 : BOOST_JSON_HANDLE_EVENT( on_null )
948 :
949 : #undef BOOST_JSON_HANDLE_EVENT
950 : };
951 :
952 : // described struct handler
953 : #if defined(BOOST_MSVC) && BOOST_MSVC < 1910
954 :
955 : template< class T >
956 : struct struct_element_list_impl
957 : {
958 : template< class D >
959 : using helper = described_member_t<T, D>;
960 :
961 : using type = mp11::mp_transform< helper, described_members<T> >;
962 : };
963 : template< class T >
964 : using struct_element_list = typename struct_element_list_impl<T>::type;
965 :
966 : #else
967 :
968 : template< class T >
969 : using struct_element_list = mp11::mp_transform_q<
970 : mp11::mp_bind_front< described_member_t, T >, described_members<T> >;
971 :
972 : #endif
973 :
974 : struct struct_accessor
975 : {
976 : template< class T >
977 : auto operator()( T*, mp11::mp_size< described_members<T> > ) const
978 : -> void*
979 : {
980 : return nullptr;
981 : }
982 :
983 : template< class T, class I >
984 : auto operator()( T* t, I ) const
985 : -> described_member_t<T, mp11::mp_at< described_members<T>, I> >*
986 : {
987 : using Ds = described_members<T>;
988 : using D = mp11::mp_at<Ds, I>;
989 : return &(t->*D::pointer);
990 : }
991 : };
992 :
993 : struct struct_key_searcher
994 : {
995 : string_view key;
996 : int& found;
997 : int index = 0;
998 :
999 : struct_key_searcher(string_view key, int& found) noexcept
1000 : : key(key), found(found)
1001 : {}
1002 :
1003 : template< class D >
1004 : void
1005 : operator()( D )
1006 : {
1007 : if( key == D::name )
1008 : found = index;
1009 : ++index;
1010 : }
1011 : };
1012 :
1013 : template<class P>
1014 : struct ignoring_handler
1015 : {
1016 : P* parent_;
1017 : std::size_t array_depth_ = 0;
1018 : std::size_t object_depth_ = 0;
1019 :
1020 : ignoring_handler(ignoring_handler const&) = delete;
1021 : ignoring_handler& operator=(ignoring_handler const&) = delete;
1022 :
1023 : ignoring_handler(void*, P* p) noexcept
1024 : : parent_(p)
1025 : {}
1026 :
1027 : bool on_object_begin(system::error_code&)
1028 : {
1029 : ++object_depth_;
1030 : return true;
1031 : }
1032 :
1033 : bool on_object_end(system::error_code& ec)
1034 : {
1035 : BOOST_ASSERT( object_depth_ > 0 );
1036 : --object_depth_;
1037 :
1038 : if( (array_depth_ + object_depth_) == 0 )
1039 : return parent_->signal_value(ec);
1040 : return true;
1041 : }
1042 :
1043 : bool on_array_begin(system::error_code&)
1044 : {
1045 : ++array_depth_;
1046 : return true;
1047 : }
1048 :
1049 : bool on_array_end(system::error_code& ec)
1050 : {
1051 : BOOST_ASSERT( array_depth_ > 0 );
1052 : --array_depth_;
1053 :
1054 : if( (array_depth_ + object_depth_) == 0 )
1055 : return parent_->signal_end(ec);
1056 : return true;
1057 : }
1058 :
1059 : bool on_key_part(system::error_code&, string_view)
1060 : {
1061 : return true;
1062 : }
1063 :
1064 : bool on_key(system::error_code&, string_view)
1065 : {
1066 : return true;
1067 : }
1068 :
1069 : bool on_string_part(system::error_code&, string_view)
1070 : {
1071 : return true;
1072 : }
1073 :
1074 : bool on_string(system::error_code& ec, string_view)
1075 : {
1076 : if( (array_depth_ + object_depth_) == 0 )
1077 : return parent_->signal_value(ec);
1078 : return true;
1079 : }
1080 :
1081 : bool on_number_part(system::error_code&)
1082 : {
1083 : return true;
1084 : }
1085 :
1086 : bool on_int64(system::error_code& ec, std::int64_t)
1087 : {
1088 : if( (array_depth_ + object_depth_) == 0 )
1089 : return parent_->signal_value(ec);
1090 : return true;
1091 : }
1092 :
1093 : bool on_uint64(system::error_code& ec, std::uint64_t)
1094 : {
1095 : if( (array_depth_ + object_depth_) == 0 )
1096 : return parent_->signal_value(ec);
1097 : return true;
1098 : }
1099 :
1100 : bool on_double(system::error_code& ec, double)
1101 : {
1102 : if( (array_depth_ + object_depth_) == 0 )
1103 : return parent_->signal_value(ec);
1104 : return true;
1105 : }
1106 :
1107 : bool on_bool(system::error_code& ec, bool)
1108 : {
1109 : if( (array_depth_ + object_depth_) == 0 )
1110 : return parent_->signal_value(ec);
1111 : return true;
1112 : }
1113 :
1114 : bool on_null(system::error_code& ec)
1115 : {
1116 : if( (array_depth_ + object_depth_) == 0 )
1117 : return parent_->signal_value(ec);
1118 : return true;
1119 : }
1120 : };
1121 :
1122 : template<class V, class P>
1123 : class converting_handler<described_class_conversion_tag, V, P>
1124 : {
1125 : #if !defined(BOOST_DESCRIBE_CXX14)
1126 :
1127 : static_assert(
1128 : sizeof(V) == 0, "Struct support for parse_into requires C++14" );
1129 :
1130 : #else
1131 :
1132 : private:
1133 : static_assert(
1134 : uniquely_named_members<V>::value,
1135 : "The type has several described members with the same name.");
1136 :
1137 : using Dm = described_members<V>;
1138 : using Dt = struct_element_list<V>;
1139 :
1140 : template<class T>
1141 : using MemberHandler = get_handler<T, converting_handler>;
1142 : using InnerHandlers = mp11::mp_push_back<
1143 : mp11::mp_transform<MemberHandler, Dt>,
1144 : ignoring_handler<converting_handler> >;
1145 : using InnerCount = mp11::mp_size<InnerHandlers>;
1146 :
1147 : V* value_;
1148 : P* parent_;
1149 :
1150 : std::string key_;
1151 :
1152 : handler_tuple<converting_handler, InnerHandlers> handlers_;
1153 : int inner_active_ = -1;
1154 : std::size_t activated_ = 0;
1155 :
1156 : public:
1157 : converting_handler( converting_handler const& ) = delete;
1158 : converting_handler& operator=( converting_handler const& ) = delete;
1159 :
1160 : converting_handler( V* v, P* p )
1161 : : value_(v), parent_(p), handlers_(struct_accessor(), v, this)
1162 : {}
1163 :
1164 : struct is_required_checker
1165 : {
1166 : bool operator()( mp11::mp_size<Dt> ) const noexcept
1167 : {
1168 : return false;
1169 : }
1170 :
1171 : template< class I >
1172 : auto operator()( I ) const noexcept
1173 : {
1174 : using T = mp11::mp_at<Dt, I>;
1175 : return !is_optional_like<T>::value;
1176 : }
1177 : };
1178 :
1179 : bool signal_value(system::error_code&)
1180 : {
1181 : BOOST_ASSERT( inner_active_ >= 0 );
1182 : bool required_member = mp11::mp_with_index<InnerCount>(
1183 : inner_active_,
1184 : is_required_checker{});
1185 : if( required_member )
1186 : ++activated_;
1187 :
1188 : key_ = {};
1189 : inner_active_ = -1;
1190 : return true;
1191 : }
1192 :
1193 : bool signal_end(system::error_code& ec)
1194 : {
1195 : key_ = {};
1196 : inner_active_ = -1;
1197 : return parent_->signal_value(ec);
1198 : }
1199 :
1200 : #define BOOST_JSON_INVOKE_INNER(fn) \
1201 : if( inner_active_ < 0 ) \
1202 : { \
1203 : BOOST_JSON_FAIL( ec, error::not_object ); \
1204 : return false; \
1205 : } \
1206 : auto f = [&](auto& handler) { return handler.fn ; }; \
1207 : using F = decltype(f); \
1208 : using H = decltype(handlers_); \
1209 : return mp11::mp_with_index<InnerCount>( \
1210 : inner_active_, \
1211 : tuple_handler_op_invoker<H, F>{handlers_, f} );
1212 :
1213 : bool on_object_begin( system::error_code& ec )
1214 : {
1215 : if( inner_active_ < 0 )
1216 : return true;
1217 :
1218 : BOOST_JSON_INVOKE_INNER( on_object_begin(ec) );
1219 : }
1220 :
1221 : bool on_object_end( system::error_code& ec )
1222 : {
1223 : if( inner_active_ < 0 )
1224 : {
1225 : using C = mp11::mp_count_if<Dt, is_optional_like>;
1226 : constexpr int N = mp11::mp_size<Dt>::value - C::value;
1227 : if( activated_ < N )
1228 : {
1229 : BOOST_JSON_FAIL( ec, error::size_mismatch );
1230 : return false;
1231 : }
1232 :
1233 : return parent_->signal_value(ec);
1234 : }
1235 :
1236 : BOOST_JSON_INVOKE_INNER( on_object_end(ec) );
1237 : }
1238 :
1239 : bool on_array_begin( system::error_code& ec )
1240 : {
1241 : BOOST_JSON_INVOKE_INNER( on_array_begin(ec) );
1242 : }
1243 :
1244 : bool on_array_end( system::error_code& ec )
1245 : {
1246 : if( inner_active_ < 0 )
1247 : return parent_->signal_end(ec);
1248 :
1249 : BOOST_JSON_INVOKE_INNER( on_array_end(ec) );
1250 : }
1251 :
1252 : bool on_key_part( system::error_code& ec, string_view sv )
1253 : {
1254 : if( inner_active_ < 0 )
1255 : {
1256 : key_.append( sv.data(), sv.size() );
1257 : return true;
1258 : }
1259 :
1260 : BOOST_JSON_INVOKE_INNER( on_key_part(ec, sv) );
1261 : }
1262 :
1263 : bool on_key( system::error_code& ec, string_view sv )
1264 : {
1265 : if( inner_active_ >= 0 )
1266 : {
1267 : BOOST_JSON_INVOKE_INNER( on_key(ec, sv) );
1268 : }
1269 :
1270 : string_view key = sv;
1271 : if( !key_.empty() )
1272 : {
1273 : key_.append( sv.data(), sv.size() );
1274 : key = key_;
1275 : }
1276 :
1277 : inner_active_ = InnerCount::value - 1;
1278 : mp11::mp_for_each<Dm>( struct_key_searcher(key, inner_active_) );
1279 : return true;
1280 : }
1281 :
1282 : bool on_string_part( system::error_code& ec, string_view sv )
1283 : {
1284 : BOOST_JSON_INVOKE_INNER( on_string_part(ec, sv) );
1285 : }
1286 :
1287 : bool on_string( system::error_code& ec, string_view sv )
1288 : {
1289 : BOOST_JSON_INVOKE_INNER( on_string(ec, sv) );
1290 : }
1291 :
1292 : bool on_number_part( system::error_code& ec )
1293 : {
1294 : BOOST_JSON_INVOKE_INNER( on_number_part(ec) );
1295 : }
1296 :
1297 : bool on_int64( system::error_code& ec, std::int64_t v )
1298 : {
1299 : BOOST_JSON_INVOKE_INNER( on_int64(ec, v) );
1300 : }
1301 :
1302 : bool on_uint64( system::error_code& ec, std::uint64_t v )
1303 : {
1304 : BOOST_JSON_INVOKE_INNER( on_uint64(ec, v) );
1305 : }
1306 :
1307 : bool on_double( system::error_code& ec, double v )
1308 : {
1309 : BOOST_JSON_INVOKE_INNER( on_double(ec, v) );
1310 : }
1311 :
1312 : bool on_bool( system::error_code& ec, bool v )
1313 : {
1314 : BOOST_JSON_INVOKE_INNER( on_bool(ec, v) );
1315 : }
1316 :
1317 : bool on_null( system::error_code& ec )
1318 : {
1319 : BOOST_JSON_INVOKE_INNER( on_null(ec) );
1320 : }
1321 :
1322 : #undef BOOST_JSON_INVOKE_INNER
1323 :
1324 : #endif
1325 : };
1326 :
1327 : // variant handler
1328 : struct object_begin_handler_event
1329 : { };
1330 :
1331 : struct object_end_handler_event
1332 : { };
1333 :
1334 : struct array_begin_handler_event
1335 : { };
1336 :
1337 : struct array_end_handler_event
1338 : { };
1339 :
1340 : struct key_handler_event
1341 : {
1342 : std::string value;
1343 : };
1344 :
1345 : struct string_handler_event
1346 : {
1347 : std::string value;
1348 : };
1349 :
1350 : struct int64_handler_event
1351 : {
1352 : std::int64_t value;
1353 : };
1354 :
1355 : struct uint64_handler_event
1356 : {
1357 : std::uint64_t value;
1358 : };
1359 :
1360 : struct double_handler_event
1361 : {
1362 : double value;
1363 : };
1364 :
1365 : struct bool_handler_event
1366 : {
1367 : bool value;
1368 : };
1369 :
1370 : struct null_handler_event
1371 : { };
1372 :
1373 : using parse_event = variant2::variant<
1374 : object_begin_handler_event,
1375 : object_end_handler_event,
1376 : array_begin_handler_event,
1377 : array_end_handler_event,
1378 : key_handler_event,
1379 : string_handler_event,
1380 : int64_handler_event,
1381 : uint64_handler_event,
1382 : double_handler_event,
1383 : bool_handler_event,
1384 : null_handler_event>;
1385 :
1386 : template< class H >
1387 : struct event_visitor
1388 : {
1389 : H& handler;
1390 : system::error_code& ec;
1391 :
1392 : bool
1393 14 : operator()(object_begin_handler_event&) const
1394 : {
1395 14 : return handler.on_object_begin(ec);
1396 : }
1397 :
1398 : bool
1399 7 : operator()(object_end_handler_event&) const
1400 : {
1401 7 : return handler.on_object_end(ec);
1402 : }
1403 :
1404 : bool
1405 42 : operator()(array_begin_handler_event&) const
1406 : {
1407 42 : return handler.on_array_begin(ec);
1408 : }
1409 :
1410 : bool
1411 21 : operator()(array_end_handler_event&) const
1412 : {
1413 21 : return handler.on_array_end(ec);
1414 : }
1415 :
1416 : bool
1417 21 : operator()(key_handler_event& ev) const
1418 : {
1419 21 : return handler.on_key(ec, ev.value);
1420 : }
1421 :
1422 : bool
1423 108 : operator()(string_handler_event& ev) const
1424 : {
1425 108 : return handler.on_string(ec, ev.value);
1426 : }
1427 :
1428 : bool
1429 154 : operator()(int64_handler_event& ev) const
1430 : {
1431 154 : return handler.on_int64(ec, ev.value);
1432 : }
1433 :
1434 : bool
1435 14 : operator()(uint64_handler_event& ev) const
1436 : {
1437 14 : return handler.on_uint64(ec, ev.value);
1438 : }
1439 :
1440 : bool
1441 21 : operator()(double_handler_event& ev) const
1442 : {
1443 21 : return handler.on_double(ec, ev.value);
1444 : }
1445 :
1446 : bool
1447 7 : operator()(bool_handler_event& ev) const
1448 : {
1449 7 : return handler.on_bool(ec, ev.value);
1450 : }
1451 :
1452 : bool
1453 7 : operator()(null_handler_event&) const
1454 : {
1455 7 : return handler.on_null(ec);
1456 : }
1457 : };
1458 :
1459 : // L<T...> -> variant< monostate, get_handler<T, P>... >
1460 : template< class P, class L >
1461 : using inner_handler_variant = mp11::mp_push_front<
1462 : mp11::mp_transform_q<
1463 : mp11::mp_bind_back<get_handler, P>,
1464 : mp11::mp_apply<variant2::variant, L>>,
1465 : variant2::monostate>;
1466 :
1467 : template< class T, class P >
1468 : class converting_handler<variant_conversion_tag, T, P>
1469 : {
1470 : private:
1471 : using variant_size = mp11::mp_size<T>;
1472 :
1473 : T* value_;
1474 : P* parent_;
1475 :
1476 : std::string string_;
1477 : std::vector< parse_event > events_;
1478 : inner_handler_variant<converting_handler, T> inner_;
1479 : int inner_active_ = -1;
1480 :
1481 : public:
1482 : converting_handler( converting_handler const& ) = delete;
1483 : converting_handler& operator=( converting_handler const& ) = delete;
1484 :
1485 90 : converting_handler( T* v, P* p )
1486 90 : : value_( v )
1487 90 : , parent_( p )
1488 90 : {}
1489 :
1490 126 : bool signal_value(system::error_code& ec)
1491 : {
1492 126 : inner_.template emplace<0>();
1493 126 : inner_active_ = -1;
1494 126 : events_.clear();
1495 126 : return parent_->signal_value(ec);
1496 : }
1497 :
1498 14 : bool signal_end(system::error_code& ec)
1499 : {
1500 14 : return parent_->signal_end(ec);
1501 : }
1502 :
1503 : struct alternative_selector
1504 : {
1505 : converting_handler* self;
1506 :
1507 : template< class I >
1508 : void
1509 227 : operator()( I ) const
1510 : {
1511 : using V = mp11::mp_at<T, I>;
1512 227 : auto& v = self->value_->template emplace<I::value>( V{} );
1513 227 : self->inner_.template emplace<I::value + 1>(&v, self);
1514 227 : }
1515 : };
1516 : void
1517 233 : next_alternative()
1518 : {
1519 233 : if( ++inner_active_ >= static_cast<int>(variant_size::value) )
1520 6 : return;
1521 :
1522 227 : mp11::mp_with_index< variant_size::value >(
1523 227 : inner_active_, alternative_selector{this} );
1524 : }
1525 :
1526 : struct event_processor
1527 : {
1528 : converting_handler* self;
1529 : system::error_code& ec;
1530 : parse_event& event;
1531 :
1532 : template< class I >
1533 416 : bool operator()( I ) const
1534 : {
1535 416 : auto& handler = variant2::get<I::value + 1>(self->inner_);
1536 : using Handler = remove_cvref<decltype(handler)>;
1537 416 : return variant2::visit(
1538 832 : event_visitor<Handler>{handler, ec}, event );
1539 : }
1540 : };
1541 286 : bool process_events(system::error_code& ec)
1542 : {
1543 286 : constexpr std::size_t N = variant_size::value;
1544 :
1545 : // should be pointers not iterators, otherwise MSVC crashes
1546 286 : auto const last = events_.data() + events_.size();
1547 286 : auto first = last - 1;
1548 286 : bool ok = false;
1549 :
1550 286 : if( inner_active_ < 0 )
1551 146 : next_alternative();
1552 : do
1553 : {
1554 373 : if( static_cast<std::size_t>(inner_active_) >= N )
1555 : {
1556 6 : BOOST_JSON_FAIL( ec, error::exhausted_variants );
1557 6 : return false;
1558 : }
1559 :
1560 696 : for ( ; first != last; ++first )
1561 : {
1562 832 : ok = mp11::mp_with_index< N >(
1563 416 : inner_active_, event_processor{this, ec, *first} );
1564 416 : if( !ok )
1565 : {
1566 87 : first = events_.data();
1567 87 : next_alternative();
1568 87 : ec.clear();
1569 87 : break;
1570 : }
1571 : }
1572 : }
1573 367 : while( !ok );
1574 :
1575 280 : return true;
1576 : }
1577 :
1578 : #define BOOST_JSON_INVOKE_INNER(ev, ec) \
1579 : events_.emplace_back( ev ); \
1580 : return process_events(ec);
1581 :
1582 7 : bool on_object_begin( system::error_code& ec )
1583 : {
1584 7 : BOOST_JSON_INVOKE_INNER( object_begin_handler_event{}, ec );
1585 : }
1586 :
1587 7 : bool on_object_end( system::error_code& ec )
1588 : {
1589 7 : BOOST_JSON_INVOKE_INNER( object_end_handler_event{}, ec );
1590 : }
1591 :
1592 21 : bool on_array_begin( system::error_code& ec )
1593 : {
1594 21 : BOOST_JSON_INVOKE_INNER( array_begin_handler_event{}, ec );
1595 : }
1596 :
1597 28 : bool on_array_end( system::error_code& ec )
1598 : {
1599 28 : if( !inner_active_ )
1600 7 : return signal_end(ec);
1601 :
1602 21 : BOOST_JSON_INVOKE_INNER( array_end_handler_event{}, ec );
1603 : }
1604 :
1605 5 : bool on_key_part( system::error_code&, string_view sv )
1606 : {
1607 5 : string_.append(sv);
1608 5 : return true;
1609 : }
1610 :
1611 14 : bool on_key( system::error_code& ec, string_view sv )
1612 : {
1613 14 : string_.append(sv);
1614 28 : BOOST_JSON_INVOKE_INNER( key_handler_event{ std::move(string_) }, ec );
1615 14 : }
1616 :
1617 31 : bool on_string_part( system::error_code&, string_view sv )
1618 : {
1619 31 : string_.append(sv);
1620 31 : return true;
1621 : }
1622 :
1623 48 : bool on_string( system::error_code& ec, string_view sv )
1624 : {
1625 48 : string_.append(sv);
1626 96 : BOOST_JSON_INVOKE_INNER(
1627 : string_handler_event{ std::move(string_) }, ec );
1628 48 : }
1629 :
1630 60 : bool on_number_part( system::error_code& )
1631 : {
1632 60 : return true;
1633 : }
1634 :
1635 133 : bool on_int64( system::error_code& ec, std::int64_t v )
1636 : {
1637 133 : BOOST_JSON_INVOKE_INNER( int64_handler_event{v}, ec );
1638 : }
1639 :
1640 7 : bool on_uint64( system::error_code& ec, std::uint64_t v )
1641 : {
1642 7 : BOOST_JSON_INVOKE_INNER( uint64_handler_event{v}, ec );
1643 : }
1644 :
1645 14 : bool on_double( system::error_code& ec, double v )
1646 : {
1647 14 : BOOST_JSON_INVOKE_INNER( double_handler_event{v}, ec );
1648 : }
1649 :
1650 7 : bool on_bool( system::error_code& ec, bool v )
1651 : {
1652 7 : BOOST_JSON_INVOKE_INNER( bool_handler_event{v}, ec );
1653 : }
1654 :
1655 7 : bool on_null( system::error_code& ec )
1656 : {
1657 7 : BOOST_JSON_INVOKE_INNER( null_handler_event{}, ec );
1658 : }
1659 :
1660 : #undef BOOST_JSON_INVOKE_INNER
1661 : };
1662 :
1663 : // optional handler
1664 : template<class V, class P>
1665 : class converting_handler<optional_conversion_tag, V, P>
1666 : {
1667 : private:
1668 : using inner_type = value_result_type<V>;
1669 : using inner_handler_type = get_handler<inner_type, converting_handler>;
1670 :
1671 : V* value_;
1672 : P* parent_;
1673 :
1674 : inner_type inner_value_ = {};
1675 : inner_handler_type inner_;
1676 : bool inner_active_ = false;
1677 :
1678 : public:
1679 : converting_handler( converting_handler const& ) = delete;
1680 : converting_handler& operator=( converting_handler const& ) = delete;
1681 :
1682 : converting_handler( V* v, P* p )
1683 : : value_(v), parent_(p), inner_(&inner_value_, this)
1684 : {}
1685 :
1686 : bool signal_value(system::error_code& ec)
1687 : {
1688 : *value_ = std::move(inner_value_);
1689 :
1690 : inner_active_ = false;
1691 : return parent_->signal_value(ec);
1692 : }
1693 :
1694 : bool signal_end(system::error_code& ec)
1695 : {
1696 : return parent_->signal_end(ec);
1697 : }
1698 :
1699 : #define BOOST_JSON_INVOKE_INNER(fn) \
1700 : if( !inner_active_ ) \
1701 : inner_active_ = true; \
1702 : return inner_.fn;
1703 :
1704 : bool on_object_begin( system::error_code& ec )
1705 : {
1706 : BOOST_JSON_INVOKE_INNER( on_object_begin(ec) );
1707 : }
1708 :
1709 : bool on_object_end( system::error_code& ec )
1710 : {
1711 : BOOST_JSON_INVOKE_INNER( on_object_end(ec) );
1712 : }
1713 :
1714 : bool on_array_begin( system::error_code& ec )
1715 : {
1716 : BOOST_JSON_INVOKE_INNER( on_array_begin(ec) );
1717 : }
1718 :
1719 : bool on_array_end( system::error_code& ec )
1720 : {
1721 : if( !inner_active_ )
1722 : return signal_end(ec);
1723 :
1724 : BOOST_JSON_INVOKE_INNER( on_array_end(ec) );
1725 : }
1726 :
1727 : bool on_key_part( system::error_code& ec, string_view sv )
1728 : {
1729 : BOOST_JSON_INVOKE_INNER( on_key_part(ec, sv) );
1730 : }
1731 :
1732 : bool on_key( system::error_code& ec, string_view sv )
1733 : {
1734 : BOOST_JSON_INVOKE_INNER( on_key(ec, sv) );
1735 : }
1736 :
1737 : bool on_string_part( system::error_code& ec, string_view sv )
1738 : {
1739 : BOOST_JSON_INVOKE_INNER( on_string_part(ec, sv) );
1740 : }
1741 :
1742 : bool on_string( system::error_code& ec, string_view sv )
1743 : {
1744 : BOOST_JSON_INVOKE_INNER( on_string(ec, sv) );
1745 : }
1746 :
1747 : bool on_number_part( system::error_code& ec )
1748 : {
1749 : BOOST_JSON_INVOKE_INNER( on_number_part(ec) );
1750 : }
1751 :
1752 : bool on_int64( system::error_code& ec, std::int64_t v )
1753 : {
1754 : BOOST_JSON_INVOKE_INNER( on_int64(ec, v) );
1755 : }
1756 :
1757 : bool on_uint64( system::error_code& ec, std::uint64_t v )
1758 : {
1759 : BOOST_JSON_INVOKE_INNER( on_uint64(ec, v) );
1760 : }
1761 :
1762 : bool on_double( system::error_code& ec, double v )
1763 : {
1764 : BOOST_JSON_INVOKE_INNER( on_double(ec, v) );
1765 : }
1766 :
1767 : bool on_bool( system::error_code& ec, bool v )
1768 : {
1769 : BOOST_JSON_INVOKE_INNER( on_bool(ec, v) );
1770 : }
1771 :
1772 : bool on_null(system::error_code& ec)
1773 : {
1774 : if( !inner_active_ )
1775 : {
1776 : *value_ = {};
1777 : return this->parent_->signal_value(ec);
1778 : }
1779 : else
1780 : {
1781 : return inner_.on_null(ec);
1782 : }
1783 : }
1784 :
1785 : #undef BOOST_JSON_INVOKE_INNER
1786 : };
1787 :
1788 : // path handler
1789 : template< class V, class P >
1790 : class converting_handler<path_conversion_tag, V, P>
1791 : : public scalar_handler<P, error::not_string>
1792 : {
1793 : private:
1794 : V* value_;
1795 : bool cleared_ = false;
1796 :
1797 : public:
1798 : converting_handler( V* v, P* p )
1799 : : converting_handler::scalar_handler(p)
1800 : , value_(v)
1801 : {}
1802 :
1803 : bool on_string_part( system::error_code&, string_view sv )
1804 : {
1805 : if( !cleared_ )
1806 : {
1807 : cleared_ = true;
1808 : value_->clear();
1809 : }
1810 :
1811 : value_->concat( sv.begin(), sv.end() );
1812 : return true;
1813 : }
1814 :
1815 : bool on_string(system::error_code& ec, string_view sv)
1816 : {
1817 : if( !cleared_ )
1818 : value_->clear();
1819 : else
1820 : cleared_ = false;
1821 :
1822 : value_->concat( sv.begin(), sv.end() );
1823 :
1824 : return this->parent_->signal_value(ec);
1825 : }
1826 : };
1827 :
1828 : // into_handler
1829 : template< class V >
1830 : class into_handler
1831 : {
1832 : private:
1833 :
1834 : using inner_handler_type = get_handler<V, into_handler>;
1835 :
1836 : inner_handler_type inner_;
1837 : bool inner_active_ = true;
1838 :
1839 : public:
1840 :
1841 : into_handler( into_handler const& ) = delete;
1842 : into_handler& operator=( into_handler const& ) = delete;
1843 :
1844 : public:
1845 :
1846 : static constexpr std::size_t max_object_size = object::max_size();
1847 : static constexpr std::size_t max_array_size = array::max_size();
1848 : static constexpr std::size_t max_key_size = string::max_size();
1849 : static constexpr std::size_t max_string_size = string::max_size();
1850 :
1851 : public:
1852 :
1853 522 : explicit into_handler( V* v ): inner_( v, this )
1854 : {
1855 522 : }
1856 :
1857 466 : bool signal_value(system::error_code&)
1858 : {
1859 466 : return true;
1860 : }
1861 :
1862 7 : bool signal_end(system::error_code&)
1863 : {
1864 7 : return true;
1865 : }
1866 :
1867 521 : bool on_document_begin( system::error_code& )
1868 : {
1869 521 : return true;
1870 : }
1871 :
1872 473 : bool on_document_end( system::error_code& )
1873 : {
1874 473 : inner_active_ = false;
1875 473 : return true;
1876 : }
1877 :
1878 : #define BOOST_JSON_INVOKE_INNER(f) \
1879 : if( !inner_active_ ) \
1880 : { \
1881 : BOOST_JSON_FAIL( ec, error::extra_data ); \
1882 : return false; \
1883 : } \
1884 : else \
1885 : return inner_.f
1886 :
1887 144 : bool on_object_begin( system::error_code& ec )
1888 : {
1889 144 : BOOST_JSON_INVOKE_INNER( on_object_begin(ec) );
1890 : }
1891 :
1892 138 : bool on_object_end( std::size_t, system::error_code& ec )
1893 : {
1894 138 : BOOST_JSON_INVOKE_INNER( on_object_end(ec) );
1895 : }
1896 :
1897 418 : bool on_array_begin( system::error_code& ec )
1898 : {
1899 418 : BOOST_JSON_INVOKE_INNER( on_array_begin(ec) );
1900 : }
1901 :
1902 404 : bool on_array_end( std::size_t, system::error_code& ec )
1903 : {
1904 404 : BOOST_JSON_INVOKE_INNER( on_array_end(ec) );
1905 : }
1906 :
1907 48 : bool on_key_part( string_view sv, std::size_t, system::error_code& ec )
1908 : {
1909 48 : BOOST_JSON_INVOKE_INNER( on_key_part(ec, sv) );
1910 : }
1911 :
1912 139 : bool on_key( string_view sv, std::size_t, system::error_code& ec )
1913 : {
1914 139 : BOOST_JSON_INVOKE_INNER( on_key(ec, sv) );
1915 : }
1916 :
1917 54 : bool on_string_part( string_view sv, std::size_t, system::error_code& ec )
1918 : {
1919 54 : BOOST_JSON_INVOKE_INNER( on_string_part(ec, sv) );
1920 : }
1921 :
1922 101 : bool on_string( string_view sv, std::size_t, system::error_code& ec )
1923 : {
1924 101 : BOOST_JSON_INVOKE_INNER( on_string(ec, sv) );
1925 : }
1926 :
1927 484 : bool on_number_part( string_view, system::error_code& ec )
1928 : {
1929 484 : BOOST_JSON_INVOKE_INNER( on_number_part(ec) );
1930 : }
1931 :
1932 707 : bool on_int64( std::int64_t v, string_view, system::error_code& ec )
1933 : {
1934 707 : BOOST_JSON_INVOKE_INNER( on_int64(ec, v) );
1935 : }
1936 :
1937 39 : bool on_uint64( std::uint64_t v, string_view, system::error_code& ec )
1938 : {
1939 39 : BOOST_JSON_INVOKE_INNER( on_uint64(ec, v) );
1940 : }
1941 :
1942 63 : bool on_double( double v, string_view, system::error_code& ec )
1943 : {
1944 63 : BOOST_JSON_INVOKE_INNER( on_double(ec, v) );
1945 : }
1946 :
1947 44 : bool on_bool( bool v, system::error_code& ec )
1948 : {
1949 44 : BOOST_JSON_INVOKE_INNER( on_bool(ec, v) );
1950 : }
1951 :
1952 39 : bool on_null( system::error_code& ec )
1953 : {
1954 39 : BOOST_JSON_INVOKE_INNER( on_null(ec) );
1955 : }
1956 :
1957 1254 : bool on_comment_part(string_view, system::error_code&)
1958 : {
1959 1254 : return true;
1960 : }
1961 :
1962 66 : bool on_comment(string_view, system::error_code&)
1963 : {
1964 66 : return true;
1965 : }
1966 :
1967 : #undef BOOST_JSON_INVOKE_INNER
1968 : };
1969 :
1970 : } // namespace detail
1971 : } // namespace boost
1972 : } // namespace json
1973 :
1974 : #endif
|