那年那夏那些不太明白的TCP1

What

可曾听说过TCP/IP协议? 嗯?那是相当的厉害啊。

结构

在这里插入图片描述
sorce port: 源端口 2个字节
destination port: 目的端口 2个字节
sequnence number : 序列号 4个字节
Acknowlegment Number: 确认序列号 4个字节
【TCP传输的可靠性就是通过序列号确认序列号来保证的】
Window: 窗口大小 2个字节 所以最大为65535. 【很重要】

几个概念要清楚

  1. MTU : Maximum Transmission Unit, 最大传输单元。物理接口(数据链路层)提供给其上层最大一次传输数据的大小。[ 注意: 这里可能会发生 IP切片,产生IP分片与重组]
  2. MSS: Maximum Segment Size, 最大TCP分段大小。不包含TCP头部,指的是TCP payload的大小, 也就是传输的应用层的数据的大小。MSS=MTU-IP头部长度20-TCP头部长度20(有时候也不是20). mss的大小是在三次握手的时候确定的。 连接的双方分别告知对方自己的MSS, 最终传输时的MSS就是这两者中的最小值。当TCP传送大量数据时,就按照MSS的大小对数据进行分割然后发送。
  3. TCP粘包、拆包

TCP vs UDP

TCP提供一种面向连接的、可靠的字节流服务。有流量控制、拥塞控制。传输速率慢。
UDP提供一种非面向连接的、不可靠的数据报服务。无流量控制、拥塞控制。传输速率快。

三次握手

在这里插入图片描述
在这里插入图片描述
在建立连接前, 客户端处于 Closed状态, 服务端处于 Listen状态。

  1. 客户端首先发送一个SYN, 告诉服务端自己的初始序列(ISN)、mss. 此时客户端处于SYN_SENT状态。
  2. 服务端接收到客户端的连接请求后, 会发送给客户端 自己的初始序列,mss, 和用于确认收到消息的ACK。此时服务端处于SYN_RCVD状态。
  3. 客户端收到服务端传来的消息后,发送给服务端ACK, 连接完成。此时客户端处于ESTABLISHED阶段, 服务端收到ACK报文段后, 也将处于ESTABLISHED阶段。
  • SYN_SENT: syn package has been sent
  • SYN_RCVD: syn package has been received
  • SYN_SENT与SYN_RCVD都是半连接(半打开)状态,一个是客户端的,一个是服务端的,半打开状态是向对方发送SYN了,但是还没有等到对方的ACK.
    为什么不是两次?
    为了防止已失效的请求报文段突然又传送到了服务端,因而产生错误。因为两次连接说明,客户端发来SYN后,服务端发送给客户端ACK确认应答后,就进入到了ESTABLISHED阶段,等待客户端接下来要发送的数据到来,但是由于该SYN是由于网络延迟等原因,客户端已经抛弃了该连接,并不会通过此连接发送数据,那么就会导致服务端在白白的等待。三次握手就不会出现这种情况,服务端在发送完SYN+ACK后,进入到SYN_REVD半连接状态,等到收到客户端的ACK后,才会进入到ESTABLISHED状态。
    为什么不是四次?
    当客户端发来连接请求后SYN报文段后,服务端一方面进行ACK确认应答,同时,又进了SYN连接请求,为了提高连接效率,将服务端的ACK和SYN合在了一起进行发送,因此将原来四次的握手过程变为了三次握手。而在挥手时,没有将两次合在一起发送,所以挥手是四次。

四次挥手

在这里插入图片描述
断开连接前,双方都处于ESTABLISHED状态。

  1. 主动关闭方发送一个FIN报文。 然后主动方处于FIN_WAIT1状态。
  2. 被动关闭方收到FIN报文后, 发送ACK确认报文。然后被动方处于CLOSE_WAIT状态。主动方收到ACK后, 进入到 FIN_WAIT2状态。
  3. 被动方发送FIN报文,然后被动方处于LAST_ACK状态。
  4. 主动方收到FIN后,发送ACK, 主动方处于TIME_WAIT状态, 过2MSL后,进入到CLOSED状态, 被动方收到ACK后 , 进入到CLOSED状态。

为什么需要四次挥手?
当服务端收到客户端的SYN连接请求报文后,可以直接发送SYN+ACK报文。其中ACK报文是用来应答的,SYN报文是用来同步的。但是在关闭连接时,当服务端收到FIN报文时,可能并不会立即关闭Socket.【个人感觉:TCP连接成功之后,数据的传输就是全双工的,双方都可以主动发送数据给对方,那么当其中的一方已经没有想要发送的数据的时候,假设这一方是客户端,那么客户端就会发送FIN报文段告诉服务端,我已经没有数据要发给你了,而此时的服务端有可能还有数据要发送给客户端,所以服务端只是发送了一个ACK确认应答给客户端,但是并没有立刻发送FIN给客户端,服务端要等到没有其他的数据要发送给客户端的时候,才会发送FIN报文段,所以造成了挥手的四次,这跟三次握手连接不同,连接时,可以将ACK与SYN一起发送给客户端】
为什么要等待2MSL?

  • 注意:是 2MSL, 不是2ms(毫秒!!)
  • MSL: Maximum Segment Lifetime 报文段最大生存时间。它是任何报文段被丢弃前在网络中的最长时间。
  • 当TCP执行一个主动关闭,并发回最后一个ACK,该连接必须在TIME_WAIT状态停留2倍的MSL. (为什么是2msl, 而不是1或者3呢? 因为我的ACK要发给对面,对面没收到后,会超时重传它的FIN报文段,一来一回,可不是2吗。)。 那么为什么要有这个2MSL呢,客户端它接收到服务端的FIN后,直接进入到CLOSED状态不好吗?对不起,虽然这样做很香,但是太不负责任了。TCP可是面向连接的、提供可靠的字节流服务的传输层协议。可靠啊!!当然是每发送完报文段后,要收到对面的ACK了。(即便是延迟ACK, 本质也是这个意思)。可是如果不等2msl, 那么万一客户端 的ACK在网络传输中丢包了,那么服务端没收到ACK后,就会不断的重发FIN。(BTW, 没有用啊,),最后就得异常关闭了,所以需要等待2MSL.
    半连接队列
    服务器在收到客户端的SYN后,返回给客户端SYN+ACK后,就进入到SYN_RCVD状态,此时双方还没有完全建立起连接,服务端会把此种状态下请求连接放在一个队列中,这种队列就叫做半连接队列。
    ISN是什么?
    ISN: 初始序列号,当建立连接时,在SYN报文段中发送的序列号就是ISN,
    TCP/IP 协议详解中的示例图
    在这里插入图片描述

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值