Linux Signals
Signals are the simplest form of inter-process communication in Linux — a way for the kernel or another process to say "hey, something happened" to a process. The kill command is misleadingly named; it actually sends any signal, not just the killing kind.
What is a Signal?
A signal is an asynchronous notification sent to a process. When a signal arrives, the process's normal execution is interrupted and a signal handler runs. Signals are identified by number or name.
# List all signals
kill -l
# Send signal by number
kill -9 1234 # SIGKILL
kill -15 1234 # SIGTERM (default when you just run: kill 1234)
# Send signal by name
kill -SIGTERM 1234
kill -HUP 1234 # reload config
The Most Important Signals
| Signal | Number | Default Action | Common Use |
|---|---|---|---|
| SIGTERM | 15 | Terminate gracefully | Normal shutdown — process can catch and clean up |
| SIGKILL | 9 | Terminate immediately | Force kill — cannot be caught, blocked, or ignored |
| SIGHUP | 1 | Terminate (or reload) | Tell daemon to reload config (nginx, sshd) |
| SIGINT | 2 | Terminate | Ctrl+C in terminal |
| SIGQUIT | 3 | Terminate + core dump | Ctrl+\\ — like SIGINT but dumps memory |
| SIGSTOP | 19 | Pause process | Uncatchable pause |
| SIGCONT | 18 | Resume process | Resume after SIGSTOP or SIGTSTP |
| SIGTSTP | 20 | Pause process | Ctrl+Z — catchable |
| SIGCHLD | 17 | Ignored | Child process state changed |
| SIGSEGV | 11 | Terminate + core dump | Segmentation fault — invalid memory access |
| SIGUSR1/2 | 10/12 | Terminate | Application-defined (e.g., toggle debug logging) |
Catching Signals in Shell Scripts
#!/bin/bash
# Catch SIGTERM and clean up before exiting
cleanup() {
echo "Cleaning up..."
rm -f /tmp/myapp.lock
exit 0
}
trap cleanup SIGTERM SIGINT
echo "Running... PID=$$"
while true; do
sleep 1
done
Why SIGKILL Cannot Be Caught
Why is SIGKILL special?
SIGKILL is handled entirely by the kernel — it never reaches the process's signal handler. The kernel forcibly terminates the process and reclaims its resources. This is why a process stuck in D state (uninterruptible sleep) can't be killed even with SIGKILL — the kernel handles signals only when returning from kernel space, which a D-state process isn't doing.
Best practice: always try SIGTERM first and wait a few seconds. Only escalate to SIGKILL if the process doesn't respond.
# Graceful shutdown pattern
kill -TERM 1234
sleep 5
kill -0 1234 2>/dev/null && kill -KILL 1234 # force if still alive