赞
踩
负责两端之间数据传输 TCP/UDP
协议格式:
16位源端端口&16位对端端口:描述了通信是哪两端进程正在进行
16位数据报长度:描述包含了udp报头在内的数据报长度
因为16位数据报所能描述的最大数字:65535
因此一个udp报文,包含udp报头在内,最大必须小于64K
反馈:应用层使用sendto发送数据时,数据长度必须小于64K~8
16位校验和字段:校验数据一致性(分析接受到的数据跟对方发送的数据是否一致),一个数据一旦在传输过程中发生改变,就不能交付给应用程序处理了。
校验算法:二级制反码求和算法
发送方发送数据时先将校验和字段置为0,然后从报头开始逐字节取反相加,高出16位的部分截断与低16位继续相加,知道数据结尾,得到一个校验和,然后填充到校验和字段中,进行发送给对方。
对方接受到数据之后,从报头开始进行二进制反码求和,如果最终是0就一致。
协议特性:
特性对于编程的影响:
**UDP不同的特点:**UDP支持局域网广播
16位源端端口&16wei对端端口:描述了通信两端
32位序号:tcp是面向字节流的,相当于对传输的每个字节都进行了编号,接受数据的一方会根据需要进行数据排序,最终进行数据的有序交付。
32位确认序号:接收方接收到一个数据之后,就会给发送方发送一个确认序号,告诉对方以前的数据都接收到了(快速重传机制,滑动窗口机制…)依赖于确认序号
4位报头长度:tcp的报头,不是一个固定长度,长度是会变化的,但不管怎么变化,前20字节都是固定的,只有选项数据这里的0~40字节的不定长度
因此在解析的时候,总是先取出20字节固定头部长度,再决定取出剩余多少的选择数据 长度-20,剩余的就是应用数据
6位保留位:暂时未使用的
6位标志位
16位窗口大小:用于实现滑动窗口机制,进行流量控制
16位校验和:二进制反码求和算法,检验数据一致性
16位紧急指针:指向带外优先数据的结束位置
0~40位选项数据
面向连接:连接管理&状态管理(三次握手建立连接和四次挥手断开连接)
三次握手
为什么握手是三次:
握手失败后,两端如何处理:
第一次握手失败,客户端重发SYN
第二次握手失败,服务器等待最后一次ACK超时 就会发送RST,然后释放资源
第三次握手失败,服务器等待最后一次ACK超时就会发送RST,然后释放资源
四次挥手
1.为什么挥手是四次:
为什么FIN包与ACK没有混在一起发送,而是分开发送?
FIN请求只能表示主动关闭方不再发送数据,并不代表不在接受数据,因此被动关闭方收到FIN并进行确认后,还有可能继续发送数据,等待上层不在发送数据了,也要关闭套接字才会发送FIN包。
2.一台主机上出现了大量的CLOSE_WAIT状态,是什么原因?
1.只有收到FIN请求并进行了确认回复的连接会进入CLOSE_WAIT
2.一直处于CLOSE_WAIT而没有进入下一步状态是因为上层没有关闭套接字操作,也就是没有发送FIN包,所以并没有进入下一步
3.因此原因就是代码中没有针对断开连接的套接字进行关闭处理。
3.TIME_WAIT状态有什么用
1.TIME_WAIT状态时主动关闭方再发送最后一次ACK后进入的状态
2.如果没有TIME_WAIT,主动关闭方直接释放套接字资源,有可能出现新启动的套接字使用了之前相同的地址信息
3.而上一次连接有可能最后一次ACK会丢失,一旦丢失被动关闭方会重传FIN包
4.就会导致上一次通信因为最后一次ACK丢失,而遗留的问题(重传FIN)对新连接造成的影响
因此不能直接释放资源,而是等待两个MSL时间,针对有可能存在的FIN重传进行处理,并保证上一次通信的所有数据都消失再网络中
4.一台主机上出现了大量的TIME_WAIT状态连接,是什么原因?
产生&作用:
time_wait是主动关闭方发送最后一此ACK后进入的状态,等待一段时间是为了处理有可能因为FIN丢失而导致的FIN重传的处理
解决:
1.time_wait等待时间是可配置的,可以将时间设置的更短
2.有一个套接字选项,叫做地址重用。setsockopt();
产生原因:
网络爬虫
5.TCP连接管理中的心跳保活机制
连接断开有个信息:recv会返回0,send会触发异常
TCP通信中,如果客户端和服务端通信频率并不高,中间网忽然断了,没有四次握手的机会,如果两端通信频率很低,可能需要很久才会发现。
在通信中,客户端与服务器若长时间无通信(默认7200s),则TCP服务器会自动向客户端发送探测心跳包,要求对方响应(默认每隔75s),若连续多次没有收到响应(默认9次),则认为连接断开。
MSL:报文最大生命周期(一个报文在网络中最大能存在的时间),默认为60s
可靠传输:安全,有序
通过很多特殊机制实现
可靠传输:
1.保证可靠:面向连接,确认应答机制,超时重传机制,序号,确认序号,校验和
2.避免丢包:滑动窗口机制,拥塞机制
3.性能挽回:快速重传机制,延迟发送机制,延迟应答机制,捎带应答机制
没有必要的性能损失处理机制:
性能的挽回:
tcp为了保证可靠传输,牺牲了部分传输性能,但是有些性能的损失是没必要的
1.因为发送数据过多,导致对方缓冲区丢包重传。
2.因为网络状况的突变,导致大量的丢包重传
3.因为确认应答丢失导致的重传
流量控制:
接收方每次接收到数据都会进行确认回复,在确认回复的时候就会计算自己接收缓冲区中的剩余空间大小,将这个数字放到窗口大小字段中给对方 回复。
发送方根据确回复中的窗口大小字段,确定自己最多发送多少数据
这就是TCP中的流量控制–避免因为发送方发送过多数据导致接收方接受缓冲区溢出而导致的丢包
窗口大小字段:接收方进行数据发送或者确认回复的时候,告诉对方最多给自己发送多少数据(大小取决于接受方的缓冲区空闲空间大小)
发送窗口:
窗口后沿:记录了从哪个序号开始对数据进行编号发送,移动取决于时候收到了后沿数据的确认回复。
窗口前沿:记录了最多发送数据到多少序号,移动取决于对方回复的窗口大小。
窗口前沿-窗口后沿<=接受方回复的窗口大小
确认序号:告诉发送方,确认序号之前的数据都已经收到了。(如果第一条数据丢了,但收到了第二条数据,这时候是不能对第二条数据进行确认回复的。)
接受窗口:
窗口后沿:记录要接受数据的起始序号,移动取决于收到起始序号的数据
窗口前沿:记录当前接受数据的结束序号,移动取决于缓冲区剩余空间大小
窗口前沿-窗口后沿<=缓冲区剩余空间大小
停等协议:
发送方发送一条数据后,收到回复才会发送吓一跳数据,适用于网络状况较差的场景
回退N步协议:
滑动窗口机制取决定了tcp传输可以管线化传输, 可以连续发送多个报文,而传输过程中,如果出现丢包,回退N步协议,指的是从丢包的这个数据开始对数据重新进行传输,适用于网络状态一般的场景
选择重传协议:
传输过程中,丢包了,哪个包丢了就对哪个包重传,适用于网络较好的场景
拥塞机制:
避免因为网络状态突变,因为网络拥塞而导致的大量丢包的情况
拥塞窗口:控制发送方发送数据量的基准
发送数据大小<=min(滑动窗口大小,拥塞窗口大小)
拥塞窗口,一般初始大小为1
拥塞控制的思想:慢启动,快增长的过程进行网络探测
拥塞窗口从初始值开始进行指数级增长,到达阈值时进行线性增长
在数据传输过程中,接收方接收数据时,并没有接受起始序号的数据,而是接受到了后边的数据(在第一条数据之前接收到第二条数据)
接收方不会对第二条数据进行回复,正常情况发送方等待确认回复,超时后进行第一条数据的超时重传,但这样效率太低,因此,接收方为提高效率,会给发送方回复一个第一条数据的序号确认。并且在接受后续的数据过程中,都会进行如此确认,而发送方连续收到三条第一条数据的确认回复,则会对第一条数据进行重传。
收到三条重传请求,才对数据进行重传,是因为有可能第一条数据延时到达,并不是丢包情况,
性能的挽回:
快速重传协议:避免每次重传都需要等待超时才进行
延迟发送机制:解决频繁的小数据发送效率低,减少IO次数,每次发送数据,数据并不会立即被发送,而是等待,在次期间又有可能有小数据被放到缓冲区中,小数据就会积累成大数据,经过一次IO可以完成传输,减少IO次数提高效率
基于确认应答机制:接收方需要对方发送这样一条数据进行确认回复,大概率数据在缓冲区并没有被取出,因此这时候的回复会导致窗口大小变小,网络吞吐率降低,因此设计者就会设计延迟一会应答,在这段时间中,程序有可能将数据取出,保持窗口不变。
捎带确认应答机制:接收方需要对发送方的每一条数据进行确认回复,但每一个回复都是最小20字节的报文,接收方刚好也有数据要发送给对方,就干脆将这个确认回复与要发送的数据结合到一起(确认应答也就是一个确认序号)发送给对方,这样可以尽可能减少空报文的传输。
提供字节流传输服务:
传输的时候,对数据以字节为单位进行编号,进行传输,不限制传输大小
数据进行发送的时候,总线放到缓冲区,发送的时候进行编号发送
粘包问题:数据之间缺乏边界管理
tcp粘包问题:tcp在传输层,并不管传输什么数据,只管从缓冲区取出合适大小的数据进行操作,没有边界管理。
解决方法:在应用层,程序员对数据进行边界管理
边界管理:明确一条数据从哪开始,到哪结束
1.特殊字符间隔,明确一条数据从哪开始,到哪结束
2.数据定长:数据固定长度,缺陷就是需要最大定长定限(浪费多)
3.数据采用TLV格式:在应用层头部定义数据长度(先取头部中的长度,决定取多少数据),典型做法:HTTP,UDP
TCP粘包问题了解吗?UDP粘包如何解决?
UDP没有粘包问题,因为UDP的面向数据报传输方式,本身就是一次最多交付一条数据(UDP本身就有数据的边界管理)
UDP的sendto接口发送数据,将数据放到缓冲区后,会立即封装头部进行发送。
数据进行边界管理
边界管理:明确一条数据从哪开始,到哪结束
1.特殊字符间隔,明确一条数据从哪开始,到哪结束
2.数据定长:数据固定长度,缺陷就是需要最大定长定限(浪费多)
3.数据采用TLV格式:在应用层头部定义数据长度(先取头部中的长度,决定取多少数据),典型做法:HTTP,UDP
TCP粘包问题了解吗?UDP粘包如何解决?
UDP没有粘包问题,因为UDP的面向数据报传输方式,本身就是一次最多交付一条数据(UDP本身就有数据的边界管理)
UDP的sendto接口发送数据,将数据放到缓冲区后,会立即封装头部进行发送。