about summary refs log tree commit diff
diff options
context:
space:
mode:
authorvan Hauser <vh@thc.org>2023-04-26 16:33:42 +0200
committerGitHub <noreply@github.com>2023-04-26 16:33:42 +0200
commit7ca1b85c5e8229fa49620d0fb542c86965ef5abb (patch)
tree49357cab6a9fea70f30f43b129b02434772f5e66
parentdbb317162415a28e3fd2ff4c574292c924493a00 (diff)
parentb18bc7b98fa23ef805ed2ee3eec04dc1929afd49 (diff)
downloadafl++-7ca1b85c5e8229fa49620d0fb542c86965ef5abb.tar.gz
Merge pull request #1715 from AFLplusplus/dev
push to stable
-rw-r--r--TODO.md1
-rwxr-xr-xafl-cmin143
-rwxr-xr-xafl-cmin.bash112
-rw-r--r--custom_mutators/atnwalk/Makefile7
-rw-r--r--custom_mutators/atnwalk/README.md4
-rw-r--r--custom_mutators/honggfuzz/custom_mutator_helpers.h22
-rw-r--r--custom_mutators/honggfuzz/honggfuzz.c18
-rw-r--r--custom_mutators/honggfuzz/mangle.c1181
l---------custom_mutators/radamsa/custom_mutator_helpers.h1
-rw-r--r--custom_mutators/radamsa/radamsa-mutator.c11
-rw-r--r--docs/Changelog.md11
-rw-r--r--docs/FAQ.md3
-rw-r--r--docs/env_variables.md9
-rw-r--r--include/envs.h4
-rw-r--r--instrumentation/SanitizerCoverageLTO.so.cc3
-rw-r--r--instrumentation/afl-compiler-rt.o.c16
-rw-r--r--src/afl-cc.c2
-rw-r--r--src/afl-fuzz-init.c35
-rw-r--r--src/afl-fuzz.c2
-rw-r--r--src/afl-showmap.c174
20 files changed, 1112 insertions, 647 deletions
diff --git a/TODO.md b/TODO.md
index dba75070..2efcefea 100644
--- a/TODO.md
+++ b/TODO.md
@@ -10,7 +10,6 @@
  - parallel builds for source-only targets
  - get rid of check_binary, replace with more forkserver communication
  - first fuzzer should be a main automatically? not sure.
- - reload fuzz binary on signal
 
 ## Maybe
 
diff --git a/afl-cmin b/afl-cmin
index e2c26d91..63cfdd7e 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 <out_dir>/.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"}
@@ -234,7 +240,7 @@ BEGIN {
   } # while options
 
   if (!mem_limit) mem_limit = "none"
-  if (!timeout) timeout = "none"
+  if (!timeout) timeout = "5000"
 
   # get program args
   i = 0
@@ -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 && !nyx_mode) {
+    print "[*] Are you aware of the '-T all' parallelize option that improves the speed for large/slow 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,79 @@ 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 "[*] 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" </dev/null; > "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" </dev/null; > "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"
-    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"\" -H \""stdin_file"\" -- \""target_bin"\" "prog_args_string" </dev/null")
-  }
+      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"\" -H \""stdin_file"\" -- \""target_bin"\" "prog_args_string" </dev/null")
+    }
 
-  if (retval && (!AFL_CMIN_CRASHES_ONLY && !AFL_CMIN_ALLOW_ANY)) {
-    print "[!] Exit code "retval" != 0 received from afl-showmap (this means a crashing or timeout input is likely present), terminating..."
+    if (retval && (!AFL_CMIN_CRASHES_ONLY && !AFL_CMIN_ALLOW_ANY)) {
+      print "[!] Exit code "retval" != 0 received from afl-showmap (this means a crashing or timeout input is likely present), terminating..."
 
-    if (!ENVIRON["AFL_KEEP_TRACES"]) {
-      system("rm -rf "trace_dir" 2>/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/afl-cmin.bash b/afl-cmin.bash
index 5258758e..d390ff65 100755
--- a/afl-cmin.bash
+++ b/afl-cmin.bash
@@ -7,6 +7,8 @@
 #
 # Copyright 2014, 2015 Google Inc. All rights reserved.
 #
+# Copyright 2019-2023 AFLplusplus
+#
 # 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:
@@ -36,7 +38,7 @@
 # array sizes.
 #
 
-echo "corpus minimization tool for afl-fuzz by Michal Zalewski"
+echo "corpus minimization tool for afl-fuzz"
 echo
 
 #########
@@ -46,14 +48,14 @@ echo
 # Process command-line options...
 
 MEM_LIMIT=none
-TIMEOUT=none
+TIMEOUT=5000
 
-unset IN_DIR OUT_DIR STDIN_FILE EXTRA_PAR MEM_LIMIT_GIVEN \
-  AFL_CMIN_CRASHES_ONLY AFL_CMIN_ALLOW_ANY QEMU_MODE UNICORN_MODE
+unset IN_DIR OUT_DIR STDIN_FILE EXTRA_PAR MEM_LIMIT_GIVEN F_ARG \
+  AFL_CMIN_CRASHES_ONLY AFL_CMIN_ALLOW_ANY QEMU_MODE UNICORN_MODE T_ARG
 
 export AFL_QUIET=1
 
-while getopts "+i:o:f:m:t:eOQUAChXY" opt; do
+while getopts "+i:o:f:m:t:T:eOQUAChXY" opt; do
 
   case "$opt" in 
 
@@ -69,6 +71,7 @@ while getopts "+i:o:f:m:t:eOQUAChXY" opt; do
          ;;
     "f")
          STDIN_FILE="$OPTARG"
+         F_ARG=1
          ;;
     "m")
          MEM_LIMIT="$OPTARG"
@@ -106,6 +109,9 @@ while getopts "+i:o:f:m:t:eOQUAChXY" opt; do
          EXTRA_PAR="$EXTRA_PAR -U"
          UNICORN_MODE=1
          ;;    
+    "T")
+         T_ARG="$OPTARG"
+         ;;
     "?")
          exit 1
          ;;
@@ -130,9 +136,10 @@ Required parameters:
 
 Execution control settings:
 
-  -f file       - location read by the fuzzed program (stdin)
-  -m megs       - memory limit for child process ($MEM_LIMIT MB)
-  -t msec       - run time limit for child process (none)
+  -T tasks      - how many parallel processes to create (default=1, "all"=nproc)
+  -f file       - location read by the fuzzed program (default: stdin)
+  -m megs       - memory limit for child process (default=$MEM_LIMIT MB)
+  -t msec       - run time limit for child process (default: 5000ms)
   -O            - use binary-only instrumentation (FRIDA mode)
   -Q            - use binary-only instrumentation (QEMU mode)
   -U            - use unicorn-based instrumentation (Unicorn mode)
@@ -199,6 +206,11 @@ fi
 
 # Check for obvious errors.
 
+if [ ! "$T_ARG" = "" -a ! "$F_ARG" = "" -a ! "$NYX_MODE" == 1 ]; then
+  echo "[-] Error: -T and -f can not be used together." 1>&2
+  exit 1
+fi
+
 if [ ! "$MEM_LIMIT" = "none" ]; then
 
   if [ "$MEM_LIMIT" -lt "5" ]; then
@@ -233,7 +245,7 @@ if [ "$NYX_MODE" = "" ]; then
 
 fi
 
-grep -aq AFL_DUMP_MAP_SIZE "./$TARGET_BIN" && {
+grep -aq AFL_DUMP_MAP_SIZE "$TARGET_BIN" && {
   echo "[!] Trying to obtain the map size of the target ..."
   MAPSIZE=`AFL_DUMP_MAP_SIZE=1 "./$TARGET_BIN" 2>/dev/null`
   test -n "$MAPSIZE" && {
@@ -299,14 +311,34 @@ if [ ! -x "$SHOWMAP" ]; then
   exit 1
 fi
 
+THREADS=
+if [ ! "$T_ARG" = "" ]; then
+  if [ "$T_ARG" = "all" ]; then
+    THREADS=$(nproc)
+  else
+    if [ "$T_ARG" -gt 1 -a "$T_ARG" -le "$(nproc)" ]; then
+      THREADS=$T_ARG
+    else
+      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`))
 
 if [ "$IN_COUNT" = "0" ]; then
-  echo "[+] Hmm, no inputs in the target directory. Nothing to be done."
+  echo "[-] Hmm, no inputs in the target directory. Nothing to be done."
   rm -rf "$TRACE_DIR"
   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`
 
 # Make sure that we're not dealing with a directory.
@@ -355,6 +387,18 @@ else
 
 fi
 
+TMPFILE=$OUT_DIR/.list.$$
+if [ ! "$THREADS" = "" ]; then
+  ls -- "$IN_DIR" > $TMPFILE 2>/dev/null
+  IN_COUNT=$(cat $TMPFILE | wc -l)
+  SPLIT=$(($IN_COUNT / $THREADS))
+  if [ "$(($IN_COUNT % $THREADS))" -gt 0 ]; then
+    SPLIT=$(($SPLIT + 1))
+  fi
+  echo "[+] Splitting workload into $THREADS tasks with $SPLIT items on average each."
+  split -l $SPLIT $TMPFILE $TMPFILE.
+fi
+
 # Let's roll!
 
 #############################
@@ -363,6 +407,7 @@ fi
 
 echo "[*] Obtaining traces for input files in '$IN_DIR'..."
 
+if [ "$THREADS" = "" ]; then
 (
 
   CUR=0
@@ -386,17 +431,58 @@ echo "[*] Obtaining traces for input files in '$IN_DIR'..."
       printf "\\r    Processing file $CUR/$IN_COUNT... "
 
       cp "$IN_DIR/$fn" "$STDIN_FILE"
-
       "$SHOWMAP" -m "$MEM_LIMIT" -t "$TIMEOUT" -o "$TRACE_DIR/$fn" -Z $EXTRA_PAR -H "$STDIN_FILE" -- "$@" </dev/null
 
     done
 
-
   fi
 
+  echo
+
 )
 
-echo
+else
+
+  PIDS=
+  CNT=0
+  for inputs in $(ls ${TMPFILE}.*); do
+
+(
+
+  if [ "$STDIN_FILE" = "" ]; then
+
+    cat $inputs | while read -r fn; do
+
+      "$SHOWMAP" -m "$MEM_LIMIT" -t "$TIMEOUT" -o "$TRACE_DIR/$fn" -Z $EXTRA_PAR -- "$@" <"$IN_DIR/$fn"
+
+    done
+
+  else
+
+    STDIN_FILE="$inputs.$$"
+    cat $inputs | while read -r fn; do
+
+      cp "$IN_DIR/$fn" "$STDIN_FILE"
+      "$SHOWMAP" -m "$MEM_LIMIT" -t "$TIMEOUT" -o "$TRACE_DIR/$fn" -Z $EXTRA_PAR -H "$STDIN_FILE" -- "$@" </dev/null
+
+    done
+
+  fi
+
+) &
+
+  PIDS="$PIDS $!"
+  done
+
+  echo "[+] Waiting for running tasks IDs:$PIDS"
+  wait
+  echo "[+] all $THREADS running tasks completed."
+  rm -f ${TMPFILE}*
+
+  echo trace dir files: $(ls $TRACE_DIR/*|wc -l)
+
+fi
+
 
 ##########################
 # STEP 2: SORTING TUPLES #
diff --git a/custom_mutators/atnwalk/Makefile b/custom_mutators/atnwalk/Makefile
new file mode 100644
index 00000000..bf83cae5
--- /dev/null
+++ b/custom_mutators/atnwalk/Makefile
@@ -0,0 +1,7 @@
+all:	atnwalk.so
+
+atnwalk.so:	atnwalk.c
+	$(CC) -I ../../include/ -shared -fPIC -O3 -o atnwalk.so atnwalk.c
+
+clean:
+	rm -f *.so *.o *~ core
diff --git a/custom_mutators/atnwalk/README.md b/custom_mutators/atnwalk/README.md
index badb856f..730349a3 100644
--- a/custom_mutators/atnwalk/README.md
+++ b/custom_mutators/atnwalk/README.md
@@ -6,9 +6,7 @@ Refer to [https://github.com/atnwalk/testbed](https://github.com/atnwalk/testbed
 
 ## Build
 
-```bash
-gcc -I ../../include/ -shared -fPIC -Wall -O3 atnwalk.c -o atnwalk.so
-```
+Just type `make` to build `atnwalk.so`.
 
 ## Run
 
diff --git a/custom_mutators/honggfuzz/custom_mutator_helpers.h b/custom_mutators/honggfuzz/custom_mutator_helpers.h
deleted file mode 100644
index 57754697..00000000
--- a/custom_mutators/honggfuzz/custom_mutator_helpers.h
+++ /dev/null
@@ -1,22 +0,0 @@
-#ifndef CUSTOM_MUTATOR_HELPERS
-#define CUSTOM_MUTATOR_HELPERS
-
-#include "config.h"
-#include "types.h"
-#include "afl-fuzz.h"
-#include <stdlib.h>
-
-#define INITIAL_GROWTH_SIZE (64)
-
-/* Use in a struct: creates a name_buf and a name_size variable. */
-#define BUF_VAR(type, name) \
-  type * name##_buf;        \
-  size_t name##_size;
-/* this filles in `&structptr->something_buf, &structptr->something_size`. */
-#define BUF_PARAMS(struct, name) \
-  (void **)&struct->name##_buf, &struct->name##_size
-
-#undef INITIAL_GROWTH_SIZE
-
-#endif
-
diff --git a/custom_mutators/honggfuzz/honggfuzz.c b/custom_mutators/honggfuzz/honggfuzz.c
index d7b3c9c5..0dd59aee 100644
--- a/custom_mutators/honggfuzz/honggfuzz.c
+++ b/custom_mutators/honggfuzz/honggfuzz.c
@@ -3,14 +3,14 @@
 #include <stdlib.h>
 #include <string.h>
 
-#include "custom_mutator_helpers.h"
+#include "afl-fuzz.h"
 #include "mangle.h"
 
 #define NUMBER_OF_MUTATIONS 5
 
-uint8_t *         queue_input;
+uint8_t          *queue_input;
 size_t            queue_input_size;
-afl_state_t *     afl_struct;
+afl_state_t      *afl_struct;
 run_t             run;
 honggfuzz_t       global;
 struct _dynfile_t dynfile;
@@ -18,8 +18,8 @@ struct _dynfile_t dynfile;
 typedef struct my_mutator {
 
   afl_state_t *afl;
-  run_t *      run;
-  u8 *         mutator_buf;
+  run_t       *run;
+  u8          *mutator_buf;
   unsigned int seed;
   unsigned int extras_cnt, a_extras_cnt;
 
@@ -65,9 +65,9 @@ my_mutator_t *afl_custom_init(afl_state_t *afl, unsigned int seed) {
 /* When a new queue entry is added we check if there are new dictionary
    entries to add to honggfuzz structure */
 
-uint8_t afl_custom_queue_new_entry(my_mutator_t * data,
-                                   const uint8_t *filename_new_queue,
-                                   const uint8_t *filename_orig_queue) {
+void afl_custom_queue_new_entry(my_mutator_t  *data,
+                                const uint8_t *filename_new_queue,
+                                const uint8_t *filename_orig_queue) {
 
   if (run.global->mutate.dictionaryCnt >= 1024) return;
 
@@ -97,7 +97,7 @@ uint8_t afl_custom_queue_new_entry(my_mutator_t * data,
 
   }
 
-  return 0;
+  return;
 
 }
 
diff --git a/custom_mutators/honggfuzz/mangle.c b/custom_mutators/honggfuzz/mangle.c
index 637d428d..7b7ccb91 100644
--- a/custom_mutators/honggfuzz/mangle.c
+++ b/custom_mutators/honggfuzz/mangle.c
@@ -39,11 +39,16 @@
 #include "libhfcommon/log.h"
 #include "libhfcommon/util.h"
 
-static inline size_t mangle_LenLeft(run_t* run, size_t off) {
-    if (off >= run->dynfile->size) {
-        LOG_F("Offset is too large: off:%zu >= len:%zu", off, run->dynfile->size);
-    }
-    return (run->dynfile->size - off - 1);
+static inline size_t mangle_LenLeft(run_t *run, size_t off) {
+
+  if (off >= run->dynfile->size) {
+
+    LOG_F("Offset is too large: off:%zu >= len:%zu", off, run->dynfile->size);
+
+  }
+
+  return (run->dynfile->size - off - 1);
+
 }
 
 /*
@@ -51,196 +56,233 @@ static inline size_t mangle_LenLeft(run_t* run, size_t off) {
  * Based on an idea by https://twitter.com/gamozolabs
  */
 static inline size_t mangle_getLen(size_t max) {
-    if (max > _HF_INPUT_MAX_SIZE) {
-        LOG_F("max (%zu) > _HF_INPUT_MAX_SIZE (%zu)", max, (size_t)_HF_INPUT_MAX_SIZE);
-    }
-    if (max == 0) {
-        LOG_F("max == 0");
-    }
-    if (max == 1) {
-        return 1;
-    }
 
-    /* Give 50% chance the the uniform distribution */
-    if (util_rnd64() & 1) {
-        return (size_t)util_rndGet(1, max);
-    }
+  if (max > _HF_INPUT_MAX_SIZE) {
+
+    LOG_F("max (%zu) > _HF_INPUT_MAX_SIZE (%zu)", max,
+          (size_t)_HF_INPUT_MAX_SIZE);
+
+  }
+
+  if (max == 0) { LOG_F("max == 0"); }
+  if (max == 1) { return 1; }
+
+  /* Give 50% chance the the uniform distribution */
+  if (util_rnd64() & 1) { return (size_t)util_rndGet(1, max); }
+
+  /* effectively exprand() */
+  return (size_t)util_rndGet(1, util_rndGet(1, max));
 
-    /* effectively exprand() */
-    return (size_t)util_rndGet(1, util_rndGet(1, max));
 }
 
 /* Prefer smaller values here, so use mangle_getLen() */
-static inline size_t mangle_getOffSet(run_t* run) {
-    return mangle_getLen(run->dynfile->size) - 1;
+static inline size_t mangle_getOffSet(run_t *run) {
+
+  return mangle_getLen(run->dynfile->size) - 1;
+
 }
 
 /* Offset which can be equal to the file size */
-static inline size_t mangle_getOffSetPlus1(run_t* run) {
-    size_t reqlen = HF_MIN(run->dynfile->size + 1, _HF_INPUT_MAX_SIZE);
-    return mangle_getLen(reqlen) - 1;
+static inline size_t mangle_getOffSetPlus1(run_t *run) {
+
+  size_t reqlen = HF_MIN(run->dynfile->size + 1, _HF_INPUT_MAX_SIZE);
+  return mangle_getLen(reqlen) - 1;
+
 }
 
-static inline void mangle_Move(run_t* run, size_t off_from, size_t off_to, size_t len) {
-    if (off_from >= run->dynfile->size) {
-        return;
-    }
-    if (off_to >= run->dynfile->size) {
-        return;
-    }
-    if (off_from == off_to) {
-        return;
-    }
+static inline void mangle_Move(run_t *run, size_t off_from, size_t off_to,
+                               size_t len) {
+
+  if (off_from >= run->dynfile->size) { return; }
+  if (off_to >= run->dynfile->size) { return; }
+  if (off_from == off_to) { return; }
 
-    size_t len_from = run->dynfile->size - off_from;
-    len             = HF_MIN(len, len_from);
+  size_t len_from = run->dynfile->size - off_from;
+  len = HF_MIN(len, len_from);
 
-    size_t len_to = run->dynfile->size - off_to;
-    len           = HF_MIN(len, len_to);
+  size_t len_to = run->dynfile->size - off_to;
+  len = HF_MIN(len, len_to);
+
+  memmove(&run->dynfile->data[off_to], &run->dynfile->data[off_from], len);
 
-    memmove(&run->dynfile->data[off_to], &run->dynfile->data[off_from], len);
 }
 
-static inline void mangle_Overwrite(
-    run_t* run, size_t off, const uint8_t* src, size_t len, bool printable) {
-    if (len == 0) {
-        return;
-    }
-    size_t maxToCopy = run->dynfile->size - off;
-    if (len > maxToCopy) {
-        len = maxToCopy;
-    }
+static inline void mangle_Overwrite(run_t *run, size_t off, const uint8_t *src,
+                                    size_t len, bool printable) {
+
+  if (len == 0) { return; }
+  size_t maxToCopy = run->dynfile->size - off;
+  if (len > maxToCopy) { len = maxToCopy; }
+
+  memmove(&run->dynfile->data[off], src, len);
+  if (printable) { util_turnToPrintable(&run->dynfile->data[off], len); }
 
-    memmove(&run->dynfile->data[off], src, len);
-    if (printable) {
-        util_turnToPrintable(&run->dynfile->data[off], len);
-    }
 }
 
-static inline size_t mangle_Inflate(run_t* run, size_t off, size_t len, bool printable) {
-    if (run->dynfile->size >= run->global->mutate.maxInputSz) {
-        return 0;
-    }
-    if (len > (run->global->mutate.maxInputSz - run->dynfile->size)) {
-        len = run->global->mutate.maxInputSz - run->dynfile->size;
-    }
+static inline size_t mangle_Inflate(run_t *run, size_t off, size_t len,
+                                    bool printable) {
 
-    input_setSize(run, run->dynfile->size + len);
-    mangle_Move(run, off, off + len, run->dynfile->size);
-    if (printable) {
-        memset(&run->dynfile->data[off], ' ', len);
-    }
+  if (run->dynfile->size >= run->global->mutate.maxInputSz) { return 0; }
+  if (len > (run->global->mutate.maxInputSz - run->dynfile->size)) {
+
+    len = run->global->mutate.maxInputSz - run->dynfile->size;
+
+  }
+
+  input_setSize(run, run->dynfile->size + len);
+  mangle_Move(run, off, off + len, run->dynfile->size);
+  if (printable) { memset(&run->dynfile->data[off], ' ', len); }
+
+  return len;
 
-    return len;
 }
 
-static inline void mangle_Insert(
-    run_t* run, size_t off, const uint8_t* val, size_t len, bool printable) {
-    len = mangle_Inflate(run, off, len, printable);
-    mangle_Overwrite(run, off, val, len, printable);
+static inline void mangle_Insert(run_t *run, size_t off, const uint8_t *val,
+                                 size_t len, bool printable) {
+
+  len = mangle_Inflate(run, off, len, printable);
+  mangle_Overwrite(run, off, val, len, printable);
+
 }
 
-static inline void mangle_UseValue(run_t* run, const uint8_t* val, size_t len, bool printable) {
-    if (util_rnd64() & 1) {
-        mangle_Overwrite(run, mangle_getOffSet(run), val, len, printable);
-    } else {
-        mangle_Insert(run, mangle_getOffSetPlus1(run), val, len, printable);
-    }
+static inline void mangle_UseValue(run_t *run, const uint8_t *val, size_t len,
+                                   bool printable) {
+
+  if (util_rnd64() & 1) {
+
+    mangle_Overwrite(run, mangle_getOffSet(run), val, len, printable);
+
+  } else {
+
+    mangle_Insert(run, mangle_getOffSetPlus1(run), val, len, printable);
+
+  }
+
 }
 
-static inline void mangle_UseValueAt(
-    run_t* run, size_t off, const uint8_t* val, size_t len, bool printable) {
-    if (util_rnd64() & 1) {
-        mangle_Overwrite(run, off, val, len, printable);
-    } else {
-        mangle_Insert(run, off, val, len, printable);
-    }
+static inline void mangle_UseValueAt(run_t *run, size_t off, const uint8_t *val,
+                                     size_t len, bool printable) {
+
+  if (util_rnd64() & 1) {
+
+    mangle_Overwrite(run, off, val, len, printable);
+
+  } else {
+
+    mangle_Insert(run, off, val, len, printable);
+
+  }
+
 }
 
-static void mangle_MemSwap(run_t* run, bool printable HF_ATTR_UNUSED) {
-    /* No big deal if those two are overlapping */
-    size_t off1    = mangle_getOffSet(run);
-    size_t maxlen1 = run->dynfile->size - off1;
-    size_t off2    = mangle_getOffSet(run);
-    size_t maxlen2 = run->dynfile->size - off2;
-    size_t len     = mangle_getLen(HF_MIN(maxlen1, maxlen2));
+static void mangle_MemSwap(run_t *run, bool printable HF_ATTR_UNUSED) {
 
-    if (off1 == off2) {
-        return;
-    }
+  /* No big deal if those two are overlapping */
+  size_t off1 = mangle_getOffSet(run);
+  size_t maxlen1 = run->dynfile->size - off1;
+  size_t off2 = mangle_getOffSet(run);
+  size_t maxlen2 = run->dynfile->size - off2;
+  size_t len = mangle_getLen(HF_MIN(maxlen1, maxlen2));
+
+  if (off1 == off2) { return; }
+
+  for (size_t i = 0; i < (len / 2); i++) {
+
+    /*
+     * First - from the head, next from the tail. Don't worry about layout of
+     * the overlapping part - there's no good solution to that, and it can be
+     * left somewhat scrambled, while still preserving the entropy
+     */
+    const uint8_t tmp1 = run->dynfile->data[off2 + i];
+    run->dynfile->data[off2 + i] = run->dynfile->data[off1 + i];
+    run->dynfile->data[off1 + i] = tmp1;
+    const uint8_t tmp2 = run->dynfile->data[off2 + (len - 1) - i];
+    run->dynfile->data[off2 + (len - 1) - i] =
+        run->dynfile->data[off1 + (len - 1) - i];
+    run->dynfile->data[off1 + (len - 1) - i] = tmp2;
+
+  }
 
-    for (size_t i = 0; i < (len / 2); i++) {
-        /*
-         * First - from the head, next from the tail. Don't worry about layout of the overlapping
-         * part - there's no good solution to that, and it can be left somewhat scrambled,
-         * while still preserving the entropy
-         */
-        const uint8_t tmp1                       = run->dynfile->data[off2 + i];
-        run->dynfile->data[off2 + i]             = run->dynfile->data[off1 + i];
-        run->dynfile->data[off1 + i]             = tmp1;
-        const uint8_t tmp2                       = run->dynfile->data[off2 + (len - 1) - i];
-        run->dynfile->data[off2 + (len - 1) - i] = run->dynfile->data[off1 + (len - 1) - i];
-        run->dynfile->data[off1 + (len - 1) - i] = tmp2;
-    }
 }
 
-static void mangle_MemCopy(run_t* run, bool printable HF_ATTR_UNUSED) {
-    size_t off = mangle_getOffSet(run);
-    size_t len = mangle_getLen(run->dynfile->size - off);
+static void mangle_MemCopy(run_t *run, bool printable HF_ATTR_UNUSED) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
 
-    /* Use a temp buf, as Insert/Inflate can change source bytes */
-    uint8_t* tmpbuf = (uint8_t*)util_Malloc(len);
-    defer {
-        free(tmpbuf);
-    };
-    memmove(tmpbuf, &run->dynfile->data[off], len);
+  /* Use a temp buf, as Insert/Inflate can change source bytes */
+  uint8_t *tmpbuf = (uint8_t *)util_Malloc(len);
+  defer {
+
+    free(tmpbuf);
+
+  };
+
+  memmove(tmpbuf, &run->dynfile->data[off], len);
+
+  mangle_UseValue(run, tmpbuf, len, printable);
 
-    mangle_UseValue(run, tmpbuf, len, printable);
 }
 
-static void mangle_Bytes(run_t* run, bool printable) {
-    uint16_t buf;
-    if (printable) {
-        util_rndBufPrintable((uint8_t*)&buf, sizeof(buf));
-    } else {
-        buf = util_rnd64();
-    }
+static void mangle_Bytes(run_t *run, bool printable) {
+
+  uint16_t buf;
+  if (printable) {
+
+    util_rndBufPrintable((uint8_t *)&buf, sizeof(buf));
+
+  } else {
+
+    buf = util_rnd64();
+
+  }
+
+  /* Overwrite with random 1-2-byte values */
+  size_t toCopy = util_rndGet(1, 2);
+  mangle_UseValue(run, (const uint8_t *)&buf, toCopy, printable);
 
-    /* Overwrite with random 1-2-byte values */
-    size_t toCopy = util_rndGet(1, 2);
-    mangle_UseValue(run, (const uint8_t*)&buf, toCopy, printable);
 }
 
-static void mangle_ByteRepeat(run_t* run, bool printable) {
-    size_t off     = mangle_getOffSet(run);
-    size_t destOff = off + 1;
-    size_t maxSz   = run->dynfile->size - destOff;
+static void mangle_ByteRepeat(run_t *run, bool printable) {
 
-    /* No space to repeat */
-    if (!maxSz) {
-        mangle_Bytes(run, printable);
-        return;
-    }
+  size_t off = mangle_getOffSet(run);
+  size_t destOff = off + 1;
+  size_t maxSz = run->dynfile->size - destOff;
+
+  /* No space to repeat */
+  if (!maxSz) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t len = mangle_getLen(maxSz);
+  if (util_rnd64() & 0x1) {
+
+    len = mangle_Inflate(run, destOff, len, printable);
+
+  }
+
+  memset(&run->dynfile->data[destOff], run->dynfile->data[off], len);
 
-    size_t len = mangle_getLen(maxSz);
-    if (util_rnd64() & 0x1) {
-        len = mangle_Inflate(run, destOff, len, printable);
-    }
-    memset(&run->dynfile->data[destOff], run->dynfile->data[off], len);
 }
 
-static void mangle_Bit(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    run->dynfile->data[off] ^= (uint8_t)(1U << util_rndGet(0, 7));
-    if (printable) {
-        util_turnToPrintable(&(run->dynfile->data[off]), 1);
-    }
+static void mangle_Bit(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  run->dynfile->data[off] ^= (uint8_t)(1U << util_rndGet(0, 7));
+  if (printable) { util_turnToPrintable(&(run->dynfile->data[off]), 1); }
+
 }
 
 static const struct {
-    const uint8_t val[8];
-    const size_t  size;
+
+  const uint8_t val[8];
+  const size_t  size;
+
 } mangleMagicVals[] = {
+
     /* 1B - No endianness */
     {"\x00\x00\x00\x00\x00\x00\x00\x00", 1},
     {"\x01\x00\x00\x00\x00\x00\x00\x00", 1},
@@ -472,436 +514,543 @@ static const struct {
     {"\x00\x00\x00\x00\x00\x00\x00\x80", 8},
     {"\x01\x00\x00\x00\x00\x00\x00\x80", 8},
     {"\xFE\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 8},
+
 };
 
-static void mangle_Magic(run_t* run, bool printable) {
-    uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleMagicVals) - 1);
-    mangle_UseValue(run, mangleMagicVals[choice].val, mangleMagicVals[choice].size, printable);
+static void mangle_Magic(run_t *run, bool printable) {
+
+  uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleMagicVals) - 1);
+  mangle_UseValue(run, mangleMagicVals[choice].val,
+                  mangleMagicVals[choice].size, printable);
+
 }
 
-static void mangle_StaticDict(run_t* run, bool printable) {
-    if (run->global->mutate.dictionaryCnt == 0) {
-        mangle_Bytes(run, printable);
-        return;
-    }
-    uint64_t choice = util_rndGet(0, run->global->mutate.dictionaryCnt - 1);
-    mangle_UseValue(run, run->global->mutate.dictionary[choice].val,
-        run->global->mutate.dictionary[choice].len, printable);
+static void mangle_StaticDict(run_t *run, bool printable) {
+
+  if (run->global->mutate.dictionaryCnt == 0) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  uint64_t choice = util_rndGet(0, run->global->mutate.dictionaryCnt - 1);
+  mangle_UseValue(run, run->global->mutate.dictionary[choice].val,
+                  run->global->mutate.dictionary[choice].len, printable);
+
 }
 
-static inline const uint8_t* mangle_FeedbackDict(run_t* run, size_t* len) {
-    if (!run->global->feedback.cmpFeedback) {
-        return NULL;
-    }
-    cmpfeedback_t* cmpf = run->global->feedback.cmpFeedbackMap;
-    uint32_t       cnt  = ATOMIC_GET(cmpf->cnt);
-    if (cnt == 0) {
-        return NULL;
-    }
-    if (cnt > ARRAYSIZE(cmpf->valArr)) {
-        cnt = ARRAYSIZE(cmpf->valArr);
-    }
-    uint32_t choice = util_rndGet(0, cnt - 1);
-    *len            = (size_t)ATOMIC_GET(cmpf->valArr[choice].len);
-    if (*len == 0) {
-        return NULL;
-    }
-    return cmpf->valArr[choice].val;
+static inline const uint8_t *mangle_FeedbackDict(run_t *run, size_t *len) {
+
+  if (!run->global->feedback.cmpFeedback) { return NULL; }
+  cmpfeedback_t *cmpf = run->global->feedback.cmpFeedbackMap;
+  uint32_t       cnt = ATOMIC_GET(cmpf->cnt);
+  if (cnt == 0) { return NULL; }
+  if (cnt > ARRAYSIZE(cmpf->valArr)) { cnt = ARRAYSIZE(cmpf->valArr); }
+  uint32_t choice = util_rndGet(0, cnt - 1);
+  *len = (size_t)ATOMIC_GET(cmpf->valArr[choice].len);
+  if (*len == 0) { return NULL; }
+  return cmpf->valArr[choice].val;
+
 }
 
-static void mangle_ConstFeedbackDict(run_t* run, bool printable) {
-    size_t         len;
-    const uint8_t* val = mangle_FeedbackDict(run, &len);
-    if (val == NULL) {
-        mangle_Bytes(run, printable);
-        return;
-    }
-    mangle_UseValue(run, val, len, printable);
+static void mangle_ConstFeedbackDict(run_t *run, bool printable) {
+
+  size_t         len;
+  const uint8_t *val = mangle_FeedbackDict(run, &len);
+  if (val == NULL) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  mangle_UseValue(run, val, len, printable);
+
 }
 
-static void mangle_MemSet(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    size_t len = mangle_getLen(run->dynfile->size - off);
-    int    val = printable ? (int)util_rndPrintable() : (int)util_rndGet(0, UINT8_MAX);
+static void mangle_MemSet(run_t *run, bool printable) {
 
-    if (util_rnd64() & 1) {
-        len = mangle_Inflate(run, off, len, printable);
-    }
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+  int    val =
+      printable ? (int)util_rndPrintable() : (int)util_rndGet(0, UINT8_MAX);
+
+  if (util_rnd64() & 1) { len = mangle_Inflate(run, off, len, printable); }
+
+  memset(&run->dynfile->data[off], val, len);
 
-    memset(&run->dynfile->data[off], val, len);
 }
 
-static void mangle_MemClr(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    size_t len = mangle_getLen(run->dynfile->size - off);
-    int    val = printable ? ' ' : 0;
+static void mangle_MemClr(run_t *run, bool printable) {
 
-    if (util_rnd64() & 1) {
-        len = mangle_Inflate(run, off, len, printable);
-    }
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+  int    val = printable ? ' ' : 0;
+
+  if (util_rnd64() & 1) { len = mangle_Inflate(run, off, len, printable); }
+
+  memset(&run->dynfile->data[off], val, len);
 
-    memset(&run->dynfile->data[off], val, len);
 }
 
-static void mangle_RandomBuf(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    size_t len = mangle_getLen(run->dynfile->size - off);
+static void mangle_RandomBuf(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  size_t len = mangle_getLen(run->dynfile->size - off);
+
+  if (util_rnd64() & 1) { len = mangle_Inflate(run, off, len, printable); }
+
+  if (printable) {
+
+    util_rndBufPrintable(&run->dynfile->data[off], len);
+
+  } else {
+
+    util_rndBuf(&run->dynfile->data[off], len);
+
+  }
+
+}
+
+static inline void mangle_AddSubWithRange(run_t *run, size_t off, size_t varLen,
+                                          uint64_t range, bool printable) {
+
+  int64_t delta = (int64_t)util_rndGet(0, range * 2) - (int64_t)range;
+
+  switch (varLen) {
+
+    case 1: {
+
+      run->dynfile->data[off] += delta;
+      break;
 
-    if (util_rnd64() & 1) {
-        len = mangle_Inflate(run, off, len, printable);
     }
 
-    if (printable) {
-        util_rndBufPrintable(&run->dynfile->data[off], len);
-    } else {
-        util_rndBuf(&run->dynfile->data[off], len);
+    case 2: {
+
+      int16_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap16(val);
+        val += delta;
+        val = __builtin_bswap16(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
+
     }
-}
 
-static inline void mangle_AddSubWithRange(
-    run_t* run, size_t off, size_t varLen, uint64_t range, bool printable) {
-    int64_t delta = (int64_t)util_rndGet(0, range * 2) - (int64_t)range;
-
-    switch (varLen) {
-        case 1: {
-            run->dynfile->data[off] += delta;
-            break;
-        }
-        case 2: {
-            int16_t val;
-            memcpy(&val, &run->dynfile->data[off], sizeof(val));
-            if (util_rnd64() & 0x1) {
-                val += delta;
-            } else {
-                /* Foreign endianess */
-                val = __builtin_bswap16(val);
-                val += delta;
-                val = __builtin_bswap16(val);
-            }
-            mangle_Overwrite(run, off, (uint8_t*)&val, varLen, printable);
-            break;
-        }
-        case 4: {
-            int32_t val;
-            memcpy(&val, &run->dynfile->data[off], sizeof(val));
-            if (util_rnd64() & 0x1) {
-                val += delta;
-            } else {
-                /* Foreign endianess */
-                val = __builtin_bswap32(val);
-                val += delta;
-                val = __builtin_bswap32(val);
-            }
-            mangle_Overwrite(run, off, (uint8_t*)&val, varLen, printable);
-            break;
-        }
-        case 8: {
-            int64_t val;
-            memcpy(&val, &run->dynfile->data[off], sizeof(val));
-            if (util_rnd64() & 0x1) {
-                val += delta;
-            } else {
-                /* Foreign endianess */
-                val = __builtin_bswap64(val);
-                val += delta;
-                val = __builtin_bswap64(val);
-            }
-            mangle_Overwrite(run, off, (uint8_t*)&val, varLen, printable);
-            break;
-        }
-        default: {
-            LOG_F("Unknown variable length size: %zu", varLen);
-        }
+    case 4: {
+
+      int32_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap32(val);
+        val += delta;
+        val = __builtin_bswap32(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
+
     }
-}
 
-static void mangle_AddSub(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
+    case 8: {
+
+      int64_t val;
+      memcpy(&val, &run->dynfile->data[off], sizeof(val));
+      if (util_rnd64() & 0x1) {
+
+        val += delta;
+
+      } else {
+
+        /* Foreign endianess */
+        val = __builtin_bswap64(val);
+        val += delta;
+        val = __builtin_bswap64(val);
+
+      }
+
+      mangle_Overwrite(run, off, (uint8_t *)&val, varLen, printable);
+      break;
 
-    /* 1,2,4,8 */
-    size_t varLen = 1U << util_rndGet(0, 3);
-    if ((run->dynfile->size - off) < varLen) {
-        varLen = 1;
     }
 
-    uint64_t range;
-    switch (varLen) {
-        case 1:
-            range = 16;
-            break;
-        case 2:
-            range = 4096;
-            break;
-        case 4:
-            range = 1048576;
-            break;
-        case 8:
-            range = 268435456;
-            break;
-        default:
-            LOG_F("Invalid operand size: %zu", varLen);
+    default: {
+
+      LOG_F("Unknown variable length size: %zu", varLen);
+
     }
 
-    mangle_AddSubWithRange(run, off, varLen, range, printable);
+  }
+
 }
 
-static void mangle_IncByte(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    if (printable) {
-        run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 1) % 95 + 32;
-    } else {
-        run->dynfile->data[off] += (uint8_t)1UL;
-    }
+static void mangle_AddSub(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+
+  /* 1,2,4,8 */
+  size_t varLen = 1U << util_rndGet(0, 3);
+  if ((run->dynfile->size - off) < varLen) { varLen = 1; }
+
+  uint64_t range;
+  switch (varLen) {
+
+    case 1:
+      range = 16;
+      break;
+    case 2:
+      range = 4096;
+      break;
+    case 4:
+      range = 1048576;
+      break;
+    case 8:
+      range = 268435456;
+      break;
+    default:
+      LOG_F("Invalid operand size: %zu", varLen);
+
+  }
+
+  mangle_AddSubWithRange(run, off, varLen, range, printable);
+
 }
 
-static void mangle_DecByte(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    if (printable) {
-        run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 94) % 95 + 32;
-    } else {
-        run->dynfile->data[off] -= (uint8_t)1UL;
-    }
+static void mangle_IncByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 1) % 95 + 32;
+
+  } else {
+
+    run->dynfile->data[off] += (uint8_t)1UL;
+
+  }
+
 }
 
-static void mangle_NegByte(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    if (printable) {
-        run->dynfile->data[off] = 94 - (run->dynfile->data[off] - 32) + 32;
-    } else {
-        run->dynfile->data[off] = ~(run->dynfile->data[off]);
-    }
+static void mangle_DecByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = (run->dynfile->data[off] - 32 + 94) % 95 + 32;
+
+  } else {
+
+    run->dynfile->data[off] -= (uint8_t)1UL;
+
+  }
+
 }
 
-static void mangle_Expand(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
-    size_t len;
-    if (util_rnd64() % 16) {
-        len = mangle_getLen(HF_MIN(16, run->global->mutate.maxInputSz - off));
-    } else {
-        len = mangle_getLen(run->global->mutate.maxInputSz - off);
-    }
+static void mangle_NegByte(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+  if (printable) {
+
+    run->dynfile->data[off] = 94 - (run->dynfile->data[off] - 32) + 32;
+
+  } else {
+
+    run->dynfile->data[off] = ~(run->dynfile->data[off]);
+
+  }
 
-    mangle_Inflate(run, off, len, printable);
 }
 
-static void mangle_Shrink(run_t* run, bool printable HF_ATTR_UNUSED) {
-    if (run->dynfile->size <= 2U) {
-        return;
-    }
+static void mangle_Expand(run_t *run, bool printable) {
 
-    size_t off_start = mangle_getOffSet(run);
-    size_t len       = mangle_LenLeft(run, off_start);
-    if (len == 0) {
-        return;
-    }
-    if (util_rnd64() % 16) {
-        len = mangle_getLen(HF_MIN(16, len));
-    } else {
-        len = mangle_getLen(len);
-    }
-    size_t off_end     = off_start + len;
-    size_t len_to_move = run->dynfile->size - off_end;
+  size_t off = mangle_getOffSet(run);
+  size_t len;
+  if (util_rnd64() % 16) {
+
+    len = mangle_getLen(HF_MIN(16, run->global->mutate.maxInputSz - off));
+
+  } else {
+
+    len = mangle_getLen(run->global->mutate.maxInputSz - off);
+
+  }
+
+  mangle_Inflate(run, off, len, printable);
 
-    mangle_Move(run, off_end, off_start, len_to_move);
-    input_setSize(run, run->dynfile->size - len);
 }
-static void mangle_ASCIINum(run_t* run, bool printable) {
-    size_t len = util_rndGet(2, 8);
 
-    char buf[20];
-    snprintf(buf, sizeof(buf), "%-19" PRId64, (int64_t)util_rnd64());
+static void mangle_Shrink(run_t *run, bool printable HF_ATTR_UNUSED) {
+
+  if (run->dynfile->size <= 2U) { return; }
+
+  size_t off_start = mangle_getOffSet(run);
+  size_t len = mangle_LenLeft(run, off_start);
+  if (len == 0) { return; }
+  if (util_rnd64() % 16) {
+
+    len = mangle_getLen(HF_MIN(16, len));
+
+  } else {
+
+    len = mangle_getLen(len);
+
+  }
+
+  size_t off_end = off_start + len;
+  size_t len_to_move = run->dynfile->size - off_end;
+
+  mangle_Move(run, off_end, off_start, len_to_move);
+  input_setSize(run, run->dynfile->size - len);
 
-    mangle_UseValue(run, (const uint8_t*)buf, len, printable);
 }
 
-static void mangle_ASCIINumChange(run_t* run, bool printable) {
-    size_t off = mangle_getOffSet(run);
+static void mangle_ASCIINum(run_t *run, bool printable) {
 
-    /* Find a digit */
-    for (; off < run->dynfile->size; off++) {
-        if (isdigit(run->dynfile->data[off])) {
-            break;
-        }
-    }
-    size_t left = run->dynfile->size - off;
-    if (left == 0) {
-        return;
-    }
+  size_t len = util_rndGet(2, 8);
 
-    size_t   len = 0;
-    uint64_t val = 0;
-    /* 20 is maximum lenght of a string representing a 64-bit unsigned value */
-    for (len = 0; (len < 20) && (len < left); len++) {
-        char c = run->dynfile->data[off + len];
-        if (!isdigit(c)) {
-            break;
-        }
-        val *= 10;
-        val += (c - '0');
-    }
+  char buf[20];
+  snprintf(buf, sizeof(buf), "%-19" PRId64, (int64_t)util_rnd64());
 
-    switch (util_rndGet(0, 7)) {
-        case 0:
-            val++;
-            break;
-        case 1:
-            val--;
-            break;
-        case 2:
-            val *= 2;
-            break;
-        case 3:
-            val /= 2;
-            break;
-        case 4:
-            val = util_rnd64();
-            break;
-        case 5:
-            val += util_rndGet(1, 256);
-            break;
-        case 6:
-            val -= util_rndGet(1, 256);
-            break;
-        case 7:
-            val = ~(val);
-            break;
-        default:
-            LOG_F("Invalid choice");
-    };
-
-    char buf[20];
-    snprintf(buf, sizeof(buf), "%-19" PRIu64, val);
-
-    mangle_UseValueAt(run, off, (const uint8_t*)buf, len, printable);
-}
-
-static void mangle_Splice(run_t* run, bool printable) {
-    if (run->global->feedback.dynFileMethod == _HF_DYNFILE_NONE) {
-        mangle_Bytes(run, printable);
-        return;
-    }
+  mangle_UseValue(run, (const uint8_t *)buf, len, printable);
 
-    size_t         sz  = 0;
-    const uint8_t* buf = input_getRandomInputAsBuf(run, &sz);
-    if (!buf) {
-        LOG_E("input_getRandomInputAsBuf() returned no input");
-        mangle_Bytes(run, printable);
-        return;
-    }
-    if (!sz) {
-        mangle_Bytes(run, printable);
-        return;
-    }
+}
 
-    size_t remoteOff = mangle_getLen(sz) - 1;
-    size_t len       = mangle_getLen(sz - remoteOff);
-    mangle_UseValue(run, &buf[remoteOff], len, printable);
-}
-
-static void mangle_Resize(run_t* run, bool printable) {
-    ssize_t oldsz = run->dynfile->size;
-    ssize_t newsz = 0;
-
-    uint64_t choice = util_rndGet(0, 32);
-    switch (choice) {
-        case 0: /* Set new size arbitrarily */
-            newsz = (ssize_t)util_rndGet(1, run->global->mutate.maxInputSz);
-            break;
-        case 1 ... 4: /* Increase size by a small value */
-            newsz = oldsz + (ssize_t)util_rndGet(0, 8);
-            break;
-        case 5: /* Increase size by a larger value */
-            newsz = oldsz + (ssize_t)util_rndGet(9, 128);
-            break;
-        case 6 ... 9: /* Decrease size by a small value */
-            newsz = oldsz - (ssize_t)util_rndGet(0, 8);
-            break;
-        case 10: /* Decrease size by a larger value */
-            newsz = oldsz - (ssize_t)util_rndGet(9, 128);
-            break;
-        case 11 ... 32: /* Do nothing */
-            newsz = oldsz;
-            break;
-        default:
-            LOG_F("Illegal value from util_rndGet: %" PRIu64, choice);
-            break;
-    }
-    if (newsz < 1) {
-        newsz = 1;
-    }
-    if (newsz > (ssize_t)run->global->mutate.maxInputSz) {
-        newsz = run->global->mutate.maxInputSz;
-    }
+static void mangle_ASCIINumChange(run_t *run, bool printable) {
+
+  size_t off = mangle_getOffSet(run);
+
+  /* Find a digit */
+  for (; off < run->dynfile->size; off++) {
+
+    if (isdigit(run->dynfile->data[off])) { break; }
+
+  }
+
+  size_t left = run->dynfile->size - off;
+  if (left == 0) { return; }
+
+  size_t   len = 0;
+  uint64_t val = 0;
+  /* 20 is maximum lenght of a string representing a 64-bit unsigned value */
+  for (len = 0; (len < 20) && (len < left); len++) {
+
+    char c = run->dynfile->data[off + len];
+    if (!isdigit(c)) { break; }
+    val *= 10;
+    val += (c - '0');
+
+  }
+
+  switch (util_rndGet(0, 7)) {
+
+    case 0:
+      val++;
+      break;
+    case 1:
+      val--;
+      break;
+    case 2:
+      val *= 2;
+      break;
+    case 3:
+      val /= 2;
+      break;
+    case 4:
+      val = util_rnd64();
+      break;
+    case 5:
+      val += util_rndGet(1, 256);
+      break;
+    case 6:
+      val -= util_rndGet(1, 256);
+      break;
+    case 7:
+      val = ~(val);
+      break;
+    default:
+      LOG_F("Invalid choice");
+
+  };
+
+  char buf[20];
+  snprintf(buf, sizeof(buf), "%-19" PRIu64, val);
+
+  mangle_UseValueAt(run, off, (const uint8_t *)buf, len, printable);
 
-    input_setSize(run, (size_t)newsz);
-    if (newsz > oldsz) {
-        if (printable) {
-            memset(&run->dynfile->data[oldsz], ' ', newsz - oldsz);
-        }
-    }
 }
 
-void mangle_mangleContent(run_t* run, int speed_factor) {
-    static void (*const mangleFuncs[])(run_t * run, bool printable) = {
-        mangle_Shrink,
-        mangle_Expand,
-        mangle_Bit,
-        mangle_IncByte,
-        mangle_DecByte,
-        mangle_NegByte,
-        mangle_AddSub,
-        mangle_MemSet,
-        mangle_MemClr,
-        mangle_MemSwap,
-        mangle_MemCopy,
-        mangle_Bytes,
-        mangle_ASCIINum,
-        mangle_ASCIINumChange,
-        mangle_ByteRepeat,
-        mangle_Magic,
-        mangle_StaticDict,
-        mangle_ConstFeedbackDict,
-        mangle_RandomBuf,
-        mangle_Splice,
-    };
-
-    if (run->mutationsPerRun == 0U) {
-        return;
-    }
-    if (run->dynfile->size == 0U) {
-        mangle_Resize(run, /* printable= */ run->global->cfg.only_printable);
+static void mangle_Splice(run_t *run, bool printable) {
+
+  if (run->global->feedback.dynFileMethod == _HF_DYNFILE_NONE) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t         sz = 0;
+  const uint8_t *buf = input_getRandomInputAsBuf(run, &sz);
+  if (!buf) {
+
+    LOG_E("input_getRandomInputAsBuf() returned no input");
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  if (!sz) {
+
+    mangle_Bytes(run, printable);
+    return;
+
+  }
+
+  size_t remoteOff = mangle_getLen(sz) - 1;
+  size_t len = mangle_getLen(sz - remoteOff);
+  mangle_UseValue(run, &buf[remoteOff], len, printable);
+
+}
+
+static void mangle_Resize(run_t *run, bool printable) {
+
+  ssize_t oldsz = run->dynfile->size;
+  ssize_t newsz = 0;
+
+  uint64_t choice = util_rndGet(0, 32);
+  switch (choice) {
+
+    case 0:                                     /* Set new size arbitrarily */
+      newsz = (ssize_t)util_rndGet(1, run->global->mutate.maxInputSz);
+      break;
+    case 1 ... 4:                         /* Increase size by a small value */
+      newsz = oldsz + (ssize_t)util_rndGet(0, 8);
+      break;
+    case 5:                              /* Increase size by a larger value */
+      newsz = oldsz + (ssize_t)util_rndGet(9, 128);
+      break;
+    case 6 ... 9:                         /* Decrease size by a small value */
+      newsz = oldsz - (ssize_t)util_rndGet(0, 8);
+      break;
+    case 10:                             /* Decrease size by a larger value */
+      newsz = oldsz - (ssize_t)util_rndGet(9, 128);
+      break;
+    case 11 ... 32:                                           /* Do nothing */
+      newsz = oldsz;
+      break;
+    default:
+      LOG_F("Illegal value from util_rndGet: %" PRIu64, choice);
+      break;
+
+  }
+
+  if (newsz < 1) { newsz = 1; }
+  if (newsz > (ssize_t)run->global->mutate.maxInputSz) {
+
+    newsz = run->global->mutate.maxInputSz;
+
+  }
+
+  input_setSize(run, (size_t)newsz);
+  if (newsz > oldsz) {
+
+    if (printable) { memset(&run->dynfile->data[oldsz], ' ', newsz - oldsz); }
+
+  }
+
+}
+
+void mangle_mangleContent(run_t *run, int speed_factor) {
+
+  static void (*const mangleFuncs[])(run_t * run, bool printable) = {
+
+      mangle_Shrink,    mangle_Expand,         mangle_Bit,
+      mangle_IncByte,   mangle_DecByte,        mangle_NegByte,
+      mangle_AddSub,    mangle_MemSet,         mangle_MemClr,
+      mangle_MemSwap,   mangle_MemCopy,        mangle_Bytes,
+      mangle_ASCIINum,  mangle_ASCIINumChange, mangle_ByteRepeat,
+      mangle_Magic,     mangle_StaticDict,     mangle_ConstFeedbackDict,
+      mangle_RandomBuf, mangle_Splice,
+
+  };
+
+  if (run->mutationsPerRun == 0U) { return; }
+  if (run->dynfile->size == 0U) {
+
+    mangle_Resize(run, /* printable= */ run->global->cfg.only_printable);
+
+  }
+
+  uint64_t changesCnt = run->global->mutate.mutationsPerRun;
+
+  if (speed_factor < 5) {
+
+    changesCnt = util_rndGet(1, run->global->mutate.mutationsPerRun);
+
+  } else if (speed_factor < 10) {
+
+    changesCnt = run->global->mutate.mutationsPerRun;
+
+  } else {
+
+    changesCnt = HF_MIN(speed_factor, 10);
+    changesCnt = HF_MAX(changesCnt, (run->global->mutate.mutationsPerRun * 5));
+
+  }
+
+  /* If last coverage acquisition was more than 5 secs ago, use splicing more
+   * frequently */
+  if ((time(NULL) - ATOMIC_GET(run->global->timing.lastCovUpdate)) > 5) {
+
+    if (util_rnd64() & 0x1) {
+
+      mangle_Splice(run, run->global->cfg.only_printable);
+
     }
 
-    uint64_t changesCnt = run->global->mutate.mutationsPerRun;
+  }
+
+  for (uint64_t x = 0; x < changesCnt; x++) {
+
+    if (run->global->feedback.cmpFeedback && (util_rnd64() & 0x1)) {
+
+      /*
+       * mangle_ConstFeedbackDict() is quite powerful if the dynamic feedback
+       * dictionary exists. If so, give it 50% chance of being used among all
+       * mangling functions.
+       */
+      mangle_ConstFeedbackDict(
+          run, /* printable= */ run->global->cfg.only_printable);
 
-    if (speed_factor < 5) {
-        changesCnt = util_rndGet(1, run->global->mutate.mutationsPerRun);
-    } else if (speed_factor < 10) {
-        changesCnt = run->global->mutate.mutationsPerRun;
     } else {
-        changesCnt = HF_MIN(speed_factor, 10);
-        changesCnt = HF_MAX(changesCnt, (run->global->mutate.mutationsPerRun * 5));
-    }
 
-    /* If last coverage acquisition was more than 5 secs ago, use splicing more frequently */
-    if ((time(NULL) - ATOMIC_GET(run->global->timing.lastCovUpdate)) > 5) {
-        if (util_rnd64() & 0x1) {
-            mangle_Splice(run, run->global->cfg.only_printable);
-        }
-    }
+      uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleFuncs) - 1);
+      mangleFuncs[choice](run,
+                          /* printable= */ run->global->cfg.only_printable);
 
-    for (uint64_t x = 0; x < changesCnt; x++) {
-        if (run->global->feedback.cmpFeedback && (util_rnd64() & 0x1)) {
-            /*
-             * mangle_ConstFeedbackDict() is quite powerful if the dynamic feedback dictionary
-             * exists. If so, give it 50% chance of being used among all mangling functions.
-             */
-            mangle_ConstFeedbackDict(run, /* printable= */ run->global->cfg.only_printable);
-        } else {
-            uint64_t choice = util_rndGet(0, ARRAYSIZE(mangleFuncs) - 1);
-            mangleFuncs[choice](run, /* printable= */ run->global->cfg.only_printable);
-        }
     }
 
-    wmb();
+  }
+
+  wmb();
+
 }
+
diff --git a/custom_mutators/radamsa/custom_mutator_helpers.h b/custom_mutators/radamsa/custom_mutator_helpers.h
deleted file mode 120000
index f7532ef9..00000000
--- a/custom_mutators/radamsa/custom_mutator_helpers.h
+++ /dev/null
@@ -1 +0,0 @@
-../examples/custom_mutator_helpers.h
\ No newline at end of file
diff --git a/custom_mutators/radamsa/radamsa-mutator.c b/custom_mutators/radamsa/radamsa-mutator.c
index 624ace3d..466bb5c3 100644
--- a/custom_mutators/radamsa/radamsa-mutator.c
+++ b/custom_mutators/radamsa/radamsa-mutator.c
@@ -1,6 +1,5 @@
 // This simple example just creates random buffer <= 100 filled with 'A'
 // needs -I /path/to/AFLplusplus/include
-//#include "custom_mutator_helpers.h"
 
 #include <stdint.h>
 #include <stdlib.h>
@@ -8,19 +7,17 @@
 #include <stdio.h>
 
 #include "radamsa.h"
-#include "custom_mutator_helpers.h"
+#include "afl-fuzz.h"
 
 typedef struct my_mutator {
 
-  afl_t *afl;
-
-  u8 *mutator_buf;
-
+  afl_state_t *afl;
+  u8          *mutator_buf;
   unsigned int seed;
 
 } my_mutator_t;
 
-my_mutator_t *afl_custom_init(afl_t *afl, unsigned int seed) {
+my_mutator_t *afl_custom_init(afl_state_t *afl, unsigned int seed) {
 
   srand(seed);
   my_mutator_t *data = calloc(1, sizeof(my_mutator_t));
diff --git a/docs/Changelog.md b/docs/Changelog.md
index f33acff9..20b915fa 100644
--- a/docs/Changelog.md
+++ b/docs/Changelog.md
@@ -5,10 +5,19 @@
 
 ### Version ++4.07a (dev)
   - afl-fuzz:
+    - reverse reading the seeds only on restarts (increases performance)
     - new env `AFL_POST_PROCESS_KEEP_ORIGINAL` to keep the orignal
-      data before post process on finds
+      data before post process on finds (for atnwalk custom mutator)
+    - new env `AFL_IGNORE_PROBLEMS_COVERAGE` to ignore coverage from
+      loaded libs after forkserver initialization (required by Mozilla)
+  - 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`
+  - afl-cmin + afl-cmin.bash:
+    - `-T threads` parallel task support, can be a huge speedup!
   - a new grammar custom mutator atnwalk was submitted by @voidptr127 !
 
 
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.
 </p></details>
 
 <details>
diff --git a/docs/env_variables.md b/docs/env_variables.md
index c5995d13..b1f23159 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).
 
@@ -404,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 23599b26..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",
@@ -160,8 +161,9 @@ static char *afl_environment_variables[] = {
     "AFL_LLVM_SKIP_NEVERZERO",
     "AFL_NO_AFFINITY",
     "AFL_TRY_AFFINITY",
-    "AFL_LLVM_LTO_STARTID",
     "AFL_LLVM_LTO_DONTWRITEID",
+    "AFL_LLVM_LTO_SKIPINIT"
+    "AFL_LLVM_LTO_STARTID",
     "AFL_NO_ARITH",
     "AFL_NO_AUTODICT",
     "AFL_NO_BUILTIN",
diff --git a/instrumentation/SanitizerCoverageLTO.so.cc b/instrumentation/SanitizerCoverageLTO.so.cc
index e41f19b6..42583f9e 100644
--- a/instrumentation/SanitizerCoverageLTO.so.cc
+++ b/instrumentation/SanitizerCoverageLTO.so.cc
@@ -1005,7 +1005,8 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
   // afl++ START
   if (dFile.is_open()) dFile.close();
 
-  if (!getenv("AFL_LLVM_LTO_DONTWRITEID") || dictionary.size() || map_addr) {
+  if (!getenv("AFL_LLVM_LTO_SKIPINIT") &&
+      (!getenv("AFL_LLVM_LTO_DONTWRITEID") || dictionary.size() || map_addr)) {
 
     // yes we could create our own function, insert it into ctors ...
     // but this would be a pain in the butt ... so we use afl-llvm-rt-lto.o
diff --git a/instrumentation/afl-compiler-rt.o.c b/instrumentation/afl-compiler-rt.o.c
index e0e40983..0912e52b 100644
--- a/instrumentation/afl-compiler-rt.o.c
+++ b/instrumentation/afl-compiler-rt.o.c
@@ -1563,17 +1563,27 @@ void __sanitizer_cov_trace_pc_guard_init(uint32_t *start, uint32_t *stop) {
           "[-] FATAL: forkserver is already up, but an instrumented dlopen() "
           "library loaded afterwards. You must AFL_PRELOAD such libraries to "
           "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 be bad for "
-          "coverage.\n");
+          "To ignore this set AFL_IGNORE_PROBLEMS=1 but this will lead to "
+          "ambiguous coverage data.\n"
+          "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_IGNORE_PROBLEMS_COVERAGE");
+      if (__afl_debug && ignore_dso_after_fs) {
+
+        fprintf(stderr, "Ignoring coverage from dynamically loaded code\n");
+
+      }
+
       static u32 offset = 5;
 
       while (start < stop) {
 
-        if (likely(inst_ratio == 100) || R(100) < inst_ratio) {
+        if (!ignore_dso_after_fs &&
+            (likely(inst_ratio == 100) || R(100) < inst_ratio)) {
 
           *(start++) = offset;
 
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
 
diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c
index 01d1e82e..bd591c8f 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];
@@ -745,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;
 
       }
 
@@ -754,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;
 
       }
 
@@ -801,18 +812,18 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
 
       }
 
-      /*
-          if (unlikely(afl->schedule >= FAST && afl->schedule <= RARE)) {
+    next_entry:
+      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);
 
   }
 
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index ebdbb3fa..71d2afd8 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"
diff --git a/src/afl-showmap.c b/src/afl-showmap.c
index 0b9fc211..d0e01cb1 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,103 @@ 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;
+
+    }
+
+    while (*fn2 &&
+           (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;
+
+    }
+
+    ++done;
+
+    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);
+
+      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 +1019,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 +1032,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 +1094,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 +1112,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 +1339,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 +1401,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 +1507,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 +1590,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 +1603,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 +1696,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);
+
+      }
 
     }