Processes vs Threads
A process is an instance of a running program with its own address space (memory), PID, and kernel state. A thread is a unit of execution that shares the address space of a process; threads in the same process share memory (global variables, heap) but have their own stack and register state. Linux implements threads as lightweight processes via clone() with shared address space (CLONE_VM); each has a TID (thread ID), and the main thread’s TID equals the process PID.
Comparison
Section titled “Comparison”| Aspect | Process | Thread |
|---|---|---|
| Address space | Separate (own virtual memory) | Shared within process |
| Creation | fork() (or clone()); then often exec() | pthread_create() (uses clone() with shared VM) |
| ID | PID (process ID) | TID (thread ID); main thread TID = PID |
| Isolation | Memory and failures isolated | One thread can crash the whole process |
| Overhead | Higher (new address space, kernel structures) | Lower (shared address space) |
| Communication | IPC (pipes, sockets, shared memory, etc.) | Shared memory (pointers, globals) |
| Failure impact | One process crash does not kill others | One thread (e.g. segfault) can kill the process |
Relevant tools
Section titled “Relevant tools”| Tool | Purpose |
|---|---|
ps -T, ps -eLf | List threads (TID, PID). |
top -H, htop | Thread view; toggle with H. |
strace -f | Trace fork/clone and all threads. |
pstack, gdb | Thread backtraces (info threads, thread apply all bt). |
perf, valgrind | Profiling; helgrind for data races. |
/proc/<pid>/task/ | One directory per thread (TID). |
Using the tools
Section titled “Using the tools”- View threads —
ps -T -p <pid>orps -eLf;top -Hor enable thread view inhtop. Each line is a thread (TID in second column forps -T). - Per-thread info —
ls /proc/<pid>/task/lists TIDs; each has its ownstatus,stack, etc. - Backtraces — In
gdb:info threads,thread <n>,bt.thread apply all btfor all threads. - Trace creation —
strace -f -e clone,fork ./programshows clone/fork calls when threads/processes are created.
Summary table
Section titled “Summary table”| Process | Thread | |
|---|---|---|
| Address space | Own | Shared |
| Creation | fork/exec or clone | pthread_create (clone with CLONE_VM) |
| ID | PID | TID |
| Isolation | Yes | No (shared memory) |
| Overhead | Higher | Lower |
| Communication | IPC | Shared memory |
| Failure impact | Isolated | Can kill process |
Memory layout
Section titled “Memory layout”Multiple processes — Each has its own virtual address space; the kernel maps each to (possibly different) physical pages. No shared memory unless explicitly set up (shared memory, mmap).
Process A (PID 1000) Process B (PID 1001)+------------------+ +------------------+| code | | code || data | | data || heap ^ | | heap ^ || ... | | | ... | || stack v | | stack v |+------------------+ +------------------+ (separate pages) (separate pages)Single process, multiple threads — Same virtual address space; each thread has its own stack (and register state), but code, data, and heap are shared.
Process (PID 1000)+------------------+| code (shared) || data (shared) || heap (shared) ^ || ... || stack T1 v || stack T2 v || stack T3 v |+------------------+Why it matters for debugging
Section titled “Why it matters for debugging”- Crashes — A segfault in one thread kills the whole process; use
gdbandthread apply all btto see which thread and where. - Races — Shared memory without synchronization causes data races; use thread sanitizers or helgrind.
- Resource usage —
top -Hshows per-thread CPU; a single runaway thread can max one CPU.