【发布时间】:2018-07-26 16:20:41
【问题描述】:
我想创建一个函数,在其中传递一个结构,该结构将存储生成的进程的 pid。
bool spawnHost(string ttyNumber, DeviceData &deviceData)
{
pid_t processID = fork();
pid_t hostProcessID = -1;
if (processID == -1)
{
printf("PID:%d-> Unable to fork a new process. Error: %s", getpid(), strerror(errno));
return false;
}
else if (!processID)
{
printf("PID:%d-> First child spawned. In Parent: %s", getpid(), processID);
signal(SIGCHLD, SIG_IGN);
hostProcessID = fork();
if (hostProcessID == -1)
{
printf("PID:%d-> Unable to fork a new process. Error: %s", getpid(), strerror(errno));
return false;
}
else if (!hostProcessID)
{
printf("PID:%d-> Starting %s at tty:%s", getpid(), hostAppPath.c_str(), ttyNumber.c_str());
char *args[] = { (char *) hostAppPath.c_str(), (char *) ttyNumber.c_str(), NULL };
execvp(hostAppPath.c_str(), args);
}
else
{
printf("PID:%d-> First child spawned. In child: %s", getpid(), hostProcessID);
sleep(5);
exit(0);
}
}
else
{
int childStatus;
waitpid(processID, &childStatus, 0);
if (WIFEXITED(childStatus))
printf("PID:%d has exited with exit code %d\n", processID, WEXITSTATUS(childStatus));
deviceData.setProcessID(hostProcessID);
return true;
}
}
这里的要求是宿主进程(在第二个 fork 中产生)不能死亡,即使父进程死亡,宿主进程的 pid 应该存储在传递给 spawnHost() 的结构中功能。目前我无法获得 pid。我这个东东有问题吗?
我什至尝试了以下方法:
bool spawnHost(string ttyNumber, DeviceData deviceData)
{
string hostAppPath = EXE_PATH;
signal(SIGCHLD, SIG_IGN);
pid_t processID = fork();
if (processID == -1)
{
printf("PID:%d-> Unable to fork a new process. Error: %s", getpid(), strerror(errno));
return false;
}
else if (!processID)
{
signal(SIGCHLD, SIG_IGN);
processID = fork();
if (processID == -1)
{
printf("PID:%d-> Unable to fork a new process. Error: %s", getpid(), strerror(errno));
return false;
}
else if (!processID)
{
if (setsid() < 0)
{
printf("PID:%d-> Unable to set new session ID. Error: %s", getpid(), strerror(errno));
return false;
}
printf("PID:%d-> Starting %s at tty:%s", getpid(), hostAppPath.c_str(), ttyNumber.c_str());
char *args[] = { (char *) hostAppPath.c_str(), (char *) ttyNumber.c_str(), NULL };
execvp(hostAppPath.c_str(), args);
}
else
{
deviceData.setProcessID(processID);
exit(0);
}
}
else
{
return true;
}
return true;
}
【问题讨论】:
-
在 Linux 上,您可以在 /proc 中跟踪进程层次结构。
-
您需要致电
pipe2(fds,O_CLOEXEC),并使用它来传递信息,直到流程开始。我在这里编写了执行此操作的代码:github.com/o11c/python-vterm/blob/master/vterm/c-sources/… -
@JesperJuhl 我试图获取第二个方法的进程树,因为新进程是在新会话中启动的,因此它嵌套在 init 进程中并且不属于主进程树
-
@o11c 非常感谢,它成功了。我能够得到孙子 pid。