jsoncons 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (155) hide show
  1. checksums.yaml +7 -0
  2. data/ext/jsoncons/extconf.rb +43 -0
  3. data/ext/jsoncons/jsoncons.cpp +161 -0
  4. data/ext/jsoncons/jsoncons.h +10 -0
  5. data/jsoncons.gemspec +44 -0
  6. data/lib/jsoncons/jsoncons/examples/input/address-book.json +13 -0
  7. data/lib/jsoncons/jsoncons/examples/input/books.json +28 -0
  8. data/lib/jsoncons/jsoncons/examples/input/countries.json +7 -0
  9. data/lib/jsoncons/jsoncons/examples/input/employees.json +30 -0
  10. data/lib/jsoncons/jsoncons/examples/input/jsonschema/name.json +15 -0
  11. data/lib/jsoncons/jsoncons/examples/input/multiple-json-objects.json +3 -0
  12. data/lib/jsoncons/jsoncons/examples/input/sales.csv +6 -0
  13. data/lib/jsoncons/jsoncons/examples/input/store.json +28 -0
  14. data/lib/jsoncons/jsoncons/examples/input/tasks.csv +6 -0
  15. data/lib/jsoncons/jsoncons/include/jsoncons/allocator_holder.hpp +38 -0
  16. data/lib/jsoncons/jsoncons/include/jsoncons/basic_json.hpp +5905 -0
  17. data/lib/jsoncons/jsoncons/include/jsoncons/bigint.hpp +1611 -0
  18. data/lib/jsoncons/jsoncons/include/jsoncons/byte_string.hpp +820 -0
  19. data/lib/jsoncons/jsoncons/include/jsoncons/config/binary_config.hpp +226 -0
  20. data/lib/jsoncons/jsoncons/include/jsoncons/config/compiler_support.hpp +375 -0
  21. data/lib/jsoncons/jsoncons/include/jsoncons/config/jsoncons_config.hpp +309 -0
  22. data/lib/jsoncons/jsoncons/include/jsoncons/config/version.hpp +40 -0
  23. data/lib/jsoncons/jsoncons/include/jsoncons/conv_error.hpp +218 -0
  24. data/lib/jsoncons/jsoncons/include/jsoncons/decode_json.hpp +209 -0
  25. data/lib/jsoncons/jsoncons/include/jsoncons/decode_traits.hpp +651 -0
  26. data/lib/jsoncons/jsoncons/include/jsoncons/detail/endian.hpp +44 -0
  27. data/lib/jsoncons/jsoncons/include/jsoncons/detail/grisu3.hpp +312 -0
  28. data/lib/jsoncons/jsoncons/include/jsoncons/detail/optional.hpp +483 -0
  29. data/lib/jsoncons/jsoncons/include/jsoncons/detail/parse_number.hpp +1133 -0
  30. data/lib/jsoncons/jsoncons/include/jsoncons/detail/span.hpp +188 -0
  31. data/lib/jsoncons/jsoncons/include/jsoncons/detail/string_view.hpp +537 -0
  32. data/lib/jsoncons/jsoncons/include/jsoncons/detail/string_wrapper.hpp +370 -0
  33. data/lib/jsoncons/jsoncons/include/jsoncons/detail/write_number.hpp +567 -0
  34. data/lib/jsoncons/jsoncons/include/jsoncons/encode_json.hpp +315 -0
  35. data/lib/jsoncons/jsoncons/include/jsoncons/encode_traits.hpp +378 -0
  36. data/lib/jsoncons/jsoncons/include/jsoncons/json.hpp +18 -0
  37. data/lib/jsoncons/jsoncons/include/jsoncons/json_array.hpp +324 -0
  38. data/lib/jsoncons/jsoncons/include/jsoncons/json_content_handler.hpp +12 -0
  39. data/lib/jsoncons/jsoncons/include/jsoncons/json_cursor.hpp +448 -0
  40. data/lib/jsoncons/jsoncons/include/jsoncons/json_decoder.hpp +420 -0
  41. data/lib/jsoncons/jsoncons/include/jsoncons/json_encoder.hpp +1587 -0
  42. data/lib/jsoncons/jsoncons/include/jsoncons/json_error.hpp +156 -0
  43. data/lib/jsoncons/jsoncons/include/jsoncons/json_exception.hpp +241 -0
  44. data/lib/jsoncons/jsoncons/include/jsoncons/json_filter.hpp +653 -0
  45. data/lib/jsoncons/jsoncons/include/jsoncons/json_fwd.hpp +23 -0
  46. data/lib/jsoncons/jsoncons/include/jsoncons/json_object.hpp +1772 -0
  47. data/lib/jsoncons/jsoncons/include/jsoncons/json_options.hpp +862 -0
  48. data/lib/jsoncons/jsoncons/include/jsoncons/json_parser.hpp +2900 -0
  49. data/lib/jsoncons/jsoncons/include/jsoncons/json_reader.hpp +731 -0
  50. data/lib/jsoncons/jsoncons/include/jsoncons/json_traits_macros.hpp +1072 -0
  51. data/lib/jsoncons/jsoncons/include/jsoncons/json_traits_macros_deprecated.hpp +144 -0
  52. data/lib/jsoncons/jsoncons/include/jsoncons/json_type.hpp +206 -0
  53. data/lib/jsoncons/jsoncons/include/jsoncons/json_type_traits.hpp +1830 -0
  54. data/lib/jsoncons/jsoncons/include/jsoncons/json_visitor.hpp +1560 -0
  55. data/lib/jsoncons/jsoncons/include/jsoncons/json_visitor2.hpp +2079 -0
  56. data/lib/jsoncons/jsoncons/include/jsoncons/pretty_print.hpp +89 -0
  57. data/lib/jsoncons/jsoncons/include/jsoncons/ser_context.hpp +62 -0
  58. data/lib/jsoncons/jsoncons/include/jsoncons/sink.hpp +289 -0
  59. data/lib/jsoncons/jsoncons/include/jsoncons/source.hpp +777 -0
  60. data/lib/jsoncons/jsoncons/include/jsoncons/source_adaptor.hpp +148 -0
  61. data/lib/jsoncons/jsoncons/include/jsoncons/staj2_cursor.hpp +1189 -0
  62. data/lib/jsoncons/jsoncons/include/jsoncons/staj_cursor.hpp +1254 -0
  63. data/lib/jsoncons/jsoncons/include/jsoncons/staj_iterator.hpp +449 -0
  64. data/lib/jsoncons/jsoncons/include/jsoncons/tag_type.hpp +245 -0
  65. data/lib/jsoncons/jsoncons/include/jsoncons/text_source_adaptor.hpp +144 -0
  66. data/lib/jsoncons/jsoncons/include/jsoncons/traits_extension.hpp +884 -0
  67. data/lib/jsoncons/jsoncons/include/jsoncons/typed_array_view.hpp +250 -0
  68. data/lib/jsoncons/jsoncons/include/jsoncons/unicode_traits.hpp +1330 -0
  69. data/lib/jsoncons/jsoncons/include/jsoncons/uri.hpp +635 -0
  70. data/lib/jsoncons/jsoncons/include/jsoncons/value_converter.hpp +340 -0
  71. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson.hpp +23 -0
  72. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_cursor.hpp +320 -0
  73. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_decimal128.hpp +865 -0
  74. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_encoder.hpp +585 -0
  75. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_error.hpp +103 -0
  76. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_oid.hpp +245 -0
  77. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_options.hpp +75 -0
  78. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_parser.hpp +645 -0
  79. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_reader.hpp +92 -0
  80. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/bson_type.hpp +44 -0
  81. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/decode_bson.hpp +201 -0
  82. data/lib/jsoncons/jsoncons/include/jsoncons_ext/bson/encode_bson.hpp +144 -0
  83. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor.hpp +26 -0
  84. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_cursor.hpp +351 -0
  85. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_cursor2.hpp +265 -0
  86. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_detail.hpp +93 -0
  87. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_encoder.hpp +1766 -0
  88. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_error.hpp +105 -0
  89. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_options.hpp +113 -0
  90. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_parser.hpp +1942 -0
  91. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/cbor_reader.hpp +116 -0
  92. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/decode_cbor.hpp +203 -0
  93. data/lib/jsoncons/jsoncons/include/jsoncons_ext/cbor/encode_cbor.hpp +151 -0
  94. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv.hpp +17 -0
  95. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_cursor.hpp +358 -0
  96. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_encoder.hpp +954 -0
  97. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_error.hpp +85 -0
  98. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_options.hpp +973 -0
  99. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_parser.hpp +2099 -0
  100. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_reader.hpp +348 -0
  101. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/csv_serializer.hpp +12 -0
  102. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/decode_csv.hpp +208 -0
  103. data/lib/jsoncons/jsoncons/include/jsoncons_ext/csv/encode_csv.hpp +122 -0
  104. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jmespath/jmespath.hpp +5215 -0
  105. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jmespath/jmespath_error.hpp +215 -0
  106. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpatch/jsonpatch.hpp +579 -0
  107. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpatch/jsonpatch_error.hpp +121 -0
  108. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/expression.hpp +3329 -0
  109. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/flatten.hpp +432 -0
  110. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/json_location.hpp +445 -0
  111. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/json_query.hpp +115 -0
  112. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/jsonpath.hpp +13 -0
  113. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/jsonpath_error.hpp +240 -0
  114. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/jsonpath_expression.hpp +2612 -0
  115. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpath/jsonpath_selector.hpp +1322 -0
  116. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpointer/jsonpointer.hpp +1577 -0
  117. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonpointer/jsonpointer_error.hpp +119 -0
  118. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/format_validator.hpp +968 -0
  119. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/json_validator.hpp +120 -0
  120. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/jsonschema.hpp +13 -0
  121. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/jsonschema_error.hpp +105 -0
  122. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/jsonschema_version.hpp +18 -0
  123. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/keyword_validator.hpp +1745 -0
  124. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/keyword_validator_factory.hpp +556 -0
  125. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/schema_draft7.hpp +198 -0
  126. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/schema_location.hpp +200 -0
  127. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/schema_version.hpp +35 -0
  128. data/lib/jsoncons/jsoncons/include/jsoncons_ext/jsonschema/subschema.hpp +144 -0
  129. data/lib/jsoncons/jsoncons/include/jsoncons_ext/mergepatch/mergepatch.hpp +103 -0
  130. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/decode_msgpack.hpp +202 -0
  131. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/encode_msgpack.hpp +142 -0
  132. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack.hpp +24 -0
  133. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_cursor.hpp +343 -0
  134. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_cursor2.hpp +259 -0
  135. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_encoder.hpp +753 -0
  136. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_error.hpp +94 -0
  137. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_options.hpp +74 -0
  138. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_parser.hpp +748 -0
  139. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_reader.hpp +116 -0
  140. data/lib/jsoncons/jsoncons/include/jsoncons_ext/msgpack/msgpack_type.hpp +63 -0
  141. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/decode_ubjson.hpp +201 -0
  142. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/encode_ubjson.hpp +142 -0
  143. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson.hpp +23 -0
  144. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_cursor.hpp +307 -0
  145. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_encoder.hpp +502 -0
  146. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_error.hpp +100 -0
  147. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_options.hpp +87 -0
  148. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_parser.hpp +880 -0
  149. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_reader.hpp +92 -0
  150. data/lib/jsoncons/jsoncons/include/jsoncons_ext/ubjson/ubjson_type.hpp +43 -0
  151. data/lib/jsoncons/version.rb +5 -0
  152. data/lib/jsoncons.rb +33 -0
  153. data/test/jsoncons_test.rb +108 -0
  154. data/test/test_helper.rb +7 -0
  155. metadata +268 -0
@@ -0,0 +1,1942 @@
1
+ // Copyright 2017 Daniel Parker
2
+ // Distributed under the Boost license, Version 1.0.
3
+ // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
4
+
5
+ // See https://github.com/danielaparker/jsoncons for latest version
6
+
7
+ #ifndef JSONCONS_CBOR_CBOR_PARSER_HPP
8
+ #define JSONCONS_CBOR_CBOR_PARSER_HPP
9
+
10
+ #include <string>
11
+ #include <vector>
12
+ #include <memory>
13
+ #include <utility> // std::move
14
+ #include <bitset> // std::bitset
15
+ #include <jsoncons/json.hpp>
16
+ #include <jsoncons/source.hpp>
17
+ #include <jsoncons/json_visitor.hpp>
18
+ #include <jsoncons/config/jsoncons_config.hpp>
19
+ #include <jsoncons_ext/cbor/cbor_error.hpp>
20
+ #include <jsoncons_ext/cbor/cbor_detail.hpp>
21
+ #include <jsoncons_ext/cbor/cbor_options.hpp>
22
+ #include <jsoncons/json_visitor2.hpp>
23
+
24
+ namespace jsoncons { namespace cbor {
25
+
26
+ enum class parse_mode {root,accept,array,indefinite_array,map_key,map_value,indefinite_map_key,indefinite_map_value,multi_dim};
27
+
28
+ struct mapped_string
29
+ {
30
+ jsoncons::cbor::detail::cbor_major_type type;
31
+ std::string s;
32
+ std::vector<uint8_t> bytes;
33
+
34
+ mapped_string(const std::string& s)
35
+ : type(jsoncons::cbor::detail::cbor_major_type::text_string), s(s)
36
+ {
37
+ }
38
+
39
+ mapped_string(std::string&& s)
40
+ : type(jsoncons::cbor::detail::cbor_major_type::text_string), s(std::move(s))
41
+ {
42
+ }
43
+
44
+ mapped_string(const std::vector<uint8_t>& bytes)
45
+ : type(jsoncons::cbor::detail::cbor_major_type::byte_string), bytes(bytes)
46
+ {
47
+ }
48
+
49
+ mapped_string(std::vector<uint8_t>&& bytes)
50
+ : type(jsoncons::cbor::detail::cbor_major_type::byte_string), bytes(std::move(bytes))
51
+ {
52
+ }
53
+
54
+ mapped_string(const mapped_string&) = default;
55
+
56
+ mapped_string(mapped_string&&) = default;
57
+
58
+ mapped_string& operator=(const mapped_string&) = default;
59
+
60
+ mapped_string& operator=(mapped_string&&) = default;
61
+ };
62
+
63
+ struct parse_state
64
+ {
65
+ parse_mode mode;
66
+ std::size_t length;
67
+ std::size_t index;
68
+ bool pop_stringref_map_stack;
69
+
70
+ parse_state(parse_mode mode, std::size_t length, bool pop_stringref_map_stack = false) noexcept
71
+ : mode(mode), length(length), index(0), pop_stringref_map_stack(pop_stringref_map_stack)
72
+ {
73
+ }
74
+
75
+ parse_state(const parse_state&) = default;
76
+ parse_state(parse_state&&) = default;
77
+ };
78
+
79
+ template <class Source,class Allocator=std::allocator<char>>
80
+ class basic_cbor_parser : public ser_context
81
+ {
82
+ using char_type = char;
83
+ using char_traits_type = std::char_traits<char>;
84
+ using allocator_type = Allocator;
85
+ using char_allocator_type = typename std::allocator_traits<allocator_type>:: template rebind_alloc<char_type>;
86
+ using byte_allocator_type = typename std::allocator_traits<allocator_type>:: template rebind_alloc<uint8_t>;
87
+ using tag_allocator_type = typename std::allocator_traits<allocator_type>:: template rebind_alloc<uint64_t>;
88
+ using parse_state_allocator_type = typename std::allocator_traits<allocator_type>:: template rebind_alloc<parse_state>;
89
+ using stringref_map = std::vector<mapped_string>;
90
+ using stringref_map_allocator_type = typename std::allocator_traits<allocator_type>:: template rebind_alloc<stringref_map>;
91
+
92
+ using string_type = std::basic_string<char_type,char_traits_type,char_allocator_type>;
93
+
94
+ enum {stringref_tag, // 25
95
+ stringref_namespace_tag, // 256
96
+ item_tag,
97
+ num_of_tags};
98
+
99
+ std::bitset<num_of_tags> other_tags_;
100
+
101
+ allocator_type alloc_;
102
+ Source source_;
103
+ cbor_decode_options options_;
104
+
105
+ bool more_;
106
+ bool done_;
107
+ string_type text_buffer_;
108
+ std::vector<uint8_t,byte_allocator_type> bytes_buffer_;
109
+ uint64_t item_tag_;
110
+ std::vector<parse_state,parse_state_allocator_type> state_stack_;
111
+ std::vector<uint8_t,byte_allocator_type> typed_array_;
112
+ std::vector<std::size_t> shape_;
113
+ std::size_t index_; // TODO: Never used!
114
+ std::vector<stringref_map,stringref_map_allocator_type> stringref_map_stack_;
115
+ int nesting_depth_;
116
+
117
+ struct read_byte_string_from_buffer
118
+ {
119
+ byte_string_view bytes;
120
+
121
+ read_byte_string_from_buffer(const byte_string_view& b)
122
+ : bytes(b)
123
+ {
124
+ }
125
+ template <class Container>
126
+ void operator()(Container& c, std::error_code&)
127
+ {
128
+ c.clear();
129
+ c.reserve(bytes.size());
130
+ for (auto b : bytes)
131
+ {
132
+ c.push_back(b);
133
+ }
134
+ }
135
+ };
136
+
137
+ struct read_byte_string_from_source
138
+ {
139
+ basic_cbor_parser<Source,Allocator>* source;
140
+
141
+ read_byte_string_from_source(basic_cbor_parser<Source,Allocator>* source)
142
+ : source(source)
143
+ {
144
+ }
145
+ template <class Container>
146
+ void operator()(Container& c, std::error_code& ec)
147
+ {
148
+ source->read_byte_string(c,ec);
149
+ }
150
+ };
151
+
152
+ public:
153
+ template <class Sourceable>
154
+ basic_cbor_parser(Sourceable&& source,
155
+ const cbor_decode_options& options = cbor_decode_options(),
156
+ const Allocator alloc = Allocator())
157
+ : alloc_(alloc),
158
+ source_(std::forward<Sourceable>(source)),
159
+ options_(options),
160
+ more_(true),
161
+ done_(false),
162
+ text_buffer_(alloc),
163
+ bytes_buffer_(alloc),
164
+ item_tag_(0),
165
+ state_stack_(alloc),
166
+ typed_array_(alloc),
167
+ index_(0),
168
+ stringref_map_stack_(alloc),
169
+ nesting_depth_(0)
170
+ {
171
+ state_stack_.emplace_back(parse_mode::root,0);
172
+ }
173
+
174
+ void restart()
175
+ {
176
+ more_ = true;
177
+ }
178
+
179
+ void reset()
180
+ {
181
+ more_ = true;
182
+ done_ = false;
183
+ text_buffer_.clear();
184
+ bytes_buffer_.clear();
185
+ item_tag_ = 0;
186
+ state_stack_.clear();
187
+ state_stack_.emplace_back(parse_mode::root,0);
188
+ typed_array_.clear();
189
+ stringref_map_stack_.clear();
190
+ nesting_depth_ = 0;
191
+ }
192
+
193
+ template <class Sourceable>
194
+ void reset(Sourceable&& source)
195
+ {
196
+ source_ = std::forward<Sourceable>(source);
197
+ reset();
198
+ }
199
+
200
+ bool done() const
201
+ {
202
+ return done_;
203
+ }
204
+
205
+ bool stopped() const
206
+ {
207
+ return !more_;
208
+ }
209
+
210
+ std::size_t line() const override
211
+ {
212
+ return 0;
213
+ }
214
+
215
+ std::size_t column() const override
216
+ {
217
+ return source_.position();
218
+ }
219
+
220
+ void parse(json_visitor2& visitor, std::error_code& ec)
221
+ {
222
+ while (!done_ && more_)
223
+ {
224
+ switch (state_stack_.back().mode)
225
+ {
226
+ case parse_mode::multi_dim:
227
+ {
228
+ if (state_stack_.back().index == 0)
229
+ {
230
+ ++state_stack_.back().index;
231
+ read_item(visitor, ec);
232
+ }
233
+ else
234
+ {
235
+ produce_end_multi_dim(visitor, ec);
236
+ }
237
+ break;
238
+ }
239
+ case parse_mode::array:
240
+ {
241
+ if (state_stack_.back().index < state_stack_.back().length)
242
+ {
243
+ ++state_stack_.back().index;
244
+ read_item(visitor, ec);
245
+ }
246
+ else
247
+ {
248
+ end_array(visitor, ec);
249
+ }
250
+ break;
251
+ }
252
+ case parse_mode::indefinite_array:
253
+ {
254
+ auto c = source_.peek();
255
+ if (c.eof)
256
+ {
257
+ ec = cbor_errc::unexpected_eof;
258
+ more_ = false;
259
+ return;
260
+ }
261
+ if (c.value == 0xff)
262
+ {
263
+ source_.ignore(1);
264
+ end_array(visitor, ec);
265
+ }
266
+ else
267
+ {
268
+ read_item(visitor, ec);
269
+ }
270
+ break;
271
+ }
272
+ case parse_mode::map_key:
273
+ {
274
+ if (state_stack_.back().index < state_stack_.back().length)
275
+ {
276
+ ++state_stack_.back().index;
277
+ state_stack_.back().mode = parse_mode::map_value;
278
+ read_item(visitor, ec);
279
+ }
280
+ else
281
+ {
282
+ end_object(visitor, ec);
283
+ }
284
+ break;
285
+ }
286
+ case parse_mode::map_value:
287
+ {
288
+ state_stack_.back().mode = parse_mode::map_key;
289
+ read_item(visitor, ec);
290
+ break;
291
+ }
292
+ case parse_mode::indefinite_map_key:
293
+ {
294
+ auto c = source_.peek();
295
+ if (c.eof)
296
+ {
297
+ ec = cbor_errc::unexpected_eof;
298
+ more_ = false;
299
+ return;
300
+ }
301
+ if (c.value == 0xff)
302
+ {
303
+ source_.ignore(1);
304
+ end_object(visitor, ec);
305
+ }
306
+ else
307
+ {
308
+ state_stack_.back().mode = parse_mode::indefinite_map_value;
309
+ read_item(visitor, ec);
310
+ }
311
+ break;
312
+ }
313
+ case parse_mode::indefinite_map_value:
314
+ {
315
+ state_stack_.back().mode = parse_mode::indefinite_map_key;
316
+ read_item(visitor, ec);
317
+ break;
318
+ }
319
+ case parse_mode::root:
320
+ {
321
+ state_stack_.back().mode = parse_mode::accept;
322
+ read_item(visitor, ec);
323
+ break;
324
+ }
325
+ case parse_mode::accept:
326
+ {
327
+ JSONCONS_ASSERT(state_stack_.size() == 1);
328
+ state_stack_.clear();
329
+ more_ = false;
330
+ done_ = true;
331
+ visitor.flush();
332
+ break;
333
+ }
334
+ }
335
+ }
336
+ }
337
+ private:
338
+ void read_item(json_visitor2& visitor, std::error_code& ec)
339
+ {
340
+ read_tags(ec);
341
+ if (!more_)
342
+ {
343
+ return;
344
+ }
345
+ auto c = source_.peek();
346
+ if (c.eof)
347
+ {
348
+ ec = cbor_errc::unexpected_eof;
349
+ more_ = false;
350
+ return;
351
+ }
352
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(c.value);
353
+ uint8_t info = get_additional_information_value(c.value);
354
+
355
+ switch (major_type)
356
+ {
357
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
358
+ {
359
+ uint64_t val = get_uint64_value(ec);
360
+ if (ec)
361
+ {
362
+ return;
363
+ }
364
+ if (!stringref_map_stack_.empty() && other_tags_[stringref_tag])
365
+ {
366
+ other_tags_[stringref_tag] = false;
367
+ if (val >= stringref_map_stack_.back().size())
368
+ {
369
+ ec = cbor_errc::stringref_too_large;
370
+ more_ = false;
371
+ return;
372
+ }
373
+ stringref_map::size_type index = (stringref_map::size_type)val;
374
+ if (index != val)
375
+ {
376
+ ec = cbor_errc::number_too_large;
377
+ more_ = false;
378
+ return;
379
+ }
380
+ auto& str = stringref_map_stack_.back().at(index);
381
+ switch (str.type)
382
+ {
383
+ case jsoncons::cbor::detail::cbor_major_type::text_string:
384
+ {
385
+ handle_string(visitor, jsoncons::basic_string_view<char>(str.s.data(),str.s.length()),ec);
386
+ if (ec)
387
+ {
388
+ return;
389
+ }
390
+ break;
391
+ }
392
+ case jsoncons::cbor::detail::cbor_major_type::byte_string:
393
+ {
394
+ read_byte_string_from_buffer read(byte_string_view(str.bytes));
395
+ write_byte_string(read, visitor, ec);
396
+ if (ec)
397
+ {
398
+ return;
399
+ }
400
+ break;
401
+ }
402
+ default:
403
+ JSONCONS_UNREACHABLE();
404
+ break;
405
+ }
406
+ }
407
+ else
408
+ {
409
+ semantic_tag tag = semantic_tag::none;
410
+ if (other_tags_[item_tag])
411
+ {
412
+ if (item_tag_ == 1)
413
+ {
414
+ tag = semantic_tag::epoch_second;
415
+ }
416
+ other_tags_[item_tag] = false;
417
+ }
418
+ more_ = visitor.uint64_value(val, tag, *this, ec);
419
+ }
420
+ break;
421
+ }
422
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
423
+ {
424
+ int64_t val = get_int64_value(ec);
425
+ if (ec)
426
+ {
427
+ return;
428
+ }
429
+ semantic_tag tag = semantic_tag::none;
430
+ if (other_tags_[item_tag])
431
+ {
432
+ if (item_tag_ == 1)
433
+ {
434
+ tag = semantic_tag::epoch_second;
435
+ }
436
+ other_tags_[item_tag] = false;
437
+ }
438
+ more_ = visitor.int64_value(val, tag, *this, ec);
439
+ break;
440
+ }
441
+ case jsoncons::cbor::detail::cbor_major_type::byte_string:
442
+ {
443
+ read_byte_string_from_source read(this);
444
+ write_byte_string(read, visitor, ec);
445
+ if (ec)
446
+ {
447
+ return;
448
+ }
449
+ break;
450
+ }
451
+ case jsoncons::cbor::detail::cbor_major_type::text_string:
452
+ {
453
+ text_buffer_.clear();
454
+ read_text_string(text_buffer_, ec);
455
+ if (ec)
456
+ {
457
+ return;
458
+ }
459
+ auto result = unicode_traits::validate(text_buffer_.data(),text_buffer_.size());
460
+ if (result.ec != unicode_traits::conv_errc())
461
+ {
462
+ ec = cbor_errc::invalid_utf8_text_string;
463
+ more_ = false;
464
+ return;
465
+ }
466
+ handle_string(visitor, jsoncons::basic_string_view<char>(text_buffer_.data(),text_buffer_.length()),ec);
467
+ if (ec)
468
+ {
469
+ return;
470
+ }
471
+ break;
472
+ }
473
+ case jsoncons::cbor::detail::cbor_major_type::semantic_tag:
474
+ {
475
+ JSONCONS_UNREACHABLE();
476
+ break;
477
+ }
478
+ case jsoncons::cbor::detail::cbor_major_type::simple:
479
+ {
480
+ switch (info)
481
+ {
482
+ case 0x14:
483
+ more_ = visitor.bool_value(false, semantic_tag::none, *this, ec);
484
+ source_.ignore(1);
485
+ break;
486
+ case 0x15:
487
+ more_ = visitor.bool_value(true, semantic_tag::none, *this, ec);
488
+ source_.ignore(1);
489
+ break;
490
+ case 0x16:
491
+ more_ = visitor.null_value(semantic_tag::none, *this, ec);
492
+ source_.ignore(1);
493
+ break;
494
+ case 0x17:
495
+ more_ = visitor.null_value(semantic_tag::undefined, *this, ec);
496
+ source_.ignore(1);
497
+ break;
498
+ case 0x19: // Half-Precision Float (two-byte IEEE 754)
499
+ {
500
+ uint64_t val = get_uint64_value(ec);
501
+ if (ec)
502
+ {
503
+ return;
504
+ }
505
+ more_ = visitor.half_value(static_cast<uint16_t>(val), semantic_tag::none, *this, ec);
506
+ break;
507
+ }
508
+ case 0x1a: // Single-Precision Float (four-byte IEEE 754)
509
+ case 0x1b: // Double-Precision Float (eight-byte IEEE 754)
510
+ {
511
+ double val = get_double(ec);
512
+ if (ec)
513
+ {
514
+ return;
515
+ }
516
+ semantic_tag tag = semantic_tag::none;
517
+ if (other_tags_[item_tag])
518
+ {
519
+ if (item_tag_ == 1)
520
+ {
521
+ tag = semantic_tag::epoch_second;
522
+ }
523
+ other_tags_[item_tag] = false;
524
+ }
525
+ more_ = visitor.double_value(val, tag, *this, ec);
526
+ break;
527
+ }
528
+ default:
529
+ {
530
+ ec = cbor_errc::unknown_type;
531
+ more_ = false;
532
+ return;
533
+ }
534
+ }
535
+ break;
536
+ }
537
+ case jsoncons::cbor::detail::cbor_major_type::array:
538
+ {
539
+ if (other_tags_[item_tag])
540
+ {
541
+ switch (item_tag_)
542
+ {
543
+ case 0x04:
544
+ text_buffer_.clear();
545
+ read_decimal_fraction(text_buffer_, ec);
546
+ if (ec)
547
+ {
548
+ return;
549
+ }
550
+ more_ = visitor.string_value(text_buffer_, semantic_tag::bigdec, *this, ec);
551
+ break;
552
+ case 0x05:
553
+ text_buffer_.clear();
554
+ read_bigfloat(text_buffer_, ec);
555
+ if (ec)
556
+ {
557
+ return;
558
+ }
559
+ more_ = visitor.string_value(text_buffer_, semantic_tag::bigfloat, *this, ec);
560
+ break;
561
+ case 40: // row major storage
562
+ produce_begin_multi_dim(visitor, semantic_tag::multi_dim_row_major, ec);
563
+ break;
564
+ case 1040: // column major storage
565
+ produce_begin_multi_dim(visitor, semantic_tag::multi_dim_column_major, ec);
566
+ break;
567
+ default:
568
+ begin_array(visitor, info, ec);
569
+ break;
570
+ }
571
+ other_tags_[item_tag] = false;
572
+ }
573
+ else
574
+ {
575
+ begin_array(visitor, info, ec);
576
+ }
577
+ break;
578
+ }
579
+ case jsoncons::cbor::detail::cbor_major_type::map:
580
+ {
581
+ begin_object(visitor, info, ec);
582
+ break;
583
+ }
584
+ default:
585
+ break;
586
+ }
587
+ other_tags_[item_tag] = false;
588
+ }
589
+
590
+ void begin_array(json_visitor2& visitor, uint8_t info, std::error_code& ec)
591
+ {
592
+ if (JSONCONS_UNLIKELY(++nesting_depth_ > options_.max_nesting_depth()))
593
+ {
594
+ ec = cbor_errc::max_nesting_depth_exceeded;
595
+ more_ = false;
596
+ return;
597
+ }
598
+ semantic_tag tag = semantic_tag::none;
599
+ bool pop_stringref_map_stack = false;
600
+ if (other_tags_[stringref_namespace_tag])
601
+ {
602
+ stringref_map_stack_.emplace_back(alloc_);
603
+ other_tags_[stringref_namespace_tag] = false;
604
+ pop_stringref_map_stack = true;
605
+ }
606
+ switch (info)
607
+ {
608
+ case jsoncons::cbor::detail::additional_info::indefinite_length:
609
+ {
610
+ state_stack_.emplace_back(parse_mode::indefinite_array,0,pop_stringref_map_stack);
611
+ more_ = visitor.begin_array(tag, *this, ec);
612
+ source_.ignore(1);
613
+ break;
614
+ }
615
+ default: // definite length
616
+ {
617
+ std::size_t len = get_size(ec);
618
+ if (!more_)
619
+ {
620
+ return;
621
+ }
622
+ state_stack_.emplace_back(parse_mode::array,len,pop_stringref_map_stack);
623
+ more_ = visitor.begin_array(len, tag, *this, ec);
624
+ break;
625
+ }
626
+ }
627
+ }
628
+
629
+ void end_array(json_visitor2& visitor, std::error_code& ec)
630
+ {
631
+ --nesting_depth_;
632
+
633
+ more_ = visitor.end_array(*this, ec);
634
+ if (state_stack_.back().pop_stringref_map_stack)
635
+ {
636
+ stringref_map_stack_.pop_back();
637
+ }
638
+ state_stack_.pop_back();
639
+ }
640
+
641
+ void begin_object(json_visitor2& visitor, uint8_t info, std::error_code& ec)
642
+ {
643
+ if (JSONCONS_UNLIKELY(++nesting_depth_ > options_.max_nesting_depth()))
644
+ {
645
+ ec = cbor_errc::max_nesting_depth_exceeded;
646
+ more_ = false;
647
+ return;
648
+ }
649
+ bool pop_stringref_map_stack = false;
650
+ if (other_tags_[stringref_namespace_tag])
651
+ {
652
+ stringref_map_stack_.emplace_back(alloc_);
653
+ other_tags_[stringref_namespace_tag] = false;
654
+ pop_stringref_map_stack = true;
655
+ }
656
+ switch (info)
657
+ {
658
+ case jsoncons::cbor::detail::additional_info::indefinite_length:
659
+ {
660
+ state_stack_.emplace_back(parse_mode::indefinite_map_key,0,pop_stringref_map_stack);
661
+ more_ = visitor.begin_object(semantic_tag::none, *this, ec);
662
+ source_.ignore(1);
663
+ break;
664
+ }
665
+ default: // definite_length
666
+ {
667
+ std::size_t len = get_size(ec);
668
+ if (!more_)
669
+ {
670
+ return;
671
+ }
672
+ state_stack_.emplace_back(parse_mode::map_key,len,pop_stringref_map_stack);
673
+ more_ = visitor.begin_object(len, semantic_tag::none, *this, ec);
674
+ break;
675
+ }
676
+ }
677
+ }
678
+
679
+ void end_object(json_visitor2& visitor, std::error_code& ec)
680
+ {
681
+ --nesting_depth_;
682
+ more_ = visitor.end_object(*this, ec);
683
+ if (state_stack_.back().pop_stringref_map_stack)
684
+ {
685
+ stringref_map_stack_.pop_back();
686
+ }
687
+ state_stack_.pop_back();
688
+ }
689
+
690
+ void read_text_string(string_type& s, std::error_code& ec)
691
+ {
692
+ auto c = source_.peek();
693
+ if (c.eof)
694
+ {
695
+ ec = cbor_errc::unexpected_eof;
696
+ more_ = false;
697
+ return;
698
+ }
699
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(c.value);
700
+ uint8_t info = get_additional_information_value(c.value);
701
+
702
+ JSONCONS_ASSERT(major_type == jsoncons::cbor::detail::cbor_major_type::text_string);
703
+ auto func = [&s](Source& source, std::size_t length, std::error_code& ec) -> bool
704
+ {
705
+ if (source_reader<Source>::read(source, s, length) != length)
706
+ {
707
+ ec = cbor_errc::unexpected_eof;
708
+ return false;
709
+ }
710
+ return true;
711
+ };
712
+ iterate_string_chunks(func, major_type, ec);
713
+ if (!stringref_map_stack_.empty() &&
714
+ info != jsoncons::cbor::detail::additional_info::indefinite_length &&
715
+ s.length() >= jsoncons::cbor::detail::min_length_for_stringref(stringref_map_stack_.back().size()))
716
+ {
717
+ stringref_map_stack_.back().emplace_back(s);
718
+ }
719
+ }
720
+
721
+ std::size_t get_size(std::error_code& ec)
722
+ {
723
+ uint64_t u = get_uint64_value(ec);
724
+ if (!more_)
725
+ {
726
+ return 0;
727
+ }
728
+ std::size_t len = static_cast<std::size_t>(u);
729
+ if (len != u)
730
+ {
731
+ ec = cbor_errc::number_too_large;
732
+ more_ = false;
733
+ }
734
+ return len;
735
+ }
736
+
737
+ bool read_byte_string(std::vector<uint8_t,byte_allocator_type>& v, std::error_code& ec)
738
+ {
739
+ bool more = true;
740
+ v.clear();
741
+ auto c = source_.peek();
742
+ if (c.eof)
743
+ {
744
+ ec = cbor_errc::unexpected_eof;
745
+ more = false;
746
+ return more;
747
+ }
748
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(c.value);
749
+ uint8_t info = get_additional_information_value(c.value);
750
+
751
+ JSONCONS_ASSERT(major_type == jsoncons::cbor::detail::cbor_major_type::byte_string);
752
+
753
+ switch(info)
754
+ {
755
+ case jsoncons::cbor::detail::additional_info::indefinite_length:
756
+ {
757
+ auto func = [&v,&more](Source& source, std::size_t length, std::error_code& ec) -> bool
758
+ {
759
+ if (source_reader<Source>::read(source, v, length) != length)
760
+ {
761
+ ec = cbor_errc::unexpected_eof;
762
+ more = false;
763
+ return more;
764
+ }
765
+ return true;
766
+ };
767
+ iterate_string_chunks(func, major_type, ec);
768
+ break;
769
+ }
770
+ default:
771
+ {
772
+ std::size_t length = get_size(ec);
773
+ if (ec)
774
+ {
775
+ more = false;
776
+ return more;
777
+ }
778
+ if (source_reader<Source>::read(source_, v, length) != length)
779
+ {
780
+ ec = cbor_errc::unexpected_eof;
781
+ more = false;
782
+ return more;
783
+ }
784
+ if (!stringref_map_stack_.empty() &&
785
+ v.size() >= jsoncons::cbor::detail::min_length_for_stringref(stringref_map_stack_.back().size()))
786
+ {
787
+ stringref_map_stack_.back().emplace_back(v);
788
+ }
789
+ break;
790
+ }
791
+ }
792
+ return more;
793
+ }
794
+
795
+ template <class Function>
796
+ void iterate_string_chunks(Function& func, jsoncons::cbor::detail::cbor_major_type type, std::error_code& ec)
797
+ {
798
+ int nesting_level = 0;
799
+
800
+ bool done = false;
801
+ while (!done)
802
+ {
803
+ auto c = source_.peek();
804
+ if (c.eof)
805
+ {
806
+ ec = cbor_errc::unexpected_eof;
807
+ more_ = false;
808
+ return;
809
+ }
810
+ if (nesting_level > 0 && c.value == 0xff)
811
+ {
812
+ --nesting_level;
813
+ if (nesting_level == 0)
814
+ {
815
+ done = true;
816
+ }
817
+ source_.ignore(1);
818
+ continue;
819
+ }
820
+
821
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(c.value);
822
+ if (major_type != type)
823
+ {
824
+ ec = cbor_errc::illegal_chunked_string;
825
+ more_ = false;
826
+ return;
827
+ }
828
+ uint8_t info = get_additional_information_value(c.value);
829
+
830
+ switch (info)
831
+ {
832
+ case jsoncons::cbor::detail::additional_info::indefinite_length:
833
+ {
834
+ ++nesting_level;
835
+ source_.ignore(1);
836
+ break;
837
+ }
838
+ default: // definite length
839
+ {
840
+ std::size_t length = get_size(ec);
841
+ if (!more_)
842
+ {
843
+ return;
844
+ }
845
+ more_ = func(source_, length, ec);
846
+ if (!more_)
847
+ {
848
+ return;
849
+ }
850
+ if (nesting_level == 0)
851
+ {
852
+ done = true;
853
+ }
854
+ break;
855
+ }
856
+ }
857
+ }
858
+ }
859
+
860
+ uint64_t get_uint64_value(std::error_code& ec)
861
+ {
862
+ uint64_t val = 0;
863
+
864
+ uint8_t initial_b;
865
+ if (source_.read(&initial_b, 1) == 0)
866
+ {
867
+ ec = cbor_errc::unexpected_eof;
868
+ more_ = false;
869
+ return 0;
870
+ }
871
+ uint8_t info = get_additional_information_value(initial_b);
872
+ switch (info)
873
+ {
874
+ case JSONCONS_CBOR_0x00_0x17: // Integer 0x00..0x17 (0..23)
875
+ {
876
+ val = info;
877
+ break;
878
+ }
879
+
880
+ case 0x18: // Unsigned integer (one-byte uint8_t follows)
881
+ {
882
+ uint8_t b;
883
+ if (source_.read(&b, 1) == 0)
884
+ {
885
+ ec = cbor_errc::unexpected_eof;
886
+ more_ = false;
887
+ return val;
888
+ }
889
+ val = b;
890
+ break;
891
+ }
892
+
893
+ case 0x19: // Unsigned integer (two-byte uint16_t follows)
894
+ {
895
+ uint8_t buf[sizeof(uint16_t)];
896
+ source_.read(buf, sizeof(uint16_t));
897
+ val = binary::big_to_native<uint16_t>(buf, sizeof(buf));
898
+ break;
899
+ }
900
+
901
+ case 0x1a: // Unsigned integer (four-byte uint32_t follows)
902
+ {
903
+ uint8_t buf[sizeof(uint32_t)];
904
+ source_.read(buf, sizeof(uint32_t));
905
+ val = binary::big_to_native<uint32_t>(buf, sizeof(buf));
906
+ break;
907
+ }
908
+
909
+ case 0x1b: // Unsigned integer (eight-byte uint64_t follows)
910
+ {
911
+ uint8_t buf[sizeof(uint64_t)];
912
+ source_.read(buf, sizeof(uint64_t));
913
+ val = binary::big_to_native<uint64_t>(buf, sizeof(buf));
914
+ break;
915
+ }
916
+ default:
917
+ break;
918
+ }
919
+ return val;
920
+ }
921
+
922
+ int64_t get_int64_value(std::error_code& ec)
923
+ {
924
+ int64_t val = 0;
925
+
926
+ auto ch = source_.peek();
927
+ if (ch.eof)
928
+ {
929
+ ec = cbor_errc::unexpected_eof;
930
+ more_ = false;
931
+ return val;
932
+ }
933
+
934
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(ch.value);
935
+ uint8_t info = get_additional_information_value(ch.value);
936
+ switch (major_type)
937
+ {
938
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
939
+ source_.ignore(1);
940
+ switch (info)
941
+ {
942
+ case JSONCONS_CBOR_0x00_0x17: // 0x00..0x17 (0..23)
943
+ {
944
+ val = static_cast<int8_t>(- 1 - info);
945
+ break;
946
+ }
947
+ case 0x18: // Negative integer (one-byte uint8_t follows)
948
+ {
949
+ uint8_t b;
950
+ if (source_.read(&b, 1) == 0)
951
+ {
952
+ ec = cbor_errc::unexpected_eof;
953
+ more_ = false;
954
+ return val;
955
+ }
956
+ val = static_cast<int64_t>(-1) - static_cast<int64_t>(b);
957
+ break;
958
+ }
959
+
960
+ case 0x19: // Negative integer -1-n (two-byte uint16_t follows)
961
+ {
962
+ uint8_t buf[sizeof(uint16_t)];
963
+ if (source_.read(buf, sizeof(uint16_t)) != sizeof(uint16_t))
964
+ {
965
+ ec = cbor_errc::unexpected_eof;
966
+ more_ = false;
967
+ return val;
968
+ }
969
+ auto x = binary::big_to_native<uint16_t>(buf, sizeof(buf));
970
+ val = static_cast<int64_t>(-1)- x;
971
+ break;
972
+ }
973
+
974
+ case 0x1a: // Negative integer -1-n (four-byte uint32_t follows)
975
+ {
976
+ uint8_t buf[sizeof(uint32_t)];
977
+ if (source_.read(buf, sizeof(uint32_t)) != sizeof(uint32_t))
978
+ {
979
+ ec = cbor_errc::unexpected_eof;
980
+ more_ = false;
981
+ return val;
982
+ }
983
+ auto x = binary::big_to_native<uint32_t>(buf, sizeof(buf));
984
+ val = static_cast<int64_t>(-1)- x;
985
+ break;
986
+ }
987
+
988
+ case 0x1b: // Negative integer -1-n (eight-byte uint64_t follows)
989
+ {
990
+ uint8_t buf[sizeof(uint64_t)];
991
+ if (source_.read(buf, sizeof(uint64_t)) != sizeof(uint64_t))
992
+ {
993
+ ec = cbor_errc::unexpected_eof;
994
+ more_ = false;
995
+ return val;
996
+ }
997
+ auto x = binary::big_to_native<uint64_t>(buf, sizeof(buf));
998
+ val = static_cast<int64_t>(-1)- static_cast<int64_t>(x);
999
+ break;
1000
+ }
1001
+ }
1002
+ break;
1003
+
1004
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
1005
+ {
1006
+ uint64_t x = get_uint64_value(ec);
1007
+ if (ec)
1008
+ {
1009
+ return 0;
1010
+ }
1011
+ if (x <= static_cast<uint64_t>((std::numeric_limits<int64_t>::max)()))
1012
+ {
1013
+ val = x;
1014
+ }
1015
+ else
1016
+ {
1017
+ // error;
1018
+ }
1019
+
1020
+ break;
1021
+ }
1022
+ break;
1023
+ default:
1024
+ break;
1025
+ }
1026
+
1027
+ return val;
1028
+ }
1029
+
1030
+ double get_double(std::error_code& ec)
1031
+ {
1032
+ double val = 0;
1033
+
1034
+ uint8_t b;
1035
+ if (source_.read(&b, 1) == 0)
1036
+ {
1037
+ ec = cbor_errc::unexpected_eof;
1038
+ more_ = false;
1039
+ return 0;
1040
+ }
1041
+ uint8_t info = get_additional_information_value(b);
1042
+ switch (info)
1043
+ {
1044
+ case 0x1a: // Single-Precision Float (four-byte IEEE 754)
1045
+ {
1046
+ uint8_t buf[sizeof(float)];
1047
+ if (source_.read(buf, sizeof(float)) !=sizeof(float))
1048
+ {
1049
+ ec = cbor_errc::unexpected_eof;
1050
+ more_ = false;
1051
+ return 0;
1052
+ }
1053
+ val = binary::big_to_native<float>(buf, sizeof(buf));
1054
+ break;
1055
+ }
1056
+
1057
+ case 0x1b: // Double-Precision Float (eight-byte IEEE 754)
1058
+ {
1059
+ uint8_t buf[sizeof(double)];
1060
+ if (source_.read(buf, sizeof(double)) != sizeof(double))
1061
+ {
1062
+ ec = cbor_errc::unexpected_eof;
1063
+ more_ = false;
1064
+ return 0;
1065
+ }
1066
+ val = binary::big_to_native<double>(buf, sizeof(buf));
1067
+ break;
1068
+ }
1069
+ default:
1070
+ break;
1071
+ }
1072
+
1073
+ return val;
1074
+ }
1075
+
1076
+ void read_decimal_fraction(string_type& result, std::error_code& ec)
1077
+ {
1078
+ std::size_t size = get_size(ec);
1079
+ if (!more_)
1080
+ {
1081
+ return;
1082
+ }
1083
+ if (size != 2)
1084
+ {
1085
+ ec = cbor_errc::invalid_decimal_fraction;
1086
+ more_ = false;
1087
+ return;
1088
+ }
1089
+
1090
+ auto c = source_.peek();
1091
+ if (c.eof)
1092
+ {
1093
+ ec = cbor_errc::unexpected_eof;
1094
+ more_ = false;
1095
+ return;
1096
+ }
1097
+ int64_t exponent = 0;
1098
+ switch (get_major_type(c.value))
1099
+ {
1100
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
1101
+ {
1102
+ exponent = get_uint64_value(ec);
1103
+ if (ec)
1104
+ {
1105
+ return;
1106
+ }
1107
+ break;
1108
+ }
1109
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
1110
+ {
1111
+ exponent = get_int64_value(ec);
1112
+ if (ec)
1113
+ {
1114
+ return;
1115
+ }
1116
+ break;
1117
+ }
1118
+ default:
1119
+ {
1120
+ ec = cbor_errc::invalid_decimal_fraction;
1121
+ more_ = false;
1122
+ return;
1123
+ }
1124
+ }
1125
+
1126
+ string_type s;
1127
+
1128
+ c = source_.peek();
1129
+ if (c.eof)
1130
+ {
1131
+ ec = cbor_errc::unexpected_eof;
1132
+ more_ = false;
1133
+ return;
1134
+ }
1135
+
1136
+ switch (get_major_type(c.value))
1137
+ {
1138
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
1139
+ {
1140
+ uint64_t val = get_uint64_value(ec);
1141
+ if (ec)
1142
+ {
1143
+ return;
1144
+ }
1145
+ jsoncons::detail::from_integer(val, s);
1146
+ break;
1147
+ }
1148
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
1149
+ {
1150
+ int64_t val = get_int64_value(ec);
1151
+ if (ec)
1152
+ {
1153
+ return;
1154
+ }
1155
+ jsoncons::detail::from_integer(val, s);
1156
+ break;
1157
+ }
1158
+ case jsoncons::cbor::detail::cbor_major_type::semantic_tag:
1159
+ {
1160
+ uint8_t b;
1161
+ if (source_.read(&b, 1) == 0)
1162
+ {
1163
+ ec = cbor_errc::unexpected_eof;
1164
+ more_ = false;
1165
+ return;
1166
+ }
1167
+ uint8_t tag = get_additional_information_value(b);
1168
+ c = source_.peek();
1169
+ if (c.eof)
1170
+ {
1171
+ ec = cbor_errc::unexpected_eof;
1172
+ more_ = false;
1173
+ return;
1174
+ }
1175
+
1176
+ if (get_major_type(c.value) == jsoncons::cbor::detail::cbor_major_type::byte_string)
1177
+ {
1178
+ bytes_buffer_.clear();
1179
+ read_byte_string(bytes_buffer_, ec);
1180
+ if (ec)
1181
+ {
1182
+ more_ = false;
1183
+ return;
1184
+ }
1185
+ if (tag == 2)
1186
+ {
1187
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1188
+ n.write_string(s);
1189
+ }
1190
+ else if (tag == 3)
1191
+ {
1192
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1193
+ n = -1 - n;
1194
+ n.write_string(s);
1195
+ }
1196
+ }
1197
+ break;
1198
+ }
1199
+ default:
1200
+ {
1201
+ ec = cbor_errc::invalid_decimal_fraction;
1202
+ more_ = false;
1203
+ return;
1204
+ }
1205
+ }
1206
+
1207
+ if (s.size() >= static_cast<std::size_t>((std::numeric_limits<int32_t>::max)()) ||
1208
+ exponent >= (std::numeric_limits<int32_t>::max)() ||
1209
+ exponent <= (std::numeric_limits<int32_t>::min)())
1210
+ {
1211
+ ec = cbor_errc::invalid_decimal_fraction;
1212
+ more_ = false;
1213
+ return;
1214
+ }
1215
+ else if (s.size() > 0)
1216
+ {
1217
+ if (s[0] == '-')
1218
+ {
1219
+ result.push_back('-');
1220
+ jsoncons::detail::prettify_string(s.c_str()+1, s.size()-1, (int)exponent, -4, 17, result);
1221
+ }
1222
+ else
1223
+ {
1224
+ jsoncons::detail::prettify_string(s.c_str(), s.size(), (int)exponent, -4, 17, result);
1225
+ }
1226
+ }
1227
+ else
1228
+ {
1229
+ ec = cbor_errc::invalid_decimal_fraction;
1230
+ more_ = false;
1231
+ return;
1232
+ }
1233
+ }
1234
+
1235
+ void read_bigfloat(string_type& s, std::error_code& ec)
1236
+ {
1237
+ std::size_t size = get_size(ec);
1238
+ if (!more_)
1239
+ {
1240
+ return;
1241
+ }
1242
+ if (size != 2)
1243
+ {
1244
+ ec = cbor_errc::invalid_bigfloat;
1245
+ more_ = false;
1246
+ return;
1247
+ }
1248
+
1249
+ auto c = source_.peek();
1250
+ if (c.eof)
1251
+ {
1252
+ ec = cbor_errc::unexpected_eof;
1253
+ more_ = false;
1254
+ return;
1255
+ }
1256
+ int64_t exponent = 0;
1257
+ switch (get_major_type(c.value))
1258
+ {
1259
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
1260
+ {
1261
+ exponent = get_uint64_value(ec);
1262
+ if (ec)
1263
+ {
1264
+ return;
1265
+ }
1266
+ break;
1267
+ }
1268
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
1269
+ {
1270
+ exponent = get_int64_value(ec);
1271
+ if (ec)
1272
+ {
1273
+ return;
1274
+ }
1275
+ break;
1276
+ }
1277
+ default:
1278
+ {
1279
+ ec = cbor_errc::invalid_bigfloat;
1280
+ more_ = false;
1281
+ return;
1282
+ }
1283
+ }
1284
+
1285
+ c = source_.peek();
1286
+ if (c.eof)
1287
+ {
1288
+ ec = cbor_errc::unexpected_eof;
1289
+ more_ = false;
1290
+ return;
1291
+ }
1292
+ switch (get_major_type(c.value))
1293
+ {
1294
+ case jsoncons::cbor::detail::cbor_major_type::unsigned_integer:
1295
+ {
1296
+ uint64_t val = get_uint64_value(ec);
1297
+ if (ec)
1298
+ {
1299
+ return;
1300
+ }
1301
+ s.push_back('0');
1302
+ s.push_back('x');
1303
+ jsoncons::detail::integer_to_string_hex(val, s);
1304
+ break;
1305
+ }
1306
+ case jsoncons::cbor::detail::cbor_major_type::negative_integer:
1307
+ {
1308
+ int64_t val = get_int64_value(ec);
1309
+ if (ec)
1310
+ {
1311
+ return;
1312
+ }
1313
+ s.push_back('-');
1314
+ s.push_back('0');
1315
+ s.push_back('x');
1316
+ jsoncons::detail::integer_to_string_hex(static_cast<uint64_t>(-val), s);
1317
+ break;
1318
+ }
1319
+ case jsoncons::cbor::detail::cbor_major_type::semantic_tag:
1320
+ {
1321
+ uint8_t b;
1322
+ if (source_.read(&b, 1) == 0)
1323
+ {
1324
+ ec = cbor_errc::unexpected_eof;
1325
+ more_ = false;
1326
+ return;
1327
+ }
1328
+ uint8_t tag = get_additional_information_value(b);
1329
+
1330
+ c = source_.peek();
1331
+ if (c.eof)
1332
+ {
1333
+ ec = cbor_errc::unexpected_eof;
1334
+ more_ = false;
1335
+ return;
1336
+ }
1337
+
1338
+ if (get_major_type(c.value) == jsoncons::cbor::detail::cbor_major_type::byte_string)
1339
+ {
1340
+ bytes_buffer_.clear();
1341
+ more_ = read_byte_string(bytes_buffer_, ec);
1342
+ if (!more_)
1343
+ {
1344
+ return;
1345
+ }
1346
+ if (tag == 2)
1347
+ {
1348
+ s.push_back('0');
1349
+ s.push_back('x');
1350
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1351
+ n.write_string_hex(s);
1352
+ }
1353
+ else if (tag == 3)
1354
+ {
1355
+ s.push_back('-');
1356
+ s.push_back('0');
1357
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1358
+ n = -1 - n;
1359
+ n.write_string_hex(s);
1360
+ s[2] = 'x'; // overwrite minus
1361
+ }
1362
+ }
1363
+ break;
1364
+ }
1365
+ default:
1366
+ {
1367
+ ec = cbor_errc::invalid_bigfloat;
1368
+ more_ = false;
1369
+ return;
1370
+ }
1371
+ }
1372
+
1373
+ s.push_back('p');
1374
+ if (exponent >=0)
1375
+ {
1376
+ jsoncons::detail::integer_to_string_hex(static_cast<uint64_t>(exponent), s);
1377
+ }
1378
+ else
1379
+ {
1380
+ s.push_back('-');
1381
+ jsoncons::detail::integer_to_string_hex(static_cast<uint64_t>(-exponent), s);
1382
+ }
1383
+ }
1384
+
1385
+ static jsoncons::cbor::detail::cbor_major_type get_major_type(uint8_t type)
1386
+ {
1387
+ static constexpr uint8_t major_type_shift = 0x05;
1388
+ uint8_t value = type >> major_type_shift;
1389
+ return static_cast<jsoncons::cbor::detail::cbor_major_type>(value);
1390
+ }
1391
+
1392
+ static uint8_t get_additional_information_value(uint8_t type)
1393
+ {
1394
+ static constexpr uint8_t additional_information_mask = (1U << 5) - 1;
1395
+ uint8_t value = type & additional_information_mask;
1396
+ return value;
1397
+ }
1398
+
1399
+ void read_tags(std::error_code& ec)
1400
+ {
1401
+ auto c = source_.peek();
1402
+ if (c.eof)
1403
+ {
1404
+ ec = cbor_errc::unexpected_eof;
1405
+ more_ = false;
1406
+ return;
1407
+ }
1408
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(c.value);
1409
+
1410
+ while (major_type == jsoncons::cbor::detail::cbor_major_type::semantic_tag)
1411
+ {
1412
+ uint64_t val = get_uint64_value(ec);
1413
+ if (!more_)
1414
+ {
1415
+ return;
1416
+ }
1417
+ switch(val)
1418
+ {
1419
+ case 25: // stringref
1420
+ other_tags_[stringref_tag] = true;
1421
+ break;
1422
+ case 256: // stringref-namespace
1423
+ other_tags_[stringref_namespace_tag] = true;
1424
+ break;
1425
+ default:
1426
+ other_tags_[item_tag] = true;
1427
+ item_tag_ = val;
1428
+ break;
1429
+ }
1430
+ c = source_.peek();
1431
+ if (c.eof)
1432
+ {
1433
+ ec = cbor_errc::unexpected_eof;
1434
+ more_ = false;
1435
+ return;
1436
+ }
1437
+ major_type = get_major_type(c.value);
1438
+ }
1439
+ }
1440
+
1441
+ void handle_string(json_visitor2& visitor, const jsoncons::basic_string_view<char>& v, std::error_code& ec)
1442
+ {
1443
+ semantic_tag tag = semantic_tag::none;
1444
+ if (other_tags_[item_tag])
1445
+ {
1446
+ switch (item_tag_)
1447
+ {
1448
+ case 0:
1449
+ tag = semantic_tag::datetime;
1450
+ break;
1451
+ case 32:
1452
+ tag = semantic_tag::uri;
1453
+ break;
1454
+ case 33:
1455
+ tag = semantic_tag::base64url;
1456
+ break;
1457
+ case 34:
1458
+ tag = semantic_tag::base64;
1459
+ break;
1460
+ default:
1461
+ break;
1462
+ }
1463
+ other_tags_[item_tag] = false;
1464
+ }
1465
+ more_ = visitor.string_value(v, tag, *this, ec);
1466
+ }
1467
+
1468
+ static jsoncons::endian get_typed_array_endianness(const uint8_t tag)
1469
+ {
1470
+ return ((tag & detail::cbor_array_tags_e_mask) >> detail::cbor_array_tags_e_shift) == 0 ? jsoncons::endian::big : jsoncons::endian::little;
1471
+ }
1472
+
1473
+ static std::size_t get_typed_array_bytes_per_element(const uint8_t tag)
1474
+ {
1475
+ const uint8_t f = (tag & detail::cbor_array_tags_f_mask) >> detail::cbor_array_tags_f_shift;
1476
+ const uint8_t ll = (tag & detail::cbor_array_tags_ll_mask) >> detail::cbor_array_tags_ll_shift;
1477
+
1478
+ return std::size_t(1) << (f + ll);
1479
+ }
1480
+
1481
+ template <typename Read>
1482
+ void write_byte_string(Read read, json_visitor2& visitor, std::error_code& ec)
1483
+ {
1484
+ if (other_tags_[item_tag])
1485
+ {
1486
+ switch (item_tag_)
1487
+ {
1488
+ case 0x2:
1489
+ {
1490
+ bytes_buffer_.clear();
1491
+ read(bytes_buffer_,ec);
1492
+ if (ec)
1493
+ {
1494
+ more_ = false;
1495
+ return;
1496
+ }
1497
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1498
+ text_buffer_.clear();
1499
+ n.write_string(text_buffer_);
1500
+ more_ = visitor.string_value(text_buffer_, semantic_tag::bigint, *this, ec);
1501
+ break;
1502
+ }
1503
+ case 0x3:
1504
+ {
1505
+ bytes_buffer_.clear();
1506
+ read(bytes_buffer_,ec);
1507
+ if (ec)
1508
+ {
1509
+ more_ = false;
1510
+ return;
1511
+ }
1512
+ bigint n = bigint::from_bytes_be(1, bytes_buffer_.data(), bytes_buffer_.size());
1513
+ n = -1 - n;
1514
+ text_buffer_.clear();
1515
+ n.write_string(text_buffer_);
1516
+ more_ = visitor.string_value(text_buffer_, semantic_tag::bigint, *this, ec);
1517
+ break;
1518
+ }
1519
+ case 0x15:
1520
+ {
1521
+ read(bytes_buffer_,ec);
1522
+ if (ec)
1523
+ {
1524
+ more_ = false;
1525
+ return;
1526
+ }
1527
+ more_ = visitor.byte_string_value(bytes_buffer_, semantic_tag::base64url, *this, ec);
1528
+ break;
1529
+ }
1530
+ case 0x16:
1531
+ {
1532
+ read(bytes_buffer_,ec);
1533
+ if (ec)
1534
+ {
1535
+ more_ = false;
1536
+ return;
1537
+ }
1538
+ more_ = visitor.byte_string_value(bytes_buffer_, semantic_tag::base64, *this, ec);
1539
+ break;
1540
+ }
1541
+ case 0x17:
1542
+ {
1543
+ read(bytes_buffer_,ec);
1544
+ if (ec)
1545
+ {
1546
+ more_ = false;
1547
+ return;
1548
+ }
1549
+ more_ = visitor.byte_string_value(bytes_buffer_, semantic_tag::base16, *this, ec);
1550
+ break;
1551
+ }
1552
+ case 0x40:
1553
+ {
1554
+ typed_array_.clear();
1555
+ read(typed_array_,ec);
1556
+ if (ec)
1557
+ {
1558
+ more_ = false;
1559
+ return;
1560
+ }
1561
+ uint8_t* data = reinterpret_cast<uint8_t*>(typed_array_.data());
1562
+ std::size_t size = typed_array_.size();
1563
+ more_ = visitor.typed_array(jsoncons::span<const uint8_t>(data,size), semantic_tag::none, *this, ec);
1564
+ break;
1565
+ }
1566
+ case 0x44:
1567
+ {
1568
+ typed_array_.clear();
1569
+ read(typed_array_,ec);
1570
+ if (ec)
1571
+ {
1572
+ more_ = false;
1573
+ return;
1574
+ }
1575
+ uint8_t* data = reinterpret_cast<uint8_t*>(typed_array_.data());
1576
+ std::size_t size = typed_array_.size();
1577
+ more_ = visitor.typed_array(jsoncons::span<const uint8_t>(data,size), semantic_tag::clamped, *this, ec);
1578
+ break;
1579
+ }
1580
+ case 0x41:
1581
+ case 0x45:
1582
+ {
1583
+ typed_array_.clear();
1584
+ read(typed_array_,ec);
1585
+ if (ec)
1586
+ {
1587
+ more_ = false;
1588
+ return;
1589
+ }
1590
+ const uint8_t tag = (uint8_t)item_tag_;
1591
+ jsoncons::endian e = get_typed_array_endianness(tag);
1592
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1593
+
1594
+ uint16_t* data = reinterpret_cast<uint16_t*>(typed_array_.data());
1595
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1596
+
1597
+ if (e != jsoncons::endian::native)
1598
+ {
1599
+ for (std::size_t i = 0; i < size; ++i)
1600
+ {
1601
+ data[i] = binary::byte_swap<uint16_t>(data[i]);
1602
+ }
1603
+ }
1604
+ more_ = visitor.typed_array(jsoncons::span<const uint16_t>(data,size), semantic_tag::none, *this, ec);
1605
+ break;
1606
+ }
1607
+ case 0x42:
1608
+ case 0x46:
1609
+ {
1610
+ typed_array_.clear();
1611
+ read(typed_array_,ec);
1612
+ if (ec)
1613
+ {
1614
+ more_ = false;
1615
+ return;
1616
+ }
1617
+ const uint8_t tag = (uint8_t)item_tag_;
1618
+ jsoncons::endian e = get_typed_array_endianness(tag);
1619
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1620
+
1621
+ uint32_t* data = reinterpret_cast<uint32_t*>(typed_array_.data());
1622
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1623
+ if (e != jsoncons::endian::native)
1624
+ {
1625
+ for (std::size_t i = 0; i < size; ++i)
1626
+ {
1627
+ data[i] = binary::byte_swap<uint32_t>(data[i]);
1628
+ }
1629
+ }
1630
+ more_ = visitor.typed_array(jsoncons::span<const uint32_t>(data,size), semantic_tag::none, *this, ec);
1631
+ break;
1632
+ }
1633
+ case 0x43:
1634
+ case 0x47:
1635
+ {
1636
+ typed_array_.clear();
1637
+ read(typed_array_,ec);
1638
+ if (ec)
1639
+ {
1640
+ more_ = false;
1641
+ return;
1642
+ }
1643
+ const uint8_t tag = (uint8_t)item_tag_;
1644
+ jsoncons::endian e = get_typed_array_endianness(tag);
1645
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1646
+
1647
+ uint64_t* data = reinterpret_cast<uint64_t*>(typed_array_.data());
1648
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1649
+ if (e != jsoncons::endian::native)
1650
+ {
1651
+ for (std::size_t i = 0; i < size; ++i)
1652
+ {
1653
+ data[i] = binary::byte_swap<uint64_t>(data[i]);
1654
+ }
1655
+ }
1656
+ more_ = visitor.typed_array(jsoncons::span<const uint64_t>(data,size), semantic_tag::none, *this, ec);
1657
+ break;
1658
+ }
1659
+ case 0x48:
1660
+ {
1661
+ typed_array_.clear();
1662
+ read(typed_array_,ec);
1663
+ if (ec)
1664
+ {
1665
+ more_ = false;
1666
+ return;
1667
+ }
1668
+ int8_t* data = reinterpret_cast<int8_t*>(typed_array_.data());
1669
+ std::size_t size = typed_array_.size();
1670
+ more_ = visitor.typed_array(jsoncons::span<const int8_t>(data,size), semantic_tag::none, *this, ec);
1671
+ break;
1672
+ }
1673
+ case 0x49:
1674
+ case 0x4d:
1675
+ {
1676
+ typed_array_.clear();
1677
+ read(typed_array_,ec);
1678
+ if (ec)
1679
+ {
1680
+ more_ = false;
1681
+ return;
1682
+ }
1683
+ const uint8_t tag = (uint8_t)item_tag_;
1684
+ jsoncons::endian e = get_typed_array_endianness(tag);
1685
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1686
+
1687
+ int16_t* data = reinterpret_cast<int16_t*>(typed_array_.data());
1688
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1689
+ if (e != jsoncons::endian::native)
1690
+ {
1691
+ for (std::size_t i = 0; i < size; ++i)
1692
+ {
1693
+ data[i] = binary::byte_swap<int16_t>(data[i]);
1694
+ }
1695
+ }
1696
+ more_ = visitor.typed_array(jsoncons::span<const int16_t>(data,size), semantic_tag::none, *this, ec);
1697
+ break;
1698
+ }
1699
+ case 0x4a:
1700
+ case 0x4e:
1701
+ {
1702
+ typed_array_.clear();
1703
+ read(typed_array_,ec);
1704
+ if (ec)
1705
+ {
1706
+ more_ = false;
1707
+ return;
1708
+ }
1709
+ const uint8_t tag = (uint8_t)item_tag_;
1710
+ jsoncons::endian e = get_typed_array_endianness(tag);
1711
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1712
+
1713
+ int32_t* data = reinterpret_cast<int32_t*>(typed_array_.data());
1714
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1715
+ if (e != jsoncons::endian::native)
1716
+ {
1717
+ for (std::size_t i = 0; i < size; ++i)
1718
+ {
1719
+ data[i] = binary::byte_swap<int32_t>(data[i]);
1720
+ }
1721
+ }
1722
+ more_ = visitor.typed_array(jsoncons::span<const int32_t>(data,size), semantic_tag::none, *this, ec);
1723
+ break;
1724
+ }
1725
+ case 0x4b:
1726
+ case 0x4f:
1727
+ {
1728
+ typed_array_.clear();
1729
+ read(typed_array_,ec);
1730
+ if (ec)
1731
+ {
1732
+ more_ = false;
1733
+ return;
1734
+ }
1735
+ const uint8_t tag = (uint8_t)item_tag_;
1736
+ jsoncons::endian e = get_typed_array_endianness(tag);
1737
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1738
+
1739
+ int64_t* data = reinterpret_cast<int64_t*>(typed_array_.data());
1740
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1741
+ if (e != jsoncons::endian::native)
1742
+ {
1743
+ for (std::size_t i = 0; i < size; ++i)
1744
+ {
1745
+ data[i] = binary::byte_swap<int64_t>(data[i]);
1746
+ }
1747
+ }
1748
+ more_ = visitor.typed_array(jsoncons::span<const int64_t>(data,size), semantic_tag::none, *this, ec);
1749
+ break;
1750
+ }
1751
+ case 0x50:
1752
+ case 0x54:
1753
+ {
1754
+ typed_array_.clear();
1755
+ read(typed_array_,ec);
1756
+ if (ec)
1757
+ {
1758
+ more_ = false;
1759
+ return;
1760
+ }
1761
+ const uint8_t tag = (uint8_t)item_tag_;
1762
+ jsoncons::endian e = get_typed_array_endianness(tag);
1763
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1764
+
1765
+ uint16_t* data = reinterpret_cast<uint16_t*>(typed_array_.data());
1766
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1767
+ if (e != jsoncons::endian::native)
1768
+ {
1769
+ for (std::size_t i = 0; i < size; ++i)
1770
+ {
1771
+ data[i] = binary::byte_swap<uint16_t>(data[i]);
1772
+ }
1773
+ }
1774
+ more_ = visitor.typed_array(half_arg, jsoncons::span<const uint16_t>(data,size), semantic_tag::none, *this, ec);
1775
+ break;
1776
+ }
1777
+ case 0x51:
1778
+ case 0x55:
1779
+ {
1780
+ typed_array_.clear();
1781
+ read(typed_array_,ec);
1782
+ if (ec)
1783
+ {
1784
+ more_ = false;
1785
+ return;
1786
+ }
1787
+ const uint8_t tag = (uint8_t)item_tag_;
1788
+ jsoncons::endian e = get_typed_array_endianness(tag);
1789
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1790
+
1791
+ float* data = reinterpret_cast<float*>(typed_array_.data());
1792
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1793
+ if (e != jsoncons::endian::native)
1794
+ {
1795
+ for (std::size_t i = 0; i < size; ++i)
1796
+ {
1797
+ data[i] = binary::byte_swap<float>(data[i]);
1798
+ }
1799
+ }
1800
+ more_ = visitor.typed_array(jsoncons::span<const float>(data,size), semantic_tag::none, *this, ec);
1801
+ break;
1802
+ }
1803
+ case 0x52:
1804
+ case 0x56:
1805
+ {
1806
+ typed_array_.clear();
1807
+ read(typed_array_,ec);
1808
+ if (ec)
1809
+ {
1810
+ more_ = false;
1811
+ return;
1812
+ }
1813
+ const uint8_t tag = (uint8_t)item_tag_;
1814
+ jsoncons::endian e = get_typed_array_endianness(tag);
1815
+ const size_t bytes_per_elem = get_typed_array_bytes_per_element(tag);
1816
+
1817
+ double* data = reinterpret_cast<double*>(typed_array_.data());
1818
+ std::size_t size = typed_array_.size()/bytes_per_elem;
1819
+
1820
+ if (e != jsoncons::endian::native)
1821
+ {
1822
+ for (std::size_t i = 0; i < size; ++i)
1823
+ {
1824
+ data[i] = binary::byte_swap<double>(data[i]);
1825
+ }
1826
+ }
1827
+ more_ = visitor.typed_array(jsoncons::span<const double>(data,size), semantic_tag::none, *this, ec);
1828
+ break;
1829
+ }
1830
+ default:
1831
+ {
1832
+ read(bytes_buffer_,ec);
1833
+ if (ec)
1834
+ {
1835
+ more_ = false;
1836
+ return;
1837
+ }
1838
+ more_ = visitor.byte_string_value(bytes_buffer_, item_tag_, *this, ec);
1839
+ break;
1840
+ }
1841
+ }
1842
+ other_tags_[item_tag] = false;
1843
+ }
1844
+ else
1845
+ {
1846
+ read(bytes_buffer_,ec);
1847
+ if (ec)
1848
+ {
1849
+ return;
1850
+ }
1851
+ more_ = visitor.byte_string_value(bytes_buffer_, semantic_tag::none, *this, ec);
1852
+ }
1853
+ }
1854
+
1855
+ void produce_begin_multi_dim(json_visitor2& visitor,
1856
+ semantic_tag tag,
1857
+ std::error_code& ec)
1858
+ {
1859
+ uint8_t b;
1860
+ if (source_.read(&b, 1) == 0)
1861
+ {
1862
+ ec = cbor_errc::unexpected_eof;
1863
+ more_ = false;
1864
+ return;
1865
+ }
1866
+ jsoncons::cbor::detail::cbor_major_type major_type = get_major_type(b);
1867
+ JSONCONS_ASSERT(major_type == jsoncons::cbor::detail::cbor_major_type::array);
1868
+ uint8_t info = get_additional_information_value(b);
1869
+
1870
+ read_shape(info, ec);
1871
+ if (ec)
1872
+ {
1873
+ return;
1874
+ }
1875
+
1876
+ state_stack_.emplace_back(parse_mode::multi_dim, 0);
1877
+ more_ = visitor.begin_multi_dim(shape_, tag, *this, ec);
1878
+ }
1879
+
1880
+ void produce_end_multi_dim(json_visitor2& visitor, std::error_code& ec)
1881
+ {
1882
+ more_ = visitor.end_multi_dim(*this, ec);
1883
+ state_stack_.pop_back();
1884
+ }
1885
+
1886
+ void read_shape(uint8_t info, std::error_code& ec)
1887
+ {
1888
+ shape_.clear();
1889
+ switch (info)
1890
+ {
1891
+ case jsoncons::cbor::detail::additional_info::indefinite_length:
1892
+ {
1893
+ while (true)
1894
+ {
1895
+ auto c = source_.peek();
1896
+ if (c.eof)
1897
+ {
1898
+ ec = cbor_errc::unexpected_eof;
1899
+ more_ = false;
1900
+ return;
1901
+ }
1902
+ if (c.value == 0xff)
1903
+ {
1904
+ source_.ignore(1);
1905
+ }
1906
+ else
1907
+ {
1908
+ std::size_t dim = get_size(ec);
1909
+ if (!more_)
1910
+ {
1911
+ return;
1912
+ }
1913
+ shape_.push_back(dim);
1914
+ }
1915
+ }
1916
+ break;
1917
+ }
1918
+ default:
1919
+ {
1920
+ std::size_t size = get_size(ec);
1921
+ if (!more_)
1922
+ {
1923
+ return;
1924
+ }
1925
+ for (std::size_t i = 0; more_ && i < size; ++i)
1926
+ {
1927
+ std::size_t dim = get_size(ec);
1928
+ if (!more_)
1929
+ {
1930
+ return;
1931
+ }
1932
+ shape_.push_back(dim);
1933
+ }
1934
+ break;
1935
+ }
1936
+ }
1937
+ }
1938
+ };
1939
+
1940
+ }}
1941
+
1942
+ #endif