Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

LFI detector fuzzer #274

Merged
merged 4 commits into from
Mar 27, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .github/workflows/fuzz.yml
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ jobs:
variant:
- uri_parse
- ssrf_detector
- lfi_detector
steps:
- uses: actions/checkout@v4
with:
Expand All @@ -86,4 +87,4 @@ jobs:
- name: Run fuzzer
run: |
cd fuzzer/${{ matrix.variant }}
./${{ matrix.variant }}_fuzzer -max_total_time=${{ github.event.inputs.duration || 60 }} corpus/
./${{ matrix.variant }}_fuzzer -max_total_time=${{ github.event.inputs.duration || 300 }} corpus/
Binary file added fuzzer/lfi_detector/corpus/corpus-0000
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0001
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0002
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0003
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0004
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0005
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0006
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0007
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0008
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0009
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0010
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0011
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0012
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0013
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0014
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0015
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0016
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0017
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0018
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0019
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0020
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0021
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0022
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0024
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0025
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0026
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0027
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0028
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0029
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0030
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0031
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0032
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0033
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0034
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0035
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0036
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0037
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0038
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0039
Binary file not shown.
Binary file added fuzzer/lfi_detector/corpus/corpus-0040
Binary file not shown.
131 changes: 131 additions & 0 deletions fuzzer/lfi_detector/src/main.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
// Unless explicitly stated otherwise all files in this repository are
// dual-licensed under the Apache-2.0 License or BSD-3-Clause License.
//
// This product includes software developed at Datadog (https://www.datadoghq.com/).
// Copyright 2021 Datadog, Inc.

#include <cstdint>

#include "condition/lfi_detector.hpp"

using namespace ddwaf;
using namespace std::literals;

extern "C" size_t LLVMFuzzerMutate(uint8_t *Data, size_t Size, size_t MaxSize);

extern "C" int LLVMFuzzerInitialize(const int * /*argc*/, char *** /*argv*/)
{
ddwaf::memory::set_local_memory_resource(std::pmr::new_delete_resource());
return 0;
}

template <typename... Args> std::vector<parameter_definition> gen_param_def(Args... addresses)
{
return {{{{std::string{addresses}, get_target_index(addresses)}}}...};
}

// NOLINTBEGIN(cppcoreguidelines-pro-type-reinterpret-cast)
std::pair<std::string_view, std::string_view> deserialize(const uint8_t *data, size_t size)
{
if (size < sizeof(std::size_t)) {
return {};
}

const auto resource_size = *reinterpret_cast<const std::size_t *>(data);
data += sizeof(std::size_t);
size -= sizeof(std::size_t);

if (size < resource_size) {
return {};
}

std::string_view resource{reinterpret_cast<const char *>(data), resource_size};
data += resource_size;
size -= resource_size;

if (size < sizeof(std::size_t)) {
return {};
}

const auto param_size = *reinterpret_cast<const std::size_t *>(data);
data += sizeof(std::size_t);
size -= sizeof(std::size_t);

if (size < param_size) {
return {};
}

std::string_view param{reinterpret_cast<const char *>(data), param_size};

return {resource, param};
}

uint8_t *serialize_string(uint8_t *Data, const std::vector<char> &str)
{
std::size_t size = str.size();
memcpy(Data, reinterpret_cast<uint8_t *>(&size), sizeof(std::size_t));
Data += sizeof(std::size_t);
memcpy(Data, str.data(), size);
Data += size;
return Data;
}

void serialize(uint8_t *Data, const std::vector<char> &resource, const std::vector<char> &param)
{
Data = serialize_string(Data, resource);
serialize_string(Data, param);
}
// NOLINTEND(cppcoreguidelines-pro-type-reinterpret-cast)

// NOLINTNEXTLINE
extern "C" size_t LLVMFuzzerCustomMutator(
uint8_t *Data, size_t Size, [[maybe_unused]] size_t MaxSize, [[maybe_unused]] unsigned int Seed)
{
auto [resource, param] = deserialize(Data, Size);

MaxSize -= sizeof(std::size_t) * 2;

std::vector<char> resource_buffer{resource.begin(), resource.end()};
resource_buffer.resize(resource_buffer.size() + MaxSize / 2);

// NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
auto new_size = LLVMFuzzerMutate(reinterpret_cast<uint8_t *>(resource_buffer.data()),
resource.size(), resource_buffer.size());
resource_buffer.resize(new_size);

std::vector<char> param_buffer{resource.begin(), resource.end()};
param_buffer.resize(resource_buffer.size() + MaxSize / 2);

// NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast)
new_size = LLVMFuzzerMutate(
reinterpret_cast<uint8_t *>(param_buffer.data()), resource.size(), resource_buffer.size());
param_buffer.resize(new_size);

serialize(Data, resource_buffer, param_buffer);

return Size;
}

extern "C" int LLVMFuzzerTestOneInput(const uint8_t *bytes, size_t size)
{
lfi_detector cond{{gen_param_def("server.io.fs.file", "server.request.query")}};

auto [resource, param] = deserialize(bytes, size);

ddwaf_object root;
ddwaf_object tmp;
ddwaf_object_map(&root);
ddwaf_object_map_add(
&root, "server.io.fs.file", ddwaf_object_stringl(&tmp, resource.data(), resource.size()));
ddwaf_object_map_add(
&root, "server.request.query", ddwaf_object_stringl(&tmp, param.data(), param.size()));

object_store store;
store.insert(root);

ddwaf::timer deadline{2s};
condition_cache cache;
(void)cond.eval(cache, store, {}, {}, deadline);

return 0;
}
Binary file added fuzzer/ssrf_detector/corpus/corpus-0091
Binary file not shown.
Binary file added fuzzer/ssrf_detector/corpus/corpus-0092
Binary file not shown.
Binary file added fuzzer/ssrf_detector/corpus/corpus-0093
Binary file not shown.
Binary file added fuzzer/ssrf_detector/corpus/corpus-0094
Binary file not shown.