osrm-backend/test/unit/fuzz_replace_map.cpp
Siarhei Fedartsou f1087e81ec Squashed 'third_party/unordered_dense/' content from commit 231e48c94
git-subtree-dir: third_party/unordered_dense
git-subtree-split: 231e48c9426bd21c273669e5fdcd042c146975cf
2024-05-30 19:06:16 +02:00

72 lines
2.5 KiB
C++

#include <ankerl/unordered_dense.h>
#include <app/doctest.h>
#include <fuzz/run.h>
#include <unordered_map>
namespace {
template <typename Map>
void replace_map(fuzz::provider p) {
auto counts = counter{};
using map_t = Map;
auto initial_size = p.bounded<size_t>(100);
auto map = map_t{};
for (size_t i = 0; i < initial_size; ++i) {
map.try_emplace(counter::obj{i, counts}, counter::obj{i, counts});
}
// create a container with data in it provided by fuzzer
auto container = typename map_t::value_container_type{};
auto comparison_container = std::vector<std::pair<size_t, size_t>>();
auto v = size_t{};
while (p.has_remaining_bytes()) {
auto key = p.integral<size_t>();
container.emplace_back(counter::obj{key, counts}, counter::obj{v, counts});
comparison_container.emplace_back(key, v);
++v;
}
// create comparison map with the same move-back-forward algorithm
auto comparison_map = std::unordered_map<size_t, size_t>{};
size_t idx = 0;
while (idx != comparison_container.size()) {
auto [key, val] = comparison_container[idx];
if (comparison_map.try_emplace(key, val).second) {
++idx;
} else {
comparison_container[idx] = comparison_container.back();
comparison_container.pop_back();
}
}
map.replace(std::move(container));
// now check if the data in the map is exactly what we expect
REQUIRE(map.size() == comparison_map.size());
for (auto [key, val] : comparison_map) {
auto key_obj = counter::obj{key, counts};
auto val_obj = counter::obj{val, counts};
auto it = map.find(key_obj);
REQUIRE(it != map.end());
REQUIRE(it->first == key_obj);
REQUIRE(it->second == val_obj);
}
}
} // namespace
TEST_CASE("fuzz_replace_map" * doctest::test_suite("fuzz")) {
fuzz::run([](fuzz::provider p) {
replace_map<ankerl::unordered_dense::map<counter::obj, counter::obj>>(p.copy());
replace_map<ankerl::unordered_dense::segmented_map<counter::obj, counter::obj>>(p.copy());
replace_map<ankerl::unordered_dense::map<counter::obj,
counter::obj,
ankerl::unordered_dense::hash<counter::obj>,
std::equal_to<counter::obj>,
std::deque<std::pair<counter::obj, counter::obj>>>>(p.copy());
});
}