-
飞牛NAS 开启自定义 IPv6 后缀 (Token模式) 完整解决方案
文档说明
适用系统: 飞牛NAS (基于 Debian12 + NetworkManager)
目标: 为飞牛NAS配置自定义固定IPv6后缀,支持外网访问和端口转发
说明: 飞牛NAS已在网络设置中集成EUI64模式,本文档专注于Token模式配置。Token模式可以自定义后缀(如::888),既保证地址固定,又不暴露MAC地址,隐私性更好。
更新: 开启临时地址方案二,避免路由器下发 /128 IPv6 被系统选定默认出站被跟踪的可行性。
核心价值:
- 固定IPv6地址,方便远程访问
- 支持路由器ACL访问控制
- 避免DDNS频繁更新
- 适合NAS、服务器场景
快速导航
- 第一部分: 环境准备
- 第二部分: Token模式配置
- 第三部分: 混合模式适配
- 第四部分: 常见问题
第一部分: 环境准备
1.1 飞牛NAS系统特点
飞牛NAS基于Debian12,使用NetworkManager管理网络,与标准Debian配置方式相同。
系统信息确认:
# SSH登录飞牛NAS后执行
# 查看系统版本
cat /etc/debian_version
# 预期: 12.x
# 查看NetworkManager状态
systemctl status NetworkManager
# 查看网络管理器
nmcli --version
1.2 查找网络参数
重要: 所有脚本需要根据你的飞牛NAS实际参数修改!
# 1. 查看网络连接名称
nmcli connection show
# 输出示例:
# NAME UUID TYPE DEVICE
# Wired connection 1 5fb06bd0-0bb0-7ffb-45f1-d6edd65f3e03 ethernet eth0
# ↑ 记录连接名称
# 2. 查看网卡接口名称
ip link show
# 输出示例:
# 2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 ...
# ↑ 记录网卡名称
# 3. 查看当前IPv6地址
ip -6 addr show eth0 | grep "scope global"
# 4. 查看MAC地址
ip link show eth0 | grep "link/ether"
记录你的参数:
连接名称 (CONNECTION_NAME): _________________
网卡名称 (INTERFACE): _________________
MAC地址: _________________
1.3 检查路由器配置
# 安装检测工具(如未安装)
apt update && apt install -y ndisc6
# 检查路由器RA配置
rdisc6 eth0 # 替换为你的网卡名称
关键信息解读:
Stateful address conf. : Yes/No ← DHCPv6状态 (M flag)
Autonomous address conf. : Yes/No ← SLAAC状态 (A flag)
Prefix : 2001:db8::/64 ← 前缀
Token配置可用性判断:
| RA配置 |
Token可用 |
说明 |
| **M=0, A=1** |
✅ |
纯SLAAC,最理想 |
| **M=1, A=1** |
⚠️ |
混合模式,需特殊处理 |
| **M=1, A=0** |
❌ |
纯DHCPv6,无法使用 |
第二部分: Token模式配置
2.1 Token模式说明
原理: 自定义IPv6后缀,更灵活且不暴露MAC
示例:
路由器前缀: 2001:db8:1234:5678::/64
自定义Token: ::888
最终地址: 2001:db8:1234:5678::888/64
优点:
- ✅ 自定义后缀,易记 (如 ::888, ::1)
- ✅ 不暴露MAC地址
- ✅ 地址固定不变
- ✅ 隐私性好,不暴露硬件信息
推荐Token:
2.2 脚本清单
/root/enable-token-888.sh # 启用Token ::888
/root/disable-token.sh # 禁用Token
/root/check-token.sh # 检查状态
2.3 快速部署流程
步骤1: 创建启用脚本
nano /root/enable-token-888.sh
脚本内容
方案一:禁用临时 IPV6
注意禁用临时 IPV6 Linux 默认 会将 /128 作为高优先级的地址出站,如果设置不当可能被跟踪,如果禁用临时 IPV6 请设置好防火墙或者修改路由器有状态、无状态信息,保护网络安全。推荐方案二。
#!/bin/bash
# 启用 Token ::888
set -e
CONNECTION_NAME="Wired connection 1"
INTERFACE="ens33"
TOKEN="::888"
echo "=== 启用 IPv6 Token ::888 ==="
echo ""
# 检查 root
if [ "$EUID" -ne 0 ]; then
echo "请使用 root 运行"
exit 1
fi
echo "配置前地址:"
ip -6 addr show $INTERFACE | grep "scope global" || echo "无"
echo ""
# 核心配置(注意顺序很重要!)
echo "1. 配置 IPv6 方法..."
nmcli connection modify "$CONNECTION_NAME" ipv6.method auto
echo "2. 禁用 DHCPv6(关键)..."
nmcli connection modify "$CONNECTION_NAME" ipv6.dhcp-timeout 0
echo "3. 设置地址生成模式(必须在 Token 之前)..."
nmcli connection modify "$CONNECTION_NAME" ipv6.addr-gen-mode eui64
echo "4. 设置 Token..."
nmcli connection modify "$CONNECTION_NAME" ipv6.token "$TOKEN"
echo "5. 禁用隐私扩展..."
nmcli connection modify "$CONNECTION_NAME" ipv6.ip6-privacy 0
echo "6. 清除旧地址..."
ip -6 addr flush dev $INTERFACE scope global 2>/dev/null || true
echo "7. 重启连接..."
nmcli connection down "$CONNECTION_NAME" 2>/dev/null || true
sleep 2
nmcli connection up "$CONNECTION_NAME"
echo ""
echo "等待10秒..."
sleep 10
echo ""
echo "=== 配置完成 ==="
echo ""
echo "新地址:"
ip -6 addr show $INTERFACE | grep "scope global"
echo ""
echo "Token状态:"
nmcli connection show "$CONNECTION_NAME" | grep "ipv6.token"
ip token show dev $INTERFACE 2>/dev/null || echo "系统 Token: 未检测到"
echo ""
# 验证
if ip -6 addr show $INTERFACE | grep "scope global" | grep -q "888"; then
echo "✅ Token ::888 已生效!"
else
echo "⚠️ Token 可能未生效,请运行 check-token.sh 检查"
fi
方案二:不禁用临时 IPV6 让临时地址作为默认出战避免被跟踪
如果临时地址不生效 请 注释 6. 清除旧地址
#!/bin/bash
# 启用 Token ::888 并使用临时 IPv6 地址优先出站
set -e
CONNECTION_NAME="Wired connection 1"
INTERFACE="ens33"
TOKEN="::888"
echo "=== 启用 IPv6 Token ::888 + 临时地址优先出站 ==="
echo ""
# 检查 root
if [ "$EUID" -ne 0 ]; then
echo "请使用 root 运行"
exit 1
fi
echo "配置前地址:"
ip -6 addr show $INTERFACE | grep "scope global" || echo "无"
echo ""
# 核心配置(注意顺序很重要!)
echo "1. 配置 IPv6 方法..."
nmcli connection modify "$CONNECTION_NAME" ipv6.method auto
echo "2. 禁用 DHCPv6(关键)..."
nmcli connection modify "$CONNECTION_NAME" ipv6.dhcp-timeout 0
echo "3. 设置地址生成模式(必须在 Token 之前)..."
nmcli connection modify "$CONNECTION_NAME" ipv6.addr-gen-mode eui64
echo "4. 设置 Token..."
nmcli connection modify "$CONNECTION_NAME" ipv6.token "$TOKEN"
echo "5. 启用隐私扩展并且强制临时IPv6 作为出站..."
nmcli connection modify "$CONNECTION_NAME" ipv6.ip6-privacy 2
echo "6. 清除旧地址..."
ip -6 addr flush dev $INTERFACE scope global 2>/dev/null || true
echo "7. 重启连接..."
nmcli connection down "$CONNECTION_NAME" 2>/dev/null || true
sleep 2
nmcli connection up "$CONNECTION_NAME"
echo ""
echo "等待10秒..."
sleep 10
echo ""
echo "=== 配置完成 ==="
echo ""
echo "新地址:"
ip -6 addr show $INTERFACE | grep "scope global"
echo ""
echo "Token状态:"
nmcli connection show "$CONNECTION_NAME" | grep "ipv6.token"
ip token show dev $INTERFACE 2>/dev/null || echo "系统 Token: 未检测到"
echo ""
# 验证
if ip -6 addr show $INTERFACE | grep "scope global" | grep -q "888"; then
echo "✅ Token ::888 已生效!"
else
echo "⚠️ Token 可能未生效,请运行 check-token.sh 检查"
fi
# 验证默认出站地址(临时地址应优先)
echo ""
echo "默认出站地址:"
ip -6 route get 2400:3200::1
步骤2: 创建禁用脚本
# 禁用脚本
nano /root/disable-token.sh
# ⚠️ 粘贴 disable-token.sh 内容
脚本内容
#!/bin/bash
# 禁用 Token,恢复默认
set -e
CONNECTION_NAME="Wired connection 1"
INTERFACE="ens33"
echo "=== 禁用 Token ==="
echo ""
if [ "$EUID" -ne 0 ]; then
echo "请使用 root 运行"
exit 1
fi
echo "当前地址:"
ip -6 addr show $INTERFACE | grep "scope global" || echo "无"
echo ""
echo "1. 清除 Token..."
nmcli connection modify "$CONNECTION_NAME" ipv6.token ""
echo "2. 恢复 DHCPv6..."
nmcli connection modify "$CONNECTION_NAME" ipv6.dhcp-timeout ""
echo "3. 恢复地址生成模式..."
nmcli connection modify "$CONNECTION_NAME" ipv6.addr-gen-mode stable-privacy
echo "4. 启用隐私扩展..."
nmcli connection modify "$CONNECTION_NAME" ipv6.ip6-privacy 2
echo "5. 清除旧地址..."
ip -6 addr flush dev $INTERFACE scope global 2>/dev/null || true
echo "6. 重启连接..."
nmcli connection down "$CONNECTION_NAME" 2>/dev/null || true
sleep 2
nmcli connection up "$CONNECTION_NAME"
echo ""
echo "等待10秒..."
sleep 10
echo ""
echo "=== 恢复完成 ==="
echo ""
echo "新地址:"
ip -6 addr show $INTERFACE | grep "scope global" || echo "无"
echo ""
echo "✅ 已恢复默认配置(DHCPv6 或 SLAAC)"
步骤3: 检查脚本
# 检查脚本
nano /root/check-token.sh
# ⚠️ 粘贴 check-token.sh 内容 (注意修改 INTERFACE 和 CONNECTION_NAME)
脚本内容
#!/bin/bash
# 检查 Token 状态(改进版 - 支持多地址分析)
CONNECTION_NAME="Wired connection 1"
INTERFACE="ens33"
echo "========================================"
echo " IPv6 Token 状态检查"
echo "========================================"
echo ""
# 1. NetworkManager 配置
echo "【NetworkManager 配置】"
echo "----------------------------------------"
nmcli connection show "$CONNECTION_NAME" | grep -E "ipv6.method|ipv6.token|ipv6.addr-gen-mode|ipv6.ip6-privacy|ipv6.dhcp-timeout"
echo ""
# 2. IPv6 地址列表
echo "【IPv6 地址列表】"
echo "----------------------------------------"
ip -6 addr show $INTERFACE | grep "inet6"
echo ""
# 3. 全局地址详细分析
echo "【全局地址分析】"
echo "----------------------------------------"
# 获取所有全局地址
GLOBAL_ADDRS=$(ip -6 addr show $INTERFACE | grep "scope global" | grep -v "temporary" | awk '{print $2}')
TOKEN_NM=$(nmcli connection show "$CONNECTION_NAME" | grep "ipv6.token:" | awk '{print $2}')
if [ -z "$GLOBAL_ADDRS" ]; then
echo "❌ 未检测到全局地址"
else
# 分析每个地址
ADDR_COUNT=0
HAS_TOKEN=false
HAS_DHCPV6=false
HAS_SLAAC=false
TOKEN_ADDR=""
DHCPV6_ADDR=""
echo "检测到 $(echo "$GLOBAL_ADDRS" | wc -l) 个全局地址:"
echo ""
while IFS= read -r addr_with_prefix; do
ADDR_COUNT=$((ADDR_COUNT + 1))
ADDR=$(echo $addr_with_prefix | cut -d'/' -f1)
PREFIX_LEN=$(echo $addr_with_prefix | cut -d'/' -f2)
echo "地址 #$ADDR_COUNT: $ADDR"
echo " 前缀长度: /$PREFIX_LEN"
if [ "$PREFIX_LEN" = "128" ]; then
echo " 类型: DHCPv6"
echo " 优先级: ⭐⭐⭐ (高)"
echo " 说明: 由 DHCPv6 服务器分配的单个地址"
HAS_DHCPV6=true
DHCPV6_ADDR="$ADDR"
elif [ "$PREFIX_LEN" = "64" ]; then
# 检查是否是Token地址
if [ "$TOKEN_NM" != "--" ] && echo "$ADDR" | grep -q "${TOKEN_NM#::}"; then
echo " 类型: SLAAC + Token"
echo " 优先级: ⭐⭐ (中)"
echo " 说明: ✅ Token 地址已生效!"
HAS_TOKEN=true
TOKEN_ADDR="$ADDR"
elif echo "$ADDR" | grep -q "ff:fe"; then
echo " 类型: SLAAC + EUI64"
echo " 优先级: ⭐ (低)"
echo " 说明: 基于 MAC 地址的 EUI64 格式"
HAS_SLAAC=true
else
echo " 类型: SLAAC + 隐私扩展"
echo " 优先级: ⭐ (低)"
echo " 说明: 隐私扩展或其他方式生成"
HAS_SLAAC=true
fi
fi
echo ""
done <<< "$GLOBAL_ADDRS"
fi
echo ""
# 4. 地址优先级说明
echo "【地址使用优先级】"
echo "----------------------------------------"
if [ "$HAS_DHCPV6" = true ] && [ "$HAS_TOKEN" = true ]; then
echo "⚠️ 系统同时拥有 DHCPv6 和 Token 地址"
echo ""
echo "外出连接可能使用的地址:"
echo " 首选: $DHCPV6_ADDR (/128 DHCPv6)"
echo " 备选: $TOKEN_ADDR (/64 Token)"
echo ""
echo "说明:"
echo " - Linux 地址选择算法通常优先使用 /128 地址"
echo " - 应用程序可能随机选择其中一个"
echo " - 两个地址都可以接收入站连接"
echo ""
echo "建议:"
echo " 1. 如果需要固定使用 Token 地址,可以手动删除 DHCPv6 地址:"
echo " ip -6 addr del $DHCPV6_ADDR/128 dev $INTERFACE"
echo ""
echo " 2. 或使用应用层绑定到特定地址:"
echo " curl --interface $TOKEN_ADDR https://example.com"
elif [ "$HAS_TOKEN" = true ]; then
echo "✅ 系统仅使用 Token 地址,配置完美!"
echo ""
echo "使用的地址: $TOKEN_ADDR"
echo "所有连接都会使用此地址"
elif [ "$HAS_DHCPV6" = true ]; then
echo "⚠️ 系统仅使用 DHCPv6 地址"
echo ""
echo "使用的地址: $DHCPV6_ADDR"
echo "Token 未生效"
fi
echo ""
# 5. Token 状态
echo "【Token 配置状态】"
echo "----------------------------------------"
if [ "$TOKEN_NM" = "--" ]; then
echo "NetworkManager: ❌ 未配置"
else
echo "NetworkManager: ✅ $TOKEN_NM"
fi
TOKEN_SYS=$(ip token show dev $INTERFACE 2>/dev/null)
if [ -n "$TOKEN_SYS" ]; then
echo "系统内核: ✅ $TOKEN_SYS"
else
echo "系统内核: ⚠️ 未检测到"
fi
echo ""
# 6. MAC 地址
echo "【MAC 地址】"
echo "----------------------------------------"
ip link show $INTERFACE | grep "link/ether"
echo ""
# 7. 路由通告
echo "【路由通告检查】"
echo "----------------------------------------"
if command -v rdisc6 &> /dev/null; then
echo "检查中(5秒)..."
timeout 5 rdisc6 $INTERFACE 2>&1 | head -15 || echo "未收到 RA"
else
echo "rdisc6 未安装"
fi
echo ""
# 8. 综合判断
echo "【综合判断】"
echo "========================================"
if [ "$TOKEN_NM" = "--" ]; then
echo "❌ Token 未配置"
echo ""
echo "启用 Token:"
echo " bash /root/enable-token-888.sh"
elif [ "$HAS_TOKEN" = true ]; then
echo "✅ Token 配置成功!"
echo ""
echo "Token 地址: $TOKEN_ADDR/64"
echo ""
if [ "$HAS_DHCPV6" = true ]; then
echo "📌 当前状态: Token 和 DHCPv6 并存"
echo ""
echo "DHCPv6 地址: $DHCPV6_ADDR/128"
echo ""
echo "这是正常现象,因为路由器设置了 M flag=1(强制DHCPv6)"
echo ""
echo "两个地址都可以使用,系统会自动选择:"
echo " - 出站连接:可能优先使用 DHCPv6 地址"
echo " - 入站连接:两个地址都可以接收"
echo ""
echo "如需仅使用 Token 地址,可以:"
echo " 1. 手动删除 DHCPv6: ip -6 addr del $DHCPV6_ADDR/128 dev $INTERFACE"
echo " 2. 应用层指定地址: 在应用程序中绑定到 $TOKEN_ADDR"
else
echo "🎉 完美!系统仅使用 Token 地址"
fi
else
echo "⚠️ Token 已配置但未生效"
echo ""
echo "可能原因:"
echo " 1. 路由器未发送 RA 或 A flag=0"
echo " 2. 网络连接未重启"
echo " 3. Token 配置未正确应用"
echo ""
echo "解决方案:"
echo " bash /root/enable-token-888.sh"
fi
echo "========================================"
步骤4: 添加权限并运行
chmod +x /root/enable-token-888.sh
chmod +x /root/disable-token.sh
chmod +x /root/check-token.sh
# 启用Token
/root/enable-token-888.sh
# 检查结果
/root/check-token.sh
预期结果:
inet6 2001:db8:1234:5678::888/64 scope global
↑ Token后缀
第三部分: 混合模式适配
3.1 问题场景
**当路由器同时启用 **DHCPv6 + SLAAC (M=1, A=1) 时,飞牛NAS可能获得两个地址:
inet6 2001:db8:1234:5678::a10/128 scope global # DHCPv6地址
inet6 2001:db8:1234:5678::888/64 scope global # Token地址
影响:
- **系统可能优先使用 **
/128 的DHCPv6地址
- Token地址虽然配置成功,但不是默认出口
3.2 解决方案
DHCPv6 禁用方案,但是 DHCPv6 会自启动,所以暂时不分享没有完全测试的脚本
方案A: 删除DHCPv6地址
# 查看当前地址
ip -6 addr show eth0 | grep "scope global"
# 删除DHCPv6地址 (替换为实际地址)
ip -6 addr del 2001:db8:1234:5678::a10/128 dev eth0
# 验证 (应只剩Token地址)
ip -6 addr show eth0 | grep "scope global"
注意: 重启后DHCPv6地址会重新获取,需使用方案2永久解决
方案B: 指定地址访问
保留两个地址,在应用层指定使用Token地址:
# curl 指定地址
curl -6 --interface 2001:db8:1234:5678::888 https://ifconfig.co
# wget 指定地址
wget --bind-address=2001:db8:1234:5678::888 https://example.com
第四部分: 常见问题
4.1 脚本修改检查清单
创建脚本后,请逐一检查以下参数:
4.2 推荐Token后缀
# Token选择建议:
# 1. ::888 - 简洁易记
# 2. ::1 - 最简洁
# 部署命令
/root/enable-token-888.sh # 启用Token
/root/check-token.sh # 验证状态
快速上手指南
新手推荐流程
# ===== 步骤1: 查看网络参数 =====
nmcli connection show
ip link show
# 记录: CONNECTION_NAME 和 INTERFACE
# ===== 步骤2: 检查路由器配置 =====
apt install -y ndisc6
rdisc6 eth0 # 替换为你的网卡
# 确认: A flag=1 (SLAAC已启用)
# ===== 步骤3: 创建Token脚本 =====
nano /root/enable-token-888.sh
# 粘贴脚本内容,修改:
# CONNECTION_NAME="你的连接名称"
# INTERFACE="你的网卡名称"
# TOKEN="::888" # 可自定义
chmod +x /root/enable-token-888.sh
chmod +x /root/disable-token.sh
chmod +x /root/check-token.sh
# ===== 步骤4: 启用Token =====
/root/enable-token-888.sh
# ===== 步骤5: 验证配置 =====
/root/check-token.sh
ip -6 addr show eth0 | grep "scope global"
# 应看到包含 ::888 的地址
# ===== 步骤6: 路由器端口转发 =====
# 登录路由器,添加IPv6端口转发规则
# 目标地址: 2001:db8:1234:5678::888
4.3 配置后没有获得IPv6地址?
检查清单:
# 1. 确认路由器IPv6功能已启用
rdisc6 eth0
# 2. 检查NetworkManager状态
systemctl status NetworkManager
# 3. 查看连接配置
nmcli connection show "Wired connection 1" | grep ipv6
# 4. 查看日志
journalctl -u NetworkManager -n 50 | grep -i ipv6
4.4 Token配置了但未生效?
可能原因:
- 路由器未启用SLAAC (A flag=0)
- **DHCPv6优先级更高 **
- 配置顺序错误
解决:
# 使用检查脚本诊断
/root/check-token.sh
4.5 飞牛NAS重启后配置丢失?
原因: 脚本只临时配置,NetworkManager配置已持久化
验证:
# 重启后检查
reboot
# 重新登录后查看
ip -6 addr show eth0 | grep "scope global"
nmcli connection show "Wired connection 1" | grep ipv6
# 配置应该仍然存在
# 如果地址未生效,运行:
nmcli connection up "Wired connection 1"
4.6 如何更换Token后缀?
# 方法1: 修改脚本中的TOKEN变量
nano /root/enable-token-888.sh
# 找到 TOKEN="::888" 改为你想要的后缀
# 然后重新运行脚本
# 方法2: 直接使用nmcli命令
nmcli connection modify "Wired connection 1" ipv6.token "::新后缀"
nmcli connection down "Wired connection 1"
nmcli connection up "Wired connection 1"
# 验证
ip -6 addr show eth0 | grep "scope global"
文档信息
版本:** 2.2**
创建日期: 2025-10-24
适用系统: 飞牛NAS (Debian12 + NetworkManager) 状态: 已验证可用
更新日志:
2025-10-24: v2.0 - 简化文档,专注Token模式,删除EUI64教程(已被飞牛集成)
2025-10-24: v2.1 - 新增开启临时 IPv6 地址作为默认出站,IPv6 EUI64 Token 模式作为自定义,避免在路由器下发 /128 位 IPv6 地址 情况下被选为默认出站造成可能被跟踪的情况)
2025-10-24: v2.2 - 修复开启临时 IPv6 地址作为默认出站,实现方式解决重启失效问题。之前版本设置的权限在启动时优先级没有 NetworkManager 高被覆盖。(虽然 2.1 忘记上传重启后生效的脚本,但是它在重启后会被覆盖需要手动执行一次。所以上不上传都一样,用 NetworkManager 进行管理解决上一个版本的问题)