我有一个使用Qt Framework的简单程序。它使用QProcess执行RAR并压缩一些文件。在我的程序中,我正在捕获SIGINT并在发生代码时做一些事情:
SIGINT
signal(SIGINT, &unix_handler);
当SIGINT发生时,我检查RAR进程是否完成,如果不是,我将等待它……问题是(我认为)RAR进程也得到SIGINT了我的程序所需要的,并且在压缩之前退出了所有的文件。
有没有一种方法可以运行RAR进程,以便SIGINT在程序接收到它时不接收它?
谢谢
如果要在Unix系统上SIGINT使用Ctrl+ 生成with C,则信号将发送到整个进程组。
Ctrl
C
您需要使用setpgid或setid将子进程放入另一个进程组,以便它不会接收控制终端生成的信号。
[编辑:]
确保setpgid仔细阅读页面的RATIONALE部分。在这里插入所有潜在的比赛条件有点棘手。
setpgid
为了保证100%不会SIGINT向您的子进程发送任何内容,您需要执行以下操作:
#define CHECK(x) if(!(x)) { perror(#x " failed"); abort(); /* or whatever */ } /* Block SIGINT. */ sigset_t mask, omask; sigemptyset(&mask); sigaddset(&mask, SIGINT); CHECK(sigprocmask(SIG_BLOCK, &mask, &omask) == 0); /* Spawn child. */ pid_t child_pid = fork(); CHECK(child_pid >= 0); if (child_pid == 0) { /* Child */ CHECK(setpgid(0, 0) == 0); execl(...); abort(); } /* Parent */ if (setpgid(child_pid, child_pid) < 0 && errno != EACCES) abort(); /* or whatever */ /* Unblock SIGINT */ CHECK(sigprocmask(SIG_SETMASK, &omask, NULL) == 0);
严格来说,这些步骤中的每一个都是必要的。您必须封锁讯号,以防使用者在拨打电话后立即按下Ctrl+ 。您必须召集孩子,以防万一在父母有时间做任何事情之前发生。您必须打电话给父母,以防 父母 奔跑而有人在_孩子_ 有时间做任何事情之前打+。C``fork``setpgid``execl``setpgid Ctrl`` C
C``fork``setpgid``execl``setpgid
Ctrl`` C
上面的序列很笨拙,但确实可以处理100%的比赛条件。