AFL_ENTRYPOINT instruction granularity
MODIFY
README.md
README.md
* qbdi_mode: fuzz android native libraries via QBDI framework
+ * The new CmpLog instrumentation for LLVM and QEMU inspired by [Redqueen](https://www.syssec.ruhr-uni-bochum.de/media/emma/veroeffentlichungen/2018/12/17/NDSS19-Redqueen.pdf)
A more thorough list is available in the PATCHES file.

MODIFY
docs/Changelog.md
docs/Changelog.md
@@ -34,6 +34,7 @@ sending a mail to <afl-users+subscribe@googlegroups.com>.
- AFL_PERSISTENT_HOOK callback module for persistent QEMU
(see examples/qemu_persistent_hook)
- added qemu_mode/README.persistent.md documentation
+ - AFL_ENTRYPOINT noew has instruction granularity
- afl-cmin is now a sh script (invoking awk) instead of bash for portability
the original script is still present as afl-cmin.bash
- afl-showmap: -i dir option now allows processing multiple inputs using the

MODIFY
qemu_mode/README.md
qemu_mode/README.md
@@ -66,8 +66,7 @@ the deferred initialization.
This can be enabled setting the environment variable AFL_ENTRYPOINT which allows
to move the forkserver to a different part, e.g. just before the file is
opened (e.g. way after command line parsing and config file loading, etc.)
-which can be a huge speed improvement. Note that the specified address
-must be an address of a basic block.
+which can be a huge speed improvement.
## 4) Bonus feature #2: persistent mode

MODIFY
qemu_mode/build_qemu_support.sh
qemu_mode/build_qemu_support.sh
@@ -158,6 +158,9 @@ patch -p1 <../patches/i386-ops_sse.diff || exit 1
patch -p1 <../patches/i386-fpu_helper.diff || exit 1
patch -p1 <../patches/softfloat.diff || exit 1
patch -p1 <../patches/configure.diff || exit 1
+patch -p1 <../patches/tcg-runtime.diff || exit 1
+patch -p1 <../patches/tcg-runtime-head.diff || exit 1
+patch -p1 <../patches/translator.diff || exit 1
echo "[+] Patching done."

MODIFY
qemu_mode/patches/afl-qemu-common.h
qemu_mode/patches/afl-qemu-common.h
@@ -69,7 +69,7 @@ typedef void (*afl_persistent_hook_fn)(uint64_t *regs, uint64_t guest_base);
extern unsigned char *afl_area_ptr;
extern unsigned int afl_inst_rms;
-extern abi_ulong afl_start_code, afl_end_code;
+extern abi_ulong afl_entry_point, afl_start_code, afl_end_code;
extern abi_ulong afl_persistent_addr;
extern abi_ulong afl_persistent_ret_addr;
extern u8 afl_compcov_level;
@@ -88,6 +88,9 @@ extern __thread abi_ulong afl_prev_loc;
extern struct cmp_map *__afl_cmp_map;
extern __thread u32 __afl_cmp_counter;
+void afl_setup(void);
+void afl_forkserver(CPUState *cpu);
+
void afl_debug_dump_saved_regs();
void afl_persistent_loop();

MODIFY
qemu_mode/patches/afl-qemu-cpu-inl.h
qemu_mode/patches/afl-qemu-cpu-inl.h
* VARIOUS AUXILIARY STUFF *
***************************/
-/* This snippet kicks in when the instruction pointer is positioned at
- _start and does the usual forkserver stuff, not very different from
- regular instrumentation injected via afl-as.h. */
-
-#define AFL_QEMU_CPU_SNIPPET2 \
- do { \
- \
- if (itb->pc == afl_entry_point) { \
- \
- afl_setup(); \
- afl_forkserver(cpu); \
- \
- } \
- \
- } while (0)
-
/* We use one additional file descriptor to relay "needs translation"
messages between the child and the fork server. */
@@ -107,9 +91,6 @@ unsigned int afl_inst_rms = MAP_SIZE; /* Exported for afl_gen_trace */
/* Function declarations. */
-static void afl_setup(void);
-static void afl_forkserver(CPUState *);
-
static void afl_wait_tsl(CPUState *, int);
static void afl_request_tsl(target_ulong, target_ulong, uint32_t, uint32_t,
TranslationBlock *, int);
@@ -155,7 +136,7 @@ static inline void tb_add_jump(TranslationBlock *tb, int n,
/* Set up SHM region and initialize other stuff. */
-static void afl_setup(void) {
+void afl_setup(void) {
char *id_str = getenv(SHM_ENV_VAR), *inst_r = getenv("AFL_INST_RATIO");
@@ -310,7 +291,7 @@ static void print_mappings(void) {
/* Fork server logic, invoked once we hit _start. */
-static void afl_forkserver(CPUState *cpu) {
+void afl_forkserver(CPUState *cpu) {
static unsigned char tmp[4];

MODIFY
qemu_mode/patches/cpu-exec.diff
qemu_mode/patches/cpu-exec.diff
diff --git a/accel/tcg/cpu-exec.c b/accel/tcg/cpu-exec.c
-index 870027d4..841ba557 100644
+index 870027d4..0bc87dfc 100644
--- a/accel/tcg/cpu-exec.c
+++ b/accel/tcg/cpu-exec.c
@@ -11,16 +11,7 @@ index 870027d4..841ba557 100644
/* -icount align implementation. */
typedef struct SyncClocks {
-@@ -144,6 +146,8 @@ static inline tcg_target_ulong cpu_tb_exec(CPUState *cpu, TranslationBlock *itb)
- int tb_exit;
- uint8_t *tb_ptr = itb->tc.ptr;
-
-+ AFL_QEMU_CPU_SNIPPET2;
-+
- qemu_log_mask_and_addr(CPU_LOG_EXEC, itb->pc,
- "Trace %d: %p ["
- TARGET_FMT_lx "/" TARGET_FMT_lx "/%#x] %s\n",
-@@ -397,11 +401,13 @@ static inline TranslationBlock *tb_find(CPUState *cpu,
+@@ -397,11 +399,13 @@ static inline TranslationBlock *tb_find(CPUState *cpu,
TranslationBlock *tb;
target_ulong cs_base, pc;
uint32_t flags;
@@ -34,7 +25,7 @@ index 870027d4..841ba557 100644
mmap_unlock();
/* We add the TB in the virtual pc hash table for the fast lookup */
atomic_set(&cpu->tb_jmp_cache[tb_jmp_cache_hash_func(pc)], tb);
-@@ -418,6 +424,10 @@ static inline TranslationBlock *tb_find(CPUState *cpu,
+@@ -418,6 +422,10 @@ static inline TranslationBlock *tb_find(CPUState *cpu,
/* See if we can patch the calling TB. */
if (last_tb) {
tb_add_jump(last_tb, tb_exit, tb);

ADD
qemu_mode/patches/tcg-runtime-head.diff
+diff --git a/accel/tcg/tcg-runtime.h b/accel/tcg/tcg-runtime.h
+index 1bd39d13..944997ee 100644
+--- a/accel/tcg/tcg-runtime.h
++++ b/accel/tcg/tcg-runtime.h
+@@ -260,3 +260,5 @@ DEF_HELPER_FLAGS_4(gvec_leu8, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+ DEF_HELPER_FLAGS_4(gvec_leu16, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+ DEF_HELPER_FLAGS_4(gvec_leu32, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+ DEF_HELPER_FLAGS_4(gvec_leu64, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
++
++DEF_HELPER_FLAGS_1(afl_entry_routine, TCG_CALL_NO_RWG, void, env)

ADD
qemu_mode/patches/tcg-runtime.diff
+diff --git a/accel/tcg/tcg-runtime.c b/accel/tcg/tcg-runtime.c
+index d0d44844..46154af1 100644
+--- a/accel/tcg/tcg-runtime.c
++++ b/accel/tcg/tcg-runtime.c
+@@ -31,6 +31,8 @@
+ #include "disas/disas.h"
+ #include "exec/log.h"
+
++#include "../../../patches/afl-qemu-common.h"
++
+ /* 32-bit helpers */
+
+ int32_t HELPER(div_i32)(int32_t arg1, int32_t arg2)
+@@ -167,3 +169,10 @@ void HELPER(exit_atomic)(CPUArchState *env)
+ {
+ cpu_loop_exit_atomic(ENV_GET_CPU(env), GETPC());
+ }
++
++
++void HELPER(afl_entry_routine)(CPUArchState *env) {
++
++ afl_forkserver(ENV_GET_CPU(env));
++
++}

ADD
qemu_mode/patches/translator.diff
+diff --git a/accel/tcg/translator.c b/accel/tcg/translator.c
+index afd0a49e..773ea712 100644
+--- a/accel/tcg/translator.c
++++ b/accel/tcg/translator.c
+@@ -18,6 +18,8 @@
+ #include "exec/log.h"
+ #include "exec/translator.h"
+
++#include "../../../patches/afl-qemu-common.h"
++
+ /* Pairs with tcg_clear_temp_count.
+ To be called by #TranslatorOps.{translate_insn,tb_stop} if
+ (1) the target is sufficiently clean to support reporting,
+@@ -92,6 +94,11 @@ void translator_loop(const TranslatorOps *ops, DisasContextBase *db,
+ break;
+ }
+ }
++
++ if (db->pc_next == afl_entry_point) {
++ afl_setup();
++ gen_helper_afl_entry_routine(cpu_env);
++ }
+
+ /* Disassemble one instruction. The translate_insn hook should
+ update db->pc_next and db->is_jmp to indicate what should be

AFL_ENTRYPOINT instruction granularity