summaryrefslogtreecommitdiff
path: root/static/freebsd/man4/divert.4 3.html
diff options
context:
space:
mode:
Diffstat (limited to 'static/freebsd/man4/divert.4 3.html')
-rw-r--r--static/freebsd/man4/divert.4 3.html178
1 files changed, 178 insertions, 0 deletions
diff --git a/static/freebsd/man4/divert.4 3.html b/static/freebsd/man4/divert.4 3.html
new file mode 100644
index 00000000..1e20fc6d
--- /dev/null
+++ b/static/freebsd/man4/divert.4 3.html
@@ -0,0 +1,178 @@
+<table class="head">
+ <tr>
+ <td class="head-ltitle">DIVERT(4)</td>
+ <td class="head-vol">Device Drivers Manual</td>
+ <td class="head-rtitle">DIVERT(4)</td>
+ </tr>
+</table>
+<div class="manual-text">
+<section class="Sh">
+<h1 class="Sh" id="NAME"><a class="permalink" href="#NAME">NAME</a></h1>
+<p class="Pp"><code class="Nm">divert</code> &#x2014; <span class="Nd">kernel
+ packet diversion mechanism</span></p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="SYNOPSIS"><a class="permalink" href="#SYNOPSIS">SYNOPSIS</a></h1>
+<p class="Pp"><code class="In">#include
+ &lt;<a class="In">sys/types.h</a>&gt;</code>
+ <br/>
+ <code class="In">#include &lt;<a class="In">sys/socket.h</a>&gt;</code>
+ <br/>
+ <code class="In">#include &lt;<a class="In">netinet/in.h</a>&gt;</code></p>
+<p class="Pp"><var class="Ft">int</var>
+ <br/>
+ <code class="Fn">socket</code>(<var class="Fa" style="white-space: nowrap;">PF_DIVERT</var>,
+ <var class="Fa" style="white-space: nowrap;">SOCK_RAW</var>,
+ <var class="Fa" style="white-space: nowrap;">0</var>);</p>
+<p class="Pp">To enable support for divert sockets, place the following lines in
+ the kernel configuration file:</p>
+<div class="Bd Pp Bd-indent"><code class="Cd">options IPDIVERT</code></div>
+<p class="Pp">Alternatively, to load the driver as a module at boot time, add
+ the following lines into the <a class="Xr">loader.conf(5)</a> file:</p>
+<div class="Bd Pp Bd-indent Li">
+<pre>ipdivert_load=&quot;YES&quot;</pre>
+</div>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="DESCRIPTION"><a class="permalink" href="#DESCRIPTION">DESCRIPTION</a></h1>
+<p class="Pp">Divert sockets allow to intercept and re-inject packets flowing
+ through the <a class="Xr">ipfw(4)</a> and <a class="Xr">pf(4)</a> firewalls.
+ A divert socket can be bound to a specific <code class="Nm">divert</code>
+ port via the <a class="Xr">bind(2)</a> system call. The sockaddr argument
+ shall be sockaddr_in with sin_port set to the desired value. Note that the
+ <code class="Nm">divert</code> port has nothing to do with TCP/UDP ports. It
+ is just a cookie whose value depends on the firewall in use. For
+ <a class="Xr">ipfw(4)</a> this is the number of the rule which diverted the
+ packet; for <a class="Xr">pf(4)</a> this is a value which indicates the
+ original direction through the firewall of the diverted packet. A divert
+ socket bound to a divert port will receive all packets diverted to that port
+ by the firewall. Packets may also be written to a divert port, in which case
+ they re-enter firewall processing at the next rule.</p>
+<p class="Pp">By reading from and writing to a divert socket, matching packets
+ can be passed through an arbitrary ``filter'' as they travel through the
+ host machine, special routing tricks can be done, etc.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="READING_PACKETS"><a class="permalink" href="#READING_PACKETS">READING
+ PACKETS</a></h1>
+<p class="Pp">Packets are diverted either as they are ``incoming'' or
+ ``outgoing.'' Incoming packets are diverted after reception on an IP
+ interface, whereas outgoing packets are diverted before next hop
+ forwarding.</p>
+<p class="Pp">Diverted packets may be read unaltered via
+ <a class="Xr">read(2)</a>, <a class="Xr">recv(2)</a>, or
+ <a class="Xr">recvfrom(2)</a>. In the latter case, the address returned will
+ have its port set to some tag supplied by the packet diverter, (usually the
+ cookie described above) and the IP address set to the (first) address of the
+ interface on which the packet was received (if the packet was incoming) or
+ <code class="Dv">INADDR_ANY</code> (if the packet was outgoing). The
+ interface name (if defined for the packet) will be placed in the 8 bytes
+ following the address, if it fits.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="WRITING_PACKETS"><a class="permalink" href="#WRITING_PACKETS">WRITING
+ PACKETS</a></h1>
+<p class="Pp">Writing to a divert socket is similar to writing to a raw IP
+ socket; the packet is injected ``as is'' into the normal kernel IP packet
+ processing using <a class="Xr">sendto(2)</a> and minimal error checking is
+ done. Packets are distinguished as either incoming or outgoing. If
+ <a class="Xr">sendto(2)</a> is used with a destination IP address of
+ <code class="Dv">INADDR_ANY</code>, then the packet is treated as if it were
+ outgoing, i.e., destined for a non-local address. Otherwise, the packet is
+ assumed to be incoming and full packet routing is done.</p>
+<p class="Pp">In the latter case, the IP address specified must match the
+ address of some local interface, or an interface name must be found after
+ the IP address. If an interface name is found, that interface will be used
+ and the value of the IP address will be ignored (other than the fact that it
+ is not <code class="Dv">INADDR_ANY</code>). This is to indicate on which
+ interface the packet &#x201C;arrived&#x201D;.</p>
+<p class="Pp">Normally, packets read as incoming should be written as incoming;
+ similarly for outgoing packets. When reading and then writing back packets,
+ passing the same socket address supplied by <a class="Xr">recvfrom(2)</a>
+ unmodified to <a class="Xr">sendto(2)</a> simplifies things (see below).</p>
+<p class="Pp" id="after">The port part of the socket address passed to the
+ <a class="Xr">sendto(2)</a> contains a tag that should be meaningful to the
+ diversion module. In the case of <a class="Xr">ipfw(8)</a> the tag is
+ interpreted as the rule number
+ <a class="permalink" href="#after"><i class="Em">after which</i></a> rule
+ processing should restart.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="LOOP_AVOIDANCE"><a class="permalink" href="#LOOP_AVOIDANCE">LOOP
+ AVOIDANCE</a></h1>
+<p class="Pp">Packets written into a divert socket (using
+ <a class="Xr">sendto(2)</a>) re-enter the packet filter at the rule number
+ following the tag given in the port part of the socket address, which is
+ usually already set at the rule number that caused the diversion (not the
+ next rule if there are several at the same number). If the 'tag' is altered
+ to indicate an alternative re-entry point, care should be taken to avoid
+ loops, where the same packet is diverted more than once at the same
+ rule.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="DETAILS"><a class="permalink" href="#DETAILS">DETAILS</a></h1>
+<p class="Pp">If a packet is diverted but no socket is bound to the port, or if
+ <code class="Dv">IPDIVERT</code> is not enabled or loaded in the kernel, the
+ packet is dropped.</p>
+<p class="Pp">Incoming packet fragments which get diverted are fully reassembled
+ before delivery; the diversion of any one fragment causes the entire packet
+ to get diverted. If different fragments divert to different ports, then
+ which port ultimately gets chosen is unpredictable.</p>
+<p class="Pp">Note that packets arriving on the divert socket by the
+ <a class="Xr">ipfw(8)</a> <code class="Cm">tee</code> action are delivered
+ as-is and packet fragments do not get reassembled in this case.</p>
+<p class="Pp">Packets are received and sent unchanged, except that packets read
+ as outgoing have invalid IP header checksums, and packets written as
+ outgoing have their IP header checksums overwritten with the correct value.
+ Packets written as incoming and having incorrect checksums will be dropped.
+ Otherwise, all header fields are unchanged (and therefore in network
+ order).</p>
+<p class="Pp">Creating a <code class="Nm">divert</code> socket requires
+ super-user access.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="ERRORS"><a class="permalink" href="#ERRORS">ERRORS</a></h1>
+<p class="Pp">Writing to a divert socket can return these errors, along with the
+ usual errors possible when writing raw packets:</p>
+<dl class="Bl-tag">
+ <dt id="EINVAL">[<a class="permalink" href="#EINVAL"><code class="Er">EINVAL</code></a>]</dt>
+ <dd>The packet had an invalid header, or the IP options in the packet and the
+ socket options set were incompatible.</dd>
+ <dt id="EADDRNOTAVAIL">[<a class="permalink" href="#EADDRNOTAVAIL"><code class="Er">EADDRNOTAVAIL</code></a>]</dt>
+ <dd>The destination address contained an IP address not equal to
+ <code class="Dv">INADDR_ANY</code> that was not associated with any
+ interface.</dd>
+</dl>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="SEE_ALSO"><a class="permalink" href="#SEE_ALSO">SEE
+ ALSO</a></h1>
+<p class="Pp"><a class="Xr">bind(2)</a>, <a class="Xr">recvfrom(2)</a>,
+ <a class="Xr">sendto(2)</a>, <a class="Xr">socket(2)</a>,
+ <a class="Xr">ipfw(4)</a>, <a class="Xr">pf(4)</a>,
+ <a class="Xr">ipfw(8)</a></p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="AUTHORS"><a class="permalink" href="#AUTHORS">AUTHORS</a></h1>
+<p class="Pp"><span class="An">Archie Cobbs</span>
+ &lt;<a class="Mt" href="mailto:archie@FreeBSD.org">archie@FreeBSD.org</a>&gt;,
+ Whistle Communications Corp.</p>
+</section>
+<section class="Sh">
+<h1 class="Sh" id="BUGS"><a class="permalink" href="#BUGS">BUGS</a></h1>
+<p class="Pp">This is an attempt to provide a clean way for user mode processes
+ to implement various IP tricks like address translation, but it could be
+ cleaner.</p>
+<p class="Pp">It is questionable whether incoming fragments should be
+ reassembled before being diverted. For example, if only some fragments of a
+ packet destined for another machine do not get routed through the local
+ machine, the packet is lost. This should probably be a settable socket
+ option in any case.</p>
+</section>
+</div>
+<table class="foot">
+ <tr>
+ <td class="foot-date">January 23, 2026</td>
+ <td class="foot-os">FreeBSD 15.0</td>
+ </tr>
+</table>