C 子进程的setpgid:没有这样的进程
我不知道为什么我的电脑会出现这样的错误。我已经在其他一些计算机上测试了代码。它工作得很好 如果我删除C 子进程的setpgid:没有这样的进程,c,unix,operating-system,C,Unix,Operating System,我不知道为什么我的电脑会出现这样的错误。我已经在其他一些计算机上测试了代码。它工作得很好 如果我删除睡眠(2),它就会工作。我想我应该能够为僵尸进程设置PGID。它是否依赖于操作系统的实现 #include <unistd.h> #include <stdlib.h> #include <stdio.h> #define CHECK(syscall, msg) do { \ if ((syscall) == -1
睡眠(2)
,它就会工作。我想我应该能够为僵尸进程设置PGID。它是否依赖于操作系统的实现
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#define CHECK(syscall, msg) do { \
if ((syscall) == -1) { \
perror(msg); \
_exit(1); \
} \
} while(0)
#define SAFE_CLOSE_NOT_STD(fd) do { \
if (fd != STDIN_FILENO && fd != STDOUT_FILENO && fd != -1) { \
CHECK(close(fd), "close error"); \
fd = -1; \
} \
} while(0)
int main () {
int ls_pid;
char *ls_argv[] = { "ls", NULL };
CHECK(ls_pid = fork(), "fork error");
if (!ls_pid) {
CHECK(setpgid(0, 0), "child setpgid error");
CHECK(execvp(ls_argv[0], ls_argv), "execve error");
} else {
printf("child pid:%d\n", ls_pid);
sleep(2); // no error arises if I remove this line
CHECK(setpgid(ls_pid, ls_pid), "setpgid error"); // error here
}
CHECK(wait(NULL), "wait error");
printf("Finish\n");
}
#包括
#包括
#包括
#定义检查(syscall,msg)do{\
如果((系统调用)=-1){\
佩罗尔(味精)\
_出口(1)\
} \
}而(0)
#定义安全关闭非标准(fd)do{\
如果(fd!=STDIN\u FILENO&&fd!=STDOUT\u FILENO&&fd!=-1){\
检查(关闭(fd),“关闭错误”)\
fd=-1\
} \
}而(0)
int main(){
int ls_pid;
char*ls_argv[]={“ls”,NULL};
检查(ls_pid=fork(),“fork error”);
如果(!ls_pid){
检查(setpgid(0,0),“子setpgid错误”);
检查(execvp(ls_argv[0],ls_argv),“execve error”);
}否则{
printf(“子pid:%d\n”,ls\u pid);
sleep(2);//如果删除此行,则不会出现错误
检查(setpgid(ls_-pid,ls_-pid),“setpgid错误”);//此处有错误
}
检查(等待(空),“等待错误”);
printf(“Finish\n”);
}
由于子进程已退出且不再存在,因此睡眠时会出现错误。当执行僵尸进程的父进程切换到子进程,子进程中的执行进程用新进程替换当前进程并退出时,你不能对僵尸进程执行任何操作,除非调用等待。当它在2秒后返回到父进程时
子进程不存在,这就是setpgid
失败的原因
CHECK(setpgid(ls_pid, ls_pid), "setpgid error");
从setpgid
的手册页可以看到,这是一个EACCES
错误
试图更改的进程组ID
调用进程和
孩子已经执行了一个execve(2)(setpgid(),
setpgrp())。假设我在子进程退出之前更改了它的PGID。现在,子进程和父进程具有不同的PGID。哪一个是前台组?在任何时候,会话中只有一个进程组可以是终端的前台进程组;其余的进程组位于后台。