Technology may have changed in the meantime.
Cheatsheet for the PF firewall (*BSD, macOS/iOS, Solaris, QNX/BlackBerry).
Show rules:
# pfctl -sr
The same, but more verbose:
# pfctl -vsr
Show anchors:
# pfctl -sA
Show anchors recursively:
# pfctl -vsA
Show rules recursively (including anchors):
# pfctl -a '*' -sr
Show anchors within the f2b anchor:
# pfctl -a 'f2b' -sA
Show rules for f2b/sshd anchor:
# pfctl -a 'f2b/sshd' -sr
Show rules recursively within the f2b anchor:
# pfctl -a 'f2b/*' -sr
Show tables:
# pfctl -sT
The same, but more verbose:
# pfctl -vsT
Show tables for f2b/sshd anchor:
# pfctl -a 'f2b/sshd' -sT
Recursively listing tables is not possible.
Show the contents of table <trusted>:
# pfctl -t 'trusted' -Ts
Show the contents of table <f2b-sshd> in the anchor f2b/sshd:
# pfctl -a 'f2b/sshd' -t 'f2b-sshd' -Ts
The same, but more verbose:
# pfctl -a 'f2b/sshd' -t 'f2b-sshd' -vTs
Add an IP address or IP range to table <trusted>:
# pfctl -t 'trusted' -Ta 203.0.113.12 # pfctl -t 'trusted' -Ta 203.0.113.0/24
Delete an IP address or IP range from table <trusted>:
# pfctl -t 'trusted' -Td 203.0.113.12 # pfctl -t 'trusted' -Td 203.0.113.0/24
Empty (flush) table <blocked>:
# pfctl -t 'blocked' -Tf
It may be a good idea to verify the syntax of the configuration file before restarting or reloading the firewall:
# pfctl -n -f /etc/pf.conf
Or, to review the ruleset generated from the new configuration:
# pfctl -n -f /etc/pf.conf -v
Use -vv to display rule and anchor numbers.
Logging
Logging must be enabled explicitly in pf.conf on a per-rule basis; see the PF User’s guide for more info.
Display log in real time:
# tcpdump -tttt -n -e -i pflog0
End output with ^C.
List all log entries for outbound traffic to port 80:
# tcpdump -tttt -n -e -r /var/log/pflog outbound and port 80
The same, but more verbose:
# tcpdump -v -tttt -n -e -r /var/log/pflog outbound and port 80
Get even more verbosity with -vv or -vvv.
Search the log file for a certain IP address:
# tcpdump -tttt -n -e -r /var/log/pflog host 203.0.113.12
The same, but with a compressed log file:
# bunzip2 -c /var/log/pflog.0.bz2 | tcpdump -tttt -n -e -r - host 203.0.113.12
List inbound traffic, except traffic to the Tor relay or Tor directory info:
# tcpdump -tttt -n -e -r /var/log/pflog inbound and not port 9001 and not port 9030
List blocked inbound traffic to the Tor relay:
# tcpdump -tttt -n -e -r /var/log/pflog inbound and dst port 9001 and action block
Since the output of tcpdump is plaintext, it can be further processed by tools like grep, sed, awk, etc.
Find all outgoing traffic that was not initiated by the users with UIDs 53, 123 and 256:
# tcpdump -tttt -n -e -r /var/log/pflog outbound | grep -Ev '\[uid (53|123|256)\]'
Logging of UIDs must be enabled explicitly in pf.conf, e.g.:
pass out log (user) all modulate state
More info:
Note:
When using fail2ban, the f2b anchors should NOT be specified like this in pf.conf:
anchor "f2b/*"
Instead, all anchors should be specified explicitly, otherwise recursive listing won’t work:
anchor f2b { anchor apache-auth anchor dovecot anchor postfix anchor sshd }