Move some stuff that applies to all firewalls to Concepts section.

Finish modernization pass through IPF Rulesets.
Next commit will look at the provided examples.

Sponsored by: iXsystems
This commit is contained in:
Dru Lavigne 2014-02-22 01:04:38 +00:00
parent 49e2f26cd5
commit e77439a35c
Notes: svn2git 2020-12-08 03:00:23 +00:00
svn path=/head/; revision=44022

View file

@ -196,11 +196,28 @@
<para>Security can be tightened further using a <quote>stateful
firewall</quote>. This type of firewall keeps track of open
connections and only allows traffic which either matches an
existing connection or opens a new, allowed connection. The
disadvantage of a stateful firewall is that it can be vulnerable
to Denial of Service (<acronym>DoS</acronym>) attacks if a lot
of new connections are opened very fast. Most firewalls use a
combination of stateful and non-stateful behavior.</para>
existing connection or opens a new, allowed connection.</para>
<para>Stateful filtering treats traffic as a bi-directional
exchange of packets comprising a session. When state is specified on a matching rule
the firewall dynamically generates
internal rules for each anticipated packet being exchanged
during the session. It has sufficient matching capabilities
to determine if a packet is valid for a session. Any packets
that do not properly fit the session template are
automatically rejected.</para>
<para>When the session completes, it is removed from the
dynamic state table.</para>
<para>Stateful filtering allows one to focus on blocking/passing
new sessions. If the new session is passed, all its
subsequent packets are allowed automatically and any impostor
packets are automatically rejected. If a new session is
blocked, none of its subsequent packets are allowed. Stateful
filtering provides advanced matching abilities capable of
defending against the flood of different attack methods
employed by attackers.</para>
<warning>
<para>When working with the firewall rules, be <emphasis>very
@ -1682,7 +1699,7 @@ ipnat_rules="/etc/ipnat.rules" # rules definition file for ipnat</programlist
</sect2>
<sect2>
<title>IPF Rulesets</title>
<title><application>IPF</application> Rulesets</title>
<indexterm>
<primary><application>IPFILTER</application></primary>
@ -1692,30 +1709,37 @@ ipnat_rules="/etc/ipnat.rules" # rules definition file for ipnat</programlist
<para>This section describes the <application>IPF</application> rule syntax
used to create stateful rules. When creating rules, keep in
mind that the default way in which filter rules are applied
is for the <emphasis>last matching rule</emphasis> to be
used. Even if the first rule to match a packet is a
mind that unless the <literal>quick</literal> keyword appears
in a rule, every rule is read
in order, with the <emphasis>last matching rule</emphasis>
being the one that is applied. This means that even if the first rule to match a packet is a
<literal>pass</literal>, if there is a later matching rule
that is a <literal>block</literal>, the packet will be dropped.
Refer to &man.ipf.5; for more details about rule syntax.</para>
Sample rulesets can be found in
<filename class="directory">/usr/share/examples/ipfilter</filename>.</para>
<para>When creating rules, a <literal>#</literal> character is used to mark the
start of a comment and may appear at the end of a rule, to explain its function,
start of a comment and may appear at the end of a rule, to explain that rule's function,
or on its own line. Any blank lines are ignored.</para>
<para>The keywords which are used in rules must be written in a specific
order, from left to right. Some keywords have sub-options which may be
order, from left to right. Some keywords are mandatory while
others are optional. Some keywords have sub-options which may be
keywords themselves and also include more sub-options. The
keyword order is as follows:</para>
<!-- This section is probably wrong. See the OpenBSD flag -->
<!-- What is the "OpenBSD flag"? Reference please -->
keyword order is as follows, where the words shown in uppercase
represent a variable and the words shown in lowercase must
precede the variable that follows it:</para>
<para><replaceable>ACTION DIRECTION OPTIONS proto PROTO_TYPE
from SRC_ADDR SRC_PORT to DST_ADDR DST_PORT OBJECT PORT_NUM TCP_FLAG
STATEFUL</replaceable></para>
from SRC_ADDR SRC_PORT to DST_ADDR DST_PORT TCP_FLAG|ICMP_TYPE
keep state STATE</replaceable></para>
<para>This section describes each keyword and its options.</para>
<para>This section describes each of these keywords and their options. It
is not an exhaustive list of every possible option. Refer to
&man.ipf.5; for a complete description of the rule
syntax that can be used when creating
<application>IPF</application> rules and examples for using
each keyword.</para>
<variablelist>
<varlistentry>
@ -1807,6 +1831,10 @@ ipnat_rules="/etc/ipnat.rules" # rules definition file for ipnat</programlist
this option is recommended so that only the triggering
packet is logged and not every packet which matches the
stateful connection.</para>
<para>Additional options are available to specify
error return messages. Refer to &man.ipf.5; for more details.</para>
</listitem>
</varlistentry>
@ -1814,15 +1842,17 @@ ipnat_rules="/etc/ipnat.rules" # rules definition file for ipnat</programlist
<term>PROTO_TYPE</term>
<listitem>
<para>The protocol type is optional. However, it is
mandatory if the rule needs to specify a a SRC_PROTO or
a DST_PROTO as it defines the type of protocol. When
mandatory if the rule needs to specify a a SRC_PORT or
a DST_PORT as it defines the type of protocol. When
specifying the type of protocol, use the
<literal>proto</literal> keyword followed by either a
protocol number or name from
<filename>/etc/protocols</filename>.
Example keywords include <literal>tcp</literal>,
Example protocol names include <literal>tcp</literal>,
<literal>udp</literal>, or
<literal>icmp</literal>.</para>
<literal>icmp</literal>. If PROTO_TYPE is specified but
no SRC_PORT or DST_PORT is specified, all port numbers
for that protocol will match that rule.</para>
</listitem>
</varlistentry>
@ -1836,173 +1866,125 @@ ipnat_rules="/etc/ipnat.rules" # rules definition file for ipnat</programlist
<acronym>CIDR</acronym> mask, an address pool, or the
keyword <literal>all</literal>. Refer to &man.ipf.5;
for examples.</para>
</listitem>
</varlistentry>
<varlistentry>
<term>SRC_PORT</term>
<listitem>
<para><literal>proto</literal> is the subject keyword
which must include one of its corresponding keyword
sub-option values. The sub-option indicates a specific
protocol to be matched against.</para>
<para><literal>tcp/udp | udp | tcp | icmp</literal> or any
protocol names found in
<filename>/etc/protocols</filename> are recognized and
may be used. The special protocol keyword
<literal>tcp/udp</literal> may be used to match either a
<acronym>TCP</acronym> or a <acronym>UDP</acronym>
packet, and has been added as a convenience to save
duplication of otherwise identical rules.</para>
</listitem>
</varlistentry>
<varlistentry>
<term>DST_ADDR</term>
<listitem>
<para>The <literal>all</literal> keyword is equivalent to
<quote>from any to any</quote> with no other match
parameters.</para>
<para><literal>from | to src to dst</literal>: the
<literal>from</literal> and <literal>to</literal>
keywords are used to match against IP addresses. Rules
must specify <emphasis>both</emphasis> the source and
destination parameters. <literal>any</literal> is a
special keyword that matches any IP address. Examples
include: <literal>from any to any</literal>,
<literal>from 0.0.0.0/0 to any</literal>, <literal>from
any to 0.0.0.0/0</literal>, <literal>from 0.0.0.0 to
any</literal>, and <literal>from any to
0.0.0.0</literal>.</para>
<para>There is no way to match ranges of IP addresses
<para>There is no way to match ranges of <acronym>IP</acronym> addresses
which do not express themselves easily using the dotted
numeric form / mask-length notation. The
<package>net-mgmt/ipcalc</package> port may be used to
ease the calculation. Additional information is
<package>net-mgmt/ipcalc</package> package or port may be used to
ease the calculation of the <acronym>CIDR</acronym> mask. Additional information is
available at the utility's web page: <uri
xlink:href="http://jodies.de/ipcalc">http://jodies.de/ipcalc</uri>.</para>
</listitem>
</varlistentry>
<varlistentry>
<term>DST_PORT</term>
<term>SRC_PORT</term>
<listitem>
<para>If a port match is included, for either or both of
source and destination, it is only applied to
<acronym>TCP</acronym> and <acronym>UDP</acronym>
packets. When composing port comparisons, either the
service name from <filename>/etc/services</filename> or
an integer port number may be used. When the port
appears as part of the <literal>from</literal> object,
it matches the source port number. When it appears as
part of the <literal>to</literal> object, it matches the
destination port number. An example usage is
<literal>from any to any port = 80</literal></para>
<para>The port number of the source is optional. However,
if it is used, it requires PROTO_TYPE to be first defined in
the rule. The port number must also be preceded by the
<literal>proto</literal> keyword.</para>
<para>Single port comparisons may be done in a number of
ways, using a number of different comparison operators.
Instead of the <literal>=</literal> shown in the example
above, the following operators may be used:
<literal>!=</literal>, <literal>&lt;</literal>,
<literal>&gt;</literal>, <literal>&lt;=</literal>,
<literal>&gt;=</literal>, <literal>eq</literal>,
<literal>ne</literal>, <literal>lt</literal>,
<literal>gt</literal>, <literal>le</literal>, and
<literal>ge</literal>.</para>
<para>A number of different comparison operators are supported:
<literal>=</literal> (equal to),
<literal>!=</literal> (not equal to),
<literal>&lt;</literal> (less than),
<literal>&gt;</literal> (greater than),
<literal>&lt;=</literal> (less than or equal to), and
<literal>&gt;=</literal> (greater than or equal to).
</para>
<para>To specify port ranges, place the two port numbers
between <literal>&lt;&gt;</literal> or
<literal>&gt;&lt;</literal></para>
between <literal>&lt;&gt;</literal> (less than and greater than ),
<literal>&gt;&lt;</literal> (greater than and less than ), or
<literal>:</literal> (greater than or equal to and
less than or equal to).</para>
</listitem>
</varlistentry>
<varlistentry>
<term><acronym>TCP</acronym>_FLAG</term>
<term>DST_ADDR</term>
<listitem>
<para>Flags are only effective for <acronym>TCP</acronym>
filtering. The letters represent one of the possible
flags that can be matched against the
<acronym>TCP</acronym> packet header.</para>
<para>The modernized rules processing logic uses the
<literal>flags S</literal> parameter to identify the TCP
session start request.</para>
<para>The <literal>to</literal> keyword is mandatory and
is followed by a keyword which represents the destination of
the packet. Similar to SRC_ADDR, it can be a hostname, an
<acronym>IP</acronym> address followed by the
<acronym>CIDR</acronym> mask, an address pool, or the
keyword <literal>all</literal>.</para>
</listitem>
</varlistentry>
<varlistentry>
<term>STATEFUL</term>
<term>DST_PORT</term>
<listitem>
<para><literal>keep state</literal> indicates that on a
pass rule, any packets that match the rules selection
parameters should activate the stateful filtering
facility.</para>
<para>Similar to SRC_PORT, the port number of the destination is optional. However,
if it is used, it requires PROTO_TYPE to be first defined in
the rule. The port number must also be preceded by the
<literal>proto</literal> keyword.</para>
</listitem>
</varlistentry>
</variablelist>
</sect2>
<sect2>
<title>Stateful Filtering</title>
<varlistentry>
<term>TCP_FLAG|ICMP_TYPE</term>
<listitem>
<para>If <literal>tcp</literal> is specifed as the PROTO_TYPE, flags
can be specified as letters, where each letter represents one of the possible
<acronym>TCP</acronym> flags used to determine
the state of a connection. Possible values
are: <literal>S</literal> (SYN),
<literal>A</literal> (ACK),
<literal>P</literal> (PSH),
<literal>F</literal> (FIN),
<literal>U</literal> (URG),
<literal>R</literal> (RST),
<literal>C</literal> (CWN), and
<literal>E</literal> (ECN).</para>
<indexterm>
<primary><application>IPFILTER</application></primary>
<para>If <literal>icmp</literal> is specifed as the PROTO_TYPE,
the <acronym>ICMP</acronym> type to match can be
specified. Refer to &man.ipf.5; for the allowable types.</para>
</listitem>
</varlistentry>
<secondary>stateful filtering</secondary>
</indexterm>
<!-- XXX: duplicated -->
<para>Stateful filtering treats traffic as a bi-directional
exchange of packets comprising a session. When activated,
<literal>keep-state</literal> dynamically generates
internal rules for each anticipated packet being exchanged
during the session. It has sufficient matching capabilities
to determine if a packet is valid for a session. Any packets
that do not properly fit the session template are
automatically rejected.</para>
<para>IPF stateful filtering will also allow
<acronym>ICMP</acronym> packets related to an existing
<acronym>TCP</acronym> or <acronym>UDP</acronym> session. So,
if an <acronym>ICMP</acronym> type 3 code 4 packet is a
response in a session started by a keep state rule, it will
automatically be allowed. Any packet that IPF can be certain
<varlistentry>
<term>STATE</term>
<listitem>
<para>If a <literal>pass</literal> rule contains
<literal>keep state</literal>,
<application>IPF</application> will add an entry to its
dynamic state table and allow subsequent packets that
match the connection.
<application>IPF</application> can track state for
<acronym>TCP</acronym>, <acronym>UDP</acronym>, and
<acronym>ICMP</acronym> sessions. Any packet that <application>IPF</application> can be certain
is part of an active session, even if it is a different
protocol, will be allowed.</para>
<para>Packets destined to go out through the interface connected
<para>In <application>IPF</application>, packets destined to go out through the interface connected
to the public Internet are first checked against the dynamic
state table. If the packet matches the next expected packet
comprising an active session conversation, it exits the
firewall and the state of the session conversation flow is
updated in the dynamic state table. Packets that do not
belong to an already active session, are checked against the
outbound ruleset.</para>
<para>Packets coming in from the interface connected to the
belong to an already active session are checked against the
outbound ruleset. Packets coming in from the interface connected to the
public Internet are first checked against the dynamic state
table. If the packet matches the next expected packet
comprising an active session, it exits the firewall and the
state of the session conversation flow is updated in the
dynamic state table. Packets that do not belong to an already
active session, are checked against the inbound
active session are checked against the inbound
ruleset.</para>
<para>When the session completes, it is removed from the
dynamic state table.</para>
<para>Stateful filtering allows one to focus on blocking/passing
new sessions. If the new session is passed, all its
subsequent packets are allowed automatically and any impostor
packets are automatically rejected. If a new session is
blocked, none of its subsequent packets are allowed. Stateful
filtering provides advanced matching abilities capable of
defending against the flood of different attack methods
employed by attackers.</para>
<para>Several keywords can be added after
<literal>keep state</literal>. If used, these keywords set
various options that control stateful filtering, such as
setting connection limits or connection age. Refer to
&man.ipf.5; for the list of available options and their
descriptions.</para>
</listitem>
</varlistentry>
</variablelist>
</sect2>
<sect2>