ARPのメカニズム

 EthernetとTCP/IPの間で,アドレス解決を行うプロトコルにARP(Address Resolution Protocol)がある。このプロトコルは,IPアドレスから該当するノードのMACアドレスを調べるために用いるプロトコルである。企業内ネットワークのようにEthernet+TCP/IPのネットワークで,常に使われているものだ(ARPプロトコルの詳細はRFC0826を参照してほしい)。

 ご存知のように,TCP/IPではIPアドレスに基づいてすべてのデータ通信が行われている。例えば,メールの送受信,WebアクセスもすべてIPアドレスで表したアドレスを基に行われている。

 しかし,実際の物理的なネットワークはEthernetである。EthernetはIPアドレスがわからない。Ethernet上は,MACアドレスに従って実際のパケットは送受信される。例えば,IPアドレスが「192.168.1.1」のノードAが,IPアドレスが「192.168.1.10」のノードBにパケットを送信したい場合には,IPアドレス「192.168.1.10」のノードが持つNICのMACアドレスを知る必要がある。ARPパケットは,この解決に使われる。

図4 ARPのメカニズム。ARPはIPアドレスとMACアドレスの対応を調べるために使う
 ARPパケットによるアドレス解決は,次のように行われる(図4[拡大表示])。

(1)リクエストするIPアドレスを「192.168.1.10」に設定したARPリクエスト・パケットを生成。

(2)そのARPリクエスト・パケットのあて先MACアドレスをブロードキャスト(FF-FF-FF-FF-FF-FF)としてネットワーク上に送信。

(3)このブロードキャスト・パケットをLAN上のすべてのノードが受信。

(4)このパケットを受信した各ノードは,リクエストIPアドレスが自分のIPアドレスと一致するかをテスト。

(5)リクエストIPアドレスが,自分のIPアドレスと一致していなければ,このパケットを破棄。

(6)リクエストIPアドレスが,自分のIPアドレスと一致すれば,ARPリプライ・パケットを生成し,自身のMACアドレスを書き加えて,リクエスト元ホストのMACアドレスあてに返信。

(7)ARPリプライ・パケットを受信したリクエスト元ホストは,IPパケットを送信するノードのMACアドレスを取得し,パケットの送信処理を行う。

 このARPリクエスト・パケットは,前述の会議室の盗聴の例における「Aさんはいらっしゃいますか」という呼びかけに似ていて,プロミスキャス検出のパケットとして使えそうである。

プロミスキャス検出の実験

 プロミスキャス・ノードを発見するには,盗聴していなければ受け取らないはずのパケットで,かつ受け取ると自動的に応答するパケットを見つけなければならない。ARPパケットは,このパケットに該当する可能性の高いパケットだが,通常のARPパケットはブロードキャスト・アドレスあてで送信され,盗聴していないノードも受信してしまう。このため,このARPパケットのあて先アドレスに細工を施す必要がある。

図5 プロミスキャス・ノードを検出するための実験。ARPリクエスト・パケットをブロードキャスト・アドレスではなく,特定のアドレスあてで送信してみた
 図5[拡大表示]のように,192.168.1.10のMACアドレスを調べるためのARPリクエスト・パケットを,ブロードキャスト・アドレス(FF-FF-FF-FF-FF-FF)あてではなく,他のホストあて(ここでは00-00-00-00-00-01)に送信したらどうなるだろうか。NICがノーマル・モードならば,自分あて,ブロードキャスト,マルチキャスト・グループ1あて以外のパケットは,NICがフィルタリングする。このため,192.168.1.10のノードを調べるためのこのARPリクエスト・パケットは受信しない。結果として,ノーマル・モードのノードは,このARPリクエストに対して応答しないだろう。

 NICがプロミスキャス・モードになっていた場合(ネットワーク盗聴をしているノードの場合)には,他のホストあてのパケット(00-00-00-00-00-01)も受け取るはずである。これは,本来受信しないはずのパケットを受信したために返事をしてしまうという,前述の会議室の例に似た原理である。

 しかし,この方法では盗聴ノードは返事をしてくれない。NICがプロミスキャス・モードならば,ARPリクエスト・パケットは確実にOSに渡っているはずだが,応答は得られないのだ。これは,OSの中にもソフトウェアによるフィルタが存在していることを表している。

図6 Linuxのソース・コードの一部。ARPパケットを判断する個所を示す
 Linuxのソース・コードで,ソフトウェアによるフィルタリングを調べてみると図6[拡大表示]のようになっている。ARPのモジュールには,いくつかのフィルタリング・ルールが書かれているが,図6の(1)と(2)にあるように,パケット・タイプとして「PACKET_OTHERHOST」と「PACKET_LOOPBACK」の時にARPモジュールが応答しないようにプログラムされている。すなわち,自分あて,ブロードキャスト,マルチキャストのパケットには応答すると読み取れる。

 この方法によってプロミスキャス検出を考える場合,もう一つの重要なポイントがある。それは,自分あて/ブロードキャスト/マルチキャストとは何かということだ。これは規格や仕様の話ではなく,実際にどのように判定されているかということが重要になる。具体的には,(1)Ethernetの仕様上のマルチキャストとブロードキャスト,(2)NICのフィルタにおけるマルチキャストとブロードキャスト,(3)OSにおけるマルチキャストとブロードキャスト,の三つの違いを知る必要がある。

図7 NICとソフトウェア(OS)のARPパケットの解釈の違いから,プロミスキャス・ノードを見つける。例えば,偽のブロードキャスト・アドレス(FF:FF:00:00:00:00)あてにARPパケットを送信すると,盗聴ノードが返答するかもしれない
 この中で,特にOSにおけるマルチキャストとブロードキャストの判定に注目したい。なぜなら,ソフトウェアではこれらの判定を簡略化している可能性があるからだ。例えば,ブロードキャストを判定する場合に,正確には「FF-FF-FF-FF-FF-FF」の6バイトを比較しなければならないが,1バイト(最初のFFだけ)や1ワード(最初のFF-FF)だけで判定している可能性もあるだろう。また,マルチキャストの判定もグループ・ビット(01-xx...)だけで判定していたり,3バイト(01-00-5E-)だけで判定する可能性もある。もし,これらのソフトウェアの判定方法がNICでの判定方法と異なっていた場合,この違いを利用してプロミスキャス・モードを検出できる可能性が生じるのだ(図7[拡大表示])。

 Linuxのソース・コードを読むと,ARPモジュールは自分あて,ブロードキャストあて,マルチキャストあてのARPリクエスト・パケットが,自分のIPアドレスをリクエストしている場合に応答することになっている。NICがマルチキャストやブロードキャストとは判断せず,しかしソフトウェアがブロードキャストやマルチキャストだと判断するようなアドレスが存在すれば,プロミスキャス・モードだけから応答が得られる。このようなARPパケットを見つければ,盗聴ノードを判定できる。例えば,ソフトウェアが「FF-FF-xx-xx-xx-xx」のように先頭の2バイトだけでブロードキャストを判定しているとすると,「FF-FF-xx-xx-xx-xx」のようなアドレスにプロミスキャス・モードのPCだけが応答してしまうはずである。

表2 プロミスキャス・ノードを見つける実験に使ったテスト・パケット
表3 表2のテスト・パケットを使った実験の結果。「×」は応答がなかったことを示す
 そこで,ブロードキャスト・アドレスやマルチキャスト・アドレスを変形したプログラム上誤判定しそうなアドレスを使って,プロミスキャス・ノード発見の実験を行った(表2[拡大表示])。その結果が表3[拡大表示]である。

WindowsとLinuxでの実験結果

 表3にあるように,Windows 9xシリーズは最初の1バイトが「FF」のパケットに応答した。WindowsNT/2000は,最初の1ワードが「FF-FF」のパケットに,Linuxはグループ・ビットがセットされていればすべて応答した。

 これらは,ノーマル状態ではNICがフィルタリングしているアドレスである。プロミスキャス・モードの時だけNICを通過し,応答が得られる。すなわち,このパケットで盗聴ノードを発見できるのだ。

 以上のように,ARPリクエスト・パケットのあて先アドレスをプロミスキャス・モードのPCだけが応答するアドレスに変形し送信すれば,盗聴している疑いのあるノードを比較的簡単に検出できる。これが,「ARPパケットを用いたネットワーク盗聴ノードの検出原理」である。

Daiji Sanai
筆者は,ネットワークセキュリティ研究チーム「SecurityFriday.com」のリーダ。2001年7月に米国ラスベガスで開催された有名なセキュリティ技術カンファレンス「The Blackhat Briefings '01」において、「ARPパケットを用いたプロミスキャスノード検出技術」についての発表を行った。