Lorenzo La Corte - 2023/2024 - Università degli Studi di Genova


<aside> 💡 Link to the web version (more readable): llacorte.notion.site/BASC-Assignment-3-Shellcoding-16e1781343c84a7ea501005fc7798a2d

</aside>


This report provides descriptions of exploits for challenges about shellcoding.

Exploit BOF101

The first challenge is a 32-bit executable:

$ file bof101_x86 
bof101_x86: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux.so.2, BuildID[sha1]=fce5de9ddde57361906ed6cb58f06280aa414e4c, for GNU/Linux 3.2.0, with debug_info, not stripped

This guided exercise not only provides the attacker with the source code but also with a lot of information on what is going on:

$ ./bof101_x86 
+---------------+
|    BOF 101    |
| (x86/32-bits) |
+---------------+

I'm in main().
Since this is your first challenge, you'll get a leak for free: &x=0xffdb979c

Now, I'll call foo().

I'm at the beginning of foo(), and this is the current stack content:
0xffdb9784 | 9c 97 db ff  | .... | 
0xffdb9780 | 48 a2 04 08  | H... | 
0xffdb977c | fa 96 04 08  | .... |  <--- saved return address (0x80496fa)
0xffdb9778 | a8 97 db ff  | .... | 
0xffdb9774 | 74 98 db ff  | t... | 
0xffdb9770 | 00 c0 04 08  | .... | 
0xffdb976c | 00 00 00 00  | .... |  <--- end of the buffer "name"
0xffdb9768 | 00 00 00 00  | .... | 
0xffdb9764 | 00 00 00 00  | .... | 
0xffdb9760 | 00 00 00 00  | .... | 
0xffdb975c | 00 00 00 00  | .... | 
0xffdb9758 | 00 00 00 00  | .... | 
0xffdb9754 | 00 00 00 00  | .... | 
0xffdb9750 | 00 00 00 00  | .... |  <--- beginning of the buffer "name"
0xffdb974c | 00 c0 04 08  | .... | 

Please enter your name:

What immediately appears evident when talking about BOF, is the use of the gets function, which doesn’t check the buffer capacity against the length of the user input.

This allows a potential attacker to overwrite other parts of the memory: as a matter of fact, if more than 32 chars in input are inserted, the result is the overflow of the buffer:

0xff994cd0 | 61 61 61 61  | aaaa | 
0xff994ccc | 61 61 61 61  | aaaa |  <--- end of the buffer "name"
0xff994cc8 | 61 61 61 61  | aaaa | 
0xff994cc4 | 61 61 61 61  | aaaa | 
0xff994cc0 | 61 61 61 61  | aaaa | 
0xff994cbc | 61 61 61 61  | aaaa | 
0xff994cb8 | 61 61 61 61  | aaaa | 
0xff994cb4 | 61 61 61 61  | aaaa | 
0xff994cb0 | 61 61 61 61  | aaaa |  <--- beginning of the buffer "name"

Find the Return Address Offset

The goal now is to find the offset from the buffer to the return address, in other to overwrite the latter. I can use cyclic and gdb, in particular:

So, the offset that I have to use to overwrite the return address is 44.

Overwriting the saved return address