[これはひどい]IEの引用符の解釈:教科書に載らないWebアプリケーションセキュリティ(1)(2/3 ページ)
XSSにCSRFにSQLインジェクションにディレクトリトラバーサル……Webアプリケーションのプログラマが知っておくべき脆弱性はいっぱいあります。そこで本連載では、そのようなメジャーなもの“以外”も掘り下げていきます(編集部)
IEに存在する“第3の引用符”
さて話は変わって、属性値をくくる引用符としてはダブルクオーテーション「"」、シングルクオーテーション「'」の2種類がありますが、実はIEの場合、バッククオーテーション「`」も属性値を囲む場合の引用記号として利用可能です。
属性値の値として「`」を含めたい場合には、「`」以外の引用符でくくってやるか、数値文字参照を使って表現する必要があります。
<input type=`text` value=`1234`> <input type=`text` value=``1234``>
これだけであれば、使える引用符が増えたというだけであり、冒頭で説明した2つの原則を守るだけで特に大きな問題はなさそうです。
何が問題なのか
単純に引用符が増えただけでは問題はないのですが、ここからがIEの残念なところです。バッククオーテーションは引用符としては限定的にしか働いていないため、状況によっては思いもよらない挙動をしてしまいます。
具体的には、JavaScriptからバッククオーテーションを含むinnerHTMLを取得したときに、引用符の整合性が崩れてしまうというバグがあるのです。言葉で説明するよりも動きを見ていただいた方が理解しやすいと思いますので、実際にinput要素のvalueの値をいろいろ変えて、そのときのinnerHTMLを見てみましょう。動作確認のためのサンプルは以下のとおりです。
<div id="div1"> <input type="text" value=" ここを適宜変化させる "> </div> <script> alert( document.getElementById( "div1" ).innerHTML ); </script>
3種類の引用符を含むいくつかのパターンを試行してみると、次のような結果となります。
valueの値 | innerHTML | |
---|---|---|
(1) | "1234"5678 | <INPUT value='"1234"5678'> |
(2) | '1234'5678 | <INPUT value="'1234'5678"> |
(3) | "1234'5678 | <INPUT value=""1234'5678"> |
(4) | "1234`5678 | <INPUT value='"1234`5678'> |
(5) | '1234`5678 | <INPUT value="'1234`5678"> |
(6) | "'1234`5678 | <INPUT value=""'1234`5678"> |
(7) | `1234`5678 | <INPUT value=`1234`5678> |
表1 3種類の引用符を組み合わせた場合の解釈 |
まずは上表(1)(2)(3)で、属性値にバッククオーテーションを含まない場合を見てみると、
- ダブルクオーテーションを含む場合には、シングルクオーテーションでくくる
- シングルクオーテーションを含む場合には、ダブルクオーテーションでくくる
- ダブルクオーテーション、シングルクオーテーションの両方を含む場合には、ダブルクオーテーションを"にエスケープしてダブルクオーテーションでくくる
という理にかなった動作になっていることが分かります。
次に(4)(5)(6)で、バッククオーテーションと、ダブルクオーテーションまたはシングルクオーテーションが含まれる場合を見てみましょう。この場合でも、属性値に含まれるダブルクオーテーションがエスケープされ、値そのものはダブルクオーテーションまたはシングルクオーテーションでくくられるという理にかなった動作になっています。
問題は(7)の、バッククオーテーションは含まれるがシングルクオーテーションおよびダブルクオーテーションが含まれない場合です。このとき、value属性の値は引用符でくくられていません。先に述べたように、IEではバッククオーテーションが引用符として使用できますので、このinnerHTMLを再利用した場合は、もともとのHTMLとは意味合いがまったく異なってしまいます。
<input type="text" value="`1234`5678"> …「`1234`5678」が属性値 <input type="text" value=`1234`5678>…「1234」が属性値
このように、バッククオーテーションは引用符として利用可能であるにもかかわらず、innerHTMLを取得する際には引用符として扱われていないという、なんともチグハグな状況があるということがお分かりいただけたと思います。
Copyright © ITmedia, Inc. All Rights Reserved.