【Linux】传输层协议UDP和TCP

目录

UDP

端口号

端⼝号范围划分

UDP协议端格式

UDP的特点

面相数据报

UDP的缓冲区

UDP使用注意事项

基于UDP的应⽤层协议

报文的封装和解包

TCP

TCP报头

可靠性

三次握手

四次挥手

滑动窗口

流量控制

拥塞控制

延迟应答

捎带应答

面相字节流

TCP异常问题

保活机制

TCP底层文件调用关系

UDP底层文件调用关系


UDP

端口号

端⼝号(Port)标识了⼀个主机上进⾏通信的不同的应⽤程序

端⼝号范围划分

• 0-1023:知名端⼝号,HTTP,FTP,SSH等这些⼴为使⽤的应⽤层协议,他们的端⼝号都是固定的.

• 1024-65535:操作系统动态分配的端⼝号.客⼾端程序的端⼝号,就是由操作系统从这个范围分配的

UDP协议端格式

1、明确规定报文的长度,不怕多个报文混在一起分不开;

2、UDP协议头部是固定长度的8字节,包含源端口号和目的端口号

3、协议就是结构体,把结构体封装到头部

4、应用层数据必须做序列化和反序列化,因为要求通信双方的大小端、对齐方式,语言等等都要一样;传输层可以不做,直接传递结构体,可以看成底层的二进制流就是序列化的结果。

5、16位UDP长度是整个报文的长度,包含8字节的报头和数据两部分。

UDP的特点

UDP传输的过程类似于寄信.

• ⽆连接:知道对端的IP和端⼝号就直接进⾏传输,不需要建⽴连接;

• 不可靠:没有确认机制,没有重传机制;如果因为⽹络故障该段⽆法发到对⽅,UDP协议层也不会给 应⽤层返回任何错误信息;

• ⾯向数据报:不能够灵活的控制读写数据的次数和数量;

面相数据报

应⽤层交给UDP多⻓的报⽂,UDP原样发送,既不会拆分,也不会合并;

⽤UDP传输100个字节的数据:

• 如果发送端调⽤⼀次sendto,发送100个字节,那么接收端也必须调⽤对应的⼀次recvfrom,接收 100个字节;⽽不能循环调⽤10次recvfrom,每次接收10个字节;

UDP的缓冲区

  • UDP没有真正意义上的发送缓冲区.调⽤sendto会直接交给内核,由内核将数据传给⽹络层协议进 ⾏后续的传输动作;
  • UDP具有接收缓冲区.但是这个接收缓冲区不能保证收到的UDP报的顺序和发送UDP报的顺序⼀ 致;如果缓冲区满了,再到达的UDP数据就会被丢弃;

发送缓冲区的作用:在TCP通信过程中,上层应用层把数据交给传输层的发送缓冲区中,系统把数据传输到网络里,当数据丢包的时候,为了保证TCP无差错的传输,需要重传,那么此时数据从哪儿来?就是发送缓冲区中的数据不会被清除。

而UDP不保证可靠,因此不需要有发送缓冲区,直接发送;但是会有接受缓冲区,使得应用层在解包的过程中传输层还能够接受数据包。

UDP使用注意事项

UDP协议⾸部中有⼀个16位的最⼤⻓度.也就是说⼀个UDP能传输的数据最⼤⻓度是 64K(包含UDP⾸部). 然⽽64K在当今的互联⽹环境下,是⼀个⾮常⼩的数字. 如果我们需要传输的数据超过64K,就需要在应⽤层⼿动的分包,多次发送,并在接收端⼿动拼装

基于UDP的应⽤层协议

• NFS:⽹络⽂件系统

• TFTP:简单⽂件传输协议

• DHCP:动态主机配置协议

• BOOTP:启动协议(⽤于⽆盘设备启动)

• DNS:域名解析协议

报文的封装和解包

1、报文也有结构体,对每个报文的管理,就是先描述再组织

2、每个报文包含包头和数据部分,也就是结构体和对应的内存空间

3、head和end分别指向缓冲区的头和尾

4、data指向数据区的起始,当每一层需要封装的时候,其实就只用移动data指针就行了,如下图所示

TCP

TCP报头

1、TCP首部大小不是固定的,是可变的,包含固定区域和选项字段,选项字段长度可变

2、整个报头最短长度是20字节,最多是60字节,其中4位首部长度是5,15的取值范围,单位是4字节,对应整个首部的大小是20,60

3、TCP在传输层把首部去掉之后,会把数据部分放入缓冲区,由应用层去分析是否是一个完整的报文;UDP只要去掉报头后,写入缓冲区的数据部分一定是一个完整的;所以说,UDP面相报文,TCP面向字节流。

4、会不会出现数据和下一个报头混在一起的情况?答:不会!因为一个报文对应一个sk_buff结构体!但是会出现当前报文的有效载荷和下一个报文的有效载荷黏在一起的情况。

5、缓冲区里面其实只会存放有效载荷的数据部分,已经把报头去掉了。

6、窗口:接收方告诉发送方自己还剩余多少缓冲区够发送方发送,也就是拥塞控制。

7、为啥报头会有标志位?因为需要标记报文的类型,有建立连接、断开连接、发送请求、应答等等,那就需要标识此次的报文是哪一种类型的,所以出现了6个标志位。

SYN:同步标志位,表示连接建立

三次握手:是发送方和接收方都只站在自己的立场,发送方第三次发出去就认为链接建立好了,接收方第三次收到才认为链接建立好了。因此要是第三次发送方发出去了,但是接收方没收到,接收方就是大大的?因此就会给发送方发送一个RST,要求重新建立连接。

URG:发送方紧急传送数据,不要在缓存里等;为1表明紧急指针有效,为0表示无效

8、序号

把发送缓冲区看成字符数组,上层把数据拿下来放到缓冲区中后,每一字节都有对应的地址,在传输层构建报文的时候,把数据从缓冲区拿出来,比如是1000个字节,那么报头就是第1000个字节的地址,也就是序号。

序号的作用:确认应答,按序到达,去重

发送方发送1-1000,接收方发1001,发送方再次发2000,注意,不是1001,因为发送方发的是数据末尾的那个

9、丢包

发送方没收到ack,接收方不一定没收到包,可能是响应的包丢失了而已。

10、超时重传:时间是根据网络变化来动态计算的

可靠性

1、本质:只能保证历史信息的可靠性,如图所示,不然就需要一直反复确认,无限循环了就。

2、可靠性的保证:只要对历史信息做应答就行,然后才能发送下一条,也就是只能一条一条发送。

3、TCP传递报文时,更通用的方式,一次发送多个报文,等待应答。收到返回的401说明401之前的报文都被服务器收到了。

4、这里有序号和确认号两种,为啥不是一种,发送方是200,服务器也返回200不就好了吗?因为服务器也可能会发信息,也就是捎带应答,那服务器发送的信息也需要客户端的确认号,因此,发送的报文里面必须含有序号和确认号两种

三次握手

1、OS自动完成

2、服务器的accept不参与三次握手

3、为啥要三次握手?以最短方式验证全双工!全双工:某一方既能发也能收

4、三次握手的本质:四次握手!因为服务器一定会应答+发送数据

5、第一次和第二次不能携带数据,第三次可以携带数据,因为站在发送方的角度,第三次报文发送出去之后,就认为连接已经建立,因此可以捎带应答。

四次挥手

1、shutdown,半双工,半关闭,客户端的fd关了,它不能再写,但是也可以再读服务器的数据

2、谁主动断开连接,最终谁就要等

time_wait的作用:保证下一次客户端再次发起连接的时候,网络中滞留的包到达服务器端后,会被丢弃,而且下一次重新建立连接的源端口号不会采用过去的。新的连接建立以后,双方都能甄别出老的报文了。

2MSL:保证报文在两个朝向上都能够消散

滑动窗口

1、滑动窗口:是发送缓冲区的一部分

2、滑动窗口中,传送的报文丢失。eg:1001、2001、3001、4001传送4个报文

(1)主机A的发送的1001报文丢失,2001-4001没丢,那么主机B发送的确认序号应该是1001,期待重新发送1001,滑动窗口不动

(2)主机B发送的1001的ack丢失,但是2001-4001的ack正常发送,此时滑动窗口可以正常滑动;即,单纯应答报文丢了,不怕!因为后续的应答报文会告诉发送方自己已经收到了。因为确认序号的定义就是,比如发送2001,意味着2001之前的我都收到了,也就是虽然没有收到1001,但是2001收到了也就是之前的也都收到了。

(3)丢失问题,全部转化为最左侧丢失,最左侧丢失,全部转化为快重传和超时重传的问题。

流量控制

1、发送方发的太快,接收方来不及接受,控制发送方的发送速度

2、利用滑动窗口去解决

3、流量控制不只是降低发送方发的速率,也可以增大发送速率,例如rwnd窗口变大;所以流量控制控制的是发送方和接收方速度匹配的,合适的大小,可以增大,也可以减小。

拥塞控制

1、慢开始:前期慢是为了探测网络情况,后面就要正常发送

延迟应答

1、接收方等一会,让上层把缓冲区中的数据拿走后,再把缓冲区大小返回给发送方,此时空间更大

捎带应答

1、ACK置1并且携带数据

面相字节流

1、发送方把数据放到发送缓冲区中,由操作系统决定什么时候发,一次发多少,这就是面向字节流

2 、由于缓冲区的存在,TCP程序的读和写不需要⼀⼀匹配,例如:

• 写100个字节数据时,可以调⽤⼀次write写100个字节,也可以调⽤100次write,每次写⼀个字节;

• 读100个字节数据时,也完全不需要考虑写的时候是怎么写的,既可以⼀次read100个字节,也可以 ⼀次read⼀个字节,重复100次;

TCP异常问题

保活机制

TCP底层文件调用关系

UDP底层文件调用关系

相关推荐
A小辣椒1 天前
TShark:Wireshark CLI 功能
linux
A小辣椒2 天前
TShark:基础知识
linux
AlfredZhao2 天前
OCI 明明分配了 200G 系统盘,为什么 df 只看到 30G?
linux·oci
AlfredZhao2 天前
vi 删除指定范围的行,不用再反复按 dd
linux·vi
用户9718356334663 天前
银河麒麟 KY10 申威(SW64) 安装 nginx-1.16.1-2.p01.ky10.sw_64.rpm 详细步骤
linux
猪脚踏浪3 天前
linux 拷贝文件或目录到指定的位置
linux
大树883 天前
金刚石散热越强,管路越先见顶
大数据·运维·服务器·人工智能·ai
摇滚侠3 天前
Linux CentOS7 rpm 安装 MySQL 5.7
linux·运维·mysql
霸道流氓气质3 天前
领域驱动设计(DDD)在 Spring Boot 微服务中的实践指南
运维·spring boot·微服务
bush43 天前
嵌入式linux学习记录十四、术语
linux·嵌入式