If two processes are connected by a pipe,
> cmd1 | cmd2
is there any way for cmd1 to find out the name (or PID) of the process on the other side of the pipe (cmd2)?
Also, vice versa, is there any way for cmd2 to get the name/PID of cmd1?
I know that there is isatty(3) to check if the output goes to (or the input comes from) a terminal, so I wondered if there is a way to find out a little bit more about the other hand side.
Answers:
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
Method 1
You can see the pipe in /proc/$PID/fd. The descriptor is a symlink to something like pipe:[188528098]. With that information you can search for the other process:
$ lsof -n | grep -w 188528098 sleep 1565 hl 1w FIFO 0,12 0t0 188528098 pipe sleep 1566 hl 0r FIFO 0,12 0t0 188528098 pipe
Or, if you want to be sure (for automatic processing) that the number is the socket and not part of a file name:
$ lsof -n | awk 'NF==9 && $5=="FIFO" && $9=="pipe" && $8==188528098'
With lsof 4.88 and above, you can also use the -E or +E flags:
In combination with -p <pid>, -d <descriptor>, you can get the endpoint information for a specific descriptor of a given pid.
$ sleep 1 | sh -c 'lsof -E -ap "$$" -d 0; exit' COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME sh 27176 chazelas 0r FIFO 0,10 0t0 2609460 pipe 27175,sleep,1w
Above telling us that fd 0 of sh is a pipe with fd 1 of sleep at the other end. If you change -E to +E, you also get the full information for that fd of sleep:
$ sleep 1 | sh -c 'lsof +E -ap "$$" -d 0; exit' COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME sleep 27066 chazelas 1w FIFO 0,10 0t0 2586272 pipe 27067,sh,0r 27068,lsof,0r sh 27067 chazelas 0r FIFO 0,10 0t0 2586272 pipe 27066,sleep,1w
(see how lsof also has the pipe on its stdin)
All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0