1namespace simdjson {
2namespace SIMDJSON_IMPLEMENTATION {
3namespace ondemand {
4
5simdjson_inline parser::parser(size_t max_capacity) noexcept
6 : _max_capacity{max_capacity} {
7}
8
9simdjson_warn_unused simdjson_inline error_code parser::allocate(size_t new_capacity, size_t new_max_depth) noexcept {
10 if (new_capacity > max_capacity()) { return CAPACITY; }
11 if (string_buf && new_capacity == capacity() && new_max_depth == max_depth()) { return SUCCESS; }
12
13 // string_capacity copied from document::allocate
14 _capacity = 0;
15 size_t string_capacity = SIMDJSON_ROUNDUP_N(5 * new_capacity / 3 + SIMDJSON_PADDING, 64);
16 string_buf.reset(p: new (std::nothrow) uint8_t[string_capacity]);
17#if SIMDJSON_DEVELOPMENT_CHECKS
18 start_positions.reset(new (std::nothrow) token_position[new_max_depth]);
19#endif
20 if (implementation) {
21 SIMDJSON_TRY( implementation->set_capacity(new_capacity) );
22 SIMDJSON_TRY( implementation->set_max_depth(new_max_depth) );
23 } else {
24 SIMDJSON_TRY( simdjson::get_active_implementation()->create_dom_parser_implementation(new_capacity, new_max_depth, implementation) );
25 }
26 _capacity = new_capacity;
27 _max_depth = new_max_depth;
28 return SUCCESS;
29}
30
31simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(padded_string_view json) & noexcept {
32 if (json.padding() < SIMDJSON_PADDING) { return INSUFFICIENT_PADDING; }
33
34 // Allocate if needed
35 if (capacity() < json.length() || !string_buf) {
36 SIMDJSON_TRY( allocate(json.length(), max_depth()) );
37 }
38
39 // Run stage 1.
40 SIMDJSON_TRY( implementation->stage1(reinterpret_cast<const uint8_t *>(json.data()), json.length(), stage1_mode::regular) );
41 return document::start(iter: { reinterpret_cast<const uint8_t *>(json.data()), this });
42}
43
44simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(const char *json, size_t len, size_t allocated) & noexcept {
45 return iterate(json: padded_string_view(json, len, allocated));
46}
47
48simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(const uint8_t *json, size_t len, size_t allocated) & noexcept {
49 return iterate(json: padded_string_view(json, len, allocated));
50}
51
52simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(std::string_view json, size_t allocated) & noexcept {
53 return iterate(json: padded_string_view(json, allocated));
54}
55
56simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(const std::string &json) & noexcept {
57 return iterate(json: padded_string_view(json));
58}
59
60simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(const simdjson_result<padded_string_view> &result) & noexcept {
61 // We don't presently have a way to temporarily get a const T& from a simdjson_result<T> without throwing an exception
62 SIMDJSON_TRY( result.error() );
63 padded_string_view json = result.value_unsafe();
64 return iterate(json);
65}
66
67simdjson_warn_unused simdjson_inline simdjson_result<document> parser::iterate(const simdjson_result<padded_string> &result) & noexcept {
68 // We don't presently have a way to temporarily get a const T& from a simdjson_result<T> without throwing an exception
69 SIMDJSON_TRY( result.error() );
70 const padded_string &json = result.value_unsafe();
71 return iterate(json);
72}
73
74simdjson_warn_unused simdjson_inline simdjson_result<json_iterator> parser::iterate_raw(padded_string_view json) & noexcept {
75 if (json.padding() < SIMDJSON_PADDING) { return INSUFFICIENT_PADDING; }
76
77 // Allocate if needed
78 if (capacity() < json.length()) {
79 SIMDJSON_TRY( allocate(json.length(), max_depth()) );
80 }
81
82 // Run stage 1.
83 SIMDJSON_TRY( implementation->stage1(reinterpret_cast<const uint8_t *>(json.data()), json.length(), stage1_mode::regular) );
84 return json_iterator(reinterpret_cast<const uint8_t *>(json.data()), this);
85}
86
87inline simdjson_result<document_stream> parser::iterate_many(const uint8_t *buf, size_t len, size_t batch_size) noexcept {
88 if(batch_size < MINIMAL_BATCH_SIZE) { batch_size = MINIMAL_BATCH_SIZE; }
89 return document_stream(*this, buf, len, batch_size);
90}
91inline simdjson_result<document_stream> parser::iterate_many(const char *buf, size_t len, size_t batch_size) noexcept {
92 return iterate_many(buf: reinterpret_cast<const uint8_t *>(buf), len, batch_size);
93}
94inline simdjson_result<document_stream> parser::iterate_many(const std::string &s, size_t batch_size) noexcept {
95 return iterate_many(buf: s.data(), len: s.length(), batch_size);
96}
97inline simdjson_result<document_stream> parser::iterate_many(const padded_string &s, size_t batch_size) noexcept {
98 return iterate_many(buf: s.data(), len: s.length(), batch_size);
99}
100
101simdjson_inline size_t parser::capacity() const noexcept {
102 return _capacity;
103}
104simdjson_inline size_t parser::max_capacity() const noexcept {
105 return _max_capacity;
106}
107simdjson_inline size_t parser::max_depth() const noexcept {
108 return _max_depth;
109}
110
111simdjson_inline void parser::set_max_capacity(size_t max_capacity) noexcept {
112 if(max_capacity < dom::MINIMAL_DOCUMENT_CAPACITY) {
113 _max_capacity = max_capacity;
114 } else {
115 _max_capacity = dom::MINIMAL_DOCUMENT_CAPACITY;
116 }
117}
118
119simdjson_inline simdjson_warn_unused simdjson_result<std::string_view> parser::unescape(raw_json_string in, uint8_t *&dst, bool allow_replacement) const noexcept {
120 uint8_t *end = implementation->parse_string(src: in.buf, dst, allow_replacement);
121 if (!end) { return STRING_ERROR; }
122 std::string_view result(reinterpret_cast<const char *>(dst), end-dst);
123 dst = end;
124 return result;
125}
126
127simdjson_inline simdjson_warn_unused simdjson_result<std::string_view> parser::unescape_wobbly(raw_json_string in, uint8_t *&dst) const noexcept {
128 uint8_t *end = implementation->parse_wobbly_string(src: in.buf, dst);
129 if (!end) { return STRING_ERROR; }
130 std::string_view result(reinterpret_cast<const char *>(dst), end-dst);
131 dst = end;
132 return result;
133}
134
135} // namespace ondemand
136} // namespace SIMDJSON_IMPLEMENTATION
137} // namespace simdjson
138
139namespace simdjson {
140
141simdjson_inline simdjson_result<SIMDJSON_IMPLEMENTATION::ondemand::parser>::simdjson_result(SIMDJSON_IMPLEMENTATION::ondemand::parser &&value) noexcept
142 : implementation_simdjson_result_base<SIMDJSON_IMPLEMENTATION::ondemand::parser>(std::forward<SIMDJSON_IMPLEMENTATION::ondemand::parser>(t&: value)) {}
143simdjson_inline simdjson_result<SIMDJSON_IMPLEMENTATION::ondemand::parser>::simdjson_result(error_code error) noexcept
144 : implementation_simdjson_result_base<SIMDJSON_IMPLEMENTATION::ondemand::parser>(error) {}
145
146} // namespace simdjson
147