Container Isolation
The security boundaries that Linux namespaces and cgroups create around a container process, limiting its view of the filesystem, network, processes, and system resources. Container isolation is weaker than VM isolation — all containers share the host kernel.
Container Isolation — What Separates Containers From Each Other
What Is Container Isolation in Simple Terms?
Container isolation is the set of boundaries Docker creates around each container process. These boundaries are implemented by the Linux kernel using two technologies: namespaces (which control what the process can see) and cgroups (which control what resources it can use).
The important thing to understand: containers are NOT virtual machines. They share the host kernel. The isolation is real and effective for most purposes, but it is not as complete as VM isolation.
+------------------------------------------+| Virtual Machine Isolation || Complete OS boundary || Different kernel per VM || Kernel exploit in one VM: || cannot affect other VMs || Escape difficulty: very high |+------------------------------------------+ +------------------------------------------+| Container Isolation || Namespace + cgroup boundary || Shared kernel || Kernel exploit: || could affect all containers on host || Escape difficulty: moderate || But: more than enough for most workloads |+------------------------------------------+The Six Namespaces Docker Uses
# PID namespace — container has its own process tree# Container sees PID 1 (nginx), host sees PID 12345docker exec my-nginx ps aux# PID 1 = nginx master ps aux | grep nginx# PID 12345 = nginx master (same process, different view) # NET namespace — container has own network interfacesdocker exec my-nginx ip addr# eth0: 172.17.0.2 <- container sees its own interface ip addr # on host# docker0: 172.17.0.1 <- host sees bridge interface # MNT namespace — container has own filesystem view# /etc/nginx/nginx.conf exists in container# same path does not exist on host # UTS namespace — container has own hostnamedocker exec my-nginx hostname# a84f9c2b1d3e <- container ID as hostname hostname # on host# prod-server-01cgroups — Resource Isolation
# Set memory and CPU limitsdocker run -d \ --memory=512m \ --cpus=1.5 \ payment-api:latest # Kernel enforces these limits# Memory exceeded: process killed (OOMKill)# CPU exceeded: process throttled # Verify cgroup limits are setcat /sys/fs/cgroup/memory/docker/$(docker inspect \ --format '{{.Id}}' payment-api)/memory.limit_in_bytes# 536870912 = 512MBIsolation Limitations
What containers DO isolate: Filesystem (each container has its own view) Network (each container has its own interfaces) Processes (containers cannot see each other's processes) Hostname (each container has its own hostname) Resources (cgroups limit CPU and memory) What containers do NOT isolate: The Linux kernel (shared by all containers) Kernel vulnerabilities (affect all containers on host) Time (containers share host clock) System calls (containers use host kernel syscalls)SecurityContainer isolation is sufficient for running trusted workloads on a shared host. For running untrusted code (like user-submitted programs), consider stronger isolation: gVisor (Google's container runtime with its own kernel), Kata Containers (lightweight VMs), or Firecracker (microVMs used by AWS Lambda and Fargate). These provide VM-level isolation with container-level startup speed.
Frequently Asked Questions
What exactly does container isolation prevent, and what does it not prevent?
Namespaces give a container its own view of the filesystem, network interfaces, process tree, and hostname, so processes inside can't see or directly interact with processes, files, or network sockets outside their namespace by default. What it doesn't provide is kernel isolation — every container on a host shares that one kernel, so a kernel vulnerability or a container running with excessive capabilities can potentially break out, which is fundamentally different from a hypervisor-isolated VM.
What's a common container isolation mistake in production?
Running containers as root inside the container (the default unless a Dockerfile specifies USER) and/or granting `--privileged` mode for convenience during debugging, then shipping that config to production. A root process inside a container that escapes isolation becomes root on the host. Best practice: run as a non-root user, drop unnecessary Linux capabilities explicitly, and use read-only root filesystems where the application allows it.