PF Rules in order, but apparently not?

This one should be an easy one, but I cannot for the life of me find the rule that's ahead of the rdr's. Mostly because I'm pretty dang sure there just isn't. In fact, no matter where I place the rdr I'm getting an ordering error.
And yes, it's the spamd example lifted straight from the handbook.

Code:
#if_pub="vtnet0"
#if_priv="vtnet1"
if_pub="vmx3f0"
if_priv="vmx3f1"

# Clean up our fragments
scrub in on $if_pub all fragment reassemble
scrub in on $if_priv all fragment reassemble
antispoof for $if_pub
antispoof for $if_priv

set skip on lo0

######################################################################
## Global Tables
######################################################################
# Use /X/X/X/X/* autoload
table <root_net> { 10.X.X.X/23, 10.X.X.X/24 }
table <root_net6> { 2001:X:X::/48, 2001:X:X:X::/64 }
table <wow_extern> { X.X.X.X }
table <aws_extern> { }

table <ssh_brute> persist
table <ssh6_brute> persist
table <mail_brute> persist
table <mail6_brute> persist

######################################################################
## Global Aliases
######################################################################
mail_access = "{ imaps, pop3s }"
mail_submit = "{ smtp, submission }"
www_access = "{ http, https }"

######################################################################
## Mail and Spam Control
######################################################################
anchor MAIL
table <spamd> persist
table <edrop> persist
table <spamd-white> persist
rdr pass on $if_pub inet proto tcp from <spamd> to \
        $if_pub port smtp -> 127.0.0.1 port 8025
rdr pass on $if_pub inet proto tcp from !<spamd-white> to \
        $if_pub port smtp -> 127.0.0.1 port 8025
block drop in quick on $if_pub from <edrop> to any
block drop out quick on $if_pub from <edrop> to any

######################################################################
## Acceptable Outgoing Traffic
######################################################################
anchor OUTPUT
pass out quick     on $if_pub inet proto udp from $if_pub to any port domain
pass out quick log on $if_pub inet proto tcp from $if_pub to any port $mail_submit
pass out quick log on $if_pub inet proto tcp from $if_pub to any port $mail_access
pass out quick log on $if_pub inet proto tcp from $if_pub to any port $www_access
pass out quick log on $if_pub inet proto tcp from $if_pub to any port ssh keep state

pass out quick     on $if_pub inet6 proto udp from $if_pub to any port domain
pass out quick log on $if_pub inet6 proto tcp from $if_pub to any port $mail_submit
pass out quick log on $if_pub inet6 proto tcp from $if_pub to any port $mail_access
pass out quick log on $if_pub inet6 proto tcp from $if_pub to any port $www_access
pass out quick log on $if_pub inet6 proto tcp from $if_pub to any port ssh keep state

pass out quick on $if_pub inet proto udp from $if_pub to any port domain
pass out quick on $if_pub inet proto udp from $if_pub to any port ntp
pass out quick on $if_pub inet6 proto udp from $if_pub to any port domain
pass out quick on $if_pub inet6 proto udp from $if_pub to any port ntp

######################################################################
## Block Brute Force Attempts
######################################################################
anchor BRUTE
block quick from <ssh_brute>
block quick from <ssh6_brute>
block quick from <mail_brute>
block quick from <mail6_brute>
pass inet proto tcp from any to $if_pub port ssh \
        flags S/SA keep state \
        (max-src-conn 10, max-src-conn-rate 5/5, \
        overload <ssh_brute> flush global)
pass inet6 proto tcp from any to $if_pub port ssh \
        flags S/SA keep state \
        (max-src-conn 10, max-src-conn-rate 5/5, \
        overload <ssh6_brute> flush global)
pass inet proto tcp from any to $if_pub port $mail_access \
        flags S/SA keep state \
        (max-src-conn 20, max-src-conn-rate 15/5, \
        overload <mail_brute> flush global)
pass inet6 proto tcp from any to $if_pub port $mail_access \
        flags S/SA keep state \
        (max-src-conn 20, max-src-conn-rate 15/5, \
        overload <mail6_brute> flush global)

Thought it was the tables pulling rules up the order, but nope, wasn't that either. This one's really got me scratching my head now, because no matter where the rdr is placed, same ordering error. I even tried trimming it down to nothing but the rdr and a block drop in on $pub_if from any to any and the same error.
 
The anchor MAIL is probably causing it.

Code:
     nat-anchor <name>
           Evaluates the nat rules in the specified anchor.

     rdr-anchor <name>
           Evaluates the rdr rules in the specified anchor.

     binat-anchor <name>
           Evaluates the binat rules in the specified anchor.

     anchor <name>
           Evaluates the filter rules in the specified anchor.
 
The anchor MAIL is probably causing it.

Code:
     nat-anchor <name>
           Evaluates the nat rules in the specified anchor.

     rdr-anchor <name>
           Evaluates the rdr rules in the specified anchor.

     binat-anchor <name>
           Evaluates the binat rules in the specified anchor.

     anchor <name>
           Evaluates the filter rules in the specified anchor.
I can confirm. :) Played a bit with the config file, and solved the rules order problem having both anchors after the redirections.
 
Yep, it's the anchor. It has so been one of those weeks. At least now I can get back to trying to figure out why the heck the pass out ssh rule isn't being hit. :(
 
Back
Top