mirror of
https://github.com/DaveGamble/cJSON.git
synced 2024-12-28 06:30:52 +08:00
Merge pull request #120 from DaveGamble/typecheck-functions
Typecheck functions
This commit is contained in:
commit
2302f4f0b2
100
cJSON.c
100
cJSON.c
@ -2149,3 +2149,103 @@ void cJSON_Minify(char *json)
|
||||
/* and null-terminate. */
|
||||
*into = '\0';
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsInvalid(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_Invalid;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsFalse(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_False;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsTrue(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xff) == cJSON_True;
|
||||
}
|
||||
|
||||
|
||||
extern cjbool cJSON_IsBool(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & (cJSON_True | cJSON_False)) != 0;
|
||||
}
|
||||
extern cjbool cJSON_IsNull(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_NULL;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsNumber(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_Number;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsString(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_String;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsArray(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_Array;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsObject(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_Object;
|
||||
}
|
||||
|
||||
extern cjbool cJSON_IsRaw(const cJSON * const item)
|
||||
{
|
||||
if (item == NULL)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return (item->type & 0xFF) == cJSON_Raw;
|
||||
}
|
||||
|
12
cJSON.h
12
cJSON.h
@ -109,6 +109,18 @@ extern int cJSON_HasObjectItem(const cJSON *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 cJSON_Parse() returns 0. 0 when cJSON_Parse() succeeds. */
|
||||
extern const char *cJSON_GetErrorPtr(void);
|
||||
|
||||
/* These functions check the type of an item */
|
||||
extern int cJSON_IsInvalid(const cJSON * const item);
|
||||
extern int cJSON_IsFalse(const cJSON * const item);
|
||||
extern int cJSON_IsTrue(const cJSON * const item);
|
||||
extern int cJSON_IsBool(const cJSON * const item);
|
||||
extern int cJSON_IsNull(const cJSON * const item);
|
||||
extern int cJSON_IsNumber(const cJSON * const item);
|
||||
extern int cJSON_IsString(const cJSON * const item);
|
||||
extern int cJSON_IsArray(const cJSON * const item);
|
||||
extern int cJSON_IsObject(const cJSON * const item);
|
||||
extern int cJSON_IsRaw(const cJSON * const item);
|
||||
|
||||
/* These calls create a cJSON item of the appropriate type. */
|
||||
extern cJSON *cJSON_CreateNull(void);
|
||||
extern cJSON *cJSON_CreateTrue(void);
|
||||
|
@ -117,7 +117,6 @@ static void cJSONUtils_PointerEncodedstrcpy(unsigned char *d, const unsigned cha
|
||||
|
||||
char *cJSONUtils_FindPointerFromObjectTo(cJSON *object, cJSON *target)
|
||||
{
|
||||
int type = object->type;
|
||||
size_t c = 0;
|
||||
cJSON *obj = 0;
|
||||
|
||||
@ -133,7 +132,7 @@ char *cJSONUtils_FindPointerFromObjectTo(cJSON *object, cJSON *target)
|
||||
unsigned char *found = (unsigned char*)cJSONUtils_FindPointerFromObjectTo(obj, target);
|
||||
if (found)
|
||||
{
|
||||
if ((type & 0xFF) == cJSON_Array)
|
||||
if (cJSON_IsArray(object))
|
||||
{
|
||||
/* reserve enough memory for a 64 bit integer + '/' and '\0' */
|
||||
unsigned char *ret = (unsigned char*)malloc(strlen((char*)found) + 23);
|
||||
@ -150,7 +149,7 @@ char *cJSONUtils_FindPointerFromObjectTo(cJSON *object, cJSON *target)
|
||||
|
||||
return (char*)ret;
|
||||
}
|
||||
else if ((type & 0xFF) == cJSON_Object)
|
||||
else if (cJSON_IsObject(object))
|
||||
{
|
||||
unsigned char *ret = (unsigned char*)malloc(strlen((char*)found) + cJSONUtils_PointerEncodedstrlen((unsigned char*)obj->string) + 2);
|
||||
*ret = '/';
|
||||
@ -176,7 +175,7 @@ cJSON *cJSONUtils_GetPointer(cJSON *object, const char *pointer)
|
||||
/* follow path of the pointer */
|
||||
while ((*pointer++ == '/') && object)
|
||||
{
|
||||
if ((object->type & 0xFF) == cJSON_Array)
|
||||
if (cJSON_IsArray(object))
|
||||
{
|
||||
size_t which = 0;
|
||||
/* parse array index */
|
||||
@ -195,7 +194,7 @@ cJSON *cJSONUtils_GetPointer(cJSON *object, const char *pointer)
|
||||
}
|
||||
object = cJSON_GetArrayItem(object, (int)which);
|
||||
}
|
||||
else if ((object->type & 0xFF) == cJSON_Object)
|
||||
else if (cJSON_IsObject(object))
|
||||
{
|
||||
object = object->child;
|
||||
/* GetObjectItem. */
|
||||
@ -269,11 +268,11 @@ static cJSON *cJSONUtils_PatchDetach(cJSON *object, const unsigned char *path)
|
||||
/* Couldn't find object to remove child from. */
|
||||
ret = NULL;
|
||||
}
|
||||
else if ((parent->type & 0xFF) == cJSON_Array)
|
||||
else if (cJSON_IsArray(parent))
|
||||
{
|
||||
ret = cJSON_DetachItemFromArray(parent, atoi((char*)childptr));
|
||||
}
|
||||
else if ((parent->type & 0xFF) == cJSON_Object)
|
||||
else if (cJSON_IsObject(parent))
|
||||
{
|
||||
ret = cJSON_DetachItemFromObject(parent, (char*)childptr);
|
||||
}
|
||||
@ -474,7 +473,7 @@ static int cJSONUtils_ApplyPatch(cJSON *object, cJSON *patch)
|
||||
cJSON_Delete(value);
|
||||
return 9;
|
||||
}
|
||||
else if ((parent->type & 0xFF) == cJSON_Array)
|
||||
else if (cJSON_IsArray(parent))
|
||||
{
|
||||
if (!strcmp((char*)childptr, "-"))
|
||||
{
|
||||
@ -485,7 +484,7 @@ static int cJSONUtils_ApplyPatch(cJSON *object, cJSON *patch)
|
||||
cJSON_InsertItemInArray(parent, atoi((char*)childptr), value);
|
||||
}
|
||||
}
|
||||
else if ((parent->type & 0xFF) == cJSON_Object)
|
||||
else if (cJSON_IsObject(parent))
|
||||
{
|
||||
cJSON_DeleteItemFromObject(parent, (char*)childptr);
|
||||
cJSON_AddItemToObject(parent, (char*)childptr, value);
|
||||
@ -508,7 +507,7 @@ int cJSONUtils_ApplyPatches(cJSON *object, cJSON *patches)
|
||||
return 1;
|
||||
}
|
||||
|
||||
if ((patches->type & 0xFF) != cJSON_Array)
|
||||
if (cJSON_IsArray(patches))
|
||||
{
|
||||
/* malformed patches. */
|
||||
return 1;
|
||||
@ -793,14 +792,14 @@ void cJSONUtils_SortObject(cJSON *object)
|
||||
|
||||
cJSON* cJSONUtils_MergePatch(cJSON *target, cJSON *patch)
|
||||
{
|
||||
if (!patch || ((patch->type & 0xFF) != cJSON_Object))
|
||||
if (!cJSON_IsObject(patch))
|
||||
{
|
||||
/* scalar value, array or NULL, just duplicate */
|
||||
cJSON_Delete(target);
|
||||
return cJSON_Duplicate(patch, 1);
|
||||
}
|
||||
|
||||
if (!target || ((target->type & 0xFF) != cJSON_Object))
|
||||
if (!cJSON_IsObject(target))
|
||||
{
|
||||
cJSON_Delete(target);
|
||||
target = cJSON_CreateObject();
|
||||
@ -809,7 +808,7 @@ cJSON* cJSONUtils_MergePatch(cJSON *target, cJSON *patch)
|
||||
patch = patch->child;
|
||||
while (patch)
|
||||
{
|
||||
if ((patch->type & 0xFF) == cJSON_NULL)
|
||||
if (cJSON_IsNull(patch))
|
||||
{
|
||||
/* NULL is the indicator to remove a value, see RFC7396 */
|
||||
cJSON_DeleteItemFromObject(target, patch->string);
|
||||
@ -832,7 +831,7 @@ cJSON *cJSONUtils_GenerateMergePatch(cJSON *from, cJSON *to)
|
||||
/* patch to delete everything */
|
||||
return cJSON_CreateNull();
|
||||
}
|
||||
if (((to->type & 0xFF) != cJSON_Object) || !from || ((from->type & 0xFF) != cJSON_Object))
|
||||
if (!cJSON_IsObject(to) || !cJSON_IsObject(from))
|
||||
{
|
||||
return cJSON_Duplicate(to, 1);
|
||||
}
|
||||
|
@ -127,6 +127,62 @@ static void cjson_get_object_item_case_sensitive_should_get_object_items(void)
|
||||
cJSON_Delete(item);
|
||||
}
|
||||
|
||||
static void typecheck_functions_should_check_type(void)
|
||||
{
|
||||
cJSON invalid[1];
|
||||
cJSON item[1];
|
||||
invalid->type = cJSON_Invalid;
|
||||
invalid->type |= cJSON_StringIsConst;
|
||||
item->type = cJSON_False;
|
||||
item->type |= cJSON_StringIsConst;
|
||||
|
||||
TEST_ASSERT_FALSE(cJSON_IsInvalid(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsInvalid(item));
|
||||
TEST_ASSERT_TRUE(cJSON_IsInvalid(invalid));
|
||||
|
||||
item->type = cJSON_False | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsFalse(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsFalse(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsFalse(item));
|
||||
TEST_ASSERT_TRUE(cJSON_IsBool(item));
|
||||
|
||||
item->type = cJSON_True | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsTrue(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsTrue(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsTrue(item));
|
||||
TEST_ASSERT_TRUE(cJSON_IsBool(item));
|
||||
|
||||
item->type = cJSON_NULL | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsNull(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsNull(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsNull(item));
|
||||
|
||||
item->type = cJSON_Number | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsNumber(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsNumber(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsNumber(item));
|
||||
|
||||
item->type = cJSON_String | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsString(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsString(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsString(item));
|
||||
|
||||
item->type = cJSON_Array | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsArray(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsArray(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsArray(item));
|
||||
|
||||
item->type = cJSON_Object | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsObject(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsObject(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsObject(item));
|
||||
|
||||
item->type = cJSON_Raw | cJSON_StringIsConst;
|
||||
TEST_ASSERT_FALSE(cJSON_IsRaw(NULL));
|
||||
TEST_ASSERT_FALSE(cJSON_IsRaw(invalid));
|
||||
TEST_ASSERT_TRUE(cJSON_IsRaw(item));
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
UNITY_BEGIN();
|
||||
@ -135,6 +191,7 @@ int main(void)
|
||||
RUN_TEST(cjson_array_foreach_should_not_dereference_null_pointer);
|
||||
RUN_TEST(cjson_get_object_item_should_get_object_items);
|
||||
RUN_TEST(cjson_get_object_item_case_sensitive_should_get_object_items);
|
||||
RUN_TEST(typecheck_functions_should_check_type);
|
||||
|
||||
return UNITY_END();
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user