TCP状态迁移图浅析(转载)

  

一.TCP简介
        TCP提供一种面向连接的,可靠的字节流服务。面对连接意味着两个使用TCP的应用,在彼此交换数据之前必须先建立一个连接。TCP通过以下方式提供可靠性:
     1. 应用数据被分割成TCP认为最适合发送的数据块,由TCP传递给IP的信息单位成为报文段。 
     2. 当TCP发出一个段后,它就启动一个定时器,等待目的端确认收到这个报文段。如果不能及时收到一个确认,将重发这个报文段。
     3. 当TCP收到TCP连接另一端的数据,它将发送一个确认。这个确认不是立即发送,而是延迟发送的。
     4. TCP将保持对它首部和数据的校验和,这是一个端到端的校验和,目的是检测数据在传输在传送过程中的任何变化。如果收到段得检验和有错误,TCP将丢弃这个报文段和不确认收到报文段。
     5. TCP将对收到的数据进行重新排序,将收到的数据以正确的方式交给应用层。
     6. TCP的接收端必须丢弃重复的数据
     7. TCP还能提供流量控制,TCP连接的每一方都有固定大小的缓冲空间。TCP的接收端只允许另一端发送接收端缓冲区所能接纳的数据。这将防止较快主机致使较慢主机的缓冲区溢出。

二. TCP状态迁移路线图

下面的文章按照client/server两条路线讲述TCP状态迁移路线图。

1. 连接建立

1) Client
当Client端调用socket函数调用时,相当于Client端产生了一个处于Closed状态的套接字。
Client端又调用connect函数调用,系统为Client随机分配一个端口,连同传入connect中的参数(Server的IP和端口),这就形成了一个连接四元组,connect调用让Client端的socket处于SYN_SENT状态
当Server返回确认,并发送SYN,Client返回确认及SYN后,套接字处于ESTABLISHED阶段,此时双方的连接已经可以进行读写操作

2)Server
当Server端调用socket函数调用时,相当于Server端产生了一个处于Closed状态的监听套接字
Server端调用bind操作,将监听套接字与指定的地址和端口关联,然后又调用listen函数,系统会为其分配未完成队列和完成队列,此时的监听套接字可以接受Client的连接,监听套接字状态处于LISTEN状态。
当Server端调用accept操作时,会从完成队列中取出一个已经完成的client连接,同时在server这段会产生一个会话套接字,用于和client端套接字的通信,这个会话套接字的状态是ESTABLISH。
 
   2. 连接关闭
与连接建立分为server/client不同,连接关闭并没有绝对的server/client之分,连接关闭分为主动关闭和被动关闭。Server和client都可以担任这两个角色中的任意一个。如client可以关闭它与server的连接,同样的server一样也可以关闭一些长时间无读写事件发生的连接。既然这么说了,下面就会分成两个部分:client主动关闭,server主动关闭。

Client主动关闭,Server被动关闭:
Client主动关闭,Server被动关闭的情况还是蛮多的,比如说短连接中,当一次会话结束时,client就可以关闭它与server之间的连接。我们这边直接说close而非shutdown。
当client想要关闭它与server之间的连接,首先client这边会首先调用close函数,client端会发送一个FIN到server端,client端处于FIN_WAIT1状态。当server端返回给client ACK后,client处于FIN_WAIT2状态,server处于CLOSE_WAIT状态。
当server端检测到client端的关闭操作(read返回为0),server端也需要调用close操作,server端会向client端发送一个FIN。此时server的状态为LAST_ACK,当client收到来自server的FIN后,client端的套接字处于TIME_WAIT状态,它会向server端再发送一个ack确认,此时server端收到ack确认后,此套接字处于CLOSED状态。

Server端主动关闭的流程与Client端关闭类似,就不再多讲,下面还需要关注的是TIME_WAIT这个状态,分别按照client/server两个部分讲述。
首先说一下TCP/IP详解中描述的关于TIME_WAIT的描述及其存在的必要性:
主动关闭的socket当收到对端的FIN操作后,该socket就会处于TIME_WAIT状态,处于TIME_WAIT状态的socket会存活2MSL(Max Segment Lifetime),之所以存活这么长时间是有理由的:
一方面是可靠的实现TCP全双工连接的终止,也就是当最后的ACK丢失后,被动关闭端会重发FIN,因此主动关闭端需要维持状态信息,以允许它重新发送最终的ACK。
另一方面TCP在2MSL等待期间,定义这个连接(4元组)不能再使用,任何迟到的报文都会丢弃。设想如果没有2MSL的限制,恰好新到的连接正好满足原先的4元组,这时候连接就可能接收到网络上的延迟报文就可能干扰最新建立的连接。
另一方面是为了重复的分节在网络中消逝。对于
另一方面是网络上仍然可能有残余的数据包
当Client主动关闭时,正常情况下client的socket会经历TIME_WAIT的状态

连接在关闭的时候,双方都会有状态的迁移,这就要求我们的程序中一定要有比较完全的

  3. Server端的监听套接字与会话套接字的不同:

当server端的socket调用bind和listen之后,监听套接字的状态就会变为LISTEN状态,监听套接字的工作决定了它只是监听连接。
当server端调用accept,相当于从套接字的完成队列中取出一个client的连接,此时可以确定四元组,即:client的IP和port;server的IP和port,双方各有一个套接字进行交互,这里需要说一下server端的socket,我称server端accept后产生的套接字为会话套接字,这个套接字一出生的状态就是ESTABLISH
由server端得四元组我们可以看出,一个server从理论上可以接收的连接数量取决于文件描述符的个数。

  4,状态为TIME_WAIT是不是所有执行主动关闭的socket都会进入TIME_WAIT状态呢?

有没有什么情况使主动关闭的socket直接进入CLOSED状态呢?

主动关闭的一方在发送最后一个 ack 后就会进入 TIME_WAIT 状态 停留2MSL(max segment lifetime)时间
这个是TCP/IP必不可少的,也就是“解决”不了的。

也就是TCP/IP设计者本来是这么设计的
主要有两个原因
1。防止上一次连接中的包,迷路后重新出现,影响新连接
                  (经过2MSL,上一次连接中所有的重复包都会消失)
2。可靠的关闭TCP连接
   在主动关闭方发送的最后一个 ack(fin) ,有可能丢失,这时被动方会重新发
   fin, 如果这时主动方处于 CLOSED 状态 ,就会响应 rst 而不是 ack。所以
   主动方要处于 TIME_WAIT 状态,而不能是 CLOSED 。

来源:http://blog.csdn.net/weiqubo/article/details/7225652

时间: 2024-08-10 17:17:12

TCP状态迁移图浅析(转载)的相关文章

TCP状态迁移,CLOSE_WAIT & FIN_WAIT2 的问题

TCP状态迁移 大家对netstat -a命令很熟悉,但是,你有没有注意到STATE一栏呢,基本上显示着established,time_wait,close_wait等,这些到底是 什么意思呢,在这篇文章,我将会详细的阐述. 大家很明白TCP初始化连接三次握手吧:发SYN包,然后返回SYN/ACK包,再发ACK包,连接正式建立.但是这里有点出入,当请求者收到SYS /ACK包后,就开始建立连接了,而被请求者第三次握手结束后才建立连接.但是大家明白关闭连接的工作原理吗?关闭连接要四次握手:发FI

TCP 状态详解 -转载

TCP 是一个面向连接的协议,无论哪一方向另一方发送数据之前,都必须先在双方之间建立一条连接.本节将详细讨论一个TCP 连接是如何建立的以及通信结束后是如何终止的. 建立一个 TCP 连接 TCP使用三次握手 ( three-way handshake ) 协议来建立连接,图 3-10 描述了三次握手的报文序列.www.2cto.com 这三次握手为: 请求端(通常称为客户)发送一个 SYN 报文段( SYN 为 1 )指明客户打算连接的服务器的端口,以及初始顺序号( ISN ). 服务器发回包

TCP状态变迁图

在读<TCP/IP协议详解>里看到的这张图:整理出来分享: 欢迎访问新博客社区:ACoder社区:  http://acoder.cc 版权声明:本文为博主原创文章,未经博主允许不得转载.

TCP状态转化图 TIME_WAIT解析

先上转换图: 重点研究TIME_WAIT状态,根据UNIX网络编程中的思路,TIME_WAIT状态有两个存在的理由: 1.假设最终的ACK丢失,服务器将重新发送它的最后那个FIN,因此客户必须维护状态信息,以允许它重新发送最终那个ACK,要是客户端 不维护状态信息,它将响应一个RST分节,该分节将被服务器解释成一个错误,如果TCP打算执行所有必要的工作以彻底终止连接上两个方向的数据流,那么它必须正确处理连接终止序列4个分节中任何一个分节丢失的情况.为什么执行主动关闭的那一端是处于TIME_WAI

TCP状态转换图解析

本文参考Unix网络编程卷1,对TCP状态转换进行总结,方便掌握TCP链接中各个状态及故障分析. 1.Linux下TCP相关工具 基于Linux系统查看网络状态,首先了解几个基本查看指令. Linux查看网络状态的命令: netstat -nat  查看TCP各个状态的数量 lsof  -i:port , 可以检测到打开套接字的状况.lsof(list open files)列出当前系统打开的文本的工具. tcpdump -iany tcp port 9000 ,对tcp端口为9000的进行抓包

TCP状态知识总结(图解)

tcp状态: LISTEN:侦听来自远方的TCP端口的连接请求 SYN-SENT:再发送连接请求后等待匹配的连接请求 SYN-RECEIVED:再收到和发送一个连接请求后等待对方对连接请求的确认 ESTABLISHED:代表一个打开的连接 FIN-WAIT-1:等待远程TCP连接中断请求,或先前的连接中断请求的确认 FIN-WAIT-2:从远程TCP等待连接中断请求 CLOSE-WAIT:等待从本地用户发来的连接中断请求 CLOSING:等待远程TCP对连接中断的确认 LAST-ACK:等待原来

TCP状态转换图(state transition diagram)

 TPC总共有11个状态,状态转换图: 状态转换的要素 状态: tcp定义的11个状态 事件: 触发TCP状态迁移.事件可以是:本地应用层调用:收到TCP消息(incoming segment):超时事件(timeout) 动作: 主要指针对远程Peer产生的动作,如发送确认等. 转换中的角色 本地应用层 Local App:产生事件. 本地tcp实现层 local TCP stack:处理事件,完成状态转换:在远程tcp上产生事件. 远程tcp实现层 remote TCP stack(or

TCP的那些事(转载)

(转载本站文章请注明作者和出处 酷 壳 – CoolShell.cn ,请勿用于任何商业用途) TCP是一个巨复杂的协议,因为他要解决很多问题,而这些问题又带出了很多子问题和阴暗面.所以学习TCP本身是个比较痛苦的过程,但对于学习的过程却能让人有很多收获.关于TCP这个协议的细节,我还是推荐你去看W.Richard Stevens的<TCP/IP 详解 卷1:协议>(当然,你也可以去读一下RFC793以及后面N多的RFC).另外,本文我会使用英文术语,这样方便你通过这些英文关键词来查找相关的技

读懂TCP状态转移

读懂TCP状态变换的过程,对于理解网络编程颇有帮助,本文将对TCP状态转移过程进行介绍,但各个状态(总共11个)的含义不在本文介绍的范围. 内容来源:<UNIX网络编程>第一卷第二章2.6节,若是读者对某个知识点不太理解,请参考原文. TCP状态转换图(state transition diagram) 1. 建立连接(three-way hand shake) 主动打开(passive open):服务器必须准备好接受外来的连接,通常通过socket.bind和listen完成. 被动打开(