diff --git a/cJSON.c b/cJSON.c index 97564bb0..6f55820f 100644 --- a/cJSON.c +++ b/cJSON.c @@ -263,10 +263,12 @@ CJSON_PUBLIC(void) cJSON_Delete(cJSON *item) if (!(item->type & cJSON_IsReference) && (item->valuestring != NULL)) { global_hooks.deallocate(item->valuestring); + item->valuestring = NULL; } if (!(item->type & cJSON_StringIsConst) && (item->string != NULL)) { global_hooks.deallocate(item->string); + item->string = NULL; } global_hooks.deallocate(item); item = next; @@ -894,6 +896,7 @@ static cJSON_bool parse_string(cJSON * const item, parse_buffer * const input_bu if (output != NULL) { input_buffer->hooks.deallocate(output); + output = NULL; } if (input_pointer != NULL) @@ -1236,6 +1239,7 @@ static unsigned char *print(const cJSON * const item, cJSON_bool format, const i /* free the buffer */ hooks->deallocate(buffer->buffer); + buffer->buffer = NULL; } return printed; @@ -1244,11 +1248,13 @@ static unsigned char *print(const cJSON * const item, cJSON_bool format, const i if (buffer->buffer != NULL) { hooks->deallocate(buffer->buffer); + buffer->buffer = NULL; } if (printed != NULL) { hooks->deallocate(printed); + printed = NULL; } return NULL; @@ -1289,6 +1295,7 @@ CJSON_PUBLIC(char *) cJSON_PrintBuffered(const cJSON *item, int prebuffer, cJSON if (!print_value(item, &p)) { global_hooks.deallocate(p.buffer); + p.buffer = NULL; return NULL; } @@ -3132,4 +3139,5 @@ CJSON_PUBLIC(void *) cJSON_malloc(size_t size) CJSON_PUBLIC(void) cJSON_free(void *object) { global_hooks.deallocate(object); + object = NULL; } diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index c7592213..9e8962f6 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -62,6 +62,7 @@ if(ENABLE_CJSON_TEST) option(ENABLE_VALGRIND OFF "Enable the valgrind memory checker for the tests.") if (ENABLE_VALGRIND) + add_compile_definitions(ENABLE_VALGRIND) find_program(MEMORYCHECK_COMMAND valgrind) if ("${MEMORYCHECK_COMMAND}" MATCHES "MEMORYCHECK_COMMAND-NOTFOUND") message(WARNING "Valgrind couldn't be found.") diff --git a/tests/misc_tests.c b/tests/misc_tests.c index ba3e003e..94dd91aa 100644 --- a/tests/misc_tests.c +++ b/tests/misc_tests.c @@ -732,6 +732,23 @@ static void cjson_set_bool_value_must_not_break_objects(void) cJSON_Delete(sobj); } +static void deallocated_pointers_should_be_set_to_null(void) +{ + /* deallocated pointers should be set to null */ + /* however, valgrind on linux reports when attempting to access a freed memory, we have to skip it */ +#ifndef ENABLE_VALGRIND + cJSON *string = cJSON_CreateString("item"); + cJSON *root = cJSON_CreateObject(); + + cJSON_Delete(string); + free(string->valuestring); + + cJSON_AddObjectToObject(root, "object"); + cJSON_Delete(root->child); + free(root->child->string); +#endif +} + int CJSON_CDECL main(void) { UNITY_BEGIN(); @@ -762,6 +779,7 @@ int CJSON_CDECL main(void) RUN_TEST(cjson_delete_item_from_array_should_not_broken_list_structure); RUN_TEST(cjson_set_valuestring_to_object_should_not_leak_memory); RUN_TEST(cjson_set_bool_value_must_not_break_objects); + RUN_TEST(deallocated_pointers_should_be_set_to_null); return UNITY_END(); }