OpenWrt 软路由用户换 sing-box 内核的动机很直接:协议兼容性更好、UDP 性能更强、规则集语法更灵活。但 PassWall2 上一切换,整套路由规则可能直接消失——网页打不开、DNS 解析失败、流量全部直连。切回来又全部正常。这个现象指向的是 PassWall2 v26.1.27 在 sing-box 1.12+ 上的一个已知兼容问题。
先看日志:是文件缺失还是语法不兼容
SSH 到路由器,看 sing-box 启动日志:
logread | grep sing-box
如果看到类似报错:
FATAL: parse rule-set[0]: open /tmp/etc/passwall2_tmp/singbox_srss/geosite-cn.srs: no such file or directory
geosite:cn convert to srs failed!
这就是本文要解决的问题:Geoview 工具没有在切换内核时生成对应的 .srs 文件。
| 日志关键词 | 问题性质 | 根因 |
|---|---|---|
no such file or directory + .srs | 文件缺失 | Geoview 转换流程未执行或失败 |
parse rule-set + failed | 语法解析失败 | sing-box 版本和 PassWall2 语法不匹配 |
convert to srs failed | 转换失败 | 源 dat 文件损坏或格式不兼容 |
| 无报错但规则不生效 | 静默失败 | 规则匹配顺序问题,见 Discussion #1035 |
如果日志里没有任何 sing-box 相关报错但规则依然不生效,不是你排查方向错了——这是 sing-box 在 PassWall2 下的静默失败,切回 Xray 做对照测试最直接。
Xray 和 sing-box 的规则之路:两条根本不同的语法
理解这个问题的根源需要先看一张表——Xray 和 sing-box 的域名规则语法是两套完全不同的体系:
| 维度 | Xray | sing-box |
|---|---|---|
| 域名规则格式 | geosite:cn (dat 文件) | rule-set:local:/path/to/geosite-cn.srs |
| IP 规则格式 | geoip:cn (dat 文件) | rule-set:local:/path/to/geoip-cn.srs |
| 规则文件后缀 | .dat | .srs |
| 远程规则集 | 不支持(需手动更新 dat) | rule-set:remote:https://... |
| 直连写法 | "geosite:cn" -> direct | "rule-set:geosite-cn" -> direct |
PassWall2 的设计初衷是在 Xray 和 sing-box 之间无缝切换。它的 Geoview 工具读取 dat 文件、把它转成 srs 格式、放到 sing-box 期望的目录——整个过程应该对用户透明。但在 sing-box 1.12.18 之后,这个转换链路断了。
三个修复路径,按风险从低到高
路径 1:切回 Xray 内核(零风险,推荐)
如果你不需要 sing-box 专有的协议(如 Hysteria 2 的某些高级配置),最省事的方案就是切回 Xray:
- PassWall2 主界面 → 基本设置 → 内核选择 → 切换到 Xray
- 保存并应用
- 检查路由规则是否恢复
Xray 继续使用 dat 文件,Geoview 工具不再需要做 srs 转换,规则直接生效。代价是失去了 sing-box 对 TUIC v5、Hysteria 2 和 Reality 的一些高级选项支持。
路径 2:手动放置 .srs 文件(中等风险)
如果你必须用 sing-box 内核,SSH 到路由器手动补文件:
# 创建目录
mkdir -p /tmp/etc/passwall2_tmp/singbox_srss/
# 从 sing-box 官方规则集仓库下载
wget -O /tmp/etc/passwall2_tmp/singbox_srss/geosite-cn.srs \
https://github.com/SagerNet/sing-geosite/releases/latest/download/geosite-cn.srs
wget -O /tmp/etc/passwall2_tmp/singbox_srss/geoip-cn.srs \
https://github.com/SagerNet/sing-geoip/releases/latest/download/geoip-cn.srs
# 重启 PassWall2
/etc/init.d/passwall2 restart
关键注意事项:
/tmp在路由器重启后会清空——你需要在启动脚本(/etc/rc.local)里加下载命令- 文件名必须和 PassWall2 规则配置里引用的名字一致,大小写敏感
- 如果你的路由器存储空间小于 50MB,不要下载全量规则集,用精简版
路径 3:自定义 Geoview 数据源 URL
PassWall2 的 Issue #979 讨论了自定义规则数据源的可行性。如果你的分流需求是特定国家(如俄罗斯、伊朗),可以用社区维护的精简规则代替全量 geosite:
- 伊朗:
Chocolate4U/Iran-v2ray-rules - 俄罗斯:
runetfreedom/russia-v2ray-rules-dat
在 PassWall2 的规则设置里把数据源 URL 替换成这些社区源,下载量从几十 MB 降到几 MB,路由器的内存和存储压力也会小很多。
低内存设备(≤512MB)的警告
如果路由器只有 512MB RAM,直接加载全量 geosite + geoip 规则集可能导致 OOM。Xray 在加载 IR 全量规则时内存占用超过 350MB(Issue #1010),sing-box 虽然内存效率更好但依然有风险。
低内存设备的建议:
- 只加载你真正需要的 3-5 个核心分类(cn、ir、ru、private、ads),不要全量加载
- 使用精简版 .srs 文件而不是官方全量版
- 把规则数控制在 5000 条以内,超出部分改用域名关键词匹配而不是 geosite 分类
全屋代理场景下的内核选择
OpenWrt 旁路由承载全屋设备代理时,内核的稳定性优先级高于协议先进性。如果你的路由规则偶尔消失一次就会让全家的电视、游戏机、智能家居全部断流,那 Xray 的稳定路径比 sing-box 的前沿特性更有价值。
这时候订阅端的兼容性也是一层保障——选一个 兼容 Clash / Singbox / V2Ray 的订阅,不管未来 PassWall2 选哪个内核,订阅格式都能直接适配,不会因为内核切换导致导入失效。
未覆盖的边界
- 本文基于 PassWall2 v26.1.27 + sing-box 1.12.18 的实测反馈。PassWall2 后续版本如果修复了 Issue #997,本文的临时方案可能不再需要。
- OpenWrt 版本为 23.05.x,其他版本(如 iStoreOS、LEDE)的 PassWall2 行为可能不同。
- 手动下载 .srs 文件的路径和命令在 ARMv7 / aarch64 / x86_64 设备上通用,但 mipsel 设备(老款路由器)的 wget SSL 兼容性可能有差异。
- sing-box 1.13+ 如果改变了 .srs 文件路径约定,本文的手动路径需要相应调整。