From 234ee4728124d8d07412d159b45dd10854b6d6d8 Mon Sep 17 00:00:00 2001 From: Petri Lehtinen Date: Sun, 6 Sep 2009 22:24:55 +0300 Subject: Better argument validation All pointer arguments are now tested for NULL. json_string() now also tests that strdup() succeeds. This is to ensure that no NULL values end up in data structures. Also desribe the different sources of errors in documentation. --- doc/apiref.rst | 10 ++++++++-- src/value.c | 25 +++++++++++++++++++++++-- test/testprogs/test_array.c | 20 ++++++++++++++++++-- test/testprogs/test_object.c | 16 +++++++++++++++- test/testprogs/test_simple.c | 4 ++++ 5 files changed, 68 insertions(+), 7 deletions(-) diff --git a/doc/apiref.rst b/doc/apiref.rst index db9b5a4..ea38343 100644 --- a/doc/apiref.rst +++ b/doc/apiref.rst @@ -41,6 +41,12 @@ Objects of :ctype:`json_t` are always used through a pointer. There are APIs for querying the type, manipulating the reference count, and for constructing and manipulating values of different types. +Unless noted otherwise, all API functions return an error value if an +error occurs. Depending on the function's signature, the error value +is either *NULL* or -1. Invalid arguments or invalid input are +apparent sources for errors. Memory allocation and I/O operations may +also cause errors. + Type ---- @@ -80,8 +86,8 @@ functions: .. cfunction:: int json_typeof(const json_t *json) Return the type of the JSON value (a :ctype:`json_type` cast to - :ctype:`int`). This function is actually implemented as a macro for - speed. + :ctype:`int`). *json* MUST NOT be *NULL*. This function is actually + implemented as a macro for speed. .. cfunction:: json_is_object(const json_t *json) json_is_array(const json_t *json) diff --git a/src/value.c b/src/value.c index d83d575..c84bfd3 100644 --- a/src/value.c +++ b/src/value.c @@ -122,6 +122,9 @@ int json_object_set_new_nocheck(json_t *json, const char *key, json_t *value) { json_object_t *object; + if(!key || !value) + return -1; + if(!json_is_object(json)) { json_decref(value); @@ -255,6 +258,10 @@ json_t *json_array_get(const json_t *json, unsigned int index) int json_array_set_new(json_t *json, unsigned int index, json_t *value) { json_array_t *array; + + if(!value) + return -1; + if(!json_is_array(json)) { json_decref(value); @@ -277,6 +284,10 @@ int json_array_set_new(json_t *json, unsigned int index, json_t *value) int json_array_append_new(json_t *json, json_t *value) { json_array_t *array; + + if(!value) + return -1; + if(!json_is_array(json)) { json_decref(value); @@ -305,18 +316,28 @@ int json_array_append_new(json_t *json, json_t *value) json_t *json_string_nocheck(const char *value) { - json_string_t *string = malloc(sizeof(json_string_t)); + json_string_t *string; + + if(!value) + return NULL; + + string = malloc(sizeof(json_string_t)); if(!string) return NULL; json_init(&string->json, JSON_STRING); string->value = strdup(value); + if(!string->value) { + free(string); + return NULL; + } + return &string->json; } json_t *json_string(const char *value) { - if(!utf8_check_string(value, -1)) + if(!value || !utf8_check_string(value, -1)) return NULL; return json_string_nocheck(value); diff --git a/test/testprogs/test_array.c b/test/testprogs/test_array.c index 97a8513..b597afb 100644 --- a/test/testprogs/test_array.c +++ b/test/testprogs/test_array.c @@ -27,6 +27,9 @@ int main() if(json_array_size(array) != 0) fail("empty array has nonzero size"); + if(!json_array_append(array, NULL)) + fail("able to append NULL"); + if(json_array_append(array, five)) fail("unable to append"); @@ -54,6 +57,9 @@ int main() if(json_array_set(array, 0, seven)) fail("unable to set value"); + if(!json_array_set(array, 0, NULL)) + fail("able to set NULL"); + if(json_array_size(array) != 2) fail("wrong array size"); @@ -85,16 +91,26 @@ int main() fail("got wrong value"); } - json_array_set_new(array, 15, json_integer(123)); + if(json_array_set_new(array, 15, json_integer(123))) + fail("unable to set new value"); + value = json_array_get(array, 15); if(!json_is_integer(value) || json_integer_value(value) != 123) fail("json_array_set_new works incorrectly"); - json_array_append_new(array, json_integer(321)); + if(!json_array_set_new(array, 15, NULL)) + fail("able to set_new NULL value"); + + if(json_array_append_new(array, json_integer(321))) + fail("unable to append new value"); + value = json_array_get(array, json_array_size(array) - 1); if(!json_is_integer(value) || json_integer_value(value) != 321) fail("json_array_append_new works incorrectly"); + if(!json_array_append_new(array, NULL)) + fail("able to append_new NULL value"); + json_decref(five); json_decref(seven); json_decref(array); diff --git a/test/testprogs/test_object.c b/test/testprogs/test_object.c index f9839c7..540109e 100644 --- a/test/testprogs/test_object.c +++ b/test/testprogs/test_object.c @@ -29,6 +29,12 @@ int main() if(json_object_set(object, "a", string)) fail("unable to set value"); + if(!json_object_set(object, NULL, string)) + fail("able to set NULL key"); + + if(!json_object_set(object, "a", NULL)) + fail("able to set NULL value"); + iter = json_object_iter(object); if(!iter) fail("unable to get iterator"); @@ -105,11 +111,19 @@ int main() fail("unable to set value"); - json_object_set_new(object, "foo", json_integer(123)); + if(json_object_set_new(object, "foo", json_integer(123))) + fail("unable to set new value"); + value = json_object_get(object, "foo"); if(!json_is_integer(value) || json_integer_value(value) != 123) fail("json_object_set_new works incorrectly"); + if(!json_object_set_new(object, NULL, json_integer(432))) + fail("able to set_new NULL key"); + + if(!json_object_set_new(object, "foo", NULL)) + fail("able to set_new NULL value"); + json_decref(string); json_decref(other_string); json_decref(object); diff --git a/test/testprogs/test_simple.c b/test/testprogs/test_simple.c index 86f841b..4491ed2 100644 --- a/test/testprogs/test_simple.c +++ b/test/testprogs/test_simple.c @@ -58,6 +58,10 @@ int main() fail("invalid string value"); json_decref(value); + value = json_string(NULL); + if(value) + fail("json_string(NULL) failed"); + value = json_integer(123); if(!value) fail("json_integer failed"); -- cgit v1.1