What a process is: PIDs, parents, ps
A running program is a process with a number, a parent and an owner; meet PID 1, the kernel threads in brackets, and your own shell in the list.
What you will learn
- Define process, PID and PPID and explain how the process tree grows from init.
- List processes with `ps` and pick columns with `-o`.
- Find your own shell's PID with `$` and its parent with `$PPID`.
Programs sit on disk, processes run
A program is a file: /bin/busybox, a script, a browser. A process is one running instance of a program, with its own memory, open files, current directory, environment and identity. Run ls twice and you have created two processes from one program, each born, doing its job and dying within milliseconds. Your shell is a process too, one that lives as long as you keep the terminal open.
The kernel gives every process a number, the PID, unique among the processes alive right now. Every process also records who created it, the PPID (parent PID): on Unix a process is always born by an existing process *forking* a copy of itself and then *exec*-ing a new program into the copy. Follow the parents upward and you always arrive at PID 1, init, the first userland process, started by the kernel at the end of the boot. When a parent dies before its children, they are adopted by init, which is why orphaned background jobs show PPID 1.
ps: a snapshot
~% ps
PID USER COMMAND
1 root init
2 root [kthreadd]
3 root [kworker/0:0]
7 root [ksoftirqd/0]
8 root [rcu_sched]
527 root [kswapd0]
855 root -/bin/sh
856 root init
859 root -/bin/sh
979 root ps
~% echo $ $PPID
859 1
~% ps -o pid,ppid,user,comm | tail -3
859 1 root sh
981 859 root sh
983 981 root ps
ps prints a snapshot of the process table, one line each. BusyBox's default columns are PID, USER and COMMAND. The entries in square brackets are kernel threads: workers that live inside the kernel, have no program file and no command line, and are children of PID 2, kthreadd. Everything else is userland. Here init appears several times because /etc/inittab starts one for each virtual console, waiting for a keypress; the -/bin/sh lines are login shells, the leading dash being the convention that marks them. ps itself is in the list: it was alive when the snapshot was taken.
The shell keeps its own PID in the special variable $ and its parent's in $PPID. In the lab your shell was started directly by init, so $PPID is 1. The -o option picks columns: pid, ppid, user, comm (the short program name) or args (the full command line) are the ones you will use most; lesson 52 covers the rest.
| PID | Name | Role |
|---|---|---|
| 0 | swapper / idle | The kernel itself; never shown by ps |
| 1 | init | First user process, ancestor and adopter of all others |
| 2 | [kthreadd] | Parent of every kernel thread |
$ | your shell | Parent of every command you type |
Commands in this lesson
| Command | What it does |
|---|---|
ps | Snapshot of all processes: PID, USER, COMMAND. |
ps -o pid,ppid,comm | Pick columns: PID, parent and program name. |
ps -o pid,user,args | Full command lines. |
echo $ | PID of the current shell. |
echo $PPID | PID of the shell's parent. |
cat /proc/sys/kernel/pid_max | Highest PID before numbers wrap around. |
Quiz
What is PID 1?
- The kernel
- init, the first user-space process and ancestor of all others
- Your login shell
What do the square brackets in `[kswapd0]` mean?
- The process is stopped
- It is a kernel thread with no command line
- It is running as root
Which shell variable holds the PID of the current shell?
- `$PID`
- `$!`
- `$`
A background job's parent shell exits. What is the job's PPID afterwards?
- 0
- 1: it is adopted by init
- It keeps the old number
Practice
Save a snapshot of all processes (plain `ps`) into `/root/lab/l51/ps.txt`.
Write the PID of your current shell into `/root/lab/l51/mypid.txt`.
Produce a listing with exactly the columns PID, PPID and program name, saved to `/root/lab/l51/tree.txt`.
Open this lesson in the app to do the tasks in a real Linux machine and have them checked.