From 8c228b0d23e303499dccf3df77c5d0b3a8b59b7b Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Mon, 24 Apr 2023 18:08:27 +0200
Subject: afl-showmap -I option
---
src/afl-showmap.c | 175 +++++++++++++++++++++++++++++++++++++++++++++++-------
1 file changed, 154 insertions(+), 21 deletions(-)
(limited to 'src')
diff --git a/src/afl-showmap.c b/src/afl-showmap.c
index 0b9fc211..09a1d2dc 100644
--- a/src/afl-showmap.c
+++ b/src/afl-showmap.c
@@ -69,7 +69,9 @@ static afl_state_t *afl;
static char *stdin_file; /* stdin file */
static u8 *in_dir = NULL, /* input folder */
- *out_file = NULL, *at_file = NULL; /* Substitution string for @@ */
+ *out_file = NULL, /* output file or directory */
+ *at_file = NULL, /* Substitution string for @@ */
+ *in_filelist = NULL; /* input file list */
static u8 outfile[PATH_MAX];
@@ -878,6 +880,104 @@ u32 execute_testcases(u8 *dir) {
}
+u32 execute_testcases_filelist(u8 *fn) {
+
+ u32 done = 0;
+ u8 buf[4096];
+ u8 val_buf[2][STRINGIFY_VAL_SIZE_MAX];
+ FILE *f;
+
+ if (!be_quiet) { ACTF("Reading from '%s'...", fn); }
+
+ if ((f = fopen(fn, "r")) == NULL) { FATAL("could not open '%s'", fn); }
+
+ while (fgets(buf, sizeof(buf), f) != NULL) {
+
+ struct stat st;
+
+ u8 *fn2 = buf, *fn3;
+ ;
+
+ while (*fn2 == ' ') {
+
+ ++fn2;
+
+ }
+
+ if (*fn2) {
+
+ while (fn2[strlen(fn2) - 1] == '\r' || fn2[strlen(fn2) - 1] == '\n' ||
+ fn2[strlen(fn2) - 1] == ' ') {
+
+ fn2[strlen(fn2) - 1] = 0;
+
+ }
+
+ }
+
+ if (debug) { printf("Getting coverage for '%s'\n", fn2); }
+
+ if (!*fn2) { continue; }
+
+ if (lstat(fn2, &st) || access(fn2, R_OK)) {
+
+ WARNF("Unable to access '%s'", fn2);
+ continue;
+
+ }
+
+ if (!S_ISREG(st.st_mode) || !st.st_size) { continue; }
+
+ if ((fn3 = strrchr(fn2, '/'))) {
+
+ ++fn3;
+
+ } else {
+
+ fn3 = fn2;
+
+ }
+
+ if (st.st_size > MAX_FILE && !be_quiet && !quiet_mode) {
+
+ WARNF("Test case '%s' is too big (%s, limit is %s), partial reading", fn2,
+ stringify_mem_size(val_buf[0], sizeof(val_buf[0]), st.st_size),
+ stringify_mem_size(val_buf[1], sizeof(val_buf[1]), MAX_FILE));
+
+ }
+
+ if (!collect_coverage)
+ snprintf(outfile, sizeof(outfile), "%s/%s", out_file, fn3);
+
+ if (read_file(fn2)) {
+
+ if (wait_for_gdb) {
+
+ fprintf(stderr, "exec: gdb -p %d\n", fsrv->child_pid);
+ fprintf(stderr, "exec: kill -CONT %d\n", getpid());
+ kill(0, SIGSTOP);
+
+ }
+
+ showmap_run_target_forkserver(fsrv, in_data, in_len);
+ ck_free(in_data);
+ ++done;
+
+ if (child_crashed && debug) { WARNF("crashed: %s", fn2); }
+
+ if (collect_coverage)
+ analyze_results(fsrv);
+ else
+ tcnt = write_results_to_file(fsrv, outfile);
+
+ }
+
+ }
+
+ return done;
+
+}
+
/* Show banner. */
static void show_banner(void) {
@@ -920,6 +1020,7 @@ static void usage(u8 *argv0) {
" With -C, -o is a file, without -C it must be a "
"directory\n"
" and each bitmap will be written there individually.\n"
+ " -I filelist - alternatively to -i, -I is a list of files\n"
" -C - collect coverage, writes all edges to -o and gives a "
"summary\n"
" Must be combined with -i.\n"
@@ -932,7 +1033,7 @@ static void usage(u8 *argv0) {
"This tool displays raw tuple data captured by AFL instrumentation.\n"
"For additional help, consult %s/README.md.\n\n"
- "If you use -i mode, then custom mutator post_process send send "
+ "If you use -i/-I mode, then custom mutator post_process send send "
"functionality\n"
"is supported.\n\n"
@@ -994,7 +1095,7 @@ int main(int argc, char **argv_orig, char **envp) {
if (getenv("AFL_QUIET") != NULL) { be_quiet = true; }
- while ((opt = getopt(argc, argv, "+i:o:f:m:t:AeqCZOH:QUWbcrshXY")) > 0) {
+ while ((opt = getopt(argc, argv, "+i:I:o:f:m:t:AeqCZOH:QUWbcrshXY")) > 0) {
switch (opt) {
@@ -1012,6 +1113,11 @@ int main(int argc, char **argv_orig, char **envp) {
in_dir = optarg;
break;
+ case 'I':
+ if (in_filelist) { FATAL("Multiple -I options not supported"); }
+ in_filelist = optarg;
+ break;
+
case 'o':
if (out_file) { FATAL("Multiple -o options not supported"); }
@@ -1234,10 +1340,12 @@ int main(int argc, char **argv_orig, char **envp) {
if (optind == argc || !out_file) { usage(argv[0]); }
- if (in_dir) {
+ if (in_dir && in_filelist) { FATAL("you can only specify either -i or -I"); }
+
+ if (in_dir || in_filelist) {
if (!out_file && !collect_coverage)
- FATAL("for -i you need to specify either -C and/or -o");
+ FATAL("for -i/-I you need to specify either -C and/or -o");
}
@@ -1294,7 +1402,7 @@ int main(int argc, char **argv_orig, char **envp) {
}
- if (in_dir) {
+ if (in_dir || in_filelist) {
/* If we don't have a file name chosen yet, use a safe default. */
u8 *use_dir = ".";
@@ -1400,7 +1508,7 @@ int main(int argc, char **argv_orig, char **envp) {
}
#ifdef __linux__
- if (!fsrv->nyx_mode && in_dir) {
+ if (!fsrv->nyx_mode && (in_dir || in_filelist)) {
(void)check_binary_signatures(fsrv->target_path);
@@ -1483,7 +1591,7 @@ int main(int argc, char **argv_orig, char **envp) {
}
- if (in_dir) {
+ if (in_dir || in_filelist) {
afl->fsrv.dev_urandom_fd = open("/dev/urandom", O_RDONLY);
afl->afl_env.afl_custom_mutator_library =
@@ -1496,33 +1604,46 @@ int main(int argc, char **argv_orig, char **envp) {
if (getenv("AFL_CUSTOM_MUTATOR_LIBRARY") || getenv("AFL_PYTHON_MODULE")) {
WARNF(
- "Custom mutator environment detected, this is only supported in -i "
- "mode!\n");
+ "Custom mutator environment detected, this is only supported in "
+ "-i/-I mode!\n");
}
}
- if (in_dir) {
+ if (in_dir || in_filelist) {
DIR *dir_in, *dir_out = NULL;
+ u8 *dn = NULL;
if (getenv("AFL_DEBUG_GDB")) wait_for_gdb = true;
fsrv->dev_null_fd = open("/dev/null", O_RDWR);
if (fsrv->dev_null_fd < 0) { PFATAL("Unable to open /dev/null"); }
- // if a queue subdirectory exists switch to that
- u8 *dn = alloc_printf("%s/queue", in_dir);
- if ((dir_in = opendir(dn)) != NULL) {
+ if (in_filelist) {
+
+ if (!be_quiet) ACTF("Reading from file list '%s'...", in_filelist);
+
+ } else {
+
+ // if a queue subdirectory exists switch to that
+ dn = alloc_printf("%s/queue", in_dir);
+
+ if ((dir_in = opendir(dn)) != NULL) {
+
+ closedir(dir_in);
+ in_dir = dn;
+
+ } else {
+
+ ck_free(dn);
- closedir(dir_in);
- in_dir = dn;
+ }
- } else
+ if (!be_quiet) ACTF("Reading from directory '%s'...", in_dir);
- ck_free(dn);
- if (!be_quiet) ACTF("Reading from directory '%s'...", in_dir);
+ }
if (!collect_coverage) {
@@ -1576,9 +1697,21 @@ int main(int argc, char **argv_orig, char **envp) {
if (fsrv->support_shmem_fuzz && !fsrv->use_shmem_fuzz)
shm_fuzz = deinit_shmem(fsrv, shm_fuzz);
- if (execute_testcases(in_dir) == 0) {
+ if (in_dir) {
+
+ if (execute_testcases(in_dir) == 0) {
+
+ FATAL("could not read input testcases from %s", in_dir);
+
+ }
+
+ } else {
- FATAL("could not read input testcases from %s", in_dir);
+ if (execute_testcases_filelist(in_filelist) == 0) {
+
+ FATAL("could not read input testcases from %s", in_filelist);
+
+ }
}
--
cgit 1.4.1
From 7c3c0b26d1ae477fbae6944c0de18256621e1993 Mon Sep 17 00:00:00 2001
From: Keno Hassler <40292329+kenohassler@users.noreply.github.com>
Date: Mon, 24 Apr 2023 20:21:54 +0200
Subject: document new env var
---
docs/env_variables.md | 6 ++++--
src/afl-cc.c | 2 ++
2 files changed, 6 insertions(+), 2 deletions(-)
(limited to 'src')
diff --git a/docs/env_variables.md b/docs/env_variables.md
index c5995d13..087ccdb7 100644
--- a/docs/env_variables.md
+++ b/docs/env_variables.md
@@ -156,7 +156,7 @@ Available options:
- LTO - LTO instrumentation
- NATIVE - clang's original pcguard based instrumentation
- NGRAM-x - deeper previous location coverage (from NGRAM-2 up to NGRAM-16)
- - PCGUARD - our own pcgard based instrumentation (default)
+ - PCGUARD - our own pcguard based instrumentation (default)
#### CMPLOG
@@ -240,7 +240,9 @@ combined.
the default `0x10000`. A value of 0 or empty sets the map address to be
dynamic (the original AFL way, which is slower).
- `AFL_LLVM_MAP_DYNAMIC` sets the shared memory address to be dynamic.
-
+ - `AFL_LLVM_LTO_SKIPINIT` skips adding initialization code. Some global vars
+ (e.g. the highest location ID) are not injected. Needed to instrument with
+ [WAFL](https://github.com/fgsect/WAFL.git).
For more information, see
[instrumentation/README.lto.md](../instrumentation/README.lto.md).
diff --git a/src/afl-cc.c b/src/afl-cc.c
index 7f15ad76..d1001187 100644
--- a/src/afl-cc.c
+++ b/src/afl-cc.c
@@ -2099,6 +2099,8 @@ int main(int argc, char **argv, char **envp) {
"bb\n"
" AFL_REAL_LD: use this lld linker instead of the compiled in "
"path\n"
+ " AFL_LLVM_LTO_SKIPINIT: don't inject initialization code "
+ "(used in WAFL mode)\n"
"If anything fails - be sure to read README.lto.md!\n");
#endif
--
cgit 1.4.1
From c0ecf7cf61fdca901b041d57e7e2bb78bc8fcf80 Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Tue, 25 Apr 2023 08:33:51 +0200
Subject: only reverse reading the queue on restart
---
docs/Changelog.md | 4 ++++
src/afl-fuzz-init.c | 30 ++++++++++++++++++++----------
2 files changed, 24 insertions(+), 10 deletions(-)
(limited to 'src')
diff --git a/docs/Changelog.md b/docs/Changelog.md
index d4e68036..14323ae0 100644
--- a/docs/Changelog.md
+++ b/docs/Changelog.md
@@ -7,6 +7,10 @@
- afl-fuzz:
- new env `AFL_POST_PROCESS_KEEP_ORIGINAL` to keep the orignal
data before post process on finds
+ - reverse reading the seeds only on restarts
+ - afl-cc:
+ - new env `AFL_LLVM_LTO_SKIPINIT` to support the AFL++ based WASM
+ (https://github.com/fgsect/WAFL) project
- afl-showmap:
- added custom mutator post_process and send support
- add `-I filelist` option, an alternative to `-i in_dir`
diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c
index 01d1e82e..002a26f8 100644
--- a/src/afl-fuzz-init.c
+++ b/src/afl-fuzz-init.c
@@ -718,10 +718,21 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
if (nl_cnt) {
- i = nl_cnt;
+ u32 done = 0;
+
+ if (unlikely(afl->in_place_resume)) {
+
+ i = nl_cnt;
+
+ } else {
+
+ i = 0;
+
+ }
+
do {
- --i;
+ if (unlikely(afl->in_place_resume)) { --i; }
struct stat st;
u8 dfn[PATH_MAX];
@@ -801,18 +812,17 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
}
- /*
- if (unlikely(afl->schedule >= FAST && afl->schedule <= RARE)) {
+ if (unlikely(afl->in_place_resume)) {
- u64 cksum = hash64(afl->fsrv.trace_bits, afl->fsrv.map_size,
- HASH_CONST); afl->queue_top->n_fuzz_entry = cksum % N_FUZZ_SIZE;
- afl->n_fuzz[afl->queue_top->n_fuzz_entry] = 1;
+ if (unlikely(i == 0)) { done = 1; }
- }
+ } else {
+
+ if (unlikely(++i == (u32)nl_cnt)) { done = 1; }
- */
+ }
- } while (i > 0);
+ } while (!done);
}
--
cgit 1.4.1
From bc969f78f634035abf88bc73a5076848660901e7 Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Tue, 25 Apr 2023 11:56:50 +0200
Subject: fixes
---
afl-cmin.bash | 9 +++++++--
src/afl-fuzz-init.c | 7 ++++---
2 files changed, 11 insertions(+), 5 deletions(-)
(limited to 'src')
diff --git a/afl-cmin.bash b/afl-cmin.bash
index ba7083fa..0e2d973d 100755
--- a/afl-cmin.bash
+++ b/afl-cmin.bash
@@ -316,12 +316,16 @@ if [ ! "$T_ARG" = "" ]; then
if [ "$T_ARG" = "all" ]; then
THREADS=$(nproc)
else
- if [ "$T_ARG" -gt 0 -a "$T_ARG" -le "$(nproc)" ]; then
+ if [ "$T_ARG" -gt 1 -a "$T_ARG" -le "$(nproc)" ]; then
THREADS=$T_ARG
else
- echo "[-] Error: -T parameter must between 1 and $(nproc) or \"all\"." 1>&2
+ echo "[-] Error: -T parameter must between 2 and $(nproc) or \"all\"." 1>&2
fi
fi
+else
+ if [ "$F_ARG" = ""]; then
+ echo "[*] Are you aware of the '-T all' parallelize option that massively improves the speed?"
+ fi
fi
IN_COUNT=$((`ls -- "$IN_DIR" 2>/dev/null | wc -l`))
@@ -332,6 +336,7 @@ if [ "$IN_COUNT" = "0" ]; then
exit 1
fi
+echo "[*] Are you aware that afl-cmin is faster than this afl-cmin.bash script?"
echo "[+] Found $IN_COUNT files for minimizing."
FIRST_FILE=`ls "$IN_DIR" | head -1`
diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c
index 002a26f8..bd591c8f 100644
--- a/src/afl-fuzz-init.c
+++ b/src/afl-fuzz-init.c
@@ -756,7 +756,7 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
free(nl[i]); /* not tracked */
read_testcases(afl, fn2);
ck_free(fn2);
- continue;
+ goto next_entry;
}
@@ -765,7 +765,7 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
if (!S_ISREG(st.st_mode) || !st.st_size || strstr(fn2, "/README.txt")) {
ck_free(fn2);
- continue;
+ goto next_entry;
}
@@ -812,13 +812,14 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
}
+ next_entry:
if (unlikely(afl->in_place_resume)) {
if (unlikely(i == 0)) { done = 1; }
} else {
- if (unlikely(++i == (u32)nl_cnt)) { done = 1; }
+ if (unlikely(++i >= (u32)nl_cnt)) { done = 1; }
}
--
cgit 1.4.1
From d822181467ec41f1ee2d840c3c5b1918c72ffc86 Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Tue, 25 Apr 2023 13:13:43 +0200
Subject: afl-cmin -T support
---
afl-cmin | 143 ++++++++++++++++++++++++++++++++++++++++++------------
docs/Changelog.md | 2 +-
src/afl-showmap.c | 23 +++++----
3 files changed, 124 insertions(+), 44 deletions(-)
(limited to 'src')
diff --git a/afl-cmin b/afl-cmin
index 6b36c261..c8bbd8d7 100755
--- a/afl-cmin
+++ b/afl-cmin
@@ -103,9 +103,10 @@ function usage() {
" -o dir - output directory for minimized files\n" \
"\n" \
"Execution control settings:\n" \
+" -T tasks - how many parallel tasks to run (default: 1, all=nproc)\n" \
" -f file - location read by the fuzzed program (stdin)\n" \
" -m megs - memory limit for child process ("mem_limit" MB)\n" \
-" -t msec - run time limit for child process (default: none)\n" \
+" -t msec - run time limit for child process (default: 5000)\n" \
" -O - use binary-only instrumentation (FRIDA mode)\n" \
" -Q - use binary-only instrumentation (QEMU mode)\n" \
" -U - use unicorn-based instrumentation (unicorn mode)\n" \
@@ -119,7 +120,6 @@ function usage() {
"For additional tips, please consult README.md\n" \
"\n" \
"Environment variables used:\n" \
-"AFL_ALLOW_TMP: allow unsafe use of input/output directories under {/var}/tmp\n" \
"AFL_CRASH_EXITCODE: optional child exit code to be interpreted as crash\n" \
"AFL_FORKSRV_INIT_TMOUT: time the fuzzer waits for the forkserver to come up\n" \
"AFL_KEEP_TRACES: leave the temporary /.traces directory\n" \
@@ -159,13 +159,19 @@ BEGIN {
# process options
Opterr = 1 # default is to diagnose
Optind = 1 # skip ARGV[0]
- while ((_go_c = getopt(ARGC, ARGV, "hi:o:f:m:t:eACOQUXY?")) != -1) {
+ while ((_go_c = getopt(ARGC, ARGV, "hi:o:f:m:t:eACOQUXYT:?")) != -1) {
if (_go_c == "i") {
if (!Optarg) usage()
if (in_dir) { print "Option "_go_c" is only allowed once" > "/dev/stderr"}
in_dir = Optarg
continue
} else
+ if (_go_c == "T") {
+ if (!Optarg) usage()
+ if (threads) { print "Option "_go_c" is only allowed once" > "/dev/stderr"}
+ threads = Optarg
+ continue
+ } else
if (_go_c == "o") {
if (!Optarg) usage()
if (out_dir) { print "Option "_go_c" is only allowed once" > "/dev/stderr"}
@@ -253,21 +259,30 @@ BEGIN {
# Do a sanity check to discourage the use of /tmp, since we can't really
# handle this safely from an awk script.
- if (!ENVIRON["AFL_ALLOW_TMP"]) {
- dirlist[0] = in_dir
- dirlist[1] = target_bin
- dirlist[2] = out_dir
- dirlist[3] = stdin_file
- "pwd" | getline dirlist[4] # current directory
- for (dirind in dirlist) {
- dir = dirlist[dirind]
-
- if (dir ~ /^(\/var)?\/tmp/) {
- print "[-] Error: do not use this script in /tmp or /var/tmp." > "/dev/stderr"
- exit 1
- }
- }
- delete dirlist
+ #if (!ENVIRON["AFL_ALLOW_TMP"]) {
+ # dirlist[0] = in_dir
+ # dirlist[1] = target_bin
+ # dirlist[2] = out_dir
+ # dirlist[3] = stdin_file
+ # "pwd" | getline dirlist[4] # current directory
+ # for (dirind in dirlist) {
+ # dir = dirlist[dirind]
+ #
+ # if (dir ~ /^(\/var)?\/tmp/) {
+ # print "[-] Error: do not use this script in /tmp or /var/tmp." > "/dev/stderr"
+ # exit 1
+ # }
+ # }
+ # delete dirlist
+ #}
+
+ if (threads && stdin_file) {
+ print "[-] Error: -T and -f cannot be used together." > "/dev/stderr"
+ exit 1
+ }
+
+ if (!threads && !stdin_file) {
+ print "[*] Are you aware of the '-T all' parallelize option that massively improves the speed for large corpuses?"
}
# If @@ is specified, but there's no -f, let's come up with a temporary input
@@ -350,6 +365,18 @@ BEGIN {
exit 1
}
+ if (threads) {
+ "nproc" | getline nproc
+ if (threads == "all") {
+ threads = nproc
+ } else {
+ if (!(threads > 1 && threads <= nproc)) {
+ print "[-] Error: -T option must be between 1 and "nproc" or \"all\"." > "/dev/stderr"
+ exit 1
+ }
+ }
+ }
+
# Check for the more efficient way to copy files...
if (0 != system("mkdir -p -m 0700 "trace_dir)) {
print "[-] Error: Cannot create directory "trace_dir > "/dev/stderr"
@@ -459,27 +486,81 @@ BEGIN {
# STEP 1: Collecting traces #
#############################
+ if (threads) {
+
+ inputsperfile = in_count / threads
+ if (in_count % threads) {
+ inputsperfile++;
+ }
+
+ cnt = 0;
+ tmpfile=out_dir "/.filelist"
+ for (instance = 1; instance < threads; instance++) {
+ for (i = 0; i < inputsperfile; i++) {
+ print in_dir"/"infilesSmallToBigFull[cnt] >> tmpfile"."instance
+ cnt++
+ }
+ }
+ for (; cnt < in_count; cnt++) {
+ print in_dir"/"infilesSmallToBigFull[cnt] >> tmpfile"."threads
+ }
+
+ print "ls -l "tmpfile"*"
+
+ }
+
print "[*] Obtaining traces for "in_count" input files in '"in_dir"'."
cur = 0;
- if (!stdin_file) {
- print " Processing "in_count" files (forkserver mode)..."
-# print AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -i \""in_dir"\" -- \""target_bin"\" "prog_args_string
- retval = system(AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -i \""in_dir"\" -- \""target_bin"\" "prog_args_string)
+
+ if (threads > 1) {
+
+ print "[*] Creating " threads " parallel tasks with about " inputsperfile " each."
+ for (i = 1; i <= threads; i++) {
+
+ if (!stdin_file) {
+# print " { "AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -I \""tmpfile"."i"\" -- \""target_bin"\" "prog_args_string"; > "tmpfile"."i".done ; } &"
+ retval = system(" { "AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -I \""tmpfile"."i"\" -- \""target_bin"\" "prog_args_string"; > "tmpfile"."i".done ; } &")
+ } else {
+ stdin_file=tmpfile"."i".stdin"
+# print " { "AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -I \""tmpfile"."i"\" -H \""stdin_file"\" -- \""target_bin"\" "prog_args_string" "tmpfile"."i".done ; } &"
+ retval = system(" { "AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -I \""tmpfile"."i"\" -H \""stdin_file"\" -- \""target_bin"\" "prog_args_string" "tmpfile"."i".done ; } &")
+ }
+ }
+ print "[*] Waiting for parallel tasks to complete ..."
+ # wait for all processes to finish
+ ok=0
+ while (ok < threads) {
+ ok=0
+ for (i = 1; i <= threads; i++) {
+ if (system("test -f "tmpfile"."i".done") == 0) {
+ ok++
+ }
+ }
+ }
+ print "[*] Done!"
+ system("rm -f "tmpfile"*")
} else {
- print " Processing "in_count" files (forkserver mode)..."
+ if (!stdin_file) {
+ print " Processing "in_count" files (forkserver mode)..."
+# print AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -i \""in_dir"\" -- \""target_bin"\" "prog_args_string
+ retval = system(AFL_MAP_SIZE AFL_CMIN_ALLOW_ANY AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -i \""in_dir"\" -- \""target_bin"\" "prog_args_string)
+ } else {
+ print " Processing "in_count" files (forkserver mode)..."
# print AFL_CMIN_CRASHES_ONLY"\""showmap"\" -m "mem_limit" -t "timeout" -o \""trace_dir"\" -Z "extra_par" -i \""in_dir"\" -H \""stdin_file"\" -- \""target_bin"\" "prog_args_string" /dev/null")
- system("rmdir "out_dir)
+ if (!ENVIRON["AFL_KEEP_TRACES"]) {
+ system("rm -rf "trace_dir" 2>/dev/null")
+ system("rmdir "out_dir)
+ }
+ exit retval
}
- exit retval
+
}
#######################################################
diff --git a/docs/Changelog.md b/docs/Changelog.md
index 816a864d..667fd634 100644
--- a/docs/Changelog.md
+++ b/docs/Changelog.md
@@ -14,7 +14,7 @@
- afl-showmap:
- added custom mutator post_process and send support
- add `-I filelist` option, an alternative to `-i in_dir`
- - afl-cmin.bash:
+ - afl-cmin + afl-cmin.bash:
- `-T threads` parallel task support, huge speedup!
- a new grammar custom mutator atnwalk was submitted by @voidptr127 !
diff --git a/src/afl-showmap.c b/src/afl-showmap.c
index 09a1d2dc..d0e01cb1 100644
--- a/src/afl-showmap.c
+++ b/src/afl-showmap.c
@@ -894,9 +894,7 @@ u32 execute_testcases_filelist(u8 *fn) {
while (fgets(buf, sizeof(buf), f) != NULL) {
struct stat st;
-
- u8 *fn2 = buf, *fn3;
- ;
+ u8 *fn2 = buf, *fn3;
while (*fn2 == ' ') {
@@ -904,14 +902,11 @@ u32 execute_testcases_filelist(u8 *fn) {
}
- if (*fn2) {
-
- while (fn2[strlen(fn2) - 1] == '\r' || fn2[strlen(fn2) - 1] == '\n' ||
- fn2[strlen(fn2) - 1] == ' ') {
-
- fn2[strlen(fn2) - 1] = 0;
+ while (*fn2 &&
+ (fn2[strlen(fn2) - 1] == '\r' || fn2[strlen(fn2) - 1] == '\n' ||
+ fn2[strlen(fn2) - 1] == ' ')) {
- }
+ fn2[strlen(fn2) - 1] = 0;
}
@@ -926,6 +921,8 @@ u32 execute_testcases_filelist(u8 *fn) {
}
+ ++done;
+
if (!S_ISREG(st.st_mode) || !st.st_size) { continue; }
if ((fn3 = strrchr(fn2, '/'))) {
@@ -946,9 +943,12 @@ u32 execute_testcases_filelist(u8 *fn) {
}
- if (!collect_coverage)
+ if (!collect_coverage) {
+
snprintf(outfile, sizeof(outfile), "%s/%s", out_file, fn3);
+ }
+
if (read_file(fn2)) {
if (wait_for_gdb) {
@@ -961,7 +961,6 @@ u32 execute_testcases_filelist(u8 *fn) {
showmap_run_target_forkserver(fsrv, in_data, in_len);
ck_free(in_data);
- ++done;
if (child_crashed && debug) { WARNF("crashed: %s", fn2); }
--
cgit 1.4.1
From 21865c622483d2e2285de3dfad4626c28ca27843 Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Tue, 25 Apr 2023 16:47:37 +0200
Subject: rename env to AFL_IGNORE_PROBLEMS_COVERAGE
---
docs/FAQ.md | 3 ++-
docs/env_variables.md | 3 ++-
include/envs.h | 1 +
instrumentation/afl-compiler-rt.o.c | 4 ++--
src/afl-fuzz.c | 2 ++
5 files changed, 9 insertions(+), 4 deletions(-)
(limited to 'src')
diff --git a/docs/FAQ.md b/docs/FAQ.md
index 4a9080f8..76350c79 100644
--- a/docs/FAQ.md
+++ b/docs/FAQ.md
@@ -229,7 +229,8 @@ If you find an interesting or important question missing, submit it via
If this is not a viable option, you can set `AFL_IGNORE_PROBLEMS=1` but then
the existing map will be used also for the newly loaded libraries, which
allows it to work, however, the efficiency of the fuzzing will be partially
- degraded.
+ degraded. Note that there is additionally `AFL_IGNORE_PROBLEMS_COVERAGE` to
+ additionally tell AFL++ to ignore any coverage from the late loaded libaries.
diff --git a/docs/env_variables.md b/docs/env_variables.md
index 087ccdb7..b1f23159 100644
--- a/docs/env_variables.md
+++ b/docs/env_variables.md
@@ -406,7 +406,8 @@ checks or alter some of the more exotic semantics of the tool:
- If afl-fuzz encounters an incorrect fuzzing setup during a fuzzing session
(not at startup), it will terminate. If you do not want this, then you can
- set `AFL_IGNORE_PROBLEMS`.
+ set `AFL_IGNORE_PROBLEMS`. If you additionally want to also ignore coverage
+ from late loaded libraries, you can set `AFL_IGNORE_PROBLEMS_COVERAGE`.
- When running in the `-M` or `-S` mode, setting `AFL_IMPORT_FIRST` causes the
fuzzer to import test cases from other instances before doing anything else.
diff --git a/include/envs.h b/include/envs.h
index 5e68c80b..fe5ee0e3 100644
--- a/include/envs.h
+++ b/include/envs.h
@@ -106,6 +106,7 @@ static char *afl_environment_variables[] = {
"AFL_HARDEN",
"AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES",
"AFL_IGNORE_PROBLEMS",
+ "AFL_IGNORE_PROBLEMS_COVERAGE",
"AFL_IGNORE_TIMEOUTS",
"AFL_IGNORE_UNKNOWN_ENVS",
"AFL_IMPORT_FIRST",
diff --git a/instrumentation/afl-compiler-rt.o.c b/instrumentation/afl-compiler-rt.o.c
index 74506e4c..0912e52b 100644
--- a/instrumentation/afl-compiler-rt.o.c
+++ b/instrumentation/afl-compiler-rt.o.c
@@ -1565,13 +1565,13 @@ void __sanitizer_cov_trace_pc_guard_init(uint32_t *start, uint32_t *stop) {
"be able to fuzz them or LD_PRELOAD to run outside of afl-fuzz.\n"
"To ignore this set AFL_IGNORE_PROBLEMS=1 but this will lead to "
"ambiguous coverage data.\n"
- "In addition, you can set AFL_LLVM_IGNORE_PROBLEMS_COVERAGE=1 to "
+ "In addition, you can set AFL_IGNORE_PROBLEMS_COVERAGE=1 to "
"ignore the additional coverage instead (use with caution!).\n");
abort();
} else {
- u8 ignore_dso_after_fs = !!getenv("AFL_LLVM_IGNORE_PROBLEMS_COVERAGE");
+ u8 ignore_dso_after_fs = !!getenv("AFL_IGNORE_PROBLEMS_COVERAGE");
if (__afl_debug && ignore_dso_after_fs) {
fprintf(stderr, "Ignoring coverage from dynamically loaded code\n");
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index ebdbb3fa..c44144f5 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -259,6 +259,8 @@ static void usage(u8 *argv0, int more_help) {
"AFL_HANG_TMOUT: override timeout value (in milliseconds)\n"
"AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES: don't warn about core dump handlers\n"
"AFL_IGNORE_PROBLEMS: do not abort fuzzing if an incorrect setup is detected\n"
+ "AFL_IGNORE_PROBLEMS_COVERAGE: if set in addition to AFL_IGNORE_PROBLEMS - also\n
+ " ignore those libs for coverage\n"
"AFL_IGNORE_TIMEOUTS: do not process or save any timeouts\n"
"AFL_IGNORE_UNKNOWN_ENVS: don't warn on unknown env vars\n"
"AFL_IMPORT_FIRST: sync and import test cases from other fuzzer instances first\n"
--
cgit 1.4.1
From 96848398d45e08eaa69be245c986375808d2b3a7 Mon Sep 17 00:00:00 2001
From: vanhauser-thc
Date: Tue, 25 Apr 2023 17:56:36 +0200
Subject: fix
---
src/afl-fuzz.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
(limited to 'src')
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index c44144f5..71d2afd8 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -259,7 +259,7 @@ static void usage(u8 *argv0, int more_help) {
"AFL_HANG_TMOUT: override timeout value (in milliseconds)\n"
"AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES: don't warn about core dump handlers\n"
"AFL_IGNORE_PROBLEMS: do not abort fuzzing if an incorrect setup is detected\n"
- "AFL_IGNORE_PROBLEMS_COVERAGE: if set in addition to AFL_IGNORE_PROBLEMS - also\n
+ "AFL_IGNORE_PROBLEMS_COVERAGE: if set in addition to AFL_IGNORE_PROBLEMS - also\n"
" ignore those libs for coverage\n"
"AFL_IGNORE_TIMEOUTS: do not process or save any timeouts\n"
"AFL_IGNORE_UNKNOWN_ENVS: don't warn on unknown env vars\n"
--
cgit 1.4.1