From f7bdb6555d74cde1632497c6bcb92b07aac1b3b6 Mon Sep 17 00:00:00 2001 From: hexcoder Date: Thu, 10 Oct 2019 21:38:12 +0200 Subject: Update README.md Found Apple's statement on not supporting statically linked binaries and mentioned it. --- README.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index f818e271..4c04e1b6 100644 --- a/README.md +++ b/README.md @@ -105,7 +105,9 @@ These build options exist: * clean: cleans everything. for qemu_mode and unicorn_mode it means it deletes all downloads as well * help: shows these build options -You can also build statically linked versions of the afl++ binaries by passing the STATIC=1 argument to make: +[https://developer.apple.com/library/archive/qa/qa1118/_index.html](Unless +you are on Mac OS X) you can also build statically linked versions of the +afl++ binaries by passing the STATIC=1 argument to make: ```shell $ make all STATIC=1 -- cgit 1.4.1 From 61a84e15ea5a798a5667c67ccfc843499e288a9b Mon Sep 17 00:00:00 2001 From: hexcoder Date: Thu, 10 Oct 2019 21:46:15 +0200 Subject: Update README.md --- README.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/README.md b/README.md index 4c04e1b6..9acddd4c 100644 --- a/README.md +++ b/README.md @@ -105,8 +105,7 @@ These build options exist: * clean: cleans everything. for qemu_mode and unicorn_mode it means it deletes all downloads as well * help: shows these build options -[https://developer.apple.com/library/archive/qa/qa1118/_index.html](Unless -you are on Mac OS X) you can also build statically linked versions of the +[Unless you are on Mac OS X](https://developer.apple.com/library/archive/qa/qa1118/_index.html) you can also build statically linked versions of the afl++ binaries by passing the STATIC=1 argument to make: ```shell -- cgit 1.4.1 From bccaf93f8b444e3cddda76057303e0ab28c1c5b3 Mon Sep 17 00:00:00 2001 From: hexcoder Date: Thu, 10 Oct 2019 23:21:52 +0200 Subject: Update README.md typos in names --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 9acddd4c..bf8f69dc 100644 --- a/README.md +++ b/README.md @@ -620,7 +620,7 @@ without feedback, bug reports, or patches from: Jonathan Gray Filipe Cabecinhas Nico Weber Jodie Cunningham Andrew Griffiths Parker Thompson - Jonathan Neuschfer Tyler Nighswander + Jonathan Neuschaefer Tyler Nighswander Ben Nagy Samir Aguiar Aidan Thornton Aleksandar Nikolich Sam Hakim Laszlo Szekeres @@ -639,7 +639,7 @@ without feedback, bug reports, or patches from: Austin Seipp Daniel Komaromy Daniel Binderman Jonathan Metzman Vegard Nossum Jan Kneschke - Kurt Roeckx Marcel Bohme + Kurt Roeckx Marcel Boehme Van-Thuan Pham Abhik Roychoudhury Joshua J. Drake Toby Hutton Rene Freingruber Sergey Davidoff -- cgit 1.4.1 From dc311b978ee950160d362866e61a1a7d783e6666 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 11 Oct 2019 02:55:48 +0200 Subject: fix FreeBSD compile error 'NBBY' is not defined --- include/afl-fuzz.h | 1 + 1 file changed, 1 insertion(+) diff --git a/include/afl-fuzz.h b/include/afl-fuzz.h index e856b23e..5da41a3e 100644 --- a/include/afl-fuzz.h +++ b/include/afl-fuzz.h @@ -82,6 +82,7 @@ #if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) #define HAVE_AFFINITY 1 #if defined(__FreeBSD__) +#include #include #include #include -- cgit 1.4.1 From 287828fe0bef3224e5e4f0b80e880235570876e4 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 11 Oct 2019 03:24:50 +0200 Subject: if afl-clang has to be used, extend the hardening test as from llvm_mode --- test/test.sh | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/test/test.sh b/test/test.sh index 44236b63..0c5c18f7 100755 --- a/test/test.sh +++ b/test/test.sh @@ -64,7 +64,7 @@ $ECHO "${RESET}${GREY}[*] starting afl++ test framework ..." $ECHO "$BLUE[*] Testing: ${AFL_GCC}, afl-showmap and afl-fuzz" test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { ../${AFL_GCC} -o test-instr.plain ../test-instr.c > /dev/null 2>&1 - AFL_HARDEN=1 ../${AFL_GCC} -o test-instr.harden ../test-instr.c > /dev/null 2>&1 + AFL_HARDEN=1 ../${AFL_GCC} -o test-compcov.harden test-compcov.c > /dev/null 2>&1 test -e test-instr.plain && { $ECHO "$GREEN[+] ${AFL_GCC} compilation succeeded" echo 0 | ../afl-showmap -m ${MEM_LIMIT} -o test-instr.plain.0 -r -- ./test-instr.plain > /dev/null 2>&1 @@ -76,11 +76,11 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { } || $ECHO "$RED[!] ${AFL_GCC} instrumentation failed" rm -f test-instr.plain.0 test-instr.plain.1 } || $ECHO "$RED[!] ${AFL_GCC} failed" - test -e test-instr.harden && { - grep -qa fstack-protector-all test-instr.harden > /dev/null 2>&1 && { + test -e test-compcov.harden && { + grep -Eqa 'stack_chk_fail|fstack-protector-all|fortified' test-compcov.harden > /dev/null 2>&1 && { $ECHO "$GREEN[+] ${AFL_GCC} hardened mode succeeded and is working" } || $ECHO "$RED[!] ${AFL_GCC} hardened mode is not hardened" - rm -f test-instr.harden + rm -f test-compcov.harden } || $ECHO "$RED[!] ${AFL_GCC} hardened mode compilation failed" # now we want to be sure that afl-fuzz is working # make sure core_pattern is set to core on linux -- cgit 1.4.1 From 1e4fb1f6febd68558350fa356554e3b886dc9363 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Fri, 11 Oct 2019 20:07:45 +0100 Subject: Systen config typo for NetBSD --- afl-system-config | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/afl-system-config b/afl-system-config index a6e0efa4..99ebc61f 100755 --- a/afl-system-config +++ b/afl-system-config @@ -48,7 +48,7 @@ if [ "$PLATFORM" = "OpenBSD" ] ; then echo echo 'System security features cannot be disabled on OpenBSD.' fi -if [ "$PLATFORM" = "FreeBSD" ] ; then +if [ "$PLATFORM" = "NetBSD" ] ; then echo echo It is recommended to enable unprivileged users to set cpu affinity to be able to use afl-gotcpu meaningfully. -- cgit 1.4.1 From b33a6addcc9e52a3050a0e25b93dce10fd4cc644 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Fri, 11 Oct 2019 21:09:24 +0100 Subject: NetBSD binding to cpu, ignore sleeping processes. --- src/afl-fuzz-init.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index 127f5217..91d4c727 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -166,7 +166,7 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { - if (procs[i].p_cpuid < sizeof(cpu_used)) cpu_used[procs[i].p_cpuid] = 1; + if (procs[i].p_cpuid < sizeof(cpu_used) && procs[i].p_pctcpu > 0) cpu_used[procs[i].p_cpuid] = 1; } -- cgit 1.4.1 From a9404fe33fbde5977ece4daef3dd4a63b7b973a0 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 11 Oct 2019 23:20:32 +0200 Subject: fix output from echo on NetBSD, now enables users to set cpu --- afl-system-config | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/afl-system-config b/afl-system-config index 99ebc61f..2a7df17f 100755 --- a/afl-system-config +++ b/afl-system-config @@ -51,7 +51,7 @@ fi if [ "$PLATFORM" = "NetBSD" ] ; then echo echo It is recommended to enable unprivileged users to set cpu affinity -to be able to use afl-gotcpu meaningfully. +echo to be able to use afl-gotcpu meaningfully. /sbin/sysctl -w security.models.extensions.user_set_cpu_affinity=1 fi if [ "$PLATFORM" = "Darwin" ] ; then -- cgit 1.4.1 From 33281b04e7d043d30a1a9d60c3e7ec75f9709366 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Fri, 11 Oct 2019 22:21:25 +0100 Subject: FreeBSD making more tolerant the cpu binding at init time --- src/afl-fuzz-init.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index 91d4c727..18ce0a2f 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -138,7 +138,7 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { - if (procs[i].ki_oncpu < sizeof(cpu_used)) cpu_used[procs[i].ki_oncpu] = 1; + if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 0) cpu_used[procs[i].ki_oncpu] = 1; } -- cgit 1.4.1 From 132ecc0580e35a629ce7b6c0d9441ac63262318d Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 12 Oct 2019 01:49:23 +0200 Subject: catch afl-fuzz's output and print it in case of errors --- test/test.sh | 22 ++++++++++++++-------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/test/test.sh b/test/test.sh index 0c5c18f7..a7376d16 100755 --- a/test/test.sh +++ b/test/test.sh @@ -97,12 +97,15 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { echo 0 > in/in $ECHO "$GREY[*] running afl-fuzz for ${AFL_GCC}, this will take approx 10 seconds" { - ../afl-fuzz -V10 -m ${MEM_LIMIT} -i in -o out -- ./test-instr.plain > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V10 -m ${MEM_LIMIT} -i in -o out -- ./test-instr.plain >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with ${AFL_GCC}" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" - rm -rf in out + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" + } + rm -rf in out errors } rm -f test-instr.plain } || $ECHO "$YELLOW[-] afl is not compiled, cannot test" @@ -144,12 +147,15 @@ test -e ../afl-clang-fast && { echo 0 > in/in $ECHO "$GREY[*] running afl-fuzz for llvm_mode, this will take approx 10 seconds" { - ../afl-fuzz -V10 -m ${MEM_LIMIT} -i in -o out -- ./test-instr.plain > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V10 -m ${MEM_LIMIT} -i in -o out -- ./test-instr.plain >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with llvm_mode" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with llvm_mode" - rm -rf in out + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with llvm_mode" + } + rm -rf in out errors } rm -f test-instr.plain -- cgit 1.4.1 From 99f2abfd711f0cdfe56f08b63b8ee2effe58cbed Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 12 Oct 2019 01:58:45 +0200 Subject: fine tuning cpu percentage limit to be detected as bound cpu on FreeBSD --- src/afl-fuzz-init.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index 18ce0a2f..a54c53d8 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -138,7 +138,7 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { - if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 0) cpu_used[procs[i].ki_oncpu] = 1; + if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 2) cpu_used[procs[i].ki_oncpu] = 1; } -- cgit 1.4.1 From bd312607a36a319ecfbd01820dc1ac222afabcd2 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 12 Oct 2019 00:39:59 +0200 Subject: add afl-fuzz error capturing for qemu_mode and unicorn_mode --- test/test.sh | 42 ++++++++++++++++++++++++++++-------------- 1 file changed, 28 insertions(+), 14 deletions(-) diff --git a/test/test.sh b/test/test.sh index a7376d16..27bf708f 100755 --- a/test/test.sh +++ b/test/test.sh @@ -222,24 +222,31 @@ test -e ../afl-qemu-trace && { echo 0 > in/in $ECHO "$GREY[*] running afl-fuzz for qemu_mode, this will take approx 10 seconds" { - ../afl-fuzz -V10 -Q -i in -o out -- ./test-instr > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V10 -Q -i in -o out -- ./test-instr >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with qemu_mode" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode" + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode" + } + rm -f errors test -e ../libcompcov.so && { $ECHO "$GREY[*] running afl-fuzz for qemu_mode libcompcov, this will take approx 10 seconds" { export AFL_PRELOAD=../libcompcov.so export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V10 -Q -i in -o out -- ./test-compcov > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V10 -Q -i in -o out -- ./test-compcov >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with qemu_mode libcompcov" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode libcompcov" + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode libcompcov" + } } || $ECHO "$YELLOW[-] we cannot test qemu_mode libcompcov because it is not present" - rm -rf in out + rm -rf in out errors } } || $ECHO "$RED[-] gcc compilation of test targets failed - what is going on??" @@ -267,21 +274,28 @@ test -d ../unicorn_mode/unicorn && { echo 0 > in/in $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 15 seconds" { - ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/simple/simple_test_harness.py @@ > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode" + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode" + } + rm -f errors $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 15 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ > /dev/null 2>&1 - } > /dev/null 2>&1 + ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" - } || $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode compcov" - rm -rf in out + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode compcov" + } + rm -rf in out errors } } || $ECHO "$RED[-] missing sample binaries in unicorn_mode/samples/ - what is going on??" -- cgit 1.4.1 From 8f854ee83a6dd70ff5a3e70f6064928b35d2ab17 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sun, 13 Oct 2019 10:34:51 +0200 Subject: test for persistent qemu --- test/test.sh | 37 ++++++++++++++++++++++--------------- 1 file changed, 22 insertions(+), 15 deletions(-) diff --git a/test/test.sh b/test/test.sh index 27bf708f..94d28047 100755 --- a/test/test.sh +++ b/test/test.sh @@ -113,7 +113,11 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { $ECHO "$BLUE[*] Testing: llvm_mode" test -e ../afl-clang-fast && { # on FreeBSD need to set AFL_CC - export AFL_CC=`llvm-config --bindir`/clang + if which clang >/dev/null; then + export AFL_CC=`which clang` + else + export AFL_CC=`llvm-config --bindir`/clang + fi ../afl-clang-fast -o test-instr.plain ../test-instr.c > /dev/null 2>&1 AFL_HARDEN=1 ../afl-clang-fast -o test-compcov.harden test-compcov.c > /dev/null 2>&1 test -e test-instr.plain && { @@ -244,25 +248,28 @@ test -e ../afl-qemu-trace && { } || { cat errors $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode libcompcov" - } + } } || $ECHO "$YELLOW[-] we cannot test qemu_mode libcompcov because it is not present" + rm -f errors + + $ECHO "$GREY[*] running afl-fuzz for persistent qemu_mode, this will take approx 10 seconds" + { + export AFL_QEMU_PERSISTENT_ADDR=0x$(nm test-instr | grep "T main" | awk '{ print $1 }') + export AFL_QEMU_PERSISTENT_GPR=1 + ../afl-fuzz -V10 -Q -i in -o out -- ./test-instr > /dev/null 2>&1 + } >>errors 2>&1 + test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { + $ECHO "$GREEN[+] afl-fuzz is working correctly with persistent qemu_mode" + } || { + cat errors + $ECHO "$RED[!] afl-fuzz is not working correctly with persistent qemu_mode" + exit 1 + } + $ECHO "$YELLOW[?] we need a test case for qemu_mode unsigaction library" rm -rf in out errors } } || $ECHO "$RED[-] gcc compilation of test targets failed - what is going on??" - $ECHO "$YELLOW[?] we need a test case for qemu_mode persistent mode" - $ECHO "$YELLOW[?] we need a test case for qemu_mode unsigaction library" - # This works but there are already problems with persistent (e.g. stability) - #$ECHO "$GREY[*] running afl-fuzz for persistent qemu_mode, this will take approx 10 seconds" - #{ - # export AFL_QEMU_PERSISTENT_ADDR=0x$(nm test-instr | grep "T main" | awk '{ print $1 }') - # export AFL_QEMU_PERSISTENT_GPR=1 - # ../afl-fuzz -V10 -Q -i in -o out -- ./test-instr > /dev/null 2>&1 - #} > /dev/null 2>&1 - #test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { - # $ECHO "$GREEN[+] afl-fuzz is working correctly with persistent qemu_mode" - #} || $ECHO "$RED[!] afl-fuzz is not working correctly with persistent qemu_mode" - rm -f test-instr test-compcov } || $ECHO "$YELLOW[-] qemu_mode is not compiled, cannot test" -- cgit 1.4.1 From ac5b0a3b34ab63e33bbaa336518f206f8ba8698f Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sun, 13 Oct 2019 10:38:13 +0200 Subject: moar doc --- .custom-format.py | 15 +++++++++++++++ qemu_mode/README.md | 2 +- unicorn_mode/README.md | 2 +- 3 files changed, 17 insertions(+), 2 deletions(-) diff --git a/.custom-format.py b/.custom-format.py index b7416843..8d762006 100755 --- a/.custom-format.py +++ b/.custom-format.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +# +# american fuzzy lop++ - custom code formatter +# -------------------------------------------- +# +# Written and maintaned by Andrea Fioraldi +# +# Copyright 2015, 2016, 2017 Google Inc. All rights reserved. +# Copyright 2019 AFLplusplus Project. All rights reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at: +# +# http://www.apache.org/licenses/LICENSE-2.0 +# import subprocess import sys diff --git a/qemu_mode/README.md b/qemu_mode/README.md index 81904cf1..a85407e4 100644 --- a/qemu_mode/README.md +++ b/qemu_mode/README.md @@ -101,7 +101,7 @@ AFL_COMPCOV_LEVEL=1 is to instrument comparisons with only immediate values / read-only memory. AFL_COMPCOV_LEVEL=2 instruments all comparison instructions and memory comparison functions when libcompcov is preloaded. Comparison instructions are currently instrumented only -on the x86 and x86_64 targets. +on the x86, x86_64 and ARM targets. Highly recommended. diff --git a/unicorn_mode/README.md b/unicorn_mode/README.md index ea3e3c9b..8f381b59 100644 --- a/unicorn_mode/README.md +++ b/unicorn_mode/README.md @@ -99,7 +99,7 @@ The options that enables Unicorn CompareCoverage are the same used for QEMU. AFL_COMPCOV_LEVEL=1 is to instrument comparisons with only immediate values. QEMU_COMPCOV_LEVEL=2 instruments all comparison instructions. Comparison instructions are currently instrumented only -on the x86 and x86_64 targets. +for the x86, x86_64 and ARM targets. ## 4) Gotchas, feedback, bugs -- cgit 1.4.1 From dcfccb2a0d6d351588d6e312410974b36462bbce Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sun, 13 Oct 2019 13:03:06 +0200 Subject: reverse bytes compcov in unicorn --- unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h | 36 +++++++++++----------- 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h index 95e68302..12e33b2f 100644 --- a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h +++ b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h @@ -38,7 +38,7 @@ void HELPER(afl_compcov_log_16)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; - if ((arg1 & 0xff) == (arg2 & 0xff)) { INC_AFL_AREA(cur_loc); } + if ((arg1 & 0xff00) == (arg2 & 0xff00)) { INC_AFL_AREA(cur_loc); } } @@ -47,13 +47,13 @@ void HELPER(afl_compcov_log_32)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; - if ((arg1 & 0xff) == (arg2 & 0xff)) { + if ((arg1 & 0xff000000) == (arg2 & 0xff000000)) { - INC_AFL_AREA(cur_loc); - if ((arg1 & 0xffff) == (arg2 & 0xffff)) { + INC_AFL_AREA(cur_loc +2); + if ((arg1 & 0xff0000) == (arg2 & 0xff0000)) { INC_AFL_AREA(cur_loc + 1); - if ((arg1 & 0xffffff) == (arg2 & 0xffffff)) { INC_AFL_AREA(cur_loc + 2); } + if ((arg1 & 0xff00) == (arg2 & 0xff00)) { INC_AFL_AREA(cur_loc); } } @@ -66,27 +66,27 @@ void HELPER(afl_compcov_log_64)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; - if ((arg1 & 0xff) == (arg2 & 0xff)) { + if ((arg1 & 0xff00000000000000) == (arg2 & 0xff00000000000000)) { - INC_AFL_AREA(cur_loc); - if ((arg1 & 0xffff) == (arg2 & 0xffff)) { + INC_AFL_AREA(cur_loc +6); + if ((arg1 & 0xff000000000000) == (arg2 & 0xff000000000000)) { - INC_AFL_AREA(cur_loc + 1); - if ((arg1 & 0xffffff) == (arg2 & 0xffffff)) { + INC_AFL_AREA(cur_loc + 5); + if ((arg1 & 0xff0000000000) == (arg2 & 0xff0000000000)) { - INC_AFL_AREA(cur_loc + 2); - if ((arg1 & 0xffffffff) == (arg2 & 0xffffffff)) { + INC_AFL_AREA(cur_loc + 4); + if ((arg1 & 0xff00000000) == (arg2 & 0xff00000000)) { INC_AFL_AREA(cur_loc + 3); - if ((arg1 & 0xffffffffff) == (arg2 & 0xffffffffff)) { + if ((arg1 & 0xff000000) == (arg2 & 0xff000000)) { - INC_AFL_AREA(cur_loc + 4); - if ((arg1 & 0xffffffffffff) == (arg2 & 0xffffffffffff)) { + INC_AFL_AREA(cur_loc + 2); + if ((arg1 & 0xff0000) == (arg2 & 0xff0000)) { - INC_AFL_AREA(cur_loc + 5); - if ((arg1 & 0xffffffffffffff) == (arg2 & 0xffffffffffffff)) { + INC_AFL_AREA(cur_loc + 1); + if ((arg1 & 0xff00) == (arg2 & 0xff00)) { - INC_AFL_AREA(cur_loc + 6); + INC_AFL_AREA(cur_loc); } -- cgit 1.4.1 From 540de896e346694dd6df03bf4b3676388b53fecf Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 14 Oct 2019 11:08:25 +0200 Subject: more time for test case --- TODO | 1 + test/test.sh | 20 +++++++++++++++++--- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/TODO b/TODO index 40828168..696e9372 100644 --- a/TODO +++ b/TODO @@ -4,6 +4,7 @@ Roadmap 2.55d: afl-fuzz: - radamsa mutator + - test the libmutator actually works and does not run infinite (need an example though) gcc_plugin: - needs to be rewritten diff --git a/test/test.sh b/test/test.sh index 94d28047..d5372233 100755 --- a/test/test.sh +++ b/test/test.sh @@ -102,7 +102,9 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with ${AFL_GCC}" } || { - cat errors + echo CUT------------------------------------------------------------------CUT + cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" } rm -rf in out errors @@ -156,7 +158,9 @@ test -e ../afl-clang-fast && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with llvm_mode" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with llvm_mode" } rm -rf in out errors @@ -231,7 +235,9 @@ test -e ../afl-qemu-trace && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with qemu_mode" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode" } rm -f errors @@ -246,7 +252,9 @@ test -e ../afl-qemu-trace && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with qemu_mode libcompcov" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode libcompcov" } } || $ECHO "$YELLOW[-] we cannot test qemu_mode libcompcov because it is not present" @@ -261,7 +269,9 @@ test -e ../afl-qemu-trace && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with persistent qemu_mode" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with persistent qemu_mode" exit 1 } @@ -286,20 +296,24 @@ test -d ../unicorn_mode/unicorn && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode" } rm -f errors - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 15 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 25 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V25 -U -i in -o out -d -- python ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" } || { + echo CUT------------------------------------------------------------------CUT cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode compcov" } rm -rf in out errors -- cgit 1.4.1 From 97f5ce52d129c460e4a8af3d55aefd05092a79a9 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 15 Oct 2019 16:48:05 +0200 Subject: v2.57c release --- README.md | 7 ++++--- TODO | 4 ++-- docs/ChangeLog | 9 +++++---- include/config.h | 2 +- 4 files changed, 12 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index bf8f69dc..f0e6faef 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,8 @@ # american fuzzy lop plus plus (afl++) - Release Version: 2.54c + Release Version: 2.57c - Github Version: 2.54d + Github Version: 2.57d includes all necessary/interesting changes from Google's afl 2.56b @@ -22,7 +22,7 @@ ## The enhancements compared to the original stock afl Many improvements were made over the official afl release - which did not - get any improvements since November 2017. + get any feature improvements since November 2017. Among other changes afl++ has a more performant llvm_mode, supports llvm up to version 9, QEMU 3.1, more speed and crashfixes for QEMU, @@ -103,6 +103,7 @@ These build options exist: * distrib: everything (for both binary-only and source code fuzzing) * install: installs everything you have compiled with the build options above * clean: cleans everything. for qemu_mode and unicorn_mode it means it deletes all downloads as well +* tests: runs test cases to ensure that all features are still working as they should * help: shows these build options [Unless you are on Mac OS X](https://developer.apple.com/library/archive/qa/qa1118/_index.html) you can also build statically linked versions of the diff --git a/TODO b/TODO index 696e9372..3ca13d6e 100644 --- a/TODO +++ b/TODO @@ -1,6 +1,6 @@ -Roadmap 2.55d: -============== +Roadmap 2.60: +============= afl-fuzz: - radamsa mutator diff --git a/docs/ChangeLog b/docs/ChangeLog index 7ccc8b66..aafb7bff 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -13,12 +13,13 @@ Want to stay in the loop on major new features? Join our mailing list by sending a mail to . ----------------------- -Version ++2.54d (dev): ----------------------- +-------------------------------- +Version ++2.54d-2.57c (release): +-------------------------------- + - we jump to 2.57 instead of 2.55 to catch up with Google's versioning - persistent mode for QEMU (see qemu_mode/README.md) - - custom mutator library is now a standard mutator, to exclusivly use it + - custom mutator library is now an additional mutator, to exclusivly use it add AFL_CUSTOM_MUTATOR_ONLY (that will trigger the previous behaviour) - new library qemu_mode/unsigaction which filters sigaction events - afl-fuzz: new command line option -I to execute a command on a new crash diff --git a/include/config.h b/include/config.h index f2732ad4..d331cd93 100644 --- a/include/config.h +++ b/include/config.h @@ -26,7 +26,7 @@ /* Version string: */ -#define VERSION "++2.54d" // c = release, d = volatile github dev +#define VERSION "++2.57c" // c = release, d = volatile github dev /****************************************************** * * -- cgit 1.4.1 From 3dec452a8a5a21fee524c5e4bc81e680c3a1fc04 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 15 Oct 2019 16:50:48 +0200 Subject: v2.57d --- include/config.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/config.h b/include/config.h index d331cd93..396224fb 100644 --- a/include/config.h +++ b/include/config.h @@ -26,7 +26,7 @@ /* Version string: */ -#define VERSION "++2.57c" // c = release, d = volatile github dev +#define VERSION "++2.57d" // c = release, d = volatile github dev /****************************************************** * * -- cgit 1.4.1 From 77695d75bb9619807dc27d3542e81b6b6332e2cf Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 15 Oct 2019 17:14:59 +0200 Subject: test.sh check to see if qemu persistent mode is faster --- test/test.sh | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/test/test.sh b/test/test.sh index d5372233..4fcd132e 100755 --- a/test/test.sh +++ b/test/test.sh @@ -234,6 +234,7 @@ test -e ../afl-qemu-trace && { } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with qemu_mode" + RUNTIME=`grep execs_done out/fuzzer_stats | awk '{print$3}'` } || { echo CUT------------------------------------------------------------------CUT cat errors @@ -268,6 +269,18 @@ test -e ../afl-qemu-trace && { } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with persistent qemu_mode" + RUNTIMEP=`grep execs_done out/fuzzer_stats | awk '{print$3}'` + test -n "$RUNTIME" -a -n "$RUNTIMEP" && { + SLOW=`expr $RUNTIME '*' 103` # persistent mode should be at least 3% faster - minimum! + FAST=`expr $RUNTIMEP '*' 100` + test "$SLOW" -lt "$FAST" && { + $ECHO "$GREEN[+] persistent qemu_mode was noticeable faster than standard qemu_mode" + } || { + $ECHO "$YELLOW[?] persistent qemu_mode was not noticeable faster than standard qemu_mode" + } + } || { + $ECHO "$YELLOW[?] we got no data on executions performed? weird!" + } } || { echo CUT------------------------------------------------------------------CUT cat errors -- cgit 1.4.1 From 1aec670c43f76c3cf5600a48f12e88c1fc79e07d Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Wed, 16 Oct 2019 20:37:58 +0200 Subject: add forgotten floating point comparisons in laf-intel/llvm_mode --- docs/ChangeLog | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/ChangeLog b/docs/ChangeLog index aafb7bff..8c799c44 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -42,6 +42,7 @@ Version ++2.54d-2.57c (release): - updated documentation - Wine mode to run Win32 binaries with the QEMU instrumentation (-W) - CompareCoverage for ARM target in QEMU/Unicorn + - laf-intel in llvm_mode now also handles floating point comparisons -------------------------- -- cgit 1.4.1 From c75abda5711d19340688be1dc8a9af7cd4ea0b7a Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 17 Oct 2019 09:30:50 +0200 Subject: return instead of exit in test-instr --- test-instr.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/test-instr.c b/test-instr.c index 71838462..3750b1b5 100644 --- a/test-instr.c +++ b/test-instr.c @@ -23,15 +23,19 @@ int main(int argc, char** argv) { char buff[8]; char* buf = buff; - if (argc > 1) + // we support command line parameter and stdin + if (argc > 1) { + buf = argv[1]; - else if (read(0, buf, sizeof(buf)) < 1) { + + } else if (read(0, buf, sizeof(buf)) < 1) { printf("Hum?\n"); - exit(1); + return 1; } + // we support three input cases (plus a 4th if stdin is used but there is no input) if (buf[0] == '0') printf("Looks like a zero to me!\n"); else if (buf[0] == '1') @@ -39,7 +43,6 @@ int main(int argc, char** argv) { else printf("Neither one or zero? How quaint!\n"); - exit(0); + return 0; } - -- cgit 1.4.1 From f2a1456e940949a1cb976795ff3bc054e0a3c3b5 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 17 Oct 2019 11:31:12 +0200 Subject: needed increased unicorn test time --- test/test.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index 4fcd132e..e93e19f8 100755 --- a/test/test.sh +++ b/test/test.sh @@ -302,9 +302,9 @@ test -d ../unicorn_mode/unicorn && { { mkdir -p in echo 0 > in/in - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 15 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 20 seconds" { - ../afl-fuzz -V15 -U -i in -o out -d -- python ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V20 -U -i in -o out -d -- python ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" -- cgit 1.4.1 From 73da639654aa4e91220eb0adcbe380800b06a768 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Fri, 18 Oct 2019 08:25:43 +0200 Subject: revert patch --- docs/ChangeLog | 7 +++++++ src/afl-fuzz-run.c | 8 ++++---- 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/docs/ChangeLog b/docs/ChangeLog index 8c799c44..f073123c 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -13,6 +13,13 @@ Want to stay in the loop on major new features? Join our mailing list by sending a mail to . +---------------------- +Version ++2.57d (dev): +---------------------- + + - revertedd patch to not unlink and recreate the input file, it resulted in performance loss + + -------------------------------- Version ++2.54d-2.57c (release): -------------------------------- diff --git a/src/afl-fuzz-run.c b/src/afl-fuzz-run.c index 46d12423..fc235b27 100644 --- a/src/afl-fuzz-run.c +++ b/src/afl-fuzz-run.c @@ -288,10 +288,10 @@ void write_to_testcase(void* mem, u32 len) { if (out_file) { - // unlink(out_file); /* Ignore errors. + unlink(out_file); /* Ignore errors. // */ - fd = open(out_file, O_WRONLY | O_CREAT | O_TRUNC, 0600); + fd = open(out_file, O_WRONLY | O_CREAT | O_EXCL, 0600); if (fd < 0) PFATAL("Unable to create '%s'", out_file); @@ -331,10 +331,10 @@ void write_with_gap(void* mem, u32 len, u32 skip_at, u32 skip_len) { if (out_file) { - // unlink(out_file); /* Ignore errors. + unlink(out_file); /* Ignore errors. // */ - fd = open(out_file, O_WRONLY | O_CREAT | O_TRUNC, 0600); + fd = open(out_file, O_WRONLY | O_CREAT | O_EXCL, 0600); if (fd < 0) PFATAL("Unable to create '%s'", out_file); -- cgit 1.4.1 From f4a74a3405d140e81111657ca28b994c5758286c Mon Sep 17 00:00:00 2001 From: van Hauser Date: Fri, 18 Oct 2019 10:10:47 +0200 Subject: added test/test-performance.sh --- docs/ChangeLog | 3 +- test/test-performance.sh | 189 +++++++++++++++++++++++++++++++++++++++++++++++ test/test.sh | 15 ++-- 3 files changed, 199 insertions(+), 8 deletions(-) create mode 100755 test/test-performance.sh diff --git a/docs/ChangeLog b/docs/ChangeLog index f073123c..9ffa17e3 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -17,7 +17,8 @@ sending a mail to . Version ++2.57d (dev): ---------------------- - - revertedd patch to not unlink and recreate the input file, it resulted in performance loss + - reverted patch to not unlink and recreate the input file, it resulted in performance loss + - added test/test-performance.sh script -------------------------------- diff --git a/test/test-performance.sh b/test/test-performance.sh new file mode 100755 index 00000000..198b58c4 --- /dev/null +++ b/test/test-performance.sh @@ -0,0 +1,189 @@ +#!/bin/bash + +FILE=~/.afl_performance + +test -e $FILE || { + echo Warning: This script measure the performance of afl++ and saves the result for future comparisons into $FILE + echo Press ENTER to continue or CONTROL-C to abort + read IN +} + +export AFL_QUIET=1 +unset AFL_EXIT_WHEN_DONE +unset AFL_SKIP_CPUFREQ +unset AFL_DEBUG +unset AFL_HARDEN +unset AFL_USE_ASAN +unset AFL_USE_MSAN +unset AFL_CC +unset AFL_PRELOAD +unset AFL_LLVM_WHITELIST +unset AFL_LLVM_INSTRIM +unset AFL_LLVM_LAF_SPLIT_SWITCHES +unset AFL_LLVM_LAF_TRANSFORM_COMPARES +unset AFL_LLVM_LAF_SPLIT_COMPARES + +# on OpenBSD we need to work with llvm from /usr/local/bin +test -e /usr/local/bin/opt && { + export PATH=/usr/local/bin:${PATH} +} +# on MacOS X we prefer afl-clang over afl-gcc, because +# afl-gcc does not work there +test `uname -s` = 'Darwin' -o `uname -s` = 'FreeBSD' && { + AFL_GCC=afl-clang +} || { + AFL_GCC=afl-gcc +} + +ECHO="printf %b\\n" +$ECHO \\101 2>&1 | grep -qE '^A' || { + ECHO= + test -e /bin/printf && { + ECHO="/bin/printf %b\\n" + $ECHO '\\101' 2>&1 | grep -qE '^A' || ECHO= + } +} +test -z "$ECHO" && { printf Error: printf command does not support octal character codes ; exit 1 ; } + +GREY="\\033[1;90m" +BLUE="\\033[1;94m" +GREEN="\\033[0;32m" +RED="\\033[0;31m" +YELLOW="\\033[1;93m" +RESET="\\033[0m" + +MEM_LIMIT=150 + +>> $FILE || { echo Error: can not write to $FILE ; exit 1 ; } + +echo Warning: this script is setting performance parameters with afl-system-config +sleep 1 +afl-system-config > /dev/null 2>&1 +echo Performance settings applied. +echo + +$ECHO "${RESET}${GREY}[*] starting afl++ performance test framework ..." + +$ECHO "$BLUE[*] Testing: ${AFL_GCC}" +GCC=x +test -e ../${AFL_GCC} -a -e ../afl-fuzz && { + ../${AFL_GCC} -o test-instr.plain ../test-instr.c > /dev/null 2>&1 + test -e test-instr.plain && { + $ECHO "$GREEN[+] ${AFL_GCC} compilation succeeded" + mkdir -p in + echo 0 > in/in + $ECHO "$GREY[*] running afl-fuzz for ${AFL_GCC} for 30 seconds" + { + ../afl-fuzz -V 30 -s 123 -m ${MEM_LIMIT} -i in -o out-gcc -- ./test-instr.plain + } >>errors 2>&1 + test -n "$( ls out-gcc/queue/id:000002* 2> /dev/null )" && { + GCC=`grep execs_done out-gcc/fuzzer_stats | awk '{print$3}'` + } || { + echo CUT---------------------------------------------------------------- + cat errors + echo CUT---------------------------------------------------------------- + $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" + } + rm -rf in out-gcc errors test-instr.plain + } || $ECHO "$RED[!] ${AFL_GCC} instrumentation failed" +} || $ECHO "$YELLOW[-] afl is not compiled, cannot test" + +$ECHO "$BLUE[*] Testing: llvm_mode" +LLVM=x +test -e ../afl-clang-fast -a -e ../afl-fuzz && { + ../afl-clang-fast -o test-instr.llvm ../test-instr.c > /dev/null 2>&1 + test -e test-instr.llvm && { + $ECHO "$GREEN[+] llvm_mode compilation succeeded" + mkdir -p in + echo 0 > in/in + $ECHO "$GREY[*] running afl-fuzz for llvm_mode for 30 seconds" + { + ../afl-fuzz -V 30 -s 123 -m ${MEM_LIMIT} -i in -o out-llvm -- ./test-instr.llvm + } >>errors 2>&1 + test -n "$( ls out-llvm/queue/id:000002* 2> /dev/null )" && { + LLVM=`grep execs_done out-llvm/fuzzer_stats | awk '{print$3}'` + } || { + echo CUT---------------------------------------------------------------- + cat errors + echo CUT---------------------------------------------------------------- + $ECHO "$RED[!] afl-fuzz is not working correctly with llvm_mode" + } + rm -rf in out-llvm errors test-instr.llvm + } || $ECHO "$RED[!] llvm_mode instrumentation failed" +} || $ECHO "$YELLOW[-] llvm_mode is not compiled, cannot test" + +$ECHO "$BLUE[*] Testing: qemu_mode" +QEMU=x +test -e ../afl-qemu-trace -a -e ../afl-fuzz && { + cc -o test-instr.qemu ../test-instr.c > /dev/null 2>&1 + test -e test-instr.qemu && { + $ECHO "$GREEN[+] native compilation with cc succeeded" + mkdir -p in + echo 0 > in/in + $ECHO "$GREY[*] running afl-fuzz for qemu_mode for 30 seconds" + { + ../afl-fuzz -Q -V 30 -s 123 -m ${MEM_LIMIT} -i in -o out-qemu -- ./test-instr.qemu + } >>errors 2>&1 + test -n "$( ls out-qemu/queue/id:000002* 2> /dev/null )" && { + QEMU=`grep execs_done out-qemu/fuzzer_stats | awk '{print$3}'` + } || { + echo CUT---------------------------------------------------------------- + cat errors + echo CUT---------------------------------------------------------------- + $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode" + } + rm -rf in out-qemu errors test-instr.qemu + } || $ECHO "$RED[!] qemu_mode instrumentation failed" +} || $ECHO "$YELLOW[-] qemu_mode is not compiled, cannot test" + +LOW_GCC= +HIGH_GCC= +LAST_GCC= +LOW_LLVM= +HIGH_LLVM= +LAST_LLVM= +LOW_QEMU= +HIGH_QEMU= +LAST_QEMU= + +test -s $FILE && { + while read LINE; do + G=`echo $LINE | awk '{print$1}'` + L=`echo $LINE | awk '{print$2}'` + Q=`echo $LINE | awk '{print$3}'` + test "$G" = x && G= + test "$L" = x && L= + test "$Q" = x && Q= + test -n "$G" && LAST_GCC=$G + test -n "$L" && LAST_LLVM=$L + test -n "$Q" && LAST_QEMU=$Q + test -n "$G" -a -z "$LOW_GCC" && LOW_GCC=$G || { + test -n "$G" -a "$G" -lt "$LOW_GCC" 2> /dev/null && LOW_GCC=$G + } + test -n "$L" -a -z "$LOW_LLVM" && LOW_LLVM=$L || { + test -n "$L" -a "$L" -lt "$LOW_LLVM" 2> /dev/null && LOW_LLVM=$L + } + test -n "$Q" -a -z "$LOW_QEMU" && LOW_QEMU=$Q || { + test -n "$Q" -a "$Q" -lt "$LOW_QEMU" 2> /dev/null && LOW_QEMU=$Q + } + test -n "$G" -a -z "$HIGH_GCC" && HIGH_GCC=$G || { + test -n "$G" -a "$G" -gt "$HIGH_GCC" 2> /dev/null && HIGH_GCC=$G + } + test -n "$L" -a -z "$HIGH_LLVM" && HIGH_LLVM=$L || { + test -n "$L" -a "$L" -gt "$HIGH_LLVM" 2> /dev/null && HIGH_LLVM=$L + } + test -n "$Q" -a -z "$HIGH_QEMU" && HIGH_QEMU=$Q || { + test -n "$Q" -a "$Q" -gt "$HIGH_QEMU" 2> /dev/null && HIGH_QEMU=$Q + } + done < $FILE + $ECHO "$YELLOW[!] Reading saved data from $FILE completed, please compare the results:" + $ECHO "$BLUE[!] afl-cc: lowest=$LOW_GCC highest=$HIGH_GCC last=$LAST_GCC current=$GCC" + $ECHO "$BLUE[!] llvm_mode: lowest=$LOW_LLVM highest=$HIGH_LLVM last=$LAST_LLVM current=$LLVM" + $ECHO "$BLUE[!] qemu_mode: lowest=$LOW_QEMU highest=$HIGH_QEMU last=$LAST_QEMU current=$QEMU" +} || { + $ECHO "$YELLOW[!] First run, just saving data" + $ECHO "$BLUE[!] afl-gcc=$GCC llvm_mode=$LLVM qemu_mode=$QEMU" +} +echo "$GCC $LLVM $QEMU" >> $FILE +$ECHO "$GREY[*] done." +$ECHO "$RESET" diff --git a/test/test.sh b/test/test.sh index e93e19f8..ab2985fe 100755 --- a/test/test.sh +++ b/test/test.sh @@ -46,10 +46,11 @@ test -e /usr/local/bin/opt && { # on MacOS X we prefer afl-clang over afl-gcc, because # afl-gcc does not work there test `uname -s` = 'Darwin' -o `uname -s` = 'FreeBSD' && { -AFL_GCC=afl-clang + AFL_GCC=afl-clang } || { -AFL_GCC=afl-gcc + AFL_GCC=afl-gcc } + GREY="\\033[1;90m" BLUE="\\033[1;94m" GREEN="\\033[0;32m" @@ -102,9 +103,9 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with ${AFL_GCC}" } || { - echo CUT------------------------------------------------------------------CUT - cat errors - echo CUT------------------------------------------------------------------CUT + echo CUT------------------------------------------------------------------CUT + cat errors + echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" } rm -rf in out errors @@ -116,9 +117,9 @@ $ECHO "$BLUE[*] Testing: llvm_mode" test -e ../afl-clang-fast && { # on FreeBSD need to set AFL_CC if which clang >/dev/null; then - export AFL_CC=`which clang` + export AFL_CC=`which clang` else - export AFL_CC=`llvm-config --bindir`/clang + export AFL_CC=`llvm-config --bindir`/clang fi ../afl-clang-fast -o test-instr.plain ../test-instr.c > /dev/null 2>&1 AFL_HARDEN=1 ../afl-clang-fast -o test-compcov.harden test-compcov.c > /dev/null 2>&1 -- cgit 1.4.1 From b1822f26022c323e4b47198abbb7d5f5ea6a57e5 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 18 Oct 2019 18:01:33 +0200 Subject: reintegrate gcc_plugin --- .gitignore | 2 + Makefile | 4 + docs/env_variables.txt | 31 ++- gcc_plugin/Makefile | 130 +++++++++++ gcc_plugin/README.gcc.md | 162 +++++++++++++ gcc_plugin/README.whitelist.md | 74 ++++++ gcc_plugin/afl-gcc-fast.c | 283 +++++++++++++++++++++++ gcc_plugin/afl-gcc-pass.so.cc | 505 +++++++++++++++++++++++++++++++++++++++++ gcc_plugin/afl-gcc-rt.o.c | 224 ++++++++++++++++++ llvm_mode/README.whitelist.md | 2 +- 10 files changed, 1406 insertions(+), 11 deletions(-) create mode 100644 gcc_plugin/Makefile create mode 100644 gcc_plugin/README.gcc.md create mode 100644 gcc_plugin/README.whitelist.md create mode 100644 gcc_plugin/afl-gcc-fast.c create mode 100644 gcc_plugin/afl-gcc-pass.so.cc create mode 100644 gcc_plugin/afl-gcc-rt.o.c diff --git a/.gitignore b/.gitignore index f7907c76..ac3a653b 100644 --- a/.gitignore +++ b/.gitignore @@ -23,6 +23,8 @@ afl-clang-fast.8 afl-cmin.8 afl-fuzz.8 afl-gcc.8 +afl-gcc-fast.8 +afl-g++-fast.8 afl-gotcpu.8 afl-plot.8 afl-showmap.8 diff --git a/Makefile b/Makefile index 4c8cf402..8cf3d4fd 100644 --- a/Makefile +++ b/Makefile @@ -99,6 +99,7 @@ all: test_x86 test_shm test_python27 ready $(PROGS) afl-as test_build all_done man: $(MANPAGES) -$(MAKE) -C llvm_mode + -$(MAKE) -C gcc_plugin tests: source-only @cd test ; ./test.sh @@ -252,6 +253,7 @@ clean: rm -f $(PROGS) afl-as as afl-g++ afl-clang afl-clang++ *.o src/*.o *~ a.out core core.[1-9][0-9]* *.stackdump .test .test1 .test2 test-instr .test-instr0 .test-instr1 qemu_mode/qemu-3.1.1.tar.xz afl-qemu-trace afl-gcc-fast afl-gcc-pass.so afl-gcc-rt.o afl-g++-fast *.so unicorn_mode/24f55a7973278f20f0de21b904851d99d4716263.tar.gz *.8 rm -rf out_dir qemu_mode/qemu-3.1.1 unicorn_mode/unicorn *.dSYM */*.dSYM -$(MAKE) -C llvm_mode clean + -$(MAKE) -C gcc_plugin clean $(MAKE) -C libdislocator clean $(MAKE) -C libtokencap clean $(MAKE) -C qemu_mode/unsigaction clean @@ -259,6 +261,7 @@ clean: distrib: all -$(MAKE) -C llvm_mode + -$(MAKE) -C gcc_plugin $(MAKE) -C libdislocator $(MAKE) -C libtokencap cd qemu_mode && sh ./build_qemu_support.sh @@ -272,6 +275,7 @@ binary-only: all source-only: all -$(MAKE) -C llvm_mode + -$(MAKE) -C gcc_plugin $(MAKE) -C libdislocator $(MAKE) -C libtokencap diff --git a/docs/env_variables.txt b/docs/env_variables.txt index e763118e..427f8cca 100644 --- a/docs/env_variables.txt +++ b/docs/env_variables.txt @@ -71,11 +71,11 @@ tools make fairly broad use of environmental variables: - Setting AFL_CAL_FAST will speed up the initial calibration, if the application is very slow -2) Settings for afl-clang-fast / afl-clang-fast++ -------------------------------------------------- +2) Settings for afl-clang-fast / afl-clang-fast++ / afl-gcc-fast / afl-g++-fast +--------------------------------------------------------------------------------- -The native LLVM instrumentation helper accepts a subset of the settings -discussed in section #1, with the exception of: +The native instrumentation helpers (llvm_mode and gcc_plugin) accept a subset +of the settings discussed in section #1, with the exception of: - AFL_AS, since this toolchain does not directly invoke GNU as. @@ -100,7 +100,7 @@ Then there are a few specific features that are only available in llvm_mode: - Setting AFL_LLVM_LAF_SPLIT_COMPARES will split all floating point and 64, 32 and 16 bit integer CMP instructions - See llvm_mode/README.laf-intel for more information. + See llvm_mode/README.laf-intel.md for more information. WHITELIST ========= @@ -109,7 +109,7 @@ Then there are a few specific features that are only available in llvm_mode: - Setting AFL_LLVM_WHITELIST with a filename will only instrument those files that match the names listed in this file. - See llvm_mode/README.whitelist for more information. + See llvm_mode/README.whitelist.md for more information. INSTRIM ======= @@ -122,7 +122,7 @@ Then there are a few specific features that are only available in llvm_mode: afl-fuzz will only be able to see the path the loop took, but not how many times it was called (unless it is a complex loop). - See llvm_mode/README.instrim + See llvm_mode/README.instrim.md NOT_ZERO ======== @@ -133,7 +133,18 @@ Then there are a few specific features that are only available in llvm_mode: slowdown due a performance issue that is only fixed in llvm 9+. This feature increases path discovery by a little bit. - See llvm_mode/README.neverzero + See llvm_mode/README.neverzero.md + +Then there are a few specific features that are only available in the gcc_plugin: + + WHITELIST + ========= + This feature allows selective instrumentation of the source + + - Setting AFL_GCC_WHITELIST with a filename will only instrument those + files that match the names listed in this file (one filename per line). + + See gcc_plugin/README.whitelist.md for more information. 3) Settings for afl-fuzz ------------------------ @@ -257,7 +268,7 @@ The QEMU wrapper used to instrument binary-only code supports several settings: - Setting AFL_COMPCOV_LEVEL enables the CompareCoverage tracing of all cmp and sub in x86 and x86_64 and memory comparions functions (e.g. strcmp, memcmp, ...) when libcompcov is preloaded using AFL_PRELOAD. - More info at qemu_mode/libcompcov/README.compcov. + More info at qemu_mode/libcompcov/README.md. There are two levels at the moment, AFL_COMPCOV_LEVEL=1 that instruments only comparisons with immediate values / read-only memory and AFL_COMPCOV_LEVEL=2 that instruments all the comparions. Level 2 is more @@ -318,7 +329,7 @@ of decimal. 8) Settings for libdislocator.so -------------------------------- -The library honors three environmental variables: +The library honors these environmental variables: - AFL_LD_LIMIT_MB caps the size of the maximum heap usage permitted by the library, in megabytes. The default value is 1 GB. Once this is exceeded, diff --git a/gcc_plugin/Makefile b/gcc_plugin/Makefile new file mode 100644 index 00000000..d10eba49 --- /dev/null +++ b/gcc_plugin/Makefile @@ -0,0 +1,130 @@ +# +# american fuzzy lop - GCC plugin instrumentation +# ----------------------------------------------- +# +# Written by Austin Seipp and +# Laszlo Szekeres and +# Michal Zalewski and +# Heiko Eißfeldt +# +# GCC integration design is based on the LLVM design, which comes +# from Laszlo Szekeres. +# +# Copyright 2015 Google Inc. All rights reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at: +# +# http://www.apache.org/licenses/LICENSE-2.0 +# + +PREFIX ?= /usr/local +HELPER_PATH = $(PREFIX)/lib/afl +BIN_PATH = $(PREFIX)/bin + +CFLAGS ?= -O3 -g -funroll-loops +CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -Wno-pointer-sign \ + -DAFL_PATH=\"$(HELPER_PATH)\" -DBIN_PATH=\"$(BIN_PATH)\" \ + +CXXFLAGS ?= -O3 -g -funroll-loops +CXXEFLAGS := $(CXXFLAGS) -Wall -D_FORTIFY_SOURCE=2 + +CC ?= gcc +CXX ?= g++ + +PLUGIN_FLAGS = -fPIC -fno-rtti -I"$(shell $(CC) -print-file-name=plugin)/include" + +PROGS = ../afl-gcc-fast ../afl-gcc-pass.so ../afl-gcc-rt.o + +ifeq "$(shell echo '\#include @\#include @int main() { int _id = shmget(IPC_PRIVATE, 65536, IPC_CREAT | IPC_EXCL | 0600); shmctl(_id, IPC_RMID, 0); return 0;}' | tr @ '\n' | $(CC) -x c - -o .test2 2>/dev/null && echo 1 || echo 0 )" "1" + SHMAT_OK=1 +else + SHMAT_OK=0 + CFLAGS+=-DUSEMMAP=1 + LDFLAGS += -lrt +endif + +ifeq "$(TEST_MMAP)" "1" + SHMAT_OK=0 + CFLAGS+=-DUSEMMAP=1 + LDFLAGS += -lrt +endif + + +all: test_shm test_deps $(PROGS) afl-gcc-fast.8 test_build all_done + +ifeq "$(SHMAT_OK)" "1" + +test_shm: + @echo "[+] shmat seems to be working." + @rm -f .test2 + +else + +test_shm: + @echo "[-] shmat seems not to be working, switching to mmap implementation" + +endif + + +test_deps: + @echo "[*] Checking for working '$(CC)'..." + @which $(CC) >/dev/null 2>&1 || ( echo "[-] Oops, can't find '$(CC)'. Make sure that it's in your \$$PATH (or set \$$CC and \$$CXX)."; exit 1 ) + @echo "[*] Checking for gcc for plugin support..." + @$(CC) -v 2>&1 | grep -q -- --enable-plugin || ( echo "[-] Oops, this gcc has not been configured with plugin support."; exit 1 ) + @echo "[*] Checking for gcc plugin development header files..." + @test -d `$(CC) -print-file-name=plugin`/include || ( echo "[-] Oops, can't find gcc header files. Be sure to install 'gcc-X-plugin-dev'."; exit 1 ) + @echo "[*] Checking for '../afl-showmap'..." + @test -f ../afl-showmap || ( echo "[-] Oops, can't find '../afl-showmap'. Be sure to compile AFL first."; exit 1 ) + @echo "[+] All set and ready to build." + +../afl-gcc-fast: afl-gcc-fast.c | test_deps + $(CC) $(CFLAGS) $< -o $@ $(LDFLAGS) + ln -sf afl-gcc-fast ../afl-g++-fast + +../afl-gcc-pass.so: afl-gcc-pass.so.cc | test_deps + $(CXX) $(CXXEFLAGS) $(PLUGIN_FLAGS) -shared $< -o $@ + +../afl-gcc-rt.o: afl-gcc-rt.o.c | test_deps + $(CC) $(CFLAGS) -fPIC -c $< -o $@ + +test_build: $(PROGS) + @echo "[*] Testing the CC wrapper and instrumentation output..." + unset AFL_USE_ASAN AFL_USE_MSAN; AFL_QUIET=1 AFL_INST_RATIO=100 AFL_PATH=. AFL_CC=$(CC) ../afl-gcc-fast $(CFLAGS) ../test-instr.c -o test-instr $(LDFLAGS) +# unset AFL_USE_ASAN AFL_USE_MSAN; AFL_INST_RATIO=100 AFL_PATH=. AFL_CC=$(CC) ../afl-gcc-fast $(CFLAGS) ../test-instr.c -o test-instr $(LDFLAGS) + ../afl-showmap -m none -q -o .test-instr0 ./test-instr ../$@ + @echo .SH NAME >> ../$@ + @echo .B $* >> ../$@ + @echo >> ../$@ + @echo .SH SYNOPSIS >> ../$@ + @../$* -h 2>&1 | head -n 3 | tail -n 1 | sed 's/^\.\///' >> ../$@ + @echo >> ../$@ + @echo .SH OPTIONS >> ../$@ + @echo .nf >> ../$@ + @../$* -h 2>&1 | tail -n +4 >> ../$@ + @echo >> ../$@ + @echo .SH AUTHOR >> ../$@ + @echo "afl++ was written by Michal \"lcamtuf\" Zalewski and is maintained by Marc \"van Hauser\" Heuse , Heiko \"hexcoder-\" Eissfeldt and Andrea Fioraldi " >> ../$@ + @echo The homepage of afl++ is: https://github.com/vanhauser-thc/AFLplusplus >> ../$@ + @echo >> ../$@ + @echo .SH LICENSE >> ../$@ + @echo Apache License Version 2.0, January 2004 >> ../$@ + ln -sf afl-gcc-fast.8 ../afl-g++-fast.8 + +clean: + rm -f *.o *.so *~ a.out core core.[1-9][0-9]* test-instr .test-instr0 .test-instr1 + rm -f $(PROGS) ../afl-g++-fast ../afl-g*-fast.8 diff --git a/gcc_plugin/README.gcc.md b/gcc_plugin/README.gcc.md new file mode 100644 index 00000000..2e19e911 --- /dev/null +++ b/gcc_plugin/README.gcc.md @@ -0,0 +1,162 @@ +=========================================== +GCC-based instrumentation for afl-fuzz +====================================== + + (See ../docs/README.md for the general instruction manual.) + (See ../llvm_mode/README.md for the LLVM-based instrumentation.) + +!!! TODO items are: +!!! => inline instrumentation has to work! +!!! + + +## 1) Introduction + +The code in this directory allows you to instrument programs for AFL using +true compiler-level instrumentation, instead of the more crude +assembly-level rewriting approach taken by afl-gcc and afl-clang. This has +several interesting properties: + + - The compiler can make many optimizations that are hard to pull off when + manually inserting assembly. As a result, some slow, CPU-bound programs will + run up to around faster. + + The gains are less pronounced for fast binaries, where the speed is limited + chiefly by the cost of creating new processes. In such cases, the gain will + probably stay within 10%. + + - The instrumentation is CPU-independent. At least in principle, you should + be able to rely on it to fuzz programs on non-x86 architectures (after + building afl-fuzz with AFL_NOX86=1). + + - Because the feature relies on the internals of GCC, it is gcc-specific + and will *not* work with LLVM (see ../llvm_mode for an alternative). + +Once this implementation is shown to be sufficiently robust and portable, it +will probably replace afl-gcc. For now, it can be built separately and +co-exists with the original code. + +The idea and much of the implementation comes from Laszlo Szekeres. + +## 2) How to use + +In order to leverage this mechanism, you need to have modern enough GCC +(>= version 4.5.0) and the plugin headers installed on your system. That +should be all you need. On Debian machines, these headers can be acquired by +installing the `gcc--plugin-dev` packages. + +To build the instrumentation itself, type 'make'. This will generate binaries +called afl-gcc-fast and afl-g++-fast in the parent directory. Once this +is done, you can instrument third-party code in a way similar to the standard +operating mode of AFL, e.g.: + + CC=/path/to/afl/afl-gcc-fast ./configure [...options...] + make + +Be sure to also include CXX set to afl-g++-fast for C++ code. + +The tool honors roughly the same environmental variables as afl-gcc (see +../docs/env_variables.txt). This includes AFL_INST_RATIO, AFL_USE_ASAN, +AFL_HARDEN, and AFL_DONT_OPTIMIZE. + +Note: if you want the GCC plugin to be installed on your system for all +users, you need to build it before issuing 'make install' in the parent +directory. + +## 3) Gotchas, feedback, bugs + +This is an early-stage mechanism, so field reports are welcome. You can send bug +reports to . + +## 4) Bonus feature #1: deferred initialization + +AFL tries to optimize performance by executing the targeted binary just once, +stopping it just before main(), and then cloning this "master" process to get +a steady supply of targets to fuzz. + +Although this approach eliminates much of the OS-, linker- and libc-level +costs of executing the program, it does not always help with binaries that +perform other time-consuming initialization steps - say, parsing a large config +file before getting to the fuzzed data. + +In such cases, it's beneficial to initialize the forkserver a bit later, once +most of the initialization work is already done, but before the binary attempts +to read the fuzzed input and parse it; in some cases, this can offer a 10x+ +performance gain. You can implement delayed initialization in LLVM mode in a +fairly simple way. + +First, locate a suitable location in the code where the delayed cloning can +take place. This needs to be done with *extreme* care to avoid breaking the +binary. In particular, the program will probably malfunction if you select +a location after: + + - The creation of any vital threads or child processes - since the forkserver + can't clone them easily. + + - The initialization of timers via setitimer() or equivalent calls. + + - The creation of temporary files, network sockets, offset-sensitive file + descriptors, and similar shared-state resources - but only provided that + their state meaningfully influences the behavior of the program later on. + + - Any access to the fuzzed input, including reading the metadata about its + size. + +With the location selected, add this code in the appropriate spot: + +``` +#ifdef __AFL_HAVE_MANUAL_CONTROL + __AFL_INIT(); +#endif +``` + +You don't need the #ifdef guards, but they will make the program still work as +usual when compiled with a tool other than afl-gcc-fast/afl-clang-fast. + +Finally, recompile the program with afl-gcc-fast (afl-gcc or afl-clang will +*not* generate a deferred-initialization binary) - and you should be all set! + +## 5) Bonus feature #2: persistent mode + +Some libraries provide APIs that are stateless, or whose state can be reset in +between processing different input files. When such a reset is performed, a +single long-lived process can be reused to try out multiple test cases, +eliminating the need for repeated fork() calls and the associated OS overhead. + +The basic structure of the program that does this would be: + +``` + while (__AFL_LOOP(1000)) { + + /* Read input data. */ + /* Call library code to be fuzzed. */ + /* Reset state. */ + + } + + /* Exit normally */ +``` + +The numerical value specified within the loop controls the maximum number +of iterations before AFL will restart the process from scratch. This minimizes +the impact of memory leaks and similar glitches; 1000 is a good starting point. + +A more detailed template is shown in ../experimental/persistent_demo/. +Similarly to the previous mode, the feature works only with afl-gcc-fast or +afl-clang-fast; #ifdef guards can be used to suppress it when using other +compilers. + +Note that as with the previous mode, the feature is easy to misuse; if you +do not reset the critical state fully, you may end up with false positives or +waste a whole lot of CPU power doing nothing useful at all. Be particularly +wary of memory leaks and the state of file descriptors. + +When running in this mode, the execution paths will inherently vary a bit +depending on whether the input loop is being entered for the first time or +executed again. To avoid spurious warnings, the feature implies +AFL_NO_VAR_CHECK and hides the "variable path" warnings in the UI. + +PS. Because there are task switches still involved, the mode isn't as fast as +"pure" in-process fuzzing offered, say, by LLVM's LibFuzzer; but it is a lot +faster than the normal fork() model, and compared to in-process fuzzing, +should be a lot more robust. diff --git a/gcc_plugin/README.whitelist.md b/gcc_plugin/README.whitelist.md new file mode 100644 index 00000000..bcc02693 --- /dev/null +++ b/gcc_plugin/README.whitelist.md @@ -0,0 +1,74 @@ +======================================== +Using afl++ with partial instrumentation +======================================== + + This file describes how you can selectively instrument only the source files + that are interesting to you using the gcc instrumentation provided by + afl++. + + Originally developed by Christian Holler (:decoder) , + adapted to gcc plugin by hexcoder-. + + +## 1) Description and purpose + +When building and testing complex programs where only a part of the program is +the fuzzing target, it often helps to only instrument the necessary parts of +the program, leaving the rest uninstrumented. This helps to focus the fuzzer +on the important parts of the program, avoiding undesired noise and +disturbance by uninteresting code being exercised. + +For this purpose, I have added a "partial instrumentation" support to the gcc +plugin of AFLFuzz that allows you to specify on a source file level which files +should be compiled with or without instrumentation. + + +## 2) Building the gcc plugin + +The new code is part of the existing afl++ gcc plugin in the gcc_plugin/ +subdirectory. There is nothing specifically to do :) + + +## 3) How to use the partial instrumentation mode + +In order to build with partial instrumentation, you need to build with +afl-gcc-fast and afl-g++-fast respectively. The only required change is +that you need to set the environment variable AFL_GCC_WHITELIST when calling +the compiler. + +The environment variable must point to a file containing all the filenames +that should be instrumented. For matching, the filename that is being compiled +must end in the filename entry contained in this whitelist (to avoid breaking +the matching when absolute paths are used during compilation). + +For example if your source tree looks like this: + +``` +project/ +project/feature_a/a1.cpp +project/feature_a/a2.cpp +project/feature_b/b1.cpp +project/feature_b/b2.cpp +``` + +and you only want to test feature_a, then create a whitelist file containing: + +``` +feature_a/a1.cpp +feature_a/a2.cpp +``` + +However if the whitelist file contains only this, it works as well: + +``` +a1.cpp +a2.cpp +``` + +but it might lead to files being unwantedly instrumented if the same filename +exists somewhere else in the project directories. + +The created whitelist file is then set to AFL_GCC_WHITELIST when you compile +your program. For each file that didn't match the whitelist, the compiler will +issue a warning at the end stating that no blocks were instrumented. If you +didn't intend to instrument that file, then you can safely ignore that warning. diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c new file mode 100644 index 00000000..8be05bb5 --- /dev/null +++ b/gcc_plugin/afl-gcc-fast.c @@ -0,0 +1,283 @@ +/* + american fuzzy lop - GCC wrapper for GCC plugin + ------------------------------------------------ + + Written by Austin Seipp and + Laszlo Szekeres and + Michal Zalewski + + GCC integration design is based on the LLVM design, which comes + from Laszlo Szekeres. + + Copyright 2015 Google Inc. All rights reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at: + + http://www.apache.org/licenses/LICENSE-2.0 + + This program is a drop-in replacement for gcc, similar in most + respects to ../afl-gcc, but with compiler instrumentation through a + plugin. It tries to figure out compilation mode, adds a bunch of + flags, and then calls the real compiler. + + */ + +#define AFL_MAIN + +#include "../config.h" +#include "../types.h" +#include "../include/debug.h" +#include "../include/alloc-inl.h" + +#include +#include +#include +#include + +static u8* obj_path; /* Path to runtime libraries */ +static u8** cc_params; /* Parameters passed to the real CC */ +static u32 cc_par_cnt = 1; /* Param count, including argv0 */ + + +/* Try to find the runtime libraries. If that fails, abort. */ + +static void find_obj(u8* argv0) { + + u8 *afl_path = getenv("AFL_PATH"); + u8 *slash, *tmp; + + if (afl_path) { + + tmp = alloc_printf("%s/afl-gcc-rt.o", afl_path); + + if (!access(tmp, R_OK)) { + obj_path = afl_path; + ck_free(tmp); + return; + } + + ck_free(tmp); + + } + + slash = strrchr(argv0, '/'); + + if (slash) { + + u8 *dir; + + *slash = 0; + dir = ck_strdup(argv0); + *slash = '/'; + + tmp = alloc_printf("%s/afl-gcc-rt.o", dir); + + if (!access(tmp, R_OK)) { + obj_path = dir; + ck_free(tmp); + return; + } + + ck_free(tmp); + ck_free(dir); + + } + + if (!access(AFL_PATH "/afl-gcc-rt.o", R_OK)) { + obj_path = AFL_PATH; + return; + } + + FATAL("Unable to find 'afl-gcc-rt.o' or 'afl-gcc-pass.so'. Please set AFL_PATH"); +} + + +/* Copy argv to cc_params, making the necessary edits. */ + +static void edit_params(u32 argc, char** argv) { + + u8 fortify_set = 0, asan_set = 0, x_set = 0, maybe_linking = 1; + u8 *name; + + cc_params = ck_alloc((argc + 64) * sizeof(u8*)); + + name = strrchr(argv[0], '/'); + if (!name) name = argv[0]; else name++; + + if (!strcmp(name, "afl-g++-fast")) { + u8* alt_cxx = getenv("AFL_CXX"); + cc_params[0] = alt_cxx ? alt_cxx : (u8*)"g++"; + } else { + u8* alt_cc = getenv("AFL_CC"); + cc_params[0] = alt_cc ? alt_cc : (u8*)"gcc"; + } + + char* fplugin_arg = alloc_printf("-fplugin=%s/afl-gcc-pass.so", obj_path); + cc_params[cc_par_cnt++] = fplugin_arg; + + while (--argc) { + u8* cur = *(++argv); + +#if defined(__x86_64__) + if (!strcmp(cur, "-m32")) FATAL("-m32 is not supported"); +#endif + + if (!strcmp(cur, "-x")) x_set = 1; + + if (!strcmp(cur, "-c") || !strcmp(cur, "-S") || !strcmp(cur, "-E") || + !strcmp(cur, "-v")) maybe_linking = 0; + + if (!strcmp(cur, "-fsanitize=address") || + !strcmp(cur, "-fsanitize=memory")) asan_set = 1; + + if (strstr(cur, "FORTIFY_SOURCE")) fortify_set = 1; + + cc_params[cc_par_cnt++] = cur; + + } + + if (getenv("AFL_HARDEN")) { + + cc_params[cc_par_cnt++] = "-fstack-protector-all"; + + if (!fortify_set) + cc_params[cc_par_cnt++] = "-D_FORTIFY_SOURCE=2"; + + } + + if (!asan_set) { + + if (getenv("AFL_USE_ASAN")) { + + cc_params[cc_par_cnt++] = "-fsanitize=address"; + + if (getenv("AFL_USE_MSAN")) + FATAL("ASAN and MSAN are mutually exclusive"); + + } else if (getenv("AFL_USE_MSAN")) { + + cc_params[cc_par_cnt++] = "-fsanitize=memory"; + + if (getenv("AFL_USE_ASAN")) + FATAL("ASAN and MSAN are mutually exclusive"); + + } + + } + + if (!getenv("AFL_DONT_OPTIMIZE")) { + + cc_params[cc_par_cnt++] = "-g"; + cc_params[cc_par_cnt++] = "-O3"; + cc_params[cc_par_cnt++] = "-funroll-loops"; + + } + + cc_params[cc_par_cnt++] = "-D__AFL_HAVE_MANUAL_CONTROL=1"; + + /* When the user tries to use persistent or deferred forkserver modes by + appending a single line to the program, we want to reliably inject a + signature into the binary (to be picked up by afl-fuzz) and we want + to call a function from the runtime .o file. This is unnecessarily + painful for three reasons: + + 1) We need to convince the compiler not to optimize out the signature. + This is done with __attribute__((used)). + + 2) We need to convince the linker, when called with -Wl,--gc-sections, + not to do the same. This is done by forcing an assignment to a + 'volatile' pointer. + + 3) We need to declare __afl_persistent_loop() in the global namespace, + but doing this within a method in a class is hard - :: and extern "C" + are forbidden and __attribute__((alias(...))) doesn't work. Hence the + __asm__ aliasing trick. + + */ + + cc_params[cc_par_cnt++] = "-D__AFL_LOOP(_A)=" + "({ static volatile char *_B __attribute__((used)); " + " _B = (char*)\"" PERSIST_SIG "\"; " +#ifdef __APPLE__ + "int _L(unsigned int) __asm__(\"___afl_persistent_loop\"); " +#else + "int _L(unsigned int) __asm__(\"__afl_persistent_loop\"); " +#endif /* ^__APPLE__ */ + "_L(_A); })"; + + cc_params[cc_par_cnt++] = "-D__AFL_INIT()=" + "do { static volatile char *_A __attribute__((used)); " + " _A = (char*)\"" DEFER_SIG "\"; " +#ifdef __APPLE__ + "void _I(void) __asm__(\"___afl_manual_init\"); " +#else + "void _I(void) __asm__(\"__afl_manual_init\"); " +#endif /* ^__APPLE__ */ + "_I(); } while (0)"; + + if (maybe_linking) { + + if (x_set) { + cc_params[cc_par_cnt++] = "-x"; + cc_params[cc_par_cnt++] = "none"; + } + + cc_params[cc_par_cnt++] = alloc_printf("%s/afl-gcc-rt.o", obj_path); + + } + + cc_params[cc_par_cnt] = NULL; + +} + + +/* Main entry point */ + +int main(int argc, char** argv) { + + if (isatty(2) && !getenv("AFL_QUIET")) { + + SAYF(cCYA "afl-gcc-fast " cBRI VERSION cRST " initially by , maintainer: hexcoder-\n"); + + } + + if (argc < 2) { + + SAYF("\n" + "This is a helper application for afl-fuzz. It serves as a drop-in replacement\n" + "for gcc, letting you recompile third-party code with the required runtime\n" + "instrumentation. A common use pattern would be one of the following:\n\n" + + " CC=%s/afl-gcc-fast ./configure\n" + " CXX=%s/afl-g++-fast ./configure\n\n" + + "In contrast to the traditional afl-gcc tool, this version is implemented as\n" + "a GCC plugin and tends to offer improved performance with slow programs\n" + "(similarly to the LLVM plugin used by afl-clang-fast).\n\n" + + "You can specify custom next-stage toolchain via AFL_CC and AFL_CXX. Setting\n" + "AFL_HARDEN enables hardening optimizations in the compiled code.\n\n", + BIN_PATH, BIN_PATH); + + exit(1); + + } + + + find_obj(argv[0]); + + edit_params(argc, argv); +/*if (isatty(2) && !getenv("AFL_QUIET")) { + printf("Calling \"%s\" with:\n", cc_params[0]); + for(int i=1; i with bits from + Emese Revfy + + Fixed by Heiko Eißfeldt 2019 for AFL++ + + GCC integration design is based on the LLVM design, which comes + from Laszlo Szekeres. Some of the boilerplate code below for + afl_pass to adapt to different GCC versions was taken from Emese + Revfy's Size Overflow plugin for GCC, licensed under the GPLv2/v3. + + (NOTE: this plugin code is under GPLv3, in order to comply with the + GCC runtime library exception, which states that you may distribute + "Target Code" from the compiler under a license of your choice, as + long as the "Compilation Process" is "Eligible", and contains no + GPL-incompatible software in GCC "during the process of + transforming high level code to target code". In this case, the + plugin will be used to generate "Target Code" during the + "Compilation Process", and thus it must be GPLv3 to be "eligible".) + + Copyright (C) 2015 Austin Seipp + + 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 3 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, see . + + */ + +#define BUILD_INLINE_INST + +#include "../config.h" +#include "../include/debug.h" + +/* clear helper AFL types pulls in, which intervene with gcc-plugin geaders from GCC-8 */ +#ifdef likely +#undef likely +#endif +#ifdef unlikely +#undef unlikely +#endif + + +#include +#include +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* -------------------------------------------------------------------------- */ +/* -- AFL instrumentation pass ---------------------------------------------- */ + +static int be_quiet = 0; +static unsigned int inst_ratio = 100; +static bool inst_ext = true; +static std::list myWhitelist; + +static unsigned int ext_call_instrument(function *fun) { + /* Instrument all the things! */ + basic_block bb; + unsigned finst_blocks = 0; + unsigned fcnt_blocks = 0; + + tree fntype = build_function_type_list( + void_type_node, /* return */ + uint32_type_node, /* args */ + NULL_TREE); /* done */ + tree fndecl = build_fn_decl("__afl_trace", fntype); + TREE_STATIC(fndecl) = 1; /* Defined elsewhere */ + TREE_PUBLIC(fndecl) = 1; /* Public */ + DECL_EXTERNAL(fndecl) = 1; /* External linkage */ + DECL_ARTIFICIAL(fndecl) = 1; /* Injected by compiler */ + + FOR_EACH_BB_FN(bb, fun) { + gimple_seq fcall; + gimple_seq seq = NULL; + gimple_stmt_iterator bentry; + ++fcnt_blocks; + + // only instrument if this basic block is the destination of a previous + // basic block that has multiple successors + // this gets rid of ~5-10% of instrumentations that are unnecessary + // result: a little more speed and less map pollution + + int more_than_one = -1; + edge ep; + edge_iterator eip; + FOR_EACH_EDGE (ep, eip, bb->preds) { + int count = 0; + if (more_than_one == -1) + more_than_one = 0; + + basic_block Pred = ep->src; + edge es; + edge_iterator eis; + FOR_EACH_EDGE (es, eis, Pred->succs) { + basic_block Succ = es->dest; + if (Succ != NULL) count++; + } + if (count > 1) + more_than_one = 1; + } + if (more_than_one != 1) + continue; + + /* Bail on this block if we trip the specified ratio */ + if (R(100) >= inst_ratio) continue; + + /* Make up cur_loc */ + unsigned int rand_loc = R(MAP_SIZE); + tree cur_loc = build_int_cst(uint32_type_node, rand_loc); + + /* Update bitmap via external call */ + /* to quote: + * /+ Trace a basic block with some ID +/ + * void __afl_trace(u32 x); + */ + + fcall = gimple_build_call(fndecl, 1, cur_loc); /* generate the function _call_ to above built reference, with *1* parameter -> the random const for the location */ + gimple_seq_add_stmt(&seq, fcall); /* and insert into a sequence */ + + /* Done - grab the entry to the block and insert sequence */ + bentry = gsi_after_labels(bb); + gsi_insert_seq_before(&bentry, seq, GSI_SAME_STMT); + + ++finst_blocks; + } + + /* Say something nice. */ + if (!be_quiet) { + if (!finst_blocks) + WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST ), + function_name(fun)); + else if (finst_blocks < fcnt_blocks) + OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST ), + finst_blocks, fcnt_blocks, + function_name(fun)); + else + OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST ), + finst_blocks, + function_name(fun)); + } + + return 0; +} + +static unsigned int inline_instrument(function *fun) { + + /* Instrument all the things! */ + basic_block bb; + unsigned finst_blocks = 0; + unsigned fcnt_blocks = 0; + + /* Set up global type declarations */ + tree map_type = build_pointer_type(unsigned_char_type_node); + tree map_ptr_g = build_decl(UNKNOWN_LOCATION, VAR_DECL, + get_identifier_with_length("__afl_area_ptr", 14), map_type); + TREE_USED(map_ptr_g) = 1; + TREE_STATIC(map_ptr_g) = 1; /* Defined elsewhere */ + DECL_EXTERNAL(map_ptr_g) = 1; /* External linkage */ + DECL_PRESERVE_P(map_ptr_g) = 1; + DECL_ARTIFICIAL(map_ptr_g) = 1; /* Injected by compiler */ + rest_of_decl_compilation(map_ptr_g, 1, 0); + + tree prev_loc_g = build_decl(UNKNOWN_LOCATION, VAR_DECL, + get_identifier_with_length("__afl_prev_loc", 14), uint32_type_node); + TREE_USED(prev_loc_g) = 1; + TREE_STATIC(prev_loc_g) = 1; /* Defined elsewhere */ + DECL_EXTERNAL(prev_loc_g) = 1; /* External linkage */ + DECL_PRESERVE_P(prev_loc_g) = 1; + DECL_ARTIFICIAL(prev_loc_g) = 1; /* Injected by compiler */ + rest_of_decl_compilation(prev_loc_g, 1, 0); + + FOR_EACH_BB_FN(bb, fun) { + gimple_seq seq = NULL; + gimple_stmt_iterator bentry; + ++fcnt_blocks; + + // only instrument if this basic block is the destination of a previous + // basic block that has multiple successors + // this gets rid of ~5-10% of instrumentations that are unnecessary + // result: a little more speed and less map pollution + + int more_than_one = -1; + edge ep; + edge_iterator eip; + FOR_EACH_EDGE (ep, eip, bb->preds) { + int count = 0; + if (more_than_one == -1) + more_than_one = 0; + + basic_block Pred = ep->src; + edge es; + edge_iterator eis; + FOR_EACH_EDGE (es, eis, Pred->succs) { + basic_block Succ = es->dest; + if (Succ != NULL) count++; + } + if (count > 1) + more_than_one = 1; + } + if (more_than_one != 1) + continue; + + /* Bail on this block if we trip the specified ratio */ + if (R(100) >= inst_ratio) continue; + + /* Make up cur_loc */ + + unsigned int rand_loc = R(MAP_SIZE); + tree cur_loc = build_int_cst(uint32_type_node, rand_loc); + + /* Load prev_loc, xor with cur_loc */ + // gimple_assign + tree prev_loc = create_tmp_var_raw(uint32_type_node, "prev_loc"); + gassign *g = gimple_build_assign(prev_loc, VAR_DECL, prev_loc_g); + gimple_seq_add_stmt(&seq, g); // load prev_loc + update_stmt(g); + + // gimple_assign + tree area_off = create_tmp_var_raw(uint32_type_node, "area_off"); + g = gimple_build_assign(area_off, BIT_XOR_EXPR, prev_loc, cur_loc); + gimple_seq_add_stmt(&seq, g); // area_off = prev_loc ^ cur_loc + update_stmt(g); + + /* Update bitmap */ + + tree one = build_int_cst(unsigned_char_type_node, 1); +// tree zero = build_int_cst(unsigned_char_type_node, 0); + + // gimple_assign + tree map_ptr = create_tmp_var(map_type, "map_ptr"); + tree map_ptr2 = create_tmp_var(map_type, "map_ptr2"); + + g = gimple_build_assign(map_ptr, map_ptr_g); + gimple_seq_add_stmt(&seq, g); // map_ptr = __afl_area_ptr + update_stmt(g); + +#if 0 + tree addr = build2(ADDR_EXPR, map_type, map_ptr, area_off); + g = gimple_build_assign(map_ptr2, MODIFY_EXPR, addr); + gimple_seq_add_stmt(&seq, g); // map_ptr2 = map_ptr + area_off + update_stmt(g); +#else + g = gimple_build_assign(map_ptr2, PLUS_EXPR, map_ptr, area_off); + gimple_seq_add_stmt(&seq, g); // map_ptr2 = map_ptr + area_off + update_stmt(g); +#endif + // gimple_assign + tree tmp1 = create_tmp_var_raw(unsigned_char_type_node, "tmp1"); + g = gimple_build_assign(tmp1, MEM_REF, map_ptr2); + gimple_seq_add_stmt(&seq, g); // tmp1 = *map_ptr2 + update_stmt(g); + + // gimple_assign + tree tmp2 = create_tmp_var_raw(unsigned_char_type_node, "tmp2"); + g = gimple_build_assign(tmp2, PLUS_EXPR, tmp1, one); + gimple_seq_add_stmt(&seq, g); // tmp2 = tmp1 + 1 + update_stmt(g); + + // TODO: neverZero: here we have to check if tmp3 == 0 + // and add 1 if so + + // gimple_assign +// tree map_ptr3 = create_tmp_var_raw(map_type, "map_ptr3"); + g = gimple_build_assign(map_ptr_g, INDIRECT_REF, tmp2); + gimple_seq_add_stmt(&seq, g); // *map_ptr3 = tmp2 + update_stmt(g); + + /* Set prev_loc to cur_loc >> 1 */ + + // gimple_assign + tree shifted_loc = build_int_cst(TREE_TYPE(prev_loc_g), rand_loc >> 1); + tree prev_loc2 = create_tmp_var_raw(uint32_type_node, "prev_loc2"); + g = gimple_build_assign(prev_loc2, shifted_loc); + gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 + update_stmt(g); + g = gimple_build_assign(prev_loc_g, prev_loc2); + gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 + update_stmt(g); + + /* Done - grab the entry to the block and insert sequence */ + + bentry = gsi_after_labels(bb); + gsi_insert_seq_before(&bentry, seq, GSI_NEW_STMT); + + ++finst_blocks; + } + + /* Say something nice. */ + if (!be_quiet) { + if (!finst_blocks) + WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST ), + function_name(fun)); + else if (finst_blocks < fcnt_blocks) + OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST ), + finst_blocks, fcnt_blocks, + function_name(fun)); + else + OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST ), + finst_blocks, + function_name(fun)); + } + + + return 0; +} + +/* -------------------------------------------------------------------------- */ +/* -- Boilerplate and initialization ---------------------------------------- */ + +static const struct pass_data afl_pass_data = { + + .type = GIMPLE_PASS, + .name = "afl-inst", + .optinfo_flags = OPTGROUP_NONE, + + .tv_id = TV_NONE, + .properties_required = 0, + .properties_provided = 0, + .properties_destroyed = 0, + .todo_flags_start = 0, + // NOTE(aseipp): it's very, very important to include + // at least 'TODO_update_ssa' here so that GCC will + // properly update the resulting SSA form, e.g., to + // include new PHI nodes for newly added symbols or + // names. Do not remove this. Do not taunt Happy Fun + // Ball. + .todo_flags_finish = TODO_update_ssa | TODO_verify_il | TODO_cleanup_cfg, +}; + +namespace { + +class afl_pass : public gimple_opt_pass { +private: + bool do_ext_call; + +public: + afl_pass(bool ext_call, gcc::context *g) : gimple_opt_pass(afl_pass_data, g), do_ext_call(ext_call) {} + + virtual unsigned int execute(function *fun) { + + if (!myWhitelist.empty()) { + bool instrumentBlock = false; + + /* EXPR_FILENAME + This macro returns the name of the file in which the entity was declared, as + a char*. For an entity declared implicitly by the compiler (like __builtin_ + memcpy), this will be the string "". + */ + const char *fname = DECL_SOURCE_FILE(fun->decl); + + if (0 != strncmp("", fname, 10) + && 0 != strncmp("", fname, 10)) + { + std::string instFilename(fname); + + /* Continue only if we know where we actually are */ + if (!instFilename.empty()) { + for (std::list::iterator it = myWhitelist.begin(); it != myWhitelist.end(); ++it) { + /* We don't check for filename equality here because + * filenames might actually be full paths. Instead we + * check that the actual filename ends in the filename + * specified in the list. */ + if (instFilename.length() >= it->length()) { + if (instFilename.compare(instFilename.length() - it->length(), it->length(), *it) == 0) { + instrumentBlock = true; + break; + } + } + } + } + } + + /* Either we couldn't figure out our location or the location is + * not whitelisted, so we skip instrumentation. */ + if (!instrumentBlock) return 0;; + } + + return do_ext_call ? ext_call_instrument(fun) : inline_instrument(fun); + } +}; /* class afl_pass */ + +} /* anon namespace */ + +static struct opt_pass *make_afl_pass(bool ext_call, gcc::context *ctxt) { + return new afl_pass(ext_call, ctxt); +} + +/* -------------------------------------------------------------------------- */ +/* -- Initialization -------------------------------------------------------- */ + +int plugin_is_GPL_compatible = 1; + +static struct plugin_info afl_plugin_info = { + .version = "20191015", + .help = "AFL++ gcc plugin\n", +}; + +int plugin_init(struct plugin_name_args *plugin_info, + struct plugin_gcc_version *version) { + + struct register_pass_info afl_pass_info; + struct timeval tv; + struct timezone tz; + u32 rand_seed; + + /* Setup random() so we get Actually Random(TM) outputs from R() */ + gettimeofday(&tv, &tz); + rand_seed = tv.tv_sec ^ tv.tv_usec ^ getpid(); + srandom(rand_seed); + + /* Pass information */ + afl_pass_info.pass = make_afl_pass(inst_ext, g); + afl_pass_info.reference_pass_name = "ssa"; + afl_pass_info.ref_pass_instance_number = 1; + afl_pass_info.pos_op = PASS_POS_INSERT_AFTER; + + if (!plugin_default_version_check(version, &gcc_version)) { + FATAL(G_("Incompatible gcc/plugin versions!")); + } + + /* Show a banner */ + if (isatty(2) && !getenv("AFL_QUIET")) { + SAYF(G_(cCYA "afl-gcc-pass " cBRI VERSION cRST " initially by , maintainer: hexcoder-\n")); + } else + be_quiet = 1; + + /* Decide instrumentation ratio */ + char* inst_ratio_str = getenv("AFL_INST_RATIO"); + + if (inst_ratio_str) { + if (sscanf(inst_ratio_str, "%u", &inst_ratio) != 1 || !inst_ratio || inst_ratio > 100) + FATAL(G_("Bad value of AFL_INST_RATIO (must be between 1 and 100)")); + else { + if (!be_quiet) + ACTF(G_("%s instrumentation at ratio of %u%% in %s mode."), + inst_ext ? G_("Call-based") : G_("Inline"), + inst_ratio, + getenv("AFL_HARDEN") ? G_("hardened") : G_("non-hardened")); + } + } + + char* instWhiteListFilename = getenv("AFL_GCC_WHITELIST"); + if (instWhiteListFilename) { + std::string line; + std::ifstream fileStream; + fileStream.open(instWhiteListFilename); + if (!fileStream) + fatal_error(0, "Unable to open AFL_GCC_WHITELIST"); + getline(fileStream, line); + while (fileStream) { + myWhitelist.push_back(line); + getline(fileStream, line); + } + } else if (!be_quiet && getenv("AFL_LLVM_WHITELIST")) + SAYF(cYEL "[-] " cRST "AFL_LLVM_WHITELIST environment variable detected - did you mean AFL_GCC_WHITELIST?\n"); + + /* Go go gadget */ + register_callback(plugin_info->base_name, PLUGIN_INFO, NULL, &afl_plugin_info); + register_callback(plugin_info->base_name, PLUGIN_PASS_MANAGER_SETUP, NULL, &afl_pass_info); + return 0; +} diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c new file mode 100644 index 00000000..8e72e108 --- /dev/null +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -0,0 +1,224 @@ +/* + american fuzzy lop - GCC plugin instrumentation bootstrap + --------------------------------------------------------- + + Written by Austin Seipp and + Laszlo Szekeres and + Michal Zalewski + + GCC integration design is based on the LLVM design, which comes + from Laszlo Szekeres. + + Copyright 2015 Google Inc. All rights reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at: + + http://www.apache.org/licenses/LICENSE-2.0 + + This code is the rewrite of afl-as.h's main_payload. + +*/ + +#include "../config.h" +#include "../types.h" + +#include +#include +#include +#include + +#include +#include +#include +#include + + +/* Globals needed by the injected instrumentation. The __afl_area_initial region + is used for instrumentation output before __afl_map_shm() has a chance to run. + It will end up as .comm, so it shouldn't be too wasteful. */ + +u8 __afl_area_initial[MAP_SIZE]; +u8* __afl_area_ptr = __afl_area_initial; +u32 __afl_prev_loc; + + +/* Running in persistent mode? */ + +static u8 is_persistent; + +/* Trace a basic block with some ID */ +void __afl_trace(u32 x) { + u32 l = __afl_prev_loc; + u32 n = l ^ x; + *(__afl_area_ptr+n) += 1; + __afl_prev_loc = (x >> 1); + return; +} + +/* SHM setup. */ + +static void __afl_map_shm(void) { + + u8 *id_str = getenv(SHM_ENV_VAR); + + /* If we're running under AFL, attach to the appropriate region, replacing the + early-stage __afl_area_initial region that is needed to allow some really + hacky .init code to work correctly in projects such as OpenSSL. */ + + if (id_str) { + + u32 shm_id = atoi(id_str); + + __afl_area_ptr = shmat(shm_id, NULL, 0); + + /* Whooooops. */ + + if (__afl_area_ptr == (void *)-1) exit(1); + + /* Write something into the bitmap so that even with low AFL_INST_RATIO, + our parent doesn't give up on us. */ + + __afl_area_ptr[0] = 1; + + } + +} + + +/* Fork server logic. */ + +static void __afl_start_forkserver(void) { + + static u8 tmp[4]; + s32 child_pid; + + u8 child_stopped = 0; + + /* Phone home and tell the parent that we're OK. If parent isn't there, + assume we're not running in forkserver mode and just execute program. */ + + if (write(FORKSRV_FD + 1, tmp, 4) != 4) return; + + while (1) { + + u32 was_killed; + int status; + + /* Wait for parent by reading from the pipe. Abort if read fails. */ + + if (read(FORKSRV_FD, &was_killed, 4) != 4) exit(1); + + /* If we stopped the child in persistent mode, but there was a race + condition and afl-fuzz already issued SIGKILL, write off the old + process. */ + + if (child_stopped && was_killed) { + child_stopped = 0; + if (waitpid(child_pid, &status, 0) < 0) exit(1); + } + + if (!child_stopped) { + + /* Once woken up, create a clone of our process. */ + + child_pid = fork(); + if (child_pid < 0) exit(1); + + /* In child process: close fds, resume execution. */ + + if (!child_pid) { + + close(FORKSRV_FD); + close(FORKSRV_FD + 1); + return; + + } + + } else { + + /* Special handling for persistent mode: if the child is alive but + currently stopped, simply restart it with SIGCONT. */ + + kill(child_pid, SIGCONT); + child_stopped = 0; + + } + + /* In parent process: write PID to pipe, then wait for child. */ + + if (write(FORKSRV_FD + 1, &child_pid, 4) != 4) exit(1); + + if (waitpid(child_pid, &status, is_persistent ? WUNTRACED : 0) < 0) + exit(1); + + /* In persistent mode, the child stops itself with SIGSTOP to indicate + a successful run. In this case, we want to wake it up without forking + again. */ + + if (WIFSTOPPED(status)) child_stopped = 1; + + /* Relay wait status to pipe, then loop back. */ + + if (write(FORKSRV_FD + 1, &status, 4) != 4) exit(1); + + } + +} + + +/* A simplified persistent mode handler, used as explained in README.llvm. */ + +int __afl_persistent_loop(unsigned int max_cnt) { + + static u8 first_pass = 1; + static u32 cycle_cnt; + + if (first_pass) { + + cycle_cnt = max_cnt; + first_pass = 0; + return 1; + + } + + if (is_persistent && --cycle_cnt) { + + raise(SIGSTOP); + return 1; + + } else return 0; + +} + + +/* This one can be called from user code when deferred forkserver mode + is enabled. */ + +void __afl_manual_init(void) { + + static u8 init_done; + + if (!init_done) { + + __afl_map_shm(); + __afl_start_forkserver(); + init_done = 1; + + } + +} + + +/* Proper initialization routine. */ + +__attribute__((constructor(101))) void __afl_auto_init(void) { + + is_persistent = !!getenv(PERSIST_ENV_VAR); + + if (getenv(DEFER_ENV_VAR)) return; + + __afl_manual_init(); + +} diff --git a/llvm_mode/README.whitelist.md b/llvm_mode/README.whitelist.md index 6a5770c2..72fb5d09 100644 --- a/llvm_mode/README.whitelist.md +++ b/llvm_mode/README.whitelist.md @@ -64,7 +64,7 @@ a2.cpp but it might lead to files being unwantedly instrumented if the same filename exists somewhere else in the project directories. -The created whitelist file is then set to AFL_INST_WHITELIST when you compile +The created whitelist file is then set to AFL_LLVM_WHITELIST when you compile your program. For each file that didn't match the whitelist, the compiler will issue a warning at the end stating that no blocks were instrumented. If you didn't intend to instrument that file, then you can safely ignore that warning. -- cgit 1.4.1 From e7ab8be0cd97f9a18e6ca2f855afa69768322dfb Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 18 Oct 2019 19:53:10 +0200 Subject: sync afl-fast-gcc with afl-clang-fast, add tests for gcc_plugin --- gcc_plugin/afl-gcc-fast.c | 50 +++++++++++++++++++++---------- gcc_plugin/afl-gcc-pass.so.cc | 4 +-- llvm_mode/afl-clang-fast.c | 4 +-- src/afl-gcc.c | 2 +- test/test.sh | 69 +++++++++++++++++++++++++++++++++++++++++++ 5 files changed, 108 insertions(+), 21 deletions(-) diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c index 8be05bb5..25ecf310 100644 --- a/gcc_plugin/afl-gcc-fast.c +++ b/gcc_plugin/afl-gcc-fast.c @@ -104,7 +104,7 @@ static void edit_params(u32 argc, char** argv) { cc_params = ck_alloc((argc + 64) * sizeof(u8*)); name = strrchr(argv[0], '/'); - if (!name) name = argv[0]; else name++; + if (!name) name = argv[0]; else ++name; if (!strcmp(name, "afl-g++-fast")) { u8* alt_cxx = getenv("AFL_CXX"); @@ -114,9 +114,15 @@ static void edit_params(u32 argc, char** argv) { cc_params[0] = alt_cc ? alt_cc : (u8*)"gcc"; } + + char* fplugin_arg = alloc_printf("-fplugin=%s/afl-gcc-pass.so", obj_path); cc_params[cc_par_cnt++] = fplugin_arg; + /* Detect stray -v calls from ./configure scripts. */ + + if (argc == 1 && !strcmp(argv[1], "-v")) maybe_linking = 0; + while (--argc) { u8* cur = *(++argv); @@ -134,6 +140,8 @@ static void edit_params(u32 argc, char** argv) { if (strstr(cur, "FORTIFY_SOURCE")) fortify_set = 1; + if (!strcmp(cur, "-shared")) maybe_linking = 0; + cc_params[cc_par_cnt++] = cur; } @@ -151,17 +159,23 @@ static void edit_params(u32 argc, char** argv) { if (getenv("AFL_USE_ASAN")) { - cc_params[cc_par_cnt++] = "-fsanitize=address"; + if (getenv("AFL_USE_MSAN")) FATAL("ASAN and MSAN are mutually exclusive"); + + if (getenv("AFL_HARDEN")) + FATAL("ASAN and AFL_HARDEN are mutually exclusive"); - if (getenv("AFL_USE_MSAN")) - FATAL("ASAN and MSAN are mutually exclusive"); + cc_params[cc_par_cnt++] = "-U_FORTIFY_SOURCE"; + cc_params[cc_par_cnt++] = "-fsanitize=address"; } else if (getenv("AFL_USE_MSAN")) { - cc_params[cc_par_cnt++] = "-fsanitize=memory"; + if (getenv("AFL_USE_ASAN")) FATAL("ASAN and MSAN are mutually exclusive"); + + if (getenv("AFL_HARDEN")) + FATAL("MSAN and AFL_HARDEN are mutually exclusive"); - if (getenv("AFL_USE_ASAN")) - FATAL("ASAN and MSAN are mutually exclusive"); + cc_params[cc_par_cnt++] = "-U_FORTIFY_SOURCE"; + cc_params[cc_par_cnt++] = "-fsanitize=memory"; } @@ -175,7 +189,13 @@ static void edit_params(u32 argc, char** argv) { } +#ifdef USEMMAP + cc_params[cc_par_cnt++] = "-lrt"; +#endif + cc_params[cc_par_cnt++] = "-D__AFL_HAVE_MANUAL_CONTROL=1"; + cc_params[cc_par_cnt++] = "-D__AFL_COMPILER=1"; + cc_params[cc_par_cnt++] = "-DFUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION=1"; /* When the user tries to use persistent or deferred forkserver modes by appending a single line to the program, we want to reliably inject a @@ -237,15 +257,10 @@ static void edit_params(u32 argc, char** argv) { int main(int argc, char** argv) { - if (isatty(2) && !getenv("AFL_QUIET")) { - - SAYF(cCYA "afl-gcc-fast " cBRI VERSION cRST " initially by , maintainer: hexcoder-\n"); - - } - - if (argc < 2) { + if (argc < 2 || strcmp(argv[1], "-h") == 0) { - SAYF("\n" + printf(cCYA "afl-gcc-fast" VERSION cRST " initially by , maintainer: hexcoder-\n" + "\n" "This is a helper application for afl-fuzz. It serves as a drop-in replacement\n" "for gcc, letting you recompile third-party code with the required runtime\n" "instrumentation. A common use pattern would be one of the following:\n\n" @@ -263,8 +278,11 @@ int main(int argc, char** argv) { exit(1); - } + } else if (isatty(2) && !getenv("AFL_QUIET")) { + SAYF(cCYA "afl-gcc-fast" VERSION cRST " initially by , maintainer: hexcoder-\n"); + + } find_obj(argv[0]); diff --git a/gcc_plugin/afl-gcc-pass.so.cc b/gcc_plugin/afl-gcc-pass.so.cc index f0f5b30b..a44f5a74 100644 --- a/gcc_plugin/afl-gcc-pass.so.cc +++ b/gcc_plugin/afl-gcc-pass.so.cc @@ -416,7 +416,7 @@ public: /* Either we couldn't figure out our location or the location is * not whitelisted, so we skip instrumentation. */ - if (!instrumentBlock) return 0;; + if (!instrumentBlock) return 0; } return do_ext_call ? ext_call_instrument(fun) : inline_instrument(fun); @@ -464,7 +464,7 @@ int plugin_init(struct plugin_name_args *plugin_info, /* Show a banner */ if (isatty(2) && !getenv("AFL_QUIET")) { - SAYF(G_(cCYA "afl-gcc-pass " cBRI VERSION cRST " initially by , maintainer: hexcoder-\n")); + SAYF(G_(cCYA "afl-gcc-pass" VERSION cRST " initially by , maintainer: hexcoder-\n")); } else be_quiet = 1; diff --git a/llvm_mode/afl-clang-fast.c b/llvm_mode/afl-clang-fast.c index 142d6331..54f9e6e9 100644 --- a/llvm_mode/afl-clang-fast.c +++ b/llvm_mode/afl-clang-fast.c @@ -112,7 +112,7 @@ static void edit_params(u32 argc, char** argv) { if (!name) name = argv[0]; else - name++; + ++name; if (!strcmp(name, "afl-clang-fast++")) { @@ -128,7 +128,7 @@ static void edit_params(u32 argc, char** argv) { /* There are three ways to compile with afl-clang-fast. In the traditional mode, we use afl-llvm-pass.so, then there is libLLVMInsTrim.so which is - much faster but has less coverage. Finally tere is the experimental + much faster but has less coverage. Finally there is the experimental 'trace-pc-guard' mode, we use native LLVM instrumentation callbacks instead. For trace-pc-guard see: http://clang.llvm.org/docs/SanitizerCoverage.html#tracing-pcs-with-guards diff --git a/src/afl-gcc.c b/src/afl-gcc.c index 8982ca97..dd7ba4d6 100644 --- a/src/afl-gcc.c +++ b/src/afl-gcc.c @@ -131,7 +131,7 @@ static void edit_params(u32 argc, char** argv) { if (!name) name = argv[0]; else - name++; + ++name; if (!strncmp(name, "afl-clang", 9)) { diff --git a/test/test.sh b/test/test.sh index ab2985fe..1c5cdda6 100755 --- a/test/test.sh +++ b/test/test.sh @@ -200,6 +200,75 @@ test -e ../afl-clang-fast && { rm -f test-persistent } || $ECHO "$YELLOW[-] llvm_mode not compiled, cannot test" +$ECHO "$BLUE[*] Testing: gcc_plugin" +export AFL_CC=`which gcc` +test -e ../afl-gcc-fast && { + ../afl-gcc-fast -o test-instr.plain.gccpi ../test-instr.c > /dev/null 2>&1 + AFL_HARDEN=1 ../afl-gcc-fast -o test-compcov.harden.gccpi test-compcov.c > /dev/null 2>&1 + test -e test-instr.plain.gccpi && { + $ECHO "$GREEN[+] gcc_plugin compilation succeeded" + echo 0 | ../afl-showmap -m ${MEM_LIMIT} -o test-instr.plain.0 -r -- ./test-instr.plain.gccpi > /dev/null 2>&1 + ../afl-showmap -m ${MEM_LIMIT} -o test-instr.plain.1 -r -- ./test-instr.plain.gccpi < /dev/null > /dev/null 2>&1 + test -e test-instr.plain.0 -a -e test-instr.plain.1 && { + diff -q test-instr.plain.0 test-instr.plain.1 > /dev/null 2>&1 && { + $ECHO "$RED[!] gcc_plugin instrumentation should be different on different input but is not" + } || $ECHO "$GREEN[+] gcc_plugin instrumentation present and working correctly" + } || $ECHO "$RED[!] gcc_plugin instrumentation failed" + rm -f test-instr.plain.0 test-instr.plain.1 + } || $ECHO "$RED[!] gcc_plugin failed" + + test -e test-compcov.harden.gccpi && { + grep -Eqa 'stack_chk_fail|fstack-protector-all|fortified' test-compcov.harden.gccpi > /dev/null 2>&1 && { + $ECHO "$GREEN[+] gcc_plugin hardened mode succeeded and is working" + } || $ECHO "$RED[!] gcc_plugin hardened mode is not hardened" + rm -f test-compcov.harden.gccpi + } || $ECHO "$RED[!] gcc_plugin hardened mode compilation failed" + # now we want to be sure that afl-fuzz is working + (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { + $ECHO "$RED[!] we cannot run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" + true + }) || + # make sure crash reporter is disabled on Mac OS X + (test "$(uname -s)" = "Darwin" && test $(launchctl list 2>/dev/null | grep -q '\.ReportCrash$') && { + $ECHO "$RED[!] we cannot run afl-fuzz with enabled crash reporter. Run 'sudo sh afl-system-config'.$RESET" + true + }) || { + mkdir -p in + echo 0 > in/in + $ECHO "$GREY[*] running afl-fuzz for gcc_plugin, this will take approx 10 seconds" + { + ../afl-fuzz -V10 -m ${MEM_LIMIT} -i in -o out -- ./test-instr.plain.gccpi >>errors 2>&1 + } >>errors 2>&1 + test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { + $ECHO "$GREEN[+] afl-fuzz is working correctly with gcc_plugin" + } || { + echo CUT------------------------------------------------------------------CUT + cat errors + echo CUT------------------------------------------------------------------CUT + $ECHO "$RED[!] afl-fuzz is not working correctly with gcc_plugin" + } + rm -rf in out errors + } + rm -f test-instr.plain.gccpi + + # now for the special gcc_plugin things + echo foobar.c > whitelist.txt + AFL_GCC_WHITELIST=whitelist.txt ../afl-gcc-fast -o test-compcov test-compcov.c > /dev/null 2>&1 + test -e test-compcov && { + echo 1 | ../afl-showmap -m ${MEM_LIMIT} -o - -r -- ./test-compcov 2>&1 | grep -q "Captured 1 tuples" && { + $ECHO "$GREEN[+] gcc_plugin whitelist feature works correctly" + } || $ECHO "$RED[!] gcc_plugin whitelist feature failed" + } || $ECHO "$RED[!] gcc_plugin whitelist feature compilation failed" + rm -f test-compcov test.out whitelist.txt + ../afl-gcc-fast -o test-persistent ../experimental/persistent_demo/persistent_demo.c > /dev/null 2>&1 + test -e test-persistent && { + echo foo | ../afl-showmap -o /dev/null -q -r ./test-persistent && { + $ECHO "$GREEN[+] gcc_plugin persistent mode feature works correctly" + } || $ECHO "$RED[!] gcc_plugin persistent mode feature failed to work" + } || $ECHO "$RED[!] gcc_plugin persistent mode feature compilation failed" + rm -f test-persistent +} || $ECHO "$YELLOW[-] gcc_plugin not compiled, cannot test" + $ECHO "$BLUE[*] Testing: shared library extensions" gcc -o test-compcov test-compcov.c > /dev/null 2>&1 test -e ../libtokencap.so && { -- cgit 1.4.1 From bf544af690798436892b313de80855d348ad272c Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 18 Oct 2019 21:21:17 +0200 Subject: new entries for gcc_plugin --- docs/ChangeLog | 2 ++ 1 file changed, 2 insertions(+) diff --git a/docs/ChangeLog b/docs/ChangeLog index 9ffa17e3..46b9e330 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -19,6 +19,8 @@ Version ++2.57d (dev): - reverted patch to not unlink and recreate the input file, it resulted in performance loss - added test/test-performance.sh script + - (re)added gcc_plugin, fast inline instrumentation is not yet finished + - added gcc_plugin tests -------------------------------- -- cgit 1.4.1 From 230c135d4e05d810397138f2b6eb1927955f8900 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 18 Oct 2019 22:43:30 +0200 Subject: typo in names --- Makefile | 2 +- llvm_mode/Makefile | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Makefile b/Makefile index 8cf3d4fd..7e3764a8 100644 --- a/Makefile +++ b/Makefile @@ -292,7 +292,7 @@ source-only: all @./$* -h 2>&1 | tail -n +4 >> $@ @echo >> $@ @echo .SH AUTHOR >> $@ - @echo "afl++ was written by Michal \"lcamtuf\" Zalewski and is maintained by Marc \"van Hauser\" Heuse , Heiko \"hexc0der\" Eissfeldt and Andrea Fioraldi " >> $@ + @echo "afl++ was written by Michal \"lcamtuf\" Zalewski and is maintained by Marc \"van Hauser\" Heuse , Heiko \"hexcoder-\" Eissfeldt and Andrea Fioraldi " >> $@ @echo The homepage of afl++ is: https://github.com/vanhauser-thc/AFLplusplus >> $@ @echo >> $@ @echo .SH LICENSE >> $@ diff --git a/llvm_mode/Makefile b/llvm_mode/Makefile index 55bfab59..0360bfbe 100644 --- a/llvm_mode/Makefile +++ b/llvm_mode/Makefile @@ -220,7 +220,7 @@ vpath % .. @../$* -h 2>&1 | tail -n +4 >> ../$@ @echo >> ../$@ @echo .SH AUTHOR >> ../$@ - @echo "afl++ was written by Michal \"lcamtuf\" Zalewski and is maintained by Marc \"van Hauser\" Heuse , Heiko \"hexc0der\" Eissfeldt and Andrea Fioraldi " >> ../$@ + @echo "afl++ was written by Michal \"lcamtuf\" Zalewski and is maintained by Marc \"van Hauser\" Heuse , Heiko \"hexcoder-\" Eissfeldt and Andrea Fioraldi " >> ../$@ @echo The homepage of afl++ is: https://github.com/vanhauser-thc/AFLplusplus >> ../$@ @echo >> ../$@ @echo .SH LICENSE >> ../$@ -- cgit 1.4.1 From 1fdb75068d6b815baf9736e63e3545b66de688c5 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Sat, 19 Oct 2019 11:44:09 +0100 Subject: afl-gotcpu: porting to Darwin using mach API. --- src/afl-gotcpu.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/src/afl-gotcpu.c b/src/afl-gotcpu.c index bdb727de..dc938b65 100644 --- a/src/afl-gotcpu.c +++ b/src/afl-gotcpu.c @@ -52,7 +52,7 @@ #include "types.h" #include "debug.h" -#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__APPLE__) #define HAVE_AFFINITY 1 #if defined(__FreeBSD__) #include @@ -62,8 +62,12 @@ #elif defined(__NetBSD__) #include #include +#elif defined(__APPLE__) +#include +#include +#include #endif -#endif /* __linux__ || __FreeBSD__ || __NetBSD__ */ +#endif /* __linux__ || __FreeBSD__ || __NetBSD__ || __APPLE__ */ /* Get unix time in microseconds. */ @@ -176,6 +180,12 @@ int main(int argc, char** argv) { if (c == NULL) PFATAL("cpuset_create failed"); cpuset_set(i, c); +#elif defined(__APPLE__) + thread_affinity_policy_data_t c = { i }; + thread_port_t native_thread = pthread_mach_thread_np(pthread_self()); + if (thread_policy_set(native_thread, THREAD_AFFINITY_POLICY, + (thread_policy_t)&c, 1) != KERN_SUCCESS) + PFATAL("thread_policy_set failed"); #endif #if defined(__FreeBSD__) -- cgit 1.4.1 From 8a786377196fbaafeecbca17fad66ea1e76c7de2 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 19 Oct 2019 16:19:46 +0200 Subject: add gcc_plugin to code formatter and run it --- Makefile | 3 + gcc_plugin/afl-gcc-fast.c | 144 ++-- gcc_plugin/afl-gcc-pass.so.cc | 768 +++++++++++---------- gcc_plugin/afl-gcc-rt.o.c | 32 +- include/afl-fuzz.h | 2 +- src/afl-fuzz-bitmap.c | 8 +- src/afl-fuzz-globals.c | 4 +- src/afl-fuzz-init.c | 6 +- src/afl-fuzz-run.c | 6 +- src/afl-fuzz-stats.c | 18 +- src/afl-fuzz.c | 8 +- test-instr.c | 4 +- unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h | 10 +- 13 files changed, 553 insertions(+), 460 deletions(-) diff --git a/Makefile b/Makefile index 7e3764a8..ce0d6781 100644 --- a/Makefile +++ b/Makefile @@ -213,6 +213,9 @@ code-format: ./.custom-format.py -i llvm_mode/*.c ./.custom-format.py -i llvm_mode/*.h ./.custom-format.py -i llvm_mode/*.cc + ./.custom-format.py -i gcc_plugin/*.c + ./.custom-format.py -i gcc_plugin/*.h + ./.custom-format.py -i gcc_plugin/*.cc ./.custom-format.py -i qemu_mode/patches/*.h ./.custom-format.py -i qemu_mode/libcompcov/*.c ./.custom-format.py -i qemu_mode/libcompcov/*.cc diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c index 25ecf310..73709321 100644 --- a/gcc_plugin/afl-gcc-fast.c +++ b/gcc_plugin/afl-gcc-fast.c @@ -36,16 +36,15 @@ #include #include -static u8* obj_path; /* Path to runtime libraries */ -static u8** cc_params; /* Parameters passed to the real CC */ -static u32 cc_par_cnt = 1; /* Param count, including argv0 */ - +static u8* obj_path; /* Path to runtime libraries */ +static u8** cc_params; /* Parameters passed to the real CC */ +static u32 cc_par_cnt = 1; /* Param count, including argv0 */ /* Try to find the runtime libraries. If that fails, abort. */ static void find_obj(u8* argv0) { - u8 *afl_path = getenv("AFL_PATH"); + u8* afl_path = getenv("AFL_PATH"); u8 *slash, *tmp; if (afl_path) { @@ -53,9 +52,11 @@ static void find_obj(u8* argv0) { tmp = alloc_printf("%s/afl-gcc-rt.o", afl_path); if (!access(tmp, R_OK)) { + obj_path = afl_path; ck_free(tmp); return; + } ck_free(tmp); @@ -66,7 +67,7 @@ static void find_obj(u8* argv0) { if (slash) { - u8 *dir; + u8* dir; *slash = 0; dir = ck_strdup(argv0); @@ -75,9 +76,11 @@ static void find_obj(u8* argv0) { tmp = alloc_printf("%s/afl-gcc-rt.o", dir); if (!access(tmp, R_OK)) { + obj_path = dir; ck_free(tmp); return; + } ck_free(tmp); @@ -86,35 +89,44 @@ static void find_obj(u8* argv0) { } if (!access(AFL_PATH "/afl-gcc-rt.o", R_OK)) { + obj_path = AFL_PATH; return; + } - FATAL("Unable to find 'afl-gcc-rt.o' or 'afl-gcc-pass.so'. Please set AFL_PATH"); -} + FATAL( + "Unable to find 'afl-gcc-rt.o' or 'afl-gcc-pass.so'. Please set " + "AFL_PATH"); +} /* Copy argv to cc_params, making the necessary edits. */ static void edit_params(u32 argc, char** argv) { - u8 fortify_set = 0, asan_set = 0, x_set = 0, maybe_linking = 1; - u8 *name; + u8 fortify_set = 0, asan_set = 0, x_set = 0, maybe_linking = 1; + u8* name; cc_params = ck_alloc((argc + 64) * sizeof(u8*)); name = strrchr(argv[0], '/'); - if (!name) name = argv[0]; else ++name; + if (!name) + name = argv[0]; + else + ++name; if (!strcmp(name, "afl-g++-fast")) { + u8* alt_cxx = getenv("AFL_CXX"); cc_params[0] = alt_cxx ? alt_cxx : (u8*)"g++"; + } else { + u8* alt_cc = getenv("AFL_CC"); cc_params[0] = alt_cc ? alt_cc : (u8*)"gcc"; - } - + } char* fplugin_arg = alloc_printf("-fplugin=%s/afl-gcc-pass.so", obj_path); cc_params[cc_par_cnt++] = fplugin_arg; @@ -124,6 +136,7 @@ static void edit_params(u32 argc, char** argv) { if (argc == 1 && !strcmp(argv[1], "-v")) maybe_linking = 0; while (--argc) { + u8* cur = *(++argv); #if defined(__x86_64__) @@ -133,10 +146,11 @@ static void edit_params(u32 argc, char** argv) { if (!strcmp(cur, "-x")) x_set = 1; if (!strcmp(cur, "-c") || !strcmp(cur, "-S") || !strcmp(cur, "-E") || - !strcmp(cur, "-v")) maybe_linking = 0; + !strcmp(cur, "-v")) + maybe_linking = 0; - if (!strcmp(cur, "-fsanitize=address") || - !strcmp(cur, "-fsanitize=memory")) asan_set = 1; + if (!strcmp(cur, "-fsanitize=address") || !strcmp(cur, "-fsanitize=memory")) + asan_set = 1; if (strstr(cur, "FORTIFY_SOURCE")) fortify_set = 1; @@ -150,8 +164,7 @@ static void edit_params(u32 argc, char** argv) { cc_params[cc_par_cnt++] = "-fstack-protector-all"; - if (!fortify_set) - cc_params[cc_par_cnt++] = "-D_FORTIFY_SOURCE=2"; + if (!fortify_set) cc_params[cc_par_cnt++] = "-D_FORTIFY_SOURCE=2"; } @@ -217,31 +230,37 @@ static void edit_params(u32 argc, char** argv) { */ - cc_params[cc_par_cnt++] = "-D__AFL_LOOP(_A)=" - "({ static volatile char *_B __attribute__((used)); " - " _B = (char*)\"" PERSIST_SIG "\"; " + cc_params[cc_par_cnt++] = + "-D__AFL_LOOP(_A)=" + "({ static volatile char *_B __attribute__((used)); " + " _B = (char*)\"" PERSIST_SIG + "\"; " #ifdef __APPLE__ - "int _L(unsigned int) __asm__(\"___afl_persistent_loop\"); " + "int _L(unsigned int) __asm__(\"___afl_persistent_loop\"); " #else - "int _L(unsigned int) __asm__(\"__afl_persistent_loop\"); " -#endif /* ^__APPLE__ */ - "_L(_A); })"; - - cc_params[cc_par_cnt++] = "-D__AFL_INIT()=" - "do { static volatile char *_A __attribute__((used)); " - " _A = (char*)\"" DEFER_SIG "\"; " + "int _L(unsigned int) __asm__(\"__afl_persistent_loop\"); " +#endif /* ^__APPLE__ */ + "_L(_A); })"; + + cc_params[cc_par_cnt++] = + "-D__AFL_INIT()=" + "do { static volatile char *_A __attribute__((used)); " + " _A = (char*)\"" DEFER_SIG + "\"; " #ifdef __APPLE__ - "void _I(void) __asm__(\"___afl_manual_init\"); " + "void _I(void) __asm__(\"___afl_manual_init\"); " #else - "void _I(void) __asm__(\"__afl_manual_init\"); " -#endif /* ^__APPLE__ */ - "_I(); } while (0)"; + "void _I(void) __asm__(\"__afl_manual_init\"); " +#endif /* ^__APPLE__ */ + "_I(); } while (0)"; if (maybe_linking) { if (x_set) { + cc_params[cc_par_cnt++] = "-x"; cc_params[cc_par_cnt++] = "none"; + } cc_params[cc_par_cnt++] = alloc_printf("%s/afl-gcc-rt.o", obj_path); @@ -252,46 +271,58 @@ static void edit_params(u32 argc, char** argv) { } - /* Main entry point */ int main(int argc, char** argv) { if (argc < 2 || strcmp(argv[1], "-h") == 0) { - printf(cCYA "afl-gcc-fast" VERSION cRST " initially by , maintainer: hexcoder-\n" - "\n" - "This is a helper application for afl-fuzz. It serves as a drop-in replacement\n" - "for gcc, letting you recompile third-party code with the required runtime\n" - "instrumentation. A common use pattern would be one of the following:\n\n" - - " CC=%s/afl-gcc-fast ./configure\n" - " CXX=%s/afl-g++-fast ./configure\n\n" - - "In contrast to the traditional afl-gcc tool, this version is implemented as\n" - "a GCC plugin and tends to offer improved performance with slow programs\n" - "(similarly to the LLVM plugin used by afl-clang-fast).\n\n" - - "You can specify custom next-stage toolchain via AFL_CC and AFL_CXX. Setting\n" - "AFL_HARDEN enables hardening optimizations in the compiled code.\n\n", - BIN_PATH, BIN_PATH); + printf( + cCYA + "afl-gcc-fast" VERSION cRST + " initially by , maintainer: hexcoder-\n" + "\n" + "This is a helper application for afl-fuzz. It serves as a drop-in " + "replacement\n" + "for gcc, letting you recompile third-party code with the required " + "runtime\n" + "instrumentation. A common use pattern would be one of the " + "following:\n\n" + + " CC=%s/afl-gcc-fast ./configure\n" + " CXX=%s/afl-g++-fast ./configure\n\n" + + "In contrast to the traditional afl-gcc tool, this version is " + "implemented as\n" + "a GCC plugin and tends to offer improved performance with slow " + "programs\n" + "(similarly to the LLVM plugin used by afl-clang-fast).\n\n" + + "You can specify custom next-stage toolchain via AFL_CC and AFL_CXX. " + "Setting\n" + "AFL_HARDEN enables hardening optimizations in the compiled code.\n\n", + BIN_PATH, BIN_PATH); exit(1); } else if (isatty(2) && !getenv("AFL_QUIET")) { - SAYF(cCYA "afl-gcc-fast" VERSION cRST " initially by , maintainer: hexcoder-\n"); + SAYF(cCYA "afl-gcc-fast" VERSION cRST + " initially by , maintainer: hexcoder-\n"); } find_obj(argv[0]); edit_params(argc, argv); -/*if (isatty(2) && !getenv("AFL_QUIET")) { - printf("Calling \"%s\" with:\n", cc_params[0]); - for(int i=1; i #include #include @@ -92,191 +92,206 @@ /* -------------------------------------------------------------------------- */ /* -- AFL instrumentation pass ---------------------------------------------- */ -static int be_quiet = 0; -static unsigned int inst_ratio = 100; -static bool inst_ext = true; +static int be_quiet = 0; +static unsigned int inst_ratio = 100; +static bool inst_ext = true; static std::list myWhitelist; static unsigned int ext_call_instrument(function *fun) { - /* Instrument all the things! */ - basic_block bb; - unsigned finst_blocks = 0; - unsigned fcnt_blocks = 0; - - tree fntype = build_function_type_list( - void_type_node, /* return */ - uint32_type_node, /* args */ - NULL_TREE); /* done */ - tree fndecl = build_fn_decl("__afl_trace", fntype); - TREE_STATIC(fndecl) = 1; /* Defined elsewhere */ - TREE_PUBLIC(fndecl) = 1; /* Public */ - DECL_EXTERNAL(fndecl) = 1; /* External linkage */ - DECL_ARTIFICIAL(fndecl) = 1; /* Injected by compiler */ - - FOR_EACH_BB_FN(bb, fun) { - gimple_seq fcall; - gimple_seq seq = NULL; - gimple_stmt_iterator bentry; - ++fcnt_blocks; - - // only instrument if this basic block is the destination of a previous - // basic block that has multiple successors - // this gets rid of ~5-10% of instrumentations that are unnecessary - // result: a little more speed and less map pollution - - int more_than_one = -1; - edge ep; - edge_iterator eip; - FOR_EACH_EDGE (ep, eip, bb->preds) { - int count = 0; - if (more_than_one == -1) - more_than_one = 0; - - basic_block Pred = ep->src; - edge es; - edge_iterator eis; - FOR_EACH_EDGE (es, eis, Pred->succs) { - basic_block Succ = es->dest; - if (Succ != NULL) count++; - } - if (count > 1) - more_than_one = 1; - } - if (more_than_one != 1) - continue; - - /* Bail on this block if we trip the specified ratio */ - if (R(100) >= inst_ratio) continue; - - /* Make up cur_loc */ - unsigned int rand_loc = R(MAP_SIZE); - tree cur_loc = build_int_cst(uint32_type_node, rand_loc); - - /* Update bitmap via external call */ - /* to quote: - * /+ Trace a basic block with some ID +/ - * void __afl_trace(u32 x); - */ - - fcall = gimple_build_call(fndecl, 1, cur_loc); /* generate the function _call_ to above built reference, with *1* parameter -> the random const for the location */ - gimple_seq_add_stmt(&seq, fcall); /* and insert into a sequence */ - - /* Done - grab the entry to the block and insert sequence */ - bentry = gsi_after_labels(bb); - gsi_insert_seq_before(&bentry, seq, GSI_SAME_STMT); - - ++finst_blocks; - } - - /* Say something nice. */ - if (!be_quiet) { - if (!finst_blocks) - WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST ), - function_name(fun)); - else if (finst_blocks < fcnt_blocks) - OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST ), - finst_blocks, fcnt_blocks, - function_name(fun)); - else - OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST ), - finst_blocks, - function_name(fun)); - } - - return 0; + + /* Instrument all the things! */ + basic_block bb; + unsigned finst_blocks = 0; + unsigned fcnt_blocks = 0; + + tree fntype = build_function_type_list(void_type_node, /* return */ + uint32_type_node, /* args */ + NULL_TREE); /* done */ + tree fndecl = build_fn_decl("__afl_trace", fntype); + TREE_STATIC(fndecl) = 1; /* Defined elsewhere */ + TREE_PUBLIC(fndecl) = 1; /* Public */ + DECL_EXTERNAL(fndecl) = 1; /* External linkage */ + DECL_ARTIFICIAL(fndecl) = 1; /* Injected by compiler */ + + FOR_EACH_BB_FN(bb, fun) { + + gimple_seq fcall; + gimple_seq seq = NULL; + gimple_stmt_iterator bentry; + ++fcnt_blocks; + + // only instrument if this basic block is the destination of a previous + // basic block that has multiple successors + // this gets rid of ~5-10% of instrumentations that are unnecessary + // result: a little more speed and less map pollution + + int more_than_one = -1; + edge ep; + edge_iterator eip; + FOR_EACH_EDGE(ep, eip, bb->preds) { + + int count = 0; + if (more_than_one == -1) more_than_one = 0; + + basic_block Pred = ep->src; + edge es; + edge_iterator eis; + FOR_EACH_EDGE(es, eis, Pred->succs) { + + basic_block Succ = es->dest; + if (Succ != NULL) count++; + + } + + if (count > 1) more_than_one = 1; + + } + + if (more_than_one != 1) continue; + + /* Bail on this block if we trip the specified ratio */ + if (R(100) >= inst_ratio) continue; + + /* Make up cur_loc */ + unsigned int rand_loc = R(MAP_SIZE); + tree cur_loc = build_int_cst(uint32_type_node, rand_loc); + + /* Update bitmap via external call */ + /* to quote: + * /+ Trace a basic block with some ID +/ + * void __afl_trace(u32 x); + */ + + fcall = gimple_build_call( + fndecl, 1, + cur_loc); /* generate the function _call_ to above built reference, with + *1* parameter -> the random const for the location */ + gimple_seq_add_stmt(&seq, fcall); /* and insert into a sequence */ + + /* Done - grab the entry to the block and insert sequence */ + bentry = gsi_after_labels(bb); + gsi_insert_seq_before(&bentry, seq, GSI_SAME_STMT); + + ++finst_blocks; + + } + + /* Say something nice. */ + if (!be_quiet) { + + if (!finst_blocks) + WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST), + function_name(fun)); + else if (finst_blocks < fcnt_blocks) + OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST), + finst_blocks, fcnt_blocks, function_name(fun)); + else + OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST), finst_blocks, + function_name(fun)); + + } + + return 0; + } static unsigned int inline_instrument(function *fun) { - /* Instrument all the things! */ - basic_block bb; - unsigned finst_blocks = 0; - unsigned fcnt_blocks = 0; - - /* Set up global type declarations */ - tree map_type = build_pointer_type(unsigned_char_type_node); - tree map_ptr_g = build_decl(UNKNOWN_LOCATION, VAR_DECL, - get_identifier_with_length("__afl_area_ptr", 14), map_type); - TREE_USED(map_ptr_g) = 1; - TREE_STATIC(map_ptr_g) = 1; /* Defined elsewhere */ - DECL_EXTERNAL(map_ptr_g) = 1; /* External linkage */ - DECL_PRESERVE_P(map_ptr_g) = 1; - DECL_ARTIFICIAL(map_ptr_g) = 1; /* Injected by compiler */ - rest_of_decl_compilation(map_ptr_g, 1, 0); - - tree prev_loc_g = build_decl(UNKNOWN_LOCATION, VAR_DECL, - get_identifier_with_length("__afl_prev_loc", 14), uint32_type_node); - TREE_USED(prev_loc_g) = 1; - TREE_STATIC(prev_loc_g) = 1; /* Defined elsewhere */ - DECL_EXTERNAL(prev_loc_g) = 1; /* External linkage */ - DECL_PRESERVE_P(prev_loc_g) = 1; - DECL_ARTIFICIAL(prev_loc_g) = 1; /* Injected by compiler */ - rest_of_decl_compilation(prev_loc_g, 1, 0); - - FOR_EACH_BB_FN(bb, fun) { - gimple_seq seq = NULL; - gimple_stmt_iterator bentry; - ++fcnt_blocks; - - // only instrument if this basic block is the destination of a previous - // basic block that has multiple successors - // this gets rid of ~5-10% of instrumentations that are unnecessary - // result: a little more speed and less map pollution - - int more_than_one = -1; - edge ep; - edge_iterator eip; - FOR_EACH_EDGE (ep, eip, bb->preds) { - int count = 0; - if (more_than_one == -1) - more_than_one = 0; - - basic_block Pred = ep->src; - edge es; - edge_iterator eis; - FOR_EACH_EDGE (es, eis, Pred->succs) { - basic_block Succ = es->dest; - if (Succ != NULL) count++; - } - if (count > 1) - more_than_one = 1; - } - if (more_than_one != 1) - continue; - - /* Bail on this block if we trip the specified ratio */ - if (R(100) >= inst_ratio) continue; - - /* Make up cur_loc */ - - unsigned int rand_loc = R(MAP_SIZE); - tree cur_loc = build_int_cst(uint32_type_node, rand_loc); - - /* Load prev_loc, xor with cur_loc */ - // gimple_assign - tree prev_loc = create_tmp_var_raw(uint32_type_node, "prev_loc"); - gassign *g = gimple_build_assign(prev_loc, VAR_DECL, prev_loc_g); - gimple_seq_add_stmt(&seq, g); // load prev_loc - update_stmt(g); + /* Instrument all the things! */ + basic_block bb; + unsigned finst_blocks = 0; + unsigned fcnt_blocks = 0; - // gimple_assign - tree area_off = create_tmp_var_raw(uint32_type_node, "area_off"); - g = gimple_build_assign(area_off, BIT_XOR_EXPR, prev_loc, cur_loc); - gimple_seq_add_stmt(&seq, g); // area_off = prev_loc ^ cur_loc - update_stmt(g); + /* Set up global type declarations */ + tree map_type = build_pointer_type(unsigned_char_type_node); + tree map_ptr_g = + build_decl(UNKNOWN_LOCATION, VAR_DECL, + get_identifier_with_length("__afl_area_ptr", 14), map_type); + TREE_USED(map_ptr_g) = 1; + TREE_STATIC(map_ptr_g) = 1; /* Defined elsewhere */ + DECL_EXTERNAL(map_ptr_g) = 1; /* External linkage */ + DECL_PRESERVE_P(map_ptr_g) = 1; + DECL_ARTIFICIAL(map_ptr_g) = 1; /* Injected by compiler */ + rest_of_decl_compilation(map_ptr_g, 1, 0); - /* Update bitmap */ + tree prev_loc_g = build_decl(UNKNOWN_LOCATION, VAR_DECL, + get_identifier_with_length("__afl_prev_loc", 14), + uint32_type_node); + TREE_USED(prev_loc_g) = 1; + TREE_STATIC(prev_loc_g) = 1; /* Defined elsewhere */ + DECL_EXTERNAL(prev_loc_g) = 1; /* External linkage */ + DECL_PRESERVE_P(prev_loc_g) = 1; + DECL_ARTIFICIAL(prev_loc_g) = 1; /* Injected by compiler */ + rest_of_decl_compilation(prev_loc_g, 1, 0); - tree one = build_int_cst(unsigned_char_type_node, 1); -// tree zero = build_int_cst(unsigned_char_type_node, 0); + FOR_EACH_BB_FN(bb, fun) { - // gimple_assign - tree map_ptr = create_tmp_var(map_type, "map_ptr"); - tree map_ptr2 = create_tmp_var(map_type, "map_ptr2"); + gimple_seq seq = NULL; + gimple_stmt_iterator bentry; + ++fcnt_blocks; - g = gimple_build_assign(map_ptr, map_ptr_g); - gimple_seq_add_stmt(&seq, g); // map_ptr = __afl_area_ptr - update_stmt(g); + // only instrument if this basic block is the destination of a previous + // basic block that has multiple successors + // this gets rid of ~5-10% of instrumentations that are unnecessary + // result: a little more speed and less map pollution + + int more_than_one = -1; + edge ep; + edge_iterator eip; + FOR_EACH_EDGE(ep, eip, bb->preds) { + + int count = 0; + if (more_than_one == -1) more_than_one = 0; + + basic_block Pred = ep->src; + edge es; + edge_iterator eis; + FOR_EACH_EDGE(es, eis, Pred->succs) { + + basic_block Succ = es->dest; + if (Succ != NULL) count++; + + } + + if (count > 1) more_than_one = 1; + + } + + if (more_than_one != 1) continue; + + /* Bail on this block if we trip the specified ratio */ + if (R(100) >= inst_ratio) continue; + + /* Make up cur_loc */ + + unsigned int rand_loc = R(MAP_SIZE); + tree cur_loc = build_int_cst(uint32_type_node, rand_loc); + + /* Load prev_loc, xor with cur_loc */ + // gimple_assign + tree prev_loc = create_tmp_var_raw(uint32_type_node, "prev_loc"); + gassign *g = gimple_build_assign(prev_loc, VAR_DECL, prev_loc_g); + gimple_seq_add_stmt(&seq, g); // load prev_loc + update_stmt(g); + + // gimple_assign + tree area_off = create_tmp_var_raw(uint32_type_node, "area_off"); + g = gimple_build_assign(area_off, BIT_XOR_EXPR, prev_loc, cur_loc); + gimple_seq_add_stmt(&seq, g); // area_off = prev_loc ^ cur_loc + update_stmt(g); + + /* Update bitmap */ + + tree one = build_int_cst(unsigned_char_type_node, 1); + // tree zero = build_int_cst(unsigned_char_type_node, 0); + + // gimple_assign + tree map_ptr = create_tmp_var(map_type, "map_ptr"); + tree map_ptr2 = create_tmp_var(map_type, "map_ptr2"); + + g = gimple_build_assign(map_ptr, map_ptr_g); + gimple_seq_add_stmt(&seq, g); // map_ptr = __afl_area_ptr + update_stmt(g); #if 0 tree addr = build2(ADDR_EXPR, map_type, map_ptr, area_off); @@ -284,68 +299,69 @@ static unsigned int inline_instrument(function *fun) { gimple_seq_add_stmt(&seq, g); // map_ptr2 = map_ptr + area_off update_stmt(g); #else - g = gimple_build_assign(map_ptr2, PLUS_EXPR, map_ptr, area_off); - gimple_seq_add_stmt(&seq, g); // map_ptr2 = map_ptr + area_off - update_stmt(g); + g = gimple_build_assign(map_ptr2, PLUS_EXPR, map_ptr, area_off); + gimple_seq_add_stmt(&seq, g); // map_ptr2 = map_ptr + area_off + update_stmt(g); #endif - // gimple_assign - tree tmp1 = create_tmp_var_raw(unsigned_char_type_node, "tmp1"); - g = gimple_build_assign(tmp1, MEM_REF, map_ptr2); - gimple_seq_add_stmt(&seq, g); // tmp1 = *map_ptr2 - update_stmt(g); + // gimple_assign + tree tmp1 = create_tmp_var_raw(unsigned_char_type_node, "tmp1"); + g = gimple_build_assign(tmp1, MEM_REF, map_ptr2); + gimple_seq_add_stmt(&seq, g); // tmp1 = *map_ptr2 + update_stmt(g); - // gimple_assign - tree tmp2 = create_tmp_var_raw(unsigned_char_type_node, "tmp2"); - g = gimple_build_assign(tmp2, PLUS_EXPR, tmp1, one); - gimple_seq_add_stmt(&seq, g); // tmp2 = tmp1 + 1 - update_stmt(g); + // gimple_assign + tree tmp2 = create_tmp_var_raw(unsigned_char_type_node, "tmp2"); + g = gimple_build_assign(tmp2, PLUS_EXPR, tmp1, one); + gimple_seq_add_stmt(&seq, g); // tmp2 = tmp1 + 1 + update_stmt(g); - // TODO: neverZero: here we have to check if tmp3 == 0 - // and add 1 if so + // TODO: neverZero: here we have to check if tmp3 == 0 + // and add 1 if so - // gimple_assign -// tree map_ptr3 = create_tmp_var_raw(map_type, "map_ptr3"); - g = gimple_build_assign(map_ptr_g, INDIRECT_REF, tmp2); - gimple_seq_add_stmt(&seq, g); // *map_ptr3 = tmp2 - update_stmt(g); + // gimple_assign + // tree map_ptr3 = create_tmp_var_raw(map_type, "map_ptr3"); + g = gimple_build_assign(map_ptr_g, INDIRECT_REF, tmp2); + gimple_seq_add_stmt(&seq, g); // *map_ptr3 = tmp2 + update_stmt(g); - /* Set prev_loc to cur_loc >> 1 */ + /* Set prev_loc to cur_loc >> 1 */ - // gimple_assign - tree shifted_loc = build_int_cst(TREE_TYPE(prev_loc_g), rand_loc >> 1); - tree prev_loc2 = create_tmp_var_raw(uint32_type_node, "prev_loc2"); - g = gimple_build_assign(prev_loc2, shifted_loc); - gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 - update_stmt(g); - g = gimple_build_assign(prev_loc_g, prev_loc2); - gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 - update_stmt(g); + // gimple_assign + tree shifted_loc = build_int_cst(TREE_TYPE(prev_loc_g), rand_loc >> 1); + tree prev_loc2 = create_tmp_var_raw(uint32_type_node, "prev_loc2"); + g = gimple_build_assign(prev_loc2, shifted_loc); + gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 + update_stmt(g); + g = gimple_build_assign(prev_loc_g, prev_loc2); + gimple_seq_add_stmt(&seq, g); // __afl_prev_loc = cur_loc >> 1 + update_stmt(g); + + /* Done - grab the entry to the block and insert sequence */ + + bentry = gsi_after_labels(bb); + gsi_insert_seq_before(&bentry, seq, GSI_NEW_STMT); + + ++finst_blocks; - /* Done - grab the entry to the block and insert sequence */ + } - bentry = gsi_after_labels(bb); - gsi_insert_seq_before(&bentry, seq, GSI_NEW_STMT); + /* Say something nice. */ + if (!be_quiet) { - ++finst_blocks; - } + if (!finst_blocks) + WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST), + function_name(fun)); + else if (finst_blocks < fcnt_blocks) + OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST), + finst_blocks, fcnt_blocks, function_name(fun)); + else + OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST), finst_blocks, + function_name(fun)); - /* Say something nice. */ - if (!be_quiet) { - if (!finst_blocks) - WARNF(G_("No instrumentation targets found in " cBRI "%s" cRST ), - function_name(fun)); - else if (finst_blocks < fcnt_blocks) - OKF(G_("Instrumented %2u /%2u locations in " cBRI "%s" cRST ), - finst_blocks, fcnt_blocks, - function_name(fun)); - else - OKF(G_("Instrumented %2u locations in " cBRI "%s" cRST ), - finst_blocks, - function_name(fun)); - } + } + return 0; - return 0; } /* -------------------------------------------------------------------------- */ @@ -353,80 +369,102 @@ static unsigned int inline_instrument(function *fun) { static const struct pass_data afl_pass_data = { - .type = GIMPLE_PASS, - .name = "afl-inst", - .optinfo_flags = OPTGROUP_NONE, - - .tv_id = TV_NONE, - .properties_required = 0, - .properties_provided = 0, - .properties_destroyed = 0, - .todo_flags_start = 0, - // NOTE(aseipp): it's very, very important to include - // at least 'TODO_update_ssa' here so that GCC will - // properly update the resulting SSA form, e.g., to - // include new PHI nodes for newly added symbols or - // names. Do not remove this. Do not taunt Happy Fun - // Ball. - .todo_flags_finish = TODO_update_ssa | TODO_verify_il | TODO_cleanup_cfg, + .type = GIMPLE_PASS, + .name = "afl-inst", + .optinfo_flags = OPTGROUP_NONE, + + .tv_id = TV_NONE, + .properties_required = 0, + .properties_provided = 0, + .properties_destroyed = 0, + .todo_flags_start = 0, + // NOTE(aseipp): it's very, very important to include + // at least 'TODO_update_ssa' here so that GCC will + // properly update the resulting SSA form, e.g., to + // include new PHI nodes for newly added symbols or + // names. Do not remove this. Do not taunt Happy Fun + // Ball. + .todo_flags_finish = TODO_update_ssa | TODO_verify_il | TODO_cleanup_cfg, + }; namespace { class afl_pass : public gimple_opt_pass { -private: - bool do_ext_call; - -public: - afl_pass(bool ext_call, gcc::context *g) : gimple_opt_pass(afl_pass_data, g), do_ext_call(ext_call) {} - - virtual unsigned int execute(function *fun) { - - if (!myWhitelist.empty()) { - bool instrumentBlock = false; - - /* EXPR_FILENAME - This macro returns the name of the file in which the entity was declared, as - a char*. For an entity declared implicitly by the compiler (like __builtin_ - memcpy), this will be the string "". - */ - const char *fname = DECL_SOURCE_FILE(fun->decl); - - if (0 != strncmp("", fname, 10) - && 0 != strncmp("", fname, 10)) - { - std::string instFilename(fname); - - /* Continue only if we know where we actually are */ - if (!instFilename.empty()) { - for (std::list::iterator it = myWhitelist.begin(); it != myWhitelist.end(); ++it) { - /* We don't check for filename equality here because - * filenames might actually be full paths. Instead we - * check that the actual filename ends in the filename - * specified in the list. */ - if (instFilename.length() >= it->length()) { - if (instFilename.compare(instFilename.length() - it->length(), it->length(), *it) == 0) { - instrumentBlock = true; - break; - } - } - } - } - } - - /* Either we couldn't figure out our location or the location is - * not whitelisted, so we skip instrumentation. */ - if (!instrumentBlock) return 0; - } - - return do_ext_call ? ext_call_instrument(fun) : inline_instrument(fun); - } -}; /* class afl_pass */ - -} /* anon namespace */ + + private: + bool do_ext_call; + + public: + afl_pass(bool ext_call, gcc::context *g) + : gimple_opt_pass(afl_pass_data, g), do_ext_call(ext_call) { + + } + + virtual unsigned int execute(function *fun) { + + if (!myWhitelist.empty()) { + + bool instrumentBlock = false; + + /* EXPR_FILENAME + This macro returns the name of the file in which the entity was declared, + as a char*. For an entity declared implicitly by the compiler (like + __builtin_ memcpy), this will be the string "". + */ + const char *fname = DECL_SOURCE_FILE(fun->decl); + + if (0 != strncmp("", fname, 10) && + 0 != strncmp("", fname, 10)) { + + std::string instFilename(fname); + + /* Continue only if we know where we actually are */ + if (!instFilename.empty()) { + + for (std::list::iterator it = myWhitelist.begin(); + it != myWhitelist.end(); ++it) { + + /* We don't check for filename equality here because + * filenames might actually be full paths. Instead we + * check that the actual filename ends in the filename + * specified in the list. */ + if (instFilename.length() >= it->length()) { + + if (instFilename.compare(instFilename.length() - it->length(), + it->length(), *it) == 0) { + + instrumentBlock = true; + break; + + } + + } + + } + + } + + } + + /* Either we couldn't figure out our location or the location is + * not whitelisted, so we skip instrumentation. */ + if (!instrumentBlock) return 0; + + } + + return do_ext_call ? ext_call_instrument(fun) : inline_instrument(fun); + + } + +}; /* class afl_pass */ + +} // namespace static struct opt_pass *make_afl_pass(bool ext_call, gcc::context *ctxt) { - return new afl_pass(ext_call, ctxt); + + return new afl_pass(ext_call, ctxt); + } /* -------------------------------------------------------------------------- */ @@ -435,71 +473,93 @@ static struct opt_pass *make_afl_pass(bool ext_call, gcc::context *ctxt) { int plugin_is_GPL_compatible = 1; static struct plugin_info afl_plugin_info = { - .version = "20191015", - .help = "AFL++ gcc plugin\n", + + .version = "20191015", + .help = "AFL++ gcc plugin\n", + }; -int plugin_init(struct plugin_name_args *plugin_info, +int plugin_init(struct plugin_name_args * plugin_info, struct plugin_gcc_version *version) { - struct register_pass_info afl_pass_info; - struct timeval tv; - struct timezone tz; - u32 rand_seed; - - /* Setup random() so we get Actually Random(TM) outputs from R() */ - gettimeofday(&tv, &tz); - rand_seed = tv.tv_sec ^ tv.tv_usec ^ getpid(); - srandom(rand_seed); - - /* Pass information */ - afl_pass_info.pass = make_afl_pass(inst_ext, g); - afl_pass_info.reference_pass_name = "ssa"; - afl_pass_info.ref_pass_instance_number = 1; - afl_pass_info.pos_op = PASS_POS_INSERT_AFTER; - - if (!plugin_default_version_check(version, &gcc_version)) { - FATAL(G_("Incompatible gcc/plugin versions!")); - } - - /* Show a banner */ - if (isatty(2) && !getenv("AFL_QUIET")) { - SAYF(G_(cCYA "afl-gcc-pass" VERSION cRST " initially by , maintainer: hexcoder-\n")); - } else - be_quiet = 1; - - /* Decide instrumentation ratio */ - char* inst_ratio_str = getenv("AFL_INST_RATIO"); - - if (inst_ratio_str) { - if (sscanf(inst_ratio_str, "%u", &inst_ratio) != 1 || !inst_ratio || inst_ratio > 100) - FATAL(G_("Bad value of AFL_INST_RATIO (must be between 1 and 100)")); - else { - if (!be_quiet) - ACTF(G_("%s instrumentation at ratio of %u%% in %s mode."), - inst_ext ? G_("Call-based") : G_("Inline"), - inst_ratio, - getenv("AFL_HARDEN") ? G_("hardened") : G_("non-hardened")); - } - } - - char* instWhiteListFilename = getenv("AFL_GCC_WHITELIST"); - if (instWhiteListFilename) { - std::string line; - std::ifstream fileStream; - fileStream.open(instWhiteListFilename); - if (!fileStream) - fatal_error(0, "Unable to open AFL_GCC_WHITELIST"); - getline(fileStream, line); - while (fileStream) { - myWhitelist.push_back(line); - getline(fileStream, line); - } - } else if (!be_quiet && getenv("AFL_LLVM_WHITELIST")) - SAYF(cYEL "[-] " cRST "AFL_LLVM_WHITELIST environment variable detected - did you mean AFL_GCC_WHITELIST?\n"); + struct register_pass_info afl_pass_info; + struct timeval tv; + struct timezone tz; + u32 rand_seed; + + /* Setup random() so we get Actually Random(TM) outputs from R() */ + gettimeofday(&tv, &tz); + rand_seed = tv.tv_sec ^ tv.tv_usec ^ getpid(); + srandom(rand_seed); + + /* Pass information */ + afl_pass_info.pass = make_afl_pass(inst_ext, g); + afl_pass_info.reference_pass_name = "ssa"; + afl_pass_info.ref_pass_instance_number = 1; + afl_pass_info.pos_op = PASS_POS_INSERT_AFTER; + + if (!plugin_default_version_check(version, &gcc_version)) { + + FATAL(G_("Incompatible gcc/plugin versions!")); + + } + + /* Show a banner */ + if (isatty(2) && !getenv("AFL_QUIET")) { + + SAYF(G_(cCYA "afl-gcc-pass" VERSION cRST + " initially by , maintainer: hexcoder-\n")); + + } else + + be_quiet = 1; + + /* Decide instrumentation ratio */ + char *inst_ratio_str = getenv("AFL_INST_RATIO"); + + if (inst_ratio_str) { + + if (sscanf(inst_ratio_str, "%u", &inst_ratio) != 1 || !inst_ratio || + inst_ratio > 100) + FATAL(G_("Bad value of AFL_INST_RATIO (must be between 1 and 100)")); + else { + + if (!be_quiet) + ACTF(G_("%s instrumentation at ratio of %u%% in %s mode."), + inst_ext ? G_("Call-based") : G_("Inline"), inst_ratio, + getenv("AFL_HARDEN") ? G_("hardened") : G_("non-hardened")); + + } + + } + + char *instWhiteListFilename = getenv("AFL_GCC_WHITELIST"); + if (instWhiteListFilename) { + + std::string line; + std::ifstream fileStream; + fileStream.open(instWhiteListFilename); + if (!fileStream) fatal_error(0, "Unable to open AFL_GCC_WHITELIST"); + getline(fileStream, line); + while (fileStream) { + + myWhitelist.push_back(line); + getline(fileStream, line); + + } + + } else if (!be_quiet && getenv("AFL_LLVM_WHITELIST")) + + SAYF(cYEL "[-] " cRST + "AFL_LLVM_WHITELIST environment variable detected - did you mean " + "AFL_GCC_WHITELIST?\n"); + + /* Go go gadget */ + register_callback(plugin_info->base_name, PLUGIN_INFO, NULL, + &afl_plugin_info); + register_callback(plugin_info->base_name, PLUGIN_PASS_MANAGER_SETUP, NULL, + &afl_pass_info); + return 0; - /* Go go gadget */ - register_callback(plugin_info->base_name, PLUGIN_INFO, NULL, &afl_plugin_info); - register_callback(plugin_info->base_name, PLUGIN_PASS_MANAGER_SETUP, NULL, &afl_pass_info); - return 0; } + diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index 8e72e108..f6754bd4 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -34,27 +34,27 @@ #include #include - /* Globals needed by the injected instrumentation. The __afl_area_initial region - is used for instrumentation output before __afl_map_shm() has a chance to run. - It will end up as .comm, so it shouldn't be too wasteful. */ + is used for instrumentation output before __afl_map_shm() has a chance to + run. It will end up as .comm, so it shouldn't be too wasteful. */ u8 __afl_area_initial[MAP_SIZE]; -u8* __afl_area_ptr = __afl_area_initial; +u8 *__afl_area_ptr = __afl_area_initial; u32 __afl_prev_loc; - /* Running in persistent mode? */ static u8 is_persistent; /* Trace a basic block with some ID */ void __afl_trace(u32 x) { + u32 l = __afl_prev_loc; u32 n = l ^ x; - *(__afl_area_ptr+n) += 1; + *(__afl_area_ptr + n) += 1; __afl_prev_loc = (x >> 1); return; + } /* SHM setup. */ @@ -86,15 +86,14 @@ static void __afl_map_shm(void) { } - /* Fork server logic. */ static void __afl_start_forkserver(void) { static u8 tmp[4]; - s32 child_pid; + s32 child_pid; - u8 child_stopped = 0; + u8 child_stopped = 0; /* Phone home and tell the parent that we're OK. If parent isn't there, assume we're not running in forkserver mode and just execute program. */ @@ -115,8 +114,10 @@ static void __afl_start_forkserver(void) { process. */ if (child_stopped && was_killed) { + child_stopped = 0; if (waitpid(child_pid, &status, 0) < 0) exit(1); + } if (!child_stopped) { @@ -150,8 +151,7 @@ static void __afl_start_forkserver(void) { if (write(FORKSRV_FD + 1, &child_pid, 4) != 4) exit(1); - if (waitpid(child_pid, &status, is_persistent ? WUNTRACED : 0) < 0) - exit(1); + if (waitpid(child_pid, &status, is_persistent ? WUNTRACED : 0) < 0) exit(1); /* In persistent mode, the child stops itself with SIGSTOP to indicate a successful run. In this case, we want to wake it up without forking @@ -167,7 +167,6 @@ static void __afl_start_forkserver(void) { } - /* A simplified persistent mode handler, used as explained in README.llvm. */ int __afl_persistent_loop(unsigned int max_cnt) { @@ -177,7 +176,7 @@ int __afl_persistent_loop(unsigned int max_cnt) { if (first_pass) { - cycle_cnt = max_cnt; + cycle_cnt = max_cnt; first_pass = 0; return 1; @@ -188,10 +187,11 @@ int __afl_persistent_loop(unsigned int max_cnt) { raise(SIGSTOP); return 1; - } else return 0; + } else -} + return 0; +} /* This one can be called from user code when deferred forkserver mode is enabled. */ @@ -210,7 +210,6 @@ void __afl_manual_init(void) { } - /* Proper initialization routine. */ __attribute__((constructor(101))) void __afl_auto_init(void) { @@ -222,3 +221,4 @@ __attribute__((constructor(101))) void __afl_auto_init(void) { __afl_manual_init(); } + diff --git a/include/afl-fuzz.h b/include/afl-fuzz.h index 5da41a3e..7e9ced46 100644 --- a/include/afl-fuzz.h +++ b/include/afl-fuzz.h @@ -252,7 +252,7 @@ extern u8 *in_dir, /* Input directory with test cases */ *file_extension, /* File extension */ *orig_cmdline, /* Original command line */ *doc_path, /* Path to documentation dir */ - *infoexec, /* Command to execute on a new crash */ + *infoexec, /* Command to execute on a new crash */ *out_file; /* File to fuzz, if any */ extern u32 exec_tmout; /* Configurable exec timeout (ms) */ diff --git a/src/afl-fuzz-bitmap.c b/src/afl-fuzz-bitmap.c index 746fc982..d001dbee 100644 --- a/src/afl-fuzz-bitmap.c +++ b/src/afl-fuzz-bitmap.c @@ -683,10 +683,12 @@ u8 save_if_interesting(char** argv, void* mem, u32 len, u8 fault) { #endif /* ^!SIMPLE_FILES */ ++unique_crashes; - - if (infoexec) // if the user wants to be informed on new crashes - do that + + if (infoexec) // if the user wants to be informed on new crashes - do + // that if (system(infoexec) == -1) - hnb += 0; // we dont care if system errors, but we dont want a compiler warning either + hnb += 0; // we dont care if system errors, but we dont want a + // compiler warning either last_crash_time = get_cur_time(); last_crash_execs = total_execs; diff --git a/src/afl-fuzz-globals.c b/src/afl-fuzz-globals.c index a5ccfdf9..8340394a 100644 --- a/src/afl-fuzz-globals.c +++ b/src/afl-fuzz-globals.c @@ -74,8 +74,8 @@ u8 *in_dir, /* Input directory with test cases */ *file_extension, /* File extension */ *orig_cmdline; /* Original command line */ u8 *doc_path, /* Path to documentation dir */ - *infoexec, /* Command to execute on a new crash */ - *out_file; /* File to fuzz, if any */ + *infoexec, /* Command to execute on a new crash */ + *out_file; /* File to fuzz, if any */ u32 exec_tmout = EXEC_TIMEOUT; /* Configurable exec timeout (ms) */ u32 hang_tmout = EXEC_TIMEOUT; /* Timeout used for hang det (ms) */ diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index a54c53d8..a37ce8ba 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -138,7 +138,8 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { - if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 2) cpu_used[procs[i].ki_oncpu] = 1; + if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 2) + cpu_used[procs[i].ki_oncpu] = 1; } @@ -166,7 +167,8 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { - if (procs[i].p_cpuid < sizeof(cpu_used) && procs[i].p_pctcpu > 0) cpu_used[procs[i].p_cpuid] = 1; + if (procs[i].p_cpuid < sizeof(cpu_used) && procs[i].p_pctcpu > 0) + cpu_used[procs[i].p_cpuid] = 1; } diff --git a/src/afl-fuzz-run.c b/src/afl-fuzz-run.c index fc235b27..5211921f 100644 --- a/src/afl-fuzz-run.c +++ b/src/afl-fuzz-run.c @@ -288,8 +288,7 @@ void write_to_testcase(void* mem, u32 len) { if (out_file) { - unlink(out_file); /* Ignore errors. - // */ + unlink(out_file); /* Ignore errors. */ fd = open(out_file, O_WRONLY | O_CREAT | O_EXCL, 0600); @@ -331,8 +330,7 @@ void write_with_gap(void* mem, u32 len, u32 skip_at, u32 skip_len) { if (out_file) { - unlink(out_file); /* Ignore errors. - // */ + unlink(out_file); /* Ignore errors. */ fd = open(out_file, O_WRONLY | O_CREAT | O_EXCL, 0600); diff --git a/src/afl-fuzz-stats.c b/src/afl-fuzz-stats.c index f1bc1c8a..7e8639f2 100644 --- a/src/afl-fuzz-stats.c +++ b/src/afl-fuzz-stats.c @@ -334,9 +334,9 @@ void show_stats(void) { /* Lord, forgive me this. */ - SAYF(SET_G1 bSTG bLT bH bSTOP cCYA + SAYF(SET_G1 bSTG bLT bH bSTOP cCYA " process timing " bSTG bH30 bH5 bH bHB bH bSTOP cCYA - " overall results " bSTG bH2 bH2 bRT "\n"); + " overall results " bSTG bH2 bH2 bRT "\n"); if (dumb_mode) { @@ -413,9 +413,9 @@ void show_stats(void) { " uniq hangs : " cRST "%-6s" bSTG bV "\n", DTD(cur_ms, last_hang_time), tmp); - SAYF(bVR bH bSTOP cCYA + SAYF(bVR bH bSTOP cCYA " cycle progress " bSTG bH10 bH5 bH2 bH2 bHB bH bSTOP cCYA - " map coverage " bSTG bH bHT bH20 bH2 bVL "\n"); + " map coverage " bSTG bH bHT bH20 bH2 bVL "\n"); /* This gets funny because we want to print several variable-length variables together, but then cram them into a fixed-width field - so we need to @@ -443,9 +443,9 @@ void show_stats(void) { SAYF(bSTOP " count coverage : " cRST "%-21s" bSTG bV "\n", tmp); - SAYF(bVR bH bSTOP cCYA + SAYF(bVR bH bSTOP cCYA " stage progress " bSTG bH10 bH5 bH2 bH2 bX bH bSTOP cCYA - " findings in depth " bSTG bH10 bH5 bH2 bH2 bVL "\n"); + " findings in depth " bSTG bH10 bH5 bH2 bH2 bVL "\n"); sprintf(tmp, "%s (%0.02f%%)", DI(queued_favored), ((double)queued_favored) * 100 / queued_paths); @@ -514,7 +514,7 @@ void show_stats(void) { /* Aaaalmost there... hold on! */ - SAYF(bVR bH cCYA bSTOP + SAYF(bVR bH cCYA bSTOP " fuzzing strategy yields " bSTG bH10 bHT bH10 bH5 bHB bH bSTOP cCYA " path geometry " bSTG bH5 bH2 bVL "\n"); @@ -633,13 +633,13 @@ void show_stats(void) { sprintf(tmp, "%s/%s", DI(stage_finds[STAGE_CUSTOM_MUTATOR]), DI(stage_cycles[STAGE_CUSTOM_MUTATOR])); SAYF(bV bSTOP " custom mut. : " cRST "%-36s " bSTG bVR bH20 bH2 bH bRB - "\n" bLB bH30 bH20 bH2 bH bRB bSTOP cRST RESET_G1, + "\n" bLB bH30 bH20 bH2 bH bRB bSTOP cRST RESET_G1, tmp); } else { SAYF(bV bSTOP " trim : " cRST "%-36s " bSTG bVR bH20 bH2 bH bRB - "\n" bLB bH30 bH20 bH2 bRB bSTOP cRST RESET_G1, + "\n" bLB bH30 bH20 bH2 bRB bSTOP cRST RESET_G1, tmp); } diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index 3460f91d..44037ce8 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -76,7 +76,8 @@ static void usage(u8* argv0) { "Other stuff:\n" " -T text - text banner to show on the screen\n" " -M / -S id - distributed mode (see parallel_fuzzing.txt)\n" - " -I command - execute this command/script when a new crash is found\n" + " -I command - execute this command/script when a new crash is " + "found\n" " -B bitmap.txt - mutate a specific test case, use the out/fuzz_bitmap " "file\n" " -C - crash exploration mode (the peruvian rabbit thing)\n" @@ -138,10 +139,7 @@ int main(int argc, char** argv) { switch (opt) { - case 'I': - - infoexec = optarg; - break; + case 'I': infoexec = optarg; break; case 's': { diff --git a/test-instr.c b/test-instr.c index 3750b1b5..2450dbf4 100644 --- a/test-instr.c +++ b/test-instr.c @@ -35,7 +35,8 @@ int main(int argc, char** argv) { } - // we support three input cases (plus a 4th if stdin is used but there is no input) + // we support three input cases (plus a 4th if stdin is used but there is no + // input) if (buf[0] == '0') printf("Looks like a zero to me!\n"); else if (buf[0] == '1') @@ -46,3 +47,4 @@ int main(int argc, char** argv) { return 0; } + diff --git a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h index 12e33b2f..3031d3a6 100644 --- a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h +++ b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h @@ -49,7 +49,7 @@ void HELPER(afl_compcov_log_32)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, if ((arg1 & 0xff000000) == (arg2 & 0xff000000)) { - INC_AFL_AREA(cur_loc +2); + INC_AFL_AREA(cur_loc + 2); if ((arg1 & 0xff0000) == (arg2 & 0xff0000)) { INC_AFL_AREA(cur_loc + 1); @@ -68,7 +68,7 @@ void HELPER(afl_compcov_log_64)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, if ((arg1 & 0xff00000000000000) == (arg2 & 0xff00000000000000)) { - INC_AFL_AREA(cur_loc +6); + INC_AFL_AREA(cur_loc + 6); if ((arg1 & 0xff000000000000) == (arg2 & 0xff000000000000)) { INC_AFL_AREA(cur_loc + 5); @@ -84,11 +84,7 @@ void HELPER(afl_compcov_log_64)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, if ((arg1 & 0xff0000) == (arg2 & 0xff0000)) { INC_AFL_AREA(cur_loc + 1); - if ((arg1 & 0xff00) == (arg2 & 0xff00)) { - - INC_AFL_AREA(cur_loc); - - } + if ((arg1 & 0xff00) == (arg2 & 0xff00)) { INC_AFL_AREA(cur_loc); } } -- cgit 1.4.1 From c83e8e1e6255374b085292ba8673efdca7388d76 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 19 Oct 2019 18:23:01 +0200 Subject: Remove lcamtuf's old email from Google (not valid anymore), also remove maintainance from him. --- Makefile | 2 +- afl-cmin | 4 ++-- afl-plot | 4 ++-- afl-whatsup | 4 ++-- dictionaries/gif.dict | 2 +- dictionaries/html_tags.dict | 2 +- dictionaries/jpeg.dict | 2 +- dictionaries/js.dict | 2 +- dictionaries/png.dict | 2 +- dictionaries/sql.dict | 2 +- dictionaries/tiff.dict | 2 +- dictionaries/webp.dict | 2 +- dictionaries/xml.dict | 2 +- docs/power_schedules.txt | 2 +- experimental/argv_fuzzing/argv-fuzz-inl.h | 2 +- experimental/asan_cgroups/limit_memory.sh | 2 +- experimental/canvas_harness/canvas_harness.html | 2 +- experimental/clang_asm_normalize/as | 2 +- experimental/crash_triage/triage_crashes.sh | 4 ++-- experimental/distributed_fuzzing/sync_script.sh | 2 +- experimental/persistent_demo/persistent_demo.c | 2 +- experimental/post_library/post_library.so.c | 2 +- experimental/post_library/post_library_png.so.c | 2 +- gcc_plugin/Makefile | 2 +- gcc_plugin/afl-gcc-fast.c | 2 +- gcc_plugin/afl-gcc-rt.o.c | 2 +- include/afl-as.h | 2 +- include/afl-fuzz.h | 2 +- include/alloc-inl.h | 2 +- include/android-ashmem.h | 2 +- include/common.h | 2 +- include/config.h | 2 +- include/debug.h | 2 +- include/forkserver.h | 2 +- include/hash.h | 2 +- include/sharedmem.h | 2 +- include/types.h | 2 +- libdislocator/Makefile | 2 +- libdislocator/libdislocator.so.c | 2 +- libtokencap/Makefile | 2 +- libtokencap/libtokencap.so.c | 2 +- llvm_mode/Makefile | 2 +- llvm_mode/afl-clang-fast.c | 2 +- llvm_mode/afl-llvm-pass.so.cc | 2 +- llvm_mode/afl-llvm-rt.o.c | 2 +- qemu_mode/build_qemu_support.sh | 2 +- qemu_mode/patches/afl-qemu-common.h | 2 +- qemu_mode/patches/afl-qemu-cpu-inl.h | 2 +- qemu_mode/patches/afl-qemu-cpu-translate-inl.h | 2 +- qemu_mode/patches/afl-qemu-tcg-inl.h | 2 +- qemu_mode/patches/afl-qemu-translate-inl.h | 2 +- src/afl-analyze.c | 4 ++-- src/afl-as.c | 4 ++-- src/afl-common.c | 2 +- src/afl-forkserver.c | 2 +- src/afl-fuzz-bitmap.c | 2 +- src/afl-fuzz-extras.c | 2 +- src/afl-fuzz-globals.c | 2 +- src/afl-fuzz-init.c | 2 +- src/afl-fuzz-misc.c | 2 +- src/afl-fuzz-one.c | 2 +- src/afl-fuzz-python.c | 2 +- src/afl-fuzz-queue.c | 2 +- src/afl-fuzz-run.c | 2 +- src/afl-fuzz-stats.c | 2 +- src/afl-fuzz.c | 4 ++-- src/afl-gcc.c | 6 +++--- src/afl-gotcpu.c | 8 ++++---- src/afl-sharedmem.c | 2 +- src/afl-showmap.c | 4 ++-- src/afl-tmin.c | 4 ++-- test-instr.c | 2 +- unicorn_mode/build_unicorn_support.sh | 2 +- unicorn_mode/patches/afl-unicorn-common.h | 2 +- unicorn_mode/patches/afl-unicorn-cpu-inl.h | 2 +- unicorn_mode/patches/afl-unicorn-cpu-translate-inl.h | 2 +- unicorn_mode/patches/afl-unicorn-tcg-op-inl.h | 2 +- unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h | 2 +- 78 files changed, 92 insertions(+), 92 deletions(-) diff --git a/Makefile b/Makefile index ce0d6781..cfcd0890 100644 --- a/Makefile +++ b/Makefile @@ -2,7 +2,7 @@ # american fuzzy lop - makefile # ----------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2013, 2014, 2015, 2016, 2017 Google Inc. All rights reserved. # diff --git a/afl-cmin b/afl-cmin index 88635550..e4e0fd85 100755 --- a/afl-cmin +++ b/afl-cmin @@ -3,7 +3,7 @@ # american fuzzy lop - corpus minimization tool # --------------------------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2014, 2015 Google Inc. All rights reserved. # @@ -36,7 +36,7 @@ # array sizes. # -echo "corpus minimization tool for afl-fuzz by " +echo "corpus minimization tool for afl-fuzz by Michal Zalewski" echo ######### diff --git a/afl-plot b/afl-plot index bc86fb85..b6108a09 100755 --- a/afl-plot +++ b/afl-plot @@ -3,7 +3,7 @@ # american fuzzy lop - Advanced Persistent Graphing # ------------------------------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # Based on a design & prototype by Michael Rash. # # Copyright 2014, 2015 Google Inc. All rights reserved. @@ -15,7 +15,7 @@ # http://www.apache.org/licenses/LICENSE-2.0 # -echo "progress plotting utility for afl-fuzz by " +echo "progress plotting utility for afl-fuzz by Michal Zalewski" echo if [ ! "$#" = "2" ]; then diff --git a/afl-whatsup b/afl-whatsup index 505f7eba..2666d208 100755 --- a/afl-whatsup +++ b/afl-whatsup @@ -3,7 +3,7 @@ # american fuzzy lop - status check tool # -------------------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2015 Google Inc. All rights reserved. # @@ -17,7 +17,7 @@ # instances of afl-fuzz. # -echo "status check tool for afl-fuzz by " +echo "status check tool for afl-fuzz by Michal Zalewski" echo test "$1" = "-h" && { echo $0 diff --git a/dictionaries/gif.dict b/dictionaries/gif.dict index 71148937..441b3b8d 100644 --- a/dictionaries/gif.dict +++ b/dictionaries/gif.dict @@ -2,7 +2,7 @@ # AFL dictionary for GIF images # ----------------------------- # -# Created by Michal Zalewski +# Created by Michal Zalewski # header_87a="87a" diff --git a/dictionaries/html_tags.dict b/dictionaries/html_tags.dict index ba946df3..2805de90 100644 --- a/dictionaries/html_tags.dict +++ b/dictionaries/html_tags.dict @@ -5,7 +5,7 @@ # A basic collection of HTML tags likely to matter to HTML parsers. Does *not* # include any attributes or attribute values. # -# Created by Michal Zalewski +# Created by Michal Zalewski # tag_a="" diff --git a/dictionaries/jpeg.dict b/dictionaries/jpeg.dict index 15efede7..40282f1a 100644 --- a/dictionaries/jpeg.dict +++ b/dictionaries/jpeg.dict @@ -2,7 +2,7 @@ # AFL dictionary for JPEG images # ------------------------------ # -# Created by Michal Zalewski +# Created by Michal Zalewski # header_jfif="JFIF\x00" diff --git a/dictionaries/js.dict b/dictionaries/js.dict index 9db37bfe..7926364c 100644 --- a/dictionaries/js.dict +++ b/dictionaries/js.dict @@ -4,7 +4,7 @@ # # Contains basic reserved keywords and syntax building blocks. # -# Created by Michal Zalewski +# Created by Michal Zalewski # keyword_arguments="arguments" diff --git a/dictionaries/png.dict b/dictionaries/png.dict index ea12d19e..ad9ea328 100644 --- a/dictionaries/png.dict +++ b/dictionaries/png.dict @@ -5,7 +5,7 @@ # Just the basic, standard-originating sections; does not include vendor # extensions. # -# Created by Michal Zalewski +# Created by Michal Zalewski # header_png="\x89PNG\x0d\x0a\x1a\x0a" diff --git a/dictionaries/sql.dict b/dictionaries/sql.dict index 58342473..efa44ba8 100644 --- a/dictionaries/sql.dict +++ b/dictionaries/sql.dict @@ -11,7 +11,7 @@ # standpoint, because they are usually not allowed in non-privileged # contexts). # -# Created by Michal Zalewski +# Created by Michal Zalewski # function_abs=" abs(1)" diff --git a/dictionaries/tiff.dict b/dictionaries/tiff.dict index 8f04b5af..720e56ce 100644 --- a/dictionaries/tiff.dict +++ b/dictionaries/tiff.dict @@ -5,7 +5,7 @@ # Just the basic, standard-originating sections; does not include vendor # extensions. # -# Created by Michal Zalewski +# Created by Michal Zalewski # header_ii="II*\x00" diff --git a/dictionaries/webp.dict b/dictionaries/webp.dict index 8a70e73b..53aa28c7 100644 --- a/dictionaries/webp.dict +++ b/dictionaries/webp.dict @@ -2,7 +2,7 @@ # AFL dictionary for WebP images # ------------------------------ # -# Created by Michal Zalewski +# Created by Michal Zalewski # header_RIFF="RIFF" diff --git a/dictionaries/xml.dict b/dictionaries/xml.dict index 8127aa28..d8375452 100644 --- a/dictionaries/xml.dict +++ b/dictionaries/xml.dict @@ -4,7 +4,7 @@ # # Several basic syntax elements and attributes, modeled on libxml2. # -# Created by Michal Zalewski +# Created by Michal Zalewski # attr_encoding=" encoding=\"1\"" diff --git a/docs/power_schedules.txt b/docs/power_schedules.txt index f5f66bd6..7b9d34c4 100644 --- a/docs/power_schedules.txt +++ b/docs/power_schedules.txt @@ -2,7 +2,7 @@ afl++'s power schedules based on AFLfast Power schedules implemented by Marcel Böhme \. -AFLFast is an extension of AFL which was written by Michal Zalewski \. +AFLFast is an extension of AFL which was written by Michal Zalewski. AFLfast has helped in the success of Team Codejitsu at the finals of the DARPA Cyber Grand Challenge where their bot Galactica took **2nd place** in terms of #POVs proven (see red bar at https://www.cybergrandchallenge.com/event#results). AFLFast exposed several previously unreported CVEs that could not be exposed by AFL in 24 hours and otherwise exposed vulnerabilities significantly faster than AFL while generating orders of magnitude more unique crashes. diff --git a/experimental/argv_fuzzing/argv-fuzz-inl.h b/experimental/argv_fuzzing/argv-fuzz-inl.h index b042d38c..5d411046 100644 --- a/experimental/argv_fuzzing/argv-fuzz-inl.h +++ b/experimental/argv_fuzzing/argv-fuzz-inl.h @@ -2,7 +2,7 @@ american fuzzy lop - sample argv fuzzing wrapper ------------------------------------------------ - Written by Michal Zalewski + Written by Michal Zalewski Copyright 2015 Google Inc. All rights reserved. diff --git a/experimental/asan_cgroups/limit_memory.sh b/experimental/asan_cgroups/limit_memory.sh index b0c77d15..97950410 100755 --- a/experimental/asan_cgroups/limit_memory.sh +++ b/experimental/asan_cgroups/limit_memory.sh @@ -7,7 +7,7 @@ # David A. Wheeler # # Edits to bring the script in line with afl-cmin and other companion scripts -# by Michal Zalewski . All bugs are my fault. +# by Michal Zalewski. All bugs are my fault. # # Copyright 2015 Institute for Defense Analyses. # diff --git a/experimental/canvas_harness/canvas_harness.html b/experimental/canvas_harness/canvas_harness.html index 19293667..7b31d8b4 100644 --- a/experimental/canvas_harness/canvas_harness.html +++ b/experimental/canvas_harness/canvas_harness.html @@ -4,7 +4,7 @@ american fuzzy lop - harness ------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2013, 2014 Google Inc. All rights reserved. diff --git a/experimental/clang_asm_normalize/as b/experimental/clang_asm_normalize/as index 4ee07e69..bd83c4ff 100755 --- a/experimental/clang_asm_normalize/as +++ b/experimental/clang_asm_normalize/as @@ -3,7 +3,7 @@ # american fuzzy lop - clang assembly normalizer # ---------------------------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # The idea for this wrapper comes from Ryan Govostes. # # Copyright 2013, 2014 Google Inc. All rights reserved. diff --git a/experimental/crash_triage/triage_crashes.sh b/experimental/crash_triage/triage_crashes.sh index 5894a4d6..205bc143 100755 --- a/experimental/crash_triage/triage_crashes.sh +++ b/experimental/crash_triage/triage_crashes.sh @@ -3,7 +3,7 @@ # american fuzzy lop - crash triage utility # ----------------------------------------- # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2013, 2014, 2017 Google Inc. All rights reserved. # @@ -22,7 +22,7 @@ # necessary. # -echo "crash triage utility for afl-fuzz by " +echo "crash triage utility for afl-fuzz by Michal Zalewski" echo ulimit -v 100000 2>/dev/null diff --git a/experimental/distributed_fuzzing/sync_script.sh b/experimental/distributed_fuzzing/sync_script.sh index 2d5e0635..31b0e436 100755 --- a/experimental/distributed_fuzzing/sync_script.sh +++ b/experimental/distributed_fuzzing/sync_script.sh @@ -3,7 +3,7 @@ # american fuzzy lop - fuzzer synchronization tool # ------------------------------------------------ # -# Written and maintained by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2014 Google Inc. All rights reserved. # diff --git a/experimental/persistent_demo/persistent_demo.c b/experimental/persistent_demo/persistent_demo.c index d091febe..a94c8374 100644 --- a/experimental/persistent_demo/persistent_demo.c +++ b/experimental/persistent_demo/persistent_demo.c @@ -2,7 +2,7 @@ american fuzzy lop - persistent mode example -------------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2015 Google Inc. All rights reserved. diff --git a/experimental/post_library/post_library.so.c b/experimental/post_library/post_library.so.c index 72620ff0..048eea70 100644 --- a/experimental/post_library/post_library.so.c +++ b/experimental/post_library/post_library.so.c @@ -2,7 +2,7 @@ american fuzzy lop - postprocessor library example -------------------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2015 Google Inc. All rights reserved. diff --git a/experimental/post_library/post_library_png.so.c b/experimental/post_library/post_library_png.so.c index 080a6938..6ba95c1a 100644 --- a/experimental/post_library/post_library_png.so.c +++ b/experimental/post_library/post_library_png.so.c @@ -2,7 +2,7 @@ american fuzzy lop - postprocessor for PNG ------------------------------------------ - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2015 Google Inc. All rights reserved. diff --git a/gcc_plugin/Makefile b/gcc_plugin/Makefile index d10eba49..a603df78 100644 --- a/gcc_plugin/Makefile +++ b/gcc_plugin/Makefile @@ -4,7 +4,7 @@ # # Written by Austin Seipp and # Laszlo Szekeres and -# Michal Zalewski and +# Michal Zalewski and # Heiko Eißfeldt # # GCC integration design is based on the LLVM design, which comes diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c index 73709321..b0461584 100644 --- a/gcc_plugin/afl-gcc-fast.c +++ b/gcc_plugin/afl-gcc-fast.c @@ -4,7 +4,7 @@ Written by Austin Seipp and Laszlo Szekeres and - Michal Zalewski + Michal Zalewski GCC integration design is based on the LLVM design, which comes from Laszlo Szekeres. diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index f6754bd4..dd79a0ec 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -4,7 +4,7 @@ Written by Austin Seipp and Laszlo Szekeres and - Michal Zalewski + Michal Zalewski GCC integration design is based on the LLVM design, which comes from Laszlo Szekeres. diff --git a/include/afl-as.h b/include/afl-as.h index 048866db..f0263312 100644 --- a/include/afl-as.h +++ b/include/afl-as.h @@ -2,7 +2,7 @@ american fuzzy lop++ - injectable parts --------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/afl-fuzz.h b/include/afl-fuzz.h index 7e9ced46..1e6140dd 100644 --- a/include/afl-fuzz.h +++ b/include/afl-fuzz.h @@ -2,7 +2,7 @@ american fuzzy lop++ - fuzzer header ------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/alloc-inl.h b/include/alloc-inl.h index b0815ab1..f5bb7246 100644 --- a/include/alloc-inl.h +++ b/include/alloc-inl.h @@ -2,7 +2,7 @@ american fuzzy lop++ - error-checking, memory-zeroing alloc routines -------------------------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/android-ashmem.h b/include/android-ashmem.h index 6c7a98db..f4d31739 100644 --- a/include/android-ashmem.h +++ b/include/android-ashmem.h @@ -2,7 +2,7 @@ american fuzzy lop++ - android shared memory compatibility layer ---------------------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/common.h b/include/common.h index e13bf0a0..7c3d4517 100644 --- a/include/common.h +++ b/include/common.h @@ -2,7 +2,7 @@ american fuzzy lop++ - common routines header --------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/config.h b/include/config.h index 396224fb..2e993a42 100644 --- a/include/config.h +++ b/include/config.h @@ -2,7 +2,7 @@ american fuzzy lop++ - vaguely configurable bits ------------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/debug.h b/include/debug.h index cccfc284..ed6c29e9 100644 --- a/include/debug.h +++ b/include/debug.h @@ -2,7 +2,7 @@ american fuzzy lop++ - debug / error handling macros ---------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/include/forkserver.h b/include/forkserver.h index 9a099888..9cabe58e 100644 --- a/include/forkserver.h +++ b/include/forkserver.h @@ -2,7 +2,7 @@ american fuzzy lop++ - forkserver header ---------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn diff --git a/include/hash.h b/include/hash.h index 7085df32..1a8ac252 100644 --- a/include/hash.h +++ b/include/hash.h @@ -12,7 +12,7 @@ Austin's original code is public domain. - Other code written and maintained by Michal Zalewski + Other code written by Michal Zalewski Copyright 2016 Google Inc. All rights reserved. diff --git a/include/sharedmem.h b/include/sharedmem.h index 18e4ee9f..cec6c025 100644 --- a/include/sharedmem.h +++ b/include/sharedmem.h @@ -2,7 +2,7 @@ american fuzzy lop++ - shared memory related header --------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn diff --git a/include/types.h b/include/types.h index 07fc7e91..c34bf522 100644 --- a/include/types.h +++ b/include/types.h @@ -2,7 +2,7 @@ american fuzzy lop++ - type definitions and minor macros -------------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/libdislocator/Makefile b/libdislocator/Makefile index cbaa05ea..91efba07 100644 --- a/libdislocator/Makefile +++ b/libdislocator/Makefile @@ -2,7 +2,7 @@ # american fuzzy lop - libdislocator # ---------------------------------- # -# Written by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2016 Google Inc. All rights reserved. # diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 8834a1fc..57607210 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -3,7 +3,7 @@ american fuzzy lop - dislocator, an abusive allocator ----------------------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2016 Google Inc. All rights reserved. diff --git a/libtokencap/Makefile b/libtokencap/Makefile index 3fd01b2c..91933140 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -2,7 +2,7 @@ # american fuzzy lop - libtokencap # -------------------------------- # -# Written by Michal Zalewski +# Written by Michal Zalewski # # Copyright 2016 Google Inc. All rights reserved. # diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 17b6190c..39095beb 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -3,7 +3,7 @@ american fuzzy lop - extract tokens passed to strcmp / memcmp ------------------------------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2016 Google Inc. All rights reserved. diff --git a/llvm_mode/Makefile b/llvm_mode/Makefile index 0360bfbe..7cfbe92d 100644 --- a/llvm_mode/Makefile +++ b/llvm_mode/Makefile @@ -3,7 +3,7 @@ # ----------------------------------------- # # Written by Laszlo Szekeres and -# Michal Zalewski +# Michal Zalewski # # LLVM integration design comes from Laszlo Szekeres. # diff --git a/llvm_mode/afl-clang-fast.c b/llvm_mode/afl-clang-fast.c index 54f9e6e9..a7f6acdc 100644 --- a/llvm_mode/afl-clang-fast.c +++ b/llvm_mode/afl-clang-fast.c @@ -3,7 +3,7 @@ ------------------------------------------------ Written by Laszlo Szekeres and - Michal Zalewski + Michal Zalewski LLVM integration design comes from Laszlo Szekeres. diff --git a/llvm_mode/afl-llvm-pass.so.cc b/llvm_mode/afl-llvm-pass.so.cc index 3ca5ccc4..475a3f33 100644 --- a/llvm_mode/afl-llvm-pass.so.cc +++ b/llvm_mode/afl-llvm-pass.so.cc @@ -3,7 +3,7 @@ --------------------------------------------------- Written by Laszlo Szekeres and - Michal Zalewski + Michal Zalewski LLVM integration design comes from Laszlo Szekeres. C bits copied-and-pasted from afl-as.c are Michal's fault. diff --git a/llvm_mode/afl-llvm-rt.o.c b/llvm_mode/afl-llvm-rt.o.c index 20b34336..5740fe42 100644 --- a/llvm_mode/afl-llvm-rt.o.c +++ b/llvm_mode/afl-llvm-rt.o.c @@ -3,7 +3,7 @@ --------------------------------------------------- Written by Laszlo Szekeres and - Michal Zalewski + Michal Zalewski LLVM integration design comes from Laszlo Szekeres. diff --git a/qemu_mode/build_qemu_support.sh b/qemu_mode/build_qemu_support.sh index 55d72e0d..f18cbdf3 100755 --- a/qemu_mode/build_qemu_support.sh +++ b/qemu_mode/build_qemu_support.sh @@ -4,7 +4,7 @@ # -------------------------------------- # # Originally written by Andrew Griffiths and -# Michal Zalewski +# Michal Zalewski # # TCG instrumentation and block chaining support by Andrea Biondo # diff --git a/qemu_mode/patches/afl-qemu-common.h b/qemu_mode/patches/afl-qemu-common.h index c86b5b45..1da3359d 100644 --- a/qemu_mode/patches/afl-qemu-common.h +++ b/qemu_mode/patches/afl-qemu-common.h @@ -3,7 +3,7 @@ ------------------------------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski TCG instrumentation and block chaining support by Andrea Biondo diff --git a/qemu_mode/patches/afl-qemu-cpu-inl.h b/qemu_mode/patches/afl-qemu-cpu-inl.h index 262a7dab..7358fc3b 100644 --- a/qemu_mode/patches/afl-qemu-cpu-inl.h +++ b/qemu_mode/patches/afl-qemu-cpu-inl.h @@ -3,7 +3,7 @@ ------------------------------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski TCG instrumentation and block chaining support by Andrea Biondo diff --git a/qemu_mode/patches/afl-qemu-cpu-translate-inl.h b/qemu_mode/patches/afl-qemu-cpu-translate-inl.h index b6d3da1f..62858724 100644 --- a/qemu_mode/patches/afl-qemu-cpu-translate-inl.h +++ b/qemu_mode/patches/afl-qemu-cpu-translate-inl.h @@ -3,7 +3,7 @@ ------------------------------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski TCG instrumentation and block chaining support by Andrea Biondo diff --git a/qemu_mode/patches/afl-qemu-tcg-inl.h b/qemu_mode/patches/afl-qemu-tcg-inl.h index d7a25695..e3de09d8 100644 --- a/qemu_mode/patches/afl-qemu-tcg-inl.h +++ b/qemu_mode/patches/afl-qemu-tcg-inl.h @@ -3,7 +3,7 @@ ------------------------------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski TCG instrumentation and block chaining support by Andrea Biondo diff --git a/qemu_mode/patches/afl-qemu-translate-inl.h b/qemu_mode/patches/afl-qemu-translate-inl.h index 5f61d7c9..881dbc8d 100644 --- a/qemu_mode/patches/afl-qemu-translate-inl.h +++ b/qemu_mode/patches/afl-qemu-translate-inl.h @@ -3,7 +3,7 @@ ------------------------------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski TCG instrumentation and block chaining support by Andrea Biondo diff --git a/src/afl-analyze.c b/src/afl-analyze.c index 2d13621b..5555a262 100644 --- a/src/afl-analyze.c +++ b/src/afl-analyze.c @@ -2,7 +2,7 @@ american fuzzy lop++ - file format analyzer ------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and @@ -841,7 +841,7 @@ int main(int argc, char** argv) { doc_path = access(DOC_PATH, F_OK) ? "docs" : DOC_PATH; - SAYF(cCYA "afl-analyze" VERSION cRST " by \n"); + SAYF(cCYA "afl-analyze" VERSION cRST " by Michal Zalewski\n"); while ((opt = getopt(argc, argv, "+i:f:m:t:eQUWh")) > 0) diff --git a/src/afl-as.c b/src/afl-as.c index b5a5ed58..2b023432 100644 --- a/src/afl-as.c +++ b/src/afl-as.c @@ -2,7 +2,7 @@ american fuzzy lop++ - wrapper for GNU as ----------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and @@ -501,7 +501,7 @@ int main(int argc, char** argv) { if (isatty(2) && !getenv("AFL_QUIET")) { - SAYF(cCYA "afl-as" VERSION cRST " by \n"); + SAYF(cCYA "afl-as" VERSION cRST " by Michal Zalewski\n"); } else diff --git a/src/afl-common.c b/src/afl-common.c index e753e797..ec010c2d 100644 --- a/src/afl-common.c +++ b/src/afl-common.c @@ -2,7 +2,7 @@ american fuzzy lop++ - common routines -------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-forkserver.c b/src/afl-forkserver.c index d9f67da5..b11ee5ce 100644 --- a/src/afl-forkserver.c +++ b/src/afl-forkserver.c @@ -2,7 +2,7 @@ american fuzzy lop++ - forkserver code -------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn diff --git a/src/afl-fuzz-bitmap.c b/src/afl-fuzz-bitmap.c index d001dbee..22876626 100644 --- a/src/afl-fuzz-bitmap.c +++ b/src/afl-fuzz-bitmap.c @@ -2,7 +2,7 @@ american fuzzy lop++ - bitmap related routines ---------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-extras.c b/src/afl-fuzz-extras.c index 1a0e2eff..23b2c235 100644 --- a/src/afl-fuzz-extras.c +++ b/src/afl-fuzz-extras.c @@ -2,7 +2,7 @@ american fuzzy lop++ - extras relates routines ---------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-globals.c b/src/afl-fuzz-globals.c index 8340394a..36ba6e14 100644 --- a/src/afl-fuzz-globals.c +++ b/src/afl-fuzz-globals.c @@ -2,7 +2,7 @@ american fuzzy lop++ - globals declarations ------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index a37ce8ba..a77904b5 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -2,7 +2,7 @@ american fuzzy lop++ - initialization related routines ------------------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-misc.c b/src/afl-fuzz-misc.c index a7372b7d..f45642f4 100644 --- a/src/afl-fuzz-misc.c +++ b/src/afl-fuzz-misc.c @@ -2,7 +2,7 @@ american fuzzy lop++ - misc stuffs from Mordor ---------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-one.c b/src/afl-fuzz-one.c index 31d58a10..bed8d254 100644 --- a/src/afl-fuzz-one.c +++ b/src/afl-fuzz-one.c @@ -2,7 +2,7 @@ american fuzzy lop++ - fuzze_one routines in different flavours --------------------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-python.c b/src/afl-fuzz-python.c index 1a28f603..1a8b7f9d 100644 --- a/src/afl-fuzz-python.c +++ b/src/afl-fuzz-python.c @@ -2,7 +2,7 @@ american fuzzy lop++ - python extension routines ------------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-queue.c b/src/afl-fuzz-queue.c index 905fd931..9f036186 100644 --- a/src/afl-fuzz-queue.c +++ b/src/afl-fuzz-queue.c @@ -2,7 +2,7 @@ american fuzzy lop++ - queue relates routines --------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-run.c b/src/afl-fuzz-run.c index 5211921f..e12b06eb 100644 --- a/src/afl-fuzz-run.c +++ b/src/afl-fuzz-run.c @@ -2,7 +2,7 @@ american fuzzy lop++ - target execution related routines -------------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz-stats.c b/src/afl-fuzz-stats.c index 7e8639f2..2ea03e94 100644 --- a/src/afl-fuzz-stats.c +++ b/src/afl-fuzz-stats.c @@ -2,7 +2,7 @@ american fuzzy lop++ - stats related routines --------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index 44037ce8..bb342112 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -2,7 +2,7 @@ american fuzzy lop - fuzzer code -------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and @@ -127,7 +127,7 @@ int main(int argc, char** argv) { SAYF(cCYA "afl-fuzz" VERSION cRST - " based on afl by and a big online community\n"); + " based on afl by Michal Zalewski and a big online community\n"); doc_path = access(DOC_PATH, F_OK) ? "docs" : DOC_PATH; diff --git a/src/afl-gcc.c b/src/afl-gcc.c index dd7ba4d6..740442dc 100644 --- a/src/afl-gcc.c +++ b/src/afl-gcc.c @@ -2,7 +2,7 @@ american fuzzy lop++ - wrapper for GCC and clang ------------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and @@ -335,7 +335,7 @@ int main(int argc, char** argv) { if (argc == 2 && strcmp(argv[1], "-h") == 0) { - printf("afl-cc" VERSION " by \n\n"); + printf("afl-cc" VERSION " by Michal Zalewski\n\n"); printf("%s \n\n", argv[0]); printf("afl-gcc has no command line options\n"); printf( @@ -347,7 +347,7 @@ int main(int argc, char** argv) { if (isatty(2) && !getenv("AFL_QUIET")) { - SAYF(cCYA "afl-cc" VERSION cRST " by \n"); + SAYF(cCYA "afl-cc" VERSION cRST " by Michal Zalewski\n"); SAYF(cYEL "[!] " cBRI "NOTE: " cRST "afl-gcc is deprecated, llvm_mode is much faster and has more " "options\n"); diff --git a/src/afl-gotcpu.c b/src/afl-gotcpu.c index dc938b65..850943dd 100644 --- a/src/afl-gotcpu.c +++ b/src/afl-gotcpu.c @@ -2,7 +2,7 @@ american fuzzy lop - free CPU gizmo ----------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Now maintained by by Marc Heuse , Heiko Eißfeldt and @@ -142,7 +142,7 @@ int main(int argc, char** argv) { if (argc > 1) { - printf("afl-gotcpu" VERSION " by \n"); + printf("afl-gotcpu" VERSION " by Michal Zalewski\n"); printf("\n%s \n\n", argv[0]); printf("afl-gotcpu does not have command line options\n"); printf("afl-gotcpu prints out which CPUs are available\n"); @@ -154,7 +154,7 @@ int main(int argc, char** argv) { u32 cpu_cnt = sysconf(_SC_NPROCESSORS_ONLN), idle_cpus = 0, maybe_cpus = 0, i; - SAYF(cCYA "afl-gotcpu" VERSION cRST " by \n"); + SAYF(cCYA "afl-gotcpu" VERSION cRST " by Michal Zalewski\n"); ACTF("Measuring per-core preemption rate (this will take %0.02f sec)...", ((double)CTEST_CORE_TRG_MS) / 1000); @@ -275,7 +275,7 @@ int main(int argc, char** argv) { u32 util_perc; - SAYF(cCYA "afl-gotcpu" VERSION cRST " by \n"); + SAYF(cCYA "afl-gotcpu" VERSION cRST " by Michal Zalewski\n"); /* Run a busy loop for CTEST_TARGET_MS. */ diff --git a/src/afl-sharedmem.c b/src/afl-sharedmem.c index 0bd1ff2f..d94100a3 100644 --- a/src/afl-sharedmem.c +++ b/src/afl-sharedmem.c @@ -2,7 +2,7 @@ american fuzzy lop++ - shared memory related code ------------------------------------------------- - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn diff --git a/src/afl-showmap.c b/src/afl-showmap.c index 31f12856..b54ac2b0 100644 --- a/src/afl-showmap.c +++ b/src/afl-showmap.c @@ -2,7 +2,7 @@ american fuzzy lop++ - map display utility ------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn @@ -395,7 +395,7 @@ static void setup_signal_handlers(void) { static void show_banner(void) { - SAYF(cCYA "afl-showmap" VERSION cRST " by \n"); + SAYF(cCYA "afl-showmap" VERSION cRST " by Michal Zalewski\n"); } diff --git a/src/afl-tmin.c b/src/afl-tmin.c index 7f354727..a72e1dda 100644 --- a/src/afl-tmin.c +++ b/src/afl-tmin.c @@ -2,7 +2,7 @@ american fuzzy lop++ - test case minimizer ------------------------------------------ - Originally written by Michal Zalewski + Originally written by Michal Zalewski Forkserver design by Jann Horn @@ -1032,7 +1032,7 @@ int main(int argc, char** argv) { doc_path = access(DOC_PATH, F_OK) ? "docs" : DOC_PATH; - SAYF(cCYA "afl-tmin" VERSION cRST " by \n"); + SAYF(cCYA "afl-tmin" VERSION cRST " by Michal Zalewski\n"); while ((opt = getopt(argc, argv, "+i:o:f:m:t:B:xeQUWh")) > 0) diff --git a/test-instr.c b/test-instr.c index 2450dbf4..161bdb8e 100644 --- a/test-instr.c +++ b/test-instr.c @@ -2,7 +2,7 @@ american fuzzy lop - a trivial program to test the build -------------------------------------------------------- - Written and maintained by Michal Zalewski + Written by Michal Zalewski Copyright 2014 Google Inc. All rights reserved. diff --git a/unicorn_mode/build_unicorn_support.sh b/unicorn_mode/build_unicorn_support.sh index 1575f66c..3bd404b8 100755 --- a/unicorn_mode/build_unicorn_support.sh +++ b/unicorn_mode/build_unicorn_support.sh @@ -6,7 +6,7 @@ # Originally written by Nathan Voss # # Adapted from code by Andrew Griffiths and -# Michal Zalewski +# Michal Zalewski # # Adapted for AFLplusplus by Dominik Maier # diff --git a/unicorn_mode/patches/afl-unicorn-common.h b/unicorn_mode/patches/afl-unicorn-common.h index fd88e21b..66d03803 100644 --- a/unicorn_mode/patches/afl-unicorn-common.h +++ b/unicorn_mode/patches/afl-unicorn-common.h @@ -3,7 +3,7 @@ ---------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski Adapted for afl-unicorn by Dominik Maier diff --git a/unicorn_mode/patches/afl-unicorn-cpu-inl.h b/unicorn_mode/patches/afl-unicorn-cpu-inl.h index 082d6d68..72092e29 100644 --- a/unicorn_mode/patches/afl-unicorn-cpu-inl.h +++ b/unicorn_mode/patches/afl-unicorn-cpu-inl.h @@ -3,7 +3,7 @@ ---------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski Adapted for afl-unicorn by Dominik Maier diff --git a/unicorn_mode/patches/afl-unicorn-cpu-translate-inl.h b/unicorn_mode/patches/afl-unicorn-cpu-translate-inl.h index 7c84058f..70472a72 100644 --- a/unicorn_mode/patches/afl-unicorn-cpu-translate-inl.h +++ b/unicorn_mode/patches/afl-unicorn-cpu-translate-inl.h @@ -3,7 +3,7 @@ ---------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski Adapted for afl-unicorn by Dominik Maier diff --git a/unicorn_mode/patches/afl-unicorn-tcg-op-inl.h b/unicorn_mode/patches/afl-unicorn-tcg-op-inl.h index d21bbcc7..8f4a8748 100644 --- a/unicorn_mode/patches/afl-unicorn-tcg-op-inl.h +++ b/unicorn_mode/patches/afl-unicorn-tcg-op-inl.h @@ -3,7 +3,7 @@ ---------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski Adapted for afl-unicorn by Dominik Maier diff --git a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h index 3031d3a6..53ab654c 100644 --- a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h +++ b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h @@ -3,7 +3,7 @@ ---------------------------------------------- Originally written by Andrew Griffiths and - Michal Zalewski + Michal Zalewski Adapted for afl-unicorn by Dominik Maier -- cgit 1.4.1 From a282ae22afec0e5d5a8455c7aaa3e472839788e4 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sun, 20 Oct 2019 03:34:46 +0200 Subject: In OpenBSD initial thread local storage is allocated with calloc(), which leads to locked mutexes and a stall. So no thread support (and no tls) here. --- libdislocator/libdislocator.so.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 57607210..f3f02c8b 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -88,6 +88,10 @@ static u8 alloc_verbose, /* Additional debug messages */ hard_fail, /* abort() when max_mem exceeded? */ no_calloc_over; /* abort() on calloc() overflows? */ +#ifdef __OpenBSD__ +#define __thread +#warning no thread support available +#endif static __thread size_t total_mem; /* Currently allocated mem */ static __thread u32 call_depth; /* To avoid recursion via fprintf() */ -- cgit 1.4.1 From d0bbef74ef4ecdf41f7b88b77ff833b563d78450 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sun, 20 Oct 2019 02:35:06 +0200 Subject: loading dynamical libraries on Darwin/MacOSX is done with DYLD_INSERT_LIBRARIES --- test/test.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index 1c5cdda6..d1be014f 100755 --- a/test/test.sh +++ b/test/test.sh @@ -281,7 +281,8 @@ test -e ../libtokencap.so && { test -e ../libdislocator.so && { { ulimit -c 1 - LD_PRELOAD=../libdislocator.so ./test-compcov BUFFEROVERFLOW > test.out 2> /dev/null + # DYLD_INSERT_LIBRARIES is used on Darwin/MacOSX + LD_PRELOAD=../libdislocator.so DYLD_INSERT_LIBRARIES=../libdislocator.so ./test-compcov BUFFEROVERFLOW > test.out 2> /dev/null } > /dev/null 2>&1 grep -q BUFFEROVERFLOW test.out > /dev/null 2>&1 && { $ECHO "$RED[!] libdislocator did not detect the memory corruption" -- cgit 1.4.1 From be6bc155ebd891eebd21eac8982784e7f2be4f41 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 21 Oct 2019 11:28:32 +0200 Subject: v2.58c --- Makefile | 9 ++++++++- README.md | 18 +++++++++--------- TODO | 5 +---- docs/ChangeLog | 14 ++++++++------ gcc_plugin/README.gcc.md | 4 ---- gcc_plugin/README.whitelist.md | 3 +-- include/config.h | 2 +- 7 files changed, 28 insertions(+), 27 deletions(-) diff --git a/Makefile b/Makefile index cfcd0890..87c7cdef 100644 --- a/Makefile +++ b/Makefile @@ -104,6 +104,13 @@ man: $(MANPAGES) tests: source-only @cd test ; ./test.sh +performance-tests: performance-test +test-performance: performance-test + +performance-test: source-only + @cd test ; ./test-performance.sh + + help: @echo "HELP --- the following make targets exist:" @echo "==========================================" @@ -307,7 +314,7 @@ install: all $(MANPAGES) install -m 755 $(PROGS) $(SH_PROGS) $${DESTDIR}$(BIN_PATH) rm -f $${DESTDIR}$(BIN_PATH)/afl-as if [ -f afl-qemu-trace ]; then install -m 755 afl-qemu-trace $${DESTDIR}$(BIN_PATH); fi - #if [ -f afl-gcc-fast ]; then set e; install -m 755 afl-gcc-fast $${DESTDIR}$(BIN_PATH); ln -sf afl-gcc-fast $${DESTDIR}$(BIN_PATH)/afl-g++-fast; install -m 755 afl-gcc-pass.so afl-gcc-rt.o $${DESTDIR}$(HELPER_PATH); fi + if [ -f afl-gcc-fast ]; then set e; install -m 755 afl-gcc-fast $${DESTDIR}$(BIN_PATH); ln -sf afl-gcc-fast $${DESTDIR}$(BIN_PATH)/afl-g++-fast; install -m 755 afl-gcc-pass.so afl-gcc-rt.o $${DESTDIR}$(HELPER_PATH); fi ifndef AFL_TRACE_PC if [ -f afl-clang-fast -a -f libLLVMInsTrim.so -a -f afl-llvm-rt.o ]; then set -e; install -m 755 afl-clang-fast $${DESTDIR}$(BIN_PATH); ln -sf afl-clang-fast $${DESTDIR}$(BIN_PATH)/afl-clang-fast++; install -m 755 libLLVMInsTrim.so afl-llvm-pass.so afl-llvm-rt.o $${DESTDIR}$(HELPER_PATH); fi else diff --git a/README.md b/README.md index f0e6faef..4b9537d2 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,8 @@ # american fuzzy lop plus plus (afl++) - Release Version: 2.57c + Release Version: 2.58c - Github Version: 2.57d + Github Version: 2.58d includes all necessary/interesting changes from Google's afl 2.56b @@ -52,13 +52,13 @@ A more thorough list is available in the PATCHES file. - | Feature/Instrumentation | LLVM | GCC | QEMU | Unicorn | - | ----------------------- |:----:|:---:|:----:| -------:| - | laf-intel / CompCov | x | | x | x | - | NeverZero | x(1)| x | x | x | - | Persistent mode | x | | x | | - | Whitelist | x | | | | - | InsTrim | x | | | | + | Feature/Instrumentation | AFL-GCC | LLVM_MODE | GCC_PLUGIN | QEMU_MODE | Unicorn | + | ----------------------- |:-------:|:---------:|:----------:|:---------:|:-------:| + | laf-intel / CompCov | | x | | x | x | + | NeverZero | X | x(1) | | x | x | + | Persistent mode | | x | X | x | | + | Whitelist | | x | X | | | + | InsTrim | | x | | | | (1) only in LLVM >= 9.0 due to a bug in llvm in previous versions diff --git a/TODO b/TODO index 3ca13d6e..f2642b1a 100644 --- a/TODO +++ b/TODO @@ -7,11 +7,8 @@ afl-fuzz: - test the libmutator actually works and does not run infinite (need an example though) gcc_plugin: - - needs to be rewritten - - whitelist support - - skip over uninteresting blocks - - laf-intel - neverZero + - laf-intel qemu_mode: - update to 4.x (probably this will be skipped :( ) diff --git a/docs/ChangeLog b/docs/ChangeLog index 46b9e330..c2d46e4d 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -13,14 +13,16 @@ Want to stay in the loop on major new features? Join our mailing list by sending a mail to . ----------------------- -Version ++2.57d (dev): ----------------------- +-------------------------- +Version ++2.58c (release): +-------------------------- - - reverted patch to not unlink and recreate the input file, it resulted in performance loss + - reverted patch to not unlink and recreate the input file, it resulted in + performance loss of ~10% - added test/test-performance.sh script - - (re)added gcc_plugin, fast inline instrumentation is not yet finished - - added gcc_plugin tests + - (re)added gcc_plugin, fast inline instrumentation is not yet finished, + however it includes the whitelisting and persistance feature! by hexcoder- + - gcc_plugin tests added to testing framework -------------------------------- diff --git a/gcc_plugin/README.gcc.md b/gcc_plugin/README.gcc.md index 2e19e911..676ef427 100644 --- a/gcc_plugin/README.gcc.md +++ b/gcc_plugin/README.gcc.md @@ -156,7 +156,3 @@ depending on whether the input loop is being entered for the first time or executed again. To avoid spurious warnings, the feature implies AFL_NO_VAR_CHECK and hides the "variable path" warnings in the UI. -PS. Because there are task switches still involved, the mode isn't as fast as -"pure" in-process fuzzing offered, say, by LLVM's LibFuzzer; but it is a lot -faster than the normal fork() model, and compared to in-process fuzzing, -should be a lot more robust. diff --git a/gcc_plugin/README.whitelist.md b/gcc_plugin/README.whitelist.md index bcc02693..8ad2068d 100644 --- a/gcc_plugin/README.whitelist.md +++ b/gcc_plugin/README.whitelist.md @@ -6,8 +6,7 @@ Using afl++ with partial instrumentation that are interesting to you using the gcc instrumentation provided by afl++. - Originally developed by Christian Holler (:decoder) , - adapted to gcc plugin by hexcoder-. + Plugin by hexcoder-. ## 1) Description and purpose diff --git a/include/config.h b/include/config.h index 2e993a42..f121025d 100644 --- a/include/config.h +++ b/include/config.h @@ -26,7 +26,7 @@ /* Version string: */ -#define VERSION "++2.57d" // c = release, d = volatile github dev +#define VERSION "++2.58c" // c = release, d = volatile github dev /****************************************************** * * -- cgit 1.4.1 From ebea44029e019960cbf075dacd7b1a1f79d1bae2 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 21 Oct 2019 11:30:28 +0200 Subject: 2.58d --- include/config.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/config.h b/include/config.h index f121025d..144d3810 100644 --- a/include/config.h +++ b/include/config.h @@ -26,7 +26,7 @@ /* Version string: */ -#define VERSION "++2.58c" // c = release, d = volatile github dev +#define VERSION "++2.58d" // c = release, d = volatile github dev /****************************************************** * * -- cgit 1.4.1 From bc3ce26e0ecbf97751c6eb444df8e5bf31dcafd7 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 21 Oct 2019 17:18:41 +0200 Subject: -V/-E not precise --- TODO | 1 + src/afl-fuzz.c | 4 +++- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/TODO b/TODO index f2642b1a..05c89679 100644 --- a/TODO +++ b/TODO @@ -3,6 +3,7 @@ Roadmap 2.60: ============= afl-fuzz: + - change -T to use alarm() instead - radamsa mutator - test the libmutator actually works and does not run infinite (need an example though) diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index bb342112..25f606fa 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -71,7 +71,9 @@ static void usage(u8* argv0) { " -V seconds - fuzz for a maximum total time of seconds then " "terminate\n" " -E execs - fuzz for a maximum number of total executions then " - "terminate\n\n" + "terminate\n" + "Note: -V/-E are not precise, they are checked after a queue entry is " + "done which\n can be many minutes/execs later\n\n" "Other stuff:\n" " -T text - text banner to show on the screen\n" -- cgit 1.4.1 From a033364d55332530b15f2a0f2863b3448bb2bab9 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 21 Oct 2019 23:07:05 +0200 Subject: implement neverZero counter for __afl_trace() --- gcc_plugin/afl-gcc-rt.o.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index dd79a0ec..6cf9f167 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -50,8 +50,10 @@ static u8 is_persistent; void __afl_trace(u32 x) { u32 l = __afl_prev_loc; - u32 n = l ^ x; - *(__afl_area_ptr + n) += 1; + const u32 n = l ^ x; + u8 *const bitmap_ptr = __afl_area_ptr + n; + *bitmap_ptr += 1 + (*bitmap_ptr == (u8)~0); /* neverZero */ + __afl_prev_loc = (x >> 1); return; -- cgit 1.4.1 From 9a5882a2909c663b58f1e36b4298eeb09ecc3bf4 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 21 Oct 2019 23:35:09 +0200 Subject: sync afl-gcc-rt.o.c from its more current llvm cousin --- gcc_plugin/afl-gcc-rt.o.c | 90 ++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 82 insertions(+), 8 deletions(-) diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index 6cf9f167..1dfca9e3 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -21,12 +21,16 @@ */ +#ifdef __ANDROID__ +#include "android-ashmem.h" +#endif #include "../config.h" #include "../types.h" #include #include #include +#include #include #include @@ -34,17 +38,21 @@ #include #include +#include +#include + /* Globals needed by the injected instrumentation. The __afl_area_initial region is used for instrumentation output before __afl_map_shm() has a chance to run. It will end up as .comm, so it shouldn't be too wasteful. */ u8 __afl_area_initial[MAP_SIZE]; u8 *__afl_area_ptr = __afl_area_initial; -u32 __afl_prev_loc; - -/* Running in persistent mode? */ -static u8 is_persistent; +#ifdef __ANDROID__ +u32 __afl_prev_loc; +#else +__thread u32 __afl_prev_loc; +#endif /* Trace a basic block with some ID */ void __afl_trace(u32 x) { @@ -59,6 +67,10 @@ void __afl_trace(u32 x) { } +/* Running in persistent mode? */ + +static u8 is_persistent; + /* SHM setup. */ static void __afl_map_shm(void) { @@ -71,9 +83,38 @@ static void __afl_map_shm(void) { if (id_str) { +#ifdef USEMMAP + const char* shm_file_path = id_str; + int shm_fd = -1; + unsigned char* shm_base = NULL; + + /* create the shared memory segment as if it was a file */ + shm_fd = shm_open(shm_file_path, O_RDWR, 0600); + if (shm_fd == -1) { + + printf("shm_open() failed\n"); + exit(1); + + } + + /* map the shared memory segment to the address space of the process */ + shm_base = mmap(0, MAP_SIZE, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fd, 0); + if (shm_base == MAP_FAILED) { + + close(shm_fd); + shm_fd = -1; + + printf("mmap() failed\n"); + exit(2); + + } + + __afl_area_ptr = shm_base; +#else u32 shm_id = atoi(id_str); __afl_area_ptr = shmat(shm_id, NULL, 0); +#endif /* Whooooops. */ @@ -97,6 +138,8 @@ static void __afl_start_forkserver(void) { u8 child_stopped = 0; + void (*old_sigchld_handler)(int) = signal(SIGCHLD, SIG_DFL); + /* Phone home and tell the parent that we're OK. If parent isn't there, assume we're not running in forkserver mode and just execute program. */ @@ -133,6 +176,8 @@ static void __afl_start_forkserver(void) { if (!child_pid) { + signal(SIGCHLD, old_sigchld_handler); + close(FORKSRV_FD); close(FORKSRV_FD + 1); return; @@ -178,18 +223,47 @@ int __afl_persistent_loop(unsigned int max_cnt) { if (first_pass) { + /* Make sure that every iteration of __AFL_LOOP() starts with a clean slate. + On subsequent calls, the parent will take care of that, but on the first + iteration, it's our job to erase any trace of whatever happened + before the loop. */ + + if (is_persistent) { + + memset(__afl_area_ptr, 0, MAP_SIZE); + __afl_area_ptr[0] = 1; + __afl_prev_loc = 0; + + } + cycle_cnt = max_cnt; first_pass = 0; return 1; } - if (is_persistent && --cycle_cnt) { + if (is_persistent) { - raise(SIGSTOP); - return 1; + if (--cycle_cnt) { + + raise(SIGSTOP); - } else + __afl_area_ptr[0] = 1; + __afl_prev_loc = 0; + + return 1; + + } else { + + /* When exiting __AFL_LOOP(), make sure that the subsequent code that + follows the loop is not traced. We do that by pivoting back to the + dummy output region. */ + + __afl_area_ptr = __afl_area_initial; + + } + + } return 0; -- cgit 1.4.1 From cc2f3afdf8ad4e4b596f66acfe148cac12f421d7 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 21 Oct 2019 23:53:56 +0200 Subject: sync llvm_mode/Makefile to gcc_plugin/Makefile --- Makefile | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/Makefile b/Makefile index 87c7cdef..e70ac892 100644 --- a/Makefile +++ b/Makefile @@ -16,9 +16,6 @@ # For Heiko: #TEST_MMAP=1 -PROGNAME = afl -VERSION = $(shell grep '^\#define VERSION ' include/config.h | cut -d '"' -f2) - PREFIX ?= /usr/local BIN_PATH = $(PREFIX)/bin HELPER_PATH = $(PREFIX)/lib/afl @@ -26,6 +23,9 @@ DOC_PATH = $(PREFIX)/share/doc/afl MISC_PATH = $(PREFIX)/share/afl MAN_PATH = $(PREFIX)/man/man8 +PROGNAME = afl +VERSION = $(shell grep '^\#define VERSION ' ../config.h | cut -d '"' -f2) + # PROGS intentionally omit afl-as, which gets installed elsewhere. PROGS = afl-gcc afl-fuzz afl-showmap afl-tmin afl-gotcpu afl-analyze @@ -34,8 +34,12 @@ MANPAGES=$(foreach p, $(PROGS) $(SH_PROGS), $(p).8) CFLAGS ?= -O3 -funroll-loops CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign -I include/ \ - -DAFL_PATH=\"$(HELPER_PATH)\" -DDOC_PATH=\"$(DOC_PATH)\" \ - -DBIN_PATH=\"$(BIN_PATH)\" -Wno-unused-function + -DAFL_PATH=\"$(HELPER_PATH)\" -DBIN_PATH=\"$(BIN_PATH)\" \ + -DVERSION=\"$(VERSION)\" -Wno-unused-function + +CXXFLAGS ?= -O3 -funroll-loops +CXXFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -I ../include/ \ + -DVERSION=\"$(VERSION)\" -Wno-variadic-macros AFL_FUZZ_FILES = $(wildcard src/afl-fuzz*.c) -- cgit 1.4.1 From 7ab11c3da946c7e1df5271d5a3439dc9e799523f Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 22 Oct 2019 13:19:08 +0200 Subject: compile fix --- Makefile | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/Makefile b/Makefile index e70ac892..3b75ac53 100644 --- a/Makefile +++ b/Makefile @@ -35,11 +35,7 @@ MANPAGES=$(foreach p, $(PROGS) $(SH_PROGS), $(p).8) CFLAGS ?= -O3 -funroll-loops CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign -I include/ \ -DAFL_PATH=\"$(HELPER_PATH)\" -DBIN_PATH=\"$(BIN_PATH)\" \ - -DVERSION=\"$(VERSION)\" -Wno-unused-function - -CXXFLAGS ?= -O3 -funroll-loops -CXXFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -I ../include/ \ - -DVERSION=\"$(VERSION)\" -Wno-variadic-macros + -DDOC_PATH=\"$(DOC_PATH)\" -Wno-unused-function AFL_FUZZ_FILES = $(wildcard src/afl-fuzz*.c) -- cgit 1.4.1 From 374f6610270a0434afe4931077e49efd9284e013 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 22 Oct 2019 13:23:00 +0200 Subject: help output adjustment --- src/afl-fuzz.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index 25f606fa..877df0d3 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -72,8 +72,8 @@ static void usage(u8* argv0) { "terminate\n" " -E execs - fuzz for a maximum number of total executions then " "terminate\n" - "Note: -V/-E are not precise, they are checked after a queue entry is " - "done which\n can be many minutes/execs later\n\n" + " Note: -V/-E are not precise, they are checked after a queue entry " + "is done\n which can be many minutes/execs later\n\n" "Other stuff:\n" " -T text - text banner to show on the screen\n" -- cgit 1.4.1 From 3ec1baee65553d83e03cd42d08a6151775b25665 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Tue, 22 Oct 2019 20:21:04 +0200 Subject: gcc_plugin adaptions Makefile help, man page SYNOPSIS --- Makefile | 2 +- gcc_plugin/Makefile | 6 +++--- gcc_plugin/afl-gcc-fast.c | 2 ++ 3 files changed, 6 insertions(+), 4 deletions(-) diff --git a/Makefile b/Makefile index 3b75ac53..c4269d6b 100644 --- a/Makefile +++ b/Makefile @@ -116,7 +116,7 @@ help: @echo "==========================================" @echo "all: just the main afl++ binaries" @echo "binary-only: everything for binary-only fuzzing: qemu_mode, unicorn_mode, libdislocator, libtokencap" - @echo "source-only: everything for source code fuzzing: llvm_mode, libdislocator, libtokencap" + @echo "source-only: everything for source code fuzzing: llvm_mode, gcc_plugin, libdislocator, libtokencap" @echo "distrib: everything (for both binary-only and source code fuzzing)" @echo "man: creates simple man pages from the help option of the programs" @echo "install: installs everything you have compiled with the build option above" diff --git a/gcc_plugin/Makefile b/gcc_plugin/Makefile index a603df78..287b6545 100644 --- a/gcc_plugin/Makefile +++ b/gcc_plugin/Makefile @@ -27,7 +27,7 @@ CFLAGS ?= -O3 -g -funroll-loops CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -Wno-pointer-sign \ -DAFL_PATH=\"$(HELPER_PATH)\" -DBIN_PATH=\"$(BIN_PATH)\" \ -CXXFLAGS ?= -O3 -g -funroll-loops +CXXFLAGS ?= -O3 -g -funroll-loops CXXEFLAGS := $(CXXFLAGS) -Wall -D_FORTIFY_SOURCE=2 CC ?= gcc @@ -35,8 +35,6 @@ CXX ?= g++ PLUGIN_FLAGS = -fPIC -fno-rtti -I"$(shell $(CC) -print-file-name=plugin)/include" -PROGS = ../afl-gcc-fast ../afl-gcc-pass.so ../afl-gcc-rt.o - ifeq "$(shell echo '\#include @\#include @int main() { int _id = shmget(IPC_PRIVATE, 65536, IPC_CREAT | IPC_EXCL | 0600); shmctl(_id, IPC_RMID, 0); return 0;}' | tr @ '\n' | $(CC) -x c - -o .test2 2>/dev/null && echo 1 || echo 0 )" "1" SHMAT_OK=1 else @@ -51,6 +49,8 @@ ifeq "$(TEST_MMAP)" "1" LDFLAGS += -lrt endif +PROGS = ../afl-gcc-fast ../afl-gcc-pass.so ../afl-gcc-rt.o + all: test_shm test_deps $(PROGS) afl-gcc-fast.8 test_build all_done diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c index b0461584..093249a0 100644 --- a/gcc_plugin/afl-gcc-fast.c +++ b/gcc_plugin/afl-gcc-fast.c @@ -282,6 +282,8 @@ int main(int argc, char** argv) { "afl-gcc-fast" VERSION cRST " initially by , maintainer: hexcoder-\n" "\n" + "afl-gcc-fast [options]\n" + "\n" "This is a helper application for afl-fuzz. It serves as a drop-in " "replacement\n" "for gcc, letting you recompile third-party code with the required " -- cgit 1.4.1 From 6bc874088fff699d170c89dd864c23507150fe3f Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 23 Oct 2019 02:58:16 +0200 Subject: readme update --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 4b9537d2..d58b49e2 100644 --- a/README.md +++ b/README.md @@ -55,7 +55,7 @@ | Feature/Instrumentation | AFL-GCC | LLVM_MODE | GCC_PLUGIN | QEMU_MODE | Unicorn | | ----------------------- |:-------:|:---------:|:----------:|:---------:|:-------:| | laf-intel / CompCov | | x | | x | x | - | NeverZero | X | x(1) | | x | x | + | NeverZero | X | x(1) | X | x | x | | Persistent mode | | x | X | x | | | Whitelist | | x | X | | | | InsTrim | | x | | | | -- cgit 1.4.1 From 1398d8d5a64b11a62e8ed25732e2114a5dc47564 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 23 Oct 2019 03:23:14 +0200 Subject: gcc sucks --- README.md | 4 +++- gcc_plugin/afl-gcc-rt.o.c | 9 +++++---- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index d58b49e2..de012e62 100644 --- a/README.md +++ b/README.md @@ -55,12 +55,14 @@ | Feature/Instrumentation | AFL-GCC | LLVM_MODE | GCC_PLUGIN | QEMU_MODE | Unicorn | | ----------------------- |:-------:|:---------:|:----------:|:---------:|:-------:| | laf-intel / CompCov | | x | | x | x | - | NeverZero | X | x(1) | X | x | x | + | NeverZero | X | x(1) | (2) | x | x | | Persistent mode | | x | X | x | | | Whitelist | | x | X | | | | InsTrim | | x | | | | + neverZero: (1) only in LLVM >= 9.0 due to a bug in llvm in previous versions + (2) gcc create non-performant code, hence it is disabled in gcc_plugin So all in all this is the best-of AFL that is currently out there :-) diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index 1dfca9e3..47049167 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -58,10 +58,11 @@ __thread u32 __afl_prev_loc; void __afl_trace(u32 x) { u32 l = __afl_prev_loc; - const u32 n = l ^ x; - u8 *const bitmap_ptr = __afl_area_ptr + n; - *bitmap_ptr += 1 + (*bitmap_ptr == (u8)~0); /* neverZero */ - + __afl_area_ptr[l ^ x]++; + /* // neverZero is disable as gcc creates non-performant code. shame on you gcc + if (__afl_area_ptr[l ^ x] == 0) + __afl_area_ptr[l ^ x]++; + */ __afl_prev_loc = (x >> 1); return; -- cgit 1.4.1 From 7d9eed0ed5a57f16b15fe2576da4aec79e0909c9 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Wed, 23 Oct 2019 11:33:20 +0200 Subject: no functional change, avoid conditional jump --- gcc_plugin/afl-gcc-rt.o.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/gcc_plugin/afl-gcc-rt.o.c b/gcc_plugin/afl-gcc-rt.o.c index 47049167..5b70a247 100644 --- a/gcc_plugin/afl-gcc-rt.o.c +++ b/gcc_plugin/afl-gcc-rt.o.c @@ -58,11 +58,14 @@ __thread u32 __afl_prev_loc; void __afl_trace(u32 x) { u32 l = __afl_prev_loc; - __afl_area_ptr[l ^ x]++; - /* // neverZero is disable as gcc creates non-performant code. shame on you gcc - if (__afl_area_ptr[l ^ x] == 0) - __afl_area_ptr[l ^ x]++; - */ + +#if 0 /* enable for neverZero feature. By default disabled since too inefficient :-( */ + /* @Marc: avoid conditional jumps here */ + __afl_area_ptr[l ^ x] += 1 + (__afl_area_ptr[l ^ x] == (u8)~0); +#else + ++__afl_area_ptr[l ^ x]; +#endif + __afl_prev_loc = (x >> 1); return; -- cgit 1.4.1 From b9bc81544a438868529fbe040f4734256dce7a1d Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Wed, 23 Oct 2019 14:53:05 +0200 Subject: debugged and fixed libdislocator malfunction on MacOSX --- libdislocator/libdislocator.so.c | 4 ++-- test/test.sh | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index f3f02c8b..7f44071a 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -88,7 +88,7 @@ static u8 alloc_verbose, /* Additional debug messages */ hard_fail, /* abort() when max_mem exceeded? */ no_calloc_over; /* abort() on calloc() overflows? */ -#ifdef __OpenBSD__ +#if defined __OpenBSD__ || defined __APPLE__ #define __thread #warning no thread support available #endif @@ -121,7 +121,7 @@ static void* __dislocator_alloc(size_t len) { ret = mmap(NULL, (1 + PG_COUNT(len + 8)) * PAGE_SIZE, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); - if (ret == (void*)-1) { + if (ret == MAP_FAILED) { if (hard_fail) FATAL("mmap() failed on alloc (OOM?)"); diff --git a/test/test.sh b/test/test.sh index d1be014f..598fb502 100755 --- a/test/test.sh +++ b/test/test.sh @@ -281,8 +281,8 @@ test -e ../libtokencap.so && { test -e ../libdislocator.so && { { ulimit -c 1 - # DYLD_INSERT_LIBRARIES is used on Darwin/MacOSX - LD_PRELOAD=../libdislocator.so DYLD_INSERT_LIBRARIES=../libdislocator.so ./test-compcov BUFFEROVERFLOW > test.out 2> /dev/null + # DYLD_INSERT_LIBRARIES and DYLD_FORCE_FLAT_NAMESPACE is used on Darwin/MacOSX + LD_PRELOAD=../libdislocator.so DYLD_INSERT_LIBRARIES=../libdislocator.so DYLD_FORCE_FLAT_NAMESPACE=1 ./test-compcov BUFFEROVERFLOW > test.out 2> /dev/null } > /dev/null 2>&1 grep -q BUFFEROVERFLOW test.out > /dev/null 2>&1 && { $ECHO "$RED[!] libdislocator did not detect the memory corruption" -- cgit 1.4.1 From 39b7f488705a7e242b7a54695ca8e03fb2e73d81 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 23 Oct 2019 17:01:05 +0200 Subject: performance doc enhancements --- docs/perf_tips.txt | 8 ++++++++ test/test-performance.sh | 7 ++++++- test/test.sh | 1 + 3 files changed, 15 insertions(+), 1 deletion(-) diff --git a/docs/perf_tips.txt b/docs/perf_tips.txt index 215895b6..2fa19234 100644 --- a/docs/perf_tips.txt +++ b/docs/perf_tips.txt @@ -50,6 +50,9 @@ Even if you don't have a lightweight harness for a particular target, remember that you can always use another, related library to generate a corpus that will be then manually fed to a more resource-hungry program later on. +Also note that reading the fuzzing input via stdin is faster than reading from +a file. + 3) Use LLVM instrumentation --------------------------- @@ -161,6 +164,11 @@ and not waste CPU time. There are several OS-level factors that may affect fuzzing speed: + - If you have no risk of power loss then run your fuzzing on a tmpfs + partition. This increases the performance noticably. + Alternatively you can use AFL_TMPDIR to point to a tmpfs location to + just write the input file to a tmpfs. + - High system load. Use idle machines where possible. Kill any non-essential CPU hogs (idle browser windows, media players, complex screensavers, etc). diff --git a/test/test-performance.sh b/test/test-performance.sh index 198b58c4..87eea665 100755 --- a/test/test-performance.sh +++ b/test/test-performance.sh @@ -1,6 +1,10 @@ #!/bin/bash -FILE=~/.afl_performance +# if you want a specific performance file (e.g. to compare features to another) +# you can set the AFL_PERFORMANCE_FILE environment variable: +FILE=$AFL_PERFORMANCE_FILE +# otherwise we use ~/.afl_performance +test -z "$FILE" && FILE=~/.afl_performance test -e $FILE || { echo Warning: This script measure the performance of afl++ and saves the result for future comparisons into $FILE @@ -17,6 +21,7 @@ unset AFL_USE_ASAN unset AFL_USE_MSAN unset AFL_CC unset AFL_PRELOAD +unset AFL_GCC_WHITELIST unset AFL_LLVM_WHITELIST unset AFL_LLVM_INSTRIM unset AFL_LLVM_LAF_SPLIT_SWITCHES diff --git a/test/test.sh b/test/test.sh index 598fb502..da0590ef 100755 --- a/test/test.sh +++ b/test/test.sh @@ -33,6 +33,7 @@ unset AFL_USE_ASAN unset AFL_USE_MSAN unset AFL_CC unset AFL_PRELOAD +unset AFL_GCC_WHITELIST unset AFL_LLVM_WHITELIST unset AFL_LLVM_INSTRIM unset AFL_LLVM_LAF_SPLIT_SWITCHES -- cgit 1.4.1 From 297e9e3cf59540f16b8260a01ef7c6cd01d9e554 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Wed, 23 Oct 2019 19:48:18 +0200 Subject: move is_valid_addr in afl-qemu-common.h --- qemu_mode/patches/afl-qemu-common.h | 18 ++++++++++++++++++ qemu_mode/patches/afl-qemu-cpu-inl.h | 18 ------------------ 2 files changed, 18 insertions(+), 18 deletions(-) diff --git a/qemu_mode/patches/afl-qemu-common.h b/qemu_mode/patches/afl-qemu-common.h index 1da3359d..409a7eab 100644 --- a/qemu_mode/patches/afl-qemu-common.h +++ b/qemu_mode/patches/afl-qemu-common.h @@ -81,3 +81,21 @@ void tcg_gen_afl_compcov_log_call(void *func, target_ulong cur_loc, void tcg_gen_afl_maybe_log_call(target_ulong cur_loc); + +/* Check if an address is valid in the current mapping */ + +static inline int is_valid_addr(target_ulong addr) { + + int l, flags; + target_ulong page; + void * p; + + page = addr & TARGET_PAGE_MASK; + l = (page + TARGET_PAGE_SIZE) - addr; + + flags = page_get_flags(page); + if (!(flags & PAGE_VALID) || !(flags & PAGE_READ)) return 0; + + return 1; + +} diff --git a/qemu_mode/patches/afl-qemu-cpu-inl.h b/qemu_mode/patches/afl-qemu-cpu-inl.h index 7358fc3b..f4c474d8 100644 --- a/qemu_mode/patches/afl-qemu-cpu-inl.h +++ b/qemu_mode/patches/afl-qemu-cpu-inl.h @@ -451,24 +451,6 @@ static void afl_request_tsl(target_ulong pc, target_ulong cb, uint32_t flags, } -/* Check if an address is valid in the current mapping */ - -static inline int is_valid_addr(target_ulong addr) { - - int l, flags; - target_ulong page; - void * p; - - page = addr & TARGET_PAGE_MASK; - l = (page + TARGET_PAGE_SIZE) - addr; - - flags = page_get_flags(page); - if (!(flags & PAGE_VALID) || !(flags & PAGE_READ)) return 0; - - return 1; - -} - /* This is the other side of the same channel. Since timeouts are handled by afl-fuzz simply killing the child, we can just wait until the pipe breaks. */ -- cgit 1.4.1 From 814242225725f338e35f9af372ee55daba5b4f38 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Wed, 23 Oct 2019 20:07:16 +0100 Subject: Porting libtokencap to Darwin. Reading only main addresses and read only's. --- libtokencap/Makefile | 3 +++ libtokencap/libtokencap.so.c | 37 +++++++++++++++++++++++++++++++++++-- 2 files changed, 38 insertions(+), 2 deletions(-) diff --git a/libtokencap/Makefile b/libtokencap/Makefile index 91933140..702ce696 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -24,6 +24,9 @@ CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign ifeq "$(shell uname)" "Linux" TARGETS = libtokencap.so endif +ifeq "$(shell uname)" "Darwin" + TARGETS = libtokencap.so +endif all: $(TARGETS) libtokencap.so: libtokencap.so.c ../config.h diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 39095beb..212fa31d 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -26,10 +26,15 @@ #include "../types.h" #include "../config.h" -#ifndef __linux__ -#error "Sorry, this library is Linux-specific for now!" +#if !defined(__linux__) && !defined(__APPLE__) +#error "Sorry, this library is unsupported in this platform for now!" #endif /* !__linux__ */ +#if defined(__APPLE__) +#include +#include +#endif + /* Mapping data and such */ #define MAX_MAPPINGS 1024 @@ -46,6 +51,7 @@ static FILE* __tokencap_out_file; static void __tokencap_load_mappings(void) { +#if defined(__linux__) u8 buf[MAX_LINE]; FILE* f = fopen("/proc/self/maps", "r"); @@ -69,7 +75,34 @@ static void __tokencap_load_mappings(void) { } fclose(f); +#elif defined(__APPLE__) + struct vm_region_submap_info_64 region; + mach_msg_type_number_t cnt = VM_REGION_SUBMAP_INFO_COUNT_64; + vm_address_t base = 0; + vm_size_t size = 0; + natural_t depth = 0; + + __tokencap_ro_loaded = 1; + + while (1) { + + if (vm_region_recurse_64(mach_task_self(), &base, &size, &depth, + (vm_region_info_64_t)®ion, &cnt) != KERN_SUCCESS) break; + + if (region.is_submap) { + depth++; + } else { + /* We only care of main map addresses and the read only kinds */ + if ((region.protection & VM_PROT_READ) && !(region.protection & VM_PROT_WRITE)) { + __tokencap_ro[__tokencap_ro_cnt].st = (void *)base; + __tokencap_ro[__tokencap_ro_cnt].en = (void *)(base + size); + + if (++__tokencap_ro_cnt == MAX_MAPPINGS) break; + } + } + } +#endif } /* Check an address against the list of read-only mappings. */ -- cgit 1.4.1 From cb7ada2e78333c3d53928adf0575cf04be8bb907 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Thu, 24 Oct 2019 22:32:37 +0200 Subject: fix libtokencap test for Darwin --- test/test.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index da0590ef..e4a5eb63 100755 --- a/test/test.sh +++ b/test/test.sh @@ -273,7 +273,7 @@ test -e ../afl-gcc-fast && { $ECHO "$BLUE[*] Testing: shared library extensions" gcc -o test-compcov test-compcov.c > /dev/null 2>&1 test -e ../libtokencap.so && { - AFL_TOKEN_FILE=token.out LD_PRELOAD=../libtokencap.so ./test-compcov foobar > /dev/null 2>&1 + AFL_TOKEN_FILE=token.out LD_PRELOAD=../libtokencap.so DYLD_INSERT_LIBRARIES=../libtokencap.so DYLD_FORCE_FLAT_NAMESPACE=1 ./test-compcov foobar > /dev/null 2>&1 grep -q BUGMENOT token.out > /dev/null 2>&1 && { $ECHO "$GREEN[+] libtokencap did successfully capture tokens" } || $ECHO "$RED[!] libtokencap did not capture tokens" -- cgit 1.4.1 From b4b26d420771ca19a26828d9fdd53cdd66dab9ee Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 24 Oct 2019 18:48:08 +0100 Subject: FreeBSD implementation --- libtokencap/Makefile | 3 +++ libtokencap/libtokencap.so.c | 50 +++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 52 insertions(+), 1 deletion(-) diff --git a/libtokencap/Makefile b/libtokencap/Makefile index 702ce696..07c13144 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -27,6 +27,9 @@ endif ifeq "$(shell uname)" "Darwin" TARGETS = libtokencap.so endif +ifeq "$(shell uname)" "FreeBSD" + TARGETS = libtokencap.so +endif all: $(TARGETS) libtokencap.so: libtokencap.so.c ../config.h diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 212fa31d..1050378c 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -22,17 +22,23 @@ #include #include #include +#include #include "../types.h" #include "../config.h" -#if !defined(__linux__) && !defined(__APPLE__) +#if !defined(__linux__) && !defined(__APPLE__) && !defined(__FreeBSD__) #error "Sorry, this library is unsupported in this platform for now!" #endif /* !__linux__ */ #if defined(__APPLE__) #include #include +#elif defined(__FreeBSD__) +#include +#include +#include +#include #endif /* Mapping data and such */ @@ -102,6 +108,48 @@ static void __tokencap_load_mappings(void) { } } +#elif defined(__FreeBSD__) + int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, getpid()}; + char *buf, *low, *high; + size_t miblen = sizeof(mib)/sizeof(mib[0]); + size_t len; + + if (sysctl(mib, miblen, NULL, &len, NULL, 0) == -1) return; + + len = len * 4 / 3; + buf = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED | MAP_ANON, -1, 0); + + if (sysctl(mib, miblen, buf, &len, NULL, 0) == -1) { + + munmap(buf, len); + return; + + } + + low = buf; + high = low + len; + + __tokencap_ro_loaded = 1; + + while (low < high) { + struct kinfo_vmentry *region = (struct kinfo_vmentry *)low; + size_t size = region->kve_structsize; + + if (size == 0) break; + + /* We go through the whole mapping of the process and track read-only addresses */ + if ((region->kve_protection & KVME_PROT_READ) && + !(region->kve_protection & KVME_PROT_WRITE)) { + __tokencap_ro[__tokencap_ro_cnt].st = (void *)region->kve_start; + __tokencap_ro[__tokencap_ro_cnt].en = (void *)region->kve_end; + + if (++__tokencap_ro_cnt == MAX_MAPPINGS) break; + } + + low += size; + } + + munmap(buf, len); #endif } -- cgit 1.4.1 From b0036759fa991f5c940e40ad4b313fbe3504f6f8 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 25 Oct 2019 01:22:20 +0200 Subject: portability fix: use cc instead of gcc for test-compcov --- test/test.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index e4a5eb63..42ddf70b 100755 --- a/test/test.sh +++ b/test/test.sh @@ -271,7 +271,7 @@ test -e ../afl-gcc-fast && { } || $ECHO "$YELLOW[-] gcc_plugin not compiled, cannot test" $ECHO "$BLUE[*] Testing: shared library extensions" -gcc -o test-compcov test-compcov.c > /dev/null 2>&1 +cc -o test-compcov test-compcov.c > /dev/null 2>&1 test -e ../libtokencap.so && { AFL_TOKEN_FILE=token.out LD_PRELOAD=../libtokencap.so DYLD_INSERT_LIBRARIES=../libtokencap.so DYLD_FORCE_FLAT_NAMESPACE=1 ./test-compcov foobar > /dev/null 2>&1 grep -q BUGMENOT token.out > /dev/null 2>&1 && { -- cgit 1.4.1 From e0ff20dd372579f4e4a540df00c8d6f4e218672b Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 25 Oct 2019 01:51:53 +0200 Subject: cosmetics --- libtokencap/libtokencap.so.c | 34 +++++++++++++++++++--------------- 1 file changed, 19 insertions(+), 15 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 1050378c..ddeae8b8 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -27,18 +27,18 @@ #include "../types.h" #include "../config.h" -#if !defined(__linux__) && !defined(__APPLE__) && !defined(__FreeBSD__) -#error "Sorry, this library is unsupported in this platform for now!" -#endif /* !__linux__ */ - -#if defined(__APPLE__) -#include -#include -#elif defined(__FreeBSD__) -#include -#include -#include -#include +#if !defined __linux__ && !defined __APPLE__ && !defined __FreeBSD__ +# error "Sorry, this library is unsupported in this platform for now!" +#endif /* !__linux__ && !__APPLE__ && ! __FreeBSD__ */ + +#if defined __APPLE__ +# include +# include +#elif defined __FreeBSD__ +# include +# include +# include +# include #endif /* Mapping data and such */ @@ -57,7 +57,8 @@ static FILE* __tokencap_out_file; static void __tokencap_load_mappings(void) { -#if defined(__linux__) +#if defined __linux__ + u8 buf[MAX_LINE]; FILE* f = fopen("/proc/self/maps", "r"); @@ -81,7 +82,9 @@ static void __tokencap_load_mappings(void) { } fclose(f); -#elif defined(__APPLE__) + +#elif defined __APPLE__ + struct vm_region_submap_info_64 region; mach_msg_type_number_t cnt = VM_REGION_SUBMAP_INFO_COUNT_64; vm_address_t base = 0; @@ -108,7 +111,8 @@ static void __tokencap_load_mappings(void) { } } -#elif defined(__FreeBSD__) +#elif defined __FreeBSD__ + int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, getpid()}; char *buf, *low, *high; size_t miblen = sizeof(mib)/sizeof(mib[0]); -- cgit 1.4.1 From b8abf27b86e74a4ab6889322ef232a00f1f018c4 Mon Sep 17 00:00:00 2001 From: hexcoder Date: Fri, 25 Oct 2019 09:36:17 +0200 Subject: Update README.md remove Linux-only :-), list supported OSes --- libtokencap/README.md | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/libtokencap/README.md b/libtokencap/README.md index baf69da1..8aae38bf 100644 --- a/libtokencap/README.md +++ b/libtokencap/README.md @@ -2,7 +2,7 @@ (See ../docs/README for the general instruction manual.) -This Linux-only companion library allows you to instrument `strcmp()`, `memcmp()`, +This companion library allows you to instrument `strcmp()`, `memcmp()`, and related functions to automatically extract syntax tokens passed to any of these libcalls. The resulting list of tokens may be then given as a starting dictionary to afl-fuzz (the -x option) to improve coverage on subsequent @@ -55,9 +55,10 @@ If you don't get any results, the target library is probably not using strcmp() and memcmp() to parse input; or you haven't compiled it with -fno-builtin; or the whole thing isn't dynamically linked, and LD_PRELOAD is having no effect. -PS. The library is Linux-only because there is probably no particularly portable -and non-invasive way to distinguish between read-only and read-write memory -mappings. The `__tokencap_load_mappings()` function is the only thing that would -need to be changed for other OSes. Porting to platforms with /proc//maps -(e.g., FreeBSD) should be trivial. +Portability hints: There is probably no particularly portable and non-invasive +way to distinguish between read-only and read-write memory mappings. +The `__tokencap_load_mappings()` function is the only thing that would +need to be changed for other OSes. + +Current supported OSes are: Linux, Darwin, FreeBSD (thanks to @devnexen) -- cgit 1.4.1 From 7e9b6fe0aa820c8bce258eaa24d230ce96347d38 Mon Sep 17 00:00:00 2001 From: hexcoder Date: Fri, 25 Oct 2019 10:44:34 +0200 Subject: Update sister_projects.txt status updates for python mutators and whitelist selective instrumentation feature. --- docs/sister_projects.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/docs/sister_projects.txt b/docs/sister_projects.txt index a2eb2a22..25e5560c 100644 --- a/docs/sister_projects.txt +++ b/docs/sister_projects.txt @@ -319,11 +319,13 @@ Fuzzer shell for SQLite (Richard Hipp) Support for Python mutation modules (Christian Holler) ------------------------------------------------------ +now integrated in AFL++, originally from here https://github.com/choller/afl/blob/master/docs/mozilla/python_modules.txt Support for selective instrumentation (Christian Holler) -------------------------------------------------------- +now integrated in AFL++, originally from here https://github.com/choller/afl/blob/master/docs/mozilla/partial_instrumentation.txt Kernel fuzzing (Dmitry Vyukov) -- cgit 1.4.1 From 644efa290582e76a9fb1dc42a7cfc782d628d3fe Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Fri, 25 Oct 2019 14:02:30 +0200 Subject: remove redundand setenv of SHM_ENV_VAR --- src/afl-sharedmem.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/afl-sharedmem.c b/src/afl-sharedmem.c index d94100a3..e11221a4 100644 --- a/src/afl-sharedmem.c +++ b/src/afl-sharedmem.c @@ -153,8 +153,6 @@ void setup_shm(unsigned char dumb_mode) { shm_str = alloc_printf("%d", shm_id); - setenv(SHM_ENV_VAR, shm_str, 1); - /* If somebody is asking us to fuzz instrumented binaries in dumb mode, we don't want them to detect instrumentation, since we won't be sending fork server commands. This should be replaced with better auto-detection -- cgit 1.4.1 From 15c920a6126e3a0b5ac5a7293188c3d7a523bbde Mon Sep 17 00:00:00 2001 From: David Carlier Date: Fri, 25 Oct 2019 14:25:37 +0100 Subject: Little compiler plugins rework regarding block location picked up. --- gcc_plugin/afl-gcc-pass.so.cc | 2 +- include/types.h | 12 ++++++++++++ llvm_mode/afl-llvm-pass.so.cc | 9 +++++++++ 3 files changed, 22 insertions(+), 1 deletion(-) diff --git a/gcc_plugin/afl-gcc-pass.so.cc b/gcc_plugin/afl-gcc-pass.so.cc index 633dedcb..84e02cb8 100644 --- a/gcc_plugin/afl-gcc-pass.so.cc +++ b/gcc_plugin/afl-gcc-pass.so.cc @@ -490,7 +490,7 @@ int plugin_init(struct plugin_name_args * plugin_info, /* Setup random() so we get Actually Random(TM) outputs from R() */ gettimeofday(&tv, &tz); rand_seed = tv.tv_sec ^ tv.tv_usec ^ getpid(); - srandom(rand_seed); + SR(rand_seed); /* Pass information */ afl_pass_info.pass = make_afl_pass(inst_ext, g); diff --git a/include/types.h b/include/types.h index c34bf522..3f34db66 100644 --- a/include/types.h +++ b/include/types.h @@ -79,9 +79,21 @@ typedef int64_t s64; }) #ifdef AFL_LLVM_PASS +#if defined(__linux__) +#define AFL_SR(s) (srandom(s)) #define AFL_R(x) (random() % (x)) #else +#define AFL_SR(s) +#define AFL_R(x) (arc4random_uniform(x)) +#endif +#else +#if defined(__linux__) +#define SR(s) (srandom(s)) #define R(x) (random() % (x)) +#else +#define SR(s) +#define R(x) (arc4random_uniform(x)) +#endif #endif /* ^AFL_LLVM_PASS */ #define STRINGIFY_INTERNAL(x) #x diff --git a/llvm_mode/afl-llvm-pass.so.cc b/llvm_mode/afl-llvm-pass.so.cc index 475a3f33..e094a0b2 100644 --- a/llvm_mode/afl-llvm-pass.so.cc +++ b/llvm_mode/afl-llvm-pass.so.cc @@ -34,6 +34,7 @@ #include #include #include +#include #include "llvm/IR/DebugInfo.h" #include "llvm/IR/BasicBlock.h" @@ -95,8 +96,16 @@ bool AFLCoverage::runOnModule(Module &M) { IntegerType *Int8Ty = IntegerType::getInt8Ty(C); IntegerType *Int32Ty = IntegerType::getInt32Ty(C); + struct timeval tv; + struct timezone tz; + u32 rand_seed; unsigned int cur_loc = 0; + /* Setup random() so we get Actually Random(TM) outputs from AFL_R() */ + gettimeofday(&tv, &tz); + rand_seed = tv.tv_sec ^ tv.tv_usec ^ getpid(); + AFL_SR(rand_seed); + /* Show a banner */ char be_quiet = 0; -- cgit 1.4.1 From 4ec4e5b394dfa4e40a26574e3053a9bd7eaa8d37 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Fri, 25 Oct 2019 20:04:16 +0200 Subject: floating point compcov --- qemu_mode/build_qemu_support.sh | 3 + qemu_mode/patches/afl-qemu-common.h | 12 ++ qemu_mode/patches/afl-qemu-floats.h | 217 +++++++++++++++++++++++++++++++++ qemu_mode/patches/i386-fpu_helper.diff | 54 ++++++++ qemu_mode/patches/i386-ops_sse.diff | 61 +++++++++ qemu_mode/patches/softfloat.diff | 10 ++ 6 files changed, 357 insertions(+) create mode 100644 qemu_mode/patches/afl-qemu-floats.h create mode 100644 qemu_mode/patches/i386-fpu_helper.diff create mode 100644 qemu_mode/patches/i386-ops_sse.diff create mode 100644 qemu_mode/patches/softfloat.diff diff --git a/qemu_mode/build_qemu_support.sh b/qemu_mode/build_qemu_support.sh index f18cbdf3..6b9f91f9 100755 --- a/qemu_mode/build_qemu_support.sh +++ b/qemu_mode/build_qemu_support.sh @@ -150,6 +150,9 @@ patch -p1 <../patches/translate-all.diff || exit 1 patch -p1 <../patches/tcg.diff || exit 1 patch -p1 <../patches/i386-translate.diff || exit 1 patch -p1 <../patches/arm-translate.diff || exit 1 +patch -p1 <../patches/i386-ops_sse.diff || exit 1 +patch -p1 <../patches/i386-fpu_helper.diff || exit 1 +patch -p1 <../patches/softfloat.diff || exit 1 echo "[+] Patching done." diff --git a/qemu_mode/patches/afl-qemu-common.h b/qemu_mode/patches/afl-qemu-common.h index 409a7eab..d4024353 100644 --- a/qemu_mode/patches/afl-qemu-common.h +++ b/qemu_mode/patches/afl-qemu-common.h @@ -31,6 +31,9 @@ */ +#ifndef __AFL_QEMU_COMMON +#define __AFL_QEMU_COMMON + #include "../../config.h" #ifndef CPU_NB_REGS @@ -81,6 +84,12 @@ void tcg_gen_afl_compcov_log_call(void *func, target_ulong cur_loc, void tcg_gen_afl_maybe_log_call(target_ulong cur_loc); +void afl_float_compcov_log_32(target_ulong cur_loc, float32 arg1, float32 arg2, + void *status); +void afl_float_compcov_log_64(target_ulong cur_loc, float64 arg1, float64 arg2, + void *status); +void afl_float_compcov_log_80(target_ulong cur_loc, floatx80 arg1, + floatx80 arg2); /* Check if an address is valid in the current mapping */ @@ -99,3 +108,6 @@ static inline int is_valid_addr(target_ulong addr) { return 1; } + +#endif + diff --git a/qemu_mode/patches/afl-qemu-floats.h b/qemu_mode/patches/afl-qemu-floats.h new file mode 100644 index 00000000..765deb74 --- /dev/null +++ b/qemu_mode/patches/afl-qemu-floats.h @@ -0,0 +1,217 @@ +/* + american fuzzy lop++ - high-performance binary-only instrumentation + ------------------------------------------------------------------- + + Originally written by Andrew Griffiths and + Michal Zalewski + + TCG instrumentation and block chaining support by Andrea Biondo + + + QEMU 3.1.1 port, TCG thread-safety, CompareCoverage and NeverZero + counters by Andrea Fioraldi + + Copyright 2015, 2016, 2017 Google Inc. All rights reserved. + Copyright 2019 AFLplusplus Project. All rights reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at: + + http://www.apache.org/licenses/LICENSE-2.0 + + This code is a shim patched into the separately-distributed source + code of QEMU 3.1.0. It leverages the built-in QEMU tracing functionality + to implement AFL-style instrumentation and to take care of the remaining + parts of the AFL fork server logic. + + The resulting QEMU binary is essentially a standalone instrumentation + tool; for an example of how to leverage it for other purposes, you can + have a look at afl-showmap.c. + + */ + +#include "tcg.h" +#include "afl-qemu-common.h" + +union afl_float32 { + float64 f; + struct { + u64 sign : 1; + u64 exp : 7; + u64 frac : 24; + }; +}; + + +union afl_float64 { + float64 f; + struct { + u64 sign : 1; + u64 exp : 11; + u64 frac : 52; + }; +}; + + +// TODO 16 and 128 bits floats +// TODO figure out why float*_unpack_canonical does not work + +void afl_float_compcov_log_32(target_ulong cur_loc, float32 arg1, float32 arg2, + void* status) { + + cur_loc = (cur_loc >> 4) ^ (cur_loc << 8); + cur_loc &= MAP_SIZE - 7; + + if (cur_loc >= afl_inst_rms) return; + + //float_status* s = (float_status*)status; + //FloatParts a = float32_unpack_canonical(arg1, s); + //FloatParts b = float32_unpack_canonical(arg2, s); + union afl_float32 a = { .f = arg1 }; + union afl_float32 b = { .f = arg2 }; + + // if (is_nan(a.cls) || is_nan(b.cls)) return; + + register uintptr_t idx = cur_loc; + + if (a.sign != b.sign) return; + INC_AFL_AREA(idx); + if (a.exp != b.exp) return; + INC_AFL_AREA(idx + 1); + + if ((a.frac & 0xff0000) == (b.frac & 0xff0000)) { + + INC_AFL_AREA(idx + 2); + if ((a.frac & 0xff00) == (b.frac & 0xff00)) { INC_AFL_AREA(idx + 3); } + + } + +} + +void afl_float_compcov_log_64(target_ulong cur_loc, float64 arg1, float64 arg2, + void* status) { + + cur_loc = (cur_loc >> 4) ^ (cur_loc << 8); + cur_loc &= MAP_SIZE - 7; + + if (cur_loc >= afl_inst_rms) return; + + //float_status* s = (float_status*)status; + //FloatParts a = float64_unpack_canonical(arg1, s); + //FloatParts b = float64_unpack_canonical(arg2, s); + union afl_float64 a = { .f = arg1 }; + union afl_float64 b = { .f = arg2 }; + + // if (is_nan(a.cls) || is_nan(b.cls)) return; + + register uintptr_t idx = cur_loc; + + if (a.sign == b.sign) INC_AFL_AREA(idx); + if ((a.exp & 0xff00) == (b.exp & 0xff00)) { + + INC_AFL_AREA(idx + 1); + if ((a.exp & 0xff) == (b.exp & 0xff)) INC_AFL_AREA(idx + 2); + + } + + if ((a.frac & 0xff000000000000) == (b.frac & 0xff000000000000)) { + + INC_AFL_AREA(idx + 3); + if ((a.frac & 0xff0000000000) == (b.frac & 0xff0000000000)) { + + INC_AFL_AREA(idx + 4); + if ((a.frac & 0xff00000000) == (b.frac & 0xff00000000)) { + + INC_AFL_AREA(idx + 5); + if ((a.frac & 0xff000000) == (b.frac & 0xff000000)) { + + INC_AFL_AREA(idx + 6); + if ((a.frac & 0xff0000) == (b.frac & 0xff0000)) { + + INC_AFL_AREA(idx + 7); + if ((a.frac & 0xff00) == (b.frac & 0xff00)) INC_AFL_AREA(idx + 8); + + } + + } + + } + + } + + } + +} + +void afl_float_compcov_log_80(target_ulong cur_loc, floatx80 arg1, + floatx80 arg2) { + + cur_loc = (cur_loc >> 4) ^ (cur_loc << 8); + cur_loc &= MAP_SIZE - 7; + + if (cur_loc >= afl_inst_rms) return; + + if (floatx80_invalid_encoding(arg1) || floatx80_invalid_encoding(arg2)) + return; + + flag a_sign = extractFloatx80Sign(arg1); + flag b_sign = extractFloatx80Sign(arg2); + + /*if (((extractFloatx80Exp(arg1) == 0x7fff) && + (extractFloatx80Frac(arg1) << 1)) || + ((extractFloatx80Exp(arg2) == 0x7fff) && + (extractFloatx80Frac(arg2) << 1))) + return;*/ + + register uintptr_t idx = cur_loc; + + if (a_sign == b_sign) INC_AFL_AREA(idx); + + if ((arg1.high & 0x7f00) == (arg2.high & 0x7f00)) { + + INC_AFL_AREA(idx + 1); + if ((arg1.high & 0xff) == (arg2.high & 0xff)) INC_AFL_AREA(idx + 2); + + } + + if ((arg1.low & 0xff00000000000000) == (arg2.low & 0xff00000000000000)) { + + INC_AFL_AREA(idx + 3); + if ((arg1.low & 0xff000000000000) == (arg2.low & 0xff000000000000)) { + + INC_AFL_AREA(idx + 4); + if ((arg1.low & 0xff0000000000) == (arg2.low & 0xff0000000000)) { + + INC_AFL_AREA(idx + 5); + if ((arg1.low & 0xff00000000) == (arg2.low & 0xff00000000)) { + + INC_AFL_AREA(idx + 6); + if ((arg1.low & 0xff000000) == (arg2.low & 0xff000000)) { + + INC_AFL_AREA(idx + 7); + if ((arg1.low & 0xff0000) == (arg2.low & 0xff0000)) { + + INC_AFL_AREA(idx + 8); + if ((arg1.low & 0xff00) == (arg2.low & 0xff00)) { + + INC_AFL_AREA(idx + 9); + //if ((arg1.low & 0xff) == (arg2.low & 0xff)) + // INC_AFL_AREA(idx + 10); + + } + + } + + } + + } + + } + + } + + } + +} + diff --git a/qemu_mode/patches/i386-fpu_helper.diff b/qemu_mode/patches/i386-fpu_helper.diff new file mode 100644 index 00000000..3bd09d9c --- /dev/null +++ b/qemu_mode/patches/i386-fpu_helper.diff @@ -0,0 +1,54 @@ +diff --git a/target/i386/fpu_helper.c b/target/i386/fpu_helper.c +index ea5a0c48..89901315 100644 +--- a/target/i386/fpu_helper.c ++++ b/target/i386/fpu_helper.c +@@ -384,10 +384,16 @@ void helper_fxchg_ST0_STN(CPUX86State *env, int st_index) + + static const int fcom_ccval[4] = {0x0100, 0x4000, 0x0000, 0x4500}; + ++#include "../patches/afl-qemu-common.h" ++ + void helper_fcom_ST0_FT0(CPUX86State *env) + { + int ret; + ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_80(env->eip, ST0, FT0); ++ + ret = floatx80_compare(ST0, FT0, &env->fp_status); + env->fpus = (env->fpus & ~0x4500) | fcom_ccval[ret + 1]; + } +@@ -396,6 +402,10 @@ void helper_fucom_ST0_FT0(CPUX86State *env) + { + int ret; + ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_80(env->eip, ST0, FT0); ++ + ret = floatx80_compare_quiet(ST0, FT0, &env->fp_status); + env->fpus = (env->fpus & ~0x4500) | fcom_ccval[ret + 1]; + } +@@ -407,6 +417,10 @@ void helper_fcomi_ST0_FT0(CPUX86State *env) + int eflags; + int ret; + ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_80(env->eip, ST0, FT0); ++ + ret = floatx80_compare(ST0, FT0, &env->fp_status); + eflags = cpu_cc_compute_all(env, CC_OP); + eflags = (eflags & ~(CC_Z | CC_P | CC_C)) | fcomi_ccval[ret + 1]; +@@ -418,6 +432,10 @@ void helper_fucomi_ST0_FT0(CPUX86State *env) + int eflags; + int ret; + ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_80(env->eip, ST0, FT0); ++ + ret = floatx80_compare_quiet(ST0, FT0, &env->fp_status); + eflags = cpu_cc_compute_all(env, CC_OP); + eflags = (eflags & ~(CC_Z | CC_P | CC_C)) | fcomi_ccval[ret + 1]; diff --git a/qemu_mode/patches/i386-ops_sse.diff b/qemu_mode/patches/i386-ops_sse.diff new file mode 100644 index 00000000..d2779ea8 --- /dev/null +++ b/qemu_mode/patches/i386-ops_sse.diff @@ -0,0 +1,61 @@ +diff --git a/target/i386/ops_sse.h b/target/i386/ops_sse.h +index ed059897..a5296caa 100644 +--- a/target/i386/ops_sse.h ++++ b/target/i386/ops_sse.h +@@ -997,6 +997,8 @@ SSE_HELPER_CMP(cmpord, FPU_CMPORD) + + static const int comis_eflags[4] = {CC_C, CC_Z, 0, CC_Z | CC_P | CC_C}; + ++#include "../patches/afl-qemu-common.h" ++ + void helper_ucomiss(CPUX86State *env, Reg *d, Reg *s) + { + int ret; +@@ -1004,6 +1006,11 @@ void helper_ucomiss(CPUX86State *env, Reg *d, Reg *s) + + s0 = d->ZMM_S(0); + s1 = s->ZMM_S(0); ++ ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_32(env->eip, s0, s1, &env->sse_status); ++ + ret = float32_compare_quiet(s0, s1, &env->sse_status); + CC_SRC = comis_eflags[ret + 1]; + } +@@ -1015,6 +1022,11 @@ void helper_comiss(CPUX86State *env, Reg *d, Reg *s) + + s0 = d->ZMM_S(0); + s1 = s->ZMM_S(0); ++ ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_32(env->eip, s0, s1, &env->sse_status); ++ + ret = float32_compare(s0, s1, &env->sse_status); + CC_SRC = comis_eflags[ret + 1]; + } +@@ -1026,6 +1038,11 @@ void helper_ucomisd(CPUX86State *env, Reg *d, Reg *s) + + d0 = d->ZMM_D(0); + d1 = s->ZMM_D(0); ++ ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_64(env->eip, d0, d1, &env->sse_status); ++ + ret = float64_compare_quiet(d0, d1, &env->sse_status); + CC_SRC = comis_eflags[ret + 1]; + } +@@ -1037,6 +1054,11 @@ void helper_comisd(CPUX86State *env, Reg *d, Reg *s) + + d0 = d->ZMM_D(0); + d1 = s->ZMM_D(0); ++ ++ if (afl_compcov_level > 2 && env->eip < afl_end_code && ++ env->eip >= afl_start_code) ++ afl_float_compcov_log_64(env->eip, d0, d1, &env->sse_status); ++ + ret = float64_compare(d0, d1, &env->sse_status); + CC_SRC = comis_eflags[ret + 1]; + } diff --git a/qemu_mode/patches/softfloat.diff b/qemu_mode/patches/softfloat.diff new file mode 100644 index 00000000..86ffb97f --- /dev/null +++ b/qemu_mode/patches/softfloat.diff @@ -0,0 +1,10 @@ +diff --git a/fpu/softfloat.c b/fpu/softfloat.c +index e1eef954..2f8d0d62 100644 +--- a/fpu/softfloat.c ++++ b/fpu/softfloat.c +@@ -7205,3 +7205,5 @@ float128 float128_scalbn(float128 a, int n, float_status *status) + , status); + + } ++ ++#include "../../patches/afl-qemu-floats.h" -- cgit 1.4.1 From 94548d228444f5f4486bea9253c39900ea27a505 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Fri, 25 Oct 2019 20:12:24 +0200 Subject: float compcov readme --- qemu_mode/README.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/qemu_mode/README.md b/qemu_mode/README.md index a85407e4..c88c1e41 100644 --- a/qemu_mode/README.md +++ b/qemu_mode/README.md @@ -100,7 +100,11 @@ afl-fuzz). AFL_COMPCOV_LEVEL=1 is to instrument comparisons with only immediate values / read-only memory. AFL_COMPCOV_LEVEL=2 instruments all comparison instructions and memory comparison functions when libcompcov -is preloaded. Comparison instructions are currently instrumented only +is preloaded. +AFL_COMPCOV_LEVEL=3 has the same effects of AFL_COMPCOV_LEVEL=2 but enables also +the instrumentation of the floating-point comparisons on x86 and x86_64 (experimental). + +Integer comparison instructions are currently instrumented only on the x86, x86_64 and ARM targets. Highly recommended. -- cgit 1.4.1 From 3e9e7e17504517d8db92e47e7a5f904b023ba91e Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sat, 26 Oct 2019 00:17:51 +0200 Subject: libtokencap ported to OpenBSD --- libtokencap/Makefile | 3 +++ libtokencap/libtokencap.so.c | 30 +++++++++++++++++++++++++++--- 2 files changed, 30 insertions(+), 3 deletions(-) diff --git a/libtokencap/Makefile b/libtokencap/Makefile index 07c13144..441412c7 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -30,6 +30,9 @@ endif ifeq "$(shell uname)" "FreeBSD" TARGETS = libtokencap.so endif +ifeq "$(shell uname)" "OpenBSD" + TARGETS = libtokencap.so +endif all: $(TARGETS) libtokencap.so: libtokencap.so.c ../config.h diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index ddeae8b8..d33de8a4 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -27,14 +27,14 @@ #include "../types.h" #include "../config.h" -#if !defined __linux__ && !defined __APPLE__ && !defined __FreeBSD__ +#if !defined __linux__ && !defined __APPLE__ && !defined __FreeBSD__ && !defined __OpenBSD__ # error "Sorry, this library is unsupported in this platform for now!" #endif /* !__linux__ && !__APPLE__ && ! __FreeBSD__ */ #if defined __APPLE__ # include # include -#elif defined __FreeBSD__ +#elif defined __FreeBSD__ || defined __OpenBSD__ # include # include # include @@ -111,17 +111,29 @@ static void __tokencap_load_mappings(void) { } } -#elif defined __FreeBSD__ +#elif defined __FreeBSD__ || defined __OpenBSD__ +#if defined __FreeBSD__ int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, getpid()}; +#elif defined __OpenBSD__ + int mib[] = {CTL_KERN, KERN_PROC_VMMAP, getpid()}; +#endif char *buf, *low, *high; size_t miblen = sizeof(mib)/sizeof(mib[0]); size_t len; if (sysctl(mib, miblen, NULL, &len, NULL, 0) == -1) return; +#if defined __FreeBSD__ len = len * 4 / 3; +#elif defined __OpenBSD__ + len -= len % sizeof(struct kinfo_vmentry); +#endif + buf = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED | MAP_ANON, -1, 0); + if (!buf) { + return; + } if (sysctl(mib, miblen, buf, &len, NULL, 0) == -1) { @@ -137,6 +149,9 @@ static void __tokencap_load_mappings(void) { while (low < high) { struct kinfo_vmentry *region = (struct kinfo_vmentry *)low; + +#if defined __FreeBSD__ + size_t size = region->kve_structsize; if (size == 0) break; @@ -144,6 +159,15 @@ static void __tokencap_load_mappings(void) { /* We go through the whole mapping of the process and track read-only addresses */ if ((region->kve_protection & KVME_PROT_READ) && !(region->kve_protection & KVME_PROT_WRITE)) { + +#elif defined __OpenBSD__ + + size_t size = sizeof (*region); + + /* We go through the whole mapping of the process and track read-only addresses */ + if ((region->kve_protection & KVE_PROT_READ) && + !(region->kve_protection & KVE_PROT_WRITE)) { +#endif __tokencap_ro[__tokencap_ro_cnt].st = (void *)region->kve_start; __tokencap_ro[__tokencap_ro_cnt].en = (void *)region->kve_end; -- cgit 1.4.1 From a2f911dbb1ac177f4e633f4e667bbf4f8c578895 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sat, 26 Oct 2019 01:14:39 +0200 Subject: typo --- qemu_mode/patches/afl-qemu-floats.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/qemu_mode/patches/afl-qemu-floats.h b/qemu_mode/patches/afl-qemu-floats.h index 765deb74..0b2ac2ae 100644 --- a/qemu_mode/patches/afl-qemu-floats.h +++ b/qemu_mode/patches/afl-qemu-floats.h @@ -35,7 +35,7 @@ #include "afl-qemu-common.h" union afl_float32 { - float64 f; + float32 f; struct { u64 sign : 1; u64 exp : 7; -- cgit 1.4.1 From c66633ccc54f98829e7035b981ad4916f14d1e70 Mon Sep 17 00:00:00 2001 From: Dominik Maier Date: Sun, 20 Oct 2019 04:45:50 +0200 Subject: no longer warns on python as path for unicorn --- src/afl-fuzz.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index 877df0d3..14d7802d 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -554,7 +554,7 @@ int main(int argc, char** argv) { if (getenv("AFL_NO_UI") && getenv("AFL_FORCE_UI")) FATAL("AFL_NO_UI and AFL_FORCE_UI are mutually exclusive"); - if (strchr(argv[optind], '/') == NULL) + if (strchr(argv[optind], '/') == NULL && !unicorn_mode) WARNF(cLRD "Target binary called without a prefixed path, make sure you are " "fuzzing the right binary: " cRST "%s", -- cgit 1.4.1 From 3eaf5560beaf5b3cb79f9a58bc986027935b7a3b Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sat, 26 Oct 2019 09:03:46 +0200 Subject: AFL_LLVM_LAF_SPLIT_FLOATS --- llvm_mode/README.laf-intel.md | 3 ++- llvm_mode/split-compares-pass.so.cc | 14 ++++++++++---- 2 files changed, 12 insertions(+), 5 deletions(-) diff --git a/llvm_mode/README.laf-intel.md b/llvm_mode/README.laf-intel.md index c787744b..462c7bac 100644 --- a/llvm_mode/README.laf-intel.md +++ b/llvm_mode/README.laf-intel.md @@ -35,4 +35,5 @@ bit_width may be 64, 32 or 16. A new experimental feature is splitting floating point comparisons into a series of sign, exponent and mantissa comparisons followed by splitting each of them into 8 bit comparisons when necessary. -It is activated with the `AFL_LLVM_LAF_SPLIT_COMPARES` setting. +It is activated with the `AFL_LLVM_LAF_SPLIT_FLOATS` setting, available only +when `AFL_LLVM_LAF_SPLIT_COMPARES` is set. diff --git a/llvm_mode/split-compares-pass.so.cc b/llvm_mode/split-compares-pass.so.cc index f1a0f94e..4248b238 100644 --- a/llvm_mode/split-compares-pass.so.cc +++ b/llvm_mode/split-compares-pass.so.cc @@ -50,6 +50,8 @@ class SplitComparesTransform : public ModulePass { } private: + int enableFPSplit; + size_t splitIntCompares(Module &M, unsigned bitw); size_t splitFPCompares(Module &M); bool simplifyCompares(Module &M); @@ -101,10 +103,11 @@ bool SplitComparesTransform::simplifyCompares(Module &M) { } - if (selectcmpInst->getPredicate() == CmpInst::FCMP_OGE || + if (enableFPSplit && ( + selectcmpInst->getPredicate() == CmpInst::FCMP_OGE || selectcmpInst->getPredicate() == CmpInst::FCMP_UGE || selectcmpInst->getPredicate() == CmpInst::FCMP_OLE || - selectcmpInst->getPredicate() == CmpInst::FCMP_ULE) { + selectcmpInst->getPredicate() == CmpInst::FCMP_ULE)) { auto op0 = selectcmpInst->getOperand(0); auto op1 = selectcmpInst->getOperand(1); @@ -1039,6 +1042,8 @@ bool SplitComparesTransform::runOnModule(Module &M) { char *bitw_env = getenv("LAF_SPLIT_COMPARES_BITW"); if (!bitw_env) bitw_env = getenv("AFL_LLVM_LAF_SPLIT_COMPARES_BITW"); if (bitw_env) { bitw = atoi(bitw_env); } + + enableFPSplit = getenv("AFL_LLVM_LAF_SPLIT_FLOATS") != NULL; simplifyCompares(M); @@ -1048,8 +1053,9 @@ bool SplitComparesTransform::runOnModule(Module &M) { errs() << "Split-compare-pass by laf.intel@gmail.com, extended by " "heiko@hexco.de\n"; - errs() << "Split-floatingpoint-compare-pass: " << splitFPCompares(M) - << " FP comparisons splitted\n"; + if (enableFPSplit) + errs() << "Split-floatingpoint-compare-pass: " << splitFPCompares(M) + << " FP comparisons splitted\n"; switch (bitw) { -- cgit 1.4.1 From f2b3f01759b7b5b4d74967ee39a6752c668e698e Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Sat, 26 Oct 2019 09:24:09 +0200 Subject: make initial inputs names consistent with others using time:0 --- src/afl-fuzz-init.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index a77904b5..e3c2e259 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -729,7 +729,7 @@ void pivot_inputs(void) { use_name += 6; else use_name = rsl; - nfn = alloc_printf("%s/queue/id:%06u,orig:%s", out_dir, id, use_name); + nfn = alloc_printf("%s/queue/id:%06u,time:0,orig:%s", out_dir, id, use_name); #else -- cgit 1.4.1 From cfd7b906cbc961892646aee9f307f6ffd4eb2253 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Sat, 26 Oct 2019 08:39:13 +0100 Subject: Porting cpu affinity to DragonFly. Thanks their API is very similar in this area. --- include/afl-fuzz.h | 9 ++++++--- src/afl-fuzz-init.c | 19 ++++++++++++------- src/afl-gotcpu.c | 10 ++++++---- 3 files changed, 24 insertions(+), 14 deletions(-) diff --git a/include/afl-fuzz.h b/include/afl-fuzz.h index 1e6140dd..637c2795 100644 --- a/include/afl-fuzz.h +++ b/include/afl-fuzz.h @@ -72,18 +72,21 @@ #include #if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) || \ - defined(__NetBSD__) + defined(__NetBSD__) || defined(__DragonFly__) #include #endif /* __APPLE__ || __FreeBSD__ || __OpenBSD__ */ /* For systems that have sched_setaffinity; right now just Linux, but one can hope... */ -#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) || \ + defined(__DragonFly__) #define HAVE_AFFINITY 1 -#if defined(__FreeBSD__) +#if defined(__FreeBSD__) || defined(__DragonFly__) #include +#if defined(__FreeBSD__) #include +#endif #include #include #include diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index a77904b5..f9525c82 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -32,7 +32,7 @@ void bind_to_free_cpu(void) { -#if defined(__linux__) || defined(__FreeBSD__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__DragonFly__) cpu_set_t c; #elif defined(__NetBSD__) cpuset_t* c; @@ -117,7 +117,7 @@ void bind_to_free_cpu(void) { } closedir(d); -#elif defined(__FreeBSD__) +#elif defined(__FreeBSD__) || defined(__DragonFly__) struct kinfo_proc* procs; size_t nprocs; size_t proccount; @@ -138,8 +138,13 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { +#if defined(__FreeBSD__) if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 2) cpu_used[procs[i].ki_oncpu] = 1; +#elif defined(__DragonFly__) + if (procs[i].kp_lwp.kl_cpuid < sizeof(cpu_used) && procs[i].kp_lwp.kl_pctcpu > 2) + cpu_used[procs[i].kp_lwp.kl_cpuid] = 1; +#endif } @@ -200,7 +205,7 @@ void bind_to_free_cpu(void) { cpu_aff = i; -#if defined(__linux__) || defined(__FreeBSD__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__DragonFly__) CPU_ZERO(&c); CPU_SET(i, &c); #elif defined(__NetBSD__) @@ -212,7 +217,7 @@ void bind_to_free_cpu(void) { #if defined(__linux__) if (sched_setaffinity(0, sizeof(c), &c)) PFATAL("sched_setaffinity failed"); -#elif defined(__FreeBSD__) +#elif defined(__FreeBSD__) || defined(__DragonFly__) if (pthread_setaffinity_np(pthread_self(), sizeof(c), &c)) PFATAL("pthread_setaffinity failed"); #elif defined(__NetBSD__) @@ -871,7 +876,7 @@ double get_runnable_processes(void) { static double res; #if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) || \ - defined(__NetBSD__) + defined(__NetBSD__) || defined(__DragonFly__) /* I don't see any portable sysctl or so that would quickly give us the number of runnable processes; the 1-minute load average can be a @@ -1605,7 +1610,7 @@ void check_cpu_governor(void) { void get_core_count(void) { -#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) +#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__) size_t s = sizeof(cpu_core_count); @@ -1651,7 +1656,7 @@ void get_core_count(void) { cur_runnable = (u32)get_runnable_processes(); -#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) +#if defined(__APPLE__) || defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__DragonFly__) /* Add ourselves, since the 1-minute average doesn't include that yet. */ diff --git a/src/afl-gotcpu.c b/src/afl-gotcpu.c index 850943dd..fe5d035f 100644 --- a/src/afl-gotcpu.c +++ b/src/afl-gotcpu.c @@ -52,12 +52,14 @@ #include "types.h" #include "debug.h" -#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__APPLE__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__APPLE__) || defined(__DragonFly__) #define HAVE_AFFINITY 1 -#if defined(__FreeBSD__) +#if defined(__FreeBSD__) || defined(__DragonFly__) #include #include +#if defined(__FreeBSD__) #include +#endif #define cpu_set_t cpuset_t #elif defined(__NetBSD__) #include @@ -168,7 +170,7 @@ int main(int argc, char** argv) { if (!fr) { u32 util_perc; -#if defined(__linux__) || defined(__FreeBSD__) +#if defined(__linux__) || defined(__FreeBSD__) || defined(__DragonFly__) cpu_set_t c; CPU_ZERO(&c); @@ -188,7 +190,7 @@ int main(int argc, char** argv) { PFATAL("thread_policy_set failed"); #endif -#if defined(__FreeBSD__) +#if defined(__FreeBSD__) || defined(__DragonFly__) if (pthread_setaffinity_np(pthread_self(), sizeof(c), &c)) PFATAL("pthread_setaffinity_np failed"); #endif -- cgit 1.4.1 From 74df3e24913a882d22a39a3ea32ec7288921f0e0 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sun, 27 Oct 2019 07:27:48 +0100 Subject: WIP for NetBSD port, iteration has an unknown problem causing a seg fault --- libtokencap/libtokencap.so.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index d33de8a4..7ed231fe 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -27,14 +27,14 @@ #include "../types.h" #include "../config.h" -#if !defined __linux__ && !defined __APPLE__ && !defined __FreeBSD__ && !defined __OpenBSD__ +#if !defined __linux__ && !defined __APPLE__ && !defined __FreeBSD__ && !defined __OpenBSD__ && !defined __NetBSD__ # error "Sorry, this library is unsupported in this platform for now!" -#endif /* !__linux__ && !__APPLE__ && ! __FreeBSD__ */ +#endif /* !__linux__ && !__APPLE__ && ! __FreeBSD__ && ! __OpenBSD__ && !__NetBSD__*/ #if defined __APPLE__ # include # include -#elif defined __FreeBSD__ || defined __OpenBSD__ +#elif defined __FreeBSD__ || defined __OpenBSD__ || defined __NetBSD__ # include # include # include @@ -111,12 +111,14 @@ static void __tokencap_load_mappings(void) { } } -#elif defined __FreeBSD__ || defined __OpenBSD__ +#elif defined __FreeBSD__ || defined __OpenBSD__ || defined __NetBSD__ #if defined __FreeBSD__ int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, getpid()}; #elif defined __OpenBSD__ int mib[] = {CTL_KERN, KERN_PROC_VMMAP, getpid()}; +#elif defined __NetBSD__ + int mib[] = {CTL_VM, VM_PROC, VM_PROC_MAP, getpid(), sizeof(struct kinfo_vmentry)}; #endif char *buf, *low, *high; size_t miblen = sizeof(mib)/sizeof(mib[0]); @@ -124,7 +126,7 @@ static void __tokencap_load_mappings(void) { if (sysctl(mib, miblen, NULL, &len, NULL, 0) == -1) return; -#if defined __FreeBSD__ +#if defined __FreeBSD__ || defined __NetBSD__ len = len * 4 / 3; #elif defined __OpenBSD__ len -= len % sizeof(struct kinfo_vmentry); @@ -150,11 +152,15 @@ static void __tokencap_load_mappings(void) { while (low < high) { struct kinfo_vmentry *region = (struct kinfo_vmentry *)low; -#if defined __FreeBSD__ +#if defined __FreeBSD__ || defined __NetBSD__ +#if defined __FreeBSD__ size_t size = region->kve_structsize; if (size == 0) break; +#elif defined __NetBSD__ + size_t size = sizeof (*region); +#endif /* We go through the whole mapping of the process and track read-only addresses */ if ((region->kve_protection & KVME_PROT_READ) && -- cgit 1.4.1 From 4de38fe40a4e0dac34c178c4ef6f4cb213fb3ee3 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Sun, 27 Oct 2019 09:04:40 +0100 Subject: docs update --- README.md | 6 +++--- docs/perf_tips.txt | 9 ++++++--- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index de012e62..88a86aaa 100644 --- a/README.md +++ b/README.md @@ -55,9 +55,9 @@ | Feature/Instrumentation | AFL-GCC | LLVM_MODE | GCC_PLUGIN | QEMU_MODE | Unicorn | | ----------------------- |:-------:|:---------:|:----------:|:---------:|:-------:| | laf-intel / CompCov | | x | | x | x | - | NeverZero | X | x(1) | (2) | x | x | - | Persistent mode | | x | X | x | | - | Whitelist | | x | X | | | + | NeverZero | x | x(1) | (2) | x | x | + | Persistent mode | | x | x | x | | + | Whitelist | | x | x | | | | InsTrim | | x | | | | neverZero: diff --git a/docs/perf_tips.txt b/docs/perf_tips.txt index 2fa19234..0cac8f7b 100644 --- a/docs/perf_tips.txt +++ b/docs/perf_tips.txt @@ -56,9 +56,9 @@ a file. 3) Use LLVM instrumentation --------------------------- -When fuzzing slow targets, you can gain 2x performance improvement by using -the LLVM-based instrumentation mode described in llvm_mode/README.llvm. Note -that this mode requires the use of clang and will not work with GCC. +When fuzzing slow targets, you can gain 20-100% performance improvement by +using the LLVM-based instrumentation mode described in llvm_mode/README.llvm. +Note that this mode requires the use of clang and will not work with GCC. The LLVM mode also offers a "persistent", in-process fuzzing mode that can work well for certain types of self-contained libraries, and for fast targets, @@ -75,6 +75,9 @@ If you are only intested in specific parts of the code being fuzzed, you can whitelist the files that are actually relevant. This improves the speed and accuracy of afl. See llvm_mode/README.whitelist +Also use the InsTrim mode on larger binaries, this improves performance and +coverage a lot. + 4) Profile and optimize the binary ---------------------------------- -- cgit 1.4.1 From 10af76a50c1ff8ffe66c4358ad08bab87d23f98e Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sun, 27 Oct 2019 08:12:01 +0100 Subject: added a TODO item for posix_memalign wrapper --- libdislocator/libdislocator.so.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 7f44071a..d172f7a2 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -188,6 +188,10 @@ void* calloc(size_t elem_len, size_t elem_cnt) { } +/* TODO: add a wrapper for posix_memalign, otherwise apps who use it, + will fail when freeing the memory. +*/ + /* The wrapper for malloc(). Roughly the same, also clobbers the returned memory (unlike calloc(), malloc() is not guaranteed to return zeroed memory). */ -- cgit 1.4.1 From f8e0e9ab1f2460c7faeca7d2e0cef5700a05859a Mon Sep 17 00:00:00 2001 From: van Hauser Date: Sun, 27 Oct 2019 11:35:40 +0100 Subject: updated todos --- TODO | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/TODO b/TODO index 05c89679..b1a96569 100644 --- a/TODO +++ b/TODO @@ -3,14 +3,14 @@ Roadmap 2.60: ============= afl-fuzz: - - change -T to use alarm() instead - - radamsa mutator - - test the libmutator actually works and does not run infinite (need an example though) + - radamsa mutator (via dlopen()) gcc_plugin: - - neverZero - laf-intel +libdislocator: + - add a wrapper for posix_memalign + qemu_mode: - update to 4.x (probably this will be skipped :( ) - instrim for QEMU mode via static analysis (with r2pipe? or angr?) -- cgit 1.4.1 From 3ad5316dd1d7a4512b5acc17381a634a82901406 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Sun, 27 Oct 2019 23:54:44 +0100 Subject: fix issue #86, we exclude floating point vectors from splitting --- llvm_mode/split-compares-pass.so.cc | 2 ++ 1 file changed, 2 insertions(+) diff --git a/llvm_mode/split-compares-pass.so.cc b/llvm_mode/split-compares-pass.so.cc index 4248b238..06bdeb60 100644 --- a/llvm_mode/split-compares-pass.so.cc +++ b/llvm_mode/split-compares-pass.so.cc @@ -479,6 +479,8 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) { if (TyOp0 != TyOp1) { continue; } + if (TyOp0->isArrayTy() || TyOp0->isVectorTy()) { continue; } + fcomps.push_back(selectcmpInst); } -- cgit 1.4.1 From 64fa11d204c13ad32f9fe0dbb9abbfedc00ebb3d Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 28 Oct 2019 11:52:31 +0100 Subject: updated changelog, afl-analyze AFL_SKIP_BIN_CHECK support --- docs/ChangeLog | 13 +++++++++++++ src/afl-analyze.c | 2 +- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/docs/ChangeLog b/docs/ChangeLog index c2d46e4d..4c51502b 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -13,6 +13,19 @@ Want to stay in the loop on major new features? Join our mailing list by sending a mail to . +---------------------- +Version ++2.58d (dev): +---------------------- + + - afl-analyze: added AFL_SKIP_BIN_CHECK support + - better random numbers for gcc_plugin and llvm_mode (thanks to devnexen) + - afl-fuzz: CPU affinity support for DragonFly + - llvm_mode: float splitting is now configured via AFL_LLVM_LAF_SPLIT_FLOATS + - libtokencap: support for *BSD/OSX added + - libcompcov floating point splitting support for qemu and unicorn + - removed unnecessary warnings + + -------------------------- Version ++2.58c (release): -------------------------- diff --git a/src/afl-analyze.c b/src/afl-analyze.c index 5555a262..ee281af8 100644 --- a/src/afl-analyze.c +++ b/src/afl-analyze.c @@ -987,7 +987,7 @@ int main(int argc, char** argv) { if (child_timed_out) FATAL("Target binary times out (adjusting -t may help)."); - if (!anything_set()) FATAL("No instrumentation detected."); + if (getenv("AFL_SKIP_BIN_CHECK") == NULL && !anything_set()) FATAL("No instrumentation detected."); analyze(use_argv); -- cgit 1.4.1 From 942f8d0ec9bed45c9038112aef7cd9b8a05f6f30 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Mon, 28 Oct 2019 11:01:37 +0000 Subject: Fix proposal for libtokencap Avoiding fopen API seems buggy on NetBSD. --- libtokencap/Makefile | 3 +++ libtokencap/libtokencap.so.c | 18 +++++++++++++----- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/libtokencap/Makefile b/libtokencap/Makefile index 441412c7..df2426ed 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -33,6 +33,9 @@ endif ifeq "$(shell uname)" "OpenBSD" TARGETS = libtokencap.so endif +ifeq "$(shell uname)" "NetBSD" + TARGETS = libtokencap.so +endif all: $(TARGETS) libtokencap.so: libtokencap.so.c ../config.h diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 7ed231fe..e1977127 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -23,6 +23,7 @@ #include #include #include +#include #include "../types.h" #include "../config.h" @@ -49,7 +50,7 @@ static struct mapping { void *st, *en; } __tokencap_ro[MAX_MAPPINGS]; static u32 __tokencap_ro_cnt; static u8 __tokencap_ro_loaded; -static FILE* __tokencap_out_file; +static int __tokencap_out_file = -1; /* Identify read-only regions in memory. Only parameters that fall into these ranges are worth dumping when passed to strcmp() and so on. Read-write @@ -211,7 +212,7 @@ static void __tokencap_dump(const u8* ptr, size_t len, u8 is_text) { u32 i; u32 pos = 0; - if (len < MIN_AUTO_EXTRA || len > MAX_AUTO_EXTRA || !__tokencap_out_file) + if (len < MIN_AUTO_EXTRA || len > MAX_AUTO_EXTRA || __tokencap_out_file == -1) return; for (i = 0; i < len; i++) { @@ -237,7 +238,9 @@ static void __tokencap_dump(const u8* ptr, size_t len, u8 is_text) { buf[pos] = 0; - fprintf(__tokencap_out_file, "\"%s\"\n", buf); + write(__tokencap_out_file, "\"", 1); + write(__tokencap_out_file, buf, pos); + write(__tokencap_out_file, "\"\n", 2); } @@ -403,8 +406,13 @@ char* strcasestr(const char* haystack, const char* needle) { __attribute__((constructor)) void __tokencap_init(void) { u8* fn = getenv("AFL_TOKEN_FILE"); - if (fn) __tokencap_out_file = fopen(fn, "a"); - if (!__tokencap_out_file) __tokencap_out_file = stderr; + if (fn) __tokencap_out_file = open(fn, O_RDWR | O_CREAT | O_APPEND, 0655); + if (__tokencap_out_file == -1) __tokencap_out_file = STDERR_FILENO; } +/* closing as best as we can the tokens file */ +__attribute__((destructor)) void __tokencap_shutdown(void) { + if (__tokencap_out_file != STDERR_FILENO) close(__tokencap_out_file); +} + -- cgit 1.4.1 From fbb131da737fdabe4908558bd839c468410ab3fc Mon Sep 17 00:00:00 2001 From: David Carlier Date: Mon, 28 Oct 2019 14:44:28 +0000 Subject: memalign/posix_memalign proposal for libdislocator --- libdislocator/libdislocator.so.c | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index d172f7a2..f1972797 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -264,6 +264,36 @@ void* realloc(void* ptr, size_t len) { } +/* posix_memalign we mainly check the proper alignment argument + if the requested size fits within the alignment we do + a normal request */ + +int posix_memalign(void** ptr, size_t align, size_t len) { + if (!ptr) FATAL("null pointer on posix_memalign()"); + if ((align % 2) || (align % sizeof(void *))) FATAL("bad alignment on posix_memalign()"); + if (align >= 4 * sizeof(size_t)) { + + len += align -1; + + } + + *ptr = malloc(len); + + DEBUGF("posix_memalign(%p %zu, %zu)", ptr, len, align); + + return 0; +} + +/* just the non-posix fashion */ + +void *memalign(size_t align, size_t len) { + void* ret; + + posix_memalign(&ret, align, len); + + return ret; +} + __attribute__((constructor)) void __dislocator_init(void) { u8* tmp = getenv("AFL_LD_LIMIT_MB"); -- cgit 1.4.1 From 80359685167309639562ece25a77782cb6ccfd54 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 28 Oct 2019 16:32:26 +0100 Subject: silence some compiler warnings --- libdislocator/libdislocator.so.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index f1972797..5246af40 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -279,7 +279,7 @@ int posix_memalign(void** ptr, size_t align, size_t len) { *ptr = malloc(len); - DEBUGF("posix_memalign(%p %zu, %zu)", ptr, len, align); + DEBUGF("posix_memalign(%p %zu, %zu)", ptr, align, len); return 0; } @@ -287,9 +287,11 @@ int posix_memalign(void** ptr, size_t align, size_t len) { /* just the non-posix fashion */ void *memalign(size_t align, size_t len) { - void* ret; + void* ret = NULL; - posix_memalign(&ret, align, len); + if (posix_memalign(&ret, align, len)) { + DEBUGF("memalign(%zu, %zu) failed", align, len); + } return ret; } -- cgit 1.4.1 From 25443918c4ab15c4c1f9ba0861f5d48daa29a412 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 28 Oct 2019 16:45:30 +0100 Subject: silence some compiler warnings --- libtokencap/libtokencap.so.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index e1977127..820f5bc4 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -238,9 +238,9 @@ static void __tokencap_dump(const u8* ptr, size_t len, u8 is_text) { buf[pos] = 0; - write(__tokencap_out_file, "\"", 1); - write(__tokencap_out_file, buf, pos); - write(__tokencap_out_file, "\"\n", 2); + int wrt_ok = ( 1 == write(__tokencap_out_file, "\"", 1)); + wrt_ok &= (pos == write(__tokencap_out_file, buf, pos)); + wrt_ok &= (2 == write(__tokencap_out_file, "\"\n", 2)); } -- cgit 1.4.1 From 38d74f0ad56a74cfed1eec04a8a46b4f8e4ec824 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Mon, 28 Oct 2019 20:48:45 +0100 Subject: second forgotten place, we need to filter out float vector types --- llvm_mode/split-compares-pass.so.cc | 2 ++ 1 file changed, 2 insertions(+) diff --git a/llvm_mode/split-compares-pass.so.cc b/llvm_mode/split-compares-pass.so.cc index 06bdeb60..60420f77 100644 --- a/llvm_mode/split-compares-pass.so.cc +++ b/llvm_mode/split-compares-pass.so.cc @@ -118,6 +118,8 @@ bool SplitComparesTransform::simplifyCompares(Module &M) { /* this is probably not needed but we do it anyway */ if (TyOp0 != TyOp1) { continue; } + if (TyOp0->isArrayTy() || TyOp0->isVectorTy()) { continue; } + fcomps.push_back(selectcmpInst); } -- cgit 1.4.1 From 6238df88a26d8498b4a821897f030a866dafdc24 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 28 Oct 2019 22:36:29 +0100 Subject: fixed warning and return --- libdislocator/libdislocator.so.c | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 5246af40..b3a90366 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -269,13 +269,11 @@ void* realloc(void* ptr, size_t len) { a normal request */ int posix_memalign(void** ptr, size_t align, size_t len) { - if (!ptr) FATAL("null pointer on posix_memalign()"); - if ((align % 2) || (align % sizeof(void *))) FATAL("bad alignment on posix_memalign()"); - if (align >= 4 * sizeof(size_t)) { - - len += align -1; - - } + if ((char*)ptr == NULL || *ptr == NULL) + return -1; // why would we do: FATAL("null pointer on posix_memalign()"); + if ((align % 2) || (align % sizeof(void *))) + return -1; // why would we do: FATAL("bad alignment on posix_memalign()"); + if (align >= 4 * sizeof(size_t)) len += align -1; *ptr = malloc(len); -- cgit 1.4.1 From 87b599f4a8b875c0ff8c81aff39ebecfd34e29fc Mon Sep 17 00:00:00 2001 From: David Carlier Date: Tue, 29 Oct 2019 08:09:43 +0000 Subject: adding aligned_alloc + little changes proposal for posix_memalign --- libdislocator/libdislocator.so.c | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index b3a90366..e27efc0f 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -23,6 +23,7 @@ #include #include #include +#include #include #include "config.h" @@ -272,7 +273,11 @@ int posix_memalign(void** ptr, size_t align, size_t len) { if ((char*)ptr == NULL || *ptr == NULL) return -1; // why would we do: FATAL("null pointer on posix_memalign()"); if ((align % 2) || (align % sizeof(void *))) - return -1; // why would we do: FATAL("bad alignment on posix_memalign()"); + return EINVAL; // why would we do: FATAL("bad alignment on posix_memalign()"); + if (len == 0) { + *ptr = NULL; + return 0; + } if (align >= 4 * sizeof(size_t)) len += align -1; *ptr = malloc(len); @@ -294,6 +299,20 @@ void *memalign(size_t align, size_t len) { return ret; } +/* sort of C11 alias of memalign only more severe, alignment-wise */ + +void *aligned_alloc(size_t align, size_t len) { + void *ret = NULL; + + if ((len % align)) return NULL; + + if (posix_memalign(&ret, align, len)) { + DEBUGF("aligned_alloc(%zu, %zu) failed", align, len); + } + + return ret; +} + __attribute__((constructor)) void __dislocator_init(void) { u8* tmp = getenv("AFL_LD_LIMIT_MB"); -- cgit 1.4.1 From ccbb0d37b33a83a0ea1bdb6128cb6c8900802944 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 29 Oct 2019 10:44:57 +0100 Subject: removed warning --- libdislocator/libdislocator.so.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index e27efc0f..7fe40afa 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -270,10 +270,10 @@ void* realloc(void* ptr, size_t len) { a normal request */ int posix_memalign(void** ptr, size_t align, size_t len) { - if ((char*)ptr == NULL || *ptr == NULL) - return -1; // why would we do: FATAL("null pointer on posix_memalign()"); + if (*ptr == NULL) + return EINVAL; if ((align % 2) || (align % sizeof(void *))) - return EINVAL; // why would we do: FATAL("bad alignment on posix_memalign()"); + return EINVAL; if (len == 0) { *ptr = NULL; return 0; -- cgit 1.4.1 From df5c7eef39ac20497d5b372033874c70bb7a47e9 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Tue, 29 Oct 2019 10:49:16 +0000 Subject: libtokencap, respect constness also considering pointer arithmetic is non C standard, some compilers might not have GNU extensions. --- libtokencap/libtokencap.so.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 820f5bc4..7e55963c 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -256,7 +256,7 @@ int strcmp(const char* str1, const char* str2) { while (1) { - unsigned char c1 = *str1, c2 = *str2; + const unsigned char c1 = *str1, c2 = *str2; if (c1 != c2) return (c1 > c2) ? 1 : -1; if (!c1) return 0; @@ -298,7 +298,7 @@ int strcasecmp(const char* str1, const char* str2) { while (1) { - unsigned char c1 = tolower(*str1), c2 = tolower(*str2); + const unsigned char c1 = tolower(*str1), c2 = tolower(*str2); if (c1 != c2) return (c1 > c2) ? 1 : -1; if (!c1) return 0; @@ -318,7 +318,7 @@ int strncasecmp(const char* str1, const char* str2, size_t len) { while (len--) { - unsigned char c1 = tolower(*str1), c2 = tolower(*str2); + const unsigned char c1 = tolower(*str1), c2 = tolower(*str2); if (!c1) return 0; if (c1 != c2) return (c1 > c2) ? 1 : -1; @@ -338,12 +338,15 @@ int memcmp(const void* mem1, const void* mem2, size_t len) { if (__tokencap_is_ro(mem1)) __tokencap_dump(mem1, len, 0); if (__tokencap_is_ro(mem2)) __tokencap_dump(mem2, len, 0); + const char *strmem1 = (const char *)mem1; + const char *strmem2 = (const char *)mem2; + while (len--) { - unsigned char c1 = *(const char*)mem1, c2 = *(const char*)mem2; + const unsigned char c1 = *strmem1, c2 = *strmem2; if (c1 != c2) return (c1 > c2) ? 1 : -1; - mem1++; - mem2++; + strmem1++; + strmem2++; } -- cgit 1.4.1 From c87210820c1566c74bf08ab4345679598cabd71b Mon Sep 17 00:00:00 2001 From: David Carlier Date: Tue, 29 Oct 2019 15:06:20 +0000 Subject: libtokencap update proposal - bcmp interception. - FreeBSD using default argument to get current pid for the mapping data gathering, getpid seems to cause some issues under certain conditions (getenv call). --- libtokencap/libtokencap.so.c | 28 ++++++++++++++++++++++++---- llvm_mode/afl-clang-fast.c | 3 +++ src/afl-gcc.c | 1 + 3 files changed, 28 insertions(+), 4 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 7e55963c..2fe9ae63 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -115,7 +115,7 @@ static void __tokencap_load_mappings(void) { #elif defined __FreeBSD__ || defined __OpenBSD__ || defined __NetBSD__ #if defined __FreeBSD__ - int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, getpid()}; + int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, -1}; #elif defined __OpenBSD__ int mib[] = {CTL_KERN, KERN_PROC_VMMAP, getpid()}; #elif defined __NetBSD__ @@ -134,9 +134,7 @@ static void __tokencap_load_mappings(void) { #endif buf = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED | MAP_ANON, -1, 0); - if (!buf) { - return; - } + if (buf == MAP_FAILED) return; if (sysctl(mib, miblen, buf, &len, NULL, 0) == -1) { @@ -354,6 +352,28 @@ int memcmp(const void* mem1, const void* mem2, size_t len) { } +#undef bcmp + +int bcmp(const void* mem1, const void* mem2, size_t len) { + + if (__tokencap_is_ro(mem1)) __tokencap_dump(mem1, len, 0); + if (__tokencap_is_ro(mem2)) __tokencap_dump(mem2, len, 0); + + const char *strmem1 = (const char *)mem1; + const char *strmem2 = (const char *)mem2; + + while (len--) { + + int diff = *strmem1 ^ *strmem2; + if (diff != 0) return 1; + strmem1++; + strmem2++; + + } + + return 0; +} + #undef strstr char* strstr(const char* haystack, const char* needle) { diff --git a/llvm_mode/afl-clang-fast.c b/llvm_mode/afl-clang-fast.c index a7f6acdc..1acf8856 100644 --- a/llvm_mode/afl-clang-fast.c +++ b/llvm_mode/afl-clang-fast.c @@ -273,6 +273,9 @@ static void edit_params(u32 argc, char** argv) { cc_params[cc_par_cnt++] = "-fno-builtin-strcasecmp"; cc_params[cc_par_cnt++] = "-fno-builtin-strncasecmp"; cc_params[cc_par_cnt++] = "-fno-builtin-memcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-bcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-strstr"; + cc_params[cc_par_cnt++] = "-fno-builtin-strcasestr"; } diff --git a/src/afl-gcc.c b/src/afl-gcc.c index 740442dc..e0706a5f 100644 --- a/src/afl-gcc.c +++ b/src/afl-gcc.c @@ -320,6 +320,7 @@ static void edit_params(u32 argc, char** argv) { cc_params[cc_par_cnt++] = "-fno-builtin-strcasecmp"; cc_params[cc_par_cnt++] = "-fno-builtin-strncasecmp"; cc_params[cc_par_cnt++] = "-fno-builtin-memcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-bcmp"; cc_params[cc_par_cnt++] = "-fno-builtin-strstr"; cc_params[cc_par_cnt++] = "-fno-builtin-strcasestr"; -- cgit 1.4.1 From 67533cf7c35c8e9e6cb8dfdde9c704187b1970da Mon Sep 17 00:00:00 2001 From: David Carlier Date: Tue, 29 Oct 2019 15:35:54 +0000 Subject: copying LLVM mode no builtins. --- gcc_plugin/afl-gcc-fast.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/gcc_plugin/afl-gcc-fast.c b/gcc_plugin/afl-gcc-fast.c index 093249a0..057b44cc 100644 --- a/gcc_plugin/afl-gcc-fast.c +++ b/gcc_plugin/afl-gcc-fast.c @@ -108,7 +108,7 @@ static void edit_params(u32 argc, char** argv) { u8 fortify_set = 0, asan_set = 0, x_set = 0, maybe_linking = 1; u8* name; - cc_params = ck_alloc((argc + 64) * sizeof(u8*)); + cc_params = ck_alloc((argc + 128) * sizeof(u8*)); name = strrchr(argv[0], '/'); if (!name) @@ -202,6 +202,19 @@ static void edit_params(u32 argc, char** argv) { } + if (getenv("AFL_NO_BUILTIN")) { + + cc_params[cc_par_cnt++] = "-fno-builtin-strcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-strncmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-strcasecmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-strncasecmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-memcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-bcmp"; + cc_params[cc_par_cnt++] = "-fno-builtin-strstr"; + cc_params[cc_par_cnt++] = "-fno-builtin-strcasestr"; + + } + #ifdef USEMMAP cc_params[cc_par_cnt++] = "-lrt"; #endif -- cgit 1.4.1 From 16953b5cfa040c886d0edfbf2f4da478c3e6014d Mon Sep 17 00:00:00 2001 From: David Carlier Date: Wed, 30 Oct 2019 17:04:43 +0000 Subject: LLVM mode passing the full path of the LLVM config bindir. On FreeBSD the system compiler does not have llvm-config however system packages provides several version of the LLVM toolchain thus forcing to pass AFL_CC/AFL_CXX to make it work fully. --- llvm_mode/Makefile | 2 +- llvm_mode/afl-clang-fast.c | 8 ++++++-- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/llvm_mode/Makefile b/llvm_mode/Makefile index 7cfbe92d..033babac 100644 --- a/llvm_mode/Makefile +++ b/llvm_mode/Makefile @@ -52,7 +52,7 @@ endif CFLAGS ?= -O3 -funroll-loops CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign -I ../include/ \ -DAFL_PATH=\"$(HELPER_PATH)\" -DBIN_PATH=\"$(BIN_PATH)\" \ - -DVERSION=\"$(VERSION)\" + -DLLVM_BINDIR=\"$(LLVM_BINDIR)\" -DVERSION=\"$(VERSION)\" ifdef AFL_TRACE_PC CFLAGS += -DUSE_TRACE_PC=1 endif diff --git a/llvm_mode/afl-clang-fast.c b/llvm_mode/afl-clang-fast.c index 1acf8856..e92fb76f 100644 --- a/llvm_mode/afl-clang-fast.c +++ b/llvm_mode/afl-clang-fast.c @@ -32,11 +32,13 @@ #include #include #include +#include #include static u8* obj_path; /* Path to runtime libraries */ static u8** cc_params; /* Parameters passed to the real CC */ static u32 cc_par_cnt = 1; /* Param count, including argv0 */ +static u8 llvm_fullpath[PATH_MAX]; /* Try to find the runtime libraries. If that fails, abort. */ @@ -117,12 +119,14 @@ static void edit_params(u32 argc, char** argv) { if (!strcmp(name, "afl-clang-fast++")) { u8* alt_cxx = getenv("AFL_CXX"); - cc_params[0] = alt_cxx ? alt_cxx : (u8*)"clang++"; + snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang++", LLVM_BINDIR); + cc_params[0] = alt_cxx ? alt_cxx : (u8*)llvm_fullpath; } else { u8* alt_cc = getenv("AFL_CC"); - cc_params[0] = alt_cc ? alt_cc : (u8*)"clang"; + snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang", LLVM_BINDIR); + cc_params[0] = alt_cc ? alt_cc : (u8*)llvm_fullpath; } -- cgit 1.4.1 From 4620d31e2aaed11c8aacf0b499301a3154a2d390 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 10:10:15 +0100 Subject: travis --- .travis.yml | 59 ++++++++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 54 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 9ef95bcf..b5684452 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,11 +1,60 @@ language: c env: - - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 + - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_STOP_MANUALLY=1 + - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_EXIT_WHEN_DONE=1 + # TODO: test AFL_BENCH_UNTIL_CRASH once we have a target that crashes + - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_BENCH_JUST_ONE=1 +before_install: + - sudo apt update + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang + +# TODO: Look into splitting off some builds using a build matrix. +# TODO: Move this all into a bash script so we don't need to write bash in yaml. script: - - make - - ./afl-gcc ./test-instr.c -o test-instr - - mkdir seeds; mkdir out + - make distrib + - ./afl-gcc ./test-instr.c -o test-instr-gcc + - mkdir seeds - echo "" > seeds/nil_seed - - timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr + - if [ -z "$AFL_STOP_MANUALLY" ]; + then ./afl-fuzz -i seeds -o out/ -- ./test-instr-gcc; + else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-gcc; + fi + #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 3 + - rm -r out/* + #- ./afl-clang ./test-instr.c -o test-instr-clang + #- if [ -z "$AFL_STOP_MANUALLY" ]; + # then ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang; + # else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang; + # fi + #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 2 + #- CC=clang CXX=clang++ make + #- cd llvm_mode + # TODO: Build with different versions of clang/LLVM since LLVM passes don't + # have a stable API. + #- CC=clang CXX=clang++ LLVM_CONFIG=llvm-config make + #- cd .. + #- rm -r out/* + - ./afl-clang-fast ./test-instr.c -o test-instr-clang-fast + - if [ -z "$AFL_STOP_MANUALLY" ]; + then ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang-fast; + else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang-fast; + fi + #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 3 + # Test fuzzing libFuzzer targets and trace-pc-guard instrumentation. + #- clang -g -fsanitize-coverage=trace-pc-guard ./test-libfuzzer-target.c -c + #- clang -c -w llvm_mode/afl-llvm-rt.o.c + #- wget https://raw.githubusercontent.com/llvm/llvm-project/master/compiler-rt/lib/fuzzer/afl/afl_driver.cpp + #- clang++ afl_driver.cpp afl-llvm-rt.o.o test-libfuzzer-target.o -o test-libfuzzer-target + #- timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-libfuzzer-target + #- cd qemu_mode + #- ./build_qemu_support.sh + #- cd .. + #- gcc ./test-instr.c -o test-no-instr + #- if [ -z "$AFL_STOP_MANUALLY" ]; + # then ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; + # else timeout --preserve-status 5s ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; + # fi + #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 12 -p 9 + - make clean -- cgit 1.4.1 From 070ccae4dd04c5315bf1daba8ee35202b4f30264 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 31 Oct 2019 09:25:43 +0000 Subject: Little tweaks --- llvm_mode/afl-clang-fast.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/llvm_mode/afl-clang-fast.c b/llvm_mode/afl-clang-fast.c index e92fb76f..b2243492 100644 --- a/llvm_mode/afl-clang-fast.c +++ b/llvm_mode/afl-clang-fast.c @@ -38,7 +38,7 @@ static u8* obj_path; /* Path to runtime libraries */ static u8** cc_params; /* Parameters passed to the real CC */ static u32 cc_par_cnt = 1; /* Param count, including argv0 */ -static u8 llvm_fullpath[PATH_MAX]; +static u8 llvm_fullpath[PATH_MAX]; /* Try to find the runtime libraries. If that fails, abort. */ @@ -106,6 +106,7 @@ static void find_obj(u8* argv0) { static void edit_params(u32 argc, char** argv) { u8 fortify_set = 0, asan_set = 0, x_set = 0, maybe_linking = 1, bit_mode = 0; + u8 has_llvm_config = 0; u8* name; cc_params = ck_alloc((argc + 128) * sizeof(u8*)); @@ -116,16 +117,20 @@ static void edit_params(u32 argc, char** argv) { else ++name; + has_llvm_config = (strlen(LLVM_BINDIR) > 0); + if (!strcmp(name, "afl-clang-fast++")) { u8* alt_cxx = getenv("AFL_CXX"); - snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang++", LLVM_BINDIR); + if (has_llvm_config) snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang++", LLVM_BINDIR); + else sprintf(llvm_fullpath, "clang++"); cc_params[0] = alt_cxx ? alt_cxx : (u8*)llvm_fullpath; } else { u8* alt_cc = getenv("AFL_CC"); - snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang", LLVM_BINDIR); + if (has_llvm_config) snprintf(llvm_fullpath, sizeof(llvm_fullpath), "%s/clang", LLVM_BINDIR); + else sprintf(llvm_fullpath, "clang"); cc_params[0] = alt_cc ? alt_cc : (u8*)llvm_fullpath; } -- cgit 1.4.1 From 98b27d0c64c849318b36bc1f70851a53a8179057 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:01:00 +0100 Subject: travis: added make tests --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index b5684452..9f7ed920 100644 --- a/.travis.yml +++ b/.travis.yml @@ -57,4 +57,5 @@ script: # else timeout --preserve-status 5s ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; # fi #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 12 -p 9 + - make tests - make clean -- cgit 1.4.1 From fce7a0c78c3b1b54af288c9f94e65947d536d993 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:17:18 +0100 Subject: update travis --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index 9f7ed920..b6e0f1d7 100644 --- a/.travis.yml +++ b/.travis.yml @@ -57,5 +57,6 @@ script: # else timeout --preserve-status 5s ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; # fi #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 12 -p 9 + - ./afl-system-config - make tests - make clean -- cgit 1.4.1 From 94a7102d3ac1adc1518e652def412fb500382d95 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:21:41 +0100 Subject: travis updates --- .travis.yml | 46 ++-------------------------------------------- 1 file changed, 2 insertions(+), 44 deletions(-) diff --git a/.travis.yml b/.travis.yml index b6e0f1d7..b1f23032 100644 --- a/.travis.yml +++ b/.travis.yml @@ -8,55 +8,13 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-9 gcc-9-plugin-dev # TODO: Look into splitting off some builds using a build matrix. # TODO: Move this all into a bash script so we don't need to write bash in yaml. script: - make distrib - - ./afl-gcc ./test-instr.c -o test-instr-gcc - - mkdir seeds - - echo "" > seeds/nil_seed - - if [ -z "$AFL_STOP_MANUALLY" ]; - then ./afl-fuzz -i seeds -o out/ -- ./test-instr-gcc; - else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-gcc; - fi - #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 3 - - rm -r out/* - #- ./afl-clang ./test-instr.c -o test-instr-clang - #- if [ -z "$AFL_STOP_MANUALLY" ]; - # then ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang; - # else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang; - # fi - #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 2 - #- CC=clang CXX=clang++ make - #- cd llvm_mode - # TODO: Build with different versions of clang/LLVM since LLVM passes don't - # have a stable API. - #- CC=clang CXX=clang++ LLVM_CONFIG=llvm-config make - #- cd .. - #- rm -r out/* - - ./afl-clang-fast ./test-instr.c -o test-instr-clang-fast - - if [ -z "$AFL_STOP_MANUALLY" ]; - then ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang-fast; - else timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-instr-clang-fast; - fi - #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 1 -p 3 - # Test fuzzing libFuzzer targets and trace-pc-guard instrumentation. - #- clang -g -fsanitize-coverage=trace-pc-guard ./test-libfuzzer-target.c -c - #- clang -c -w llvm_mode/afl-llvm-rt.o.c - #- wget https://raw.githubusercontent.com/llvm/llvm-project/master/compiler-rt/lib/fuzzer/afl/afl_driver.cpp - #- clang++ afl_driver.cpp afl-llvm-rt.o.o test-libfuzzer-target.o -o test-libfuzzer-target - #- timeout --preserve-status 5s ./afl-fuzz -i seeds -o out/ -- ./test-libfuzzer-target - #- cd qemu_mode - #- ./build_qemu_support.sh - #- cd .. - #- gcc ./test-instr.c -o test-no-instr - #- if [ -z "$AFL_STOP_MANUALLY" ]; - # then ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; - # else timeout --preserve-status 5s ./afl-fuzz -Q -i seeds -o out/ -- ./test-no-instr; - # fi - #- .travis/check_fuzzer_stats.sh -o out -k peak_rss_mb -v 12 -p 9 - ./afl-system-config + - sudo echo core > /proc/sys/kernel/core_pattern - make tests - make clean -- cgit 1.4.1 From c21b78b2979edbccf44b022d565eeddef9dd1d21 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:24:47 +0100 Subject: travis updates --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index b1f23032..ceb3f820 100644 --- a/.travis.yml +++ b/.travis.yml @@ -8,7 +8,7 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-9 gcc-9-plugin-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-5 gcc-5-plugin-dev # TODO: Look into splitting off some builds using a build matrix. # TODO: Move this all into a bash script so we don't need to write bash in yaml. -- cgit 1.4.1 From 7ab2e1d184e51f38b5a26e54746d708787605b84 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:29:22 +0100 Subject: travis update --- .travis.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index ceb3f820..d8f12483 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,3 +1,4 @@ +dist: bionic language: c env: @@ -8,7 +9,7 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-5 gcc-5-plugin-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev # TODO: Look into splitting off some builds using a build matrix. # TODO: Move this all into a bash script so we don't need to write bash in yaml. -- cgit 1.4.1 From ae990ce8dcf3074d770d2595a98d4c7706959dff Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 11:38:01 +0100 Subject: travis updates --- .travis.yml | 4 ---- test/test.sh | 7 ++++--- 2 files changed, 4 insertions(+), 7 deletions(-) diff --git a/.travis.yml b/.travis.yml index d8f12483..f1d74952 100644 --- a/.travis.yml +++ b/.travis.yml @@ -11,11 +11,7 @@ before_install: - sudo apt update - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev -# TODO: Look into splitting off some builds using a build matrix. -# TODO: Move this all into a bash script so we don't need to write bash in yaml. script: - make distrib - - ./afl-system-config - - sudo echo core > /proc/sys/kernel/core_pattern - make tests - make clean diff --git a/test/test.sh b/test/test.sh index 42ddf70b..e75d9fc7 100755 --- a/test/test.sh +++ b/test/test.sh @@ -26,6 +26,7 @@ test -z "$ECHO" && { printf Error: printf command does not support octal charact export AFL_EXIT_WHEN_DONE=1 export AFL_SKIP_CPUFREQ=1 +export AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 unset AFL_QUIET unset AFL_DEBUG unset AFL_HARDEN @@ -87,7 +88,7 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { # now we want to be sure that afl-fuzz is working # make sure core_pattern is set to core on linux (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { - $ECHO "$RED[!] we cannot run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" + $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || # make sure crash reporter is disabled on Mac OS X @@ -143,7 +144,7 @@ test -e ../afl-clang-fast && { } || $ECHO "$RED[!] llvm_mode hardened mode compilation failed" # now we want to be sure that afl-fuzz is working (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { - $ECHO "$RED[!] we cannot run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" + $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || # make sure crash reporter is disabled on Mac OS X @@ -226,7 +227,7 @@ test -e ../afl-gcc-fast && { } || $ECHO "$RED[!] gcc_plugin hardened mode compilation failed" # now we want to be sure that afl-fuzz is working (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { - $ECHO "$RED[!] we cannot run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" + $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || # make sure crash reporter is disabled on Mac OS X -- cgit 1.4.1 From c7c622377af95990181d044adace73d877cbfdca Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 12:25:20 +0100 Subject: travis debug --- .travis.yml | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/.travis.yml b/.travis.yml index f1d74952..6640ddd4 100644 --- a/.travis.yml +++ b/.travis.yml @@ -12,6 +12,15 @@ before_install: - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev script: + - echo DEBUG + - uname -a + - which python + - ls -l /bin/python* /usr/bin/python* + - file /bin/python* /usr/bin/python* + - dpkg -l | grep -i python + - pwd + - id + - echo END DEBUG - make distrib - make tests - make clean -- cgit 1.4.1 From 7fdc7e01a5889fba365b8b841ba19602e26b5bd7 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 31 Oct 2019 11:39:08 +0000 Subject: Fix some silent warnings and put some var to some usage... --- llvm_mode/LLVMInsTrim.so.cc | 15 +++++++++------ llvm_mode/afl-llvm-pass.so.cc | 2 ++ llvm_mode/compare-transform-pass.so.cc | 4 ++++ 3 files changed, 15 insertions(+), 6 deletions(-) diff --git a/llvm_mode/LLVMInsTrim.so.cc b/llvm_mode/LLVMInsTrim.so.cc index 4b5597e2..89738812 100644 --- a/llvm_mode/LLVMInsTrim.so.cc +++ b/llvm_mode/LLVMInsTrim.so.cc @@ -158,6 +158,7 @@ struct InsTrim : public ModulePass { bool instrumentBlock = false; DebugLoc Loc; StringRef instFilename; + unsigned int instLine = 0; for (auto &BB : F) { @@ -171,7 +172,7 @@ struct InsTrim : public ModulePass { DILocation *cDILoc = dyn_cast(Loc.getAsMDNode()); - unsigned int instLine = cDILoc->getLine(); + instLine = cDILoc->getLine(); instFilename = cDILoc->getFilename(); if (instFilename.str().empty()) { @@ -217,11 +218,13 @@ struct InsTrim : public ModulePass { * not whitelisted, so we skip instrumentation. */ if (!instrumentBlock) { - if (!instFilename.str().empty()) - SAYF(cYEL "[!] " cBRI "Not in whitelist, skipping %s ...\n", - instFilename.str().c_str()); - else - SAYF(cYEL "[!] " cBRI "No filename information found, skipping it"); + if (!be_quiet) { + if (!instFilename.str().empty()) + SAYF(cYEL "[!] " cBRI "Not in whitelist, skipping %s line %u...\n", + instFilename.str().c_str(), instLine); + else + SAYF(cYEL "[!] " cBRI "No filename information found, skipping it"); + } continue; } diff --git a/llvm_mode/afl-llvm-pass.so.cc b/llvm_mode/afl-llvm-pass.so.cc index e094a0b2..0c68136b 100644 --- a/llvm_mode/afl-llvm-pass.so.cc +++ b/llvm_mode/afl-llvm-pass.so.cc @@ -190,6 +190,8 @@ bool AFLCoverage::runOnModule(Module &M) { } + (void)instLine; + /* Continue only if we know where we actually are */ if (!instFilename.str().empty()) { diff --git a/llvm_mode/compare-transform-pass.so.cc b/llvm_mode/compare-transform-pass.so.cc index e1b6e671..0ccce875 100644 --- a/llvm_mode/compare-transform-pass.so.cc +++ b/llvm_mode/compare-transform-pass.so.cc @@ -234,6 +234,10 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp, ConstantInt *ilen = dyn_cast(op2); sizedLen = ilen->getZExtValue(); + } else { + + sizedLen = 0; + } if (HasStr1) { -- cgit 1.4.1 From 744910ad1b458e5e713fd4bd0c383cc019ab2c6e Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 12:43:51 +0100 Subject: travis update --- test/test.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index e75d9fc7..02eea821 100755 --- a/test/test.sh +++ b/test/test.sh @@ -377,7 +377,7 @@ test -d ../unicorn_mode/unicorn && { echo 0 > in/in $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 20 seconds" { - ../afl-fuzz -V20 -U -i in -o out -d -- python ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V20 -U -i in -o out -d -- python2.7 ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" @@ -392,7 +392,7 @@ test -d ../unicorn_mode/unicorn && { $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 25 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V25 -U -i in -o out -d -- python ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V25 -U -i in -o out -d -- python2.7 ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" -- cgit 1.4.1 From 7b0ab778e3850333c6cc2eef7a9db112cf09538b Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 12:46:55 +0100 Subject: travis update --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 6640ddd4..71c241ab 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,7 +9,7 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev script: - echo DEBUG -- cgit 1.4.1 From 822a3e505a6f2fb8dd2524172d69c34d15a9c650 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 12:49:33 +0100 Subject: travis update --- .travis.yml | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/.travis.yml b/.travis.yml index 71c241ab..6b718409 100644 --- a/.travis.yml +++ b/.travis.yml @@ -12,15 +12,7 @@ before_install: - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev script: - - echo DEBUG - - uname -a - - which python - - ls -l /bin/python* /usr/bin/python* - - file /bin/python* /usr/bin/python* - - dpkg -l | grep -i python - - pwd - - id - - echo END DEBUG + - which python2.7 - make distrib - make tests - make clean -- cgit 1.4.1 From e8d0ffa8b474532c0364128f42a76f5ed9578dfe Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 12:56:59 +0100 Subject: travis update --- test/test.sh | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index 02eea821..2d5c5e39 100755 --- a/test/test.sh +++ b/test/test.sh @@ -373,11 +373,15 @@ $ECHO "$BLUE[*] Testing: unicorn_mode" test -d ../unicorn_mode/unicorn && { test -e ../unicorn_mode/samples/simple/simple_target.bin -a -e ../unicorn_mode/samples/compcov_x64/compcov_target.bin && { { + # travis workaround + PY=`which python2.7` + test "$PY" = "/opt/pyenv/shims/python2.7" -a -x /usr/bin/python2.7 && PY=/usr/bin/python2.7 mkdir -p in echo 0 > in/in + $ECHO "$GREY[*] Using python binary $PY" $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 20 seconds" { - ../afl-fuzz -V20 -U -i in -o out -d -- python2.7 ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V20 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" @@ -392,7 +396,7 @@ test -d ../unicorn_mode/unicorn && { $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 25 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V25 -U -i in -o out -d -- python2.7 ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V25 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" -- cgit 1.4.1 From 74f7576313d49f47d003e653d1b13e6da250b6f0 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 13:24:15 +0100 Subject: travis update --- .travis.yml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 6b718409..1481bf49 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,10 +9,11 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev libc++-7-dev script: - - which python2.7 + - gcc -v + - clang -v - make distrib - make tests - make clean -- cgit 1.4.1 From b17afc10a23cf87b3a0b8290491de4edd80c9c71 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 31 Oct 2019 13:27:48 +0100 Subject: travis update --- .travis.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 1481bf49..87b3ef04 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,7 +9,8 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev libc++-7-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev +# libc++-7-dev script: - gcc -v -- cgit 1.4.1 From 664f603a31ff7b118d14fa6409dd662ee604b36c Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Thu, 31 Oct 2019 16:19:12 +0100 Subject: better wine trace with winepath on .cur_input --- afl-wine-trace | 26 ++++++++++++++++++++------ 1 file changed, 20 insertions(+), 6 deletions(-) diff --git a/afl-wine-trace b/afl-wine-trace index f8284d7e..65525a33 100755 --- a/afl-wine-trace +++ b/afl-wine-trace @@ -4,9 +4,10 @@ import os import sys import pefile import shutil +import subprocess if len(sys.argv) < 2: - print("[afl-wine-trace] usage: wine-cov binary [args...]\n") + print("[afl-wine-trace] usage: ./afl-wine-trace binary [args...]\n") exit(1) if os.getenv("AFL_PATH"): @@ -42,14 +43,20 @@ else: elif pe.FILE_HEADER.Machine == pefile.MACHINE_TYPE["IMAGE_FILE_MACHINE_I386"]: qemu_path += "i386" else: - print ("[wine-cov] unsuppoted architecture\n") + print ("[afl-wine-trace] unsuppoted architecture\n") exit(1) qemu_path = shutil.which(qemu_path) -if os.getenv("WINECOV_WINE_PATH"): - wine_path = os.getenv("WINECOV_WINE_PATH") +wine_path = None +if os.getenv("AFL_WINE_PATH"): + wine_path = os.getenv("AFL_WINE_PATH") else: - wine_path = "/usr/lib/wine/wine" + if not wine_path and shutil.which("wine"): + wine_path = shutil.which("wine") + if not wine_path and os.path.exists("/usr/bin/wine"): + wine_path = "/usr/bin/wine" + if not wine_path and os.path.exists("/usr/lib/wine/wine"): + wine_path = "/usr/lib/wine/wine" if pe.FILE_HEADER.Machine == pefile.MACHINE_TYPE["IMAGE_FILE_MACHINE_AMD64"] or pe.FILE_HEADER.Machine == pefile.MACHINE_TYPE["IMAGE_FILE_MACHINE_IA64"]: wine_path += "64" elif pe.FILE_HEADER.Machine == pefile.MACHINE_TYPE["IMAGE_FILE_MACHINE_I386"]: @@ -58,4 +65,11 @@ else: print ("[afl-wine-trace] unsopported architecture\n") exit(1) -os.execve(qemu_path, [qemu_path, wine_path] + sys.argv[1:], os.environ) +argv = sys.argv[1:] +for i in range(len(argv)): + if ".cur_input" in argv[i]: + argv[i] = subprocess.run([os.path.join(os.path.dirname(wine_path), "winepath"), "--windows", argv[i]], universal_newlines=True, stdout=subprocess.PIPE).stdout + break + +print("[afl-wine-trace] exec:", " ".join([qemu_path, wine_path] + argv)) +os.execve(qemu_path, [qemu_path, wine_path] + argv, os.environ) -- cgit 1.4.1 From b33bb0943ac4957eaf7b16ef694a4e4b4a538212 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 31 Oct 2019 15:50:58 +0000 Subject: libtokencap/libdislocator README rename proposals and fixing the install tasks in the process. --- README.md | 2 +- docs/notes_for_asan.txt | 2 +- libdislocator/Makefile | 2 +- libdislocator/README.dislocator.md | 60 +++++++++++++++++++++++++++++++++++ libdislocator/README.md | 60 ----------------------------------- libdislocator/libdislocator.so.c | 2 +- libtokencap/Makefile | 2 +- libtokencap/README.md | 64 -------------------------------------- libtokencap/README.tokencap.md | 64 ++++++++++++++++++++++++++++++++++++++ libtokencap/libtokencap.so.c | 2 +- 10 files changed, 130 insertions(+), 130 deletions(-) create mode 100644 libdislocator/README.dislocator.md delete mode 100644 libdislocator/README.md delete mode 100644 libtokencap/README.md create mode 100644 libtokencap/README.tokencap.md diff --git a/README.md b/README.md index 88a86aaa..e8d4e6a8 100644 --- a/README.md +++ b/README.md @@ -457,7 +457,7 @@ parsers and grammars, but isn't nearly as good as the -x mode. If a dictionary is really hard to come by, another option is to let AFL run for a while, and then use the token capture library that comes as a companion -utility with AFL. For that, see [libtokencap/README.md](libtokencap/README.md). +utility with AFL. For that, see [libtokencap/README.md](libtokencap/README.tokencap.md). ## 11) Crash triage diff --git a/docs/notes_for_asan.txt b/docs/notes_for_asan.txt index 972ca909..09ca172e 100644 --- a/docs/notes_for_asan.txt +++ b/docs/notes_for_asan.txt @@ -34,7 +34,7 @@ Note that ASAN is incompatible with -static, so be mindful of that. There is also the option of generating a corpus using a non-ASAN binary, and then feeding it to an ASAN-instrumented one to check for bugs. This is faster, and can give you somewhat comparable results. You can also try using -libdislocator (see libdislocator/README.dislocator in the parent directory) as a +libdislocator (see libdislocator/README.dislocator.md in the parent directory) as a lightweight and hassle-free (but less thorough) alternative. 2) Long version diff --git a/libdislocator/Makefile b/libdislocator/Makefile index 91efba07..05ba26b3 100644 --- a/libdislocator/Makefile +++ b/libdislocator/Makefile @@ -34,5 +34,5 @@ clean: install: all install -m 755 ../libdislocator.so $${DESTDIR}$(HELPER_PATH) - install -m 644 README.dislocator $${DESTDIR}$(HELPER_PATH) + install -m 644 README.dislocator.md $${DESTDIR}$(HELPER_PATH) diff --git a/libdislocator/README.dislocator.md b/libdislocator/README.dislocator.md new file mode 100644 index 00000000..5d5a1464 --- /dev/null +++ b/libdislocator/README.dislocator.md @@ -0,0 +1,60 @@ +# libdislocator, an abusive allocator + + (See ../docs/README for the general instruction manual.) + +This is a companion library that can be used as a drop-in replacement for the +libc allocator in the fuzzed binaries. It improves the odds of bumping into +heap-related security bugs in several ways: + + - It allocates all buffers so that they are immediately adjacent to a + subsequent PROT_NONE page, causing most off-by-one reads and writes to + immediately segfault, + + - It adds a canary immediately below the allocated buffer, to catch writes + to negative offsets (won't catch reads, though), + + - It sets the memory returned by malloc() to garbage values, improving the + odds of crashing when the target accesses uninitialized data, + + - It sets freed memory to PROT_NONE and does not actually reuse it, causing + most use-after-free bugs to segfault right away, + + - It forces all realloc() calls to return a new address - and sets + PROT_NONE on the original block. This catches use-after-realloc bugs, + + - It checks for calloc() overflows and can cause soft or hard failures + of alloc requests past a configurable memory limit (AFL_LD_LIMIT_MB, + AFL_LD_HARD_FAIL). + +Basically, it is inspired by some of the non-default options available for the +OpenBSD allocator - see malloc.conf(5) on that platform for reference. It is +also somewhat similar to several other debugging libraries, such as gmalloc +and DUMA - but is simple, plug-and-play, and designed specifically for fuzzing +jobs. + +Note that it does nothing for stack-based memory handling errors. The +-fstack-protector-all setting for GCC / clang, enabled when using AFL_HARDEN, +can catch some subset of that. + +The allocator is slow and memory-intensive (even the tiniest allocation uses up +4 kB of physical memory and 8 kB of virtual mem), making it completely unsuitable +for "production" uses; but it can be faster and more hassle-free than ASAN / MSAN +when fuzzing small, self-contained binaries. + +To use this library, run AFL like so: + +``` +AFL_PRELOAD=/path/to/libdislocator.so ./afl-fuzz [...other params...] +``` + +You *have* to specify path, even if it's just ./libdislocator.so or +$PWD/libdislocator.so. + +Similarly to afl-tmin, the library is not "proprietary" and can be used with +other fuzzers or testing tools without the need for any code tweaks. It does not +require AFL-instrumented binaries to work. + +Note that the AFL_PRELOAD approach (which AFL internally maps to LD_PRELOAD or +DYLD_INSERT_LIBRARIES, depending on the OS) works only if the target binary is +dynamically linked. Otherwise, attempting to use the library will have no +effect. diff --git a/libdislocator/README.md b/libdislocator/README.md deleted file mode 100644 index 5d5a1464..00000000 --- a/libdislocator/README.md +++ /dev/null @@ -1,60 +0,0 @@ -# libdislocator, an abusive allocator - - (See ../docs/README for the general instruction manual.) - -This is a companion library that can be used as a drop-in replacement for the -libc allocator in the fuzzed binaries. It improves the odds of bumping into -heap-related security bugs in several ways: - - - It allocates all buffers so that they are immediately adjacent to a - subsequent PROT_NONE page, causing most off-by-one reads and writes to - immediately segfault, - - - It adds a canary immediately below the allocated buffer, to catch writes - to negative offsets (won't catch reads, though), - - - It sets the memory returned by malloc() to garbage values, improving the - odds of crashing when the target accesses uninitialized data, - - - It sets freed memory to PROT_NONE and does not actually reuse it, causing - most use-after-free bugs to segfault right away, - - - It forces all realloc() calls to return a new address - and sets - PROT_NONE on the original block. This catches use-after-realloc bugs, - - - It checks for calloc() overflows and can cause soft or hard failures - of alloc requests past a configurable memory limit (AFL_LD_LIMIT_MB, - AFL_LD_HARD_FAIL). - -Basically, it is inspired by some of the non-default options available for the -OpenBSD allocator - see malloc.conf(5) on that platform for reference. It is -also somewhat similar to several other debugging libraries, such as gmalloc -and DUMA - but is simple, plug-and-play, and designed specifically for fuzzing -jobs. - -Note that it does nothing for stack-based memory handling errors. The --fstack-protector-all setting for GCC / clang, enabled when using AFL_HARDEN, -can catch some subset of that. - -The allocator is slow and memory-intensive (even the tiniest allocation uses up -4 kB of physical memory and 8 kB of virtual mem), making it completely unsuitable -for "production" uses; but it can be faster and more hassle-free than ASAN / MSAN -when fuzzing small, self-contained binaries. - -To use this library, run AFL like so: - -``` -AFL_PRELOAD=/path/to/libdislocator.so ./afl-fuzz [...other params...] -``` - -You *have* to specify path, even if it's just ./libdislocator.so or -$PWD/libdislocator.so. - -Similarly to afl-tmin, the library is not "proprietary" and can be used with -other fuzzers or testing tools without the need for any code tweaks. It does not -require AFL-instrumented binaries to work. - -Note that the AFL_PRELOAD approach (which AFL internally maps to LD_PRELOAD or -DYLD_INSERT_LIBRARIES, depending on the OS) works only if the target binary is -dynamically linked. Otherwise, attempting to use the library will have no -effect. diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 7fe40afa..106b44f4 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -14,7 +14,7 @@ http://www.apache.org/licenses/LICENSE-2.0 This is a companion library that can be used as a drop-in replacement - for the libc allocator in the fuzzed binaries. See README.dislocator for + for the libc allocator in the fuzzed binaries. See README.dislocator.md for more info. */ diff --git a/libtokencap/Makefile b/libtokencap/Makefile index df2426ed..6e1319d8 100644 --- a/libtokencap/Makefile +++ b/libtokencap/Makefile @@ -49,5 +49,5 @@ clean: install: all install -m 755 ../libtokencap.so $${DESTDIR}$(HELPER_PATH) - install -m 644 README.tokencap $${DESTDIR}$(HELPER_PATH) + install -m 644 README.tokencap.md $${DESTDIR}$(HELPER_PATH) diff --git a/libtokencap/README.md b/libtokencap/README.md deleted file mode 100644 index 8aae38bf..00000000 --- a/libtokencap/README.md +++ /dev/null @@ -1,64 +0,0 @@ -# strcmp() / memcmp() token capture library - - (See ../docs/README for the general instruction manual.) - -This companion library allows you to instrument `strcmp()`, `memcmp()`, -and related functions to automatically extract syntax tokens passed to any of -these libcalls. The resulting list of tokens may be then given as a starting -dictionary to afl-fuzz (the -x option) to improve coverage on subsequent -fuzzing runs. - -This may help improving coverage in some targets, and do precisely nothing in -others. In some cases, it may even make things worse: if libtokencap picks up -syntax tokens that are not used to process the input data, but that are a part -of - say - parsing a config file... well, you're going to end up wasting a lot -of CPU time on trying them out in the input stream. In other words, use this -feature with care. Manually screening the resulting dictionary is almost -always a necessity. - -As for the actual operation: the library stores tokens, without any deduping, -by appending them to a file specified via AFL_TOKEN_FILE. If the variable is not -set, the tool uses stderr (which is probably not what you want). - -Similarly to afl-tmin, the library is not "proprietary" and can be used with -other fuzzers or testing tools without the need for any code tweaks. It does not -require AFL-instrumented binaries to work. - -To use the library, you *need* to make sure that your fuzzing target is compiled -with -fno-builtin and is linked dynamically. If you wish to automate the first -part without mucking with CFLAGS in Makefiles, you can set AFL_NO_BUILTIN=1 -when using afl-gcc. This setting specifically adds the following flags: - -``` - -fno-builtin-strcmp -fno-builtin-strncmp -fno-builtin-strcasecmp - -fno-builtin-strcasencmp -fno-builtin-memcmp -fno-builtin-strstr - -fno-builtin-strcasestr -``` - -The next step is simply loading this library via LD_PRELOAD. The optimal usage -pattern is to allow afl-fuzz to fuzz normally for a while and build up a corpus, -and then fire off the target binary, with libtokencap.so loaded, on every file -found by AFL in that earlier run. This demonstrates the basic principle: - -``` - export AFL_TOKEN_FILE=$PWD/temp_output.txt - - for i in /queue/id*; do - LD_PRELOAD=/path/to/libtokencap.so \ - /path/to/target/program [...params, including $i...] - done - - sort -u temp_output.txt >afl_dictionary.txt -``` - -If you don't get any results, the target library is probably not using strcmp() -and memcmp() to parse input; or you haven't compiled it with -fno-builtin; or -the whole thing isn't dynamically linked, and LD_PRELOAD is having no effect. - -Portability hints: There is probably no particularly portable and non-invasive -way to distinguish between read-only and read-write memory mappings. -The `__tokencap_load_mappings()` function is the only thing that would -need to be changed for other OSes. - -Current supported OSes are: Linux, Darwin, FreeBSD (thanks to @devnexen) - diff --git a/libtokencap/README.tokencap.md b/libtokencap/README.tokencap.md new file mode 100644 index 00000000..8aae38bf --- /dev/null +++ b/libtokencap/README.tokencap.md @@ -0,0 +1,64 @@ +# strcmp() / memcmp() token capture library + + (See ../docs/README for the general instruction manual.) + +This companion library allows you to instrument `strcmp()`, `memcmp()`, +and related functions to automatically extract syntax tokens passed to any of +these libcalls. The resulting list of tokens may be then given as a starting +dictionary to afl-fuzz (the -x option) to improve coverage on subsequent +fuzzing runs. + +This may help improving coverage in some targets, and do precisely nothing in +others. In some cases, it may even make things worse: if libtokencap picks up +syntax tokens that are not used to process the input data, but that are a part +of - say - parsing a config file... well, you're going to end up wasting a lot +of CPU time on trying them out in the input stream. In other words, use this +feature with care. Manually screening the resulting dictionary is almost +always a necessity. + +As for the actual operation: the library stores tokens, without any deduping, +by appending them to a file specified via AFL_TOKEN_FILE. If the variable is not +set, the tool uses stderr (which is probably not what you want). + +Similarly to afl-tmin, the library is not "proprietary" and can be used with +other fuzzers or testing tools without the need for any code tweaks. It does not +require AFL-instrumented binaries to work. + +To use the library, you *need* to make sure that your fuzzing target is compiled +with -fno-builtin and is linked dynamically. If you wish to automate the first +part without mucking with CFLAGS in Makefiles, you can set AFL_NO_BUILTIN=1 +when using afl-gcc. This setting specifically adds the following flags: + +``` + -fno-builtin-strcmp -fno-builtin-strncmp -fno-builtin-strcasecmp + -fno-builtin-strcasencmp -fno-builtin-memcmp -fno-builtin-strstr + -fno-builtin-strcasestr +``` + +The next step is simply loading this library via LD_PRELOAD. The optimal usage +pattern is to allow afl-fuzz to fuzz normally for a while and build up a corpus, +and then fire off the target binary, with libtokencap.so loaded, on every file +found by AFL in that earlier run. This demonstrates the basic principle: + +``` + export AFL_TOKEN_FILE=$PWD/temp_output.txt + + for i in /queue/id*; do + LD_PRELOAD=/path/to/libtokencap.so \ + /path/to/target/program [...params, including $i...] + done + + sort -u temp_output.txt >afl_dictionary.txt +``` + +If you don't get any results, the target library is probably not using strcmp() +and memcmp() to parse input; or you haven't compiled it with -fno-builtin; or +the whole thing isn't dynamically linked, and LD_PRELOAD is having no effect. + +Portability hints: There is probably no particularly portable and non-invasive +way to distinguish between read-only and read-write memory mappings. +The `__tokencap_load_mappings()` function is the only thing that would +need to be changed for other OSes. + +Current supported OSes are: Linux, Darwin, FreeBSD (thanks to @devnexen) + diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 2fe9ae63..7495180d 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -15,7 +15,7 @@ This Linux-only companion library allows you to instrument strcmp(), memcmp(), and related functions to automatically extract tokens. - See README.tokencap for more info. + See README.tokencap.md for more info. */ -- cgit 1.4.1 From c3b2fee07413fcab6f13d0c66ea0ca30760b2b1b Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 31 Oct 2019 21:20:09 +0000 Subject: Unicorn mode for BSD proposal. Darwin fix --- unicorn_mode/build_unicorn_support.sh | 61 +++++++++++++++++++++++++++-------- 1 file changed, 48 insertions(+), 13 deletions(-) diff --git a/unicorn_mode/build_unicorn_support.sh b/unicorn_mode/build_unicorn_support.sh index 3bd404b8..88dae90b 100755 --- a/unicorn_mode/build_unicorn_support.sh +++ b/unicorn_mode/build_unicorn_support.sh @@ -43,9 +43,11 @@ echo echo "[*] Performing basic sanity checks..." -if [ ! "`uname -s`" = "Linux" ]; then +PLT=`uname -s` - echo "[-] Error: Unicorn instrumentation is supported only on Linux." +if [ ! "$PLT" = "Linux" ] && [ ! "$PLT" = "Darwin" ] && [ ! "$PLT" = "FreeBSD" ] && [ ! "$PLT" = "NetBSD" ] && [ ! "$PLT" = "OpenBSD" ]; then + + echo "[-] Error: Unicorn instrumentation is unsupported on $PLT." exit 1 fi @@ -64,7 +66,39 @@ if [ ! -f "../afl-showmap" ]; then fi -for i in wget python automake autoconf sha384sum; do +if [ "$PLT" = "Linux" ]; then + CKSUMCMD='sha384sum --' + PYTHONBIN=python2 + MAKECMD=make + TARCMD=tar + EASY_INSTALL=easy_install +fi + +if [ "$PLT" = "Darwin" ]; then + CKSUMCMD="shasum -a 384 --tag" + PYTHONBIN=python2.7 + MAKECMD=make + TARCMD=tar + EASY_INSTALL=easy_install-2.7 +fi + +if [ "$PLT" = "FreeBSD" ]; then + CKSUMCMD="sha384 -q" + PYTHONBIN=python2.7 + MAKECMD=gmake + TARCMD=gtar + EASY_INSTALL=easy_install-2.7 +fi + +if [ "$PLT" = "NetBSD" ] || [ "$PLT" = "OpenBSD" ]; then + CKSUMCMD="cksum -a sha384 -q" + PYTHONBIN=python2.7 + MAKECMD=gmake + TARCMD=gtar + EASY_INSTALL=easy_install-2.7 +fi + +for i in wget $PYTHONBIN automake autoconf $MAKECMD $TARCMD; do T=`which "$i" 2>/dev/null` @@ -77,10 +111,10 @@ for i in wget python automake autoconf sha384sum; do done -if ! which easy_install > /dev/null; then +if ! which $EASY_INSTALL > /dev/null; then # work around for unusual installs - if [ '!' -e /usr/lib/python2.7/dist-packages/easy_install.py ]; then + if [ '!' -e /usr/lib/python2.7/dist-packages/easy_install.py ] && [ '!' -e /usr/local/lib/python2.7/dist-packages/easy_install.py ] && [ '!' -e /usr/pkg/lib/python2.7/dist-packages/easy_install.py ]; then echo "[-] Error: Python setup-tools not found. Run 'sudo apt-get install python-setuptools'." exit 1 @@ -100,15 +134,16 @@ echo "[+] All checks passed!" ARCHIVE="`basename -- "$UNICORN_URL"`" -CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` +CKSUM=`$CKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` if [ ! "$CKSUM" = "$UNICORN_SHA384" ]; then echo "[*] Downloading Unicorn v1.0.1 from the web..." rm -f "$ARCHIVE" - wget -O "$ARCHIVE" -- "$UNICORN_URL" || exit 1 + # NetBSD does not support SSL in the userland, we gotta trust github url + wget --no-check-certificate -O "$ARCHIVE" -- "$UNICORN_URL" || exit 1 - CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` + CKSUM=`CHKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` fi @@ -127,7 +162,7 @@ echo "[*] Uncompressing archive (this will take a while)..." rm -rf "unicorn" || exit 1 mkdir "unicorn" || exit 1 -tar xzf "$ARCHIVE" -C ./unicorn --strip-components=1 || exit 1 +$TARCMD xzf "$ARCHIVE" -C ./unicorn --strip-components=1 || exit 1 echo "[+] Unpacking successful." @@ -149,7 +184,7 @@ echo "[+] Configuration complete." echo "[*] Attempting to build Unicorn (fingers crossed!)..." -UNICORN_QEMU_FLAGS='--python=python2' make -j `nproc` || exit 1 +UNICORN_QEMU_FLAGS="--python=$PYTHONBIN" $MAKECMD -j4 || exit 1 echo "[+] Build process successful!" @@ -157,10 +192,10 @@ echo "[*] Installing Unicorn python bindings..." cd bindings/python || exit 1 if [ -z "$VIRTUAL_ENV" ]; then echo "[*] Info: Installing python unicorn using --user" - python setup.py install --user || exit 1 + $PYTHONBIN setup.py install --user || exit 1 else echo "[*] Info: Installing python unicorn to virtualenv: $VIRTUAL_ENV" - python setup.py install || exit 1 + $PYTHONBIN setup.py install || exit 1 fi export LIBUNICORN_PATH='$(pwd)' # in theory, this allows to switch between afl-unicorn and unicorn so files. @@ -175,7 +210,7 @@ cd ../samples/simple || exit 1 # Run afl-showmap on the sample application. If anything comes out then it must have worked! unset AFL_INST_RATIO -echo 0 | ../../../afl-showmap -U -m none -q -o .test-instr0 -- python simple_test_harness.py ./sample_inputs/sample1.bin || exit 1 +echo 0 | ../../../afl-showmap -U -m none -q -o .test-instr0 -- $PYTHONBIN simple_test_harness.py ./sample_inputs/sample1.bin || exit 1 if [ -s .test-instr0 ] then -- cgit 1.4.1 From 1c7b6a5e0590b4a34819fec3cdfe430d32b041d5 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Mon, 4 Nov 2019 13:10:52 +0100 Subject: travis --- .travis.yml | 3 +- dictionaries/regexp.dict | 244 +++++++++++++++++++++++++++++++++++++++++++++++ docs/ChangeLog | 1 + test/test.sh | 162 ++++++++++++++++++++++++------- 4 files changed, 376 insertions(+), 34 deletions(-) create mode 100644 dictionaries/regexp.dict diff --git a/.travis.yml b/.travis.yml index 87b3ef04..00d58853 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,8 +9,7 @@ env: before_install: - sudo apt update - - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-8 gcc-8-plugin-dev libc++-8-dev -# libc++-7-dev + - sudo apt install -y libtool libtool-bin automake bison libglib2.0 build-essential clang gcc-7 gcc-7-plugin-dev libc++-7-dev script: - gcc -v diff --git a/dictionaries/regexp.dict b/dictionaries/regexp.dict new file mode 100644 index 00000000..957d18e2 --- /dev/null +++ b/dictionaries/regexp.dict @@ -0,0 +1,244 @@ +# +# AFL dictionary for JS regex +# --------------------------- +# +# Contains various regular expressions. +# +# Created by Yang Guo +# +# Contributed by Dhiraj Mishra +# +"?" +"abc" +"()" +"[]" +"abc|def" +"abc|def|ghi" +"^xxx$" +"ab\\b\\d\\bcd" +"\\w|\\d" +"a*?" +"abc+" +"abc+?" +"xyz?" +"xyz??" +"xyz{0,1}" +"xyz{0,1}?" +"xyz{93}" +"xyz{1,32}" +"xyz{1,32}?" +"xyz{1,}" +"xyz{1,}?" +"a\\fb\\nc\\rd\\te\\vf" +"a\\nb\\bc" +"/^\d*\./" +"(?:foo)" +"(?: foo )" +"foo|(bar|baz)|quux" +"foo(?=bar)baz" +"foo(?!bar)baz" +"foo(?<=bar)baz" +"foo(?)" +"(?.)" +"(?.)\\k" +"\\p{Script=Greek}" +"\\P{sc=Greek}" +"\\p{Script_Extensions=Greek}" +"\\P{scx=Greek}" +"\\p{General_Category=Decimal_Number}" +"\\P{gc=Decimal_Number}" +"\\p{gc=Nd}" +"\\P{Decimal_Number}" +"\\p{Nd}" +"\\P{Any}" +"\\p{Changes_When_NFKC_Casefolded}" diff --git a/docs/ChangeLog b/docs/ChangeLog index 4c51502b..3a5961ad 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -23,6 +23,7 @@ Version ++2.58d (dev): - llvm_mode: float splitting is now configured via AFL_LLVM_LAF_SPLIT_FLOATS - libtokencap: support for *BSD/OSX added - libcompcov floating point splitting support for qemu and unicorn + - ripped regex.dictionary from Google afl PR - removed unnecessary warnings diff --git a/test/test.sh b/test/test.sh index 2d5c5e39..f954776f 100755 --- a/test/test.sh +++ b/test/test.sh @@ -24,6 +24,8 @@ $ECHO \\101 2>&1 | grep -qE '^A' || { } test -z "$ECHO" && { printf Error: printf command does not support octal character codes ; exit 1 ; } +CODE=0 + export AFL_EXIT_WHEN_DONE=1 export AFL_SKIP_CPUFREQ=1 export AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 @@ -75,16 +77,26 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { test -e test-instr.plain.0 -a -e test-instr.plain.1 && { diff -q test-instr.plain.0 test-instr.plain.1 > /dev/null 2>&1 && { $ECHO "$RED[!] ${AFL_GCC} instrumentation should be different on different input but is not" + CODE=1 } || $ECHO "$GREEN[+] ${AFL_GCC} instrumentation present and working correctly" - } || $ECHO "$RED[!] ${AFL_GCC} instrumentation failed" + } || { + $ECHO "$RED[!] ${AFL_GCC} instrumentation failed" + CODE=1 + } rm -f test-instr.plain.0 test-instr.plain.1 } || $ECHO "$RED[!] ${AFL_GCC} failed" test -e test-compcov.harden && { grep -Eqa 'stack_chk_fail|fstack-protector-all|fortified' test-compcov.harden > /dev/null 2>&1 && { $ECHO "$GREEN[+] ${AFL_GCC} hardened mode succeeded and is working" - } || $ECHO "$RED[!] ${AFL_GCC} hardened mode is not hardened" + } || { + $ECHO "$RED[!] ${AFL_GCC} hardened mode is not hardened" + CODE=1 + } rm -f test-compcov.harden - } || $ECHO "$RED[!] ${AFL_GCC} hardened mode compilation failed" + } || { + $ECHO "$RED[!] ${AFL_GCC} hardened mode compilation failed" + CODE=1 + } # now we want to be sure that afl-fuzz is working # make sure core_pattern is set to core on linux (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { @@ -109,6 +121,7 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with ${AFL_GCC}" + CODE=1 } rm -rf in out errors } @@ -132,16 +145,29 @@ test -e ../afl-clang-fast && { test -e test-instr.plain.0 -a -e test-instr.plain.1 && { diff -q test-instr.plain.0 test-instr.plain.1 > /dev/null 2>&1 && { $ECHO "$RED[!] llvm_mode instrumentation should be different on different input but is not" + CODE=1 } || $ECHO "$GREEN[+] llvm_mode instrumentation present and working correctly" - } || $ECHO "$RED[!] llvm_mode instrumentation failed" + } || { + $ECHO "$RED[!] llvm_mode instrumentation failed" + CODE=1 + } rm -f test-instr.plain.0 test-instr.plain.1 - } || $ECHO "$RED[!] llvm_mode failed" + } || { + $ECHO "$RED[!] llvm_mode failed" + CODE=1 + } test -e test-compcov.harden && { grep -Eqa 'stack_chk_fail|fstack-protector-all|fortified' test-compcov.harden > /dev/null 2>&1 && { $ECHO "$GREEN[+] llvm_mode hardened mode succeeded and is working" - } || $ECHO "$RED[!] llvm_mode hardened mode is not hardened" + } || { + $ECHO "$RED[!] llvm_mode hardened mode is not hardened" + CODE=1 + } rm -f test-compcov.harden - } || $ECHO "$RED[!] llvm_mode hardened mode compilation failed" + } || { + $ECHO "$RED[!] llvm_mode hardened mode compilation failed" + CODE=1 + } # now we want to be sure that afl-fuzz is working (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" @@ -150,6 +176,7 @@ test -e ../afl-clang-fast && { # make sure crash reporter is disabled on Mac OS X (test "$(uname -s)" = "Darwin" && test $(launchctl list 2>/dev/null | grep -q '\.ReportCrash$') && { $ECHO "$RED[!] we cannot run afl-fuzz with enabled crash reporter. Run 'sudo sh afl-system-config'.$RESET" + CODE=1 true }) || { mkdir -p in @@ -165,6 +192,7 @@ test -e ../afl-clang-fast && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with llvm_mode" + CODE=1 } rm -rf in out errors } @@ -175,30 +203,54 @@ test -e ../afl-clang-fast && { test -e test-compcov.instrim && { grep -Eq " [1-3] location" test.out && { $ECHO "$GREEN[+] llvm_mode InsTrim feature works correctly" - } || $ECHO "$RED[!] llvm_mode InsTrim feature failed" - } || $ECHO "$RED[!] llvm_mode InsTrim feature compilation failed" + } || { + $ECHO "$RED[!] llvm_mode InsTrim feature failed" + CODE=1 + } + } || { + $ECHO "$RED[!] llvm_mode InsTrim feature compilation failed" + CODE=1 + } rm -f test-compcov.instrim test.out AFL_LLVM_LAF_SPLIT_SWITCHES=1 AFL_LLVM_LAF_TRANSFORM_COMPARES=1 AFL_LLVM_LAF_SPLIT_COMPARES=1 ../afl-clang-fast -o test-compcov.compcov test-compcov.c > /dev/null 2> test.out test -e test-compcov.compcov && { grep -Eq " [3-9][0-9] location" test.out && { $ECHO "$GREEN[+] llvm_mode laf-intel/compcov feature works correctly" - } || $ECHO "$RED[!] llvm_mode laf-intel/compcov feature failed" - } || $ECHO "$RED[!] llvm_mode laf-intel/compcov feature compilation failed" + } || { + $ECHO "$RED[!] llvm_mode laf-intel/compcov feature failed" + CODE=1 + } + } || { + $ECHO "$RED[!] llvm_mode laf-intel/compcov feature compilation failed" + CODE=1 + } rm -f test-compcov.compcov test.out echo foobar.c > whitelist.txt AFL_LLVM_WHITELIST=whitelist.txt ../afl-clang-fast -o test-compcov test-compcov.c > test.out 2>&1 test -e test-compcov && { grep -q "No instrumentation targets found" test.out && { $ECHO "$GREEN[+] llvm_mode whitelist feature works correctly" - } || $ECHO "$RED[!] llvm_mode whitelist feature failed" - } || $ECHO "$RED[!] llvm_mode whitelist feature compilation failed" + } || { + $ECHO "$RED[!] llvm_mode whitelist feature failed" + CODE=1 + } + } || { + $ECHO "$RED[!] llvm_mode whitelist feature compilation failed" + CODE=1 + } rm -f test-compcov test.out whitelist.txt ../afl-clang-fast -o test-persistent ../experimental/persistent_demo/persistent_demo.c > /dev/null 2>&1 test -e test-persistent && { echo foo | ../afl-showmap -o /dev/null -q -r ./test-persistent && { $ECHO "$GREEN[+] llvm_mode persistent mode feature works correctly" - } || $ECHO "$RED[!] llvm_mode persistent mode feature failed to work" - } || $ECHO "$RED[!] llvm_mode persistent mode feature compilation failed" + } || { + $ECHO "$RED[!] llvm_mode persistent mode feature failed to work" + CODE=1 + } + } || { + $ECHO "$RED[!] llvm_mode persistent mode feature compilation failed" + CODE=1 + } rm -f test-persistent } || $ECHO "$YELLOW[-] llvm_mode not compiled, cannot test" @@ -214,17 +266,32 @@ test -e ../afl-gcc-fast && { test -e test-instr.plain.0 -a -e test-instr.plain.1 && { diff -q test-instr.plain.0 test-instr.plain.1 > /dev/null 2>&1 && { $ECHO "$RED[!] gcc_plugin instrumentation should be different on different input but is not" - } || $ECHO "$GREEN[+] gcc_plugin instrumentation present and working correctly" - } || $ECHO "$RED[!] gcc_plugin instrumentation failed" + CODE=1 + } || { + $ECHO "$GREEN[+] gcc_plugin instrumentation present and working correctly" + } + } || { + $ECHO "$RED[!] gcc_plugin instrumentation failed" + CODE=1 + } rm -f test-instr.plain.0 test-instr.plain.1 - } || $ECHO "$RED[!] gcc_plugin failed" + } || { + $ECHO "$RED[!] gcc_plugin failed" + CODE=1 + } test -e test-compcov.harden.gccpi && { grep -Eqa 'stack_chk_fail|fstack-protector-all|fortified' test-compcov.harden.gccpi > /dev/null 2>&1 && { $ECHO "$GREEN[+] gcc_plugin hardened mode succeeded and is working" - } || $ECHO "$RED[!] gcc_plugin hardened mode is not hardened" + } || { + $ECHO "$RED[!] gcc_plugin hardened mode is not hardened" + CODE=1 + } rm -f test-compcov.harden.gccpi - } || $ECHO "$RED[!] gcc_plugin hardened mode compilation failed" + } || { + $ECHO "$RED[!] gcc_plugin hardened mode compilation failed" + CODE=1 + } # now we want to be sure that afl-fuzz is working (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" @@ -233,6 +300,7 @@ test -e ../afl-gcc-fast && { # make sure crash reporter is disabled on Mac OS X (test "$(uname -s)" = "Darwin" && test $(launchctl list 2>/dev/null | grep -q '\.ReportCrash$') && { $ECHO "$RED[!] we cannot run afl-fuzz with enabled crash reporter. Run 'sudo sh afl-system-config'.$RESET" + CODE=1 true }) || { mkdir -p in @@ -248,6 +316,7 @@ test -e ../afl-gcc-fast && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with gcc_plugin" + CODE=1 } rm -rf in out errors } @@ -259,15 +328,27 @@ test -e ../afl-gcc-fast && { test -e test-compcov && { echo 1 | ../afl-showmap -m ${MEM_LIMIT} -o - -r -- ./test-compcov 2>&1 | grep -q "Captured 1 tuples" && { $ECHO "$GREEN[+] gcc_plugin whitelist feature works correctly" - } || $ECHO "$RED[!] gcc_plugin whitelist feature failed" - } || $ECHO "$RED[!] gcc_plugin whitelist feature compilation failed" + } || { + $ECHO "$RED[!] gcc_plugin whitelist feature failed" + CODE=1 + } + } || { + $ECHO "$RED[!] gcc_plugin whitelist feature compilation failed" + CODE=1 + } rm -f test-compcov test.out whitelist.txt ../afl-gcc-fast -o test-persistent ../experimental/persistent_demo/persistent_demo.c > /dev/null 2>&1 test -e test-persistent && { echo foo | ../afl-showmap -o /dev/null -q -r ./test-persistent && { $ECHO "$GREEN[+] gcc_plugin persistent mode feature works correctly" - } || $ECHO "$RED[!] gcc_plugin persistent mode feature failed to work" - } || $ECHO "$RED[!] gcc_plugin persistent mode feature compilation failed" + } || { + $ECHO "$RED[!] gcc_plugin persistent mode feature failed to work" + CODE=1 + } + } || { + $ECHO "$RED[!] gcc_plugin persistent mode feature compilation failed" + CODE=1 + } rm -f test-persistent } || $ECHO "$YELLOW[-] gcc_plugin not compiled, cannot test" @@ -277,7 +358,10 @@ test -e ../libtokencap.so && { AFL_TOKEN_FILE=token.out LD_PRELOAD=../libtokencap.so DYLD_INSERT_LIBRARIES=../libtokencap.so DYLD_FORCE_FLAT_NAMESPACE=1 ./test-compcov foobar > /dev/null 2>&1 grep -q BUGMENOT token.out > /dev/null 2>&1 && { $ECHO "$GREEN[+] libtokencap did successfully capture tokens" - } || $ECHO "$RED[!] libtokencap did not capture tokens" + } || { + $ECHO "$RED[!] libtokencap did not capture tokens" + CODE=1 + } rm -f token.out } || $ECHO "$YELLOW[-] libtokencap is not compiled, cannot test" test -e ../libdislocator.so && { @@ -288,6 +372,7 @@ test -e ../libdislocator.so && { } > /dev/null 2>&1 grep -q BUFFEROVERFLOW test.out > /dev/null 2>&1 && { $ECHO "$RED[!] libdislocator did not detect the memory corruption" + CODE=1 } || $ECHO "$GREEN[+] libdislocator did successfully detect the memory corruption" rm -f test.out core test-compcov.core core.test-compcov } || $ECHO "$YELLOW[-] libdislocator is not compiled, cannot test" @@ -313,6 +398,7 @@ test -e ../afl-qemu-trace && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode" + CODE=1 } rm -f errors @@ -330,6 +416,7 @@ test -e ../afl-qemu-trace && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with qemu_mode libcompcov" + CODE=1 } } || $ECHO "$YELLOW[-] we cannot test qemu_mode libcompcov because it is not present" rm -f errors @@ -359,12 +446,16 @@ test -e ../afl-qemu-trace && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with persistent qemu_mode" + CODE=1 exit 1 } $ECHO "$YELLOW[?] we need a test case for qemu_mode unsigaction library" rm -rf in out errors } - } || $ECHO "$RED[-] gcc compilation of test targets failed - what is going on??" + } || { + $ECHO "$RED[-] gcc compilation of test targets failed - what is going on??" + CODE=1 + } rm -f test-instr test-compcov } || $ECHO "$YELLOW[-] qemu_mode is not compiled, cannot test" @@ -379,9 +470,9 @@ test -d ../unicorn_mode/unicorn && { mkdir -p in echo 0 > in/in $ECHO "$GREY[*] Using python binary $PY" - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 20 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode, this will take approx 25 seconds" { - ../afl-fuzz -V20 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V25 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/simple/simple_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000002* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode" @@ -390,13 +481,14 @@ test -d ../unicorn_mode/unicorn && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode" + CODE=1 } rm -f errors - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 25 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 35 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V25 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V35 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" @@ -405,12 +497,18 @@ test -d ../unicorn_mode/unicorn && { cat errors echo CUT------------------------------------------------------------------CUT $ECHO "$RED[!] afl-fuzz is not working correctly with unicorn_mode compcov" + CODE=1 } rm -rf in out errors } - } || $ECHO "$RED[-] missing sample binaries in unicorn_mode/samples/ - what is going on??" + } || { + $ECHO "$RED[-] missing sample binaries in unicorn_mode/samples/ - what is going on??" + CODE=1 + } } || $ECHO "$YELLOW[-] unicorn_mode is not compiled, cannot test" $ECHO "$GREY[*] all test cases completed.$RESET" - +test "$CODE" = "0" && $ECHO "$GREEN[+] all tests were successful :-)$RESET" +test "$CODE" = "0" || $ECHO "$RED[-] failure in tests :-($RESET" +exit $CODE -- cgit 1.4.1 From adae07d0138d25594efb765dc30e19af32222bee Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Mon, 4 Nov 2019 15:46:49 +0100 Subject: restored big-endian compcov in unicorn --- unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h | 74 +++++++++++++++++++++- 1 file changed, 73 insertions(+), 1 deletion(-) diff --git a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h index 53ab654c..3603fae0 100644 --- a/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h +++ b/unicorn_mode/patches/afl-unicorn-tcg-runtime-inl.h @@ -33,6 +33,78 @@ #include "uc_priv.h" #include "afl-unicorn-common.h" +void HELPER(afl_compcov_log_16)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, + uint64_t arg2) { + + u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; + + if ((arg1 & 0xff) == (arg2 & 0xff)) { INC_AFL_AREA(cur_loc); } + +} + +void HELPER(afl_compcov_log_32)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, + uint64_t arg2) { + + u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; + + if ((arg1 & 0xff) == (arg2 & 0xff)) { + + INC_AFL_AREA(cur_loc); + if ((arg1 & 0xffff) == (arg2 & 0xffff)) { + + INC_AFL_AREA(cur_loc + 1); + if ((arg1 & 0xffffff) == (arg2 & 0xffffff)) { INC_AFL_AREA(cur_loc + 2); } + + } + + } + +} + +void HELPER(afl_compcov_log_64)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, + uint64_t arg2) { + + u8* afl_area_ptr = ((struct uc_struct*)uc_ptr)->afl_area_ptr; + + if ((arg1 & 0xff) == (arg2 & 0xff)) { + + INC_AFL_AREA(cur_loc); + if ((arg1 & 0xffff) == (arg2 & 0xffff)) { + + INC_AFL_AREA(cur_loc + 1); + if ((arg1 & 0xffffff) == (arg2 & 0xffffff)) { + + INC_AFL_AREA(cur_loc + 2); + if ((arg1 & 0xffffffff) == (arg2 & 0xffffffff)) { + + INC_AFL_AREA(cur_loc + 3); + if ((arg1 & 0xffffffffff) == (arg2 & 0xffffffffff)) { + + INC_AFL_AREA(cur_loc + 4); + if ((arg1 & 0xffffffffffff) == (arg2 & 0xffffffffffff)) { + + INC_AFL_AREA(cur_loc + 5); + if ((arg1 & 0xffffffffffffff) == (arg2 & 0xffffffffffffff)) { + + INC_AFL_AREA(cur_loc + 6); + + } + + } + + } + + } + + } + + } + + } + +} + +/* // Little endian CompCov void HELPER(afl_compcov_log_16)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, uint64_t arg2) { @@ -99,4 +171,4 @@ void HELPER(afl_compcov_log_64)(void* uc_ptr, uint64_t cur_loc, uint64_t arg1, } } - +*/ -- cgit 1.4.1 From 14c359700b6b1d4408853f878931937ac586059c Mon Sep 17 00:00:00 2001 From: David Carlier Date: Mon, 4 Nov 2019 15:37:56 +0000 Subject: Basic docker build proposal. --- Dockerfile | 21 +++++++++++++++++++++ docs/QuickStartGuide.txt | 2 ++ 2 files changed, 23 insertions(+) create mode 100644 Dockerfile diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 00000000..af85ee8d --- /dev/null +++ b/Dockerfile @@ -0,0 +1,21 @@ +FROM gcc:8.3.0 + +RUN apt-get update && apt-get install -y --no-install-recommends \ + automake \ + bison \ + clang \ + flex \ + gcc-8-plugin-dev \ + libc++-7-dev \ + libtool \ + libtool-bin \ + llvm-7-tools \ + python-setuptools \ + && rm -fr /var/lib/apt/lists/* +RUN mkdir /app +WORKDIR ["/app"] +COPY . . +ENV CC=gcc-8 +ENV CXX=g++-8 +ENV LLVM_CONFIG=llvm-config-7 +RUN make clean && make distrib && make tests diff --git a/docs/QuickStartGuide.txt b/docs/QuickStartGuide.txt index 9190dc98..723611e3 100644 --- a/docs/QuickStartGuide.txt +++ b/docs/QuickStartGuide.txt @@ -45,6 +45,8 @@ how to hit the ground running: 7) compile and use llvm_mode (afl-clang-fast/afl-clang-fast++) as it is way faster and has a few cool features +8) There is a basic docker build with 'docker build -t aflplusplus .' + That's it. Sit back, relax, and - time permitting - try to skim through the following files: -- cgit 1.4.1 From 67ae54c957926bd382433c2a08ebba9f1dd711da Mon Sep 17 00:00:00 2001 From: David Carlier Date: Mon, 4 Nov 2019 17:15:56 +0000 Subject: Using LLVM/GCC 9 tooling --- Dockerfile | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/Dockerfile b/Dockerfile index af85ee8d..7defa8e9 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,21 +1,25 @@ -FROM gcc:8.3.0 - +FROM ubuntu:eoan RUN apt-get update && apt-get install -y --no-install-recommends \ automake \ bison \ + build-essential \ clang \ + clang-9 \ flex \ - gcc-8-plugin-dev \ - libc++-7-dev \ + gcc-9 \ + gcc-9-plugin-dev \ + libc++-9-dev \ libtool \ libtool-bin \ - llvm-7-tools \ + libglib2.0-dev \ + llvm-9-tools \ python-setuptools \ + wget \ && rm -fr /var/lib/apt/lists/* RUN mkdir /app WORKDIR ["/app"] COPY . . -ENV CC=gcc-8 -ENV CXX=g++-8 -ENV LLVM_CONFIG=llvm-config-7 +ENV CC=gcc-9 +ENV CXX=g++-9 +ENV LLVM_CONFIG=llvm-config-9 RUN make clean && make distrib && make tests -- cgit 1.4.1 From dede2e976400cec53099ab42fa3f4fa73e324d2c Mon Sep 17 00:00:00 2001 From: van Hauser Date: Tue, 5 Nov 2019 09:16:04 +0100 Subject: dockerfile additions --- Dockerfile | 4 +++- README.md | 8 ++++++++ docs/ChangeLog | 1 + 3 files changed, 12 insertions(+), 1 deletion(-) diff --git a/Dockerfile b/Dockerfile index 7defa8e9..558968d8 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,4 +1,6 @@ FROM ubuntu:eoan +MAINTAINER David Carlier +LABEL "about"="AFLplusplus docker image" RUN apt-get update && apt-get install -y --no-install-recommends \ automake \ bison \ @@ -22,4 +24,4 @@ COPY . . ENV CC=gcc-9 ENV CXX=g++-9 ENV LLVM_CONFIG=llvm-config-9 -RUN make clean && make distrib && make tests +RUN make clean && make distrib && make install diff --git a/README.md b/README.md index e8d4e6a8..583b7df8 100644 --- a/README.md +++ b/README.md @@ -115,6 +115,14 @@ afl++ binaries by passing the STATIC=1 argument to make: $ make all STATIC=1 ``` +Note that afl++ is faster and better the newer the compilers used. +Hence gcc-9 and especially llvm-9 should be the compilers of choice. +If your distribution does not have them, you can use the Dockerfile: + +```shell +$ docker build -t aflplusplus +``` + ## 1) Challenges of guided fuzzing diff --git a/docs/ChangeLog b/docs/ChangeLog index 3a5961ad..3924226e 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -23,6 +23,7 @@ Version ++2.58d (dev): - llvm_mode: float splitting is now configured via AFL_LLVM_LAF_SPLIT_FLOATS - libtokencap: support for *BSD/OSX added - libcompcov floating point splitting support for qemu and unicorn + - Dockerfile by courtesy of devnexen - ripped regex.dictionary from Google afl PR - removed unnecessary warnings -- cgit 1.4.1 From 61e46a636ccf143dc648fef6189112dfdce37933 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Tue, 5 Nov 2019 10:59:22 +0000 Subject: catching current pid before library usage in case implementations rely on those string calls --- libtokencap/libtokencap.so.c | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/libtokencap/libtokencap.so.c b/libtokencap/libtokencap.so.c index 7495180d..467be05b 100644 --- a/libtokencap/libtokencap.so.c +++ b/libtokencap/libtokencap.so.c @@ -51,6 +51,7 @@ static struct mapping { void *st, *en; } __tokencap_ro[MAX_MAPPINGS]; static u32 __tokencap_ro_cnt; static u8 __tokencap_ro_loaded; static int __tokencap_out_file = -1; +static pid_t __tokencap_pid = -1; /* Identify read-only regions in memory. Only parameters that fall into these ranges are worth dumping when passed to strcmp() and so on. Read-write @@ -115,11 +116,11 @@ static void __tokencap_load_mappings(void) { #elif defined __FreeBSD__ || defined __OpenBSD__ || defined __NetBSD__ #if defined __FreeBSD__ - int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, -1}; + int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_VMMAP, __tokencap_pid}; #elif defined __OpenBSD__ - int mib[] = {CTL_KERN, KERN_PROC_VMMAP, getpid()}; + int mib[] = {CTL_KERN, KERN_PROC_VMMAP, __tokencap_pid}; #elif defined __NetBSD__ - int mib[] = {CTL_VM, VM_PROC, VM_PROC_MAP, getpid(), sizeof(struct kinfo_vmentry)}; + int mib[] = {CTL_VM, VM_PROC, VM_PROC_MAP, __tokencap_pid, sizeof(struct kinfo_vmentry)}; #endif char *buf, *low, *high; size_t miblen = sizeof(mib)/sizeof(mib[0]); @@ -431,6 +432,7 @@ __attribute__((constructor)) void __tokencap_init(void) { u8* fn = getenv("AFL_TOKEN_FILE"); if (fn) __tokencap_out_file = open(fn, O_RDWR | O_CREAT | O_APPEND, 0655); if (__tokencap_out_file == -1) __tokencap_out_file = STDERR_FILENO; + __tokencap_pid = getpid(); } -- cgit 1.4.1 From 73cb58726649b860cbea9eef727e90ad14be4b31 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Tue, 5 Nov 2019 18:39:16 +0100 Subject: test unicorn && AFL_DISABLE_TRIM env var --- include/afl-fuzz.h | 3 ++- src/afl-fuzz-globals.c | 3 ++- src/afl-fuzz-one.c | 2 +- src/afl-fuzz.c | 3 +++ test/test.sh | 1 + unicorn_mode/samples/compcov_x64/compcov_target.bin | Bin 86 -> 86 bytes unicorn_mode/samples/compcov_x64/compcov_target.c | 4 +--- unicorn_mode/samples/compcov_x64/compcov_target.elf | Bin 5728 -> 5728 bytes 8 files changed, 10 insertions(+), 6 deletions(-) diff --git a/include/afl-fuzz.h b/include/afl-fuzz.h index 637c2795..90f3b419 100644 --- a/include/afl-fuzz.h +++ b/include/afl-fuzz.h @@ -315,7 +315,8 @@ extern u8 skip_deterministic, /* Skip deterministic stages? */ deferred_mode, /* Deferred forkserver mode? */ fixed_seed, /* do not reseed */ fast_cal, /* Try to calibrate faster? */ - uses_asan; /* Target uses ASAN? */ + uses_asan, /* Target uses ASAN? */ + disable_trim; /* Never trim in fuzz_one */ extern s32 out_fd, /* Persistent fd for out_file */ #ifndef HAVE_ARC4RANDOM diff --git a/src/afl-fuzz-globals.c b/src/afl-fuzz-globals.c index 36ba6e14..06eb06d8 100644 --- a/src/afl-fuzz-globals.c +++ b/src/afl-fuzz-globals.c @@ -122,7 +122,8 @@ u8 skip_deterministic, /* Skip deterministic stages? */ deferred_mode, /* Deferred forkserver mode? */ fixed_seed, /* do not reseed */ fast_cal, /* Try to calibrate faster? */ - uses_asan; /* Target uses ASAN? */ + uses_asan, /* Target uses ASAN? */ + disable_trim; /* Never trim in fuzz_one */ s32 out_fd, /* Persistent fd for out_file */ #ifndef HAVE_ARC4RANDOM diff --git a/src/afl-fuzz-one.c b/src/afl-fuzz-one.c index bed8d254..8ca219b5 100644 --- a/src/afl-fuzz-one.c +++ b/src/afl-fuzz-one.c @@ -449,7 +449,7 @@ u8 fuzz_one_original(char** argv) { * TRIMMING * ************/ - if (!dumb_mode && !queue_cur->trim_done && !custom_mutator) { + if (!dumb_mode && !queue_cur->trim_done && !custom_mutator && !disable_trim) { u8 res = trim_case(argv, queue_cur, in_buf); diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c index 14d7802d..26ed7b61 100644 --- a/src/afl-fuzz.c +++ b/src/afl-fuzz.c @@ -551,6 +551,9 @@ int main(int argc, char** argv) { } + if (getenv("AFL_DISABLE_TRIM")) + disable_trim = 1; + if (getenv("AFL_NO_UI") && getenv("AFL_FORCE_UI")) FATAL("AFL_NO_UI and AFL_FORCE_UI are mutually exclusive"); diff --git a/test/test.sh b/test/test.sh index f954776f..f086ee50 100755 --- a/test/test.sh +++ b/test/test.sh @@ -485,6 +485,7 @@ test -d ../unicorn_mode/unicorn && { } rm -f errors + echo -e '\xbf' > in/in $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 35 seconds" { export AFL_COMPCOV_LEVEL=2 diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.bin b/unicorn_mode/samples/compcov_x64/compcov_target.bin index 091bf1db..30eada89 100644 Binary files a/unicorn_mode/samples/compcov_x64/compcov_target.bin and b/unicorn_mode/samples/compcov_x64/compcov_target.bin differ diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.c b/unicorn_mode/samples/compcov_x64/compcov_target.c index eb1205b1..f4576261 100644 --- a/unicorn_mode/samples/compcov_x64/compcov_target.c +++ b/unicorn_mode/samples/compcov_x64/compcov_target.c @@ -16,11 +16,9 @@ int main(void) { unsigned int *data_buf = (unsigned int *) DATA_ADDRESS; - if (data_buf[0] == 0xabadcafe) { - // Cause an 'invalid read' crash if data[0..3] == '\x01\x02\x03\x04' + if (((unsigned short*)data_buf)[0] == 0xaabb) { unsigned char invalid_read = *(unsigned char *) 0x00000000; } else if (data_buf[1] == data_buf[2] + 0x4141) { - // Cause an 'invalid read' crash if (0x10 < data[0] < 0x20) and data[1] > data[2] unsigned char invalid_read = *(unsigned char *) 0x00000000; } diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.elf b/unicorn_mode/samples/compcov_x64/compcov_target.elf index 7015fb46..9f90f8d2 100755 Binary files a/unicorn_mode/samples/compcov_x64/compcov_target.elf and b/unicorn_mode/samples/compcov_x64/compcov_target.elf differ -- cgit 1.4.1 From e13fdfb2ce4d3f97c8fa4ef3adfaa93e84835e39 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Tue, 5 Nov 2019 18:41:23 +0100 Subject: reduce time for unicorn compcov test --- test/test.sh | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index f086ee50..89310389 100755 --- a/test/test.sh +++ b/test/test.sh @@ -486,10 +486,12 @@ test -d ../unicorn_mode/unicorn && { rm -f errors echo -e '\xbf' > in/in - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 35 seconds" + # This seed is close to the first byte of the comparison. + # If CompCov works, a new tuple will appear in the map => new input in queue + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 15 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V35 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V15 -U -i in -o out -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" -- cgit 1.4.1 From ed1628173717a91dbb8bd5b0498cb618da6d349c Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Tue, 5 Nov 2019 19:48:17 +0100 Subject: mmmm travis doh --- test/test.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index 89310389..a56466c4 100755 --- a/test/test.sh +++ b/test/test.sh @@ -488,10 +488,10 @@ test -d ../unicorn_mode/unicorn && { echo -e '\xbf' > in/in # This seed is close to the first byte of the comparison. # If CompCov works, a new tuple will appear in the map => new input in queue - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 15 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 30 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V15 -U -i in -o out -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V30 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" -- cgit 1.4.1 From 62d972962938fc84150768bbda448841e6c9d3e7 Mon Sep 17 00:00:00 2001 From: Andrea Fioraldi Date: Tue, 5 Nov 2019 20:06:11 +0100 Subject: travis is drunk --- test/test.sh | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/test/test.sh b/test/test.sh index a56466c4..3b071468 100755 --- a/test/test.sh +++ b/test/test.sh @@ -485,13 +485,13 @@ test -d ../unicorn_mode/unicorn && { } rm -f errors - echo -e '\xbf' > in/in + printf '\xbf' > in/in # This seed is close to the first byte of the comparison. # If CompCov works, a new tuple will appear in the map => new input in queue - $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 30 seconds" + $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 35 seconds" { export AFL_COMPCOV_LEVEL=2 - ../afl-fuzz -V30 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 + ../afl-fuzz -V35 -U -i in -o out -d -- "$PY" ../unicorn_mode/samples/compcov_x64/compcov_test_harness.py @@ >>errors 2>&1 } >>errors 2>&1 test -n "$( ls out/queue/id:000001* 2> /dev/null )" && { $ECHO "$GREEN[+] afl-fuzz is working correctly with unicorn_mode compcov" -- cgit 1.4.1 From a09cfd57a475e8e5ec9549b87938791c131ae2f5 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 31 Oct 2019 21:20:09 +0000 Subject: Unicorn mode for BSD proposal. Darwin fix --- unicorn_mode/build_unicorn_support.sh | 58 +++++++++++++++++++++++++++-------- 1 file changed, 46 insertions(+), 12 deletions(-) diff --git a/unicorn_mode/build_unicorn_support.sh b/unicorn_mode/build_unicorn_support.sh index 3bd404b8..51941cbb 100755 --- a/unicorn_mode/build_unicorn_support.sh +++ b/unicorn_mode/build_unicorn_support.sh @@ -43,9 +43,11 @@ echo echo "[*] Performing basic sanity checks..." -if [ ! "`uname -s`" = "Linux" ]; then +PLT=`uname -s` - echo "[-] Error: Unicorn instrumentation is supported only on Linux." +if [ ! "$PLT" = "Linux" ] && [ ! "$PLT" = "Darwin" ] && [ ! "$PLT" = "FreeBSD" ] && [ ! "$PLT" = "NetBSD" ] && [ ! "$PLT" = "OpenBSD" ]; then + + echo "[-] Error: Unicorn instrumentation is unsupported on $PLT." exit 1 fi @@ -64,7 +66,39 @@ if [ ! -f "../afl-showmap" ]; then fi -for i in wget python automake autoconf sha384sum; do +if [ "$PLT" = "Linux" ]; then + CKSUMCMD='sha384sum --' + PYTHONBIN=python2 + MAKECMD=make + TARCMD=tar + EASY_INSTALL=easy_install +fi + +if [ "$PLT" = "Darwin" ]; then + CKSUMCMD="shasum -a 384" + PYTHONBIN=python2.7 + MAKECMD=make + TARCMD=tar + EASY_INSTALL=easy_install-2.7 +fi + +if [ "$PLT" = "FreeBSD" ]; then + CKSUMCMD="sha384 -q" + PYTHONBIN=python2.7 + MAKECMD=gmake + TARCMD=gtar + EASY_INSTALL=easy_install-2.7 +fi + +if [ "$PLT" = "NetBSD" ] || [ "$PLT" = "OpenBSD" ]; then + CKSUMCMD="cksum -a sha384 -q" + PYTHONBIN=python2.7 + MAKECMD=gmake + TARCMD=gtar + EASY_INSTALL=easy_install-2.7 +fi + +for i in wget $PYTHONBIN automake autoconf $MAKECMD $TARCMD; do T=`which "$i" 2>/dev/null` @@ -77,10 +111,10 @@ for i in wget python automake autoconf sha384sum; do done -if ! which easy_install > /dev/null; then +if ! which $EASY_INSTALL > /dev/null; then # work around for unusual installs - if [ '!' -e /usr/lib/python2.7/dist-packages/easy_install.py ]; then + if [ '!' -e /usr/lib/python2.7/dist-packages/easy_install.py ] && [ '!' -e /usr/local/lib/python2.7/dist-packages/easy_install.py ] && [ '!' -e /usr/pkg/lib/python2.7/dist-packages/easy_install.py ]; then echo "[-] Error: Python setup-tools not found. Run 'sudo apt-get install python-setuptools'." exit 1 @@ -100,7 +134,7 @@ echo "[+] All checks passed!" ARCHIVE="`basename -- "$UNICORN_URL"`" -CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` +CKSUM=`$CKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` if [ ! "$CKSUM" = "$UNICORN_SHA384" ]; then @@ -108,7 +142,7 @@ if [ ! "$CKSUM" = "$UNICORN_SHA384" ]; then rm -f "$ARCHIVE" wget -O "$ARCHIVE" -- "$UNICORN_URL" || exit 1 - CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` + CKSUM=`CKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` fi @@ -127,7 +161,7 @@ echo "[*] Uncompressing archive (this will take a while)..." rm -rf "unicorn" || exit 1 mkdir "unicorn" || exit 1 -tar xzf "$ARCHIVE" -C ./unicorn --strip-components=1 || exit 1 +$TARCMD xzf "$ARCHIVE" -C ./unicorn --strip-components=1 || exit 1 echo "[+] Unpacking successful." @@ -149,7 +183,7 @@ echo "[+] Configuration complete." echo "[*] Attempting to build Unicorn (fingers crossed!)..." -UNICORN_QEMU_FLAGS='--python=python2' make -j `nproc` || exit 1 +UNICORN_QEMU_FLAGS="--python=$PYTHONBIN" $MAKECMD -j4 || exit 1 echo "[+] Build process successful!" @@ -157,10 +191,10 @@ echo "[*] Installing Unicorn python bindings..." cd bindings/python || exit 1 if [ -z "$VIRTUAL_ENV" ]; then echo "[*] Info: Installing python unicorn using --user" - python setup.py install --user || exit 1 + $PYTHONBIN setup.py install --user || exit 1 else echo "[*] Info: Installing python unicorn to virtualenv: $VIRTUAL_ENV" - python setup.py install || exit 1 + $PYTHONBIN setup.py install || exit 1 fi export LIBUNICORN_PATH='$(pwd)' # in theory, this allows to switch between afl-unicorn and unicorn so files. @@ -175,7 +209,7 @@ cd ../samples/simple || exit 1 # Run afl-showmap on the sample application. If anything comes out then it must have worked! unset AFL_INST_RATIO -echo 0 | ../../../afl-showmap -U -m none -q -o .test-instr0 -- python simple_test_harness.py ./sample_inputs/sample1.bin || exit 1 +echo 0 | ../../../afl-showmap -U -m none -q -o .test-instr0 -- $PYTHONBIN simple_test_harness.py ./sample_inputs/sample1.bin || exit 1 if [ -s .test-instr0 ] then -- cgit 1.4.1 From 5cb0012c836965bbf7828dcb1e3d9f31f97dc346 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 6 Nov 2019 13:08:07 +0100 Subject: test travis --- .travis.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 00d58853..9ff3edef 100644 --- a/.travis.yml +++ b/.travis.yml @@ -16,4 +16,3 @@ script: - clang -v - make distrib - make tests - - make clean -- cgit 1.4.1 From 7c99027c3165e2f411ca6caa0c119e7b69a2132c Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 6 Nov 2019 13:31:58 +0100 Subject: unicorn libcompcov testcase made easier --- unicorn_mode/samples/compcov_x64/compcov_target.bin | Bin 86 -> 86 bytes unicorn_mode/samples/compcov_x64/compcov_target.c | 4 ++-- unicorn_mode/samples/compcov_x64/compcov_target.elf | Bin 5728 -> 13200 bytes 3 files changed, 2 insertions(+), 2 deletions(-) diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.bin b/unicorn_mode/samples/compcov_x64/compcov_target.bin index 30eada89..2874860b 100644 Binary files a/unicorn_mode/samples/compcov_x64/compcov_target.bin and b/unicorn_mode/samples/compcov_x64/compcov_target.bin differ diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.c b/unicorn_mode/samples/compcov_x64/compcov_target.c index f4576261..0c863b25 100644 --- a/unicorn_mode/samples/compcov_x64/compcov_target.c +++ b/unicorn_mode/samples/compcov_x64/compcov_target.c @@ -16,9 +16,9 @@ int main(void) { unsigned int *data_buf = (unsigned int *) DATA_ADDRESS; - if (((unsigned short*)data_buf)[0] == 0xaabb) { + if (((unsigned short*)data_buf)[0] == 0x0100) { unsigned char invalid_read = *(unsigned char *) 0x00000000; - } else if (data_buf[1] == data_buf[2] + 0x4141) { + } else if (data_buf[1] == data_buf[2] + 0xfffe) { unsigned char invalid_read = *(unsigned char *) 0x00000000; } diff --git a/unicorn_mode/samples/compcov_x64/compcov_target.elf b/unicorn_mode/samples/compcov_x64/compcov_target.elf index 9f90f8d2..0f1ad916 100755 Binary files a/unicorn_mode/samples/compcov_x64/compcov_target.elf and b/unicorn_mode/samples/compcov_x64/compcov_target.elf differ -- cgit 1.4.1 From db7c990346ea9e24269358bee02d9efcbf5230cb Mon Sep 17 00:00:00 2001 From: van Hauser Date: Wed, 6 Nov 2019 13:41:23 +0100 Subject: even easier test case solving :) --- test/test.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index 3b071468..617401eb 100755 --- a/test/test.sh +++ b/test/test.sh @@ -485,7 +485,7 @@ test -d ../unicorn_mode/unicorn && { } rm -f errors - printf '\xbf' > in/in + printf '\x01\x01' > in/in # This seed is close to the first byte of the comparison. # If CompCov works, a new tuple will appear in the map => new input in queue $ECHO "$GREY[*] running afl-fuzz for unicorn_mode compcov, this will take approx 35 seconds" -- cgit 1.4.1 From cc301c18d569dac3486a0466cdf5c70ff6685bc8 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Wed, 6 Nov 2019 22:27:04 +0000 Subject: libdislocator, optional huge pages support. --- libdislocator/libdislocator.so.c | 29 ++++++++++++++++++++++++++--- 1 file changed, 26 insertions(+), 3 deletions(-) diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index 106b44f4..eb8e9de3 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -26,6 +26,10 @@ #include #include +#ifdef __APPLE__ +#include +#endif + #include "config.h" #include "types.h" @@ -37,6 +41,8 @@ #define MAP_ANONYMOUS MAP_ANON #endif /* !MAP_ANONYMOUS */ +#define SUPER_PAGE_SIZE 1<<21 + /* Error / message handling: */ #define DEBUGF(_x...) \ @@ -105,6 +111,7 @@ static __thread u32 call_depth; /* To avoid recursion via fprintf() */ static void* __dislocator_alloc(size_t len) { void* ret; + int flags, fd, sp; if (total_mem + len > max_mem || total_mem + len < total_mem) { @@ -116,11 +123,27 @@ static void* __dislocator_alloc(size_t len) { } + flags = MAP_PRIVATE | MAP_ANONYMOUS; + fd = -1; +#if defined(USEHUGEPAGE) + sp = (len >= SUPER_PAGE_SIZE && !(len % SUPER_PAGE_SIZE)); + +#if defined(__APPLE__) + if (sp) fd = VM_FLAGS_SUPERPAGE_SIZE_2MB; +#elif defined(__linux__) + if (sp) flags |= MAP_HUGETLB; +#elif defined(__FreeBSD__) + if (sp) flags |= MAP_ALIGNED_SUPER; +#endif +#else + (void)sp; +#endif + /* We will also store buffer length and a canary below the actual buffer, so let's add 8 bytes for that. */ ret = mmap(NULL, (1 + PG_COUNT(len + 8)) * PAGE_SIZE, PROT_READ | PROT_WRITE, - MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + flags, fd, 0); if (ret == MAP_FAILED) { @@ -315,11 +338,11 @@ void *aligned_alloc(size_t align, size_t len) { __attribute__((constructor)) void __dislocator_init(void) { - u8* tmp = getenv("AFL_LD_LIMIT_MB"); + u8* tmp = (u8 *)getenv("AFL_LD_LIMIT_MB"); if (tmp) { - max_mem = atoi(tmp) * 1024 * 1024; + max_mem = atoi((char *)tmp) * 1024 * 1024; if (!max_mem) FATAL("Bad value for AFL_LD_LIMIT_MB"); } -- cgit 1.4.1 From 3ce808688f793a72bcd28b31d0766fc90304c622 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 7 Nov 2019 04:56:57 +0000 Subject: Little additions from feedback --- libdislocator/Makefile | 4 ++++ libdislocator/README.dislocator.md | 2 ++ libdislocator/libdislocator.so.c | 18 +++++++++++++++++- 3 files changed, 23 insertions(+), 1 deletion(-) diff --git a/libdislocator/Makefile b/libdislocator/Makefile index 05ba26b3..216d2862 100644 --- a/libdislocator/Makefile +++ b/libdislocator/Makefile @@ -21,6 +21,10 @@ VERSION = $(shell grep '^\#define VERSION ' ../config.h | cut -d '"' -f2) CFLAGS ?= -O3 -funroll-loops -I ../include/ CFLAGS += -Wall -D_FORTIFY_SOURCE=2 -g -Wno-pointer-sign +ifdef USEHUGEPAGE + CFLAGS += -DUSEHUGEPAGE +endif + all: libdislocator.so libdislocator.so: libdislocator.so.c ../config.h diff --git a/libdislocator/README.dislocator.md b/libdislocator/README.dislocator.md index 5d5a1464..77626901 100644 --- a/libdislocator/README.dislocator.md +++ b/libdislocator/README.dislocator.md @@ -25,6 +25,8 @@ heap-related security bugs in several ways: - It checks for calloc() overflows and can cause soft or hard failures of alloc requests past a configurable memory limit (AFL_LD_LIMIT_MB, AFL_LD_HARD_FAIL). + - Optionally, in platforms supporting it, huge pages can be used by passing + USEHUGEPAGE=1 to make. Basically, it is inspired by some of the non-default options available for the OpenBSD allocator - see malloc.conf(5) on that platform for reference. It is diff --git a/libdislocator/libdislocator.so.c b/libdislocator/libdislocator.so.c index eb8e9de3..0268cc52 100644 --- a/libdislocator/libdislocator.so.c +++ b/libdislocator/libdislocator.so.c @@ -111,6 +111,7 @@ static __thread u32 call_depth; /* To avoid recursion via fprintf() */ static void* __dislocator_alloc(size_t len) { void* ret; + size_t tlen; int flags, fd, sp; if (total_mem + len > max_mem || total_mem + len < total_mem) { @@ -123,6 +124,7 @@ static void* __dislocator_alloc(size_t len) { } + tlen = (1 + PG_COUNT(len + 8)) * PAGE_SIZE; flags = MAP_PRIVATE | MAP_ANONYMOUS; fd = -1; #if defined(USEHUGEPAGE) @@ -142,8 +144,22 @@ static void* __dislocator_alloc(size_t len) { /* We will also store buffer length and a canary below the actual buffer, so let's add 8 bytes for that. */ - ret = mmap(NULL, (1 + PG_COUNT(len + 8)) * PAGE_SIZE, PROT_READ | PROT_WRITE, + ret = mmap(NULL, tlen, PROT_READ | PROT_WRITE, flags, fd, 0); +#if defined(USEHUGEPAGE) + /* We try one more time with regular call */ + if (ret == MAP_FAILED) { +#if defined(__APPLE__) + fd = -1; +#elif defined(__linux__) + flags &= -MAP_HUGETLB; +#elif defined(__FreeBSD__) + flags &= -MAP_ALIGNED_SUPER; +#endif + ret = mmap(NULL, tlen, PROT_READ | PROT_WRITE, + flags, fd, 0); + } +#endif if (ret == MAP_FAILED) { -- cgit 1.4.1 From 92669e65ee7bfb588134b29e569858ba91408140 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 7 Nov 2019 10:38:16 +0100 Subject: we only do one vm for the testing. having 3 just gives headache --- .travis.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 9ff3edef..4569bd9c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,9 +3,9 @@ language: c env: - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_STOP_MANUALLY=1 - - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_EXIT_WHEN_DONE=1 + # - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_EXIT_WHEN_DONE=1 # TODO: test AFL_BENCH_UNTIL_CRASH once we have a target that crashes - - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_BENCH_JUST_ONE=1 + # - AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1 AFL_NO_UI=1 AFL_BENCH_JUST_ONE=1 before_install: - sudo apt update -- cgit 1.4.1 From 499f078c3759a22dd5cfd81d2271969f19b75090 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Thu, 7 Nov 2019 11:48:39 +0100 Subject: f*ckin travis --- docs/ChangeLog | 2 ++ qemu_mode/build_qemu_support.sh | 5 ++++- unicorn_mode/build_unicorn_support.sh | 5 ++++- 3 files changed, 10 insertions(+), 2 deletions(-) diff --git a/docs/ChangeLog b/docs/ChangeLog index 3924226e..7bc6dec4 100644 --- a/docs/ChangeLog +++ b/docs/ChangeLog @@ -25,6 +25,8 @@ Version ++2.58d (dev): - libcompcov floating point splitting support for qemu and unicorn - Dockerfile by courtesy of devnexen - ripped regex.dictionary from Google afl PR + - qemu and unicorn download scripts now try to download until the full + download succeeded. f*ckin travis fails downloading 40% of the time! - removed unnecessary warnings diff --git a/qemu_mode/build_qemu_support.sh b/qemu_mode/build_qemu_support.sh index 6b9f91f9..c3983aa1 100755 --- a/qemu_mode/build_qemu_support.sh +++ b/qemu_mode/build_qemu_support.sh @@ -100,7 +100,10 @@ if [ ! "$CKSUM" = "$QEMU_SHA384" ]; then echo "[*] Downloading QEMU ${VERSION} from the web..." rm -f "$ARCHIVE" - wget -O "$ARCHIVE" -- "$QEMU_URL" || exit 1 + OK= + while [ -z "$OK" ]; do + wget -c -O "$ARCHIVE" -- "$QEMU_URL" && OK=1 + done CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` diff --git a/unicorn_mode/build_unicorn_support.sh b/unicorn_mode/build_unicorn_support.sh index 3bd404b8..fdbcda62 100755 --- a/unicorn_mode/build_unicorn_support.sh +++ b/unicorn_mode/build_unicorn_support.sh @@ -106,7 +106,10 @@ if [ ! "$CKSUM" = "$UNICORN_SHA384" ]; then echo "[*] Downloading Unicorn v1.0.1 from the web..." rm -f "$ARCHIVE" - wget -O "$ARCHIVE" -- "$UNICORN_URL" || exit 1 + OK= + while [ -z "$OK" ]; do + wget -c -O "$ARCHIVE" -- "$UNICORN_URL" && OK=1 + done CKSUM=`sha384sum -- "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` -- cgit 1.4.1 From f6c44a83bcb63c3cfebe9d117835e8544eb0e7df Mon Sep 17 00:00:00 2001 From: David Carlier Date: Thu, 7 Nov 2019 15:06:48 +0000 Subject: typo for the checksum --- unicorn_mode/build_unicorn_support.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/unicorn_mode/build_unicorn_support.sh b/unicorn_mode/build_unicorn_support.sh index 885329bb..589ab852 100755 --- a/unicorn_mode/build_unicorn_support.sh +++ b/unicorn_mode/build_unicorn_support.sh @@ -149,7 +149,7 @@ if [ ! "$CKSUM" = "$UNICORN_SHA384" ]; then wget -c -O "$ARCHIVE" -- "$UNICORN_URL" && OK=1 done - CKSUM=`CKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` + CKSUM=`$CKSUMCMD "$ARCHIVE" 2>/dev/null | cut -d' ' -f1` fi -- cgit 1.4.1 From a3932d7f002b840887475482934d93ae3efdad5b Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 8 Nov 2019 04:39:22 +0100 Subject: raise limit for free core detection on FreeBSD and dragonFlyBSD --- src/afl-fuzz-init.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c index 64b24087..82ba6f8a 100644 --- a/src/afl-fuzz-init.c +++ b/src/afl-fuzz-init.c @@ -139,10 +139,10 @@ void bind_to_free_cpu(void) { for (i = 0; i < proccount; i++) { #if defined(__FreeBSD__) - if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 2) + if (procs[i].ki_oncpu < sizeof(cpu_used) && procs[i].ki_pctcpu > 10) cpu_used[procs[i].ki_oncpu] = 1; #elif defined(__DragonFly__) - if (procs[i].kp_lwp.kl_cpuid < sizeof(cpu_used) && procs[i].kp_lwp.kl_pctcpu > 2) + if (procs[i].kp_lwp.kl_cpuid < sizeof(cpu_used) && procs[i].kp_lwp.kl_pctcpu > 10) cpu_used[procs[i].kp_lwp.kl_cpuid] = 1; #endif -- cgit 1.4.1 From 8290bb337451e06e71af2f1a1e3dc241a10b8652 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Fri, 8 Nov 2019 13:46:08 +0000 Subject: test, /sbin not necessarily in the path os casual users. --- test/test.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/test.sh b/test/test.sh index 617401eb..679a514e 100755 --- a/test/test.sh +++ b/test/test.sh @@ -99,7 +99,7 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { } # now we want to be sure that afl-fuzz is working # make sure core_pattern is set to core on linux - (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { + (test "$(uname -s)" = "Linux" && test "$(/sbin/sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || @@ -169,7 +169,7 @@ test -e ../afl-clang-fast && { CODE=1 } # now we want to be sure that afl-fuzz is working - (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { + (test "$(uname -s)" = "Linux" && test "$(/sbin/sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || -- cgit 1.4.1 From 7a20cc2f58d2709a6b26c98bb6a931dfe5e186b6 Mon Sep 17 00:00:00 2001 From: hexcoder- Date: Fri, 8 Nov 2019 19:27:25 +0100 Subject: additional test, if afl-as is called by afl-gcc/afl-clang (seen in OpenIndiana) --- Makefile | 4 +++- src/afl-as.c | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/Makefile b/Makefile index c4269d6b..4d77b6cf 100644 --- a/Makefile +++ b/Makefile @@ -131,6 +131,8 @@ help: ifndef AFL_NO_X86 test_x86: + @echo "[*] Checking for the default compiler cc..." + @which $(CC) >/dev/null || ( echo; echo "Oops, looks like there is no compiler '"$(CC)"' in your path."; echo; echo "Don't panic! You can restart with '"$(_)" CC='."; echo; exit 1 ) @echo "[*] Checking for the ability to compile x86 code..." @echo 'main() { __asm__("xorb %al, %al"); }' | $(CC) -w -x c - -o .test1 || ( echo; echo "Oops, looks like your compiler can't generate x86 code."; echo; echo "Don't panic! You can use the LLVM or QEMU mode, but see docs/INSTALL first."; echo "(To ignore this error, set AFL_NO_X86=1 and try again.)"; echo; exit 1 ) @rm -f .test1 @@ -236,7 +238,7 @@ ifndef AFL_NO_X86 test_build: afl-gcc afl-as afl-showmap @echo "[*] Testing the CC wrapper and instrumentation output..." - unset AFL_USE_ASAN AFL_USE_MSAN AFL_CC; AFL_QUIET=1 AFL_INST_RATIO=100 AFL_PATH=. ./$(TEST_CC) $(CFLAGS) test-instr.c -o test-instr $(LDFLAGS) + @unset AFL_USE_ASAN AFL_USE_MSAN AFL_CC; AFL_INST_RATIO=100 AFL_PATH=. ./$(TEST_CC) $(CFLAGS) test-instr.c -o test-instr $(LDFLAGS) 2>&1 | grep 'afl-as' >/dev/null || (echo "Oops, afl-as did not get called from "$(TEST_CC)". This is normally achieved by "$(CC)" honoring the -B option."; exit 1 ) ./afl-showmap -m none -q -o .test-instr0 ./test-instr < /dev/null echo 1 | ./afl-showmap -m none -q -o .test-instr1 ./test-instr @rm -f test-instr diff --git a/src/afl-as.c b/src/afl-as.c index 2b023432..312ae0a7 100644 --- a/src/afl-as.c +++ b/src/afl-as.c @@ -499,7 +499,7 @@ int main(int argc, char** argv) { clang_mode = !!getenv(CLANG_ENV_VAR); - if (isatty(2) && !getenv("AFL_QUIET")) { + if (!getenv("AFL_QUIET")) { SAYF(cCYA "afl-as" VERSION cRST " by Michal Zalewski\n"); -- cgit 1.4.1 From b22145d0c4d81651f25d912bb7ea5f7fed958873 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Sat, 9 Nov 2019 10:37:44 +0000 Subject: gcc plugin llittle update proposal to match better LLVM's --- gcc_plugin/afl-gcc-pass.so.cc | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/gcc_plugin/afl-gcc-pass.so.cc b/gcc_plugin/afl-gcc-pass.so.cc index 84e02cb8..0fa07774 100644 --- a/gcc_plugin/afl-gcc-pass.so.cc +++ b/gcc_plugin/afl-gcc-pass.so.cc @@ -401,11 +401,13 @@ class afl_pass : public gimple_opt_pass { } - virtual unsigned int execute(function *fun) { + unsigned int execute(function *fun) override { if (!myWhitelist.empty()) { bool instrumentBlock = false; + std::string instFilename; + unsigned int instLine = 0; /* EXPR_FILENAME This macro returns the name of the file in which the entity was declared, @@ -417,7 +419,8 @@ class afl_pass : public gimple_opt_pass { if (0 != strncmp("", fname, 10) && 0 != strncmp("", fname, 10)) { - std::string instFilename(fname); + instFilename = fname; + instLine = DECL_SOURCE_LINE(fun->decl); /* Continue only if we know where we actually are */ if (!instFilename.empty()) { @@ -449,7 +452,17 @@ class afl_pass : public gimple_opt_pass { /* Either we couldn't figure out our location or the location is * not whitelisted, so we skip instrumentation. */ - if (!instrumentBlock) return 0; + if (!instrumentBlock) { + + if (!be_quiet) { + if (!instFilename.empty()) + SAYF(cYEL "[!] " cBRI "Not in whitelist, skipping %s line %u...\n", + instFilename.c_str(), instLine); + else + SAYF(cYEL "[!] " cBRI "No filename information found, skipping it"); + } + return 0; + } } -- cgit 1.4.1 From 58a18ea50bb5e73ce43e73151bdaa893fb7e2e84 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Sat, 9 Nov 2019 15:23:16 +0100 Subject: not all sysctl are in /sbin, e.g. with busybox --- test/test.sh | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index 679a514e..98482d05 100755 --- a/test/test.sh +++ b/test/test.sh @@ -64,6 +64,8 @@ RESET="\\033[0m" MEM_LIMIT=150 +export PATH=$PATH:/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/sbin:/usr/local/bin + $ECHO "${RESET}${GREY}[*] starting afl++ test framework ..." $ECHO "$BLUE[*] Testing: ${AFL_GCC}, afl-showmap and afl-fuzz" @@ -99,7 +101,7 @@ test -e ../${AFL_GCC} -a -e ../afl-showmap -a -e ../afl-fuzz && { } # now we want to be sure that afl-fuzz is working # make sure core_pattern is set to core on linux - (test "$(uname -s)" = "Linux" && test "$(/sbin/sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { + (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || -- cgit 1.4.1 From 01d55372441960c435af8f3bd6b61d1302042728 Mon Sep 17 00:00:00 2001 From: van Hauser Date: Sat, 9 Nov 2019 16:48:01 +0100 Subject: /sbin in path --- test/test.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/test.sh b/test/test.sh index 98482d05..781313a7 100755 --- a/test/test.sh +++ b/test/test.sh @@ -171,7 +171,7 @@ test -e ../afl-clang-fast && { CODE=1 } # now we want to be sure that afl-fuzz is working - (test "$(uname -s)" = "Linux" && test "$(/sbin/sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { + (test "$(uname -s)" = "Linux" && test "$(sysctl kernel.core_pattern)" != "kernel.core_pattern = core" && { $ECHO "$YELLOW[!] we should not run afl-fuzz with enabled core dumps. Run 'sudo sh afl-system-config'.$RESET" true }) || -- cgit 1.4.1