core: Adjust cJSON code for use in GPGME.
* src/cJSON.c: Remove util.h. Use gpgrt alloc functions. (cJSON_Delete): Do not clobber ERRNO. (cJSON_AddItemToObject): Return OBJECT or NULL. (cJSON_AddNullToObject): New. (cJSON_AddTrueToObject): New. (cJSON_AddFalseToObject): New. (cJSON_AddBoolToObject): New. (cJSON_AddNumberToObject): New. (cJSON_AddStringToObject): New. * src/cJSON.h (cJSON__h): Replace macro by cJSON_h for C compliance. (cJSON_AddNullToObject): Remove macro. (cJSON_AddTrueToObject): Remove macro. (cJSON_AddFalseToObject): Remove macro. (cJSON_AddBoolToObject): Remove macro. (cJSON_AddNumberToObject): Remove macro. (cJSON_AddStringToObject): Remove macro. -- The gpgrt malloc functions are used so that we can easily mix memory returned by gpgrt (e.g. es_read_line) with memory returned from the JSON function. In general that is not needed but on Windows it makes a difference if the gpgme DLL is linked to a different C runtime than the application. The macros have been replaced to allow error checking (i.e out of core) for these functions. More error checking should be implemented instead of silently creating objects which are not as requested. Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
parent
8eb08b3189
commit
81c90d0cd0
147
src/cJSON.c
147
src/cJSON.c
@ -20,6 +20,9 @@
|
|||||||
* THE SOFTWARE.
|
* THE SOFTWARE.
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: MIT
|
* SPDX-License-Identifier: MIT
|
||||||
|
*
|
||||||
|
* Note that this code has been modified from the original code taken
|
||||||
|
* from cjson-code-58.zip.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifdef HAVE_CONFIG_H
|
#ifdef HAVE_CONFIG_H
|
||||||
@ -35,9 +38,23 @@
|
|||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|
||||||
#include "util.h" /* (Payproc specific.) */
|
|
||||||
#include "cJSON.h"
|
#include "cJSON.h"
|
||||||
|
|
||||||
|
/* We use malloc function wrappers from gpgrt (aka libgpg-error). */
|
||||||
|
#if 1
|
||||||
|
# include <gpgrt.h>
|
||||||
|
# define xtrymalloc(a) gpgrt_malloc ((a))
|
||||||
|
# define xtrycalloc(a,b) gpgrt_calloc ((a), (b))
|
||||||
|
# define xtrystrdup(a) gpgrt_strdup ((a))
|
||||||
|
# define xfree(a) gpgrt_free ((a))
|
||||||
|
#else
|
||||||
|
# define xtrymalloc(a) malloc ((a))
|
||||||
|
# define xtrycalloc(a,b) calloc ((a), (b))
|
||||||
|
# define xtrystrdup(a) strdup ((a))
|
||||||
|
# define xfree(a) free ((a))
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
static int
|
static int
|
||||||
cJSON_strcasecmp (const char *s1, const char *s2)
|
cJSON_strcasecmp (const char *s1, const char *s2)
|
||||||
{
|
{
|
||||||
@ -60,11 +77,17 @@ cJSON_New_Item (void)
|
|||||||
return xtrycalloc (1, sizeof (cJSON));
|
return xtrycalloc (1, sizeof (cJSON));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Delete a cJSON structure. */
|
/* Delete a cJSON structure. (Does not clobber ERRNO). */
|
||||||
void
|
void
|
||||||
cJSON_Delete (cJSON * c)
|
cJSON_Delete (cJSON * c)
|
||||||
{
|
{
|
||||||
cJSON *next;
|
cJSON *next;
|
||||||
|
int save_errno;
|
||||||
|
|
||||||
|
if (!c)
|
||||||
|
return;
|
||||||
|
|
||||||
|
save_errno = errno;
|
||||||
while (c)
|
while (c)
|
||||||
{
|
{
|
||||||
next = c->next;
|
next = c->next;
|
||||||
@ -77,6 +100,7 @@ cJSON_Delete (cJSON * c)
|
|||||||
xfree (c);
|
xfree (c);
|
||||||
c = next;
|
c = next;
|
||||||
}
|
}
|
||||||
|
errno = save_errno;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Parse the input text to generate a number, and populate the result
|
/* Parse the input text to generate a number, and populate the result
|
||||||
@ -132,13 +156,13 @@ print_number (cJSON * item)
|
|||||||
&& d >= INT_MIN)
|
&& d >= INT_MIN)
|
||||||
{
|
{
|
||||||
/* 2^64+1 can be represented in 21 chars. */
|
/* 2^64+1 can be represented in 21 chars. */
|
||||||
str = (char *) xtrymalloc (21);
|
str = xtrymalloc (21);
|
||||||
if (str)
|
if (str)
|
||||||
sprintf (str, "%d", item->valueint);
|
sprintf (str, "%d", item->valueint);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
str = (char *) xtrymalloc (64); /* This is a nice tradeoff. */
|
str = xtrymalloc (64); /* This is a nice tradeoff. */
|
||||||
if (str)
|
if (str)
|
||||||
{
|
{
|
||||||
if (fabs (floor (d) - d) <= DBL_EPSILON && fabs (d) < 1.0e60)
|
if (fabs (floor (d) - d) <= DBL_EPSILON && fabs (d) < 1.0e60)
|
||||||
@ -328,7 +352,7 @@ print_string_ptr (const char *str)
|
|||||||
ptr++;
|
ptr++;
|
||||||
}
|
}
|
||||||
|
|
||||||
out = (char *) xtrymalloc (len + 3);
|
out = xtrymalloc (len + 3);
|
||||||
if (!out)
|
if (!out)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
@ -606,13 +630,13 @@ print_array (cJSON * item, int depth, int fmt)
|
|||||||
/* Explicitly handle numentries==0 */
|
/* Explicitly handle numentries==0 */
|
||||||
if (!numentries)
|
if (!numentries)
|
||||||
{
|
{
|
||||||
out = (char *) xtrymalloc (3);
|
out = xtrymalloc (3);
|
||||||
if (out)
|
if (out)
|
||||||
strcpy (out, "[]");
|
strcpy (out, "[]");
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
/* Allocate an array to hold the values for each */
|
/* Allocate an array to hold the values for each */
|
||||||
entries = (char **) xtrymalloc (numentries * sizeof (char *));
|
entries = xtrymalloc (numentries * sizeof (char *));
|
||||||
if (!entries)
|
if (!entries)
|
||||||
return 0;
|
return 0;
|
||||||
memset (entries, 0, numentries * sizeof (char *));
|
memset (entries, 0, numentries * sizeof (char *));
|
||||||
@ -629,9 +653,9 @@ print_array (cJSON * item, int depth, int fmt)
|
|||||||
child = child->next;
|
child = child->next;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If we didn't fail, try to malloc the output string */
|
/* If we didn't fail, try to xtrymalloc the output string */
|
||||||
if (!fail)
|
if (!fail)
|
||||||
out = (char *) xtrymalloc (len);
|
out = xtrymalloc (len);
|
||||||
/* If that fails, we fail. */
|
/* If that fails, we fail. */
|
||||||
if (!out)
|
if (!out)
|
||||||
fail = 1;
|
fail = 1;
|
||||||
@ -748,7 +772,7 @@ print_object (cJSON * item, int depth, int fmt)
|
|||||||
/* Explicitly handle empty object case */
|
/* Explicitly handle empty object case */
|
||||||
if (!numentries)
|
if (!numentries)
|
||||||
{
|
{
|
||||||
out = (char *) xtrymalloc (fmt ? depth + 4 : 3);
|
out = xtrymalloc (fmt ? depth + 4 : 3);
|
||||||
if (!out)
|
if (!out)
|
||||||
return 0;
|
return 0;
|
||||||
ptr = out;
|
ptr = out;
|
||||||
@ -764,10 +788,10 @@ print_object (cJSON * item, int depth, int fmt)
|
|||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
/* Allocate space for the names and the objects */
|
/* Allocate space for the names and the objects */
|
||||||
entries = (char **) xtrymalloc (numentries * sizeof (char *));
|
entries = xtrymalloc (numentries * sizeof (char *));
|
||||||
if (!entries)
|
if (!entries)
|
||||||
return 0;
|
return 0;
|
||||||
names = (char **) xtrymalloc (numentries * sizeof (char *));
|
names = xtrymalloc (numentries * sizeof (char *));
|
||||||
if (!names)
|
if (!names)
|
||||||
{
|
{
|
||||||
xfree (entries);
|
xfree (entries);
|
||||||
@ -794,7 +818,7 @@ print_object (cJSON * item, int depth, int fmt)
|
|||||||
|
|
||||||
/* Try to allocate the output string */
|
/* Try to allocate the output string */
|
||||||
if (!fail)
|
if (!fail)
|
||||||
out = (char *) xtrymalloc (len);
|
out = xtrymalloc (len);
|
||||||
if (!out)
|
if (!out)
|
||||||
fail = 1;
|
fail = 1;
|
||||||
|
|
||||||
@ -920,15 +944,106 @@ cJSON_AddItemToArray (cJSON * array, cJSON * item)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
cJSON *
|
||||||
cJSON_AddItemToObject (cJSON * object, const char *string, cJSON * item)
|
cJSON_AddItemToObject (cJSON * object, const char *string, cJSON * item)
|
||||||
{
|
{
|
||||||
|
char *tmp;
|
||||||
|
|
||||||
if (!item)
|
if (!item)
|
||||||
return;
|
return 0;
|
||||||
|
tmp = xtrystrdup (string);
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
if (item->string)
|
if (item->string)
|
||||||
xfree (item->string);
|
xfree (item->string);
|
||||||
item->string = xtrystrdup (string);
|
item->string = tmp;
|
||||||
cJSON_AddItemToArray (object, item);
|
cJSON_AddItemToArray (object, item);
|
||||||
|
return object;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddNullToObject (cJSON *object, const char *name)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateNull ();
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddTrueToObject (cJSON *object, const char *name)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateTrue ();
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddFalseToObject (cJSON *object, const char *name)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateFalse ();
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddBoolToObject (cJSON *object, const char *name, int b)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateBool (b);
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddNumberToObject (cJSON *object, const char *name, double num)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateNumber (num);
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
cJSON *
|
||||||
|
cJSON_AddStringToObject (cJSON *object, const char *name, const char *string)
|
||||||
|
{
|
||||||
|
cJSON *obj, *tmp;
|
||||||
|
|
||||||
|
tmp = cJSON_CreateString (string);
|
||||||
|
if (!tmp)
|
||||||
|
return NULL;
|
||||||
|
obj = cJSON_AddItemToObject(object, name, tmp);
|
||||||
|
if (!obj)
|
||||||
|
cJSON_Delete (tmp);
|
||||||
|
return obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
39
src/cJSON.h
39
src/cJSON.h
@ -20,10 +20,13 @@
|
|||||||
* THE SOFTWARE.
|
* THE SOFTWARE.
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: MIT
|
* SPDX-License-Identifier: MIT
|
||||||
|
*
|
||||||
|
* Note that this code has been modified from the original code taken
|
||||||
|
* from cjson-code-58.zip.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef cJSON__h
|
#ifndef cJSON_h
|
||||||
#define cJSON__h
|
#define cJSON_h
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C"
|
extern "C"
|
||||||
@ -119,10 +122,20 @@ extern cJSON *cJSON_CreateFloatArray(const float *numbers,int count);
|
|||||||
extern cJSON *cJSON_CreateDoubleArray(const double *numbers,int count);
|
extern cJSON *cJSON_CreateDoubleArray(const double *numbers,int count);
|
||||||
extern cJSON *cJSON_CreateStringArray(const char **strings,int count);
|
extern cJSON *cJSON_CreateStringArray(const char **strings,int count);
|
||||||
|
|
||||||
/* Append item to the specified array/object. */
|
/* Append item to the specified array. */
|
||||||
extern void cJSON_AddItemToArray(cJSON *array, cJSON *item);
|
extern void cJSON_AddItemToArray(cJSON *array, cJSON *item);
|
||||||
extern void cJSON_AddItemToObject(cJSON *object,
|
|
||||||
const char *string, cJSON *item);
|
/* Append item to the specified object. */
|
||||||
|
extern cJSON *cJSON_AddItemToObject(cJSON *object, const char *name,
|
||||||
|
cJSON *item);
|
||||||
|
extern cJSON *cJSON_AddNullToObject (cJSON *object, const char *name);
|
||||||
|
extern cJSON *cJSON_AddTrueToObject (cJSON *object, const char *name);
|
||||||
|
extern cJSON *cJSON_AddFalseToObject (cJSON *object, const char *name);
|
||||||
|
extern cJSON *cJSON_AddBoolToObject (cJSON *object, const char *name, int b);
|
||||||
|
extern cJSON *cJSON_AddNumberToObject (cJSON *object, const char *name,
|
||||||
|
double num);
|
||||||
|
extern cJSON *cJSON_AddStringToObject (cJSON *object, const char *name,
|
||||||
|
const char *string);
|
||||||
|
|
||||||
/* Append reference to item to the specified array/object. Use this
|
/* Append reference to item to the specified array/object. Use this
|
||||||
when you want to add an existing cJSON to a new cJSON, but don't
|
when you want to add an existing cJSON to a new cJSON, but don't
|
||||||
@ -161,20 +174,6 @@ extern cJSON *cJSON_ParseWithOpts(const char *value,
|
|||||||
|
|
||||||
extern void cJSON_Minify(char *json);
|
extern void cJSON_Minify(char *json);
|
||||||
|
|
||||||
/* Macros for creating things quickly. */
|
|
||||||
#define cJSON_AddNullToObject(object,name) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateNull())
|
|
||||||
#define cJSON_AddTrueToObject(object,name) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateTrue())
|
|
||||||
#define cJSON_AddFalseToObject(object,name) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateFalse())
|
|
||||||
#define cJSON_AddBoolToObject(object,name,b) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateBool(b))
|
|
||||||
#define cJSON_AddNumberToObject(object,name,n) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateNumber(n))
|
|
||||||
#define cJSON_AddStringToObject(object,name,s) \
|
|
||||||
cJSON_AddItemToObject(object, name, cJSON_CreateString(s))
|
|
||||||
|
|
||||||
/* When assigning an integer value, it needs to be propagated to
|
/* When assigning an integer value, it needs to be propagated to
|
||||||
valuedouble too. */
|
valuedouble too. */
|
||||||
#define cJSON_SetIntValue(object,val) \
|
#define cJSON_SetIntValue(object,val) \
|
||||||
@ -184,4 +183,4 @@ extern void cJSON_Minify(char *json);
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#endif /* cJSON__h */
|
#endif /* cJSON_h */
|
||||||
|
Loading…
Reference in New Issue
Block a user