Bottom line: Use TUN when an app ignores the system proxy
If your browser connects but a game, command-line tool, or desktop app doesn't, first check whether it honors the system proxy. System proxy settings give apps an HTTP proxy to use or ignore. TUN captures IP packets routed to a virtual network adapter at the network layer, so you don't have to configure a proxy address in each app.
The configuration in this guide uses fields for mihomo, the successor project to Clash Meta. Clash is commonly used to refer to a family of cores and clients; seeing “TUN” in an interface doesn't mean implementations are identical across cores or operating systems. Check the core in use under the client's About or core information before applying a configuration.
- Browser only: The system proxy is usually enough and easier to troubleshoot.
- Apps without proxy settings: TUN is a better fit, but check whether it captures the app's TCP and UDP traffic.
- Games, voice chat, or QUIC: In addition to TUN, confirm that the proxy protocol and server support UDP forwarding.
- Company VPN or remote desktop in use: Save your work and note the current routes and DNS settings first. Don't change the default route on a system you can access only remotely.
How a virtual network adapter works: from IP packets to rule-based routing
Traffic passes through four steps
- An app starts a connection. It tries to reach a domain or IP address, and the operating system uses its routing table to choose a network interface.
- Routing sends traffic to TUN. The client creates a virtual network adapter and installs routes; matching packets enter the TUN device.
- The core handles the connection. The network stack receives IP packets, extracts the destination address and port, and—when available—the domain name, then passes them to the rule engine.
- The outbound policy takes effect. Direct traffic leaves through the actual network interface; proxied traffic leaves through the selected proxy connection. Responses return to the app along the corresponding path.
A “virtual network adapter” is not a new physical network. It's an interface for exchanging packets between the operating system and a user-space networking program. The client must also keep its own proxy traffic from re-entering TUN, which would create a routing loop. That's why identifying the outbound interface and configuring permissions matter.
Routes and exclusions determine what gets captured
auto-route: true automatically configures routes to TUN, while auto-detect-interface: true identifies the outbound interface. Neither guarantees capture in every situation. Routes from other VPNs, apps bound to a specific interface, client exclusions, and IPv6 settings can all change the actual path.
If only IPv4 is captured while an app prefers IPv6, some connections may take a different route. Don't assume capture is complete just because a website loads; check the target app's connection log, matched rules, and actual outbound policy. TUN also doesn't automatically proxy other devices on the same LAN; sharing through a gateway requires separate forwarding and routing configuration.
system vs. gvisor: Choose a stack, then test compatibility
stack controls which network stack processes TUN packets. It isn't a node protocol or a proxy encryption method. Performance depends on the operating system, kernel version, connection type, and device capabilities, so no single stack is always “the fastest.”
| Stack | How it works | When to use it |
|---|---|---|
system |
Uses the operating system's network stack to handle connections; the implementation varies by platform. | A good starting point. Try another stack if you run into compatibility issues with a specific app or UDP. |
gvisor |
Processes packets with a gVisor-based user-space network stack. | Useful for comparison with system; user-space processing may increase CPU usage. |
mixed |
In mihomo, TCP uses system and UDP uses gvisor. | Can use different stacks for TCP and UDP; confirm that your core and client support this option. |
Change one variable at a time
- Keep the proxy policy, rules mode, and network conditions the same, then start with
system. - Open the target app, observe it for about 60 seconds, and note whether it connects, disconnects, or keeps CPU usage unusually high.
- Change only the stack to
gvisor, restart the core, and repeat the same test. - If only UDP apps have issues, check whether the proxy server supports UDP instead of blaming every problem on the network stack.
A sample note might read “system: web browsing works, voice chat won't connect; gvisor: web browsing works, voice chat connects.” This is an example of how to record results, not a test result from this guide. A latency reading of 40 ms also doesn't prove that game traffic is being forwarded correctly over UDP.
mihomo configuration: Check TUN, DNS, and routing together
This is a basic snippet to merge into a complete configuration; it doesn't include proxy server details or policy groups. Keep the existing proxies, proxy-groups, and rules from your subscription. Use the client's override or merge feature when possible; directly editing a generated subscription file may mean your changes get overwritten on update.
mixed-port: 7890
allow-lan: false
mode: rule
log-level: info
tun:
enable: true
stack: system
auto-route: true
auto-detect-interface: true
dns-hijack:
- any:53
- tcp://any:53
dns:
enable: true
listen: 127.0.0.1:1053
ipv6: false
enhanced-mode: fake-ip
fake-ip-range: 198.18.0.1/16
fake-ip-filter:
- "*.lan"
- "*.local"
nameserver:
- 1.1.1.1
- 8.8.8.8
What each port is for
7890: A mixed HTTP and SOCKS proxy port for the system proxy or apps that connect to it explicitly. TUN does not send every IP packet to this port.127.0.0.1:1053: A local DNS listener that avoids taking over the system's port 53. This does not automatically point system DNS to this address.any:53andtcp://any:53: Match regular UDP and TCP DNS requests on port 53 that enter the captured route, then pass them to the built-in DNS handler.198.18.0.1/16: The address pool used by fake-ip to map domains to virtual addresses. It is not a proxy server address.
Limits of DNS hijacking
Apps' built-in DoH and DoT don't use regular port 53 queries, so dns-hijack can't rewrite their DNS requests as described above. Their connections may still pass through TUN, but the built-in DNS may not know the final domain. Whether domain rules match also depends on fake-ip mapping, sniffing settings, and the protocol in use.
In fake-ip mode, an external domain resolving to an address such as 198.18.0.23 can be normal; this is a mapping, not the destination website's real IP. If a LAN printer, NAS, or internal domain has compatibility issues, configure filtering or DNS routing for the specific domain. Don't exclude every domain from fake-ip just to fix one internal name.
Enable TUN by platform: Grant permissions, then start the core
Menu names vary between client versions. The steps below describe the goal of each common entry point. If you don't see an exact match, look for the relevant feature under Service, Permissions, TUN, or Virtual Network Adapter. Don't assume another client's menu path applies to your version. For help choosing a client, see the client comparison.
Windows: Service mode and virtual network adapter drivers
- After importing your configuration, first use the system proxy to confirm that the same proxy policy can reach the target service. Make sure the app is configured to use the mixed port, for example
7890. - Using the common Clash Verge Rev interface as an example, go to “Settings” → “Service Mode” and install or enable the service as prompted. This may require administrator approval.
- Return to the home screen and turn on “TUN Mode,” or enable TUN in the network settings for your version. If the service is unavailable, fix its status first instead of repeatedly toggling the switch.
- Check the core logs for permission or driver errors while the virtual adapter and routes initialize, then test the app that previously ignored the proxy.
Windows clients usually need a compatible virtual network adapter driver, such as Wintun. Get and install the driver through a process supported by the client. Don't copy driver files from untrusted sources. You can use PowerShell to inspect the current adapters and IPv4 routes:
Get-NetAdapter
Get-NetRoute -AddressFamily IPv4 |
Sort-Object RouteMetric |
Format-Table DestinationPrefix, InterfaceAlias, NextHop, RouteMetric
The client or configuration determines the virtual adapter's name; it isn't necessarily called Clash. Seeing the adapter only confirms that the device was created—check routes and connection logs too. If another VPN is running, quit one before testing to prevent the two traffic-capture mechanisms from competing.
macOS: Helper service permissions and utun interfaces
- Confirm that both the client and its core support TUN. A client with only system proxy support can't gain full TUN functionality just by adding YAML fields.
- In the client's service or permissions settings, install the helper service as prompted and grant administrator approval.
- Enable TUN and check the logs for device, route, and DNS initialization details.
- Use Terminal to inspect interfaces and routes, then launch the target app to test it.
ifconfig
netstat -rn -f inet
scutil --dns
On macOS, virtual interfaces are commonly named utun followed by a number, but other VPNs and system services can create utun interfaces too. The presence of utun3 alone doesn't show that it belongs to the current client. If problems start after waking from sleep or switching Wi-Fi, check the outbound interface again instead of just switching proxy nodes.
Linux: TUN devices and network management permissions
Linux typically needs an available /dev/net/tun device and network management permissions to create interfaces and change routes. Desktop clients may obtain permissions through a service; if you run the core directly, configure permissions for your distribution and service setup. Don't grant elevated permissions to executables from unknown sources or recursively open up an entire client directory for convenience.
ls -l /dev/net/tun
ip link show
ip rule show
ip route show table all
When checking routes, inspect all tables: automatic traffic capture may use policy routing, which a plain ip route command may not show in full. Containerized setups also need the host to provide a TUN device and the required permissions; enabling a switch inside a container does not capture traffic from host apps.
Android and iOS: Use the system VPN permission flow
Common Clash clients for Android use VpnService to capture traffic. The first time you enable it, Android shows a system VPN connection permission prompt; root is generally not required. Check the app's VPN mode, bypass list, and the system's background battery restrictions. Typically, only one standard VPN service can be active per user, so starting another VPN may replace the current connection.
On iOS, the client itself must provide and be approved to use system capabilities such as Network Extension. A TUN field in a desktop configuration cannot create that capability. Add the VPN configuration through the client's workflow, grant permission, and check which configuration syntax it supports. Don't apply a complete mihomo TUN snippet directly to an iOS client with different syntax.
Verify traffic capture: Don't rely on the TUN switch alone
Cross-check these three things
- Device and routes: The virtual interface exists, capture routes are installed, and the logs show no persistent permission errors or device-open failures.
- Target app connections: Open an app that previously ignored the system proxy and look for its destination address and port on the client's Connections page. HTTPS commonly uses TCP 443 and QUIC commonly uses UDP 443, but a port alone can't identify an app's traffic type.
- Rules and outbound policy: Confirm that the connection matches the expected rule and policy. If a destination that needs a proxy matches DIRECT, TUN may be working but the result still won't be what you expect.
To distinguish the two traffic paths, temporarily turn off the system proxy and clear any manually configured HTTP or SOCKS proxy in the target app, leaving only TUN enabled for a test. A browser still being able to connect is not conclusive; the site may be reachable directly. Cross-check connection logs and outbound policy, then restore the settings you need.
Narrow down the cause by symptom
| Symptom | Check first |
|---|---|
| All apps lose internet access when TUN is enabled | Service permissions, outbound interface detection, DNS reachability, and route conflicts with other VPNs. |
| Web browsing works, but voice chat or games don't | UDP capture, UDP support on the proxy server, app exclusions, then compare the network stacks. |
| Public internet works, but the NAS or printer is unreachable | LAN routing, internal DNS, fake-ip filtering, and the actual subnet used by the current network. |
| Stops working after switching Wi-Fi | Check whether the outbound interface updated and whether old routes remain. Re-enable TUN, then check the logs again. |
| The target app doesn't appear in the connection log | Check whether the app is excluded, uses uncaptured IPv6 or a specific interface, or has been filtered out of the logs. |
Temporarily set the log level to debug while troubleshooting, and note the exact times you enable TUN and launch the target app. For example, if you enable it at 14:32:10 and launch the app at 14:32:20, check for device, route, DNS, and connection errors around that 10-second window. Set the level back to info once you've found the issue. Before sharing logs, redact subscription URLs, tokens, and personal network information.
Turn TUN off and roll back: Restore connectivity before troubleshooting further
If the whole system loses internet access, turn off TUN first so the client can remove its automatic routes, then restore the system proxy if needed. Exiting the client normally gives it a better chance to clean up than force-quitting the core. If problems persist after exit, check whether the system proxy still points to the stopped listener at 127.0.0.1:7890, and whether DNS, virtual interfaces, and routes have been restored.
- Don't delete the entire routing table on a whim; corporate networks, containers, and other VPNs may depend on its rules.
- Don't disable every virtual network adapter blindly. Use the client logs and interface changes to identify the device that belongs to the current client first.
- If a fake-ip cache still gives the app a virtual address, quit and reopen the app. If needed, flush the DNS cache using the method for your operating system.
- Once the network is restored, troubleshoot in this order: permissions and devices → routes and outbound interface → DNS → rules and policy → app protocol. Change only one setting per attempt.
Keep a configuration you can explain, verify, and roll back: TUN handles ingress, DNS supplies domain information, rules determine outbound policy, and proxy servers carry the actual connections. For more field details, see TUN configuration in the advanced guide. If you're importing a subscription for the first time, follow the quick start to establish a basic connection first.