我们正在尝试从给予多个子进程的管道中读取char *数据。
每个子进程都将char *写入父进程读取的共享管道中。
我们要做的是解析在xv6中运行的子进程的信息。
在解析单个进程时,我们没有任何问题,但在解析一个对“runcmd”进行递归调用的管道进程时,会出现以下问题:
我们在父母的最后使用了以下代码:
while(read(p[0],buff,sizeof(buff)) > 0){
printf(1,"\nprocess from pipe in main: " );
printf(1,buff);
printf(1,"\n");
}
在孩子们的结尾:
char * name = ecmd->argv[0];
char * data=(char*)malloc(strlen(name)*sizeof(char)+strlen(pidc2)*sizeof(char)+3);
strcpy(data,name);
char* delimiter="#";
strcpy(data+strlen(name),delimiter);
strcpy(data+strlen(name)+strlen(delimiter),pidc2);
strcpy(data+strlen(name)+strlen(delimiter)+strlen(pidc2),"\0");
write(pp[1],data,sizeof(char)*(strlen(data)));
当我们使用“ls | cat”运行此代码时,它将打印:
ls#*some_pid*cat#*some_pid*
而不是从每个孩子读取并打印
ls#*some_pid*
cat#*some_pid*
为什么不单独发送它们?
答案 0 :(得分:0)
因为这就是管道工作的方式。在内部,操作系统将来自所有写入器的数据组合成单个流。正如上面的评论所示,您可以让每个作者插入某种记录分隔符(' \ 0'或' \ n'),然后让阅读过程查找并拆分记录在分隔符。
我并不特别了解xv6,但传统上类似unix的系统已经保证(事实上这是posix.1的要求),任何低于某个指定长度的消息的写入都是原子的(即如果两个进程都写了“foo”,那么读者就会看到“foo foo”,“ffooo o”或“其他任何排列”。