猿问

将exec输出重定向到缓冲区或文件

我正在写一个C程序中我fork()exec()wait()。我想将执行的程序的输出写入文件或缓冲区。

例如,如果我执行,ls 我想写入file1 file2 etc缓冲区/文件。我认为没有办法读取stdout,这是否意味着我必须使用管道?这里有我找不到的一般程序吗?


慕田峪7331174
浏览 759回答 3
3回答

跃然一笑

为了将输出发送到另一个文件(我省去了错误检查,将重点放在重要的细节上):if (fork() == 0){    // child    int fd = open(file, O_RDWR | O_CREAT, S_IRUSR | S_IWUSR);    dup2(fd, 1);   // make stdout go to file    dup2(fd, 2);   // make stderr go to file - you may choose to not do this                   // or perhaps send stderr to another file    close(fd);     // fd no longer needed - the dup'ed handles are sufficient    exec(...);}要将输出发送到管道,以便随后将输出读入缓冲区:int pipefd[2];pipe(pipefd);if (fork() == 0){    close(pipefd[0]);    // close reading end in the child    dup2(pipefd[1], 1);  // send stdout to the pipe    dup2(pipefd[1], 2);  // send stderr to the pipe    close(pipefd[1]);    // this descriptor is no longer needed    exec(...);}else{    // parent    char buffer[1024];    close(pipefd[1]);  // close the write end of the pipe in the parent    while (read(pipefd[0], buffer, sizeof(buffer)) != 0)    {    }}

呼唤远方

您需要准确地决定要做什么-最好对其进行更清晰的说明。选项1:文件如果知道要将执行的命令的输出转到哪个文件,则:确保父母和孩子在姓名上达成一致(父母在分叉之前确定姓名)。父叉-您有两个过程。子级重新组织事物,以便文件描述符1(标准输出)进入文件。通常,您可以不理会标准错误;您可以从/ dev / null重定向标准输入。然后孩子执行相关命令;该命令运行,所有标准输出到达文件(这是基本的Shell I / O重定向)。然后执行的过程终止。同时,父流程可以采用以下两种主要策略之一:打开文件进行读取,并继续读取直到到达EOF。然后,它需要仔细检查孩子是否死亡(因此不再需要读取任何数据),或者闲逛以等待孩子的更多输入。等待孩子死亡,然后打开文件进行阅读。第一个优点是父母可以在孩子还奔跑的同时做一些工作。第二个优点是您不必迷惑I / O系统(重复读取过去的EOF)。选项2:管道如果希望父级从子级读取输出,请安排子级将其输出通过管道返回给父级。使用popen()可以很容易地做到这一点。它将运行该进程并将输出发送到您的父进程。请注意,在子级生成输出时,父级必须处于活动状态,因为管道的缓冲区大小较小(通常为4-5 KB),并且如果子级生成的数据多于父级不读取时的数据,则子级将阻塞直到父母读。如果父母正在等待孩子的死亡,那么您将陷入僵局。使用pipe()等很难做到这一点。父级调用pipe(),然后进行派生。子进程对管道进行分类,以使管道的写端成为其标准输出,并确保关闭与管道有关的所有其他文件描述符。这很可能使用dup2()系统调用。然后,它执行所需的过程,该过程将其标准输出发送到管道。同时,父级还会关闭管道的多余末端,然后开始阅读。当它在管道上发生EOF时,它知道孩子已经完成并关闭了管道。它也可以关闭管道的末端。
随时随地看视频慕课网APP
我要回答