利用 Dnsmasq 的 ipset 实现智能路由、科学上网

上一篇文章《在 EdgeRouter Lite 上实现科学上网》是用的比较传统的方式,即简单地添加目的路由。对于比较大规模的 ICP 例如 Google, Facebook,挖出他们的网段然后添加到路由表里是可行的(主要是他们有较好的网络基础设施建设,都申请了自己的 IP 地址段,并且用 BGP 互联广播到全网)。不过对于绝大多数被封的站点,想要一个一个地追踪他们的 IP 地址是多少并保持更新,这无疑是非常吃力的。好在昨天翻 Dnsmasq 的 Manpage 读到了 ipset 的功能选项,放狗一搜发现早有人提到这项功能了,不过都是在 Openwrt 上实现的。这回我决定在 EdgeRouter Lite 上也实现一次。

目前 ER-Lite 上最新的固件是 1.5.0 版本,基于 Debian Squeeze 6.0.9 ,很遗憾其中的 Dnsmasq 版本是 2.62,根据 Change Log,需要到 2.66 版本才能有 ipset 支持,这样只好自己编译了。好在编译起来不麻烦,把几个需要的 feature 在 src/config.h 里加上,然后在 Makefile 里把 CC CFLAGS LDFLAGS PKG_CONFIG_PATH 等几个变量设好,就可以直接编译了。(当然有些 feature 需要额外的依赖,需要事先编译好)我这里编译的 dnsmasq 2.71 版本,feature 尽量和原系统预装的 2.62 保持一致。

ubnt@ERL:~$ /usr/sbin/dnsmasq --version
Dnsmasq version 2.71 Copyright (c) 2000-2014 Simon Kelley
Compile time options: IPv6 GNU-getopt no-RTC DBus no-i18n IDN DHCP DHCPv6 no-Lua TFTP conntrack ipset auth no-DNSSEC

This software comes with ABSOLUTELY NO WARRANTY.
Dnsmasq is free software, and you are welcome to redistribute it
under the terms of the GNU General Public License, version 2 or 3.

直接替换原系统里的 2.62 版本,就可以无缝工作了。以 Google 为例,在配置中添加如下选项:

ubnt@ERL:~$ configure
[edit]
ubnt@ERL# set service dns forwarding options server=/google.com/8.8.8.8
[edit]
ubnt@ERL# set service dns forwarding options ipset=/google.com/CROSS_WALL

第一行是指定 google.com 下所有的域名都交给 8.8.8.8 这个 DNS Server 来解析,第二行是指定所有 google.com 域名下解析出来的 IP 都扔到名为 CROSS_WALL 的这个 ipset 里(当然 ipset 需要事先创建好)

到 8.8.8.8/32 的路由可以通过之前建立的 OpenVPN tunnel 出去,直接添加到路由表。这样防止解析出来的域名受到污染。随后在 firewall rule 里让所有 destination addr 符合 CROSS_WALL 这个 ipset 的包都走特定的 tunnel 出去,这样就实现了智能路由,科学上网了。trace route 如下:

C:\Users\Xiaoding>tracert -d www.google.com

Tracing route to www.google.com [173.194.127.210]
over a maximum of 30 hops:

  1     6 ms     1 ms     5 ms  192.168.111.1
  2   281 ms   285 ms   286 ms  10.8.0.1
  3   276 ms   282 ms   271 ms  96.44.154.33
  4   267 ms   271 ms   275 ms  72.11.150.105
  5   283 ms   279 ms   277 ms  96.44.180.97
  6   280 ms   280 ms   277 ms  206.72.210.41
  7   290 ms   283 ms   284 ms  64.233.174.41
  8   291 ms   308 ms   290 ms  64.233.174.190
  9   400 ms   408 ms   393 ms  64.233.174.177
 10   403 ms   402 ms   422 ms  209.85.243.249
 11   437 ms   406 ms   410 ms  66.249.94.30
 12   407 ms   411 ms   413 ms  209.85.240.133
 13   426 ms   442 ms   442 ms  173.194.127.210

Trace complete.

 

“利用 Dnsmasq 的 ipset 实现智能路由、科学上网”的29个回复

    1. 嗯,可以发给你。 不过你得确认一下你用的是 EdgeRouter Lite 而且系统版本是 1.5.0,否则因为系统架构和依赖库的版本差异,编译好的文件可能没法运行。

      1. 编译好的文件我也想要一份,请发邮箱谢谢!另外编译能不能写一个详细教程,实在是痛苦到死

  1. 请教这一步具体怎么做?

    这样防止解析出来的域名受到污染。随后在 firewall rule 里让所有 destination addr 符合 CROSS_WALL 这个 ipset 的包都走特定的 tunnel 出去

  2. 博主您好,能否编译一份满足需求的 1.7.0系统适用的dnsmasq-2.75呢,能详细说下怎么替换原有的dnsmasq吗?手头没有交叉编译环境。多谢了!
    另外,有兴趣将openconnect client移植过来么,感觉这个比l2tp/pptp更健壮点。目前能找到的是针对1.7.0以前的系统,还没尝试过。

    1. 之前换了SSD,我的编译环境也没了。可以参考之前评论里的链接建立交叉编译环境。替换的话直接用 cp 复制到 /usr/sbin 里就可以。
      openconnect 这货需要 gnutls 等等一些依赖,搞起来比较麻烦。等 EdgeOS 里的 strongswan 更新到 5.0+ 以后,直接上 IKEv2 吧。

      1. 多谢!
        一个是iptables的自定义规则有哪些? 怎么实现启动加载的?
        IPset现在我已经可以正常工作了, 但是重启以后就全灭了, 包括iptables加上的规则
        因为是用的SS-redir作为下一跳, 所以iptables不能加载比较郁闷, 不想每次都自己写一边啊
        我加了一个iptables-persistent 然而service无法自启动….rc.local写了service start也没用….郁闷..

          1. 自带的居然可以识别Ipset的标记吗?
            求指导…如果能用自带的FW的话倒是不用担心不能加载规则了..

          2. 可以的。在 firewall 这个配置里,可以设置匹配 ipset 的地址标记。比如

            set firewall modify MY_MODIFY rule 10 destination address-group GROUP_NAME

            就设置了一条匹配 GROUP_NAME 这个 ipset 的规则,规则的具体内容还需要配置,这个可以参考 Vyatta 系统的配置手册。或者你去 UBNT 的社区里看帮助,写的例子比较多很好找。

  3. 请教一下,我现在的固件1.8.0的erl,能使用你这个包吗,然后这个包该怎么写到系统里面去啊,请原谅我是个小白,刚接触这些!!!

    1. 应该可以用,如果不行你可以看看hi-pda论坛,上面有人发过更新版本的。

      具体你直接用scp把文件上传到路由器上,然后用mv直接覆盖原有的dnsmasq即可。

      1. 非常感谢楼主的回复,用你的2.71的包可用正常使用,现在我有点不明白怎么建立这个ipset呢,然后它的位置放在哪里?

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注