Apache のサーバーサイドイメージマップ処理モジュールのクロスサイトスクリプティングの脆弱性について

Webサーバーの雄、Apache におけるサーバーサイドイメージマップ処理モジュールにクロスサイトスクリプティング脆弱性がありました。詳しくは以下をご参照下さい。

巡回などをしているとイメージマップ処理を時々見かけます。主としてメニューやナビゲーターとして使われていると思います。一枚絵の画像に複数の特定の領域を用意しておき、ユーザが任意の領域をクリックすればその領域に結び付けられたページへのリンクとして使うことが出来るというものです。

イメージマップ処理には大別して2通りあります。サーバーサイドイメージマップ処理、およびにクライアントサイドイメージマップ処理です。通常良く使われているのは後者のクライアントサイドイメージマップ処理です。

歴史的にはサーバーサイドイメージマップ処理が先行して使われました。NCSA ウェブサーバの頃に発達し、新興勢力のApacheに引き継がれました。サーバ側の負荷が高かったり、設定が難しかったりしましたので、ブラウザの発達に伴い、クライアントサイドイメージマップ処理により、次第に取って代わられた感があります。実際、現在ではほとんどのイメージマップの記述はクライアントサイドの処理によるものです。HTMLの記法では両者は区別され、みかけ上はよく似ている、といった感じでしょうか。

しかしながらサーバーサイドイメージマップ処理はまだ生きています。クライアントサイドでは不可能なきめ細かな工夫や配慮が可能だからでしょうか。例えば古めのブラウザをもサポート可能ですし、リンクとなる画像領域の形も豊富にコントロール出来ますのでひょっとしたらビジュアルデザイン面で有利かも知れません。視覚面でのこけおどしにならないように工夫(別途テキストでアンカーを作るなど)をする前提が必要ですけれど、サイトデザインにおいて面白い武器だと思います。

この種の解説をあまり見ませんので、あくまで私見なのですが、サーバーサイドイメージマップ処理には、もうひとつ有利な点があります。それはサイトコンテンツのメンテナンスの容易性です。ひとつのサイトの各ページに共通のメニューを置くことを考えましょう。メニュー構成への変更を考えたときに全ページのメニュー部分の内容を置き換える替わりにそのメニューをサーバーサイドイメージマップ処理で実現しますと、メンテナンスすべきコンテンツはイメージマップの定義を1個だけですむ可能性があります。※但し、テキストによる代替の案内について考慮するのであるならばもう少し考えて見るべきでしょう。この可能性は試しておいたほうが良いかも知れません。そうすれば、よくある悪名高い逃げ、すなわちframeset要素を使うことを、避けることが出来るかもしれません。

今、ページA1,A2,A3,A4 があったときに、各ページでサーバサイドイメージマップである m0 を別途用意、メニュー代わりに使ったとします。A1からm0へのアンカーを用意して適宜画像の上をクリックすると、m0はクリックされた、その画像の領域の座標に従って本当のリンク先のURLを用意、ユーザをそちらへ導きます。A2,A3,A4 でも同様です。

さて、考慮しておくべきことがあります。画像全体をUとした時に、画像の各領域をu1,u2,u3,u4 だったとしましょう。u1をクリックすればサイトのトップのURLへ導かれる、そのような仕組みが4個あるわけです。問題は、各領域u1,u2,u3,u4の全てでもって、全領域Uを覆い尽くしているかどうかです。ユーザの立場に立ってみましょう。メニュー画像をクリックしましたが、どうやらハズレのようだ、の時のことです。

色々な考え方で対処できるかも知れません。たとえば、ハズレ座標なら反応しないような仕組みを用意しておくことも有効でしょう。また、ハズレならば、イメージマップが意識している各リンク先の一覧をまとめたテキストによる代替リンク集のページをユーザに与えることも可能なのです。今、説明の為に「代替リンク集」という言葉を使っていますがコレは私のこの場だけでの造語です、ご了承下さい。

余談ですが、どんなにイメージマップを上手に作っても、座標(0,0)を与えれば、この代替リンク集が表示されることと思います。そういう仕様だと思って良いでしょう。このことを意識しておくことは重要です。なぜならば、たとえハズレ座標では何も起きないようにイメージマップを設置したとしても、わずかながらではありますが代替リンク集が表示されてしまうことがあり、そのせいでユーザが道に迷ったら困るからです。親切なものを作っておくべきです。

さて、ひとたび代替リンク集が表示されたとしましょう。ユーザは、u1〜u4に割り当てられたリンク先を見ることとなりますが、当然のことながら、元々いた場所に戻りたいと思うかもしれません。ユーザはブラウザの「戻る」ボタンを使っても良いのですが、サーバサイドとしては親切に「戻る」為のリンクを用意しておいたほうが良いでしょう。(用語集やヘルプ用途でも同様です。)

戻るために固定のURLを用意してしまうとすると、ちょっと失敗かも知れません。A1から来たときにはA1に戻りたい、A2から来たときにはA2に戻りたいのです。

そこで、Apacheのイメージマップ処置としては、refererを用意しています。例えばdefaultではrefererに戻れるリンクを用意可能ですし、その方がユーザに対して親切です。ちなみに、古いイメージマップ処理ではHTTP_REFERER がそのまま格納されていました。今後もそうなのかな?

今回発見されたXSS脆弱性は、HTML様に出力された代替リンク集にrefererがアンカーのhrefとして埋め込まれた際に、【"】や【< >】などがサニタイズされていなかったというものです。実験環境では、サイトX上のページをユーザが閲覧するだけで、脆弱性を抱えるサイトYのドメインの情報(Cookieなど)を、サイトZの記録用CGIに送付されてしまうことが確かめられました。特に画像をクリックするとかの操作は不要です。ぼうっとしているだけで盗まれてしまうかもです。(Windows上でFirefoxOperaは被害にあわないようです。リファラがURL(パーセント)エンコードされるからのようです。)

正直に申し上げますと、仮に私だったら、そのような罠には簡単にハマルことでしょう。気がつくことはほとんど無理です。XSS攻撃の特徴のひとつと云えるでしょう。もしくは大々的な嘘ページを偽装されてURLのドメインは確かに信頼済みなのにページコンテンツは詐欺、という事態も考えられます。

さて、それではユーザとしては、どれほど危険に備えて準備しなくてはいけないのでしょうか?まず第一に、Apacheでサーバサイドイメージマップ処理を実際に活かしているサーバがどれほどあるかです。今やクライアントサイドイメージマップ処理が全盛の時代です。少ないかもしれません。仮に活かされていたとしても代替リンク集がrefererを使っていないかも知れません。(各種の説明やサンプルで具体的にrefererの用例をコーディングしている例を私は知りません。)。そもそも、見知らぬサイトでJavaScriptをオンにしているのであるならばある程度の覚悟が必要である、といった定石通りのことしか言えないのかも知れません。


只今22:21、気になったので追記しています。上記でも掲げたリンク先のJVN,IPAの両文献、JVN#06045169および、「mod_imap」におけるクロスサイト・スクリプティングの脆弱性において、ユーザに脆弱性の発現の状況を誤解させる表現があることに気がつきました。まず少し引用します。ついで、どこがまずいのかを記します。

想定される影響

mod_imap または mod_imagemap が使用されているウェブページにアクセスしたユーザのブラウザ上で、悪意あるスクリプトを実行される可能性があります。

影響:
「mod_imap」「mod_imagemap」を利用するウェブサイトで、利用者の意図しないスクリプトがウェブブラウザ上で実行される可能性があります。

ちょっとまずいなと感じた点を書きます。引用した上記文献を見る限り、イメージマップを使ったページを訪問しなければ大丈夫だ、という印象が起こるかもしれません。(もしくは、画像を切ってあれば大丈夫かもと思う人がいるかもしれません。あるいはクリッカブルマップを利用しなければ良いと思われるかもしれません。)それは間違いです。ユーザは、悪意ある者が作成した、イメージマップなど全くない罠ページに行くだけでXSS脆弱性の悪用を通じて、被害を受けます。誤解を訂正する為にもはっきりと書きましょう。罠ページには視認できないiframe要素があり、その埋め込みリンク先として対象のイメージマップのあるサイトのページのアドレスを指定してある、そのような形が実際に使われる手法でしょう。けして複雑な罠ではありません。罠ページそのもののURLアドレスにスクリプトが書かれていれば良く、iframe要素で呼ばれた対象サイトのページはrefererとしてその罠ページのURLを受け取ります。これで攻撃が発動してしまいます。refererを汚す一例です。mod_imap または mod_imagemap が使用されているウェブページにアクセスというのは、人間が意識してアクセスするのではなく、機械が勝手に行ってしまうのだ、ということに留意して下さい。また、iframe要素を複数組み合わせれば、ひとめで怪しいと思うようなURLアドレスでなくとも、罠ページを構成できます。怪しいかどうかなぞ、アドレスを見ただけでわかりません。以上は今回に限らず、XSS攻撃で密かにCookie等を抜かれる時の常套手段だと思っても良いでしょう。変種はさまざまですが…。ここまで、ちょっとまずいなと思った事項です。話を元に戻します。追記終わり。


以上がユーザの視点でのお話しでした。さて一方、サーバサイドの管理者さん達は何に気をつけなくてはいけないのでしょう。危険があるかどうかApacheの設定をもう一度見直すことをお勧めしておきたいと思います。イメージマップ処理のモジュールである、mod_imapは、ビルトインモジュールです。わざわざ取り除いていますか?おそらく配慮なさっておいででないと思います。その他の設定で不活性にしているかもしれません。活性化したままかもしれません。htaccessをユーザに許可していれば、普段は寝ているmod_imapが目を覚ましているかもしれません。(これは実際にありそうなことです。)サーバでサイト構築をする時に何かのサンプル、あるいはTESTでイメージマップを試したことがあれば、そのファイルを狙われるかも知れません。…ビルトインモジュールの置き換えは大変な苦痛が伴うことであろうと推察いたしております。ですがmod_imapだけはなんとか殺しておくことが有効な手だと思います。

以下参考リンクです。

apacheイメージマップネタ::極楽せきゅあ日記(20051215)
あちきのアパッチ構築時のお勧めは、--disable-include --disable-imap っすねー。これ要らない!っていうか危険!ってなモジュールは2.0以降かなり減ったんですが、この二つは今でも不要って言い切りたいかも。特にSSIはそうだったんだけど、これでIMAPも同じランクに格上げかなあ。微妙に反応すると、再構築ってそんなに難しい話ではありませんですが、サービス展開してるところとしてはテストしたいかもですね。でもIMAP外しても特に何の問題も無いと思うデスよ。…とのことです。
「mod_imap に XSS 脆弱性」@水無月ばけらのえび日記
まあ、きょうびサーバ側イメージマップを使う機会はほぼゼロですので、Apache をインストールしたら最初に無効にするのがセオリーだと思いますが。
※念のため私が管理している Apache なサーバを全部確認しましたが、すべて mod_imap は無効でした。
WCAG1.0の件は知りませんでした。なるほど。XHTML1.1でismap属性があったのを見てちょっと誤解していました。HTML,XHTML的にもサーバーサイドイメージマップは使用しないのが吉なのですね。
セキュリティーホールMEMO
1.3 / 2.0 用の patch 関連の情報もあります。差し支えなければmod_imapそのものを消してしまったほうが良いのでしょうか。パッチを当ててからの方が後日のウッカリがなくなるのでしょうか。
20 ways to Secure your Apache Configuration
Disable any unnecessary modules
Here are some modules that are typically enabled but often not needed: mod_imap, mod_include, mod_info, mod_userdir, mod_status, mod_cgi, mod_autoindex
不要なら turn off 。

謝辞:しかPさん。これらをみつけて悶々とし、アタフタしていた私に心からのサポートを頂きました。ありがとうございました。