Skip to main content

Lesson: What's Running and Why

What you'll learn

  • Inspect running programs with ps, top, and htop.
  • Send signals to processes and stop them with kill.
  • Understand systemd units and what a "service" really is.
  • Drive services with systemctl — status, start, stop, restart, enable.
  • Read logs with journalctl and know where logs live.

Skill gained: the ability to answer "what's running, is it healthy, and why did it stop?" — the daily job of operations.

The lesson

A running Linux box is a swarm of processes. Most of the time you care about a handful: the services that do real work (a web server, a database). This chapter teaches you to see them, control them, and read what they're telling you. Practise on the Jumpbox (10.100.100.254, user ubuntu).

1. Seeing processes: ps

Recall from Chapter 1: a process is a running program with a numeric PID. ps lists processes. The most common invocation:

ubuntu@Jumpbox:~$ ps aux
USER   PID %CPU %MEM    VSZ   RSS TTY   STAT START   TIME COMMAND
root     1  0.0  0.1 168000 11000 ?     Ss   May01   0:12 /sbin/init
ubuntu 4711  0.0  0.0   9000  5000 pts/0 Ss   10:00   0:00 bash
ubuntu 4990  0.0  0.0  10000  3500 pts/0 R+   10:05   0:00 ps aux

a = all users, u = user-readable columns, x = include background processes. Key columns: PID, %CPU, %MEM, and COMMAND. Notice PID 1 (/sbin/init, which is systemd) — the ancestor of everything.

To find a specific process, pipe into grep:

ubuntu@Jumpbox:~$ ps aux | grep ssh

2. Live view: top and htop

ps is a snapshot. top updates continuously, sorted by CPU use — perfect for "what's eating the machine right now?"

ubuntu@Jumpbox:~$ top      # press 'q' to quit, 'M' to sort by memory, 'P' by CPU

htop is a friendlier, colored version with scrolling and a mouse. It may need installing:

ubuntu@Jumpbox:~$ sudo apt install -y htop
ubuntu@Jumpbox:~$ htop     # F10 or q to quit

3. Signals and kill

You control a process by sending it a signal — a small message the kernel delivers. kill sends signals (despite the name, most signals don't kill).

ubuntu@Jumpbox:~$ kill 4990         # sends SIGTERM (15): "please shut down nicely"
ubuntu@Jumpbox:~$ kill -9 4990      # sends SIGKILL (9): "die NOW" — last resort
  • SIGTERM (15) — the polite default. The program can clean up first. Try this first.
  • SIGKILL (9) — forceful, cannot be ignored, no cleanup. Use only if SIGTERM fails.
  • SIGHUP (1) — often means "reload your config."
  • Ctrl-C in your terminal sends SIGINT (2) to the foreground program.

You can target by name with pkill nginx, but be careful you don't match more than you mean to.

4. What is a service? Enter systemd

A service (also called a daemon) is a program that runs in the background, usually started automatically at boot — a web server, a logging agent, an SSH server. On Ubuntu, all of these are managed by systemd, the system and service manager that runs as PID 1.

systemd organizes everything into units. The kind you'll touch most is a service unit, named like ssh.service. A unit is described by a small text file (e.g. /lib/systemd/system/ssh.service or /etc/systemd/system/...) that tells systemd how to start the program, when, and what to do if it crashes.

        +------------------- systemd (PID 1) -------------------+
        |                                                       |
        |  ssh.service     nginx.service     cron.service       |
        |     |                 |                  |            |
        |  starts            starts             starts          |
        |     v                 v                  v            |
        |  sshd process     nginx process     cron process      |
        +-------------------------------------------------------+

5. Driving services: systemctl

systemctl is the command to control systemd units. The five you'll use constantly:

ubuntu@Jumpbox:~$ systemctl status ssh         # is it running? recent log lines?
ubuntu@Jumpbox:~$ sudo systemctl start ssh     # start it now
ubuntu@Jumpbox:~$ sudo systemctl stop ssh      # stop it now
ubuntu@Jumpbox:~$ sudo systemctl restart ssh   # stop then start (apply new config)
ubuntu@Jumpbox:~$ sudo systemctl reload ssh    # re-read config WITHOUT dropping connections

A typical status output tells you a lot:

● ssh.service - OpenBSD Secure Shell server
   Loaded: loaded (/lib/systemd/system/ssh.service; enabled; preset: enabled)
   Active: active (running) since Mon 2026-06-01 09:00:00 UTC; 2h ago
 Main PID: 812 (sshd)

Read it like this: Active: active (running) = healthy. enabled = it will start automatically at boot. If you see failed, the service crashed — go read its logs (next section).

Enabled vs active trips up beginners:

  • active = running right now.
  • enabled = configured to start on boot.

You set boot behavior separately:

ubuntu@Jumpbox:~$ sudo systemctl enable ssh    # start automatically at every boot
ubuntu@Jumpbox:~$ sudo systemctl disable ssh   # don't start at boot
ubuntu@Jumpbox:~$ systemctl is-enabled ssh     # check
ubuntu@Jumpbox:~$ sudo systemctl enable --now ssh   # enable AND start in one go

6. Reading logs: journalctl

systemd captures the output of every service into a central log called the journal. journalctl reads it.

ubuntu@Jumpbox:~$ journalctl -u ssh             # all log lines for the ssh unit
ubuntu@Jumpbox:~$ journalctl -u ssh -n 50       # last 50 lines
ubuntu@Jumpbox:~$ journalctl -u ssh -f          # FOLLOW live (like tail -f)
ubuntu@Jumpbox:~$ journalctl -u ssh --since "1 hour ago"
ubuntu@Jumpbox:~$ journalctl -p err -b          # only errors, since this boot (-b)

-u selects a unit, -n limits lines, -f follows, -p filters by priority, -b limits to the current boot. When a service won't start, the workflow is always: systemctl status <svc> to see that it failed, then journalctl -u <svc> -n 50 to see why.

7. Where logs live

There are two complementary places:

  • The systemd journal — read with journalctl (often stored under /var/log/journal). This is the modern default on Ubuntu.
  • Plain text files in /var/log — e.g. /var/log/syslog, /var/log/auth.log. Many services still also write here, and you read them with cat, less, grep, tail -f.

On every host in this lab, all of these logs are also shipped to a central Loki log server at 10.100.100.5, so you can search across the whole fleet from one place — invaluable when a problem spans several machines. But when you're logged into the box itself, journalctl and /var/log are right there.

8. The diagnostic workflow

Put the whole chapter together. A teammate says "the SSH service seems down." You:

ubuntu@Jumpbox:~$ systemctl status ssh          # 1. is it active? enabled?
ubuntu@Jumpbox:~$ journalctl -u ssh -n 50        # 2. why did it fail? read the errors
ubuntu@Jumpbox:~$ ps aux | grep sshd             # 3. is a process actually there?
ubuntu@Jumpbox:~$ sudo systemctl restart ssh     # 4. try a restart
ubuntu@Jumpbox:~$ journalctl -u ssh -f           # 5. watch it come back (or fail again)

See it, control it, read what it says. That loop — ps/top to see, systemctl to control, journalctl to understand — is the core of day-to-day operations work. Everything more advanced builds on it.

Dig deeper

Search terms

  • ps aux vs top vs htop
  • linux kill signals sigterm sigkill
  • systemctl status start enable explained
  • journalctl -u -f follow service logs
  • systemd service unit file beginner

Check yourself

  1. What is the difference between a process being active and being enabled?
  2. Which signal should you try first to stop a process, and which is the forceful last resort?
  3. What is a systemd "service unit," and what manages it?
  4. A service shows failed in systemctl status. What's your very next command?
  5. Name the two places service logs live on an Ubuntu host, and the command to read each.