LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 712|回复: 3

请教各位关于pipe的一个问题

[复制链接]
发表于 2009-3-25 21:39:59 | 显示全部楼层 |阅读模式
我正在实现一个简单的shell,其中就有管道的实现。比如ls -l | more,如果我在一个进程中fork一个子进程,父进程作为ls,子进程作为more,就会出现这样的问题:more在运行时需要从终端接受命令,如果把more的标准输入绑定到pipe上,就无法接受指令,程序无法正常结束。但如果我这样实现:在一个进程中fork一个子进程和一个孙进程,子进程实现ls,孙进程实现more,把more的标准输入绑定到pipe上,这时more能够正常工作,即能接受终端的命令。这两者区别在哪儿?我是初学者,能帮我详细解答下吗?谢谢了!
 楼主| 发表于 2009-3-26 10:23:50 | 显示全部楼层
void sort_pipe(char *argv[SIZE], int mark)
{
        int fd[2];
        pid_t pid;

        argv[mark] = (char *) 0;
       
        if ((pid = fork()) < 0)
                printf("sub fork error\n");
        else if (pid == 0) {                                               
                if (pipe(fd))
                        printf("error in creating pipe\n");
                if (fork() == 0) {
                        close(fd[0]);
                        close(STDOUT_FILENO);
                        dup(fd[1]);
                        close(fd[1]);
                        if (execvp(argv[0], argv) < 0)
                                printf("%s: %s\n", argv[0], strerror(errno));
                        exit(0);
                }
                close(fd[1]);
                close(STDIN_FILENO);
                dup(fd[0]);
                close(fd[0]);
                if (execvp(argv[mark + 1], &argv[mark + 1]) < 0)
                        printf("%s: %s\n", argv[mark + 1], strerror(errno));
                exit(0);
        }
        if ((pid = waitpid(pid, NULL, 0)) < 0) {
                        printf("waitpid error\n");
                        printf("%s\n", strerror(errno));
        }
}
回复 支持 反对

使用道具 举报

 楼主| 发表于 2009-3-26 10:26:11 | 显示全部楼层
上面是实现pipe的源代码。仔细试了一下,发现还是有问题。ls -l | more是可以正确显示,但随后执行的每条命令都自动加上了 | more (pwd变成了pwd | more),more没有正确结束。原因跟more应该无关,我试了一下cat也是一样
回复 支持 反对

使用道具 举报

 楼主| 发表于 2009-3-26 10:53:39 | 显示全部楼层
如果用子进程实现more,孙进程实现ls,结果和原来的问题一样,神奇
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表