File: simdjson_dom.h

package info (click to toggle)
simdjson 4.2.4-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 27,936 kB
  • sloc: cpp: 171,612; ansic: 19,122; sh: 1,126; python: 842; makefile: 47; ruby: 25; javascript: 13
file content (138 lines) | stat: -rw-r--r-- 3,847 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
#pragma once
#if SIMDJSON_EXCEPTIONS


#include "json2msgpack.h"

namespace json2msgpack {

using namespace simdjson;

struct simdjsondom2msgpack {
  /**
   * @brief Converts the provided JSON into msgpack.
   *
   * @param json JSON input
   * @param buf temporary buffer (must be large enough, with simdjson::SIMDJSON_PADDING bytes
   * of padding)
   * @return std::string_view msgpack output, writing to the temporary buffer
   */
  inline std::string_view to_msgpack(const simdjson::padded_string &json,
                                     uint8_t *buf);

private:
  simdjson_really_inline void write_double(const double d) noexcept;
  simdjson_really_inline void write_string(const std::string_view v) noexcept;
  simdjson_really_inline void write_byte(const uint8_t b) noexcept;
  simdjson_really_inline void write_uint32(const uint32_t w) noexcept;
  simdjson_really_inline uint8_t *skip_uint32() noexcept;
  simdjson_really_inline void write_uint32_at(const uint32_t w,
                                              uint8_t *p) noexcept;

  inline void recursive_processor(simdjson::dom::element element);

  dom::parser parser;
  uint8_t *buff{};
};

std::string_view
simdjsondom2msgpack::to_msgpack(const simdjson::padded_string &json,
                             uint8_t *buf) {
  buff = buf;

  recursive_processor(parser.parse(json));
  return std::string_view(reinterpret_cast<char *>(buf), size_t(buff - buf));
}
void simdjsondom2msgpack::write_string(const std::string_view v) noexcept {
  write_byte(0xdb);
  write_uint32(uint32_t(v.size()));
  ::memcpy(buff, v.data(), v.size());
  buff += v.size();
}
void simdjsondom2msgpack::write_double(const double d) noexcept {
  *buff++ = 0xcb;
  ::memcpy(buff, &d, sizeof(d));
  buff += sizeof(d);
}

void simdjsondom2msgpack::write_byte(const uint8_t b) noexcept {
  *buff = b;
  buff++;
}

void simdjsondom2msgpack::write_uint32(const uint32_t w) noexcept {
  ::memcpy(buff, &w, sizeof(w));
  buff += sizeof(w);
}

uint8_t *simdjsondom2msgpack::skip_uint32() noexcept {
  uint8_t *ret = buff;
  buff += sizeof(uint32_t);
  return ret;
}

void simdjsondom2msgpack::write_uint32_at(const uint32_t w, uint8_t *p) noexcept {
  ::memcpy(p, &w, sizeof(w));
}


void simdjsondom2msgpack::recursive_processor(simdjson::dom::element element) {
  switch (element.type()) {
    case dom::element_type::ARRAY: {
      uint32_t counter = 0;
      write_byte(0xdd);
      uint8_t *location = skip_uint32();
      for (auto child : dom::array(element)) {
        counter++;
        recursive_processor(child);
      }
      write_uint32_at(counter, location);}
      break;
    case dom::element_type::OBJECT:{
      uint32_t counter = 0;
      write_byte(0xdf);
      uint8_t *location = skip_uint32();
      for (dom::key_value_pair field : dom::object(element)) {
        counter++;
        write_string(field.key);
        recursive_processor(field.value);
      }
      write_uint32_at(counter, location);
      }
      break;
    case dom::element_type::INT64:
    case dom::element_type::UINT64:
    case dom::element_type::DOUBLE:
      write_double( double(element));
      break;
    case dom::element_type::STRING:
      write_string(std::string_view(element));
      break;
    case dom::element_type::BOOL:
      write_byte(0xc2 + bool(element));
      break;
    case dom::element_type::NULL_VALUE:
      write_byte(0xc0);
      break;
    default:
      break;
  }
}

struct simdjson_dom {
  using StringType = std::string_view;

  simdjsondom2msgpack parser{};

  bool run(simdjson::padded_string &json, char *buffer,
           std::string_view &result) {
    result = parser.to_msgpack(json, reinterpret_cast<uint8_t *>(buffer));
    return true;
  }
};

BENCHMARK_TEMPLATE(json2msgpack, simdjson_dom)->UseManualTime();

} // namespace json2msgpack

#endif // SIMDJSON_EXCEPTIONS