-
Notifications
You must be signed in to change notification settings - Fork 11
/
n_cjson.h
332 lines (283 loc) · 15.3 KB
/
n_cjson.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
/*!
* @file n_cjson.h
*
* Written by Ray Ozzie and Blues Inc. team.
*
* Portions Copyright (c) 2019 Blues Inc. MIT License. Use of this source code is
* governed by licenses granted by the copyright holder including that found in
* the
* <a href="https://github.com/blues/note-c/blob/master/LICENSE">LICENSE</a>
* file.
*
* MODIFIED for use in notecard primarily by altering default memory allocator
* and by renaming the functions so that they won't conflict with a developer's
* own decision to incorporate the actual production cJSON into their own app.
* In no way shall this interfere with a production cJSON.
*
* Renaming was done as follows:
* CJSON_ -> N_CJSON_
* cJSON_ -> J
* cJSON -> J
*
* Portions Copyright (c) 2009-2017 Dave Gamble and cJSON contributors
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software i
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#ifndef J_h
#define J_h
#ifdef __cplusplus
extern "C"
{
#endif
/* project version */
#define N_CJSON_VERSION_MAJOR 1
#define N_CJSON_VERSION_MINOR 7
#define N_CJSON_VERSION_PATCH 7
#include <stddef.h>
/* J Types: */
#define JInvalid (0)
#define JFalse (1 << 0)
#define JTrue (1 << 1)
#define JNULL (1 << 2)
#define JNumber (1 << 3)
#define JString (1 << 4)
#define JArray (1 << 5)
#define JObject (1 << 6)
#define JRaw (1 << 7) /* raw json */
#define JIsReference 256
#define JStringIsConst 512
/*!
@brief The core JSON object type used by note-c.
When using note-c, treat this struct as opaque. You should never have to work
directly with its members.
*/
typedef struct J {
/* next/prev allow you to walk array/object chains. Alternatively, use GetArraySize/GetArrayItem/GetObjectItem */
struct J *next;
struct J *prev;
/* An array or object item will have a child pointer pointing to a chain of the items in the array/object. */
struct J *child;
/* The type of the item, as above. */
int type;
/* The item's string, if type==JString and type == JRaw */
char *valuestring;
/* writing to valueint is DEPRECATED, use JSetNumberValue instead */
JINTEGER valueint;
/* The item's number, if type==JNumber */
JNUMBER valuenumber;
/* The item's name string, if this item is the child of, or is in the list of subitems of an object. */
char *string;
} J;
typedef struct JHooks {
void *(*malloc_fn)(size_t sz);
void (*free_fn)(void *ptr);
} JHooks;
typedef int Jbool;
#if !defined(__WINDOWS__) && (defined(WIN32) || defined(WIN64) || defined(_MSC_VER) || defined(_WIN32))
#define __WINDOWS__
#endif
#ifdef __WINDOWS__
/* When compiling for windows, we specify a specific calling convention to avoid issues where we are being called from a project with a different default calling convention. For windows you have 2 define options:
N_CJSON_HIDE_SYMBOLS - Define this in the case where you don't want to ever dllexport symbols
N_CJSON_EXPORT_SYMBOLS - Define this on library build when you want to dllexport symbols (default)
N_CJSON_IMPORT_SYMBOLS - Define this if you want to dllimport symbol
For *nix builds that support visibility attribute, you can define similar behavior by
setting default visibility to hidden by adding
-fvisibility=hidden (for gcc)
or
-xldscope=hidden (for sun cc)
to CFLAGS
then using the N_CJSON_API_VISIBILITY flag to "export" the same symbols the way N_CJSON_EXPORT_SYMBOLS does
*/
/* export symbols by default, this is necessary for copy pasting the C and header file */
#if !defined(N_CJSON_HIDE_SYMBOLS) && !defined(N_CJSON_IMPORT_SYMBOLS) && !defined(N_CJSON_EXPORT_SYMBOLS)
#define N_CJSON_EXPORT_SYMBOLS
#endif
#if defined(N_CJSON_HIDE_SYMBOLS)
#define N_CJSON_PUBLIC(type) type __stdcall
#elif defined(N_CJSON_EXPORT_SYMBOLS)
#define N_CJSON_PUBLIC(type) __declspec(dllexport) type __stdcall
#elif defined(N_CJSON_IMPORT_SYMBOLS)
#define N_CJSON_PUBLIC(type) __declspec(dllimport) type __stdcall
#endif
#else /* !WIN32 */
#if (defined(__GNUC__) || defined(__SUNPRO_CC) || defined (__SUNPRO_C)) && defined(N_CJSON_API_VISIBILITY)
#define N_CJSON_PUBLIC(type) __attribute__((visibility("default"))) type
#else
#define N_CJSON_PUBLIC(type) type
#endif
#endif
/*!
@brief The maximum nesting level for JSON objects before a parsing error.
Default value: `100`
For example, if you have a JSON object that contains multiple, nested
objects like this
{
"x":
{
"x:"
{
.
.
.
}
}
}
And the nesting level exceeds `N_CJSON_NESTING_LIMIT`, then calling `JParse` on
a `J *` representing this object will return an error (NULL).
This exists to prevent the cJSON parser from causing a stack overflow. The
user may override this macro at build time (e.g.
-DN_CJSON_NESTING_LIMIT=200) to increase or reduce the limit.
*/
#ifndef N_CJSON_NESTING_LIMIT
#define N_CJSON_NESTING_LIMIT 100
#endif
/* returns the version of J as a string */
N_CJSON_PUBLIC(const char*) JVersion(void);
/* Supply malloc, realloc and free functions to J */
N_CJSON_PUBLIC(void) JInitHooks(JHooks* hooks);
/* Memory Management: the caller is always responsible to free the results from all variants of JParse (with JDelete) and JPrint (with stdlib free, JHooks.free_fn, or JFree as appropriate). The exception is JPrintPreallocated, where the caller has full responsibility of the buffer. */
/* Supply a block of JSON, and this returns a J object you can interrogate. */
N_CJSON_PUBLIC(J *) JParse(const char *value);
/* ParseWithOpts allows you to require (and check) that the JSON is null terminated, and to retrieve the pointer to the final byte parsed. */
/* If you supply a ptr in return_parse_end and parsing fails, then return_parse_end will contain a pointer to the error so will match JGetErrorPtr(). */
N_CJSON_PUBLIC(J *) JParseWithOpts(const char *value, const char **return_parse_end, Jbool require_null_terminated);
/* Render a J entity to text for transfer/storage. */
N_CJSON_PUBLIC(char *) JPrint(const J *item);
/* Render a J entity to text for transfer/storage without any formatting. */
N_CJSON_PUBLIC(char *) JPrintUnformatted(const J *item);
/* Render a J entity to text for transfer/storage without any formatting and without fields that are false, 0, or "". */
N_CJSON_PUBLIC(char *) JPrintUnformattedOmitEmpty(const J *item);
/* Render a J entity to text using a buffered strategy. prebuffer is a guess at the final size. guessing well reduces reallocation. fmt=0 gives unformatted, =1 gives formatted */
N_CJSON_PUBLIC(char *) JPrintBuffered(const J *item, int prebuffer, Jbool fmt);
/* Render a J entity to text using a buffer already allocated in memory with given length. Returns 1 on success and 0 on failure. */
/* NOTE: J is not always 100% accurate in estimating how much memory it will use, so to be safe allocate 5 bytes more than you actually need */
N_CJSON_PUBLIC(Jbool) JPrintPreallocated(J *item, char *buffer, const int length, const Jbool format);
N_CJSON_PUBLIC(Jbool) JPrintPreallocatedOmitEmpty(J *item, char *buffer, const int length, const Jbool format);
/* Delete a J entity and all subentities. */
N_CJSON_PUBLIC(void) JDelete(J *c);
/* Returns the number of items in an array (or object). */
N_CJSON_PUBLIC(int) JGetArraySize(const J *array);
#define JGetObjectItems JGetArraySize
/* Retrieve item number "index" from array "array". Returns NULL if unsuccessful. */
N_CJSON_PUBLIC(J *) JGetArrayItem(const J *array, int index);
/* Get item "string" from object. Case insensitive. */
N_CJSON_PUBLIC(J *) JGetObjectItem(const J * const object, const char * const string);
N_CJSON_PUBLIC(J *) JGetObjectItemCaseSensitive(const J * const object, const char * const string);
N_CJSON_PUBLIC(Jbool) JHasObjectItem(const J *object, const char *string);
/* For analysing failed parses. This returns a pointer to the parse error. You'll probably need to look a few chars back to make sense of it. Defined when JParse() returns 0. 0 when JParse() succeeds. */
N_CJSON_PUBLIC(const char *) JGetErrorPtr(void);
/* Check if the item is a string and return its valuestring */
N_CJSON_PUBLIC(char *) JGetStringValue(J *item);
/* These functions check the type of an item */
N_CJSON_PUBLIC(Jbool) JIsInvalid(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsFalse(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsTrue(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsBool(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsNull(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsNumber(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsString(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsArray(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsObject(const J * const item);
N_CJSON_PUBLIC(Jbool) JIsRaw(const J * const item);
/* These calls create a J item of the appropriate type. */
N_CJSON_PUBLIC(J *) JCreateTrue(void);
N_CJSON_PUBLIC(J *) JCreateFalse(void);
N_CJSON_PUBLIC(J *) JCreateBool(Jbool boolean);
N_CJSON_PUBLIC(J *) JCreateNumber(JNUMBER num);
N_CJSON_PUBLIC(J *) JCreateInteger(JINTEGER integer);
N_CJSON_PUBLIC(J *) JCreateString(const char *string);
/* raw json */
N_CJSON_PUBLIC(J *) JCreateRaw(const char *raw);
N_CJSON_PUBLIC(J *) JCreateArray(void);
N_CJSON_PUBLIC(J *) JCreateObject(void);
/* Create a string where valuestring references a string so
* it will not be freed by JDelete */
N_CJSON_PUBLIC(J *) JCreateStringValue(const char *string);
N_CJSON_PUBLIC(J *) JCreateStringReference(const char *string);
/* Create an object/arrray that only references it's elements so
* they will not be freed by JDelete */
N_CJSON_PUBLIC(J *) JCreateObjectReference(const J *child);
N_CJSON_PUBLIC(J *) JCreateArrayReference(const J *child);
/* These utilities create an Array of count items. */
N_CJSON_PUBLIC(J *) JCreateIntArray(const long int *numbers, int count);
N_CJSON_PUBLIC(J *) JCreateNumberArray(const JNUMBER *numbers, int count);
N_CJSON_PUBLIC(J *) JCreateStringArray(const char **strings, int count);
/* Append item to the specified array/object. */
N_CJSON_PUBLIC(void) JAddItemToArray(J *array, J *item);
N_CJSON_PUBLIC(void) JAddItemToObject(J *object, const char *string, J *item);
/* Use this when string is definitely const (i.e. a literal, or as good as), and will definitely survive the J object.
* WARNING: When this function was used, make sure to always check that (item->type & JStringIsConst) is zero before
* writing to `item->string` */
N_CJSON_PUBLIC(void) JAddItemToObjectCS(J *object, const char *string, J *item);
/* Append reference to item to the specified array/object. Use this when you want to add an existing J to a new J, but don't want to corrupt your existing J. */
N_CJSON_PUBLIC(void) JAddItemReferenceToArray(J *array, J *item);
N_CJSON_PUBLIC(void) JAddItemReferenceToObject(J *object, const char *string, J *item);
/* Remove/Detatch items from Arrays/Objects. */
N_CJSON_PUBLIC(J *) JDetachItemViaPointer(J *parent, J * const item);
N_CJSON_PUBLIC(J *) JDetachItemFromArray(J *array, int which);
N_CJSON_PUBLIC(void) JDeleteItemFromArray(J *array, int which);
N_CJSON_PUBLIC(J *) JDetachItemFromObject(J *object, const char *string);
N_CJSON_PUBLIC(J *) JDetachItemFromObjectCaseSensitive(J *object, const char *string);
N_CJSON_PUBLIC(void) JDeleteItemFromObject(J *object, const char *string);
N_CJSON_PUBLIC(void) JDeleteItemFromObjectCaseSensitive(J *object, const char *string);
/* Update array items. */
N_CJSON_PUBLIC(void) JInsertItemInArray(J *array, int which, J *newitem); /* Shifts pre-existing items to the right. */
N_CJSON_PUBLIC(Jbool) JReplaceItemViaPointer(J * const parent, J * const item, J * replacement);
N_CJSON_PUBLIC(void) JReplaceItemInArray(J *array, int which, J *newitem);
N_CJSON_PUBLIC(void) JReplaceItemInObject(J *object,const char *string,J *newitem);
N_CJSON_PUBLIC(void) JReplaceItemInObjectCaseSensitive(J *object,const char *string,J *newitem);
/* Duplicate a J item */
N_CJSON_PUBLIC(J *) JDuplicate(const J *item, Jbool recurse);
/* Duplicate will create a new, identical J item to the one you pass, in new memory that will
need to be released. With recurse!=0, it will duplicate any children connected to the item.
The item->next and ->prev pointers are always zero on return from Duplicate. */
/* Recursively compare two J items for equality. If either a or b is NULL or invalid, they will be considered unequal.
* case_sensitive determines if object keys are treated case sensitive (1) or case insensitive (0) */
N_CJSON_PUBLIC(Jbool) JCompare(const J * const a, const J * const b, const Jbool case_sensitive);
N_CJSON_PUBLIC(void) JMinify(char *json);
/* Helper functions for creating and adding items to an object at the same time.
* They return the added item or NULL on failure. */
N_CJSON_PUBLIC(J*) JAddTrueToObject(J * const object, const char * const name);
N_CJSON_PUBLIC(J*) JAddFalseToObject(J * const object, const char * const name);
N_CJSON_PUBLIC(J*) JAddBoolToObject(J * const object, const char * const name, const Jbool boolean);
N_CJSON_PUBLIC(J*) JAddNumberToObject(J * const object, const char * const name, const JNUMBER number);
N_CJSON_PUBLIC(J*) JAddIntToObject(J * const object, const char * const name, const JINTEGER integer);
N_CJSON_PUBLIC(J*) JAddStringToObject(J * const object, const char * const name, const char * const string);
N_CJSON_PUBLIC(J*) JAddRawToObject(J * const object, const char * const name, const char * const raw);
N_CJSON_PUBLIC(J*) JAddObjectToObject(J * const object, const char * const name);
N_CJSON_PUBLIC(J*) JAddArrayToObject(J * const object, const char * const name);
#define JConvertToJSONString JPrintUnformatted
#define JConvertFromJSONString JParse
/* When assigning an integer value, it needs to be propagated to valuenumber too. */
#define JSetIntValue(object, number) ((object) ? (object)->valueint = (object)->valuenumber = (number) : (number))
/* helper for the JSetNumberValue macro */
N_CJSON_PUBLIC(JNUMBER) JSetNumberHelper(J *object, JNUMBER number);
#define JSetNumberValue(object, number) ((object != NULL) ? JSetNumberHelper(object, (JNUMBER)number) : (number))
/* Macro for iterating over an array or object */
#define JArrayForEach(element, array) for(element = (array != NULL) ? (array)->child : NULL; element != NULL; element = element->next)
// Iterate over the fields of an object
#define JObjectForEach(element, array) JArrayForEach(element, array)
/* malloc/free objects using the malloc/free functions that have been set with JInitHooks */
N_CJSON_PUBLIC(void *) JMalloc(size_t size);
N_CJSON_PUBLIC(void) JFree(void *object);
#ifdef __cplusplus
}
#endif
#endif