Lan Tian @ Blog

pfSense 配置 IPv6 多 WAN 自动切换

就在几天前,HE.NET Tunnelbroker 的法国服务器出了一次故障。因为我在配置 Kimsufi 服务器时,将 Kimsufi 原生的 IPv6 分给了 ESXi 单独使用(见这篇文章),pfSense 只具有原生 IPv4 并通过 Tunnelbroker 获取 IPv6 地址,所以这次服务器上的所有虚拟机都失去了 IPv6 连接。更严重的是,由于我在服务器上也参照这篇文章搭了个 NAT64 服务,为了优先使用 IPv6,我设置了 pfSense 的 DNS 解析优先使用 Google DNS 的 NAT64 解析服务器,就是 2001:4860:4860::64 和 2001:4860:4860::6464 这两个,只在这两个 DNS 全部失效后才去使用 IPv4 解析。由于 IPv6 不通了,而 pfSense DNS 服务器的超时又很长,内部的 DNS 解析几乎全部失败。

为了防止 IPv6 出问题后再次引起连锁反应,我准备使用多个 Tunnelbroker 互相作为备份,并配置 pfSense 的 Multi-WAN Failover 功能,在一个 Tunnelbroker 断线后立即切换到其它 Tunnelbroker,保证 IPv6 对外连接不中断。

设置额外的 Tunnelbroker

目前还在运行的 Tunnelbroker 列表可以直接查看 Wikipedia 页面,List of IPv6 tunnel brokers。其中我申请成功的是 HE.NET,IP4Market 和 NetAssist,其中 NetAssist 的服务器之前工作正常,但现在常年不通。

IP4Market 是一个俄罗斯网站,网页也是俄文的,但是通过 Google 翻译可以毫无障碍地完成申请。

注册完成后就可以获得服务器和客户端的 IPv4、IPv6 地址等信息:(下图 IP 地址被截断)

插图

接下来就用这些信息在 pfSense 中创建隧道。在 Interface / Assignments / GIFs 中添加一条 GIF 隧道:(IP 依然被截断)

插图

然后给这条隧道创建一个 Interface。在 Interface / Assignments 界面中,添加刚刚创建的这条隧道,并进入这个 Interface 的设置界面,启用它:

插图

进入 Status / Gateways 界面确认隧道对端可以 ping 通就完成了。

设置多 WAN 自动切换

接下来就要设置在一个隧道断线时自动切换的功能了。在 pfSense 的 System / Routing 界面中可以看到 Gateway Groups 选项,它可以将多个网关(包括隧道的对端)作为一个整体来使用,并实现负载均衡、断线切换等功能。

在 System / Routing / Gateway Groups 中添加一个网关组,并将几个 Tunnel 的网关按优先级从高到低设置成 Tier 1,Tier 2 等等,并将 Trigger Level(切换条件)设置成 Member Down(成员离线):

插图

但是此时如果你将默认网关设置成这个 Gateway Group,你会发现当你的主要网关掉线后,尽管 Gateway Group 已经作出切换,网内的其它机器还是无法访问 IPv6。这是因为 LAN 中每台机器的 IPv6 地址一般而言是从主要网关(我的是 HE.NET)的地址池分配的,而其它的 Tunnelbroker(例如 IP4Market)不认识这个 IPv6 地址,自然不会让数据包通过。即使数据包通过了,远程服务器返回数据时也会发回到主要网关(我的是 HE.NET)的地址上,但此时这个网关已经离线,也无法将数据转发回来。

解决方法是用 pfSense 的 NPt(Network Prefix Translation,网络前缀转换)功能。这个功能可以将一个 IPv6 子网的地址 1:1 映射到另一个子网,在此处就是将 HE.NET 的地址映射到 IP4Market 的地址,让它认出这些地址并且放行。

进入 Firewall / NAT / NPt,添加一个条目,将 LAN 上的地址映射到 IP4Market 提供的地址池:

插图

之后 LAN 上的机器也就可以通过 IP4Market 的 Tunnelbroker 上网了。

使用 ZeroTier One 建立自己的 IPv6 隧道

前言

天朝绝大多数 ISP 均不为用户提供 IPv6 地址,除了教育网。但是教育网的 IPv6 很不稳定(可能和我的学校有关),而且一旦离开学校就没有 IPv6 了,很不爽。

有一种方法是使用 HE.NET 的隧道服务。在 SixXS 关闭之后,他们是目前仅存的最大的 IPv6 隧道提供者,而且他们的服务完全免费。但是他们的服务并不适用于天朝的家庭网络环境,因为家庭网络普遍是动态 IP,并且部分运营商为了节省成本已经开始使用大内网,用户无法获取独立 IP,在同一内网就会产生冲突。

好消息是,我有好几台 VPS,均由 VPS 提供商或者 HE.NET 的隧道服务提供了 IPv6。这意味着我可以使用 VPN 方案。但是 Open^_^VPN 早就无法正常跨境使用了,其它 VPN 方案或多或少都有一些问题。

之前我拿来 Docker 组网的 ZeroTier One VPN 倒是能很好的解决这个问题。有中心管理面板,配置简单;跨境使用目前没有问题;官方甚至提供了详细的教程。

准备

ZeroTier One 的注册安装和加入网络,请参见这篇文章。本文假定 VPS 已经有了一个 IPv6 地址块,并且已经和你需要 IPv6 的设备加入了同一个网络,已经能够互通。

如果你之前有像这篇文章一样开启了整个地址块,必须把它先关闭。你应该在 /etc/rc.local 之类的地方添加过这样的指令:

ip -6 route add local 2333:3333:3333:3333:3333::/80 dev lo

把它删了并重启 VPS。

设置转发

本文假定 IPv6 地址池是 2333:3333:3333:3333:3333::/80 ,并且 ZeroTier One 生成的虚拟网卡是 zt0,请注意替换。

登陆你的 VPS,向 /etc/sysctl.conf 添加如下指令:

net.ipv6.conf.default.forwarding=1
net.ipv6.conf.all.forwarding=1
net.ipv6.conf.all.proxy_ndp=1
net.ipv6.conf.all.accept_ra=2

保存后运行 sysctl -p 生效。

如果你有配置 iptables 防火墙,向配置中添加如下两行,并保存生效:

ip6tables -A FORWARD -i zt0 -s 2333:3333:3333:3333:3333::/80 -j ACCEPT
ip6tables -A FORWARD -i henet -d 2333:3333:3333:3333:3333::/80 -j ACCEPT

ZeroTier 管理页面设置

登陆 ZeroTier 管理界面,点击进入你已经创建好的网络,找到 IPv6 Auto Assign(应该在屏幕右下角):

插图

勾上 Auto Assign from Range(从地址池中自动分配)选项。

插图

它会要求输入你的地址池的开始与结束地址。对于我们用做演示的 2333:3333:3333:3333:3333::/80,其配置如图所示:

插图

你会发现 ZeroTier One 还没有给网络内的设备在这个地址池内分配 IPv6 地址,因为你还没有设置这个地址池的路由。看到屏幕右上角的 Managed Routes 选项,在第一个框输入要用的地址池 2333:3333:3333:3333:3333::/80,第二个框留空,如图。

插图

然后,我们要告诉设备,将 ZeroTier 的虚拟网卡默认用于 IPv6 连接。继续添加,在第一个框输入 ::0/0,第二个输入你的 VPS 的内网 IPv6 地址,就是 ZeroTier RFC4193 分配的地址,类似如图:(记得替换地址)

插图

保存。这时页面下方应该已经显示你的设备拥有了一个公网 IPv6 地址。

ZeroTier 客户端设置

但是当你到你的电脑上查看,会发现看不到分配的公网 IPv6。这是由于 ZeroTier 的安全策略所致。为了防止用户不知情地将所有流量转发到一个 ZeroTier 网络上(即不知情地将 ZeroTier 作为全局 VPN 使用),并允许该网络的管理员为所欲为,你必须手动在每台设备上允许该功能。

在 Windows 和 Mac 设备上,通过 GUI 界面就能打开。打开 Network Details 界面:

插图

找到你的网络,打开 Allow Global 和 Allow Default 选项即可,立即生效。

插图

在 Linux 设备上,假设你的网络 ID 是 2333333333333333,运行如下命令:

zerotier-cli set 2333333333333333 allowGlobal=true
zerotier-cli set 2333333333333333 allowDefault=true

立即生效。如此配置后,你就建好了自己的、在动态 IP 下也可方便使用的 IPv6 隧道了。

使用 ZeroTier One 在多台 Docker 服务器间建立双栈互通网络

前言

多台 Docker 服务器上的容器互通是一个不好解决的问题。如果自建一个 Overlay 网络,就需要在一台服务器上建立 etcd 之类的服务。但如果 etcd 所在的服务器挂了,整个网络就 GG 了。我用的便宜 VPS 有偶尔网络中断的情况,我自己搞崩也服务器是常有的事,所以我不能采取这种方式。

Docker 也有其它的基于 Overlay 的商业化组网方案,例如 Weave,但是对于个人用户来说这些方案的价格太高了(我只是搞来玩玩),所以也不考虑。

在这些网络结构上,etcd 或者 Weave 之类的中心服务器记录了每个容器所在的服务器和内部 IP,所以在任何容器上都可以直接 DNS 解析到其它容器。也就是说,假如我设置了 lantian-nginx 和 lantian-phpfpm 两个容器,在 nginx 的配置文件里我可以直接把 php-fpm 的地址填成 lantian-phpfpm:[端口号],方便配置。

但我好像可以放弃这个功能啊?我的容器数量并不多,而且只有几个 MariaDB 需要跨服务器连接,做数据库主从备份,手动指定一下 IP 并不麻烦。

那么我就可以直接使用传统的 VPN 方案来做互通了。

问题又来了:由于自己的服务器不稳定,我不希望某台服务器挂掉导致网络互通挂掉,所以 Open^_^VPN 之类需要架设中心 VPN 服务器的也算了。Tinc 这类 P2P VPN 符合我的要求,但是我的服务器常有增减,难道我每次都要一台台上去改配置吗?

有中央管理面板的 P2P VPN,我或许可以用 LogMeIn Hamachi。这款免费软件通过和 LogMeIn 公司的中心服务器连接,获取网络内其它计算机的实际 IP,并分别建立 P2P 连接。我的服务器上倒是有 Hamachi,但是它只给每台计算机一个 IPv4 和一个 IPv6,对于 Docker 组网来说不够用啊。而且它每个网络只能让 5 台计算机互联,否则就要加钱。

到现在为止,我的需求如下:

  1. 任何一台服务器 GG 不能影响其它服务器
  2. 需要一个统一的管理面板可以快速增减服务器
  3. 不需要 Docker 的 DNS 解析之类功能
  4. 每台服务器可以获得多于一个的 IPv4 和 IPv6(可以是内网 ULA 网段),最好有一个内网网段

经过一番搜索,我选定了 ZeroTier One 这款软件。它类似于 Hamachi,但是相比之下它有如下优点:

  1. 我可以指定哪些 IPv4 网段被路由到 ZeroTier One,并且可以任意设置分配地址池。
  2. 我可以让每台计算机分配到一个 IPv6 ULA 下的 /80 网段,足够 Docker 使用。
  3. 每个用户可以免费添加 100 台计算机。

第一点尤其重要,例如,我可以设置给每台计算机在 172.27.0.0/16 下自动分配 IP,但是我又可以统一指定把 172.28.0.0/24 路由到某台 Docker 服务器,172.28.1.0/24 路由到另一台,以此类推。

安装与配置

ZeroTier One 官方提供一键安装脚本。在你的服务器上运行如下命令即可。

curl -s 'https://pgp.mit.edu/pks/lookup?op=get&search=0x1657198823E52A61' | gpg --import && \ if z=$(curl -s 'https://install.zerotier.com/' | gpg); then echo "$z" | sudo bash; fi

然后在 ZeroTier One 官方注册一个账号。这里需要你的手机号。我测试中国电信手机号可以收到验证短信,但是隔了 7 个小时……最后我用的是 Google Voice 的号码。

注册登录后你就能看到如下界面:

插图

点击上方的 Network(网络),再点击 Create New Network(创建新网络),你会看到列表上多了一个网络。

插图

如图,第二个是我已有的网络,第一个是新创建的。点击进去。

插图

左上角是 Network ID,稍后你要输入到你的 ZeroTier 客户端去。

Short Name 是网络名称,你可以自定义以使得它更好辨别。

右上角 Managed Routes 是路由表设置,稍后再改。

IPv4 Auto-Assign 是 IPv4 地址的自动分配,我们要把它打开。

插图

打开后,在列出的网段中选一个看得顺眼的。这个网段不能与你服务器实际在用的网段有重合。例如,如果有一台 NAT VPS,其 IPv4 所在网段是 172.17.0.0/16,那么你就不能选它,否则它有可能会断网。选择后,会自动给你添加好路由表设置,如图:

插图

IPv6 Auto-Assign 是 IPv6 的自动分配,下有两个选项。

插图

RFC4193 选项会为你随机生成一个 ULA 网段(在 fd00::/8 下),每台服务器获得一个 IPv6(/128);6PLANE 在另一个 ULA 网段(fc00::/8 下),每台服务器获得一个 /80 段。为了 Docker 组网,我们需要的就是 6PLANE 网段。

接下来,我们把服务器加进这个网络。在服务器上输入命令:

zerotier-cli join [网络ID]

然后在设置页面的下方,勾上对应服务器的 Auth 选项:

插图

页面上会显示服务器对应的 IPv4 和 IPv6,各台服务器也能互相 ping 通了。

配置 Docker - 原生 Docker

在这个例子中,假定这台 Docker 服务器分配到了 10.147.17.233 和 fc23:3333:3333:3333:3333::1/80,我们希望添加一个 172.28.233.x/24 供它使用,系统环境是 Debian 8。

我们需要指定 Docker 使用一些启动命令参数。在 Debian 8 这类 systemd 发行版上,我们需要修改一下 systemd 的配置。输入以下命令:

cd /etc/systemd/system
mkdir docker.service.d
cd docker.service.d
nano docker.conf

向 docker.conf 输入如下内容:

[Service]
EnvironmentFile=-/etc/default/docker
ExecStart=
ExecStart=/usr/bin/dockerd -H fd:// $DOCKER_OPTS

Ctrl+X,Y,回车保存退出,再运行:

systemctl daemon-reload
cd /etc/default
nano docker

经过如上修改,此处显示的 DOCKER_OPTS 环境变量就能生效了。将对应的这一行修改成:

DOCKER_OPTS="--fixed-cidr=172.28.233.0/24 --ipv6 --fixed-cidr-v6=fc23:3333:3333:3333:3333::/80"

重启 Docker:

service docker restart

然后你的 Docker 容器就有了在这两个网段上的 IP。

问题又来了,由于容器获得的是 ULA 网段,无法访问 IPv6 公网,怎么办?我们需要借助 docker-ipv6nat。这个软件(容器)可以根据你的容器设置自动配置 IPv6 NAT,就像 Docker 在 IPv4 上做的一样。

等等,为什么要用 IPv6 NAT?我认为它的优点如下:

  1. 某些主机商只提供一个 IPv6 地址
  2. 更方便的防火墙配置(外网无法直接访问到容器)
  3. 它在 ULA 网段上运行,刚好符合这次的需求

启动这个容器:

docker run -d --restart=always -v /var/run/docker.sock:/var/run/docker.sock:ro --privileged --net=host robbertkl/ipv6nat

你可能需要重新启动一下其它容器以使配置生效。这样你的容器就能访问 IPv6 公网了。

如果你愿意,可以在 DOCKER_OPTS 里加一句 --userland-proxy=false,禁用 Docker 的应用层代理,可以节省内存。

配置 Docker - Compose

如果你用 Docker-Compose,那么事情就方便了许多,不需要修改 systemd 配置了。将你的 docker-compose.yml 里修改成如下内容:

version: "2.1"
services:
  docker-ipv6nat:
    image: robbertkl/ipv6nat
    container_name: docker-ipv6nat
    restart: always
    privileged: true
    network_mode: host
    volumes:
      - "/var/run/docker.sock:/var/run/docker.sock:ro"

  你原有的容器:
    [...]
    depends_on:
      - docker-ipv6nat

  [你原有的容器们...]

networks:
  default:
    driver: bridge
    enable_ipv6: true
    ipam:
      driver: default
      config:
      - subnet: 172.28.233.0/24
        gateway: 172.28.233.1
      - subnet: fc23:3333:3333:3333:3333::/80
        gateway: fc23:3333:3333:3333:3333::1

注意要给原有的每个容器添加依赖 docker-ipv6nat。然后重新 docker-compose up -d 即可。

配置系统转发

在 /etc/sysctl.conf 里添加以下内容:

net.ipv4.ip_forward = 1
net.ipv6.conf.default.forwarding=1
net.ipv6.conf.all.forwarding=1
net.ipv6.conf.all.proxy_ndp=1

执行 sysctl -p 开启转发。如果你有防火墙,记得给相应的网段放行。

配置 ZeroTier 路由表

在右上角 Managed Routes 里添加“172.28.233.1/24,10.147.17.233”,代表把 172.28.233.1/24 网段的请求全部交由 10.147.17.233 处理。

插图

然后,你在其它服务器就能 ping 通 10.147.17.233 上的 Docker 容器了。在其它服务器上如法炮制(记得 IP 段不能重合),就能在所有 Docker 服务器和容器之间建成一张双栈局域网了。

OpenVZ 配置 Hurricane Electric IPv6 隧道,开启整个地址池并与原生 IPv6 共同使用

AlphaRacks 是一个物美价廉的主机商,1CPU、512M内存、10G硬盘的 VPS 只要 9.9 美元/年。但是这家主机商在 IPv6 地址上比较抠,需要用户说明用 IPv6 的理由,据说最多给20个?但是不一定给满20个,比如我告诉主机商要用 IPv6 地址给仅支持 IPv6 的用户提供服务,主机商回复:

我们已经为你的 VPS 增加了1个IPv6地址。

一个 IPv6 自然是不够我折腾的。好在美国 Hurricane Electric 公司提供 IPv6 隧道服务,为每个用户提供5个隧道,每个隧道有1个/64地址池,并可以一键开通1个/48地址池。

如此良心的服务,要在 OpenVZ 的 VPS 上使用却还要费一番周折。因为 OpenVZ 的内核版本往往是2.6.32,2.6.32的老内核不原生支持隧道功能,而支持的新版3.10的内核刚刚发布,很多主机商没有更新。

1. 在 OpenVZ 上开启 HE 隧道

我们需要借助一个第三方小程序,它可以把 Hurricane Electric 的隧道转换为 Tun/Tap 的隧道(相当于 Windows 下 OpenVPN 的那个网络适配器)并且在服务器上配置好。下载安装教程如下:


apt-get install iproute gcc
wget http://tb-tun.googlecode.com/files/tb-tun_r18.tar.gz
tar -xf tb-tun_r18.tar.gz
gcc tb_userspace.c -l pthread -o tb_userspace
mv tb_userspace /usr/bin/tb_userspace

然后创建/etc/init.d/ipv6tb,输入下面这个从https://www.cybermilitia.net/2013/07/22/ipv6-tunnel-on-openvz/弄来的启动代码:

(注意替换其中的 IP 地址)


touch /etc/init.d/ipv6tb
chmod +x /etc/init.d/ipv6tb
nano /etc/init.d/ipv6tb


#!/bin/sh
case "$1" in
  start)
    echo "Starting ipv6tb"
      setsid /usr/bin/tb_userspace tb  <你 VPS 的 IPv4 地址> sit > /dev/null 2>&1 &
      sleep 1s
      ifconfig tb up
      ifconfig tb inet6 add <你的 HE 隧道的客户端 IPv6 地址>/128
      ifconfig tb inet6 add <分配给你的/64 地址池>::1/64
      ifconfig tb inet6 add <分配给你的/48 地址池,没有就把这行删掉>::1/48
      ifconfig tb mtu 1480
      route -A inet6 add ::/0 dev tb
      route -A inet6 del ::/0 dev venet0
    ;;
  stop)
    echo "Stopping ipv6tb"
      ifconfig tb down
      route -A inet6 del ::/0 dev tb
      killall tb_userspace
    ;;
  *)
    echo "Usage: /etc/init.d/ipv6tb {start|stop}"
    exit 1
    ;;
esac
exit 0

然后输入:

/etc/init.d/ipv6tb start

隧道就起来了。但是这时你会发现两个问题:

1. 虽然你有一整个/64(可能还有个/48),但是你只能使用末尾是::1的地址;

2. VPS 原生的 IPv6 不通了,所有流量走了隧道。

接下来我们就要一步步解决这个问题。

2. 开启整个地址池

Linux 内核支持一个叫 AnyIP 的功能。这个功能允许你将一整个地址池快速地设置到一个网络接口上,这样就不需要你手动给网络接口把地址池里的 IP 挂上去,或者写个脚本帮你挂。

顺带提一句,一个/64地址池有 18,446,744,073,709,551,616 个 IP。

那么如何开启这个功能呢?输入以下代码即可:

ip -6 route add local <分配给你的/64 地址池>/64 dev lo
ip -6 route add local <分配给你的/48 地址池,没有就把这行删掉>/48 dev lo

输完回车,你的地址池里其它的 IP 就全部可用了。

3. 同时使用原生 IPv6 和隧道

当你的 VPS 上同时有多种 IPv6 接入方式时,你会发现你同时只能使用一个。因为 Linux 在非默认网络接口上接收到数据包后,会从默认的那个接口回复,而不是原路返回。

幸亏 Linux 提供策略路由功能,也就是根据一定条件,让各个数据包走到它们该走的接口上。

如何配置?按照步骤操作即可:

1. 输入如下命令,设置路由表并关闭之前建立的隧道:

echo 200 ipv6tb >> /etc/iproute2/rt_tables
/etc/init.d/ipv6tb stop

2. 修改你前面创建的 /etc/init.d/ipv6tb,删除所有内容,用如下内容代替:

(下面的代码修改自http://itkia.com/ipv6-policy-routing-linux-gotchas/


#! /bin/sh
touch /var/lock/ipv6tb
case "$1" in
    start)
        setsid /usr/bin/tb_userspace tb  <你 VPS 的 IPv4 地址> sit > /dev/null 2>&1 &
        sleep 1s
        # bring up the tunnel interface & set mtu
        ifconfig tb up
        ifconfig tb mtu 1480
        # hack: show ip in ifconfig
        ifconfig tb inet6 add <你的 HE 隧道的客户端 IPv6 地址>/128
        ifconfig tb inet6 add <分配给你的/64 地址池>::1/64
        ifconfig tb inet6 add <分配给你的/48 地址池,没有就把这行删掉>::1/48
        # make use of the whole ipv6 block
        ip -6 route add local <你的 VPS 的原生 IPv6 地址>/128 dev lo
        ip -6 route add local <你的 HE 隧道的客户端 IPv6 地址>/128 dev lo
        ip -6 route add local <分配给你的/64 地址池>/64 dev lo
        ip -6 route add local <分配给你的/48 地址池,没有就把这行删掉>/48 dev lo
        # nullroute native ipv6 to prevent sending via wrong interface
        ip -6 route add unreachable <你的 VPS 的原生 IPv6 地址>/128
        # nullroute ipv6 tunnel to prevent sending via wrong interface
        ip -6 route add unreachable <你的 HE 隧道的客户端 IPv6 地址>/128
        ip -6 route add unreachable <分配给你的/64 地址池>/64
        ip -6 route add unreachable <分配给你的/48 地址池,没有就把这行删掉>/48
        # flush route table & route the interfaces
        ip -6 route flush table ipv6tb
        ip -6 route add 2000::/3 dev venet0 src <你的 VPS 的原生 IPv6 地址>
        ip -6 route add 2000::/3 dev tb src <你的 HE 隧道的客户端 IPv6 地址> table ipv6tb
        # flush rule table
        ip -6 rule flush
        # restore routing in ipv6 tunnel address block
        ip -6 rule add priority 200 to <你的 HE 隧道的客户端 IPv6 地址>/128 table main
        ip -6 rule add priority 201 to <分配给你的/64 地址池>/64 table main
        ip -6 rule add priority 202 to <分配给你的/48 地址池,没有就把这行删掉>/48 table main
        # restore routing in native ipv6 address block
        ip -6 rule add priority 210 to <你的 VPS 的原生 IPv6 地址>/128 table main
        # restore routing to reserved ipv6 range
        ip -6 rule add priority 1000 to 2001:db8::/32 table main
        # route packets from tunnel back to the tunnel
        ip -6 rule add priority 30000 from <你的 HE 隧道的客户端 IPv6 地址>/128 to 2000::/3 table ipv6tb
        ip -6 rule add priority 30001 from <分配给你的/64 地址池>/64 to 2000::/3 table ipv6tb
        ip -6 rule add priority 30002 from <分配给你的/48 地址池,没有就把这行删掉>/48 to 2000::/3 table ipv6tb
        # restore ipv6 main route & flush cache
        ip -6 rule add priority 32766 from all table main
        ip -6 route flush cache
    ;;
    stop)
        ifconfig tb down
        # restore rule table
        ip -6 rule flush
        ip -6 rule add priority 32766 from all table main
        pkill -9 tb_userspace
    ;;
    *)
        echo "Usage: /etc/init.d/ipv6tb {start|stop}"
        exit 1
        ;;
esac
exit 0

3. 输入如下命令重新开启隧道:

/etc/init.d/ipv6tb start

4. (可选)开机自动启动:打开 /etc/rc.local,在exit 0之前建立一行,输入:

/etc/init.d/ipv6tb start

当你改完后,文件应该是这样的:

插图

保存后,隧道就能自动启动了。

这样设置出来的 IPv6 隧道,可以与原生 IPv6 和平共处,同时系统发起的网络操作(比如软件更新)都会经过原生 IPv6 而不走隧道,大大提高了稳定性与速度。

gogoCLIENT DNS解析问题解决

这几天Google服务不怎么正常,所以我决定使用IPv6隧道来连接Google,以便获得较好的访问速度。

按照我去年10月写的文章《Windows 8.1 下 gogoCLIENT 的安装使用与Bug修复》,我在我的电脑上设置好了隧道。但是此时我打开命令提示符Ping ipv6.google.com,系统竟然提示“Ping 请求找不到主机 ipv6.google.com”。

这样我相当于还是在通过IPv4连接谷歌服务,无法达到我想要的效果。一般这个时候我都会去Google,但是问题是Google连接时断时通……

很长时间过后,我终于找到了解决方案。

原因是微软在设计操作系统的时候,默认不会从IPv6隧道中查询DNS。解决方法如下:

1.开始-运行(或者Win+R),输入regedit回车。

插图

2.在左边窗口打开HKEY_LOCAL_MACHINE - SYSTEM - CurrentControlSet - services - Dnscache - Parameters。

插图

3.在右边窗口右键新建-DWORD值,名字为AddrConfigControl。

经过以上操作,无需重启计算机,你就可以正常解析IPv6地址了。

感谢 http://blog.ihipop.info/2012/01/2953.html 和 http://ipv6-or-no-ipv6.blogspot.sg/2009/02/teredo-ipv6-on-vista-no-aaaa-resolving.html 。

Windows 8.1 下 gogoCLIENT 的安装使用与Bug修复

半年前,当我还在用Ubuntu的时候,我插图

这个的解决方法倒也简单,右键选择安装程序,兼容性模式修改成Vista即可解决,主程序不会有任何异常。

插图

安装完成后,我启动了主程序,输入了上次我就使用的hg.tfn.net.tw,连接。10秒后,右下角弹出提示,连接成功。但是我到网络连接里一看,IPv6,没有网络访问权限!我打开详细信息一看:

插图

我只想说,默认网关到哪里去了。(其实DNS也是我手动设置的)

用百度搜了一通,无果。然后用谷歌改成英文搜“windows gogo6 default gateway”,结果真的出来了,是个Bug!

修改方法:

1.开始菜单(或者开始屏幕)找到记事本,右键管理员权限打开。

2.用记事本打开C:\Program Files\gogo6\gogoCLIENT\template\windows.cmd,做以下替换:

把所有的这句话:

netsh int ipv6 add route ::/0 "%TSP_TUNNEL_INTERFACE%" publish=yes %NETSH_PERS% > NUL

改成:

netsh int ipv6 add route ::/0 "%TSP_TUNNEL_INTERFACE%" nexthop=%TSP_SERVER_ADDRESS_IPV6%  publish=yes %NETSH_PERS% > NUL

保存。

3.打开GC,重新连接服务器。

这样,默认网关就设置成功了,IPv6也能连上Internet了。

IPv4 与 IPv6 的互通

IPv4 是目前支持最广泛的网络协议,网内计算机以IP地址标记,理论总共能放2^32台(IPv4:8个16进制位)网络设备,可惜现在已经用完了,真不知道各大ISP是怎样把有限的IP分给无限的计算机的。

IPv6 则要NB的多,每个地址有32个16进制位,也就是2^128台网络设备,在人类因为地球撑不住而挂掉之前,这些IP完全够用。这一协议被各大互联网公司推崇,包括Google,DNSPod,等等。但是目前天朝好像只有大学里用IPv6,普通百姓家只能用IPv4。

(吐槽:大学里也不完善,国外一般都是IPv4v6通吃,教育网内只有v6)

而现在IPv6资源也越来越多,所以在天朝ISP采取行动前,我们可以先通过软件辅助,让我们用上IPv6。