|
@@ -87,7 +87,7 @@ static int run_count = 1;
|
|
|
static bool no_inherit = false;
|
|
|
static bool scale = true;
|
|
|
static enum aggr_mode aggr_mode = AGGR_GLOBAL;
|
|
|
-static pid_t child_pid = -1;
|
|
|
+static volatile pid_t child_pid = -1;
|
|
|
static bool null_run = false;
|
|
|
static int detailed_run = 0;
|
|
|
static bool big_num = true;
|
|
@@ -1148,13 +1148,34 @@ static void skip_signal(int signo)
|
|
|
done = 1;
|
|
|
|
|
|
signr = signo;
|
|
|
+ /*
|
|
|
+ * render child_pid harmless
|
|
|
+ * won't send SIGTERM to a random
|
|
|
+ * process in case of race condition
|
|
|
+ * and fast PID recycling
|
|
|
+ */
|
|
|
+ child_pid = -1;
|
|
|
}
|
|
|
|
|
|
static void sig_atexit(void)
|
|
|
{
|
|
|
+ sigset_t set, oset;
|
|
|
+
|
|
|
+ /*
|
|
|
+ * avoid race condition with SIGCHLD handler
|
|
|
+ * in skip_signal() which is modifying child_pid
|
|
|
+ * goal is to avoid send SIGTERM to a random
|
|
|
+ * process
|
|
|
+ */
|
|
|
+ sigemptyset(&set);
|
|
|
+ sigaddset(&set, SIGCHLD);
|
|
|
+ sigprocmask(SIG_BLOCK, &set, &oset);
|
|
|
+
|
|
|
if (child_pid != -1)
|
|
|
kill(child_pid, SIGTERM);
|
|
|
|
|
|
+ sigprocmask(SIG_SETMASK, &oset, NULL);
|
|
|
+
|
|
|
if (signr == -1)
|
|
|
return;
|
|
|
|