Hanno Böck
https://hboeck.de/
https://fuzzing-project.org/
Everyone should have Linux environment with afl installed.
(preferrably with clang 4.0 or later)
Provided: Debian VM image.
Use random / malformed inputs to search for bugs.
Usually: Start with valid file, add errors.
Dump fuzzing: Only random mutations, no knowledge about application.
Template-based fuzzing: Individual fuzzer for each data input format.
Either not very good or a lot of work.
New approach: Instrumentation-based fuzzing.
Use code paths as a feedback mechanism.
Smart and easy to use.
Compile application with afl-gcc/afl-clang/afl-clang-fast.
Run afl-fuzz.
./configure CC=afl-clang-fast CXX=afl-clang-fast++ --disable-shared; make
Place sample file(s) in directory "in/".
afl-fuzz -i in -o out ./[path_to_executable] [params] @@
Exercise: Run afl on latest version of lha.
Small buffer overflows, out of bounds read, use after free: They often don't crash.
Feature of gcc/clang.
Relatively fast (~1.5x).
Finds many bug classes, some of them can't be found with runtime-only tools like valgrind.
int main() { char *a = malloc(10); a[0]=1; free(a); printf("%i\n",a[0]); }
int main() { int i[2] = {1, 0}; printf("%i\n",i[2]); }
Add -fsanitize=address to CFLAGS/CXXFLAGS/LDFLAGS.
Control with environment variable ASAN_OPTIONS, e. g. ASAN_OPTIONS="log_path=/var/log/asan/asan-error".
Exercise: Run test suite of glib version 2.48.1 with Address Sanitizer.
ASAN finds hidden bugs, so combining Fuzzing and ASAN is smart.
Environment variable AFL_USE_ASAN=1.
Disable memory limit: -m none
Exercise: Fuzz lha again, with ASAN enabled.
Good targets: Everything that parses complex data.
Tools that support many file formats (ImageMagick, 7-zip, libarchive, ffmpeg, ...)
Exercise: Find something interesting to fuzz.
Functions:
AFL works on executables, LibFuzzer on functions.
No forking / startup: Faster.
But: Need to write code, fragile.
#include <openssl/rsa.h> extern "C" int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { unsigned char out[512]; RSA_padding_check_PKCS1_type_1(out, 512, Data, Size, 512); return 0; }
Write function LLVMFuzzerTestOneInput that takes buffer and size argument, call function to be tested.
Be careful: Memory leaks will kill your fuzzing process.
Run libfuzzer for OPENSSL_uni2asc with provided test stub.
https://github.com/hannob/libfuzzer-examples/blob/master/libfuzzer-openssl-uni2asc.cpp
Write libfuzzer stub for c-ares vulnerability CVE-2016-5180.
Minimize testcases with afl-tmin.
We can use small wrapper to use afl-tmin with libfuzzer stubs.
Recompile c-ares with afl / asan, compile stub, aflize-libfuzzer.cpp + c-ares.
https://github.com/hannob/libfuzzer-examples/blob/master/aflize-libfuzzer.cpp
-fsanitize=address
-fsanitize=undefined
-fsanitize=memory
-fsanitize=thread
Problem: You will find a lot of low severity bugs.
Finds use of uninitialized memory.
Only clang, no gcc.
Many pitfalls.
Combine with -O2 and don't use FORTIFY_SOURCE.
Different approach of protocol fuzzing.
Sets up irc server, sends garbage.
AFL persistent mode.
Kernel: KASAN, Syzcaller, vUSBf.
Google's OSS-Fuzz project.