Unix 如何捕获execvp的输出

Unix 如何捕获execvp的输出,unix,named-pipes,Unix,Named Pipes,我正在开发一个程序,它使用execvp执行一个程序。它需要捕获子进程的结果并在主进程中解析它们。似乎有一种方法,使用命名管道和复制。我正在努力寻找一个很好的例子,但到目前为止运气不好。如果有人对此有任何建议、链接和/或建议,我将不胜感激 您不能只使用popen()吗?您不需要命名管道;未命名的管道工作正常。实际上,通常您可以使用popen而不是自己执行管道/分叉/dup/execpopen是这样工作的(尽管libc的实现可能有更多的错误检查): 这将创建一个未命名的管道和forks。在子级中,它

我正在开发一个程序,它使用execvp执行一个程序。它需要捕获子进程的结果并在主进程中解析它们。似乎有一种方法,使用命名管道和复制。我正在努力寻找一个很好的例子,但到目前为止运气不好。如果有人对此有任何建议、链接和/或建议,我将不胜感激

您不能只使用popen()吗?

您不需要命名管道;未命名的管道工作正常。实际上,通常您可以使用
popen
而不是自己执行
管道
/
分叉
/
dup
/
exec
popen
是这样工作的(尽管
libc
的实现可能有更多的错误检查):


这将创建一个未命名的管道和
fork
s。在子级中,它将stdout(或stdin)重新连接到管道的一端,然后执行子级。家长只需从管道的另一端读取(或写入)。

下面是一个简单的示例,演示如何使用popen实现您的目标。只需将比“echo”更有趣的内容作为命令:)

#包括
int main()
{
char-buf[100];
int i=0;
文件*p=popen(“echo\“Test\”,“r”);
如果(p!=NULL)
{
而(!feof(p)&(i<99))
{
fread(&buf[i++],1,1,p);
}
buf[i]=0;
printf(“%s”,buf);
pclose(p);
返回0;
}
其他的
{
返回-1;
}
}

相关:很好。我已经回顾了管道是如何工作的,这应该会起到作用。如果有人无意中发现了这一点,请记录在案。基于类型[0]的条件不完全正确。需要在dup2之前关闭stdout/stdin,以使其成为可能。此外,管道是单向的,fds[1]是写入端,因此对于读取案例,它需要是dup2中的fds[0]。@TommiKyntola来自
dup2
手册页:“使
newfd
成为
oldfd
的副本,如有必要,首先关闭
newfd
”,这样就可以在不首先手动关闭stdout/stdin的情况下工作。
FILE *popen(const char *command, const char *type) {
    int fds[2];
    const char *argv[4] = {"/bin/sh", "-c", command};
    pipe(fds);
    if (fork() == 0) {
        close(fds[0]);
        dup2(type[0] == 'r' ? 0 : 1, fds[1]);
        close(fds[1]);
        execvp(argv[0], argv);
        exit(-1);
    }
    close(fds[1]);
    return fdopen(fds[0], type);
}
#include <stdio.h>

int main() 
{
    char buf[100];
    int i = 0;
    FILE *p = popen("echo \"Test\"","r");
    if (p != NULL )
    {
        while (!feof(p) && (i < 99) )
        {
            fread(&buf[i++],1,1,p);
        }
        buf[i] = 0;
        printf("%s",buf);
        pclose(p);
        return 0;
    }
    else
    {
        return -1;
    }
}