Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright (C) 2016 Intel Corporation.
3 : : * All rights reserved.
4 : : */
5 : :
6 : : #include "spdk/json.h"
7 : :
8 : : #include "spdk_internal/utf.h"
9 : : #include "spdk/log.h"
10 : :
11 : : #define SPDK_JSON_DEBUG(...) SPDK_DEBUGLOG(json_util, __VA_ARGS__)
12 : :
13 : : size_t
14 : 273788 : spdk_json_val_len(const struct spdk_json_val *val)
15 : : {
16 [ - + ]: 273788 : if (val == NULL) {
17 : 0 : return 0;
18 : : }
19 : :
20 [ + + + + ]: 273788 : if (val->type == SPDK_JSON_VAL_ARRAY_BEGIN || val->type == SPDK_JSON_VAL_OBJECT_BEGIN) {
21 : 49745 : return val->len + 2;
22 : : }
23 : :
24 : 224043 : return 1;
25 : : }
26 : :
27 : : bool
28 : 43735887 : spdk_json_strequal(const struct spdk_json_val *val, const char *str)
29 : : {
30 : : size_t len;
31 : :
32 [ + + + + ]: 43735887 : if (val->type != SPDK_JSON_VAL_STRING && val->type != SPDK_JSON_VAL_NAME) {
33 : 6 : return false;
34 : : }
35 : :
36 [ - + ]: 43735881 : len = strlen(str);
37 [ + + ]: 43735881 : if (val->len != len) {
38 : 40971140 : return false;
39 : : }
40 : :
41 [ - + - + ]: 2764736 : return memcmp(val->start, str, len) == 0;
42 : : }
43 : :
44 : : char *
45 : 50740 : spdk_json_strdup(const struct spdk_json_val *val)
46 : : {
47 : : size_t len;
48 : : char *s;
49 : :
50 [ + + + - ]: 50740 : if (val->type != SPDK_JSON_VAL_STRING && val->type != SPDK_JSON_VAL_NAME) {
51 : 30 : return NULL;
52 : : }
53 : :
54 : 50710 : len = val->len;
55 : :
56 [ + + + + ]: 50710 : if (memchr(val->start, '\0', len)) {
57 : : /* String contains embedded NUL, so it is not a valid C string. */
58 : 12 : return NULL;
59 : : }
60 : :
61 : 50698 : s = malloc(len + 1);
62 [ - + ]: 50698 : if (s == NULL) {
63 : 0 : return s;
64 : : }
65 : :
66 [ - + - + ]: 50698 : memcpy(s, val->start, len);
67 : 50698 : s[len] = '\0';
68 : :
69 : 50698 : return s;
70 : : }
71 : :
72 : : struct spdk_json_num {
73 : : bool negative;
74 : : uint64_t significand;
75 : : int64_t exponent;
76 : : };
77 : :
78 : : static int
79 : 26056 : json_number_split(const struct spdk_json_val *val, struct spdk_json_num *num)
80 : : {
81 : : const char *iter;
82 : : size_t remaining;
83 : : uint64_t *pval;
84 : 26056 : uint64_t frac_digits = 0;
85 : 26056 : uint64_t exponent_u64 = 0;
86 : 26056 : bool exponent_negative = false;
87 : : enum {
88 : : NUM_STATE_INT,
89 : : NUM_STATE_FRAC,
90 : : NUM_STATE_EXP,
91 : : } state;
92 : :
93 [ - + ]: 26056 : memset(num, 0, sizeof(*num));
94 : :
95 [ + + ]: 26056 : if (val->type != SPDK_JSON_VAL_NUMBER) {
96 : 48 : return -EINVAL;
97 : : }
98 : :
99 : 26008 : remaining = val->len;
100 [ - + ]: 26008 : if (remaining == 0) {
101 : 0 : return -EINVAL;
102 : : }
103 : :
104 : 26008 : iter = val->start;
105 [ + + ]: 26008 : if (*iter == '-') {
106 : 127 : num->negative = true;
107 : 127 : iter++;
108 : 127 : remaining--;
109 : : }
110 : :
111 : 26008 : state = NUM_STATE_INT;
112 : 26008 : pval = &num->significand;
113 [ + + ]: 97668 : while (remaining--) {
114 : 71666 : char c = *iter++;
115 : :
116 [ + + ]: 71666 : if (c == '.') {
117 : 162 : state = NUM_STATE_FRAC;
118 [ + + + + ]: 71504 : } else if (c == 'e' || c == 'E') {
119 : 276 : state = NUM_STATE_EXP;
120 : 276 : pval = &exponent_u64;
121 [ + + ]: 71228 : } else if (c == '-') {
122 [ - + ]: 126 : assert(state == NUM_STATE_EXP);
123 : 126 : exponent_negative = true;
124 [ - + ]: 71102 : } else if (c == '+') {
125 [ # # ]: 0 : assert(state == NUM_STATE_EXP);
126 : : /* exp_negative = false; */ /* already false by default */
127 : : } else {
128 : : uint64_t new_val;
129 : :
130 [ + - + + ]: 71102 : assert(c >= '0' && c <= '9');
131 : 71102 : new_val = *pval * 10 + c - '0';
132 [ + + ]: 71102 : if (new_val < *pval) {
133 : 6 : return -ERANGE;
134 : : }
135 : :
136 [ + + ]: 71096 : if (state == NUM_STATE_FRAC) {
137 : 360 : frac_digits++;
138 : : }
139 : :
140 : 71096 : *pval = new_val;
141 : : }
142 : : }
143 : :
144 [ + + ]: 26002 : if (exponent_negative) {
145 [ - + ]: 126 : if (exponent_u64 > 9223372036854775808ULL) { /* abs(INT64_MIN) */
146 : 0 : return -ERANGE;
147 : : }
148 : 126 : num->exponent = (int64_t) - exponent_u64;
149 : : } else {
150 [ - + ]: 25876 : if (exponent_u64 > INT64_MAX) {
151 : 0 : return -ERANGE;
152 : : }
153 : 25876 : num->exponent = exponent_u64;
154 : : }
155 : 26002 : num->exponent -= frac_digits;
156 : :
157 : : /* Apply as much of the exponent as possible without overflow or truncation */
158 [ + + ]: 26002 : if (num->exponent < 0) {
159 [ + + + + : 492 : while (num->exponent && num->significand >= 10 && num->significand % 10 == 0) {
+ + ]
160 : 246 : num->significand /= 10;
161 : 246 : num->exponent++;
162 : : }
163 : : } else { /* positive exponent */
164 [ + + ]: 26164 : while (num->exponent) {
165 : 426 : uint64_t new_val = num->significand * 10;
166 : :
167 [ + + ]: 426 : if (new_val < num->significand) {
168 : 18 : break;
169 : : }
170 : :
171 : 408 : num->significand = new_val;
172 : 408 : num->exponent--;
173 : : }
174 : : }
175 : :
176 : 26002 : return 0;
177 : : }
178 : :
179 : : int
180 : 466 : spdk_json_number_to_uint8(const struct spdk_json_val *val, uint8_t *num)
181 : : {
182 : 263 : struct spdk_json_num split_num;
183 : : int rc;
184 : :
185 : 466 : rc = json_number_split(val, &split_num);
186 [ - + ]: 466 : if (rc) {
187 : 0 : return rc;
188 : : }
189 : :
190 [ + - - + : 466 : if (split_num.exponent || split_num.negative) {
- + ]
191 : 0 : return -ERANGE;
192 : : }
193 : :
194 [ - + ]: 466 : if (split_num.significand > UINT8_MAX) {
195 : 0 : return -ERANGE;
196 : : }
197 : 466 : *num = (uint8_t)split_num.significand;
198 : 466 : return 0;
199 : : }
200 : :
201 : : int
202 : 307 : spdk_json_number_to_uint16(const struct spdk_json_val *val, uint16_t *num)
203 : : {
204 : 155 : struct spdk_json_num split_num;
205 : : int rc;
206 : :
207 : 307 : rc = json_number_split(val, &split_num);
208 [ + + ]: 307 : if (rc) {
209 : 6 : return rc;
210 : : }
211 : :
212 [ + + + + : 301 : if (split_num.exponent || split_num.negative) {
+ + ]
213 : 60 : return -ERANGE;
214 : : }
215 : :
216 [ + + ]: 241 : if (split_num.significand > UINT16_MAX) {
217 : 12 : return -ERANGE;
218 : : }
219 : 229 : *num = (uint16_t)split_num.significand;
220 : 229 : return 0;
221 : : }
222 : :
223 : : int
224 : 2181 : spdk_json_number_to_int32(const struct spdk_json_val *val, int32_t *num)
225 : : {
226 : 634 : struct spdk_json_num split_num;
227 : : int rc;
228 : :
229 : 2181 : rc = json_number_split(val, &split_num);
230 [ + + ]: 2181 : if (rc) {
231 : 12 : return rc;
232 : : }
233 : :
234 [ + + ]: 2169 : if (split_num.exponent) {
235 : 54 : return -ERANGE;
236 : : }
237 : :
238 [ + + + + ]: 2115 : if (split_num.negative) {
239 [ + + ]: 65 : if (split_num.significand > 2147483648) { /* abs(INT32_MIN) */
240 : 6 : return -ERANGE;
241 : : }
242 : 59 : *num = (int32_t) - (int64_t)split_num.significand;
243 : 59 : return 0;
244 : : }
245 : :
246 : : /* positive */
247 [ + + ]: 2050 : if (split_num.significand > INT32_MAX) {
248 : 6 : return -ERANGE;
249 : : }
250 : 2044 : *num = (int32_t)split_num.significand;
251 : 2044 : return 0;
252 : : }
253 : :
254 : : int
255 : 15444 : spdk_json_number_to_uint32(const struct spdk_json_val *val, uint32_t *num)
256 : : {
257 : 6079 : struct spdk_json_num split_num;
258 : : int rc;
259 : :
260 : 15444 : rc = json_number_split(val, &split_num);
261 [ + + ]: 15444 : if (rc) {
262 : 24 : return rc;
263 : : }
264 : :
265 [ + + + + : 15420 : if (split_num.exponent || split_num.negative) {
+ + ]
266 : 38 : return -ERANGE;
267 : : }
268 : :
269 [ + + ]: 15382 : if (split_num.significand > UINT32_MAX) {
270 : 6 : return -ERANGE;
271 : : }
272 : 15376 : *num = (uint32_t)split_num.significand;
273 : 15376 : return 0;
274 : : }
275 : :
276 : : int
277 : 7658 : spdk_json_number_to_uint64(const struct spdk_json_val *val, uint64_t *num)
278 : : {
279 : 3626 : struct spdk_json_num split_num;
280 : : int rc;
281 : :
282 : 7658 : rc = json_number_split(val, &split_num);
283 [ + + ]: 7658 : if (rc) {
284 : 12 : return rc;
285 : : }
286 : :
287 [ + + + + : 7646 : if (split_num.exponent || split_num.negative) {
+ + ]
288 : 72 : return -ERANGE;
289 : : }
290 : :
291 : 7574 : *num = split_num.significand;
292 : 7574 : return 0;
293 : : }
294 : :
295 : : static int
296 : 90133 : _json_decode_object(const struct spdk_json_val *values,
297 : : const struct spdk_json_object_decoder *decoders, size_t num_decoders, void *out, bool relaxed)
298 : : {
299 : : uint32_t i;
300 : 90133 : bool invalid = false;
301 : : size_t decidx;
302 : : bool *seen;
303 : :
304 [ + - + + ]: 90133 : if (values == NULL || values->type != SPDK_JSON_VAL_OBJECT_BEGIN) {
305 : 6 : return -1;
306 : : }
307 : :
308 : 90127 : seen = calloc(sizeof(bool), num_decoders);
309 [ - + ]: 90127 : if (seen == NULL) {
310 : 0 : return -1;
311 : : }
312 : :
313 [ + + ]: 357339 : for (i = 0; i < values->len;) {
314 : 267212 : const struct spdk_json_val *name = &values[i + 1];
315 : 267212 : const struct spdk_json_val *v = &values[i + 2];
316 : 267212 : bool found = false;
317 : :
318 [ + + ]: 738489 : for (decidx = 0; decidx < num_decoders; decidx++) {
319 : 734163 : const struct spdk_json_object_decoder *dec = &decoders[decidx];
320 [ + + ]: 734163 : if (spdk_json_strequal(name, dec->name)) {
321 : 262886 : void *field = (void *)((uintptr_t)out + dec->offset);
322 : :
323 : 262886 : found = true;
324 : :
325 [ + + + + ]: 262886 : if (seen[decidx]) {
326 : : /* duplicate field name */
327 : 6 : invalid = true;
328 [ - + - + ]: 6 : SPDK_JSON_DEBUG("Duplicate key '%s'\n", dec->name);
329 : : } else {
330 : 262880 : seen[decidx] = true;
331 [ + + ]: 262880 : if (dec->decode_func(v, field)) {
332 : 8 : invalid = true;
333 [ - + - + ]: 8 : SPDK_JSON_DEBUG("Decoder failed to decode key '%s'\n", dec->name);
334 : : /* keep going to fill out any other valid keys */
335 : : }
336 : : }
337 : 262886 : break;
338 : : }
339 : : }
340 : :
341 [ + + + + ]: 267212 : if (!relaxed && !found) {
342 : 6 : invalid = true;
343 [ - + - + ]: 6 : SPDK_JSON_DEBUG("Decoder not found for key '%.*s'\n", name->len, (char *)name->start);
344 : : }
345 : :
346 : 267212 : i += 1 + spdk_json_val_len(v);
347 : : }
348 : :
349 [ + + ]: 450402 : for (decidx = 0; decidx < num_decoders; decidx++) {
350 [ + + + + : 360293 : if (!decoders[decidx].optional && !seen[decidx]) {
- + + + ]
351 : : /* required field is missing */
352 : 18 : invalid = true;
353 : 18 : break;
354 : : }
355 : : }
356 : :
357 : 90127 : free(seen);
358 [ + + ]: 90127 : return invalid ? -1 : 0;
359 : : }
360 : :
361 : : void
362 : 6 : spdk_json_free_object(const struct spdk_json_object_decoder *decoders, size_t num_decoders,
363 : : void *obj)
364 : : {
365 : 6 : struct spdk_json_val invalid_val = {
366 : : .start = "",
367 : : .len = 0,
368 : : .type = SPDK_JSON_VAL_INVALID
369 : : };
370 : : size_t decidx;
371 : :
372 [ + + ]: 30 : for (decidx = 0; decidx < num_decoders; decidx++) {
373 : 24 : const struct spdk_json_object_decoder *dec = &decoders[decidx];
374 : 24 : void *field = (void *)((uintptr_t)obj + dec->offset);
375 : :
376 : : /* decoding an invalid value will free the
377 : : * previous memory without allocating it again.
378 : : */
379 : 24 : dec->decode_func(&invalid_val, field);
380 : : }
381 : 6 : }
382 : :
383 : :
384 : : int
385 : 88745 : spdk_json_decode_object(const struct spdk_json_val *values,
386 : : const struct spdk_json_object_decoder *decoders, size_t num_decoders, void *out)
387 : : {
388 : 88745 : return _json_decode_object(values, decoders, num_decoders, out, false);
389 : : }
390 : :
391 : : int
392 : 1388 : spdk_json_decode_object_relaxed(const struct spdk_json_val *values,
393 : : const struct spdk_json_object_decoder *decoders, size_t num_decoders, void *out)
394 : : {
395 : 1388 : return _json_decode_object(values, decoders, num_decoders, out, true);
396 : : }
397 : :
398 : : int
399 : 1354 : spdk_json_decode_array(const struct spdk_json_val *values, spdk_json_decode_fn decode_func,
400 : : void *out, size_t max_size, size_t *out_size, size_t stride)
401 : : {
402 : : uint32_t i;
403 : : char *field;
404 : : char *out_end;
405 : :
406 [ + - + + ]: 1354 : if (values == NULL || values->type != SPDK_JSON_VAL_ARRAY_BEGIN) {
407 : 6 : return -1;
408 : : }
409 : :
410 : 1348 : *out_size = 0;
411 : 1348 : field = out;
412 : 1348 : out_end = field + max_size * stride;
413 [ + + ]: 4100 : for (i = 0; i < values->len;) {
414 : 2770 : const struct spdk_json_val *v = &values[i + 1];
415 : :
416 [ + + ]: 2770 : if (field == out_end) {
417 : 6 : return -1;
418 : : }
419 : :
420 [ + + ]: 2764 : if (decode_func(v, field)) {
421 : 12 : return -1;
422 : : }
423 : :
424 : 2752 : i += spdk_json_val_len(v);
425 : 2752 : field += stride;
426 : 2752 : (*out_size)++;
427 : : }
428 : :
429 : 1330 : return 0;
430 : : }
431 : :
432 : : int
433 : 7137 : spdk_json_decode_bool(const struct spdk_json_val *val, void *out)
434 : : {
435 : 7137 : bool *f = out;
436 : :
437 [ + + + + ]: 7137 : if (val->type != SPDK_JSON_VAL_TRUE && val->type != SPDK_JSON_VAL_FALSE) {
438 : 6 : return -1;
439 : : }
440 : :
441 : 7131 : *f = val->type == SPDK_JSON_VAL_TRUE;
442 : 7131 : return 0;
443 : : }
444 : :
445 : : int
446 : 466 : spdk_json_decode_uint8(const struct spdk_json_val *val, void *out)
447 : : {
448 : 466 : uint8_t *i = out;
449 : :
450 : 466 : return spdk_json_number_to_uint8(val, i);
451 : : }
452 : :
453 : : int
454 : 219 : spdk_json_decode_uint16(const struct spdk_json_val *val, void *out)
455 : : {
456 : 219 : uint16_t *i = out;
457 : :
458 : 219 : return spdk_json_number_to_uint16(val, i);
459 : : }
460 : :
461 : : int
462 : 2109 : spdk_json_decode_int32(const struct spdk_json_val *val, void *out)
463 : : {
464 : 2109 : int32_t *i = out;
465 : :
466 : 2109 : return spdk_json_number_to_int32(val, i);
467 : : }
468 : :
469 : : int
470 : 15444 : spdk_json_decode_uint32(const struct spdk_json_val *val, void *out)
471 : : {
472 : 15444 : uint32_t *i = out;
473 : :
474 : 15444 : return spdk_json_number_to_uint32(val, i);
475 : : }
476 : :
477 : : int
478 : 6609 : spdk_json_decode_uint64(const struct spdk_json_val *val, void *out)
479 : : {
480 : 6609 : uint64_t *i = out;
481 : :
482 : 6609 : return spdk_json_number_to_uint64(val, i);
483 : : }
484 : :
485 : : int
486 : 50714 : spdk_json_decode_string(const struct spdk_json_val *val, void *out)
487 : : {
488 : 50714 : char **s = out;
489 : :
490 : 50714 : free(*s);
491 : :
492 : 50714 : *s = spdk_json_strdup(val);
493 : :
494 [ + + ]: 50714 : if (*s) {
495 : 50672 : return 0;
496 : : } else {
497 : 42 : return -1;
498 : : }
499 : : }
500 : :
501 : : int
502 : 1268 : spdk_json_decode_uuid(const struct spdk_json_val *val, void *out)
503 : : {
504 : 1268 : struct spdk_uuid *uuid = out;
505 : 1268 : char *str = NULL;
506 : : int rc;
507 : :
508 : 1268 : rc = spdk_json_decode_string(val, &str);
509 [ + + ]: 1268 : if (rc != 0) {
510 : 6 : return rc;
511 : : }
512 : :
513 : 1262 : rc = spdk_uuid_parse(uuid, str);
514 : 1262 : free(str);
515 : :
516 [ + + ]: 1262 : return rc == 0 ? 0 : -1;
517 : : }
518 : :
519 : : static struct spdk_json_val *
520 : 8800 : json_first(struct spdk_json_val *object, enum spdk_json_val_type type)
521 : : {
522 : : /* 'object' must be JSON object or array. 'type' might be combination of these two. */
523 [ - + ]: 8800 : assert((type & (SPDK_JSON_VAL_ARRAY_BEGIN | SPDK_JSON_VAL_OBJECT_BEGIN)) != 0);
524 : :
525 [ - + ]: 8800 : assert(object != NULL);
526 : :
527 [ + + ]: 8800 : if ((object->type & type) == 0) {
528 : 64 : return NULL;
529 : : }
530 : :
531 : 8736 : object++;
532 [ - + ]: 8736 : if (object->len == 0) {
533 : 0 : return NULL;
534 : : }
535 : :
536 : 8736 : return object;
537 : : }
538 : :
539 : : static struct spdk_json_val *
540 : 3215 : json_value(struct spdk_json_val *key)
541 : : {
542 [ + - ]: 3215 : return key->type == SPDK_JSON_VAL_NAME ? key + 1 : NULL;
543 : : }
544 : :
545 : : int
546 : 1600 : spdk_json_find(struct spdk_json_val *object, const char *key_name, struct spdk_json_val **key,
547 : : struct spdk_json_val **val, enum spdk_json_val_type type)
548 : : {
549 : 1600 : struct spdk_json_val *_key = NULL;
550 : 1600 : struct spdk_json_val *_val = NULL;
551 : : struct spdk_json_val *it_first, *it;
552 : :
553 [ - + ]: 1600 : assert(object != NULL);
554 : :
555 : 1600 : it_first = json_first(object, SPDK_JSON_VAL_OBJECT_BEGIN);
556 [ + + ]: 1600 : if (!it_first) {
557 [ - + - + ]: 30 : SPDK_JSON_DEBUG("Not enclosed in {}\n");
558 : 30 : return -EPROTOTYPE;
559 : : }
560 : :
561 [ + + ]: 1784 : for (it = it_first;
562 [ + + ]: 2754 : it != NULL;
563 : 1603 : it = spdk_json_next(it)) {
564 [ - + ]: 1633 : if (it->type != SPDK_JSON_VAL_NAME) {
565 : 0 : continue;
566 : : }
567 : :
568 [ + + ]: 1633 : if (spdk_json_strequal(it, key_name) != true) {
569 : 69 : continue;
570 : : }
571 : :
572 [ - + ]: 1564 : if (_key) {
573 [ # # # # ]: 0 : SPDK_JSON_DEBUG("Duplicate key '%s'", key_name);
574 : 0 : return -EINVAL;
575 : : }
576 : :
577 : 1564 : _key = it;
578 : 1564 : _val = json_value(_key);
579 : :
580 [ + + + + ]: 1564 : if (type != SPDK_JSON_VAL_ANY && (_val->type & type) == 0) {
581 [ - + - + ]: 30 : SPDK_JSON_DEBUG("key '%s' type is %#x but expected one of %#x\n", key_name, _val->type, type);
582 : 30 : return -EDOM;
583 : : }
584 : : }
585 : :
586 [ + + ]: 1540 : if (key) {
587 : 30 : *key = _key;
588 : : }
589 : :
590 [ + - ]: 1540 : if (val) {
591 : 1540 : *val = _val;
592 : : }
593 : :
594 [ + + ]: 1540 : return _val ? 0 : -ENOENT;
595 : : }
596 : :
597 : : int
598 : 0 : spdk_json_find_string(struct spdk_json_val *object, const char *key_name,
599 : : struct spdk_json_val **key, struct spdk_json_val **val)
600 : : {
601 : 0 : return spdk_json_find(object, key_name, key, val, SPDK_JSON_VAL_STRING);
602 : : }
603 : :
604 : : int
605 : 1558 : spdk_json_find_array(struct spdk_json_val *object, const char *key_name,
606 : : struct spdk_json_val **key, struct spdk_json_val **val)
607 : : {
608 : 1558 : return spdk_json_find(object, key_name, key, val, SPDK_JSON_VAL_ARRAY_BEGIN);
609 : : }
610 : :
611 : : struct spdk_json_val *
612 : 12 : spdk_json_object_first(struct spdk_json_val *object)
613 : : {
614 : 12 : struct spdk_json_val *first = json_first(object, SPDK_JSON_VAL_OBJECT_BEGIN);
615 : :
616 : : /* Empty object? */
617 [ + - + - ]: 12 : return first && first->type != SPDK_JSON_VAL_OBJECT_END ? first : NULL;
618 : : }
619 : :
620 : : struct spdk_json_val *
621 : 7188 : spdk_json_array_first(struct spdk_json_val *array_begin)
622 : : {
623 : 7188 : struct spdk_json_val *first = json_first(array_begin, SPDK_JSON_VAL_ARRAY_BEGIN);
624 : :
625 : : /* Empty array? */
626 [ + + + + ]: 7188 : return first && first->type != SPDK_JSON_VAL_ARRAY_END ? first : NULL;
627 : : }
628 : :
629 : : static struct spdk_json_val *
630 : 14357 : json_skip_object_or_array(struct spdk_json_val *val)
631 : : {
632 : : unsigned lvl;
633 : : enum spdk_json_val_type end_type;
634 : : struct spdk_json_val *it;
635 : :
636 [ + + ]: 14357 : if (val->type == SPDK_JSON_VAL_OBJECT_BEGIN) {
637 : 12778 : end_type = SPDK_JSON_VAL_OBJECT_END;
638 [ + - ]: 1579 : } else if (val->type == SPDK_JSON_VAL_ARRAY_BEGIN) {
639 : 1579 : end_type = SPDK_JSON_VAL_ARRAY_END;
640 : : } else {
641 [ # # # # ]: 0 : SPDK_JSON_DEBUG("Expected JSON object (%#x) or array (%#x) but got %#x\n",
642 : : SPDK_JSON_VAL_OBJECT_BEGIN, SPDK_JSON_VAL_ARRAY_BEGIN, val->type);
643 : 0 : return NULL;
644 : : }
645 : :
646 : 14357 : lvl = 1;
647 [ + - + + ]: 402636 : for (it = val + 1; it->type != SPDK_JSON_VAL_INVALID && lvl != 0; it++) {
648 [ + + ]: 388279 : if (it->type == val->type) {
649 : 26036 : lvl++;
650 [ + + ]: 362243 : } else if (it->type == end_type) {
651 : 40393 : lvl--;
652 : : }
653 : : }
654 : :
655 : : /* if lvl != 0 we have invalid JSON object */
656 [ - + ]: 14357 : if (lvl != 0) {
657 [ # # # # ]: 0 : SPDK_JSON_DEBUG("Can't find end of object (type: %#x): lvl (%u) != 0)\n", val->type, lvl);
658 : 0 : it = NULL;
659 : : }
660 : :
661 : 14357 : return it;
662 : : }
663 : :
664 : : struct spdk_json_val *
665 : 16050 : spdk_json_next(struct spdk_json_val *it)
666 : : {
667 : : struct spdk_json_val *val, *next;
668 : :
669 [ + + + - : 16050 : switch (it->type) {
- ]
670 : 1633 : case SPDK_JSON_VAL_NAME:
671 : 1633 : val = json_value(it);
672 : 1633 : next = spdk_json_next(val);
673 : 1633 : break;
674 : :
675 : : /* We are in the middle of an array - get to next entry */
676 : 60 : case SPDK_JSON_VAL_NULL:
677 : : case SPDK_JSON_VAL_TRUE:
678 : : case SPDK_JSON_VAL_FALSE:
679 : : case SPDK_JSON_VAL_NUMBER:
680 : : case SPDK_JSON_VAL_STRING:
681 : 60 : val = it + 1;
682 : 60 : return val;
683 : :
684 : 14357 : case SPDK_JSON_VAL_ARRAY_BEGIN:
685 : : case SPDK_JSON_VAL_OBJECT_BEGIN:
686 : 14357 : next = json_skip_object_or_array(it);
687 : 14357 : break;
688 : :
689 : : /* Can't go to the next object if started from the end of array or object */
690 : 0 : case SPDK_JSON_VAL_ARRAY_END:
691 : : case SPDK_JSON_VAL_OBJECT_END:
692 : : case SPDK_JSON_VAL_INVALID:
693 : 0 : return NULL;
694 : 0 : default:
695 : 0 : assert(false);
696 : : return NULL;
697 : :
698 : : }
699 : :
700 : : /* EOF ? */
701 [ + + ]: 15990 : if (next == NULL) {
702 : 1552 : return NULL;
703 : : }
704 : :
705 [ + + ]: 14438 : switch (next->type) {
706 : 6708 : case SPDK_JSON_VAL_ARRAY_END:
707 : : case SPDK_JSON_VAL_OBJECT_END:
708 : : case SPDK_JSON_VAL_INVALID:
709 : 6708 : return NULL;
710 : 7730 : default:
711 : : /* Next value */
712 : 7730 : return next;
713 : : }
714 : : }
715 : :
716 : 3672 : SPDK_LOG_REGISTER_COMPONENT(json_util)
|