about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorAndrea Fioraldi <andreafioraldi@gmail.com>2020-04-14 10:09:03 +0200
committerAndrea Fioraldi <andreafioraldi@gmail.com>2020-04-14 10:09:03 +0200
commit1fbface656ae4f64fc8643def840fa488098e580 (patch)
treee4e57d2c4a280b3f31f971e7ce0dea4571bb6b2f /src
parent0e1d82dd9f5cfe48b294e876924acea2f5094f01 (diff)
downloadafl++-1fbface656ae4f64fc8643def840fa488098e580.tar.gz
cmplog is now better
Diffstat (limited to 'src')
-rw-r--r--src/afl-fuzz-one.c35
-rw-r--r--src/afl-fuzz-redqueen.c54
-rw-r--r--src/afl-fuzz.c6
3 files changed, 70 insertions, 25 deletions
diff --git a/src/afl-fuzz-one.c b/src/afl-fuzz-one.c
index 92210c8b..c4d49ec1 100644
--- a/src/afl-fuzz-one.c
+++ b/src/afl-fuzz-one.c
@@ -495,7 +495,7 @@ u8 fuzz_one_original(afl_state_t *afl) {
 
   if (afl->use_radamsa > 1) goto radamsa_stage;
 
-  if (afl->shm.cmplog_mode) {
+  if (afl->shm.cmplog_mode && !afl->queue_cur->fully_colorized) {
 
     if (input_to_state_stage(afl, in_buf, out_buf, len,
                              afl->queue_cur->exec_cksum))
@@ -2508,20 +2508,15 @@ u8 mopt_common_fuzzing(afl_state_t *afl, MOpt_globals_t MOpt_globals) {
 
   orig_perf = perf_score = calculate_score(afl, afl->queue_cur);
 
-  /* Skip right away if -d is given, if we have done deterministic fuzzing on
-     this entry ourselves (was_fuzzed), or if it has gone through deterministic
-     testing in earlier, resumed runs (passed_det). */
+  if (afl->shm.cmplog_mode && !afl->queue_cur->fully_colorized) {
 
-  if (afl->skip_deterministic || afl->queue_cur->was_fuzzed ||
-      afl->queue_cur->passed_det)
-    goto havoc_stage;
+    if (input_to_state_stage(afl, in_buf, out_buf, len,
+                             afl->queue_cur->exec_cksum))
+      goto abandon_entry;
 
-  /* Skip deterministic fuzzing if exec path checksum puts this out of scope
-     for this master instance. */
+  }
 
-  if (afl->master_max &&
-      (afl->queue_cur->exec_cksum % afl->master_max) != afl->master_id - 1)
-    goto havoc_stage;
+  /* Go to pacemker fuzzing if MOpt is doing well */
 
   cur_ms_lv = get_cur_time();
   if (!(afl->key_puppet == 0 &&
@@ -2534,6 +2529,22 @@ u8 mopt_common_fuzzing(afl_state_t *afl, MOpt_globals_t MOpt_globals) {
     goto pacemaker_fuzzing;
 
   }
+  
+  /* Skip right away if -d is given, if we have done deterministic fuzzing on
+     this entry ourselves (was_fuzzed), or if it has gone through deterministic
+     testing in earlier, resumed runs (passed_det). */
+
+  if (afl->skip_deterministic || afl->queue_cur->was_fuzzed ||
+      afl->queue_cur->passed_det)
+    goto havoc_stage;
+
+  /* Skip deterministic fuzzing if exec path checksum puts this out of scope
+     for this master instance. */
+
+  if (afl->master_max &&
+      (afl->queue_cur->exec_cksum % afl->master_max) != afl->master_id - 1)
+    goto havoc_stage;
+
 
   doing_det = 1;
 
diff --git a/src/afl-fuzz-redqueen.c b/src/afl-fuzz-redqueen.c
index c910e75e..c8d54ce2 100644
--- a/src/afl-fuzz-redqueen.c
+++ b/src/afl-fuzz-redqueen.c
@@ -127,9 +127,14 @@ static u8 colorization(afl_state_t *afl, u8 *buf, u32 len, u32 exec_cksum) {
     rand_replace(afl, buf + rng->start, s);
 
     u32 cksum;
+    u64 start_us = get_cur_time_us();
     if (unlikely(get_exec_checksum(afl, buf, len, &cksum))) goto checksum_fail;
+    u64 stop_us = get_cur_time_us();
 
-    if (cksum != exec_cksum) {
+    /* Discard if the mutations change the paths or if it is too decremental
+       in speed */
+    if (cksum != exec_cksum ||
+        (stop_us - start_us > 2 * afl->queue_cur->exec_us)) {
 
       ranges = add_range(ranges, rng->start, rng->start + s / 2);
       ranges = add_range(ranges, rng->start + s / 2 + 1, rng->end);
@@ -365,9 +370,12 @@ static u8 cmp_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
 
   u8 status;
   // opt not in the paper
-  u32 fails = 0;
+  u32 fails;
+  u8 found_one = 0;
 
   for (i = 0; i < loggeds; ++i) {
+  
+    fails = 0;
 
     struct cmp_operands *o = &afl->shm.cmp_map->log[key][i];
 
@@ -396,12 +404,17 @@ static u8 cmp_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
         break;
 
     }
+    
+    if (status == 1)
+      found_one = 1;
 
     // If failed, add to dictionary
     if (fails == 8) {
 
-      try_to_add_to_dict(afl, o->v0, SHAPE_BYTES(h->shape));
-      try_to_add_to_dict(afl, o->v1, SHAPE_BYTES(h->shape));
+      if (afl->pass_stats[key].total == 0) {
+        try_to_add_to_dict(afl, o->v0, SHAPE_BYTES(h->shape));
+        try_to_add_to_dict(afl, o->v1, SHAPE_BYTES(h->shape));
+      }
 
     }
 
@@ -409,6 +422,11 @@ static u8 cmp_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
     afl->stage_cur++;
 
   }
+  
+  if (!found_one && afl->pass_stats[key].faileds < 0xff) {
+    afl->pass_stats[key].faileds++;
+  }
+  if (afl->pass_stats[key].total < 0xff) afl->pass_stats[key].total++;
 
   return 0;
 
@@ -450,9 +468,12 @@ static u8 rtn_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
 
   u8 status;
   // opt not in the paper
-  u32 fails = 0;
+  u32 fails;
+  u8 found_one = 0;
 
   for (i = 0; i < loggeds; ++i) {
+  
+    fails = 0;
 
     struct cmpfn_operands *o =
         &((struct cmpfn_operands *)afl->shm.cmp_map->log[key])[i];
@@ -482,12 +503,17 @@ static u8 rtn_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
         break;
 
     }
+    
+    if (status == 1)
+      found_one = 1;
 
     // If failed, add to dictionary
     if (fails == 8) {
 
-      maybe_add_auto(afl, o->v0, SHAPE_BYTES(h->shape));
-      maybe_add_auto(afl, o->v1, SHAPE_BYTES(h->shape));
+      if (afl->pass_stats[key].total == 0) {
+        maybe_add_auto(afl, o->v0, SHAPE_BYTES(h->shape));
+        maybe_add_auto(afl, o->v1, SHAPE_BYTES(h->shape));
+      }
 
     }
 
@@ -495,6 +521,11 @@ static u8 rtn_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u32 len) {
     afl->stage_cur++;
 
   }
+  
+  if (!found_one && afl->pass_stats[key].faileds < 0xff) {
+    afl->pass_stats[key].faileds++;
+  }
+  if (afl->pass_stats[key].total < 0xff) afl->pass_stats[key].total++;
 
   return 0;
 
@@ -507,6 +538,9 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len,
                         u32 exec_cksum) {
 
   u8 r = 1;
+  
+  if (afl->pass_stats == NULL)
+    afl->pass_stats = ck_alloc(sizeof(struct afl_pass_stat) * CMP_MAP_W);
 
   if (unlikely(colorization(afl, buf, len, exec_cksum))) return 1;
 
@@ -528,6 +562,12 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len,
   for (k = 0; k < CMP_MAP_W; ++k) {
 
     if (!afl->shm.cmp_map->headers[k].hits) continue;
+    
+    if (afl->pass_stats[k].total &&
+        (UR(afl, afl->pass_stats[k].total) < afl->pass_stats[k].faileds ||
+         afl->pass_stats[k].total == 0xff))
+      afl->shm.cmp_map->headers[k].hits = 0;
+    
     if (afl->shm.cmp_map->headers[k].type == CMP_TYPE_INS)
       afl->stage_max += MIN(afl->shm.cmp_map->headers[k].hits, CMP_MAP_H);
     else
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index 10fee76c..b89bccb4 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -966,12 +966,6 @@ int main(int argc, char **argv_orig, char **envp) {
 
   if (afl->cmplog_binary) {
 
-    if (afl->limit_time_sig)
-      FATAL(
-          "MOpt and CmpLog are mutually exclusive. We accept pull requests "
-          "that integrates MOpt with the optional mutators "
-          "(custom/radamsa/redquenn/...).");
-
     if (afl->unicorn_mode)
       FATAL("CmpLog and Unicorn mode are not compatible at the moment, sorry");
     if (!afl->qemu_mode) check_binary(afl, afl->cmplog_binary);