This post is also available in: English (英語)
概要
パロアルトネットワークス脅威インテリジェンス調査チームUnit 42の調査によると、この数カ月間、Patchworkサイバー脅威グループ(別名「Dropping Elephant」、「Monsoon」)がインド亜大陸を標的にしたキャンペーンを行っています。Patchworkグループは、更新されたBADNEWSペイロードを拡散するために、正規文書にEPSエクスプロイトをひと組埋め込んだ悪意のある文書を利用していました。正規文書を兵器化する手法は、このサイバー脅威グループが以前からよく使用している方法です。
最近の活動で用いられている悪意のある文書としては、パキスタン軍の最近の軍事活動、パキスタン原子力委員会やパキスタン内務省に関する話題のものが多く確認されています。
このような文書により最終的に配信されるBADNEWSマルウェアペイロードは、2017年12月に発表された前回の公開レポート以降、進化し続けています。BADNEWSは、攻撃者にとっての侵入経路となり、この裏口から標的マシンの完全制御を可能にします。サードパーティの正規Webサイトを利用して、マルウェアのコマンド&コントロール(C2)情報をホストし、「デッドドロップ」を行うという手法は、以前から長い間使われています。C2情報を収集した後、BADNEWSはHTTPを使ってリモートサーバーと通信します。
私たちの調査結果によると、マルウェアがC2サーバー情報を取得する方法、およびC2との通信方法に変化が見られます。このようなBADNEWSの変化、およびEPSベースのエクスプロイト利用という最近の流れは、このサイバー脅威グループがセキュリティコミュニティの裏をかこうとして、利用しているツールセットを積極的に更新し続けていることの表れと考えられます。
このブログでは、私たちが新しく発見したこと、および上記のような変化について詳しく解説したいと思います。
配信
Unit 42が確認した悪意ある文書には、正規と見せかけたルアー(わな)や、CVE-2015-2545およびCVE-2017-0261の脆弱性を利用した悪意ある埋め込みEPSファイルが仕掛けられていました。これらの脆弱性については以前の公開レポートでも解説されており、PWCやFireEyeからご覧いただけます。Patchworkは以前、CVE-2017-0261の脆弱性を標的にした文書を利用していましたが、2018年1月後半に発見された新しい文書では、ターゲットをこの脆弱性から、より古いCVE-2015-2545の脆弱性へと切り替えていました。
そして主に、使用されていたルアー(わな)は、以下のようなパキスタンの原子力組織や軍事関連の文書でした。
図 1 a67220bcf289af6a99a9760c05d197d09502c2119f62762f78523aa7cbc96ef1から抽出したルアー
図 2 07d5509988b1aa6f8d5203bc4b75e6d7be6acf5055831cc961a51d3e921f96bdから抽出したルアー
図 3 b8abf94017b159f8c1f0746dca24b4eeaf7e27d2ffa83ca053a87deb7560a571から抽出したルアー
図 4 d486ed118a425d902044fb7a84267e92b49169c24051ee9de41327ee5e6ac7c2およびfd8394b2ff9cd00380dc2b5a870e15183f1dc3bd82ca6ee58f055b44074c7fd4から抽出したルアー
これら悪意ある各文書に埋め込まれているペイロードは、BADNEWSマルウェアファミリの更新バージョンです。悪意あるEPS内に埋め込まれているシェルコードが実行されると、以下の3つのファイルがドロップされます。
- %PROGRAMDATA%\Microsoft\DeviceSync\VMwareCplLauncher.exe
- %PROGRAMDATA%\Microsoft\DeviceSync\vmtools.dll
- %PROGRAMDATA%\Microsoft\DeviceSync\MSBuild.exe
ドロップされるファイルの1つであるVMwareCplLauncher.exeは、正規の署名済みVMware実行ファイルで、BADNEWSペイロードを最終的に配信するのに利用されます。vmtools.dllファイルは改変されたDLLファイルで、永続性を確保するとともに、改名により正規のMicrosoft Visual Studioツールに偽装したBADNEWSマルウェア、MSBuild.exeをロードします。
これらのファイルはドロップされた後、VMwareCplLauncher.exe実行ファイルが起動して、これがvmtools.dll DLLファイルをロードします。このDLLファイルは、BaiduUpdateTask1という名前のスケジュールタスクを生成し、このタスクはその後1分ごとに悪意ある偽装MSBuild.exeの実行を試みます。
署名済みの正規の実行ファイルに悪意あるライブラリをロードさせるテクニックは、一般的にサイドローディングと呼ばれ、過去、多くのキャンペーンやマルウェアファミリで確認されています。
感染ホストが、悪意あるMicrosoft Word文書を開くと、BADNEWSが次の流れで実行されます。
図 5 BADNEWSを配信するためのサイドローディングテクニック
以下の図は、BADNEWSが感染ホスト上で実行し続けるように、変更されたvmtools.dllが生成してスケジュールされたタスクを示しています。
図 6 BADNEWSをロードするために生成され、スケジュールされたタスク
BADNEWS
BADNEWSには、2016年8月にForcepointが最初の説明を行ったときから、大きな変化はありません。Trend Microの最近の分析によると、2017年にはいくつかの小さな変更点が確認されました。簡単におさらいすると、BADNEWSマルウェアファミリは、HTTP経由で通信を伴うバックドアとして機能します。攻撃用のコマンドが多数用意されており、追加情報をダウンロードして実行したり、興味の対象となった文書をアップロードしたり、デスクトップのスクリーンショットを撮影したりできます。
このマルウェアは、まず「デッドドロップ リゾルバー」から実行されて、C2情報を収集します。デッドドロップ リゾルバーは、さまざまなマルウェアファミリを利用する複数のサイバー脅威グループにより使用されているもので、Patchworkグループもこの戦術には精通しています。この戦術では、マルウェアによりデコードされるエンコード化コマンドを含むコンテンツを、一般に公開されているWebサービスを利用してホストします。
この調査ブログの後半では、次のファイルについて解説します。
SHA256 | 290ac98de80154705794e96d0c6d657c948b7dff7abf25ea817585e4c923adb2 |
MD5 | 79ad2084b057847ce2ec2e48fda64073 |
コンパイル日 | 2017-12-22 11:54:03 UTC |
この新しいBADNEWS亜種で最初に確認された変更点の1つは、単一のBADNEWSインスタンスを指定時間に実行させるための新しいミューテックスの生成です。このマルウェアファミリは、新しいミューテックス「com_mycompany_apps_appname_new」を使用していました。
このBADNEWS亜種では、以前のバージョンとは異なるファイル名が使用されています。BADNEWSの実行中は、次のファイル名が使用されます。これらのファイルはすべて、感染ホストの%TEMP%ディレクトリに格納されます。
ファイル名 | 説明 |
9PT568.dat | 感染ホストを特定する一意のIDを含む |
TPX498.dat | キーストロークのログ |
edg499.dat | 興味の対象ファイルのリスト |
TPX499.dat | C2によるコマンド実行時におけるスクリーンショットの一時保管 |
up | C2によるコマンド実行時に実行されるダウンロードファイルの一時保管 |
この亜種において私たちが気付いた他の変更点には、デッドドロップ リゾルバー経由で格納されるC2情報の難読化方法も含まれます。以前のBADNEWS亜種は、「{{」と「}}」の間のデータを探して、簡単な暗号を使ってこのデータをデコードしていました。しかしこの新しい亜種では、多くのハードコードされたURLから「[[」と「]]」の間のデータを探します。このデータは、hxxp:// feeds.rapidfeeds[.]com/88604/から取得した次のイメージ内で確認できます。これは、このサンプルで私たちが見つけたデッドドロップ リゾルバーの1つです。
図 7 BADNEWSが使用するデッドドロップ リゾルバー
このデータを復号するために、このマルウェアの作成者は、以前のバージョンにはない追加のステップを含めています。この情報をデコードするために、BADNEWSは以下のことを行います。
- 文字列をBase64でデコードします。
- 以前のバージョンで使用されていたデコーディングを実行します。
- 結果をBase64でデコードします。
- Blowfishアルゴリズムと静的キーを使って結果を復号します。
付録に含まれているスクリプトが、これらのデッドドロップ リゾルバーのデータを復号します。上記の例では、この4つの手順を踏むと、結果は185.203.118[.]115になります。
BADNEWSは、キーロギングや興味の対象となるファイルの識別など、以前のバージョンからあった多くの機能を実行します。ただ、この新しいバージョンでは、以前報告された亜種とは異なり、USBドライバに対するファイルの検索を行いません。検索先は固定ドライブのみです。検索対象ファイルは依然、次の拡張子のファイルです。
- .xls
- .xlsx
- .doc
- .docx
- .ppt
- .pptx
C2通信のために、BADNEWSはさまざまな標的情報を集約し、2つの文字列に付加します。これらの文字列の形式は次のとおりです。
1 |
uuid=[Victim ID]#un=[Username]#cn=[Hostname]#on=[OS Version]#lan=[IP Address]#nop=#ver=1.0 |
1 |
uuid=[Victim ID]#un=[Username]# |
以下は最初の文字列の例です。
1 |
uuid=e29ac6c0-7037-11de-816d-806e6f6e696351c5#un=Josh Grunzweig#cn=WIN-LJLV2NKIOKP#on=mav6miv1#lan=192.168.217.141#nop=#ver=1.0 |
この文字列で使用されている変数が以前のバージョンとは異なる点には注目すべきでしょう。例えば、以前のBADNEWS亜種では、感染ホストの一意のIDは変数「uid」に格納され、ユーザー名は変数「u」に格納されていました。さらに、ハードコードされているバージョン文字列「1.0」も以前のサンプルとは異なります。
また、C2通信も、以前のバージョンから更新され、次のコマンドがサポートされるようになっています。
コマンド | 説明 |
0 | BADNEWSをkillします。 |
4 | 目的のファイルのリストを含むedg499.datをアップロードします。これ以降、新しいBADNEWSのインスタンスが生成されます。 |
5 | C2が指定するファイルをアップロードします。 |
8 | 収集されたキーストロークのリストが含まれるTPX498.datファイルをアップロードします。 |
13 | ファイルをadbFle.tmpにコピーして、これをC2にアップロードします。 |
23 | スクリーンショットを撮って、TPX499.datとして一時保管し、これをC2にアップロードします。 |
33 | 指定ファイルを%TEMP%\upにダウンロードし、これを新しいプロセスで実行します。 |
C2通信時、BADNEWSは、HTTP経由で事前に識別されたC2と対話します。通常のC2との通信には、次のハードコードされたURIが使用されます(余分なスラッシュが前に追加されています)。
- //e3e7e71a0b28b5e96cc492e636722f73//4sVKAOvu3D//ABDYot0NxyG.php
データが攻撃者にアップロードされる場合、次のハードコードされたURIが使用されます(ここではバックスラッシュが使用されています)。
- \e3e7e71a0b28b5e96cc492e636722f73\4sVKAOvu3D\UYEfgEpXAOE.php
初期pingがリモートサーバーに送信されると、BADNEWSは、感染ホストの情報を含む事前に作成された2つの文字列の1つを含めます。以下は、サンドボックス環境で行われたリクエスト例です。
図 8 BADNEWSによるリクエスト例
POSTリクエストにより送信されたデータを復号するには、多くのステップを踏む必要があります。最初に攻撃者は、データストリーム内に余分な「=」文字と「&」文字を挿入しています。これらを削除すると、データはbase64でデコードされます。最後に、この結果がAES-128と以下の静的キー(16進でエンコードされたもの)を使って復号されます。
- DD1876848203D9E10ABCEEC07282FF37
結論
Patchworkグループは、インド亜大陸で被害を広げ続けています。このグループは、比較的新しいエクスプロイトや、進化し続けるマルウェアツールセットを利用し、著名な個人・組織を侵害することにより、自身の目的を達成しようとします。最近の活動では、パキスタンの軍隊や原子力委員会、内務省関連の多くのルアー(わな)が確認されています。
このグループがよく利用しているマルウェアファミリの1つがBADNEWSですが、そのデッドドロップ リゾルバーの利用方法やリモートC2サーバーとの通信方法は絶えず更新されています。
パロアルトネットワークのお客様は、この脅威から以下に示す数々の方法で保護されています。
- Trapsは、このキャンペーン中に確認されているエクスプロイト文書をブロックします。
- WildFireは、このブログで示されているサンプルを悪意あるコードとして正しく特定します。
- AutoFocusのPatchworkタグとBADNEWSタグで、この脅威の監視と追跡が引き続き行われる可能性があります。
デッドドロップに悪用されていたwebサイトの所有者にも通知済みです。
IOC
悪意あるWord文書のSHA256ハッシュ
- a67220bcf289af6a99a9760c05d197d09502c2119f62762f78523aa7cbc96ef1
- 07d5509988b1aa6f8d5203bc4b75e6d7be6acf5055831cc961a51d3e921f96bd
- fd8394b2ff9cd00380dc2b5a870e15183f1dc3bd82ca6ee58f055b44074c7fd4
- b8abf94017b159f8c1f0746dca24b4eeaf7e27d2ffa83ca053a87deb7560a571
- d486ed118a425d902044fb7a84267e92b49169c24051ee9de41327ee5e6ac7c2
BADNEWS SHA256ハッシュ
- ab4f86a3144642346a3a40e500ace71badc06a962758522ca13801b40e9e7f4a
- 290ac98de80154705794e96d0c6d657c948b7dff7abf25ea817585e4c923adb2
C2サーバー
- 185.203.118[.]115
- 94.156.35[.]204
デッドドロップ リゾルバー
- hxxp://feed43[.]com/8166706728852850.xml
- hxxp://feed43[.]com/3210021137734622.xml
- hxxp://www.webrss[.]com/createfeed.php?feedid=49966
- hxxp://feeds.rapidfeeds[.]com/88604/
デッドドロップ リゾルバーの復号スクリプト
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
import requests import base64 import binascii import re from Crypto.Cipher import Blowfish from struct import pack rol = lambda val, r_bits, max_bits: (val << r_bits%max_bits) & (2**max_bits-1) | ((val & (2**max_bits-1)) >> (max_bits-(r_bits%max_bits))) ror = lambda val, r_bits, max_bits: ((val & (2**max_bits-1)) >> r_bits%max_bits) | (val << (max_bits-(r_bits%max_bits)) & (2**max_bits-1)) def unhexData(d): if len(d) % 2: d = d.zfill(len(d)+1) return ord(binascii.unhexlify(d)) def decodeDecrypt(data): decdata = '' for x in range(len(data)): x = x*2 if x < len(data): c = unhexData(data[x]) add_num = unhexData(data[x+1]) c = c << 4 c = (c + add_num) & 0xff c ^= 0x23 c = rol(c, 3, 8) decdata += chr(c) data2 = base64.b64decode(decdata) key = binascii.unhexlify("F0E1D2C3B4A5968778695A4B3C2D1E0F0011223344556677") cipher = Blowfish.new(key, Blowfish.MODE_ECB) dec = cipher.decrypt(data2) return dec urls = [ "http://feeds.rapidfeeds.com/88604" ] for d in urls: r = requests.get(d) body = r.text r = re.search("\[+\s*([a-zA-Z0-9\=]+)\]+", body) if r: data = base64.b64decode(r.group(0)) print("[{}] Decrypted C2: {}".format(d, decodeDecrypt(data).split("\x00")[0])) |