im即时通讯开发:网络通信传输层协议——UDP和TCP

互联网发展至今已经高度发达,而对于互联网应用(尤其即时通讯网专注的即时通讯技术这一块)的开发者来说,网络编程是基础中的基础,只有更好地理解相关基础知识,对于应用层的开发才能做到游刃有余。

相信计算机专业的朋友在大学都学过《计算机网络》这门课程,但据我个人了解计算机专业普通大学生对计算机网络的了解浅之又浅,很多人说这门学科没用,开发的时候也用不着,其实这样想是不对的。

UDP的全称是User Date Protocal,翻译成中文是用户数据包协议,它是一种不可靠的传输协议,一般情况下一个数据包(大概64K)能完成的数据通讯使用UDP协议,比如请求DNS解析IP地址使用的就是UDP协议,因为解析IP一个数据包完全足够。还有就是文字聊天一般用的也是UDP,通常一段文字消息一个数据包就足够了,如果发送失败就再次发送,反正就一个数据包。还有一种传递大量数据包使用UDP协议的场景,就是广播,类似对讲机之类的,接收方并不一定能接收到所有的数据包。所以说UDP是一种不可靠的传输协议。

UDP的主要特点:

1)UDP是无连接的,即发送数据之前是不需要建立连接的;

2)UDP使用尽最大努力交付,不保证可靠交付,同时不使用阻塞控制;

3)UDP是面向报文的,UDP没有拥塞控制,很适合多媒体通信的要求;

4)UDP支持一对一、一对多、多对一、多对多的交互通信;

5)UDP的首部开销小,只需要8个字节。

UDP首部总共是8个字节,其中源端口、目的端口、长度、检验和各占2字节。有的同学可能要问了,你怎么没把伪首部加进去呢?这个我来讲一下,伪首部顾名思义,就是假的首部,它是不会跟随UDP数据报进行传输的,它存在的意义就是为了计算UDP首部中的检验和。

UDP首部存储的信息:

1)源端口:即发送方的端口号,需要接收方回应时选用,不需要全为0;

2)目的端口:接收方端口号;

3)长度:UDP数据报长度,最小为0(只存在首部);

4)检验和: 检验UDP数据报在传输中是否出错,是就丢弃。

UDP首部组装完毕后会将完整的数据报发送到网络层,跟IP数据报首部组成IP数据报再向上发送。

TCP全称为Transmission Control Protocol(传输控制协议),是一种可靠的面向连接传输协议,同时它也是一种client-server模式的协议,因为是可靠的传输协议,所以它比UDP要复杂的多。

首先说一下TCP具有的一些特性:

1)TCP是面向连接的传输协议;

2)每一条TCP有且只有两个端点,为一对一关系;

3)TCP提供可靠交互的服务;

4)TCP提供全双工通信,全双工为即可传输又可接收;

5)TCP是面向字节流的。

TCP的应用场景:

如果两个台主机想要在网络上传递一部1G大小的电影,需要通过什么协议进行传输呢?UDP为不可靠传输协议,传递过程中可能会出现丢包,所以UDP不行,而传输层就两个协议,一个是UDP一个是TCP,UDP传输效率高但不可靠,TCP传输效率低但它是可靠的,所以想要将传递的文件完整的到达目的地可以通过TCP协议进行传输。

im即时通讯开发:网络通信传输层协议——UDP和TCP_第1张图片

客户端向服务端发起建立连接的请求,服务端接收到请求后告诉客户端:“我准备好了”,客户端接收到服务端的响应再给服务端一个确认,此过程总共分为三步被大家亲切的成为:“三次握手”,三次握手后一个可靠的连接就建立了,随后就可以进行数据的传输了,图中SYN、ACK这些字段我会在TCP首部中详细介绍,此处大家可以忽略。

疑点: TCP建立连接为什么是三次握手?两次握手不是已经可以建立一个连接了吗?网络上很多文章对此处的描述大多是轻描淡写,还有的说是必须要三次握手才能建立一个可靠连接,其实这样说是不对的,当时我也因为这些不负责任的回答费解了很久。一般情况下,两次握手是可以建立一个TCP连接的,在《计算机网络-谢希仁》中大概是这样解释的:“第三次握手是为了避免服务端造成资源的浪费”,为什么这样说呢?我来给大家举一个例子:

假如TCP是两次握手:主机A向主机B发送了一个建立连接的请求x,但这个请求在半路里给堵了,主机A没有得到主机B的响应于是又发了一个建立连接的请求y,主机B收到了请求y,于是给主机A发送了一个确认,此时连接建立,数据传输完毕后断开了连接,但在断开连接后堵在半路的请求x到达了主机B,此时主机B认为主机A又给自己发送了一个建立连接的请求,于是给主机A发送了一个确认,此时主机B认为连接已经建立,处于等待状态从而导致主机B资源的浪费。但如果是三次握手就可以避免这种情况的出现,所以这才是TCP第三次握手的原因。

主机A至主机B数据传输结束后主机A会向主机B发送一个断开连接请求,主机B收到后给主机A一个确认,A就不可向B传输数据了,但此时主机B仍然可以往主机A传输数据,等B->A数据传输结束后主机B向主机A发送一个断开连接请求。主机A收到后给予一个确认,这样就成功断开一个TCP连接,过程分四步,也被大家亲切的称为:“四次挥手”。即时通讯聊天软件开发可以咨询蔚可云。

疑点:断开连接为什么是四次挥手?两次不就可以了吗?下面我来用一个形象的例子来个大家解除疑点

TCP是全双工的:即client和server都可以进行传输和接收,假设主机A和主机B建立了一个TCP连接,主机A可以往主机B发送数据同时主机B也可以往主机A发送数据,现在我将主机A->主机B描述成一根水管x,水管x只能由A流到B,主机B->主机A为水管y,水管y只能由B流到A,现在水管x已经完成的它的输送水源工作,此时就可以将水管x切除,对应图中前两次挥手,但此时水管y还在工作,必须要等水管y工作完成后才能够将其切除,切除水管y对应图中后两次挥手。

im即时通讯开发:网络通信传输层协议——UDP和TCP_第2张图片

TCP首部的各项内容解释:

1)源端口:发送方端口号;

2)目的端口:接收方端口;

3)序号:数据包的序号,以数据包第一个字节进行表示;

4)确认号:确认收到数据包的序号,同样以字节进行标识;

5)数据偏移:TCP首部长度,以字节为单位;

6)保留:保留位,总共6为,必须都为0;

7)URG:紧急处理,可提升数据包发送的优先级;

8)ACK:代表确认号是否有效;

9)RST:将建立的连接重置;

10)PSH:接收方应尽快将这个报文交给应用层;

11)SYN:同步序号用来发起一个连接;

12)FIN:终止一个连接。

TCP进行可靠传输

我们知道网络传输是不可靠的,可能存在丢包的现象,TCP是可靠的传输协议,那么它是怎么做到可靠传输呢?我来用几张图为大家分析TCP师怎样进行可靠传输的。

情况a:A发送给B数据包M1,B收到之后进行确认,这样M1包就发送成功了,以此类推,这是无差错的情况。

情况b:A发送数据包M1给B,但中途被丢弃了,如果A迟迟等不到B的响应那么A就会重新发送M1包给B。

情况a:A发送数据包M1给B,B收到后给A发送一个M1的确认包但该确认包在中途被丢弃了,A迟迟未收到B的确认包就认为M1发送包或者M1确认包早中途丢失了,于是又发送了一个M1包给B,B又收到了一个M1包,此时B就可以认为M1确认包可能在中途丢失了,将重复的M1包丢弃后再给A发送一个M1确认包;

情况b:A发送数据包M1给B,B收到后给A发送一个M1确认包,但该确认包选择了一个较远的传输路线或者被阻塞了,A迟迟未收到M1确认包就再给B发送一个M1包,B收到重复的M1包后将其丢弃然后再给A发送一个M1确认包,A收到M1确认后就认为M1发送成功,但此时A收到半路阻塞的那个M1确认包,而A已经确认了M1包发送成功,所以再次受到M1确认包后什么也不做。

client-server可以通过传递确认的方式来实现可靠传输,但这种传输方式有一个缺点,效率太低,因为在未收到确认包前是不可以发送下一个包的,那么我们能不能突破这一限制来提升传输效率呢?我们可以通过提升信道的利用率来提升传输效率。

注意点:

上面的内容中我为了方便讲解都是把数据包编成编号进行描述,其实真正的数据包编号不是这样的,TCP协议是面向字节流的,所以说序号和确认号应以字节为标准,比如:A现在向B发送了5和数据包共100个字节,B收到这5个数据包后会给A回复一个101,此时A就会从第101个字节开始进行发送,以此类推。同时通过这种机制也可以实现断点的下载。

你可能感兴趣的:(即时通讯)