转载:http://blog168.chinaunix.net/space.phpuid=20196318&do=blog&id=168206

挺好的,方便记忆!!!

TCP状态转换--值得学习--方便记忆_第1张图片

实线:表示客户的正常状态转换    虚线:表示服务器的正常状态装换

应用:表示状态转换在应用进程发起操作时发生

接受:表示状态转换在接受到分节时发生  发送:表示这个转换发送什么

 

三次握手建立连接

服务器调用socketbindlisten来完成,即执行被动打开,准备好接受外来的请求。

1. 客户端发调用connect发送SYN分节(同步),它告诉服务器客户将在连接中发送的数据的初始序列号。此时客户端进入SYN_SENT状态。

2. 服务器接受到客户端SYN分节后,必须进行确认,同时发送一个SYN分节到客户端。服务器发送ACK+SYN后,服务器进入SYN_RECV状态。

3. 客户端收到服务器发送的SYN,并进行确认。客户端发送ACK后进入ESTABLISHED状态,服务器接收到ACK后也进入到ESTABLISHED状态。

 

l 当客户端与服务器都进入ESTABLISHED状态后,就说明TCP连接成功建立。

l 当客户端处于SYN_SENT状态,如果没有收到ACK(超时),客户端会多次(几次?)重发SYN,如果连接仍未能建立,则进入CLOSED状态。

l 当服务器处于SYN_RECV状态时,如果收到RST分节,则进入CLOSED状态。SYN_RECV状态的服务器没有收到ACK时,其一直处于半连接状态,其信息会存在服务器的缓冲区中,直到超时,SYN Flood***就是靠大量的半连接SYN来耗尽服务器的资源。

l 同时打开:为了处理同时打开,对于同时打开它仅建立一条连接而不是两条连接。两端几乎在同时发送SYN,并进入SYN_SENT状态。当每一端收到SYN时,状态变为SYN_RCVD,同时他们都再发SYN并对收到的SYN进行确认。当双方都收到SYN及相应的ACK时,状态都变为ESTABLISHED

 

四次挥手断开连接

1. 某个应用进程首先调用close,执行主动关闭,导致发送一个FIN分节,表示数据发送完毕,进入FIN_WAIT_1状态。

2. 接受FIN的另一端执行被动关闭,其确认收的FIN,接受到的FIN作为文件结束符传递给接收端的应用进程(放在已排队等候该应用进程接受的任何其它数据之后),进入CLOSE_WAIT状态。同时原发送端接受到FIN后进入TIME_WAIT_2状态。

3. 一段时间后,接收到文件结束符的应用进程将调用CLOSE关闭它的套接口,向对端发送一个FIN,进入LAST_ACK状态。

4. 接受到这个FIN的原发送端对它进行确认,发送ACK,并进入TIME_WAIT状态,在此状态保留2MSL时间后,进入CLOSED状态。而另一端收到ACK后进入CLOSED状态。

 

l 被动关闭的一段的ACKFIN可能同时发送(捎带),则主动关闭的一端由TIME_WAIT_1直接进入TIME_WAIT状态。

l 主动关闭一端存在TIME_WAIT状态的原因。

1. 如果主动关闭端最后发送的ACK丢失,则被动关闭一端将重发FIN,此时主动关闭一端必须重发最后的ACK,所以其不能再发送ACK后立即进入CLOSED状态。

2. 防止IP和端口立即被重用,而还在“线上”的数据将影响重用的进程。2MSL的时间允许某个方向的分组最多存活MSL时间即被丢弃。

l 同时关闭:当应用层发出关闭命令,两端均从ESTABLISHED变为FIN_WAIT_1。这将导致双方各发送一个FIN,两个FIN经过网络传送后分别到达另一端。收到FIN后,状态由FIN_WAIT_1变为CLOSING,并发送最后的ACK。当收到最后的ACK,状态变为TIME_WAIT