Ivanti Connect Secure VPN のゼロデイエクスプロイトを Splunk で検知する

2024.03.07

2024年1月10日に、Ivanti Connect Secure(旧: Pulse Connect Secure)およびIvanti Policy Secureゲートウェイにおける脆弱性(CVE-2023-46805CVE-2024-21887)が公表されました。さらに1月31日(CVE-2024-21888CVE-2024-21893)、2月8日(CVE-2024-22024)にも相次いで脆弱性が公表されています。

公開日 CVE CVSS 内容
2024/1/10 CVE-2023-46805 8.2 Webコンポーネントの認証バイパス
2024/1/10 CVE-2024-21887 9.1 Webコンポーネントのコマンドインジェクション
2024/1/31 CVE-2024-21888 8.8 Webコンポーネントの権限昇格
2024/1/31 CVE-2024-21893 8.2 SAMLコンポーネントのSSRF
2024/2/8 CVE-2024-22024 8.3 SAMLコンポーネントのXXE

こちらについてはJPCERTでも脆弱性のサマリが記載されています。

対応策としてはIvantiからも公開されていますが、パッチが公開されているので最優先はパッチの適用になるかと思います。

また、Invatiによると、CVE-2024-21888、CVE-2024-22024においては現時点では顧客への攻撃が確認されていないものの、CVE-2023-46805、CVE-2024-21887、CVE-2024-21893においては実際の顧客への攻撃が確認されているとあります。

Mandiantの調査レポートでは、これらの攻撃は UNC5221 と呼ばれる脅威アクターによるものと見ているとされているようです。

このようなクリティカルな脆弱性が公表された時に、まずパッチの適用を検討されると思いますが、既に攻撃を受けて侵入を許してしまっている可能性があるかを確認する必要もあります。
また、何らかの事情により今すぐにパッチを当てれない状況である可能性もあります。

過去にもLog4j2の脆弱性の時のように、パッチ自体の提供に時間がかかってしまう場合は、一つのクリティカルな脆弱性を派生にして次々と脆弱性が発見される場合も少なくありません。
こういった時に、SIEM製品を導入しているとログから攻撃の痕跡を監視したり、調査することができるようになります。

Splunkでは、セキュリティ攻撃をログで検出するルールを Splunk Security Content で公開しています。
Ivanti Connect Secure VPN のゼロデイエクスプロイトについても Splunk のブログで説明および検知するためのクエリについて紹介しているのでこちらを参考に詳しく見ていきます。

ゼロデイエクスプロイトの検知

攻撃者はこの(CVE-2023-46805)(CVE-2024-21887)(CVE-2024-21893)の脆弱性に該当するシステムかどうかを確認するため、下記のいくつかの特定のURLへWebリクエストを発行します。

URL method statud code
/api/v1/totp/user-backup-code/../../system/system-information POST 200
/api/v1/totp/user-backup-code/../../system/maintenance/archiving/cloud-server-test-connection POST 200
/api/v1/configuration/users/user-roles/user-role/rest-userrole1/web/web-bookmarks/bookmark GET 403
/api/v1/license/keys-status/ GET 200

Bookmark Endpoint に関する脆弱性をついた攻撃

Ivanti Connect Secure の Bookmark EndpointへのWebリクエストとそのレスポンスを確認することで認証をバイパスをする脆弱性が存在しているかを確認することができます。
そのため攻撃者はターゲットになるシステムを探索するために、エンドポイントに特定のリクエストを発行します。

Splunk では下記の検知ルールを公開しています。

Splunkでクエリする検知ルールをまず確認しておきます。

| tstats count min(_time) as firstTime max(_time) as lastTime from datamodel=Web where Web.url="*/api/v1/configuration/users/user-roles/user-role/rest-userrole1/web/web-bookmarks/bookmark*" Web.http_method=GET Web.status=403 by Web.src, Web.dest, Web.http_user_agent, Web.status, Web.url source 
| `drop_dm_object_name("Web")` 
| `security_content_ctime(firstTime)` 
| `security_content_ctime(lastTime)` 
| `access_to_vulnerable_ivanti_connect_secure_bookmark_endpoint_filter`

このクエリ文は、Webシステムから出力されるログを対象としています。

サンプルデータを使って、検知できるかやってみます。

Splunk では Attack Data という、検知ルールを確認することができるデータセットが用意されているので、それをSplunk Cloudにアップします。

データセットはローカル端末(Mac)に落として、Splunk Cloudにファイルアップロードするようにします。

git-lfsをインストールして、試してみるデータセットを落としてきます。(もし、gitもインストールしていない場合はgitもインストールしてください)
対象のデータはa href="https://github.com/splunk/attack_data/tree/master/datasets/attack_techniques/T1190/ivanti" target="_blank" rel="noopener noreferrer">「T1190」の「ivanti」になりますので、ディレクトリごと落とします。
アップロードの時にZipファイルだと、一括でアップロードできるので、Zipで固めてアップロードするといいかと思います。

brew install git-lfs
git lfs install --skip-smudge
git clone https://github.com/splunk/attack_data
git lfs pull --include=datasets/attack_techniques/T1190/ivanti/
zip -r ivanti.zip datasets/attack_techniques/T1190/ivanti

落としてきたログの中身を確認してみるとこのサンプルデータは、suricataで出力されるログファイルとなっていることが分かります。

データをSplunk Cloudにアップする前に、データを取り込む際のデータソースを確認しておきます。
suricata用のデータソースはSplunkにデフォルトでは用意されていないので、Splunk Databaseから利用できるAdd-onをインストールしておきます。
また、Splunk Security Content の先程の検知ルールは、CIMを利用しているので、CIMのAppも同じくインストールします。
(SplunkにおいてCIMは非常に強力かつ、有用な機能なので後日、別途ブログでご紹介します。。)

では、これらのAdd-onとAppをインストールしていきます。

Appのインストール画面で、suricataと検索します。
今回は、「Artica TA Add-on」をインストールしました。

さらに、CIMと検索して、Utilityにチェックをし検索します。
「Splunk Common Information Model」をインストールします。

次にSplunk Cloudの「設定 > データの追加」でデータをアップロードします。

Zipにしたファイルを選択して、ソースタイプの指定に「artica:suricata:http」を入力/選択します。

後は、デフォルトの設定でも問題ありませんので、アップデートを実行します。

これで取り込んだログは、Webのデータモデルとして解釈されるので、検知ルールを使って検索をしてみます。(※検索は全期間を指定して検索してください)
検索クエリのバックスラッシュで囲まれた、4行程度はマクロ関数で、事前に登録がいるので、今回は省きました。(マクロ関数は、Flase Positiveなどがあった場合のチューニング用として利用できます。)
利用したい場合は、こちらのテンプレートを登録していくことができます。

出力されているので、検知することができそうです。

コマンドインジェクションの脆弱性をついた攻撃

Ivanti Connect Secure の特定のURIエンドポイントにリクエストを発行し、200レスポンスが返ってくるかどうかを調べることでコマンドインジェクションが成立する脆弱性を持っているか確認するための攻撃を仕掛けてきます。

Splunk の検知ルールは下記になります。

Splunkでクエリする検知ルールを確認しておきます。

| tstats count min(_time) as firstTime max(_time) as lastTime from datamodel=Web where Web.url IN("*/api/v1/totp/user-backup-code/../../system/maintenance/archiving/cloud-server-test-connection*","*/api/v1/totp/user-backup-code/../../license/keys-status/*") Web.http_method IN ("POST", "GET") Web.status=200 by Web.src, Web.dest, Web.http_user_agent, Web.url, Web.http_method, Web.status 
| `drop_dm_object_name("Web")` 
| `security_content_ctime(firstTime)` 
| `security_content_ctime(lastTime)` 
| `ivanti_connect_secure_command_injection_attempts_filter`

既にサンプルデータは入っているので、早速クエリをかけてみます。(先ほどと同様にマクロ関数を含む下の4行はクエリから省いています)

検知することができました。

認証バイパスの脆弱性をついた攻撃

この脆弱性をつくことで、認証バイパスを行いながら Ivanti Connect Secure のシステムインフォメーションを取得することができるようになります。
攻撃者は、この脆弱性が利用できるかを確認するため、特定のURLへのリクエストとレスポンスコードを確認するための攻撃を仕掛けてきます。

Splunk の検知ルールは下記になります。

Splunkでクエリする検知ルールを確認しておきます。

| tstats count min(_time) as firstTime max(_time) as lastTime from datamodel=Web where Web.url="*/api/v1/totp/user-backup-code/../../system/system-information*" Web.http_method=GET Web.status=200 by Web.src, Web.dest, Web.http_user_agent, Web.url 
| `drop_dm_object_name("Web")` 
| `security_content_ctime(firstTime)` 
| `security_content_ctime(lastTime)` 
| `ivanti_connect_secure_system_information_access_via_auth_bypass_filter`

既にサンプルデータは入っているので、これらもクエリをかけてみます。(先ほどと同様にマクロ関数を含む下の4行はクエリから省いています)

検知することができました。

aa

SAMLコンポーネントの脆弱性をついたSSRF

Ivanti Connect Secure のSAMLコンポーネントの脆弱性をつくことで、SSRFを成立させることができます。
特定のURLへのリクエストとレスポンスコードを確認することで、SSRFが実行可能なことが分かります。

Splunk の検知ルールは下記になります。

Splunkでクエリする検知ルールを確認しておきます。

| tstats count min(_time) as firstTime max(_time) as lastTime from datamodel=Web where Web.url IN ("*/dana-ws/saml20.ws*","*/dana-ws/saml.ws*","*/dana-ws/samlecp.ws*","*/dana-na/auth/saml-logout.cgi/*") Web.http_method=POST Web.status=200 by Web.src, Web.dest, Web.http_user_agent, Web.url, Web.status, Web.http_method 
| `drop_dm_object_name("Web")` 
| `security_content_ctime(firstTime)` 
| `security_content_ctime(lastTime)` 
| `ivanti_connect_secure_ssrf_in_saml_component_filter`

既にサンプルデータは入っているので、これらもクエリをかけてみます。(先ほどと同様にマクロ関数を含む下の4行はクエリから省いています)

検知することができました。

まとめ

仮に攻撃を受けていた場合、これらのクエリで検知することで確認することができそうです。
実際の被害報告も出ている脆弱性なので、いち早く対策を行っていきたいものですね。

参考情報

https://forums.ivanti.com/s/article/KB-CVE-2023-46805-Authentication-Bypass-CVE-2024-21887-Command-Injection-for-Ivanti-Connect-Secure-and-Ivanti-Policy-Secure-Gateways?language=en_US
https://forums.ivanti.com/s/article/Recovery-Steps-Related-to-CVE-2023-46805-and-CVE-2024-21887?language=en_US
https://forums.ivanti.com/s/article/CVE-2024-21888-Privilege-Escalation-for-Ivanti-Connect-Secure-and-Ivanti-Policy-Secure?language=en_US
https://www.mandiant.jp/resources/blog/suspected-apt-targets-ivanti-zero-day
https://www.mandiant.jp/resources/blog/investigating-ivanti-zero-day-exploitation
https://www.mandiant.com/resources/blog/investigating-ivanti-exploitation-persistence
https://services.google.com/fh/files/misc/ivanti-connect-secure-remediation-hardening.pdf