about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--docs/Changelog.md1
-rw-r--r--instrumentation/afl-compiler-rt.o.c22
-rw-r--r--src/afl-fuzz.c9
3 files changed, 27 insertions, 5 deletions
diff --git a/docs/Changelog.md b/docs/Changelog.md
index 9426ed54..3c20f8bd 100644
--- a/docs/Changelog.md
+++ b/docs/Changelog.md
@@ -38,6 +38,7 @@ sending a mail to <afl-users+subscribe@googlegroups.com>.
     - added INTROSPECTION make target that writes all mutations to
       out/NAME/introspection.txt
     - print special compile time options used in help output
+    - when using -c cmplog, one of the childs was not killed, fixed
     - somewhere we broke -n dumb fuzzing, fixed
   - instrumentation
     - We received an enhanced gcc_plugin module from AdaCore, thank you
diff --git a/instrumentation/afl-compiler-rt.o.c b/instrumentation/afl-compiler-rt.o.c
index 485f500c..b07aeb83 100644
--- a/instrumentation/afl-compiler-rt.o.c
+++ b/instrumentation/afl-compiler-rt.o.c
@@ -101,6 +101,11 @@ int __afl_sharedmem_fuzzing __attribute__((weak));
 
 struct cmp_map *__afl_cmp_map;
 
+/* Child pid? */
+
+static s32 child_pid;
+static void (*old_sigterm_handler)(int) = 0;
+
 /* Running in persistent mode? */
 
 static u8 is_persistent;
@@ -109,6 +114,14 @@ static u8 is_persistent;
 
 static u8 _is_sancov;
 
+/* ensure we kill the child on termination */
+
+void at_exit(int signal) {
+
+  if (child_pid > 0) { kill(child_pid, SIGKILL); }
+
+}
+
 /* Uninspired gcc plugin instrumentation */
 
 void __afl_trace(const u32 x) {
@@ -432,7 +445,6 @@ static void __afl_map_shm(void) {
 static void __afl_start_snapshots(void) {
 
   static u8 tmp[4] = {0, 0, 0, 0};
-  s32       child_pid;
   u32       status = 0;
   u32       already_read_first = 0;
   u32       was_killed;
@@ -579,6 +591,7 @@ static void __afl_start_snapshots(void) {
         //(void)nice(-20);  // does not seem to improve
 
         signal(SIGCHLD, old_sigchld_handler);
+        signal(SIGTERM, old_sigterm_handler);
 
         close(FORKSRV_FD);
         close(FORKSRV_FD + 1);
@@ -633,6 +646,11 @@ static void __afl_start_snapshots(void) {
 
 static void __afl_start_forkserver(void) {
 
+  struct sigaction orig_action;
+  sigaction(SIGTERM, NULL, &orig_action);
+  old_sigterm_handler = orig_action.sa_handler;
+  signal(SIGTERM, at_exit);
+
 #ifdef __linux__
   if (/*!is_persistent &&*/ !__afl_cmp_map && !getenv("AFL_NO_SNAPSHOT") &&
       afl_snapshot_init() >= 0) {
@@ -645,7 +663,6 @@ static void __afl_start_forkserver(void) {
 #endif
 
   u8  tmp[4] = {0, 0, 0, 0};
-  s32 child_pid;
   u32 status = 0;
   u32 already_read_first = 0;
   u32 was_killed;
@@ -793,6 +810,7 @@ static void __afl_start_forkserver(void) {
         //(void)nice(-20);
 
         signal(SIGCHLD, old_sigchld_handler);
+        signal(SIGTERM, old_sigterm_handler);
 
         close(FORKSRV_FD);
         close(FORKSRV_FD + 1);
diff --git a/src/afl-fuzz.c b/src/afl-fuzz.c
index 1008f28c..b60908da 100644
--- a/src/afl-fuzz.c
+++ b/src/afl-fuzz.c
@@ -40,7 +40,7 @@ extern u64 time_spent_working;
 
 static void at_exit() {
 
-  int   i;
+  s32   i, pid1 = 0, pid2 = 0;
   char *list[4] = {SHM_ENV_VAR, SHM_FUZZ_ENV_VAR, CMPLOG_SHM_ENV_VAR, NULL};
   char *ptr;
 
@@ -48,10 +48,10 @@ static void at_exit() {
   if (ptr && *ptr) unlink(ptr);
 
   ptr = getenv("__AFL_TARGET_PID1");
-  if (ptr && *ptr && (i = atoi(ptr)) > 0) kill(i, SIGKILL);
+  if (ptr && *ptr && (pid1 = atoi(ptr)) > 0) kill(pid1, SIGTERM);
 
   ptr = getenv("__AFL_TARGET_PID2");
-  if (ptr && *ptr && (i = atoi(ptr)) > 0) kill(i, SIGKILL);
+  if (ptr && *ptr && (pid2 = atoi(ptr)) > 0) kill(pid2, SIGTERM);
 
   i = 0;
   while (list[i] != NULL) {
@@ -75,6 +75,9 @@ static void at_exit() {
 
   }
 
+  if (pid1 > 0) { kill(pid1, SIGKILL); }
+  if (pid2 > 0) { kill(pid2, SIGKILL); }
+
 }
 
 /* Display usage hints. */