Bootstrap

拥塞控制与TCP子问题(粘包问题,异常情况等)

​拥塞控制

除了拥塞控制

以上的策越都是为了解决tcp 客户端和服务端提高效率,解决丢包的策略

但是拥塞控制是了为解决网络拥堵

出现了大面积丢包,我们发送方会判定是网络出现了问题?

丢包好解决,我们直接采用超时重传,但是此时网络已经出问题了,你再重传,不还是丢包吗,并且网络出问题,其他服务器也会出现问题,此时大量的报文重传,对网络造成更的重创

TCP考虑了网络,出现大面积丢包->判断网络出现堵塞->拥堵避免算法

虽然TCP有了滑动窗口这个大杀器,能够高效可靠的发送大量的数据,但是如果在刚开始阶段就发送大量的数据,仍然可能引发问题.

因为网络上有很多的计算机,可能当前的网络状态就已经比较拥堵,在不清楚当前网络状态下,贸然发送大量的数据是很有可能引起雪上加霜的.

拥塞窗口

拥塞窗口采用慢启动策略

慢启动策略 2的n次方 以指数级增长

前期慢,增数快

​​​​

拥塞窗口就是一个数字,放发送数据量超过了拥塞窗口,就很大概率,引发网络拥塞

滑动窗口不仅仅考虑对方接受数据能力的多少,还要考虑网络情况

滑动窗口决定了我们一次发送数据量的大小

要做到上面两点?

滑动窗口大小=min(拥塞窗口,对方窗口大小)

滑动窗口初始end=min(拥塞窗口,对方窗口大小)

我们需要担心后期指数增速太快,造成网络拥塞?

a.不用担心,滑动窗口大小=min(拥塞窗口,对方窗口大小),当拥塞床快增长到一定程度,会被对方窗口大小所牵制

b.我们还引入了慢启动的阈值 ssthresh,当超过阈值,指数增长变成线性增长,造成了网络拥塞,我们直接将拥塞窗口降为1,但此时我们已经知道会引起网络拥塞的最大典,后面增长就可以避免拥塞,这种策越我们就叫做拥塞控制算法

但是网络窗口不会停止变化,它要一直变化,对网络的状况进行检测

tips:这张图并不是网络实际的发送量,还要考虑对方的窗口大小

总结: 通过控制拥塞窗口和慢启动阈值达到发送数据速率达到最大值就叫拥塞控制

Tcp想要尽快的传输数据给对方,又要考虑网络拥堵所采取的折中的方案

延迟应答

如果接收数据的主机立刻返回ACK应答, 这时候返回的窗口可能比较小.

提高了tcp传输效率

​​​

当主机A发出第一个报文,主机B可以等一等,再应答,等主机发了地等上层取走缓冲区的数据,主机B可以给主机A一个更大的窗口。

捎带应答

发送ACK+数据的报文

确认序号填的就是ACK的确认序号

序号填的是数据序号

合在一起就叫捎带应答

TCP子问题

面向字节流

创建TCP的一个socket,同时会在内核中创建发送缓冲区和接受缓冲区

可能10个报文的数据都是在缓冲区的,也可能是20个,我们不管,我们只要考虑上层从缓冲区读取一个个字节再到上层进行处理。

粘包问题

没有定任何协议,我们没有对从缓冲区读取的字节流做处理,导致数据多读或少读,导致数据粘黏

由用户层定义协议就是为了解决数据粘包问题

例如http按行读取报头,再读到空行,再读到携带数据。解决了基于tcp的http协议的粘包问题

而udp有没有这个问题呢?

没有,他是以数据包的形式发送的

所以我们用户使用tcp得解决两个问题?

1.解决粘包问题

2.对数据进行序列化和反序列化

Tcp异常情况

进程终止:自动正常关闭(四次挥手)

机器重启:提示用户是否关闭进程

机器断电/拔网线:没机会四次挥手,服务端会保活,试探客户端是否还活着。

网线一拔一插:客户端建立新连接,但莫名收到服务器上一次连接的报文,此时客户端发送RST,立即终止旧的连接。

;