Blog
4 min read

CRIU: Checkpoint and Restore Running Linux Processes

CRIU (Checkpoint/Restore In Userspace) freezes a running process tree, saves its complete state to disk, and restores it later — on the same machine or another. How it works, using it with Podman, Docker and Kubernetes, what it can't capture (GPUs, external connections), permissions, and how it compares with VM snapshots for persistent agent workspaces.

Imagine pausing a running program — its memory, open files, sockets, threads, everything — saving it to disk, and resuming it tomorrow or on another machine, exactly where it left off. That's what CRIU (Checkpoint/Restore In Userspace) does for Linux processes.

It's used for live migration of containers, fast startup of slow-to-initialise applications (restore a warmed-up JVM instead of booting one), forensic snapshots of suspicious containers, and keeping long-running work alive across host maintenance.

How it works

Checkpoint (dump):

  1. Freeze the process tree (using the cgroup freezer or ptrace) so state stops changing.
  2. Collect state from the kernel: memory mappings and their contents, registers, open file descriptors and offsets, pipes, sockets, signal handlers, namespaces, cgroup membership, timers.
  3. To read state that's only visible from inside the process, CRIU injects a small parasite code blob into the frozen process, uses it to dump memory and other private state, then removes it.
  4. Write it all to a directory of image files.

Restore reverses it: CRIU recreates the process tree with the same PIDs (inside a PID namespace), rebuilds mappings, restores memory, reopens files, reconnects pipes and sockets, and lets the processes run.

All of this happens in userspace using ordinary kernel interfaces — hence the name — though it relies on many kernel features that were added specifically to support it.

Trying it

# Start something stateful
setsid sh -c 'i=0; while true; do echo $i; i=$((i+1)); sleep 1; done' > /tmp/count.log 2>&1 < /dev/null &
PID=$!

mkdir /tmp/ckpt
sudo criu dump -t $PID -D /tmp/ckpt -v4 -o dump.log
# the process is gone…

sudo criu restore -D /tmp/ckpt -d
tail -f /tmp/count.log      # …and continues counting from where it stopped

With containers

  • Podman has first-class support: podman container checkpoint <name> and podman container restore, including exporting a checkpoint to a tarball to restore on another host.
  • Docker has docker checkpoint create, behind experimental features.
  • Kubernetes supports forensic container checkpointing through the kubelet API, producing a checkpoint archive of a running container for analysis — restoring it as a new container is possible with compatible runtimes.
  • LXD/Incus use CRIU for live migration of system containers.

(runc and OCI Runtimes, containerd vs Docker)

What it can't capture (well)

  • External connections. An established TCP connection to a database or API can be checkpointed with --tcp-established, but restoring it elsewhere only works if the peer still accepts it and the IP moves too. In practice, applications must reconnect.
  • Devices and GPUs. Device state lives in hardware and drivers; GPU checkpointing needs vendor-specific support.
  • Some kernel objects and newer interfaces may not be supported yet; check CRIU's compatibility for your kernel.
  • Kernel and CPU differences. Restoring onto a different kernel version or a CPU with different features can fail.
  • Files must match. Open files are restored by path; if the file changed or isn't there on the target, restore fails. Shared filesystems or copying the rootfs solve this.

Permissions

CRIU traditionally needs root (CAP_SYS_ADMIN). Since Linux 5.9, the narrower CAP_CHECKPOINT_RESTORE capability allows unprivileged checkpoint/restore in more cases. Inspecting and rewriting another process's memory is powerful — treat checkpoint images as sensitive, since they contain the full memory of the process: secrets, keys, tokens. (Linux Capabilities)

CRIU vs VM snapshots

CRIU (process/container) VM snapshot (e.g. Firecracker)
Captures A process tree An entire machine: kernel, devices, all processes
Fidelity Depends on supported kernel features Very high — the guest doesn't know
Portability Needs compatible kernel/CPU Needs compatible hypervisor/CPU
Size Just the processes' memory Full guest memory
Typical use Container migration, fast app startup Sandbox reuse, fast VM startup

(Firecracker Snapshots, Kata Containers)

Why this matters for agent workspaces

Agent sandboxes are usually ephemeral: tear down after each task, losing installed dependencies, running dev servers, and in-memory state. Checkpoint/restore — at the process level with CRIU or the machine level with VM snapshots — is one route to "pause the whole environment and resume it later". The other route is simply not tearing it down: a persistent machine that's still there tomorrow. (Why AI Coding Agents Need Persistent Workspaces, The Sandbox Is the Wrong Abstraction)

The summary

  • CRIU freezes a process tree, dumps its full state, and restores it later or elsewhere.
  • Podman, Docker (experimental), Kubernetes and LXD/Incus build on it.
  • External connections, GPUs and kernel differences are the hard limits; images contain secrets.

EasySpawn takes the persistent route: each server is its own VM that keeps your processes, files and database between sessions, so there's nothing to checkpoint or rebuild. See how it works or join the waitlist.

Related: Linux Namespaces Explained · vsock Explained · Firecracker vs gVisor vs Containers · PID 1 in Containers

Keep reading