From 959ac9ef804b0c7f27bce35b6c7ad9cb829098ce Mon Sep 17 00:00:00 2001 From: Alex Hultman Date: Fri, 14 Aug 2020 16:34:14 +0200 Subject: [PATCH] Simplify PerMessageDeflate fuzzing regions --- fuzzing/PerMessageDeflate.cpp | 83 ++++++++++++++++++----------------- 1 file changed, 43 insertions(+), 40 deletions(-) diff --git a/fuzzing/PerMessageDeflate.cpp b/fuzzing/PerMessageDeflate.cpp index dd5afe2..3aea55e 100644 --- a/fuzzing/PerMessageDeflate.cpp +++ b/fuzzing/PerMessageDeflate.cpp @@ -4,6 +4,7 @@ #include #include +#include /* We test the permessage deflate module */ #include "../src/PerMessageDeflate.h" @@ -13,48 +14,50 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) { /* First byte determines what compressor to use */ - if (size < 1) { - return 0; + if (size >= 1) { + + int compressors[] = { + uWS::DEDICATED_COMPRESSOR_3KB, + uWS::DEDICATED_COMPRESSOR_4KB, + uWS::DEDICATED_COMPRESSOR_8KB, + uWS::DEDICATED_COMPRESSOR_16KB, + uWS::DEDICATED_COMPRESSOR_32KB, + uWS::DEDICATED_COMPRESSOR_64KB, + uWS::DEDICATED_COMPRESSOR_128KB, + uWS::DEDICATED_COMPRESSOR_256KB + }; + + auto compressor = compressors[data[0] % 8]; + data++; + size--; + + /* Bits 0 - 256 are okay */ + std::bitset<257> b; + + /* If we could specify LARGE_BUFFER_SIZE small here we could force it to inflate in chunks, + * triggering more line coverage. Currently it is set to 16kb which is always too much */ + struct StaticData { + uWS::DeflationStream deflationStream; + uWS::ZlibContext zlibContext; + + uWS::InflationStream inflationStream; + } staticData = {compressor}; + + /* Why is this padded? */ + makeChunked(makePadded(data, size), size, [&staticData, &b](const uint8_t *data, size_t size) { + auto [inflation, valid] = staticData.inflationStream.inflate(&staticData.zlibContext, std::string_view((char *) data, size), 256); + + /* Trigger ASAN flaws if length is more than 256 */ + b.set(inflation.length()); + }); + + makeChunked(makePadded(data, size), size, [&staticData](const uint8_t *data, size_t size) { + /* Always reset */ + staticData.deflationStream.deflate(&staticData.zlibContext, std::string_view((char *) data, size), true); + }); + } - int compressors[] = { - uWS::DEDICATED_COMPRESSOR_3KB, - uWS::DEDICATED_COMPRESSOR_4KB, - uWS::DEDICATED_COMPRESSOR_8KB, - uWS::DEDICATED_COMPRESSOR_16KB, - uWS::DEDICATED_COMPRESSOR_32KB, - uWS::DEDICATED_COMPRESSOR_64KB, - uWS::DEDICATED_COMPRESSOR_128KB, - uWS::DEDICATED_COMPRESSOR_256KB - }; - - auto compressor = compressors[data[0] % 8]; - data++; - size--; - - /* If we could specify LARGE_BUFFER_SIZE small here we could force it to inflate in chunks, - * triggering more line coverage. Currently it is set to 16kb which is always too much */ - struct StaticData { - uWS::DeflationStream deflationStream; - uWS::ZlibContext zlibContext; - - uWS::InflationStream inflationStream; - } staticData = {compressor}; - - /* Why is this padded? */ - makeChunked(makePadded(data, size), size, [&staticData](const uint8_t *data, size_t size) { - auto [inflation, valid] = staticData.inflationStream.inflate(&staticData.zlibContext, std::string_view((char *) data, size), 256); - if (inflation.length() > 256) { - /* Cause ASAN to freak out */ - delete (int *) (void *) 1; - } - }); - - makeChunked(makePadded(data, size), size, [&staticData](const uint8_t *data, size_t size) { - /* Always reset */ - staticData.deflationStream.deflate(&staticData.zlibContext, std::string_view((char *) data, size), true); - }); - return 0; }