about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorvan Hauser <vh@thc.org>2022-10-24 20:46:31 +0200
committerGitHub <noreply@github.com>2022-10-24 20:46:31 +0200
commita075cddef6ae71516a960116f3d944efd5671e5d (patch)
tree724dd6978ebb10f52c4bdda86eb44a5494b33409 /src
parentd1e1bbc713b22d620956143634ecdf97223aa59f (diff)
parent05e0825d66d938308842c25c4c74b5cdd4a885eb (diff)
downloadafl++-a075cddef6ae71516a960116f3d944efd5671e5d.tar.gz
Merge pull request #1561 from AFLplusplus/dev
push to stable
Diffstat (limited to 'src')
-rw-r--r--src/afl-analyze.c5
-rw-r--r--src/afl-cc.c2
-rw-r--r--src/afl-common.c54
-rw-r--r--src/afl-forkserver.c18
-rw-r--r--src/afl-fuzz-state.c23
-rw-r--r--src/afl-fuzz-stats.c12
-rw-r--r--src/afl-fuzz.c8
-rw-r--r--src/afl-showmap.c21
-rw-r--r--src/afl-tmin.c8
9 files changed, 102 insertions, 49 deletions
diff --git a/src/afl-analyze.c b/src/afl-analyze.c
index a21f014f..757c9306 100644
--- a/src/afl-analyze.c
+++ b/src/afl-analyze.c
@@ -114,7 +114,7 @@ static void kill_child() {
 
   if (fsrv.child_pid > 0) {
 
-    kill(fsrv.child_pid, fsrv.kill_signal);
+    kill(fsrv.child_pid, fsrv.child_kill_signal);
     fsrv.child_pid = -1;
 
   }
@@ -1115,8 +1115,7 @@ int main(int argc, char **argv_orig, char **envp) {
 
   }
 
-  fsrv.kill_signal =
-      parse_afl_kill_signal_env(getenv("AFL_KILL_SIGNAL"), SIGKILL);
+  configure_afl_kill_signals(&fsrv, NULL, NULL);
 
   read_initial_file();
   (void)check_binary_signatures(fsrv.target_path);
diff --git a/src/afl-cc.c b/src/afl-cc.c
index 469aa825..cd2061e6 100644
--- a/src/afl-cc.c
+++ b/src/afl-cc.c
@@ -955,7 +955,7 @@ static void edit_params(u32 argc, char **argv, char **envp) {
   if (plusplus_mode && strlen(libdir) && strncmp(libdir, "/usr", 4) &&
       strncmp(libdir, "/lib", 4)) {
 
-    cc_params[cc_par_cnt++] = "-rpath";
+    cc_params[cc_par_cnt++] = "-Wl,-rpath";
     cc_params[cc_par_cnt++] = libdir;
 
   } else {
diff --git a/src/afl-common.c b/src/afl-common.c
index f3e78ac5..6f5e4a38 100644
--- a/src/afl-common.c
+++ b/src/afl-common.c
@@ -25,6 +25,7 @@
 
 #include <stdlib.h>
 #include <stdio.h>
+#include "forkserver.h"
 #ifndef _GNU_SOURCE
   #define _GNU_SOURCE
 #endif
@@ -47,6 +48,7 @@
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <fcntl.h>
+#include <signal.h>
 
 u8  be_quiet = 0;
 u8 *doc_path = "";
@@ -456,38 +458,56 @@ u8 *find_afl_binary(u8 *own_loc, u8 *fname) {
 
 }
 
-/* Parses the kill signal environment variable, FATALs on error.
-  If the env is not set, sets the env to default_signal for the signal handlers
-  and returns the default_signal. */
-int parse_afl_kill_signal_env(u8 *afl_kill_signal_env, int default_signal) {
+int parse_afl_kill_signal(u8 *numeric_signal_as_str, int default_signal) {
 
-  if (afl_kill_signal_env && afl_kill_signal_env[0]) {
+  if (numeric_signal_as_str && numeric_signal_as_str[0]) {
 
     char *endptr;
     u8    signal_code;
-    signal_code = (u8)strtoul(afl_kill_signal_env, &endptr, 10);
+    signal_code = (u8)strtoul(numeric_signal_as_str, &endptr, 10);
     /* Did we manage to parse the full string? */
-    if (*endptr != '\0' || endptr == (char *)afl_kill_signal_env) {
+    if (*endptr != '\0' || endptr == (char *)numeric_signal_as_str) {
 
-      FATAL("Invalid AFL_KILL_SIGNAL: %s (expected unsigned int)",
-            afl_kill_signal_env);
+      FATAL("Invalid signal name: %s", numeric_signal_as_str);
+
+    } else {
+
+      return signal_code;
 
     }
 
-    return signal_code;
+  }
 
-  } else {
+  return default_signal;
 
-    char *sigstr = alloc_printf("%d", default_signal);
-    if (!sigstr) { FATAL("Failed to alloc mem for signal buf"); }
+}
 
-    /* Set the env for signal handler */
-    setenv("AFL_KILL_SIGNAL", sigstr, 1);
-    free(sigstr);
-    return default_signal;
+void configure_afl_kill_signals(afl_forkserver_t *fsrv,
+                                char             *afl_kill_signal_env,
+                                char             *afl_fsrv_kill_signal_env) {
+
+  afl_kill_signal_env =
+      afl_kill_signal_env ? afl_kill_signal_env : getenv("AFL_KILL_SIGNAL");
+  afl_fsrv_kill_signal_env = afl_fsrv_kill_signal_env
+                                 ? afl_fsrv_kill_signal_env
+                                 : getenv("AFL_FORK_SERVER_KILL_SIGNAL");
+
+  fsrv->child_kill_signal = parse_afl_kill_signal(afl_kill_signal_env, SIGKILL);
+
+  if (afl_kill_signal_env && !afl_fsrv_kill_signal_env) {
+
+    /*
+    Set AFL_FORK_SERVER_KILL_SIGNAL to the value of AFL_KILL_SIGNAL for
+    backwards compatibility. However, if AFL_FORK_SERVER_KILL_SIGNAL is set, is
+    takes precedence.
+    */
+    afl_fsrv_kill_signal_env = afl_kill_signal_env;
 
   }
 
+  fsrv->fsrv_kill_signal =
+      parse_afl_kill_signal(afl_fsrv_kill_signal_env, SIGTERM);
+
 }
 
 static inline unsigned int helper_min3(unsigned int a, unsigned int b,
diff --git a/src/afl-forkserver.c b/src/afl-forkserver.c
index 628ff590..a241f2c6 100644
--- a/src/afl-forkserver.c
+++ b/src/afl-forkserver.c
@@ -100,7 +100,7 @@ void afl_fsrv_init(afl_forkserver_t *fsrv) {
   fsrv->init_tmout = EXEC_TIMEOUT * FORK_WAIT_MULT;
   fsrv->mem_limit = MEM_LIMIT;
   fsrv->out_file = NULL;
-  fsrv->kill_signal = SIGKILL;
+  fsrv->child_kill_signal = SIGKILL;
 
   /* exec related stuff */
   fsrv->child_pid = -1;
@@ -134,7 +134,7 @@ void afl_fsrv_init_dup(afl_forkserver_t *fsrv_to, afl_forkserver_t *from) {
   fsrv_to->no_unlink = from->no_unlink;
   fsrv_to->uses_crash_exitcode = from->uses_crash_exitcode;
   fsrv_to->crash_exitcode = from->crash_exitcode;
-  fsrv_to->kill_signal = from->kill_signal;
+  fsrv_to->child_kill_signal = from->child_kill_signal;
   fsrv_to->debug = from->debug;
 
   // These are forkserver specific.
@@ -793,7 +793,7 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
       s32 tmp_pid = fsrv->fsrv_pid;
       if (tmp_pid > 0) {
 
-        kill(tmp_pid, fsrv->kill_signal);
+        kill(tmp_pid, fsrv->child_kill_signal);
         fsrv->fsrv_pid = -1;
 
       }
@@ -804,7 +804,7 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
       s32 tmp_pid = fsrv->fsrv_pid;
       if (tmp_pid > 0) {
 
-        kill(tmp_pid, fsrv->kill_signal);
+        kill(tmp_pid, fsrv->child_kill_signal);
         fsrv->fsrv_pid = -1;
 
       }
@@ -1242,11 +1242,11 @@ void afl_fsrv_start(afl_forkserver_t *fsrv, char **argv,
 
 void afl_fsrv_kill(afl_forkserver_t *fsrv) {
 
-  if (fsrv->child_pid > 0) { kill(fsrv->child_pid, fsrv->kill_signal); }
+  if (fsrv->child_pid > 0) { kill(fsrv->child_pid, fsrv->child_kill_signal); }
   if (fsrv->fsrv_pid > 0) {
 
-    kill(fsrv->fsrv_pid, fsrv->kill_signal);
-    if (waitpid(fsrv->fsrv_pid, NULL, 0) <= 0) { WARNF("error waitpid\n"); }
+    kill(fsrv->fsrv_pid, fsrv->fsrv_kill_signal);
+    waitpid(fsrv->fsrv_pid, NULL, 0);
 
   }
 
@@ -1545,7 +1545,7 @@ afl_fsrv_run_target(afl_forkserver_t *fsrv, u32 timeout,
     s32 tmp_pid = fsrv->child_pid;
     if (tmp_pid > 0) {
 
-      kill(tmp_pid, fsrv->kill_signal);
+      kill(tmp_pid, fsrv->child_kill_signal);
       fsrv->child_pid = -1;
 
     }
@@ -1605,7 +1605,7 @@ afl_fsrv_run_target(afl_forkserver_t *fsrv, u32 timeout,
   /* Did we timeout? */
   if (unlikely(fsrv->last_run_timed_out)) {
 
-    fsrv->last_kill_signal = fsrv->kill_signal;
+    fsrv->last_kill_signal = fsrv->child_kill_signal;
     return FSRV_RUN_TMOUT;
 
   }
diff --git a/src/afl-fuzz-state.c b/src/afl-fuzz-state.c
index 5199f7e6..8bd465f0 100644
--- a/src/afl-fuzz-state.c
+++ b/src/afl-fuzz-state.c
@@ -23,6 +23,7 @@
 
  */
 
+#include <signal.h>
 #include "afl-fuzz.h"
 #include "envs.h"
 
@@ -487,7 +488,14 @@ void read_afl_environment(afl_state_t *afl, char **envp) {
 
                               afl_environment_variable_len)) {
 
-            afl->afl_env.afl_kill_signal =
+            afl->afl_env.afl_child_kill_signal =
+                (u8 *)get_afl_env(afl_environment_variables[i]);
+
+          } else if (!strncmp(env, "AFL_FORK_SERVER_KILL_SIGNAL",
+
+                              afl_environment_variable_len)) {
+
+            afl->afl_env.afl_fsrv_kill_signal =
                 (u8 *)get_afl_env(afl_environment_variables[i]);
 
           } else if (!strncmp(env, "AFL_TARGET_ENV",
@@ -654,8 +662,17 @@ void afl_states_stop(void) {
 
   LIST_FOREACH(&afl_states, afl_state_t, {
 
-    if (el->fsrv.child_pid > 0) kill(el->fsrv.child_pid, el->fsrv.kill_signal);
-    if (el->fsrv.fsrv_pid > 0) kill(el->fsrv.fsrv_pid, el->fsrv.kill_signal);
+    /* NOTE: We need to make sure that the parent (the forkserver) reap the
+     * child (see below). */
+    if (el->fsrv.child_pid > 0)
+      kill(el->fsrv.child_pid, el->fsrv.child_kill_signal);
+    if (el->fsrv.fsrv_pid > 0) {
+
+      kill(el->fsrv.fsrv_pid, el->fsrv.fsrv_kill_signal);
+      /* Make sure the forkserver does not end up as zombie. */
+      waitpid(el->fsrv.fsrv_pid, NULL, 0);
+
+    }
 
   });
 
diff --git a/src/afl-fuzz-stats.c b/src/afl-fuzz-stats.c
index 713f3a3c..61956dc3 100644
--- a/src/afl-fuzz-stats.c
+++ b/src/afl-fuzz-stats.c
@@ -1410,9 +1410,15 @@ void show_stats_pizza(afl_state_t *afl) {
 
   /* AFL_EXIT_ON_TIME. */
 
-  if (unlikely(afl->last_find_time && !afl->non_instrumented_mode &&
-               afl->afl_env.afl_exit_on_time &&
-               (cur_ms - afl->last_find_time) > afl->exit_on_time)) {
+  /* If no coverage was found yet, check whether run time is greater than
+   * exit_on_time. */
+
+  if (unlikely(
+          !afl->non_instrumented_mode && afl->afl_env.afl_exit_on_time &&
+          ((afl->last_find_time &&
+            (cur_ms - afl->last_find_time) > afl->exit_on_time) ||
+           (!afl->last_find_time && (afl->prev_run_time + cur_ms -
+                                     afl->start_time) > afl->exit_on_time)))) {
 
     afl->stop_soon = 2;
 
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index d116822a..6ff4d266 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -25,6 +25,7 @@
 
 #include "afl-fuzz.h"
 #include "cmplog.h"
+#include "common.h"
 #include <limits.h>
 #include <stdlib.h>
 #ifndef USEMMAP
@@ -261,6 +262,9 @@ static void usage(u8 *argv0, int more_help) {
       "AFL_INPUT_LEN_MIN/AFL_INPUT_LEN_MAX: like -g/-G set min/max fuzz length produced\n"
       "AFL_PIZZA_MODE: 1 - enforce pizza mode, 0 - disable for April 1st\n"
       "AFL_KILL_SIGNAL: Signal ID delivered to child processes on timeout, etc. (default: SIGKILL)\n"
+      "AFL_FORK_SERVER_KILL_SIGNAL: Signal delivered to fork server processes on termination\n"
+      "                             (default: SIGTERM). If this is not set and AFL_KILL_SIGNAL is set,\n"
+      "                             this will be set to the same value.\n"
       "AFL_MAP_SIZE: the shared memory size for that target. must be >= the size\n"
       "              the target was compiled for\n"
       "AFL_MAX_DET_EXTRAS: if more entries are in the dictionary list than this value\n"
@@ -1358,8 +1362,8 @@ int main(int argc, char **argv_orig, char **envp) {
 
   #endif
 
-  afl->fsrv.kill_signal =
-      parse_afl_kill_signal_env(afl->afl_env.afl_kill_signal, SIGKILL);
+  configure_afl_kill_signals(&afl->fsrv, afl->afl_env.afl_child_kill_signal,
+                             afl->afl_env.afl_fsrv_kill_signal);
 
   setup_signal_handlers();
   check_asan_opts(afl);
diff --git a/src/afl-showmap.c b/src/afl-showmap.c
index 0b724758..ce1f8004 100644
--- a/src/afl-showmap.c
+++ b/src/afl-showmap.c
@@ -129,7 +129,7 @@ static void kill_child() {
   timed_out = 1;
   if (fsrv->child_pid > 0) {
 
-    kill(fsrv->child_pid, fsrv->kill_signal);
+    kill(fsrv->child_pid, fsrv->child_kill_signal);
     fsrv->child_pid = -1;
 
   }
@@ -822,8 +822,8 @@ static void usage(u8 *argv0) {
       "  -o file    - file to write the trace data to\n\n"
 
       "Execution control settings:\n"
-      "  -t msec    - timeout for each run (none)\n"
-      "  -m megs    - memory limit for child process (%u MB)\n"
+      "  -t msec    - timeout for each run (default: 1000ms)\n"
+      "  -m megs    - memory limit for child process (default: none)\n"
 #if defined(__linux__) && defined(__aarch64__)
       "  -A         - use binary-only instrumentation (ARM CoreSight mode)\n"
 #endif
@@ -864,8 +864,14 @@ static void usage(u8 *argv0) {
       "AFL_DEBUG: enable extra developer output\n"
       "AFL_FORKSRV_INIT_TMOUT: time spent waiting for forkserver during "
       "startup (in milliseconds)\n"
-      "AFL_KILL_SIGNAL: Signal ID delivered to child processes on timeout, "
-      "etc. (default: SIGKILL)\n"
+      "AFL_KILL_SIGNAL: Signal ID delivered to child processes on timeout,\n"
+      "                 etc. (default: SIGKILL)\n"
+      "AFL_FORK_SERVER_KILL_SIGNAL: Signal delivered to fork server processes "
+      "on termination\n"
+      "                             (default: SIGTERM). If this is not set and "
+      "AFL_KILL_SIGNAL is set,\n"
+      "                             this will be set to the same value as "
+      "AFL_KILL_SIGNAL.\n"
       "AFL_MAP_SIZE: the shared memory size for that target. must be >= the "
       "size the target was compiled for\n"
       "AFL_PRELOAD: LD_PRELOAD / DYLD_INSERT_LIBRARIES settings for target\n"
@@ -873,7 +879,7 @@ static void usage(u8 *argv0) {
       "printed to stdout\n"
       "AFL_QUIET: do not print extra informational output\n"
       "AFL_NO_FORKSRV: run target via execve instead of using the forkserver\n",
-      argv0, MEM_LIMIT, doc_path);
+      argv0, doc_path);
 
   exit(1);
 
@@ -1258,8 +1264,7 @@ int main(int argc, char **argv_orig, char **envp) {
                                  : 0);
     be_quiet = save_be_quiet;
 
-    fsrv->kill_signal =
-        parse_afl_kill_signal_env(getenv("AFL_KILL_SIGNAL"), SIGKILL);
+    configure_afl_kill_signals(fsrv, NULL, NULL);
 
     if (new_map_size) {
 
diff --git a/src/afl-tmin.c b/src/afl-tmin.c
index 694c9c21..3a27b879 100644
--- a/src/afl-tmin.c
+++ b/src/afl-tmin.c
@@ -113,7 +113,7 @@ static void kill_child() {
 
   if (fsrv->child_pid > 0) {
 
-    kill(fsrv->child_pid, fsrv->kill_signal);
+    kill(fsrv->child_pid, fsrv->child_kill_signal);
     fsrv->child_pid = -1;
 
   }
@@ -881,6 +881,9 @@ static void usage(u8 *argv0) {
       "AFL_CRASH_EXITCODE: optional child exit code to be interpreted as crash\n"
       "AFL_FORKSRV_INIT_TMOUT: time spent waiting for forkserver during startup (in milliseconds)\n"
       "AFL_KILL_SIGNAL: Signal ID delivered to child processes on timeout, etc. (default: SIGKILL)\n"
+      "AFL_FORK_SERVER_KILL_SIGNAL: Signal delivered to fork server processes on termination\n"
+      "                             (default: SIGTERM). If this is not set and AFL_KILL_SIGNAL is set,\n"
+      "                             this will be set to the same value as AFL_KILL_SIGNAL.\n"
       "AFL_MAP_SIZE: the shared memory size for that target. must be >= the size\n"
       "              the target was compiled for\n"
       "AFL_PRELOAD:  LD_PRELOAD / DYLD_INSERT_LIBRARIES settings for target\n"
@@ -1195,8 +1198,7 @@ int main(int argc, char **argv_orig, char **envp) {
 
   }
 
-  fsrv->kill_signal =
-      parse_afl_kill_signal_env(getenv("AFL_KILL_SIGNAL"), SIGKILL);
+  configure_afl_kill_signals(fsrv, NULL, NULL);
 
   if (getenv("AFL_CRASH_EXITCODE")) {