Due Date: October 15, 2014, 5pm
- The goal of this lab is to gain hands-on experience
with the effects of buffer overflow bugs. All work in this project must be done on the server that we provide to you.
- You are given the source code for six exploitable programs (/bin/target1, ... , /bin/target6). These programs are all installed with the setuid flag on the server. Your goal is to write five (+1 for extra credit) exploit programs (sploit1, ..., sploit6). Program sploit[i] will execute program /bin/target[i], giving it certain input that should result in a shell running under its owner on the server.
The skeletons for sploits 1 through 6 are provided in the
~/sploits directory. Note that the exploit programs are very short, so there is no need to write a lot of code here.
You are to write an exploit for targets 1 through 5. Each exploit should yield a shell (/bin/sh) under its respective owner.
You are only required to write exploit programs for targets 1 through 5. Target 6 serves as extra credit. You should not feel any pressure to work on target #6.
- You will test your exploit programs within a server running Debian Linux. To connect to the server, SSH into 22.214.171.124 with your CSE credentials. Please try to SSH into the server early and let us know if you have any problems!
- We provide editors such as vim, nano, and emacs on the server for you to write your sploits. However, if you feel more comfortable writing these sploits on your local computer, feel free to download the sploits through the SFTP protocal.
- Make sure that your exploits work within the server we provided.
- Start early. Theoretical knowledge of exploits does not
readily translate into the ability to write working exploits. Target1
is relatively simple and the other problems are quite a bit more
- You may wish to back up or write your code elsewhere. We suggest using SCP or SFTP to access files on the server. For Windows, WinSCP is a great tool. SCP and SFTP run on top of SSH, so use your SSH parameters (port, key, etc.) to connect.
- The targets and their corresponding sources are stored in /bin. You are free to study the source code of each target (located in ~/sources).
- Your exploits should assume that the compiled target programs
are installed in /bin.
- Each target is setuid to a user with the same name (i.e. /bin/target1 is setuid to target1, /bin/target2 is setuid to target2, etc.) This means that they run as their respective owners regardless of who runs it. The one exception is when they're run under a debugger. Allowing users to debug a setuid executable is a GIANT security flaw, so setuid programs temporarily lose their setuid-ness under a debugger. This means that you can only get a target user's shell when your sploits are ran outside of gdb.
- The sploits directory in the user home directory contains the
source for the exploits which you are to write, along with a Makefile for building them. Also included is shellcode.h, which gives Aleph One's
- Your exploit is only considered to be working if 1) you have a shell and 2) the 'whoami' command yields the name of the target you've exploited.
- You should work by yourself, although you can talk to others and interact with the TAs.
- Since we have access to your sploits, you won't need to submit any code.
- You have until the deadline to work on your sploits. You will, however, be unable to make changes to your code once the deadline has passed.
- Read Aleph One's "Smashing the Stack for Fun and Profit."
Carefully! We also recommend reading Chien and Szor's
"Blended Attacks" paper. These readings will
help you have a good understanding of what happens to the stack,
program counter, and relevant registers before and after a function
call, but you may wish to experiment as well. It will be helpful to
have a solid understanding of the basic buffer overflow exploits before
reading the more advanced exploits.
- Read scut's
"format strings" paper. You may
also wish to read
gdb is your best friend in this lab, particularly to
understand what's going on. Specifically, note the disassemble and stepi commands. You may find the x command useful to examine memory (and the different ways you can print the contents such as /a /i after x). The info register command is helpful in printing out the contents of registers such as ebp and esp. The 'info frame' command also tells you useful information, such as where the return EIP is saved.
A useful way to run gdb is to use the -e and -s command line flags; for example, the command gdb -e sploit3 -s /bin/target3 in the vm tells gdb to execute sploit3 and use the symbol file in target3. These flags let you trace the execution of the target3 after the sploit has forked off the execve process.
When running gdb using these command line flags, be sure to first issue catch exec then run the program before you set any breakpoints; the command run naturally breaks the execution at the first execve call before the target is actually exec-ed, so you can set your breakpoints when gdb catches the execve.
Note that if you try to set break points before entering the command run, you'll get a segmentation fault.
If you wish, you can instrument your code with arbitrary assembly using the asm() pseudofunction.
Aleph One gives code that calculates addresses on the target's stack based on addresses on the exploit's stack. Addresses on the exploit's stack can change based on how the exploit is executed (directory, arguments, environment, etc.); in our testing, we do not guarantee to execute your exploits as bash does.
You must therefore hard-code target stack locations in your exploits. You should not use a function such as get_sp() in the exploits you hand in.
- There's lots of online documentation for GDB. Here's one you might start with: GDB notes.
- GDB will be discussed in section as well.
This project was originally designed for Dan Boneh and John Mitchell's
CS155 course at Stanford, and was then also extended by Hovav Shacham at UCSD and Yoshi Kohno at UW. Thanks Dan, John, Hovav, and Yoshi!