OpenWrt 路由器部署 mihomo 核心:旁路由分流實戰紀錄

把代理核心從電腦搬到路由器上,是不少家用網路的終局形態:電視、遊戲機這類不方便安裝用戶端的裝置也能一併接管。本文記錄在 OpenWrt 旁路由上部署 mihomo(Clash Meta)核心的完整過程——從部署形態抉擇、二進位檔安裝、訂閱設定落地,到 TUN 接管、procd 守護與分流驗證,每一步都給出可直接照抄的指令與明確的檢查點。

mihomo 核心·TUN 接管模式·procd 開機守護·OpenWrt 23.05 示範環境

一、部署形態:主路由直裝還是旁路由

在路由器上運行代理核心,先要做一道選擇題:核心裝在哪台裝置上。兩種形態各有清楚的使用界線,選錯形態是新手翻車的第一個原因。

主路由直裝

核心直接運行在出口閘道上,區域網路所有流量天然經過它,用戶端零設定。代價是耦合過深:核心崩潰、規則寫錯、記憶體耗盡,任何一處出問題都是全家斷網;同時 NAT 與加解密疊加在同一顆晶片上,對算力要求最高,百兆以上頻寬的低階 MIPS 機型基本吃不消。

旁路由(單臂閘道)

另備一台裝置——淘汰的電視盒子、樹莓派、x86 小主機都行——刷入 OpenWrt,網路埠接入主路由所在的區域網路,固定一個同網段 IP。需要走代理的裝置,把預設閘道與 DNS 伺服器指向這台旁路由即可;不想被接管的裝置維持原樣,互不干擾。旁路由當機時,把閘道改回主路由,十秒內恢復上網,風險完全隔離。

本文以旁路由為主線展開。兩種形態在核心安裝與設定部分完全相同,差異只在流量入口,選擇主路由直裝的讀者可跳過第四節中「閘道指向」小節。

批注

旁路由的最大價值不是效能,而是可回退:任何設定失誤都有一條十秒鐘的退路。這是把代理核心放進生產網路之前,先鋪好的一層安全墊。

二、核心選型與安裝

mihomo 是 Clash 原版核心歸檔後由社群延續維護的分支(原 Clash.Meta),以單一檔案二進位發布,無額外依賴、可直接在 OpenWrt 上運行,是目前在路由器上部署的首選核心。它的 release 產物是 gzip 壓縮的裸二進位檔,依 CPU 架構分包,因此第一步是先確認自己裝置的架構。

SSH 登入路由器,執行 uname -m,依下表對照選擇下載包:

uname -m 輸出典型裝置release 檔名關鍵字
aarch64樹莓派 4/5、NanoPi R4S、多數 ARM 盒子linux-arm64
armv7l樹莓派 2/3(32 位元系統)、老款開發板linux-armv7
mipselMT7621 等 MIPS 路由(K2P、新三)linux-mipsle-softfloat
x86_64軟路由小主機、虛擬機linux-amd64-compatible

兩個容易踩的坑:其一,x86 軟路由請選帶 compatible 後綴的包,OpenWrt 的 x86 建置面向較舊的指令集,一般 amd64 包在部分 CPU 上會直接報 Illegal instruction;其二,MT7621 這類 MIPS 裝置是 little-endian 且多數沒有硬體浮點運算單元,必須選 mipsle-softfloat。

以 arm64 裝置為例,完整安裝指令如下:

opkg update
opkg install curl ca-bundle kmod-tun
curl -L -o /tmp/mihomo.gz https://github.com/MetaCubeX/mihomo/releases/download/v1.19.5/mihomo-linux-arm64-v1.19.5.gz
gunzip /tmp/mihomo.gz
mv /tmp/mihomo /usr/bin/mihomo
chmod +x /usr/bin/mihomo
mihomo -v

最後一行 mihomo -v 能印出版本號,說明架構選對了;若提示 Illegal instruction 或 Exec format error,回上表換包重試。指令中的版本號僅為示例,下載前請到 mihomo 的 releases 頁面核對目前穩定版與確切檔名。kmod-tun 一併在此裝好,第四節會用到。

批注

/tmp 在 OpenWrt 上是記憶體磁碟,重啟即清空,只適合中轉;核心與設定必須落進快閃記憶體,例如 /usr/bin 與 /etc/mihomo。快閃記憶體不足 32MB 的機型請先做 extroot 或改用外接儲存,否則連 GeoIP 資料庫都放不下。

三、設定落地:訂閱下載與關鍵欄位

約定設定目錄為 /etc/mihomo,核心以 -d /etc/mihomo 參數啟動,目錄下會依次出現 config.yaml、GeoIP 資料庫與快取檔案。先建目錄,再把訂閱拉下來:

mkdir -p /etc/mihomo
curl -L -o /etc/mihomo/config.yaml "你的訂閱網址"

多數機場的訂閱連結在被 Clash 系用戶端請求時會直接回傳 YAML 設定,存成 config.yaml 即可使用。如果下載到的是 base64 編碼的節點清單,說明伺服端回傳的是通用訂閱,需要在請求裡帶上 Clash 的 User-Agent,或者先在電腦上完成轉換再 scp 上傳到路由器——不建議在路由器上跑訂閱轉換程式,徒增維運面。

拿到訂閱後,依旁路由的角色修改以下關鍵欄位,其餘保持訂閱原樣:

mixed-port: 7890            # HTTP 與 SOCKS 混合入口
allow-lan: true             # 允許區域網路裝置連線,旁路由必須開啟
bind-address: "*"
log-level: warning
external-controller: 0.0.0.0:9090   # 外部控制介面
external-ui: ui             # 面板靜態檔案目錄
secret: "請改成自訂密碼"
dns:
  enable: true
  listen: 0.0.0.0:1053
  enhanced-mode: fake-ip
  fake-ip-range: 198.18.0.1/16
  nameserver:
    - 223.5.5.5
    - 119.29.29.29
  fallback:
    - https://1.1.1.1/dns-query
    - https://dns.google/dns-query
tun:
  enable: true
  stack: system
  auto-route: true
  auto-detect-interface: true
  dns-hijack:
    - any:53

三個欄位決定旁路由能否運作:allow-lan 沒開,區域網路裝置根本連不上 7890 埠;external-controller 綁定 0.0.0.0,電腦上的瀏覽器才能存取面板;tun 段則是下一節接管流量的核心。修改完成後,用核心自帶的檢查功能驗證語法:

mihomo -t -d /etc/mihomo

輸出提示 configuration file test is successful 即通過;若報錯,訊息裡會給出具體行號,依行號回去修。

批注

external-controller 暴露在區域網路時務必設定 secret,且切勿把它對外映射到公網。9090 埠握有切換節點、查看連線、修改設定的全部權限,裸奔等於把網路出口交給同網段的任何人。

四、接管流量:TUN 模式與閘道指向

接管方式選 TUN,理由是它把路由維護收進核心內部:啟用後 mihomo 建立名為 utun 的虛擬網卡,auto-route 自動寫入路由規則,把本機發出的與被轉發進來的 TCP、UDP 流量全部收進核心,無需手寫一條 iptables REDIRECT 規則,也不必為 UDP 另外處理。stack 選 system 相容性最好;追求吞吐量可換 gvisor 對比測試。

TUN 的前提是核心態支援,第二節安裝的 kmod-tun 即為此準備。確認裝置節點存在:

ls /dev/net/tun

輸出 /dev/net/tun 即正常;提示不存在則說明 kmod-tun 未裝好或未載入,重裝後重新開機。

用戶端閘道指向

旁路由本身不與任何裝置直連,流量要靠「指路」過來。三種做法依推薦度排列:

  1. 主路由 DHCP 派發:在主路由的 DHCP 選項裡,把閘道(option 3)與 DNS(option 6)改為旁路由 IP,全屋裝置無感切換,新接入裝置自動生效。
  2. 單一裝置手動指定:只讓需要的裝置改閘道與 DNS,其餘裝置直連主路由——這是旁路由獨有的細緻度,適合先拿一台裝置試跑驗證。
  3. 旁路由自建 DHCP:關掉主路由的 DHCP 由旁路由接管,控制最徹底,但旁路由故障時全屋拿不到位址,新手不建議。

兩個系統層確認:OpenWrt 預設開啟 IP 轉發,可用 sysctl net.ipv4.ip_forward 覆核回傳值為 1;防火牆方面,進入「網路 → 防火牆 → 區域」,把 utun 裝置加入 lan 區域的裝置清單,否則被轉發進來的流量會在 netfilter 層被丟棄,表現為用戶端能連上旁路由,卻打不開任何網頁。

五、開機自啟:交給 procd 守護

OpenWrt 的服務管理器是 procd,寫一個 init 腳本即可獲得開機自啟與崩潰拉起。新建 /etc/init.d/mihomo,內容如下:

#!/bin/sh /etc/rc.common
# mihomo 核心守護腳本
START=99
STOP=10
USE_PROCD=1

start_service() {
    procd_open_instance mihomo
    procd_set_param command /usr/bin/mihomo -d /etc/mihomo
    procd_set_param respawn 3600 5 5
    procd_set_param stdout 1
    procd_set_param stderr 1
    procd_close_instance
}

respawn 一行的三個數字依次是門檻值、間隔與重試次數,意思是行程退出後 5 秒拉起,一小時內反覆崩潰超過 5 次就放棄;stdout 與 stderr 重新導向到 syslog,之後用 logread 就能翻核心日誌。賦予執行權限並啟用:

chmod +x /etc/init.d/mihomo
/etc/init.d/mihomo enable
service mihomo start

enable 會在 /etc/rc.d 下建立 S99 開頭的軟連結,重新開機路由器後核心自動啟動。訂閱更新也可以順手自動化:在 crontab 裡加一條每週凌晨重新下載 config.yaml 再執行 service mihomo restart 的任務,節點清單即可保持新鮮。

六、驗證與排障清單

部署完成不代表分流正確,依下面的順序逐項驗證,每一步都有明確判準:

  1. 行程存活

    pgrep mihomo 有輸出,/etc/init.d/mihomo status 顯示 running。首次啟動會自動下載 GeoIP 資料庫到 /etc/mihomo,確認該目錄可寫且剩餘空間充足。

  2. 日誌乾淨

    logread -e mihomo 無反覆報錯。持續刷同一行錯誤通常是設定或網路問題,依錯誤訊息定位。

  3. 面板可連

    瀏覽器開啟 http://旁路由IP:9090/ui,輸入 secret 後能看到即時連線。external-ui 指向的 ui 目錄,需要先把 metacubexd 或 zashboard 的建置產物解壓進去。

  4. DNS 已接管

    在用戶端執行 nslookup www.google.com 旁路由IP,fake-ip 模式下回傳 198.18.x.x 段位址,說明查詢進入了核心而非繞路洩漏。

  5. 出口正確

    用戶端打開任一 IP 查詢站點,顯示的應是節點出口位址;再存取一個台灣本地站點,確認其走直連且速度正常,分流即告成立。

高頻故障與對策:

至此,一台可自我修復、可回退、按需接管的旁路由就部署完成了。後續維護只剩兩件事:留意 mihomo 的版本更新節奏,以及定期備份 /etc/mihomo 目錄——裡面躺著全部設定與資料庫,換機搬移時整個目錄拷走即可。

下載Clash