]> git.ipfire.org Git - thirdparty/json-c.git/commitdiff
Add fuzz tests for json_object/point/array apis 883/head
authorSimon Resch <simon.resch@code-intelligence.de>
Sat, 9 Nov 2024 03:20:40 +0000 (22:20 -0500)
committerSimon Resch <simon.resch@code-intelligence.de>
Fri, 22 Nov 2024 06:43:32 +0000 (07:43 +0100)
Extends the coverage of fuzz tests executed in OSS-Fuzz.

fuzz/json_array_fuzzer.cc [new file with mode: 0644]
fuzz/json_array_fuzzer.dict [new file with mode: 0644]
fuzz/json_object_fuzzer.cc [new file with mode: 0644]
fuzz/json_object_fuzzer.dict [new file with mode: 0644]
fuzz/json_pointer_fuzzer.cc [new file with mode: 0644]
fuzz/json_pointer_fuzzer.dict [new file with mode: 0644]
fuzz/tokener_parse_ex_fuzzer.dict

diff --git a/fuzz/json_array_fuzzer.cc b/fuzz/json_array_fuzzer.cc
new file mode 100644 (file)
index 0000000..999cd82
--- /dev/null
@@ -0,0 +1,27 @@
+#include <fuzzer/FuzzedDataProvider.h>
+
+#include "json.h"
+
+extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
+       FuzzedDataProvider fdp(data, size);
+       json_object *my_array = json_object_new_array();
+       for (int i = 0; i < 3; ++i) {
+               json_object *jso = json_tokener_parse(fdp.ConsumeRandomLengthString(10).c_str());
+               if (jso == NULL) {
+                       continue;
+               }
+               json_object_array_add(my_array, jso);
+       }
+       json_object_array_insert_idx(my_array, fdp.ConsumeIntegralInRange<size_t>(0, 10),
+                                    json_object_new_int(fdp.ConsumeIntegral<int>()));
+       json_object_array_get_idx(my_array, fdp.ConsumeIntegralInRange<size_t>(0, 10));
+       json_object_array_put_idx(my_array, fdp.ConsumeIntegralInRange<size_t>(0, 10),
+                                 json_object_new_int(fdp.ConsumeIntegral<int>()));
+       json_object_array_del_idx(my_array, fdp.ConsumeIntegralInRange<size_t>(0, 10),
+                                 fdp.ConsumeIntegralInRange<size_t>(0, 10));
+       json_object_array_shrink(my_array, fdp.ConsumeIntegralInRange<size_t>(0, 10));
+       json_object_array_sort(my_array, [](const void *a, const void *b) { return 0; });
+       json_object_array_length(my_array);
+       json_object_put(my_array);
+       return 0;
+}
diff --git a/fuzz/json_array_fuzzer.dict b/fuzz/json_array_fuzzer.dict
new file mode 100644 (file)
index 0000000..ad4e77b
--- /dev/null
@@ -0,0 +1,21 @@
+"{"
+"}"
+","
+"["
+"]"
+","
+":"
+"e"
+"e+"
+"e-"
+"E"
+"E+"
+"E-"
+"\""
+"null"
+"1"
+"1.234"
+"3e4"
+"NaN"
+"Infinity"
+"-Infinity"
diff --git a/fuzz/json_object_fuzzer.cc b/fuzz/json_object_fuzzer.cc
new file mode 100644 (file)
index 0000000..5a697e8
--- /dev/null
@@ -0,0 +1,44 @@
+#include <fuzzer/FuzzedDataProvider.h>
+
+#include "json.h"
+#include "json_visit.h"
+
+// Function to test json_c_visit
+static int emit_object(json_object *jso, int flags, json_object *parent_jso, const char *jso_key,
+                       size_t *jso_index, void *userarg) {
+       return JSON_C_VISIT_RETURN_CONTINUE;
+}
+
+extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
+       FuzzedDataProvider fdp(data, size);
+       json_object *jso = json_tokener_parse(fdp.ConsumeRandomLengthString(20).c_str());
+
+       json_object_get_boolean(jso);
+       json_object_get_double(jso);
+       json_object_get_int(jso);
+       json_object_get_int64(jso);
+       json_object_get_uint64(jso);
+       json_object_get_string(jso);
+       json_object_get_string_len(jso);
+       json_object_get_object(jso);
+       json_object_get_array(jso);
+       json_object_get_type(jso);
+
+       json_c_visit(jso, 0, emit_object, NULL);
+
+       json_object_set_int(jso, fdp.ConsumeIntegral<int>());
+       json_object_set_int64(jso, fdp.ConsumeIntegral<int64_t>());
+       json_object_set_uint64(jso, fdp.ConsumeIntegral<uint64_t>());
+       json_object_set_double(jso, fdp.ConsumeFloatingPoint<double>());
+       json_object_set_string(jso, fdp.ConsumeRandomLengthString(10).c_str());
+       json_object_set_boolean(jso, fdp.ConsumeBool());
+       std::string str = fdp.ConsumeRandomLengthString(10);
+       json_object_set_string_len(jso, str.c_str(), str.size());
+
+       json_object *dst = NULL;
+       json_object_deep_copy(jso, &dst, json_c_shallow_copy_default);
+       json_object_put(dst);
+
+       json_object_put(jso);
+       return 0;
+}
diff --git a/fuzz/json_object_fuzzer.dict b/fuzz/json_object_fuzzer.dict
new file mode 100644 (file)
index 0000000..ad4e77b
--- /dev/null
@@ -0,0 +1,21 @@
+"{"
+"}"
+","
+"["
+"]"
+","
+":"
+"e"
+"e+"
+"e-"
+"E"
+"E+"
+"E-"
+"\""
+"null"
+"1"
+"1.234"
+"3e4"
+"NaN"
+"Infinity"
+"-Infinity"
diff --git a/fuzz/json_pointer_fuzzer.cc b/fuzz/json_pointer_fuzzer.cc
new file mode 100644 (file)
index 0000000..809a147
--- /dev/null
@@ -0,0 +1,53 @@
+#include <fuzzer/FuzzedDataProvider.h>
+
+#include "json.h"
+
+extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
+       FuzzedDataProvider fdp(data, size);
+
+       struct json_tokener *tokener =
+           json_tokener_new_ex(fdp.ConsumeIntegralInRange<int>(1, JSON_TOKENER_DEFAULT_DEPTH));
+       int flags = 0;
+       if (fdp.ConsumeBool()) {
+               flags |= JSON_TOKENER_VALIDATE_UTF8;
+       }
+       if (fdp.ConsumeBool()) {
+               flags |= JSON_TOKENER_ALLOW_TRAILING_CHARS;
+       }
+       if (fdp.ConsumeBool()) {
+               flags |= JSON_TOKENER_STRICT;
+       }
+       json_tokener_set_flags(tokener, flags);
+
+       std::string path = fdp.ConsumeRandomLengthString(5);
+       std::string sub_json_str = fdp.ConsumeRandomLengthString(10);
+       bool use_format_string = fdp.ConsumeBool();
+       std::string json_str = fdp.ConsumeRemainingBytesAsString();
+
+       struct json_object *jo1 = json_tokener_parse_ex(tokener, json_str.c_str(), json_str.size());
+
+       struct json_object *sub_json = json_tokener_parse(sub_json_str.c_str());
+       if (sub_json == NULL) {
+               sub_json = json_object_new_object();
+       }
+
+       struct json_object *jo2 = NULL;
+       if (use_format_string) {
+               json_pointer_getf(jo1, &jo2, "%s", path.c_str());
+               if (json_pointer_setf(&jo1, sub_json, "%s", path.c_str()))
+               {
+                       json_object_put(sub_json);
+               }
+       } else {
+               json_pointer_get(jo1, path.c_str(), &jo2);
+               if (json_pointer_set(&jo1, path.c_str(), sub_json))
+               {
+                       json_object_put(sub_json);
+               }
+       }
+
+       // Clean up the main JSON object
+       json_object_put(jo1);
+       json_tokener_free(tokener);
+       return 0;
+}
diff --git a/fuzz/json_pointer_fuzzer.dict b/fuzz/json_pointer_fuzzer.dict
new file mode 100644 (file)
index 0000000..ad4e77b
--- /dev/null
@@ -0,0 +1,21 @@
+"{"
+"}"
+","
+"["
+"]"
+","
+":"
+"e"
+"e+"
+"e-"
+"E"
+"E+"
+"E-"
+"\""
+"null"
+"1"
+"1.234"
+"3e4"
+"NaN"
+"Infinity"
+"-Infinity"
index 23c6fa2c164b728399e2d9e85e74c139f9b6c946..ad4e77b5290d978a9630b0e12172ddac7a55268e 100644 (file)
@@ -16,3 +16,6 @@
 "1"
 "1.234"
 "3e4"
+"NaN"
+"Infinity"
+"-Infinity"