đź§ Linux Enumeration - Docker Container
What is it?
- Concept: Once Linux Enumeration - General and its container-detection checks confirm you’re inside a Docker container (not Kubernetes), what’s left to enumerate is everything the general checklist skips because it’s Docker-specific: how the container is confined, what of the host leaks in through mounts/sockets/network, and what would let you break out to the host.
Exploitation
1. Container Identity
Goal: Confirm exactly what container/image you’re in before you start hunting for an escape.
- Container ID:
## Native alternatives (no `docker` CLI available inside the container by default)
head -1 /proc/self/cgroup # cgroup v1: path ends in the full container ID
cat /etc/hostname # Docker defaults the hostname to the short container ID- Image / Build Context Leftovers:
cat /proc/1/environ | tr '\0' '\n' # env vars baked into the image or passed via `-e`/`--env-file`
ls -la / # look for leftover COPY'd source, Dockerfiles, .git
cat /proc/1/cmdline # the ENTRYPOINT/CMD the image was built to run2. Privilege & Confinement Boundary
Goal: Determine how tightly this container is actually locked down — a privileged or under-confined container is a near-instant host escape.
- Privileged Mode Check:
ls -la /dev # a privileged container exposes ALL host devices (sda, mem, kmsg, etc.)
# a normal container only sees a handful (null, zero, random, tty, pts/*)
cat /proc/self/status | grep CapEff # compare against Linux Enumeration - General's capsh check;
# CapEff = full 64-bit mask (0000003fffffffff) is a strong privileged-mode signal- MAC (AppArmor/SELinux) Confinement:
cat /proc/self/attr/current 2>/dev/null # SELinux label, or...
cat /proc/1/attr/current 2>/dev/null
## AppArmor status is usually not visible from inside the container itself;
## absence of any enforced profile here is itself a signal worth noting.- Kernel Module Loading Ability:
cat /proc/sys/kernel/modprobe # if CAP_SYS_MODULE + host kernel modules dir is reachable, module-load escapes are possible
lsmod 2>/dev/null # usually blocked/empty inside a container regardless3. Docker Socket Exposure
Goal: Find out if the container can talk back to the Docker Engine — this is one of the most common and reliable full host-compromise vectors.
- Locating a Mounted Docker Socket:
ls -la /var/run/docker.sock /run/docker.sock 2>/dev/null
find / -name "docker.sock" 2>/dev/null- Talking to the Engine API Over the Socket (if present):
curl --unix-socket /var/run/docker.sock http://localhost/version
curl --unix-socket /var/run/docker.sock http://localhost/containers/json
## If reachable, you can typically spin up a new container with `/` bind-mounted from the host — full host root.4. Mounted Volumes & Host Paths
Goal: Identify what parts of the host filesystem (or other containers’ data) have been bind-mounted or volume-mounted in — these often bypass the container boundary entirely.
cat /proc/1/mountinfo # more detail than /proc/mounts: shows the host source path for each bind mount
findmnt 2>/dev/null # nicer formatting, if available
## Flag anything that isn't a container-internal overlay/tmpfs/proc/sysfs mount —
## especially a mount whose source looks like a host root path, /etc, /var/run, or another container's data dir.5. Docker-Specific Secrets & Linked Services
Goal: Find credentials that arrive specifically through Docker’s own mechanisms, rather than generic config files already covered by Linux Enumeration - General.
ls -la /run/secrets/ # Docker Swarm secrets — mounted read-only, not part of the regular env
cat /run/secrets/* 2>/dev/null
grep -i -E "_ENV|_PORT|_ADDR" <(cat /proc/1/environ | tr '\0' '\n')
## Legacy `--link`-style env vars (e.g. DB_PORT_5432_TCP_ADDR) reveal linked containers and their internal IPs/ports.6. Docker Networking Peculiarities
Goal: Understand container-to-container and container-to-host reachability, which differs from a normal host’s network layout.
cat /etc/hosts # Docker auto-populates entries for --link'd containers and compose service names
getent hosts host.docker.internal 2>/dev/null # if resolvable, this reaches the Docker host itself from inside the container
ip route | grep default # the default gateway on the docker0/bridge network IS the host — often a valuable pivot target directlyRelated Usage
| File | Created |
|---|