最近在折腾家里的服务器,尤其想用 Ubuntu 用 IPv6 直连公网。
但是默认 Ubuntu 会自动生成“临时 IPv6 地址”(privacy extension),虽然有隐私保护作用,但对服务器来说并不友好——地址会定期更换,远程连接时容易搞不清楚到底连的是哪台。

(PS:解决方案看最后)


🌐 IPv6 地址是怎么来的?

1. 前缀部分:由运营商发下来的 /64

当你的路由器(或光猫)连接上运营商的 IPv6 网络后,它会通过 DHCPv6 前缀委派(Prefix Delegation)路由器通告(Router Advertisement,RA) 获得一个 /64 网络前缀。这个前缀通常会是公网可访问的,也可能在切换网络时发生变化。

2. 后缀部分:设备自己生成的 Interface ID

主机的后 64 位 ID 通常由操作系统通过 SLAAC(无状态地址自动配置) 自行生成:

  • 传统方式是使用 modified EUI‑64 算法,从设备的 MAC 地址派生出一个固定的地址后缀;

  • 为增强隐私,现代系统(包括 Ubuntu 在内)支持使用 随机数 生成的临时地址后缀,这样每隔一段时间就换一个,称为 privacy/temporary address。

为什么会有多种地址?

Ubuntu(以及很多 Linux 系统)默认会生成:

  • 一个 基于 EUI‑64 的稳定地址(可用于入站连接)

  • 还有一个或多个 临时随机地址,主要用于出站连接以隐藏设备真实身份 (Ask Ubuntu, Super User)。

所以,最终你会在 ip -6 addr 看到两个 IPv6 地址:一个稳定的,一个临时的。


对服务器不友好的原因

临时地址虽好,但不是用于服务器场景的理想方式,因为:

  • 地址会 定期变化,客户端无法稳定连接;

  • 纷繁复杂的日志、过滤规则、DDNS 配置都可能错乱;

  • 而我们真正需要的是一个 “永远不变”的地址(但是前面分配的部分还是会遍啦),这样服务器才能可靠被访问。


如何关闭临时动态IPv6地址功能?

只需两行配置,告诉 Ubuntu:

别生成那些临时地址,仅保留稳定的 EUI‑64 地址。

执行以下命令:

cat >> /etc/sysctl.conf <<EOT
net.ipv6.conf.all.use_tempaddr=0
net.ipv6.conf.default.use_tempaddr=0
EOT

然后生效配置:

sudo sysctl -p

完成后,用 ip -6 addr 查看,你会发现系统只保留主 IPv6 地址,不再生成临时的那条。