Javaの「Click-to-Play」を回避する脆弱性「CVE-2015-4902」、「Pawn Storm 作戦」で利用される

Java の「Click-to-Play」を回避する脆弱性「CVE-2015-4902」、「Pawn Storm作戦」で利用される

トレンドマイクロは、2015年7月、標的型サイバー攻撃キャンペーン「Pawn Storm作戦」において、当時未確認であった Java に存在するゼロデイ脆弱性「CVE-2015-2590」を突く攻撃を確認し、本ブログ上で報告しました。その際、この脆弱性とは別に、Java が使用する「Click-to-Play」を回避する脆弱性「CVE-2015-4902」も確認。Oracle は、10月20日、四半期ごとの定例セキュリティ更新で「CVE-2015-4902」に対応する修正プログラムを公開し、この脆弱性確認についてトレンドマイクロについて明記しています。

問題の脆弱性「CVE-2015-4902」が悪用する「Click-to-Play」とは、Javaアプレットを実行する前に、ユーザに本当に実行したいかどうかをポップアップ画面で警告する機能です。つまり、Java を実行するかどうかユーザに確認させ、クリックしなければ Java のコードは実行されません 。

Click-to-Play が回避されると、この警告画面が表示されずに、不正な Java のコードが実行される恐れがあります。この手法は「Pawn Storm作戦」にとって非常に有効でした。「Pawn Storm作戦」は、同年7月、脆弱性を利用して「北大西洋条約機構(NATO)」の関係者やアメリカ大統領官邸(ホワイトハウス)を攻撃の標的にしました。この攻撃キャンペーンは、ゼロデイ脆弱性を頻繁に利用することで知られています。今回の Java の脆弱性以外にも、Adobe Flash Player に存在する当時ゼロデイ脆弱性「CVE-2015-7645」を突く攻撃が 10月中旬に確認されています。なお、この脆弱性は、Adobeにより修正プログラムが公開されています。

トレンドマイクロは、事前にこの脆弱性について Oracle に通報しました。Click-to-Play を回避するのに利用された方法は非常に巧妙なものでした。この脆弱性の詳細を説明する前に、まずは背景の情報について言及します。

Oracle が提供する「Java Network Launch Protocol(JNLP)」とは、遠隔の Webサーバ上にホストされたファイルを使用してクライアントPC上のアプリケーションを起動させる技術です。JNLP によって、アプレットや Java Web Start を起動させることが可能です。この攻撃のシナリオでは、アプレットを起動させるために JNLP を利用します。

JNLP を実装するために、Java には「Java Naming and Directory Interface(JNDI)」のディレクトリサービスが提供されています。このディレクトリサービスによって、Java のソフトウェアクライアントは、ユーザ名などからオブジェクトを検索することが可能になります。JNDI は、「Remote Method Invocation(RMI)」と呼ばれる Java の「Remote Procedure Call(RPC)」の基盤となるものです。JNDI には、今回の脆弱性に関連する以下の基本概念があります。

  • Context – 名前とオブジェクトを関連させる。つまり、Contextオブジェクトは名前をオブジェクトに解決することができる。このオブジェクトには複数の種類があり、「RegistryContext」はそのうちの 1つである
  • ContextFactory -呼び出し側に Contextオブジェクトを生成する Contextオブジェクトの工場(ファクトリ)。「RegisterContextFactory」は、ContextFactoryオブジェクトを生成するファクトリである

図1 は、この脆弱性を利用した攻撃がどのように実行されるかを示したものです。

図1:「Click-to-Play」を回避する手法
図1:「Click-to-Play」を回避する手法

また、攻撃を実行する前に、攻撃者は以下の 3つを実行する必要があります。

  1. 攻撃者は図2 の HTML のコードを不正な Webサイトに追加する
  2. 攻撃者はパブリックIPアドレスを持つ RMIレジストリサーバを作成する
  3. 攻撃者は不正な Javaのコードを保存するための別の Webサーバを作成する。このサーバもパブリックIPアドレスを持つ

図2:不正な Webサーバに挿入される HTMLのコード
図2:不正な Webサーバに挿入される HTMLのコード

以下は、攻撃の手順です。

  1. 攻撃対象の PC上で、Javaクライアントの一部である “jp2launcher.exe” プロセスが Webブラウザのプロセスによって生成され、不正な Webサーバに “init.jnlp” を要求する。これは図2 の HTML のコードによって実行される。(JNLPファイルは、Java Web Start から Java のコードを起動するために JNLP が 使用するファイル)
  2. 不正な Webサイトから “init.jnlp” が送信される。図3 はこのファイルの内容である。

    図3:
    図3:”init.jnlp” の内容

    赤字で囲んだ文字が通常と異なる。progressクラスのタグの意味は、Java開発者ガイドで確認できる。このクラスは、Java のインターフェイス「DownloadServiceListener」の実装でなければならない。しかし、攻撃者は、「classjavax.naming.InitialContext」を利用する。「Java Runtime Environment(JRE)」がこれを確認しないため、コードが実行される

  3. Javaクラス「javax.naming.InitialContext」のコンストラクタは、アプリケーションの “JNDI.properties”(JNDI環境設定ファイル)を不正な Webサイトに要求する
  4. 不正な Webサイトは、”JNDI.properties” をクライアントに送信する。図4 はこのファイルの内容である

    図4:
    図4:”JNDI.properties” の内容

    「java.naming.factory.initial」は初期コンテキストのファクトリクラスを特定する。「java.naming.provider」は、レジストリサービスの位置を特定する。「javax.naming.InitialContext」のコンストラクタ関数は、com.sun.jndi.rmi.registry.RegistryContextFactoryオブジェクトを生成し、初期コンテキストを生成するために利用する

  5. 初期コンテキストの作成中、コンテキストの情報を取得するために、RMIレジストリサーバと通信する。図4 では、その URL は、java.naming.provider.url=rmi://<不正なサーバ>/Go となっている。また、この URL は、次の形式を利用する:rmi://[host]/[object]. So [object] is Go。これにより、クライアントは RMIサーバ上のオブジェクト情報を検索することが可能となる
  6. RMIサーバは応答を送信し、クライアントは、HTTP経由で不正な Javaクラスサーバに Goクラスを要求することが可能となる
  7. サーバは、Goクラスの内容をクライアントに送信し、これをインスタンスにする。Javaクラスのコードは攻撃対象とされた PC上で実行される

手順3~7 は、javax.naming.InitialContext のコンストラクタ関数内で実行されます。これにより、非常に巧妙な手法で Click-to-Play が回避されます。

Java が現在も幅広く使用されていたら、この「Click-to-Play」を回避する手法による影響は広範囲に及んだことでしょう。今後ゼロデイ脆弱性が新たに確認された時に、この手法を用いて「ドライブバイダウンロード(drive-by download)攻撃」が実行される恐れがあります。

今回の事例は、Java のような複雑なシステムに Click-to-Play といった新しいセキュリティ対策が導入された場合、新機能と既存のコンポーネント間の通信を精査することがいかに重要であるかを浮き彫りにしました。既存の機能とセキュリティが混在した際に不都合が起きないことを確かめることが大切です。

今回の脆弱性は、Java の最新バージョンで修正されています。Java を使用する必要のあるユーザは直ちに最新バージョンに更新して下さい。しかしながら、多くの場合 Java は、今後、徐々に使われなくなる可能性 があります。依然 Java に依存している組織にとっては、現在常用しているアプリケーションソフトウェアが使用するプラットフォームを最新のものへと移行するのも、ひとつの方法です。

参考記事:

 翻訳:品川 暁子・室賀 美和(Core Technology Marketing, TrendLabs)