Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F108658399
D29558.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
7 KB
Referenced Files
None
Subscribers
None
D29558.diff
View Options
diff --git a/sbin/pfctl/Makefile b/sbin/pfctl/Makefile
--- a/sbin/pfctl/Makefile
+++ b/sbin/pfctl/Makefile
@@ -27,7 +27,7 @@
YFLAGS=
-LIBADD= m md
+LIBADD= m md nv
HAS_TESTS=
SUBDIR.${MK_TESTS}+= tests
diff --git a/sbin/pfctl/pfctl.c b/sbin/pfctl/pfctl.c
--- a/sbin/pfctl/pfctl.c
+++ b/sbin/pfctl/pfctl.c
@@ -40,6 +40,7 @@
#include <sys/types.h>
#include <sys/ioctl.h>
+#include <sys/nv.h>
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/endian.h>
@@ -1422,19 +1423,217 @@
}
+static void
+pfctl_nv_add_addr(nvlist_t *nvparent, const char *name,
+ const struct pf_addr *addr)
+{
+ nvlist_t *nvl = nvlist_create(0);
+
+ nvlist_add_binary(nvl, "addr", addr, sizeof(*addr));
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static void
+pfctl_nv_add_addr_wrap(nvlist_t *nvparent, const char *name,
+ const struct pf_addr_wrap *addr)
+{
+ nvlist_t *nvl = nvlist_create(0);
+
+ nvlist_add_number(nvl, "type", addr->type);
+ nvlist_add_number(nvl, "iflags", addr->iflags);
+ nvlist_add_string(nvl, "ifname", addr->v.ifname);
+ nvlist_add_string(nvl, "tblname", addr->v.tblname);
+ pfctl_nv_add_addr(nvl, "addr", &addr->v.a.addr);
+ pfctl_nv_add_addr(nvl, "mask", &addr->v.a.mask);
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static void
+pfctl_nv_add_rule_addr(nvlist_t *nvparent, const char *name,
+ const struct pf_rule_addr *addr)
+{
+ u_int64_t ports[2];
+ nvlist_t *nvl = nvlist_create(0);
+
+ pfctl_nv_add_addr_wrap(nvl, "addr", &addr->addr);
+ ports[0] = addr->port[0];
+ ports[1] = addr->port[1];
+ nvlist_add_number_array(nvl, "port", ports, 2);
+ nvlist_add_number(nvl, "neg", addr->neg);
+ nvlist_add_number(nvl, "port_op", addr->port_op);
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static void
+pfctl_nv_add_pool(nvlist_t *nvparent, const char *name,
+ const struct pf_pool *pool)
+{
+ u_int64_t ports[2];
+ nvlist_t *nvl = nvlist_create(0);
+
+ nvlist_add_binary(nvl, "key", &pool->key, sizeof(pool->key));
+ pfctl_nv_add_addr(nvl, "counter", &pool->counter);
+ nvlist_add_number(nvl, "tblidx", pool->tblidx);
+
+ ports[0] = pool->proxy_port[0];
+ ports[1] = pool->proxy_port[1];
+ nvlist_add_number_array(nvl, "proxy_port", ports, 2);
+ nvlist_add_number(nvl, "opts", pool->opts);
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static void
+pfctl_nv_add_uid(nvlist_t *nvparent, const char *name,
+ const struct pf_rule_uid *uid)
+{
+ u_int64_t uids[2];
+ nvlist_t *nvl = nvlist_create(0);
+
+ uids[0] = uid->uid[0];
+ uids[1] = uid->uid[1];
+ nvlist_add_number_array(nvl, "uid", uids, 2);
+ nvlist_add_number(nvl, "op", uid->op);
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static void
+pfctl_nv_add_divert(nvlist_t *nvparent, const char *name,
+ const struct pf_rule *r)
+{
+ nvlist_t *nvl = nvlist_create(0);
+
+ pfctl_nv_add_addr(nvl, "addr", &r->divert.addr);
+ nvlist_add_number(nvl, "port", r->divert.port);
+
+ nvlist_add_nvlist(nvparent, name, nvl);
+}
+
+static int
+pfctl_addrule(struct pfctl *pf, const struct pf_rule *r, const char *anchor,
+ const char *anchor_call, u_int32_t ticket, u_int32_t pool_ticket)
+{
+ struct pfioc_nv nv;
+ u_int64_t timeouts[PFTM_MAX];
+ u_int64_t set_prio[2];
+ nvlist_t *nvl, *nvlr;
+ int ret;
+
+ nvl = nvlist_create(0);
+ nvlr = nvlist_create(0);
+
+ nvlist_add_number(nvl, "ticket", ticket);
+ nvlist_add_number(nvl, "pool_ticket", pool_ticket);
+ nvlist_add_string(nvl, "anchor", anchor);
+ nvlist_add_string(nvl, "anchor_call", anchor_call);
+
+ nvlist_add_number(nvlr, "nr", r->nr);
+ pfctl_nv_add_rule_addr(nvlr, "src", &r->src);
+ pfctl_nv_add_rule_addr(nvlr, "dst", &r->dst);
+
+ nvlist_add_string(nvlr, "label", r->label);
+ nvlist_add_string(nvlr, "ifname", r->ifname);
+ nvlist_add_string(nvlr, "qname", r->qname);
+ nvlist_add_string(nvlr, "pqname", r->pqname);
+ nvlist_add_string(nvlr, "tagname", r->tagname);
+ nvlist_add_string(nvlr, "match_tagname", r->match_tagname);
+ nvlist_add_string(nvlr, "overload_tblname", r->overload_tblname);
+
+ pfctl_nv_add_pool(nvlr, "rpool", &r->rpool);
+
+ nvlist_add_number(nvlr, "os_fingerprint", r->os_fingerprint);
+
+ nvlist_add_number(nvlr, "rtableid", r->rtableid);
+ for (int i = 0; i < PFTM_MAX; i++)
+ timeouts[i] = r->timeout[i];
+ nvlist_add_number_array(nvlr, "timeout", timeouts, PFTM_MAX);
+ nvlist_add_number(nvlr, "max_states", r->max_states);
+ nvlist_add_number(nvlr, "max_src_nodes", r->max_src_nodes);
+ nvlist_add_number(nvlr, "max_src_states", r->max_src_states);
+ nvlist_add_number(nvlr, "max_src_conn", r->max_src_conn);
+ nvlist_add_number(nvlr, "max_src_conn_rate.limit",
+ r->max_src_conn_rate.limit);
+ nvlist_add_number(nvlr, "max_src_conn_rate.seconds",
+ r->max_src_conn_rate.seconds);
+ nvlist_add_number(nvlr, "prob", r->prob);
+ nvlist_add_number(nvlr, "cuid", r->cuid);
+ nvlist_add_number(nvlr, "cpid", r->cpid);
+
+ nvlist_add_number(nvlr, "return_icmp", r->return_icmp);
+ nvlist_add_number(nvlr, "return_icmp6", r->return_icmp6);
+
+ nvlist_add_number(nvlr, "max_mss", r->max_mss);
+ nvlist_add_number(nvlr, "scrub_flags", r->scrub_flags);
+
+ pfctl_nv_add_uid(nvlr, "uid", &r->uid);
+ pfctl_nv_add_uid(nvlr, "gid", (struct pf_rule_uid *)&r->gid);
+
+ nvlist_add_number(nvlr, "rule_flag", r->rule_flag);
+ nvlist_add_number(nvlr, "action", r->action);
+ nvlist_add_number(nvlr, "direction", r->direction);
+ nvlist_add_number(nvlr, "log", r->log);
+ nvlist_add_number(nvlr, "logif", r->logif);
+ nvlist_add_number(nvlr, "quick", r->quick);
+ nvlist_add_number(nvlr, "ifnot", r->ifnot);
+ nvlist_add_number(nvlr, "match_tag_not", r->match_tag_not);
+ nvlist_add_number(nvlr, "natpass", r->natpass);
+
+ nvlist_add_number(nvlr, "keep_state", r->keep_state);
+ nvlist_add_number(nvlr, "af", r->af);
+ nvlist_add_number(nvlr, "proto", r->proto);
+ nvlist_add_number(nvlr, "type", r->type);
+ nvlist_add_number(nvlr, "code", r->code);
+ nvlist_add_number(nvlr, "flags", r->flags);
+ nvlist_add_number(nvlr, "flagset", r->flagset);
+ nvlist_add_number(nvlr, "min_ttl", r->min_ttl);
+ nvlist_add_number(nvlr, "allow_opts", r->allow_opts);
+ nvlist_add_number(nvlr, "rt", r->rt);
+ nvlist_add_number(nvlr, "return_ttl", r->return_ttl);
+ nvlist_add_number(nvlr, "tos", r->tos);
+ nvlist_add_number(nvlr, "set_tos", r->set_tos);
+ nvlist_add_number(nvlr, "anchor_relative", r->anchor_relative);
+ nvlist_add_number(nvlr, "anchor_wildcard", r->anchor_wildcard);
+
+ nvlist_add_number(nvlr, "flush", r->flush);
+
+ nvlist_add_number(nvlr, "prio", r->prio);
+ set_prio[0] = r->set_prio[0];
+ set_prio[1] = r->set_prio[1];
+ nvlist_add_number_array(nvlr, "set_prio", set_prio, 2);
+
+ pfctl_nv_add_divert(nvlr, "divert", r);
+
+ nvlist_add_nvlist(nvl, "rule", nvlr);
+
+ /* Now do the call. */
+ nv.data = nvlist_pack(nvl, &nv.len);
+ nv.size = nv.len;
+
+ ret = ioctl(pf->dev, DIOCADDRULENV, &nv);
+
+ free(nv.data);
+ nvlist_destroy(nvl);
+
+ return (ret);
+}
+
int
pfctl_load_rule(struct pfctl *pf, char *path, struct pf_rule *r, int depth)
{
u_int8_t rs_num = pf_get_ruleset_number(r->action);
char *name;
- struct pfioc_rule pr;
+ u_int32_t ticket;
+ char anchor[PF_ANCHOR_NAME_SIZE];
int len = strlen(path);
- bzero(&pr, sizeof(pr));
/* set up anchor before adding to path for anchor_call */
if ((pf->opts & PF_OPT_NOACTION) == 0)
- pr.ticket = pfctl_get_ticket(pf->trans, rs_num, path);
- if (strlcpy(pr.anchor, path, sizeof(pr.anchor)) >= sizeof(pr.anchor))
+ ticket = pfctl_get_ticket(pf->trans, rs_num, path);
+ if (strlcpy(anchor, path, sizeof(anchor)) >= sizeof(anchor))
errx(1, "pfctl_load_rule: strlcpy");
if (r->anchor) {
@@ -1454,13 +1653,9 @@
if ((pf->opts & PF_OPT_NOACTION) == 0) {
if (pfctl_add_pool(pf, &r->rpool, r->af))
return (1);
- pr.pool_ticket = pf->paddr.ticket;
- memcpy(&pr.rule, r, sizeof(pr.rule));
- if (r->anchor && strlcpy(pr.anchor_call, name,
- sizeof(pr.anchor_call)) >= sizeof(pr.anchor_call))
- errx(1, "pfctl_load_rule: strlcpy");
- if (ioctl(pf->dev, DIOCADDRULE, &pr))
- err(1, "DIOCADDRULE");
+ if (pfctl_addrule(pf, r, anchor, name, ticket,
+ pf->paddr.ticket))
+ err(1, "DIOCADDRULENV");
}
if (pf->opts & PF_OPT_VERBOSE) {
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Tue, Jan 28, 3:16 AM (10 h, 41 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
16243389
Default Alt Text
D29558.diff (7 KB)
Attached To
Mode
D29558: pfctl: Move to DIOCADDRULENV
Attached
Detach File
Event Timeline
Log In to Comment