Просмотр исходного кода

BProcess: restore signal dispositions and signal mask for the child

ambrop7 15 лет назад
Родитель
Сommit
d358e23c27
1 измененных файлов с 35 добавлено и 4 удалено
  1. 35 4
      process/BProcess.c

+ 35 - 4
process/BProcess.c

@@ -186,16 +186,39 @@ int BProcess_InitWithFds (BProcess *o, BProcessManager *m, BProcess_handler hand
     size_t num_fds;
     for (num_fds = 0; fds[num_fds] >= 0; num_fds++);
     
-    // fork
-    pid_t pid = fork();
-    if (pid < 0) {
-        BLog(BLOG_ERROR, "fork failed");
+    // block signals
+    // needed to prevent parent's signal handlers from being called
+    // in the child
+    sigset_t sset_all;
+    sigfillset(&sset_all);
+    sigset_t sset_old;
+    if (sigprocmask(SIG_SETMASK, &sset_all, &sset_old) < 0) {
+        BLog(BLOG_ERROR, "sigprocmask failed");
         goto fail0;
     }
     
+    // fork
+    pid_t pid = fork();
+    
     if (pid == 0) {
         // this is child
         
+        // restore signal dispositions
+        for (int i = 1; i < NSIG; i++) {
+            struct sigaction sa;
+            memset(&sa, 0, sizeof(sa));
+            sa.sa_handler = SIG_DFL;
+            sa.sa_flags = 0;
+            sigaction(i, &sa, NULL);
+        }
+        
+        // unblock signals
+        sigset_t sset_none;
+        sigemptyset(&sset_none);
+        if (sigprocmask(SIG_SETMASK, &sset_none, NULL) < 0) {
+            abort();
+        }
+        
         // copy fds array
         int *fds2 = malloc((num_fds + 1) * sizeof(fds2[0]));
         if (!fds2) {
@@ -282,6 +305,14 @@ int BProcess_InitWithFds (BProcess *o, BProcessManager *m, BProcess_handler hand
         abort();
     }
     
+    // restore original signal mask
+    ASSERT_FORCE(sigprocmask(SIG_SETMASK, &sset_old, NULL) == 0)
+    
+    if (pid < 0) {
+        BLog(BLOG_ERROR, "fork failed");
+        goto fail0;
+    }
+    
     // remember pid
     o->pid = pid;