PF Table Loading in PF Issues

Good afternoon... I've got a FreeBSD environment running 13.1-RELEASE and 16 GB RAM... I'm attempting to implement some geo-ip blocking which involves having some fairly large tables I'm trying to load into PF... I've got everything working for the most part, but PF won't load on start, and I feel like it's because the options aren't being processed properly when FreeBSD boots and loads PF. Across my tables I have around 1.5 million IP address records to load in. Initially I hit some limits, so I tuned and am able to load things manually. The pfctl man page says I must define MACROS, then TABLES, then OPTIONS, and so on. So naturally, I do that, and load my macros, then the tables, following by setting the options:

Code:
##########
# MACROS #
##########

ext_if="ena0"

# ADDR1 PUBLIC / PRIVATE PORTS - HOST
external_addr1="1.2.3.4"
public_ports_tcp_addr1="{ 443 }"

##########
# TABLES #
##########

table <blocklist_europe1> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe1"
table <blocklist_europe2> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe2"
table <blocklist_europe3> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe3"
table <blocklist_europe4> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe4"
table <blocklist_europe5> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe5"
table <blocklist_europe6> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe6"
table <blocklist_europe7> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe7"
table <blocklist_europe8> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe8"
table <blocklist_europe9> persist file "/usr/local/etc/pf_lists/pf_blocklist_europe9"

###########
# OPTIONS #
###########

set limit table-entries 2000000
set limit frags 10000
set limit states 25000

When FreeBSD boots, rules are not loaded. If I run pfctl -f /etc/pf.conf, I get the following:

Code:
/etc/pf.conf:24: cannot define table blocklist_europe1: Cannot allocate memory
/etc/pf.conf:25: cannot define table blocklist_europe2: Cannot allocate memory
/etc/pf.conf:26: cannot define table blocklist_europe3: Cannot allocate memory
/etc/pf.conf:27: cannot define table blocklist_europe4: Cannot allocate memory
/etc/pf.conf:28: cannot define table blocklist_europe5: Cannot allocate memory
/etc/pf.conf:29: cannot define table blocklist_europe6: Cannot allocate memory
/etc/pf.conf:30: cannot define table blocklist_europe7: Cannot allocate memory
/etc/pf.conf:31: cannot define table blocklist_europe8: Cannot allocate memory
/etc/pf.conf:32: cannot define table blocklist_europe9: Cannot allocate memory
pfctl: Syntax error in config file: pf rules not loaded

This confused me, as I already set my table-entries value properly (as well as tuned kern.maxdsiz and net.pf.request_maxcount accordingly). So then I said what if I load the options first, then load the rules, and this worked fine:

Code:
root@host ~ # pfctl -Of /etc/pf.conf
root@host ~ # pfctl -f /etc/pf.conf
root@host ~ # pfctl -sa
FILTER RULES:
scrub in all fragment reassemble
pass in quick on ...
pass in quick on ...
pass in quick on ...
block drop in quick from <blocklist_europe1> to any
block drop in quick from <blocklist_europe2> to any
block drop in quick from <blocklist_europe3> to any
block drop in quick from <blocklist_europe4> to any
block drop in quick from <blocklist_europe5> to any
block drop in quick from <blocklist_europe6> to any
block drop in quick from <blocklist_europe7> to any
block drop in quick from <blocklist_europe8> to any
block drop in quick from <blocklist_europe9> to any
...

The options don't appear to be getting set prior to loading the tables. I attempted to move the OPTIONS above the table definitions but the behavior didn't change. At the moment, I'm a little stuck how to configure this such that the PF rules load properly at boot time.

Any advice would be great, thanks!
 
My guess is that your number of entries in your table succeeds the standard limit. You can check your limits with pfctl -sm. You could try to increase the table entries in pf.conf with set limit table-entries 10000000
 
My guess is that your number of entries in your table succeeds the standard limit. You can check your limits with pfctl -sm. You could try to increase the table entries in pf.conf with set limit table-entries 10000000
If you read my question you will see I clearly have the "table-entries" limit defined. I don't know that you read through my question, specifically because my statement is "I feel like it's because the options aren't being processed properly when FreeBSD boots and loads PF". If you look at my third code block, you can clearly see that loading the options first using pftctl, then loading the rules, works fine.

So given that after pfctl -Of /etc/pf.conf, I can properly load the rules using pfctl -f /etc/pf.conf, I'd say I have table-entries set properly.
  1. After a reboot, where the rules don't load properly, a pfctl -s memory shows table-entries very low, some sort of default.
  2. Running pfctl -f /etc/pf.conf (where I have table-entries set properly in pf.conf, see above), it still won't load the rules and states "Cannot allocate memory".
  3. Next, running pfctl -Of /etc/pf.conf to force ONLY loading the options first, THEN immediately running pfctl -f /etc/pf.conf, the rules and tables load properly and all is good.
Obviously, I could create a custom boot script to do the pfctl -Of /etc/pf.conf first then pfctl -f /etc/pf.conf but the purpose of my post to this forum is to call out a potential issue with PF implementation in FreeBSD, or learn that there is an option to do something similar.
 
Just to provide some more info...

After a fresh boot, pfctl -a, and dmesg shows an error trying to load:
Code:
Enabling pf/etc/pf.conf:24: cannot define table blocklist_nonus: Cannot allocate memory
pfctl: Syntax error in config file: pf rules not loaded
/etc/rc: WARNING: Unable to load /etc/pf.conf.

I ran pfctl -s memory to see what the current value of table-entries is, and it differs from what I have set in /etc/pf.conf:
Code:
root@host ~ # pfctl -s memory
states        hard limit   100000
src-nodes     hard limit    10000
frags         hard limit     5000
table-entries hard limit   200000
root@host ~ # cat /etc/pf.conf | grep table-entries
set limit table-entries 1500000

Then I run pfctl -Of /etc/pf.conf to load only the OPTIONS from /etc/pf.conf, and check PF again with pfctl -s memory and now table-entries shows as expects:
Code:
root@host ~ # pfctl -Of /etc/pf.conf
root@host ~ # pfctl -s memory
states        hard limit    25000
src-nodes     hard limit    10000
frags         hard limit    10000
table-entries hard limit  1500000

Finally, I load the rules using pfctl -f /etc/pf.conf and everything loads properly:
Code:
root@host ~ # pfctl -f /etc/pf.conf
root@host ~ # pfctl -T show -t blocklist_nonus | wc -l
 1007709
root@host ~ #

All of this proves to me that I have OPTIONS correct in /etc/pf.conf and that there is an issue with PF not processing the OPTIONS prior to attempting to load the tables. Is there another place that defines the default value for table-entries or something?
 
hm, came to the same conclusion as you did, the assumption seems valid from a non-developers view, which is weird. Maybe someone from the mailing list will respond, or you could try to create a bug. I am sure someone of the developers will chime in and enlighten us, please post the link to the bugreport/mailing list entry here.
 
Back
Top