私は次のことを理解していません:
mkfifo p;
$ (>p ps -f | >>p echo $BASHPID) &
[1] 983527
$ cat p
983529
PID PPID C STIME TTY TIME CMD
981815 165343 0 19:57 pts/27 00:00:00 bash
983527 981815 0 21:09 pts/27 00:00:00 bash # <- child bash process `(...)`
983528 983527 0 21:09 pts/27 00:00:00 ps -f
983530 981815 0 21:09 pts/27 00:00:00 cat p
(...) &
結果はPID 983527の子プロセスです。バッシュプロセスです。
ps -f
PID 983528を使用して子プロセスで実行されます。(...)
パイプラインの左側のコンポーネントコマンドです...|...
。
echo $BASHPID
レポートはPID 983529として実行されています。これはパイプラインの正しいコンポーネントでなければならず、...|...
bashプロセスとしてリストする必要があります。
最後の説明は正しいですか?ps -f
コマンドでリストされた最後のプロセスが表示されないのはなぜですか?
答え1
>p ps -f | >>p echo $BASHPID
inはbash
同時に2つのサブプロセスを開始し、パイプを介して接続します。どちらのプロセスも書き込みp
専用モードでfifoを開きます(O_APPEND
2番目のプロセスのフラグを使用しますが、パイプには影響しません)。
fifoはまだリーダーを持っていないので、両方のopen()
sはそこに停止し、いくつかのプロセスが読み取りモードでfifoを開くのを待ちます。
したがって、その時点ですでに2つのプロセスの開始点があります。
左側にあるのはまだ実行が必要です。ps
これは/bin/ps
、実行可能ファイルの検索とロード、ダイナミックリンカーのロード、ライブラリのロードと接続、読み取りの開始/proc
などを意味し、多くの作業が必要です。正しい方法は、Expandを実行し、$BASHPID
それに対して分割+globを実行し、組み込みecho
関数(内部関数のみを呼び出す)を呼び出すと、関数は拡張を作成して終了することです。
実行時にfifoが開いている限り、上記の2つのcat p
プロセスcat
は同時にブロック解除されます。正しい(echo
)は単純な操作を実行し、ps
ロードが完了する前に終了した可能性があるため、見つからず、ps
これ/proc
が表示されない理由を説明します。
1であり、その死は親プロセスによって確認されます。それ以外の場合、プロセスはまだゾンビプロセスとして表示されます。