A rule set is a group of IPF rules coded to pass or block packets based on the values contained in the packet. The bi-directional exchange of packets between hosts comprises a session conversation. The firewall rule set processes the packet two times, once on its arrival from the public Internet host and again as it leaves for its return trip back to the public Internet host. Each TCP/IP service (IE: telnet, www, mail, etc;) is predefined by its protocol, source and destination IP address, or the source and destination port number. This is the basic selection criteria used to create rules which will pass or block services.
IPF was originally written using a rules processing logic of ‘the last matching rule wins’ and used only stateless types of rules. Over time IPF has been enhanced to include a ‘quick’ option and a stateful ‘keep state’ option which drastically modernized the rules processing logic.
The instructions contained in this section are based on using rules that contain the ‘quick' option and the stateful ‘keep state’ option. This is the basic framework for coding an inclusive firewall rule set.
An inclusive firewall only allows services matching the rules through. This way you can control what services can originate behind the firewall destined for the public Internet and also control the services which can originate from the public Internet accessing your private network. Everything else is blocked and logged by default design. Inclusive firewall rule sets are much more secure than exclusive firewall rule sets and are the only rule set type covered herein.
Installers Note:Warning, when working with the firewall rules, always, always do it from the root console of the system running the firewall or you can end up locking yourself out.
The rule syntax presented here has been simplified to only address the modern stateful rule context and ‘first matching rule wins’ logic. For the complete legacy rule syntax description see the online ‘man ipf’ page at http://www.freebsd.org/cgi/man.cgi?query=ipf&apropos=0&sektion=0&manpath=FreeBSD+5.2-RELEASE+and+Ports&format=html
# is used to mark the start of a comment and may appear at the end of a rule line or on its own line. Blank lines are ignored.
Rules contain keywords. These keywords have to be coded in a specific order from left to right on the line. Keywords are identified in bold type. Some keywords have sub-options which may be keywords themselves and also include more sub-options. Each of the headings in the below syntax has a bold section header which expands on the content.
Syntax = ACTION IN-OUT OPTIONS SELECTION STATEFUL
ACTION = block | pass
IN-OUT = in | out
OPTIONS = log | quick | on interface-name
SELECTION = proto value | source/destination IP | port = number | flags flag-value
Where value = tcp/udp | udp | tcp | icmp
Where source/destination IP = all | from object to object
Where object = IP address | any
Where number = port number
Where flag-value = S
STATEFUL = keep state
The | symbol used in the above syntax means ‘or’.
The action indicates what to do with the packet if it matches the rest of the filter rule. Each rule MUST have an action. The following actions are recognized:
block indicates that the packet should be dropped if the selection parameters match the packet.
pass indicates that the packet should exit the firewall if the selection parameters match the packet.
IN-OUT It is a mandatory requirement that each filter rule explicitly states which side of the I/O it is to be used on. The next keyword must be either in or out and one or the other has to be coded or the rule will not pass syntax check.
in means this rule is being applied against an inbound packet which has just been received on the interface facing the public Internet.
out means this rule is being applied against an outbound packet destined for the interface facing the public Internet.
OPTIONS Must be used in the order shown here.
log indicates that the packet header will be written to the ipl log (as described in the LOGGING section below) if the selection parameters match the packet.
quick indicates that if the selection parameters match the packet, this rule will be the last rule checked, allowing a "short-circuit" path to avoid processing any following rules for this packet. This option is a mandatory requirement for the modernized rules processing logic.
on indicates the interface name to be incorporated into the selection parameters. Interface names are as displayed by ifconfig. Using this option, the rule will only match if the packet is going through that interface in the specified direction (in/out). This option is a mandatory requirement for the modernized rules processing logic.
When a packet is logged, the headers of the packet are written to the IPL packet logging pseudo-device. Immediately following the log keyword, the following qualifiers may be used (in this order):
body indicates that the first 128 bytes of the packet contents will be logged after the headers.
first If the ‘log’ keyword is being used in conjunction with a "keep state" option, it is recommended that this option is also applied so that only the triggering packet is logged and not every packet thereafter which matches the ‘keep state’ information.
The keywords described in this section are used to describe attributes of the packet to be interrogated when determining whether rules match or don't match. There is a keyword subject, and it has sub-option keywords, one of which has to be selected. The following general-purpose attributes are provided for matching and must be used in this order:
proto value Proto is the subject keyword; it must be coded along with one of it’s corresponding keyword sub-option values. The value allows a specific protocol to be matched against it. This option is a mandatory requirement for the modernized rules processing logic.
Valid sub-option value keywords are:
tcp/udp | udp | tcp | icmp or any protocol names found in /etc/protocols are recognized and may be used. The special protocol keyword tcp/udp may be used to match either a TCP or a UDP packet, and has been added as a convenience to save duplication of otherwise identical rules.
source/destination IP =
all keyword is essentially a synonym for "from any to any" with no other match parameters.
from src to dst The from and to keywords are used to match against IP addresses. Rules must specify BOTH source and destination parameters. ‘any’ is a special keyword that matches any IP address. As in "from any to any" or
"from 0.0.0.0/0 to any" or "from any to 0.0.0.0/0 " or
"from 0.0.0.0 to any" or "from any to 0.0.0.0 "
IP addresses may be specified as a dotted IP address numeric form/mask-length, or as a single dotted IP address numeric form.
There isn't a way to match ranges of IP addresses which do not express themselves easily as mask-length. See this link for help on writing mask-length.http://jodies.de/ipcalc
port If a port match is included, for either or both of the source and destination, then it is only applied to TCP and UDP packets. When composing port comparisons, either the service name from /etc/services or an integer port number may be used. When the port appears as part of the from object, it matches the source port number; when it appears as part of the to object, it matches the destination port number. The use of the port option with the ‘to’ object is a mandatory requirement for the modernized rules processing logic.
As in ‘from any to any port = 80’
Port comparisons may be done in a number of forms, with a number of comparison operators, or port ranges may be specified.
port "=" | "!=" | "<" | ">" | "<=" | ">=" | "eq" | "ne" | "lt" | "gt" | "le" | "ge".
To specify port ranges, port "<>" | "><" .
Following the source and destination matching parameters, the following two parameters are mandatory requirements for the modernized rules processing logic.
flags is only effective for TCP filtering. The letters represents one of the possible flags that can be interrogated in the TCP packet header.
The modernized rules processing logic uses the ‘flags S’ parameter to identify the tcp session start request.
keep state indicates that on a pass rule, any packets that match the rules selection parameters are to activate the stateful filtering facility.
This option is a mandatory requirement for the modernized rules processing logic.
Stateful filtering treats traffic as a bi-directional exchange of packets comprising a session conversation. When activated keep-state dynamically generates internal rules for each anticipated packet being exchanged during the bi-directional session conversation. It has the interrogation abilities to determine if the session conversation between the originating sender and the destination are following the valid procedure of bi-directional packet exchange. Any packets that do not properly fit the session conversation template are automatically rejected as impostors.
Keep state will also allow ICMP packets related to a TCP or UDP session through. So if you get ICMP type 3 code 4 in response to some web surfing allowed out by a keep state rule, they will be automatically allowed in. Any packet that IPF can be certain is part of an active session, even if it's a different protocol, will be let in.
What happens is:
Packets destined to go out through the NIC connected to the public Internet are first checked against the dynamic state table. If the packet matches the next expected packet of that active session conversation, then it exits the firewall and the state of the session conversation flow is updated in the dynamic state table. The remaining packets get checked against the outbound rule set.
Packets coming in through the NIC connected to the public Internet are first checked against the dynamic state table. If the packet matches the next expected packet of that active session conversation, then it exits the firewall and the state of the session conversation flow is updated in the dynamic state table. The remaining packets get checked against the inbound rule set.
When the conversation completes, it's removed from the dynamic state table.
Stateful filtering allows you to focus on blocking/passing new sessions. If the new session is passed, all its subsequent packets will be allowed through automatically and any impostors automatically rejected. If a new session is blocked, none of its subsequent packets will be allowed through. Stateful filtering has technically advanced interrogation abilities capable of defending against the flood of different attack methods currently employed by attackers.
This FreeBSD Installer Guide is an public domain HOW-TO. This content may be reproduced, in any form or by any means, and used by all without permission in writing from the author.