[英]Not getting all the lines from a pipe
我正在做一个作业,需要一些流程(父母和孩子)进行沟通。 父级将文件路径发送给子级,并且子级必须在子级上运行linux file
(/ usr / bin / file),并将输出返回给父级。
目前,我仍在努力让一个孩子上班,所以现在,我假设有一个孩子。
我打算将多个文件路径发送给每个孩子(一批文件),然后读取file
的输出。
问题:
我使用循环来write
一些文件路径,但是当我read
孩子的输出管道时,并没有得到我应该得到的所有输出。
编码:
#define Read 0
#define Write 1
#define ParentRead read_pipe[0]
#define ParentWrite write_pipe[1]
#define ChildRead write_pipe[0]
#define ChildWrite read_pipe[1]
#define PIPE_BUF_LEN 4096
using namespace std;
int main()
{
/** Pipe for reading for subprocess */
int read_pipe[2];
/** Pipe for writing to subprocess */
int write_pipe[2];
char buffer[PIPE_BUF_LEN] = "";
if (pipe(read_pipe) == 0 && pipe(write_pipe) == 0)
{
pid_t pid = fork();
if (pid == -1)
{
fprintf(stderr, "Fork failure");
exit(EXIT_FAILURE);
}
else if (pid == 0) //Child process
{
close(ParentRead);
close(ParentWrite);
dup2 (ChildRead, STDIN_FILENO); /*redirect ChildRead to stdin*/
dup2 (ChildWrite, STDOUT_FILENO); /*redirect stdout to ChildWrite*/
char* paramArgs[]={"/usr/bin/file","-n","-f-",NULL};
execv("/usr/bin/file",paramArgs);
exit(EXIT_FAILURE);
}
else { //Parent process
close(ChildRead);
close(ChildWrite);
for (int i=0; i < 3 ;i++)
{
/*write to processes which are ready for writing: */
fd_set rfds;
int retval;
FD_ZERO(&rfds);
FD_SET(ParentWrite, &rfds);
retval = select(10, NULL, &rfds, NULL, NULL);
if (retval == -1)
{
perror("select()");
}
else if (retval)
{
write(ParentWrite, "file1\nfile2\n", 12);
}
/*read from processes which are ready for reading*/
FD_ZERO(&rfds);
FD_SET(ParentRead, &rfds);
retval = select(10, &rfds, NULL, NULL, NULL);
if (retval == -1)
{
perror("select()");
}
else if (retval)
{
read(ParentRead, buffer, PIPE_BUF_LEN);
cout << buffer;
}
}
}
}
exit(EXIT_SUCCESS);
}
在这种情况下,我尝试在3次迭代的循环中在“ file1 \\ nfile2 \\ n”上运行file
(注意使用了-n -f-标志),期望得到六行,但仅得到三行:
file1:错误:无法打开`file1'(没有这样的文件或目录)
file2:错误:无法打开`file2'(没有这样的文件或目录)
file1:错误:无法打开`file1'(没有这样的文件或目录)
当我不将孩子的输出重定向到管道(将其写入std_out)时,我确实得到了全部六行。
任何帮助将不胜感激。
调度程序。 您处于一个循环中,要求孩子(即pgm file
)三遍地查找两个文件。 您只能在父级的每个循环中读取一次。
请注意,至少每次读取都获得完整的子级输出的原因是,如果管道写操作的长度小于PIPE_BUF,则保证它们是原子的。 如果在套接字上使用这种例行程序,则每次读取时最终可能会得到消息的一部分。
解决方案:您必须循环阅读,直到获得所需的字节数(或完整消息)为止。 在这种情况下,我假设file
的输出始终是一个以换行符结尾的字符串。 但是您每次通过循环都要求两个file
输出。 因此,请阅读直到满足该条件为止,即直到您阅读了两个完整的字符串。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.