[openexr] Replace buf_to_file with IStream (#4094)

* Add a working skeleton for OpenEXR fuzzers.

* added openexr fuzzers, updated build script to include them

* cleaned up bash loop

* [openexr] Replace buf_to_file with StdISStream.

Version 2.5.0 of OpenEXR added a StdISStream class that turns
a std::string into an Imf::IStream, which can be used instead of
filenames when opening an OpenEXR image.  This commit adds code which
wraps the fuzzer input into a StdISStream, which enables us to remove
the hacky buf_to_file function.

* updated deepscanlines_fuzzer to use IStream instead of filenames

* replace "/work" with  in build.sh

* Reformat CMake settings, and also prevent building utils and examples.

* Reformat and change names in build.sh.

* Omit the version prefix when building OpenEXR and IlmBase libraries.

* updated final two fuzzers to use istream

* fixed additional conflict in project.yaml

* get header size from input

* increased header size

* Fix argument types in readFileSingle

Co-authored-by: Michael Jezierny <mtjz@google.com>
Co-authored-by: Abhishek Arya <inferno@chromium.org>
This commit is contained in:
Ravi Jotwani 2020-07-14 14:01:37 -07:00 committed by GitHub
parent 4f5c06fbf7
commit 96c3d4f440
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 56 additions and 132 deletions

View File

@ -24,6 +24,9 @@
#include <ImfDeepScanLineInputPart.h>
#include <ImfMultiPartInputFile.h>
#include <ImfNamespace.h>
#include <ImfStdIO.h>
#include <fuzzer/FuzzedDataProvider.h>
namespace IMF = OPENEXR_IMF_NAMESPACE;
using namespace IMF;
@ -108,10 +111,11 @@ static void readFile(T *inpart) {
}
}
static void readFileSingle(const char filename[]) {
static void readFileSingle(IStream& is, uint64_t width, uint64_t height) {
DeepScanLineInputFile *file = NULL;
Header header(width, height);
try {
file = new DeepScanLineInputFile(filename, 0);
file = new DeepScanLineInputFile(header, &is, EXR_VERSION, 0);
} catch (...) {
return;
}
@ -124,10 +128,10 @@ static void readFileSingle(const char filename[]) {
delete file;
}
static void readFileMulti(const char filename[]) {
static void readFileMulti(IStream& is) {
MultiPartInputFile *file = NULL;
try {
file = new MultiPartInputFile(filename, 0);
file = new MultiPartInputFile(is, 0);
} catch (...) {
return;
}
@ -151,35 +155,19 @@ static void readFileMulti(const char filename[]) {
} // namespace
// from cl/164883104
static char *buf_to_file(const char *buf, size_t size) {
char *name = strdup("/dev/shm/fuzz-XXXXXX");
int fd = mkstemp(name);
if (fd < 0) {
perror("open");
exit(1);
}
size_t pos = 0;
while (pos < size) {
int nbytes = write(fd, &buf[pos], size - pos);
if (nbytes <= 0) {
perror("write");
exit(1);
}
pos += nbytes;
}
if (close(fd) != 0) {
perror("close");
exit(1);
}
return name;
}
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
char *file = buf_to_file((const char *)data, size);
readFileSingle(file);
readFileMulti(file);
unlink(file);
free(file);
if (size < 16) return 0;
FuzzedDataProvider stream(data, size);
uint64_t width = stream.ConsumeIntegral<uint64_t>();
uint64_t height = stream.ConsumeIntegral<uint64_t>();
std::vector<char> buffer = stream.ConsumeRemainingBytes<char>();
const std::string s(buffer.data(), buffer.size());
StdISStream is;
is.str(s);
readFileSingle(is, width, height);
readFileMulti(is);
return 0;
}

View File

@ -23,6 +23,7 @@
#include <ImfDeepTiledInputFile.h>
#include <ImfDeepTiledInputPart.h>
#include <ImfTiledInputPart.h>
#include <ImfStdIO.h>
namespace IMF = OPENEXR_IMF_NAMESPACE;
using namespace IMF;
@ -115,10 +116,10 @@ static void readFile(T *part) {
}
}
static void readFileSingle(const char filename[]) {
static void readFileSingle(IStream& is) {
DeepTiledInputFile *file;
try {
file = new DeepTiledInputFile(filename, 8);
file = new DeepTiledInputFile(is, 8);
} catch (...) {
return;
}
@ -131,11 +132,11 @@ static void readFileSingle(const char filename[]) {
delete file;
}
static void readFileMulti(const char filename[]) {
static void readFileMulti(IStream& is) {
MultiPartInputFile *file;
try {
file = new MultiPartInputFile(filename, 8);
file = new MultiPartInputFile(is, 8);
} catch (...) {
return;
}
@ -161,36 +162,15 @@ static void readFileMulti(const char filename[]) {
} // namespace
// from cl/164883104
static char *buf_to_file(const char *buf, size_t size) {
char *name = strdup("/dev/shm/fuzz-XXXXXX");
int fd = mkstemp(name);
if (fd < 0) {
perror("open");
exit(1);
}
size_t pos = 0;
while (pos < size) {
int nbytes = write(fd, &buf[pos], size - pos);
if (nbytes <= 0) {
perror("write");
exit(1);
}
pos += nbytes;
}
if (close(fd) != 0) {
perror("close");
exit(1);
}
return name;
}
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
char *file = buf_to_file((const char *)data, size);
const std::string s(reinterpret_cast<const char*>(data), size);
StdISStream is;
is.str(s);
Header::setMaxImageSize(10000, 10000);
readFileSingle(file);
readFileMulti(file);
unlink(file);
free(file);
readFileSingle(is);
readFileMulti(is);
return 0;
}

View File

@ -22,16 +22,17 @@
#include <ImfInputPart.h>
#include <ImfMultiPartInputFile.h>
#include <ImfRgbaFile.h>
#include <ImfStdIO.h>
using namespace OPENEXR_IMF_INTERNAL_NAMESPACE;
using IMATH_NAMESPACE::Box2i;
namespace {
static void readSingle(const char fileName[]) {
static void readSingle(IStream& is) {
RgbaInputFile *in = NULL;
try {
in = new RgbaInputFile(fileName);
in = new RgbaInputFile(is);
} catch (...) {
return;
}
@ -54,10 +55,10 @@ static void readSingle(const char fileName[]) {
delete in;
}
static void readMulti(const char fileName[]) {
static void readMulti(IStream& is) {
MultiPartInputFile *file;
try {
file = new MultiPartInputFile(fileName);
file = new MultiPartInputFile(is);
} catch (...) {
return;
}
@ -98,35 +99,12 @@ static void readMulti(const char fileName[]) {
} // namespace
// from cl/164883104
static char *buf_to_file(const char *buf, size_t size) {
char *name = strdup("/dev/shm/fuzz-XXXXXX");
int fd = mkstemp(name);
if (fd < 0) {
perror("open");
exit(1);
}
size_t pos = 0;
while (pos < size) {
int nbytes = write(fd, &buf[pos], size - pos);
if (nbytes <= 0) {
perror("write");
exit(1);
}
pos += nbytes;
}
if (close(fd) != 0) {
perror("close");
exit(1);
}
return name;
}
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
char *file = buf_to_file((const char *)data, size);
readSingle(file);
readMulti(file);
unlink(file);
free(file);
const std::string s(reinterpret_cast<const char*>(data), size);
StdISStream is;
is.str(s);
readSingle(is);
readMulti(is);
return 0;
}

View File

@ -29,6 +29,7 @@
#include <ImfTiledInputPart.h>
#include <ImfTiledOutputPart.h>
#include <OpenEXRConfig.h>
#include <ImfStdIO.h>
using namespace OPENEXR_IMF_INTERNAL_NAMESPACE;
using IMATH_NAMESPACE::Box2i;
@ -49,10 +50,10 @@ void readImageONE(TiledRgbaInputFile *in, int dwx, int dwy) {
}
}
void readImageONE2(const char fileName[]) {
void readImageONE2(IStream& is) {
MultiPartInputFile *in;
try {
in = new MultiPartInputFile(fileName);
in = new MultiPartInputFile(is);
} catch (...) {
return;
}
@ -140,13 +141,13 @@ void readImageRIP(TiledRgbaInputFile *in, int dwx, int dwy) {
} // namespace
static void fuzzImage(const char filename[]) {
static void fuzzImage(IStream& is) {
Header::setMaxImageSize(10000, 10000);
Header::setMaxTileSize(10000, 10000);
TiledRgbaInputFile *in;
try {
in = new TiledRgbaInputFile(filename);
in = new TiledRgbaInputFile(is);
} catch (...) {
return;
}
@ -158,39 +159,16 @@ static void fuzzImage(const char filename[]) {
readImageMIP(in, dwx, dwy);
readImageRIP(in, dwx, dwy);
readImageONE(in, dwx, dwy);
readImageONE2(filename);
readImageONE2(is);
delete in;
}
// from cl/164883104
static char *buf_to_file(const char *buf, size_t size) {
char *name = strdup("/dev/shm/fuzz-XXXXXX");
int fd = mkstemp(name);
if (fd < 0) {
perror("open");
exit(1);
}
size_t pos = 0;
while (pos < size) {
int nbytes = write(fd, &buf[pos], size - pos);
if (nbytes <= 0) {
perror("write");
exit(1);
}
pos += nbytes;
}
if (close(fd) != 0) {
perror("close");
exit(1);
}
return name;
}
extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
char *file = buf_to_file((const char *)data, size);
fuzzImage(file);
unlink(file);
free(file);
const std::string s(reinterpret_cast<const char*>(data), size);
StdISStream is;
is.str(s);
fuzzImage(is);
return 0;
}