我在某些代码中看到了以下用法:

struct sigaction term_handler;  // global variable without initialization
...
sigaction(SIGTERM, &term_handler, NULL);  // install uninitialized sigaction for SIGTERM


这段代码似乎分配了sigaction struct,使所有成员都为null或0,这让我感到非常困惑。
如果触发SIGTERM,会发生什么?

我使用以下代码进行了测试:

struct sigaction int_handler;
int main(int argc, char **argv) {
    sigaction(SIGINT, &int_handler, NULL);
    while(1) {}
    return 0;
}


并使用“ kill -2”进行测试,该过程以任何方式被杀死。这是否意味着该进程已采取与其信号相关的默认操作?

最佳答案

SIG_DFL在我的系统上为零,因此,如果您有一个类似的系统,则它将导致SIGTERM采取其默认行为。

除非事先修改了SIGTERM的行为(包括在exec程序之前),否则此操作无效。如果是这样,将还原默认行为(杀死进程)。



以下说明:

a.c

#include <signal.h>
#include <string.h>
#include <sys/types.h>
#include <unistd.h>

static struct sigaction term_handler;

int main(int argv, char* argc[]) {
   if (argv && strcmp(argc[0], "1") == 0)
      sigaction(SIGTERM, &term_handler, NULL);

   kill(getpid(), SIGTERM);
   sleep(2);
   return 0;
}


harness.c

#include <signal.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <stdio.h>

void test(const char* arg) {
   pid_t pid = fork();
   if (pid) {
      int status;
      waitpid(pid, &status, 0);
      printf("%d\n", WIFSIGNALED(status) ? WTERMSIG(status) : 0);
   } else {
      struct sigaction term_handler;
      char * const newargv[]    = { "./a", arg, NULL };
      char * const newenviron[] = { NULL };

      term_handler.sa_handler = SIG_IGN;
      sigaction(SIGTERM, &term_handler, NULL);

      execve("./a", newargv, newenviron);
   }
}

int main() {
   test("0");
   test("1");
   return 0;
}


输出:

$ ./harness
0     # Without sigaction in child, wasn't killed by a signal
15    # With    sigaction in child, was killed by TERM

关于c - 使用未初始化的sigaction结构调用sigaction?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20755252/

10-12 00:43