Due: Fri Mar 17 11:59 pm
No late submissions accepted.
Assignment by Matthew Volk and CS107 Staff
Learning goals
Completing this assignment will give you:
- a small taste of security topics
- experience writing buffer overflow and other classic attacks
- a compelling reason to consider CS155!
Introduction
Welcome to Wells Buggy! The Wells Buggy bank is concerned that their bank database API may have some security vulnerabilities in it, and they've come to seek your expert advice to find them. As a security consultant, you've been given full access to their database API code, which is written in C. Your job is to look at the C source code and determine how the functions in the database API could be called in ways that would cause security problems for the database. While it is not prohibited to look at the disassemble as you did with Binary Bomb, you shouldn't need to do that to find or exploit the vulnerabilities. There are three levels to progress through (three different vulnerabilites to find), and they can be done in any order.
Your job in this assignment is to use your elite CS107 skills to break into this bank. You'll be demonstrating that you can: (1) steal money from the bank, (2) bypass the login function and access all user data without a password, and (3) log in as the privileged CEO user and take down the bank from the inside.
Logistics
Note that this is not a partner project! You need to write your own solution.
Take a look at the files in your repo. All your edits should be made in the exploits.c file, but you should be familiar with the contets of all files. This is what each file does:
- database.[h,c]: This is Wells Buggy's buggy database API. Though you can't change it, you're welcome to dig through the C code to your heart's content.
- exploits.[h,c]: This is your main deliverable for this project. You shouldn't modify the .h file, but the attacks you write for the three levels will go in the .c file.
- runexploits.c: This calls the functions you write in exploits.c to test them.
- readme.txt: This file is initially empty and is your second deliverable for this assignment. You'll do a brief writeup here.
- database.tsv: This file holds the actual database data (customers' names, passwords, and account balances). You may edit it for testing purposes, but none of the exploits involves editing it directly, and your exploits.c code needs to work without editing this file. Note: it is ok to use your knowledge of the contents of this file in order to write your code in exploits.c.
Level One
First, you will demonstrate that people who call db_withdraw
with carefully chosen values can steal money from the bank and add it to anyone's account! Your task here is to steal money from the bank and give it to your favorite CS107 TA, Matt (his username is mvolk). Write code in exploits.c, including malicious input to the db_withdraw
function, to make Matt's account balance $1,000,000.
Because you have access to the software and the database text file, you could edit Matt's account balance that way (i.e., just edit the database text file; or run the code in gdb and find the database entries in memory, and then change account balances by writing memory in gdb; or do some fancy custom void* pointer arithmetic work in C to write memory in the database). But all of these approaches are off-limits. We're interested in seeing what vulnerabilities can be exploited through the API.
Level Two
A careful reading of the database.h and database.c files will show you that database.c contains two kinds of functions: (1) "public" API functions that are listed in database.h and intended to be called by users of the API, and (2) "private" helper functions that are used by the public functions, but cannot be called from outside the database.c file.
Recall that in C, there are no "public" and "private" function/method descriptors like we have in Java classes and C++ classes (indeed, C doesn't have classes at all!). But the "static" keyword can be added to a function signature to achieve a sort of analogous thing. Specifically, if a function has "static" in its signature, it is not "visible" (cannot be called from) anywhere outside the .c file in which it is contained. For example:
[in a file api.c]
static void my_private_helper_function(int x)
{
printf("private! %d\n", x);
}
void my_public_function(int x)
{
printf("public! %d\n", x);
}
[in a file foo.c]
// function prototypes
void my_private_helper_function(int x);
void my_public_function(int x);
int main(int argc, char *argv[])
{
int num = 5;
my_private_helper_function(num); // will not compile! (specifically, linker will fail to find the implementation)
my_public_function(num); // this is just fine
return 0;
}
So you should look for the static keyword in the database.c file, and notice that there is one particular static function, debug_print_database
that you should not be able to call. There is a good reason that the software engineer who wrote the database code made this function static and inaccessible outside the database code--it prints the contents of the entire database, including customers' names, passwords, and account balances! The software engineer wrote this so that, when debugging their own code, they could call it to check the database values for correctness. You would like to show the Wells Buggy staff that this function, which was supposed to be protected, can be caused to execute, simply by making malicious-input call(s) to the public functions.
As with your Level 1 exploit, you must accomplish this only by sending malicious input(s) to otherwise "normal" calls to the public functions. Of course, as the security consultant, you already have the ability to read the database file and throgh memory, but you're going to demonstrate that anybody who can call functions listed in database.h can get the debug function to print the database of users and passwords.
Level Three
Lastly, you're going to blow the bank's server apart. To do this, you're going to need to call db_destroy. You'll soon realize that there's a bit of a problem though.... Only the CEO can call this function, and his password is special. Good luck! (As with Levels 1 and 2, this exploit is to be performed by sending malicious input to the functions listed in database.h.)
Readme File
Once you've finished your attacks, write three to four sentences on each level, explaining the techniques that you used. These explanations go in the file readme.txt. For each attack, first describe the security hole you took advantage of. Then, describe what your attack does and why it works. Lastly, suggest a change (or changes) that Wells Buggy could make to patch the security hole.
SPECIAL FOR WINTER 2017 QUARTER: This is a relatively new assignment for CS107. If you have any thoughts about the difficulty and enjoyability of the different levels, about how much they did or didn't contribute to your learning, or any other helpful feedback, we strongly encourage you to include those comments in your readme.txt so we can incorporate that feedback into future quarters' course design. Thanks!
Even if you're not quite able to get your security attack working, you can describe what you would've done or an approach you think might've worked for partial credit.
Remember, you do NOT need to finish one attack before moving on to the next. They are independent of each other.
Grading
This assignment is entirely extra credit this quarter. The whole assignment will be out of 15 points (5 points per level). Three points are for the exploit in exploits.c, and two points are for the explanation in readme.txt.
Reminders on what you can and can't do for your exploits in this assignment:
- This is not a pair assignment - all work must be your own!
- You shouldn't modify any files besides exploits.c and readme.txt.
- You can change the tsv file containing your unique database for testing purposes, but we'll be grading against your original, unmodified database, so changes to it won't be tested.
Getting started
The starter project contains your database with the files given above. Check out a copy of your cs107 repositor with the command:
hg clone /afs/ir/class/cs107/repos/assign6/$USER assign6
Finishing
The committed version of exploits.c
should contain your three attacks, and the committed version of readme.txt
should contain three or four sentences on each of the attacks implemented. When grading, we will run you exploits with the original, unmodified database.tsv
file. When finished, you must submit to send your files for grading.