fuzz: support std::byte in Consume{Fixed,Variable}LengthByteVector

This commit is contained in:
Pieter Wuille 2023-07-18 16:48:01 -04:00
parent 7d1cd93234
commit bdcbc8594c
3 changed files with 26 additions and 25 deletions

View file

@ -17,15 +17,15 @@ FUZZ_TARGET(crypto_chacha20)
{ {
FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()}; FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()};
const std::vector<unsigned char> key = ConsumeFixedLengthByteVector(fuzzed_data_provider, 32); const auto key = ConsumeFixedLengthByteVector<std::byte>(fuzzed_data_provider, ChaCha20::KEYLEN);
ChaCha20 chacha20{MakeByteSpan(key)}; ChaCha20 chacha20{key};
LIMITED_WHILE(fuzzed_data_provider.ConsumeBool(), 10000) { LIMITED_WHILE(fuzzed_data_provider.ConsumeBool(), 10000) {
CallOneOf( CallOneOf(
fuzzed_data_provider, fuzzed_data_provider,
[&] { [&] {
std::vector<unsigned char> key = ConsumeFixedLengthByteVector(fuzzed_data_provider, 32); auto key = ConsumeFixedLengthByteVector<std::byte>(fuzzed_data_provider, ChaCha20::KEYLEN);
chacha20.SetKey(MakeByteSpan(key)); chacha20.SetKey(key);
}, },
[&] { [&] {
chacha20.Seek( chacha20.Seek(
@ -39,9 +39,9 @@ FUZZ_TARGET(crypto_chacha20)
chacha20.Keystream(MakeWritableByteSpan(output)); chacha20.Keystream(MakeWritableByteSpan(output));
}, },
[&] { [&] {
std::vector<uint8_t> output(fuzzed_data_provider.ConsumeIntegralInRange<size_t>(0, 4096)); std::vector<std::byte> output(fuzzed_data_provider.ConsumeIntegralInRange<size_t>(0, 4096));
const std::vector<uint8_t> input = ConsumeFixedLengthByteVector(fuzzed_data_provider, output.size()); const auto input = ConsumeFixedLengthByteVector<std::byte>(fuzzed_data_provider, output.size());
chacha20.Crypt(MakeByteSpan(input), MakeWritableByteSpan(output)); chacha20.Crypt(input, output);
}); });
} }
} }
@ -60,8 +60,7 @@ template<bool UseCrypt>
void ChaCha20SplitFuzz(FuzzedDataProvider& provider) void ChaCha20SplitFuzz(FuzzedDataProvider& provider)
{ {
// Determine key, iv, start position, length. // Determine key, iv, start position, length.
auto key_bytes = provider.ConsumeBytes<std::byte>(ChaCha20::KEYLEN); auto key_bytes = ConsumeFixedLengthByteVector<std::byte>(provider, ChaCha20::KEYLEN);
key_bytes.resize(ChaCha20::KEYLEN);
uint64_t iv = provider.ConsumeIntegral<uint64_t>(); uint64_t iv = provider.ConsumeIntegral<uint64_t>();
uint32_t iv_prefix = provider.ConsumeIntegral<uint32_t>(); uint32_t iv_prefix = provider.ConsumeIntegral<uint32_t>();
uint64_t total_bytes = provider.ConsumeIntegralInRange<uint64_t>(0, 1000000); uint64_t total_bytes = provider.ConsumeIntegralInRange<uint64_t>(0, 1000000);

View file

@ -14,14 +14,13 @@ FUZZ_TARGET(crypto_poly1305)
{ {
FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()}; FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()};
const std::vector<uint8_t> key = ConsumeFixedLengthByteVector(fuzzed_data_provider, Poly1305::KEYLEN); const auto key = ConsumeFixedLengthByteVector<std::byte>(fuzzed_data_provider, Poly1305::KEYLEN);
const std::vector<uint8_t> in = ConsumeRandomLengthByteVector(fuzzed_data_provider); const auto in = ConsumeRandomLengthByteVector<std::byte>(fuzzed_data_provider);
std::vector<std::byte> tag_out(Poly1305::TAGLEN); std::vector<std::byte> tag_out(Poly1305::TAGLEN);
Poly1305{MakeByteSpan(key)}.Update(MakeByteSpan(in)).Finalize(tag_out); Poly1305{key}.Update(in).Finalize(tag_out);
} }
FUZZ_TARGET(crypto_poly1305_split) FUZZ_TARGET(crypto_poly1305_split)
{ {
FuzzedDataProvider provider{buffer.data(), buffer.size()}; FuzzedDataProvider provider{buffer.data(), buffer.size()};
@ -36,10 +35,10 @@ FUZZ_TARGET(crypto_poly1305_split)
// Process input in pieces. // Process input in pieces.
LIMITED_WHILE(provider.remaining_bytes(), 100) { LIMITED_WHILE(provider.remaining_bytes(), 100) {
auto in = provider.ConsumeRandomLengthString(); auto in = ConsumeRandomLengthByteVector<std::byte>(provider);
poly_split.Update(MakeByteSpan(in)); poly_split.Update(in);
// Update total_input to match what was processed. // Update total_input to match what was processed.
total_input.insert(total_input.end(), MakeByteSpan(in).begin(), MakeByteSpan(in).end()); total_input.insert(total_input.end(), in.begin(), in.end());
} }
// Process entire input at once. // Process entire input at once.

View file

@ -53,12 +53,16 @@ auto& PickValue(FuzzedDataProvider& fuzzed_data_provider, Collection& col)
return *it; return *it;
} }
[[nodiscard]] inline std::vector<uint8_t> ConsumeRandomLengthByteVector(FuzzedDataProvider& fuzzed_data_provider, const std::optional<size_t>& max_length = std::nullopt) noexcept template<typename B = uint8_t>
[[nodiscard]] inline std::vector<B> ConsumeRandomLengthByteVector(FuzzedDataProvider& fuzzed_data_provider, const std::optional<size_t>& max_length = std::nullopt) noexcept
{ {
static_assert(sizeof(B) == 1);
const std::string s = max_length ? const std::string s = max_length ?
fuzzed_data_provider.ConsumeRandomLengthString(*max_length) : fuzzed_data_provider.ConsumeRandomLengthString(*max_length) :
fuzzed_data_provider.ConsumeRandomLengthString(); fuzzed_data_provider.ConsumeRandomLengthString();
return {s.begin(), s.end()}; std::vector<B> ret(s.size());
std::copy(s.begin(), s.end(), reinterpret_cast<char*>(ret.data()));
return ret;
} }
[[nodiscard]] inline std::vector<bool> ConsumeRandomLengthBitVector(FuzzedDataProvider& fuzzed_data_provider, const std::optional<size_t>& max_length = std::nullopt) noexcept [[nodiscard]] inline std::vector<bool> ConsumeRandomLengthBitVector(FuzzedDataProvider& fuzzed_data_provider, const std::optional<size_t>& max_length = std::nullopt) noexcept
@ -209,14 +213,13 @@ inline void SetFuzzedErrNo(FuzzedDataProvider& fuzzed_data_provider) noexcept
* Returns a byte vector of specified size regardless of the number of remaining bytes available * Returns a byte vector of specified size regardless of the number of remaining bytes available
* from the fuzzer. Pads with zero value bytes if needed to achieve the specified size. * from the fuzzer. Pads with zero value bytes if needed to achieve the specified size.
*/ */
[[nodiscard]] inline std::vector<uint8_t> ConsumeFixedLengthByteVector(FuzzedDataProvider& fuzzed_data_provider, const size_t length) noexcept template<typename B = uint8_t>
[[nodiscard]] inline std::vector<B> ConsumeFixedLengthByteVector(FuzzedDataProvider& fuzzed_data_provider, const size_t length) noexcept
{ {
std::vector<uint8_t> result(length); static_assert(sizeof(B) == 1);
const std::vector<uint8_t> random_bytes = fuzzed_data_provider.ConsumeBytes<uint8_t>(length); auto random_bytes = fuzzed_data_provider.ConsumeBytes<B>(length);
if (!random_bytes.empty()) { random_bytes.resize(length);
std::memcpy(result.data(), random_bytes.data(), random_bytes.size()); return random_bytes;
}
return result;
} }
class FuzzedFileProvider class FuzzedFileProvider