Compare commits

...

21 Commits

Author SHA1 Message Date
9f6b012fbf Merge pull request #2117 from AFLplusplus/dev
push to stable
2024-06-09 19:09:17 +02:00
ec0b83f127 4.21c 2024-06-09 18:39:56 +02:00
0c81982e67 nit 2024-06-09 18:32:36 +02:00
5014b86c3c fix AFL_FRIDA_DEBUG_MAPS 2024-06-09 15:44:10 +02:00
44b5e1f488 fix no_forkserver mode 2024-06-09 12:26:48 +02:00
31652eeb2a nit 2024-06-09 12:19:58 +02:00
4bb4d4ad00 fix -n 2024-06-09 12:16:32 +02:00
5331eca5d9 allow multiple -m 2024-06-09 12:02:59 +02:00
74e264a20a move function 2024-06-07 13:46:15 +02:00
f0937f96d4 target hash 2024-06-07 11:48:58 +02:00
92cbdb9f45 update unicorn 2024-06-07 11:41:35 +02:00
fe36ceaa55 minor testcache optimizations 2024-06-07 11:16:42 +02:00
0618bfd4ae fix 2024-06-07 09:58:27 +02:00
bdfd38771a add cmplog_time measurement 2024-06-07 09:47:29 +02:00
477063e9ee memory adjustments 2024-06-06 17:52:21 +02:00
e46c106b89 new seed selection algorithm 2024-06-06 10:25:23 +02:00
69630338ff Merge pull request #2114 from WorksButNotTested/frida-rlimit
Fix issue for setrlimit
2024-06-05 20:21:51 +02:00
112759cd39 Merge pull request #2113 from AFLplusplus/fix_mmap_cmplog
Fix cmplog shared memory size when USEMMAP=1
2024-06-05 20:19:38 +02:00
f8767c397b Fix issue for setrlimit 2024-06-05 18:43:20 +01:00
fd713413e8 Merge pull request #2109 from AFLplusplus/dev
fix afl-showmap
2024-06-01 16:56:35 +02:00
348f980f21 Merge pull request #2108 from AFLplusplus/dev
push to stable
2024-06-01 16:37:28 +02:00
17 changed files with 307 additions and 194 deletions

View File

@ -2,9 +2,9 @@
<img align="right" src="https://raw.githubusercontent.com/AFLplusplus/Website/main/static/aflpp_bg.svg" alt="AFL++ logo" width="250" heigh="250">
Release version: [4.20c](https://github.com/AFLplusplus/AFLplusplus/releases)
Release version: [4.21c](https://github.com/AFLplusplus/AFLplusplus/releases)
GitHub version: 4.21a
GitHub version: 4.21c
Repository:
[https://github.com/AFLplusplus/AFLplusplus](https://github.com/AFLplusplus/AFLplusplus)

View File

@ -2,6 +2,8 @@
## Must
- fast restart of afl-fuzz if cmdline + target hash is the same
- check for null ptr for xml/curl/g_ string transform functions
- hardened_usercopy=0 page_alloc.shuffle=0
- add value_profile but only enable after 15 minutes without finds
- cmplog max items env?
@ -11,7 +13,6 @@
- afl-showmap -f support
- afl-fuzz multicore wrapper script
- when trimming then perform crash detection
- cyclomatic complexity: 2 + calls + edges - blocks
## Should

View File

@ -3,14 +3,17 @@
This is the list of all noteworthy changes made in every public
release of the tool. See README.md for the general instruction manual.
### Version ++4.21a (dev)
### Version ++4.21c (release)
* afl-fuzz
- fixed a regression in afl-fuzz that resulted in a 5-10% performace loss
do a switch from gettimeofday() to clock_gettime() which should be rather
three times faster. The reason for this is unknown.
- new queue selection algorithm based on 2 core years of queue data
analysis. gives a noticable improvement on coverage although the results
seem counterintuitive :-)
- added AFL_DISABLE_REDUNDANT for huge queues
- fix AFL_PERSISTENT_RECORD
- added `AFL_NO_SYNC` environment variable that does what you think it does
- fix AFL_PERSISTENT_RECORD
- run custom_post_process after standard trimming
- prevent filenames in the queue that have spaces
- minor fix for FAST schedules
@ -20,6 +23,9 @@
- -V timing is now accurately the fuzz time (without syncing), before
long calibration times and syncing could result in now fuzzing being
made when the time was already run out until then, thanks to @eqv!
- fix -n uninstrumented mode when ending fuzzing
- enhanced the ASAN configuration
- make afl-fuzz use less memory with cmplog and fix a memleak
* afl-cc:
- re-enable i386 support that was accidently disabled
- fixes for LTO and outdated afl-gcc mode for i386
@ -33,8 +39,8 @@
* afl-showmap
- fix memory leak on shmem testcase usage (thanks to @ndrewh)
- minor fix to collect coverage -C (thanks to @bet4it)
* Fixed a shmem mmap bug (that rarely came up on MacOS)
* libtokencap: script generate_libtoken_dict.sh added by @a-shvedov
* enhanced the ASAN configuration
### Version ++4.20c (release)

View File

@ -49,14 +49,23 @@ void instrument_cache_init(void) {
if (setrlimit(RLIMIT_AS, &data_limit) != 0) {
FFATAL("Failed to setrlimit: %d", errno);
FWARNF("Failed to setrlimit: %d, you may need root or CAP_SYS_RESOURCE",
errno);
}
map_base =
gum_memory_allocate(NULL, instrument_cache_size, instrument_cache_size,
GUM_PAGE_READ | GUM_PAGE_WRITE);
if (map_base == MAP_FAILED) { FFATAL("Failed to map segment: %d", errno); }
if (map_base == MAP_FAILED) {
FFATAL(
"Failed to map segment: %d. This can be caused by failure to setrlimit."
"Disabling or reducing the size of the allocation using "
"AFL_FRIDA_INST_NO_CACHE or AFL_FRIDA_INST_CACHE_SIZE may help",
errno);
}
FOKF(cBLU "Instrumentation" cRST " - " cGRN "cache addr:" cYEL " [0x%016lX]",
GUM_ADDRESS(map_base));

View File

@ -194,8 +194,7 @@ static gboolean print_ranges_callback(const GumRangeDetails *details,
if (details->file == NULL) {
FVERBOSE("\t0x%016" G_GINT64_MODIFIER "x-0x%016" G_GINT64_MODIFIER
"X %c%c%c",
OKF("\t0x%016" G_GINT64_MODIFIER "x-0x%016" G_GINT64_MODIFIER "X %c%c%c",
details->range->base_address,
details->range->base_address + details->range->size,
details->protection & GUM_PAGE_READ ? 'R' : '-',
@ -204,14 +203,14 @@ static gboolean print_ranges_callback(const GumRangeDetails *details,
} else {
FVERBOSE("\t0x%016" G_GINT64_MODIFIER "x-0x%016" G_GINT64_MODIFIER
OKF("\t0x%016" G_GINT64_MODIFIER "x-0x%016" G_GINT64_MODIFIER
"X %c%c%c %s(0x%016" G_GINT64_MODIFIER "x)",
details->range->base_address,
details->range->base_address + details->range->size,
details->protection & GUM_PAGE_READ ? 'R' : '-',
details->protection & GUM_PAGE_WRITE ? 'W' : '-',
details->protection & GUM_PAGE_EXECUTE ? 'X' : '-',
details->file->path, details->file->offset);
details->protection & GUM_PAGE_EXECUTE ? 'X' : '-', details->file->path,
details->file->offset);
}
@ -581,7 +580,7 @@ static GArray *merge_ranges(GArray *a) {
void ranges_print_debug_maps(void) {
FVERBOSE("Maps");
OKF("Maps");
gum_process_enumerate_ranges(GUM_PAGE_NO_ACCESS, print_ranges_callback, NULL);
}

View File

@ -656,6 +656,7 @@ typedef struct afl_state {
switch_fuzz_mode, /* auto or fixed fuzz mode */
calibration_time_us, /* Time spend on calibration */
sync_time_us, /* Time spend on sync */
cmplog_time_us, /* Time spend on cmplog */
trim_time_us; /* Time spend on trimming */
u32 slowest_exec_ms, /* Slowest testcase non hang in ms */
@ -1226,6 +1227,7 @@ void show_init_stats(afl_state_t *);
void update_calibration_time(afl_state_t *afl, u64 *time);
void update_trim_time(afl_state_t *afl, u64 *time);
void update_sync_time(afl_state_t *afl, u64 *time);
void update_cmplog_time(afl_state_t *afl, u64 *time);
/* StatsD */
@ -1276,6 +1278,7 @@ void get_core_count(afl_state_t *);
void fix_up_sync(afl_state_t *);
void check_asan_opts(afl_state_t *);
void check_binary(afl_state_t *, u8 *);
u64 get_binary_hash(u8 *fn);
void check_if_tty(afl_state_t *);
void save_cmdline(afl_state_t *, u32, char **);
void read_foreign_testcases(afl_state_t *, int);

View File

@ -26,7 +26,7 @@
/* Version string: */
// c = release, a = volatile github dev, e = experimental branch
#define VERSION "++4.21a"
#define VERSION "++4.21c"
/******************************************************
* *

View File

@ -1849,7 +1849,7 @@ void __sanitizer_cov_trace_pc_guard_init(uint32_t *start, uint32_t *stop) {
to avoid duplicate calls (which can happen as an artifact of the underlying
implementation in LLVM). */
if (__afl_final_loc < 5) __afl_final_loc = 5; // we skip the first 5 entries
if (__afl_final_loc < 4) __afl_final_loc = 4; // we skip the first 5 entries
*(start++) = ++__afl_final_loc;

View File

@ -1655,7 +1655,8 @@ void afl_fsrv_kill(afl_forkserver_t *fsrv) {
if (fsrv->fsrv_pid > 0) {
kill(fsrv->fsrv_pid, fsrv->fsrv_kill_signal);
waitpid(fsrv->fsrv_pid, NULL, 0);
usleep(25);
waitpid(fsrv->fsrv_pid, NULL, WNOHANG);
}

View File

@ -60,32 +60,6 @@ inline u32 select_next_queue_entry(afl_state_t *afl) {
}
double compute_weight(afl_state_t *afl, struct queue_entry *q,
double avg_exec_us, double avg_bitmap_size,
double avg_top_size) {
double weight = 1.0;
if (likely(afl->schedule >= FAST && afl->schedule <= RARE)) {
u32 hits = afl->n_fuzz[q->n_fuzz_entry];
if (likely(hits)) { weight /= (log10(hits) + 1); }
}
if (likely(afl->schedule < RARE)) { weight *= (avg_exec_us / q->exec_us); }
weight *= (log(q->bitmap_size) / avg_bitmap_size);
weight *= (1 + (q->tc_ref / avg_top_size));
if (unlikely(weight < 0.1)) { weight = 0.1; }
if (unlikely(q->favored)) { weight *= 5; }
if (unlikely(!q->was_fuzzed)) { weight *= 2; }
if (unlikely(q->fs_redundant)) { weight *= 0.8; }
return weight;
}
/* create the alias table that allows weighted random selection - expensive */
void create_alias_table(afl_state_t *afl) {
@ -117,7 +91,7 @@ void create_alias_table(afl_state_t *afl) {
double avg_exec_us = 0.0;
double avg_bitmap_size = 0.0;
double avg_top_size = 0.0;
double avg_len = 0.0;
u32 active = 0;
for (i = 0; i < n; i++) {
@ -129,7 +103,7 @@ void create_alias_table(afl_state_t *afl) {
avg_exec_us += q->exec_us;
avg_bitmap_size += log(q->bitmap_size);
avg_top_size += q->tc_ref;
avg_len += q->len;
++active;
}
@ -138,7 +112,7 @@ void create_alias_table(afl_state_t *afl) {
avg_exec_us /= active;
avg_bitmap_size /= active;
avg_top_size /= active;
avg_len /= active;
for (i = 0; i < n; i++) {
@ -146,8 +120,59 @@ void create_alias_table(afl_state_t *afl) {
if (likely(!q->disabled)) {
q->weight =
compute_weight(afl, q, avg_exec_us, avg_bitmap_size, avg_top_size);
double weight = 1.0;
{ // inline does result in a compile error with LTO, weird
if (likely(afl->schedule >= FAST && afl->schedule <= RARE)) {
u32 hits = afl->n_fuzz[q->n_fuzz_entry];
if (likely(hits)) { weight /= (log10(hits) + 1); }
}
if (likely(afl->schedule < RARE)) {
double t = q->exec_us / avg_exec_us;
if (likely(t < 0.1)) {
// nothing
} else if (likely(t <= 0.25))
weight *= 0.9;
else if (likely(t <= 0.5)) {
// nothing
} else if (likely(t < 1.0))
weight *= 1.15;
else if (unlikely(t > 2.5 && t < 5.0))
weight *= 1.1;
// else nothing
}
double l = q->len / avg_len;
if (likely(l < 0.1))
weight *= 0.75;
else if (likely(l < 0.25))
weight *= 1.1;
else if (unlikely(l >= 10))
weight *= 1.1;
double bms = q->bitmap_size / avg_bitmap_size;
if (likely(bms < 0.5))
weight *= (1.0 + ((bms - 0.5) / 2));
else if (unlikely(bms > 1.33))
weight *= 1.1;
if (unlikely(!q->was_fuzzed)) { weight *= 2.5; }
if (unlikely(q->fs_redundant)) { weight *= 0.75; }
}
q->weight = weight;
q->perf_score = calculate_score(afl, q);
sum += q->weight;
@ -596,6 +621,8 @@ void add_to_queue(afl_state_t *afl, u8 *fname, u32 len, u8 passed_det) {
q->trace_mini = NULL;
q->testcase_buf = NULL;
q->mother = afl->queue_cur;
q->weight = 1.0;
q->perf_score = 100;
#ifdef INTROSPECTION
q->bitsmap_size = afl->bitsmap_size;
@ -1201,9 +1228,11 @@ inline void queue_testcase_retake(afl_state_t *afl, struct queue_entry *q,
u32 len = q->len;
if (len != old_len) {
// only realloc if necessary or useful
// (a custom trim can make the testcase larger)
if (unlikely(len > old_len || len < old_len + 1024)) {
afl->q_testcase_cache_size = afl->q_testcase_cache_size + len - old_len;
afl->q_testcase_cache_size += len - old_len;
q->testcase_buf = (u8 *)realloc(q->testcase_buf, len);
if (unlikely(!q->testcase_buf)) {
@ -1232,22 +1261,25 @@ inline void queue_testcase_retake_mem(afl_state_t *afl, struct queue_entry *q,
if (likely(q->testcase_buf)) {
u32 is_same = in == q->testcase_buf;
if (likely(in != q->testcase_buf)) {
if (likely(len != old_len)) {
// only realloc if we save memory
if (unlikely(len < old_len + 1024)) {
u8 *ptr = (u8 *)realloc(q->testcase_buf, len);
if (likely(ptr)) {
q->testcase_buf = ptr;
afl->q_testcase_cache_size = afl->q_testcase_cache_size + len - old_len;
afl->q_testcase_cache_size += len - old_len;
}
}
if (unlikely(!is_same)) { memcpy(q->testcase_buf, in, len); }
memcpy(q->testcase_buf, in, len);
}
}
@ -1258,15 +1290,19 @@ inline void queue_testcase_retake_mem(afl_state_t *afl, struct queue_entry *q,
inline u8 *queue_testcase_get(afl_state_t *afl, struct queue_entry *q) {
if (likely(q->testcase_buf)) { return q->testcase_buf; }
u32 len = q->len;
double weight = q->weight;
/* first handle if no testcase cache is configured */
// first handle if no testcase cache is configured, or if the
// weighting of the testcase is below average.
if (unlikely(!afl->q_testcase_max_cache_size)) {
if (unlikely(weight < 1.0 || !afl->q_testcase_max_cache_size)) {
u8 *buf;
if (unlikely(q == afl->queue_cur)) {
if (likely(q == afl->queue_cur)) {
buf = (u8 *)afl_realloc((void **)&afl->testcase_buf, len);
@ -1292,9 +1328,7 @@ inline u8 *queue_testcase_get(afl_state_t *afl, struct queue_entry *q) {
}
/* now handle the testcase cache */
if (unlikely(!q->testcase_buf)) {
/* now handle the testcase cache and we know it is an interesting one */
/* Buf not cached, let's load it */
u32 tid = afl->q_testcase_max_cache_count;
@ -1308,18 +1342,17 @@ inline u8 *queue_testcase_get(afl_state_t *afl, struct queue_entry *q) {
/* We want a max number of entries to the cache that we learn.
Very simple: once the cache is filled by size - that is the max. */
if (unlikely(afl->q_testcase_cache_size + len >=
if (unlikely(
afl->q_testcase_cache_size + len >=
afl->q_testcase_max_cache_size &&
(afl->q_testcase_cache_count <
afl->q_testcase_max_cache_entries &&
(afl->q_testcase_cache_count < afl->q_testcase_max_cache_entries &&
afl->q_testcase_max_cache_count <
afl->q_testcase_max_cache_entries) &&
!do_once)) {
if (afl->q_testcase_max_cache_count > afl->q_testcase_cache_count) {
afl->q_testcase_max_cache_entries =
afl->q_testcase_max_cache_count + 1;
afl->q_testcase_max_cache_entries = afl->q_testcase_max_cache_count + 1;
} else {
@ -1405,8 +1438,6 @@ inline u8 *queue_testcase_get(afl_state_t *afl, struct queue_entry *q) {
}
}
return q->testcase_buf;
}
@ -1418,12 +1449,13 @@ inline void queue_testcase_store_mem(afl_state_t *afl, struct queue_entry *q,
u32 len = q->len;
if (unlikely(afl->q_testcase_cache_size + len >=
if (unlikely(q->weight < 1.0 ||
afl->q_testcase_cache_size + len >=
afl->q_testcase_max_cache_size ||
afl->q_testcase_cache_count >=
afl->q_testcase_max_cache_entries - 1)) {
// no space? will be loaded regularly later.
// no space or uninteresting? will be loaded regularly later.
return;
}

View File

@ -322,7 +322,7 @@ static u8 colorization(afl_state_t *afl, u8 *buf, u32 len,
memcpy(backup, buf, len);
memcpy(changed, buf, len);
if (afl->cmplog_random_colorization) {
if (likely(afl->cmplog_random_colorization)) {
random_replace(afl, changed, len);
@ -402,6 +402,7 @@ static u8 colorization(afl_state_t *afl, u8 *buf, u32 len,
u32 i = 1;
u32 positions = 0;
while (i) {
restart:
@ -2937,6 +2938,7 @@ static u8 rtn_fuzz(afl_state_t *afl, u32 key, u8 *orig_buf, u8 *buf, u8 *cbuf,
// afl->queue_cur->exec_cksum
u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
u64 cmplog_start_us = get_cur_time_us();
u8 r = 1;
if (unlikely(!afl->pass_stats)) {
@ -2965,7 +2967,12 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
if (!afl->queue_cur->taint || !afl->queue_cur->cmplog_colorinput) {
if (unlikely(colorization(afl, buf, len, &taint))) { return 1; }
if (unlikely(colorization(afl, buf, len, &taint))) {
update_cmplog_time(afl, &cmplog_start_us);
return 1;
}
// no taint? still try, create a dummy to prevent again colorization
if (!taint) {
@ -2974,6 +2981,7 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
fprintf(stderr, "TAINT FAILED\n");
#endif
afl->queue_cur->colorized = CMPLOG_LVL_MAX;
update_cmplog_time(afl, &cmplog_start_us);
return 0;
}
@ -2994,17 +3002,20 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
}
update_cmplog_time(afl, &cmplog_start_us);
struct tainted *t = taint;
#ifdef _DEBUG
while (t) {
#ifdef _DEBUG
fprintf(stderr, "T: idx=%u len=%u\n", t->pos, t->len);
#endif
t = t->next;
}
#endif
#if defined(_DEBUG) || defined(CMPLOG_INTROSPECTION)
u64 start_time = get_cur_time();
u32 cmp_locations = 0;
@ -3025,6 +3036,7 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
}
update_cmplog_time(afl, &cmplog_start_us);
return 1;
}
@ -3048,6 +3060,7 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
}
update_cmplog_time(afl, &cmplog_start_us);
return 1;
}
@ -3066,6 +3079,7 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
u64 orig_hit_cnt, new_hit_cnt;
u64 orig_execs = afl->fsrv.total_execs;
orig_hit_cnt = afl->queued_items + afl->saved_crashes;
update_cmplog_time(afl, &cmplog_start_us);
afl->stage_name = "input-to-state";
afl->stage_short = "its";
@ -3142,13 +3156,15 @@ u8 input_to_state_stage(afl_state_t *afl, u8 *orig_buf, u8 *buf, u32 len) {
}
update_cmplog_time(afl, &cmplog_start_us);
}
r = 0;
exit_its:
if (afl->cmplog_lvl == CMPLOG_LVL_MAX) {
// if (afl->cmplog_lvl == CMPLOG_LVL_MAX) {
afl->queue_cur->colorized = CMPLOG_LVL_MAX;
@ -3168,7 +3184,7 @@ exit_its:
afl->queue_cur->taint = NULL;
} else {
/*} else {
afl->queue_cur->colorized = LVL2;
@ -3182,7 +3198,7 @@ exit_its:
}
}
}*/
#ifdef CMPLOG_COMBINE
if (afl->queued_items + afl->saved_crashes > orig_hit_cnt + 1) {
@ -3270,6 +3286,7 @@ exit_its:
#endif
update_cmplog_time(afl, &cmplog_start_us);
return r;
}

View File

@ -33,15 +33,15 @@ u8 is_det_timeout(u64 cur_ms, u8 is_flip) {
u8 should_det_fuzz(afl_state_t *afl, struct queue_entry *q) {
if (!afl->skipdet_g->virgin_det_bits) {
if (unlikely(!afl->skipdet_g->virgin_det_bits)) {
afl->skipdet_g->virgin_det_bits =
(u8 *)ck_alloc(sizeof(u8) * afl->fsrv.map_size);
}
if (!q->favored || q->passed_det) return 0;
if (!q->trace_mini) return 0;
if (likely(!q->favored || q->passed_det)) return 0;
if (unlikely(!q->trace_mini)) return 0;
if (!afl->skipdet_g->last_cov_undet)
afl->skipdet_g->last_cov_undet = get_cur_time();
@ -122,7 +122,8 @@ u8 skip_deterministic_stage(afl_state_t *afl, u8 *orig_buf, u8 *out_buf,
afl->stage_cur = 0;
orig_hit_cnt = afl->queued_items + afl->saved_crashes;
u8 *inf_eff_map = (u8 *)ck_alloc(sizeof(u8) * len);
static u8 *inf_eff_map;
inf_eff_map = (u8 *)ck_realloc(inf_eff_map, sizeof(u8) * len);
memset(inf_eff_map, 1, sizeof(u8) * len);
if (common_fuzz_stuff(afl, orig_buf, len)) { return 0; }

View File

@ -769,8 +769,9 @@ void afl_states_stop(void) {
if (el->fsrv.fsrv_pid > 0) {
kill(el->fsrv.fsrv_pid, el->fsrv.fsrv_kill_signal);
usleep(100);
/* Make sure the forkserver does not end up as zombie. */
waitpid(el->fsrv.fsrv_pid, NULL, 0);
waitpid(el->fsrv.fsrv_pid, NULL, WNOHANG);
}

View File

@ -207,6 +207,12 @@ void load_stats_file(afl_state_t *afl) {
}
if (starts_with("cmplog_time", keystring)) {
afl->cmplog_time_us = strtoull(lptr, &nptr, 10) * 1000000;
}
if (starts_with("trim_time", keystring)) {
afl->trim_time_us = strtoull(lptr, &nptr, 10) * 1000000;
@ -322,8 +328,9 @@ void write_stats_file(afl_state_t *afl, u32 t_bytes, double bitmap_cvg,
if (getrusage(RUSAGE_CHILDREN, &rus)) { rus.ru_maxrss = 0; }
#endif
u64 runtime_ms = afl->prev_run_time + cur_time - afl->start_time;
u64 overhead_ms =
(afl->calibration_time_us + afl->sync_time_us + afl->trim_time_us) / 1000;
u64 overhead_ms = (afl->calibration_time_us + afl->sync_time_us +
afl->trim_time_us + afl->cmplog_time_us) /
1000;
if (!runtime_ms) { runtime_ms = 1; }
fprintf(
@ -337,6 +344,7 @@ void write_stats_file(afl_state_t *afl, u32 t_bytes, double bitmap_cvg,
"time_wo_finds : %llu\n"
"fuzz_time : %llu\n"
"calibration_time : %llu\n"
"cmplog_time : %llu\n"
"sync_time : %llu\n"
"trim_time : %llu\n"
"execs_done : %llu\n"
@ -385,8 +393,9 @@ void write_stats_file(afl_state_t *afl, u32 t_bytes, double bitmap_cvg,
? 0
: (cur_time - afl->last_find_time) / 1000),
(runtime_ms - MIN(runtime_ms, overhead_ms)) / 1000,
afl->calibration_time_us / 1000000, afl->sync_time_us / 1000000,
afl->trim_time_us / 1000000, afl->fsrv.total_execs,
afl->calibration_time_us / 1000000, afl->cmplog_time_us / 1000000,
afl->sync_time_us / 1000000, afl->trim_time_us / 1000000,
afl->fsrv.total_execs,
afl->fsrv.total_execs / ((double)(runtime_ms) / 1000),
afl->last_avg_execs_saved, afl->queued_items, afl->queued_favored,
afl->queued_discovered, afl->queued_imported, afl->queued_variable,
@ -2511,3 +2520,11 @@ inline void update_sync_time(afl_state_t *afl, u64 *time) {
}
inline void update_cmplog_time(afl_state_t *afl, u64 *time) {
u64 cur = get_cur_time_us();
afl->cmplog_time_us += cur - *time;
*time = cur;
}

View File

@ -915,9 +915,16 @@ int main(int argc, char **argv_orig, char **envp) {
u8 suffix = 'M';
if (mem_limit_given) { FATAL("Multiple -m options not supported"); }
if (mem_limit_given) {
WARNF("Overriding previous -m option.");
} else {
mem_limit_given = 1;
}
if (!optarg) { FATAL("Wrong usage of -m"); }
if (!strcmp(optarg, "none")) {
@ -1462,9 +1469,10 @@ int main(int argc, char **argv_orig, char **envp) {
#endif
configure_afl_kill_signals(&afl->fsrv, afl->afl_env.afl_child_kill_signal,
configure_afl_kill_signals(
&afl->fsrv, afl->afl_env.afl_child_kill_signal,
afl->afl_env.afl_fsrv_kill_signal,
(afl->fsrv.qemu_mode || afl->unicorn_mode
(afl->fsrv.qemu_mode || afl->unicorn_mode || afl->fsrv.use_fauxsrv
#ifdef __linux__
|| afl->fsrv.nyx_mode
#endif

View File

@ -95,6 +95,24 @@ inline u64 hash64(u8 *key, u32 len, u64 seed) {
}
/* Hash a file */
u64 get_binary_hash(u8 *fn) {
int fd = open(fn, O_RDONLY);
if (fd < 0) { PFATAL("Unable to open '%s'", fn); }
struct stat st;
if (fstat(fd, &st) < 0) { PFATAL("Unable to fstat '%s'", fn); }
u32 f_len = st.st_size;
u8 *f_data = mmap(0, f_len, PROT_READ, MAP_PRIVATE, fd, 0);
if (f_data == MAP_FAILED) { PFATAL("Unable to mmap file '%s'", fn); }
close(fd);
u64 hash = hash64(f_data, f_len, 0);
if (munmap(f_data, f_len)) { PFATAL("unmap() failed"); }
return hash;
}
// Public domain SHA1 implementation copied from:
// https://github.com/x42/liboauth/blob/7001b8256cd654952ec2515b055d2c5b243be600/src/sha1.c