一、TCP概述
每一条TCP连接都有两个端点,这种端点我们叫作套接字(socket),它的定义为端口号拼接到IP地址即构成了套接字,
例如,若IP地址为192.0.0.1 而端口号为8000,那么得到的套接字为192.0.0.1:8000
二、TCP报文格式
ACK、SYN和FIN这些大写的单词表示标志位,其值要么是1,要么是0;ack、seq小写的单词表示序号
同步SYN:(Synchronize ),SYN=1表示这是一个连接请求报文,或连接接受报文。SYN这个标志位只有在TCP建产连接时才会被置1,握手完成后SYN标志位被置0
确认ACK:仅当ACK=1时,确认号字段才有效。ACK=0时,确认号无效。如:当SYN=1,ACK=0时表示这是一个连接请求报文段,若同意连接,则在响应报文段中使得SYN=1,ACK=1
终止FIN:用来释放一个连接。FIN=1表示:此报文段的发送方的数据已经发送完毕,并要求释放
序列号seq:(Sequence Number),占4个字节,表示报文段携带数据的第一个字节的编号,TCP连接中传送的字节流中的每个字节都按顺序编号。例如,一段报文的序号值是 301 ,而携带的数据共有100字段,显然下一个报文段(如果还有的话)的数据序号应该从401开始;,图中的 x 和 y,
确认号ack:占4个字节,期待收到对方下一个报文段的第一个数据字节的序号,例如,B收到了A发送过来的报文段,其序列号seq是1,而数据长度是100字节,这表明B正确的收到了A发送的到序号从1到100为止的数据。因此,B期望收到A的下一个数据序号是100+1,于是B在发送给A的确认报文段中把确认号置为101
三、三次握手,四次挥手
3.1 TCP连接的建立过程——三次握手
建立双向通道的过程称之为三次握手,建立通道的发起者可以是客户端也可以是服务端,下面我们就以客户端先主动发起为例
-
客户端会朝服务端发送一个请求询问服务端:"我能不能挖一条通往你家的地道"
-
服务端收到请求,回复说:"好吧 你挖吧",由于TCP是双向通道,客户端挖向服务端的通道只能给客户端朝服务端发消息使用,服务端要向给客户端发消息是没办法走这一条通道的,需要自己挖一条通往客户端的通道
所以服务端在回复同意客户端挖通道的同时还会问一句:"那我能不能也挖一条通往你家的通道"
-
客户端收到服务端请求后客户端到服务端的通道就挖成功了,然后也会同意服务端的请求,服务端挖向客户端的通道也会成功
- 1.服务器准备:TCP服务器进程先创建传输控制块TCB,时刻准备接受客户进程的连接请求,此时服务器就进入了LISTEN(监听)状态
- 2.客户端准备:TCP客户进程也是先创建传输控制块TCB
-
3.第一次握手:客户端向服务器发出连接请求报文,报文首部中的同步标志SYN=1,同时生成一个初始序列号 seq=x ,此时,TCP客户端进程进入了 SYN-SENT(同步已发送状态)状态。TCP规定,SYN报文段(SYN=1的报文段)不能携带数据,但需要消耗掉一个序号
-
4.第二次握手:TCP服务器收到请求报文后,如果同意连接,则发出确认报文。确认报文中确认标志 ACK=1,SYN=1,确认号是ack=x+1,同时也要为自己初始化一个序列号 seq=y,此时,TCP服务器进程进入了SYN-RCVD(同步收到)状态。这个报文也不能携带数据,但是同样要消耗一个序号
-
5.第三次握手:TCP客户端收到确认后,还要向服务器再次给出确认。确认报文的确认标志ACK=1,确认号ack=y+1,自己的序列号seq=x+1,此时,TCP连接建立,客户端进入ESTABLISHED(已建立连接)状态。TCP规定,ACK报文段可以携带数据,但是如果不携带数据则不消耗序号
- 6.连接成功:当服务器收到客户端的确认后也进入ESTABLISHED状态,此后双方就可以开始通信了
LISTEN - 侦听来自远方TCP端口的连接请求; SYN-SENT -在发送连接请求后等待匹配的连接请求; SYN-RECEIVED - 在收到和发送一个连接请求后等待对连接请求的确认; ESTABLISHED- 代表一个打开的连接,数据可以传送给用户; FIN-WAIT-1 - 等待远程TCP的连接中断请求,或先前的连接中断请求的确认; FIN-WAIT-2 - 从远程TCP等待连接中断请求; CLOSE-WAIT - 等待从本地用户发来的连接中断请求; CLOSING -等待远程TCP对连接中断的确认; LAST-ACK - 等待原来发向远程TCP的连接中断请求的确认; TIME-WAIT -等待足够的时间以确保远程TCP接收到连接中断请求的确认; CLOSED - 没有任何连接状态;