Squashed 'external/toxcore/c-toxcore/' changes from 8f0d505f9a..6d634674a9
6d634674a9 cleanup: Remove old type-ordered event getters. d1d48d1dfc feat: add ngc events 994ffecc6b refactor: Make event dispatch ordered by receive time. 812f931d5f fix: Make sure there's enough space for CONSUME1 in fuzzers. 50f1b30fa9 test: Add fuzz tests to the coverage run. df76f5cf47 chore: Move from gcov to llvm source-based coverage. 072e3beb3f fix: issues with packet broadcast error reporting 6b6718e4d2 cleanup: Make group packet entry creation less error-prone 5b9c420ce1 refactor: packet broadcast functions now return errors af4cb31028 refactor: Use `operator==` for equality tests of `Node_format`. 9592d590cf refactor(test): Slightly nicer C++ interface to tox Random. c66e10fb7a refactor: Minor refactoring of get_close_nodes functions. ebc9643862 fix: don't pass garbage data buffer to packet send functions 32b68cffca cleanup: Some more test cleanups, removing overly smart code. 0426624dcb refactor: Assign malloc return to a local variable first. afc38f2458 test: Add more unit tests for `add_to_list`. 05ce5c1ab9 test: Add "infer" CI check to github, remove from circle. REVERT: 8f0d505f9a feat: add ngc events REVERT: 9b8216e70c refactor: Make event dispatch ordered by receive time. git-subtree-dir: external/toxcore/c-toxcore git-subtree-split: 6d634674a929edb0ab70689dcbcb195b3547be13
This commit is contained in:
@ -1,26 +1,33 @@
|
||||
# For coverage tests
|
||||
target_compile_definitions(toxcore_static PUBLIC "FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION")
|
||||
|
||||
# Override network and random functions
|
||||
add_library(fuzz_support func_conversion.h fuzz_support.cc fuzz_support.h)
|
||||
|
||||
set(LIBFUZZER_LINKER_FLAGS)
|
||||
if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
|
||||
if(CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
|
||||
set(LIBFUZZER_LINKER_FLAGS "-fsanitize=fuzzer")
|
||||
else()
|
||||
message(SEND_ERROR "Compiler must be Clang to build fuzz targets")
|
||||
endif()
|
||||
|
||||
function(fuzz_test target source_dir)
|
||||
set(${target}_CORPUS_DIR ${CMAKE_CURRENT_SOURCE_DIR}/toktok-fuzzer/corpus/${target}_fuzz_test)
|
||||
file(GLOB ${target}_fuzz_CORPUS "${${target}_CORPUS_DIR}/*")
|
||||
add_executable(${target}_fuzz_test ${source_dir}/${target}_fuzz_test.cc)
|
||||
target_link_libraries(${target}_fuzz_test PRIVATE toxcore_fuzz fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
if(${target}_fuzz_CORPUS)
|
||||
add_test(NAME ${target}_fuzz COMMAND ${CROSSCOMPILING_EMULATOR} ${target}_fuzz_test -max_total_time=10 ${${target}_fuzz_CORPUS})
|
||||
endif()
|
||||
endfunction()
|
||||
|
||||
# Fuzzes the toxsave API
|
||||
add_executable(toxsave_fuzzer toxsave_harness.cc)
|
||||
target_link_libraries(toxsave_fuzzer PRIVATE toxcore_static fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
target_link_libraries(toxsave_fuzzer PRIVATE toxcore_fuzz fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
|
||||
# Fuzzes the bootstrap process
|
||||
add_executable(bootstrap_fuzzer bootstrap_harness.cc)
|
||||
target_link_libraries(bootstrap_fuzzer PRIVATE toxcore_static fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
target_link_libraries(bootstrap_fuzzer PRIVATE toxcore_fuzz fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
|
||||
add_executable(DHT_fuzz_test ../../toxcore/DHT_fuzz_test.cc)
|
||||
target_link_libraries(DHT_fuzz_test PRIVATE toxcore_static fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
|
||||
add_executable(tox_events_fuzz_test ../../toxcore/tox_events_fuzz_test.cc)
|
||||
target_link_libraries(tox_events_fuzz_test PRIVATE toxcore_static fuzz_support ${LIBFUZZER_LINKER_FLAGS})
|
||||
fuzz_test(DHT ../../toxcore)
|
||||
fuzz_test(forwarding ../../toxcore)
|
||||
fuzz_test(group_announce ../../toxcore)
|
||||
fuzz_test(group_moderation ../../toxcore)
|
||||
fuzz_test(tox_events ../../toxcore)
|
||||
|
@ -126,7 +126,7 @@ void TestBootstrap(Fuzz_Data &input)
|
||||
}
|
||||
});
|
||||
|
||||
CONSUME1_OR_RETURN(const uint8_t proxy_type, input);
|
||||
CONSUME1_OR_RETURN(const uint8_t, proxy_type, input);
|
||||
if (proxy_type == 0) {
|
||||
tox_options_set_proxy_type(opts.get(), TOX_PROXY_TYPE_NONE);
|
||||
} else if (proxy_type == 1) {
|
||||
@ -139,7 +139,7 @@ void TestBootstrap(Fuzz_Data &input)
|
||||
tox_options_set_proxy_port(opts.get(), 8080);
|
||||
}
|
||||
|
||||
CONSUME1_OR_RETURN(const uint8_t tcp_relay_enabled, input);
|
||||
CONSUME1_OR_RETURN(const uint8_t, tcp_relay_enabled, input);
|
||||
if (tcp_relay_enabled >= (UINT8_MAX / 2)) {
|
||||
tox_options_set_tcp_port(opts.get(), 33445);
|
||||
}
|
||||
|
@ -8,6 +8,7 @@
|
||||
#include <fstream>
|
||||
#include <vector>
|
||||
|
||||
#include "../../toxcore/crypto_core.h"
|
||||
#include "../../toxcore/tox.h"
|
||||
#include "../../toxcore/tox_dispatch.h"
|
||||
#include "../../toxcore/tox_events.h"
|
||||
|
@ -30,6 +30,16 @@ struct Network_Addr {
|
||||
size_t size;
|
||||
};
|
||||
|
||||
System::System(std::unique_ptr<Tox_System> in_sys, std::unique_ptr<Memory> in_mem,
|
||||
std::unique_ptr<Network> in_ns, std::unique_ptr<Random> in_rng)
|
||||
: sys(std::move(in_sys))
|
||||
, mem(std::move(in_mem))
|
||||
, ns(std::move(in_ns))
|
||||
, rng(std::move(in_rng))
|
||||
{
|
||||
}
|
||||
System::System(System &&) = default;
|
||||
|
||||
System::~System() { }
|
||||
|
||||
static int recv_common(Fuzz_Data &input, uint8_t *buf, size_t buf_len)
|
||||
@ -67,7 +77,7 @@ static int recv_common(Fuzz_Data &input, uint8_t *buf, size_t buf_len)
|
||||
template <typename F>
|
||||
static void *alloc_common(Fuzz_Data &data, F func)
|
||||
{
|
||||
CONSUME1_OR_RETURN_VAL(const uint8_t want_alloc, data, func());
|
||||
CONSUME1_OR_RETURN_VAL(const uint8_t, want_alloc, data, func());
|
||||
if (!want_alloc) {
|
||||
return nullptr;
|
||||
}
|
||||
|
@ -7,11 +7,12 @@
|
||||
|
||||
#include <cstdint>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <deque>
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
#include <unordered_map>
|
||||
#include <utility>
|
||||
#include <vector>
|
||||
|
||||
#include "../../toxcore/tox.h"
|
||||
|
||||
@ -20,19 +21,28 @@ struct Fuzz_Data {
|
||||
std::size_t size;
|
||||
|
||||
Fuzz_Data(const uint8_t *input_data, std::size_t input_size)
|
||||
: data(input_data), size(input_size)
|
||||
{}
|
||||
: data(input_data)
|
||||
, size(input_size)
|
||||
{
|
||||
}
|
||||
|
||||
Fuzz_Data &operator=(const Fuzz_Data &rhs) = delete;
|
||||
Fuzz_Data(const Fuzz_Data &rhs) = delete;
|
||||
|
||||
uint8_t consume1()
|
||||
{
|
||||
const uint8_t val = data[0];
|
||||
++data;
|
||||
--size;
|
||||
return val;
|
||||
}
|
||||
struct Consumer {
|
||||
Fuzz_Data &fd;
|
||||
|
||||
template <typename T>
|
||||
operator T()
|
||||
{
|
||||
const uint8_t *bytes = fd.consume(sizeof(T));
|
||||
T val;
|
||||
std::memcpy(&val, bytes, sizeof(T));
|
||||
return val;
|
||||
}
|
||||
};
|
||||
|
||||
Consumer consume1() { return Consumer{*this}; }
|
||||
|
||||
const uint8_t *consume(std::size_t count)
|
||||
{
|
||||
@ -50,14 +60,14 @@ struct Fuzz_Data {
|
||||
*
|
||||
* @example
|
||||
* @code
|
||||
* CONSUME1_OR_RETURN(const uint8_t one_byte, input);
|
||||
* CONSUME1_OR_RETURN(const uint8_t, one_byte, input);
|
||||
* @endcode
|
||||
*/
|
||||
#define CONSUME1_OR_RETURN(DECL, INPUT) \
|
||||
if (INPUT.size < 1) { \
|
||||
return; \
|
||||
} \
|
||||
DECL = INPUT.consume1()
|
||||
#define CONSUME1_OR_RETURN(TYPE, NAME, INPUT) \
|
||||
if (INPUT.size < sizeof(TYPE)) { \
|
||||
return; \
|
||||
} \
|
||||
TYPE NAME = INPUT.consume1()
|
||||
|
||||
/** @brief Consumes 1 byte of the fuzzer input or returns a value if no data
|
||||
* available.
|
||||
@ -70,11 +80,11 @@ struct Fuzz_Data {
|
||||
* CONSUME1_OR_RETURN_VAL(const uint8_t one_byte, input, nullptr);
|
||||
* @endcode
|
||||
*/
|
||||
#define CONSUME1_OR_RETURN_VAL(DECL, INPUT, VAL) \
|
||||
if (INPUT.size < 1) { \
|
||||
return VAL; \
|
||||
} \
|
||||
DECL = INPUT.consume1()
|
||||
#define CONSUME1_OR_RETURN_VAL(TYPE, NAME, INPUT, VAL) \
|
||||
if (INPUT.size < sizeof(TYPE)) { \
|
||||
return VAL; \
|
||||
} \
|
||||
TYPE NAME = INPUT.consume1()
|
||||
|
||||
/** @brief Consumes SIZE bytes of the fuzzer input or returns if not enough data available.
|
||||
*
|
||||
@ -93,6 +103,12 @@ struct Fuzz_Data {
|
||||
} \
|
||||
DECL = INPUT.consume(SIZE)
|
||||
|
||||
#define CONSUME_OR_RETURN_VAL(DECL, INPUT, SIZE, VAL) \
|
||||
if (INPUT.size < SIZE) { \
|
||||
return VAL; \
|
||||
} \
|
||||
DECL = INPUT.consume(SIZE)
|
||||
|
||||
inline void fuzz_select_target(uint8_t selector, Fuzz_Data &input)
|
||||
{
|
||||
// The selector selected no function, so we do nothing and rely on the
|
||||
@ -100,7 +116,7 @@ inline void fuzz_select_target(uint8_t selector, Fuzz_Data &input)
|
||||
}
|
||||
|
||||
template <typename Arg, typename... Args>
|
||||
void fuzz_select_target(uint8_t selector, Fuzz_Data &input, Arg &&fn, Args &&... args)
|
||||
void fuzz_select_target(uint8_t selector, Fuzz_Data &input, Arg &&fn, Args &&...args)
|
||||
{
|
||||
if (selector == sizeof...(Args)) {
|
||||
return fn(input);
|
||||
@ -109,11 +125,11 @@ void fuzz_select_target(uint8_t selector, Fuzz_Data &input, Arg &&fn, Args &&...
|
||||
}
|
||||
|
||||
template <typename... Args>
|
||||
void fuzz_select_target(const uint8_t *data, std::size_t size, Args &&... args)
|
||||
void fuzz_select_target(const uint8_t *data, std::size_t size, Args &&...args)
|
||||
{
|
||||
Fuzz_Data input{data, size};
|
||||
|
||||
CONSUME1_OR_RETURN(uint8_t selector, input);
|
||||
CONSUME1_OR_RETURN(const uint8_t, selector, input);
|
||||
return fuzz_select_target(selector, input, std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
@ -127,6 +143,10 @@ struct System {
|
||||
std::unique_ptr<Network> ns;
|
||||
std::unique_ptr<Random> rng;
|
||||
|
||||
System(std::unique_ptr<Tox_System> sys, std::unique_ptr<Memory> mem,
|
||||
std::unique_ptr<Network> ns, std::unique_ptr<Random> rng);
|
||||
System(System &&);
|
||||
|
||||
// Not inline because sizeof of the above 2 structs is not known everywhere.
|
||||
~System();
|
||||
|
||||
|
@ -1,96 +1,17 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
* Copyright © 2022 The TokTok team.
|
||||
* Copyright © 2022-2024 The TokTok team.
|
||||
*/
|
||||
|
||||
#ifndef C_TOXCORE_TESTING_FUZZING_FUZZ_TOX_H
|
||||
#define C_TOXCORE_TESTING_FUZZING_FUZZ_TOX_H
|
||||
|
||||
#include <cassert>
|
||||
#include <memory>
|
||||
|
||||
#include "../../toxcore/DHT.h"
|
||||
#include "../../toxcore/logger.h"
|
||||
#include "../../toxcore/network.h"
|
||||
#include "fuzz_support.h"
|
||||
|
||||
constexpr uint16_t SIZE_IP_PORT = SIZE_IP6 + sizeof(uint16_t);
|
||||
|
||||
template <typename T>
|
||||
using Ptr = std::unique_ptr<T, void (*)(T *)>;
|
||||
|
||||
/** @brief Construct any Tox resource using fuzzer input data.
|
||||
*
|
||||
* Constructs (or fails by returning) a valid object of type T and passes it to
|
||||
* a function specified on the rhs of `>>`. Takes care of cleaning up the
|
||||
* resource after the specified function returns.
|
||||
*
|
||||
* Some `with` instances require additional inputs such as the `Fuzz_Data`
|
||||
* reference or a logger.
|
||||
*/
|
||||
template <typename T>
|
||||
struct with;
|
||||
|
||||
/** @brief Construct a Logger without logging callback.
|
||||
*/
|
||||
template <>
|
||||
struct with<Logger> {
|
||||
template <typename F>
|
||||
void operator>>(F &&f)
|
||||
{
|
||||
Ptr<Logger> logger(logger_new(), logger_kill);
|
||||
assert(logger != nullptr);
|
||||
f(std::move(logger));
|
||||
}
|
||||
};
|
||||
|
||||
/** @brief Construct an IP_Port by unpacking fuzzer input with `unpack_ip_port`.
|
||||
*/
|
||||
template <>
|
||||
struct with<IP_Port> {
|
||||
Fuzz_Data &input_;
|
||||
|
||||
template <typename F>
|
||||
void operator>>(F &&f)
|
||||
{
|
||||
CONSUME_OR_RETURN(const uint8_t *ipp_packed, input_, SIZE_IP_PORT);
|
||||
IP_Port ipp;
|
||||
unpack_ip_port(&ipp, ipp_packed, SIZE_IP6, true);
|
||||
|
||||
f(ipp);
|
||||
}
|
||||
};
|
||||
|
||||
/** @brief Construct a Networking_Core object using the Network vtable passed.
|
||||
*
|
||||
* Use `with<Logger>{} >> with<Networking_Core>{input, ns, mem} >> ...` to construct
|
||||
* a logger and pass it to the Networking_Core constructor function.
|
||||
*/
|
||||
template <>
|
||||
struct with<Networking_Core> {
|
||||
Fuzz_Data &input_;
|
||||
const Network *ns_;
|
||||
const Memory *mem_;
|
||||
Ptr<Logger> logger_{nullptr, logger_kill};
|
||||
|
||||
friend with operator>>(with<Logger> f, with self)
|
||||
{
|
||||
f >> [&self](Ptr<Logger> logger) { self.logger_ = std::move(logger); };
|
||||
return self;
|
||||
}
|
||||
|
||||
template <typename F>
|
||||
void operator>>(F &&f)
|
||||
{
|
||||
with<IP_Port>{input_} >> [&f, this](const IP_Port &ipp) {
|
||||
Ptr<Networking_Core> net(
|
||||
new_networking_ex(logger_.get(), mem_, ns_, &ipp.ip, ipp.port, ipp.port + 100, nullptr),
|
||||
kill_networking);
|
||||
if (net == nullptr) {
|
||||
return;
|
||||
}
|
||||
f(std::move(net));
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
#endif // C_TOXCORE_TESTING_FUZZING_FUZZ_TOX_H
|
||||
|
@ -1,6 +1,7 @@
|
||||
#include <cassert>
|
||||
#include <cstdio>
|
||||
|
||||
#include "../../toxcore/crypto_core.h"
|
||||
#include "../../toxcore/tox.h"
|
||||
#include "../../toxcore/tox_dispatch.h"
|
||||
#include "../../toxcore/tox_events.h"
|
||||
|
Reference in New Issue
Block a user