今回から5回にわたって,アプリケーション全体に関する文字コードの問題と対策について説明する。文字コードがセキュリティとどう関わるのか,疑問に思うかもしれないが,Webアプリケーションで文字コードを指定可能な個所は非常に多く,しかも文字コードの選定や処理方法次第ではぜい弱性の原因になることが分かってきている(図1)。実は文字コードはWebアプリケーションのセキュリティ問題の最新の話題と言ってよい。

図1●Webアプリケーションにおいて文字コードを指定可能な個所

 2008年10月に開催されたセキュリティ・イベントBlack Hat Japan 2008では,ネットエージェントの長谷川陽介氏が「趣味と実益の文字コード攻撃」と題して,文字コード問題の広範なプレゼンテーションを発表した 。そのプレゼンテーション資料が発表されている のでこの問題の詳細に関心のある方は参照されたい。ここでは,セキュアなWebアプリケーションを開発するために文字コードの問題をどのようにとらえればよいかを体系的に解説する。

 文字コードの問題は大別すると2種類に分けられる。文字集合(character set)の問題と文字エンコーディング(文字符号化方式,character encoding scheme)の問題だ。まずは,これらの用語の説明から始めよう。

■ 文字集合とは
 文字集合とは,コンピュータ上で扱うことのできる文字を集めたものだ。代表的なのが英語圏で利用されてきたASCII(US-ASCII)がで,7ビットのコードですべての文字を表現する。これを8ビットに拡張して,カタカナや円記号などを扱えるようにしたのがJIS X 0201,西欧で使う文字や記号を扱えるようにしたのがISO-8859-1である。これらの包含関係を図2に示す。

図2●1バイト文字集合の包含関係

 漢字を含めた日本語を使うための文字集合としては,JIS X 0208や,その拡張版であるJIS X 0213があり,広く利用されている。これらの文字集合は2バイトでコード化されており,いわゆる「全角文字」が規定されている。

 これらは通常,単独で使われることはなく,JIS X 0201とJIS X 0208というように組み合わせて英語と日本語の両方に対応できるようにする。さらに,OSのベンダーによって独自に拡張されている場合が多い。マイクロソフトはWindows 3.1日本語版で「マイクロソフト標準キャラクタセット」を策定した。これは,JIS X 0201とJIS X 0208の組み合わせに,NECと日本IBMの文字集合拡張を取り込んだもので,現在最も広く使われている文字集合の一つだ。

 一方,各国固有の文字集合がばらばらに存在していたのではソフトウエアの国際化やローカライズが煩雑になる。このため,世界共通の文字集合を定義したいという機運が高まり,米国企業を中心にしたグループがUnicodeを提唱した。Unicodeでは文字を区別する抽象的なコードとしてコードポイントという整数値を使う。Unicodeのコードポイントは元々16ビットで規定されていたが,これでは世界中のすべての文字を規定するのに不十分だったため,現在では21ビットに拡張されている。元の16ビットで記述できる文字の範囲をBMP(Basic Multilingual Plane; 基本多言語面)と呼ぶ。コードポイントを記述する場合は,U+XXXX(XXXXは4桁から6桁の16進数)という形式を使う。

 現在のUnicode5.1は,前述のUS-ASCIIやISO-8859-1,JIS X 0201,JIS X 0208,JIS X 0213などをすべて包含している。これらの包含関係を図3に示した。

図3●マルチバイト文字集合の包含関係

 文字集合間では,同じコードに異なる文字が割り当てられている場合がある。代表的な個所が0x5Cで,ASCIIでは「\」(バックスラッシュ)が当てはめられているのに対して,JIS X 0201では「\」(円記号)が当てられている。さらに,ISO-8859-1およびUnicodeでは0x5Cはバックスラッシュだが,これとは別に0xA5に「\」が当てられている(表1)。こうしたコードの重複は混乱を招きやすく,ぜい弱性の原因にもなる。

表1●マルチバイト文字のコード割り当ての違い
(*1) US-ASCIIは7ビットのコードなので,最上位ビットを無視する結果,0x25すなわち「%」として扱われる
(*2) 中黒(なかぐろ)