aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorvan Hauser <vh@thc.org>2020-05-25 16:40:55 +0200
committervan Hauser <vh@thc.org>2020-05-25 16:40:55 +0200
commit707145c491366825b5595eada29fbb2e87e800fd (patch)
treed18c72f88e2d69b171a71815d62e3dedf92b0270 /src
parent4c394a9d7b0477811531e8567dccb043a9c4a279 (diff)
downloadafl++-707145c491366825b5595eada29fbb2e87e800fd.tar.gz
persistent mode: shared memory test case transfer
Diffstat (limited to 'src')
-rw-r--r--src/afl-forkserver.c79
-rw-r--r--src/afl-fuzz-init.c24
-rw-r--r--src/afl-fuzz-run.c10
-rw-r--r--src/afl-fuzz.c8
4 files changed, 100 insertions, 21 deletions
diff --git a/src/afl-forkserver.c b/src/afl-forkserver.c
index b67aedde..137a4f99 100644
--- a/src/afl-forkserver.c
+++ b/src/afl-forkserver.c
@@ -442,7 +442,7 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
if ((status & FS_OPT_ENABLED) == FS_OPT_ENABLED) {
- if (!be_quiet && getenv("AFL_DEBUG")) {
+ if (getenv("AFL_DEBUG")) {
ACTF("Extended forkserver functions received (%08x).", status);
@@ -455,6 +455,28 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
}
+ if ((status & FS_OPT_SHDMEM_FUZZ) == FS_OPT_SHDMEM_FUZZ) {
+
+ if (fsrv->support_shdmen_fuzz) {
+
+ fsrv->use_shdmen_fuzz = 1;
+ if (!be_quiet) { ACTF("Using SHARED MEMORY FUZZING feature."); }
+
+ if ((status & FS_OPT_AUTODICT) == 0) {
+
+ u32 send_status = (FS_OPT_ENABLED | FS_OPT_SHDMEM_FUZZ);
+ if (write(fsrv->fsrv_ctl_fd, &send_status, 4) != 4) {
+
+ FATAL("Writing to forkserver failed.");
+
+ }
+
+ }
+
+ }
+
+ }
+
if ((status & FS_OPT_MAPSIZE) == FS_OPT_MAPSIZE) {
u32 tmp_map_size = FS_OPT_GET_MAPSIZE(status);
@@ -490,7 +512,10 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
if (fsrv->function_ptr == NULL || fsrv->function_opt == NULL) {
// this is not afl-fuzz - we deny and return
- status = (0xffffffff ^ (FS_OPT_ENABLED | FS_OPT_AUTODICT));
+ if (fsrv->use_shdmen_fuzz)
+ status = (FS_OPT_ENABLED | FS_OPT_AUTODICT | FS_OPT_SHDMEM_FUZZ);
+ else
+ status = (FS_OPT_ENABLED | FS_OPT_AUTODICT);
if (write(fsrv->fsrv_ctl_fd, &status, 4) != 4) {
FATAL("Writing to forkserver failed.");
@@ -749,39 +774,48 @@ static void afl_fsrv_kill(afl_forkserver_t *fsrv) {
void afl_fsrv_write_to_testcase(afl_forkserver_t *fsrv, u8 *buf, size_t len) {
- s32 fd = fsrv->out_fd;
+ if (fsrv->shdmem_fuzz) {
- if (fsrv->out_file) {
+ memcpy(fsrv->shdmem_fuzz, buf, len);
+ fsrv->shdmem_fuzz_len = len;
- if (fsrv->no_unlink) {
+ } else {
- fd = open(fsrv->out_file, O_WRONLY | O_CREAT | O_TRUNC, 0600);
+ s32 fd = fsrv->out_fd;
- } else {
+ if (fsrv->out_file) {
- unlink(fsrv->out_file); /* Ignore errors. */
- fd = open(fsrv->out_file, O_WRONLY | O_CREAT | O_EXCL, 0600);
+ if (fsrv->no_unlink) {
- }
+ fd = open(fsrv->out_file, O_WRONLY | O_CREAT | O_TRUNC, 0600);
- if (fd < 0) { PFATAL("Unable to create '%s'", fsrv->out_file); }
+ } else {
- } else {
+ unlink(fsrv->out_file); /* Ignore errors. */
+ fd = open(fsrv->out_file, O_WRONLY | O_CREAT | O_EXCL, 0600);
- lseek(fd, 0, SEEK_SET);
+ }
- }
+ if (fd < 0) { PFATAL("Unable to create '%s'", fsrv->out_file); }
- ck_write(fd, buf, len, fsrv->out_file);
+ } else {
- if (!fsrv->out_file) {
+ lseek(fd, 0, SEEK_SET);
- if (ftruncate(fd, len)) { PFATAL("ftruncate() failed"); }
- lseek(fd, 0, SEEK_SET);
+ }
- } else {
+ ck_write(fd, buf, len, fsrv->out_file);
- close(fd);
+ if (!fsrv->out_file) {
+
+ if (ftruncate(fd, len)) { PFATAL("ftruncate() failed"); }
+ lseek(fd, 0, SEEK_SET);
+
+ } else {
+
+ close(fd);
+
+ }
}
@@ -795,6 +829,7 @@ fsrv_run_result_t afl_fsrv_run_target(afl_forkserver_t *fsrv, u32 timeout,
s32 res;
u32 exec_ms;
+ u32 write_value = fsrv->last_run_timed_out;
/* After this memset, fsrv->trace_bits[] are effectively volatile, so we
must prevent any earlier operations from venturing into that
@@ -804,10 +839,12 @@ fsrv_run_result_t afl_fsrv_run_target(afl_forkserver_t *fsrv, u32 timeout,
MEM_BARRIER();
+ if (fsrv->shdmem_fuzz_len) write_value += (fsrv->shdmem_fuzz_len << 8);
+
/* we have the fork server (or faux server) up and running
First, tell it if the previous run timed out. */
- if ((res = write(fsrv->fsrv_ctl_fd, &fsrv->last_run_timed_out, 4)) != 4) {
+ if ((res = write(fsrv->fsrv_ctl_fd, &write_value, 4)) != 4) {
if (*stop_soon_p) { return 0; }
RPFATAL(res, "Unable to request new process from fork server (OOM?)");
diff --git a/src/afl-fuzz-init.c b/src/afl-fuzz-init.c
index dd85a8f4..9349fefe 100644
--- a/src/afl-fuzz-init.c
+++ b/src/afl-fuzz-init.c
@@ -2153,6 +2153,30 @@ void check_binary(afl_state_t *afl, u8 *fname) {
OKF(cPIN "Persistent mode binary detected.");
setenv(PERSIST_ENV_VAR, "1", 1);
afl->persistent_mode = 1;
+ // do not fail if we can not get the fuzzing shared mem
+ if ((afl->shm_fuzz = calloc(1, sizeof(sharedmem_t)))) {
+
+ // we need to set the dumb mode to not overwrite the SHM_ENV_VAR
+ if ((afl->fsrv.shdmem_fuzz = afl_shm_init(afl->shm_fuzz, MAX_FILE, 1))) {
+
+#ifdef USEMMAP
+ setenv(SHM_FUZZ_ENV_VAR, afl->shm_fuzz->g_shm_file_path, 1);
+#else
+ u8 *shm_str;
+ shm_str = alloc_printf("%d", afl->shm_fuzz->shm_id);
+ setenv(SHM_FUZZ_ENV_VAR, shm_str, 1);
+ ck_free(shm_str);
+#endif
+ afl->fsrv.support_shdmen_fuzz = 1;
+
+ } else {
+
+ free(afl->shm_fuzz);
+ afl->shm_fuzz = NULL;
+
+ }
+
+ }
} else if (getenv("AFL_PERSISTENT")) {
diff --git a/src/afl-fuzz-run.c b/src/afl-fuzz-run.c
index 8a1f02a7..04450363 100644
--- a/src/afl-fuzz-run.c
+++ b/src/afl-fuzz-run.c
@@ -231,6 +231,16 @@ u8 calibrate_case(afl_state_t *afl, struct queue_entry *q, u8 *use_mem,
afl_fsrv_start(&afl->fsrv, afl->argv, &afl->stop_soon,
afl->afl_env.afl_debug_child_output);
+ if (afl->fsrv.support_shdmen_fuzz && !afl->fsrv.use_shdmen_fuzz) {
+
+ afl_shm_deinit(afl->shm_fuzz);
+ free(afl->shm_fuzz);
+ afl->shm_fuzz = NULL;
+ afl->fsrv.support_shdmen_fuzz = 0;
+ afl->fsrv.shdmem_fuzz = NULL;
+
+ }
+
}
if (q->exec_cksum) {
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index c07371a8..e024e9a4 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -1379,6 +1379,14 @@ stop_fuzzing:
destroy_extras(afl);
destroy_custom_mutators(afl);
afl_shm_deinit(&afl->shm);
+
+ if (afl->shm_fuzz) {
+
+ afl_shm_deinit(afl->shm_fuzz);
+ free(afl->shm_fuzz);
+
+ }
+
afl_fsrv_deinit(&afl->fsrv);
if (afl->orig_cmdline) { ck_free(afl->orig_cmdline); }
ck_free(afl->fsrv.target_path);