Skip to content

Commit 912d71c

Browse files
committed
ubjson_cursor
1 parent bc67a39 commit 912d71c

File tree

2 files changed

+97
-27
lines changed

2 files changed

+97
-27
lines changed

include/jsoncons_ext/ubjson/ubjson_cursor.hpp

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ class basic_ubjson_cursor : public basic_staj_cursor<char>, private virtual ser_
5252
: parser_(std::forward<Sourceable>(source), options, alloc),
5353
cursor_visitor_(accept_all)
5454
{
55+
parser_.cursor_mode(true);
5556
if (!done())
5657
{
5758
next();
@@ -90,6 +91,7 @@ class basic_ubjson_cursor : public basic_staj_cursor<char>, private virtual ser_
9091
cursor_visitor_(accept_all),
9192
eof_(false)
9293
{
94+
parser_.cursor_mode(true);
9395
if (!done())
9496
{
9597
next(ec);
@@ -170,9 +172,23 @@ class basic_ubjson_cursor : public basic_staj_cursor<char>, private virtual ser_
170172
void read_to(basic_json_visitor<char_type>& visitor,
171173
std::error_code& ec) override
172174
{
173-
if (cursor_visitor_.event().send_json_event(visitor, *this, ec))
175+
if (is_begin_container(current().event_type()))
174176
{
175-
read_next(visitor, ec);
177+
parser_.cursor_mode(false);
178+
parser_.mark_level(parser_.level());
179+
if (cursor_visitor_.event().send_json_event(visitor, *this, ec))
180+
{
181+
read_next(visitor, ec);
182+
}
183+
parser_.cursor_mode(true);
184+
parser_.mark_level(0);
185+
}
186+
else
187+
{
188+
if (cursor_visitor_.event().send_json_event(visitor, *this, ec))
189+
{
190+
read_next(visitor, ec);
191+
}
176192
}
177193
}
178194

include/jsoncons_ext/ubjson/ubjson_parser.hpp

Lines changed: 79 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -58,10 +58,13 @@ class basic_ubjson_parser : public ser_context
5858
using byte_allocator_type = typename std::allocator_traits<temp_allocator_type>:: template rebind_alloc<uint8_t>;
5959
using parse_state_allocator_type = typename std::allocator_traits<temp_allocator_type>:: template rebind_alloc<parse_state>;
6060

61-
Source source_;
62-
ubjson_decode_options options_;
6361
bool more_{true};
6462
bool done_{false};
63+
bool cursor_mode_{false};
64+
int mark_level_{0};
65+
66+
Source source_;
67+
ubjson_decode_options options_;
6568
std::basic_string<char,std::char_traits<char>,char_allocator_type> text_buffer_;
6669
std::vector<parse_state,parse_state_allocator_type> state_stack_;
6770
int nesting_depth_{0};
@@ -100,6 +103,26 @@ class basic_ubjson_parser : public ser_context
100103
reset();
101104
}
102105

106+
void cursor_mode(bool value)
107+
{
108+
cursor_mode_ = value;
109+
}
110+
111+
int level() const
112+
{
113+
return static_cast<int>(state_stack_.size());
114+
}
115+
116+
int mark_level() const
117+
{
118+
return mark_level_;
119+
}
120+
121+
void mark_level(int value)
122+
{
123+
mark_level_ = value;
124+
}
125+
103126
bool done() const
104127
{
105128
return done_;
@@ -343,7 +366,8 @@ class basic_ubjson_parser : public ser_context
343366
{
344367
case jsoncons::ubjson::ubjson_type::null_type:
345368
{
346-
more_ = visitor.null_value(semantic_tag::none, *this, ec);
369+
visitor.null_value(semantic_tag::none, *this, ec);
370+
more_ = !cursor_mode_;
347371
break;
348372
}
349373
case jsoncons::ubjson::ubjson_type::no_op_type:
@@ -352,12 +376,14 @@ class basic_ubjson_parser : public ser_context
352376
}
353377
case jsoncons::ubjson::ubjson_type::true_type:
354378
{
355-
more_ = visitor.bool_value(true, semantic_tag::none, *this, ec);
379+
visitor.bool_value(true, semantic_tag::none, *this, ec);
380+
more_ = !cursor_mode_;
356381
break;
357382
}
358383
case jsoncons::ubjson::ubjson_type::false_type:
359384
{
360-
more_ = visitor.bool_value(false, semantic_tag::none, *this, ec);
385+
visitor.bool_value(false, semantic_tag::none, *this, ec);
386+
more_ = !cursor_mode_;
361387
break;
362388
}
363389
case jsoncons::ubjson::ubjson_type::int8_type:
@@ -370,7 +396,8 @@ class basic_ubjson_parser : public ser_context
370396
return;
371397
}
372398
int8_t val = binary::big_to_native<int8_t>(buf, sizeof(buf));
373-
more_ = visitor.int64_value(val, semantic_tag::none, *this, ec);
399+
visitor.int64_value(val, semantic_tag::none, *this, ec);
400+
more_ = !cursor_mode_;
374401
break;
375402
}
376403
case jsoncons::ubjson::ubjson_type::uint8_type:
@@ -382,7 +409,8 @@ class basic_ubjson_parser : public ser_context
382409
more_ = false;
383410
return;
384411
}
385-
more_ = visitor.uint64_value(b, semantic_tag::none, *this, ec);
412+
visitor.uint64_value(b, semantic_tag::none, *this, ec);
413+
more_ = !cursor_mode_;
386414
break;
387415
}
388416
case jsoncons::ubjson::ubjson_type::int16_type:
@@ -395,7 +423,8 @@ class basic_ubjson_parser : public ser_context
395423
return;
396424
}
397425
int16_t val = binary::big_to_native<int16_t>(buf, sizeof(buf));
398-
more_ = visitor.int64_value(val, semantic_tag::none, *this, ec);
426+
visitor.int64_value(val, semantic_tag::none, *this, ec);
427+
more_ = !cursor_mode_;
399428
break;
400429
}
401430
case jsoncons::ubjson::ubjson_type::int32_type:
@@ -408,7 +437,8 @@ class basic_ubjson_parser : public ser_context
408437
return;
409438
}
410439
int32_t val = binary::big_to_native<int32_t>(buf, sizeof(buf));
411-
more_ = visitor.int64_value(val, semantic_tag::none, *this, ec);
440+
visitor.int64_value(val, semantic_tag::none, *this, ec);
441+
more_ = !cursor_mode_;
412442
break;
413443
}
414444
case jsoncons::ubjson::ubjson_type::int64_type:
@@ -421,7 +451,8 @@ class basic_ubjson_parser : public ser_context
421451
return;
422452
}
423453
int64_t val = binary::big_to_native<int64_t>(buf, sizeof(buf));
424-
more_ = visitor.int64_value(val, semantic_tag::none, *this, ec);
454+
visitor.int64_value(val, semantic_tag::none, *this, ec);
455+
more_ = !cursor_mode_;
425456
break;
426457
}
427458
case jsoncons::ubjson::ubjson_type::float32_type:
@@ -434,7 +465,8 @@ class basic_ubjson_parser : public ser_context
434465
return;
435466
}
436467
float val = binary::big_to_native<float>(buf, sizeof(buf));
437-
more_ = visitor.double_value(val, semantic_tag::none, *this, ec);
468+
visitor.double_value(val, semantic_tag::none, *this, ec);
469+
more_ = !cursor_mode_;
438470
break;
439471
}
440472
case jsoncons::ubjson::ubjson_type::float64_type:
@@ -447,7 +479,8 @@ class basic_ubjson_parser : public ser_context
447479
return;
448480
}
449481
double val = binary::big_to_native<double>(buf, sizeof(buf));
450-
more_ = visitor.double_value(val, semantic_tag::none, *this, ec);
482+
visitor.double_value(val, semantic_tag::none, *this, ec);
483+
more_ = !cursor_mode_;
451484
break;
452485
}
453486
case jsoncons::ubjson::ubjson_type::char_type:
@@ -466,7 +499,8 @@ class basic_ubjson_parser : public ser_context
466499
more_ = false;
467500
return;
468501
}
469-
more_ = visitor.string_value(text_buffer_, semantic_tag::none, *this, ec);
502+
visitor.string_value(text_buffer_, semantic_tag::none, *this, ec);
503+
more_ = !cursor_mode_;
470504
break;
471505
}
472506
case jsoncons::ubjson::ubjson_type::string_type:
@@ -490,7 +524,8 @@ class basic_ubjson_parser : public ser_context
490524
more_ = false;
491525
return;
492526
}
493-
more_ = visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::none, *this, ec);
527+
visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::none, *this, ec);
528+
more_ = !cursor_mode_;
494529
break;
495530
}
496531
case jsoncons::ubjson::ubjson_type::high_precision_number_type:
@@ -509,11 +544,13 @@ class basic_ubjson_parser : public ser_context
509544
}
510545
if (jsoncons::detail::is_base10(text_buffer_.data(),text_buffer_.length()))
511546
{
512-
more_ = visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::bigint, *this, ec);
547+
visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::bigint, *this, ec);
548+
more_ = !cursor_mode_;
513549
}
514550
else
515551
{
516-
more_ = visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::bigdec, *this, ec);
552+
visitor.string_value(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), semantic_tag::bigdec, *this, ec);
553+
more_ = !cursor_mode_;
517554
}
518555
break;
519556
}
@@ -587,7 +624,8 @@ class basic_ubjson_parser : public ser_context
587624
return;
588625
}
589626
state_stack_.emplace_back(parse_mode::strongly_typed_array,length,b);
590-
more_ = visitor.begin_array(length, semantic_tag::none, *this, ec);
627+
visitor.begin_array(length, semantic_tag::none, *this, ec);
628+
more_ = !cursor_mode_;
591629
}
592630
else
593631
{
@@ -611,20 +649,27 @@ class basic_ubjson_parser : public ser_context
611649
return;
612650
}
613651
state_stack_.emplace_back(parse_mode::array,length);
614-
more_ = visitor.begin_array(length, semantic_tag::none, *this, ec);
652+
visitor.begin_array(length, semantic_tag::none, *this, ec);
653+
more_ = !cursor_mode_;
615654
}
616655
else
617656
{
618657
state_stack_.emplace_back(parse_mode::indefinite_array,0);
619-
more_ = visitor.begin_array(semantic_tag::none, *this, ec);
658+
visitor.begin_array(semantic_tag::none, *this, ec);
659+
more_ = !cursor_mode_;
620660
}
621661
}
622662

623663
void end_array(json_visitor& visitor, std::error_code& ec)
624664
{
625665
--nesting_depth_;
626666

627-
more_ = visitor.end_array(*this, ec);
667+
visitor.end_array(*this, ec);
668+
more_ = !cursor_mode_;
669+
if (level() == mark_level_)
670+
{
671+
more_ = false;
672+
}
628673
state_stack_.pop_back();
629674
}
630675

@@ -676,7 +721,8 @@ class basic_ubjson_parser : public ser_context
676721
return;
677722
}
678723
state_stack_.emplace_back(parse_mode::strongly_typed_map_key,length,b);
679-
more_ = visitor.begin_object(length, semantic_tag::none, *this, ec);
724+
visitor.begin_object(length, semantic_tag::none, *this, ec);
725+
more_ = !cursor_mode_;
680726
}
681727
else
682728
{
@@ -709,20 +755,27 @@ class basic_ubjson_parser : public ser_context
709755
return;
710756
}
711757
state_stack_.emplace_back(parse_mode::map_key,length);
712-
more_ = visitor.begin_object(length, semantic_tag::none, *this, ec);
758+
visitor.begin_object(length, semantic_tag::none, *this, ec);
759+
more_ = !cursor_mode_;
713760
}
714761
else
715762
{
716763
state_stack_.emplace_back(parse_mode::indefinite_map_key,0);
717-
more_ = visitor.begin_object(semantic_tag::none, *this, ec);
764+
visitor.begin_object(semantic_tag::none, *this, ec);
765+
more_ = !cursor_mode_;
718766
}
719767
}
720768
}
721769

722770
void end_object(json_visitor& visitor, std::error_code& ec)
723771
{
724772
--nesting_depth_;
725-
more_ = visitor.end_object(*this, ec);
773+
visitor.end_object(*this, ec);
774+
more_ = !cursor_mode_;
775+
if (level() == mark_level_)
776+
{
777+
more_ = false;
778+
}
726779
state_stack_.pop_back();
727780
}
728781

@@ -878,7 +931,8 @@ class basic_ubjson_parser : public ser_context
878931
more_ = false;
879932
return;
880933
}
881-
more_ = visitor.key(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), *this, ec);
934+
visitor.key(jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()), *this, ec);
935+
more_ = !cursor_mode_;
882936
}
883937
};
884938

0 commit comments

Comments
 (0)