摘要

本報告針對 kkRAT (一種在近期惡意軟體活動中被發現的複雜 Remote Access Trojan) 提供全面的技術分析。分析深入探討了其多階段攻擊鏈、沙箱與虛擬機器規避技術、反分析與混淆方法,以及它繞過防毒軟體 (AntiVirus, AV) 和端點偵測與回應 (Endpoint Detection and Response, EDR) 系統的機制。此外,本報告還檢視了該 RAT 的資料通訊協定及其 payload 傳遞方法。為了說明 kkRAT 操作的技術複雜性,報告中包含概念性程式碼片段和詳細的攻擊鏈圖表。

駭客圈新寵!揭密 KKRAT 遠端木馬如何繞過你的 EDR 與防毒軟體? | 資訊安全新聞

1. 簡介

在不斷變化的網路威脅環境中,Remote Access Trojan (RAT) 由於能夠讓攻擊者對被滲透的系統擁有廣泛控制權,持續構成重大風險。本報告聚焦於 kkRAT,一種新發現的 RAT,它展現了進階的規避與持續運作能力。kkRAT 與 Ghost RAT 和 Big Bad Wolf (大灰狼) 等知名 RAT 有顯著的程式碼相似性,這表明在網路犯罪生態系中,可能存在某種血緣關係或共享開發資源。本分析的主要目標是剖析 kkRAT 的技術基礎,深入了解其操作方法以及為達成惡意目標所使用的複雜技術。透過了解這些機制,網路安全專業人士可以針對此類和類似威脅,開發更有效的偵測與緩解策略。

2. 關鍵技術特徵

kkRAT 透過幾個關鍵技術特徵使其脫穎而出,這些特徵有助於其有效性與隱匿性。一個突出的特徵是其網路通訊協定,儘管與 Ghost RAT 相似,但在資料壓縮後額外增加了一層加密。這種雙層方法增強了其命令與控制 (C2) 通訊的機密性與完整性,使得網路安全解決方案更難以偵測與分析其流量。除了通訊方法之外,kkRAT 還具備剪貼簿操作功能,特別設計用於替換加密貨幣位址,這表明其部署背後存在財務動機。它也促進了合法遠端監控工具 (如 Sunlogin 和 GotoHTTP) 的部署,這些工具可用於持續存取與監視。kkRAT 規避策略的一個關鍵環節是其利用 Bring Your Own Vulnerable Driver (BYOVD) 技術。此方法允許 RAT 利用合法 driver 中已知的漏洞來移除已註冊的來自防毒軟體 (AV) 和端點偵測與回應 (EDR) driver 的 callbacks,從而有效停用或嚴重損害安全軟體的功能。這些綜合特徵突顯了 kkRAT 被設計為惡意 Threat actor 的強大且適應性強的工具。

3. 攻擊鏈分析

kkRAT 所使用的攻擊鏈是一個多階段程序,旨在確保隱密的初始危害、穩健的持續運作以及有效的 payload 傳遞。初始載體通常涉及託管在 GitHub Pages 等平台上的釣魚網站,冒充合法的軟體安裝程式。這些欺騙性的網站分發包含惡意可執行檔的 ZIP 壓縮檔。一旦執行,惡意軟體會啟動一系列檢查與規避動作,然後才進入後續階段。攻擊的整體流程可視化如下:

graph TD A[User clicks malicious link] --> B{GitHub Pages phishing site} B --> C[Downloads ZIP archive
malicious executable] C --> D{First Stage Execution} D --> E{Sandbox/VM Check} E -- Detected --> F[Evasive Actions PEB
alteration, process
termination] E -- Not Detected --> G[Anti-analysis/Obfuscation
API resolution,
file decryption] G --> H{Second Stage Execution} H --> I{AV/EDR Bypass
Privilege check,
network disable,
driver disable,
callback removal} I --> J[Registry Modification] J --> K[Network Re-enable] K --> L{Third Stage Execution Downloader} L --> M[Downloads
2025.bin shellcode] M --> N[Downloads
output.log Base64
encoded structured data] N --> O[Decodes
output.log URLs
for trx38.zip and *.zip] O --> P[Downloads trx38.zip
legitimate executable
+ malicious DLL] O --> Q[Downloads *.zip
longlq.cl
- encrypted payload] P --> R[Creates shortcut for
legitimate executable] Q --> S[Final Payload Decryption
and Execution]

圖 1: kkRAT 技術攻擊鏈

3.1. 第一階段: 規避與混淆

kkRAT 攻擊鏈的第一階段主要專注於環境檢查與反分析技術,以規避沙箱環境和虛擬機器 (Virtual Machines, VM) 的偵測。惡意軟體為此目的採用兩種不同的方法。首先,它使用 QueryPerformanceCounter 執行時間穩定性分析。這涉及測量重複操作所需的時間,並將平均持續時間 (預期約 300 毫秒) 與預設的 thresholds (0.0008) 進行比較。與此 thresholds 的顯著偏差表明存在沙箱或 VM 環境,會觸發規避動作 [1]。其次,惡意軟體評估硬體設定,特別是檢查最少 50 GB 的磁碟空間和至少兩個 CPU 核心。如果未滿足這些 thresholds,惡意軟體會啟動規避動作,包括修改 Process Environment Block (PEB) 結構。這種修改涉及變更 ProcessParameters->ImagePathName ProcessParameters->CommandLine 以模仿 %WINDIR%\explorer.exe 。此外,惡意軟體會檢查 InLoadOrderModuleList ,如果任何項目的 BaseDllName 與當前 程序 名稱相符,則 BaseDllName FullDllName 都會被更名為 %WINDIR%\explorer.exe 。這些修改旨在破壞沙箱所採取的最終 程序 快照,導致惡意軟體的執行終止,從而阻止分析 [1]。

除了環境檢查之外,第一階段還包含了反分析與混淆方法。API 解析是動態執行的,所需 Windows API 函式透過對堆疊字串執行單一位元組 XOR 操作 (key 為 0x4 ) 來載入。此技術使得靜態分析工具更難以識別被呼叫的 APIs。同樣地,對於下一階段的檔案解密,惡意軟體會應用單一位元組 XOR 操作 (key 為 0x1 ) 來提取解密 key。然後為這些下一階段的 shellcodes 分配記憶體,隨後進行解密、寫入並直接執行。在此攻擊中使用的所有 shellcodes 都利用了 pe_to_shellcode 轉換邏輯,進一步使其分析複雜化 [1]。

概念性程式碼: PEB 變更

  1. // Conceptual code for PEB alteration
  2. // This is a simplified representation based on the article's description
  3. // Actual implementation would involve direct memory manipulation and system calls
  4. typedef struct _UNICODE_STRING {
  5. USHORT Length;
  6. USHORT MaximumLength;
  7. PWSTR Buffer;
  8. } UNICODE_STRING, *PUNICODE_STRING;
  9. typedef struct _RTL_USER_PROCESS_PARAMETERS {
  10. BYTE Reserved1[16];
  11. PVOID Reserved2[10];
  12. UNICODE_STRING ImagePathName;
  13. UNICODE_STRING CommandLine;
  14. } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS;
  15. typedef struct _PEB {
  16. BYTE Reserved1[2];
  17. BYTE BeingDebugged;
  18. BYTE Reserved2[1];
  19. PVOID Reserved3[2];
  20. PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
  21. } PEB, *PPEB;
  22. // Function to get PEB (simplified)
  23. PPEB GetPEB() {
  24. return (PPEB)__readgsqword(0x60); // For 64-bit systems
  25. }
  26. void AlterPEB() {
  27. PPEB peb = GetPEB();
  28. if (peb) {
  29. // Alter ImagePathName and CommandLine to mimic explorer.exe
  30. // This would involve allocating new buffers and copying 'explorer.exe' path
  31. // For demonstration, we'll just conceptually show the target strings
  32. // peb->ProcessParameters->ImagePathName.Buffer = L"%WINDIR%\\explorer.exe";
  33. // peb->ProcessParameters->CommandLine.Buffer = L"%WINDIR%\\explorer.exe";
  34. // Traverse InLoadOrderModuleList and rewrite BaseDllName and FullDllName
  35. // This is a complex operation involving PEB_LDR_DATA and LDR_DATA_TABLE_ENTRY
  36. // For demonstration, conceptually:
  37. // For each module in InLoadOrderModuleList:
  38. // if (module->BaseDllName matches current process name)
  39. // module->BaseDllName = L"%WINDIR%\\explorer.exe";
  40. // module->FullDllName = L"%WINDIR%\\explorer.exe";
  41. }
  42. }

概念性程式碼: API 解析

  1. // Conceptual code for API resolution using single-byte XOR
  2. // This is a simplified representation
  3. char* decrypt_string(char* encrypted_string, int len, char key) {
  4. char* decrypted_string = (char*)malloc(len + 1);
  5. for (int i = 0; i < len; i++) {
  6. decrypted_string[i] = encrypted_string[i] ^ key;
  7. }
  8. decrypted_string[len] = '\0';
  9. return decrypted_string;
  10. }
  11. void* resolve_api(char* encrypted_api_name, int len, char key, const char* module_name) {
  12. char* api_name = decrypt_string(encrypted_api_name, len, key);
  13. HMODULE hModule = GetModuleHandleA(module_name);
  14. if (hModule) {
  15. void* func_ptr = GetProcAddress(hModule, api_name);
  16. free(api_name);
  17. return func_ptr;
  18. }
  19. free(api_name);
  20. return NULL;
  21. }
  22. // Example usage:
  23. // char encrypted_getprocaddress[] = {0x47 ^ 0x4, 0x65 ^ 0x4, ...};
  24. // FARPROC pGetProcAddress = (FARPROC)resolve_api(encrypted_getprocaddress, sizeof(encrypted_getprocaddress)-1, 0x4, "kernel32.dll");

概念性程式碼: 下一階段檔案解密

  1. // Conceptual code for next-stage file decryption using single-byte XOR
  2. void decrypt_file_content(unsigned char* buffer, size_t size, unsigned char key) {
  3. for (size_t i = 0; i < size; i++) {
  4. buffer[i] = buffer[i] ^ key;
  5. }
  6. }
  7. // Example usage:
  8. // unsigned char encrypted_shellcode[] = { ... };
  9. // decrypt_file_content(encrypted_shellcode, sizeof(encrypted_shellcode), 0x1);

3.2. 第二階段: AV/EDR 繞過與持續運作

在成功執行第一階段後,kkRAT 繼續進入其第二階段,此階段主要致力於繞過防毒軟體 (AV) 和端點偵測與回應 (EDR) 系統,並建立持續運作。惡意軟體首先會驗證其是否擁有管理者權限。如果沒有,它會用中文顯示一則訊息,提示使用者提升存取權限,然後終止其執行,這表明其完全依賴於提升的權限來實現其完整的操作功能 [1]。如果確認為管理者權限,惡意軟體會列舉所有運作中的網路介面卡並暫時停用它們。此舉是切斷 AV/EDR 解決方案與其各自供應商伺服器之間通訊的關鍵步驟,在繞過過程中有效地將安全軟體與更新和遠端管理隔離 [1]。

在網路中斷後,kkRAT 掃描系統中是否存在特定的 AV 和 EDR 程序。文章提及的例子有 360 Total Security、QQ電腦管家、HeroBravo System Diagnostics suite 和 Kingsoft Internet Security [1]。如果偵測到這些目標程序,惡意軟體會利用一個已知的漏洞 driver,特別是 RTCore64.sys,來停用 AV/EDR 功能。這是透過比較註冊每個 callback 的 AV/EDR driver 名稱來實現的。惡意軟體整合了從 RealBlindingEDR project 借用的程式碼,以移除已註冊的系統 callbacks,目標是三種特定類型:ObRegister callbacks (監控 handle 建立/複製)、MiniFilter callbacks (過濾檔案 I/O 操作) 和 CmRegister callbacks (監控 Windows 註冊表操作) [1]。透過移除這些 callbacks,kkRAT 有效地蒙蔽並削弱了旨在偵測與防止其惡意攻擊的安全機制。

在停用 callbacks 後,惡意軟體會終止並刪除與已識別的 AV/EDR 程序相關的用戶層級檔案。為確保持續運作和反覆讓安全軟體失去作用,kkRAT 建立了一個排定的任務,設定為以 SYSTEM 權限運行。此任務在每次使用者登入時執行一個 batch script,確保 AV/EDR 程序被反覆殺死 [1]。此外,惡意軟體修改了與 360 Total Security 相關的註冊表 keys。具體來說,在 HKLM\SOFTWARE\WOW6432Node\360Safe\360Scan 下的 NetCheck 註冊表值被設為 0,據推測是為了停用網路檢查。它還向 HKU\360SPDM\CC2FCASH\speedmem2\x\b5e3891842b605bf7917ba84 下的一個空值名稱添加隨機資料 [1]。一旦這些修改完成,惡意軟體會重新啟用先前停用的網路介面卡,恢復系統的網路連線能力。隨後,第一階段的 shellcode 會執行第三階段的 shellcode,該 shellcode 充當 downloader,用於攻擊的下一階段。

3.3. 第三階段: Payload 傳遞與資料結構

kkRAT 攻擊鏈的第三階段負責取得和執行最終的 payload。此階段始於惡意軟體從一個 hardcoded URL 下載並執行一個名為 2025.bin 的 shellcode 檔案。此下載是透過利用 EnumDateFormatsA API callback 來實現的,這是一種常被用來將網路攻擊偽裝成合法系統功能以規避偵測的技術。下載的 shellcode 被大量混淆了 junk code,這使得安全研究人員更難以分析 [1]。

2025.bin 執行後,惡意軟體會下載一個名為 output.log 的 Base64 編碼檔案。這個檔案儘管名稱無害,但包含用於後續攻擊階段的關鍵結構化資料。解碼後,output.log 揭示了一個由獨特分隔符定義的特定資料結構。十六進制序列 0xA1 0xF9 作為欄位分隔符,用於劃定一個 record 內的個別欄位,而 0xA1 0xF6 則作為 record 終止符,標記每個 record 的結束。被分析的樣本包含 62 個 records,每個都從 0 到 61 編號 [1]。

在每個 record 中,第二個欄位包含兩個 URLs,用於下載兩個不同的壓縮檔:trx38.zip 和一個 wildcard ZIP 壓縮檔 (*.zip)。trx38.zip 檔案解壓縮後,包含一個合法的可執行檔和一個惡意的 DLL。另一方面,wildcard ZIP 壓縮檔則包含一個名為 longlq.cl 的檔案,其中存放著加密的最終 payload [1]。惡意軟體展現了選擇性下載機制:它根據當前 程序 檔名的最後一個字元選擇一個 record。例如,如果檔名是 setup.exe,則會下載 p.zip 檔案。下載後,惡意軟體會為從 trx38.zip 中提取的合法可執行檔建立一個捷徑,並將此捷徑添加到系統的啟動項,以確保這個看起來合法的元件能持續運作,然後該元件很可能會載入惡意 DLL [1]。這種多層次的 payload 傳遞與執行方法突顯了 kkRAT 為了維持立足點並執行其最終惡意目標而進行的複雜設計。

已解碼的資料結構分隔符

- Field separator: 0xA1 0xF9
- Record terminator: 0xA1 0xF6
       

針對 360 Total Security 的註冊表修改

- HKLM\SOFTWARE\WOW6432Node\360Safe\360Scan
    - NetCheck value set to 0
- HKU\360SPDM\CC2FCASH\speedmem2\x\b5e3891842b605bf7917ba84
    - Adds random data to a null value name
        

4. 結論

對 kkRAT 的技術分析揭示了一個複雜且適應性強的 Remote Access Trojan,旨在規避偵測並在被滲透的系統上維持持續運作。其多階段攻擊鏈,加上進階的反分析技術,如 PEB 變更、動態 API 解析和基於 XOR 的解密,凸顯了該惡意軟體保持隱匿的意圖。利用 BYOVD 技術來停用 AV/EDR callbacks,顯示了以關閉安全防禦為目的的高度技術熟練度。此外,其結構化的資料通訊和選擇性的 payload 傳遞機制,突顯了其在部署後續惡意元件方面的效率。了解這些錯綜複雜的技術細節,對於開發強大的網路安全防禦並為威脅情報工作提供資訊至關重要。此類惡意軟體的持續演進,需要不斷的研究與主動措施,以保護數位環境。