Skip to content
DevOps devops linux-admin 6 min read

Managing Processes

Every running program on a Linux server is a process — an instance of a program that the kernel (the core of the operating system) is actively executing. Each process has a unique number called a PID (Process ID) that you use to inspect or control it. As a DevOps engineer you will constantly ask “what is running?”, “why is the server slow?”, and “how do I stop this stuck program?” — and the answer always comes down to managing processes. This page shows you how to list, watch, prioritise, and kill processes on Ubuntu.

What a process is

When you run a command like nginx or python app.py, the kernel creates a process for it. That process has a PID, an owner (the user that started it), a parent (the process that launched it), and a state (running, sleeping, or stopped). Processes can start other processes — for example systemd (Ubuntu’s service manager, PID 1) starts almost everything else when the machine boots.

You mostly interact with processes in two situations: inspecting them (to understand load or find a misbehaving program) and controlling them (to stop, pause, or reprioritise them). We’ll cover both.

Listing processes with ps

ps (process status) prints a snapshot of processes at the moment you run it. The most common form is ps aux, which shows all processes from all users with usage details.

ps aux

Output:

USER       PID %CPU %MEM    VSZ   RSS TTY   STAT START   TIME COMMAND
root         1  0.0  0.4 168140 12996 ?     Ss   09:01   0:02 /sbin/init
www-data  1423  0.1  1.2 145820 49180 ?     S    09:05   0:11 nginx: worker process
deploy    2204 78.3  3.1 998120 12840 ?     Rl   10:32   4:55 python app.py

Key columns: USER (owner), PID, %CPU and %MEM (share of CPU and memory used), STAT (state — R running, S sleeping, Z zombie), and COMMAND. Use it when you need a one-time list you can pipe into grep or save to a file.

To find one program, pipe ps aux into grep:

ps aux | grep nginx

When to use this: quick, scriptable snapshots. For watching live, use top or htop instead.

Watching live with top

top is built into every Ubuntu system and refreshes every few seconds, sorted by CPU usage by default. It’s the fastest way to spot a process eating the server.

top

While top runs, useful keys are: P (sort by CPU), M (sort by memory), k (kill a process — it asks for the PID), and q (quit). Press 1 to see each CPU core separately.

A friendlier view with htop

htop is an interactive, colourful version of top with mouse support, scrolling, and easy killing. It isn’t installed by default, so add it:

sudo apt update
sudo apt install -y htop
htop

In htop you can scroll with the arrow keys, press F6 to change the sort column, F3 to search by name, and F9 to send a signal (kill) to the highlighted process. It’s the tool most engineers reach for when troubleshooting interactively.

ToolInstalled by default?Best for
ps auxYesOne-time snapshots, scripting
topYesLive monitoring on a bare server
htopNo (apt install htop)Comfortable interactive troubleshooting

Finding a process that’s hogging CPU

Suppose the server feels slow. List the top CPU users in one line:

ps aux --sort=-%cpu | head -n 5

Output:

USER       PID %CPU %MEM    VSZ   RSS TTY   STAT START   TIME COMMAND
deploy    2204 78.3  3.1 998120 12840 ?     Rl   10:32   4:55 python app.py
www-data  1423  0.1  1.2 145820 49180 ?     S    09:05   0:11 nginx: worker
root         1  0.0  0.4 168140 12996 ?     Ss   09:01   0:02 /sbin/init

The --sort=-%cpu flag sorts highest-first. Here PID 2204 (python app.py) is using 78% of a CPU — the likely culprit. Swap %cpu for %mem to hunt down memory hogs instead.

Background jobs: jobs, bg, and fg

When you run a long command in a terminal, it runs in the foreground and blocks your prompt. You can pause and background it without killing it:

  • Press Ctrl+Z to suspend (pause) the foreground command.
  • Run bg to resume it in the background so your prompt is free.
  • Run fg to pull it back to the foreground.
  • Run jobs to list jobs started from this shell.
sleep 300
# press Ctrl+Z to suspend
bg
jobs

Output:

[1]+  Running                 sleep 300 &

When to use this: for tasks tied to your current terminal session. For anything that must survive logout, use a systemd service instead — background jobs die when the shell closes.

Killing processes and signals

To stop a process you send it a signal — a message asking it to do something. The two you’ll use most are TERM (terminate gracefully) and KILL (force-stop immediately).

SignalNumberMeaningCan the process ignore it?
SIGTERM15Politely ask to shut down (default)Yes — it can clean up first
SIGKILL9Force-kill immediatelyNo — kernel ends it instantly
SIGHUP1Hang up — often means “reload config”Yes

kill — by PID

kill sends a signal to a specific PID. Always try TERM first so the program can shut down cleanly (flush data, close files):

kill 2204          # sends SIGTERM (graceful)
kill -9 2204       # sends SIGKILL (force) — only if TERM fails

Reach for kill -9 only as a last resort. SIGKILL gives the process no chance to save data or release locks, which can corrupt files or leave stale lock files behind. Try plain kill first and wait a few seconds.

killall and pkill — by name

When you don’t know the PID, target the process by name:

killall nginx           # kill every process literally named "nginx"
pkill -f "python app.py"  # match against the full command line

killall matches the exact program name; pkill -f matches a pattern anywhere in the command line, which is handy for scripts. Both accept -9 to force-kill.

Changing priority with nice and renice

Every process has a niceness value from -20 (highest priority) to 19 (lowest). A “nicer” (higher) number means the process yields CPU to others — useful for background jobs like backups that shouldn’t slow down your app.

Start a command with lower priority:

nice -n 10 tar -czf backup.tar.gz /var/www

Change the priority of a process already running (needs sudo to raise priority):

sudo renice -n 5 -p 2204

Output:

2204 (process ID) old priority 0, new priority 5

When to use this: to keep heavy batch work from starving interactive or production processes — not to “speed up” a program, since lowering niceness only helps when the CPU is contended.

Best practices

  • Use htop (or top) to diagnose live load; use ps aux --sort=-%cpu for a quick scriptable snapshot.
  • Always send SIGTERM first; only use SIGKILL (-9) when a process ignores a graceful stop.
  • Prefer pkill -f over guessing PIDs when targeting a known command line, but double-check the match — a loose pattern can kill the wrong process.
  • For anything that must keep running after you log out, create a systemd service instead of backgrounding a shell job.
  • Use nice/renice to keep backups and batch jobs from starving production processes.
  • Watch out for Z (zombie) states in ps — they usually point to a parent process that isn’t cleaning up its children correctly.
Last updated June 15, 2026
Was this helpful?