![]() |
Winsock Programmer's FAQ |
![]() |
TCP/IP のデバッグWarren Young 著 (この文章は Winsock プログラマを念頭に書いてありますが、ここ での情報は Unix プログラマやネットワーク管理者、技術者に対しても 同様に通用するものです。) TCPは、「データを送る。それを配送する」というだけの、ある意味 単純なプロトコルです。TCPは品質状態が変化するネットワーク上で信 頼性を確保するために開発されたものなので、数多くの問題をエンドユー ザの手を煩わせることなく回避するようになっています。しかし、ある 意味この信頼性のおかげで、TCPはプロトコルを本当に理解していない 人をびっくりさせるような振舞いを示すことがあります。このチュート リアルではそれらの問題の最も重要な部分を紹介していきますが、しか しこれは氷山の一角に過ぎません。水面下に埋もれている部分について は TCP/IP Illustrated を参照して下さい。ちなみに以下で示している状態遷移図は、このシリー ズの第2巻から引用したものです。そのシリーズの第1巻にも Stevens の Unix Network Programming 第1巻 にも、同様に印刷されています。さらに、この図の Postscript 形式を Web 上で入手することもできます。この FAQ の その他の情報源 の章を参照して 下さい。 このチュートリアルの中では、「パケット」という用語を「データ グラム」の意味ではなく「フレーム」の意味で使っています。すなわち、 我々の意味でのパケットとは TCP フレームの中に包まれたデータの集 まりのことです。「ネットワーク」と呼ばれるぼんやりした雲のような ものは、TCPフレーム内のデータを複数のハードウェアフレームに分割 したり、複数のTCPフレームのデータを一つのTCPフレームに合体させた りすることがあります。しかしフレーム自身は機能的には無傷のまま残っ ています。これは「データグラム」と言う意味の「パケット」とは対照 的です。データの塊が送信者から受信者まで変化しない不可侵のブロッ クを意味するのが「データグラム」です。 TCP 制御ビットTCP実装が、データパケットを接続相手に送信しようとしたとき、ま ず最初に「ヘッダ」と呼ばれる20バイトのデータで送信データを包みま す。ヘッダはネットワークプロトコルにおいて必須のものであり、これ によってネットワーク上の関係者が、データをどのように流せばよいか を決定することができるのです。どんなプロトコルでも、送信データに はヘッダが(物によっては末尾にトレイラーも)付加されます。TCP およ び IP ヘッダの詳細については Richard W. Stevens 氏の本など良い本 がありますので、ここでは議論しません。 ヘッダの中に、私が「制御ビット」と呼んでいるフィールドがあり ます(他に良い用語が見当たらないので)。ここでの我々にとって重要な ビットは、SYN、ACK、FIN、RST と呼ばれています。これらはそれぞれ 「同期」(synchronize)、「確認」(acknowledge)、「終了」(finish)、 「中断」(reset)という意味です。TCPパケット中のこれらのビットは、 接続先相手のネットワークスタックだけのためにセットされます。つま り、普通の人々はこれらのビットの値を検査することはなく、機械的に 覆い隠されています。 状態遷移図以下に TCP プロトコルの状態遷移図を示します。状態は丸縁の箱で、 状態遷移はラベル付きの矢印で表されています。状態遷移は、あなたの プログラムがTCP の状態をどのように移動させるかを示しています。ま たプロトコルスタックの TCP 状態の変化が接続先の状態をどのように 変化させるかについてや、その状態の変化をアプリケーションレベルで どのようにして知ることができるかについても示してます。ちなみに状 態遷移のラベルは BSD ソケット関数の名前からつけられています。 Winsock API とは違いがありますが、その影響はこのレベルにおいては 同じです(図の文字の可読性がそこそこレベルなのはご容赦ください。 これでも既にサイズが 20K もあり、これ以上サイズを大きくしたくな かったのです。もっときれいで読みやすい図が欲しいときは、 Postscript ファイルを入手して印刷してください)。
この図を理解することは、TCPを理解する一つの重要な鍵ですので、
ちょっと練習問題をやってみましょう。ですがその前に、
Microsoft の ミニ FAQさて、先ほどお約束した練習問題です。
TCP屋さんのためのツール以下は私が "showwait" と呼んでいる、TCP状態の問題を扱うのに便 利な短いバッチファイルです。基本的にこれは、Ctrl-C を叩くまで、 現在の WAIT 状態を一秒ごとに表示するものです。私は Unix マシン上 でも同様なスクリプトを用意しています。 @echo off :loop netstat -na |grep WAIT delay 1 goto loop このスクリプトは "delay" と呼ばれる 4DOS の機能に依存していま す。もしこのシェルをお使いでなければ、同様のことを行う "sleep" コマンドの実装を入手してください。前述した Cygwin ツールセットに はこれも含まれています(もしかして、私のことを隠れUnix屋だと思い 始めてる? いやあ、そんなことないですよおおおだ B-> )。 このツールには一つ問題があります。このツールは名前の通り "WAIT" の問題しか捕らえることができません。LAST_ACK や SYN_RCVD といったあまり出てこない状態はこのスクリプトでは見えないのです。 特に SYN_RCVD は、この状態にある程度の時間留まっているということ は重大な問題の前兆を示しています。なぜならこれは、リモートマシン があなたのマシンに SYN パケットを送り、あなたのマシンがそれを ACK したのにも関わらず、リモートマシンがあなたの SYN/ACK を ACK できていない、という状態を示しているからです。通常この交換には数 十〜数百ミリ秒しかかからないので、SYN_RCVD が持続しているという ことは、ネットワークスタックの出来が悪いか、とても「よく落ちる」 コンピュータであることを示しています。もしこの状態が同時にたくさ ん現れているのであれば、「SYN 攻撃」を受けている可能性があります。 「SYN 攻撃」は最近広まってきた「サービス妨害攻撃」"Denial of Service" の一種です。ここまで来てしまったら、ネットワークスニファ を取り出して調査作業を開始すべき時でしょう。 まとめこの文章におけるテクニックと情報は、あなたの組織においても展 開すべき、基本的な知識ツールを反映しているものです。たとえこの教 材の内容を全てマスターさせる「ネットワークのプロ」をたった一人任 命するだけであっても、社内で他の開発者のための情報源となるでしょ う。この知識は非常に広い範囲で有益なものです。例えば、スニファの出力ダンプをあ まり苦しまず、かつより有用に読めるようになります。またこれらのテ クニックは、技術者と知識のあるユーザとが電話越しであっても、あな たのプログラムの問題点について情報を収集するために有効に適用する ことができます。そうでなければ「何かときどき問題が発生する」以上 の情報は収集できないでしょう。 私はあなたがこの記事から、TCP/IP のデバッグについて何かを掴ん でくれたと期待しています。もしこの記事の範囲に含めるべきことを何 か他に考えていただけるなら、ご提案していただけると、私はその追加 補足を真剣に検討します。 では、ハッピーハッキング! Copyright © 1998-2000 by Warren Young. All rights reserved. |
<< ザ・間違いリスト | Winsock と BSD ソケットとの互換性 >> |
Last modified: $Id: debugging-tcp.html,v 1.5 2002/11/09 20:40:32 ksk Exp $ | Go to the original FAQ page |
< Go to the main FAQ page | << Go to the Home Page |