1. Overview

In the Linux operating system, we can run a process in foreground or background mode. Sometimes, it’s important to retrieve the process IDs from these processes. In this tutorial, we’ll run jobs in the foreground and background and get the process ID.

2. Foreground and Background Jobs

When we run a process in foreground mode, the shell is suspended until the termination of the process. However, a background process executes independently of the shell.

2.1. Foreground Process

We can run a process in the foreground by calling it directly on the command line. Let’s run the xeyes process:

$ xeyes

If we run a process in the foreground, we can suspend, or pause, it using ctrl+z and send it to the background.

2.2. Background Process

We can run the same process in the background using the & command:

$ xeyes &
[2] 3044

Then, using the jobs command, we can see the processes being run in the background:

$ jobs
[1]+ Running xeyes &

If a process is suspended, we can use the bg command to start it in the background. The process in the background can then be run in the foreground via the fg command.

3. Monitoring Processes

Every process in Linux has a process ID called the PID and a parent process ID called the PPID. In Linux, the ps command shows running processes:

$ ps
PID TTY TIME CMD
1937 pts/2 00:00:00 bash
2567 pts/2 00:00:00 ps

Also, we can use ps -aux or ps -ef to show all processes on the system:

$ ps -aux
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 1 0.0 0.2 119924 6100 ? Ss 14:52 0:01 /sbin/init spla
root 2 0.0 0.0 0 0 ? S 14:52 0:00 [kthreadd]
root 4 0.0 0.0 0 0 ? I< 14:52 0:00 [kworker/0:0H]
root 6 0.0 0.0 0 0 ? I< 14:52 0:00 [mm_percpu_wq]
root 7 0.0 0.0 0 0 ? S 14:52 0:00 [ksoftirqd/0]
.
.
baeldung 2575 0.0 0.1 44432 3328 pts/2 R+ 16:31 0:00 ps -aux

Using grep along with ps, we can monitor a specific process:

$ xeyes &
[1] 2606
$ ps -aux | grep xeyes
baeldung 2606 0.1 0.2 48580 4092 pts/2 S 16:41 0:00 xeyes
baeldung 2608 0.0 0.0 21292 1084 pts/2 S+ 16:42 0:00 grep --color=auto xeyes

Additionally, by using ps -ef with grep, we can retrieve the PID and PPID:

$ xeyes &
[1] 2660
$ ps -ef | grep xeyes
baeldung 2660 1937 0 16:51 pts/2 00:00:00 xeyes
baeldung 2662 1937 0 16:51 pts/2 00:00:00 grep --color=auto xeyes

In this case, the xeyes process has a PID value of 2660 and a PPID value of 1937. Using the PPID, we can find the parent process:

$ ps -ef | grep 1937
baeldung 1937 1930 0 14:55 pts/2 00:00:00 bash

This shows us that the parent process of xeyes is bash. Finally, we can use ps -l to see the processes in the current bash:

$ ps -l
F S   UID   PID  PPID  C PRI  NI ADDR SZ WCHAN  TTY          TIME CMD
0 S  1001  3935  3928  0  80   0 -  7375 wait   pts/1    00:00:00 bash
0 S  1001  4028  3935  1  80   0 - 12145 poll_s pts/1    00:00:00 xeyes
4 R  1001  4029  3935  0  80   0 -  8996 -      pts/1    00:00:00 ps

4. Manipulating Processes

4.1. Getting the Process ID

We have seen that ps -ef shows processes from all users, and combining it with grep, we can find the specific PID and PPID of a process. However, there is also a more direct way:

$ xeyes &
[3] 2726
$ ps -C xeyes -o user,pid
USER PID
baeldung 2726

Here, we’re using the -C option to only return matches for the xeyes process, and the -o option to return specific columns. Additionally, we can see the process ID with jobs -l:

$ xeyes &
[1] 2546
$ jobs -l
[1]+ 2546 Running

Moreover, the $! command returns the PID of the last background process:

$ xeyes &
[1] 2546
$ cat $!
cat: 2546: No such file or directory

4.2. Kill the Process

In Linux, we can control processes by signals. In fact, when we press ctrl+c and ctrl+z, we’re also sending signals to the process. The kill command allows us to stop a process. The command uses different signals, depending on how we should terminate the process:

 signal number | signal name | meaning 
     15        |   SIGHUP    | normal terminate request 
      9        |   SIGKILL   | force kills the procsess

Let’s use kill to stop the xeyes process:

$ xeyes &
[1] 2390
$ kill 2390
$ jobs
[1]+ Terminated xeyes

The process is closed normally (SIGHUP) by the kill command. We can force the process to be closed by the kill -9 command:

$ xeyes &
[1] 2402
$ kill -9 2402
$ jobs
[1]+ Killed xeyes

Let’s find the process ID with jobs -l and then kill the process:

$ xeyes &
[1] 2546
$ jobs -l
[1]+ 2546 Running
$ kill -9 2546
$ jobs
[1]+ Killed xeyes

5. Conclusion

In this article, we described foreground and background processes. Also, we saw how we can monitor a process. Finally, we looked at different ways of getting the process ID and killing the associated process.