FortiGuard Labs 脅威リサーチ

ウクライナ企業Energoatomのドキュメントを偽装したマルウェア、Havoc Demonバックドアを配信

投稿者 FortiGuard Labs | 2023年6月30日

影響を受けるプラットフォーム: Microsoft Windows
影響を受けるユーザー:     標的とされたWindowsユーザー
影響:             侵害されたマシンの脅威アクターによる乗っ取り
重大度:            

FortiGuard Labsは、ロシア・ウクライナ戦争で使用されているマルウェアを調査する中で、ウクライナのEnergoatom社を騙った悪意のある偽装ドキュメントを発見しました。同社はウクライナの原子力発電所を運営する国営企業です。

ロシアとの戦争勃発以来、ウクライナのエネルギー部門は絶えずサイバー攻撃を受けています。たとえば、2022年4月の攻撃では、エネルギー企業に対してワイパー型マルウェアのINDUSTROYER2とCADDYWIPERが仕掛けられました。2022年8月16日には、EnergoatomのWebサイトがDDoS攻撃の標的になりました。さらに2022年10月、エネルギー部門に対し、NikoWiperと呼ばれるワイパーを使った別のワイパー攻撃が行われました。

このブログでは、最新の多段階攻撃の技術的な詳細と、そこで用いられる複数の回避手法のほか、開発途中であるかレッドチーム演習の一環ではないかと思われる奇妙な攻撃の痕跡について解説します。

ドキュメント分析

マクロが有効化されたこのドキュメントには「zatverdzhenniy_spisok_osib_na_otrim」という名前が付けられています。これはおおよそのところ、ウクライナ語の「承認受領者リスト」を意味します。このドキュメントは、同じファイル名を持つISOイメージアーカイブに格納して配信されます。今年の3月中旬、初めて同ドキュメントがVirusTotalに提出されました。

ドキュメントを開くと画像が表示され、ユーザーはWordのマクロコード実行を有効にして、M.E.Doc(My Electronic Document)で保護されている情報を表示するよう指示されます。M.E.Docはウクライナの有名なドキュメント管理システムで、関係機関(規制当局を含む)との間で重要文書や機密文書を電子形式でやり取りするために使用されます。

指示の背後に不鮮明なコンテンツとEnergoatomのロゴが表示されており、あたかも重要な情報が保護されているように見えます(図1)。しかし実際には、ドキュメントの一番上に普通の画像が表示されているにすぎません。画像を横に移動させると、下側にある保護されているはずの情報がはっきりと表示されます。

図1:偽装ドキュメント

マクロを有効にするとこの画像が消え、どうにか重要情報を表示できたという印象を与えます。ドキュメントには、防護用品の受け取りを承認された人物の一覧が示されています(図2)。

図2:マクロ実行後の偽装ドキュメント

VBAコード分析

分析を混乱させ検知を回避するために、マクロのVBAコードにはいくつかの興味深い手法が使われています。

ドキュメントのVBAコードを表示またはデバッグしようとすると、Wordアプリケーションがクラッシュします。同様に、oletools(Microsoft OLE2ファイルの解析に使用されるpythonツールのパッケージ)を使用してドキュメントの構造を解析しようとすると、複数のエラーが発生します(定義はされているがアーカイブ内に存在しないストリームファイルなど)。さらに、ファイル内の特定のストリームを解凍しようとすると、不正なシグネチャに関するエラーが通知されます。こうした異常のいずれかが、前述したクラッシュの直接的な原因かどうかは確認できていません。ただし最終的には、ドキュメントでの実行を意図した不正なVBAマクロコードをoletoolsですべて抽出できました。

恐らくはマクロコードの場所をわかりにくくするために、実際のVBAコードが格納されたVBAプロジェクトのバイナリファイルは、デフォルトの「vbaProject.bin」ではなく「EbDYTPZ.vEypm」ファイルにリダイレクトされます。この関連付けは、Office Open XMLアーカイブの「word\_rels\ document.xml.rels」で次のように定義されています。

“<Relationship Id="rId1" 

Type="http://schemas.microsoft.com/office/2006/relationships/vbaProject

Target="EbDYTPZ.vEypm"/>”

通常のVBAコードと同様に、AutoOpenおよびDocument_Openイベントによってドキュメントが開かれると、このVBAコードが実行されるように設定されています。

前述したとおり、マクロはオーバーレイ画像を削除することで起動します。この画像は、内部的にはName属性「happy」を持つShapeオブジェクトです。この画像を検索するために、ドキュメント内のすべてのShapeオブジェクトが反復処理され、同じ名前のオブジェクトが削除されます。

マクロの実行時に使う文字列を隠すために、主として単純なエンコードが使用されています。つまり、元の文字列の各文字から35を減算し、その結果をBase64でエンコードしています。さらに、デコードの前には、文字列の反転や文字の分割といった操作も使用されます。

デバッグ回避の手法としては、1次感染ルーチンの実行にApplication.OnTime関数が使用されています。これは、特定のVBAプロシージャを直接呼び出す代わりに、その実行をスケジュールするために広く利用されている関数です。今回のケースでは、「ostrategicy」関数の即時実行がスケジュールされています。デバッグを実行すると、コードのこの行でエラー「中断モードではコードを実行できません」が発生し、デバッグは中止されます。

図3:デバッグ回避と画像削除が記述されたコード

図3に示すように、VBAコードには無意味で無用に思えるコメントも挿入されています。

この後、マルウェアはハードコードされたパス「C:\Users\user\AppData\Local\Microsoft\Office\OfficeTelemetry.dll」がシステムに存在するかどうか確認します。後述するように、これはペイロードが記述される場所と同じファイルパスです。こうした奇妙な実装コードは、それが未完成であること、あるいは、間もなく開始予定の攻撃用に作成されたテストサンプルであることを疑わせます。

前述のパスにファイルがある場合は、そのファイルが実行されます。ファイルがない場合、コードはペイロードを抽出します。ペイロードは、ドキュメントのカスタムXMLパーツに「TwXfx」というノード名で巧妙に格納されています。

カスタムXMLパーツは、Office Open XML形式と共に導入された機能です。この機能を使用して、ドキュメントがプログラムでアクセスする任意のデータが保存されます。

ペイロードデータを取得するために、マルウェアはドキュメント内のカスタムXMLパーツのオブジェクトをすべて列挙し、「TwXfx」という名前のノードがないか確認します。そのノードには、エンコードされたペイロードが保存されています。

図4は、ドキュメントアーカイブの「customXml\item1.xml」に保存されたエンコード済みペイロードのスクリーンショットです。

図4:エンコードされたバイナリペイロード

このドキュメント内のペイロードは単一のノードに保存されていますが、VBAコードは、複数のノードに分割されたエンコード済みペイロードもサポートしており、その場合は抽出がさらに複雑になります。実際、マルウェアはペイロードデータが単一のノードに保存されていると推定する前に、複数のノードにデータが保存されていないかどうかを確認しています。そのためにはノード名、この場合は「TwXfx」にインデックスを付けた「TwXfx_0」を検索します。このノードが存在していれば、インデックスを増やして(TwXfx_1)次のノードの検索を続けます。ノードが検索できなくなるまで、つまりペイロードの末尾に到達するまでこの処理を繰り返します。

ノードが見つかると、そのコンテンツが読み取られ、XMLタグは削除されます。さらに、データの先頭に文字列「__b_」がある場合は、その文字列も削除されます。文字列のデコードと同様に、Base64を使用してデータをデコードし、35を可算することで、バイナリペイロードが抽出されます。今回に限っては、取得したバイトがxor 82を使ってさらにデコードされています。デコードされたペイロードは64ビットの実行ファイル(.exe)です。

ペイロードのバイナリをドキュメントのカスタムXMLパーツとして保存する手法は、mgeeky.tech Webサイトのブログで紹介されている方法と非常によく似ています。コードレベルで見ても、不正ドキュメントで使用されているコードと、同ブログで紹介されたコードは驚くほど似ています。このWebサイトの作成者は、同様の機能を備えた個人用ツールを提供しています。さらには、不正ドキュメントの作成者が、このブログにリンクされている一般利用可能なPoCから、この手法を容易に複製できた可能性もあります。ドキュメント内のペイロードノードを検索する関数で確認された、コードの類似性の一部を図5に示します。

図5:ドキュメントとブログのコード比較

デコードされたペイロードは、ハードコードされたパス「C:\Users\user\AppData\Local\Microsoft\Office\OfficeTelemetry.dll」に書き込まれ、次のコマンドラインでShellExecuteを使って実行されます。

C:\Windows\System32\conhost.exe --headless 

"C:\Users\user\AppData\Local\Microsoft\Office\OfficeTelemetry.dll" "”

そして、最終的にHavoc Demonエージェントが実行されます。これについては次のセクションで説明します。

ペイロード分析

ステージ1:OfficeTelemetry.dll

ペイロードバイナリのファイル名からもわかるように、マルウェアはMicrosoft Officeの正当なコンポーネントを偽装しようとします。さらには、無効なportal.office.comの証明書に署名まで施しています(図6)。

図6:証明書に署名する偽のportal.office.comコード

このファイルにはDLL拡張子が付けられ、複数のエクスポート関数(図7)が含まれていますが、これは独立したEXEファイルです。

図7:OfficeTelemetry.dllによってエクスポートされた関数

このファイルが実行されると、現在のプロセスに割り当てられたメモリの.vdataセクション(図8)にある、パッケージ化され圧縮されたペイロードが検索されます。

図8:暗号化され圧縮された.vdataセクションのペイロード

ペイロードストレージの構造は次のとおりです。

1.     Offset 0x0:マジック(8バイト)

2.     Offset 0x8:暗号化されたフラグ(0 = 暗号化なし、3 = RC4暗号化)

3.     Offset 0x9:圧縮フラグ(0 = 圧縮なし、3 = LZNT1圧縮)

4.     Offset 0xa:RC4キー(64バイト)

5.     0ffset 0x4a:圧縮サイズ(4バイト)

6.     Offset 0x4e:解凍サイズ(4バイト)

7.     Offset 0x52:ローダー構成の文字列長(2バイト)

8.     Offset 0x154:暗号化 / 圧縮されたローダー構成とペイロードの先頭

ペイロードを復号して解凍すると、パイプ区切りの構成を確認できます。構成の後には、実行される実際のシェルコードが続いています(図9)。

図9:復号 / 解凍されたペイロード

ローダー構成の形式は次のとおりです。

  • フィールド1:インジェクションタイプ:現在のプロセス(1)または新規プロセス(2)
  • フィールド2:ローダーの終了前にインジェクションスレッドの終了を待機するフラグ(インジェクションタイプ1のみ)
  • フィールド3:インジェクションの対象となるプロセス(インジェクションタイプ2のみ)
  • フィールド4:インジェクションの対象となるプロセス(インジェクションタイプ2のみ)
  • フィールド5:インジェクション完了時に空のファイルを%TEMP%に書き込むフラグ
  • フィールド6:コード内のWindowsイベントに使用する待機のタイムアウト
  • フィールド7:使用する未知のフラグ(インジェクションタイプ1のみ)
  • フィールド8:挿入するスレッドの作成後にスリープの難読化を有効にするフラグ(インジェクションタイプ1のみ)
  • フィールド9:別のスレッドを介してスリープの難読化を有効にするフラグ
  • フィールド10:スリープの難読化を有効にするフラグ
  • フィールド11:APIにパッチを適用するフラグ

構成の解析後、ローダーは実際のペイロード(シェルコード)の前に、79バイトのジャンク(意味のない)命令が格納されたスタブを挿入します。シェルコードの検知を回避するために、このスタブ内のハードコードされたオフセット25にあるバイトが、ランダムなバイトに置換されます。

マルウェアはペイロードを起動する前に、%TEMP%にファイルがないことを確認します。このファイルの名前は、現在時刻の時間/3 + 年 + 月 + 日から算出された値で構成されます。したがって、ペイロードは1日に8回までしか実行されません。

シェルコードを起動するために、ローダーはZwCreateThreadExを呼び出し、スレッド作成フラグのTHREAD_CREATE_FLAGS_CREATE_SUSPENDED(0x01)を使用して新しい一時停止インジェクションスレッドを作成し、THREAD_CREATE_FLAGS_HIDE_FROM_DEBUGGER(0x4)を使用してデバッガーに対してこのスレッドを非表示にします。ZwCreateThreadEx呼び出しの前にTHREAD_CREATE_FLAGS_HIDE_FROM_DEBUGGERフラグを削除し、メモリのブレークポイントを使用すると、スレッドが実行を再開したときに、通常の方法でシェルコードをデバッグできます。

このサンプルでは有効化されていませんが、ローダーはメモリスキャナによる検知を回避するためにスリープの難読化もサポートしています。そのためには、Windows Sleep APIへの呼び出しを独自の関数にリダイレクトし、以下の処理を実行します。

1.     現在のプロセスのスレッドをすべて一時停止する。

2.     パッチが適用されたSleep APIのコードバイトを元の状態に戻す。

3.     セキュリティAPIのパッチを元の状態に戻す(パッチが構成されている場合のみ)。

4.     ランダム化されたXORキーを使用して、現在のプロセスに含まれる機密性の高いメモリ領域をエンコードする。

5.     所定のタイムアウトを使用してSleepを呼び出す。

6.     同じXORキーを使用して、現在のプロセスに含まれる機密性の高いメモリ領域をデコードする。

7.     セキュリティ関連のAPIにパッチを適用し、APIを無効化する。

8.     Sleepにパッチを適用し、もう一度この関数にSleepをリダイレクトする。

9.     現在のプロセスのスレッドをすべて再開する。

パッチが適用されたAPIは次のとおりです。

  • wldp.dllのWldpQueryDynamicCodeTrust
  • amsi.dllのAmsiScanBuffer
  • ntdll.dllのEtwEventWrite

興味深いことに、このサンプルには有名なCobalt Strikeの構成フィールド名(図10)も平文で含まれています。これは恐らく、静的分析ツールを混乱させるためでしょう。

図10:サンプルに含まれているCobalt Strikeの構成フィールド

ステージ2:KaynLdr

ステージ2は、Havoc C2エージェントDLLが追加されたシェルコードで構成されます。Havoc C2フレームワークは、C5piderが開発したオープンソースのポストエクスプロイトツールであり、以下のコンポーネントが含まれます。

  • Demonエージェント:感染したマシン上で展開され、構成済みのTeamserverと通信します。
  • Teamserver:エージェントとの通信を管理するコマンド&コントロール(C2)サーバー。
  • クライアント:接続先エージェントの管理およびコマンド発行を目的に、脅威アクターがTeamserverとの通信で使用します。クライアントは展開されるマルウェアに含まれていないため、以降の説明は省略します。

シェルコードはメモリ内のペイロードの場所を特定するために、0x4d 0x5aバイトと0x50 0x45バイトを探索します。これらはそれぞれ、Windows PE実行ファイルの「MZ」ヘッダーと「PE」ヘッダーを意味します。その後、ローダー(ソースコード内ではKaynLdrとして参照されます)を呼び出します。

KaynLdrは、APIのハッシュ化を通じてネイティブAPIのLdrLoadDllZwAllocateVirtualMemoryNtProtectVirtualMemoryを解決した後、それらを使用してメモリを割り当て、Demonエージェントのペイロードを読み込み、メモリから直接ペイロードを実行します。

関連するAPIハッシュは次のとおりです。

  • LdrLoadDll: 0x9e456a43
  • NtAllocateVirtualMemory: 0xf783b8ec
  • NtProtectVirtualMemory: 0x50e92888

ステージ3:Havoc Demonエージェント                                                   

KaynLdrによって読み込まれたDLLはHavoc Demonエージェントであり、有名なCobalt StrikeフレームワークのBeaconに似ています。構成はDemonサンプルに埋め込まれています。

Demonは、HTTPまたはHTTPS POSTリクエストを介して、構成で指定されたC2サーバーと通信します。初回のチェックインリクエスト(図11)では、ランダム化された256ビットキーと128ビットIVが生成され、C2サーバーと共有されます。これは、エージェントとC2サーバー間でやり取りする後続のデータをAES-256-CTRで暗号化するためです。

図11:チェックインリクエストのデータ構造

チェックインリクエストの関連フィールドは次のとおりです。

1.     データパッケージのサイズ

2.     マジック値:0xDE 0xAD 0xBE 0xEF(Havocにハードコードされています)

3.     エージェントID

4.     コマンドID:0x63(DEMON_INITIALIZE)

5.     32バイトのAESキー

6.     16バイトのAES IV

7.     AESで暗号化されたデータ

Demonは複数のC2ドメイン間を巡回するように設定できますが、このサンプルに指定されているC2ドメインは「ukrtatnafta[.]org」だけです。このドメインは、ウクライナの石油精製会社、Ukrtatnaftaが所有しているukrtatnafta[.]comと非常によく似ています。

正当なHTTP/HTTPSトラフィックを偽装するために、Demonは構成で指定された複数のURIからいずれか1つを無作為に選択し、C2へのリクエストに所定のHTTPヘッダーリストを追加します。このサンプルから抽出したTeamserver C2の構成を以下に示します。

  • ホスト:ukrtatnafta[.]org:443
  • HTTPS:True
  • 有効なプロキシ:なし
  • メソッド:POST
  • ヘッダー:
    • Content-Type: application/javascript
    • Pragma: public
    • ETag: W/736fh0-3e
    • Last-Modified: Mon, 05 Dec 2016 14:54:50 GMT
    • Server: nginx/1.14.2
    • Connection: keep-alive
    • Expires: Mon, 06 Mar 2023 13:23:47 GMT
    • User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36
  • URI:
    • /wp-content/themes/pressa/js/avias.js
    • /wp-content/themes/pressa/js/mobile_menu.js
    • /wp-content/plugins/contact-form-7/includes/js/scripts.js
    • /wp-content/themes/pressa/js/bootstrap.js
    • /wp-content/themes/pressa/js/hovermenu.js
    • /wp-content/themes/pressa/js/retina-1.1.0.js
    • /wp-content/plugins/js_composer/assets/lib/bower/isotope/dist/isotope.pkgd.min.js
    • /wp-content/themes/pressa/js/custom-script.js
    • /wp-includes/js/wp-emoji-release.min.js
    • /maps-api-v3/api/js/52/1/intl/uk_ALL/util.js
    • /wp-includes/js/wp-embed.min.js

Demonの主な機能は次のとおりです。

  • ホストおよびネットワーク情報(ユーザー、グループ、ドメイン、共有など)の列挙
  • コマンドプロンプトからのコマンド実行
  • PowerShellコマンドの実行
  • DLL、シェルコード、.NETアセンブリ、Cobalt Strike BOFファイルのインジェクションと実行
  • プロセスの操作(一覧、作成、検索、強制終了など)
  • ファイルとディレクトリの操作(一覧、ダウンロード、アップロード、表示、削除など)
  • アクセストークンの操作(窃取、偽装など)
  • スクリーンショットの作成

このDemonサンプルは、Githubで公開されたバージョンから変更されていないため、ここでは分析しません。ご興味のある方は、GitHubのドキュメントソースコードを参照してください。

結論

このマルウェア攻撃には、攻撃者が検知や分析の回避に使用する興味深い手法がいくつか見られます。それらの手法を組み合わせて使用することで、感染に成功した攻撃者は、攻撃が検知されるまでに、時間的余裕をもってポストエクスプロイトコマンドを実行することができます。

ディスクにペイロードを保存しておくためのハードコードされたパスや、比較的新しいペイロード暗号化手法など、ドキュメントにはレッドチーム演習の可能性を示すものがいくつか含まれていますが、最近は多数のレッドチーム用ツールが不正な目的で武器化されていることから、これが開発途中の攻撃である可能性も十分にあります。目的不明のリモートオペレーターは、このドキュメントが仕掛けたバックドアから、感染したユーザーのシステムをひそかに制御できます。したがって、安全性を高めるには、細心の注意を払い保護対策を徹底することをお勧めします。

オープンソースの攻撃型セキュリティフレームワークの普及は、両刃の剣です。ソースコードを入手できるということは、レッドチームとブルーチームの双方にとって、攻撃手法の解明、検知ギャップの解消、組織のサイバーレジリエンス強化などのメリットがあります。一方、脅威アクターも、これらのフレームワークを悪用して攻撃を仕掛けることができ、カスタムマルウェアの開発や購入は不要です。

フォーティネットのソリューション

FortiGuardアンチウイルスは、このレポートで特定した悪意のあるファイルを、以下の不正プログラムとして検知します。

  • VBA/Havoc.FGLT!tr
  • W64/Havoc.FGLTA!tr.bdr
  • W64/Havoc.FGLTB!tr.bdr

FortiGuardアンチウイルスサービスは、FortiGate、FortiMail、FortiClient、FortiEDRによってサポートされます。これらの各ソリューションには、Fortinetアンチウイルスエンジンが含まれています。したがって、最新の保護機能を備えたこれらの製品をお使いのお客様は、脅威から保護されています。

このブログで取り上げた脅威は、通常はEメールの添付ファイルとして配信されます。FortiMailは、そうした攻撃に利用される不正な添付ファイルを検知し、隔離することができます。

フォーティネットのCDR(コンテンツ無害化)サービスは、Wordドキュメントに埋め込まれたマクロを無力化できます。

FortiGuard Webフィルタリングサービスは、このレポートで解説したC2 URLを、不正なURLとして報告しブロックします。

FortiGuard Labsは、Havoc C2ネットワーク通信をブロックするためのBackdoor.Havoc.Agent IPSシグネチャを公開しています。

頻繁なシステム停止、日常業務への損害、組織の評判への影響、個人情報の破損や望ましくない公表などを考えると、すべてのアンチウイルスおよびIPSシグネチャを最新の状態で維持することが重要です。

組織においては、フォーティネットが無償で提供しているNSEトレーニング:NSE 1 – 情報セキュリティ意識向上の受講をエンドユーザーに奨励することもお勧めします。このトレーニングには、インターネットの脅威に関するモジュールが含まれ、エンドユーザーはさまざまな種類のフィッシング攻撃を識別して自らを保護する方法を学習できます。

組織がHavoc Demonやその他のサイバーセキュリティ攻撃を受けていると思われる場合は、フォーティネットのグローバルFortiGuardインシデントレスポンスチームまでご連絡ください。

IOC(Indicators of Compromise:侵害指標)

ファイルハッシュ

b773fa65bb375e6fe6d387f301f6bf33219189ea1d4a06762e965a9eba7de4e8

17637fac7f989549acd248ca9e5293d2b9a1a2e4bb0f7e4edf5571df35129f0c

9f797d705facebd1687b7765cbf65231e71821eb3c38dcc171a3fc88b9f52328

b6cb8a7cdce0bfd3a7402d22fb0014dedb259d6c91c1538ac74097b8ca22ca5c

 

C2 URL

hxxps://ukrtatnafta[.]org

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/avias.js

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/mobile_menu.js

hxxps://ukrtatnafta[.]org/wp-content/plugins/contact-form-7/includes/js/scripts.js

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/bootstrap.js

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/hovermenu.js

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/retina-1.1.0.js

hxxps://ukrtatnafta[.]org/wp-content/plugins/js_composer/assets/lib/bower/isotope/dist/isotope.pkgd.min.js

hxxps://ukrtatnafta[.]org/wp-content/themes/pressa/js/custom-script.js

hxxps://ukrtatnafta[.]org/wp-includes/js/wp-emoji-release.min.js

hxxps://ukrtatnafta[.]org/maps-api-v3/api/js/52/1/intl/uk_ALL/util.js

hxxps://ukrtatnafta[.]org/wp-includes/js/wp-embed.min.js