简体   繁体   English

使用pipe()和fork()读取文件并输出到控制台/新文件

[英]Using pipe() and fork() to read from a file and output to the console/new file

I'm trying to learn how to use the pipe() and fork() system calls. 我正在尝试学习如何使用pipe()和fork()系统调用。 I'm using pipe and fork to create parent and child processes where the child will read a character from the text file, and then send it through the pipe to the parent that will then output the character to the console, with the desired result that it will print out the entire text to the console. 我正在使用管道和叉子创建父进程和子进程,在该进程中,子进程将从文本文件中读取字符,然后通过管道将其发送到父进程,然后将其输出到控制台,并获得所需的结果它将整个文本打印到控制台。 Later I'm going to be doing some text processing on the file with the child process reading and processing then sending the updated text to the parent but for now I just want to make sure I'm getting the basics of pipe() correct. 稍后,我将对文件进行一些文本处理,并读取和处理子进程,然后将更新后的文本发送给父进程,但是现在,我只想确保我正确使用pipe()的基础知识。

example file: 示例文件:

This is a test file; it is 1 of many.
Others will follow. 

Relevant code: 相关代码:

  pid = fork();

  ifstream fin;
  fin.open(inputFilename);
  fin.get(inputChar);

  if (pid == -1)
  {
    perror("Trouble");
    exit(2);
  }
  else if (pid == 0) //child process that reads text file and writes to parent
  {
    close(pipefds[0]);
    while(!fin.eof())
    {
      write(pipefds[1], &inputChar, sizeof(inputChar));
      fin.get(inputChar);
    }

    close(pipefds[1]);

    exit(0);
  }
  else
  {
    close(pipefds[1]);
    read(pipefds[0], readbuffer, sizeof(readbuffer));
    cout << readbuffer << endl;
    close(pipefds[0]);
    exit(0);

  }
      fin.close();

However, when I compile and run, the output is always of a varying length. 但是,当我编译并运行时,输出始终是变化的长度。 Sometimes it will print the whole file, others it will just print out a few letters, or half of a line. 有时它会打印整个文件,而其他时候它只会打印出几个字母或一行的一半。 Such as. 如。

This i

I've tried going through the man pages and researching more but I haven't been able to find any answers. 我尝试浏览手册页并进行更多研究,但找不到任何答案。 What exactly is going on with my program that it will sometimes read everything from the file but other times won't. 我的程序到底在做什么,它有时会从文件中读取所有内容,而其他时候则不会。 Any help is greatly appreciated! 任何帮助是极大的赞赏!

It looks as though you're trying to read all the data from the pipe with one call to read(2) . 似乎您正在尝试通过调用read(2)从管道读取所有数据。 But, as with any I/O operation, this may always return fewer bytes than you requested. 但是,与任何I / O操作一样,这可能总是返回比您请求的字节少的字节。 You should always check the return value of read(2) and write(2) system calls (and others), to make sure that they acted as expected. 您应该始终检查read(2)write(2)系统调用(及其他)的返回值,以确保它们按预期方式工作。

In this case, you should loop until you get some independent notification from the child process that they're done sending data. 在这种情况下,您应该循环播放,直到从子进程收到一些独立的通知,告知它们已完成发送数据。 This can be signaled in this case by read(2) returning 0 , meaning that the child closed their end of the pipe. 在这种情况下,这可以通过read(2)返回0来表示,这意味着孩子关闭了管道的末端。

You are assuming that the parent can read everything written to the pipe by the child via one read() call. 您假设父级可以通过一个read()调用read()子级写入管道的所有内容。 That might be a safe assumption for a pipe if the child were writing everything via a single write() call, as long as the overall data size did not exceed the size of the pipe's internal buffer. 如果子级通过单个write()调用编写所有内容,则对于管道而言,这可能是一个安全的假设,只要总数据大小不超过管道内部缓冲区的大小即可。 It is not at all safe when, as in this case, the child is sending data via many little writes. 在这种情况下,孩子通过许多小写操作发送数据时,这一点也不安全。

How much data the parent actually gets will depend in part on how its one read() call is ordered relative to the child's writes. 父母实际获得多少数据将部分取决于相对于孩子的写操作,其一次read()调用的顺序。 Inasmuch as the two are separate processes and you're employing no IPC other than the pipe itself, it's basically unpredictable how much data the parent will successfully read. 由于这两个是独立的过程,并且您除了管道本身外没有使用任何IPC,因此基本上无法预测父级将成功读取多少数据。

In the general case, one must assume that the reader will need to perform multiple read() calls to read all data that are sent. 在一般情况下,必须假定读取器将需要执行多个read()调用来读取所有已发送的数据。 It must keep calling read() and processing the resulting data appropriately until read 's return value indicates that an I/O error has occurred or that the end of the file has been reached. 它必须继续调用read()并适当地处理结果数据,直到read的返回值指示发生I / O错误或到达文件末尾为止。 Note well that end of file does not mean just that no more bytes are available now , but that no more bytes will ever be available. 注意以及该文件的结束并不意味着只是没有更多的字节,现在是可用的,但没有更多的字节将永远是可用的。 That happens after all processes have closed all copies of the write end of the pipe. 在所有进程都关闭了管道写入端的所有副本之后,就会发生这种情况。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM