no title以降、こちらの更新を原則的に停止していましたが、恒久的に更新を停止し、tumblrに移行することに致しました。詳しくは、ブログとソーシャルブックマークの移行について - 徳丸浩のtumblrを参照下さい。

コメント
0件
トラックバック
1件
ブックマーク
0 users

はてなブックマークボタンがマイクロアド社の新ガイドラインに従ったらこうなる

すでにこちらでご案内の通り、私のブログno titleおよびEGセキュアソリューションズオフィシャルブログ)に貼っていた「はてなブックマークボタン」により、読者の皆様の閲覧行動がマイクロアド社によりトラッキングされておりました。読者の皆様に断りなく不快な結果を強いていたことに対してお詫び申し上げます。既に当該ボタンは撤去しております。

その後、株式会社はてな社長の近藤淳也氏およびはてなの日記にて行動情報の提供をやめる旨のアナウンスが一昨日ありました(ここここ)。さらに、マイクロアド社からは、昨日以下のアナウンスがありました。


今後マイクロアドでは、ブログパーツや外部ボタン等、マイクロアドと直接提携関係にあるパートナー以外の第三者にあたる媒体・配信面に付与される可能性のあるものについて、それらの表示領域にマイクロアドからの行動履歴情報の蓄積を無効化するオプトアウトページへの導線設置を義務化いたします。

http://www.microad.jp/press/20120314/

ちょっと分かりにくい文面なので、はてなブックマークの例を使って補足すると、「直接提携関係にあるパートナー」が株式会社はてな、「第三者にあたる媒体・配信面」は私の日記、「それらの表示領域」は「はてなブックマークボタン」になります。

ということは、仮に、はてなブックマークボタンが行動履歴収集を継続していた場合、はてなブックマークの表示領域に「マイクロアドからの行動履歴情報の蓄積を無効化するオプトアウトページへの導線設置を義務化」されることになります。

しかし、読者がオプトアウトしたいと思うためには、まず、当該ボタンが行動履歴を収集していることを表明していなければならないはずです。

これが、「直接提携関係にあるパートナー」に表示される広告などの場合は、パートナーサイトのプライバシーポリシーにて、行動ターゲティング広告を利用している旨を告知しているはずです。たとえば、NAVERプライバシーポリシーには、以下のように明記されています。

また、本サービスでは効果的な広告配信のために当社と提携する会社が提供する行動ターゲティング広告を利用しています。行動ターゲティング広告提供会社が利用するクッキー等に関する説明、無効化の手順については提供会社サイトにてご確認いただけます。

http://www.naver.jp/privacy/policy/

これに対して、「第三者にあたる媒体・配信面」については、プライバシーポリシーに上記告知はないはずです。このため、「オプトアウトページへの導線」を表示する前に、行動履歴を収集している旨を読者に告知しなければなりません。

この方針に沿って、はてなブックマークボタンが、仮に行動履歴収集を続けていたら、以下に示すようなボタンになるのではないでしょうか。


f:id:ockeghem:20120315080336p:image


実際には、前述の通り「はてなブックマークボタンから収集した行動情報の第三者提供をやめます」とのことなので、上記ボタンが使われることはないはずです。現実のブログパーツとしてはどのようなものがあり得るのでしょうか。以下、それについて考えてみました。

ブログパーツが読者の行動履歴を収集する場合、ブログ主には金銭的なメリットがない代わり、行動履歴が収集されるというデメリットもありません。デメリットがあるのはブログ読者の方です。従って、読者が行動履歴を収集される見返りに、読者にとって相当魅力的なコンテンツが表示されるべきでしょう。私が妄想したコンテンツは以下です。

それは、魅力的な男性あるいは女性が時計を持っていて現在の時刻を教えてくれるものです。読者にとって魅力的であることが望ましい訳ですが、マイクロアド社の誇る行動分析を駆使しして、読者が魅力的と思う異性(読者によっては同性)の写真を表示してくれることでありましょう。読者はそれを見て、「すげー、めっちゃストライクゾーンじゃん、気持ちわるー」と驚いたり、「なんだ、全然分かってないな、ダメじゃん」と呆れたりすることできます。

私は行動ターゲティング広告自体を否定するものではありませんが、ブログオーナーないし読者として、透明性の高い説明を要望すると共に、読者にとっても魅力的なコンテンツ提供につながることを希望します。

補足

こちらはてなのサービスの新規の更新をやめると書きましたが、このテーマについてのみ更新を継続します。

コメント
6件
トラックバック
0件
ブックマーク
0 users

PHPカンファレンス北海道で講演します

PHPカンファレンス北海道で講演する機会を頂きましたので報告します。

日時:2012年4月21日(土曜日) 10時20分〜17時20分(徳丸の出番は15:30〜16:10

場所:札幌市産業振興センターセミナールームA (北海道札幌市)

費用:無料(申し込みはこちら

講演タイトル:徳丸本に載っていないWebアプリケーションセキュリティ


講演の概要は以下となります。技術よりの話題で、デモあり(たくさん仕込みたいですね)、初級〜中級です。

キャッシュからの情報漏洩は徳丸本に載せても良かったなと思うテーマです。PROXYやフレームワークのキャッシュが悪さをして情報漏洩するリスクについて説明します。

クリックジャッキングは、PHP Conference 2011でも説明しましたが、もう少し詳しく説明できればと思います。クリックジャッキングはついこの間まで「知る人ぞ知る」というレベル感だったのに、いつの間にか「対策必須」という感じになってきましたね。

Ajaxのセキュリティは徳丸本に載せられなかったテーマとしては最大のものと考えています。以下のブログエントリにて説明した内容を詳しく説明します。

ドリランドの件は運営側から詳細原因が公表されていないため、あくまで推測、ないし妄想レベルの話になってしまいますが、ドリランド カード増殖祭り | 水無月ばけらのえび日記に排他制御の問題かもしれないと説明されているように、排他制御の問題だったと仮定して原因と対策を説明します。私自身はドリランドの問題について詳しく知っているわけではありませんので、今後類似の問題を発生させないことを目的としてドリランドの事故を題材として使わせていただくということですね。


それでは、札幌でお会いしましょう。


[PR]
安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
0件
ブックマーク
0 users

徳丸本の台湾版が発売開始されました

拙著「体系的に学ぶ 安全なWebアプリケーションの作り方(以下、徳丸本)」が中国語繁体字に翻訳され、台湾で販売開始されましたので報告します。出版社の紹介ページ

@kuroneko_stacyさんが、早くも台湾で購入されたそうで、書店での平積みの様子を写真にとって下さいました。画像をクリックすると拡大します。


昨日見本が届きましたので、いくつか写真を紹介します。まずは表紙。

f:id:ockeghem:20120301082058p:image


謝辞のところ。

f:id:ockeghem:20120301082246p:image


人気の(?)3章、悪人と銀行員の会話。

f:id:ockeghem:20120301082247p:image


台湾の本屋さんのコメント(@kuroneko_stacyさんと現地本屋さんの会話)

徳丸本、台湾でも人気だそうです。本屋のおじちゃんが良さを熱く語ってくれました。「この本は凄く良くできている!日本人が書いているんだ。知ってたか?」って聞かれたので、おこがましくも著者は友人ですよって言わせていただきました(笑)

https://twitter.com/kuroneko_stacy/status/174069549304516608

たくさんの方に読んでいただくことになりとても嬉しいです。

以上、ご報告まで。


[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
0件
ブックマーク
0 users

書籍「Android Security」の暗号鍵生成方法には課題がある

書籍「Android Security  安全なアプリケーションを作成するために」は既に各方面で絶賛されているように、Androidアプリケーションの開発者には必携の書籍だと思いますが、新しい分野だけに、首をひねらざるを得ない箇所もありました。このエントリでは、同書第10章「暗号化手法」から共通鍵の生成方法について議論します。

はじめに

書籍「Android Security」(業界では「タオ本」と呼ばれているので、以下タオ本と記述)の10章では、端末内のファイルを暗号化して保存する手法について説明されています。その際に問題となるのが、鍵の生成と保管の方法です。スマートフォン端末、とくにAndroid端末は、アプリケーションのリバースエンジニアリングとルート化の可能性は常にあるため、あらゆる場合にも破られない暗号化というものはありません。このため、守るべき情報資産と、想定する脅威(言い換えれば受容する脅威)を定義しなければ、有効な実装方法は得られないと考えます。

このエントリでは、典型的な脅威を3パターン想定した上で、タオ本の説明の妥当性について検証します。


典型的脅威シナリオ3パターン

スマートフォンに格納されたデータが、アプリ提供者の意図しない形で漏洩するシナリオを以下に3種類示します。

最初のマルウェアからの漏洩シナリオ(X)では、マルウェアはルート権限を得ていないと想定します。実際には、ルート権限を悪用するマルウェアもあり得ますが、端末のルート化は利用者の自己責任で行うべきという考え方は一般に浸透しており、アプリケーション側の対策としては、ルート権限を持つマルウェアに対しては免責されると考えて良いでしょう。

二番目(Y)と三番目(Z)については、保護される情報と登場人物こそ異なるものの、端末を操作できる人が(暗号化された)情報を盗み出すという行為については共通です。従って、(Y)と(Z)については、技術的には同じ課題があると考えられます。(Y)と(Z)については、操作者がルート権限を得る可能性は現実的な脅威であり、考慮しなければならないと想定します。

(X)、(Y)、(Z)共通の前提として、アプリケーションのAPKファイルは攻撃者にとって取得可能であり、リバースエンジニアリングされ得ると想定します。これは、スマートフォンのセキュリティでは常識な前提だと考えます。


タオ本で説明されている鍵生成方法

タオ本で説明されている鍵生成方法は以下の3種類です(タオ本P232)。

(A)は、ソースコードに暗号鍵(の元となるパスワード)をハードコードするものです。これについて、タオ本は以下のように批判しています(タオ本P232)。

この方法の場合、リバースエンジニアリングによってソースコードが取得されれば、簡単にパスワードが判明してしまいます。簡単に解析されないように2つの文字定数のANDを取ったり、シフト演算したりする例も見られますが、効果はほとんどないと言ってよいでしょう。【中略】この方法は非常に危険なので使用しないでください。

(B)については、以下のような注釈があります(タオ本P233)。

ただし、この方法では、アプリケーションは同じ値の乱数を再生成できないので、アプリケーションが暗号化したデータを復号化(原文ママ)するためには、生成したパスワードをどこかに保存しておく必要があります。ファイルにそのまま保存したのでは、パスワードを平文でファイルに書き込んだのと何ら変わりありません。したがって、この方法が有効となるのは、データをファイルに保存する必要がない場合になります。

暗号化データをファイルに保存する応用には使えないと説明しています。

ということで、タオ本では方法(C)が暗号鍵生成の本命として説明されています。

タオ本で推奨されている暗号鍵生成方法

それでは、タオ本で推奨されている暗号鍵生成方法(C)を検証してみましょう。同書P233以下には、暗号鍵生成の実装例として以下が紹介されています。

同書P233には、この方式のメリットとして以下のように説明されています。

パスワードを端末内に保存する必要がないため、パスワードを解析しにくくなります。また、端末固有の値を使用するため、端末ごとに異なるパスワードとなり、暗号化したデータが流出してパスワードが解析されても被害が最小限で済みます。

このように書いてありますが、本当でしょうか。


タオ本方式も結局リバースエンジニアリングには弱い

タオ本方式(C)でも、リバースエンジニアリングされると、パスワードの生成方式は攻撃者に解析されると考えるべきでしょう。定数なら解析されて、ロジックなら解析されないとは考えられません。となると、パッケージ名とインストール日時を攻撃者が知ることができるかどうかが問題になります。

まず、パッケージ名はリバースエンジニアリングの時点でAPKファイル内のAndroidManifest.xmlから読み取れます。

残りは、インストール日時ということになりますが、そもそもインストール日時を鍵の元とすることが好ましくありません。インストール日時は、アプリケーションが公表された日付などから推測できるからです。昔々、Netscapeブラウザの有名な脆弱性として、日時を元に暗号鍵の元を生成していたという事例がありました(論文のリンク)。

しかも、シナリオ(X)〜(Z)においては、攻撃者がインストール日時を正確に求めることができます。

シナリオ(X)では、マルウェアがPackageInfo#firstInstallTimeを参照して、攻撃対象アプリのインストール日時を正確に求めることができます。

シナリオ(Y)とシナリオ(Z)では、端末が攻撃者の手元にあるわけですから、やはりインストール日時を正確に求めることができます。

すなわち、タオ本推奨の方法(C)は、暗号鍵生成方式がリバースエンジニアリングで求められる脅威に脆弱であり、方法(A)と大差ないことが分かります。


方法(B)はマルウェアの脅威に対しては有効

ここで、方法(B)についてあらためて評価します。タオ本には「ファイルにそのまま保存したのでは、パスワードを平文でファイルに書き込んだのと何ら変わりありません」とありますが、マルウェアによる脅威シナリオ(X)に対しては、有効です。

Androidでは、アプリケーション毎にユーザIDが割り振られ、端末のファイルシステムもこのユーザIDによって権限管理されます。すなわち、元々、他のアプリケーションのデータを参照できないように設定することになっています。このため、マルウエアから他のアプリケーションのデータファイルを参照することは(権限設定の不備がない限り)できません。

例外はSDカード内のファイルであり、SDカードはユーザIDによる権限設定がありません。このため、SDカード内のファイルを保護するために、データを暗号化するニーズがあるわけです(タオ本P229)。

すなわち、暗号鍵を乱数で生成して、Androidのローカルファイルに(適切な権限設定をして)保存すれば、暗号鍵はマルウェアから参照できません。すなわち、マルウェアの脅威に対しては、暗号鍵をローカルファイルに保存する方法は有効です。


考察

Androidアプリケーションにとって鍵管理は困難なテーマです。あらゆる脅威を想定しなければならない想定では、ルート化された端末から、あらゆる情報が参照できるため、鍵の安全性は、アプリケーションの難読化の強度に依存します。この想定では、完全な暗号化は存在せず、商用の難読化ツールを使えばある程度の強度は期待できる、と言う程度でしょう。

しかしながら、脅威について現実的な線を引けば、話は変わってきます。多くのアプリケーションは、端末を紛失した場合のデータ保護を保証しません。また、暗号化してまで著作権保護すべきデータが実質なく、著作権法による保護で十分という場合も多いでしょう。

この想定下では、もっとも警戒すべき脅威はマルウェアによる情報漏洩であり、このケースでは「乱数により生成した鍵をローカルファイルに保存する」という鍵管理が有効です。

タオ本は、このあたりの脅威分析が詰められておらず、鍵管理方式の評価が大ざっぱな内容になったものと考えます。


どうするのがよいのか

では、Androidアプリケーションでは鍵の生成と保存をどうすればよいでしょうか。

一案として、方法(A)と方法(B)のハイブリッドが考えられます。アプリケーションの初期設定時に乱数で生成してファイルに保存した鍵と、アプリケーション内に埋め込んだ定数の鍵を連結して、暗号鍵の元とする方法です。

この場合、ローカルファイルを読める権限を持つ攻撃者には鍵がばれてしまいますが、その脅威に対してはアプリケーションの難読化でがんばるしかありません。例えば、商用の難読化ツールの使用が考えられます。それでも駄目な場合はあきらめる(受容する)ということです。

これでダメなケースの典型例は、利用者が端末を紛失あるいは盗まれた場合や、著作権保護されたデータが盗用されることです。前者は利用者の過失もあるので「最大限頑張るけど破られたら申し訳ない」ですし、後者は、権利者に対して適切に説明しておくしかないでしょう。


まとめ


[PR]

3月2日、株式会社DNPデジタルコム主催の「スマートフォン向けセキュリティセミナー」(五反田、無料)で基調講演します。この中で、スマートフォンアプリケーションのセキュリティに関する責任範囲や対策などについて、基礎的なところから説明できればと思います。

スマートフォンアプリケーションのセキュリティ強化策についての相談は、HASHコンサルティング株式会社まで。

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
8件
トラックバック
0件
ブックマーク
0 users

昨日Webサイトを守るためのセキュリティ講習会の講師を担当しました。講習会の終了後、受講生から「管理者パスワードの定期的変更」に関する質問がありました。備忘の為、質疑内容を以下に記録します。


Q1:上位ポリシーにて、管理者パスワードは定期的に変更するように義務づけられているが、何日毎に変更するのが正しいのか。最近の専門家の見解をお伺いしたい
A1:専門家の見解は分かれているとお答えしました

現在の主流はパスワードを定期的に変更するべしという考え方ですが、それに異論を持つ人もいて、私もその一人です。

一般ユーザのパスワードとは異なり、管理者パスワードは、業務の必要上複数の人が知っている状況があります。その状況では、「定期的に変更」するのではなく、管理者パスワードを知っている人が、他業務に異動、あるいは退職するタイミングで遅滞なく変更するべきです。そうしないと、「管理者でなくなった人が管理者パスワードを知っている」という状況が起きます。

管理者パスワードを定期的に変更するというのは、上記運用ができない(したくない)場合の代替策ととらえることができます。この場合、一定期間「管理者でない人が管理者パスワードを知っている」状態があり得ます。本来避けなければならない状況であり、積極的にそうする必然性はありません。

rootログインやsuコマンドを使っていると、管理者業務をする人にrootパスワードを教えなければなりません。一方、sudoコマンドを使って管理者業務をすると、rootパスワードを教えなくてもすむので、rootパスワードを変更する頻度を少なくすることができます。また、誰が、いつ、どのrootコマンドを実行したかというログも取得できるので、管理レベルが向上する点でおすすめです。


Q2:Windowsなどでは、パスワードポリシーとして、一定回数前までのパスワードを使用できないようにできるが、この点はどうか
A2:管理者パスワードの場合は、一度設定したパスワードを再利用することは禁止すべきとお答えしました

パスワードポリシーとして、例えば3回前までのパスワードは再利用禁止などというものがあります。しかし、これを「4回前のパスワードであれば再利用してもよい」と捉えるべきではありません。管理者パスワードを管理者以外のものが知っている状態は避けなければならないからです。

とはいえ、過去のパスワードをすべて記録して、衝突を防ぐという作業も煩わしく、「パスワード台帳」の管理が困難なため、かえってパスワード漏洩の原因になりそうです。

このため、パスワードは乱数などで生成することで、結果として過去のものと衝突しない方法をとればよいと考えます。わざわざ過去のものと照合する必要はありません。


あわせて読みたい

パスワードの定期変更は「神話」なのか? - ockeghem(徳丸浩)の日記
続パスワードの定期変更は神話なのか - ockeghem(徳丸浩)の日記
パスワードの定期変更という“不自然なルール”:セキュリティ・ダークナイト(6) - @IT


[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
14件
ブックマーク
0 users

PostgreSQL Conference 2012で講演します

PostgreSQL Conference 2012で講演する機会を頂きましたので報告します。

日時:2012年2月24日(金曜日) 14時30分〜17時20分(徳丸の出番は16:30〜17:00

場所:AP 品川 (東京都港区)

費用:3,500円(申し込みはこちら

講演タイトル:安全なSQLの呼び出し方

今回は、IPAの安全なSQLの呼び出し方を題材として、SQLインジェクションの発生原理から、安全なSQLの利用方法を基礎から実際までを説明します。

あまりトリッキーな攻撃の方法はしないつもりで、基礎的な話が中心となります。安全なSQLの呼び出し方の作成経緯については、「今夜こそわかる安全なSQLの呼び出し方 〜 高木浩光氏に聞いてみた」を参照下さい。

さて、「安全なSQLの呼び出し方」は以下の五名による執筆となっています。

執筆者 徳丸 浩   永安 佑希允   相馬 基邦   勝海 直人

    高木 浩光 独立行政法人産業技術総合研究所

執筆者に肩書きがないのは、独立行政法人情報処理推進機構(IPA)の職員ということです。安全なSQLの呼び出し方の執筆者の一人に、IPAの徳丸浩という人がいる、ということですね。一方、今回の講演は、HASHコンサルティング株式会社代表としての徳丸浩がしゃべります。

ややこしいですが、こうすることで、IPAとしての公式な立場ではなく、徳丸の個人としての意見を自由にしゃべることができます。具体的には、独立行政法人のセミナーでは仕込みにくい*ネタ*を取り入れることもできるわけですね(これ、けっこう重要)。

昨年は、PHP ConferenceYAPC::Asia TOKYO(Perlの祭典)で講演する機会を頂きました。今年の講演はじめはPostgreSQL Conferenceということで、オープンソースソフトウェアのカンファレンスでしゃべらせていただけることを嬉しく思います。

参加者190名ということですので、お申し込みはお早めに。

[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
3件
ブックマーク
0 users

今年読まれた人気記事トップ10+10

今年も残りわずかとなり、今年の○○トップ10というタイトルを目にする機会も増えました。徳丸のブログでも、トップ10を発表したいと思います。今年書いたブログ限定ではなく、今年もっとも読まれたブログエントリのトップ10です。

  1. Apache killerは危険〜Apache killerを評価する上での注意〜
  2. PHP5.3.7のcrypt関数のバグはこうして生まれた
  3. もし『よくわかるPHPの教科書』の著者が徳丸浩の『安全なWebアプリケーションの作り方』を読んだら
  4. SQLのエスケープ再考
  5. EZwebの2011年秋冬モデル以降の変更内容とセキュリティ上の注意点
  6. PHP5.3.7のcrypt関数に致命的な脆弱性(Bug #55439)
  7. 都道府県型JPドメインがCookieに及ぼす影響の調査
  8. モテるセキュ女子力を磨くための4つの心得「SQLインジェクションができない女をアピールせよ」等
  9. evernoteのテキストをevernote社の管理者にも見えないように暗号化する
  10. 私はいかにしてソフトバンク端末60機種のJavaScriptを検証したか

ページビュー数では、1.の「Apache killerは危険〜Apache killerを評価する上での注意〜」がぶっちぎりでした。Apache Killerへの関心の高さが伺われますね。

2位の、PHP5.3.7のcrypt関数バグも大きな話題となりました。この問題への態度を観察していると、PHPerよりも他のクラスタの方が騒いでいる印象を受けました。なんというか、「真のPHPerはこの程度の問題では動じないのだ」という無言のメッセージを感じた気がしました。現実問題として、crypt関数あんまり使われてないような気がしますしね。

4位には、「SQLのエスケープ再考」がランクインしています。3年半前のエントリですが、継続して読んでいただいています。私にとっても思い入れの深いエントリです。

8位の「セキュ女子力」も多くの方に読んでいただきました。本格的なコピペを書いたのは実は2回目でして、1回目は「Webアプリ脆弱性オタがふつーのSEの彼女に脆弱性世界を軽く紹介(ry」なんですが、元ネタが増田で出してきたのまで真似して増田で発表したという行きがかり上今まで匿名にしていました。あれから三年も経つのですね。もうばらしてもいいでしょう。

ちなみに、11位〜20位は以下の通りです。

  1. PHPのイタい入門書を読んでAjaxのXSSについて検討した(1)
  2. ソフトバンクのゲートウェイ型SSLの脆弱性を振り返る
  3. 「SQLインジェクション対策」でGoogle検索して上位15記事を検証した
  4. ぼくがPDOを採用しなかったわけ(Shift_JISによるSQLインジェクション)
  5. CSRF対策のトークンをワンタイムにしたら意図に反して脆弱になった実装例
  6. SQLの暗黙の型変換はワナがいっぱい
  7. KDDIの新GWで「かんたんログイン」なりすましの危険性あり直ちに対策された
  8. PHP5.4のhtmlspecialcharsに非互換問題
  9. 「安全なWebアプリケーションの作り方」電子書籍版9月28日(水)販売開始します
  10. 僕が「ホワイトリスト」を採用しなかった訳

今年は、なんと言っても「「徳丸本」を完成させることができ、多くの方に読んでいただいたことに尽きると思います。多くの方に支えられて初めてできたことです。本当にありがとうございました。来年もよろしくお願いいたします。

[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
2件
ブックマーク
0 users

大垣本を読んで「バリデーションはセキュリティ対策」について検討した

このエントリでは、セキュリティの観点から、バリデーション実装について検討します。大垣さんの本を読んで「大垣流バリデーション」について勉強した結果を報告します。

はじめに

大垣さんの記事「入力バリデーションはセキュリティ対策」では、「入力バリデーションはセキュリティ対策である」が力説されています。この記事はおそらくid:ajiyoshiさんのブログ記事「妥当性とは仕様の所作 - SQLインジェクション対策とバリデーション」を受けてのことだと思います。id:ajiyoshiさんのエントリでは、「妥当性検証は仕様の問題であってセキュリティ対策ではありません」と明言されています。私はid:ajiyoshiさんに近い考えを持っていますので、大垣さんの主張について、私なりに考えてみました。

記事を書くにあたり、徳丸の立場を明確にしておきたいと思います。

以下、順に説明します。

バリデーションの基準は何か

バリデーションの問題を議論する上での最初の(そして最大の)問題は、「何を基準に(正として)バリデーションするか」です。セキュリティの教科書によっては、セキュリティの都合により入力値の制約を定め、その制約を元にバリデーションするように説明しているものがあります。その具体例については、コレコレを参照下さい。

id:ajiyoshiさんのブログでは、バリデーションの基準はアプリケーションの仕様だと明記されています。徳丸も同意で、私の本のP79には「入力値検証の基準はアプリケーション要件」という節があります。

大垣さんの本では、「入力値はポジティブセキュリティモデルを使用して確実に検証する(P171)」などとありますが、「ポジティブセキュリティモデルってなんだ?」と、よく分からないので、大垣さんとtwitterで会話してみました。togetterにまとめましたので参照下さい。結論としては、大垣さんも「バリデーションはアプリケーションの仕様(文書化されているかどうかは別として)に従う」と考えられているようです。

つまり、バリデーションの基準についてはid:ajiyoshiさんと大垣さんの考えは同じということになります。

バリデーションのセキュリティ上の効果

次に、バリデーションのセキュリティ上の効果について検討します。

id:ajiyoshiさんは、バリデーションのセキュリティ上の効果については言及されていないようです。これは実に潔い態度と言えますが、一般的には、バリデーションに一定のセキュリティ上の効果を認める人が多いと思います。このあたりの話題は、稿を改めて書きたいと思っています。

一方、大垣さんは、ご自身の本の中で以下のように書いておられます。

クロスサイトスクリプティング、SQLインジェクション、HTTPレスポンススプリッテイングなど、入力さえ厳密に確認していればセキュリティホールとならずにすむ場合が数多くあります。

様々な脆弱性について防御上の効果があるが、常に攻撃を防げるわけではない、ということですね。これはセキュリティ観点から見たバリデーションの特徴です。

「さまざまな脅威に対して効果がある」という、いわば万能性に着目すると、「バリデーションはなんて素晴らしい『セキュリティ対策』なんだ」という評価になります。一方、常に防げるわけではない点に着目すると、「バリデーションで常に防御できるわけではないし、そもそも本質な対策ではない。そのようなものは『セキュリティ対策』とは認めない」という評価になるのでしょう。

つまり、バリデーションにどのような効果があるかについて見解が分かれているわけではなく、どの特徴に着目するかによって、バリデーションとは何かという表現が変わっていることです。「バリデーションはセキュリティ対策か否か」という問題の答えは「セキュリティ対策とは何か」という定義次第で変わるため、私はこの「セキュリティ対策か否か」という議論には興味がありません。

バリデーションの結果何をするのか

次に、バリデーションの結果「基準(=仕様)を満たさない」入力をどう扱うかについて考えます。

id:ajiyoshiさんのエントリには、『それ以外の入力については、「郵便番号を入力してください」というメッセージを表示して再入力を促す』などと例示されているので、入力画面に戻って再入力させるということですね。これは(曖昧な用語を敢えて使いますが)正常系の流れの一部とみなすことができ、「セキュリティ対策なんてもんじゃないよ」というid:ajiyoshiさんの主張もうなずけます。

一方、大垣さんの主張はどうでしょうか。先のエントリを読んでもよく分からなかったので、大垣さんの本から拾ってみました。同書のP168〜P169には、入力値の確認方法の「よい」例として以下のスクリプトが紹介されています。

if (is_number($_GET['int'])) {
  $n = $_GET['int'];
} else {
  trigger_error('数値ではありません。$n=', $n);
}
if ($min >= $n && $n >= $max) {
  trigger_error('数値が範囲外です。$n=', $n);
}

これを見ると、バリデーションの結果仕様外と判定された入力については、trigger_error関数を呼んでエラーとしています。trigger_error関数は、ユーザ定義のエラーを発生させる関数です。このスクリプトの後に、以下の説明が続きます。

trigger_errorで登録されたユーザーエラーハンドラで、無効なリクエストのエラー情報、送信したIP、ブラウザ、時間などを記録し、必要であればメールで通知したりアクセスを禁止しセッションを破棄するなどの処理を行えば、ほとんどのサイトでは十分でしょう。

かなり物々しいことが書いてありますね。このようなアプリケーションを利用することは、かなりの緊張感を伴いそうです。この前のところには、「人の年齢の場合は-10才などという数値はないはずですし、普通は0〜130くらいまでで十分でしょう」とあります。この文の内容には同意ですが、trigger_errorの処理内容とあわせて考えると、年齢を31と入れようとして手が滑って311と入力した場合でも、セッションが破棄され(結果としてログアウトし)、アクセスを遮断され、(管理者に?)メールで通知されるのでしょうか。

同書のAPPENDIX.Cには、P237からエラーハンドラの実装例が出ています。これを読むと、メール通信やアクセスの遮断はしていませんが、セッション破棄のコードはあります。

if (empty($_SESSION)) {
    $_SESSION = array();
}

empty関数は、変数が空の場合に真を返します。空とは、空文字列、0、NULL、FALSE、空の配列などを指します。このサンプルはプログラムの最初の方でsession_start()を呼んでいますので、$_SESSIONの値はなんらかの配列のはずです。すなわち、上のスクリプトは、$_SESSIONが空配列の場合に、あらためて空配列を代入していることになります。しかし、これは恐らくバグで、$_SESSIONが空でない場合に空にしたいのでしょう*1。以下、私の推定が正しいと仮定して議論を進めます。

エラーハンドラは、セッション破棄の他に、スタックトレース、$_GET、$_POST、$_SESSION、$_SERVERの全ての値をログに生成しています*2

そして、エラーハンドラの最後にexitでアプリケーションを明示的に終了しています。その前には、「//すべてのエラーは致命的なエラーとして処理」とコメントがついています。

これは中々タフなユーザー体験です。年齢や郵便番号などをうっかり間違えただけで、ログアウトしてエラー表示されるわけですから。複数のエラーがある場合、表示されるのは最初の1つのみです。このようなアプリケーションを使うと、かなり「残念な」思いをするように思います。一方、「なるほど、『セキュリティ対策』とはこれを指していたのか」という異様な説得力があります。

しかし、このような「セキュリティ対策」は本当に「世界の常識」なのでしょうか。Googleも、Facebookも、Amazonも「不正な入力」に対してそのような挙動は示さないようです。

現実にはそこまで厳しくしなくても、アプリケーションの安全性は保てると思います。バリデーションの結果、仕様外の入力があった場合は、間違いの理由を明示して再入力を促すのがよいと思います。「そんな対応ではセキュリティ対策とは言えない」ということであれば、バリデーションはセキュリティ対策でなくて結構と思いますし、それで安全性が損なわれるとも思えません。

まとめ

「入力バリデーションはセキュリティ対策」かという命題について検討しました。バリデーションの基準については、アプリケーションの仕様と言うことで一致しているようですが、仕様外の入力があった場合の挙動については、大垣本の教えは独特であることがわかりました*3

私自身は、バリデーションは「セキュリティ対策」の一種ととらえてもよい(どうでもいい)と思いますが、仕様外の入力に際しては利用者に分かりやすいメッセージを表示して、再入力を促すのがよいと考えます。

蛇足

先に引用した数値検証のスクリプトにはバグがあります。

※ このスクリプトは「間違い探し用のコードが手違いで収録されていました」と指摘されていますので、以下はその間違い探しの答えに当たりますね。

これらのバグの結果、実行時に未定義関数のエラーになりますが、is_numberをis_numericに置き換えて実行すると、$nの値に関わらず常にチェックを通ることになります。「数値が範囲外です」というエラーメッセージが表示されることはありません。

このスクリプトに続くのは「よい文字列確認」と題されたスクリプトです。以下に引用します。

if (strlen($_GET['name']) > 20) {
  trigger_error('名前が長すぎます');
} else if (strlen($_GET['name']) <= 1) {
  trigger_error('名前が短すぎます');
} else if (strlen($_GET['name']) != strspn('abcdefghijklmnopqrstuvwxyz')) {
  trigger_error('名前には小文字のアルファベットのみが使用できます');
}

ここにstrspnという関数が出てきます。以下の仕様です。

int strspn ( string $subject , string $mask [, int $start [, int $length )

subject : 調べたい文字列。

mask : 許可する文字の一覧。

start : subject の中で調べ始める位置。

length : subject 内で調べる部分の長さ。

返り値 : subject の中で、全て mask の中の文字からなる最初のセグメントの長さを返します。

http://php.net/manual/ja/function.strspn.php

すなわち、第1引数の文字列の中から英小文字だけからなる部分を探しその長さを返すということなのですが、残念ながら第1引数('$_GET['name'])が抜けているので、実行時にエラーになります。これもバグですね。書きっぱなしで、テストはしなかったのでしょうね。

そもそも、strspnをバリデーションに用いるのはどうなのでしょうね。aからzを漏れなく入力しているか不安で仕方ありませんし、プログラムが読みにくく、なにか意図しない動作をしてしまいそうです。その懸念は、次のサンプルで現実のものとなります。

次のバリデーションサンプルは、入力文字列がSHA1ハッシュの要件(16進数40桁)を満たしていることを確認するものです。以下に主要部分のみ引用します。

// hex形式のsha1値は0-9, a-fまでの40文字
$error = (40 != strspn($str, '1234567890abcdef'));

40桁の16進数であることを確認したつもりなのでしょうが、このスクリプトだと、*先頭40文字が16進数* であることのチェックになります。要件を満たすには、文字列長が40であることも確認しなければなりません。

この結果、41文字目以降に攻撃文字列がある場合も、バリデーションをすり抜けます。以下に例を示します。

<?php
$str = "0123456789012345678901234567890123456789'or'a'='a";
$error = (40 != strspn($str, '1234567890abcdef'));
var_dump($error);
【実行結果】
bool(false)

$errorがfalse、すなわちエラーなしという結果になります。これはまずい。SQL呼び出し部分にSQLインジェクション脆弱性がある場合、任意のハッシュ値でチェック処理を通過できるなどの攻撃が考えられます。

脆弱性診断で上記が確認できた場合を考えましょう。SQLインジェクション脆弱性があればもちろん高危険度の脆弱性ですが、危険な脆弱性が発見されず、バリデーションの不備のみである場合、私なら低危険度、あるいは単なる指摘(Information)とします。

しかし、大垣さんのお考えですと、「入力バリデーションは非常に重要なセキュリティ対策の第一番目」ということですので、その「非常に重要なセキュリティ対策」に欠陥があるということは、上記は重大な脆弱性ということでしょうか。

この蛇足から導ける教訓は以下の通りです。

訂正(2011/12/26 8:36)

タイトルが「パリデーション」となっていたのでバリデーションに修正しました。本文も同様に2カ所修正しました。

[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

*1:私が同じことをしたい場合は、if文なしに問答無用で空配列を代入してしまうと思います。

*2:もっとも、$_SESSIONはログデータを作る前に破棄しているので、意味がないように思えます。

*3:但し5年前に発行された本ですので、大垣さんの現在のお考えは変わっているかもしれません。

*4:is_numberをGoogle検索すると、「次の検索結果を表示しています: is_numeric」と表示されます

コメント
2件
トラックバック
6件
ブックマーク
0 users

「徳丸本をブロガーに差し上げちゃうキャンペーン」当選者のお知らせ

徳丸本をブロガーに差し上げちゃうキャンペーン」ですが、先週末に選考を行い、当選者には個別に連絡させていただきました。当選表明のブログが出そろいましたので発表いたします。当選者は以下のブロガーの皆様です。

本日より順次書籍を発送致します。徳丸本は重い(約1kg)ので、3冊ずつ発送するつもりです。しばらくお待ち下さい。クリスマスには間に合うと思いますw

土日にいそいそと宛名書きをしていましたら、こんな指摘が

@ockeghem 今回のイベント、なんだかプレゼントの送り手が一番しあわせそうですね (^^)

https://twitter.com/#!/tt4cs/status/148325070501191680

おっと、これは図星でした。贈り物というのは、送り手が幸せになる為にするのですね。私の為に付き合って下さった皆様ありがとうございました。

選に漏れた方、ゴメンナサイ。徳丸の勘でテキトーに選んでおりますので、優劣を決めたものではないことを申し添えます。

それでは、当選者の皆様、感想のブログをお待ちしております。

読むのに時間が掛かると思いますので、焦って書く必要はありませんよ。

[PR]

安全なWebアプリケーションの作り方DRMフリーのPDFによる電子版もあります。

コメント
0件
トラックバック
2件
ブックマーク
0 users
ockeghem
ockeghem