Vulnserver - TRUN Command
As part of my preparation for the taking the CTP course and OSCE exam I used the vulnserver.exe to practice and develop my skills.
1. Intro
Vulnserver is a Windows based threaded TCP server application that is designed to be exploited. The program is intended to be used as a learning tool to teach about the process of software exploitation, as well as a good victim program for testing new exploitation techniques and shellcode.

You can get a copy of the application here https://github.com/zflemingg1/OSCE/tree/master/Vulnserver
2. The Setup
2.1 Interface
Using netcat connect to X.X.X.X:9999 and issue the HELP command to confirm that everything is working as expected:

3. Fuzzing
For the purpose of this tutorial we will be focusing on fuzzing the TRUN command. Observing that the valid argument structure for the TRUN command is roughly <trun>[space]<command_value> we can try sending TRUN hello as a test and see if it’s accepted.


As can bee seen above, the command and argument executed successfully. Now that we have confirmed the structure of a command and its arguments, we can start fuzzing this command to see if we can get the program to crash when submitting various argument values to the TRUN command.
The following BOOFUZZ template was created to fuzz the TRUN command in an effort to get the program to crash.
3.1 Crash
The following command appears to have crashed the program indicating that the "TRUN" command can be manipulated to force the program to crash.


3.2 Analysing The Crash
Based on the TCP stream (Figure 5), the number of bytes that was sent by the fuzzer and that caused the crash was around 5000 bytes.
To gain a better understanding of this, the following template was used to identify the length needed to overflow the TRUN command and cause the crash:


As can be seen from figure 6 the program crashes when a string of 5990 chars is sent. Checking the dump using immunity it can be seen that we control a buffer of length 2990 bytes - Figure 7.
4. Determine Offset
Using msf-pattern_create create a pattern of length 2990 bytes.

Update the exploit and execute it

4.1 Get Offset
Using msf-pattern_offset and the value 386F4337 (Figure 9 EIP Value) we can determine our exact offset.

4.2 Confirm Offset
Restart the application in immunity and execute the updated POC below

As can be seen from Figure 11, we can successfully control EIP. It can also be observed that the buffer of C’s is located directly after the 4 bytes of B’s. This means that we will be able to simply place our shellcode right after the 4 bytes of B’s.
5. Bad Character Analysis
Clone the https://github.com/zflemingg1/OSCE/tree/master git repository and configure the dependency package as instructed.
5.1 Modifying The Script
Outlined below are the changes you will need to make:

5.2 Results
Execute the script. Once finished you should have identical results to those outlined below in Figure 13.


As can be seen from Figure 14, '\x00' is the only bad character.
6. Redirecting Execution Flow
As can be seen from Figure 13 all the expected characters (\x01 to \xFF) are accepted. This means that the only bad character was the NULL byte (\x00 - Figure 14). The next step was to find an address that contains a JMP ESP instruction. ]
NOTE: It’s always recommended to use an address from the application itself, or a DLL that comes with the application for compatibility purposes. I.E. the exploit will work even if the application was installed on a different machine. For Vulnserver.exe we can look at the DLL that comes with it (essfunc.dll).
Restart the application in Immunity and execute the following command !mona jmp -r esp -m "essfunc.dll".

Take note of the address highlighted in the above picture (0x625011AF)
6.1 Taking Control of EIP
Restart the application in Immunity, set a breakpoint at address 0x625011AF and execute the updated POC below

Step through the breakpoint using F7 and you will land in the C buffer - Figure 17.

7. Generating Shellcode
Using all the information that we've gathered we can now generate the payload as shown below:
msfvenom -p windows/shell_bind_tcp EXITFUNC=thread -b "\x00" -f python -v shellcode

7.1 Getting Shell
Restart the application and execute the updated POC shown below:
NOTE: A nopsled (8 NOP instructions) were added before the shellcode to give room for the decoder to work
Using netcat, connect to the target host using port 4444 and you should now have a reverse shell:

Last updated
Was this helpful?