Line data Source code
1 : /*
2 : * Copyright (c) 2004, 2005 Metaparadigm Pte. Ltd.
3 : * Michael Clark <michael@metaparadigm.com>
4 : * Copyright (c) 2009 Hewlett-Packard Development Company, L.P.
5 : *
6 : * This library is free software; you can redistribute it and/or modify
7 : * it under the terms of the MIT license. See COPYING for details.
8 : *
9 : */
10 :
11 : #include "cpl_port.h"
12 :
13 : #include "config.h"
14 :
15 : #include "strerror_override.h"
16 :
17 : #include <assert.h>
18 : #include <ctype.h>
19 : #ifdef HAVE_LIMITS_H
20 : #include <limits.h>
21 : #endif
22 : #include <math.h>
23 : #include <stddef.h>
24 : #include <stdio.h>
25 : #include <stdlib.h>
26 : #include <string.h>
27 :
28 : #include "arraylist.h"
29 : #include "debug.h"
30 : #include "json_inttypes.h"
31 : #include "json_object.h"
32 : #include "json_object_private.h"
33 : #include "json_util.h"
34 : #include "linkhash.h"
35 : #include "math_compat.h"
36 : #include "printbuf.h"
37 : #include "snprintf_compat.h"
38 : #include "strdup_compat.h"
39 :
40 : #include "cpl_string.h"
41 :
42 : #if SIZEOF_LONG_LONG != SIZEOF_INT64_T
43 : #error "The long long type isn't 64-bits"
44 : #endif
45 :
46 : #ifndef SSIZE_T_MAX
47 : #if SIZEOF_SSIZE_T == SIZEOF_INT
48 : #define SSIZE_T_MAX INT_MAX
49 : #elif SIZEOF_SSIZE_T == SIZEOF_LONG
50 : #define SSIZE_T_MAX LONG_MAX
51 : #elif SIZEOF_SSIZE_T == SIZEOF_LONG_LONG
52 : #define SSIZE_T_MAX LLONG_MAX
53 : #else
54 : #error Unable to determine size of ssize_t
55 : #endif
56 : #endif
57 :
58 : // Don't define this. It's not thread-safe.
59 : /* #define REFCOUNT_DEBUG 1 */
60 :
61 : const char *json_hex_chars = "0123456789abcdefABCDEF";
62 :
63 : static void json_object_generic_delete(struct json_object *jso);
64 :
65 : #if defined(_MSC_VER) && (_MSC_VER <= 1800)
66 : /* VS2013 doesn't know about "inline" */
67 : #define inline __inline
68 : #elif defined(AIX_CC)
69 : #define inline
70 : #endif
71 :
72 : /*
73 : * Helper functions to more safely cast to a particular type of json_object
74 : */
75 4957040 : static inline struct json_object_object *JC_OBJECT(struct json_object *jso)
76 : {
77 4957040 : return (void *)jso;
78 : }
79 1176970 : static inline const struct json_object_object *JC_OBJECT_C(const struct json_object *jso)
80 : {
81 1176970 : return (const void *)jso;
82 : }
83 2181080 : static inline struct json_object_array *JC_ARRAY(struct json_object *jso)
84 : {
85 2181080 : return (void *)jso;
86 : }
87 2154360 : static inline const struct json_object_array *JC_ARRAY_C(const struct json_object *jso)
88 : {
89 2154360 : return (const void *)jso;
90 : }
91 1250 : static inline struct json_object_boolean *JC_BOOL(struct json_object *jso)
92 : {
93 1250 : return (void *)jso;
94 : }
95 182 : static inline const struct json_object_boolean *JC_BOOL_C(const struct json_object *jso)
96 : {
97 182 : return (const void *)jso;
98 : }
99 2143 : static inline struct json_object_double *JC_DOUBLE(struct json_object *jso)
100 : {
101 2143 : return (void *)jso;
102 : }
103 390227 : static inline const struct json_object_double *JC_DOUBLE_C(const struct json_object *jso)
104 : {
105 390227 : return (const void *)jso;
106 : }
107 90814 : static inline struct json_object_int *JC_INT(struct json_object *jso)
108 : {
109 90814 : return (void *)jso;
110 : }
111 505216 : static inline const struct json_object_int *JC_INT_C(const struct json_object *jso)
112 : {
113 505216 : return (const void *)jso;
114 : }
115 1750560 : static inline struct json_object_string *JC_STRING(struct json_object *jso)
116 : {
117 1750560 : return (void *)jso;
118 : }
119 429709 : static inline const struct json_object_string *JC_STRING_C(const struct json_object *jso)
120 : {
121 429709 : return (const void *)jso;
122 : }
123 :
124 : #define JC_CONCAT(a, b) a##b
125 : #define JC_CONCAT3(a, b, c) a##b##c
126 :
127 : #define JSON_OBJECT_NEW(jtype) \
128 : (struct JC_CONCAT(json_object_, jtype) *)json_object_new( \
129 : JC_CONCAT(json_type_, jtype), sizeof(struct JC_CONCAT(json_object_, jtype)), \
130 : &JC_CONCAT3(json_object_, jtype, _to_json_string))
131 :
132 : static inline struct json_object *json_object_new(enum json_type o_type, size_t alloc_size,
133 : json_object_to_json_string_fn *to_json_string);
134 :
135 : static void json_object_object_delete(struct json_object *jso_base);
136 : static void json_object_string_delete(struct json_object *jso);
137 : static void json_object_array_delete(struct json_object *jso);
138 :
139 : static json_object_to_json_string_fn json_object_object_to_json_string;
140 : static json_object_to_json_string_fn json_object_boolean_to_json_string;
141 : static json_object_to_json_string_fn json_object_double_to_json_string_default;
142 : static json_object_to_json_string_fn json_object_int_to_json_string;
143 : static json_object_to_json_string_fn json_object_string_to_json_string;
144 : static json_object_to_json_string_fn json_object_array_to_json_string;
145 : static json_object_to_json_string_fn _json_object_userdata_to_json_string;
146 :
147 : #ifndef JSON_NORETURN
148 : #if defined(_MSC_VER)
149 : #define JSON_NORETURN __declspec(noreturn)
150 : #elif defined(__OS400__)
151 : #define JSON_NORETURN
152 : #else
153 : /* 'cold' attribute is for optimization, telling the computer this code
154 : * path is unlikely.
155 : */
156 : #define JSON_NORETURN __attribute__((noreturn, cold))
157 : #endif
158 : #endif
159 : /**
160 : * Abort and optionally print a message on standard error.
161 : * This should be used rather than assert() for unconditional abortion
162 : * (in particular for code paths which are never supposed to be run).
163 : * */
164 : JSON_NORETURN static void json_abort(const char *message);
165 :
166 : /* ref count debugging */
167 :
168 : #ifdef REFCOUNT_DEBUG
169 :
170 : static struct lh_table *json_object_table;
171 :
172 : static void json_object_init(void) __attribute__((constructor));
173 : static void json_object_init(void)
174 : {
175 : MC_DEBUG("json_object_init: creating object table\n");
176 : json_object_table = lh_kptr_table_new(128, NULL);
177 : }
178 :
179 : static void json_object_fini(void) __attribute__((destructor));
180 : static void json_object_fini(void)
181 : {
182 : struct lh_entry *ent;
183 : if (MC_GET_DEBUG())
184 : {
185 : if (json_object_table->count)
186 : {
187 : MC_DEBUG("json_object_fini: %d referenced objects at exit\n",
188 : json_object_table->count);
189 : lh_foreach(json_object_table, ent)
190 : {
191 : struct json_object *obj = (struct json_object *)lh_entry_v(ent);
192 : MC_DEBUG("\t%s:%p\n", json_type_to_name(obj->o_type), obj);
193 : }
194 : }
195 : }
196 : MC_DEBUG("json_object_fini: freeing object table\n");
197 : lh_table_free(json_object_table);
198 : }
199 : #endif /* REFCOUNT_DEBUG */
200 :
201 : /* helper for accessing the optimized string data component in json_object
202 : */
203 429708 : static inline char *get_string_component_mutable(struct json_object *jso)
204 : {
205 429708 : if (JC_STRING_C(jso)->len < 0)
206 : {
207 : /* Due to json_object_set_string(), we might have a pointer */
208 0 : return JC_STRING(jso)->c_string.pdata;
209 : }
210 429708 : return JC_STRING(jso)->c_string.idata;
211 : }
212 429708 : static inline const char *get_string_component(const struct json_object *jso)
213 : {
214 429708 : return get_string_component_mutable((void *)(uintptr_t)(const void *)jso);
215 : }
216 :
217 : /* string escaping */
218 :
219 172822 : static int json_escape_str(struct printbuf *pb, const char *str, size_t len, int flags)
220 : {
221 172822 : int pos = 0, start_offset = 0;
222 : unsigned char c;
223 2759390 : while (len)
224 : {
225 2586560 : --len;
226 2586560 : c = str[pos];
227 2586560 : switch (c)
228 : {
229 35510 : case '\b':
230 : case '\n':
231 : case '\r':
232 : case '\t':
233 : case '\f':
234 : case '"':
235 : case '\\':
236 : case '/':
237 35510 : if ((flags & JSON_C_TO_STRING_NOSLASHESCAPE) && c == '/')
238 : {
239 936 : pos++;
240 936 : break;
241 : }
242 :
243 34574 : if (pos - start_offset > 0)
244 33674 : printbuf_memappend(pb, str + start_offset, pos - start_offset);
245 :
246 34574 : if (c == '\b')
247 0 : printbuf_memappend(pb, "\\b", 2);
248 34574 : else if (c == '\n')
249 7088 : printbuf_memappend(pb, "\\n", 2);
250 27486 : else if (c == '\r')
251 0 : printbuf_memappend(pb, "\\r", 2);
252 27486 : else if (c == '\t')
253 0 : printbuf_memappend(pb, "\\t", 2);
254 27486 : else if (c == '\f')
255 0 : printbuf_memappend(pb, "\\f", 2);
256 27486 : else if (c == '"')
257 22785 : printbuf_memappend(pb, "\\\"", 2);
258 4701 : else if (c == '\\')
259 183 : printbuf_memappend(pb, "\\\\", 2);
260 4518 : else if (c == '/')
261 4518 : printbuf_memappend(pb, "\\/", 2);
262 :
263 34574 : start_offset = ++pos;
264 34574 : break;
265 2551050 : default:
266 2551050 : if (c < ' ')
267 : {
268 : char sbuf[7];
269 0 : if (pos - start_offset > 0)
270 0 : printbuf_memappend(pb, str + start_offset,
271 : pos - start_offset);
272 0 : snprintf(sbuf, sizeof(sbuf), "\\u00%c%c", json_hex_chars[c >> 4],
273 0 : json_hex_chars[c & 0xf]);
274 0 : printbuf_memappend_fast(pb, sbuf, (int)sizeof(sbuf) - 1);
275 0 : start_offset = ++pos;
276 : }
277 : else
278 2551050 : pos++;
279 : }
280 : }
281 172822 : if (pos - start_offset > 0)
282 172201 : printbuf_memappend(pb, str + start_offset, pos - start_offset);
283 172822 : return 0;
284 : }
285 :
286 : /* reference counting */
287 :
288 3624110 : struct json_object *json_object_get(struct json_object *jso)
289 : {
290 3624110 : if (!jso)
291 56103 : return jso;
292 :
293 : // Don't overflow the refcounter.
294 3568010 : assert(jso->_ref_count < UINT32_MAX);
295 :
296 : #if defined(HAVE_ATOMIC_BUILTINS) && defined(ENABLE_THREADING)
297 : __sync_add_and_fetch(&jso->_ref_count, 1);
298 : #else
299 3568010 : ++jso->_ref_count;
300 : #endif
301 :
302 3568010 : return jso;
303 : }
304 :
305 8941760 : int json_object_put(struct json_object *jso)
306 : {
307 8941760 : if (!jso)
308 2212370 : return 0;
309 :
310 : /* Avoid invalid free and crash explicitly instead of (silently)
311 : * segfaulting.
312 : */
313 6729380 : assert(jso->_ref_count > 0);
314 :
315 : #if defined(HAVE_ATOMIC_BUILTINS) && defined(ENABLE_THREADING)
316 : /* Note: this only allow the refcount to remain correct
317 : * when multiple threads are adjusting it. It is still an error
318 : * for a thread to decrement the refcount if it doesn't "own" it,
319 : * as that can result in the thread that loses the race to 0
320 : * operating on an already-freed object.
321 : */
322 : if (__sync_sub_and_fetch(&jso->_ref_count, 1) > 0)
323 : return 0;
324 : #else
325 6729380 : if (--jso->_ref_count > 0)
326 3568010 : return 0;
327 : #endif
328 :
329 3161380 : if (jso->_user_delete)
330 133551 : jso->_user_delete(jso, jso->_userdata);
331 3161380 : switch (jso->o_type)
332 : {
333 477170 : case json_type_object: json_object_object_delete(jso); break;
334 453098 : case json_type_array: json_object_array_delete(jso); break;
335 1273650 : case json_type_string: json_object_string_delete(jso); break;
336 957456 : default: json_object_generic_delete(jso); break;
337 : }
338 3161380 : return 1;
339 : }
340 :
341 : /* generic object construction and destruction parts */
342 :
343 3161380 : static void json_object_generic_delete(struct json_object *jso)
344 : {
345 : #ifdef REFCOUNT_DEBUG
346 : MC_DEBUG("json_object_delete_%s: %p\n", json_type_to_name(jso->o_type), jso);
347 : lh_table_delete(json_object_table, jso);
348 : #endif /* REFCOUNT_DEBUG */
349 3161380 : printbuf_free(jso->_pb);
350 3161380 : free(jso);
351 3161380 : }
352 :
353 3161380 : static inline struct json_object *json_object_new(enum json_type o_type, size_t alloc_size,
354 : json_object_to_json_string_fn *to_json_string)
355 : {
356 : struct json_object *jso;
357 :
358 3161380 : jso = (struct json_object *)malloc(alloc_size);
359 3161380 : if (!jso)
360 0 : return NULL;
361 :
362 3161380 : jso->o_type = o_type;
363 3161380 : jso->_ref_count = 1;
364 3161380 : jso->_to_json_string = to_json_string;
365 3161380 : jso->_pb = NULL;
366 3161380 : jso->_user_delete = NULL;
367 3161380 : jso->_userdata = NULL;
368 : //jso->... // Type-specific fields must be set by caller
369 :
370 : #ifdef REFCOUNT_DEBUG
371 : lh_table_insert(json_object_table, jso, jso);
372 : MC_DEBUG("json_object_new_%s: %p\n", json_type_to_name(jso->o_type), jso);
373 : #endif /* REFCOUNT_DEBUG */
374 3161380 : return jso;
375 : }
376 :
377 : /* type checking functions */
378 :
379 0 : int json_object_is_type(const struct json_object *jso, enum json_type type)
380 : {
381 0 : if (!jso)
382 0 : return (type == json_type_null);
383 0 : return (jso->o_type == type);
384 : }
385 :
386 7226030 : enum json_type json_object_get_type(const struct json_object *jso)
387 : {
388 7226030 : if (!jso)
389 1369 : return json_type_null;
390 7224660 : return jso->o_type;
391 : }
392 :
393 31031 : void *json_object_get_userdata(json_object *jso)
394 : {
395 31031 : return jso ? jso->_userdata : NULL;
396 : }
397 :
398 168084 : void json_object_set_userdata(json_object *jso, void *userdata, json_object_delete_fn *user_delete)
399 : {
400 : // Can't return failure, so abort if we can't perform the operation.
401 168084 : assert(jso != NULL);
402 :
403 : // First, clean up any previously existing user info
404 168084 : if (jso->_user_delete)
405 0 : jso->_user_delete(jso, jso->_userdata);
406 :
407 168084 : jso->_userdata = userdata;
408 168084 : jso->_user_delete = user_delete;
409 168084 : }
410 :
411 : /* set a custom conversion to string */
412 :
413 168084 : void json_object_set_serializer(json_object *jso, json_object_to_json_string_fn *to_string_func,
414 : void *userdata, json_object_delete_fn *user_delete)
415 : {
416 168084 : json_object_set_userdata(jso, userdata, user_delete);
417 :
418 168084 : if (to_string_func == NULL)
419 : {
420 : // Reset to the standard serialization function
421 0 : switch (jso->o_type)
422 : {
423 0 : case json_type_null: jso->_to_json_string = NULL; break;
424 0 : case json_type_boolean:
425 0 : jso->_to_json_string = &json_object_boolean_to_json_string;
426 0 : break;
427 0 : case json_type_double:
428 0 : jso->_to_json_string = &json_object_double_to_json_string_default;
429 0 : break;
430 0 : case json_type_int: jso->_to_json_string = &json_object_int_to_json_string; break;
431 0 : case json_type_object:
432 0 : jso->_to_json_string = &json_object_object_to_json_string;
433 0 : break;
434 0 : case json_type_array:
435 0 : jso->_to_json_string = &json_object_array_to_json_string;
436 0 : break;
437 0 : case json_type_string:
438 0 : jso->_to_json_string = &json_object_string_to_json_string;
439 0 : break;
440 : }
441 0 : return;
442 : }
443 :
444 168084 : jso->_to_json_string = to_string_func;
445 : }
446 :
447 : /* extended conversion to string */
448 :
449 41018 : const char *json_object_to_json_string_length(struct json_object *jso, int flags, size_t *length)
450 : {
451 41018 : const char *r = NULL;
452 41018 : size_t s = 0;
453 :
454 41018 : if (!jso)
455 : {
456 0 : s = 4;
457 0 : r = "null";
458 : }
459 41018 : else if ((jso->_pb) || (jso->_pb = printbuf_new()))
460 : {
461 41018 : printbuf_reset(jso->_pb);
462 :
463 41018 : if (jso->_to_json_string(jso, jso->_pb, 0, flags) >= 0)
464 : {
465 41018 : s = (size_t)jso->_pb->bpos;
466 41018 : r = jso->_pb->buf;
467 : }
468 : }
469 :
470 41018 : if (length)
471 0 : *length = s;
472 41018 : return r;
473 : }
474 :
475 41018 : const char *json_object_to_json_string_ext(struct json_object *jso, int flags)
476 : {
477 41018 : return json_object_to_json_string_length(jso, flags, NULL);
478 : }
479 :
480 : /* backwards-compatible conversion to string */
481 :
482 9214 : const char *json_object_to_json_string(struct json_object *jso)
483 : {
484 9214 : return json_object_to_json_string_ext(jso, JSON_C_TO_STRING_SPACED);
485 : }
486 :
487 364934 : static void indent(struct printbuf *pb, int level, int flags)
488 : {
489 364934 : if (flags & JSON_C_TO_STRING_PRETTY)
490 : {
491 262213 : if (flags & JSON_C_TO_STRING_PRETTY_TAB)
492 : {
493 0 : printbuf_memset(pb, -1, '\t', level);
494 : }
495 : else
496 : {
497 262213 : printbuf_memset(pb, -1, ' ', level * 2);
498 : }
499 : }
500 364934 : }
501 :
502 : /* json_object_object */
503 :
504 57359 : static int json_object_object_to_json_string(struct json_object *jso, struct printbuf *pb,
505 : int level, int flags)
506 : {
507 57359 : int had_children = 0;
508 : struct json_object_iter iter;
509 :
510 57359 : printbuf_strappend(pb, "{" /*}*/);
511 57359 : if (flags & JSON_C_TO_STRING_PRETTY)
512 17227 : printbuf_strappend(pb, "\n");
513 182984 : json_object_object_foreachC(jso, iter)
514 : {
515 125625 : if (had_children)
516 : {
517 81445 : printbuf_strappend(pb, ",");
518 81445 : if (flags & JSON_C_TO_STRING_PRETTY)
519 53068 : printbuf_strappend(pb, "\n");
520 : }
521 125625 : had_children = 1;
522 125625 : if (flags & JSON_C_TO_STRING_SPACED && !(flags & JSON_C_TO_STRING_PRETTY))
523 15362 : printbuf_strappend(pb, " ");
524 125625 : indent(pb, level + 1, flags);
525 125625 : printbuf_strappend(pb, "\"");
526 125625 : json_escape_str(pb, iter.key, strlen(iter.key), flags);
527 125625 : if (flags & JSON_C_TO_STRING_SPACED)
528 15362 : printbuf_strappend(pb, "\": ");
529 : else
530 110263 : printbuf_strappend(pb, "\":");
531 125625 : if (iter.val == NULL)
532 12694 : printbuf_strappend(pb, "null");
533 112931 : else if (iter.val->_to_json_string(iter.val, pb, level + 1, flags) < 0)
534 0 : return -1;
535 : }
536 57359 : if (flags & JSON_C_TO_STRING_PRETTY)
537 : {
538 17227 : if (had_children)
539 16438 : printbuf_strappend(pb, "\n");
540 17227 : indent(pb, level, flags);
541 : }
542 57359 : if (flags & JSON_C_TO_STRING_SPACED && !(flags & JSON_C_TO_STRING_PRETTY))
543 7984 : return printbuf_strappend(pb, /*{*/ " }");
544 : else
545 49375 : return printbuf_strappend(pb, /*{*/ "}");
546 : }
547 :
548 1489760 : static void json_object_lh_entry_free(struct lh_entry *ent)
549 : {
550 1489760 : if (!ent->k_is_constant)
551 1489760 : free(lh_entry_k(ent));
552 1489760 : json_object_put((struct json_object *)lh_entry_v(ent));
553 1489760 : }
554 :
555 477170 : static void json_object_object_delete(struct json_object *jso_base)
556 : {
557 477170 : lh_table_free(JC_OBJECT(jso_base)->c_object);
558 477170 : json_object_generic_delete(jso_base);
559 477170 : }
560 :
561 477170 : struct json_object *json_object_new_object(void)
562 : {
563 477170 : struct json_object_object *jso = JSON_OBJECT_NEW(object);
564 477170 : if (!jso)
565 0 : return NULL;
566 477170 : jso->c_object =
567 477170 : lh_kchar_table_new(JSON_OBJECT_DEF_HASH_ENTRIES, &json_object_lh_entry_free);
568 477170 : if (!jso->c_object)
569 : {
570 0 : json_object_generic_delete(&jso->base);
571 0 : errno = ENOMEM;
572 0 : return NULL;
573 : }
574 477170 : return &jso->base;
575 : }
576 :
577 188073 : struct lh_table *json_object_get_object(const struct json_object *jso)
578 : {
579 188073 : if (!jso)
580 0 : return NULL;
581 188073 : switch (jso->o_type)
582 : {
583 188067 : case json_type_object: return JC_OBJECT_C(jso)->c_object;
584 6 : default: return NULL;
585 : }
586 : }
587 :
588 1489900 : int json_object_object_add_ex(struct json_object *jso, const char *const key,
589 : struct json_object *const val, const unsigned opts)
590 : {
591 1489900 : struct json_object *existing_value = NULL;
592 : struct lh_entry *existing_entry;
593 : unsigned long hash;
594 :
595 1489900 : assert(json_object_get_type(jso) == json_type_object);
596 :
597 : // We lookup the entry and replace the value, rather than just deleting
598 : // and re-adding it, so the existing key remains valid.
599 1489900 : hash = lh_get_hash(JC_OBJECT(jso)->c_object, (const void *)key);
600 1489900 : existing_entry =
601 1489900 : (opts & JSON_C_OBJECT_ADD_KEY_IS_NEW)
602 : ? NULL
603 1489900 : : lh_table_lookup_entry_w_hash(JC_OBJECT(jso)->c_object, (const void *)key, hash);
604 :
605 : // The caller must avoid creating loops in the object tree, but do a
606 : // quick check anyway to make sure we're not creating a trivial loop.
607 1489900 : if (jso == val)
608 0 : return -1;
609 :
610 1489900 : if (!existing_entry)
611 : {
612 1489760 : const void *const k =
613 1489760 : (opts & JSON_C_OBJECT_KEY_IS_CONSTANT) ? (const void *)key : strdup(key);
614 1489760 : if (k == NULL)
615 0 : return -1;
616 1489760 : return lh_table_insert_w_hash(JC_OBJECT(jso)->c_object, k, val, hash, opts);
617 : }
618 144 : existing_value = (json_object *)lh_entry_v(existing_entry);
619 144 : if (existing_value)
620 144 : json_object_put(existing_value);
621 144 : existing_entry->v = val;
622 144 : return 0;
623 : }
624 :
625 1489900 : int json_object_object_add(struct json_object *jso, const char *key, struct json_object *val)
626 : {
627 1489900 : return json_object_object_add_ex(jso, key, val, 0);
628 : }
629 :
630 3 : int json_object_object_length(const struct json_object *jso)
631 : {
632 3 : assert(json_object_get_type(jso) == json_type_object);
633 3 : return lh_table_length(JC_OBJECT_C(jso)->c_object);
634 : }
635 :
636 1315 : size_t json_c_object_sizeof(void)
637 : {
638 1315 : return sizeof(struct json_object);
639 : }
640 :
641 0 : struct json_object *json_object_object_get(const struct json_object *jso, const char *key)
642 : {
643 0 : struct json_object *result = NULL;
644 0 : json_object_object_get_ex(jso, key, &result);
645 0 : return result;
646 : }
647 :
648 990033 : json_bool json_object_object_get_ex(const struct json_object *jso, const char *key,
649 : struct json_object **value)
650 : {
651 990033 : if (value != NULL)
652 990033 : *value = NULL;
653 :
654 990033 : if (NULL == jso)
655 742 : return 0;
656 :
657 989291 : switch (jso->o_type)
658 : {
659 988899 : case json_type_object:
660 988899 : return lh_table_lookup_ex(JC_OBJECT_C(jso)->c_object, (const void *)key,
661 : (void **)value);
662 392 : default:
663 392 : if (value != NULL)
664 392 : *value = NULL;
665 392 : return 0;
666 : }
667 : }
668 :
669 10319 : void json_object_object_del(struct json_object *jso, const char *key)
670 : {
671 10319 : assert(json_object_get_type(jso) == json_type_object);
672 10319 : lh_table_delete(JC_OBJECT(jso)->c_object, key);
673 10319 : }
674 :
675 : /* json_object_boolean */
676 :
677 1250 : static int json_object_boolean_to_json_string(struct json_object *jso, struct printbuf *pb,
678 : int level, int flags)
679 : {
680 : (void)level;
681 : (void)flags;
682 1250 : if (JC_BOOL(jso)->c_boolean)
683 1009 : return printbuf_strappend(pb, "true");
684 241 : return printbuf_strappend(pb, "false");
685 : }
686 :
687 38244 : struct json_object *json_object_new_boolean(json_bool b)
688 : {
689 38244 : struct json_object_boolean *jso = JSON_OBJECT_NEW(boolean);
690 38244 : if (!jso)
691 0 : return NULL;
692 38244 : jso->c_boolean = b;
693 38244 : return &jso->base;
694 : }
695 :
696 83 : json_bool json_object_get_boolean(const struct json_object *jso)
697 : {
698 83 : if (!jso)
699 3 : return 0;
700 80 : switch (jso->o_type)
701 : {
702 79 : case json_type_boolean: return JC_BOOL_C(jso)->c_boolean;
703 0 : case json_type_int:
704 0 : switch (JC_INT_C(jso)->cint_type)
705 : {
706 0 : case json_object_int_type_int64: return (JC_INT_C(jso)->cint.c_int64 != 0);
707 0 : case json_object_int_type_uint64: return (JC_INT_C(jso)->cint.c_uint64 != 0);
708 0 : default: json_abort("invalid cint_type");
709 : }
710 0 : case json_type_double: return (JC_DOUBLE_C(jso)->c_double != 0);
711 1 : case json_type_string: return (JC_STRING_C(jso)->len != 0);
712 0 : default: return 0;
713 : }
714 : }
715 :
716 0 : int json_object_set_boolean(struct json_object *jso, json_bool new_value)
717 : {
718 0 : if (!jso || jso->o_type != json_type_boolean)
719 0 : return 0;
720 0 : JC_BOOL(jso)->c_boolean = new_value;
721 0 : return 1;
722 : }
723 :
724 : /* json_object_int */
725 :
726 44636 : static int json_object_int_to_json_string(struct json_object *jso, struct printbuf *pb, int level,
727 : int flags)
728 : {
729 : (void)level;
730 : (void)flags;
731 : /* room for 19 digits, the sign char, and a null term */
732 : char sbuf[21];
733 44636 : if (JC_INT(jso)->cint_type == json_object_int_type_int64)
734 43804 : snprintf(sbuf, sizeof(sbuf), "%" PRId64, JC_INT(jso)->cint.c_int64);
735 : else
736 832 : snprintf(sbuf, sizeof(sbuf), "%" PRIu64, JC_INT(jso)->cint.c_uint64);
737 44636 : return printbuf_memappend(pb, sbuf, (int)strlen(sbuf));
738 : }
739 :
740 16534 : struct json_object *json_object_new_int(int32_t i)
741 : {
742 16534 : return json_object_new_int64(i);
743 : }
744 :
745 25160 : int32_t json_object_get_int(const struct json_object *jso)
746 : {
747 25160 : int64_t cint64=0;
748 : double cdouble;
749 : enum json_type o_type;
750 :
751 25160 : if (!jso)
752 0 : return 0;
753 :
754 25160 : o_type = jso->o_type;
755 25160 : if (o_type == json_type_int)
756 : {
757 25085 : const struct json_object_int *jsoint = JC_INT_C(jso);
758 25085 : if (jsoint->cint_type == json_object_int_type_int64)
759 : {
760 25085 : cint64 = jsoint->cint.c_int64;
761 : }
762 : else
763 : {
764 0 : if (jsoint->cint.c_uint64 >= INT64_MAX)
765 0 : cint64 = INT64_MAX;
766 : else
767 0 : cint64 = (int64_t)jsoint->cint.c_uint64;
768 : }
769 : }
770 75 : else if (o_type == json_type_string)
771 : {
772 : /*
773 : * Parse strings into 64-bit numbers, then use the
774 : * 64-to-32-bit number handling below.
775 : */
776 1 : if (json_parse_int64(get_string_component(jso), &cint64) != 0)
777 1 : return 0; /* whoops, it didn't work. */
778 0 : o_type = json_type_int;
779 : }
780 :
781 25159 : switch (o_type)
782 : {
783 25085 : case json_type_int:
784 : /* Make sure we return the correct values for out of range numbers. */
785 25085 : if (cint64 <= INT32_MIN)
786 0 : return INT32_MIN;
787 25085 : if (cint64 >= INT32_MAX)
788 0 : return INT32_MAX;
789 25085 : return (int32_t)cint64;
790 0 : case json_type_double:
791 0 : cdouble = JC_DOUBLE_C(jso)->c_double;
792 0 : if (cdouble <= INT32_MIN)
793 0 : return INT32_MIN;
794 0 : if (cdouble >= INT32_MAX)
795 0 : return INT32_MAX;
796 0 : return (int32_t)cdouble;
797 74 : case json_type_boolean: return JC_BOOL_C(jso)->c_boolean;
798 0 : default: return 0;
799 : }
800 : }
801 :
802 0 : int json_object_set_int(struct json_object *jso, int new_value)
803 : {
804 0 : return json_object_set_int64(jso, (int64_t)new_value);
805 : }
806 :
807 376025 : struct json_object *json_object_new_int64(int64_t i)
808 : {
809 376025 : struct json_object_int *jso = JSON_OBJECT_NEW(int);
810 376025 : if (!jso)
811 0 : return NULL;
812 376025 : jso->cint.c_int64 = i;
813 376025 : jso->cint_type = json_object_int_type_int64;
814 376025 : return &jso->base;
815 : }
816 :
817 823 : struct json_object *json_object_new_uint64(uint64_t i)
818 : {
819 823 : struct json_object_int *jso = JSON_OBJECT_NEW(int);
820 823 : if (!jso)
821 0 : return NULL;
822 823 : jso->cint.c_uint64 = i;
823 823 : jso->cint_type = json_object_int_type_uint64;
824 823 : return &jso->base;
825 : }
826 :
827 48722 : int64_t json_object_get_int64(const struct json_object *jso)
828 : {
829 : int64_t cint;
830 :
831 48722 : if (!jso)
832 0 : return 0;
833 48722 : switch (jso->o_type)
834 : {
835 48689 : case json_type_int:
836 : {
837 48689 : const struct json_object_int *jsoint = JC_INT_C(jso);
838 48689 : switch (jsoint->cint_type)
839 : {
840 48684 : case json_object_int_type_int64: return jsoint->cint.c_int64;
841 5 : case json_object_int_type_uint64:
842 5 : if (jsoint->cint.c_uint64 >= INT64_MAX)
843 2 : return INT64_MAX;
844 3 : return (int64_t)jsoint->cint.c_uint64;
845 0 : default: json_abort("invalid cint_type");
846 : }
847 : }
848 1 : case json_type_double:
849 : // INT64_MAX can't be exactly represented as a double
850 : // so cast to tell the compiler it's ok to round up.
851 1 : if (JC_DOUBLE_C(jso)->c_double >= (double)INT64_MAX)
852 0 : return INT64_MAX;
853 1 : if (JC_DOUBLE_C(jso)->c_double <= INT64_MIN)
854 0 : return INT64_MIN;
855 1 : return (int64_t)JC_DOUBLE_C(jso)->c_double;
856 21 : case json_type_boolean: return JC_BOOL_C(jso)->c_boolean;
857 11 : case json_type_string:
858 11 : if (json_parse_int64(get_string_component(jso), &cint) == 0)
859 11 : return cint;
860 : /* FALLTHRU */
861 0 : default: return 0;
862 : }
863 : }
864 :
865 0 : uint64_t json_object_get_uint64(const struct json_object *jso)
866 : {
867 : uint64_t cuint;
868 :
869 0 : if (!jso)
870 0 : return 0;
871 0 : switch (jso->o_type)
872 : {
873 0 : case json_type_int:
874 : {
875 0 : const struct json_object_int *jsoint = JC_INT_C(jso);
876 0 : switch (jsoint->cint_type)
877 : {
878 0 : case json_object_int_type_int64:
879 0 : if (jsoint->cint.c_int64 < 0)
880 0 : return 0;
881 0 : return (uint64_t)jsoint->cint.c_int64;
882 0 : case json_object_int_type_uint64: return jsoint->cint.c_uint64;
883 0 : default: json_abort("invalid cint_type");
884 : }
885 : }
886 0 : case json_type_double:
887 : // UINT64_MAX can't be exactly represented as a double
888 : // so cast to tell the compiler it's ok to round up.
889 0 : if (JC_DOUBLE_C(jso)->c_double >= (double)UINT64_MAX)
890 0 : return UINT64_MAX;
891 0 : if (JC_DOUBLE_C(jso)->c_double < 0)
892 0 : return 0;
893 0 : return (uint64_t)JC_DOUBLE_C(jso)->c_double;
894 0 : case json_type_boolean: return JC_BOOL_C(jso)->c_boolean;
895 0 : case json_type_string:
896 0 : if (json_parse_uint64(get_string_component(jso), &cuint) == 0)
897 0 : return cuint;
898 : /* FALLTHRU */
899 0 : default: return 0;
900 : }
901 : }
902 :
903 0 : int json_object_set_int64(struct json_object *jso, int64_t new_value)
904 : {
905 0 : if (!jso || jso->o_type != json_type_int)
906 0 : return 0;
907 0 : JC_INT(jso)->cint.c_int64 = new_value;
908 0 : JC_INT(jso)->cint_type = json_object_int_type_int64;
909 0 : return 1;
910 : }
911 :
912 0 : int json_object_set_uint64(struct json_object *jso, uint64_t new_value)
913 : {
914 0 : if (!jso || jso->o_type != json_type_int)
915 0 : return 0;
916 0 : JC_INT(jso)->cint.c_uint64 = new_value;
917 0 : JC_INT(jso)->cint_type = json_object_int_type_uint64;
918 0 : return 1;
919 : }
920 :
921 0 : int json_object_int_inc(struct json_object *jso, int64_t val)
922 : {
923 : struct json_object_int *jsoint;
924 0 : if (!jso || jso->o_type != json_type_int)
925 0 : return 0;
926 0 : jsoint = JC_INT(jso);
927 0 : switch (jsoint->cint_type)
928 : {
929 0 : case json_object_int_type_int64:
930 0 : if (val > 0 && jsoint->cint.c_int64 > INT64_MAX - val)
931 : {
932 0 : jsoint->cint.c_uint64 = (uint64_t)jsoint->cint.c_int64 + (uint64_t)val;
933 0 : jsoint->cint_type = json_object_int_type_uint64;
934 : }
935 0 : else if (val < 0 && jsoint->cint.c_int64 < INT64_MIN - val)
936 : {
937 0 : jsoint->cint.c_int64 = INT64_MIN;
938 : }
939 : else
940 : {
941 0 : jsoint->cint.c_int64 += val;
942 : }
943 0 : return 1;
944 0 : case json_object_int_type_uint64:
945 0 : if (val > 0 && jsoint->cint.c_uint64 > UINT64_MAX - (uint64_t)val)
946 : {
947 0 : jsoint->cint.c_uint64 = UINT64_MAX;
948 : }
949 0 : else if (val < 0 && jsoint->cint.c_uint64 < (uint64_t)(-val))
950 : {
951 0 : jsoint->cint.c_int64 = (int64_t)jsoint->cint.c_uint64 + val;
952 0 : jsoint->cint_type = json_object_int_type_int64;
953 : }
954 0 : else if (val < 0 && jsoint->cint.c_uint64 >= (uint64_t)(-val))
955 : {
956 0 : jsoint->cint.c_uint64 -= (uint64_t)(-val);
957 : }
958 : else
959 : {
960 0 : jsoint->cint.c_uint64 += val;
961 : }
962 0 : return 1;
963 0 : default: json_abort("invalid cint_type");
964 : }
965 : }
966 :
967 : /* json_object_double */
968 :
969 : #if defined(HAVE___THREAD)
970 : // i.e. __thread or __declspec(thread)
971 : static SPEC___THREAD char *tls_serialization_float_format = NULL;
972 : #endif
973 : static char *global_serialization_float_format = NULL;
974 :
975 0 : int json_c_set_serialization_double_format(const char *double_format, int global_or_thread)
976 : {
977 0 : if (global_or_thread == JSON_C_OPTION_GLOBAL)
978 : {
979 : #if defined(HAVE___THREAD)
980 : if (tls_serialization_float_format)
981 : {
982 : free(tls_serialization_float_format);
983 : tls_serialization_float_format = NULL;
984 : }
985 : #endif
986 0 : if (global_serialization_float_format)
987 0 : free(global_serialization_float_format);
988 0 : global_serialization_float_format = double_format ? strdup(double_format) : NULL;
989 : }
990 0 : else if (global_or_thread == JSON_C_OPTION_THREAD)
991 : {
992 : #if defined(HAVE___THREAD)
993 : if (tls_serialization_float_format)
994 : {
995 : free(tls_serialization_float_format);
996 : tls_serialization_float_format = NULL;
997 : }
998 : tls_serialization_float_format = double_format ? strdup(double_format) : NULL;
999 : #else
1000 0 : _json_c_set_last_err("json_c_set_option: not compiled with __thread support\n");
1001 0 : return -1;
1002 : #endif
1003 : }
1004 : else
1005 : {
1006 0 : _json_c_set_last_err("json_c_set_option: invalid global_or_thread value: %d\n",
1007 : global_or_thread);
1008 0 : return -1;
1009 : }
1010 0 : return 0;
1011 : }
1012 :
1013 2122 : static int json_object_double_to_json_string_format(struct json_object *jso, struct printbuf *pb,
1014 : int level, int flags, const char *format)
1015 : {
1016 : (void)level;
1017 2122 : struct json_object_double *jsodbl = JC_DOUBLE(jso);
1018 : char buf[128], *p, *q;
1019 : int size;
1020 : /* Although JSON RFC does not support
1021 : * NaN or Infinity as numeric values
1022 : * ECMA 262 section 9.8.1 defines
1023 : * how to handle these cases as strings
1024 : */
1025 2122 : if (isnan(jsodbl->c_double))
1026 : {
1027 0 : size = snprintf(buf, sizeof(buf), "NaN");
1028 : }
1029 2122 : else if (isinf(jsodbl->c_double))
1030 : {
1031 0 : if (jsodbl->c_double > 0)
1032 0 : size = snprintf(buf, sizeof(buf), "Infinity");
1033 : else
1034 0 : size = snprintf(buf, sizeof(buf), "-Infinity");
1035 : }
1036 : else
1037 : {
1038 2122 : const char *std_format = "%.17g";
1039 2122 : int format_drops_decimals = 0;
1040 2122 : int looks_numeric = 0;
1041 :
1042 2122 : if (!format)
1043 : {
1044 : #if defined(HAVE___THREAD)
1045 : if (tls_serialization_float_format)
1046 : format = tls_serialization_float_format;
1047 : else
1048 : #endif
1049 2122 : if (global_serialization_float_format)
1050 0 : format = global_serialization_float_format;
1051 : else
1052 2122 : format = std_format;
1053 : }
1054 2122 : size = snprintf(buf, sizeof(buf), format, jsodbl->c_double);
1055 :
1056 2122 : if (size < 0)
1057 0 : return -1;
1058 :
1059 2122 : p = strchr(buf, ',');
1060 2122 : if (p)
1061 0 : *p = '.';
1062 : else
1063 2122 : p = strchr(buf, '.');
1064 :
1065 2122 : if (format == std_format || strstr(format, ".0f") == NULL)
1066 2122 : format_drops_decimals = 1;
1067 :
1068 2122 : looks_numeric = /* Looks like *some* kind of number */
1069 2177 : isdigit((unsigned char)buf[0]) ||
1070 55 : (size > 1 && buf[0] == '-' && isdigit((unsigned char)buf[1]));
1071 :
1072 2122 : if (size < (int)sizeof(buf) - 2 && looks_numeric && !p && /* Has no decimal point */
1073 1615 : strchr(buf, 'e') == NULL && /* Not scientific notation */
1074 : format_drops_decimals)
1075 : {
1076 : // Ensure it looks like a float, even if snprintf didn't,
1077 : // unless a custom format is set to omit the decimal.
1078 1615 : strcat(buf, ".0");
1079 1615 : size += 2;
1080 : }
1081 2122 : if (p && (flags & JSON_C_TO_STRING_NOZERO))
1082 : {
1083 : /* last useful digit, always keep 1 zero */
1084 0 : p++;
1085 0 : for (q = p; *q; q++)
1086 : {
1087 0 : if (*q != '0')
1088 0 : p = q;
1089 : }
1090 : /* drop trailing zeroes */
1091 0 : if (*p != 0)
1092 0 : *(++p) = 0;
1093 0 : size = (int)(p - buf);
1094 : }
1095 : }
1096 : // although unlikely, snprintf can fail
1097 2122 : if (size < 0)
1098 0 : return -1;
1099 :
1100 2122 : if (size >= (int)sizeof(buf))
1101 : // The standard formats are guaranteed not to overrun the buffer,
1102 : // but if a custom one happens to do so, just silently truncate.
1103 0 : size = sizeof(buf) - 1;
1104 2122 : printbuf_memappend(pb, buf, size);
1105 2122 : return size;
1106 : }
1107 :
1108 2122 : static int json_object_double_to_json_string_default(struct json_object *jso, struct printbuf *pb,
1109 : int level, int flags)
1110 : {
1111 2122 : return json_object_double_to_json_string_format(jso, pb, level, flags, NULL);
1112 : }
1113 :
1114 0 : int json_object_double_to_json_string(struct json_object *jso, struct printbuf *pb, int level,
1115 : int flags)
1116 : {
1117 0 : return json_object_double_to_json_string_format(jso, pb, level, flags,
1118 0 : (const char *)jso->_userdata);
1119 : }
1120 :
1121 542364 : struct json_object *json_object_new_double(double d)
1122 : {
1123 542364 : struct json_object_double *jso = JSON_OBJECT_NEW(double);
1124 542364 : if (!jso)
1125 0 : return NULL;
1126 542364 : jso->base._to_json_string = &json_object_double_to_json_string_default;
1127 542364 : jso->c_double = d;
1128 542364 : return &jso->base;
1129 : }
1130 :
1131 133551 : struct json_object *json_object_new_double_s(double d, const char *ds)
1132 : {
1133 : char *new_ds;
1134 133551 : struct json_object *jso = json_object_new_double(d);
1135 133551 : if (!jso)
1136 0 : return NULL;
1137 :
1138 133551 : new_ds = strdup(ds);
1139 133551 : if (!new_ds)
1140 : {
1141 0 : json_object_generic_delete(jso);
1142 0 : errno = ENOMEM;
1143 0 : return NULL;
1144 : }
1145 133551 : json_object_set_serializer(jso, _json_object_userdata_to_json_string, new_ds,
1146 : json_object_free_userdata);
1147 133551 : return jso;
1148 : }
1149 :
1150 : /*
1151 : * A wrapper around json_object_userdata_to_json_string() used only
1152 : * by json_object_new_double_s() just so json_object_set_double() can
1153 : * detect when it needs to reset the serializer to the default.
1154 : */
1155 75320 : static int _json_object_userdata_to_json_string(struct json_object *jso, struct printbuf *pb,
1156 : int level, int flags)
1157 : {
1158 75320 : return json_object_userdata_to_json_string(jso, pb, level, flags);
1159 : }
1160 :
1161 75320 : int json_object_userdata_to_json_string(struct json_object *jso, struct printbuf *pb, int level,
1162 : int flags)
1163 : {
1164 : (void)level;
1165 : (void)flags;
1166 75320 : int userdata_len = (int)strlen((const char *)jso->_userdata);
1167 75320 : printbuf_memappend(pb, (const char *)jso->_userdata, userdata_len);
1168 75320 : return userdata_len;
1169 : }
1170 :
1171 133551 : void json_object_free_userdata(struct json_object *jso, void *userdata)
1172 : {
1173 : (void)jso;
1174 133551 : free(userdata);
1175 133551 : }
1176 :
1177 606001 : double json_object_get_double(const struct json_object *jso)
1178 : {
1179 : double cdouble;
1180 606001 : char *errPtr = NULL;
1181 :
1182 606001 : if (!jso)
1183 48 : return 0.0;
1184 605953 : switch (jso->o_type)
1185 : {
1186 390224 : case json_type_double: return JC_DOUBLE_C(jso)->c_double;
1187 215721 : case json_type_int:
1188 215721 : switch (JC_INT_C(jso)->cint_type)
1189 : {
1190 215721 : case json_object_int_type_int64: return JC_INT_C(jso)->cint.c_int64;
1191 0 : case json_object_int_type_uint64: return JC_INT_C(jso)->cint.c_uint64;
1192 0 : default: json_abort("invalid cint_type");
1193 : }
1194 8 : case json_type_boolean: return JC_BOOL_C(jso)->c_boolean;
1195 0 : case json_type_string:
1196 0 : errno = 0;
1197 0 : cdouble = CPLStrtod(get_string_component(jso), &errPtr);
1198 :
1199 : /* if conversion stopped at the first character, return 0.0 */
1200 0 : if (errPtr == get_string_component(jso))
1201 : {
1202 0 : errno = EINVAL;
1203 0 : return 0.0;
1204 : }
1205 :
1206 : /*
1207 : * Check that the conversion terminated on something sensible
1208 : *
1209 : * For example, { "pay" : 123AB } would parse as 123.
1210 : */
1211 0 : if (*errPtr != '\0')
1212 : {
1213 0 : errno = EINVAL;
1214 0 : return 0.0;
1215 : }
1216 :
1217 : /*
1218 : * If strtod encounters a string which would exceed the
1219 : * capacity of a double, it returns +/- HUGE_VAL and sets
1220 : * errno to ERANGE. But +/- HUGE_VAL is also a valid result
1221 : * from a conversion, so we need to check errno.
1222 : *
1223 : * Underflow also sets errno to ERANGE, but it returns 0 in
1224 : * that case, which is what we will return anyway.
1225 : *
1226 : * See CERT guideline ERR30-C
1227 : */
1228 0 : if ((HUGE_VAL == cdouble || -HUGE_VAL == cdouble) && (ERANGE == errno))
1229 0 : cdouble = 0.0;
1230 0 : return cdouble;
1231 0 : default: errno = EINVAL; return 0.0;
1232 : }
1233 : }
1234 :
1235 0 : int json_object_set_double(struct json_object *jso, double new_value)
1236 : {
1237 0 : if (!jso || jso->o_type != json_type_double)
1238 0 : return 0;
1239 0 : JC_DOUBLE(jso)->c_double = new_value;
1240 0 : if (jso->_to_json_string == &_json_object_userdata_to_json_string)
1241 0 : json_object_set_serializer(jso, NULL, NULL, NULL);
1242 0 : return 1;
1243 : }
1244 :
1245 : /* json_object_string */
1246 :
1247 47197 : static int json_object_string_to_json_string(struct json_object *jso, struct printbuf *pb,
1248 : int level, int flags)
1249 : {
1250 : (void)level;
1251 47197 : ssize_t len = JC_STRING(jso)->len;
1252 47197 : printbuf_strappend(pb, "\"");
1253 47197 : json_escape_str(pb, get_string_component(jso), len < 0 ? -(ssize_t)len : len, flags);
1254 47197 : printbuf_strappend(pb, "\"");
1255 47197 : return 0;
1256 : }
1257 :
1258 1273650 : static void json_object_string_delete(struct json_object *jso)
1259 : {
1260 1273650 : if (JC_STRING(jso)->len < 0)
1261 0 : free(JC_STRING(jso)->c_string.pdata);
1262 1273650 : json_object_generic_delete(jso);
1263 1273650 : }
1264 :
1265 1273650 : static struct json_object *_json_object_new_string(const char *s, const size_t len)
1266 : {
1267 : size_t objsize;
1268 : struct json_object_string *jso;
1269 :
1270 : /*
1271 : * Structures Actual memory layout
1272 : * ------------------- --------------------
1273 : * [json_object_string [json_object_string
1274 : * [json_object] [json_object]
1275 : * ...other fields... ...other fields...
1276 : * c_string] len
1277 : * bytes
1278 : * of
1279 : * string
1280 : * data
1281 : * \0]
1282 : */
1283 1273650 : if (len > (SSIZE_T_MAX - (sizeof(*jso) - sizeof(jso->c_string)) - 1))
1284 0 : return NULL;
1285 1273650 : objsize = (sizeof(*jso) - sizeof(jso->c_string)) + len + 1;
1286 1273650 : if (len < sizeof(void *))
1287 : // We need a minimum size to support json_object_set_string() mutability
1288 : // so we can stuff a pointer into pdata :(
1289 309448 : objsize += sizeof(void *) - len;
1290 :
1291 1273650 : jso = (struct json_object_string *)json_object_new(json_type_string, objsize,
1292 : &json_object_string_to_json_string);
1293 :
1294 1273650 : if (!jso)
1295 0 : return NULL;
1296 1273650 : jso->len = len;
1297 : char* strdata;
1298 1273650 : uintptr_t strdata_addr = (uintptr_t)&(jso->c_string.idata);
1299 1273650 : memcpy(&strdata, &(strdata_addr), sizeof(char*));
1300 1273650 : memcpy(strdata, s, len);
1301 1273650 : strdata[len] = '\0';
1302 1273650 : return &jso->base;
1303 : }
1304 :
1305 63064 : struct json_object *json_object_new_string(const char *s)
1306 : {
1307 63064 : return _json_object_new_string(s, strlen(s));
1308 : }
1309 :
1310 1210590 : struct json_object *json_object_new_string_len(const char *s, const int len)
1311 : {
1312 1210590 : return _json_object_new_string(s, len);
1313 : }
1314 :
1315 390739 : const char *json_object_get_string(struct json_object *jso)
1316 : {
1317 390739 : if (!jso)
1318 24 : return NULL;
1319 390715 : switch (jso->o_type)
1320 : {
1321 382453 : case json_type_string: return get_string_component(jso);
1322 8262 : default: return json_object_to_json_string(jso);
1323 : }
1324 : }
1325 0 : int json_object_get_string_len(const struct json_object *jso)
1326 : {
1327 : ssize_t len;
1328 0 : if (!jso)
1329 0 : return 0;
1330 0 : switch (jso->o_type)
1331 : {
1332 0 : case json_type_string:
1333 : {
1334 0 : len = JC_STRING_C(jso)->len;
1335 0 : return (len < 0) ? (int)(-(ssize_t)len) : (int)len;
1336 : }
1337 0 : default: return 0;
1338 : }
1339 : }
1340 :
1341 0 : static int _json_object_set_string_len(json_object *jso, const char *s, size_t len)
1342 : {
1343 : char *dstbuf;
1344 : ssize_t curlen;
1345 : ssize_t newlen;
1346 0 : if (jso == NULL || jso->o_type != json_type_string)
1347 0 : return 0;
1348 :
1349 0 : if (len >= SSIZE_T_MAX - 1)
1350 : // jso->len is a signed ssize_t, so it can't hold the
1351 : // full size_t range.
1352 0 : return 0;
1353 :
1354 0 : dstbuf = get_string_component_mutable(jso);
1355 0 : curlen = JC_STRING(jso)->len;
1356 0 : if (curlen < 0)
1357 0 : curlen = -curlen;
1358 0 : newlen = len;
1359 :
1360 0 : if ((ssize_t)len > curlen)
1361 : {
1362 : // We have no way to return the new ptr from realloc(jso, newlen)
1363 : // and we have no way of knowing whether there's extra room available
1364 : // so we need to stuff a pointer in to pdata :(
1365 0 : dstbuf = (char *)malloc(len + 1);
1366 0 : if (dstbuf == NULL)
1367 0 : return 0;
1368 0 : if (JC_STRING(jso)->len < 0)
1369 0 : free(JC_STRING(jso)->c_string.pdata);
1370 0 : JC_STRING(jso)->c_string.pdata = dstbuf;
1371 0 : newlen = -(ssize_t)len;
1372 : }
1373 0 : else if (JC_STRING(jso)->len < 0)
1374 : {
1375 : // We've got enough room in the separate allocated buffer,
1376 : // so use it as-is and continue to indicate that pdata is used.
1377 0 : newlen = -(ssize_t)len;
1378 : }
1379 :
1380 0 : memcpy(dstbuf, (const void *)s, len);
1381 0 : dstbuf[len] = '\0';
1382 0 : JC_STRING(jso)->len = newlen;
1383 0 : return 1;
1384 : }
1385 :
1386 0 : int json_object_set_string(json_object *jso, const char *s)
1387 : {
1388 0 : return _json_object_set_string_len(jso, s, strlen(s));
1389 : }
1390 :
1391 0 : int json_object_set_string_len(json_object *jso, const char *s, int len)
1392 : {
1393 0 : return _json_object_set_string_len(jso, s, len);
1394 : }
1395 :
1396 : /* json_object_array */
1397 :
1398 67690 : static int json_object_array_to_json_string(struct json_object *jso, struct printbuf *pb, int level,
1399 : int flags)
1400 : {
1401 67690 : int had_children = 0;
1402 : size_t ii;
1403 :
1404 67690 : printbuf_strappend(pb, "[");
1405 67690 : if (flags & JSON_C_TO_STRING_PRETTY)
1406 47066 : printbuf_strappend(pb, "\n");
1407 242706 : for (ii = 0; ii < json_object_array_length(jso); ii++)
1408 : {
1409 : struct json_object *val;
1410 175016 : if (had_children)
1411 : {
1412 108218 : printbuf_strappend(pb, ",");
1413 108218 : if (flags & JSON_C_TO_STRING_PRETTY)
1414 81770 : printbuf_strappend(pb, "\n");
1415 : }
1416 175016 : had_children = 1;
1417 175016 : if (flags & JSON_C_TO_STRING_SPACED && !(flags & JSON_C_TO_STRING_PRETTY))
1418 33776 : printbuf_strappend(pb, " ");
1419 175016 : indent(pb, level + 1, flags);
1420 175016 : val = json_object_array_get_idx(jso, ii);
1421 175016 : if (val == NULL)
1422 2357 : printbuf_strappend(pb, "null");
1423 172659 : else if (val->_to_json_string(val, pb, level + 1, flags) < 0)
1424 0 : return -1;
1425 : }
1426 67690 : if (flags & JSON_C_TO_STRING_PRETTY)
1427 : {
1428 47066 : if (had_children)
1429 46644 : printbuf_strappend(pb, "\n");
1430 47066 : indent(pb, level, flags);
1431 : }
1432 :
1433 67690 : if (flags & JSON_C_TO_STRING_SPACED && !(flags & JSON_C_TO_STRING_PRETTY))
1434 13697 : return printbuf_strappend(pb, " ]");
1435 53993 : return printbuf_strappend(pb, "]");
1436 : }
1437 :
1438 1537570 : static void json_object_array_entry_free(void *data)
1439 : {
1440 1537570 : json_object_put((struct json_object *)data);
1441 1537570 : }
1442 :
1443 453098 : static void json_object_array_delete(struct json_object *jso)
1444 : {
1445 453098 : array_list_free(JC_ARRAY(jso)->c_array);
1446 453098 : json_object_generic_delete(jso);
1447 453098 : }
1448 :
1449 453098 : struct json_object *json_object_new_array(void)
1450 : {
1451 453098 : return json_object_new_array_ext(ARRAY_LIST_DEFAULT_SIZE);
1452 : }
1453 453098 : struct json_object *json_object_new_array_ext(int initial_size)
1454 : {
1455 453098 : struct json_object_array *jso = JSON_OBJECT_NEW(array);
1456 453098 : if (!jso)
1457 0 : return NULL;
1458 453098 : jso->c_array = array_list_new2(&json_object_array_entry_free, initial_size);
1459 453098 : if (jso->c_array == NULL)
1460 : {
1461 0 : free(jso);
1462 0 : return NULL;
1463 : }
1464 453098 : return &jso->base;
1465 : }
1466 :
1467 0 : struct array_list *json_object_get_array(const struct json_object *jso)
1468 : {
1469 0 : if (!jso)
1470 0 : return NULL;
1471 0 : switch (jso->o_type)
1472 : {
1473 0 : case json_type_array: return JC_ARRAY_C(jso)->c_array;
1474 0 : default: return NULL;
1475 : }
1476 : }
1477 :
1478 0 : void json_object_array_sort(struct json_object *jso, int (*sort_fn)(const void *, const void *))
1479 : {
1480 0 : assert(json_object_get_type(jso) == json_type_array);
1481 0 : array_list_sort(JC_ARRAY(jso)->c_array, sort_fn);
1482 0 : }
1483 :
1484 0 : struct json_object *json_object_array_bsearch(const struct json_object *key,
1485 : const struct json_object *jso,
1486 : int (*sort_fn)(const void *, const void *))
1487 : {
1488 : struct json_object **result;
1489 :
1490 0 : assert(json_object_get_type(jso) == json_type_array);
1491 0 : result = (struct json_object **)array_list_bsearch((const void **)(void *)&key,
1492 0 : JC_ARRAY_C(jso)->c_array, sort_fn);
1493 :
1494 0 : if (!result)
1495 0 : return NULL;
1496 0 : return *result;
1497 : }
1498 :
1499 824900 : size_t json_object_array_length(const struct json_object *jso)
1500 : {
1501 824900 : assert(json_object_get_type(jso) == json_type_array);
1502 824581 : return array_list_length(JC_ARRAY_C(jso)->c_array);
1503 : }
1504 :
1505 1540020 : int json_object_array_add(struct json_object *jso, struct json_object *val)
1506 : {
1507 1540020 : assert(json_object_get_type(jso) == json_type_array);
1508 1540020 : return array_list_add(JC_ARRAY(jso)->c_array, val);
1509 : }
1510 :
1511 0 : int json_object_array_put_idx(struct json_object *jso, size_t idx, struct json_object *val)
1512 : {
1513 0 : assert(json_object_get_type(jso) == json_type_array);
1514 0 : return array_list_put_idx(JC_ARRAY(jso)->c_array, idx, val);
1515 : }
1516 :
1517 0 : int json_object_array_del_idx(struct json_object *jso, size_t idx, size_t count)
1518 : {
1519 0 : assert(json_object_get_type(jso) == json_type_array);
1520 0 : return array_list_del_idx(JC_ARRAY(jso)->c_array, idx, count);
1521 : }
1522 :
1523 1329930 : struct json_object *json_object_array_get_idx(const struct json_object *jso, size_t idx)
1524 : {
1525 1329930 : assert(json_object_get_type(jso) == json_type_array);
1526 1329930 : return (struct json_object *)array_list_get_idx(JC_ARRAY_C(jso)->c_array, idx);
1527 : }
1528 :
1529 0 : static int json_array_equal(struct json_object *jso1, struct json_object *jso2)
1530 : {
1531 : size_t len, i;
1532 :
1533 0 : len = json_object_array_length(jso1);
1534 0 : if (len != json_object_array_length(jso2))
1535 0 : return 0;
1536 :
1537 0 : for (i = 0; i < len; i++)
1538 : {
1539 0 : if (!json_object_equal(json_object_array_get_idx(jso1, i),
1540 : json_object_array_get_idx(jso2, i)))
1541 0 : return 0;
1542 : }
1543 0 : return 1;
1544 : }
1545 :
1546 187966 : int json_object_array_shrink(struct json_object *jso, int empty_slots)
1547 : {
1548 187966 : if (empty_slots < 0)
1549 0 : json_abort("json_object_array_shrink called with negative empty_slots");
1550 187966 : return array_list_shrink(JC_ARRAY(jso)->c_array, empty_slots);
1551 : }
1552 :
1553 0 : struct json_object *json_object_new_null(void)
1554 : {
1555 0 : return NULL;
1556 : }
1557 :
1558 0 : static int json_object_all_values_equal(struct json_object *jso1, struct json_object *jso2)
1559 : {
1560 : struct json_object_iter iter;
1561 : struct json_object *sub;
1562 :
1563 0 : assert(json_object_get_type(jso1) == json_type_object);
1564 0 : assert(json_object_get_type(jso2) == json_type_object);
1565 : /* Iterate over jso1 keys and see if they exist and are equal in jso2 */
1566 0 : json_object_object_foreachC(jso1, iter)
1567 : {
1568 0 : if (!lh_table_lookup_ex(JC_OBJECT(jso2)->c_object, (void *)iter.key,
1569 : (void **)(void *)&sub))
1570 0 : return 0;
1571 0 : if (!json_object_equal(iter.val, sub))
1572 0 : return 0;
1573 : }
1574 :
1575 : /* Iterate over jso2 keys to see if any exist that are not in jso1 */
1576 0 : json_object_object_foreachC(jso2, iter)
1577 : {
1578 0 : if (!lh_table_lookup_ex(JC_OBJECT(jso1)->c_object, (void *)iter.key,
1579 : (void **)(void *)&sub))
1580 0 : return 0;
1581 : }
1582 :
1583 0 : return 1;
1584 : }
1585 :
1586 0 : int json_object_equal(struct json_object *jso1, struct json_object *jso2)
1587 : {
1588 0 : if (jso1 == jso2)
1589 0 : return 1;
1590 :
1591 0 : if (!jso1 || !jso2)
1592 0 : return 0;
1593 :
1594 0 : if (jso1->o_type != jso2->o_type)
1595 0 : return 0;
1596 :
1597 0 : switch (jso1->o_type)
1598 : {
1599 0 : case json_type_boolean: return (JC_BOOL(jso1)->c_boolean == JC_BOOL(jso2)->c_boolean);
1600 :
1601 0 : case json_type_double: return (JC_DOUBLE(jso1)->c_double == JC_DOUBLE(jso2)->c_double);
1602 :
1603 0 : case json_type_int:
1604 : {
1605 0 : struct json_object_int *int1 = JC_INT(jso1);
1606 0 : struct json_object_int *int2 = JC_INT(jso2);
1607 0 : if (int1->cint_type == json_object_int_type_int64)
1608 : {
1609 0 : if (int2->cint_type == json_object_int_type_int64)
1610 0 : return (int1->cint.c_int64 == int2->cint.c_int64);
1611 0 : if (int1->cint.c_int64 < 0)
1612 0 : return 0;
1613 0 : return ((uint64_t)int1->cint.c_int64 == int2->cint.c_uint64);
1614 : }
1615 : // else jso1 is a uint64
1616 0 : if (int2->cint_type == json_object_int_type_uint64)
1617 0 : return (int1->cint.c_uint64 == int2->cint.c_uint64);
1618 0 : if (int2->cint.c_int64 < 0)
1619 0 : return 0;
1620 0 : return (int1->cint.c_uint64 == (uint64_t)int2->cint.c_int64);
1621 : }
1622 :
1623 0 : case json_type_string:
1624 : {
1625 0 : return (json_object_get_string_len(jso1) == json_object_get_string_len(jso2) &&
1626 0 : memcmp(get_string_component(jso1), get_string_component(jso2),
1627 0 : json_object_get_string_len(jso1)) == 0);
1628 : }
1629 :
1630 0 : case json_type_object: return json_object_all_values_equal(jso1, jso2);
1631 :
1632 0 : case json_type_array: return json_array_equal(jso1, jso2);
1633 :
1634 0 : case json_type_null: return 1;
1635 : };
1636 :
1637 0 : return 0;
1638 : }
1639 :
1640 844 : static int json_object_copy_serializer_data(struct json_object *src, struct json_object *dst)
1641 : {
1642 844 : if (!src->_userdata && !src->_user_delete)
1643 843 : return 0;
1644 :
1645 1 : if (dst->_to_json_string == json_object_userdata_to_json_string ||
1646 1 : dst->_to_json_string == _json_object_userdata_to_json_string)
1647 : {
1648 0 : assert(src->_userdata);
1649 0 : dst->_userdata = strdup(src->_userdata);
1650 : }
1651 : // else if ... other supported serializers ...
1652 : else
1653 : {
1654 : void* func_ptr;
1655 1 : memcpy(&func_ptr, &(dst->_to_json_string), sizeof(void*));
1656 1 : _json_c_set_last_err(
1657 : "json_object_deep_copy: unable to copy unknown serializer data: %p\n",
1658 : func_ptr);
1659 1 : return -1;
1660 : }
1661 0 : dst->_user_delete = src->_user_delete;
1662 0 : return 0;
1663 : }
1664 :
1665 : /**
1666 : * The default shallow copy implementation. Simply creates a new object of the same
1667 : * type but does *not* copy over _userdata nor retain any custom serializer.
1668 : * If custom serializers are in use, json_object_deep_copy() must be passed a shallow copy
1669 : * implementation that is aware of how to copy them.
1670 : *
1671 : * This always returns -1 or 1. It will never return 2 since it does not copy the serializer.
1672 : */
1673 844 : int json_c_shallow_copy_default(json_object *src, json_object *parent, const char *key,
1674 : size_t index, json_object **dst)
1675 : {
1676 : (void)parent;
1677 : (void)key;
1678 : (void)index;
1679 844 : switch (src->o_type)
1680 : {
1681 0 : case json_type_boolean: *dst = json_object_new_boolean(JC_BOOL(src)->c_boolean); break;
1682 :
1683 21 : case json_type_double: *dst = json_object_new_double(JC_DOUBLE(src)->c_double); break;
1684 :
1685 771 : case json_type_int:
1686 771 : switch (JC_INT(src)->cint_type)
1687 : {
1688 771 : case json_object_int_type_int64:
1689 771 : *dst = json_object_new_int64(JC_INT(src)->cint.c_int64);
1690 771 : break;
1691 0 : case json_object_int_type_uint64:
1692 0 : *dst = json_object_new_uint64(JC_INT(src)->cint.c_uint64);
1693 0 : break;
1694 0 : default: json_abort("invalid cint_type");
1695 : }
1696 771 : break;
1697 :
1698 46 : case json_type_string: *dst = json_object_new_string(get_string_component(src)); break;
1699 :
1700 3 : case json_type_object: *dst = json_object_new_object(); break;
1701 :
1702 3 : case json_type_array: *dst = json_object_new_array(); break;
1703 :
1704 0 : default: errno = EINVAL; return -1;
1705 : }
1706 :
1707 844 : if (!*dst)
1708 : {
1709 0 : errno = ENOMEM;
1710 0 : return -1;
1711 : }
1712 844 : (*dst)->_to_json_string = src->_to_json_string;
1713 : // _userdata and _user_delete are copied later
1714 844 : return 1;
1715 : }
1716 :
1717 : /*
1718 : * The actual guts of json_object_deep_copy(), with a few additional args
1719 : * needed so we can keep track of where we are within the object tree.
1720 : *
1721 : * Note: caller is responsible for freeing *dst if this fails and returns -1.
1722 : */
1723 844 : static int json_object_deep_copy_recursive(struct json_object *src, struct json_object *parent,
1724 : const char *key_in_parent, size_t index_in_parent,
1725 : struct json_object **dst,
1726 : json_c_shallow_copy_fn *shallow_copy)
1727 : {
1728 : struct json_object_iter iter;
1729 : size_t src_array_len, ii;
1730 :
1731 844 : int shallow_copy_rc = 0;
1732 844 : shallow_copy_rc = shallow_copy(src, parent, key_in_parent, index_in_parent, dst);
1733 : /* -1=error, 1=object created ok, 2=userdata set */
1734 844 : if (shallow_copy_rc < 1)
1735 : {
1736 0 : errno = EINVAL;
1737 0 : return -1;
1738 : }
1739 844 : assert(*dst != NULL);
1740 :
1741 844 : switch (src->o_type)
1742 : {
1743 3 : case json_type_object:
1744 15 : json_object_object_foreachC(src, iter)
1745 : {
1746 12 : struct json_object *jso = NULL;
1747 : /* This handles the `json_type_null` case */
1748 12 : if (!iter.val)
1749 0 : jso = NULL;
1750 12 : else if (json_object_deep_copy_recursive(iter.val, src, iter.key, -1, &jso,
1751 : shallow_copy) < 0)
1752 : {
1753 0 : json_object_put(jso);
1754 0 : return -1;
1755 : }
1756 :
1757 12 : if (json_object_object_add(*dst, iter.key, jso) < 0)
1758 : {
1759 0 : json_object_put(jso);
1760 0 : return -1;
1761 : }
1762 : }
1763 3 : break;
1764 :
1765 3 : case json_type_array:
1766 3 : src_array_len = json_object_array_length(src);
1767 771 : for (ii = 0; ii < src_array_len; ii++)
1768 : {
1769 768 : struct json_object *jso = NULL;
1770 768 : struct json_object *jso1 = json_object_array_get_idx(src, ii);
1771 : /* This handles the `json_type_null` case */
1772 768 : if (!jso1)
1773 0 : jso = NULL;
1774 768 : else if (json_object_deep_copy_recursive(jso1, src, NULL, ii, &jso,
1775 : shallow_copy) < 0)
1776 : {
1777 0 : json_object_put(jso);
1778 0 : return -1;
1779 : }
1780 :
1781 768 : if (json_object_array_add(*dst, jso) < 0)
1782 : {
1783 0 : json_object_put(jso);
1784 0 : return -1;
1785 : }
1786 : }
1787 3 : break;
1788 :
1789 838 : default:
1790 838 : break;
1791 : /* else, nothing to do, shallow_copy already did. */
1792 : }
1793 :
1794 844 : if (shallow_copy_rc != 2)
1795 844 : return json_object_copy_serializer_data(src, *dst);
1796 :
1797 0 : return 0;
1798 : }
1799 :
1800 64 : int json_object_deep_copy(struct json_object *src, struct json_object **dst,
1801 : json_c_shallow_copy_fn *shallow_copy)
1802 : {
1803 : int rc;
1804 :
1805 : /* Check if arguments are sane ; *dst must not point to a non-NULL object */
1806 64 : if (!src || !dst || *dst)
1807 : {
1808 0 : errno = EINVAL;
1809 0 : return -1;
1810 : }
1811 :
1812 64 : if (shallow_copy == NULL)
1813 64 : shallow_copy = json_c_shallow_copy_default;
1814 :
1815 64 : rc = json_object_deep_copy_recursive(src, NULL, NULL, -1, dst, shallow_copy);
1816 64 : if (rc < 0)
1817 : {
1818 1 : json_object_put(*dst);
1819 1 : *dst = NULL;
1820 : }
1821 :
1822 64 : return rc;
1823 : }
1824 :
1825 0 : static void json_abort(const char *message)
1826 : {
1827 0 : if (message != NULL)
1828 0 : fprintf(stderr, "json-c aborts with error: %s\n", message);
1829 0 : abort();
1830 : }
|