mobile wallpaper 1mobile wallpaper 2mobile wallpaper 3mobile wallpaper 4
6882 字
20 分钟
IP地址与子网:互联网的坐标系统
2022-03-11

你的手机连上 WiFi,瞬间获得一个 192.168.1.105 的地址;你的服务器在云上,绑定了一个 203.0.113.42 的公网 IP;你 ping6 一个地址,发现它长得像 2001:db8::1——128 位,用冒号分隔的十六进制。这些数字就是互联网的坐标。

没有 IP 地址,数据包不知道该往哪走。路由器的路由表里存的是 IP 前缀,交换机的 ARP 缓存映射的是 IP 到 MAC,DNS 返回的是 IP 地址。IP 地址是整个互联网寻址体系的基石——理解了 IP 地址的结构和子网划分,你就理解了路由表为什么能聚合、NAT 为什么能工作、CIDR 为什么取代了分类地址。

本章从 IPv4 的 32 位地址空间出发,讲清楚分类地址、CIDR、子网掩码、子网划分计算,然后进入 IPv6 的 128 位世界——地址表示法、单播/组播/任播、扩展头部,再到 DHCP 的 DORA 四步交互和 IPv6 的 SLAAC 无状态配置,最后落地到 IPv6 过渡机制(双栈、隧道、翻译)和 2026 年的全球部署现实。

一、IP地址:互联网的坐标系统#

1.1 为什么需要 IP 地址#

以太网与交换 中,看到链路层用 MAC 地址在同一个广播域内定位设备。但 MAC 地址是扁平的——00:1a:2b:3c:4d:5e 这串数字不包含任何”你在哪个网络”的信息。如果路由器按 MAC 地址转发,它需要一张包含全世界每块网卡地址的转发表——这在规模上不可行。

IP 地址解决了这个问题。它采用层次化结构:网络号 + 主机号。网络号标识”你在哪个网络”,主机号标识”你是这个网络里的哪台设备”。路由器的转发表只需记录”网络号 → 下一跳”,而非每台主机的映射。这是互联网能扩展到数十亿设备的关键设计。

# 查看本机 IP 地址
ip addr show
# 典型输出:
# 2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500
# link/ether 00:1a:2b:3c:4d:5e brd ff:ff:ff:ff:ff:ff
# inet 192.168.1.100/24 brd 192.168.1.255 scope global eth0
# inet6 fe80::21a:2bff:fe3c:4d5e/64 scope link
# inet6 2001:db8:1234::100/64 scope global
# 旧式 ifconfig 输出(部分系统仍可用)
ifconfig eth0
# eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
# inet 192.168.1.100 netmask 255.255.255.0 broadcast 192.168.1.255
# inet6 fe80::21a:2bff:fe3c:4d5e prefixlen 64 scopeid 0x20<link>
# ether 00:1a:2b:3c:4d:5e txqueuelen 1000 (Ethernet)

ip addr 的输出中你能读到:IPv4 地址(192.168.1.100)、子网前缀长度(/24)、IPv6 链路本地地址(fe80:: 开头)和全局地址(2001:db8: 开头)、MAC 地址(00:1a:2b:3c:4d:5e)。

1.2 IP 地址的层次结构#

IP 地址的层次结构可以用一棵树来表示——从根到叶子,逐级细分:

graph TB ROOT["IP 地址空间"] --> V4["IPv4<br/>32 位"] ROOT --> V6["IPv6<br/>128 位"] V4 --> A["A 类<br/>/8"] V4 --> B["B 类<br/>/16"] V4 --> C["C 类<br/>/24"] V4 --> CIDR["CIDR<br/>/8 ~ /30"] V6 --> GUA["全局单播<br/>2000::/3"] V6 --> LLA["链路本地<br/>fe80::/10"] V6 --> ULA["唯一本地<br/>fc00::/7"] V6 --> MC["组播<br/>ff00::/8"] A --> A1["0.0.0.0/8<br/>当前网络"] A --> A2["10.0.0.0/8<br/>私有地址"] B --> B1["172.16.0.0/12<br/>私有地址"] C --> C1["192.168.0.0/16<br/>私有地址"] C --> C2["127.0.0.0/8<br/>回环地址"] style ROOT fill:#e8eaf6,stroke:#283593 style V4 fill:#e3f2fd,stroke:#1565c0 style V6 fill:#e8f5e9,stroke:#2e7d32 style CIDR fill:#fff3e0,stroke:#e65100

这个层次结构的核心洞察是:前缀越长,地址越具体,路由越精确/8 只匹配前 8 位,覆盖 1600 万个地址;/24 匹配前 24 位,覆盖 256 个地址;/32 精确匹配一个地址。路由器按最长前缀匹配原则选择路由——这和 ARP与首跳路由 中讨论的查表逻辑直接相关。

二、IPv4 地址详解#

2.1 分类地址:A/B/C/D/E#

IPv4 地址最初被分为五类,由地址的前几位决定类别:

类别前缀位首字节范围网络前缀主机位每个网络主机数用途
A01-1268 位24 位16,777,214大型网络
B10128-19116 位16 位65,534中型网络
C110192-22324 位8 位254小型网络
D1110224-239组播
E1111240-255保留/实验

分类地址的问题显而易见:一个 C 类网络只有 254 个主机位,一个 B 类网络有 65534 个——中间没有过渡。一个 500 台主机的公司不得不申请一个 B 类地址,浪费 65000 多个地址。这种粗粒度分配是 IPv4 地址早期快速耗尽的根本原因之一。

Note

分类地址在 1993 年被 CIDR 正式取代(RFC 1518/1519),但分类概念仍然残留在很多地方——比如 10.0.0.0/8 被称为”A 类私有地址”,172.16.0.0/12 被称为”B 类私有地址”。理解分类地址是理解 CIDR 为什么出现的前提。

2.2 CIDR:无类域间路由#

CIDR(Classless Inter-Domain Routing)打破了分类地址的硬边界,允许前缀长度在 /8/32 之间任意取值。192.168.1.0/24 表示前 24 位是网络前缀,后 8 位是主机号——不管 192 开头”应该”是 C 类。

CIDR 带来的两个核心改进:

  1. 灵活分配:一个 500 台主机的网络可以分配 /23(512 个地址),而不是浪费一个 /16
  2. 路由聚合:连续的 /24 可以聚合为 /23/22……直到 /8,路由表条目大幅减少
# 用 ipcalc 计算子网信息
ipcalc 192.168.1.100/24
# 输出:
# Address: 192.168.1.100
# Netmask: 255.255.255.0 = 24
# Network: 192.168.1.0/24
# HostMin: 192.168.1.1
# HostMax: 192.168.1.254
# Broadcast: 192.168.1.255
# Hosts/Net: 254
# 计算一个 /22 网络的范围
ipcalc 10.0.0.0/22
# Network: 10.0.0.0/22
# HostMin: 10.0.0.1
# HostMax: 10.0.3.254
# Broadcast: 10.0.3.255
# Hosts/Net: 1022

路由聚合的威力:假设一个 ISP 拥有 203.0.112.0/24203.0.115.0/24 四个连续的 /24 网段。在分类地址时代,上游路由器需要四条路由条目。在 CIDR 时代,这四个 /24 可以聚合为一条 203.0.112.0/22——路由表缩减为原来的四分之一。

2.3 子网掩码#

子网掩码是 CIDR 前缀长度的另一种表示方式。/24 等价于 255.255.255.0/22 等价于 255.255.252.0。掩码中连续的 1 对应网络前缀,连续的 0 对应主机号。

IP 地址: 192.168.1.100
二进制: 11000000.10101000.00000001.01100100
子网掩码: 11111111.11111111.11111111.00000000 (/24)
网络号: 11000000.10101000.00000001.00000000 (192.168.1.0)
主机号: 00000000.00000000.00000000.01100100 (0.0.0.100)
广播地址: 11000000.10101000.00000001.11111111 (192.168.1.255)

关键规则:

  • 网络号 = IP 地址 AND 子网掩码(按位与)
  • 广播地址 = 网络号 OR 取反的子网掩码(按位或)
  • 可用主机范围 = 网络号 + 1 到 广播地址 - 1
  • 全 0 主机号 是网络地址本身,全 1 主机号 是广播地址——这两个不能分配给设备
# 用 ipcalc 快速验证(推荐)
ipcalc 192.168.1.100/24
# Network: 192.168.1.0/24 HostMin: 192.168.1.1
# Broadcast: 192.168.1.255 HostMax: 192.168.1.254

2.4 特殊 IPv4 地址#

不是所有 IPv4 地址都能分配给设备。以下地址有特殊用途:

地址范围名称用途
0.0.0.0/8当前网络主机启动时还不知道自身 IP
10.0.0.0/8A 类私有内部网络,不可公网路由(RFC 1918)
127.0.0.0/8回环地址本机通信,数据包不离开协议栈
169.254.0.0/16链路本地DHCP 失败时自动配置(APIPA)
172.16.0.0/12B 类私有内部网络(RFC 1918)
192.168.0.0/16C 类私有内部网络(RFC 1918)
224.0.0.0/4组播一对多通信
240.0.0.0/4保留未来使用
Warning

RFC 1918 定义的三个私有地址段(10.0.0.0/8172.16.0.0/12192.168.0.0/16)在公网上不可路由。你的家庭路由器给你的正是这些地址——然后通过 NAT 转换成公网 IP。详见 NAT与中间盒

2.5 子网划分计算#

子网划分是把一个大网络拆成多个小网络。核心操作是借用主机位作为子网位

例题:将 192.168.1.0/24 划分为 4 个等大子网。

  1. 需要 4 个子网 → 需要借用 2 位主机位(2² = 4)
  2. 新的前缀长度 = 24 + 2 = 26 → /26
  3. 每个子网的主机数 = 2^(32-26) - 2 = 62
子网网络地址可用主机范围广播地址
子网 0192.168.1.0/26192.168.1.1 - 62192.168.1.63
子网 1192.168.1.64/26192.168.1.65 - 126192.168.1.127
子网 2192.168.1.128/26192.168.1.129 - 190192.168.1.191
子网 3192.168.1.192/26192.168.1.193 - 254192.168.1.255

VLSM(可变长子网掩码):不同子网可以使用不同长度的前缀。一个 /24 可以划分成一个 /25(126 台主机)和两个 /26(各 62 台主机),而不是只能切成四个等大的 /26。VLSM 让地址利用率最大化——一个 30 台主机的部门不需要浪费 62 个地址的 /26,用 /27(30 台)就够了。

# VLSM 划分示例:将 10.0.0.0/22 划分为不同大小的子网
ipcalc 10.0.0.0/25 # 126 台 — 研发部
ipcalc 10.0.0.128/26 # 62 台 — 市场部
ipcalc 10.0.0.192/27 # 30 台 — 财务部
ipcalc 10.0.0.224/28 # 14 台 — 管理层
ipcalc 10.0.0.240/30 # 2 台 — 点对点链路

三、IPv6:更大的地址空间#

3.1 为什么需要 IPv6#

IPv4 只有 32 位,约 43 亿个地址。2019 年 11 月 25 日,RIPE NCC 宣布其 IPv4 地址池耗尽——这是全球五个区域互联网注册机构(RIR)中最后一个耗尽的。在此之前,APNIC(亚太)在 2011 年、RIPE NCC(欧洲)在 2012 年、ARIN(北美)在 2015 年、LACNIC(拉美)在 2014 年已先后耗尽。

NAT 延缓了 IPv4 地址耗尽的冲击——一个公网 IP 可以让成百上千台内网设备共享。但 NAT 破坏了端到端原则,给 P2P 应用、IPSec、VoIP 带来了复杂性。IPv6 的目标不是”修补”IPv4,而是提供足够的地址空间让每台设备都有全局唯一地址,恢复端到端通信。

IPv6 地址长度 128 位——2^128 约等于 3.4×10^38,这个数字大到什么程度?如果给地球表面每平方米分配 10^24 个 IPv6 地址,也用不完。

3.2 IPv6 地址表示法#

128 位地址用冒号分隔的八组十六进制数表示:

完整形式:2001:0db8:0000:0000:0000:ff00:0042:8329
压缩规则1:每组前导零可省略
2001:db8:0:0:0:ff00:42:8329
压缩规则2:连续的全零组可用 :: 替换(只能用一次)
2001:db8::ff00:42:8329
Warning

:: 只能使用一次。2001:db8::1::2 是非法的——解析器无法判断两组零各有多少位。如果地址中有两段连续零,只能压缩较长的那一段。

# 验证 IPv6 地址格式
python3 -c "
import ipaddress
addr = ipaddress.IPv6Address('2001:db8::ff00:42:8329')
print(f'压缩形式: {addr.compressed}')
print(f'完整形式: {addr.exploded}')
print(f'整数: {int(addr)}')
"
# 压缩形式: 2001:db8::ff00:42:8329
# 完整形式: 2001:0db8:0000:0000:0000:ff00:0042:8329
# IPv6 地址中嵌入 IPv4 地址(最后 32 位用点分十进制)
# ::ffff:192.168.1.1 — IPv4 映射地址
# ::192.168.1.1 — IPv4 兼容地址(已废弃)

3.3 IPv6 地址类型#

IPv6 取消了广播地址,用三种地址类型替代:

类型前缀作用对应 IPv4
单播(Unicast)2000::/3(全局)、fe80::/10(链路本地)、fc00::/7(唯一本地)标识一个接口单播地址
组播(Multicast)ff00::/8标识一组接口,数据包发给组内所有成员组播地址
任播(Anycast)与单播相同地址空间标识一组接口,数据包发给最近的一个无直接对应

任播是 IPv6 新引入的概念(技术上 IPv4 也有,但 IPv6 明确定义了它)。任播地址从单播地址空间中分配,格式上无法区分——区别在于它被配置到多个接口上,路由器将数据包送到拓扑上最近的一个。DNS 根服务器大量使用任播——13 个逻辑根服务器实际上由全球 1000 多个物理实例组成,查询总是被路由到最近的实例。

3.4 IPv6 全局单播地址结构#

一个 IPv6 全局单播地址由三部分组成:

|<-- 48 位 -->|<-- 16 位 -->|<-- 64 位 -->|
| 全局路由前缀 | 子网 ID | 接口 ID |
| /48 或 /32 | | /64 后半 |
  • 全局路由前缀(48 位或更短):由 IANA 分配给 RIR,RIR 分配给 ISP,ISP 分配给客户。/32 是 ISP 级别,/48 是站点级别
  • 子网 ID(16 位):站点内部划分子网,最多 65536 个子网
  • 接口 ID(64 位):标识具体接口,通常由 EUI-64 算法从 MAC 地址生成,或随机生成(隐私扩展)
# 从 MAC 地址生成 EUI-64 接口 ID
# MAC: 00:1a:2b:3c:4d:5e
# 步骤1: 在中间插入 ff:fe → 00:1a:2b:ff:fe:3c:4d:5e
# 步骤2: 翻转第7位(U/L位)→ 02:1a:2b:ff:fe:3c:4d:5e
# 接口ID: 021a:2bff:fe3c:4d5e
# 验证:查看本机 IPv6 地址的接口 ID
ip -6 addr show eth0
# inet6 fe80::21a:2bff:fe3c:4d5e/64 scope link
# ^^^^^^^^^^^^^^^^
# 这就是 EUI-64 生成的接口 ID

3.5 IPv6 扩展头部#

IPv4 的选项字段被放在 IP 头部内部,路由器必须解析整个头部才能转发——即使选项很少见,也拖慢了转发速度。IPv6 采用了链式扩展头部设计:固定 40 字节的基本头部之后,通过 Next Header 字段串联零个或多个扩展头部,最后才是上层协议数据。

基本头部 (40字节)
Next Header = 43 (路由头部)
路由头部
Next Header = 51 (AH 认证头部)
AH 认证头部
Next Header = 6 (TCP)
TCP 数据

常见的扩展头部:

Next Header 值扩展头部用途
0逐跳选项路由器必须处理的选项(如路由器警报)
43路由头部源路由(类似 IPv4 松散源路由)
44分片头部分片信息(IPv6 路由器不再分片,只有源端分片)
50ESP加密安全载荷(IPSec)
51AH认证头部(IPSec)
60目的选项目的端处理的选项
Note

IPv6 路由器不再对数据包分片——如果数据包超过链路 MTU,路由器直接丢弃并返回 ICMPv6 “Packet Too Big”消息,源端负责调整大小后重发。这消除了路由器分片的性能开销,也避免了分片攻击面。MTU 发现是 IPv6 的强制要求。

3.6 IPv4 与 IPv6 对比#

特性IPv4IPv6
地址长度32 位128 位
地址表示点分十进制冒号分隔十六进制
头部长度20-60 字节(可变)40 字节(固定)
校验和有(每跳重算)无(由链路层和传输层负责)
分片路由器和源端均可仅源端(Path MTU Discovery)
选项头部内嵌链式扩展头部
广播无(用组播替代)
地址配置DHCP 或手动SLAAC 或 DHCPv6
IPSec可选原生支持(但非强制)
NAT普遍使用不需要(地址空间足够)
组播可选原生支持

四、DHCP:自动获取 IP 地址#

4.1 手动配置的困境#

想象你是一个网络管理员,管理着 500 台电脑。如果每台电脑的 IP 地址都要手动配置——打开控制面板、输入 IP、子网掩码、网关、DNS——你大概需要一整天。更糟的是,有人配错了 IP 导致地址冲突,有人配错了网关导致上不了网,有人换了办公室但 IP 没改……

DHCP(Dynamic Host Configuration Protocol,动态主机配置协议)解决了这个问题:设备接入网络后自动获取 IP 地址和所有配置参数,租约到期后自动续租或释放。

4.2 DORA:DHCP 的四步交互#

DHCP 的核心交互是四个报文:Discover、Offer、Request、Acknowledge——简称 DORA

sequenceDiagram participant C as 客户端<br/>(0.0.0.0) participant R1 as DHCP服务器1<br/>192.168.1.1 participant R2 as DHCP服务器2<br/>192.168.1.2 C->>R1: DHCP Discover(广播)<br/>src: 0.0.0.0:68 → dst: 255.255.255.255:67<br/>"谁给我一个IP?" C->>R2: DHCP Discover(广播) R1->>C: DHCP Offer<br/>"给你 192.168.1.100,租期86400秒"<br/>附带: 子网掩码、网关、DNS R2->>C: DHCP Offer<br/>"给你 192.168.1.101,租期86400秒" C->>R1: DHCP Request(广播)<br/>"我选 192.168.1.100,来自服务器 192.168.1.1" R1->>C: DHCP ACK<br/>"确认,租期 86400 秒" Note over C: IP 配置完成<br/>192.168.1.100/24

为什么 Request 是广播? 因为客户端此时还没有正式获得 IP 地址,不能发送单播。更重要的是,广播让所有 DHCP 服务器都知道客户端选择了哪个服务器——没被选中的服务器可以回收它们 Offer 的地址。

为什么客户端可能收到多个 Offer? 网络中可能有多个 DHCP 服务器(冗余或恶意)。客户端通常选择第一个到达的 Offer。

4.3 DORA 报文详解#

报文方向传输方式核心字段说明
Discover客户端 → 服务器广播(255.255.255.255请求的 IP(可选)、客户端 MAC、主机名客户端还没有 IP,源地址填 0.0.0.0
Offer服务器 → 客户端单播或广播分配的 IP、子网掩码、租期、DHCP 服务器标识服务器暂时”预留”这个 IP
Request客户端 → 服务器广播请求的 IP、选中的服务器标识告诉所有服务器”我选了谁”
ACK服务器 → 客户端单播或广播确认的 IP、租期、所有配置选项正式分配,租期开始计时
# 用 dhcpdump 捕获 DHCP 交互(需要 root)
sudo dhcpdump -i eth0
# 典型输出(简化):
# TIME: 2026-04-28 10:30:00.123
# IP: 0.0.0.0 (aa:bb:cc:dd:ee:ff) > 255.255.255.255 (ff:ff:ff:ff:ff:ff)
# OP: 1 (BOOTREQUEST) HTYPE: 1 HLEN: 6 HOPS: 0
# XID: 12345678 SECS: 0 FLAGS: 0
# CIADDR: 0.0.0.0 YIADDR: 0.0.0.0
# SIADDR: 0.0.0.0 GIADDR: 0.0.0.0
# CHADDR: aa:bb:cc:dd:ee:ff
# OPTION: 53 ( 1) DHCP Message Type = 1 (Discover)
# OPTION: 50 ( 4) Requested IP Address = 192.168.1.100
# OPTION: 12 ( 8) Host Name = my-laptop
# TIME: 2026-04-28 10:30:00.156
# IP: 192.168.1.1 (11:22:33:44:55:66) > 192.168.1.100 (aa:bb:cc:dd:ee:ff)
# OPTION: 53 ( 1) DHCP Message Type = 2 (Offer)
# OPTION: 54 ( 4) Server Identifier = 192.168.1.1
# OPTION: 51 ( 4) IP Address Lease Time = 86400
# OPTION: 1 ( 4) Subnet Mask = 255.255.255.0
# OPTION: 3 ( 4) Router = 192.168.1.1
# OPTION: 6 ( 8) DNS Server = 8.8.8.8, 8.8.4.4

4.4 DHCP 选项与租约续租#

DHCP 不只分配 IP 地址——它通过 DHCP 选项(Option)传递大量配置信息:

选项号名称典型值说明
1Subnet Mask255.255.255.0子网掩码
3Router192.168.1.1默认网关
6DNS Server8.8.8.8DNS 服务器
15Domain Nameexample.com默认搜索域
42NTP Server192.168.1.1时间服务器
51Lease Time86400租约时长(秒)
54Server Identifier192.168.1.1DHCP 服务器自身地址
81Client FQDN客户端全限定域名(用于 DDNS)
119Domain Searchexample.comDNS 搜索列表
121Classless Static Route无类静态路由

租约续租机制:客户端在租期的 50% 时尝试向原 DHCP 服务器发送单播的 DHCP Request 续租。如果服务器回复 ACK,租期重置。如果服务器没有回复,客户端在租期的 87.5% 时再次尝试,这次是广播——任何 DHCP 服务器都可以响应。如果租期到期仍未续租成功,客户端必须放弃 IP 地址,重新从 Discover 开始。

# 查看当前 DHCP 租约
cat /var/lib/dhcp/dhclient.leases
# 典型内容:
# lease {
# interface "eth0";
# fixed-address 192.168.1.100;
# option subnet-mask 255.255.255.0;
# option routers 192.168.1.1;
# option domain-name-servers 8.8.8.8, 8.8.4.4;
# option dhcp-lease-time 86400;
# option dhcp-server-identifier 192.168.1.1;
# renew 2 2026/04/28 22:30:00; # 50% 租期
# rebind 3 2026/04/29 10:00:00; # 87.5% 租期
# expire 3 2026/04/29 14:00:00; # 100% 租期
# }
# 手动释放和重新获取 IP
sudo dhclient -r eth0 # 释放租约
sudo dhclient eth0 # 重新获取

五、IPv6 自动配置:SLAAC#

5.1 从 DHCP 到 SLAAC#

IPv6 设计了一个比 DHCP 更轻量的自动配置机制——SLAAC(Stateless Address Autoconfiguration,无状态地址自动配置)。“无状态”意味着路由器不维护任何地址分配状态——它只广播网络前缀,客户端自己拼出完整地址。

SLAAC 的核心思路:路由器定期发送 Router Advertisement(RA) 报文,其中包含网络前缀(如 2001:db8:1234::/64)。客户端收到 RA 后,将前缀与自己的接口 ID 拼接,生成完整的 IPv6 地址。不需要服务器、不需要租约、不需要四步交互。

flowchart TB START["主机接入网络"] --> RA_WAIT["等待 Router Advertisement"] RA_WAIT -->|收到 RA| PREFIX["提取网络前缀<br/>如 2001:db8:1234::/64"] PREFIX --> IID["生成接口 ID"] IID -->|EUI-64| EUI64["从 MAC 地址生成<br/>02:1a:2b:ff:fe:3c:4d:5e"] IID -->|隐私扩展| RAND["随机生成<br/>临时接口 ID"] EUI64 --> COMBINE["拼接完整地址<br/>2001:db8:1234::21a:2bff:fe3c:4d5e"] RAND --> COMBINE2["拼接临时地址<br/>2001:db8:1234::随机ID"] COMBINE --> DAD["重复地址检测(DAD)<br/>发送 Neighbor Solicitation"] COMBINE2 --> DAD DAD -->|无冲突| DONE["地址可用"] DAD -->|冲突| FAIL["放弃地址,重新生成"] RA_WAIT -->|超时未收到 RA| DHCPV6["尝试 DHCPv6"] style START fill:#e3f2fd,stroke:#1565c0 style DONE fill:#e8f5e9,stroke:#2e7d32 style FAIL fill:#fce4ec,stroke:#c62828 style DHCPV6 fill:#fff3e0,stroke:#e65100

5.2 RA 报文与地址配置标志#

RA 报文中有三个关键标志位,决定客户端的配置方式:

标志含义客户端行为
Managed Flag(M)是否使用 DHCPv6 获取地址M=1:通过 DHCPv6 获取全局地址
Other Flag(O)是否使用 DHCPv6 获取其他配置O=1:通过 DHCPv6 获取 DNS 等配置
Autonomous Flag(A)前缀是否可用于 SLAACA=1:用 SLAAC 自动配置地址

常见的组合:

  • M=0, O=0, A=1:纯 SLAAC,最常见。客户端用 RA 中的前缀自动配置地址,DNS 通过 RA 的 RDNSS 选项获取
  • M=0, O=1, A=1:SLAAC + DHCPv6。地址用 SLAAC 配置,DNS 等额外信息从 DHCPv6 获取
  • M=1, O=1, A=0:纯 DHCPv6。类似 IPv4 的 DHCP,服务器控制地址分配
# 用 rdisc6 查看 RA 报文
sudo rdisc6 eth0
# 典型输出:
# Soliciting ff02::2 (ff02::2) on eth0...
# Hop limit : 64 (0x40)
# Flags : Onlink, Autonomous
# Prefix : 2001:db8:1234::/64
# Valid time : 2592000 (30 days)
# Preferred time : 604800 (7 days)
# Recursive DNS : 2001:db8:1234::1
# DNS search list : example.com
# Source link-layer address : 00:1a:2b:3c:4d:5e
# MTU : 1500
# 注意 Flags 行:Onlink + Autonomous = A=1, M=0, O=0 → 纯 SLAAC

5.3 重复地址检测(DAD)#

IPv6 要求在正式使用一个地址之前,必须执行 重复地址检测(Duplicate Address Detection, DAD)。客户端发送 Neighbor Solicitation 报文,目标地址是自己即将使用的地址。如果在一定时间内收到 Neighbor Advertisement 回复,说明地址已被占用。

DAD 是 IPv6 的强制步骤——即使是手动配置的地址也必须经过 DAD。这和 IPv4 的 gratuitous ARP 类似,但 IPv4 不强制执行。

5.4 隐私扩展#

EUI-64 接口 ID 从 MAC 地址生成——这意味着你的 IPv6 地址中包含了你的 MAC 地址,且无论你连接到哪个网络,接口 ID 始终不变。这带来了隐私问题:网站可以通过接口 ID 追踪你的设备。

隐私扩展(RFC 4941/8064)解决了这个问题:生成随机的临时接口 ID,定期更换。Windows、macOS、Linux(较新版本)默认启用隐私扩展。

# Linux 上启用 IPv6 隐私扩展
sysctl net.ipv6.conf.eth0.use_tempaddr
# 0 = 禁用, 1 = 生成但优先 EUI-64, 2 = 优先临时地址(推荐)
sudo sysctl -w net.ipv6.conf.all.use_tempaddr=2
# 查看临时地址
ip -6 addr show eth0
# inet6 2001:db8:1234:0:21a:2bff:fe3c:4d5e/64 scope global dynamic mngtmpaddr
# ^^^^^^^^^
# EUI-64 地址
# inet6 2001:db8:1234:0:a1b2:c3d4:e5f6:7890/64 scope global temporary dynamic
# ^^^^^^^^^
# 隐私扩展临时地址

5.5 SLAAC vs DHCPv6#

特性SLAACDHCPv6
服务器需求无(路由器发送 RA 即可)需要 DHCPv6 服务器
状态管理无状态有状态(维护租约数据库)
地址分配客户端自行拼接服务器指定
DNS 配置RA 的 RDNSS 选项(RFC 8106)DHCPv6 选项
地址追踪困难(隐私扩展)可追踪(服务器记录分配)
部署复杂度
适用场景消费者网络、移动网络企业网络、需要审计的环境

六、IPv6 过渡机制与现实部署#

6.1 过渡的三个阶段#

IPv6 的部署不是一个”切换日”——不可能像 1983 年 NCP 到 TCP/IP 那样一夜完成。IPv4 和 IPv6 必须长期共存。过渡分三个阶段:

  1. 早期阶段:IPv4 为主,IPv6 是附加。用隧道技术让 IPv6 孤岛通过 IPv4 海洋互联
  2. 过渡阶段:IPv4 和 IPv6 双栈并行。应用和操作系统同时支持两种协议
  3. 后期阶段:IPv6 为主,IPv4 是遗留。用翻译技术让 IPv6-only 网络访问 IPv4-only 服务

6.2 双栈(Dual Stack)#

双栈是最简单的过渡策略——设备同时运行 IPv4 和 IPv6 协议栈,各自独立工作。应用优先尝试 IPv6(Happy Eyeballs 算法,RFC 8305),如果 IPv6 连接失败则回退到 IPv4。

# 检查双栈状态
ip -4 addr show eth0 # IPv4 地址
ip -6 addr show eth0 # IPv6 地址
# 测试 IPv4 和 IPv6 连通性
ping -c 3 8.8.8.8 # IPv4
ping6 -c 3 2001:4860:4860::8888 # IPv6
# 用 curl 测试双栈
curl -4 https://example.com # 强制 IPv4
curl -6 https://example.com # 强制 IPv6
# Happy Eyeballs:同时发起 IPv4 和 IPv6 连接,优先使用先成功的
curl https://example.com # 自动选择

双栈的问题:你需要同时维护两套协议栈——两套路由、两套防火墙规则、两套监控。这增加了运维复杂度。而且双栈并没有减少 IPv4 地址需求——你仍然需要给每台设备分配 IPv4 地址。

6.3 隧道技术:6to4、Teredo、6in4#

隧道技术将 IPv6 数据包封装在 IPv4 数据包中传输,让 IPv6 孤岛通过 IPv4 网络互联。

6to4(RFC 3056):使用 2002::/16 前缀,将 IPv4 地址嵌入 IPv6 地址中。2002:V4ADDR::/48 自动映射到 IPv4 地址 V4ADDR。6to4 中继路由器负责在 6to4 网络和原生 IPv6 网络之间转发。6to4 的问题在于中继路由器不可靠、性能不可预测——2011 年后 6to4 被认为不推荐使用。

Teredo(RFC 4380):通过 UDP 封装 IPv6,设计用于穿越 NAT。Teredo 服务器帮助客户端发现自己的公网 IPv4 地址和 NAT 类型,Teredo 中继负责与原生 IPv6 网络通信。Teredo 的延迟高、性能差,Windows 曾内置支持但已在 Windows 10 中默认禁用。

6in4(RFC 4213):手动配置的点对点隧道,将 IPv6 包封装在 IPv4 协议号 41 中。6in4 简单可靠,常用于企业站点间的 IPv6 互联。HE(Hurricane Electric)的免费隧道代理就是基于 6in4。

# 配置 6in4 隧道(HE 隧道代理示例)
sudo ip tunnel add he-ipv6 mode sit remote 216.66.80.30 local 203.0.113.42 ttl 255
sudo ip link set he-ipv6 up
sudo ip addr add 2001:470:a:xxx::2/64 dev he-ipv6
sudo ip -6 route add ::/0 dev he-ipv6
# 验证
ping6 -c 3 2001:470:a:xxx::1 # 隧道对端
traceroute6 -n google.com # IPv6 路径追踪

6.4 翻译技术:NAT64、DNS64、464XLAT#

当网络演进到 IPv6-only 阶段,仍需要访问 IPv4-only 服务时,翻译技术出场了。

NAT64(RFC 6146):在 IPv6 和 IPv4 之间做地址和协议翻译。IPv6-only 客户端访问 IPv4 服务器时,NAT64 设备将 IPv6 地址(使用 64:ff9b::/96 前缀,将 IPv4 地址嵌入后 32 位)翻译为 IPv4 地址,反之亦然。

DNS64(RFC 6147):当 IPv6-only 客户端查询一个只有 A 记录的域名时,DNS64 服务器合成一条 AAAA 记录——将 IPv4 地址嵌入 64:ff9b::/96 前缀。客户端向 NAT64 发送 IPv6 数据包,NAT64 翻译成 IPv4 转发。

客户端(IPv6-only) DNS64 NAT64 网关 IPv4 服务器
| | | |
|-- AAAA 查询 ---->| | |
| |-- A 查询 ---->| (递归查询) |
|<-- 合成 AAAA ----| | |
| 64:ff9b::5db8:d822 | |
|-- IPv6 到 64:ff9b::5db8:d822 --->| |
| | NAT64 翻译 |-- IPv4 ------>|
|<-- IPv6 响应 <---|<-- IPv4 响应 <-| |

464XLAT(RFC 6877):解决 NAT64 的一个盲区——如果应用直接使用 IPv4 地址字面量(如 93.184.216.34)而不经过 DNS,DNS64 就帮不上忙。464XLAT 在客户端设备上运行一个 CLAT(Customer-side translator),将应用的 IPv4 请求翻译成 IPv6 发给 NAT64(PLAT),两次翻译后到达 IPv4 服务器。Android 从 4.3 开始支持 464XLAT,iOS 从 13 开始支持。

6.5 过渡策略决策#

flowchart TB START["需要 IPv6 连通性"] --> Q1{"网络是否支持<br/>原生 IPv6?"} Q1 -->|是| DUAL["双栈运行<br/>IPv4 + IPv6 同时工作"] Q1 -->|否| Q2{"能否获得<br/>公网 IPv4 地址?"} Q2 -->|能| TUNNEL["隧道技术<br/>6in4 / HE 隧道代理"] Q2 -->|否| Q3{"是否可以部署<br/>NAT64 + DNS64?"} Q3 -->|是| NAT64["NAT64 + DNS64<br/>IPv6-only 网络"] Q3 -->|否| Q4{"应用是否使用<br/>IPv4 地址字面量?"} Q4 -->|是| XLAT["464XLAT<br/>CLAT + NAT64"] Q4 -->|否| NAT64 DUAL --> Q5{"IPv4 地址是否<br/>仍然充足?"} Q5 -->|是| MAINTAIN["维持双栈<br/>逐步增加 IPv6 流量"] Q5 -->|否| Q6{"是否可以转为<br/>IPv6-only?"} Q6 -->|是| V6ONLY["IPv6-only + NAT64<br/>用翻译访问遗留 IPv4"] Q6 -->|否| MAINTAIN style START fill:#e3f2fd,stroke:#1565c0 style DUAL fill:#e8f5e9,stroke:#2e7d32 style TUNNEL fill:#fff3e0,stroke:#e65100 style NAT64 fill:#fce4ec,stroke:#c62828 style XLAT fill:#f3e5f5,stroke:#6a1b9a style V6ONLY fill:#e0f2f1,stroke:#00695c

6.6 过渡策略对比#

策略原理优势劣势适用阶段
双栈同时运行 IPv4 和 IPv6简单、兼容性好需要两套协议栈、仍需 IPv4 地址早期/过渡期
6in4 隧道IPv6 封装在 IPv4 协议号 41可靠、手动可控需要公网 IPv4、不支持 NAT 后早期
6to4自动隧道,IPv4 地址嵌入 IPv6零配置中继不可靠、已不推荐早期(已废弃)
TeredoUDP 封装 IPv6,穿越 NAT可穿越 NAT延迟高、性能差早期(已废弃)
NAT64 + DNS64IPv6-only 网络通过翻译访问 IPv4不需要 IPv4 地址不支持 IPv4 地址字面量后期
464XLAT客户端 CLAT + 网络 NAT64完全兼容 IPv4 应用两次翻译开销后期(移动网络)

6.7 全球 IPv6 部署现状(2026)#

截至 2026 年初,全球 IPv6 部署的关键数据:

  • Google 统计:全球约 45% 的 Google 用户通过 IPv6 访问(2024 年初约 40%,2022 年约 35%)
  • APNIC 统计:全球 IPv6 能力率约 48%(能通过 IPv6 传输数据的网络比例)
  • 前五名国家/地区:印度(~70%)、美国(~55%)、德国(~55%)、日本(~50%)、法国(~50%)
  • 主要 CDN:Cloudflare、Akamai、Fastly 的 IPv6 支持率均超过 80%
  • 移动网络:T-Mobile US、Reliance Jio(印度)已实现 IPv6-only(配合 464XLAT),IPv4 流量占比低于 5%

6.8 中国 IPv6 部署现状#

中国的 IPv6 部署有其独特性:

  • 政策驱动:2017 年中共中央办公厅、国务院办公厅印发《推进互联网协议第六版(IPv6)规模部署行动计划》,设定了明确的时间表和指标
  • 用户规模:截至 2025 年底,中国 IPv6 活跃用户数超过 8 亿,占网民比例超过 75%
  • 三大运营商:中国移动、中国电信、中国联通的 LTE 网络已全面支持 IPv6,固定宽带 IPv6 支持率超过 70%
  • 教育网:CERNET2 是全球最大的纯 IPv6 骨干网之一,连接 200+ 高校
  • 内容生态:Top 100 网站 IPv6 支持率超过 80%,但部分中小网站和传统企业应用仍不支持
  • 挑战:家庭路由器的 IPv6 支持参差不齐,许多老旧路由器默认关闭 IPv6 或不支持 PD 前缀下发,导致”最后一公里”IPv6 不通
# 测试你的 IPv6 连通性
ping6 -c 3 ipv6.google.com # Google
ping6 -c 3 ipv6.baidu.com # 百度
ping6 -c 3 2400:3200::1 # 阿里 DNS
# 测试 IPv6 地址分配
ip -6 addr show | grep "scope global"
# 如果有输出,说明你已获得全局 IPv6 地址
# 测试 IPv6 路由
ip -6 route show
# default via fe80::1 dev eth0 # 默认 IPv6 路由
# 在线测试
# https://test-ipv6.com/ — 综合测试
# https://ipv6-test.com/ — 连通性测试

七、动手实践:IP 地址与子网实验#

7.1 查看和计算 IP 地址信息#

# 查看所有网络接口的 IP 地址
ip addr show
# 只看 IPv4
ip -4 addr show
# 只看 IPv6
ip -6 addr show
# 查看路由表
ip route show # IPv4
ip -6 route show # IPv6
# 用 ipcalc 计算子网(安装:sudo apt install ipcalc)
ipcalc 10.0.0.0/22
ipcalc 192.168.1.0/26
# 计算两个子网之间的包含关系
ipcalc 10.0.0.0/22 | grep -E "Network|HostMin|HostMax|Broadcast"

7.2 DHCP 抓包分析#

sudo dhclient -r eth0 # 释放租约
sudo tcpdump -i eth0 -n port 67 or port 68 -vv # 另一终端抓包
sudo dhclient eth0 # 重新获取
# 抓包输出:Discover → Offer → Request → ACK

7.3 IPv6 连通性测试#

sysctl net.ipv6.conf.all.disable_ipv6 # 检查 IPv6 支持(0=启用)
ping6 -c 3 ::1 # 本机回环
ping6 -c 3 2001:4860:4860::8888 # Google DNS
traceroute6 -n google.com # IPv6 路径追踪
ip -6 neigh show # 邻居缓存(类似 ARP 缓存)

7.4 Linux IPv6 系统参数调优#

# 关键参数
sysctl net.ipv6.conf.all.forwarding # 转发(路由器=1)
sysctl net.ipv6.conf.all.accept_ra # 接受 RA(主机=1,路由器=0)
sysctl net.ipv6.conf.all.use_tempaddr # 隐私扩展(推荐=2)
# 永久配置
cat << 'EOF' | sudo tee /etc/sysctl.d/99-ipv6.conf
net.ipv6.conf.all.forwarding = 0
net.ipv6.conf.all.accept_ra = 2
net.ipv6.conf.all.use_tempaddr = 2
net.ipv6.conf.default.use_tempaddr = 2
EOF
sudo sysctl -p /etc/sysctl.d/99-ipv6.conf

八、本章小结#

概念要点
IP 地址层次结构网络号 + 主机号,层次化使得路由表可聚合,是互联网可扩展的基础
分类地址A/B/C/D/E 五类,粗粒度分配导致地址浪费,已被 CIDR 取代
CIDR无类域间路由,前缀长度任意取值,灵活分配 + 路由聚合
子网掩码CIDR 前缀的另一种表示,网络号 = IP AND 掩码,广播 = 网络号 OR ~掩码
特殊地址私有地址(RFC 1918)、回环、链路本地、组播——各有用途,不能随意分配
子网划分借用主机位作为子网位,VLSM 允许不同子网使用不同前缀长度
IPv6 地址128 位,冒号分隔十六进制,:: 压缩连续零组,单播/组播/任播三种类型
IPv6 扩展头部链式设计,路由器只处理基本头部,提升转发效率
DHCP DORADiscover → Offer → Request → ACK,四步交互获取 IP 和配置
DHCP 租约50% 时单播续租,87.5% 时广播续租,到期释放
SLAAC路由器 RA 广播前缀,客户端自行拼接地址,DAD 检测冲突
隐私扩展随机临时接口 ID,定期更换,防止 MAC 地址被追踪
双栈同时运行 IPv4/IPv6,最简单但运维成本高
隧道6in4 可靠、6to4/Teredo 已废弃,IPv6 封装在 IPv4 中传输
NAT64/DNS64IPv6-only 网络访问 IPv4 服务,DNS64 合成 AAAA 记录
464XLAT解决 IPv4 地址字面量问题,CLAT + PLAT 两次翻译
全球部署2026 年约 45% Google 用户通过 IPv6 访问,中国活跃用户超 8 亿

本章建立了 IP 地址与子网的完整认知。下一章进入 NAT与中间盒——看看 IPv4 地址不够用时,NAT 如何让一个公网 IP 服务成百上千台设备,以及 NAT 对端到端通信的破坏。


参考#

支持与分享

如果这篇文章对你有帮助,欢迎支持作者或分享给更多人

IP地址与子网:互联网的坐标系统
https://blog.souloss.com/posts/internet-architecture/ip-addressing-and-subnetting/
作者
Souloss
发布于
2022-03-11
许可协议
CC BY-NC-SA 4.0

部分信息可能已经过时