探讨下有没有国内流量保留 ipv6, 国外流量禁用 ipv6 的优雅姿势

201 天前
 momody2099
家里电信双栈网络,路由器是 lede/openwrt ,DNS 用 adguard home 做了一层缓存转发,启用 ipv6 地址和 ipv6 解析。国内访问一切正常而且很爽,但国外流量一是因为机场不支持 ipv6 ,二是出国 ipv6 直连线路确实拉跨,经常访问不了或者出奇的慢。

当前的方案是将直连不能访问的网站(如 V2EX )使用 adguard home 的 ipset 功能,将解析到的 ipv6 加到一个指定的 ipset, 然后在 openwrt ip6table forward 转发链上 reject 掉,这样的问题是还会时不时碰到无法访问或访问慢的网站,需要不停的加这个 ipset 清单。于是想着有没有简洁优雅的方式可以直接保留国内 ipv6 流量,禁用国外 ipv6 。

先说我能想到的 2 个方案,一是 DNS 层面,另一是 iptables 层面:
1. 当前使用的 adguard home 能做的只能全局停用或者启用 ipv6 解析,无法指定对部分域名进行 ipv6 的停用或启用解析,这样的话就得多加一层 DNS 解析,多加的这层负责国外所有 DNS 解析,并且配置停用 ipv6 解析。这个方案的问题是需要 2 层 DNS 解析,而且国内,国外的域名清单能否找全,哪里能有?

2. 在 openwrt 上使用 ip6tables 的 FORWARD 转发链,配置只允许国内的 ipv6 网段通过,REJECT 所有其它网段,找了个国内的 ipv6 网段清单而且不多,这个实现容易。但弊端是实际所有客户端还是能拿到 ipv6 地址,而且像浏览器之类的客户端都是 ipv6 优先,会先进行 ipv6 请求,待 ipv6 请求失败后再次进行 ipv4 请求,多少对使用体验会有影响。附一个 iptables 实现:
ip6tables -F FORWARD
ip6tables -I FORWARD -d 240e::/18 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2408:8000::/20 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2409:8000::/20 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240a:c000::/20 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240c:c000::/20 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240a:4000::/21 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240a:8000::/21 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240b:8000::/21 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240c:8000::/21 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240d:4000::/21 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2408:4000::/22 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240c:4000::/22 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240d:8000::/24 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240f:4000::/24 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240f:8000::/24 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2400:dd00::/28 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 240c::/28 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2001:4510::/29 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2400:a980::/29 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2a0c:f480::/29 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2a0d:2480::/29 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2406:cf00::/30 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2001:250::/31 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2001:da8::/31 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -d 2403:800::/31 -j ACCEPT -m comment --comment "CHINA MAINLAND ipv6"
ip6tables -A FORWARD -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
ip6tables -A FORWARD -j REJECT
2963 次点击
所在节点    宽带症候群
17 条回复
evalfun
201 天前
用 mosdns ,对非国内域名优先使用 ipv4 解析结果就可以了。不推荐动防火墙规则
vcn8yjOogEL
201 天前
github 上有提前做好的 bgp ip 表, 直接让非国内 v6 全部返回无路由/拒绝即可, 但这个方法可能会让设备认为它在纯 v4 环境

dns 走 geosite, 只有国内域名返回 aaaa 记录
yaott2020
201 天前
屏蔽国外 aaaa 解析即可
pagxir
201 天前
dns 的设置,我一般是这样子
1 国内 IPv4
2 国外 NAT64
3 国外 IPv6
4 国外 IPv6
5 国内 IPv6
这样的选择顺序。

然后路由器上对 NAT64 的 IPv6 地址做一下转换或者 NAT 就可以了,完全不需要 ipset 。
TerenceRust
201 天前
chinadns ,屏蔽海外 ipv6 解析。iptables 用 ipset 兜底
TerenceRust
201 天前
首先需要一个中国 ipv6 地址表,网上有,每天 crontab 更新就行。chinadns 会根据这个地址表屏蔽非国内的 ipv6 地址返回,iptables 也可以用这个表的 ipset 来做拦截
chinawrj
201 天前
ip6table 配合 geoip ,比如:
ip6tables -A FORWARD -m geoip ! --dst-cc CN -j DROP
TwoBall
201 天前
我用的 paopao 的一套方案,目前还可以
mantouboji
201 天前
你国外机场换一个支持 IPv6 的吧,gigs racknerd2 v.ps 都可以
keyfunc
201 天前
mosdns ,维护个 CN IP 列表

```
- tag: local_sequence
type: sequence
args:
- exec: $forward_local
- matches:
- "resp_ip $local_ip"
exec: accept
- exec: drop_resp

- tag: remote_sequence
type: sequence
args:
- exec: prefer_ipv4
- exec: ecs 58.32.0.0
- exec: $forward_remote
- exec: accept
```

就行了
xiaoke
201 天前
paipaodns ? 作者也在 v 站
maybeonly
201 天前
说真的
reject-with icmp6-port-unreachable
还是蛮快的
这样客户端就不会等超时
直接就尝试 ipv4 了
屏蔽 4a ?太麻烦了吧……
cst4you
201 天前
直接全关闭 ipv6 解决问题(
pagxir
201 天前
如果是 linux 系统的话,你也可以用 ip addrlabel 处理,将国内全归到一个 label 去,然后也修改一下/etc/gai.conf 。因为国内跟国外不在一个 label ,就会优先级很低,变成国内 ipv6 -> ipv4 -> 国外 ipv6 的选择顺序。
menurable
200 天前
两个 adguardhome 首先用一个 adguardhome dns 分下流 再套娃
sentivcn
199 天前
mosdns ,污染域名的上游 prefer_ipv4
fengyaochen
198 天前
vps 上安装 adguard 禁用 aaaa 解析就行了,dns 就填 vps 的 adguard 地址,反正结果 vps 的流量都是国外流量,就能达到目的了

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

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

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

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

© 2021 V2EX