【问题标题】:C - Parent process waits indefinitely on forked child process running authopenC - 父进程无限期等待运行 authopen 的分叉子进程
【发布时间】:2014-12-04 00:33:14
【问题描述】:

我试图让我的父进程等待运行authopen 的子分支,以写入具有提升权限的文件。父进程中的wait/waitpid 无限期挂起,以便子进程终止。我相信这是因为authopen 在程序退出之前不会释放文件。

authopen 写入的文件在程序的生命周期内被锁定,因此无法读取该文件,无法使用另一个authopen 进程写入该文件,并在例如打开该文件。 vim 在程序退出之前不会显示文件的内容。

首先,我想了解这里发生了什么。 execl完成后,不应该也释放所有资源吗?

其次,我想要一些解决方案。

下面是一个演示问题的程序。

我的平台是 OSX。

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>
#include <string.h>

int main(int argc, const char * argv[]) {

    int pip[2];

    if (pipe(pip) != 0) exit(1);    //error creating pipe

    pid_t processId;
    processId = fork();

    if (processId == -1) exit(1);    //pipe error

    if (processId == 0) {   //child process

        //close 'write end' of pipe
        close(pip[1]);

        //close stdin and duplicate the 'read end' of pipe to stdin
        close(0);
        dup(pip[0]);

        //run authopen
        const char * authopenPath = "/usr/libexec/authopen";

        execl(authopenPath, authopenPath, "-c","-w","/usr/local/authopenTest.txt",NULL);

        _exit(1);    //exec* does not return in case of success.
    }
    else {      //parent process

        //close 'read end' of pipe
        close(pip[0]);

        //write to 'write end' of pipe
        char * cstr = "write this to file...";
        write(pip[1], cstr, (strlen(cstr)));

        int status;
        //waitpid(0, &status, WNOHANG);     //this is ok, but doesn't block on child completing
        int p_id = wait(&status);           //PROBLEM: this hangs indefinitely. Why?
        if(p_id != -1)  {
            printf("Exit status %d\n", status);
        }
    }

    return 0;
}

【问题讨论】:

  • 在你dup(pip[0])之后你应该close(pip[0])
  • 但更重要的是,父节点需要关闭 pip[1],因为子节点可能会阻塞从管道读取。
  • 是的,authopen 在其标准输入上收到 EOF 之前不会退出。
  • 感谢两位的洞察力。 @william Closing pip[1] 在父级做到了。如果您提交,我可以接受作为答案。

标签: c macos pipe exec fork


【解决方案1】:

您需要在完成写入后关闭管道。否则,阅读器继续等待更多数据。例如:

write(pip[1], ...);
close(pip[1]);
wait(...);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-24
    • 2013-08-11
    相关资源
    最近更新 更多