The Chroot Escape Tool is a proof-of-concept utility designed to demonstrate various classic techniques for escaping a chroot(2) environment on Unix-like systems.
This tool attempts to escape the chroot environment using three distinct methods, each exploiting a different weakness in how chroot isolation can be circumvented when the process retains root privileges inside the jail.
Important: Chroot is not a security mechanism. It was never designed to contain privileged processes. This tool illustrates why relying solely on chroot for security is insufficient.
The program implements three independent escape methods. Each is attempted sequentially until one succeeds. All methods require the process to be running with UID 0 (root) inside the chroot jail.
This is the classic chroot escape technique that relies on the fact that the kernel does not track the "jail" origin after the first chroot call.
- The process changes its current working directory to
/within the jail. - It creates a new directory named
escape_tunnelinside the jail root. - It calls
chroot("escape_tunnel"), establishing a new root at that subdirectory. - From this new root, the process repeatedly calls
chdir("..")to walk upwards. Because the kernel's internal root pointer was moved toescape_tunnel, the..entry at that level points to the original host root that existed before the first chroot was applied. - Once the loop detects the presence of the target shell (
bin/sh) by repeatedly checkingstat(), it performs a finalchroot(".")to lock the root directory to the actual host root. - Finally, the program executes a shell, giving the user full access to the host filesystem.
This method leverages the fact that file descriptors opened before entering a chroot jail retain a reference to the original filesystem namespace.
- Before the jail is established, the process opens a file descriptor to the host's
/directory usingopen("/", O_RDONLY). (In a real scenario, the jail is already active, so this method relies on the process having opened such a descriptor earlier or being able to open/before the first chroot call. The POC simulates this by opening the descriptor while inside the jail but before creating the new chroot environment.) - The process changes directory to
/inside the jail, creates theescape_tunneldirectory, and chroots into it. - It then calls
fchdir(fd)wherefdis the descriptor pointing to the original host root. This changes the current working directory of the process to the host root despite the chroot confinement. - A final
chroot(".")is executed, breaking out completely. - The file descriptor is closed and a shell is spawned.
This method demonstrates that a root process inside a chroot jail can still create device nodes using mknod(2), provided the jail contains a /dev directory or the process has permission to create files.
- The program attempts to create a block device node for the primary disk (e.g.,
/dev/sdafor SCSI/SATA devices or/dev/hdafor older IDE devices). - If
mknodsucceeds, the process has direct block-level access to the underlying host storage. - It then attempts to invoke
debugfs(a filesystem debugger for ext2/ext3/ext4) with write access to the device. Ifdebugfsis present in the jail, this can be used to read or modify arbitrary files on the host filesystem. - This method does not automatically spawn a shell; it only confirms that raw device access is possible. An attacker with such access could mount filesystems, read sensitive data, or inject malicious code into host binaries.
If successful, the program will print a message indicating which method worked and then drop you into a root shell outside the chroot jail. You can verify the escape by examining the filesystem or checking the output of ls /.
Copy the compiled binary into the chroot jail and execute it:
./chroot-escape-toolIf successful, the program will print a message indicating which method worked and then drop you into a root shell outside the chroot jail. You can verify the escape by examining the filesystem or checking the output of ls /.
=== chroot escape POC ===
Method 1 failed, trying method 2...
$
After this prompt, you are outside the jail.
- The tool only works if the process is running with effective UID 0. Non-root processes cannot perform the
chroot()system call. - Modern systems may employ additional protections (e.g., mount namespaces, seccomp filters, Linux Security Modules) that prevent these escape techniques. The tool is effective against traditional chroot setups without such hardening.
- Method 3 requires the
mknodsyscall to be permitted and the presence of a/devdirectory where device files can be created. Some chroot configurations mount atmpfson/devor usedevtmpfs, which may still allow device node creation. - The tool cleans up after itself (removes the
escape_tunneldirectory and device nodes) only partially. Theescape_tunneldirectory remains in the jail after successful execution; it can be removed manually