simdjson 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (132) hide show
  1. checksums.yaml +7 -0
  2. data/.clang-format +5 -0
  3. data/.gitignore +14 -0
  4. data/.gitmodules +3 -0
  5. data/.rubocop.yml +9 -0
  6. data/.travis.yml +7 -0
  7. data/Gemfile +4 -0
  8. data/LICENSE.txt +21 -0
  9. data/README.md +39 -0
  10. data/Rakefile +32 -0
  11. data/benchmark/apache_builds.json +4421 -0
  12. data/benchmark/demo.json +15 -0
  13. data/benchmark/github_events.json +1390 -0
  14. data/benchmark/run_benchmark.rb +30 -0
  15. data/ext/simdjson/extconf.rb +22 -0
  16. data/ext/simdjson/simdjson.cpp +76 -0
  17. data/ext/simdjson/simdjson.hpp +6 -0
  18. data/lib/simdjson/version.rb +3 -0
  19. data/lib/simdjson.rb +2 -0
  20. data/simdjson.gemspec +35 -0
  21. data/vendor/.gitkeep +0 -0
  22. data/vendor/simdjson/AUTHORS +3 -0
  23. data/vendor/simdjson/CMakeLists.txt +63 -0
  24. data/vendor/simdjson/CONTRIBUTORS +27 -0
  25. data/vendor/simdjson/Dockerfile +10 -0
  26. data/vendor/simdjson/LICENSE +201 -0
  27. data/vendor/simdjson/Makefile +203 -0
  28. data/vendor/simdjson/Notes.md +85 -0
  29. data/vendor/simdjson/README.md +581 -0
  30. data/vendor/simdjson/amalgamation.sh +158 -0
  31. data/vendor/simdjson/benchmark/CMakeLists.txt +8 -0
  32. data/vendor/simdjson/benchmark/benchmark.h +223 -0
  33. data/vendor/simdjson/benchmark/distinctuseridcompetition.cpp +347 -0
  34. data/vendor/simdjson/benchmark/linux/linux-perf-events.h +93 -0
  35. data/vendor/simdjson/benchmark/minifiercompetition.cpp +181 -0
  36. data/vendor/simdjson/benchmark/parse.cpp +393 -0
  37. data/vendor/simdjson/benchmark/parseandstatcompetition.cpp +305 -0
  38. data/vendor/simdjson/benchmark/parsingcompetition.cpp +298 -0
  39. data/vendor/simdjson/benchmark/statisticalmodel.cpp +208 -0
  40. data/vendor/simdjson/dependencies/jsoncppdist/json/json-forwards.h +344 -0
  41. data/vendor/simdjson/dependencies/jsoncppdist/json/json.h +2366 -0
  42. data/vendor/simdjson/dependencies/jsoncppdist/jsoncpp.cpp +5418 -0
  43. data/vendor/simdjson/doc/apache_builds.jsonparseandstat.png +0 -0
  44. data/vendor/simdjson/doc/gbps.png +0 -0
  45. data/vendor/simdjson/doc/github_events.jsonparseandstat.png +0 -0
  46. data/vendor/simdjson/doc/twitter.jsonparseandstat.png +0 -0
  47. data/vendor/simdjson/doc/update-center.jsonparseandstat.png +0 -0
  48. data/vendor/simdjson/images/halvarflake.png +0 -0
  49. data/vendor/simdjson/images/logo.png +0 -0
  50. data/vendor/simdjson/include/simdjson/common_defs.h +102 -0
  51. data/vendor/simdjson/include/simdjson/isadetection.h +152 -0
  52. data/vendor/simdjson/include/simdjson/jsoncharutils.h +301 -0
  53. data/vendor/simdjson/include/simdjson/jsonformatutils.h +202 -0
  54. data/vendor/simdjson/include/simdjson/jsonioutil.h +32 -0
  55. data/vendor/simdjson/include/simdjson/jsonminifier.h +30 -0
  56. data/vendor/simdjson/include/simdjson/jsonparser.h +250 -0
  57. data/vendor/simdjson/include/simdjson/numberparsing.h +587 -0
  58. data/vendor/simdjson/include/simdjson/padded_string.h +70 -0
  59. data/vendor/simdjson/include/simdjson/parsedjson.h +544 -0
  60. data/vendor/simdjson/include/simdjson/portability.h +172 -0
  61. data/vendor/simdjson/include/simdjson/simdjson.h +44 -0
  62. data/vendor/simdjson/include/simdjson/simdjson_version.h +13 -0
  63. data/vendor/simdjson/include/simdjson/simdprune_tables.h +35074 -0
  64. data/vendor/simdjson/include/simdjson/simdutf8check_arm64.h +180 -0
  65. data/vendor/simdjson/include/simdjson/simdutf8check_haswell.h +198 -0
  66. data/vendor/simdjson/include/simdjson/simdutf8check_westmere.h +169 -0
  67. data/vendor/simdjson/include/simdjson/stage1_find_marks.h +121 -0
  68. data/vendor/simdjson/include/simdjson/stage1_find_marks_arm64.h +210 -0
  69. data/vendor/simdjson/include/simdjson/stage1_find_marks_flatten.h +93 -0
  70. data/vendor/simdjson/include/simdjson/stage1_find_marks_flatten_haswell.h +95 -0
  71. data/vendor/simdjson/include/simdjson/stage1_find_marks_haswell.h +210 -0
  72. data/vendor/simdjson/include/simdjson/stage1_find_marks_macros.h +239 -0
  73. data/vendor/simdjson/include/simdjson/stage1_find_marks_westmere.h +194 -0
  74. data/vendor/simdjson/include/simdjson/stage2_build_tape.h +85 -0
  75. data/vendor/simdjson/include/simdjson/stringparsing.h +105 -0
  76. data/vendor/simdjson/include/simdjson/stringparsing_arm64.h +56 -0
  77. data/vendor/simdjson/include/simdjson/stringparsing_haswell.h +43 -0
  78. data/vendor/simdjson/include/simdjson/stringparsing_macros.h +88 -0
  79. data/vendor/simdjson/include/simdjson/stringparsing_westmere.h +41 -0
  80. data/vendor/simdjson/jsonexamples/small/jsoniter_scala/README.md +4 -0
  81. data/vendor/simdjson/scripts/dumpsimplestats.sh +11 -0
  82. data/vendor/simdjson/scripts/issue150.sh +14 -0
  83. data/vendor/simdjson/scripts/javascript/README.md +3 -0
  84. data/vendor/simdjson/scripts/javascript/generatelargejson.js +19 -0
  85. data/vendor/simdjson/scripts/minifier.sh +11 -0
  86. data/vendor/simdjson/scripts/parseandstat.sh +24 -0
  87. data/vendor/simdjson/scripts/parser.sh +11 -0
  88. data/vendor/simdjson/scripts/parsingcompdata.sh +26 -0
  89. data/vendor/simdjson/scripts/plotparse.sh +98 -0
  90. data/vendor/simdjson/scripts/selectparser.sh +11 -0
  91. data/vendor/simdjson/scripts/setupfortesting/disablehyperthreading.sh +15 -0
  92. data/vendor/simdjson/scripts/setupfortesting/powerpolicy.sh +32 -0
  93. data/vendor/simdjson/scripts/setupfortesting/setupfortesting.sh +6 -0
  94. data/vendor/simdjson/scripts/setupfortesting/turboboost.sh +51 -0
  95. data/vendor/simdjson/scripts/testjson2json.sh +99 -0
  96. data/vendor/simdjson/scripts/transitions/Makefile +10 -0
  97. data/vendor/simdjson/scripts/transitions/generatetransitions.cpp +20 -0
  98. data/vendor/simdjson/singleheader/README.md +1 -0
  99. data/vendor/simdjson/singleheader/amalgamation_demo.cpp +20 -0
  100. data/vendor/simdjson/singleheader/simdjson.cpp +1652 -0
  101. data/vendor/simdjson/singleheader/simdjson.h +39692 -0
  102. data/vendor/simdjson/src/CMakeLists.txt +67 -0
  103. data/vendor/simdjson/src/jsonioutil.cpp +35 -0
  104. data/vendor/simdjson/src/jsonminifier.cpp +285 -0
  105. data/vendor/simdjson/src/jsonparser.cpp +91 -0
  106. data/vendor/simdjson/src/parsedjson.cpp +323 -0
  107. data/vendor/simdjson/src/parsedjsoniterator.cpp +272 -0
  108. data/vendor/simdjson/src/simdjson.cpp +30 -0
  109. data/vendor/simdjson/src/stage1_find_marks.cpp +41 -0
  110. data/vendor/simdjson/src/stage2_build_tape.cpp +567 -0
  111. data/vendor/simdjson/style/clang-format-check.sh +25 -0
  112. data/vendor/simdjson/style/clang-format.sh +25 -0
  113. data/vendor/simdjson/style/run-clang-format.py +326 -0
  114. data/vendor/simdjson/tape.md +134 -0
  115. data/vendor/simdjson/tests/CMakeLists.txt +25 -0
  116. data/vendor/simdjson/tests/allparserscheckfile.cpp +192 -0
  117. data/vendor/simdjson/tests/basictests.cpp +75 -0
  118. data/vendor/simdjson/tests/jsoncheck.cpp +136 -0
  119. data/vendor/simdjson/tests/numberparsingcheck.cpp +224 -0
  120. data/vendor/simdjson/tests/pointercheck.cpp +38 -0
  121. data/vendor/simdjson/tests/singleheadertest.cpp +22 -0
  122. data/vendor/simdjson/tests/stringparsingcheck.cpp +408 -0
  123. data/vendor/simdjson/tools/CMakeLists.txt +3 -0
  124. data/vendor/simdjson/tools/cmake/FindCTargets.cmake +15 -0
  125. data/vendor/simdjson/tools/cmake/FindOptions.cmake +52 -0
  126. data/vendor/simdjson/tools/json2json.cpp +112 -0
  127. data/vendor/simdjson/tools/jsonpointer.cpp +93 -0
  128. data/vendor/simdjson/tools/jsonstats.cpp +143 -0
  129. data/vendor/simdjson/tools/minify.cpp +21 -0
  130. data/vendor/simdjson/tools/release.py +125 -0
  131. data/vendor/simdjson/windows/dirent_portable.h +1043 -0
  132. metadata +273 -0
@@ -0,0 +1,408 @@
1
+ #include <assert.h>
2
+ #include <climits>
3
+ #include <cstring>
4
+ #include <dirent.h>
5
+ #include <inttypes.h>
6
+ #include <iostream>
7
+ #include <math.h>
8
+ #include <stdbool.h>
9
+ #include <stdio.h>
10
+ #include <stdlib.h>
11
+
12
+ #ifndef JSON_TEST_STRINGS
13
+ #define JSON_TEST_STRINGS
14
+ #endif
15
+
16
+ #include "simdjson/common_defs.h"
17
+
18
+ char *fullpath;
19
+
20
+ size_t bad_string;
21
+ size_t good_string;
22
+ size_t empty_string;
23
+
24
+ size_t total_string_length;
25
+ bool probable_bug;
26
+ // borrowed code (sajson?)
27
+
28
+ static inline bool read_hex(const char *p, unsigned &u) {
29
+ unsigned v = 0;
30
+ int i = 4;
31
+ while (i--) {
32
+ unsigned char c = *p++;
33
+ if (c >= '0' && c <= '9') {
34
+ c -= '0';
35
+ } else if (c >= 'a' && c <= 'f') {
36
+ c = c - 'a' + 10;
37
+ } else if (c >= 'A' && c <= 'F') {
38
+ c = c - 'A' + 10;
39
+ } else {
40
+ return false;
41
+ }
42
+ v = (v << 4) + c;
43
+ }
44
+
45
+ u = v;
46
+ return true;
47
+ }
48
+
49
+ static inline void write_utf8(unsigned codepoint, char *&end) {
50
+ if (codepoint < 0x80) {
51
+ *end++ = codepoint;
52
+ } else if (codepoint < 0x800) {
53
+ *end++ = 0xC0 | (codepoint >> 6);
54
+ *end++ = 0x80 | (codepoint & 0x3F);
55
+ } else if (codepoint < 0x10000) {
56
+ *end++ = 0xE0 | (codepoint >> 12);
57
+ *end++ = 0x80 | ((codepoint >> 6) & 0x3F);
58
+ *end++ = 0x80 | (codepoint & 0x3F);
59
+ } else {
60
+ assert(codepoint < 0x200000);
61
+ *end++ = 0xF0 | (codepoint >> 18);
62
+ *end++ = 0x80 | ((codepoint >> 12) & 0x3F);
63
+ *end++ = 0x80 | ((codepoint >> 6) & 0x3F);
64
+ *end++ = 0x80 | (codepoint & 0x3F);
65
+ }
66
+ }
67
+
68
+ static bool parse_string(const char *p, char *output, char **end) {
69
+ if (*p != '"')
70
+ return false;
71
+ p++;
72
+
73
+ for (;;) {
74
+ #if (CHAR_MIN < 0) || (!defined(CHAR_MIN)) // the '!defined' is just paranoia
75
+ // in this path, char is *signed*
76
+ if ((*p >= 0 && *p < 0x20)) {
77
+ return false; // unescaped
78
+ }
79
+ #else
80
+ // we have unsigned chars
81
+ if (*p < 0x20) {
82
+ return false; // unescaped
83
+ }
84
+ #endif
85
+
86
+ switch (*p) {
87
+ case '"':
88
+ *output = '\0'; // end
89
+ *end = output;
90
+ return true;
91
+ case '\\':
92
+ ++p;
93
+
94
+ char replacement;
95
+ switch (*p) {
96
+ case '"':
97
+ replacement = '"';
98
+ goto replace;
99
+ case '\\':
100
+ replacement = '\\';
101
+ goto replace;
102
+ case '/':
103
+ replacement = '/';
104
+ goto replace;
105
+ case 'b':
106
+ replacement = '\b';
107
+ goto replace;
108
+ case 'f':
109
+ replacement = '\f';
110
+ goto replace;
111
+ case 'n':
112
+ replacement = '\n';
113
+ goto replace;
114
+ case 'r':
115
+ replacement = '\r';
116
+ goto replace;
117
+ case 't':
118
+ replacement = '\t';
119
+ goto replace;
120
+ replace:
121
+ *output++ = replacement;
122
+ ++p;
123
+ break;
124
+ case 'u': {
125
+ ++p;
126
+ unsigned u;
127
+ if (!read_hex(p, u))
128
+ return false;
129
+
130
+ p += 4;
131
+ if (u >= 0xD800 && u <= 0xDBFF) {
132
+ char p0 = p[0];
133
+ char p1 = p[1];
134
+ if (p0 != '\\' || p1 != 'u') {
135
+ return false;
136
+ }
137
+ p += 2;
138
+ unsigned v;
139
+ if (!read_hex(p, v))
140
+ return false;
141
+
142
+ p += 4;
143
+
144
+ if (v < 0xDC00 || v > 0xDFFF) {
145
+ return false;
146
+ }
147
+ u = 0x10000 + (((u - 0xD800) << 10) | (v - 0xDC00));
148
+ }
149
+ write_utf8(u, output);
150
+ break;
151
+ }
152
+ default:
153
+ return false;
154
+ }
155
+ break;
156
+
157
+ default:
158
+ // validate UTF-8
159
+ unsigned char c0 = p[0];
160
+ if (c0 < 128) {
161
+ *output++ = *p++;
162
+ } else if (c0 < 224) {
163
+ unsigned char c1 = p[1];
164
+ if (c1 < 128 || c1 >= 192) {
165
+ return false;
166
+ }
167
+ output[0] = c0;
168
+ output[1] = c1;
169
+ output += 2;
170
+ p += 2;
171
+ } else if (c0 < 240) {
172
+ unsigned char c1 = p[1];
173
+ if (c1 < 128 || c1 >= 192) {
174
+ return false;
175
+ }
176
+ unsigned char c2 = p[2];
177
+ if (c2 < 128 || c2 >= 192) {
178
+ return false;
179
+ }
180
+ output[0] = c0;
181
+ output[1] = c1;
182
+ output[2] = c2;
183
+ output += 3;
184
+ p += 3;
185
+ } else if (c0 < 248) {
186
+ unsigned char c1 = p[1];
187
+ if (c1 < 128 || c1 >= 192) {
188
+ return false;
189
+ }
190
+ unsigned char c2 = p[2];
191
+ if (c2 < 128 || c2 >= 192) {
192
+ return false;
193
+ }
194
+ unsigned char c3 = p[3];
195
+ if (c3 < 128 || c3 >= 192) {
196
+ return false;
197
+ }
198
+ output[0] = c0;
199
+ output[1] = c1;
200
+ output[2] = c2;
201
+ output[3] = c3;
202
+ output += 4;
203
+ p += 4;
204
+ } else {
205
+ return false;
206
+ }
207
+ break;
208
+ }
209
+ }
210
+ }
211
+ // end of borrowed code
212
+ char *big_buffer; // global variable
213
+
214
+ void found_bad_string(const uint8_t *buf) {
215
+ bad_string++;
216
+ char *end;
217
+ if (parse_string((const char *)buf, big_buffer, &end)) {
218
+ printf("WARNING: Sajson-like parser seems to think that the string is "
219
+ "valid %32s \n",
220
+ buf);
221
+ probable_bug = true;
222
+ }
223
+ }
224
+
225
+ void print_hex(const char *s, size_t len) {
226
+ for (size_t i = 0; i < len; i++) {
227
+ printf("%02x ", s[i] & 0xFF);
228
+ }
229
+ }
230
+
231
+ void print_cmp_hex(const char *s1, const char *s2, size_t len) {
232
+ for (size_t i = 0; i < len; i++) {
233
+ printf("%02x ", (s1[i] ^ s2[i]) & 0xFF);
234
+ }
235
+ }
236
+
237
+ void found_string(const uint8_t *buf, const uint8_t *parsed_begin,
238
+ const uint8_t *parsed_end) {
239
+ size_t this_len = parsed_end - parsed_begin;
240
+ total_string_length += this_len;
241
+ good_string++;
242
+ char *end = NULL;
243
+ if (!parse_string((const char *)buf, big_buffer, &end)) {
244
+ printf("WARNING: reference parser seems to think that the string is NOT "
245
+ "valid %32s \n",
246
+ buf);
247
+ }
248
+ if (end == big_buffer) {
249
+ // we have a zero-length string
250
+ if (parsed_begin != parsed_end) {
251
+ printf("WARNING: We have a zero-length but gap is %zu \n",
252
+ (size_t)(parsed_end - parsed_begin));
253
+ probable_bug = true;
254
+ }
255
+ empty_string++;
256
+ return;
257
+ }
258
+ size_t len = end - big_buffer;
259
+ if (len != this_len) {
260
+ printf("WARNING: lengths on parsed strings disagree %zu %zu \n", this_len,
261
+ len);
262
+ printf("\nour parsed string : '%*s'\n\n", (int)this_len,
263
+ (const char *)parsed_begin);
264
+ print_hex((const char *)parsed_begin, this_len);
265
+ printf("\n");
266
+
267
+ printf("reference parsing :'%*s'\n\n", (int)len, big_buffer);
268
+ print_hex((const char *)big_buffer, len);
269
+ printf("\n");
270
+
271
+ probable_bug = true;
272
+ }
273
+ if (memcmp(big_buffer, parsed_begin, this_len) != 0) {
274
+ printf("WARNING: parsed strings disagree \n");
275
+ printf("Lengths %zu %zu \n", this_len, len);
276
+
277
+ printf("\nour parsed string : '%*s'\n", (int)this_len,
278
+ (const char *)parsed_begin);
279
+ print_hex((const char *)parsed_begin, this_len);
280
+ printf("\n");
281
+
282
+ printf("reference parsing :'%*s'\n", (int)len, big_buffer);
283
+ print_hex((const char *)big_buffer, len);
284
+ printf("\n");
285
+
286
+ print_cmp_hex((const char *)parsed_begin, big_buffer, this_len);
287
+
288
+ probable_bug = true;
289
+ }
290
+ }
291
+
292
+ #include "simdjson/jsonparser.h"
293
+ #include "src/stage2_build_tape.cpp"
294
+
295
+ /**
296
+ * Does the file filename ends with the given extension.
297
+ */
298
+ static bool has_extension(const char *filename, const char *extension) {
299
+ const char *ext = strrchr(filename, '.');
300
+ return (ext && !strcmp(ext, extension));
301
+ }
302
+
303
+ bool starts_with(const char *pre, const char *str) {
304
+ size_t lenpre = strlen(pre), lenstr = strlen(str);
305
+ return lenstr < lenpre ? false : strncmp(pre, str, lenpre) == 0;
306
+ }
307
+
308
+ bool validate(const char *dirname) {
309
+ size_t total_strings = 0;
310
+ probable_bug = false;
311
+ const char *extension = ".json";
312
+ size_t dirlen = strlen(dirname);
313
+ struct dirent **entry_list;
314
+ int c = scandir(dirname, &entry_list, 0, alphasort);
315
+ if (c < 0) {
316
+ printf("error accessing %s \n", dirname);
317
+ return false;
318
+ }
319
+ if (c == 0) {
320
+ printf("nothing in dir %s \n", dirname);
321
+ return false;
322
+ }
323
+ bool needsep = (strlen(dirname) > 1) && (dirname[strlen(dirname) - 1] != '/');
324
+ for (int i = 0; i < c; i++) {
325
+ const char *name = entry_list[i]->d_name;
326
+ if (has_extension(name, extension)) {
327
+ size_t filelen = strlen(name);
328
+ fullpath = (char *)malloc(dirlen + filelen + 1 + 1);
329
+ strcpy(fullpath, dirname);
330
+ if (needsep) {
331
+ fullpath[dirlen] = '/';
332
+ strcpy(fullpath + dirlen + 1, name);
333
+ } else {
334
+ strcpy(fullpath + dirlen, name);
335
+ }
336
+ simdjson::padded_string p;
337
+ try {
338
+ simdjson::get_corpus(fullpath).swap(p);
339
+ } catch (const std::exception &e) {
340
+ std::cout << "Could not load the file " << fullpath << std::endl;
341
+ return EXIT_FAILURE;
342
+ }
343
+ simdjson::ParsedJson pj;
344
+ bool allocok = pj.allocate_capacity(p.size(), 1024);
345
+ if (!allocok) {
346
+ std::cerr << "can't allocate memory" << std::endl;
347
+ return false;
348
+ }
349
+ big_buffer = (char *)malloc(p.size());
350
+ if (big_buffer == NULL) {
351
+ std::cerr << "can't allocate memory" << std::endl;
352
+ return false;
353
+ }
354
+ bad_string = 0;
355
+ good_string = 0;
356
+ total_string_length = 0;
357
+ empty_string = 0;
358
+ bool isok = json_parse(p, pj);
359
+ free(big_buffer);
360
+ if (good_string > 0) {
361
+ printf("File %40s %s --- bad strings: %10zu \tgood strings: %10zu\t "
362
+ "empty strings: %10zu "
363
+ "\taverage string length: %.1f \n",
364
+ name, isok ? " is valid " : " is not valid ", bad_string,
365
+ good_string, empty_string,
366
+ (double)total_string_length / good_string);
367
+ } else if (bad_string > 0) {
368
+ printf("File %40s %s --- bad strings: %10zu \n", name,
369
+ isok ? " is valid " : " is not valid ", bad_string);
370
+ }
371
+ total_strings += bad_string + good_string;
372
+ free(fullpath);
373
+ }
374
+ }
375
+ printf("%zu strings checked.\n", total_strings);
376
+ if (probable_bug) {
377
+ fprintf(stderr, "STRING PARSING FAILS?\n");
378
+ } else {
379
+ printf("All ok.\n");
380
+ }
381
+ for (int i = 0; i < c; ++i)
382
+ free(entry_list[i]);
383
+ free(entry_list);
384
+ return probable_bug == false;
385
+ }
386
+
387
+ int main(int argc, char *argv[]) {
388
+ if (argc != 2) {
389
+ std::cerr << "Usage: " << argv[0] << " <directorywithjsonfiles>"
390
+ << std::endl;
391
+ #if defined(SIMDJSON_TEST_DATA_DIR) && defined(SIMDJSON_BENCHMARK_DATA_DIR)
392
+ std::cout << "We are going to assume you mean to use the '"
393
+ << SIMDJSON_TEST_DATA_DIR << "' and '"
394
+ << SIMDJSON_BENCHMARK_DATA_DIR << "'directories." << std::endl;
395
+ return validate(SIMDJSON_TEST_DATA_DIR) &&
396
+ validate(SIMDJSON_BENCHMARK_DATA_DIR)
397
+ ? EXIT_SUCCESS
398
+ : EXIT_FAILURE;
399
+ #else
400
+ std::cout << "We are going to assume you mean to use the 'jsonchecker' and "
401
+ "'jsonexamples' directories."
402
+ << std::endl;
403
+ return validate("jsonchecker/") && validate("jsonexamples/") ? EXIT_SUCCESS
404
+ : EXIT_FAILURE;
405
+ #endif
406
+ }
407
+ return validate(argv[1]) ? EXIT_SUCCESS : EXIT_FAILURE;
408
+ }
@@ -0,0 +1,3 @@
1
+ add_cpp_tool(json2json)
2
+ add_cpp_tool(jsonstats)
3
+ add_cpp_tool(minify)
@@ -0,0 +1,15 @@
1
+ function(add_cpp_test TEST_NAME)
2
+ add_executable(${TEST_NAME} ${TEST_NAME}.cpp)
3
+ target_link_libraries(${TEST_NAME} ${SIMDJSON_LIB_NAME})
4
+ add_test(${TEST_NAME} ${TEST_NAME})
5
+ endfunction(add_cpp_test)
6
+
7
+ function(add_cpp_benchmark BENCH_NAME)
8
+ add_executable(${BENCH_NAME} ${BENCH_NAME}.cpp)
9
+ target_link_libraries(${BENCH_NAME} ${SIMDJSON_LIB_NAME})
10
+ endfunction(add_cpp_benchmark)
11
+
12
+ function(add_cpp_tool TOOL_NAME)
13
+ add_executable(${TOOL_NAME} ${TOOL_NAME}.cpp)
14
+ target_link_libraries(${TOOL_NAME} ${SIMDJSON_LIB_NAME})
15
+ endfunction(add_cpp_tool)
@@ -0,0 +1,52 @@
1
+ macro(append var string)
2
+ set(${var} "${${var}} ${string}")
3
+ endmacro(append)
4
+
5
+ set(SANITIZE_FLAGS "")
6
+ if(SIMDJSON_SANITIZE)
7
+ set(SIMDJSON_SANITIZE_FLAGS "-fsanitize=address -fno-omit-frame-pointer -fsanitize=undefined -fno-sanitize-recover=all")
8
+ if (CMAKE_COMPILER_IS_GNUCC)
9
+ # Ubuntu bug for GCC 5.0+ (safe for all versions)
10
+ append(CMAKE_EXE_LINKER_FLAGS "-fuse-ld=gold")
11
+ append(CMAKE_SHARED_LINKER_FLAGS "-fuse-ld=gold")
12
+ endif()
13
+ endif()
14
+
15
+
16
+ if(SIMDJSON_DISABLE_AVX)
17
+ if(NOT MSVC)
18
+ set (OPT_FLAGS "${OPT_FLAGS} -mno-avx -mno-bmi -mno-pclmul -msse4.2")
19
+ else()
20
+ set (OPT_FLAGS "${OPT_FLAGS}")
21
+ endif()
22
+ else()
23
+ # some compilers like clang do not automagically define __AVX2__ and __BMI2__ even when the hardware supports it
24
+ if(NOT MSVC)
25
+ #set (OPT_FLAGS "${OPT_FLAGS} -mpclmul")
26
+ else()
27
+ #set (OPT_FLAGS "${OPT_FLAGS} /arch:AVX2")
28
+ endif()
29
+ endif()
30
+
31
+ if(NOT MSVC)
32
+ set(CXXSTD_FLAGS "-std=c++17 -fPIC")
33
+ endif()
34
+
35
+ set(WARNING_FLAGS "-Wall")
36
+ if(NOT MSVC)
37
+ set(WARNING_FLAGS "${WARNING_FLAGS} -Wextra -Wsign-compare -Wshadow -Wwrite-strings -Wpointer-arith -Winit-self")
38
+ set(CMAKE_C_FLAGS_DEBUG "-ggdb")
39
+ set(CMAKE_C_FLAGS_RELEASE "-O3")
40
+ endif()
41
+
42
+ set(CMAKE_C_FLAGS "${STD_FLAGS} ${OPT_FLAGS} ${INCLUDE_FLAGS} ${WARNING_FLAGS} ${SIMDJSON_SANITIZE_FLAGS} ")
43
+
44
+ if(NOT MSVC)
45
+ set(CMAKE_CXX_FLAGS_DEBUG "-ggdb")
46
+ set(CMAKE_CXX_FLAGS_RELEASE "-O3")
47
+ endif()
48
+ set(CMAKE_CXX_FLAGS "${CXXSTD_FLAGS} ${OPT_FLAGS} ${INCLUDE_FLAGS} ${WARNING_FLAGS} ${SIMDJSON_SANITIZE_FLAGS} ")
49
+
50
+ if(MSVC)
51
+ add_definitions( "${OPT_FLAGS} /W3 /D_CRT_SECURE_NO_WARNINGS /wd4005 /wd4996 /wd4267 /wd4244 /wd4113 /nologo")
52
+ endif()
@@ -0,0 +1,112 @@
1
+ #include <iostream>
2
+ #ifndef _MSC_VER
3
+ #include <unistd.h>
4
+ #endif
5
+ #include "simdjson/jsonioutil.h"
6
+ #include "simdjson/jsonparser.h"
7
+
8
+ void compute_dump(simdjson::ParsedJson::Iterator &pjh) {
9
+ if (pjh.is_object()) {
10
+ std::cout << "{";
11
+ if (pjh.down()) {
12
+ pjh.print(std::cout); // must be a string
13
+ std::cout << ":";
14
+ pjh.next();
15
+ compute_dump(pjh); // let us recurse
16
+ while (pjh.next()) {
17
+ std::cout << ",";
18
+ pjh.print(std::cout);
19
+ std::cout << ":";
20
+ pjh.next();
21
+ compute_dump(pjh); // let us recurse
22
+ }
23
+ pjh.up();
24
+ }
25
+ std::cout << "}";
26
+ } else if (pjh.is_array()) {
27
+ std::cout << "[";
28
+ if (pjh.down()) {
29
+ compute_dump(pjh); // let us recurse
30
+ while (pjh.next()) {
31
+ std::cout << ",";
32
+ compute_dump(pjh); // let us recurse
33
+ }
34
+ pjh.up();
35
+ }
36
+ std::cout << "]";
37
+ } else {
38
+ pjh.print(std::cout); // just print the lone value
39
+ }
40
+ }
41
+
42
+ int main(int argc, char *argv[]) {
43
+ bool rawdump = false;
44
+ bool apidump = false;
45
+
46
+ #ifndef _MSC_VER
47
+ int c;
48
+
49
+ while ((c = getopt(argc, argv, "da")) != -1) {
50
+ switch (c) {
51
+ case 'd':
52
+ rawdump = true;
53
+ break;
54
+ case 'a':
55
+ apidump = true;
56
+ break;
57
+ default:
58
+ abort();
59
+ }
60
+ }
61
+ #else
62
+ int optind = 1;
63
+ #endif
64
+ if (optind >= argc) {
65
+ std::cerr << "Reads json in, out the result of the parsing. " << std::endl;
66
+ std::cerr << "Usage: " << argv[0] << " <jsonfile>" << std::endl;
67
+ std::cerr << "The -d flag dumps the raw content of the tape." << std::endl;
68
+
69
+ exit(1);
70
+ }
71
+ const char *filename = argv[optind];
72
+ if (optind + 1 < argc) {
73
+ std::cerr << "warning: ignoring everything after " << argv[optind + 1]
74
+ << std::endl;
75
+ }
76
+ simdjson::padded_string p;
77
+ try {
78
+ simdjson::get_corpus(filename).swap(p);
79
+ } catch (const std::exception &) { // caught by reference to base
80
+ std::cout << "Could not load the file " << filename << std::endl;
81
+ return EXIT_FAILURE;
82
+ }
83
+ simdjson::ParsedJson pj;
84
+ bool allocok = pj.allocate_capacity(p.size(), 1024);
85
+ if (!allocok) {
86
+ std::cerr << "failed to allocate memory" << std::endl;
87
+ return EXIT_FAILURE;
88
+ }
89
+ int res =
90
+ simdjson::json_parse(p, pj); // do the parsing, return false on error
91
+ if (res != simdjson::SUCCESS) {
92
+ std::cerr << " Parsing failed. Error is '" << simdjson::error_message(res)
93
+ << "'." << std::endl;
94
+ return EXIT_FAILURE;
95
+ }
96
+ if (apidump) {
97
+ simdjson::ParsedJson::Iterator pjh(pj);
98
+ if (!pjh.is_ok()) {
99
+ std::cerr << " Could not iterate parsed result. " << std::endl;
100
+ return EXIT_FAILURE;
101
+ }
102
+ compute_dump(pjh);
103
+ } else {
104
+ const bool is_ok =
105
+ rawdump ? pj.dump_raw_tape(std::cout) : pj.print_json(std::cout);
106
+ if (!is_ok) {
107
+ std::cerr << " Could not print out parsed result. " << std::endl;
108
+ return EXIT_FAILURE;
109
+ }
110
+ }
111
+ return EXIT_SUCCESS;
112
+ }
@@ -0,0 +1,93 @@
1
+ #include "simdjson/jsonioutil.h"
2
+ #include "simdjson/jsonparser.h"
3
+ #include <iostream>
4
+
5
+ void compute_dump(simdjson::ParsedJson::Iterator &pjh) {
6
+ if (pjh.is_object()) {
7
+ std::cout << "{";
8
+ if (pjh.down()) {
9
+ pjh.print(std::cout); // must be a string
10
+ std::cout << ":";
11
+ pjh.next();
12
+ compute_dump(pjh); // let us recurse
13
+ while (pjh.next()) {
14
+ std::cout << ",";
15
+ pjh.print(std::cout);
16
+ std::cout << ":";
17
+ pjh.next();
18
+ compute_dump(pjh); // let us recurse
19
+ }
20
+ pjh.up();
21
+ }
22
+ std::cout << "}";
23
+ } else if (pjh.is_array()) {
24
+ std::cout << "[";
25
+ if (pjh.down()) {
26
+ compute_dump(pjh); // let us recurse
27
+ while (pjh.next()) {
28
+ std::cout << ",";
29
+ compute_dump(pjh); // let us recurse
30
+ }
31
+ pjh.up();
32
+ }
33
+ std::cout << "]";
34
+ } else {
35
+ pjh.print(std::cout); // just print the lone value
36
+ }
37
+ }
38
+
39
+ int main(int argc, char *argv[]) {
40
+ if (argc < 3) {
41
+ std::cerr << "Usage: " << argv[0] << " <jsonfile> <jsonpath>" << std::endl;
42
+ std::cerr << "Follows the rfc6901 standard's syntax: "
43
+ "https://tools.ietf.org/html/rfc6901"
44
+ << std::endl;
45
+ std::cerr << " Example: " << argv[0]
46
+ << " jsonexamples/small/demo.json /Image/Width /Image/Height "
47
+ "/Image/IDs/2 "
48
+ << std::endl;
49
+ std::cerr << "Multiple <jsonpath> can be issued in the same command, but "
50
+ "at least one is needed."
51
+ << std::endl;
52
+ exit(1);
53
+ }
54
+ const char *filename = argv[1];
55
+ simdjson::padded_string p;
56
+ try {
57
+ simdjson::get_corpus(filename).swap(p);
58
+ } catch (const std::exception &e) { // caught by reference to base
59
+ std::cout << "Could not load the file " << filename << std::endl;
60
+ return EXIT_FAILURE;
61
+ }
62
+ simdjson::ParsedJson pj;
63
+ bool allocok = pj.allocate_capacity(p.size(), 1024);
64
+ if (!allocok) {
65
+ std::cerr << "failed to allocate memory" << std::endl;
66
+ return EXIT_FAILURE;
67
+ }
68
+ int res =
69
+ simdjson::json_parse(p, pj); // do the parsing, return false on error
70
+ if (res) {
71
+ std::cerr << " Parsing failed with error " << simdjson::error_message(res)
72
+ << std::endl;
73
+ return EXIT_FAILURE;
74
+ }
75
+ std::cout << "[" << std::endl;
76
+ for (int idx = 2; idx < argc; idx++) {
77
+ const char *jsonpath = argv[idx];
78
+ simdjson::ParsedJson::Iterator it(pj);
79
+ if (it.move_to(std::string(jsonpath))) {
80
+ std::cout << "{\"jsonpath\": \"" << jsonpath << "\"," << std::endl;
81
+ std::cout << "\"value\":";
82
+ compute_dump(it);
83
+ std::cout << "}" << std::endl;
84
+ } else {
85
+ std::cout << "null" << std::endl;
86
+ }
87
+ if (idx + 1 < argc) {
88
+ std::cout << "," << std::endl;
89
+ }
90
+ }
91
+ std::cout << "]" << std::endl;
92
+ return EXIT_SUCCESS;
93
+ }