如何产生不与父亲一起死亡的儿童过程?

zac*_*618 6 c++ linux fork parent-child spawn

我有一个C++程序,可以作为其他人的监督者.如果它检测到进程不再运行,则通过它重新启动它system.问题是,如果我杀死看门狗进程,它启动的任何进程也会死掉.

void* ProcessWatchdog::worker(void* arg)
{
    //Check if process is running
    if( !processRunning )
        system("processName /path/to/processConfig.xml &");
}
Run Code Online (Sandbox Code Playgroud)

新的子进程正确启动,并且运行没有任何问题.但是当父母(现在这个ProcessWatchdog过程)死亡时,孩子也会死亡.如何生成完全独立于父级的子进程?

我已经尝试过使用pclosepopen运行启动进程的shell脚本,以及其他一些策略,但无济于事.我忽略SIGHUP了子进程中的信号,但它们仍然死亡.

理想情况下,我想告诉系统启动一个完全独立于父级的进程.我希望孩子trace以孩子结束,因为它/系统不知道从一ProcessWatchdog开始就开始了它.

有没有办法可以做到这一点?

我在Linux上用C++编写这个.

gru*_*ubs 5

这个有点旧,但没有得到完整的答案。这是我在嵌入式系统上所做的,以生成与父级无关的 bash 子级。请注意,我执行了一个 bash shell,然后在另一个 bash shell 中运行我的命令。在您的情况下,这可能不是必需的。对我来说,它允许我做一些没有它就不能正常工作的 I/O 重定向。

两个重要的概念是setsid() 和双fork()。这两者的结合可以防止在孤儿完成时创建僵尸,以及在父完成时防止孤儿被杀死。

还有许多其他问题可能会出现,例如继承的 I/O 句柄、工作目录等,但此代码完成了基本工作。

int spawn_orphan(char* cmd) {
    char command[1024]; // We could segfault if cmd is longer than 1000 bytes or so
    int pid;
    int Stat;
    pid = fork();
    if (pid < 0) { perror("FORK FAILED\n"); return pid; }
    if (pid == 0) { // CHILD
        setsid(); // Make this process the session leader of a new session
        pid = fork();
        if (pid < 0) { printf("FORK FAILED\n"); exit(1); }
        if (pid == 0) { // GRANDCHILD
            sprintf(command,"bash -c '%s'",cmd);
            execl("/bin/bash", "bash", "-c", command, NULL); // Only returns on error
            perror("execl failed");
            exit(1);
        }
        exit(0); // SUCCESS (This child is reaped below with waitpid())
    }

    // Reap the child, leaving the grandchild to be inherited by init
    waitpid(pid, &Stat, 0);
    if ( WIFEXITED(Stat) && (WEXITSTATUS(Stat) == 0) ) {
        return 0; // Child forked and exited successfully
    }
    else {
        perror("failed to spawn orphan\n");
        return -1;
    }
}
Run Code Online (Sandbox Code Playgroud)


din*_*elk 1

尝试在进程名称之前使用systemwith 。setsid

system("setsid processname /path/to/processConfig.xml &");
Run Code Online (Sandbox Code Playgroud)

这将在新会话中启动该程序。