我想了解shell如何执行管道命令,例如cat | more。我知道对于执行普通命令,shell会进行fork,执行该命令,然后子进程返回。但是shell如何在内部处理管道命令的执行呢?
例如考虑 cat | grep
,shell 首先创建一个子进程来启动 cat
,然后再创建一个子进程来启动 grep
。
在调用 exec*
函数族中的任意一个函数来启动这两个程序的新进程之前,需要设置管道并重定向描述符。在 shell 进程中使用 pipe(2)
系统调用,在分叉之前返回一对描述符,两个子进程都会从父进程继承这些描述符 - 一个读描述符和一个写描述符。
第一个进程(cat
)将关闭读描述符,并使用 dup2(2)
系统调用将标准输出重定向到写描述符。类似地,第二个进程(grep
)将关闭写描述符,并使用 dup2(2)
将标准输入重定向回读描述符。
这样,两个程序都不知道有一个管道存在,因为它们只使用标准输入/输出。
它使用pipe
系统调用设置管道,不是一个进程而是两个进程,将管道的一端连接到第一个进程的标准输出,另一端连接到第二个进程的标准输入。
dup2
,但你已经从Blagovest的答案中找到了。@Downvoter:除了太短之外,这个答案有什么问题吗? - Fred Foo