dns 分流,国内 ip 直连, fakeip 转发到 clash

2023-11-06 19:16:43 +08:00
 xjx0524

最近开始用上了 RouterOS ,科学上网通过旁路由 openwrt ,具体方案参考了站内一些大佬 fakeip 的方案。

具体方案如下:

  1. ROS 基础配置参考了这个文档 https://gitee.com/callmer/routeros_toss_notes
  2. 旁路由部署了 mosdns 和 openclash ( fakeip 模式),mosdns 国内域名查询阿里腾讯 dns 返回真实 ip ,国外域名请求 clash 的 dns 端口返回 fakeip 。
  3. 主路由 ROS 设置 dns 指向旁路由,增加 to_op 路由表默认网关为旁路由,通过 mangle mark-routing 将目的地址为 fakeip 和 telegram ip 的流量 指向 to_op 路由表

有一些疑问希望大佬们能帮忙解答一下

  1. 对于一些国外 ip (非域名)的连接,如果不像 telegram 那样特别配置,是不是就没法走科学线路,不知道这种 ip 直连的情况多不多?
  2. 我的 clash 直接用的机场的配置,我是希望 clash 保留原有域名规则的情况下,不去进行 dns 查询。我现在手动把所有 ip 规则配上了 no-resolve ,不知道这样是否有用,或者有没有更好的解决办法?
  3. 现在的配置下,打开国外网站不够丝滑,以谷歌为例,具体表现为
    1. 浏览器首次打开谷歌或过了较长一段时间后再打开,会白屏约 1 秒,后续再打开正常。推测应该是 dns 问题,没有了缓存就会这样?
    2. 无论是否首次打开,显示出页面后,网页 tab 处仍然会转圈一段时间

上面 3 的这个情况,在我将设备网关手动设置成旁路由的时候,基本不会出现,希望大佬能提供一些排查思路。

目前网络知识还是半吊子水平,有些问题不好直接搜索到,希望大佬们能帮忙解答一下

6851 次点击
所在节点    宽带症候群
24 条回复
LisaSue
2023-11-06 20:53:54 +08:00
https://github.com/vernesong/OpenClash/issues/2767
第三点的话你 f12 看下是不是这个情况.我 openclash 已经放弃 fakeip 了
xjx0524
2023-11-06 23:53:10 +08:00
@LisaSue 还真是,测试了几个国外网站,Initial connection 和 SSL 耗时 7 、8 秒,还有一部分 Waiting (TTFB) 耗时比较长。
之前用 openwrt 做主路由,所有流量全过 openclash 都没有这问题
lkjkkk
2023-11-07 01:12:53 +08:00
fakeip 加混合模式试试
imKiva
2023-11-07 05:18:40 +08:00
都用策略路由了就不需要在分流机器上用 openclash/shellclash 了。直接在“旁路由”上跑 clash 核心开 tun 模式和 fake ip ,然后 ip route add 198.18.0.0/16 dev utun

从目前你的描述来看,ROS 上也不需要用 mangle ,更不需要 “to_op 的默认网关为旁路由”。一种性能更好的方法是:直接往 main 表里加一条 198.18.0.0/16 下一跳为旁路由的地址。但是你需要注意不能让你的机场域名被解析成 fake ip ,否则流量会成环。不过也可以用另一张路由表,假设叫做 bypass ,然后所有 src ip 为旁路由的流量走 bypass 表,bypass 表里的默认网关为 pppoe-out1 之类,再加上几条局域网的地址网关为 bridge 口就行。命令大概类似这样:

/routing/table add fib name=bypass

/routing/rule add src-address=旁路由 IP table=bypass

/ip/route add distance=1 gateway=pppoe-out1@main dst-address=0.0.0.0/0 routing-table=bypass
/ip/route add distance=1 gateway=bridge@main dst-address=192.168.0.0/16 routing-table=bypass

然后 main 表上把 fake ip 导向旁路由

/ip/route add distance=110 gateway=旁路由 IP dst-address=198.18.0.0/16 routing-table=main

手机上靠印象打的,可能不太对,你自己弄的时候善用 tab 补全就好了
imKiva
2023-11-07 05:19:58 +08:00
对于 Telegram 这类,用同样的方法

/ip/route add distance=110 gateway=旁路由 IP dst-address=<TelegramIPCIDR> routing-table=main
imKiva
2023-11-07 05:20:52 +08:00
@imKiva 我目前就在用同类方案,没有发现除了 TG 以外的 IP 直连的主流应用
imKiva
2023-11-07 05:36:31 +08:00
不推荐在策略路由下用这种带有包装的 clash 例如 openclash/shellclash 是因为:它们的配置是给一个路由器透明代理的最傻瓜级解决方案。

但是在你有正确的 DNS 分流和 fake ip 之后,很多 shellclash/openclash 中的配置(例如什么打标记,tproxy 转发,53 端口放行云云)就不再需要了,因为策略路由已经完成了同样的事情。那么此时再让这些包装工具带上这些规则,只会增加调试难度,并且可能在你意想不到的地方带来问题。
carrionlee
2023-11-07 06:54:23 +08:00
1. 是的,ip 直连的手动添加静态路由或者 routing rules (二选一),不建议用 mangle 。这种情况多不多要看你的使用场景。
2. 是的,所有 ip 规则加上 no-resolve 就行
3. 应该是你的默认防火墙规则导致的。应该有一条"drop invalid"的规则,把里面的 In. Interface List 改为 !LAN ,不然的话,clash 过来的流量会标记为 invalid 而造成 TCP 流量握手缓慢
xjx0524
2023-11-07 08:00:27 +08:00
@carrionlee 感谢大佬,3 的问题改完确实好了。但为什么 tcp 握手流量会被判断为 invalid 呢?
xjx0524
2023-11-07 08:08:02 +08:00
@imKiva 1 、ros 直接设置路由表的方式也试过,是没问题的。只不过想到会国外 ip 直连的情况,会加很多路由规则。所以就想着路由表看着清爽点,mangle 表复杂点。不过直接用路由表性能更优的话,那我还是改回来吧

2 、用 openclash 也是因为之前习惯了图形界面,那这次我也直接改成部署核心吧。这种情况下,除了 ip route add 198.18.0.0/16 dev utun ;对于 udp 流量,或者国外 ip 直连的情况,也需要单独配置转发吧?我先研究下 openclash 自动加了哪些防火墙规则
carrionlee
2023-11-07 08:29:35 +08:00
@xjx0524 好像说是加密流量的关系,具体没深究。静态路由的确性能更好。也可以用策略路由的方式(因为我有 2 条 vlan 都要走 fakeip ,所以用策略路由比静态路由灵活一点),性能应该差不多。总之都比 mangle 好。
用虚拟机单纯装 shellclash 或者有个叫 paopapgateway 的项目,相对来说规则清爽一点,不过归根结底还是看 clash 配置文件。
XIU2
2023-11-07 08:39:12 +08:00
一直没折腾过路由器,看了下你的描述,就想问下:

路由器上搞代理时,单纯的国内外 IP 分流很简单,但是否可以实现只让国外的 HTTP 协议流量走代理,其他的那些游戏啊什么 IP 直连(比如 TG )、或其他特殊协议的依然直连?
毕竟对我来说大部分情况下只让网页类型的流量走代理就够了。

如果说只能手动排除 IP 段的话,岂不是很麻烦而且无穷无尽?。。。
xjx0524
2023-11-07 10:12:12 +08:00
@XIU2 这种需求是不是浏览器装个插件,使用 http 或 socks 代理就行?在路由器上去识别 http 协议比较麻烦吧
imKiva
2023-11-07 13:17:45 +08:00
@xjx0524 1. 一般来说 mangle 表会让 fasttrack 失效,这是最主要的性能影响。在需求简单的情况下用 /routing/rules 更好,你可以把这个当成一个更弱的 mangle ,但需要注意如果两个一起用,mangle 表优先。

2. udp 流量不需要单独配置,因为 ip route 这条命令加的路由表对所有 ip 包都生效。并且 premium 和 meta 核心的 tun 都可以处理 udp 入站流量。
对于国外 IP 需要进代理的,用同样的方法加路由表就行。如果你嫌要同时在两台设备上维护相同的路由表很麻烦,可以考虑用一些路由协议,比如 ospf 或者 bgp

3. 如果你有 IPv6 策略路由的需求,方法同 IPv4 ,但 premium 核心的 tun 不支持 IPv6 入站流量,需要用 meta 内核
xjx0524
2023-11-07 14:06:51 +08:00
@imKiva 感谢大佬解答,之后准备再把 ipv6 配置一下,有问题再来请教~
hsj1992
2023-12-05 17:54:25 +08:00
@imKiva 想请问一下大佬,我同样是 ROS 主路由,本地 DNS 服务器和 fakeip 旁路网关使用了 PaoPaoDNS 和 PaoPaoGateWay 。
ROS 是在静态路由表里加一条 11.0.0.0/8 ,下一跳为旁路网关的地址。

在 ROS 开启了 Endpoint-Independent NAT 后,地址是直连的 STUN 服务器,NAT 类型测试的映射/过滤行为都是 EndpointIndependent;
但是不直连而是经过旁路网关的 STUN 服务器,NAT 类型测试的映射/过滤行为变成了 AddressDependent/EndpointIndependent;
终端把 IPV4 网关地址 手动设置成旁路网关 IP 地址,NAT 类型测试映射/过滤行为就都是 EndpointIndependent 了,说明旁路网关的 Full Cone NAT 没问题。

这个情况是设置因为静态路由导致的么?
imKiva
2023-12-05 23:50:42 +08:00
@hsj1992 这个问题我前两天刚好在调试,阅读了一下 NatTypeTester 的源码,正好可以解答。我不清楚 PaoPaoGateway 里用的 Clash 是 Premium 核心还是 Meta 核心。Premium 核心似乎是不支持 Endpoint-Independent NAT 的(存疑),但是 Meta 核心在 tun 小节的配置里有一条 `endpoint-independent-nat: true` 设置之后就可以做到 mapping/filtering 都变成 EndpointIndependent 。

在上面的设置的基础上,从你的描述中 “终端把 IPV4 网关地址 手动设置成旁路网关 IP 地址....” 这一段可以看出,你用的核心应该已经给你做好了 EndpointIndependentNat (应该?),所以上面的内容可以忽略(打的时候没看到这一句,但是懒得删了,希望对后人有帮助)。这可能和 STUN 协议的原理有关,STUN 检测 filtering 行为的原理可以简单描述为:

1. 你向 stun server (记为 A ) 说 “请返回我现在访问你用的 IP:Port”
2. stun server 返回以下内容:
1. 你当前访问 stun server 的 IP:Port ,记为 Self
2. 给你发这条回复的 stun server 的 IP:Port ,即上面的 A
3. 另一个 stun server 的 IP:Port ,记为 B
3. 你向同一个 stun server A 发起一个请求,说 “请 改变 IP 和端口 向我发起一条请求”
4. stun server B 会向你的 Self 发送一个 stun 包,如果你能接收到,那么说明 filtering 行为是 EndpointIndependent

从这个过程中可以看出,Clash 会在第 4 步的时候用一个“之前你没有主动发起连接”的 IP 向你回包。但是我在测试的时候发现:tun 使用的 stack 不同( gvisor 或者 system ),会有不同的回包 IP 行为,其中使用 system stack 存在 bug 。所以如果你的 PaoPaoGateway 里的 tun 用的是 system stack ,考虑切换到 gvisor 并配合 Meta 核心的 `endpoint-independent-nat: true` 再做尝试。
此外,还可以把 ROS 里的有一条 “drop invalids” 的规则里的 In. Interface. List 改成 !LAN ,我看前人的一些教程一上手就把这个规则改了,但我没测试过这个防火墙规则是否有影响,你也可以试一试。

这个问题其实非常复杂,我自己调试的时候费了不少功夫,最后还修改了 Clash Meta 核心的代码才实现了 filtering/mapping 都是 EndpointIndependent 。如果你按照上述的方法不能得到预期的结果,可以加个联系方式,我有空的时候可以帮你看看,文字我觉得很难说清楚这个过程(主要是我没有用过 PaoPaoGateway 不知道里面的细节)。
imKiva
2023-12-05 23:59:01 +08:00
@hsj1992

> 这个情况是设置因为静态路由导致的么?

99% 不是。我也使用静态路由的方式,客户端的网关均指向 ROS ,但在我的配置中得不到 FullCone NAT 的原因有两个:
1. 我的静态路由配置不完全:因为我的 DNS 对 stun server 始终返回真实 IP ,在上面的第 3 步的时候会变成直连从而测出未定义行为。
2. Clash Meta 的 tun 入站对 `conn.LocalAddr()` 的赋值存在 bug ,在我修复这个问题后,成功测出 FullCone Nat
hsj1992
2023-12-06 01:19:05 +08:00
@imKiva
谢谢您的答复!
PaoPaoGateWay 好像不是使用 tun ( ip addr 和 clash yacd 面板里没看到 tun 设备),是 TProxy 和 nftables 。

作者博客的详细说明文章: https://blog.03k.org/post/paopaogateway.html
Github 项目地址: https://github.com/kkkgo/PaoPaoGateWay
相关的两条 nftables 脚本和 clash 的基础 yaml:
https://github.com/kkkgo/PaoPaoGateWay/blob/main/FILES/usr/bin/nft.sh
https://github.com/kkkgo/PaoPaoGateWay/blob/main/FILES/usr/bin/nft_tcp.sh
https://github.com/kkkgo/PaoPaoGateWay/blob/main/FILES/etc/config/clash/base.yaml

我当时的使用是有替换为 Clash meta 内核(好像还是 2023-10-13 时候自己编译的)。
不知道编译新版内核去替换再试试会不会有区别。
imKiva
2023-12-06 03:14:08 +08:00
@hsj1992 tproxy 我就不清楚了,我自己没有使用 tproxy 的动机。你可以在客户端上开个 wireshark 抓包一下用 NatTypeTester 之类软件测试过程中的 stun 包。用经过 clash 和不经过 clash 的 stun server 的两种流量互相对比一下,看看哪里不一样。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/989243

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX