Lab 1: Buffer OverflowsLab OverviewImportant Note: This course's labs, including this lab, ask you to design exploits and to perform attacks. These exploits and attacks are realistic enough that you might be able to use them to perform a real-world attack, but you should not do so. The only goal of the designing exploits is to teach you how to defend against them, not how to use them to attack others---attacking computer systems is illegal and can get you into serious trouble. Don't do it.You will do a sequence of labs in this course. These sequence of labs will give you practical experience with common attacks and counter measures. These labs consist of the following:
This is lab 1, in this lab, you will study the basic principal of buffer overflows and then use this knowledge to attack a real-world application: a web server. Finally, you'll fix the buffer overflows by patching the source code. Software SetupYou should finish all labs on the Linux OS we given, so you should first install the Ubuntu OS listed on the tools page. Especially, you should download and install the Ubuntu 12.04. (Download this software to your machine and unpack it into some directory.) Important note: install the OS in a virtual machine (say, VMWare), instead of on your bare machine, or else the attack may bite yourself. Getting StartedWe've offered some code here to start with. Download this code to your machine and unpack it into some directory.Lab RequirementThere are two kinds of exercises: normal exercises and challenge ones. Challenge exercises may not be that hard, but may involve substantial code hacking. You are required to do ALL normal exercises. All challenge exercises are optional (but you're encouraged to try them).Hand-in ProcedureWhen you finished your lab, zip you solutions and submit to the school's information system.Part A: Buffer Overflow PrincipalIn this part of the lab, you will study the basic principal of buffer overflows, and then you will study how to use buffer overflows to attack a simple vulnerability program, some basic theorem will assistant you to realise the goal.
Now, you should browse the source code we given and find out
the file $ gcc -g stack1.c -o stack1 $ ./stack1note the use of the -g parameter, which will
be useful when you debug the executable using gdb.
Stack Layout and BuffersIn computer science, a call stack is a stack-like data structure holding information to control function calls and returns. Stack layout is the convention on how the stack frame is used. As an example, read the simple C program given you (the C filestack1.c ).
When the function +------------------+ high address | ... | | stack frame of | | main | | ... | +------------------+ | str(a pointer) | (4 bytes) | return address | (4 bytes) %ebp----> | saved %ebp | (4 bytes) +------------------+ | buf[11] | | ... | (12 bytes) buf----> | buf[0] | | variable_a | (4 bytes) | ... | +------------------+ low address
Exercise 1.
Now, you can write some code. Your job is to
print the address of the variable
Challenge!
Read the file gdb . In this and future labs, you will
use gdb heavily.
Exercise 2.
Use $ gdb stack1 (gdb) b func Breakpoint 1 at 0x8048412: file stack.c, line 8. (gdb) r Starting program: /tmp/stack1 8 strcpy(buffer,str); (gdb) info r eax 0x80484e8 134513896 ecx 0xbffff504 -1073744636 edx 0xbffff494 -1073744748 ebx 0xb7fc8000 -1208188928 esp 0xbffff410 0xbffff410 ebp 0xbffff438 0xbffff438 esi 0x0 0 edi 0x0 0 eip 0x8048412 0x8048412 Address Space Layout RandomizationIn order to protect against buffer overflows, most recent operating systems introduce many protection mechanisms, among which the most important one is address space layout randomization (ASLR). Basically, in a system with ASLR, the starting address of the heap and the stack, along with other segments, will be randomized, so it's will be difficult for the attack to know or guess the specific address of any memory segments, say the stack. Here is a brief introduction, in lab 2, you will study ASLR in detail and learn how to defeat ASLR. For the purpose of this lab, you should simply turn off ASLR (in lab 2, you'll perform attacks when ASLR is effective), which will make your attack easier to achieve. To turn off ASLR, you can run these commands:$ su root Password : (enter root password) # sysctl -w kernel.randomize_va_space=0 Exercise 3.
Turn off the address space layout randomization, and then do
exercise 1 again, write down the three addresses in
Buffer Overflow and ShellcodeA buffer overflow occurs when data written to a buffer exceeds the length of the buffer, so that corrupting data values in memory addresses adjacent the end of the buffer. This often occurs when copying data into a buffer without sufficient bounds checking. You can refer to Aleph One's famous article to figure out how buffer overflows work.
Now, you run the program $ ./stack1 aaaaaaaaaa Returned Properly $ ./stack1 aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Segmentation faultIf you don't observe Segmentation fault , just
increase the number of the input a s. Here, the message
Segmentation fault indicates that your program
crashed due to invalid memory access (for instance, refer to
memory address 0).
Exercise 4.
Use Challenge!
Try to write a C program which prints every
return address in the call stack until the
invocation of the current function. This is often
called a
backtrace. This behaves like
the a s (0x61616161).
Interestingly, you can supply the starting address of the current
buffer being overflowed, whose address has been studied in
exercise 1. More interestingly, if the buffer contains
some binary code, that code will be executed. Any binary
code can be supplied, especially, Alpha One offers
a binary code to pop a shell, so this kind of binary
code is often called
shellcode, although
such kind of binary code can do much more interesting things (attacks).
Now compile the supplied C program $ gcc -z execstack test-shell.c -o test-shell $ ./test-shell sh-3.2$ id uid=1000(seed) gid=1000(seed) groups=4(adm),20(dialout),24(cdrom), 46(plugdev),106(lpadmin),121(admin),122(sambashare),1000(seed) sh-3.2$ exit $The -z execstack option will mark the stack segment
executable, which you'll study in detail in lab 2.
Exercise 5.
The shellcode we offered can pop up a shell, Now it's your
turn to attack the C program named $ gcc -g -z execstack -fno-stack-protector stack2.c -o stack2 $ ./stack2 sh-3.2$ id uid=1000(seed) gid=1000(seed) groups=4(adm),20(dialout),24(cdrom), 46(plugdev),106(lpadmin),121(admin),122(sambashare),1000(seed) sh-3.2$ exit $Here, the -fno-stack-protector option will
disable gcc's
stack canary.
Hint: you can use the gdb when necessary, but keep in mind that
there are some minor differences between the result from gdb and
that from the stand-alone executable.
Challenge! Write other kind of (more interesting) shellcode, do whatever you want to do. Part B: Buffer Overflows in the Touchstone Web ServerIn this part of the lab, you will explore how buffer overflows happen in real-world and how to exploit them. To make the discussion concrete and realistic, you will study a small web server called Touchstone. The touchstone web server is realistic enough to serve static pages (though you can extend it with other features), and meanwhile small enough whose source code can be studied very quickly. We have left some bugs and vulnerabilities in the touchstone web server, some of which will be studied in this lab, whereas others will be studied in future labs.The Touchstone Web ServerAll the source code for touchstone is stored in the code repository. Now compile the touchstone web server and deploy it:$ cd web-server $ make $ ./touchstoneOpen your browser to input this URL http://127.0.0.1:8080 , you
will get a simple "hello, world" page. If that fails,
try to re-run the web
server like as ./touchstone 8899, and your browser
URL should input http://127.0.0.1:8899 . Contact us, if
you still have problems.
Exercise 6.
Study the web server's code, and look for code vulnerability
which can be exploited to crash the server by buffer
overflows, pay special attention to the file Attack the Web ServerEven though the vulnerability has been detected in the web server, it's still difficult for you to crash the server, because your browser will do most of the dirty work for you that you can not control, that is, you can only do good things with such a browser. So, as a hacker, you have to write your own browser from scratch. We have offered you a simple browser in the filebrowser.c , basically, this browser will
construct an
http request and then send to the web server, waiting for
the server's response. The browser is simple enough that
is does not come with an html render, however, it's not
difficult to add an html render engine and a UI to make
it more realistic. In fact, there are many
open source html render engine, say webkit. You are
encouraged to do so, if you're interested in.
Exercise 7.
For the buffer overflow vulnerability you've found,
construct an input to send to the touchstone web server, your goal
is to crash the web server (the http server daemon).
Note: if you're successful to crash the web server, your browser
will remain dead-waiting to receive data from the
server. Don't forget
that any valid request must end up with grades.txt ).
To start with, you can use
the program create-shellcode.c ,
to construct your shellcode,
you may have to modify the file according to your need. And you
can copy your
shellcode to the C program test-shell.c .
Exercise 8.
Perform your attack by constructing an exploit that hijacks control
flow of the web server and unlink (delete) Challenge! Write a remote shellcode, so that you can gain control of a remote machine. Remote shellcode is used when an attacker wants to target a vulnerable process running on another machine on a local network or intranet. If successfully executed, the shellcode can provide the attacker access to the target machine across the network. Remote shellcodes normally use standard TCP/IP socket connections to allow the attacker access to the shell on the target machine. Such shellcode can be categorised based on how this connection is set up: if the shellcode can establish this connection, it is called a "reverse shell" or a connect-back shellcode because the shellcode connects back to the attacker's machine. To bypass the firewalls, you can use the port reuse techniques. Part C: Fixing buffer overflowThe source of buffer overflow vulnerability comes from the web server's source code, so you should realize the importance to write secure code from the first place, though it's, nevertheless to say, not easy. For the specific buffer overflows in this lab, you can fix buffer overflows relatively easily by modifying the source code. If you can not gain access to the source code, say your Windows has a buffer overflow (that's often the case), you will have to wait for M$ to publish a security update.Exercise 9.
Try to fix the buffer overflow vulnerabilities of the
touchstone web server. You can use whatever techniques
to achieve this, say use safe string copying function
HandinThis completes the lab. Remember to hand in your solution to the information system. |