How Linux Uses TUN/TAP Interfaces for VPNs
Virtual Private Networks (VPNs) rely heavily on Linux TUN and TAP interfaces to create secure, encrypted tunnels over public networks. Rather than routing traffic directly to physical hardware like an Ethernet or Wi-Fi card, the operating system uses these virtual kernel devices to pass raw network packets directly to user-space applications. This article breaks down how TUN and TAP devices function, the distinction between them, and the step-by-step mechanism Linux uses to encrypt and transmit traffic through a VPN tunnel.
Understanding TUN and TAP Devices
In standard networking, network interfaces (such as eth0
or wlan0) are backed by physical hardware. TUN (network
tunnel) and TAP (network tap) are virtual software-only network
interfaces supported directly by the Linux kernel via the universal
TUN/TAP driver.
The primary difference lies in the network layer at which they operate:
- TUN (Layer 3 - Network Layer): Operates with IP packets. It strips Ethernet framing, dealing purely with raw IP traffic. This makes it ideal for most point-to-point VPN connections, such as OpenVPN routed mode or WireGuard, where only IP routing is required.
- TAP (Layer 2 - Data Link Layer): Operates with Ethernet frames. It includes MAC addresses and behaves exactly like a virtual Ethernet switch port. TAP is used when a VPN needs to bridge networks, pass broadcast traffic, or support non-IP protocols.
The Userspace-to-Kernel Interaction
The core feature of TUN/TAP devices is that they bridge the gap between kernel-space routing and user-space programs.
Every TUN/TAP interface is bound to a special character device node
located at /dev/net/tun. When a VPN application (such as
OpenVPN) starts, it performs an ioctl() system call on
/dev/net/tun to request the creation of a virtual network
interface (for example, tun0). The application obtains a
standard file descriptor pointing to this device, allowing it to read
and write raw network packets just like regular file data.
The Step-by-Step VPN Traffic Flow
When a VPN connection is active, outgoing data travels through the following sequence:
- Traffic Generation: A local application (such as a web browser) sends an IP packet bound for an external server.
- Kernel Routing: The Linux kernel inspects its
routing table. When the VPN connection was established, the VPN software
configured default routes pointing through
tun0. The kernel routes the packet totun0. - Kernel-to-Userspace Transfer: Instead of
transmitting the packet over physical wire, the kernel places the raw IP
packet into the buffer of
/dev/net/tun. - Encapsulation and Encryption: The user-space VPN
client reads the unencrypted packet from
/dev/net/tun, encrypts the payload, and wraps it into a new outer packet (typically a standard UDP or TCP packet). - Physical Transmission: The VPN client writes the
newly encrypted packet to a standard network socket bound to the
physical interface (
eth0). The physical network card transmits this packet across the internet to the remote VPN server.
For incoming traffic, the process reverses: the physical interface
receives an encrypted UDP/TCP packet, passes it to the VPN application,
which decrypts it to recover the original raw packet. The application
then writes that raw packet into /dev/net/tun, causing the
Linux kernel to receive it on tun0 as if it arrived from a
standard network interface.
Advantages of the TUN/TAP Architecture
By abstracting network I/O through file descriptors, Linux decouples encryption and tunnel logic from kernel internals:
- System Stability: Cryptographic protocols, authentication handshakes, and compression run in user space. If the VPN application crashes, it does not bring down the entire operating system with a kernel panic.
- Full Kernel Integration: Despite being virtual,
tunandtapinterfaces interact seamlessly with native Linux networking utilities, includingiptables,nftables, traffic shaping (tc), and policy-based routing (ip route). - Protocol Independence: Because the Linux kernel merely hands over raw packets, user-space developers can implement proprietary encapsulation methods, advanced cipher suites, or custom transport protocols without modifying the underlying operating system.