• 締切済み

TCP/IPでのエラーシーケンス

TCP/IPで1台のサーバSから複数のコンピュータA,B,C...に データを送信している途中で、 Cがハングパップした時のエラーシーケンスを知りたいのですが。 例えば、 サーバSからA,B,Cに1つのデータを複数のパケットに分けて送信するときに、 送信途中でCがハングアップ(通信不能)した場合に、 サーバSがCにパケットを送信しなくなるのは、どのタイミングなのでしょうか? 例えば、5つ目のパケットで通信不能になった時は Cへのそれ以降のパケットを送信しないのでしょうか? 初歩できなことですが、お願いいたします。 ここら辺のことで、参考になる文献がある場合にも教えて頂きたく思います。

みんなの回答

  • kawausok
  • ベストアンサー率46% (13/28)
回答No.1

おっしゃっている「ハングアップ」とは、突然通信不能状態に陥るような事象を指していると仮定してですが・・ TCPプロトコルでは、データを送る場合、数個のデータ毎に送達確認を行います。簡単に言うと、「データを受け取ったよ」という「応答パケット」を返信します。 おっしゃっているように、通信相手が「ハングアップ」した状態になると、この「応答パケット」が帰ってこない状態になります。 応答がなくても、送信側はある程度データを送ることができます(これをウィンドウサイズといいます)。 ですので、相手側がハングアップしたからといって、サーバが直ちにパケット送信を止めるわけではありません。 # これで答えになっていますかね?? ご質問の例ですと、5個目でCが受信不能になっても、サーバー側は6個目、7個目・・・と送信します。送信ウィンドウサイズが一杯担った時点で、それ以上送信できなくなり、応答がくるまで待ち状態になります。 応答待ち時間はあらかじめ設定された値があり(通常は数分ぐらいだったかな??)その時間を過ぎても応答がなければ初めてリンクの障害とみなしてリンクを切断 という動作になります。 # 説明を簡単にするために、厳密に言うとすこし不正確な点もあるとおもいますが、イメージとしてはこのような感じですよ。

Fumizoh
質問者

お礼

有り難うございます。イメージすることができました。 「ハングアップ」は、予告なく通信不能状態になることです。 あと、このようにCが通信不能状態になった場合に、 サーバSのパフォーマンス(レスポンス?)が悪くなると聴いたのですが、 このようなことが起こるのでしょうか? 起こるとすれば、TCPが原因なのでしょうか? それより上のアプリケーションが原因なのでしょうか? 心当たりがあれば教えていただきたく思います。

関連するQ&A

  • IPヘッダの識別番号とTCPヘッダのシーケンス番号の違いってなんですか

    ネットワークの勉強を始めたばかりのものです。質問文に不可解な文章があるかもしれませんが、ご了承ください。 私の読んでいる参考書で、識別番号は「MTUによってデータを分割配送する際に使用する」と書いてあり、シーケンス番号は「ある程度データサイズが大きい場合、MMSによってデータを固定長に分割し、分割の組み立てに使用する」とありました。 つまり、送信側がMMSによってデータをA・B・Cの3つに分解し、Aを送信したところ、MTUがAのデータ量以下だったので、Aをパケットで分割して送信し、受信側で組み立てる・・・という見解で合っていますか? もし合っていた場合、「パケット1つが届いたよー」という確認応答は送信側に送られるのでしょうか?それとも確認応答はパケットの組み立てが終ってから送られるのでしょうか?

  • TCP/IP通信3ハンドシェイクについて

    TCP/IPのTCP通信の3ハンドシェイク通信に関して質問なのですが、インターネットを使ったある端末でセンターのサーバーと6秒に1度程度3ハンドシェイク通信を行ってインターネット回線が正常かどうかを判定する機能を持っているそうなのですが、その時に1回の通信でどの程度のパケットをやり取りしているのかということを質問してみたら、約1.2kbyte程度のパケットをやり取りしていると業者の方が言っていました。 ちょっと興味があってWireSharkでこの端末とサーバ間のパケット通信をのぞいてみたところ、端末が1.2kbyte送信していたのですが、サーバからのACKと思われるパケットが1.2kbyteのパケットを返してきていて、再度端末が60バイト程度のパケットをサーバのIPアドレスに送信していました。 私はてっきり、端末とサーバー間のこの3ウェイハンドシェイクのパケットの総量が1.2kbyteだと思っていたのですが、これだと1.2k + 1.2k + 60 = 2.46kbyteとなると思うのですが、パケットのやり取りとしては正しいのでしょうか? サーバー側が受信したら同じ容量の1.2kbyteのデータをACKとして返してきているように思うのですが、Wiresharkで見ても全く同じデータでは無いようでした。サーバはデータを受け取ったら、ちゃんと受信したという1 or 0のデータみたいなものを返せばよいだけだと思うのですが、理由はあるのでしょうか?

  • TCP/IPの仕組みと改良点。サイバー攻撃

    わたしは素人ですが、今のインターネットではサイバー攻撃と言って、ひとつのサーバーに多数がアクセスしてサーバーをダウンさせるということが行われています。 なぜこんなことが可能なのか、改善することは出来ないのかを素人ながら考えたので、詳しい方は是非ご意見をお聞かせください。 たとえば、P、Q二人のユーザーがサーバーSからデータを取っていたとします。 途中にはA、B、C、Dのルーターを経由してデータが送られるとします。 データのパスは、 P<-C<-B<-A<-S Q<-D<-B<-A<-S と流れるとします。つまり、サーバーSから、ルーターA,Bまでは同じパスを通りますが、Bからはデータは分岐して、PへはC経由、QへはD経由とします。 P,Qが全く同じデータをサーバーから取ってくる場合は、にもかかわらず、サーバーは2回アクセスされて、A,Bには全く同じデータが2回通ることになるのですよね。だから、ユーザー数が同時に何万とかになるとパンクすると認識しています。 ですが、Pが最初にサーバーにアクセスして、そのデータがルーターA,Bに残っていたら、QはデータをSまで取っていかずに、ルーターBに残っているデータを取ってきたらいいのではないですか。 中継ルーターに残る残存時間はサーバーSのデータを作る際に指定します。HPを作る際に指定します。 このデータはほとんど変更しないので60秒にしよう、とか、このデータはリアルタイムに変更されるから、0.1秒ごとの更新にしようとか。 で、中継ルーターにはこのルーター残存時間も送られるので、この時間内であれば中継ルーターにはこのデータは残っているので、ほかの人がアクセスした場合はサーバーSまでいかずに、中継ルーターからデータをとってきたらいい。 こうなっていると、多量にサーバーを攻撃しようとしても、中継ルーターでデータが返されるので攻撃できませんよね。 また、大阪の人1000人が東京のネットテレビを見ようとすると、東京ー大阪間のネットに1000人分の全く同じデータが流れますが、上記のようになっていると、東京ー大阪間にもデータが1人分づつしか流れないのでネットの使用効率が劇的に向上すると思うのですが、現在はそうはなっていないのですか。 ミラーサイトというのがあるのは知っていますが、これはリアルタイムに自動的にされるものではなく意図的に作られるものなので、これはちょっとはずして考えています。

  • TCP/IPお勉強中です

    TCP/IPのレイヤー2、3についての質問なのですが、 CISCOのCAT2900XLのL2スイッチが一台あって、それにPC-A、PC-Bの2台接続しています。 最初にAとBとL2スイッチを同一のネットワークアドレスに設定して、現在は通信できる状態になっています。 ただ、後になって疑問に思ったのですが、 1・L2スイッチはレイヤー2であって、パケットの送信をしているわけではないので、別にL2スイッチのIPアドレスは必要ない? 2・L2スイッチにIPアドレスを設定するのはL2スイッチ自体を調整するときの為? 3・L2スイッチにAとBを同一ネットワークアドレスにして接続して、 さらに、別のネットワークアドレスのCとDを接続したとき、 A-B,C-D間の通信は出来ますか? なんか本読んでいるとレイヤ2はMACアドレスで通信するからIPアドレスとか関係なさそうだと思ったのに、ネットワークアドレス違うと通信できないとか・・・ちょっと混乱してます。

  • TCP/IPでの通信の仕組み(パケット分割)について

    TCP/IPでのパケットの分割の仕組みで疑問に思ったことがあったので質問します。 本を見ると(日経NETWORK 新ネットワーク超入門より) TCPの役割:IP機能の負荷を減らすため、データが伝送途中で分割されないで送れる最大サイズになるように区切る。 ルータの役割:ルータ内のIP機能が、転送先の回線で決められたサイズに合わせて分割したりする。 と書いてあったのですが、 端末A -- ルータ1 -- ルータ2 -- サーバ (MTU:1500B) (1000B) (500B) (それぞれ、端末A ルータ1 MTU 1500B ルータ1 ルータ2 MTU 1000B ルータ2 サーバ MTU 500B と仮定) のようなトポロジを仮定した場合 端末Aがサーバと通信する場合はどのように通信が行なわれるのでしょうか?

  • TCP/IP ACKについて

    初めて質問させて頂きます。 現在WinpCapを使ってTCPの通信プログラムを作成しています。 単純にパケットの受信や送信は出来たので、ローカルサーバーに接続出来るか試しているのですが、通信が確立しません。 状況としては、こちらからSYN = 1でサーバーに信号を送ると、サーバーから返事が来ます。 サーバーの返事を待ってACK = 1でサーバーに返事をするのですが、そのときの状態をWiresharkで確認すると、ACKの番号が2067011292等と表示されて通信が確立しません。 ACKの値が異常なのは判りますが、この数値はどこから来るのか、又対処方法などが有りましたら教えてください。 環境はVC2003、WInXP/Win7です。

  • TCP/IPで同じパケットが2つ送信される。なぜ?

    Windows8 PC上のブラウザから、LAN上の機器(HTTPサーバ)にアクセスしようとしています。 Wiresharkでそのときの通信を覗いてみると、PCから送信されるパケットはなぜか2回同じものが短時間の間に連続して送信されているようです。その理由に心当たりがある方がいらっしゃいましたら、教えて下さいませんか? また、設定で回避できるのであれば、その設定項目などもわかるとありがたいです。 詳しい状況です。Wiresharkのキャプチャ画像と合わせて見て下さい。 *PC側IPは192.168.0.12、HTTPサーバは192.168.0.18です。 *Wiresharkでは、パケット6と7、9と11、10と12、14と15は内容的に同じパケットのようです(seqとackが同じ) *同じパケットのうち、前の方のパケットではIPパケットのチェックサムが0000hとなっているようです(チェックサムオフロード?)。後の方のパケットには、具体的なチェックサムの値が入っています。 *前のパケットが短い場合(54バイトとか)、後のパケットにはパディングとして00hが追加されて、60バイト長となるようです。それ以上の長さのパケットは、前述のチェックサム以外には違いは見られません。 *同じ2つのパケットは、極短い期間で連続して送信されているので、HTTPサーバからの応答タイムアウトで再送しているという風には思えないです。 *PC側のブラウザは、ChromeでもIEでも同じように2つの同じパケットが送信されていました。しかし、LANの外(ルーター外のインターネット)に接続するときは、このように2つの同じパケットはWiresharkで見ると出ていないようです。 *ちなみに、PC側のLANはRealtekのGigabit Ether(有線)です。 よろしくお願いいたします。

  • TCP通信のブロッキングについて

    初めて投稿させて頂きます。 javaでTCP接続での4人で遊ぶ大富豪を作っております。 サーバーを用意し、各ユーザーがサーバーに接続して遊ぶタイプです。 サーバーの構造は次のようになっております。 ・クライアントから接続を受け付ける待機クラス(Server.java)を常時走らせておく ・待機クラスに接続があれば、1ユーザーごとに送受信のスレッド(client.java)を立ち上げる。各ユーザーからのデータはこのクラスが受け取る ・人数が4人集まれば、テーブルスレッド(table.java)を立ち上げる。各ユーザーと接続されているclient.java(*4)がデータを受け取るとここが計算を行う 各ユーザーがサーバーに接続し、データのやり取りをするところまでは成功したのですが、以下の事について色々調べたのですが分からず、教えて頂けると幸いです。 (質問)ユーザーの接続が切断されたときのTCPの動作について 例えばABCDの4人のプレイヤーが居て、A→B→C→Dの順番だとします。今Aが◇3を切ったとします。するとAから「◇3を切った」というデータをサーバー(サーバーが発行したAとの送受信クラス)に送信し、サーバーが受信、それをABCD全員に送信して手番がBに移ります。この時、仮にCが切断されていてABCDにデータを送信したけどCだけデータが届かない、というケースの場合について、全員のデータの整合性を取るために「サーバーが、"Aが◇3を切った送信"に対するACKパケットを全ユーザーから受信したのを確認してから手番をBに移す」という手順を踏みたいのです。 各クライアントとの送受信のスレッドは余計なところは省略すると以下のようになっております。 class client implements Runnable{ (変数宣言) (コンストラクタ) public void run(){ while(true){ try{ ※(1) in.read(b); // inはSocket.getInputStreamの戻り値 (データを受け取ったことで色々な処理) out.write(b); // outはSocket.getOutputStreamの戻り値 out.flush(); ※(2) }catch(Exception e){} } } } Aと接続されているclientクラスのin.readで「◇3を切った」を受信し、色々な処理を行った後、ABCDと接続している各clientクラスのout.writeで「◇3を切った」を送信します。 ここで質問なのですが、接続が途切れているCの場合、out.write(b)の部分ACKパケットを受信するまで何度もリトライをすると思うのですが、プログラムの動作としてはリトライをしながらもout.write(b)以下の処理に進んでしまうのでしょうか?それともACKを受信するまでここでプログラムはブロックされるorタイムアウト等が発生するまでリトライorサーバーが即切断を認識してExceptionに移行する のでしょうか?私の希望としては例えば上記プログラムの※(1)にf=false;(fはboolean)、※(2)にf=trueなどを置いて「全スレッドのf==trueになれば、次の作業をしてもOK」という風に出来ればプログラム的に楽なのですが、接続が途切れているプレイヤーCのスレッドはout.writeの結果に関わらず(リトライされようが)下の命令を実行してしまうのでしょうか?「ACKパケットを受け取ったか否か」を判断したいのですが、プログラムの動作としては パケットを受け取った/受け取ってない で、どのように差が出るのでしょうか。また、out.writeの内容に関わらずプログラム処理が進んでしまう場合、どのようなプログラムが最適でしょうか。 このサンプルの場合だと、Cとの接続クラスはin.readのところで確実にブロックされますが、もしout.writeでブロックされなければACDのプログラムはBを放っておいてどんどん先に進んでしまい、データの整合性が怪しくなってきます。 詳しい方居られましたらお教え頂ければ幸いです。

  • TCP/IPで受信エラー

    自作Linuxマシン:クライアント、Windows:サーバの組み合わせで、TCP/IPによる大量受信をすると1000回に1回程度 "could not read received packet length error=7"というエラーがでます。実際に受信内容が化けていることも正常なこともあります。 受信側: Linux-2.6.18-at9 Debian。PowerPc 300MHz 100Base 送信側: Vista Ultimate Core-duo 1.2GHz です。 このエラーはGrepした結果、/drivers/net/temac/adaptor.cというデバイスドライバのFifoReceiveHandlerというモジュールが発しているらしいことが分かりました。 受信側プログラム: void* tcpReceiveThread(void* pParam) という受信専用のスレッドを設け、 while(1){ rcvSize = recv(socket, buf, 1024*9, 0); // Blocking Mode  ・・・・データ処理 } で常時待ちます。 Windows側には別のprocess側チャネルで送信要求をだします。 送信側プログラム:  int ok = send(socket_h, buf, 1024*9, 0); これを1回の送信要求に対し2回続けて実行します。 Windows側は同じPortNoでacceptしてあります。 不具合の推定原因: 1.受信側データ処理が重く、2回目の送信データが処理しきれていない。データ処理は1ms程度 2.受信process側の処理が重く、受信スレッドにリソースが回らない。 3.一回の送受信データ1024*9バイトが大きすぎる。あるいは必要な設定を行っていない。 などが考えられます。実行の時間的制約が厳し過ぎるのかもしれません: 受信側マシン全体で13msの間にコアジョブ3msと2個以上のpacket(1024*9)を受信しなければなりません。 ご示唆願えることがあればお願いいたします。

  • TCP/IPのデータ送受信の"確実性"はどの程度??

    Winsock2を使ってソケットプログラミングをするため通信プロトコルを考えています。そこでソケットの挙動について疑問があります。 sendを複数回使って以下のバイト数のデータを送信したとします。 1.3byte送信[AAA] 2.5byte送信[BBBBB] 3.3byte送信[CCC] このとき正常に通信ができたときは受信側では1~3回のrecvによって [AAABBBBBCCC] というデータが受信できると思います。ここまではいいのですが、疑問があるのは送受信に異常があった場合です。 1.send単位で欠落(再度connectの必要なし)。損失受信データ例[AAACCC]、[BBBBBCCC] 2.TCP上での送信パケット単位で欠落(再度connectの必要なし)。損失データ例[AAABB] 3.send単位で欠落して以後は全て欠落(再度connect必要あり)。損失データ例[AAABBBBB]、[AAA] 4.TCPのパケット単位で欠落して以後は全て欠落(再度connect必要あり)。損失データ例[AAABB] おそらくこれらのいずれかの方法でデータが欠落することになるかと思います。データの再送信をするのであればconnectが必要になるのかという点も分かりません。 ソケットがcloseになったという理由によるデータ欠落であれば4番になるかと思いますが。。。@FreeDのようにドーマントに入るようなネットワークの場合単純にcloseを期待することもできないような気がしますし。。。 どなたか教えていただけないでしょうか?よろしくお願いします。