前言
在几年前玩过软路由,配置是 J4125,当时觉得 OpenWrt 过于难配置、很多 Package 必须在编译的时候加上,当时是直接装了 Ubuntu 拨号,iptables 做 NAT 转发,再用 Docker 起一些服务,也够用,但是后来换了 AX3600 以后,就不想折腾送给朋友了。
随着使用 NAS、Xbox、Apple TV 等对网络需求的日益提高,以及 ShellClash 的内存泄露和 AX3600 连开个源都要耍猴等诸多问题,去年中旬购入了一台畅网 N5105,从 OpenWrt 到 ESXI 到 PVE、再到编译固件、云编译、折腾 DNS,过程很有意思,也很久没写博客了,就记录一下。
2024-05-12 更新:
更换 MosDNS 为 SmartDNS
0x00 初见
和大多数初次接触软路由的小白一样,用 U 盘安装 PE 以 img 写盘的方式写恩山上的镜像,问题在于:
- 硬件 OpenWrt 太浪费,另外很多小众功能在这种嵌入式系统中支持不友好。
- 要什么软件包只能看作者有没有编译好,没有的话自己装有很多编译时就要加上的内核级依赖,安装时必出错。
- 一大堆功能自己用不上。
- 折腾完后再做改动可能出问题,一出问题又要重装重新配置。
那有没有一种方案可以解决这些问题,还能什么都能跑,又能随时恢复呢?
0x01 虚拟化
ESXI
中间学习编译固件和配置直通等基础操作也没什么讲的,网络上太多相关资料了,这里就不多说了。
ESXI 解决了我几大问题:
- OpenWrt 系统只要 1 核 1G 内存就够用了,不浪费硬件,甚至对于不在 OpenWrt 上跑 Docker 的来说,1G 内存都是奢侈。资源得到了极大的节省。
- 虚拟机可以随时备份,不用担心出问题了重装,还可以随时恢复。
- OpenWrt 跑不了的,或者不想破环 OpenWrt 系统环境,可以创建另外的虚拟机。
已经很理想了对吧,直到家里断了一次电,ESXI 老牛拉破车般的启动速度也就不说了,甚至还把 OpenWrt 的虚拟磁盘搞挂了,顺便再记录一下修复命令吧:
# 检查磁盘
vmkfstools -x check openwrt.vmdk
# 以下结果表示磁盘需要修复
Disk needs repair.
# 修复磁盘
vmkfstools -x repair openwrt.vmdk
# 以下结果表示此盘修复成功
Disk was successfully repaired.
很幸运,这次只是小问题,但是在找解决方法的过程中,发现了还有人甚至 vmdk 都消失了。
另外在 ESXI 中再启动其它虚拟机,如果运行时间比较长还有几率出现虚拟机内磁盘消失的情况,可能 N5105 对于企业级的平台来说还是太弱了,所以也就放弃了 ESXI。
PVE
直到遇见了 PVE,底层 Debian、LXC 模板一键部署虚拟机、惊人的启动速度、热修改虚拟机硬件配置,确实很强大
目前来说 PVE 使用上方便、稳定,暂时没有出现任何问题,最主要的就是不要什么东西都在 PVE 上跑,用 LXC 快速部署一台 Linux,用完就删,稳定性也非常好,温度表现上也比 ESXI 好太多。
至此,PVE 成为了我的主力虚拟化平台,接下来就是 OpenWrt 上令人头疼的 DNS 了。
0x02 DNS
OpenClash 内置分流
OpenClash 写好规则可以达到较为理想的分流效果,但是如果要加入去广告等功能,规则可能达到几万条,这在 PC 平台可能没什么问题,但是我一向习惯于统一管理,手机、路由器等设备都用同一份规则,不仅仅是路由器平台的处理效率低下,而且 iOS 对于 APP 的内存限制非常严格,并且 iOS 平台 stash 的处理性能也十分有限,于是使用了 AdGuardHome
AdGuardHome
流程图:
似乎也很完美,但是不管是只使用 OpenClash 还是搭配 AdGuardHome,在使用过程中发现了两个问题:
1. 国际厂商 DNS 分流
例如 Apple、Microsoft,这两大厂商在大陆有 CDN 但是部分服务只有国外 IP,由于运营商优化了这一点使得不同地区解析到的 IP 虽然是国外的,但基本上是最优的(排除某些地区或某些运营商的垃圾 DNS 和线路)
那就出现了一个问题:
通常 Apple、Microsoft 服务是选直连,但是会触发 FallBack,使得请求变得非常慢,例如:
- 外区 APP Store/Apple Music 中,部分国区没有的 APP/音乐,大陆的 CDN 中没有此资源,会导致请求变得非常慢,甚至下载失败。
- iOS 网络检测域名:
captive.apple.com
,大陆的 CDN 中没有此资源,被 Fallback 到直连很差的 IP,导致网络检测失败,弹窗提示无法连接到互联网,Windows 网络检测域名:www.msftncsi.com
也偶现此问题,但 Azure 线路比较好,出现的概率比 iOS 小很多。
2. 猝不及防的 iOS 16 DNS 安全更新
如果说 OpenClash 启用 绕过中国大陆 IP
,再让 Microsoft、Apple 的域名走代理,那么有大陆 CDN 有资源的会直接直连,否则走代理,这样似乎又完美解决了,直到 iOS 16 的正式版发布,Apple 宣布了 DNS 安全更新:
如果您的网络支持发现指定解析器(也称为 DDR ),则 DNS 查询将自动使用 TLS 或 HTTPS。要使用加密的 DNS,您的设备需要知道解析器支持 TLS 或 HTTPS,并且可能还需要学习端口或 URL 路径。诸如 DHCP 或路由器播发等常见机制仅提供普通 IP 地址。DDR 是 Apple 与其他行业合作伙伴在 IETF 中开发的一种新协议。
截止至写本文时(2023-04-09),AdGuardHome 对此支持仍不完善,导致 iOS 16 设备解析缓慢,甚至无法解析,日志中也有一大堆 SERVFAIL,Github 中也有人提出了这个问题,但是官方给出的解决方案与版本更新仍然不完美,即使使用了上面说的 绕过中国大陆 IP
& Microsoft
、Apple
走代理,也会出现 DNS 解析缓慢的问题,并且还带来一个问题,如果节点不稳定或直接挂了,那 iOS 设备直接判断无网,导致频繁弹窗,或触发无线局域网助理功能,这样虽然 Wi-Fi 是已连接的状态,但是实际走的是蜂窝网络。
MosDNS
综上所述,目前看来需要一个这样的 DNS 服务器:
- 支持国际厂商 DNS 分流
- 支持 iOS 16 安全 DNS
- 支持去广告
- 支持 DNS 缓存
于是找到了 MosDNS,目前来看是最完美的解决方案,它支持 DNS 缓存、DNSSEC、DOH/DOT 等功能,iOS 16 也完美支持,而且还支持域名分流。
微软某些服务会验证返回 IP 真实性(Xbox 居多,例如微软模拟飞行),如果你出现了某些服务无法访问,除了真的可能是连接问题,还有可能是 DNS 验证失败,这时候你可以尝试检查一下你的 DNS 服务器是否支持 EDNS 和 DNSSEC。
流程图:
对于我来说 MosDNS 内置的配置文件已经非常完善,只需要手动勾选 TCP/DoT 连接复用
和 启用 EDNS 客户端子网
完成功能性问题即可,并且内置了去广告规则,但是目前来看去广告需求不是那么大了,DNS 层只能去广告域名,还有很大一部分网站还是会通过 URL 的方式加载,所以我还是使用了浏览器插件的方式去广告
MosDNS 设置远程 DNS 必须使用 DoT,如果你使用的是 DoH,那么 Bootstrap 最好也使用国外的,因为如果是大陆的 DNS 服务作为 Bootstrap,那么对于节点来说可能并不是最快的 IP,这样会影响本就不快的 Fallback 速度,如果使用的是 DoT,由于不需要被 Bootstrap 解析,所以可以被节点连接查询 IP,在 Clash 控制面板中也能看到 Process 为 MosDNS,对节点来说能拿到最快的 IP。
SmartDNS
在一段时间的使用下来,发现连接一些国内的网站并不能优选,且运营商 DNS 解析到的 IP 有时不是最优
为了更好的网络体验,调研一番以后,决定使用 SmartDNS + OpenClash 这样的组合
并且通过 OpenClash 分流国内外 DNS 查询
SmartDNS 服务使用的端口为:6053
第二 DNS 服务器端口为:6153
流程图:
之前 ImmortalWrt 默认配置了 SmartDNS 的第二服务器,但是在最新的版本中已经删除了,所以我们需要手动配置一下
已删除: https://github.com/immortalwrt/packages/commit/f187ad1d5d5e86f37760631aef764c4f05dc709f
首先设置好第二 DNS 服务器的端口和组名,我这里设置为 6153
和 Global
常规设置:(不勾选 自动设置 Dnsmasq
)(打码部分为运营商 DNS):
你也可以填写你喜欢的国内公共 DNS 服务商
注意这里国际组的 DNS 配置最好填写 DOT,因为不需要额外 Bootstrap 解析,服务器组名填写 Global
(和上一步设置的一样),另外在配置 Global
组 DNS 服务器时,记得勾选 从默认组中排除
,以免影响到国内组解析
OpenClash 配置:
由于 Fallback 即将被弃用,我们将使用 nameserver-policy 来分流 DNS,达到 DNS 分流和防泄露的效果
勾选 自定义上游 DNS 服务器
不勾选 追加上游 DNS
、追加默认 DNS
NameServer 使用 SmartDNS 第二服务器
FallBack 和 Default-NameServer 可不填
OpenClash 集成了 nameserver-policy
的自定义功能,所以我们可以很方便的配置,在自定义选项中加入:
"geosite:cn,private,apple":
- 127.0.0.1:6053
如果你的订阅提供商的节点域名解析比较奇怪,可添加一个 SmartDNS 国内组或是任意你喜欢的国内 DNS 服务器到default-nameserver
并勾选节点域名解析
或在配置文件的 DNS 下添加类似下面的选项:
以下为示例:
proxy-server-nameserver:
- https://120.53.53.53/dns-query
- https://223.5.5.5/dns-query
为什么不用 fake-ip?
fake-ip 的优点是可以解决 DNS 污染,但是缺点也很明显,无法解决国际厂商 DNS 分流,导致国际厂商的服务无法直连,而且也无法解决 iOS 16 的 DNS 问题、DNS 不能缓存、BT 下载无法使用、部分游戏无法连接、加速器的节点全是 1ms 等一大堆兼容性问题,当然这些问题都可以通过 fake-ip-filter
解决,但是这样就失去了 fake-ip 的优点,而且维护起来也很麻烦,所以我还是选择了 redir-host 方案,只要配置正确也不会出现 DNS 污染的问题。
虽然 Clash 内核移除了 redir-host
,但是 OpenClash 作者在 v0.45.87-beta
版本中解决了这个问题:
除 Meta 内核,其他内核的 redir-host 模式均改为使用 fake-ip 进行模拟 (上游内核已移除 redir-host)
所以 OpenClash 还是可以正常使用 redir-host 模式的。
另外由于原版内核已停更,现更建议使用 Meta 内核
附:Clash DNS 防泄露最简配置
dns:
enable: true
use-hosts: true
nameserver:
- "tls://1.1.1.1#\U0001F680 节点选择"
- "tls://8.8.8.8#\U0001F680 节点选择"
- "https://cloudflare-dns.com/dns-query#\U0001F680 节点选择"
- "https://dns.google/dns-query#\U0001F680 节点选择"
nameserver-policy:
geosite:cn,apple:
- system
- 119.29.29.29
- 223.5.5.5
proxy-server-nameserver:
- https://120.53.53.53/dns-query
- https://223.5.5.5/dns-query
nameserver 中 "#\U0001F680 节点选择" 这部分修改为你的策略组名称