3

Sorry for this color screen shot but I think it helps highlight the problem better than copy & paste + code format:

ps display-auto-brightness

Here is the same screen in code format:

───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ ps a | grep display-
26457 pts/2    S+     0:00 grep --color=auto display-
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ ps a | grep display-
28927 pts/18   S+     0:00 sudo /usr/local/bin/display-auto-brightness
29174 pts/18   S+     0:00 /bin/bash /usr/local/bin/display-auto-brightness
30183 pts/2    S+     0:00 grep --color=auto display-
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ pstree | grep display-
        |-cron---cron---sh---display-auto-br---sleep
        |         |         |         |                 |-bash---sudo---display-auto-br---sleep
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ ps a | grep cron
16031 pts/2    S+     0:00 grep --color=auto cron
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ ps a | grep display
26773 pts/2    S+     0:00 grep --color=auto display
28927 pts/18   S+     0:00 sudo /usr/local/bin/display-auto-brightness
29174 pts/18   S+     0:00 /bin/bash /usr/local/bin/display-auto-brightness
───────────────────────────────────────────────────────────────────────────────

This morning after reboot the cron job - /etc/cron.d/display-auto-brightness should have started up. I thought it never started on it's on based on the first section.

I manually started the script with sudo /usr/local/bin/display-auto-brightness. The second section shows how ps returns two process ID's for the single job. Oncefor the sudo elevation that started the job and the second for the script itself.

Is there a programmatic way of identifying these two PIDs as one job? The reason being the next development step is when resuming from suspend to see if the single job (not two processes) are already running and kill it when starting the same job again. This will give instant display brightness adjustment if resuming in daylight after suspending in darkness or vice versa.

In the third section I used the pstree command and discovered the cron job that didn't appear with ps command is showing here. Why is that?.

In the fourth section I pipe ps output through grep using cron as filter and nothing shows up. Why is that?

In the fifth and final section I repeat the second section ps a | grep display- to reaffirm previous findings.


Edit 1

I think I've figured out why the fourth section doesn't show cron running. It's because of normal user status whilst cron is running as root. The solution is to use:

$ sudo ps aux | grep cron
root      1122  0.0  0.0  29008  2936 ?        Ss   04:16   0:00 /usr/sbin/cron -f
rick      7273  0.0  0.0  14224  1028 pts/2    S+   17:50   0:00 grep --color=auto cron

Now we can see the original reboot at 4:16am is still running under cron job. Process ID 1122 might be the one that needs to be killed when resuming from suspend in future program changes. This still doesn't tie into the script name display-auto-brightness which pstree command finds.


Edit 2 Windows Subsystem for Linux desktop shortcut

When setting up an icon to call a bash script from Windows 10 desktop you get more running programs than under plain Ubuntu 16.04 and Unity:

$ ps -ef | grep lock-screen
rick     29243 29242  0 17:13 tty1     00:00:00 /bin/bash -c cd && DISPLAY=0:0 /mnt/e/bin/lock-screen-timer
rick     29244 29243  0 17:13 tty1     00:00:00 /bin/bash /mnt/e/bin/lock-screen-timer

When you use pstree there are even more PID's:

$ pstree -gp | grep lock-screen
          |-init(29242,29242)---bash(29243,29242)---lock-screen-tim(29244,29242)---sleep(29777,29242)

In the "old" method I would kill lock-screen-timer "29244". Looking at ps -aux I think I should kill "29243". Looking at pstree though the init parent process should be killed which is "29242".

Further testing reveals you can't kill init PID

This screen shot shows how you can't kill init PID directly. You can kill it's child which causes it to die, but the grandchild and great-grandchild keep running. It would appear you need to kill three PID's under Windows 10 WSL when a desktop shortcut is used:

rick@alien:/mnt/c/Windows/System32$ pstree -gp | grep lock-screen
          |-init(30554,30554)---bash(30555,30554)---lock-screen-tim(30556,30554)---sleep(30587,30554)
rick@alien:/mnt/c/Windows/System32$ kill 30554
-bash: kill: (30554) - Operation not permitted
rick@alien:/mnt/c/Windows/System32$ sudo kill 30554
[sudo] password for rick:
rick@alien:/mnt/c/Windows/System32$ pstree -gp | grep lock-screen
          |-init(30554,30554)---bash(30555,30554)---lock-screen-tim(30556,30554)---sleep(30587,30554)
rick@alien:/mnt/c/Windows/System32$ kill 30555
rick@alien:/mnt/c/Windows/System32$ pstree -gp | grep lock-screen
          |-lock-screen-tim(30556,30554)---sleep(30612,30554)
rick@alien:/mnt/c/Windows/System32$ pstree -gp | grep sleep
          |-lock-screen-tim(30556,30554)---sleep(30633,30554)
rick@alien:/mnt/c/Windows/System32$ kill 30556
rick@alien:/mnt/c/Windows/System32$ pstree -gp | grep sleep
          `-sleep(30633,30554)
rick@alien:/mnt/c/Windows/System32$ kill 30633
2
  • You could post text alongside the screenshots. I don't see why the second image has to be a screenshot at all.
    – muru
    Mar 9, 2017 at 1:12
  • You're right as always :) Block code format looks better than the second image now removed. Mar 9, 2017 at 1:15

3 Answers 3

1

Effectively, yes, there is a way to identify them as single process, but with a condition.

Suppose we have this:

#!/bin/bash
loop_function(){
    while :
    do
       sleep 3
    done
}

loop_function &

while true
do
    sleep 3
done

And we launch it in background:

bash-4.3$ ./simple_example.sh &
[1] 16180

Here we see that the script itself has 16180 PID. All its children would have different one. Now, all of them have common parent: the shell that is specified in #! line, i.e. that exact same PID that was reported when we executed script in background. Thus, by using ps with specifying ppid , we can search for all processes belonging to same process.

bash-4.3$ ps -e  -o ppid,command | grep 16180 | grep -v grep
16180 /bin/bash ./simple_example.sh
16180 sleep 3

Now , obviously, this implies two things:

  • to group the processes together, you must know the parent PID
  • children's child processes will have different parent PID, thus if you have more than one level of function calls, it will be difficult to trace all processes.

As for pstree part of the question, the job did appear there - it was simply cut off by grep. You also do not need sudo for viewing cronjobs:

$ ps -ef | grep cron | grep -v grep && echo $USER                                                                        
root       896     1  0 09:47 ?        00:00:00 /usr/sbin/cron -f
xieerqi
1
  • The | grep -v grep && echo $USER is a very nice touch! But how do we narrow it down to display-auto-brightness like the pstree shows it? It could be any cron job running under PID # 896 in your example and we don't want to kill the wrong script resuming from suspend. Also our script might not be running in the first place in which case we start running without killing anything. Mar 9, 2017 at 1:40
1

Since you want to find only PIDs of the process running, and not anything indirectly associated (i.e. the PID of the sudo call, and the grep searching for the process name), you can just grep out the offending words from the initial search.

$ ps aux | grep display-auto-brightness | grep -vw -e grep -e sudo | awk '{print $2}'
1
  • To clarify there is a script started by cron on boot. The goal is to relaunch the script when resuming from suspend and killing the version that was started by cron. Cron tree has eight PIDs and systemd (resume from suspend) has two PIDs. The goal is to cancel the right PID. Mar 12, 2017 at 4:32
0

Thanks to this Q&A (how to kill a cron job if it doesn't show in ps? or get it to show in ps?) I was set on the right path:

───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ ps wwuxa |grep display-auto | grep -v grep
root      1584  0.0  0.0   4508   780 ?        Ss   14:02   0:00 /bin/sh -c    /usr/local/bin/display-auto-brightness
root      1592  0.0  0.0  12564  2984 ?        S    14:02   0:00 /bin/bash /usr/local/bin/display-auto-brightness
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ pstree -p -g | grep display-auto
             |-cron(1376,1376)---cron(1436,1376)---sh(1584,1584)---display-auto-br(1592,1584)---sleep(16989,1584)
───────────────────────────────────────────────────────────────────────────────
rick@dell:~$ 

Killing cron (with pid's 1376 and 1436) is probably a bad idea. However killing bash shell (1584) which is the parent to display-auto-brightness (1592) and grandparent to sleep (16989) should kill the child and grandchild. Then two copies of the child process (display-auto-brightness) won't be running at the same time.

Now comes the challenge of programming the script but at least now I know how to extract the information.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .