PEAK XOOPS - anti-XSS system (4) in englishin japanese

Archive | RSS |
PHP
PHP : anti-XSS system (4)
Poster : GIJOE on 2006-06-25 18:20:31 (11396 reads)

in englishin japanese
「大きな傘」(BigUmbrella)XSS対策システムの最終回。考察編です。
(3)に示したコードには、議論の余地が2つ残っています。

・疑うべきリクエストのパターンがそれで良いのか

(3)で示したチェックパターンはこうです。

preg_match( '/[<\'"].{15}/s' , $val , $regs )


タグの開始文字<および、HTMLのクオーティングを破るための'と"から始まる全16文字について、そのまま出力されていたらアウト、というチェックですが、それで本当に抜けがないでしょうか?

とりあえず怖いのは、リクエスト文字列をそのまま、<a>タグのhrefや<img>タグのsrcに渡しているケースで、この場合、java-script: から始まる文字列も(IE対策のためにはその間に制御文字が入っているものも)潰す必要があります。つまり、BigUmbrellaを本格運用するなら、"java-script:"対策も追加しておくべきでしょう。

リテラルクオーティングキャラクターである"および'を潰しているからといって、JavaScriptでリテラルを表現できないなどと考えるのは軽率で、文字コードを羅列し結合することで、十分に攻撃力を持つリテラルの表現は可能なはずです。

・チェック対象リクエストは、POSTとGETだけで良いのか

(3)では、GETとPOSTのみについてチェックしていますが、これも本来なら不十分です。ただし、それはCOOKIEについてではありません。もちろん、COOKIE経由のXSSがないという保証はありませんから、チェックを入れても構いません。ただ、冷静に考えれば、COOKIEに意図しないそんなリクエストが埋め込まれている時点でXSSなどの攻撃を受けているのは明らかで、手遅れと言わざるを得ないでしょう。すでに体がびしょ濡れなのに、「傘」をさしても意味がないのです。

むしろ問題となりがちなのは、SERVER(ENV)変数です。PHP側でデコードされるSERVER変数が3つほどあります。その中で一番有名なのはPHP_SELFですが、PATH_INFOなどを直接表示してしまっているスクリプトも少なからず存在してそうです。

とりあえず最低限足しておくべきなのは、3つのSERVER変数(PHP_SELF,PATH_INFO,PATH_TRANSLATED)についてのチェックです。実際には他のSERVER変数についても、通常のリクエストで<'"が登場することは滅多にないようなので、SERVER変数全てについて無条件でチェックする、なんていうのでも、サーバ負荷への影響は大きくないかもしれません。


なお、この「大きな傘」は、XSS対策にしかなりません。同じJavaScript系攻撃でも、ScriptInsertion(別名 HtmlInjection)にはほぼ無力です。

「対策方法」という観点からも、XSSとScriptInsertionは別物であることがお判りいただけるでしょう。

ScriptInsertion攻撃からサイト全体を守るための「大きな傘」となると難しいのですが、怪しいリクエストが見つかった時点で、サーバ管理者にメールをする、なんて地道な方法しかないかもしれません。

メールを送るとなると、可能な限りノイズを減らしたいところです。リクエストが怪しいかどうかの判断には、<'"なんて汎用的なキャラクターではなく、JavaScript特有の関数名であればかなりノイズは減らせますが、それで十分かどうかはなんとも言えないところです。

とにかく、JavaScriptで最も怖いのは、"XMLHttpRequest"なので、この文字列と、動的にXMLHttpRequestという関数名を生成・実行する"eval"の2つを検出することは最低限必要でしょう。あとは定番ですが、cookieも押さえておきます。

実際の所、こんな方法でサイト全体のScriptInsertion対策になるのか、と問われたら、自分自身でも「疑わしい」としか答えようがないのですが…

以上、宿題を残しつつも、anti-XSSシステムについてはこれにていったん終了とします。


Related articles
Printer friendly page Send this story to a friend

Comments list

GIJOE  Posted on 2006/7/14 15:03
Quote:
Quote:
やはり外部からの「HTML許可」はあり得ない設定ですね。
そうなんですよね。HTMLタグありのプレビュー機能がいかに難しいか・・・。今のところ、私は自分が納得できる範囲での解決方法が見つけられてないです。
「HTMLタグありのプレビュー」は、XSSの方ですね。
これだと、BigUmbrellaも効かないですし。

ただ、記事にも書きましたが、このHTMLプレビュー以外はすべてBigUmbrellaでXSSを封じ込める事ができるので、あとは、HTMLプレビューにチケットなりリファラーチェックなりを埋め込めばOKじゃないかと踏んでます。

Quote:
Quote:
承認制でも事実上意味のないケースが多く見られますし。
管理者にCSRF攻撃を仕掛けられるだけですからね。
私が書いたのは、承認制のチェックにおいて、ScriptInsertionが成立しているものが多い、という意味だったのですが、tohokuaikiさんのおっしゃる通り、承認行為そのものを、別途XSS+CSRFで強制する、なんて手はありますね。

ただ後者は、BigUmbrellaで防げるとは思いますが、ずっとベターな対策として、管理者承認にcapchaを導入するしか!
tohokuaiki  Posted on 2006/7/13 18:47
Quote:
やはり外部からの「HTML許可」はあり得ない設定ですね。
そうなんですよね。HTMLタグありのプレビュー機能がいかに難しいか・・・。今のところ、私は自分が納得できる範囲での解決方法が見つけられてないです。

Quote:
承認制でも事実上意味のないケースが多く見られますし。
管理者にCSRF攻撃を仕掛けられるだけですからね。
GIJOE  Posted on 2006/7/13 17:57 | Last modified
Quote:
安易にprototype.jsなんかをincludeしてしまうと、このフィルタリングが非常に難しい・・・。たとえば、Ajaxは new Ajax.Request で生成されてしまう・・・。
外部ライブラリ自体の脆弱性ではないけど、それが引き起こす脆弱性が増えそうですね。
あ〜、なるほど〜。そりゃ潰しようがないですね。
やっぱり、Script Insertionについては、本体側で真面目に作ってもらうしかないですね。

やはり外部からの「HTML許可」はあり得ない設定ですね。
承認制でも事実上意味のないケースが多く見られますし。

Quote:
便利さと完全にトレードオフです。困ったものです・・。
実際、CSRF対策は
・とりあえずチケット
・後は何とかどっかで引っかかってくれ
という状況で。
これ、Mozzilaとかのブラウザプロジェクトにみんなでお願いしましょうよ。

XMLHttpRequest の場合には、それがWebアプリケーション側で確実に判別できるHTTPリクエストを送る(しかもJavaScriptからはキャンセルできない)、という仕様を追加してもらうしかないですよ。
tohokuaiki  Posted on 2006/7/13 12:32
Quote:
とにかく、JavaScriptで最も怖いのは、"XMLHttpRequest"なので、この文字列と、動的にXMLHttpRequestという関数名を生成・実行する"eval"の2つを検出することは最低限必要でしょう。
うーん。外部JavaScriptライブラリをincludeしている場合、潰す箇所がべらぼうに増えますね・・・。

安易にprototype.jsなんかをincludeしてしまうと、このフィルタリングが非常に難しい・・・。たとえば、Ajaxは new Ajax.Request で生成されてしまう・・・。
外部ライブラリ自体の脆弱性ではないけど、それが引き起こす脆弱性が増えそうですね。

便利さと完全にトレードオフです。困ったものです・・。
実際、CSRF対策は
・とりあえずチケット
・後は何とかどっかで引っかかってくれ
という状況で。
Login
Username or e-mail:

Password:

Remember Me

Lost Password?

Register now!