+++ /dev/null
-.\" $OpenBSD: tun.4,v 1.2 1996/12/16 16:08:52 deraadt Exp $
-.Dd March 10, 1996
-.Dt TUN 4
-.Os OpenBSD 1.2
-.Sh NAME
-.Nm tun
-.Nd Tunnel Network Interface
-.Sh SYNOPSIS
-.Cd "pseudo-device tun 4"
-.Sh DESCRIPTION
-The
-.Nm tun
-interface is a software loopback mechanism that can be loosely
-described as the network interface analog of the
-.Xr pty 4 ,
-that is,
-.Nm tun
-does for network interfaces what the
-.Nm pty
-driver does for terminals.
-.Pp
-The
-.Nm tun
-driver, like the
-.Nm pty
-driver, provides two interfaces: an interface like the usual facility
-it is simulating (a network interface in the case of
-.Nm tun ,
-or a terinal for
-.Nm pty ) ,
-and a character-special device
-.Dq control
-interface.
-.Pp
-The network interfaces are named
-.Sy tun Ns Ar 0 ,
-.Sy tun Ns Ar 1 ,
-etc, as many in all as the
-.Ar count
-figure given on the
-.Sy pseudo-device
-line. Each one supports the usual network-interface
-.Xr ioctl 2 Ns s ,
-such as
-.Dv SIOCSIFADDR
-and
-.Dv SIOCSIFNETMASK ,
-and thus can be used with
-.Xr ifconfig 8
-like any other interface. At boot time, they are
-.Dv POINTOPOINT
-interfaces, but this can be changed; see the description of the control
-device, below. When the system chooses to transmit a packet on the
-network interface, the packet can be read from the control device (it
-appears as
-.Dq input
-there); writing a packet to the control device generates an input
-packet on the network interface, as if the (nonexistent) hardware had
-just received it.
-.Pp
-There are two control interfaces. The
-.Em data
-interface, normally
-.Pa /dev/tun Ns Sy N ,
-is exclusive-open (it cannot be opened if it is already open), is
-normally restricted to the super-user, and can
-.Dq transmit
-and
-.Dq receive
-packets. The
-.Em control
-interface, normally
-.Pa /dev/tunc Ns Sy N ,
-cannot send and receive packets, but can be opened by many processes at
-once; it is intended for status queries and changes (many of which can
-also be implemented with
-.Fn ioctl
-calls on the data interface). There are a number of status bits that
-can be set or cleared via the control interfaces; they are mentioned
-below where applicable, and they are all summarized in the discussions
-of the control interfaces.
-.\" Why isn't .Ss documented in mdoc(7) and mdoc.samples(7)?
-.Ss The data interface
-The data interface supports
-.Xr read 2 ,
-.Xr write 2 ,
-and
-.Xr ioctl 2
-calls to, respectively, collect
-.Dq output
-packets, generate
-.Dq input
-packets, and perform control functions. As mentioned above, this
-interface is exclusive-open; if the
-.Dv SUONLY
-bit is set (which it is by default), it cannot be opened at all except
-by the super-user. By default, a
-.Fn read
-call will return an error
-.Pf ( Er EHOSTDOWN )
-if the interface is not
-.Dq ready
-(which means that the control device is open and the interface's
-address has been set); if preferred, the
-.Dv RRWAIT
-bit can be set, in which case a
-.Fn read
-call will block (even if non-blocking I/O has been enabled) until the
-interface is ready. Once the interface is ready,
-.Fn read
-will return a packet if one is available; if not, it will either block
-until one is or return
-.Er EWOULDBLOCK ,
-depending on whether non-blocking I/O has been enabled. If the packet
-is longer than is allowed for in the buffer passed to
-.Fn read ,
-the extra data will be silently dropped.
-.Pp
-The first byte of data will always be the address family (eg,
-.Dv AF_INET )
-of the packet. By default, the packet data follows immediately, but if
-the
-.Dv PREPADDR
-bit is set, the address to which the packet is to be sent is placed
-after the address family byte and before the packet data. The size and
-layout of the address depends on the address family; for
-.Dv AF_INET ,
-for example, it is a
-.Va struct in_addr .
-A
-.Xr write 2
-call passes a packet in to be
-.Dq received
-on the pseudo-interface. Each
-.Fn write
-call supplies exactly one packet; the packet length is taken from the
-amount of data provided to
-.Fn write .
-The first byte must be the address family of the packet, much as in
-packets returned by
-.Fn read ;
-the packet data always follows immediately.
-A large number of
-.Xr ioctl 2
-calls are also supported. They are defined in
-.Aq Pa net/if_tun.h Ns .
-.Bl -tag -width TUN_PREPADDR
-.It Dv TUNSDEBUG
-The argument should be a pointer to an
-.Va int ;
-this sets the internal debugging variable to that value. What, if
-anything, this variable controls is not documented here; see the source
-code.
-.It Dv TUNGDEBUG
-The argument should be a pointer to an
-.Va int ;
-this stores the internal debugging variable's value into it.
-.It Dv TUNSMODE
-The argument should be a pointer to an
-.Va int ;
-its value must be
-.Dv IFF_POINTOPOINT
-or
-.Dv IFF_BROADCAST .
-The type of the corresponding
-.Em tun Ns Sy n
-interface is set to the supplied type. If the value is anything else,
-an
-.Er EINVAL
-error occurs. The interface must be down at the time; if it is up, an
-.Er EBUSY
-error occurs.
-.\" X .It Dv TUNSFLAG
-.\" X The interface's flag bits are set as specified in the
-.\" X .Va int
-.\" X argument. Only some of the bits can be modified; the rest are
-.\" X read-only. The bits are defined in
-.\" X .Aq Pa net/if_tun.h
-.\" X with a
-.\" X .Dv TUN_
-.\" X prefix; for example, the bit called
-.\" X .Dv RRWAIT
-.\" X in this document would be referred to in source code as
-.\" X .Dv TUN_RRWAIT .
-.\" X The bits are:
-.\" X .\" Why isn't the way to create a table like this documented in mdoc(7)
-.\" X .\" or mdoc.samples(7)?!
-.\" X .Bl -column "TUN_PREPADDR" "RO/RW" -compact -indent-two
-.\" X .It Name Ta RO/RW Ta Meaning
-.\" X .It Dv TUN_OPEN Ta RO Ta "Data control device is open."
-.\" X .It Dv TUN_INITED Ta RO Ta "Initialized."
-.\" X .It Dv TUN_RCOLL Ta RO Ta "Select-for-read collision."
-.\" X .It Dv TUN_IASET Ta RO Ta "Address has been set."
-.\" X .It Dv TUN_DSTADDR Ta RO Ta "Destination address has been set."
-.\" X .It Dv TUN_RWAIT Ta RO Ta "A process is blocked in Fn read Ns ."
-.\" X .It Dv TUN_ASYNC Ta RO Ta "Generate Dv SIGIO No for readers."
-.\" X .It Dv TUN_NBIO Ta RO Ta "Non-blocking I/O for reads."
-.\" X .It Dv TUN_BRDADDR Ta RO Ta "Broadcast address has been set."
-.\" X .It Dv TUN_PREPADDR Ta RW Ta "Prepend sent-to address for reads."
-.\" X .It Dv TUN_STAYUP Ta RW Ta "Don't take interface down on close."
-.\" X .It Dv TUN_SUONLY Ta RW Ta "Data control device is super-user only."
-.\" X .It Dv TUN_RRWAIT Ta RW Ta "Wait for ready when reading."
-.\" X .El
-.\" X .It Dv TUNGFLAG
-.\" X The interface's flag bits are fetched into the argument
-.\" X .Va int .
-.\" X The flags and their meanings are as for
-.\" X .Dv TUNSFLAG .
-.\" X .It Dv FIONBIO
-.\" X Turn non-blocking I/O for reads off or on, according as the argument
-.\" X .Va int Ns 's
-.\" X value is or isn't zero. (Writes are always nonblocking.)
-.\" X .It Dv FIOASYNC
-.\" X Turn asynchronous I/O for reads (ie, generation of
-.\" X .Dv SIGIO
-.\" X when data is available to be read) off or on, according as the argument
-.\" X .Va int Ns 's
-.\" X value is or isn't zero.
-.\" X .It Dv FIONREAD
-.\" X If any packets are queued to be read, store the size of the first one
-.\" X into the argument
-.\" X .Va int ;
-.\" X otherwise, store zero.
-.\" X .It Dv TIOCSPGRP
-.\" X Set the process group to receive
-.\" X .Dv SIGIO
-.\" X signals, when asynchronous I/O is enabled, to the argument
-.\" X .Va int
-.\" X value.
-.\" X .It Dv TIOCGPGRP
-.\" X Retrieve the process group value for
-.\" X .Dv SIGIO
-.\" X signals into the argument
-.\" X .Va int
-.\" X value.
-.El
-The data control device also supports
-.Xr select 2
-for read; selecting for write is pointless, and always succeeds, since
-writes are always nonblocking (if the packet cannot be accepted for a
-transient reason (eg, no buffer space available), it is silently
-dropped; if the reason is not transient (eg, packet too large), an
-error is returned).
-.Pp
-On the last close of the data device, by default, the interface is
-brought down (as if with
-.Dq ifconfig tun Ns Sy n down ) ;
-if the
-.Dv STAYUP
-bit is set, this is not done. In either case, all queued packets are
-thrown away. (If the interface is up when the data device is not open,
-either because of
-.Dv STAYUP
-or because it was explicitly brought up, output packets are always
-thrown away rather than letting them pile up.)
-.Ss The control interface
-The alternative control interface is a text-based interface designed
-for shell-script or human use; it allows control of many of the things
-that can be done with
-.Fn ioctl
-calls on the data interface, and a few more as well.
-.Pp
-.Fn read Ns s
-on the control interface always return a single line of text (or just
-the beginning of the line, if the buffer passed to
-.Xr read 2
-was too small to take the whole line). The line contains items in the
-general format
-.Do
-.Li item=value
-.Dc ,
-where
-.Li item
-is a keyword and
-.Li value
-is a value appropriate to the keyword. This line is intended for human
-use; programs should use the
-.Fn ioctl
-interface. Here is an actual example (broken because of width
-restrictions):
-.Bd -literal
-unit=0 flags=(open,inited,!rcoll,iaset,!dstaddr,!rwait,!async,
-!nbio,!brdaddr,prepaddr,stayup,suonly,rrwait) type=broadcast
-mtu=1500 coll=0 ipkts=0/0 opkts=0/0 pgrp=0
-.Ed
-.Pp
-Note that the current file offset is ignored for reads, so using a tool like
-.Xr cat 1
-will result in infinite output. Use something more like
-.Dq head\ \&-1
-for command-line use. It is possible to
-.Xr select 2
-for reading on this device, which will indicate that the device is
-readable whenever the state is changed.
-.Pp
-Writes to the control interface are interpreted as modifications to the
-state. Each
-.Fn write
-call is treated separately. The data written is broken at whitespace
-(blanks, tabs, newlines); each resulting fragment has its first
-character examined. If this character is a
-.Ql \&+
-or
-.Ql \&\- ,
-the rest of the fragment is taken as a flag name, and the flag is
-turned on (for
-.Ql \&+ )
-or off (for
-.Ql \&\- ) .
-(Flag names are as generated on reads; they are the same as the
-.Dv TUN_ Ns Em xxx
-constants, with the leading
-.Dv TUN_
-removed and the rest lowercased.) If the first character is
-.Ql t ,
-the second character must be
-.Ql b
-or
-.Ql p ,
-and the interface type is set to
-.Dv IFF_BROADCAST
-or
-.Dv IFF_POINTOPOINT ,
-respectively. If the first character is
-.Ql g
-or
-.Ql m ,
-the rest of the fragment is taken as a number in decimal (possibly with
-a leading \&\- sign) and the result is taken as a new process group,
-for
-.Ql g
-or MTU, for
-.Ql m .
-(The MTU must not be less than 1; attempts to set it so return
-.Er EIO . )
-.Pp
-This interface is useful for command-line reconfiguration, such as
-setting the interface type at boot time, with
-.Sh SEE ALSO
-.Xr inet 4 ,
-.Xr intro 4
-.Sh BUGS
-The
-.Dv SUONLY
-bit is a botch, especially since the control interface, which is never
-restricted by the kernel, can change it. Access control really should
-be handled by the permission bits on the
-.Pa /dev
-entries for the data and control devices; this bit is a historical
-artifact.
-.Pp
-The process-group values for
-.Dv SIGIO
-signals should be checked; as it stands, the driver can be used (by
-anyone who can open the control or data device) to send any desired
-signal to an arbitrary process or process group. (Until this is fixed,
-you should be careful to set the permisison bits to allow only root to
-open the control device, and either do the same for the data device or
-leave the
-.Dv SUONLY
-bit set.)