网络知识小结:TCP与UDP,HTTP与HTTPS

295 阅读14分钟

我曾七次鄙视自己的灵魂

第一次

当它本可进取时

却故作谦卑

—— 纪伯伦《我曾七次鄙视自己的灵魂》

OSI七层网络模型

七层网络模型是网络理论的基础,单靠死记硬背并不那么轻松,很容易搞混,重要的还是理解为什么这样设计分层。

osi.jpg

TCP与UDP

它们同属于传输层Transport的协议。

TCP的三次握手与四次挥手

TCP建立连接需要经历三次握手,断开连接需要经历四次挥手。它是一种面向连接的协议,基于虚拟的管道进行通信。

对于三次握手通俗的解释如下:

  1. 客户端通知服务器,我已准备好,尝试向你建立连接(类型为SYN=1,值为seq=x
  2. 服务器收到客户端的请求,并通知客户端,我已收到你的数据(类型为ACK=1,值为ack=x+1),现在请确认你是否可以收到我的数据(类型为SYN=1,值为seq=y
  3. 客户端再次通知服务器,我可以收到你的数据(类型为ACK=1,值为ack=y+1)。双方进入ESTABLISHED状态

3shakes.webp

建立连接后,双方进行数据传输。当双方同处于ESTABLISHED状态下,完成数据传输后,可以进行四次挥手,通俗解释如下:

  1. 客户端判断自己已经获取到全部想要取得的数据,通知服务器我想要断开连接(类型为FIN=1,值为seq=u
  2. 服务器收到请求后,立即发出确认报文(类型为ACK=1,值为ack=u+1,同时传递seq=v)。此时客户端->服务器这条方向的连接被释放,客户端主机已经不再有数据发送;但服务器->客户端这条方向的数据可能仍处于传输中
  3. 当服务器不再有数据传输时,服务器通知客户端我已经把数据全都传完了(报文类型为FIN=1,值为seq=w,同时类型为ACK=1ack=u+1)。注意此时seq=w与第二次挥手中的seq=v不一定相等,因为二三次挥手之间可能又传输了一些数据
  4. 客户端收到服务器发来的报文,通知服务器断开连接(类型ACK=1,值为ack=w+1,同时seq=u+1

可以看到四次挥手分成两部分,分别是客户端->服务器尝试断开连接的报文来回,以及服务器->客户端确认断开连接的报文来回。

4shakes.webp

TCP是面向连接的,数据正式传输前需要建立一条虚拟连接,数据的传输在这条虚拟连接上进行,并且完成传输后需要断开连接。而UDP传输不面向连接,并且,UDP不关心接收方的接收状态。

TCP与UDP的差异

这两个传输层协议在可靠性、有序性、报文结构、传输效率方面有所差别。

可靠性差异

可靠性即指发送方是否保证数据传输到,以及发送方是否知悉发送结果。TCP是可靠的传输层协议,UDP则不可靠。

TCP通过应答号ACK和序列号SEQ来保证可靠性。首先说应答信号ACK,当发送方发送数据后,必须等待接收方返回ACK信号,如果经过一段时间没有收到对方返回的ACK信号,则发送方判断此次发送失败,会进行重试。

此过程中有两个地方可能导致发送方收不到ACK信号,分别是发送数据传输失败,和ACK信号传输失败,在发送方看来这都是发送失败,都需要进行重试。

发送失败

send_fail.webp

ACK失败

ack_fail.webp

我们假设一个场景,发送方发送了一条数据A出去,此时由于网络环境波动,传输速率下降,导致经过超时时间仍未返回ACK信号。此时发送方认为自己发送失败了,再次发送同一条数据A'过去,但网络恢复后,接收方会同时收到AA'两条“相同”的数据。对于接收方而言,又要如何判断采纳哪一条、抛弃哪一条?这种现象称为“延迟到达”

这就是序列号SEQ的用武之地,发送方在发送数据时,会按照数据本身字节的顺序,为报文增加一个序列号U;接收方在收到数据并回文ACK时,同样携带一个序列号U+1,表明我已收到你发来的U,接下来请发送U+1的数据。对于延迟到达的情况,接收方收到两个相同的数据包,自然可以根据序列号保留它所需要的正确的那个。

有序性差异

TCP协议在传输数据时,接收方会根据序列号SEQ对收到的报文进行重排,从而保证接收的有序性。而UDP则不具备这些机制,这是两者在有序性上存在的巨大差异。

报文段差异

作为传输层Transport协议,传输的数据统称为报文段

UDP报文段

udp_msg.webp

  • 源端口号(Source Port): 这个字段占据 UDP 报文头的前 16 位,通常包含发送数据报的应用程序所使用的 UDP 端口。接收端的应用程序利用这个字段的值作为发送响应的目的地址。这个字段是可选项,有时不会设置源端口号。没有源端口号就默认为 0 ,通常用于不需要返回消息的通信中
  • 目的端口号(Destination Port): 表示接收端端口,字段长为 16 位
  • 长度(Length): 该字段占据 16 位,表示 UDP 数据报长度,包含 UDP 报文头和 UDP 数据长度。因为 UDP 报文头长度是 8 个字节,所以这个值最小为 8,最大长度为 2 ^ 16 = 65535 字节
  • 校验和(Checksum):UDP使用校验和来保证数据安全性,UDP的校验和也提供了差错检测功能,差错检测用于校验报文段从源到目标主机的过程中,数据的完整性是否发生了改变

TCP报文段

tcp_msg.webp

相比于UDP,TCP的报文结构上增加了一些用来保证可靠性、有序性的字段。

  • 32 比特的序号字段(sequence number field) 和 32 比特的 确认号字段(acknowledgment number field) 。这些字段被 TCP 发送方和接收方用来实现可靠的数据传输。
  • 4 比特的首部字段长度字段(header length field),这个字段指示了以 32 比特的字为单位的 TCP 首部长度。TCP 首部的长度是可变的,但是通常情况下,选项字段为空,所以 TCP 首部字段的长度是 20 字节。
  • 16 比特的接受窗口字段(receive window field) ,这个字段用于流量控制、拥塞控制。它用于指示接收方能够/愿意接受的字节数量
  • 可变的选项字段(options field),这个字段用于发送方和接收方协商最大报文长度,也就是 MSS 时使用
  • 6 比特的标志字段(flag field), ACK 标志用于指示确认字段中的值是有效的,这个报文段包括一个对已被成功接收报文段的确认;RST、SYN、FIN 标志用于连接的建立和关闭;CWR 和 ECE 用于拥塞控制;PSH 标志用于表示立刻将数据交给上层处理;URG 标志用来表示数据中存在需要被上层处理的 紧急 数据。紧急数据最后一个字节由 16 比特的紧急数据指针字段(urgeent data pointer field) 指出。一般情况下,PSH 和 URG 并没有使用。

效率差异

UDP发送的报文段是不需要确认的,传输效率相对较高。

TCP则引入了用来解决性能问题的“窗口”概念,在往返时间较长、频次较多的情况下,可以克制网络性能带来的传输速率下降。

滑动窗口是用来一次发送多个报文段的容器,在一个窗口中的报文可以不经确认应答便持续发送,在窗口的缓冲区中,记录了发送出去的报文,当有确认请求回来时,将相对应的请求从缓冲区移除。

如果窗口中的某个请求失败,整个缓冲区会进行重新发送。

笔者:不确定,这样效率难道不会降低吗,为啥不单独重试?

window.webp

使用场景差异

TCP协议的使用场景

  • 对传输可靠性有要求:HTTP协议

UDP协议的使用场景

  • 对传输速率有要求:Ping、DNS Lookup、视频流、即时通讯

在即时通讯场景下,如何避免UDP带来的丢包、时序问题

qq.jpeg

以QQ为例,QQ采用的通信协议以UDP为主,TCP为辅。由于UDP本身不是可靠的传输协议,QQ采用了上层协议来保证数据传输的可靠性:如果客户端使用UDP协议发出消息后,服务器收到该包,需要使用UDP协议发回一个应答包,如此来保证消息可以无遗漏传输。之所以会发生在客户端明明看到"消息发送失败"但对方又收到了这个消息的情况,就是因为客户端发出的消息服务器已经收到并转发成功,但客户端由于网络原因没有收到服务器的应答包引起的。

QQ 并不是端对端的聊天软件,是得经过服务器转发消息的,通过 QQ 聊天,数据是 A 发到服务器,服务器再转发到 B。

HTTP与HTTPS

它们都是应用层协议,定义了客户端与服务器之间响应的模型。客户端与服务器的角色是不固定的,取决于在一次数据传输中,谁担任发送者,谁担任接收者。

HTTP 超文本传输协议 Hyper Text Transport Protocal

HTTP协议建立在传输层协议TCP之上,客户端通过与服务器建立TCP连接,之后发送HTTP请求与接收HTTP响应都是通过访问Socket接口来调用TCP协议实现。

http.webp

HTTP目前已经演化到3.0版本,它们中高版本是向下兼容低版本的。

http_versions.webp

  • HTTP/0.9:已过时。只接受 GET 一种请求方法,没有在通讯中指定版本号,且不支持请求头。由于该版本不支持 POST 方法,所以客户端无法向服务器传递太多信息。
  • HTTP/1.0:这是第一个在通讯中指定版本号的 HTTP 协议版本,至今仍被广泛采用,特别是在代理服务器中。可以支持POST、HEAD方法,支持HTML文件以外的其他类型,但不支持持久连接。
  • HTTP/1.1:引入了持久连接,即TCP连接默认不关闭,可以被多个请求复用,能很好地配合代理服务器工作。还支持管道方式机制,即在同一个TCP连接里面,客户端可以同时发送多个请求,以便降低线路负载,提高传输速度。
  • HTTP/2.0:完全多路复用,在一个连接里,客户端和浏览器都可以同时发送多个请求或回应,而且不用按照顺序一一对应。引入了头信息压缩机制,使用gzip或compress压缩后再发送。支持服务端推送,允许服务器未经请求,主动向客户端发送资源。
  • HTTP/3.0:不用TCP作为传输层协议,使用基于UDP的QUIC(Quick UDP Internet Connections)协议。QUIC集成了TLS加密、流量控制、多路复用等功能,并在用户空间实现了快速连接建立、前向纠错、更精细的拥塞控制等特性。采用TLS1.3作为默认安全层协议,提供更强的安全性。

HTTP协议的特点

注意,这些特点是HTTP、HTTPS协议所共有的,因为HTTPS就是基于HTTP增加了安全机制。

  • 支持客户端/服务器模式
  • 简单快速:客户向服务器请求服务时,只需传送请求方法和路径
  • 灵活:HTTP允许传输任意类型的数据对象。正在传输的类型由Content-Type加以标记
  • 无连接:限制每次连接只处理一个请求。服务器处理完客户的请求,并收到客户的应答后,即断开连接。采用这种方式可以节省传输时间
  • 无状态:协议对于事务处理没有记忆能力,服务器不知道客户端是什么状态。即我们给服务器发送HTTP请求之后,服务器根据请求,会给我们发送数据过来,但是,发送完,不会记录任何信息

HTTP状态码

状态码含义举例
1XX信息提示
2XX正常200
3XX重定向301永久,302临时
4XX客户端错误401用户密码错误,403访问被拒绝,404文件不存在
5XX服务器错误501服务器内部错误,502无效网关,504网关请求超时

HTTPS 安全套接字层超文本传输协议 Hyper Text Transport Protocal Secure

HTTPS是在HTTP的基础上在HTTP和TCP之间又加入了SSL/TLS协议,通过这个协议可以验证服务器的真实身份,也可以对数据传输进行加密保证它的安全性。需要CA证书,且端口变为443(HTTP端口是80)。

私钥、公钥、对称/非对称加密

私钥与公钥是非对称加密用到的概念:

  • 公钥:在加密过程中,用于编码数据;在签名过程中,用于验证签名
  • 私钥:在加密过程中,用于解码数据;在签名过程中,用于生成签名

在对称加密中,加密&解密使用同一个密钥,一旦这个密钥泄漏,传输的数据就相当于变为明文。而在非对称加密中,即使泄漏了公钥,只要私钥仍然有效,服务器的身份就还是安全的。私钥的存在可以保证服务器大盘的安全性。

HTTPS流程

  1. 客户端发起HTTPS请求,连接到服务器的443端口。
  2. 服务器必须要先申请好一套数字证书(证书内容有公钥、证书颁发机构、失效日期等)。
  3. 服务器将自己的数字证书发送给客户端(公钥在证书里面,私钥由服务器持有)。
  4. 客户端收到数字证书之后,会先验证证书的合法性。如果证书验证通过,就会使用伪随机数生成器(/dev/random)随机生成一个【对称密钥】,使用证书的公钥加密这个【对称密钥】。
  5. 客户端将公钥加密后的【对称密钥】发送到服务器。
  6. 服务器接收到客户端发来的密文密钥之后,用自己之前保留的私钥对其进行非对称解密,解密之后就得到客户端的【对称密1. 钥】,然后用客户端的【对称密钥】对返回数据进行加密,这样传输的数据都是密文了。
  7. 服务器将加密后的密文数据返回到客户端。
  8. 客户端收到后,用自己的【对称密钥】对其进行对称解密,得到服务器返回的数据。

encryption.webp

HTTP与HTTPS的区别

  • HTTP 是明文传输协议,HTTPS 协议是由 SSL+HTTP 协议构建的可进行加密传输、身份认证的网络协议,比 HTTP 协议安全。
  • HTTPS比HTTP更加安全,对搜索引擎更友好,利于SEO,谷歌、百度优先索引HTTPS网页;
  • HTTPS需要用到SSL证书,而HTTP不用【(HTTPS是安装SSL的服务器,HTTP是未安装SSL的服务器)】;
  • HTTPS标准端口443,HTTP标准端口80;
  • HTTPS基于应用层+表现层+传输层,HTTP基于应用层+传输层;
  • HTTPS在浏览器显示绿色安全锁,HTTP没有显示。

参考资料