ESTABLISHED - 代表一个打开的连接,数据可以传送给用户;
FIN-WAIT-1 - 等待远程TCP的连接中断请求,或先前的连接中断请求的确认;
FIN-WAIT-2 - 从远程TCP等待连接中断请求;
CLOSE-WAIT - 等待从本地用户发来的连接中断请求;
CLOSING - 等待远程TCP对连接中断的确认;
LAST-ACK - 等待原来发向远程TCP的连接中断请求的确认;
TIME-WAIT - 等待足够的时间以确保远程TCP接收到连接中断请求的确认;
CLOSED - 没有任何连接状态;
TCP连接过程是状态的转换,促使发生状态转换的是用户调用:OPEN,SEND,RECEIVE,
CLOSE,ABORT和STATUS;传送过来的数据段,特别那些包括以下标记的数据段SYN,ACK
,RST和FIN;还有超时,上面所说的都会时TCP状态发生变化。
下面的图表示了TCP状态的转换,但这图中没有包括错误的情况和错误处理,不要把这幅
图看成是总说明了。
3.3. 序列号
请注意,我们在TCP连接中发送的字节都有一个序列号。因为编了号,所以可以确认它们
的收到。对序列号的确认是累积性的,也就是说,如果用户收到对X的确认信息,这表示
在X以前的数据(不包括X)都收到了。在每个段中字节是这样安排的:第一个字节在包
头后面,按这个顺序排列。我们需要认记实际的序列空间是有限的,虽然很大,但是还
是有限的,它的范围是0到2的32次方减1。我想熟悉编程的一定知道为什么要在计算两个
段是不是相继的时候要使用2的32次方为模了。TCP必须进行的序列号比较操作种类包括
以下几种:
(a) 决定一些发送了的但未确认的序列号;
(b) 决定所有的序列号都已经收到了;
(c) 决定下一个段中应该包括的序列号。
对于发送的数据TCP要接收确认,处理确认时必须进行下面的比较操作:
SND.UNA = 最老的确认了的序列号;
SND.NXT = 下一个要发送的序列号;
SEG.ACK = 接收TCP的确认,接收TCP期待的下一个序列号;
SEG.SEQ = 一个数据段的第一个序列号;
SEG.LEN = 数据段中包括的字节数;
SEG.SEQ SEG.LEN-1 = 数据段的最后一个序列号。
请注意下面的关系:
SND.UNA < SEG.ACK =< SND.NXT
如果一个数据段的序列号小于等于确认号的值,那么整个数据段就被确认了。而在接收
数据时下面的比较操作是必须的:
RCV.NXT = 期待的序列号和接收窗口的最低沿;
RCV.NXT RCV.WND-1 = 最后一个序列号和接收窗口的最高沿;
SEG.SEQ = 接收到的第一个序列号;
SEG.SEQ SEG.LEN-1 = 接收到的最后一个序列号;
上面几个量有如下关系:
RCV.NXT =< SEG.SEQ < RCV.NXT RCV.WND 或 RCV.NXT =< SEG.SEQ SEG.LEN-1 < RCV.N
XT RCV.WND
测试的第一部分是检查数据段的开始部分是否在接收窗口中,第二部分是检查数据段的
结束部分是否也在接收窗口内;上面两个检查通过任何一个就说明它包括窗口要求的数
据。实际中的情况会更复杂一些,因为有零窗口和零数据段长,因此我们有下面四种情
况:
段长度
接收窗口
测试
0
0
SEG.SEQ = RCV.NXT
0
>0
RCV.NXT =< SEG.SEQ < RCV.NXT RCV.WND
>0
0
不可接受
>0
>0
RCV.NXT =< SEG.SEQ < RCV.NXT RCV.WND或RCV.NXT =< SEG.SEQ SEG.LEN-1 < RCV.NX
T RCV.WND
请注意接收窗口的大小可以为零,在窗口为零时它只用来接收ACK信息,因此对于一个T
CP来说,它可以使用零大小窗口在发送数据的同时接收数据。即使接收窗口的大小为零
,TCP必须处理所有接收到信息的RST和URG域。
我们也应用计数的方式保护了一些特定的控制信息,这是通过隐式地使用一些控制标记
使数据段能够可靠地重新发送(或确认)为达到的。控制信息并不在段数据空间中传送
,因此,我们必须采用隐式指定序列号进行控制。SYN和FIN是需要保护的控制量,这两
个控制量也只在连接打开和关闭时使用。SYN被认为是在第一个实际数据之间的数据,而
FIN是最后一个实际数据之后的数据。段长度(SEG.LEN)包括数据和序列号空间,如果
出现了SYN,那么SEG.SEQ是SYN的序列号。
初始序列号选择
协议对于特定连接被重复使用没有什么限制。连接是由一对套接字定义的。新的连接实
例被定义为连接的另一次恢复,这就带来了问题:TCP如果确定多个数据段是从以前连接
的另一次恢复中取得的呢?这个问题在连接迅速打开和关闭,或因为内存原因被关闭然
后又迅速建立后显示特别突出。
为了避免混乱,用户必须避免因此恢复使用某一连接,而使序列号发生混乱。我们必须
保证序列号的正确性,即使TCP失败,根本不知道以前的序列号是什么的情况下也要保证
序列号的正确性。当新的连接被创建时,产生一个新的初始序列号(ISN)产生子,它用
来选择一个新的32位ISN。产生子和32位时钟的低度位字节相关,低位字节的刷新频率大
概是4微秒,因此ISN的循环时间大概是4.55小时。因此我们把网络包的最长生存时间(
MSL)小于4.55小时,因此我们可以认为ISN是唯一的。对于每个连接都有发送序列号和
接收序列号,初始发送序列号(ISS)由发送TCP选择,而初始接收序列号是在连接建立
过程中产生的。
对于将要连接或初始化的连接,两个TCP必须和对方的初始序列号同步。这通过交换一个
控制位SYN和初始序列号完成。我们把带有SYN的数据段称为"SYNs"。同步的获得过程这
里就不重复了,每方必须发送自己的序列号并返回对对方序列号的确认。
1) A --> B SYN 本方序列号是X
2) A <-- B ACK 本方序列号被确认
3) A <-- B SYN 对方序列号是Y
4) A --> B ACK 确认对方序列号
上面的第2步和第3步可以合并,这时可以成为3阶段,所以我们可以称它为三消息握手。
这个过程是必须的,因为序列号不和全局时钟关联,TCP也可以有不同的机制选择ISN。
接收到第一个SYN的接收方不可能知道这个数据段是不是被延时,除非它记住了在连接上
使用的最近的序列号(这通常是不可能的),因此它必须要求发送者确认。
为了保证TCP获得的确认是刚才发送的段产生的,而不是仍然在网络中的老数据段产生的
,因此TCP必须在MSL时间之内保持沉默。在本文中,我们假设MSL=2小时,这是出于工程
的需要,如果用户觉得可以,他可以改变MSL。请注意如果TCP重新初始化,而内存中的
文章整理:西部数码--专业提供域名注册、虚拟主机服务
http://www.west263.com
以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!




