sq_detailed_metrics 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (69) hide show
  1. checksums.yaml +7 -0
  2. data/extconf.rb +26 -0
  3. data/include/half.hpp +4575 -0
  4. data/include/msgpack.h +24 -0
  5. data/include/msgpack/fbuffer.h +42 -0
  6. data/include/msgpack/gcc_atomic.h +25 -0
  7. data/include/msgpack/object.h +118 -0
  8. data/include/msgpack/pack.h +174 -0
  9. data/include/msgpack/pack_define.h +18 -0
  10. data/include/msgpack/pack_template.h +952 -0
  11. data/include/msgpack/sbuffer.h +115 -0
  12. data/include/msgpack/sysdep.h +221 -0
  13. data/include/msgpack/timestamp.h +58 -0
  14. data/include/msgpack/unpack.h +281 -0
  15. data/include/msgpack/unpack_define.h +89 -0
  16. data/include/msgpack/unpack_template.h +471 -0
  17. data/include/msgpack/util.h +15 -0
  18. data/include/msgpack/version.h +38 -0
  19. data/include/msgpack/version_master.h +3 -0
  20. data/include/msgpack/vrefbuffer.h +144 -0
  21. data/include/msgpack/zbuffer.h +205 -0
  22. data/include/msgpack/zone.h +163 -0
  23. data/include/rapidjson/allocators.h +271 -0
  24. data/include/rapidjson/document.h +2575 -0
  25. data/include/rapidjson/encodedstream.h +299 -0
  26. data/include/rapidjson/encodings.h +716 -0
  27. data/include/rapidjson/error/en.h +74 -0
  28. data/include/rapidjson/error/error.h +155 -0
  29. data/include/rapidjson/filereadstream.h +99 -0
  30. data/include/rapidjson/filewritestream.h +104 -0
  31. data/include/rapidjson/fwd.h +151 -0
  32. data/include/rapidjson/internal/biginteger.h +290 -0
  33. data/include/rapidjson/internal/diyfp.h +258 -0
  34. data/include/rapidjson/internal/dtoa.h +245 -0
  35. data/include/rapidjson/internal/ieee754.h +78 -0
  36. data/include/rapidjson/internal/itoa.h +304 -0
  37. data/include/rapidjson/internal/meta.h +181 -0
  38. data/include/rapidjson/internal/pow10.h +55 -0
  39. data/include/rapidjson/internal/regex.h +701 -0
  40. data/include/rapidjson/internal/stack.h +230 -0
  41. data/include/rapidjson/internal/strfunc.h +55 -0
  42. data/include/rapidjson/internal/strtod.h +269 -0
  43. data/include/rapidjson/internal/swap.h +46 -0
  44. data/include/rapidjson/istreamwrapper.h +115 -0
  45. data/include/rapidjson/memorybuffer.h +70 -0
  46. data/include/rapidjson/memorystream.h +71 -0
  47. data/include/rapidjson/msinttypes/inttypes.h +316 -0
  48. data/include/rapidjson/msinttypes/stdint.h +300 -0
  49. data/include/rapidjson/ostreamwrapper.h +81 -0
  50. data/include/rapidjson/pointer.h +1358 -0
  51. data/include/rapidjson/prettywriter.h +255 -0
  52. data/include/rapidjson/rapidjson.h +615 -0
  53. data/include/rapidjson/reader.h +1879 -0
  54. data/include/rapidjson/schema.h +2006 -0
  55. data/include/rapidjson/stream.h +179 -0
  56. data/include/rapidjson/stringbuffer.h +117 -0
  57. data/include/rapidjson/writer.h +610 -0
  58. data/include/xxhash.h +328 -0
  59. data/json_conv.cpp +284 -0
  60. data/json_conv.hpp +17 -0
  61. data/metrics.cpp +239 -0
  62. data/metrics.hpp +84 -0
  63. data/msgpack/objectc.c +482 -0
  64. data/msgpack/unpack.c +703 -0
  65. data/msgpack/version.c +22 -0
  66. data/msgpack/vrefbuffer.c +250 -0
  67. data/msgpack/zone.c +222 -0
  68. data/sq_detailed_metrics.cpp +248 -0
  69. metadata +199 -0
@@ -0,0 +1,328 @@
1
+ /*
2
+ xxHash - Extremely Fast Hash algorithm
3
+ Header File
4
+ Copyright (C) 2012-2016, Yann Collet.
5
+
6
+ BSD 2-Clause License (http://www.opensource.org/licenses/bsd-license.php)
7
+
8
+ Redistribution and use in source and binary forms, with or without
9
+ modification, are permitted provided that the following conditions are
10
+ met:
11
+
12
+ * Redistributions of source code must retain the above copyright
13
+ notice, this list of conditions and the following disclaimer.
14
+ * Redistributions in binary form must reproduce the above
15
+ copyright notice, this list of conditions and the following disclaimer
16
+ in the documentation and/or other materials provided with the
17
+ distribution.
18
+
19
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20
+ "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21
+ LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22
+ A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23
+ OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24
+ SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27
+ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28
+ (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
+
31
+ You can contact the author at :
32
+ - xxHash source repository : https://github.com/Cyan4973/xxHash
33
+ */
34
+
35
+ /* Notice extracted from xxHash homepage :
36
+
37
+ xxHash is an extremely fast Hash algorithm, running at RAM speed limits.
38
+ It also successfully passes all tests from the SMHasher suite.
39
+
40
+ Comparison (single thread, Windows Seven 32 bits, using SMHasher on a Core 2 Duo @3GHz)
41
+
42
+ Name Speed Q.Score Author
43
+ xxHash 5.4 GB/s 10
44
+ CrapWow 3.2 GB/s 2 Andrew
45
+ MumurHash 3a 2.7 GB/s 10 Austin Appleby
46
+ SpookyHash 2.0 GB/s 10 Bob Jenkins
47
+ SBox 1.4 GB/s 9 Bret Mulvey
48
+ Lookup3 1.2 GB/s 9 Bob Jenkins
49
+ SuperFastHash 1.2 GB/s 1 Paul Hsieh
50
+ CityHash64 1.05 GB/s 10 Pike & Alakuijala
51
+ FNV 0.55 GB/s 5 Fowler, Noll, Vo
52
+ CRC32 0.43 GB/s 9
53
+ MD5-32 0.33 GB/s 10 Ronald L. Rivest
54
+ SHA1-32 0.28 GB/s 10
55
+
56
+ Q.Score is a measure of quality of the hash function.
57
+ It depends on successfully passing SMHasher test set.
58
+ 10 is a perfect score.
59
+
60
+ A 64-bit version, named XXH64, is available since r35.
61
+ It offers much better speed, but for 64-bit applications only.
62
+ Name Speed on 64 bits Speed on 32 bits
63
+ XXH64 13.8 GB/s 1.9 GB/s
64
+ XXH32 6.8 GB/s 6.0 GB/s
65
+ */
66
+
67
+ #ifndef XXHASH_H_5627135585666179
68
+ #define XXHASH_H_5627135585666179 1
69
+
70
+ #if defined (__cplusplus)
71
+ extern "C" {
72
+ #endif
73
+
74
+
75
+ /* ****************************
76
+ * Definitions
77
+ ******************************/
78
+ #include <stddef.h> /* size_t */
79
+ typedef enum { XXH_OK=0, XXH_ERROR } XXH_errorcode;
80
+
81
+
82
+ /* ****************************
83
+ * API modifier
84
+ ******************************/
85
+ /** XXH_INLINE_ALL (and XXH_PRIVATE_API)
86
+ * This is useful to include xxhash functions in `static` mode
87
+ * in order to inline them, and remove their symbol from the public list.
88
+ * Inlining can offer dramatic performance improvement on small keys.
89
+ * Methodology :
90
+ * #define XXH_INLINE_ALL
91
+ * #include "xxhash.h"
92
+ * `xxhash.c` is automatically included.
93
+ * It's not useful to compile and link it as a separate module.
94
+ */
95
+ #if defined(XXH_INLINE_ALL) || defined(XXH_PRIVATE_API)
96
+ # ifndef XXH_STATIC_LINKING_ONLY
97
+ # define XXH_STATIC_LINKING_ONLY
98
+ # endif
99
+ # if defined(__GNUC__)
100
+ # define XXH_PUBLIC_API static __inline __attribute__((unused))
101
+ # elif defined (__cplusplus) || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */)
102
+ # define XXH_PUBLIC_API static inline
103
+ # elif defined(_MSC_VER)
104
+ # define XXH_PUBLIC_API static __inline
105
+ # else
106
+ /* this version may generate warnings for unused static functions */
107
+ # define XXH_PUBLIC_API static
108
+ # endif
109
+ #else
110
+ # define XXH_PUBLIC_API /* do nothing */
111
+ #endif /* XXH_INLINE_ALL || XXH_PRIVATE_API */
112
+
113
+ /*! XXH_NAMESPACE, aka Namespace Emulation :
114
+ *
115
+ * If you want to include _and expose_ xxHash functions from within your own library,
116
+ * but also want to avoid symbol collisions with other libraries which may also include xxHash,
117
+ *
118
+ * you can use XXH_NAMESPACE, to automatically prefix any public symbol from xxhash library
119
+ * with the value of XXH_NAMESPACE (therefore, avoid NULL and numeric values).
120
+ *
121
+ * Note that no change is required within the calling program as long as it includes `xxhash.h` :
122
+ * regular symbol name will be automatically translated by this header.
123
+ */
124
+ #ifdef XXH_NAMESPACE
125
+ # define XXH_CAT(A,B) A##B
126
+ # define XXH_NAME2(A,B) XXH_CAT(A,B)
127
+ # define XXH_versionNumber XXH_NAME2(XXH_NAMESPACE, XXH_versionNumber)
128
+ # define XXH32 XXH_NAME2(XXH_NAMESPACE, XXH32)
129
+ # define XXH32_createState XXH_NAME2(XXH_NAMESPACE, XXH32_createState)
130
+ # define XXH32_freeState XXH_NAME2(XXH_NAMESPACE, XXH32_freeState)
131
+ # define XXH32_reset XXH_NAME2(XXH_NAMESPACE, XXH32_reset)
132
+ # define XXH32_update XXH_NAME2(XXH_NAMESPACE, XXH32_update)
133
+ # define XXH32_digest XXH_NAME2(XXH_NAMESPACE, XXH32_digest)
134
+ # define XXH32_copyState XXH_NAME2(XXH_NAMESPACE, XXH32_copyState)
135
+ # define XXH32_canonicalFromHash XXH_NAME2(XXH_NAMESPACE, XXH32_canonicalFromHash)
136
+ # define XXH32_hashFromCanonical XXH_NAME2(XXH_NAMESPACE, XXH32_hashFromCanonical)
137
+ # define XXH64 XXH_NAME2(XXH_NAMESPACE, XXH64)
138
+ # define XXH64_createState XXH_NAME2(XXH_NAMESPACE, XXH64_createState)
139
+ # define XXH64_freeState XXH_NAME2(XXH_NAMESPACE, XXH64_freeState)
140
+ # define XXH64_reset XXH_NAME2(XXH_NAMESPACE, XXH64_reset)
141
+ # define XXH64_update XXH_NAME2(XXH_NAMESPACE, XXH64_update)
142
+ # define XXH64_digest XXH_NAME2(XXH_NAMESPACE, XXH64_digest)
143
+ # define XXH64_copyState XXH_NAME2(XXH_NAMESPACE, XXH64_copyState)
144
+ # define XXH64_canonicalFromHash XXH_NAME2(XXH_NAMESPACE, XXH64_canonicalFromHash)
145
+ # define XXH64_hashFromCanonical XXH_NAME2(XXH_NAMESPACE, XXH64_hashFromCanonical)
146
+ #endif
147
+
148
+
149
+ /* *************************************
150
+ * Version
151
+ ***************************************/
152
+ #define XXH_VERSION_MAJOR 0
153
+ #define XXH_VERSION_MINOR 6
154
+ #define XXH_VERSION_RELEASE 5
155
+ #define XXH_VERSION_NUMBER (XXH_VERSION_MAJOR *100*100 + XXH_VERSION_MINOR *100 + XXH_VERSION_RELEASE)
156
+ XXH_PUBLIC_API unsigned XXH_versionNumber (void);
157
+
158
+
159
+ /*-**********************************************************************
160
+ * 32-bit hash
161
+ ************************************************************************/
162
+ typedef unsigned int XXH32_hash_t;
163
+
164
+ /*! XXH32() :
165
+ Calculate the 32-bit hash of sequence "length" bytes stored at memory address "input".
166
+ The memory between input & input+length must be valid (allocated and read-accessible).
167
+ "seed" can be used to alter the result predictably.
168
+ Speed on Core 2 Duo @ 3 GHz (single thread, SMHasher benchmark) : 5.4 GB/s */
169
+ XXH_PUBLIC_API XXH32_hash_t XXH32 (const void* input, size_t length, unsigned int seed);
170
+
171
+ /*====== Streaming ======*/
172
+ typedef struct XXH32_state_s XXH32_state_t; /* incomplete type */
173
+ XXH_PUBLIC_API XXH32_state_t* XXH32_createState(void);
174
+ XXH_PUBLIC_API XXH_errorcode XXH32_freeState(XXH32_state_t* statePtr);
175
+ XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t* dst_state, const XXH32_state_t* src_state);
176
+
177
+ XXH_PUBLIC_API XXH_errorcode XXH32_reset (XXH32_state_t* statePtr, unsigned int seed);
178
+ XXH_PUBLIC_API XXH_errorcode XXH32_update (XXH32_state_t* statePtr, const void* input, size_t length);
179
+ XXH_PUBLIC_API XXH32_hash_t XXH32_digest (const XXH32_state_t* statePtr);
180
+
181
+ /*
182
+ * Streaming functions generate the xxHash of an input provided in multiple segments.
183
+ * Note that, for small input, they are slower than single-call functions, due to state management.
184
+ * For small inputs, prefer `XXH32()` and `XXH64()`, which are better optimized.
185
+ *
186
+ * XXH state must first be allocated, using XXH*_createState() .
187
+ *
188
+ * Start a new hash by initializing state with a seed, using XXH*_reset().
189
+ *
190
+ * Then, feed the hash state by calling XXH*_update() as many times as necessary.
191
+ * The function returns an error code, with 0 meaning OK, and any other value meaning there is an error.
192
+ *
193
+ * Finally, a hash value can be produced anytime, by using XXH*_digest().
194
+ * This function returns the nn-bits hash as an int or long long.
195
+ *
196
+ * It's still possible to continue inserting input into the hash state after a digest,
197
+ * and generate some new hashes later on, by calling again XXH*_digest().
198
+ *
199
+ * When done, free XXH state space if it was allocated dynamically.
200
+ */
201
+
202
+ /*====== Canonical representation ======*/
203
+
204
+ typedef struct { unsigned char digest[4]; } XXH32_canonical_t;
205
+ XXH_PUBLIC_API void XXH32_canonicalFromHash(XXH32_canonical_t* dst, XXH32_hash_t hash);
206
+ XXH_PUBLIC_API XXH32_hash_t XXH32_hashFromCanonical(const XXH32_canonical_t* src);
207
+
208
+ /* Default result type for XXH functions are primitive unsigned 32 and 64 bits.
209
+ * The canonical representation uses human-readable write convention, aka big-endian (large digits first).
210
+ * These functions allow transformation of hash result into and from its canonical format.
211
+ * This way, hash values can be written into a file / memory, and remain comparable on different systems and programs.
212
+ */
213
+
214
+
215
+ #ifndef XXH_NO_LONG_LONG
216
+ /*-**********************************************************************
217
+ * 64-bit hash
218
+ ************************************************************************/
219
+ typedef unsigned long long XXH64_hash_t;
220
+
221
+ /*! XXH64() :
222
+ Calculate the 64-bit hash of sequence of length "len" stored at memory address "input".
223
+ "seed" can be used to alter the result predictably.
224
+ This function runs faster on 64-bit systems, but slower on 32-bit systems (see benchmark).
225
+ */
226
+ XXH_PUBLIC_API XXH64_hash_t XXH64 (const void* input, size_t length, unsigned long long seed);
227
+
228
+ /*====== Streaming ======*/
229
+ typedef struct XXH64_state_s XXH64_state_t; /* incomplete type */
230
+ XXH_PUBLIC_API XXH64_state_t* XXH64_createState(void);
231
+ XXH_PUBLIC_API XXH_errorcode XXH64_freeState(XXH64_state_t* statePtr);
232
+ XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t* dst_state, const XXH64_state_t* src_state);
233
+
234
+ XXH_PUBLIC_API XXH_errorcode XXH64_reset (XXH64_state_t* statePtr, unsigned long long seed);
235
+ XXH_PUBLIC_API XXH_errorcode XXH64_update (XXH64_state_t* statePtr, const void* input, size_t length);
236
+ XXH_PUBLIC_API XXH64_hash_t XXH64_digest (const XXH64_state_t* statePtr);
237
+
238
+ /*====== Canonical representation ======*/
239
+ typedef struct { unsigned char digest[8]; } XXH64_canonical_t;
240
+ XXH_PUBLIC_API void XXH64_canonicalFromHash(XXH64_canonical_t* dst, XXH64_hash_t hash);
241
+ XXH_PUBLIC_API XXH64_hash_t XXH64_hashFromCanonical(const XXH64_canonical_t* src);
242
+ #endif /* XXH_NO_LONG_LONG */
243
+
244
+
245
+
246
+ #ifdef XXH_STATIC_LINKING_ONLY
247
+
248
+ /* ================================================================================================
249
+ This section contains declarations which are not guaranteed to remain stable.
250
+ They may change in future versions, becoming incompatible with a different version of the library.
251
+ These declarations should only be used with static linking.
252
+ Never use them in association with dynamic linking !
253
+ =================================================================================================== */
254
+
255
+ /* These definitions are only present to allow
256
+ * static allocation of XXH state, on stack or in a struct for example.
257
+ * Never **ever** use members directly. */
258
+
259
+ #if !defined (__VMS) \
260
+ && (defined (__cplusplus) \
261
+ || (defined (__STDC_VERSION__) && (__STDC_VERSION__ >= 199901L) /* C99 */) )
262
+ # include <stdint.h>
263
+
264
+ struct XXH32_state_s {
265
+ uint32_t total_len_32;
266
+ uint32_t large_len;
267
+ uint32_t v1;
268
+ uint32_t v2;
269
+ uint32_t v3;
270
+ uint32_t v4;
271
+ uint32_t mem32[4];
272
+ uint32_t memsize;
273
+ uint32_t reserved; /* never read nor write, might be removed in a future version */
274
+ }; /* typedef'd to XXH32_state_t */
275
+
276
+ struct XXH64_state_s {
277
+ uint64_t total_len;
278
+ uint64_t v1;
279
+ uint64_t v2;
280
+ uint64_t v3;
281
+ uint64_t v4;
282
+ uint64_t mem64[4];
283
+ uint32_t memsize;
284
+ uint32_t reserved[2]; /* never read nor write, might be removed in a future version */
285
+ }; /* typedef'd to XXH64_state_t */
286
+
287
+ # else
288
+
289
+ struct XXH32_state_s {
290
+ unsigned total_len_32;
291
+ unsigned large_len;
292
+ unsigned v1;
293
+ unsigned v2;
294
+ unsigned v3;
295
+ unsigned v4;
296
+ unsigned mem32[4];
297
+ unsigned memsize;
298
+ unsigned reserved; /* never read nor write, might be removed in a future version */
299
+ }; /* typedef'd to XXH32_state_t */
300
+
301
+ # ifndef XXH_NO_LONG_LONG /* remove 64-bit support */
302
+ struct XXH64_state_s {
303
+ unsigned long long total_len;
304
+ unsigned long long v1;
305
+ unsigned long long v2;
306
+ unsigned long long v3;
307
+ unsigned long long v4;
308
+ unsigned long long mem64[4];
309
+ unsigned memsize;
310
+ unsigned reserved[2]; /* never read nor write, might be removed in a future version */
311
+ }; /* typedef'd to XXH64_state_t */
312
+ # endif
313
+
314
+ # endif
315
+
316
+
317
+ #if defined(XXH_INLINE_ALL) || defined(XXH_PRIVATE_API)
318
+ # include "xxhash.c" /* include xxhash function bodies as `static`, for inlining */
319
+ #endif
320
+
321
+ #endif /* XXH_STATIC_LINKING_ONLY */
322
+
323
+
324
+ #if defined (__cplusplus)
325
+ }
326
+ #endif
327
+
328
+ #endif /* XXHASH_H_5627135585666179 */
@@ -0,0 +1,284 @@
1
+ #include "json_conv.hpp"
2
+ #include <msgpack.h>
3
+ #include <map>
4
+ #include <vector>
5
+ #include <memory>
6
+ #include <sstream>
7
+ #include <iomanip>
8
+ #define RAPIDJSON_NO_SIZETYPEDEFINE 1
9
+ namespace rapidjson { typedef std::size_t SizeType; }
10
+ #include <rapidjson/writer.h>
11
+ #include <rapidjson/ostreamwrapper.h>
12
+ #include "metrics.hpp"
13
+
14
+ namespace sq_detailed_metrics
15
+ {
16
+ using namespace half_float::literal;
17
+
18
+ class UnexpectedData : public std::exception {
19
+ std::string what_v;
20
+
21
+ public:
22
+ UnexpectedData(std::string what_) : what_v(what_) {}
23
+ virtual ~UnexpectedData() = default;
24
+ virtual const char *what() const noexcept;
25
+ };
26
+ const char *UnexpectedData::what() const noexcept {
27
+ return what_v.c_str();
28
+ }
29
+
30
+ struct ReadRequest {
31
+ std::string route;
32
+ index_t overtime_cb_idx;
33
+ std::vector<meas_entry_t> measurements;
34
+ };
35
+
36
+ class Unpacker {
37
+ using unpacker_ptr = std::unique_ptr<msgpack_unpacker, decltype(&msgpack_unpacker_free)>;
38
+ unpacker_ptr unp{msgpack_unpacker_new(1024), msgpack_unpacker_free};
39
+
40
+ msgpack_unpacked unpacked{};
41
+
42
+ const msgpack_object_array& root_array() {
43
+ if (unpacked.data.type != MSGPACK_OBJECT_ARRAY) {
44
+ throw UnexpectedData("Expected array at root, got type " +
45
+ std::to_string(unpacked.data.type));
46
+ }
47
+ msgpack_object_array& obj = unpacked.data.via.array;
48
+ if (obj.size != 2) {
49
+ throw UnexpectedData("Expected root array to have size 2");
50
+ }
51
+
52
+ return obj;
53
+ }
54
+
55
+ public:
56
+
57
+ static void print_hex(const char *s, size_t size)
58
+ {
59
+ for (size_t i = 0; i < size; i++)
60
+ std::cout << std::hex << std::setfill('0') << std::setw(2) <<
61
+ std::uppercase << (int)(unsigned char)s[i];
62
+ }
63
+
64
+ Unpacker(const char *src, size_t size) {
65
+ print_hex(src, size);
66
+ bool result = msgpack_unpacker_reserve_buffer(unp.get(), size);
67
+ if (!result) {
68
+ throw std::bad_alloc{};
69
+ }
70
+
71
+ std::memcpy(msgpack_unpacker_buffer(unp.get()), src, size);
72
+ msgpack_unpacker_buffer_consumed(unp.get(), size);
73
+ }
74
+
75
+ ~Unpacker() {
76
+ msgpack_unpacked_destroy(&unpacked);
77
+ }
78
+
79
+ bool unpack() {
80
+ if (unpacked.zone) {
81
+ return false;
82
+ }
83
+
84
+ msgpack_unpacked_init(&unpacked);
85
+ msgpack_unpack_return ret = msgpack_unpacker_next(unp.get(), &unpacked);
86
+
87
+ return ret == MSGPACK_UNPACK_SUCCESS;
88
+ }
89
+
90
+ std::map<index_t, std::string> meas_types() {
91
+ std::map<index_t, std::string> ret;
92
+
93
+ auto& route_array = root_array();
94
+
95
+ if (route_array.ptr[0].type != MSGPACK_OBJECT_MAP) {
96
+ throw UnexpectedData("Expected first element of root array "
97
+ "to be a map");
98
+ }
99
+ msgpack_object_map& map = route_array.ptr[0].via.map;
100
+
101
+ for (uint32_t i = 0; i < map.size; i++) {
102
+ auto& key = map.ptr[i].key;
103
+ auto& val = map.ptr[i].val;
104
+
105
+ if (key.type != MSGPACK_OBJECT_POSITIVE_INTEGER) {
106
+ throw UnexpectedData("Expected keys of map first element "
107
+ "of root array to be positive numbers");
108
+ }
109
+ if (val.type != MSGPACK_OBJECT_STR) {
110
+ throw UnexpectedData("Expected values of map first element "
111
+ "of root array to be strings");
112
+ }
113
+
114
+ ret[static_cast<index_t>(key.via.u64)] =
115
+ std::string{val.via.str.ptr, val.via.str.size};
116
+ }
117
+
118
+ return ret;
119
+ }
120
+
121
+ std::vector<ReadRequest> requests() {
122
+ std::vector<ReadRequest> ret;
123
+
124
+ auto& route_array = root_array();
125
+
126
+ if (route_array.ptr[1].type != MSGPACK_OBJECT_ARRAY) {
127
+ throw UnexpectedData("Expected second element of root array "
128
+ "to be an array, the type is instead " +
129
+ std::to_string(route_array.ptr[1].type));
130
+ }
131
+ msgpack_object_array& reqs = route_array.ptr[1].via.array;
132
+ ret.resize(reqs.size);
133
+
134
+ for (uint32_t i = 0; i < reqs.size; i++) {
135
+ msgpack_object& obj = reqs.ptr[i];
136
+
137
+ if (obj.type != MSGPACK_OBJECT_ARRAY ||
138
+ obj.via.array.size != 3) {
139
+ std::string msg = "Expected root > #2 > #" + std::to_string(i)
140
+ + " to be an array of size 3";
141
+ throw UnexpectedData(msg);
142
+ }
143
+
144
+ msgpack_object_array& arr = obj.via.array;
145
+ to_req(ret[i], i, ret, arr.ptr[0], arr.ptr[1], arr.ptr[2]);
146
+ }
147
+
148
+ return ret;
149
+ }
150
+
151
+ static void to_req(ReadRequest& req,
152
+ uint32_t req_num,
153
+ const std::vector<ReadRequest>& prev_reqs,
154
+ msgpack_object& route,
155
+ msgpack_object& overtime_cb_object,
156
+ msgpack_object& measurements) {
157
+ if (overtime_cb_object.type != MSGPACK_OBJECT_POSITIVE_INTEGER) {
158
+ throw UnexpectedData("Request " + std::to_string(req_num) +
159
+ " has no positive number on #2");
160
+ }
161
+ if (measurements.type != MSGPACK_OBJECT_BIN) {
162
+ throw UnexpectedData("Request " + std::to_string(req_num) +
163
+ " has no binary data on #3");
164
+ }
165
+
166
+ if (route.type == MSGPACK_OBJECT_STR) {
167
+ req.route = {route.via.str.ptr, route.via.str.size};
168
+ } else if (route.type == MSGPACK_OBJECT_POSITIVE_INTEGER) {
169
+ req_index_t i = static_cast<req_index_t>(route.via.u64);
170
+ if (i >= prev_reqs.size()) {
171
+ throw UnexpectedData("Request " + std::to_string(req_num) +
172
+ " points to req " + std::to_string(req_num) +
173
+ ", which is ahead");
174
+ }
175
+ const ReadRequest& prev_r = prev_reqs[i];
176
+ req.route = prev_r.route;
177
+ } else {
178
+ throw UnexpectedData("Request " + std::to_string(req_num) +
179
+ " has no string or positive integer on #1");
180
+ }
181
+
182
+ req.overtime_cb_idx = static_cast<index_t>(overtime_cb_object.via.u64);
183
+
184
+ msgpack_object_bin& bin = measurements.via.bin;
185
+ if (bin.size % 3 != 0) {
186
+ throw UnexpectedData("Request " + std::to_string(req_num) +
187
+ " has binary data on #3 with size "
188
+ "not a multiple of 3");
189
+ }
190
+ uint32_t num_meas = bin.size / 3;
191
+ req.measurements.resize(num_meas);
192
+ for (uint32_t i = 0; i < num_meas; i++) {
193
+ const unsigned char *p = reinterpret_cast<const unsigned char*>(
194
+ &bin.ptr[i *3]);
195
+ half_float::half half;
196
+ std::memcpy(&half, p + 1, sizeof(half));
197
+ req.measurements[i] = {
198
+ *reinterpret_cast<const index_t*>(p),
199
+ half
200
+ };
201
+ }
202
+ }
203
+ };
204
+
205
+ class WriterConv : public rapidjson::Writer<rapidjson::OStreamWrapper> {
206
+ public:
207
+ WriterConv(rapidjson::OStreamWrapper &wrapper) :
208
+ rapidjson::Writer<rapidjson::OStreamWrapper>(wrapper) {
209
+ }
210
+
211
+ bool StdString(const std::string& str) {
212
+ return String(&str[0], str.size());
213
+ }
214
+
215
+ bool HalfFloat(const half_float::half half) {
216
+ std::stringstream ss;
217
+ ss << std::setprecision(4) << float{half};
218
+ auto str = ss.str();
219
+ Prefix(rapidjson::kNumberType);
220
+ return EndValue(WriteRawValue(&str[0], str.size()));
221
+ }
222
+ };
223
+
224
+ void JsonConv::parse(const char *src, size_t size) {
225
+ std::map<index_t, std::string> meas_types;
226
+ std::vector<ReadRequest> requests;
227
+
228
+ {
229
+ Unpacker unpacker{src, size};
230
+ if (!unpacker.unpack()) {
231
+ throw UnexpectedData{"Error unpacking"};
232
+ }
233
+ meas_types = unpacker.meas_types();
234
+ meas_types[max_index_t] = "other";
235
+ requests = unpacker.requests();
236
+ }
237
+
238
+ rapidjson::OStreamWrapper osw{os};
239
+ WriterConv writer(osw);
240
+
241
+ writer.StartArray();
242
+ for (ReadRequest& r: requests) {
243
+ writer.StartObject();
244
+ if (r.route.size() > 0) {
245
+ writer.Key("route");
246
+ writer.StdString(r.route);
247
+ }
248
+ if (r.overtime_cb_idx != undef_index_t) {
249
+ writer.Key("overtime_cb");
250
+ writer.StdString(meas_types[r.overtime_cb_idx]);
251
+ }
252
+ writer.Key("measurements");
253
+ writer.StartArray();
254
+ for (const meas_entry_t& e: r.measurements) {
255
+ writer.StartArray();
256
+
257
+ writer.StdString(meas_types[e.first]);
258
+
259
+ half_float::half f = e.second * 8.0_h;
260
+
261
+ bool conditions_passed = false;
262
+ // doesn't work on older compilers
263
+ // if (std::signbit(f)) { // negative
264
+ if ((*reinterpret_cast<uint16_t*>(&f) & 0x8000U) == 0x8000U) {
265
+ conditions_passed = true;
266
+ f *= -1.0_h;
267
+ }
268
+ if (!std::isinf(f)) {
269
+ writer.HalfFloat(f);
270
+ } else {
271
+ static float max_val =
272
+ std::numeric_limits<half_float::half>::max() * 8.0f;
273
+ writer.Double(static_cast<double>(max_val));
274
+ }
275
+ writer.Bool(conditions_passed);
276
+
277
+ writer.EndArray();
278
+ }
279
+ writer.EndArray();
280
+ writer.EndObject();
281
+ }
282
+ writer.EndArray();
283
+ }
284
+ }