Merge pull request #728 from simdjson/jkeiser/cmake-fuzz-noexceptions

Compile fuzzers without exceptions, run as part of tests
This commit is contained in:
John Keiser 2020-04-23 10:13:33 -07:00 committed by GitHub
commit 587ba9bec0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 125 additions and 140 deletions

View File

@ -118,7 +118,7 @@ jobs:
sanitize-gcc9: sanitize-gcc9:
description: Build and run tests on GCC 9 and AVX 2 with a cmake sanitize build description: Build and run tests on GCC 9 and AVX 2 with a cmake sanitize build
executor: gcc9 executor: gcc9
environment: { CMAKE_FLAGS: -DSIMDJSON_BUILD_STATIC=OFF -DSIMDJSON_SANITIZE=ON, CTEST_FLAGS: -j4 --output-on-failure -E checkperf } environment: { CMAKE_FLAGS: -DSIMDJSON_BUILD_STATIC=OFF -DSIMDJSON_SANITIZE=ON, BUILD_FLAGS: "", CTEST_FLAGS: -j4 --output-on-failure -E checkperf }
steps: [ install_cmake, cmake_test_all ] steps: [ install_cmake, cmake_test_all ]
sanitize-clang6: sanitize-clang6:
description: Build and run tests on clang 6 and AVX 2 with a cmake sanitize build description: Build and run tests on clang 6 and AVX 2 with a cmake sanitize build

View File

@ -182,12 +182,7 @@ add_subdirectory(dependencies)
add_subdirectory(tests) add_subdirectory(tests)
add_subdirectory(examples) add_subdirectory(examples)
add_subdirectory(benchmark) add_subdirectory(benchmark)
# for fuzzing, read the comments in the fuzz/CMakeLists.txt file
option(ENABLE_FUZZING "enable building the fuzzers" ON)
if(ENABLE_FUZZING AND SIMDJSON_EXCEPTIONS)
add_subdirectory(fuzz) add_subdirectory(fuzz)
endif()
# #
# CPack # CPack

View File

@ -1,3 +1,7 @@
option(ENABLE_FUZZING "enable building the fuzzers" ON)
if(ENABLE_FUZZING)
# First attempt at a fuzzer, using libFuzzer. # First attempt at a fuzzer, using libFuzzer.
# #
# compile like this: # compile like this:
@ -11,7 +15,6 @@
# cmake .. -GNinja -DCMAKE_BUILD_TYPE=Debug -DENABLE_FUZZING=On -DSIMDJSON_FUZZ_LINKMAIN=Off -DSIMDJSON_FUZZ_LDFLAGS=-fsanitize=fuzzer # cmake .. -GNinja -DCMAKE_BUILD_TYPE=Debug -DENABLE_FUZZING=On -DSIMDJSON_FUZZ_LINKMAIN=Off -DSIMDJSON_FUZZ_LDFLAGS=-fsanitize=fuzzer
# ninja # ninja
# settings this links in a main. useful for reproducing, # settings this links in a main. useful for reproducing,
# kcov, gdb, afl, valgrind. # kcov, gdb, afl, valgrind.
# (note that libFuzzer can also reproduce, just pass it the files) # (note that libFuzzer can also reproduce, just pass it the files)
@ -25,32 +28,32 @@ option(SIMDJSON_FUZZ_LINKMAIN "links a main into fuzz targets for building repro
# the fuzz targets, otherwise the cmake configuration step fails. # the fuzz targets, otherwise the cmake configuration step fails.
set(SIMDJSON_FUZZ_LDFLAGS "" CACHE STRING "LDFLAGS for the fuzz targets") set(SIMDJSON_FUZZ_LDFLAGS "" CACHE STRING "LDFLAGS for the fuzz targets")
set(SOURCES
fuzz_parser.cpp
fuzz_minify.cpp
fuzz_dump.cpp
fuzz_print_json.cpp
fuzz_dump_raw_tape.cpp
)
add_custom_target(print_all_fuzz_targets add_custom_target(print_all_fuzz_targets
COMMAND ${CMAKE_COMMAND} -E echo ${SOURCES} COMMAND ${CMAKE_COMMAND} -E echo ${SOURCES}
) )
macro(implement_fuzzer sourcefile) # Fuzzer build flags and libraries
get_filename_component(basename ${sourcefile} NAME_WE) add_library(simdjson-fuzzer INTERFACE)
set(name ${basename})
add_executable(${name} ${sourcefile})
if (SIMDJSON_FUZZ_LINKMAIN) if (SIMDJSON_FUZZ_LINKMAIN)
target_sources(${name} PRIVATE main.cpp) target_link_libraries(simdjson-fuzzer INTERFACE simdjson-source)
target_sources(simdjson-fuzzer INTERFACE $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>/main.cpp)
else ()
target_link_libraries(simdjson-fuzzer INTERFACE simdjson)
endif () endif ()
target_link_libraries(${name} PRIVATE simdjson simdjson-flags) target_link_libraries(simdjson-fuzzer INTERFACE simdjson-flags)
if (SIMDJSON_FUZZ_LDFLAGS) target_link_libraries(simdjson-fuzzer INTERFACE ${SIMDJSON_FUZZ_LDFLAGS})
target_link_libraries(${name} PRIVATE ${SIMDJSON_FUZZ_LDFLAGS})
function(implement_fuzzer name)
add_executable(${name} ${name}.cpp)
target_link_libraries(${name} PRIVATE simdjson-fuzzer)
add_test(${name} ${name})
set_property(TEST ${name} APPEND PROPERTY LABELS fuzz)
endfunction()
implement_fuzzer(fuzz_parser)
implement_fuzzer(fuzz_minify)
implement_fuzzer(fuzz_dump)
implement_fuzzer(fuzz_print_json)
implement_fuzzer(fuzz_dump_raw_tape)
endif() endif()
endmacro ()
foreach (X IN ITEMS ${SOURCES})
implement_fuzzer(${X})
endforeach ()

View File

@ -9,12 +9,11 @@
// example from doc/basics.md#tree-walking-and-json-element-types // example from doc/basics.md#tree-walking-and-json-element-types
static void print_json(std::ostream& os, simdjson::dom::element element) { static void print_json(std::ostream& os, simdjson::dom::element element) {
#if SIMDJSON_EXCEPTIONS
const char endl='\n'; const char endl='\n';
switch (element.type()) { switch (element.type()) {
case simdjson::dom::element_type::ARRAY: case simdjson::dom::element_type::ARRAY:
os << "["; os << "[";
for (simdjson::dom::element child : simdjson::dom::array(element)) { for (simdjson::dom::element child : element.get<simdjson::dom::array>().first) {
print_json(os, child); print_json(os, child);
os << ","; os << ",";
} }
@ -22,44 +21,41 @@ static void print_json(std::ostream& os, simdjson::dom::element element) {
break; break;
case simdjson::dom::element_type::OBJECT: case simdjson::dom::element_type::OBJECT:
os << "{"; os << "{";
for (simdjson::dom::key_value_pair field : simdjson::dom::object(element)) { for (simdjson::dom::key_value_pair field : element.get<simdjson::dom::object>().first) {
os << "\"" << field.key << "\": "; os << "\"" << field.key << "\": ";
print_json(os, field.value); print_json(os, field.value);
} }
os << "}"; os << "}";
break; break;
case simdjson::dom::element_type::INT64: case simdjson::dom::element_type::INT64:
os << int64_t(element) << endl; os << element.get<int64_t>().first << endl;
break; break;
case simdjson::dom::element_type::UINT64: case simdjson::dom::element_type::UINT64:
os << uint64_t(element) << endl; os << element.get<uint64_t>().first << endl;
break; break;
case simdjson::dom::element_type::DOUBLE: case simdjson::dom::element_type::DOUBLE:
os << double(element) << endl; os << element.get<double>().first << endl;
break; break;
case simdjson::dom::element_type::STRING: case simdjson::dom::element_type::STRING:
os << std::string_view(element) << endl; os << element.get<std::string_view>().first << endl;
break; break;
case simdjson::dom::element_type::BOOL: case simdjson::dom::element_type::BOOL:
os << bool(element) << endl; os << element.get<bool>().first << endl;
break; break;
case simdjson::dom::element_type::NULL_VALUE: case simdjson::dom::element_type::NULL_VALUE:
os << "null" << endl; os << "null" << endl;
break; break;
} }
#endif
} }
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
#if SIMDJSON_EXCEPTIONS simdjson::dom::parser parser;
try { simdjson::error_code error;
simdjson::dom::parser pj; simdjson::dom::element elem;
auto elem=pj.parse(Data, Size); parser.parse(Data, Size).tie(elem, error);
auto v=elem.value();
if (error) { return 1; }
NulOStream os; NulOStream os;
//std::ostream& os(std::cout); //std::ostream& os(std::cout);
print_json(os,v); print_json(os,elem);
} catch (...) {
}
#endif
return 0; return 0;
} }

View File

@ -7,15 +7,13 @@
#include "NullBuffer.h" #include "NullBuffer.h"
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
#if SIMDJSON_EXCEPTIONS simdjson::dom::parser parser;
try { simdjson::error_code error;
simdjson::dom::parser pj; simdjson::dom::element elem;
auto elem=pj.parse(Data, Size); parser.parse(Data, Size).tie(elem, error);
auto v=elem.value(); if (error) { return 1; }
NulOStream os; NulOStream os;
UNUSED auto dumpstatus=v.dump_raw_tape(os); UNUSED auto dumpstatus = elem.dump_raw_tape(os);
} catch (...) {
}
#endif
return 0; return 0;
} }

View File

@ -8,15 +8,13 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
auto end = begin + Size; auto end = begin + Size;
std::string str(begin, end); std::string str(begin, end);
#if SIMDJSON_EXCEPTIONS
try {
simdjson::dom::parser parser; simdjson::dom::parser parser;
simdjson::dom::element doc = parser.parse(str); simdjson::error_code error;
std::string minified=simdjson::minify(doc); simdjson::dom::element elem;
(void)minified; parser.parse(str).tie(elem, error);
} catch (...) { if (error) { return 1; }
} std::string minified=simdjson::minify(elem);
#endif (void)minified;
return 0; return 0;
} }

View File

@ -3,13 +3,9 @@
#include <cstdint> #include <cstdint>
#include <string> #include <string>
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
#if SIMDJSON_EXCEPTIONS simdjson::dom::parser parser;
try { UNUSED simdjson::error_code error;
simdjson::dom::parser pj; UNUSED simdjson::dom::element elem;
auto result=pj.parse(Data, Size); parser.parse(Data, Size).tie(elem, error);
UNUSED auto v=result.value();
}catch(...) {
}
#endif
return 0; return 0;
} }

View File

@ -7,14 +7,13 @@
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
#if SIMDJSON_EXCEPTIONS simdjson::dom::parser parser;
try { simdjson::error_code error;
simdjson::dom::parser pj; simdjson::dom::element elem;
auto elem=pj.parse(Data, Size); parser.parse(Data, Size).tie(elem, error);
if (!error) {
NulOStream os; NulOStream os;
os<<elem; os<<elem;
} catch (...) {
} }
#endif
return 0; return 0;
} }