2

For example, I run

sleep 1 | sleep 2 | sleep 3 &

How do I get process ids of each part? I could examine output of jobs -l but its format may wary among shells and I am looking for a simpler way.

jarno
  • 620
  • ps -ef|grep 'sleep ' – lainatnavi Mar 18 '20 at 14:21
  • 1
    If you want a list of shell child-processes, try ps --ppid $$ – Panki Mar 18 '20 at 14:31
  • 1
    If you're running in a shell with job-control (the default for interactive shells), all the processes in a pipeline will be members of the same process group (= job), and you could look them up by their process group id (eg. with pgrep -g). If they're in the background, as in your example, you can grab them by $! (but notice that $! is not necessarily the session leader). Example: sleep 1 | sleep 2 | sleep 3 & pgrep -ag $(ps -ho pgrp $!). –  Mar 18 '20 at 19:59
  • BTW, please DO NOT add the [bash] tag if your question is about POSIX, pipelines, shells and processes in general. In addition of being very bad taste to refer to the whole command line interface of a Linux/Unix system as "bash", it means that your Q will be summarily closed by any reputable user with a [bash] badge ;-) –  Mar 18 '20 at 20:10
  • @mosvy I am just interested in Bash and POSIX shell solutions, neither claiming they are necessarily the same nor claiming there are not other shells. Anyway, thanks for your answer. – jarno Mar 19 '20 at 02:46
  • @jarno the problem with both a POSIX shell and bash is that they offer very few ways to obtain information about other processes. –  Mar 19 '20 at 02:54
  • @mosvy unlike some other shells? – jarno Mar 19 '20 at 15:19
  • Unlike non-shell related solutions -- eg. on linux you can get all the process info you want directly from the /proc/PID/ files, without having to fight with ps, pgrep and their limitations. –  Mar 19 '20 at 15:22
  • @Panki I used that in my answer for the older question. – jarno Mar 29 '20 at 12:51

1 Answers1

0

You can use pgrep with -a option for a full listing:

pgrep -a sleep
  • 3
    How would you distinguish the PIDs of the three sleeps started here from the PIDs of any other sleep running simultaneously? How would you generalise this to a real solution for whatever the OP is actually trying to do (which probably doesn’t involve sleep)? – Stephen Kitt Mar 18 '20 at 14:30
  • I have a generic script solution: #:: psTree: List the process tree rooted at whatever process executes this script, excepting psTree itself. Being as this thread is closed, is it acceptable to post it in the referenced 5-year-old thread, or by some other means? – Paul_Pedant Mar 18 '20 at 19:09
  • @Paul_Pedant if it is able to distinguish between piped processes then yes, but it seems not possible anyways (or at least there's no easy way). Check Stephen's comment above and the other question linked. – lainatnavi Mar 18 '20 at 19:48
  • @Iainatnavi Transcript lousy formatting. Newline at each row of dots. Paul--) ( sleep 80 | ( sleep 60 | sleep 70 ) | sleep 100 ) & [2] 11328 Paul--) ./psTree .. 11140 :: bash .... 11321 :: /home/paul/wdog -t 5m sleep 300 ...... 11322 :: sleep 300 .... 11328 :: bash ...... 11329 :: sleep 80 ...... 11330 :: bash ........ 11332 :: sleep 60 ........ 11333 :: sleep 70 ...... 11331 :: sleep 100 – Paul_Pedant Mar 18 '20 at 21:06
  • @lainatnavi Not easy, but possible. I have a script to show a process tree rooted anywhere you like. Currently easy to intuit pipes, although that may become obfuscated when the process list wraps around the pids. I have a design to get all pipes for those processes from lsof, and join all the processes that connect write/read to the same pipe. So definitely achievable. Question is presentation, and is it worth the effort? – Paul_Pedant Mar 20 '20 at 12:23