#include<stdlib.h>
#include<unistd.h>
#include<signal.h>
int main(){
pid_t pid = fork();
if(pid==0){
system("watch ls");
}
else{
sleep(5);
killpg(getpid(),SIGTERM); //to kill the complete process tree.
}
return 0;
}
终端:
anirudh@anirudh-Aspire-5920:~/Desktop/testing$ gcc test.c
anirudh@anirudh-Aspire-5920:~/Desktop/testing$ ./a.out
Terminated
在前5秒显示“watch ls”的输出,然后它终止,因为我发送了一个SIGTERM。
问题:一个进程如何杀死自己?我做过kill(getpid(),SIGTERM);
我的假设: 所以在kill()调用期间,进程切换到内核模式。 kill调用将SIGTERM发送到进程并将其复制到进程的进程表中。当进程返回到用户模式时,它会看到其表中的信号并终止自身(如何?我真的不知道) (我想我错了(可能是一个错误)在我的假设的某个地方......所以请赐教)
这段代码实际上是一个存根,我用它来测试我项目的其他模块。 它为我做的工作,我很高兴,但在我的脑海里有一个问题,一个过程实际上是如何杀死自己的。我想知道一步一步的假设。
提前致谢
Anirudh Tomer
答案 0 :(得分:2)
您的流程因为使用killpg()
而死亡,它会向流程组发送信号,而不是向流程发送信号。
当你fork()
时,孩子们从父亲那里继承了过程组。来自man fork
:
* The child's parent process ID is the same as the parent's process ID.
所以你和孩子一起杀了父母。
如果你做了一个简单的kill(getpid(), SIGTERM)
,那么父亲会杀死孩子(即watch
ls
},然后就会安静地退出。
答案 1 :(得分:1)
所以在kill()调用期间,进程切换到内核模式。 kill调用将SIGTERM发送到进程并将其复制到进程的进程表中。当进程回到用户模式时,它会看到表中的信号,并自动终止(如何?我真的不知道)
在Linux中,当从内核模式返回到用户空间模式时,内核会检查是否有可以传递的待处理信号。如果有一些它在返回用户空间模式之前传递信号。它还可以在其他时间传递信号,例如,如果进程在select()
上被阻止然后被杀死,或者当线程访问未映射的内存位置时。
答案 2 :(得分:0)
我认为当它在其进程表中看到SIGTERM信号时,它首先会杀死它的子进程(因为我调用了killpg(),所以完成了树)然后调用了exit()。
我仍在寻找这个问题的更好答案。
答案 3 :(得分:0)
kill(getpid(), SIGKILL); // itself I think
我在fork
之后使用案例0测试了它:它从单独的父进程中退出常规。
我不知道这是否是标准认证方法....
(我可以从我的psensor工具中看到,CPU使用率在正常程序代码中返回34% 一个柜台停了。)
答案 4 :(得分:-4)
这在Perl中非常简单:
{
local $SIG{TERM} = "IGNORE";
kill TERM => -$$;
}
转换为C留给读者练习。