XSS(クロスサイトスクリプティング)とは、webサイトのフォームなどによる入力に関して、その文字列の出力時に特定の文字(>, <, “, ‘, &, など、HTML構文に悪影響を及ぼしそうな文字)が含まれている際に起きる問題のことです。
PHPでは、特定の文字をエスケープ処理する関数として「htmlspecialchars」と「htmlentities」が用意されています。
この2つはほとんど同じ動作をする関数なのですが、「htmlentities」のほうがエスケープしてくれる文字の種類が圧倒的に多い、という違いがあります。
ただ、普通のwebページでは「htmlspecialchars」でも特に問題はないかと思います。
実際の使い方としては、
1 2 3 4 5 6 | <?PHP ・・・ echo htmlentities($str, ENT_QUOTES, "UTF-8"); ・・・ |
と書けば、危険な文字をエスケープしてくれます。
★注意したい点★
第2引数と第3引数はオプションなのですが、指定しないと問題を引き起こしかねません。
指定しないと、デフォルトの「ENT_COMPAT」が使われますが、これはダブルクォートは処理してくれますが、シングルクォートは処理してくれません。
もし、HTMLタグの要素などをシングルクォートで囲んでいるなら問題があります。
PHP
1 2 3 4 5 6 7 8 9 | ・・・ <?php $str = "tmp_value"; ?> <input type='text' name='sample' value='<?php echo htmlentities($str)?>' /> ・・・ |
もし、$strがシングルクォートを含む文字列だった場合、不正な処理が行われたりjavaScriptが実行されたりしてしまいます!
例
1 2 3 4 5 6 7 8 9 | ・・・ <?php $str = "tmp_value' onMouseover='alert("XSS")"; ?> <input type='text' name='sample' value='<?php echo htmlentities($str)?>' /> ・・・ |
ですから、第2引数には忘れずに「ENT_QUOTES」を指定するようにしましょう。
これはエスケープ処理に使用されるエンコーディングを指定する引数です。
XSS対策とは少し関係ないところの問題ですが、PHP5.4.0 以前では「ISO-8859-1」がデフォルト値だったのですが、PHP5.4.0 以降では「UTF-8」がデフォルト値になっています。
この点を留意しておかないと問題が発生する可能性がありますので、やはり第3引数も忘れずに指定しておくほうが良いと思います。
南本貴之