这是本节的多页打印视图。 点击此处打印.

返回本页常规视图.

1 - DoT vs DoH vs DoQ

DoT

DNS over TLS(DoT)是一种基于 TLS 的 DNS 加密协议。TLS 1.2 至少需要四次往返,TLS 1.3 则至少需要三次往返,而 DNS 请求仅需一次往返。

时间轴
  ┌───────────────────────────────────────────────────────────────────────┐
  │                          客户端                                       服务器
  │                                                                        │
  │  客户端发送 SYN 段                                                    │
  │  ────────────────────────────────────────────────────────────────────▶│
  │  SYN = 1, Seq = x                                                     │
  │                                                                        │
  │  ←─────────────────────────────────────────────────────────────────────│
  │  服务器响应 SYN-ACK 段                                                │
  │  SYN = 1, ACK = 1, Seq = y, Ack = x + 1                               │
  │                                                                        │
  │  客户端发送 ACK 段                                                    │
  │  ────────────────────────────────────────────────────────────────────▶│
  │  ACK = 1, Seq = x + 1, Ack = y + 1                                    │
  │                                                                        │
  │  TCP 连接建立                                                         │
  │  客户端发送 ClientHello                                               │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │  ←─────────────────────────────────────────────────────────────────────│
  │  服务器响应 ServerHello                                               │
  │  服务器发送证书链                                                      │
  │                                                                        │
  │  客户端发送密钥交换消息                                                │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │  服务器发送密钥交换消息                                                │
  │  ←─────────────────────────────────────────────────────────────────────│
  │                                                                        │
  │  客户端发送 Finished                                                   │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │  服务器发送 Finished                                                   │
  │  ←─────────────────────────────────────────────────────────────────────│
  │                                                                        │
  │  TLS 握手完成                                                         │
  │  客户端发送 DNS 查询                                                   │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │  ←─────────────────────────────────────────────────────────────────────│
  │  服务器响应 DNS 查询                                                   │
  │                                                                        │
  └───────────────────────────────────────────────────────────────────────┘

TLS 1.2 的握手过程需要至少两个往返(RTT),即客户端发送 ClientHello,服务器回复 ServerHello 和证书,然后客户端发送 ClientKeyExchange 和 ChangeCipherSpec,最后服务器发送 Finished。TLS 1.3 将握手过程简化为一个往返(1-RTT)。客户端在发送 ClientHello 时可以包含密钥共享信息(ClientKeyShare),服务器在回复 ServerHello 时也包含密钥共享信息,从而在第一个往返内完成密钥协商和握手。

DoH

DNS over HTTPS(DoH)是一种基于 HTTPS 的 DNS 加密协议。HTTPS 是基于 TCP 的协议,建立连接需要至少三次往返,而 DNS 请求仅需一次往返。因此,DoH 在三种加密 DNS 协议中速度最慢。

相较于 DoT,DoH 的协议开销较大,需要额外的 HTTP 协议头,导致服务略慢于 DoT。其他方面与 DoT 类似。

DoQ

DNS over QUIC(DoQ)是一种基于 QUIC 的 DNS 加密协议。QUIC 是基于 UDP 的协议,建立连接需要两次往返,DNS 请求仅需一次往返。因此,DoQ 是三种加密 DNS 协议中速度最快的。

时间轴
  ┌───────────────────────────────────────────────────────────────────────┐
  │                         客户端                                      服务器
  │                                                                        │
  │  客户端发送初始包(Initial Packet)                                   │
  │  包含:QUIC版本号、连接ID、加密握手消息(ClientHello)、可能的应用层数据  │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │                                                                        │
  │  ←─────────────────────────────────────────────────────────────────────│
  │  服务器响应初始包(Initial Packet)                                   │
  │  包含:加密握手消息(ServerHello、Certificate、ServerKeyExchange等)    │
  │  可能包含对客户端0-RTT数据的确认或拒绝                                │
  │                                                                        │
  │  客户端发送加密握手消息(EndOfEarlyData、Finished)                    │
  │  ────────────────────────────────────────────────────────────────────▶│
  │                                                                        │
  │  服务器发送加密握手消息(Finished)                                   │
  │  ←─────────────────────────────────────────────────────────────────────│
  │                                                                        │
  │  握手完成                                                             │
  │  连接建立                                                             │
  │  数据传输开始                                                         │
  │  ────────────────────────────────────────────────────────────────────▶│
  │  ←─────────────────────────────────────────────────────────────────────│
  │  数据传输                                                             │
  │  数据传输                                                             │
  │  数据传输                                                             │
  └───────────────────────────────────────────────────────────────────────┘

QUIC 使用 TLS 1.3 或更高版本来保护其连接的安全性。加密握手过程与传统的 TLS 握手相似,但通过 QUIC 的数据包格式进行,允许在握手的同时开始数据传输。如果客户端之前已与服务器建立了 QUIC 连接,则在新的连接尝试中可以立即发送应用层数据,无需等待服务器响应。这种机制称为 0-RTT,可以显著减少交互延迟。然而,0-RTT 数据可能因重放攻击的风险而被服务器拒绝。

QUIC 的设计目标是提供比 TCP 更快的连接建立速度和更好的拥塞控制,同时保持与现有网络基础设施的兼容性。通过上述步骤,QUIC 能够在首次连接时实现快速握手,并在后续连接中利用 0-RTT 进一步减少延迟。

结论

在较为稳定的网络环境中,DoQ 理论上速度最快,这得益于其基于 UDP 和 TLS 1.3 的特性。然而,实际网络中由于 UDP 的无连接状态,业务繁忙时可能会被运营商随机丢弃,导致连接不稳定。DoT 的速度略慢于 DoQ,但基于 TCP,其连接更为稳定。DoH 的速度稍慢,由于基于 HTTP 的协议功能更多,可以在服务后端实现更多功能。应根据自身的网络环境和需求选择合适的加密 DNS 协议。

Reference

2 - 最快的DNS

普通用户通常测量的是明文 DNS 的 IP 的 ping 相应速度,但这很难保证是否是真正到达对应服务器的速度。现代 DNS 至少需要使用加密 DNS 才能确保服务未被劫持。

从客户端到终端通常会经过 5 到 8 个网络设备,在其中任意一个设备上都可以劫持 UDP:53 请求,这种劫持命令非常简单。因此,不要对明文 DNS 抱有任何侥幸的期待,特别是企业用户,基本上都会遭遇劫持。

以下是劫持命令示例: sudo iptables -t nat -A PREROUTING -p udp --dport 53 -j DNAT --to-destination 1.1.1.1:53

设置劫持非常简单,许多企业内网用户的 DNS 速度都在个位数毫秒范围内,而在家庭网络中通常小于 1 毫秒。无论配置什么明文 DNS,最终都是自建的 DNS 服务在响应。

接下来讨论加密 DNS 的速度。在讨论之前,先介绍三种常见的加密 DNS 协议:DNS over TLS (DoT)、DNS over HTTP (DoH) 和 DNS over QUIC (DoQ)。

理论上,三种加密协议和未加密 DNS 的简化实现方式:

  • 最快的是 DoQ。QUIC 基于 UDP,建立连接需要一次往返,DNS 请求只需一次往返。
  • DoT 建立连接, tls1.2 需要至少四次往返, tls1.3 需要三次往返,略慢于 DoQ,DNS 请求一次往返。
  • DoH 基于 HTTPS,建立连接需要至少四次往返, 由于 HTTP 协议较重, 导致服务会略慢于 DoT。
  • 传统的 UDP:53 不需要建立连接,只有一次往返。

也就是说,从零开始的 DNS 请求,加密 DNS 的耗时是未加密 DNS 的 2~4 倍左右,但在建立连接后,耗时与未加密 DNS 相同(未考虑连接强制关闭的情况)。

考虑到实际网络情况,运营商在流量繁忙时会随机丢弃 UDP 报文。由于 TCP 有重传机制,丢弃后会再次传输,无法通过丢弃 TCP 来减轻网络负担,因此运营商较少丢弃 TCP 报文。因此,TCP 的 DNS 请求速度会更稳定,特别是在晚间网络高峰时段。

此外,仅关注连接时间不会显著提升上网体验。DNS 协议中包含许多可设置的参数,其中一些参数的合理配置比选择一个服务器更能提升上网体验。

阅读本文的读者可能已经了解,上网大致分为两步:首先请求域名的 IP 地址,然后将实际请求发送到 IP 地址。实际上,这里并不一定是向 DNS 服务器请求 IP 地址,更多的是在本地 DNS 缓存中查询是否已有解析。如果本地没有缓存解析,则需要询问 DNS;有缓存时优先使用缓存,而查询本地缓存的时间只有几纳秒,耗时可以忽略不计。通过设置 DNS 请求响应的 TTL(Time to Live)值,可以控制请求结果的缓存时间。例如,TTL 设置为 600,则 10 分钟内 DNS 响应结果都有效,系统不会再次查询相同域名。许多企业将这个值设置为 10,即 10 秒内不必再查。

如果您有自己的 DNS 服务器,可以自行修改这个值。在www.adguardprivate.com上可以自建一个 DNS 服务,延长 TTL 值,减少 DNS 请求次数,提升上网体验。

除了速度以外,DNS 服务还有许多特性影响上网体验, 这里只讨论了连接速度, 其它特性暂不讨论。