NAT NAT

  • 资料来源:

    • https://arthurchiao.art/blog/how-nat-traversal-works-zh/
      • 这个 blog 是个宝藏, 与网络有关的上至内核下至协议等等质量相当之高
    • https://eh5.me/zh-cn/blog/nat-behavior-explained/
  • 更新

    1
    2
    2025.05.13 初始
    2025.06.08 更新一点内容

导语

尝试理解 NAT 是什么, 各种 Cone 是什么意思, CGNAT 又是什么…

Network Address Translation(NAT) 网络地址转换协议, 数据包经过 NAT 会改变网络地址 (废话);

功能上区分:

  • SNAT 源地址转换
  • DNAT 目的地址转换
  • Bidirectional NAT 同时对源和目的进行转换

RFC

rfc3489: 定义 NAT1234 和 各种圆锥, 相关讨论下会反复出现,但是已经不是实际应用开发标准了.

rfc4787 Network Address Translation (NAT) Behavioral Requirements for Unicast UDP

  • 实际的现行标准, UDP NAT

rfc5382 NAT Behavioral Requirements for TCP

  • TCP NAT, 提到的地方不多

* Cone / NAT1234

涉及内网透传相关帖子总有 * Cone 或 NAT 1234, 其翻译是异常绕口…

* Cone 来自 STUN RFC 3489 定义, Cone 是圆锥意思, 可以将其想象为一个漏斗, 所有外来流量是注水, 漏斗形状 (NAT 类型) 决定什么水可以漏过去.

Full Cone NAT(全锥形 NAT, NAT1):

  • 内网设备 A:P1 -> 公网 B:P2;
  • 任何公网 ip 都可以通过 B:P2 访问到内网设备
    Restricted Cone NAT(受限锥形 NAT, NAT2):
  • 内网设备 A:P1 -> 公网 B:P2;
  • 限定只有 DIP 才能通过 B:P2 访问到内网设备
    Port Restricted Cone NAT(端口受限锥形 NAT, NAT3):
  • 进一步限制只有 DIP:DPORT 才能通过 B:P2 访问到内网设备
    Symmetric NAT(对称 NAT, NAT4):
  • 最不是人的一种类型;
  • 五元组任何变化, 都可能对应不同的 公网映射;
  • 其实不属于 Cone 类型

Rfc4787

* Cone 其实并不能完全区分 NAT, NAT 还有更多维度…因此又出现了 RFC 4787

映射行为

Endpoint-Independent Mapping (EIM,终点无关的映射)

  • A:P1–B:P2 映射, 只看源 A:P1, 只要 A:P1 不变, 这个映射就不变.
  • 反之公网任意设备都能通过 B:P2 --> A:P1

Address-Dependent Mapping(ADM)

  • A:P1–B:P2 映射,看 A:P1 和 DIP.
  • 只有 DIP 的设备能通过 B:P2 --> A:P1

Address and Port-Dependent Mapping (APDM)

  • A:P1–B:P2 映射,看 A:P1, DIP DPort.
  • 只有 DIP:DPORT 能通过 B:P2 --> A:P1
  • 几乎和 conntrack 相同了

过滤行为

应该是公网 pkt 哪些能进入到内网的过滤行为

Endpoint-Independent Filtering(EIF)

  • 没有任何限制, 随便进入内网

Address-Dependent Filtering(ADF)

  • 只允许来自特定 DIP 的 pkt 进入内网, 不管端口是什么

Address and Port-Dependent Filtering(APDF)

  • 只允许来自特定 DIP:DPORT 的 pkt 进入内网

总结

将 映射行为 和 过滤行为组合

EIFADFADPF
EIMFull Cone NAT / NAT1Restricted Cone / NAT2Port Restricted Cone / NAT3
ADMN/A*ADM + ADFADM + ADPF
ADPMN/A*N/A*Symmetric / NAT4
实现和理论总是会有差异, kernel 中 nat 相关实体有多种行为也不稀奇.

NAT 穿透场景下, 一堆东西太复杂了, 简化下 Easy / Hard NAT

  • Easy / Hard 对应的是否是 EIM,终点无关的映射;
  • 决定 B:P2 的是否只是 A:P1; 是 -> Easy 否 -> Hard;
EIMEDM
EasyHard

只要双边不同时是 Hard NAT 就有非常高的概率打洞成功.

NAT 嵌套 NAT

一般是木桶效应, 整个环节最严格的节点决定了整条链路最终的 NAT 等级

CGNAT

CGNAT (Carrier-Grade NAT) 运营商级 NAT 也叫 LSN (Large Scale NAT) 还叫 NAT444

1
2
3
家庭/企业内网 -> 家用路由器 NAT -> ISP 的 CGNAT -> 互联网
(192.168.1.x) (10.x.x.x) (公网 IP) (公网)
NAT 4 4 4

运营商一侧对自己的公网 IP 又做了一个 NAT, 因此多个用户可能分配到同一个 " 假公网 IP";

用户侧看到的一个公网 IP 和 Server 侧看到的公网 IP 不同; 打洞访问就麻烦多了.

  • 但是似乎这成了近些年大陆地区的标配…

借用 NAT 穿透是如何工作的 的图说明,CGNAT 带来的额外麻烦;

如图: 在假公网同侧下, STUN 获取到的地址是假的, 穿透就失效了;

可能解决方式

  • NAT hairpin 模式, 在 Carrier Grade NAT 在绕一圈; 有的 Router 支持, 有的不支持…
    • 发卡?
  • 或者任何一边支持端口映射协议, 这样就会在 192.168.0.x 这一侧而是在 Carrier Grade NAT <-> 192.168.0.x

NAT64/DNS64

比较少遇见, 但教育网非常常见; ipv6 地址但是仍然能够方案 ipv4 网络;

至于 NAT 穿透遇到这样的配置, 判断下是否是 NAT64, 同样的流程获取到公网 ip:port ; 稍微麻烦了一点点;