其次是安全问题,也就是反射攻击,即伪造原地址。这个指发送数据包时的原地址是伪造的,不是真正的地址,会引起放大攻击。原因是 QUIC 握手过程是不对称的,特别是第一次请求时,客户端只需要发送几个字节的信息到服务器,而服务器则需要把证书等很多东西返还给客户端,这个不对称的机会造成了放大。草案 27 定义了两个规则和机制来限制反射攻击:客户端发送Initial包,即第一个数据包时,其长度必须在 1200 bytes以上,不足部分用 Padding 帧填充,同时,当服务端不确定客户端可靠性时,可以发送 Retry 包要求客户端再次提供验证信息。
开源 QUIC 的实现接下来我们简单说一下目前开源的使用情况:
quiche:这个是用 Rust 做的库,通过 Nginx 调用。google 自己的库也叫 quiche,C++写的。
ATS:Apache Traffic Server
golang:Caddy;
python+C,aioquic
微软msquic
开源 QUIC 的实现有很多,上面只是其中的一部分,同时我选择了quiche 和 aioquic 做了一些简单测试。
上图展示的是从 cloudflare 提供支持 HTTP3 的 curl ,可以看到这个返回的值就是 HTTP/3 200。其中 alternative service 段,指示为 h3—27,表示支持 http3 draft-27 的服务跑在 UDP 443 端口。这个 alt-svc 是 HTTP2 时代就存在,在 HTTP3 也持续使用,因为有些时候浏览器并不知道服务器是否支持 QUIC,所以通过 TCP 发起请求,确定有 H3 支持后,再通过 UDP连接。
这个是 HTTP2 的,目前可能是因为本身库的问题,使用 curl 打不开谷歌,但是从信息上可以看到 27、25 这些都是支持的。
如何部署以及达成 HTTP3 的 QUIC 实现目前主要有两种方式来实现,一种是代理,第二种是通过 Nginx。
腾讯是通过整合到 Nginx 利用它来实现框架的。同时因为 QUIC 每一条请求的含有头的数据都会经过加密,腾讯有一个单独的硬件加密群,如果你使用腾讯,那么你所有的加解密都会通过他们的硬件来加速。
从腾讯这个可以看出加解密部分有着很可观的 CPU 占用率,如果后续所有的请求都是通过 HTTP3 来进行的话,在提升这块占用率上需要未雨绸缪。当然就像前面提到的 DPDK,也就是把数据丢到 FPGA 内去加解密是一个可以考虑的解决方案。
通过代理来实现的这种方式,目前官方暂时还没有消息。我可以像 cloudflare 那样,先在外面进行整合,然后再讲整合链接转到 Nginx 内。
又拍云目前有 LBS 和 Marco ,这个是因为 LBS 只认 TCP/UDP,它看不到 HTTP。也就是我们做了一个负载均衡的集群,通过这个集群在转到 Nginx 上。而使用 UDP 则相当于已经走过了一个四层的负载均衡,那么后续可以尝试将 QUIC 的基线提取出来使用,在代理上做加解密,从而提高效率。