A Searchable Linux/POSIX Signal Reference — Why SIGRTMIN Is 34, Not 32
kill -9kills a process.kill -HUPtells nginx to reload its config.kill -TERMasks politely. But which number is which? What's the difference between SIGUSR1 and SIGUSR2? Why can you catch SIGTERM but not SIGKILL? This reference answers all of those, with bilingual descriptions and examplekillcommands.
Signals are one of those Unix primitives everyone uses but few people memorize. The man pages exist, but they're reference documentation, not fast lookup. A searchable, filtered, visual reference is faster — especially when you need to answer "what number is SIGUSR1 again?" in the middle of writing a service.
🔗 Live demo: https://sen.ltd/portfolio/linux-signals/
📦 GitHub: https://github.com/sen-ltd/linux-signals
Features:
- 33 signals (POSIX + Linux extensions + RT range)
- Search by name or number
- Filter by default action (Term, Core, Ign, Stop, Cont)
- Per-signal info: description, use cases, example command, catch/ignore/block flags
- Bilingual Japanese / English descriptions
- Dark / light theme
- Zero dependencies, 41 tests
Why SIGRTMIN is 34 on Linux, not 32
The POSIX spec defines real-time signals starting at SIGRTMIN. On most Unix systems this is 32, but on Linux with glibc it's 34. Why?
glibc reserves signals 32 and 33 for NPTL (Native POSIX Thread Library) internal use — thread cancellation and setxid broadcasting. User code can't use them without breaking threading. So SIGRTMIN starts one past those: 34.
This is why you'll sometimes see "signal 34 received" in logs on Linux but never on macOS. Same code, different signal numbering.
Can't catch SIGKILL or SIGSTOP
The kernel guarantees that SIGKILL and SIGSTOP always take effect. You can't install a handler for them, can't ignore them, can't block them in a signal mask:
{
number: 9,
name: 'SIGKILL',
canCatch: false, // can't install a handler
canIgnore: false, // SIG_IGN is refused
canBlock: false, // sigprocmask ignores it
description: {
en: 'Forceful termination. Cannot be caught, ignored, or blocked.',
},
}
This is by design: if any code could block SIGKILL, a runaway program could make itself unkillable. The kernel refuses to allow that.
The default action matrix
Each signal has a default action if the process doesn't install a handler:
| Action | Meaning |
|---|---|
| Term | Terminate the process |
| Core | Terminate + write a core dump |
| Ign | Ignored (process continues) |
| Stop | Stop the process (like Ctrl+Z) |
| Cont | Resume a stopped process |
Most terminal-related signals are Term (SIGHUP, SIGINT, SIGPIPE), most fatal fault signals are Core (SIGSEGV, SIGBUS, SIGFPE, SIGABRT), and the child-process signals are Ign (SIGCHLD default is to ignore, though many programs override).
Common use cases
Beyond "kill a process":
- SIGHUP — nginx / Apache / sshd reload config. Originally meant "terminal hung up" but got repurposed for daemons that don't have controlling terminals.
- SIGUSR1 / SIGUSR2 — Reserved for application-specific use. PostgreSQL uses SIGUSR1 for backend signaling, Apache for graceful restart.
- SIGWINCH — Terminal window resized. Shells and TUI apps listen for this to redraw.
-
SIGCHLD — A child process changed state (died, stopped). Parent uses this to
wait()without polling.
Each entry has a ja/en description and a real example command so you can copy-paste to try it.
Series
This is entry #62 in my 100+ public portfolio series.
- 📦 Repo: https://github.com/sen-ltd/linux-signals
- 🌐 Live: https://sen.ltd/portfolio/linux-signals/
- 🏢 Company: https://sen.ltd/

Top comments (0)