git: 029532e77b92 - main - pf: also allocate ethernet anchors from a UMA zone
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Tue, 05 Aug 2025 22:28:11 UTC
The branch main has been updated by kp:
URL: https://cgit.FreeBSD.org/src/commit/?id=029532e77b92d0c74976e3e3fc79a0ca5e0e3dc0
commit 029532e77b92d0c74976e3e3fc79a0ca5e0e3dc0
Author: Kristof Provost <kp@FreeBSD.org>
AuthorDate: 2025-07-30 15:22:36 +0000
Commit: Kristof Provost <kp@FreeBSD.org>
CommitDate: 2025-08-05 22:27:15 +0000
pf: also allocate ethernet anchors from a UMA zone
As per the previous commit, ensure we can't endlessly allocate ethernet
anchors.
Sponsored by: Rubicon Communications, LLC ("Netgate")
---
sbin/pfctl/pfctl.c | 1 +
sys/net/pfvar.h | 2 ++
sys/netpfil/pf/pf.c | 7 +++++++
sys/netpfil/pf/pf.h | 3 ++-
sys/netpfil/pf/pf_ioctl.c | 1 +
sys/netpfil/pf/pf_norm.c | 1 +
sys/netpfil/pf/pf_ruleset.c | 8 ++++----
7 files changed, 18 insertions(+), 5 deletions(-)
diff --git a/sbin/pfctl/pfctl.c b/sbin/pfctl/pfctl.c
index a96eed7fc94a..ae772395e0ef 100644
--- a/sbin/pfctl/pfctl.c
+++ b/sbin/pfctl/pfctl.c
@@ -184,6 +184,7 @@ static const struct {
{ "frags", PF_LIMIT_FRAGS },
{ "table-entries", PF_LIMIT_TABLE_ENTRIES },
{ "anchors", PF_LIMIT_ANCHORS },
+ { "eth-anchors", PF_LIMIT_ETH_ANCHORS },
{ NULL, 0 }
};
diff --git a/sys/net/pfvar.h b/sys/net/pfvar.h
index c933ff395992..c397f0b67896 100644
--- a/sys/net/pfvar.h
+++ b/sys/net/pfvar.h
@@ -2340,6 +2340,8 @@ VNET_DECLARE(uma_zone_t, pf_state_scrub_z);
#define V_pf_state_scrub_z VNET(pf_state_scrub_z)
VNET_DECLARE(uma_zone_t, pf_anchor_z);
#define V_pf_anchor_z VNET(pf_anchor_z)
+VNET_DECLARE(uma_zone_t, pf_eth_anchor_z);
+#define V_pf_eth_anchor_z VNET(pf_eth_anchor_z)
extern void pf_purge_thread(void *);
extern void pf_unload_vnet_purge(void);
diff --git a/sys/netpfil/pf/pf.c b/sys/netpfil/pf/pf.c
index 408d0d3c96e3..19702fde7d22 100644
--- a/sys/netpfil/pf/pf.c
+++ b/sys/netpfil/pf/pf.c
@@ -1262,6 +1262,13 @@ pf_initialize(void)
uma_zone_set_max(V_pf_anchor_z, PF_ANCHOR_HIWAT);
uma_zone_set_warning(V_pf_anchor_z, "PF anchor limit reached");
+ V_pf_eth_anchor_z = uma_zcreate("pf Ethernet anchors",
+ sizeof(struct pf_keth_anchor), NULL, NULL, NULL, NULL,
+ UMA_ALIGN_PTR, 0);
+ V_pf_limits[PF_LIMIT_ETH_ANCHORS].zone = V_pf_eth_anchor_z;
+ uma_zone_set_max(V_pf_eth_anchor_z, PF_ANCHOR_HIWAT);
+ uma_zone_set_warning(V_pf_eth_anchor_z, "PF Ethernet anchor limit reached");
+
/* ALTQ */
TAILQ_INIT(&V_pf_altqs[0]);
TAILQ_INIT(&V_pf_altqs[1]);
diff --git a/sys/netpfil/pf/pf.h b/sys/netpfil/pf/pf.h
index a41443fb9404..51b3fd6390e1 100644
--- a/sys/netpfil/pf/pf.h
+++ b/sys/netpfil/pf/pf.h
@@ -120,7 +120,8 @@ enum {
enum { PF_NOPFROUTE, PF_FASTROUTE, PF_ROUTETO, PF_DUPTO, PF_REPLYTO };
enum { PF_LIMIT_STATES, PF_LIMIT_SRC_NODES, PF_LIMIT_FRAGS,
- PF_LIMIT_TABLE_ENTRIES, PF_LIMIT_ANCHORS, PF_LIMIT_MAX };
+ PF_LIMIT_TABLE_ENTRIES, PF_LIMIT_ANCHORS, PF_LIMIT_ETH_ANCHORS,
+ PF_LIMIT_MAX };
#define PF_POOL_IDMASK 0x0f
enum { PF_POOL_NONE, PF_POOL_BITMASK, PF_POOL_RANDOM,
PF_POOL_SRCHASH, PF_POOL_ROUNDROBIN };
diff --git a/sys/netpfil/pf/pf_ioctl.c b/sys/netpfil/pf/pf_ioctl.c
index 935747d9f58a..b6f5d74b5b42 100644
--- a/sys/netpfil/pf/pf_ioctl.c
+++ b/sys/netpfil/pf/pf_ioctl.c
@@ -332,6 +332,7 @@ pfattach_vnet(void)
V_pf_limits[PF_LIMIT_STATES].limit = PFSTATE_HIWAT;
V_pf_limits[PF_LIMIT_SRC_NODES].limit = PFSNODE_HIWAT;
V_pf_limits[PF_LIMIT_ANCHORS].limit = PF_ANCHOR_HIWAT;
+ V_pf_limits[PF_LIMIT_ETH_ANCHORS].limit = PF_ANCHOR_HIWAT;
RB_INIT(&V_pf_anchors);
pf_init_kruleset(&pf_main_ruleset);
diff --git a/sys/netpfil/pf/pf_norm.c b/sys/netpfil/pf/pf_norm.c
index 2b822dca55b5..a684d778ab42 100644
--- a/sys/netpfil/pf/pf_norm.c
+++ b/sys/netpfil/pf/pf_norm.c
@@ -119,6 +119,7 @@ VNET_DEFINE_STATIC(uma_zone_t, pf_frnode_z);
VNET_DEFINE_STATIC(uma_zone_t, pf_frag_z);
#define V_pf_frag_z VNET(pf_frag_z)
VNET_DEFINE(uma_zone_t, pf_anchor_z);
+VNET_DEFINE(uma_zone_t, pf_eth_anchor_z);
TAILQ_HEAD(pf_fragqueue, pf_fragment);
TAILQ_HEAD(pf_cachequeue, pf_fragment);
diff --git a/sys/netpfil/pf/pf_ruleset.c b/sys/netpfil/pf/pf_ruleset.c
index 7f21b3f8fc47..039908a53126 100644
--- a/sys/netpfil/pf/pf_ruleset.c
+++ b/sys/netpfil/pf/pf_ruleset.c
@@ -613,7 +613,7 @@ pf_find_or_create_keth_ruleset(const char *path)
rs_free(p);
return (NULL);
}
- anchor = (struct pf_keth_anchor *)rs_malloc(sizeof(*anchor));
+ anchor = uma_zalloc(V_pf_eth_anchor_z, M_NOWAIT | M_ZERO);
if (anchor == NULL) {
rs_free(p);
return (NULL);
@@ -631,7 +631,7 @@ pf_find_or_create_keth_ruleset(const char *path)
printf("%s: RB_INSERT1 "
"'%s' '%s' collides with '%s' '%s'\n", __func__,
anchor->path, anchor->name, dup->path, dup->name);
- rs_free(anchor);
+ uma_zfree(V_pf_eth_anchor_z, anchor);
rs_free(p);
return (NULL);
}
@@ -645,7 +645,7 @@ pf_find_or_create_keth_ruleset(const char *path)
anchor->name, dup->path, dup->name);
RB_REMOVE(pf_keth_anchor_global, &V_pf_keth_anchors,
anchor);
- rs_free(anchor);
+ uma_zfree(V_pf_eth_anchor_z, anchor);
rs_free(p);
return (NULL);
}
@@ -754,7 +754,7 @@ pf_remove_if_empty_keth_ruleset(struct pf_keth_ruleset *ruleset)
if ((parent = ruleset->anchor->parent) != NULL)
RB_REMOVE(pf_keth_anchor_node, &parent->children,
ruleset->anchor);
- rs_free(ruleset->anchor);
+ uma_zfree(V_pf_eth_anchor_z, ruleset->anchor);
if (parent == NULL)
return;
ruleset = &parent->ruleset;