You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

2.6 KiB

title linkTitle
Fuzzing Fuzzing

Reproducing using fuzz

We assume that you can build Skia. Many fuzzes only reproduce when building with ASAN or MSAN; see those instructions for more details.

When building, you should add the following args to BUILD.gn to make reproducing less machine- and platform- dependent:

skia_use_fontconfig=false
skia_use_freetype=true
skia_use_system_freetype2=false
skia_use_wuffs=true
skia_enable_skottie=true
skia_enable_fontmgr_custom_directory=false
skia_enable_fontmgr_custom_embedded=false
skia_enable_fontmgr_custom_empty=true

All that is needed to reproduce a fuzz downloaded from ClusterFuzz or oss-fuzz is to run something like:

out/ASAN/fuzz -b /path/to/downloaded/testcase

The fuzz binary will try its best to guess what the type/name should be based on the name of the testcase. Manually providing type and name is also supported, like:

out/ASAN/fuzz -t filter_fuzz -b /path/to/downloaded/testcase
out/ASAN/fuzz -t api -n RasterN32Canvas -b /path/to/downloaded/testcase

To enumerate all supported types and names, run the following:

out/ASAN/fuzz --help  # will list all types
out/ASAN/fuzz -t api  # will list all names

If the crash does not show up, try to add the flag --loops:

out/ASAN/fuzz -b /path/to/downloaded/testcase --loops <times-to-run>

Writing fuzzers with libfuzzer

libfuzzer is an easy way to write new fuzzers, and how we run them on oss-fuzz. Your fuzzer entry point should implement this API:

extern "C" int LLVMFuzzerTestOneInput(const uint8_t*, size_t);

First install Clang and libfuzzer, e.g.

sudo apt install clang-10 libc++-10-dev libfuzzer-10-dev

You should now be able to use -fsanitize=fuzzer with Clang.

Set up GN args to use libfuzzer:

cc = "clang-10"
cxx = "clang++-10"
sanitize = "fuzzer"
extra_cflags = [ "-O1" ]  # Or whatever you want.
...

Build Skia and your fuzzer entry point:

ninja -C out/libfuzzer skia
clang++-10 -I. -O1 -fsanitize=fuzzer fuzz/oss_fuzz/whatever.cpp out/libfuzzer/libskia.a

Run your new fuzzer binary

./a.out

Fuzzing Defines

There are some defines that can help guide a fuzzer to be more productive (e.g. avoid OOMs, avoid unnecessarily slow code).

// Required for fuzzing with afl-fuzz to prevent OOMs from adding noise.
SK_BUILD_FOR_AFL_FUZZ

// Required for fuzzing with libfuzzer
SK_BUILD_FOR_LIBFUZZER

// This define adds in guards to abort when we think some code path will take a long time or
// use a lot of RAM. It is set by default when either of the above defines are set.
SK_BUILD_FOR_FUZZER