基于树莓派4B构建支持透明代理的辅助路由器
基础环境
- Raspberry Lite OS: 基于ARM V7,32位操作系统
- dnsmasq: 自建域名服务器 + DHCP服务器, 192.168.0.8
- hostapd: 提供AP服务器,SSID=xxx-PI, 192.168.11.x/24
- clash: 作为v2ray节点的客户端,自带Dashboard
主路由器: 192.168.0.1
从路由器:
- eth0: 192.168.0.8
- waln0:192.168.11.1
- DHCP Range: 192.168.11.100-150
- DHCP Default Gateway: 192.168.11.1
Clash:
- 7890: http/https代理端口
- 7891: socks5代理端口
- 7892: 流量重定向端口
- 9090: Dashboard端口
- 53: 内建DNS端口(UDP)
Clash控制面板:http://192.168.0.8:9090/ui
安装步骤
一、安装树莓派并启动
Raspbian是树莓派的官方操作系统,是官基于Debain的深度定制,软件升级策略偏保守,强调稳定第一。
桌面版下载链接:http://downloads.raspberrypi.org/raspbian_latest
Lite 版(无桌面)下载链接:https://downloads.raspberrypi.org/raspbian_lite_latest
树莓派4B的BCM2711芯片采用四核Cortex A72架构,28nm工艺,主频1.5GHz,GPU 500MHz,因此是armv7
的技术架构,32位操作系统。
虽然树莓派4B宣称已支持64位操作系统,但还在测试阶段;也可以采用Ubuntu、Centos等第三方系统,但软件依赖还是比较麻烦,因此本次安装采用的是Raspberry Lite OS,下载镜像文件是:2020-05-27-raspios-buster-lite-armhf.img
。
采用Etcher刻录CF卡,将写好的CF卡插入树莓派,连接有线网卡并加电后,就可以正常启动了。
为避免安全问题,Raspberry OS默认关闭了ssh登录。解决方法是:在烧录SD卡成功后,手工mount并在根目录下touch一个空文件,名称是ssh
树莓派首次启动时,默认采用DHCP方式获取IP地址,在接入路由器上找到相应IP地址,通过ssh远程登录。
默认帐号:Username: pi Password: raspberry
当然,如果连接了显示器和键盘,就不需要处理ssh登录的问题了。
二、设置树莓派的运行环境
设置网络参数,并重新启动
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20# 激活无线网卡
sudo rfkill unblock wlan
# 设置两张网卡的网络参数
sudo tee /etc/network/interfaces > /dev/null << EOF
auto lo
iface lo inet loopback
auto eth0
iface eth0 inet static
address 192.168.0.8
netmask 255.255.255.0
gateway 192.168.0.1
allow-hotplug wlan0
iface wlan0 inet static
address 192.168.11.1
netmask 255.255.255.0
EOF网络参数设置成功后,使用
sudo reboot
重启树莓派。
以ssh pi@192.168.0.8
从新的IP地址登录,并使用ip a
检查网络情况,如果获得以下输出就OK了!1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17pi@raspberrypi:~ $ ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP group default qlen 1000
link/ether dc:a6:32:ad:ad:78 brd ff:ff:ff:ff:ff:ff
inet 192.168.0.8/24 brd 192.168.0.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::dea6:32ff:fead:ad78/64 scope link
valid_lft forever preferred_lft forever
3: wlan0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 1500 qdisc pfifo_fast state DOWN group default qlen 1000
link/ether dc:a6:32:ad:ad:79 brd ff:ff:ff:ff:ff:ff
inet 192.168.11.1/24 brd 192.168.11.255 scope global wlan0
valid_lft forever preferred_lft forever设置软件源,并安装基础软件
1
2
3
4
5
6
7
8
9
10# 关闭默认源
sudo sed -i 's/^deb http/#deb http/g' /etc/apt/sources.list
# 设置Aliyun国内源
sudo sh -c 'echo "deb https://mirrors.aliyun.com/raspbian/raspbian/ buster main non-free contrib" >> /etc/apt/sources.list'
sudo sh -c 'echo "deb-src https://mirrors.aliyun.com/raspbian/raspbian/ buster main non-free contrib" >> /etc/apt/sources.list'
# 更新源仓库,并安装基础软件
sudo apt update
sudo apt install net-tools dnsutils ntp hostapd git iptables-persistent netfilter-persistent dnsmasq -y- 基础软件安装都在此步骤完成!!! 因为后续启动Clash内建DNS,将域名解析到伪地址,会影响本机Terminal的外网访问
关闭不需要的Systemd自启动服务
1
2
3
4
5
6# 关闭avahi自动网络发现功能,类似Bonjure
sudo systemctl disable avahi-daemon
sudo systemctl stop avahi-daemon
# 暂时关闭dnsmasq服务,避免影响Clash安装
sudo systemctl stop dnsmasq- dsnmasq安装时会自动修改/etc/resolv.conf,将默认DNS修改为127.0.0.1
三、安装并设置Clash
Clash的Github地址是https://github.com/Dreamacro/clash, 技术文档位于https://lancellc.gitbook.io/clash
基于众所周知的原因,建议采用手工下载并通过sftp传入树莓派,主要包括以下文件:
文件名 | 说明 |
---|---|
clash-linux-armv7-v1.0.0.gz | clash的可执行文件 |
Country.mmdb | 各个国家的IP地址数据文件, clash启动时会自动下载 |
yacd-gh-pages.zip | 第三方控制面板插件,比官方的好看一些 |
config.yaml | VPS客户端的配置文件 |
传入文件默认存放在
/home/pi/
,解压并手工安装1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20# 建立clash的home目录
cd $HOME
mkdir .config
mkdir .config/clash
# 配置/usr/bin/clash,并添加绑定低位端口的权限
sudo gunzip clash-linux-armv7-v1.0.0.gz
sudo mv clash-linux-armv7-v1.0.0 /usr/bin/clash
sudo chmod a+x /usr/bin/clash
sudo setcap cap_net_bind_service=+ep /usr/bin/clash
ls -l /usr/bin/clash
# 安装配置文件
unzip yacd-gh-pages.zip
mv yacd-gh-pages /home/pi/.config/clash/yacd-dashboard
mv Country.mmdb /home/pi/.config/clash/
mv config.yaml /home/pi/.config/clash/
ls -l /home/pi/.config/clash/输入
sudo clash -d /home/pi/.config/clash
,启动clash正常情况下屏幕将显示如下内容,就表示启动成功并打开了相应的侦听端口
1
2
3
4
5
6
7
8pi@raspberrypi:~/.config/clash $ sudo clash -d /home/pi/.config/clash
INFO[0000] Start initial compatible provider auto
INFO[0000] Start initial compatible provider Proxy
INFO[0000] HTTP proxy listening at: :7890
INFO[0000] SOCKS proxy listening at: :7891
INFO[0000] DNS server listening at: 0.0.0.0:53
INFO[0000] Redir proxy listening at: :7892
INFO[0000] RESTful API listening at: 0.0.0.0:9090也可以自行检查端口占用情况
1
2
3
4
5
6
7
8pi@raspberrypi:~ $ sudo netstat -tunpl |grep clash
tcp6 0 0 :::7890 :::* LISTEN 3001/clash
tcp6 0 0 :::7891 :::* LISTEN 3001/clash
tcp6 0 0 :::7892 :::* LISTEN 3001/clash
tcp6 0 0 :::9090 :::* LISTEN 3001/clash
udp6 0 0 :::53 :::* 3001/clash
udp6 0 0 :::7891 :::* 3001/clash
udp6 0 0 :::7892 :::* 3001/clashvmess等协议对Server和CLient的时钟同步有严格要求,如果没有NTP服务,可能导致无法连通
输入
curl -x http://localhost:7890 google.com
, 检查KX上网的效果1
2
3
4
5
6
7pi@raspberrypi:~ $ curl -x http://localhost:7890 google.com
<HTML><HEAD><meta http-equiv="content-type" content="text/html;charset=utf-8">
<TITLE>301 Moved</TITLE></HEAD><BODY>
<H1>301 Moved</H1>
The document has moved
<A HREF="http://www.google.com/">here</A>.
</BODY></HTML>浏览器输入地址
http://192.168.0.8:9090/ui
,打开控制面板

四、配置并启动AP热点
输入
sudo vi /etc/dnsmasq.conf
, 也可以根据本次环境自行修改网络参数注意:dnsmasq仅作为DHCP服务器,不启动DNS,因为Clash有自建的DNS
1
2
3
4
5
6
7
8
9
10
11
12
13# DHCP
interface=wlan0
listen-address=192.168.11.1
dhcp-range=192.168.11.100, 192.168.11.150, 12h
# set default route
dhcp-option=3,192.168.11.1
# set default nameserver
dhcp-option=6, 192.168.11.1
# without DNS
port=0输入
sudo vi /etc/default/hostapd
, 设置hostapd启动配置文件。
将其中包含#DAEMON_CONF=""
的行,修改为1
DAEMON_CONF="/etc/hostapd/hostapd.conf"
输入
sudo vi /etc/hostapd/hostapd.conf
, 根据本地网络环境自行修改配置AP接入参数1
2
3
4
5
6
7
8
9
10
11
12
13
14
15interface=wlan0
driver=nl80211
hw_mode=g
ssid=< Your SSID >
channel=6
wpa=2
wpa_passphrase=< Your Passeword >
wpa_key_mgmt=WPA-PSK
wpa_pairwise=CCMP
rsn_pairwise=CCMP
auth_algs=3
wmm_enabled=1
max_num_sta=10
logger_stdout=-1
logger_stdout_level=2注意:将
< Your SSID >
和< Your Passeword >
修改为用户定义数据通过systemd,启动AP热点
1
2
3
4
5
6# hostapd启动解锁
sudo systemctl unmask hostapd
# 重启服务
sudo systemctl restart hostapd
sudo systemctl restart dnsmasq启动完成后,另外找一台PC设备,寻找SSID并连接登录,此时应该分配一个
198.168.11.x
的地址。
检查该PC的网络参数,默认路由是192.168.11.1
,DNS设置为198.19.0.1
,但是并不能上网(DNS是个fake-ip的假地址),因为下面还有一个关键步骤。
五、为从路由器设置透明代理
为AP热点设置动态NAT转发,只出不进
1
2
3
4# 为 wlan0--->eth0 设置动态NAT出口转换
sudo iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
sudo iptables -A FORWARD -i eth0 -o wlan0 -m state --state RELATED,ESTABLISHED -j ACCEPT
sudo iptables -A FORWARD -i wlan0 -o eth0 -j ACCEPT为Clash设置全量数据转发
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26# 新建两条链,clash用于数据访问,clash_dns用于内建DNS
sudo iptables -t nat -N clash
sudo iptables -t nat -N clash_dns
# 为内建DNS设置NAT转换,从198.18.0.1--->198.19.x.x,同时支持UDP和TCP,但当前版本实际只使用UDP
# 重要:192.168.0.8是你的Clash出口地址,应根据网络环境自行修改!!!
sudo iptables -t nat -A PREROUTING -p tcp --dport 53 -d 198.19.0.0/24 -j clash_dns
sudo iptables -t nat -A PREROUTING -p udp --dport 53 -d 198.19.0.0/24 -j clash_dns
sudo iptables -t nat -A clash_dns -p udp --dport 53 -d 198.19.0.0/24 -j DNAT --to-destination 192.168.0.8:53
sudo iptables -t nat -A clash_dns -p tcp --dport 53 -d 198.19.0.0/24 -j DNAT --to-destination 192.168.0.8:53
# 为Clash数据访问建立NAT转换
sudo iptables -t nat -A PREROUTING -p tcp -j clash
# 为本机网段、私有网段、保留网段等提供直通车
sudo iptables -t nat -A clash -d 0.0.0.0/8 -j RETURN
sudo iptables -t nat -A clash -d 10.0.0.0/8 -j RETURN
sudo iptables -t nat -A clash -d 127.0.0.0/8 -j RETURN
sudo iptables -t nat -A clash -d 169.254.0.0/16 -j RETURN
sudo iptables -t nat -A clash -d 172.16.0.0/12 -j RETURN
sudo iptables -t nat -A clash -d 192.168.0.0/16 -j RETURN
sudo iptables -t nat -A clash -d 224.0.0.0/4 -j RETURN
sudo iptables -t nat -A clash -d 240.0.0.0/4 -j RETURN
# 上述条件之外的数据流量,一律转发给7892端口,实现免代理的透明网关
sudo iptables -t nat -A clash -p tcp -j REDIRECT --to-ports 7892设置iptables路由表的持久化
执行完上面的 iptables 命令之后,就完成了旁路由的路由功能了,但是此时 iptables 并没有永久保存,下次开机上面的配置就会丢失。
为了使得重启之后 iptables 命令仍然存在,我们需要安装iptables-persistent软件
来实现(前面步骤二已完成):
执行以下命令,就即可将最新的 iptables 规则保存下来。1
2# sudo apt install iptables-persistent
sudo sh -c 'iptables-save > /etc/iptables/rules.v4'安装的过程中会提示你是否需要保存 iptables 配置,直接选是就行。这时候即使电脑重启了也会应用这些路由规则。
六、设置Clash开机自启动
1 | sudo tee /etc/systemd/system/clash.service > /dev/null << EOF |
到此为止,Clash透明网关就算是大功告成了,现在可以重启树莓派,检查科学成果了!!!
当然,从系统安全的角度,做一些扫尾的工作也很重要,包括:
- 编辑树莓派的公匙文件
mkdir $HOME/.ssh && vi $HOME/.ssh/authorized_keys
,将各台需要管理PC的 RSA 公匙加入 - 在树莓派上,设置文件权限并重启ssh服务
1 | sudo chmod 600 $HOME/.ssh/authorized_keys |
- 在管理PC上,尝试ssh登录,如果免密码成功,就可以关闭口令登录了
- 编辑树莓派的
sudo vi /etc/ssh/sshd_config
,将PasswordAuthentication
设为no
,以禁止采用口令登录
这样一来,树莓派就在指定PC上就可以pi
用户实现免密码登录,而其它用户、其它PC都无法登录了
Clash透明网关的使用方法
首先找到相应SSID,连接AP热点后自动设置默认网关和DNS,浏览器打开直接上网,再也不用 HTTP 或 SOCK5 代理了。
如果想要观察Clash运行情况,可以在浏览器打开http://192.168.0.8:9090/ui
Clash的配置是一件比较复杂的工作,准备下次专门讨论,这里就不啰嗦了。
补充问题
附录1: Clash的Home目录结构
1 | pi@raspberrypi:~ $ tree $HOME/.config/clash/ |
附录2:关于avahi服务
Zeroconf
(Zero configuration networking)零配置网络服务规范,是一种用于自动生成可用IP地址的网络技术,不需要额外的手动配置和专属的配置服务器。
Zeroconf规范的提出者是Apple公司,目标是让非专业用户也能便捷的连接各种网络设备,例如计算机,打印机等。整个搭建网络的过程都是通过程式自动化实现。如果没有 zeroconf,用户必须手动配置一些服务,例如DHCP、DNS,计算机网络的其他设置等。这些对非技术用户和新用户们来说是很难的事情。
Avahi
是Zeroconf规范的开源实现,常见使用在Linux上。包含了一整套多播DNS(multicastDNS)/DNS-SD网络服务的实现。它使用 的发布授权是LGPL。Zeroconf规范的另一个实现是Apple公司的Bonjour程式。Avahi
和Bonjour
相互兼容(废话,都走同一个 规范标准嘛,就象IE,Firefox,chrome都能跑HTTP1.1一样)。
Avahi
允许程序在不需要进行手动网络配置的情况 下,在一个本地网络中发布和获知各种服务和主机。例如,当某用户把他的计算机接入到某个局域网时,如果他的机器运行有Avahi服务,则Avahi程式自 动广播,从而发现网络中可用的打印机、共享文件和可相互聊天的其他用户。这有点象他正在接收局域网中的各种网络广告一样。
Linux下系统实际启动的进程名,是avahi-daemon
。除非你有兼容的设备或使用 zeroconf 协议的服务,否则应该关闭它。
参考目录
核心参考文献
- 在 Raspberry Pi上运行Clash作为透明代理
- 在树莓派上搭建软路由
- 使用PVE运行Clash旁路由虚拟机实现透明代理
- 树莓派搭建简略WiFi无线路由器
- 使用 PVE 运行 Clash 旁路由虚拟机实现透明代理
- Ubuntu18.04 上使用 clash 部署旁路代理网关
关于网络协议
关于Clash