SeeSeeYouExec: CcmExec を利用した Windows システムのセッション ハイジャック
Mandiant
※この投稿は米国時間 2024 年 3 月 29 日に、Google Cloud blog に投稿されたものの抄訳です。
この数年間、セキュリティ コミュニティでは System Center Configuration Manager(SCCM)関連の攻撃の増加が確認されてきました。攻撃者は、ネットワーク アクセス アカウント(NAA)の認証情報の不正取得や、ターゲット デバイスへの不正アプリケーションのデプロイなど、SCCM を悪用することで既存の検出機能による検知を回避しながら複雑な目標を達成することに成功しています。Mandiant のレッドチームは、十分なセキュリティ体制を備え既存の手法による攻撃への耐性を持つクライアントを攻撃する際に、SCCM 技術を利用しています。今回のブログ投稿では、そうした SCCM 攻撃の一例をご紹介します。
かつて、レッドチームは Windows システムにおける権限を昇格させることで簡単にシェルコードを無防備なユーザーのプロセスに挿入することができました。レッドチームは、プロセスへの侵入成功後、そのプロセス内でキーロギングや対象ユーザーの LDAP への不正アクセスといった攻撃を行いました。しかしながら、エンドポイント検出対応(EDR)システムの性能向上に伴い、リモートでのプロセス インジェクションはリスクの高い操作となったため、ユーザーのセッションをハイジャックするために別の手法を検討する必要が生じました。
そこで着目されたのが CcmExec です。CcmExec は SCCM Windows クライアントのネイティブ サービスであり、その設計には、レッドチームにとって有用な興味深い特徴が備わっています。このブログ投稿では、CcmExec サービスを利用してセッション ハイジャックを行う方法を解説するほか、この手法による攻撃を促進するために設計された CcmPwn ツールについて紹介します。また、この投稿の最後では、セキュリティ チームがとるべき検出機能戦略を説明します。
AppDomainManager インジェクション
CcmExec の詳細を確認する前に、AppDomainManager インジェクションの複雑な内容を理解することが重要です。AppDomainManager インジェクションは攻撃者が .NET アプリケーション内で任意のコードを実行するのに利用されるローダ ハイジャック手法です。基本的に、.NET フレームワークはアプリケーション ドメインを管理する方法を提供します。アプリケーション ドメインは隔離された環境であり、.NET アプリケーションはこの環境内でコードを実行します。AppDomainManager クラスはこのインフラストラクチャの主要な部分を構成し、アプリケーション ドメインの作成や管理を行います。ただし、攻撃者が AppDomainManager クラスのコンストラクタをオーバーライドする場合、アプリケーション ドメインを作成する際に攻撃者が定義した動作をホスティング アプリケーションに強制的に実行させる可能性があります。
AppDomainManager インジェクションを実行する最も一般的な手段は、.config ファイルを利用するものです。この手段では、アプリケーションの構成ファイルを書き換えて、.NET アプリケーションが実行するカスタムのダイナミック リンク ライブラリ(DLL)ファイルと AppDomainManager を指定します。手順は次のとおりです。
-
カスタム AppDomainManager を作成する: AppDomainManager の派生クラスを作成し、悪意のあるコードを埋め込みます。このクラスを DLL にコンパイルします。
- 構成ファイルを作成する: アプリケーションの
.config
ファイル(たとえば「application.exe.config
」という名前のファイル)を変更または作成し、以下の XML 要素を追加してカスタム DLL と AppDomainManager を指定します。
<configuration>
<runtime>
<appDomainManagerAssembly value="YourDLL, Version=1.0.0.0,
Culture=neutral, PublicKeyToken=null" />
<appDomainManagerType value="YourAppDomainManager" />
</runtime>
</configuration>
- アプリケーションを実行する: .NET アプリケーションが実行されると、.NET ランタイムが同じフォルダ内にある
.config
ファイルを読み取り、指定されたカスタム AppDomainManager を読み込みます。すると、アプリケーションの環境で、AppDomainManager 内のコードが実行されます。
CcmExec のハイジャック
CcmExec サービスのプロセスである CcmExec.exe
を Process Explorer などのプロセス分析ツールを使って分析すると、すぐにいくつかの点が明らかになります。まず目を引くのは、図 1 に示すとおり、Windows システムでインタラクティブ セッションが実行されるたびに、C:\Windows\CCM\SCNotification.exe
プロセスが生成されていることです。SCNotification.exe は SCCM クライアントのコンポーネントであり、ソフトウェアのインストール指示や再起動の通知など、ユーザーへの通知を表示する役割を持ちます。


図 1: CcmExec.exe の子プロセス
さらに詳しく調べると、SCNotification.exe
ファイルは .NET アプリケーションであり、C:\Windows\CCM\SCNotification.exe.config
にこのアプリケーションに付属する構成ファイルがあることがわかります。これが何を意味するかおわかりでしょうか?
Windows システムの管理者権限を SCCM クライアントとして構成させることで、悪意のある DLL を読み込んでログイン ユーザーの代わりにコードを実行する指示を .NET アプリケーションに対して出すよう構成ファイルを書き換えることができます。攻撃の手順は簡単です。
-
ターゲットのシステムに悪意のある DLL をアップロードする: この DLL には、ユーザーのセッションで実行される AppDomainManager コードが含まれています。
-
構成ファイル(SCNotification.exe.config)を書き換える: ファイル内の悪意のある DLL を参照します。
-
CcmExec サービスを再起動する: この操作により、すべてのログイン ユーザーを対象に
CcmExec.exe
プロセスを再起動し、SCNotification.exe
を実行します。
この手法を使うことで、リモートでシェルコードの挿入を行わなくても、ユーザーに気づかれることなく複数のユーザー セッションでコードを実行できるようになります。
CcmPwn によるセッション ハイジャックの武器化
セッション ハイジャックを武器化する仕組みは単純です。Impacket ライブラリを利用して、前述の攻撃やユーザー セッションのハイジャックを実行する CcmPwn を開発しました。CcmPwn にはさまざまなモジュールが実装されています。exec
モジュールはターゲットのシステムにカスタム構成ファイルと DLL ファイルをアップロードし、リモートで CcmExec サービスを再起動したうえで、オリジナルの構成ファイルを再アップロードします。この仕組みを図示したものが、図 2 と図 3 です。CcmPwn を使って Cobalt Strike ビーコンをハイジャックされたセッションに展開する例が示されています。


図 2: CcmPwn の exec モジュール


図 3: 各ログイン ユーザーに対して展開された Cobalt Strike ビーコン
また、CcmPwn にはすべてのログイン ユーザーに対して SMB または HTTP 認証リクエストを強制する coerce
モジュールも含まれています。レッドチームはこの強制認証を利用してパスワードのクラッキングやリレー攻撃を仕掛けます。このモジュールは、悪意のある構成ファイルをターゲットにアップロードするだけなので、DLL は必要としません。このファイルは、攻撃者が管理するファイル共有からファイルを読み込むよう SCNotification.exe
に指示します。このプロセスを示したのが図 4 と図 5 です。


図 4: CcmExec の coerce モジュール


図 5: パスワードのハッシュ値の強制取得
防御における考慮事項
使用するセキュリティ情報およびイベント管理(SIEM)ソリューションや EDR ソリューションに応じて、この攻撃はさまざまな方法で検知することが可能です。推奨される防御手段は以下のとおりです。
- SCNotification.exe で発生する 1026 イベントをモニタリングする: イベント ID 1026 は、.NET ランタイムのエラーに関連するイベントを指します。CcmPwn の
coerce
モジュールの使用時、SCNotification.exe
は攻撃者が管理するファイル共有から存在しない DLL を読み込もうとします。DLL が見つからないため、アプリケーションはSystem.IO.FileLoadException
エラーを発生させます。この挙動の例を示したものが図 6 です。


図 6: SCNotification.exe での .NET ランタイム エラー
-
イベント 7036 とログオンタイプ 3(ネットワーク)をモニタリングする: イベント 7036 はサービスの起動時と停止時に記録されます。セキュリティ チームは、このイベントをモニタリングすることで、ユーザー セッションのハイジャックが試行された可能性を示す、CcmExec サービスの不審な起動を検知できます。CcmPwn を使用すると、サービス停止と同時にログオンタイプ値 3(ネットワーク ログオン)イベントが発生し、その後サービスが再起動するまでに 20 秒の遅延が生じます。このパターンをモニタリングすることで、これらのサービス イベントの優先順位付けを行い、悪意のあるアクティビティの可能性があるアクティビティの詳しい状況を把握することができます。
-
ファイルの変更と構成ファイル内の文字列をモニタリングする: 攻撃を行うには
SCNotification.exe.config
ファイルの書き換えが必要なため、このファイルに対する変更をモニタリングすることで早期に警告を受け取ることができます。また、構成ファイル内の「AppDomainManagerType
」文字列は AppDomainManager インジェクション攻撃に使用されるため、この文字列を注意深く調べる必要があります。セキュリティ チームは、SCNotification.exe.config
内にこの文字列が予期せず生成されていないか調査しなくてはなりません。
組織は、こうした防御手段を実施し、SIEM ソリューションや EDR ソリューションの特定の機能に適応させることで、CcmExec サービスを使ったセッション ハイジャック攻撃を検出し、それに対応する能力を向上させることができます。
ー Mandiant, Andrew Oliveau