Notes on Dirty COW — particularly relating to Docker container escape
Dirty COW is an exploit in how the linux kernel handles file access. The steps involved are:
- Open a read-only file
- Map the file in memory using mmap
This uses a memory address at which we can access (our copy of) the file contents - Simultaneously kick off the next two steps in parallel:
- Write to the file
No problem; although the original file is read-only, we’re only writing to our copy (which is “wherever the pointer from step 2 points”) - Say we no longer need our copy of the file (MADVISE_DONTNEED)
This reverts the memory address to the original read-only file
The vulnerability comes with the memory address of the file flipping between the original and our copy, caused by our constant writing and calling MADVISE_DONTNEED.
If these two operations are done in parallel and quickly enough, there will eventually come a time where #4 occurs right before #3
i.e. the memory address is reverted to the original file, right before we’re allowed to write to (what was previously our ok-to-write-to copy — but is now the original file!)
Setup
The first challenge is running a linux kernel which contains the vulnerability.
By far the easiest way to do this is to run a VM using VirtualBox.
In general, these are downloaded from http://kernel.ubuntu.com/
For the shortcut — this page has the 3 commands you need to run https://tecadmin.net/install-linux-kernel-on-ubuntu/
wget http://kernel.ubuntu.com/~kernel-ppa/mainline/v4.3-wily/linux-headers-4.3.0-040300_4.3.0-040300.201511020949_all.deb
wget http://kernel.ubuntu.com/~kernel-ppa/mainline/v4.3-wily/linux-headers-4.3.0-040300-generic_4.3.0-040300.201511020949_amd64.deb
wget http://kernel.ubuntu.com/~kernel-ppa/mainline/v4.3-wily/linux-image-4.3.0-040300-generic_4.3.0-040300.201511020949_amd64.debdpkg -i *deb
update-grub
reboot
Then, when booting, after bios screen, but before OS loads, you need to get to the grub boot menu. In my experience this was always done by holding “shift”, however now it seems to be “escape”. Once you’re in the grub boot menu, choose to boot with the old kernel.
References
https://raw.githubusercontent.com/dirtycow/dirtycow.github.io/master/pokemon.c