前言:为什么使用 TUN 模式
在 Linux 上运行 Clash Meta 或 Mihomo 时,很多用户首先想到的是设置环境变量,例如 http_proxy、https_proxy,或者在桌面环境中勾选系统代理。这些方式对浏览器、终端工具和部分支持代理协议的应用比较有效,但它们并不能自动接管所有网络连接。没有主动读取代理设置的程序、容器服务、软件更新器、DNS 请求以及部分 UDP 流量,仍然可能直接访问网络。
TUN 模式的工作方式不同。Clash 会在系统中创建一个虚拟网络设备,把进入该设备的流量交给内核处理,再按照配置文件中的规则决定走代理节点还是直接连接。这样,应用不需要单独支持 HTTP 或 SOCKS 代理,也能被统一纳入分流体系。对 Linux 服务器、开发机、软路由和桌面系统来说,这种方式尤其适合需要统一管理流量的场景。
不过,TUN 模式并不是简单地打开一个开关。它会涉及 Linux 的 tun 内核模块、路由表、DNS 劫持、权限管理以及防火墙规则。如果配置不完整,常见结果包括网络完全中断、DNS 解析失败、代理流量循环转发,或者重启后虚拟网卡消失。本文会从检查环境开始,逐步完成配置,并在最后介绍如何验证和回滚。
本文适用范围
适用于使用 Clash Meta 或 Mihomo 内核的 Linux 用户。不同发行版的服务管理命令可能略有差异,但核心配置和排查思路基本一致。
1开启前的准备工作
开始修改配置前,建议先确认几个基础条件。第一,系统需要使用较新的 Linux 内核,并且当前内核能够加载 TUN 设备。第二,你需要拥有 Clash Meta 的可执行文件、一个能够正常使用的配置文件,以及至少一个可用的代理节点。第三,启动内核的用户必须具备创建网络设备和修改路由的权限。
检查发行版、内核与 TUN 模块
使用以下命令查看系统版本和内核版本。命令本身不会修改系统,可以先在普通用户权限下执行:
如果最后一条命令提示文件不存在,可以尝试加载 TUN 模块。大多数 Debian、Ubuntu、Fedora 和 Arch Linux 系统都已经内置该模块:
正常情况下,lsmod 会显示 tun,并且能够看到字符设备文件。如果模块加载成功但重启后又消失,可以把模块名称写入系统的模块自动加载配置。需要注意的是,部分 VPS 服务商会在宿主机层面禁用 TUN,即使你拥有 root 权限也无法自行创建设备。
先确认云服务器限制
如果 modprobe tun 返回权限错误、模块不存在或设备始终无法创建,请先查看 VPS 服务商的网络限制。不要反复修改路由表,否则可能影响远程 SSH 连接。
备份原始配置
正式编辑前,先复制一份配置文件。假设配置存放在 /etc/mihomo/config.yaml,可以执行:
备份的意义不只是防止 YAML 写错。当 TUN 模式导致默认路由发生变化时,你可以快速恢复到原来的系统代理模式。配置文件中的订阅地址、节点密码和密钥也属于敏感信息,建议限制文件读取权限,不要把它提交到公开代码仓库。
2编辑 TUN 配置
打开 Clash Meta 使用的 YAML 配置文件,在顶层加入或调整 tun 模块。YAML 对缩进非常敏感,建议使用两个空格,不要混用制表符。下面是一份适合大多数桌面或单机 Linux 环境的基础示例:
关键参数说明
- enable:设置为
true后启用 TUN。若只想暂时停用,可以改为false,不必删除整个模块。 - stack:常见值包括
system、gvisor和mixed。system通常性能较好,优先使用系统网络栈;如果遇到兼容性问题,可根据内核版本尝试其他值。 - device:指定虚拟网卡名称。使用固定名称便于通过
ip link和日志观察状态。 - auto-route:自动写入必要路由。初次配置建议开启,否则需要手动处理流量进入 TUN 的路径。
- auto-detect-interface:让内核自动识别实际出口网卡,适合笔记本在有线、无线网络之间切换的情况。
- dns-hijack:把指定端口的 DNS 请求交给 Clash 处理。它能减少应用绕过代理直接使用运营商 DNS 的情况,但企业内网或特殊本地 DNS 环境需要谨慎配置。
- mtu:表示虚拟设备的最大传输单元。1500 是常见起点;如果出现网页部分加载、视频卡住或隧道协议丢包,可以尝试降低到 1400 或 1350。
配合 DNS 模块避免解析绕过
TUN 只负责接管流量,DNS 是否按照预期工作还取决于 Clash 的 DNS 模块。如果系统仍把域名请求发送给本地运营商 DNS,可能出现解析污染、域名与出口不匹配或应用连接失败。可以先使用下面的基础配置,再根据网络环境调整:
fake-ip 模式会为域名分配虚拟地址,使规则匹配更加稳定,但少数依赖真实 DNS 返回地址的程序可能需要加入 fake-ip-filter。例如局域网打印机、路由器管理地址、公司内网域名等,都应该根据实际情况排除。不要直接照搬网上的超长排除列表,过多例外会让问题变得难以定位。
配置修改后的检查方法
每次修改 YAML 后,先使用 Clash Meta 的配置检查参数或客户端内置校验功能确认格式正确。YAML 缩进错误通常会导致内核完全无法启动,先校验再重启服务可以避免不必要的断网。
3加载权限并启动内核
Linux 的普通用户通常不能直接创建 TUN 设备或写入系统路由,因此启动方式很重要。最简单的测试方法是临时使用 sudo 运行 Clash Meta,确认配置可用后,再迁移到 systemd 服务。这样既方便观察日志,也不会一开始就把错误配置设置为开机自启。
- 确认配置文件路径和可执行文件名称,例如
/usr/local/bin/mihomo与/etc/mihomo/config.yaml。 - 先加载 TUN 模块:
sudo modprobe tun。 - 在前台启动内核,保留终端窗口观察日志。
- 看到虚拟设备创建、配置载入和控制端口监听成功后,再打开另一个终端进行测试。
正常日志特征
日志通常会出现配置载入成功、RESTful API 监听成功以及 TUN 设备启动等信息。具体文字会随 Mihomo 版本变化,重点是确认没有 YAML、权限、路由和端口占用错误。
使用 systemd 管理服务
确认临时启动无误后,可以创建 systemd 服务,让 Clash Meta 在系统启动后自动运行。下面的示例使用专用用户运行程序;如果该用户没有创建 TUN 的权限,需要额外配置 capabilities,或者在服务中使用受控的 root 权限。
创建 /etc/systemd/system/mihomo.service:
保存后重新加载服务并启动:
不同版本对权限能力的要求可能不同。如果日志提示无法创建设备或修改路由,可以暂时用 root 方式验证问题来源,再按照发行版安全策略细化权限。不要为了省事长期给所有程序开放不必要的系统能力。
4验证代理是否生效
看到服务处于 running 状态并不代表所有流量都已经通过代理。建议按照“设备、路由、DNS、出口”四个层次检查,每一步都能帮助缩小故障范围。
检查虚拟网卡和路由
如果配置中的设备名称是 mihomo,第一条命令应该能够看到对应接口。接口可能没有传统意义上的公网地址,但应该处于启用状态。路由表中应存在把相关流量导向 TUN 的规则;如果只看到网卡却没有路由,通常需要检查 auto-route、系统权限以及是否有其他网络管理工具覆盖了路由。
检查 DNS 解析路径
可以使用 resolvectl status、dig 或 nslookup 查看当前 DNS 状态。不同发行版可能使用 systemd-resolved、NetworkManager 或静态的 /etc/resolv.conf。如果本机 DNS 服务与 Clash 的监听端口冲突,需要让两者使用不同端口,或者明确指定由哪一个服务负责转发。
这里的 curl 命令只是验证代理端口是否可用,并不能单独证明 TUN 生效。要测试透明接管能力,应关闭命令行代理环境变量,再访问一个外部地址,并查看 Clash 日志中的连接记录:
如果出口地址与预期节点一致,且日志显示请求被规则分配到代理策略组,说明基本链路已经建立。测试时不要只访问一个网站,最好分别验证国内直连域名、国外代理域名、IPv4 和 IPv6,避免某一条协议路径恰好绕过了 TUN。
远程 SSH 用户的特别提醒
在远程服务器上启用 auto-route 可能改变默认路由,导致 SSH 连接中断。建议先在本地控制台、带外管理终端或可恢复快照环境中测试,并准备一个定时回滚任务。
5常见故障排查
没有创建 TUN 设备
首先查看 ls -l /dev/net/tun,确认内核设备存在;然后查看服务日志中是否有权限错误。如果是专用用户启动,重点检查 systemd 的 AmbientCapabilities、CapabilityBoundingSet 和设备访问权限。某些容器环境默认不允许 CAP_NET_ADMIN,需要在容器启动参数中显式开放,或者改用宿主机运行。
开启后完全无法上网
这类问题通常与默认路由、DNS 劫持或代理节点不可用有关。先停止 Clash,确认基础网络是否恢复;如果恢复,临时把 auto-route 改为 false,只保留 TUN 设备,再逐步启用路由。这样可以判断是虚拟网卡创建失败,还是路由接管后产生了循环。与此同时,检查节点是否过期、策略组是否选择了不可用节点,以及本地监听端口是否已经被其他程序占用。
DNS 循环或域名无法解析
当 Clash 的 DNS 监听端口、systemd-resolved 和 NetworkManager 互相转发时,可能形成 DNS 循环。可以查看端口占用:
确认每个端口只由预期服务监听。测试阶段可以先关闭 dns-hijack,使用明确的 DNS 地址验证代理主体是否正常,然后再恢复劫持功能。对于局域网域名和路由器地址,应加入正确的直连或 fake-ip 排除规则。
IPv6 流量绕过代理
如果节点和规则只处理 IPv4,而系统同时拥有 IPv6 默认路由,部分应用可能通过 IPv6 直连。可以在 Clash 规则和 DNS 设置中明确处理 IPv6;如果当前网络没有可靠的 IPv6 代理能力,可暂时关闭系统 IPv6 进行对比测试。不要只根据 IPv4 出口地址判断代理已经完全生效。
推荐的排查顺序
先看内核日志,再看虚拟网卡,然后检查路由,接着检查 DNS,最后验证出口地址。每次只改一个变量并记录结果,比同时更换内核、规则和节点更容易找到根因。
6安全回滚与日常管理
任何涉及系统路由的配置都应该具备明确的回滚方法。最简单的回滚方式是停止服务、关闭 TUN,再恢复备份配置:
如果停止服务后网络仍然异常,可以查看路由表并确认是否残留了由 Clash 创建的策略路由。不要直接删除所有路由,尤其是在 SSH 远程连接中。应根据启动前后的差异,删除明确属于 TUN 的接口、规则和路由。使用 NetworkManager 或 systemd-networkd 的系统,还要检查它们是否会在服务停止后自动重建网络配置。
日常运行中,建议定期检查日志大小、订阅更新状态和节点可用性。对服务器而言,可以通过 journalctl --vacuum-time 或日志轮转机制限制日志占用;对桌面系统而言,则应在升级 Clash Meta 前保留当前可用版本和配置。升级内核后,如果出现 TUN 行为变化,优先对比版本说明,再判断是否需要调整 stack 或 MTU。
- 配置文件保留至少一份最近可用备份。
- 修改路由前记录
ip route和ip rule输出。 - 远程机器设置可用的带外控制台或自动恢复方案。
- 不要公开包含订阅链接、节点密码和 API 密钥的日志或配置。
总结与推荐
在 Linux 上开启 Clash Meta TUN 模式,核心并不是简单复制一段 YAML,而是同时处理虚拟网卡、系统权限、路由、DNS 和故障恢复五个部分。正确的流程应该是先确认 TUN 设备可用,再备份配置,之后启用基础参数,使用前台模式观察日志,最后才交给 systemd 长期管理。
与只依赖环境变量的传统代理方式相比,TUN 模式可以覆盖更多不支持代理设置的应用,减少后台程序绕过规则的情况。部分 Linux 图形化代理工具虽然提供了一键开关,但在远程服务器、无桌面环境或需要精确控制路由时,直接管理 Clash Meta 配置更透明,也更容易通过日志定位问题。另一方面,NetworkManager、代理软件和某些 VPN 客户端可能会争夺默认路由,因此不建议在不了解网络拓扑的情况下叠加多个透明代理。
- 规则分流更清晰:可以按照域名、IP、进程和网络类型决定直连或代理。
- 跨应用接管能力更强:不要求每个程序分别支持 HTTP 或 SOCKS 代理。
- 排查手段完整:虚拟网卡、路由、DNS 和连接日志都可以独立验证。
- 适合多种 Linux 场景:桌面、开发环境、家庭服务器和部分云主机都能采用相同思路。
如果你希望在 Windows、macOS 和 Linux 之间使用统一的 Clash 配置,可以先准备好订阅和规则,再根据不同系统分别设置 TUN 权限与启动方式。Linux 用户尤其要保留回滚路径,先在可控环境中验证,确认 IPv4、IPv6、DNS 和远程管理都正常后,再把配置用于长期运行。