QUIC(Quick UDP Internet Connection)是Google提出的一个基于UDP的传输协议,因其高效的传输效率和多路并发的能力,已经成为下一代互联网协议HTTP/3的底层传输协议。除了应用于Web领域,它的优势同样适用于一些通用的需要低延迟、高吞吐特性的传输场景。本文从QUIC的由来和优势出发,分享实际项目中需要考虑的问题和解决思路,通过测试对比QUIC和TCP的实际传输能力,希望有助于大家理解和实践QUIC协议。

PART 01 为什么需要QUIC?

众所周知,HTTP从最初的HTTP/0.9,经历了HTTP/1.x,HTTP/2到最新的HTTP/3这几个大的更新版本。在HTTP/3版本之前,HTTP底层都是用TCP传输数据,而伴随着移动互联网的发展,网络交互场景越来越丰富并要求及时性,传统TCP固有的性能瓶颈越来越不能满足需求,原因有以下几点:
建立连接的握手延迟大
HTTPS包含两个握手:1)TCP三次握手,1个RTT;2)TLS握手,2个RTT。完整握手总共需要3个RTT,对于直播等需要首帧秒开场景,握手延迟太大。
多路复用的队首阻塞
以HTTP/2多路复用为例,多个数据请求作为不同的流,共用一条TCP连接发送,所有的流应用层都必须按序处理。若某个流的数据丢失,后面其他流的数据都会被阻塞,直到丢失的流数据重传完成其他流才能被继续传输。即使接收端已经收到之后流的数据包,HTTP协议也不会通知应用层去处理。
TCP协议的更新滞后
TCP协议是实现在操作系统内核内,但是用户端的操作系统版本升级非常困难,很多老旧的系统像WindowsXP还有大量用户使用,因此TCP协议的一些更新很难被快速推广。
正是考虑到以上的这些问题,QUIC在应用层之上基于UDP实现丢包恢复,拥塞控制,加解密,多路复用等功能,既能优化握手延迟,同时又完全解决内核协议更新滞后问题。

PART 02 QUIC的优势

这里列举下QUIC的主要优势。
握手建连更快
QUIC建连时间大约0~1 RTT,在两方面做了优化:
1)传输层使用了UDP,减少了1个RTT三次握手的延迟。
2)加密协议采用了TLS 协议的最新版本TLS 1.3,相对之前的TLS 1.1-1.2,TLS1.3允许客户端无需等待TLS握手完成就开始发送应用程序数据的操作,可以支持1 RTT和0RTT。
对于QUIC协议,客户端第一次建连的握手协商需1-RTT,而已建连的客户端重新建连可以使用之前协商好的缓存信息来恢复TLS连接,仅需0-RTT时间。因此QUIC建连时间大部分0-RTT、极少部分1-RTT,相比HTTPS的3-RTT的建连,具有极大的优势。
避免队首阻塞的多路复用
QUIC同样支持多路复用,相比HTTP/2,QUIC的流与流之间完全隔离的,互相没有时序依赖。如果某个流出现丢包,不会阻塞其他流数据的传输和应用层处理,所以这个方案并不会造成队首阻塞。
支持连接迁移
什么是连接迁移?举个例子,当你用手机使用蜂窝网络参加远程会议,当你把网络切换到WLAN时,会议客户端会立马重连,视频同时出现一瞬间的卡顿。这是因为,TCP采用四元组(包括源IP、源端口、目标地址、目标端口)标识一个连接,在网络切换时,客户端的IP发生变化,TCP连接被瞬间切断然后重连。连接迁移就是当四元组中任一值发生变化时,连接依旧能保持,不中断业务。QUIC支持连接迁移,它用一个(一般是64位随机数)ConnectionID标识连接,这样即使源的IP或端口发生变化,只要ConnectionID一致,连接都可以保持,不会发生切断重连。
可插拔的拥塞控制
QUIC是应用层协议,用户可以插拔式选择像Cubic、BBR、Reno等拥塞控制算法,也可以根据具体的场景定制私有算法。
前向纠错(FEC)
QUIC支持前向纠错,弱网丢包环境下,动态的增加一些FEC数据包,可以减少重传次数,提升传输效率。

PART 03 基于QUIC的服务架构

实际项目在应用QUIC之前,首先要对整体服务架构做一些宏观上的思考,对下面的问题进行一定的思考后,再去考虑项目本身的细节,可以规避一些技术弯路。
哪些链路需要提升传输效率?
TCP的性能瓶颈主要体现在具有数据丢包的网络,由于TCP的AIMD(加性增、乘性减)的拥塞避免策略,网络上出现少量丢包,TCP拥塞控制算法会指数级降低传输速率,导致其无法有效利用带宽。对于一些比较理想的网络,比如局域网内,TCP与QUIC的传输能力相当,传输速率受限于实际带宽,引入QUIC反而增加了复杂度。
如何兼容老的客户端?
新的架构不能影响老的客户端,因此需要同时支持TCP和QUIC。
如何实现连接迁移?
用户在4G和WIFI之间切换,如何实现连接迁移,保证业务层不中断?
QUIC是否会带来一些弊端,如何解决?
新事物产生往往会伴随新的问题,QUIC实现在内核之上的应用层,用UDP替代TCP传输,也带来了一些问题:
(1)国内运营商针对UDP做QOS限速和丢包,一些企业的局域网防火墙有时候会禁用 UDP 协议,导致网络UDP传输低效不可用。
(2)QUIC的协议栈运行在用户态,同时因为协议的复杂度,对CPU的消耗会比TCP高不少,实际实现时如何尽可能的减少QUIC对服务器性能的影响?
(3)UDP的报文长度受限于MTU,对于大块数据,QUIC在应用层切成大量的小包,收发会造成大量的系统调用sendmsg/recvmsg,因此QUIC的网络吞吐相比TCP有很大劣势。Linux系统提供了多种优化手段:1)支持批量发送函数sendmmsg,多个UDP报文,通过一次系统调用完成发送;2)开启内核GRO/GSO,在网卡驱动完成拆包和组包;3)网卡支持硬件UDP GSO offload。
考虑到以上问题之后,一般QUIC服务可以类似按照下图的架构设计。

加速链路
对以下两段链路使用QUIC加速:
1)最后一公里:因受wifi设备性能、蜂窝网络信号覆盖范围强弱等因素影响,用户终端的最后一公里网络能力参差不齐,是比较容易出现弱网的一段链路。
2)数据中心间级联:数据中心之间的数据一般会走骨干网,但在一些流量高峰时段,可能会出现网络拥塞,比较容易出现数据丢包,延时加剧。
双链路备份
客户端一般会同时支持TCP和QUIC两种传输通道,互为备份,根据两条链路的实际状况(RTT、丢包等)智能选择最优传输通道。
连接迁移的实现
如前文所述,QUIC socket采用UDP收发数据,一个连接用一个ConnectionID唯一标识,无论用户在蜂窝网络与WLAN之间如何切换,只要数据包中的ConnectionID不变,服务端可以将不同的四元组关联到同一个连接上下文,从而避免出现断网重连。但是实现无缝的连接迁移困难并不小,为了实现高并发,服务端一般都会采用多线程,多进程的架构,负载均衡根据四元组将连接ConnectionID关联到特定的运行环境(线程或进程),连接迁移大概率会导致缓存的连接上下文失效。以下图多线程的设计举例,设想CID1连接迁移发生时,用户源IP和端口由A变成C,socket绑定的线程由1迁移到2,因线程2查找不到CID1连接的上下文,导致连接迁移失败。

上图只是多线程的架构,我们可以想办法把新的socket重新bind回线程1。如果是多进程架构,负载均衡会寻址到不同的服务器上,如何将连接重新寻址到原始服务器?
业内一般的解决思路借鉴了雪花算法,在建连完成就给Server的destination ConnectionId打上初始服务器的地址标记,根据这些标记信息(集群ID+机器ID+线程ID),让新的服务器寻址到初始的服务器,后续数据再透明转发给初始服务器,整个过程仅增加了一次转发动作,对用户没有任何感知。

PART 04 传输时延测试

建连时延

上图可以看到建连有将近50%的提升,QUIC节省了2-RTT时间,对于一些RTT高网络,效果更显著。

丢包时延
为了对比TCP和QUIC在丢包网络下的表现,分别对5%、15%、30%的丢包率场景做了对比测试。每一种场景,进行1000次测试,每次测试发送10KB数据,统计最终落在指定时延以下的概率。最终的结果参考下图,横坐标表示时延,纵坐标用百分比表示指定时延下的样本数量,曲线收敛速度越快,落在较低时延范围的样本数量越多,所以时延表现越好。
5%丢包下,200ms内传输完成的测试样本,QUIC占95%,TCP占78%,QUIC比TCP提升了17%左右。

15%丢包下,200ms内传输完成的测试样本,QUIC占90%,TCP占50%,QUIC比TCP提升了90%左右。

30%丢包下,200ms内传输完成的测试样本,QUIC占62%,TCP占22%,QUIC比TCP提升了300%左右。

总结起来,QUIC相比TCP的弱网丢包下的延时提升比较比较明显,丢包率越高,提升越明显。

PART 05 总结

本文对QUIC实践中遇到的主要问题和相应解决思路做了一些分享,实际项目应用时,由于需求的多样性、现有服务架构的差异,需要因地制宜,将QUIC的一些好的特性以比较优雅地姿势应用。
关注拍乐云Pano,了解更多音视频相关技术、产品实践!

深入解析QUIC协议相关推荐

  1. 实战|QUIC协议助力腾讯业务提速30%

    hi ,大家周五好,之前分享过一篇QUIC在蚂蚁金服落地的文章: 实战|QUIC协议在蚂蚁集团落地 今天我们分析一篇,QUIC在腾讯落地的文章,希望大家了解和学习新技术是如何在大厂落地,其中会遇到什么 ...

  2. E百科 | 第2期 扒一扒能加速互联网的QUIC协议

    简介: 众所周知,QUIC(Quick UDP Internet Connection)是谷歌制定的一种互联网传输层协议,它基于UDP传输层协议,同时兼具TCP.TLS.HTTP/2等协议的可靠性与安 ...

  3. 扒一扒能加速互联网的QUIC协议

    简介:众所周知,QUIC(Quick UDP Internet Connection)是谷歌制定的一种互联网传输层协议,它基于UDP传输层协议,同时兼具TCP.TLS.HTTP/2等协议的可靠性与安全 ...

  4. HTTP和QUIC协议以及HTTPS——学习笔记

    HTTP的特征 HTTP 简单 灵活和易于扩展 HTTP在应用层,他的下层可以随意变化,比如:HTTPS就是在HTTP和TCP之间加上SSL/TLS安全传输层,HTTP/3把下层的TCP换成了基于UD ...

  5. 谈谈QUIC协议原理

    QUIC,又名HTTP3,是近年来诞生的非常厉害的传输协议,它利用UDP解决了当前基于TCP协议的HTTP的许多问题,提升了在弱网环境下的网络通信体验.让我们来一探究竟! 1.1 什么是QUIC? Q ...

  6. QUIC协议原理详解

    1.QUIC是啥? 1.1 什么是QUIC QUIC(Quick UDP Internet Connection)是谷歌推出的一套基于UDP的传输协议,它实现了TCP + HTTPS + HTTP/2 ...

  7. QUIC 协议是如何在蚂蚁集团落地的?

    点击上方"芋道源码",选择"设为星标" 管她前浪,还是后浪? 能浪的浪,才是好浪! 每天 10:33 更新文章,每天掉亿点点头发... 源码精品专栏 原创 | ...

  8. 网络编程之一泡尿的时间,快速读懂QUIC协议

    网络编程之一泡尿的时间,快速读懂QUIC协议 TCP协议到底怎么了? QUIC协议登场 QUIC协议的目标 QUIC协议这么好,可以大规模切换为QUIC吗? QUIC协议实践 我想试试QUIC协议,可 ...

  9. QUIC协议初探-iOS实践

    本文来自于腾讯Bugly公众号(weixinBugly), 作者:emilymmwang,未经作者同意,请勿转载,原文地址:https://mp.weixin.qq.com/s/NbewZ1NU49q ...

最新文章

  1. php播放音乐视频,html5停止(暂停)当前播放的音频或视频的方法pause()
  2. Oracle数据库名与Oracle实例名的关系
  3. c++ege为什么直线画不出来_今天让我们来练习画一款椭圆茶几
  4. 肝!Python 教程:从零到大师
  5. 使用 ASMCMD 工具管理ASM目录及文件
  6. Free Code Camp现在有本地组
  7. java nio copy_使用NIO快速复制Java文件
  8. os如何读取图片_CV:基于face库利用cv2调用摄像头根据人脸图片实现找人
  9. Python之路:初识
  10. 【PAT甲】1001 A+B Format (20分) 格式化输出
  11. QT之计算器对四则运算表达式的解析(九)
  12. linux运行j2me,Linux下用Eclipse搭建J2me开发环境过程
  13. Python 数据挖掘(一) 模块安装部署 numpy等
  14. 前端vue后台管理系统项目优化
  15. 读书笔记:《世说新语》
  16. P2141 珠心算测验
  17. 2012服务器系统如何备份,windows server 2012 r2 如何进行系统备份?
  18. 《沟通的技术——让交流、会议与演讲更有效》一1.1 一切尽在计划之中
  19. Apple M1 上安装tensorflow开发环境
  20. C# 闹钟「定时提醒,整点报时」

热门文章

  1. 原神迷城战线光界篇增幅试炼怎么过
  2. linux在线模拟终端
  3. jquery的delegate实现原理
  4. 一文搞懂 Node入门框架 Koa2 原理,学它!
  5. Submit Text 3 使用SVN
  6. 内网外网同时使用——双网关设置
  7. App.Config详解及读写操作
  8. Connected component
  9. 同一行中输出不同颜色文字
  10. 算法设计与分析——十大经典排序算法二(6--10)