带有信号的Fork()子进程

时间:2018-10-22 22:33:45

标签: linux process signals fork

我必须派生两个被阻止SIGINT命令的子进程,但是其中一个应在收到SIGTERM信号时解除对它的阻止,而另一个子进程和父进程都将由于同一个SIGTERM而打印其PID信号。第二个子进程应立即终止,但父进程应等待其子进程结束然后停止。

我刚刚开始学习Linux中的C编程,但我真的不太了解分叉和信号的工作方式。据我了解,到目前为止,我编写的这段代码将派生一个进程,子进程将阻止Ctrl-C命令,并且除非我使用kill -9 pid < / em>。

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>

void handler(int n) {
    write(STDOUT_FILENO, "I won't die!! Haha\n",13);
}

int main()
{
    pid_t pid = fork();
    if (pid < 0) {
        perror("Fork() error!");
        exit(-1);
    }
    if (pid == 0)
        signal(SIGINT,handler);
    while(1) {
        printf("Wasting the iteration. %d\n", getpid());
        sleep(1);
    }
    return 0;
}
  • 我如何使用SIGTERM?我应该在哪里打电话?
  • 如何让父级创建另一个也会阻止Ctrl-C命令的子级进程?

1 个答案:

答案 0 :(得分:0)

不确定是否要分叉多个进程,因为我从未这样做过。就SIGTERM而言,您需要一个回调来处理终止信号。以下是我在编写的许多服务中使用的一个:

/***************************************************************************************************
 * Function signal_callback_handler - allows for a graceful shutdown process.
 * *************************************************************************************************/
void signal_callback_handler(int signum) {
    //here we receive some sort of notification to terminate.
    //Log this event and change the state of the process control variable
    //so that the main processing loop knows to stop
    syslog(LOG_NOTICE, "Recived signal to shutdown - Signal %d", signum);
    //put code here to do preshutdown clean up, terminating threads, etc....
}

然后,您需要为要处理的每个终止信号注册回调。以下是我在分叉之前放置在主函数中的变量:

if (signal(SIGINT, signal_callback_handler) == SIG_ERR) {
    syslog(LOG_CRIT, "An error occurred while setting SIGINT signal handler.");
    return(EXIT_FAILURE);
}
if (signal(SIGUSR1, signal_callback_handler) == SIG_ERR) {
    syslog(LOG_CRIT, "An error occurred while setting SIGUSR1 signal handler.");
    return(EXIT_FAILURE);
}
if (signal(SIGUSR2, signal_callback_handler) == SIG_ERR) {
    syslog(LOG_CRIT, "An error occurred while setting SIGUSR signal handler.");
    return(EXIT_FAILURE);
}
if (signal(SIGTERM, signal_callback_handler) == SIG_ERR) {
    syslog(LOG_CRIT, "An error occurred while setting SIGTERM signal handler.");
    return(EXIT_FAILURE);
}
if (signal(SIGTSTP, signal_callback_handler) == SIG_ERR) {
    syslog(LOG_CRIT, "An error occurred while setting SIGTSTP signal handler.");
    return(EXIT_FAILURE);
}