All tests should give some portion of data to the producer and use the rest.

This commit is contained in:
Dario Pavlovic 2019-09-10 16:52:38 -07:00
parent 4dfc1bbf48
commit 23cc2d8510
8 changed files with 50 additions and 32 deletions

View File

@ -52,9 +52,13 @@ static size_t roundTripTest(void *result, size_t resultCapacity,
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
int cLevel = FUZZ_dataProducer_uint32(producer) % kMaxClevel;
size = FUZZ_dataProducer_remainingBytes(producer);
size_t neededBufSize = size;
if (size > ZSTD_BLOCKSIZE_MAX)

View File

@ -24,7 +24,12 @@ static ZSTD_DCtx *dctx = NULL;
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
FUZZ_dict_t dict;
ZSTD_DDict* ddict = NULL;
int i;
@ -43,8 +48,8 @@ int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
(ZSTD_dictLoadMethod_e)FUZZ_dataProducer_uint32Range(producer, 0, 1),
(ZSTD_dictContentType_e)FUZZ_dataProducer_uint32Range(producer, 0, 2)));
}
/* Run it 10 times over 10 output sizes. Reuse the context and dict. */
for (i = 0; i < 10; ++i) {
{
size_t const bufSize = FUZZ_dataProducer_uint32Range(producer, 0, 2 * size);
void* rBuf = malloc(bufSize);
FUZZ_ASSERT(rBuf);

View File

@ -68,13 +68,16 @@ static size_t roundTripTest(void *result, size_t resultCapacity,
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
size_t const rBufSize = size;
void* rBuf = malloc(rBufSize);
size_t cBufSize = ZSTD_compressBound(size);
void* cBuf;
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
void *cBuf;
/* Half of the time fuzz with a 1 byte smaller output size.
* This will still succeed because we force the checksum to be disabled,
* giving us 4 bytes of overhead.

View File

@ -24,14 +24,17 @@ static ZSTD_CCtx *cctx = NULL;
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
int const level = (int)FUZZ_dataProducer_uint32Range(
producer, 0, 19 + 3) - 3; /* [-3, 19] */
size_t const maxSize = ZSTD_compressBound(size);
size_t const bufSize = FUZZ_dataProducer_uint32Range(producer, 0, maxSize);
size = FUZZ_dataProducer_remainingBytes(producer);
int const level = (int)FUZZ_dataProducer_uint32Range(
producer, 0, 19 + 3) - 3; /* [-3, 19] */
if (!cctx) {
cctx = ZSTD_createCCtx();

View File

@ -23,7 +23,11 @@ static ZSTD_DCtx *dctx = NULL;
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
if (!dctx) {
dctx = ZSTD_createDCtx();
@ -34,10 +38,6 @@ int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
void *rBuf = malloc(bufSize);
FUZZ_ASSERT(rBuf);
/* Restrict to remaining data. If we run out of data while generating params,
we should still continue and let decompression happen on empty data. */
size = FUZZ_dataProducer_remainingBytes(producer);
ZSTD_decompressDCtx(dctx, rBuf, bufSize, src, size);
free(rBuf);

View File

@ -52,12 +52,19 @@ int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
size_t cBufSize = ZSTD_compressBound(size);
void* cBuf;
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
/* Half of the time fuzz with a 1 byte smaller output size.
* This will still succeed because we don't use a dictionary, so the dictID
* field is empty, giving us 4 bytes of overhead.
*/
cBufSize -= FUZZ_dataProducer_uint32Range(producer, 0, 1);
size = FUZZ_dataProducer_remainingBytes(producer);
cBuf = malloc(cBufSize);
FUZZ_ASSERT(cBuf && rBuf);

View File

@ -125,15 +125,15 @@ static size_t compress(uint8_t *dst, size_t capacity,
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
size_t neededBufSize;
neededBufSize = ZSTD_compressBound(size) * 5;
/* Give a random portion of src data to the producer, to use for
parameter generation. The rest will be used for (de)compression */
FUZZ_dataProducer_t *producer = FUZZ_dataProducer_create(src, size);
size_t producerSliceSize = FUZZ_dataProducer_uint32Range(producer, 0, size);
size = FUZZ_dataProducer_contract(producer, producerSliceSize);
size_t neededBufSize;
neededBufSize = ZSTD_compressBound(size) * 5;
/* Allocate all buffers and contexts if not already allocated */
if (neededBufSize > bufSize) {
free(cBuf);

View File

@ -21,10 +21,6 @@
int LLVMFuzzerTestOneInput(const uint8_t *src, size_t size)
{
ZSTD_frameHeader zfh;
/* Consume the seed to be compatible with the corpora of other decompression
* fuzzers.
*/
FUZZ_seed(&src, &size);
/* You can fuzz any helper functions here that are fast, and take zstd
* compressed data as input. E.g. don't expect the input to be a dictionary,
* so don't fuzz ZSTD_getDictID_fromDict().