Shell

管道如何影響標準輸入?

  • July 7, 2020

我想寫一個 C 程序,我需要解析stdin. 如果我輸入,從cat file.txt | grep -v match如何解決?它們是串聯的嗎?它們是兩個不同的字元串嗎?我跑了,所以我沒有發現任何(似乎)有用的東西。stdout``cat``-v match``cat /dev/pts/0``file /dev/pts/0

C 程序主函式的標准定義是

int main(int argc, char *argv[])

在這裡,argcargv是命令行參數,-v在這種情況下match是 for 。grep請注意,它們不是單個字元串,但 shell 已經將參數拆分為不同的字元串(NUL/\0終止,就像 C 中的通常情況一樣)。argc包含參數的數量和argv參數本身。

另一方面,標準輸入只是一個FILE *,您可以直接將它與任何stdio功能一起使用。fgets(buf, sizeof(buf), stdin)等等


我不確定你從哪裡得到cat /dev/pts/0的。它將從那個特定的偽終端讀取,可能與您的 shell 在同一終端上的讀取衝突。(嘗試打開兩個終端,xterm,SSH 會話,螢幕,等等。然後tty在第一個上執行,它在那裡顯示終端的名稱,例如/dev/pts/123。在第二個終端中執行cat /dev/pts/123(使用給定名稱),然後嘗試輸入第一件事。)

管道是在核心中分配的緩衝區,文件描述符與讀寫端相關聯。當你執行cat file.txt | grep -v match

  • shell 創建一個管道(使用pipe()系統呼叫)
  • 貝殼fork()s. 子程序使用dup2()系統呼叫關閉其標準輸出流並將管道的寫入端複製到標準輸出。(此後,對標準輸出的寫入將轉到核心緩衝區。)然後子exec()scat具有更新的標準輸出。
  • fork()再次。子程序使用dup2()系統呼叫關閉其標準輸入流並將管道的讀取端複製到標準輸入。(在此之後,標準輸入的讀取將來自核心緩衝區。)然後子exec()sgrep具有更新的標準輸入。

此時,兩者catgrep在執行。如果grep嘗試從標準輸入(管道)讀取並且管道為空,則讀取將阻塞。如果cat嘗試寫入標準輸出(同樣是管道)並且管道已滿,則寫入將阻塞。否則,當cat寫入緩衝區時,grep可以從緩衝區中讀取。

引用自:https://unix.stackexchange.com/questions/597083