TCP---传输控制协议
- 一种面向连接(虚连接)的传输层协议
- 每一条TCP有且只能有两个端点
- 可靠、有序、无丢弃、不重复
- TCP是面向字节流的(TCP将应用层数据仅看作是一串无结构的字节流)
- 提供全双工通讯
发送缓存
-
存放发送方TCP准备发送的数据
-
TCP已发送但是没有收到的数据
接收缓存
- 存放发送端发来的不按顺序到达的数据
- 按照顺序到达的数据,但并未被应用程序读取
TCP连接的四元组:源IP、源端口、目的IP、目的端口)——>唯一标识一条TCP连接
套接字——>IP:port(是计算机网络中进行网络通信的编程接口 )
确认序列号:接收方期望收到发送方发送的下一个字节的序号
累计确认机制:
- 累积确认是一个很重要的技术,因为通过累积确认我们就可以判断出来传输过程中是否存在 乱序 或者 丢包 的情况,从而决定是否进行 超时重传 或者 快速重传
- 累积确认依靠的是 TCP head 中的 确认号 Acknowledgement 以及 ACK 标志位
确认位ACK:当ACK=1时,确认号有意义。在连接建立以后,所有传输的报文段都必须将该标志位置为1.
同步位SYN:SYN=1时,代表该数据段是一个连接请求报文。
终止位FIN:当FIN=1时,表明此报文段发送方数据已发送完毕,要求释放连接。复位RST:表明TCP连接出现严重错误,需要释放连接并重新建立连接。
紧急位URG:代表该报文中存在高优先级的数据,应尽快处理。需要配合紧急指针使用。
推送位PSH:接收方应尽快将接收到的数据交付给对应应用程序。
TCP可靠性
确认、重传、排序、流控。
MTU:最大传输单元--->以太网环境下1500字节--->数据包大小。
MSS:最大数据段长度RTT--->往返时间(指发出端将数据发送后,到本端接收到对端反馈的确认报文的时间总和)
RTO--->超时重传时间--->RTO数值是动态变化的数值。超时间隔加倍。RTO取值略大于RTT值。
快速重传机制--->根据接收方的反馈信息进行数据重传。
- 客户端需要连续接收到三次确认序列号相同的ACK报文,则认为数据丢失,需要进行数据重传。
- 快速重传机制会导致部分数据重复传输,降低数据传输效率。
解决思路:
使用选择确认机制。--->在TCP首部的选项字段中,添加上未接收到的数据信息。发送方接收到该确认报文后,会根据选项字段内容,重新传输缺少的数据部分。
选择确认机制是否可以执行是需要通讯双方进行协商的。--->在三次握手的前两次SYN报文中进行协商。
快速重传 & 超时重传
- 快速重传相对应的是慢速重传,那么什么样的重传操作是快速的,什么样的是慢速的呢?
超时重传是慢速的重传方式,即当发送方 S 在设定的时间之内没有收到来自接收方 R 的确认信息,这个时候 S 会认为 R 并没有收到这条消息,因此 S 会重新向 R 再发送一遍,这个过程叫做超时重传
快速重传:当 S 接收到 3 个冗余 ACK 的时候,会立刻将信息进行重发。
窗口
- 窗口的大小是可以指定的
- 窗口大小指的是无需等待确认报文,而可以直接发送的数据包的最大值。
- rwnd(接收窗口)---最开始等于整个缓存区的大小,浮动变化。
- TCP要求发送方依据rwnd发送数据量。发送方的发送窗口大小是依据接收方的反馈信息中的接收窗口大小而设定的。
TCP连接的建立
三次握手
TCP连接连接需要解决的问题:
1、知晓对端的套接字信息
2、允许双方进行参数的协商(窗口值、选择确认机制、是否使用窗口扩大因子)
3、对设备进行资源分配
三次握手要用到的标志位:
- SYN 发送方
- ACK 接收方
- 三次握手的作用是为了约定双方的起始 sequence number,进而保证通信是可靠的,保证此次通信不受前面的连接的影响
在上面的例子中体现出了两个重要的问题:
- 双方都需要对当前建立的连接的初始的 sequence number 进行指定,只有通过 3 次握手才能保证双方的 sequence number 相互约定完成 如果只有两次握手,那么 B 就不能确认 A 是否已经知晓了 B 的 sequence number
- 双方的 sequence number 的指定需要通过某种方式来指定,而不能简陋地每次都从 0 开始。
当TCP连接建立成功,但是客户端突发故障。
此时服务端会等到2小时时间,若2小时时间内没有收到任何客户端的数据,则服务端发送一个探测报文,以后每隔75秒发送一次。若一连发送10次仍没有回复,则服务器认为客户端出现故障,关闭连接。
TCP释放连接
1、TCP连接的释放实际上是在释放本地分配给TCP连接的资源
2、本地没有新的数据需要发送
四次挥手
四次挥手是TCP 连接断开的时候采用的方式
通信的双方都可以发起连接断开的请求
这个过程中使用的标志位是 FIN
- A 首先发送给 B 一个断开的请求 FIN=1
- B 接收请求并回复 ACK 表示 B 收到了 A 的断开请求
- A 关闭对 B 的数据传送;但是这个时候 B 依然可以发消息给 A,A 也可以发内容给 B,但是不能发送数据了(发送的内容可以包含 TCP head 的其他部分)
- 这时候如果 B 也想断开连接了,那么 B 也发送一个 FIN=1 给 A,A 接收之后回复一个 ACK,那么这个时候 A,B 之间的连接彻底中断(这个 connection 断掉)
- 当 A 或者 B 处在单方面断开的情况我们称之为 half-closed 即半关闭状态,在上文的描述中,当 A 主动发送 FIN 并收到 B 的 ACK 之后,依然可以接收和回复 B 的状态就处于 half-closed 状态。