我正在尝试将信号从子进程发送到 C 中的父进程,并且我有一个信号处理程序设置:
void handler(int signumber,siginfo_t* info,void* nonused)
{
printf("Signal with number %i has arrived\n",signumber);
switch (info->si_code){
case SI_USER: printf("Process (PID number %i) sent the signal (calling kill)\n",info->si_pid); break;
case SI_TIMER: printf("It was sent by a timer\n");
printf("Additional data: %i\n",info->si_value.sival_int);
// timer_delete(t_id); //stops timer
break;
case SI_QUEUE: printf("It was sent by a sigqueue, sending process (PID %i)\n",info->si_pid);
printf("Additional value: %i\n",info->si_value.sival_int);
// struct student* d=(struct student*)info->si_value.sival_ptr;
// printf("Additional value: %s, %i\n",d->name,d->year);
break;
default: printf("It was sent by something else \n");
}
}
并尝试使用 sigqueue 发送带有附加数据的信号:
struct sigaction action;
action.sa_sigaction = handler;
sigemptyset(&action.sa_mask);
action.sa_flags=SA_SIGINFO;
if (sigaction(SIGTERM, &action, NULL) < 0)
{
perror("Sigaction failed");
exit(1);
}
pid = fork();
if (pid == -1)
{
perror("Forking error");
exit(EXIT_FAILURE);
}
if (pid == 0) //child process
{
printf("Child process (PID %i), will send a SIGTERM to parent %i\n",getpid(),getppid());
// sleep(1);
// kill(getppid(),SIGTERM); //this works
//sending an integer as an additional data
sleep(1);
union sigval s_value_int={5};
sigqueue(getppid(),SIGTERM,s_value_int);
printf("Child process ended\n");
}
else
{
printf("Parent (PID %i) waits for a signal from child (PID %i) \n",getpid(),pid);
pause();
wait(NULL);
printf("Parent process ended\n");
}
问题是,我没有收到任何类型的输出(来自处理程序)并且父进程永远冻结(由于pause()
调用而等待来自子进程的信号),因此我怀疑信号永远不会到达。“子进程结束”将输出到控制台。
有趣的是,如果我通过 发送信号kill()
,父母会很好地接收它,并且处理程序也会打印出附加信息。不幸的是,我需要sigqueue 替代方案,因为我必须向父级发送一个额外的整数作为数据。我读到了可能的信号丢失,因为太多的信号进入并且他们排队,这可能也是我的问题吗?如果是这样,可以做些什么来解决它?非常感谢