gpt4 book ai didi

c - 为什么 sigchld_handler 也会得到一个 SIGTSTP?

转载 作者:太空狗 更新时间:2023-10-29 12:42:34 26 4
gpt4 key购买 nike

我正在制作一个小的shell程序。我想在sigtstp_handler中暂停前台程序。和sigchld_handler来获取zombie 。但是当我输入 ctrl z 时,即使我没有前台程序,sigchld_handler 仍然会得到 SIGTSTP。

    Signal(SIGINT,  sigint_handler);   /* ctrl-c */
Signal(SIGTSTP, sigtstp_handler); /* ctrl-z */
Signal(SIGCHLD, sigchld_handler); /* Terminated or stopped child */

处理程序

void sigchld_handler(int sig) 
{
int status;
pid_t pid;

while ((pid = waitpid(-1, &status, WNOHANG | WUNTRACED)) > 0 ) {

if (WIFEXITED(status)) { /*checks if child terminated normally */
deletejob(jobs, pid);
}

if (WIFSIGNALED(status)) { /*checks if child was terminated by a signal that was not caught */
printf("Job [%d] (%d) terminated by signal %d\n", pid2jid(pid), pid, WTERMSIG(status));
deletejob(jobs,pid);
}

if (WIFSTOPPED(status)) { /*checks if child process that caused return is currently stopped */
getjobpid(jobs, pid)->state = ST;
printf("Job [%d] (%d) stopped by signal %d\n", pid2jid(pid), pid, WTERMSIG(status));
//printf("[%d] Stopped %s\n", pid2jid(pid), jobs->cmdline);
}

}
if (pid < 0 && errno != ECHILD) {
printf("waitpid error: %s\n", strerror(errno));
}

return;
}


void sigtstp_handler(int sig)
{
pid_t pid = fgpid(jobs);//Return PID of current foreground job, 0 if no such job

if (pid!=0){
struct job_t *p = getjobpid(jobs, pid);
printf("kill %d %s %d\n",p->pid,p->cmdline,p->state);

kill(pid,SIGTSTP);
}
return;
}

void sigint_handler(int sig)
{

pid_t pid = fgpid(jobs);
if (pid!=0){
struct job_t *p = getjobpid(jobs, pid);
printf("kill %d %s %d\n",p->pid,p->cmdline,p->state);
kill(pid,SIGINT);
}
return;
}

我只是setpgid(0,0),在我fork一个子进程后,就解决了这个问题。但我不知道到底是怎么回事.. .

最佳答案

您必须有一个前台进程(如果您使用终端)。如果您没有启动子进程,则 shell 本身处于前台状态,TSTP 的接收者也是如此。前台/后台管理需要做的不仅仅是信号处理。您需要设置进程组并声明哪个组是前台组。

基本任务是:

  1. 在启动命令时创建一个组(setpgid)
  2. 如果需要,将该组声明为前台组 (tcsetpgrp)
  3. 让 shell 了解子状态变化(处理 SIGCHLD 和状态 WIFSTOPPED/WSTOPPED 并相应地管理您的作业列表
  4. 使交互式 shell 对 SIGTSTP 不敏感(忽略 shell 中的这个信号)

作业控制是一项艰巨的任务...请仔细阅读文档。

关于c - 为什么 sigchld_handler 也会得到一个 SIGTSTP?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37110442/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com