summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMax Dymond <cmeister2@gmail.com>2019-06-25 17:22:02 +0100
committerMax Dymond <cmeister2@gmail.com>2019-06-28 08:30:02 +0100
commita5cf079d4dc9097c4e58f0eb7b0996b0a6d91696 (patch)
tree9c91b612a8bcbcfb0137518509d0fe3bcead50cc
parent798301b4e144fab5d25fc34566c1419685f5f1eb (diff)
downloadlz4-a5cf079d4dc9097c4e58f0eb7b0996b0a6d91696.tar.gz
lz4-a5cf079d4dc9097c4e58f0eb7b0996b0a6d91696.tar.bz2
lz4-a5cf079d4dc9097c4e58f0eb7b0996b0a6d91696.zip
Add a fuzzing target that compiles in the oss-fuzz environment
-rw-r--r--.travis.yml6
-rw-r--r--Makefile1
-rw-r--r--ossfuzz/Makefile54
-rw-r--r--ossfuzz/compress_fuzzer.cc22
-rwxr-xr-xossfuzz/ossfuzz.sh26
-rw-r--r--ossfuzz/standaloneengine.cc74
-rw-r--r--ossfuzz/testinput.h3
-rwxr-xr-xossfuzz/travisoss.sh24
8 files changed, 210 insertions, 0 deletions
diff --git a/.travis.yml b/.travis.yml
index ee643e5..4d45e89 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -194,5 +194,11 @@ matrix:
- pushd build
- DESTDIR=./staging ninja install
- tree ./staging
+
+ # oss-fuzz compilation test
+ - name: Compile OSS-Fuzz targets
+ script:
+ - ./ossfuzz/travisoss.sh
+
allow_failures:
- env: ALLOW_FAILURES=true
diff --git a/Makefile b/Makefile
index e24cec5..34835fd 100644
--- a/Makefile
+++ b/Makefile
@@ -34,6 +34,7 @@ LZ4DIR = lib
PRGDIR = programs
TESTDIR = tests
EXDIR = examples
+FUZZDIR = ossfuzz
include Makefile.inc
diff --git a/ossfuzz/Makefile b/ossfuzz/Makefile
new file mode 100644
index 0000000..94829b2
--- /dev/null
+++ b/ossfuzz/Makefile
@@ -0,0 +1,54 @@
+# ##########################################################################
+# LZ4 oss fuzzer - Makefile
+#
+# GPL v2 License
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License along
+# with this program; if not, write to the Free Software Foundation, Inc.,
+# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+#
+# You can contact the author at :
+# - LZ4 homepage : http://www.lz4.org
+# - LZ4 source repository : https://github.com/lz4/lz4
+# ##########################################################################
+# lz4_fuzzer : OSS Fuzz test tool
+# ##########################################################################
+
+LZ4DIR := ../lib
+LIB_FUZZING_ENGINE ?= standaloneengine.o
+
+DEBUGLEVEL?= 1
+DEBUGFLAGS = -g -DLZ4_DEBUG=$(DEBUGLEVEL)
+
+CFLAGS += -I$(LZ4DIR) $(DEBUGFLAGS) $(MOREFLAGS)
+CPPFLAGS+= -I$(LZ4DIR) -DXXH_NAMESPACE=LZ4_
+FLAGS = $(CFLAGS) $(CPPFLAGS) $(LDFLAGS)
+
+include ../Makefile.inc
+
+# Include a rule to build the static library if calling this target
+# directly.
+$(LZ4DIR)/liblz4.a:
+ $(MAKE) -C $(LZ4DIR) CFLAGS="$(CFLAGS)" liblz4.a
+
+%.o: %.cc
+ $(CXX) -c $(CFLAGS) $(CPPFLAGS) $< -o $@
+
+.PHONY: compress_fuzzer
+compress_fuzzer: compress_fuzzer.o $(LZ4DIR)/liblz4.a
+ # Compile the standalone code just in case. The OSS-Fuzz code might
+ # override the LIB_FUZZING_ENGINE value to "-fsanitize=fuzzer"
+ $(CXX) -c $(CFLAGS) $(CPPFLAGS) standaloneengine.cc -o standaloneengine.o
+
+ # Now compile the actual fuzzer.
+ $(CXX) $(FLAGS) $(LIB_FUZZING_ENGINE) $^ -o $@$(EXT)
diff --git a/ossfuzz/compress_fuzzer.cc b/ossfuzz/compress_fuzzer.cc
new file mode 100644
index 0000000..006a0ab
--- /dev/null
+++ b/ossfuzz/compress_fuzzer.cc
@@ -0,0 +1,22 @@
+#include <stddef.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include "lz4.h"
+
+extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size)
+{
+ size_t const compressed_dest_size = LZ4_compressBound(size);
+ char *const dest_buffer = (char *)malloc(compressed_dest_size);
+
+ int result = LZ4_compress_default((const char*)data, dest_buffer,
+ size, compressed_dest_size);
+
+ if (result == 0)
+ {
+ abort();
+ }
+
+ free(dest_buffer);
+
+ return 0;
+}
diff --git a/ossfuzz/ossfuzz.sh b/ossfuzz/ossfuzz.sh
new file mode 100755
index 0000000..e0cb63c
--- /dev/null
+++ b/ossfuzz/ossfuzz.sh
@@ -0,0 +1,26 @@
+#!/bin/bash -eu
+
+# This script is called by the oss-fuzz main project when compiling the fuzz
+# targets. This script is regression tested by travisoss.sh.
+
+# Save off the current folder as the build root.
+export BUILD_ROOT=$PWD
+
+# lz4 uses CPPFLAGS rather than CXX flags.
+export CPPFLAGS="${CXXFLAGS}"
+
+echo "CC: $CC"
+echo "CXX: $CXX"
+echo "LIB_FUZZING_ENGINE: $LIB_FUZZING_ENGINE"
+echo "CFLAGS: $CFLAGS"
+echo "CPPFLAGS: $CPPFLAGS"
+echo "OUT: $OUT"
+
+export MAKEFLAGS+="-j$(nproc)"
+
+pushd ossfuzz
+make V=1 compress_fuzzer
+popd
+
+# Copy the fuzzers to the target directory.
+cp -v ossfuzz/compress_fuzzer $OUT/
diff --git a/ossfuzz/standaloneengine.cc b/ossfuzz/standaloneengine.cc
new file mode 100644
index 0000000..175360e
--- /dev/null
+++ b/ossfuzz/standaloneengine.cc
@@ -0,0 +1,74 @@
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "testinput.h"
+
+/**
+ * Main procedure for standalone fuzzing engine.
+ *
+ * Reads filenames from the argument array. For each filename, read the file
+ * into memory and then call the fuzzing interface with the data.
+ */
+int main(int argc, char **argv)
+{
+ int ii;
+ for(ii = 1; ii < argc; ii++)
+ {
+ FILE *infile;
+ printf("[%s] ", argv[ii]);
+
+ /* Try and open the file. */
+ infile = fopen(argv[ii], "rb");
+ if(infile)
+ {
+ uint8_t *buffer = NULL;
+ size_t buffer_len;
+
+ printf("Opened.. ");
+
+ /* Get the length of the file. */
+ fseek(infile, 0L, SEEK_END);
+ buffer_len = ftell(infile);
+
+ /* Reset the file indicator to the beginning of the file. */
+ fseek(infile, 0L, SEEK_SET);
+
+ /* Allocate a buffer for the file contents. */
+ buffer = (uint8_t *)calloc(buffer_len, sizeof(uint8_t));
+ if(buffer)
+ {
+ /* Read all the text from the file into the buffer. */
+ fread(buffer, sizeof(uint8_t), buffer_len, infile);
+ printf("Read %zu bytes, fuzzing.. ", buffer_len);
+
+ /* Call the fuzzer with the data. */
+ LLVMFuzzerTestOneInput(buffer, buffer_len);
+
+ printf("complete !!");
+
+ /* Free the buffer as it's no longer needed. */
+ free(buffer);
+ buffer = NULL;
+ }
+ else
+ {
+ fprintf(stderr,
+ "[%s] Failed to allocate %zu bytes \n",
+ argv[ii],
+ buffer_len);
+ }
+
+ /* Close the file as it's no longer needed. */
+ fclose(infile);
+ infile = NULL;
+ }
+ else
+ {
+ /* Failed to open the file. Maybe wrong name or wrong permissions? */
+ fprintf(stderr, "[%s] Open failed. \n", argv[ii]);
+ }
+
+ printf("\n");
+ }
+}
diff --git a/ossfuzz/testinput.h b/ossfuzz/testinput.h
new file mode 100644
index 0000000..6ab9b51
--- /dev/null
+++ b/ossfuzz/testinput.h
@@ -0,0 +1,3 @@
+#include <inttypes.h>
+
+extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size);
diff --git a/ossfuzz/travisoss.sh b/ossfuzz/travisoss.sh
new file mode 100755
index 0000000..3b2f26f
--- /dev/null
+++ b/ossfuzz/travisoss.sh
@@ -0,0 +1,24 @@
+#!/bin/bash
+
+set -ex
+
+# Clone the oss-fuzz repository
+git clone https://github.com/google/oss-fuzz.git /tmp/ossfuzz
+
+if [[ ! -d /tmp/ossfuzz/projects/lz4 ]]
+then
+ echo "Could not find the lz4 project in ossfuzz"
+
+ # Exit with a success code while the lz4 project is not expected to exist
+ # on oss-fuzz.
+ exit 0
+fi
+
+# Modify the oss-fuzz Dockerfile so that we're checking out the current branch on travis.
+sed -i "s@https://github.com/lz4/lz4.git@-b $TRAVIS_BRANCH https://github.com/lz4/lz4.git@" /tmp/ossfuzz/projects/lz4/Dockerfile
+
+# Try and build the fuzzers
+pushd /tmp/ossfuzz
+python infra/helper.py build_image --pull lz4
+python infra/helper.py build_fuzzers lz4
+popd