本稿は『日経オープンシステム 2001年5月(no. 98)』に掲載された記事「オープンセミナー 実践!セキュアなWebプログラミング 第2回 ASP(Active Server Pages)編 Part1」をHTML化したものです。内容は雑誌掲載時とほぼ同じですが,誤記訂正や小さな改善を施してあります。(2001年9月)



セキュアWebプログラミング

ASP(Active Server Pages)編 Part 1

佐名木智貴 著
元セントラル・コンピュータ・サービス株式会社 インターネットビジネス部
セキュリティ担当エンジニア




Webアプリケーションで入出力データのチェックに漏れがあると,クラッカにCookieを入手されてユーザーになりすまされる,送りつけられたSQLやコマンドを実行させられる,公開していないはずのファイルを読まれるなどのセキュリティ・ホールができてしまう。データは必ずチェックし,危険な特殊文字を排除あるいは無効化する必要がある。クライアントでのチェックは容易にう回されてしまうので,サーバー側でチェックしなければならない。



 本稿は,Webアプリケーションにセキュリティ・ホールを作らないためのプログラミングの解説である。ここでは題材として,Internet Information Server(IIS)上のActive Server Pages(ASP)*0のプログラミングをとりあげている。
 記事はPart 1とPart 2の2つに分かれており,今回のPart 1では,データの入出力に関連する問題と,その対策を紹介する。


*0
【ASP】Active Server Pages
MicrosoftのWWWサーバーであるInternet Information Serverが備える,サーバー上でスクリプトを実行する機能。HTML中にスクリプトを埋め込んだASPファイルにWWWブラウザがアクセスすると,スクリプトが実行され,実行結果がWWWブラウザに出力される。スクリプトとしてVBScriptなどが実行できる。





データのチェック漏れをふさぎDBMSやOS,ファイルを守る
 入出力データのチェックに漏れがあると,Webアプリケーションがユーザーの個人情報を漏えいする,他人に別のユーザーになりすまされる,送りつけられたSQLやコマンドを実行してしまう,公開していないはずのファイルを読まれるなどのセキュリティ・ホールができてしまう。
 データは必ずチェックし,不正なデータを排除あるいは無効化しよう。チェック漏れが発生しないようにするためには,入出力にあたってはチェック処理を組み込んだ関数を定義し,必ずそれを使うようにすべきである。また,IISがWebアプリケーションへデータを渡す際に検査して,不正な文字を置換あるいは排除する方法もある*1
 以下,危険なWebアプリケーションと対策を実際のコードを挙げて説明していく。本記事で紹介したプログラムのソース・コードは,日経オープンシステムのホームページ*2からダウンロードできる。


*1
IISからWebアプリケーションへの入力をフィルタするためのツールとしては,NTTデータCCSが無償公開しているguard3.dllがある。詳しくは後述する。

*2
http://itpro.nikkeibp.co.jp/NOS/










クラッカの不正なスクリプトを
ユーザーに送信してしまう
 入出力データのチェック漏れによる問題の代表的なものに,クロスサイト・スクリプティングという攻撃方法がある*3
 復習を兼ねて,その危険と対策を整理しておこう。問題は,「入力されたデータ○○は不正です」といったエラー表示や,「入力データは○○でよろしいですか」という確認など,外部からの入力データをそのままWWW画面に表示するようなWebアプリケーションで起こる。クラッカがデータとして不正なスクリプトを入力すると,それをユーザーに実行させてしまうのである。
 具体的な攻撃方法を図1に示す。まず,ユーザーがクラッカのWWWサイトにアクセスした場合,クラッカは標的サイトとなるWebアプリケーションに,ユーザーからのアクセスをリダイレクトする。リダイレクトの時に,クラッカが作成したスクリプトも入力データとして送信する。これにより,その入力データとして送ったスクリプトをユーザーのWWWブラウザで実行してしまう。スクリプトは標的サイトから発行したものとして実行されるため,標的サイトが発行したCookie情報をクラッカに送信するスクリプトなども実行可能になる。
 電子掲示板やチャットのように,ユーザーの入力をWWWページに表示する場合は,書き込みにスクリプトを仕込んでおけば,読みに来たユーザーはそのスクリプトを実行してしまう。
 Cookieでユーザーを認証しているWebアプリケーションでは,クラッカがそのCookie情報を使ってユーザーになりすまし,クレジット・カード番号など個人情報を盗み見たり,不正に操作してしまう可能性がある。


図1●クロスサイト・スクリプティングによる情報の漏えい
エラー表示や入力の確認など,外部からの入力データをそのままWWW画面に表示するようなWebアプリケーションは,クラッカが流し込むスクリプトをユーザーに送って実行させてしまう。例えばクラッカにCookie情報を送るスクリプトなどを実行される。Cookieでユーザーを認証しているWebアプリケーションでは,クラッカがそのCookie情報を使ってユーザーになりすまし,クレジット・カード番号など個人情報を盗み見たり,不正に操作してしまう可能性がある。
( 拡大表示 )

*3
マイクロソフトの技術情報「クロスサイト スクリプティングのセキュリティ上のぜい弱性に関する情報」(http://www.microsoft.com/japan/technet/security/crssite.asp)を参照。NTTデータCCSの「セキュリティ関連情報」(http://www.trusnet.com/secinfo.html)では後述のJetエンジン問題なども掲載している。





IISにクロスサイト・スクリプティングの弱点
 注意すべきなのは,クロスサイト・スクリプティングは,Webアプリケーションでの対策だけでは防げないということだ。WWWサーバーであるIIS4.0およびIIS5.0にも,クロスサイト・スクリプティングを実行されてしまうセキュリティ・ホールが指摘されている*4
 IISなどのWWWサーバーの多くは,SSI(Server Side Include)という機能を備えている。WWWサーバーがHTMLを送り出す際に,HTMLファイル中に指定されているファイルを読み込み,挿入して送出する機能だ。通常,ファイル名の拡張子がshtmlである場合,IISはこのSSI処理を行ってから送出する。問題は,WWWブラウザなどからリクエストされたファイル名が存在しなかった時の処理にある。「ファイルが存在しない」というエラー・メッセージを表示する際に,ユーザーが指定したファイル名をそのまま表示してしまうのである。この時,ファイル名の中にスクリプトが書かれていると,IISはWWWブラウザにスクリプトを送出してしまう(図2)。
 拡張子idcのファイル,インターネット・データベース・コネクタ・ファイルがリクエストされた場合にも,同じ現象が発生する。
 すでに修正ファイルが提供されているので,これを適用する。これらはプログラミングの問題ではない。当たり前のことだが,OSや基本ソフトウェアのセキュリティ・ホールをふさがなければ,セキュリティは守れない。


図2●IIS本体に対するクロスサイト・スクリプティング
IIS 5.0およびIIS 4.0などでは,SSIのエラー・メッセージとしてリクエストされたファイル名をそのまま出力する。そのためファイル名にスクリプトを含めることでクロスサイト・スクリプティングにより攻撃されてしまう。



*4
マイクロソフト技術情報「『IISクロスサイトスクリプティング』に対するぜい弱性を解決する修正プログラム(MS00-060)」(http://www.microsoft.com/japan/technet/security/prekb.asp?sec_cd=MS00-060),「IIS 5.0クロスサイトスクリプティング問題の修正プログラム(JP275657)」(http://www.microsoft.com/JAPAN/support/kb/articles/JP275/6/57.HTM)を参照のこと。





対策となる処理を関数化して組み込む
 Webアプリケーションに対するクロスサイト・スクリプティングを防ぐためには,入力データ中のHTMLタグを無効にする。VBScriptにはServer.HTMLEncode()というメソッドがあるので,これを使い,HTMLのタグを示す記号「<」「>」をそれぞれ「&lt;」「&gt;」に変換する(図3*5。WWWブラウザ上では「&lt;」「&gt;」は「<」「>」と表示され,HTMLタグとは解釈されなくなる。
 しかし,Webアプリケーションの開発・改良は日々発生しており,改良するたびに見落としが発生する可能性がある。見落としや漏れを防ぐために,データの入出力にあたっては,チェックしてから入出力を行う処理を関数化し,Response.Writeの代わりに使用するようにする(図4)。
 また,フォームやクエリー文字列,Cookieのデータは直接使わず,一度セッション変数に落としてチェックを行ってから利用する。
 なお,Server.HTMLEncode()ではすべてのタグを禁止することになる。電子掲示板などで,ユーザーがHTMLタグを書き込みたいという場合にはこの方法は使えない。その場合は個々のタグを示す文字列を禁止することになるが,危険なタグをすべてリスト・アップすることは困難であり,セキュリティ・レベルが低下する恐れもある*6


図3●クロスサイト・スクリプティングへの対策
スクリプトを示すHTMLタグを無効にする。ASPではServer.HTMLEncode()というメソッドで,タグを示す記号である「<」「>」を無効化できる。



図4●クロスサイト・スクリプティングを防ぐためのコーディング標準化
見落としや漏れを防ぐために,データの入出力にあたっては,チェックを実行してから入出力を行う処理を関数化したものを呼び出す。入出力関数を直接呼び出さないようにする
(1) データをWWWブラウザに出力する時,すなわちResponse.Writeするときは,必ずServer.HTMLEncode()をかける。その処理をモジュール化しておき,表示するときは必ずそれを呼び出す
 
HTMLタグを無効化してから出力するサブルーチンHTMLoutputの定義
Sub HTMLoutput(str)
    Response.Write(Server.HTMLEncode(str))
End Sub
 
 
(2) フォームや,クエリー文字列,Cookieのデータは直接使わずに,一度セッション変数に落としてHTMLタグを無効化してから使用する
 
コーディング例
Option Explicit
Dim i
For Each i In Request.Form
    Session(i) = Server.HTMLEncode(Request.Form(i))
Next
 
 
(3) さらに厳重を期す場合,フォーム,Cookie,クエリー文字列,環境変数のすべてについてHTMLタグを無効化する
 
コーディング例
Option Explicit
Dim i
For Each i In Request.Form
    Session("F" & i) = Server.HTMLEncode(Request.Form(i))
Next
For Each i In Request.Cookies
    Session("C" & i) = Server.HTMLEncode(Request.Cookies(i))
Next
For Each i In Request.QueryString
    Session("Q" & i) = Server.HTMLEncode(Request.QueryString(i))
Next
For Each i In Request.ServerVariables
    Session("S" & i) = Server.HTMLEncode(Request.ServerVariables(i))
Next


*5
IIS 3.0では,Server.HTMLEncode()により文字化けが生じることがある。「[IIS]Server.HTMLEncode処理で日本語の文字化けが発生(J041066)」(http://www.microsoft.com/japan/support/kb/articles/j041/0/66.htm)を参照されたい。


*6
最低限禁止すべきタグを以下に示す。これ以外にも危険なタグがある可能性があるので,以下のリストは参考程度にとどめてほしい。
(1)スクリプトなどプログラムを起動するタグ
   script,object,applet,img,image
(2)HTMLヘッダー関連のタグ
   html,head,meta,base,body
(3)フレームなど別のファイルを呼び出せるもの
   frame,frameset,iframe,fieldset,legend,link,style
(4)フォームなどユーザーがデータを入力できるもの
   form,isindex,input,button,textarea,select,option,optgroup
(5)サウンドや動画など
   embed,bgsound







TRUSNETトップセキュリティ関連情報 目次

Copyright (C) 2001-2008 NTT DATA CCS CORPORATION