xref: /freebsd/sys/netpfil/pf/pf_ioctl.c (revision b51f459a2098622c31ed54f5c1bf0e03efce403b)
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause
3  *
4  * Copyright (c) 2001 Daniel Hartmeier
5  * Copyright (c) 2002,2003 Henning Brauer
6  * Copyright (c) 2012 Gleb Smirnoff <glebius@FreeBSD.org>
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  *    - Redistributions of source code must retain the above copyright
14  *      notice, this list of conditions and the following disclaimer.
15  *    - Redistributions in binary form must reproduce the above
16  *      copyright notice, this list of conditions and the following
17  *      disclaimer in the documentation and/or other materials provided
18  *      with the distribution.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
27  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31  * POSSIBILITY OF SUCH DAMAGE.
32  *
33  * Effort sponsored in part by the Defense Advanced Research Projects
34  * Agency (DARPA) and Air Force Research Laboratory, Air Force
35  * Materiel Command, USAF, under agreement number F30602-01-2-0537.
36  *
37  *	$OpenBSD: pf_ioctl.c,v 1.213 2009/02/15 21:46:12 mbalmer Exp $
38  */
39 
40 #include <sys/cdefs.h>
41 __FBSDID("$FreeBSD$");
42 
43 #include "opt_inet.h"
44 #include "opt_inet6.h"
45 #include "opt_bpf.h"
46 #include "opt_pf.h"
47 
48 #include <sys/param.h>
49 #include <sys/_bitset.h>
50 #include <sys/bitset.h>
51 #include <sys/bus.h>
52 #include <sys/conf.h>
53 #include <sys/endian.h>
54 #include <sys/fcntl.h>
55 #include <sys/filio.h>
56 #include <sys/hash.h>
57 #include <sys/interrupt.h>
58 #include <sys/jail.h>
59 #include <sys/kernel.h>
60 #include <sys/kthread.h>
61 #include <sys/lock.h>
62 #include <sys/mbuf.h>
63 #include <sys/module.h>
64 #include <sys/nv.h>
65 #include <sys/proc.h>
66 #include <sys/smp.h>
67 #include <sys/socket.h>
68 #include <sys/sysctl.h>
69 #include <sys/md5.h>
70 #include <sys/ucred.h>
71 
72 #include <net/if.h>
73 #include <net/if_var.h>
74 #include <net/vnet.h>
75 #include <net/route.h>
76 #include <net/pfil.h>
77 #include <net/pfvar.h>
78 #include <net/if_pfsync.h>
79 #include <net/if_pflog.h>
80 
81 #include <netinet/in.h>
82 #include <netinet/ip.h>
83 #include <netinet/ip_var.h>
84 #include <netinet6/ip6_var.h>
85 #include <netinet/ip_icmp.h>
86 #include <netpfil/pf/pf_nv.h>
87 
88 #ifdef INET6
89 #include <netinet/ip6.h>
90 #endif /* INET6 */
91 
92 #ifdef ALTQ
93 #include <net/altq/altq.h>
94 #endif
95 
96 static struct pf_kpool	*pf_get_kpool(char *, u_int32_t, u_int8_t, u_int32_t,
97 			    u_int8_t, u_int8_t, u_int8_t);
98 
99 static void		 pf_mv_kpool(struct pf_kpalist *, struct pf_kpalist *);
100 static void		 pf_empty_kpool(struct pf_kpalist *);
101 static int		 pfioctl(struct cdev *, u_long, caddr_t, int,
102 			    struct thread *);
103 #ifdef ALTQ
104 static int		 pf_begin_altq(u_int32_t *);
105 static int		 pf_rollback_altq(u_int32_t);
106 static int		 pf_commit_altq(u_int32_t);
107 static int		 pf_enable_altq(struct pf_altq *);
108 static int		 pf_disable_altq(struct pf_altq *);
109 static u_int32_t	 pf_qname2qid(char *);
110 static void		 pf_qid_unref(u_int32_t);
111 #endif /* ALTQ */
112 static int		 pf_begin_rules(u_int32_t *, int, const char *);
113 static int		 pf_rollback_rules(u_int32_t, int, char *);
114 static int		 pf_setup_pfsync_matching(struct pf_kruleset *);
115 static void		 pf_hash_rule(MD5_CTX *, struct pf_krule *);
116 static void		 pf_hash_rule_addr(MD5_CTX *, struct pf_rule_addr *);
117 static int		 pf_commit_rules(u_int32_t, int, char *);
118 static int		 pf_addr_setup(struct pf_kruleset *,
119 			    struct pf_addr_wrap *, sa_family_t);
120 static void		 pf_addr_copyout(struct pf_addr_wrap *);
121 static void		 pf_src_node_copy(const struct pf_ksrc_node *,
122 			    struct pf_src_node *);
123 #ifdef ALTQ
124 static int		 pf_export_kaltq(struct pf_altq *,
125 			    struct pfioc_altq_v1 *, size_t);
126 static int		 pf_import_kaltq(struct pfioc_altq_v1 *,
127 			    struct pf_altq *, size_t);
128 #endif /* ALTQ */
129 
130 VNET_DEFINE(struct pf_krule,	pf_default_rule);
131 
132 #ifdef ALTQ
133 VNET_DEFINE_STATIC(int,		pf_altq_running);
134 #define	V_pf_altq_running	VNET(pf_altq_running)
135 #endif
136 
137 #define	TAGID_MAX	 50000
138 struct pf_tagname {
139 	TAILQ_ENTRY(pf_tagname)	namehash_entries;
140 	TAILQ_ENTRY(pf_tagname)	taghash_entries;
141 	char			name[PF_TAG_NAME_SIZE];
142 	uint16_t		tag;
143 	int			ref;
144 };
145 
146 struct pf_tagset {
147 	TAILQ_HEAD(, pf_tagname)	*namehash;
148 	TAILQ_HEAD(, pf_tagname)	*taghash;
149 	unsigned int			 mask;
150 	uint32_t			 seed;
151 	BITSET_DEFINE(, TAGID_MAX)	 avail;
152 };
153 
154 VNET_DEFINE(struct pf_tagset, pf_tags);
155 #define	V_pf_tags	VNET(pf_tags)
156 static unsigned int	pf_rule_tag_hashsize;
157 #define	PF_RULE_TAG_HASH_SIZE_DEFAULT	128
158 SYSCTL_UINT(_net_pf, OID_AUTO, rule_tag_hashsize, CTLFLAG_RDTUN,
159     &pf_rule_tag_hashsize, PF_RULE_TAG_HASH_SIZE_DEFAULT,
160     "Size of pf(4) rule tag hashtable");
161 
162 #ifdef ALTQ
163 VNET_DEFINE(struct pf_tagset, pf_qids);
164 #define	V_pf_qids	VNET(pf_qids)
165 static unsigned int	pf_queue_tag_hashsize;
166 #define	PF_QUEUE_TAG_HASH_SIZE_DEFAULT	128
167 SYSCTL_UINT(_net_pf, OID_AUTO, queue_tag_hashsize, CTLFLAG_RDTUN,
168     &pf_queue_tag_hashsize, PF_QUEUE_TAG_HASH_SIZE_DEFAULT,
169     "Size of pf(4) queue tag hashtable");
170 #endif
171 VNET_DEFINE(uma_zone_t,	 pf_tag_z);
172 #define	V_pf_tag_z		 VNET(pf_tag_z)
173 static MALLOC_DEFINE(M_PFALTQ, "pf_altq", "pf(4) altq configuration db");
174 static MALLOC_DEFINE(M_PFRULE, "pf_rule", "pf(4) rules");
175 
176 #if (PF_QNAME_SIZE != PF_TAG_NAME_SIZE)
177 #error PF_QNAME_SIZE must be equal to PF_TAG_NAME_SIZE
178 #endif
179 
180 static void		 pf_init_tagset(struct pf_tagset *, unsigned int *,
181 			    unsigned int);
182 static void		 pf_cleanup_tagset(struct pf_tagset *);
183 static uint16_t		 tagname2hashindex(const struct pf_tagset *, const char *);
184 static uint16_t		 tag2hashindex(const struct pf_tagset *, uint16_t);
185 static u_int16_t	 tagname2tag(struct pf_tagset *, char *);
186 static u_int16_t	 pf_tagname2tag(char *);
187 static void		 tag_unref(struct pf_tagset *, u_int16_t);
188 
189 #define DPFPRINTF(n, x) if (V_pf_status.debug >= (n)) printf x
190 
191 struct cdev *pf_dev;
192 
193 /*
194  * XXX - These are new and need to be checked when moveing to a new version
195  */
196 static void		 pf_clear_states(void);
197 static int		 pf_clear_tables(void);
198 static void		 pf_clear_srcnodes(struct pf_ksrc_node *);
199 static void		 pf_kill_srcnodes(struct pfioc_src_node_kill *);
200 static void		 pf_tbladdr_copyout(struct pf_addr_wrap *);
201 
202 /*
203  * Wrapper functions for pfil(9) hooks
204  */
205 #ifdef INET
206 static pfil_return_t pf_check_in(struct mbuf **m, struct ifnet *ifp,
207     int flags, void *ruleset __unused, struct inpcb *inp);
208 static pfil_return_t pf_check_out(struct mbuf **m, struct ifnet *ifp,
209     int flags, void *ruleset __unused, struct inpcb *inp);
210 #endif
211 #ifdef INET6
212 static pfil_return_t pf_check6_in(struct mbuf **m, struct ifnet *ifp,
213     int flags, void *ruleset __unused, struct inpcb *inp);
214 static pfil_return_t pf_check6_out(struct mbuf **m, struct ifnet *ifp,
215     int flags, void *ruleset __unused, struct inpcb *inp);
216 #endif
217 
218 static void		hook_pf(void);
219 static void		dehook_pf(void);
220 static int		shutdown_pf(void);
221 static int		pf_load(void);
222 static void		pf_unload(void);
223 
224 static struct cdevsw pf_cdevsw = {
225 	.d_ioctl =	pfioctl,
226 	.d_name =	PF_NAME,
227 	.d_version =	D_VERSION,
228 };
229 
230 volatile VNET_DEFINE_STATIC(int, pf_pfil_hooked);
231 #define V_pf_pfil_hooked	VNET(pf_pfil_hooked)
232 
233 /*
234  * We need a flag that is neither hooked nor running to know when
235  * the VNET is "valid".  We primarily need this to control (global)
236  * external event, e.g., eventhandlers.
237  */
238 VNET_DEFINE(int, pf_vnet_active);
239 #define V_pf_vnet_active	VNET(pf_vnet_active)
240 
241 int pf_end_threads;
242 struct proc *pf_purge_proc;
243 
244 struct rmlock			pf_rules_lock;
245 struct sx			pf_ioctl_lock;
246 struct sx			pf_end_lock;
247 
248 /* pfsync */
249 VNET_DEFINE(pfsync_state_import_t *, pfsync_state_import_ptr);
250 VNET_DEFINE(pfsync_insert_state_t *, pfsync_insert_state_ptr);
251 VNET_DEFINE(pfsync_update_state_t *, pfsync_update_state_ptr);
252 VNET_DEFINE(pfsync_delete_state_t *, pfsync_delete_state_ptr);
253 VNET_DEFINE(pfsync_clear_states_t *, pfsync_clear_states_ptr);
254 VNET_DEFINE(pfsync_defer_t *, pfsync_defer_ptr);
255 pfsync_detach_ifnet_t *pfsync_detach_ifnet_ptr;
256 
257 /* pflog */
258 pflog_packet_t			*pflog_packet_ptr = NULL;
259 
260 extern u_long	pf_ioctl_maxcount;
261 
262 static void
263 pfattach_vnet(void)
264 {
265 	u_int32_t *my_timeout = V_pf_default_rule.timeout;
266 
267 	pf_initialize();
268 	pfr_initialize();
269 	pfi_initialize_vnet();
270 	pf_normalize_init();
271 
272 	V_pf_limits[PF_LIMIT_STATES].limit = PFSTATE_HIWAT;
273 	V_pf_limits[PF_LIMIT_SRC_NODES].limit = PFSNODE_HIWAT;
274 
275 	RB_INIT(&V_pf_anchors);
276 	pf_init_kruleset(&pf_main_ruleset);
277 
278 	/* default rule should never be garbage collected */
279 	V_pf_default_rule.entries.tqe_prev = &V_pf_default_rule.entries.tqe_next;
280 #ifdef PF_DEFAULT_TO_DROP
281 	V_pf_default_rule.action = PF_DROP;
282 #else
283 	V_pf_default_rule.action = PF_PASS;
284 #endif
285 	V_pf_default_rule.nr = -1;
286 	V_pf_default_rule.rtableid = -1;
287 
288 	V_pf_default_rule.evaluations = counter_u64_alloc(M_WAITOK);
289 	for (int i = 0; i < 2; i++) {
290 		V_pf_default_rule.packets[i] = counter_u64_alloc(M_WAITOK);
291 		V_pf_default_rule.bytes[i] = counter_u64_alloc(M_WAITOK);
292 	}
293 	V_pf_default_rule.states_cur = counter_u64_alloc(M_WAITOK);
294 	V_pf_default_rule.states_tot = counter_u64_alloc(M_WAITOK);
295 	V_pf_default_rule.src_nodes = counter_u64_alloc(M_WAITOK);
296 
297 	/* initialize default timeouts */
298 	my_timeout[PFTM_TCP_FIRST_PACKET] = PFTM_TCP_FIRST_PACKET_VAL;
299 	my_timeout[PFTM_TCP_OPENING] = PFTM_TCP_OPENING_VAL;
300 	my_timeout[PFTM_TCP_ESTABLISHED] = PFTM_TCP_ESTABLISHED_VAL;
301 	my_timeout[PFTM_TCP_CLOSING] = PFTM_TCP_CLOSING_VAL;
302 	my_timeout[PFTM_TCP_FIN_WAIT] = PFTM_TCP_FIN_WAIT_VAL;
303 	my_timeout[PFTM_TCP_CLOSED] = PFTM_TCP_CLOSED_VAL;
304 	my_timeout[PFTM_UDP_FIRST_PACKET] = PFTM_UDP_FIRST_PACKET_VAL;
305 	my_timeout[PFTM_UDP_SINGLE] = PFTM_UDP_SINGLE_VAL;
306 	my_timeout[PFTM_UDP_MULTIPLE] = PFTM_UDP_MULTIPLE_VAL;
307 	my_timeout[PFTM_ICMP_FIRST_PACKET] = PFTM_ICMP_FIRST_PACKET_VAL;
308 	my_timeout[PFTM_ICMP_ERROR_REPLY] = PFTM_ICMP_ERROR_REPLY_VAL;
309 	my_timeout[PFTM_OTHER_FIRST_PACKET] = PFTM_OTHER_FIRST_PACKET_VAL;
310 	my_timeout[PFTM_OTHER_SINGLE] = PFTM_OTHER_SINGLE_VAL;
311 	my_timeout[PFTM_OTHER_MULTIPLE] = PFTM_OTHER_MULTIPLE_VAL;
312 	my_timeout[PFTM_FRAG] = PFTM_FRAG_VAL;
313 	my_timeout[PFTM_INTERVAL] = PFTM_INTERVAL_VAL;
314 	my_timeout[PFTM_SRC_NODE] = PFTM_SRC_NODE_VAL;
315 	my_timeout[PFTM_TS_DIFF] = PFTM_TS_DIFF_VAL;
316 	my_timeout[PFTM_ADAPTIVE_START] = PFSTATE_ADAPT_START;
317 	my_timeout[PFTM_ADAPTIVE_END] = PFSTATE_ADAPT_END;
318 
319 	bzero(&V_pf_status, sizeof(V_pf_status));
320 	V_pf_status.debug = PF_DEBUG_URGENT;
321 
322 	V_pf_pfil_hooked = 0;
323 
324 	/* XXX do our best to avoid a conflict */
325 	V_pf_status.hostid = arc4random();
326 
327 	for (int i = 0; i < PFRES_MAX; i++)
328 		V_pf_status.counters[i] = counter_u64_alloc(M_WAITOK);
329 	for (int i = 0; i < LCNT_MAX; i++)
330 		V_pf_status.lcounters[i] = counter_u64_alloc(M_WAITOK);
331 	for (int i = 0; i < FCNT_MAX; i++)
332 		V_pf_status.fcounters[i] = counter_u64_alloc(M_WAITOK);
333 	for (int i = 0; i < SCNT_MAX; i++)
334 		V_pf_status.scounters[i] = counter_u64_alloc(M_WAITOK);
335 
336 	if (swi_add(&V_pf_swi_ie, "pf send", pf_intr, curvnet, SWI_NET,
337 	    INTR_MPSAFE, &V_pf_swi_cookie) != 0)
338 		/* XXXGL: leaked all above. */
339 		return;
340 }
341 
342 static struct pf_kpool *
343 pf_get_kpool(char *anchor, u_int32_t ticket, u_int8_t rule_action,
344     u_int32_t rule_number, u_int8_t r_last, u_int8_t active,
345     u_int8_t check_ticket)
346 {
347 	struct pf_kruleset	*ruleset;
348 	struct pf_krule		*rule;
349 	int			 rs_num;
350 
351 	ruleset = pf_find_kruleset(anchor);
352 	if (ruleset == NULL)
353 		return (NULL);
354 	rs_num = pf_get_ruleset_number(rule_action);
355 	if (rs_num >= PF_RULESET_MAX)
356 		return (NULL);
357 	if (active) {
358 		if (check_ticket && ticket !=
359 		    ruleset->rules[rs_num].active.ticket)
360 			return (NULL);
361 		if (r_last)
362 			rule = TAILQ_LAST(ruleset->rules[rs_num].active.ptr,
363 			    pf_krulequeue);
364 		else
365 			rule = TAILQ_FIRST(ruleset->rules[rs_num].active.ptr);
366 	} else {
367 		if (check_ticket && ticket !=
368 		    ruleset->rules[rs_num].inactive.ticket)
369 			return (NULL);
370 		if (r_last)
371 			rule = TAILQ_LAST(ruleset->rules[rs_num].inactive.ptr,
372 			    pf_krulequeue);
373 		else
374 			rule = TAILQ_FIRST(ruleset->rules[rs_num].inactive.ptr);
375 	}
376 	if (!r_last) {
377 		while ((rule != NULL) && (rule->nr != rule_number))
378 			rule = TAILQ_NEXT(rule, entries);
379 	}
380 	if (rule == NULL)
381 		return (NULL);
382 
383 	return (&rule->rpool);
384 }
385 
386 static void
387 pf_mv_kpool(struct pf_kpalist *poola, struct pf_kpalist *poolb)
388 {
389 	struct pf_kpooladdr	*mv_pool_pa;
390 
391 	while ((mv_pool_pa = TAILQ_FIRST(poola)) != NULL) {
392 		TAILQ_REMOVE(poola, mv_pool_pa, entries);
393 		TAILQ_INSERT_TAIL(poolb, mv_pool_pa, entries);
394 	}
395 }
396 
397 static void
398 pf_empty_kpool(struct pf_kpalist *poola)
399 {
400 	struct pf_kpooladdr *pa;
401 
402 	while ((pa = TAILQ_FIRST(poola)) != NULL) {
403 		switch (pa->addr.type) {
404 		case PF_ADDR_DYNIFTL:
405 			pfi_dynaddr_remove(pa->addr.p.dyn);
406 			break;
407 		case PF_ADDR_TABLE:
408 			/* XXX: this could be unfinished pooladdr on pabuf */
409 			if (pa->addr.p.tbl != NULL)
410 				pfr_detach_table(pa->addr.p.tbl);
411 			break;
412 		}
413 		if (pa->kif)
414 			pfi_kkif_unref(pa->kif);
415 		TAILQ_REMOVE(poola, pa, entries);
416 		free(pa, M_PFRULE);
417 	}
418 }
419 
420 static void
421 pf_unlink_rule(struct pf_krulequeue *rulequeue, struct pf_krule *rule)
422 {
423 
424 	PF_RULES_WASSERT();
425 
426 	TAILQ_REMOVE(rulequeue, rule, entries);
427 
428 	PF_UNLNKDRULES_LOCK();
429 	rule->rule_flag |= PFRULE_REFS;
430 	TAILQ_INSERT_TAIL(&V_pf_unlinked_rules, rule, entries);
431 	PF_UNLNKDRULES_UNLOCK();
432 }
433 
434 void
435 pf_free_rule(struct pf_krule *rule)
436 {
437 
438 	PF_RULES_WASSERT();
439 
440 	if (rule->tag)
441 		tag_unref(&V_pf_tags, rule->tag);
442 	if (rule->match_tag)
443 		tag_unref(&V_pf_tags, rule->match_tag);
444 #ifdef ALTQ
445 	if (rule->pqid != rule->qid)
446 		pf_qid_unref(rule->pqid);
447 	pf_qid_unref(rule->qid);
448 #endif
449 	switch (rule->src.addr.type) {
450 	case PF_ADDR_DYNIFTL:
451 		pfi_dynaddr_remove(rule->src.addr.p.dyn);
452 		break;
453 	case PF_ADDR_TABLE:
454 		pfr_detach_table(rule->src.addr.p.tbl);
455 		break;
456 	}
457 	switch (rule->dst.addr.type) {
458 	case PF_ADDR_DYNIFTL:
459 		pfi_dynaddr_remove(rule->dst.addr.p.dyn);
460 		break;
461 	case PF_ADDR_TABLE:
462 		pfr_detach_table(rule->dst.addr.p.tbl);
463 		break;
464 	}
465 	if (rule->overload_tbl)
466 		pfr_detach_table(rule->overload_tbl);
467 	if (rule->kif)
468 		pfi_kkif_unref(rule->kif);
469 	pf_kanchor_remove(rule);
470 	pf_empty_kpool(&rule->rpool.list);
471 
472 	pf_krule_free(rule);
473 }
474 
475 static void
476 pf_init_tagset(struct pf_tagset *ts, unsigned int *tunable_size,
477     unsigned int default_size)
478 {
479 	unsigned int i;
480 	unsigned int hashsize;
481 
482 	if (*tunable_size == 0 || !powerof2(*tunable_size))
483 		*tunable_size = default_size;
484 
485 	hashsize = *tunable_size;
486 	ts->namehash = mallocarray(hashsize, sizeof(*ts->namehash), M_PFHASH,
487 	    M_WAITOK);
488 	ts->taghash = mallocarray(hashsize, sizeof(*ts->taghash), M_PFHASH,
489 	    M_WAITOK);
490 	ts->mask = hashsize - 1;
491 	ts->seed = arc4random();
492 	for (i = 0; i < hashsize; i++) {
493 		TAILQ_INIT(&ts->namehash[i]);
494 		TAILQ_INIT(&ts->taghash[i]);
495 	}
496 	BIT_FILL(TAGID_MAX, &ts->avail);
497 }
498 
499 static void
500 pf_cleanup_tagset(struct pf_tagset *ts)
501 {
502 	unsigned int i;
503 	unsigned int hashsize;
504 	struct pf_tagname *t, *tmp;
505 
506 	/*
507 	 * Only need to clean up one of the hashes as each tag is hashed
508 	 * into each table.
509 	 */
510 	hashsize = ts->mask + 1;
511 	for (i = 0; i < hashsize; i++)
512 		TAILQ_FOREACH_SAFE(t, &ts->namehash[i], namehash_entries, tmp)
513 			uma_zfree(V_pf_tag_z, t);
514 
515 	free(ts->namehash, M_PFHASH);
516 	free(ts->taghash, M_PFHASH);
517 }
518 
519 static uint16_t
520 tagname2hashindex(const struct pf_tagset *ts, const char *tagname)
521 {
522 	size_t len;
523 
524 	len = strnlen(tagname, PF_TAG_NAME_SIZE - 1);
525 	return (murmur3_32_hash(tagname, len, ts->seed) & ts->mask);
526 }
527 
528 static uint16_t
529 tag2hashindex(const struct pf_tagset *ts, uint16_t tag)
530 {
531 
532 	return (tag & ts->mask);
533 }
534 
535 static u_int16_t
536 tagname2tag(struct pf_tagset *ts, char *tagname)
537 {
538 	struct pf_tagname	*tag;
539 	u_int32_t		 index;
540 	u_int16_t		 new_tagid;
541 
542 	PF_RULES_WASSERT();
543 
544 	index = tagname2hashindex(ts, tagname);
545 	TAILQ_FOREACH(tag, &ts->namehash[index], namehash_entries)
546 		if (strcmp(tagname, tag->name) == 0) {
547 			tag->ref++;
548 			return (tag->tag);
549 		}
550 
551 	/*
552 	 * new entry
553 	 *
554 	 * to avoid fragmentation, we do a linear search from the beginning
555 	 * and take the first free slot we find.
556 	 */
557 	new_tagid = BIT_FFS(TAGID_MAX, &ts->avail);
558 	/*
559 	 * Tags are 1-based, with valid tags in the range [1..TAGID_MAX].
560 	 * BIT_FFS() returns a 1-based bit number, with 0 indicating no bits
561 	 * set.  It may also return a bit number greater than TAGID_MAX due
562 	 * to rounding of the number of bits in the vector up to a multiple
563 	 * of the vector word size at declaration/allocation time.
564 	 */
565 	if ((new_tagid == 0) || (new_tagid > TAGID_MAX))
566 		return (0);
567 
568 	/* Mark the tag as in use.  Bits are 0-based for BIT_CLR() */
569 	BIT_CLR(TAGID_MAX, new_tagid - 1, &ts->avail);
570 
571 	/* allocate and fill new struct pf_tagname */
572 	tag = uma_zalloc(V_pf_tag_z, M_NOWAIT);
573 	if (tag == NULL)
574 		return (0);
575 	strlcpy(tag->name, tagname, sizeof(tag->name));
576 	tag->tag = new_tagid;
577 	tag->ref = 1;
578 
579 	/* Insert into namehash */
580 	TAILQ_INSERT_TAIL(&ts->namehash[index], tag, namehash_entries);
581 
582 	/* Insert into taghash */
583 	index = tag2hashindex(ts, new_tagid);
584 	TAILQ_INSERT_TAIL(&ts->taghash[index], tag, taghash_entries);
585 
586 	return (tag->tag);
587 }
588 
589 static void
590 tag_unref(struct pf_tagset *ts, u_int16_t tag)
591 {
592 	struct pf_tagname	*t;
593 	uint16_t		 index;
594 
595 	PF_RULES_WASSERT();
596 
597 	index = tag2hashindex(ts, tag);
598 	TAILQ_FOREACH(t, &ts->taghash[index], taghash_entries)
599 		if (tag == t->tag) {
600 			if (--t->ref == 0) {
601 				TAILQ_REMOVE(&ts->taghash[index], t,
602 				    taghash_entries);
603 				index = tagname2hashindex(ts, t->name);
604 				TAILQ_REMOVE(&ts->namehash[index], t,
605 				    namehash_entries);
606 				/* Bits are 0-based for BIT_SET() */
607 				BIT_SET(TAGID_MAX, tag - 1, &ts->avail);
608 				uma_zfree(V_pf_tag_z, t);
609 			}
610 			break;
611 		}
612 }
613 
614 static u_int16_t
615 pf_tagname2tag(char *tagname)
616 {
617 	return (tagname2tag(&V_pf_tags, tagname));
618 }
619 
620 #ifdef ALTQ
621 static u_int32_t
622 pf_qname2qid(char *qname)
623 {
624 	return ((u_int32_t)tagname2tag(&V_pf_qids, qname));
625 }
626 
627 static void
628 pf_qid_unref(u_int32_t qid)
629 {
630 	tag_unref(&V_pf_qids, (u_int16_t)qid);
631 }
632 
633 static int
634 pf_begin_altq(u_int32_t *ticket)
635 {
636 	struct pf_altq	*altq, *tmp;
637 	int		 error = 0;
638 
639 	PF_RULES_WASSERT();
640 
641 	/* Purge the old altq lists */
642 	TAILQ_FOREACH_SAFE(altq, V_pf_altq_ifs_inactive, entries, tmp) {
643 		if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
644 			/* detach and destroy the discipline */
645 			error = altq_remove(altq);
646 		}
647 		free(altq, M_PFALTQ);
648 	}
649 	TAILQ_INIT(V_pf_altq_ifs_inactive);
650 	TAILQ_FOREACH_SAFE(altq, V_pf_altqs_inactive, entries, tmp) {
651 		pf_qid_unref(altq->qid);
652 		free(altq, M_PFALTQ);
653 	}
654 	TAILQ_INIT(V_pf_altqs_inactive);
655 	if (error)
656 		return (error);
657 	*ticket = ++V_ticket_altqs_inactive;
658 	V_altqs_inactive_open = 1;
659 	return (0);
660 }
661 
662 static int
663 pf_rollback_altq(u_int32_t ticket)
664 {
665 	struct pf_altq	*altq, *tmp;
666 	int		 error = 0;
667 
668 	PF_RULES_WASSERT();
669 
670 	if (!V_altqs_inactive_open || ticket != V_ticket_altqs_inactive)
671 		return (0);
672 	/* Purge the old altq lists */
673 	TAILQ_FOREACH_SAFE(altq, V_pf_altq_ifs_inactive, entries, tmp) {
674 		if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
675 			/* detach and destroy the discipline */
676 			error = altq_remove(altq);
677 		}
678 		free(altq, M_PFALTQ);
679 	}
680 	TAILQ_INIT(V_pf_altq_ifs_inactive);
681 	TAILQ_FOREACH_SAFE(altq, V_pf_altqs_inactive, entries, tmp) {
682 		pf_qid_unref(altq->qid);
683 		free(altq, M_PFALTQ);
684 	}
685 	TAILQ_INIT(V_pf_altqs_inactive);
686 	V_altqs_inactive_open = 0;
687 	return (error);
688 }
689 
690 static int
691 pf_commit_altq(u_int32_t ticket)
692 {
693 	struct pf_altqqueue	*old_altqs, *old_altq_ifs;
694 	struct pf_altq		*altq, *tmp;
695 	int			 err, error = 0;
696 
697 	PF_RULES_WASSERT();
698 
699 	if (!V_altqs_inactive_open || ticket != V_ticket_altqs_inactive)
700 		return (EBUSY);
701 
702 	/* swap altqs, keep the old. */
703 	old_altqs = V_pf_altqs_active;
704 	old_altq_ifs = V_pf_altq_ifs_active;
705 	V_pf_altqs_active = V_pf_altqs_inactive;
706 	V_pf_altq_ifs_active = V_pf_altq_ifs_inactive;
707 	V_pf_altqs_inactive = old_altqs;
708 	V_pf_altq_ifs_inactive = old_altq_ifs;
709 	V_ticket_altqs_active = V_ticket_altqs_inactive;
710 
711 	/* Attach new disciplines */
712 	TAILQ_FOREACH(altq, V_pf_altq_ifs_active, entries) {
713 		if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
714 			/* attach the discipline */
715 			error = altq_pfattach(altq);
716 			if (error == 0 && V_pf_altq_running)
717 				error = pf_enable_altq(altq);
718 			if (error != 0)
719 				return (error);
720 		}
721 	}
722 
723 	/* Purge the old altq lists */
724 	TAILQ_FOREACH_SAFE(altq, V_pf_altq_ifs_inactive, entries, tmp) {
725 		if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
726 			/* detach and destroy the discipline */
727 			if (V_pf_altq_running)
728 				error = pf_disable_altq(altq);
729 			err = altq_pfdetach(altq);
730 			if (err != 0 && error == 0)
731 				error = err;
732 			err = altq_remove(altq);
733 			if (err != 0 && error == 0)
734 				error = err;
735 		}
736 		free(altq, M_PFALTQ);
737 	}
738 	TAILQ_INIT(V_pf_altq_ifs_inactive);
739 	TAILQ_FOREACH_SAFE(altq, V_pf_altqs_inactive, entries, tmp) {
740 		pf_qid_unref(altq->qid);
741 		free(altq, M_PFALTQ);
742 	}
743 	TAILQ_INIT(V_pf_altqs_inactive);
744 
745 	V_altqs_inactive_open = 0;
746 	return (error);
747 }
748 
749 static int
750 pf_enable_altq(struct pf_altq *altq)
751 {
752 	struct ifnet		*ifp;
753 	struct tb_profile	 tb;
754 	int			 error = 0;
755 
756 	if ((ifp = ifunit(altq->ifname)) == NULL)
757 		return (EINVAL);
758 
759 	if (ifp->if_snd.altq_type != ALTQT_NONE)
760 		error = altq_enable(&ifp->if_snd);
761 
762 	/* set tokenbucket regulator */
763 	if (error == 0 && ifp != NULL && ALTQ_IS_ENABLED(&ifp->if_snd)) {
764 		tb.rate = altq->ifbandwidth;
765 		tb.depth = altq->tbrsize;
766 		error = tbr_set(&ifp->if_snd, &tb);
767 	}
768 
769 	return (error);
770 }
771 
772 static int
773 pf_disable_altq(struct pf_altq *altq)
774 {
775 	struct ifnet		*ifp;
776 	struct tb_profile	 tb;
777 	int			 error;
778 
779 	if ((ifp = ifunit(altq->ifname)) == NULL)
780 		return (EINVAL);
781 
782 	/*
783 	 * when the discipline is no longer referenced, it was overridden
784 	 * by a new one.  if so, just return.
785 	 */
786 	if (altq->altq_disc != ifp->if_snd.altq_disc)
787 		return (0);
788 
789 	error = altq_disable(&ifp->if_snd);
790 
791 	if (error == 0) {
792 		/* clear tokenbucket regulator */
793 		tb.rate = 0;
794 		error = tbr_set(&ifp->if_snd, &tb);
795 	}
796 
797 	return (error);
798 }
799 
800 static int
801 pf_altq_ifnet_event_add(struct ifnet *ifp, int remove, u_int32_t ticket,
802     struct pf_altq *altq)
803 {
804 	struct ifnet	*ifp1;
805 	int		 error = 0;
806 
807 	/* Deactivate the interface in question */
808 	altq->local_flags &= ~PFALTQ_FLAG_IF_REMOVED;
809 	if ((ifp1 = ifunit(altq->ifname)) == NULL ||
810 	    (remove && ifp1 == ifp)) {
811 		altq->local_flags |= PFALTQ_FLAG_IF_REMOVED;
812 	} else {
813 		error = altq_add(ifp1, altq);
814 
815 		if (ticket != V_ticket_altqs_inactive)
816 			error = EBUSY;
817 
818 		if (error)
819 			free(altq, M_PFALTQ);
820 	}
821 
822 	return (error);
823 }
824 
825 void
826 pf_altq_ifnet_event(struct ifnet *ifp, int remove)
827 {
828 	struct pf_altq	*a1, *a2, *a3;
829 	u_int32_t	 ticket;
830 	int		 error = 0;
831 
832 	/*
833 	 * No need to re-evaluate the configuration for events on interfaces
834 	 * that do not support ALTQ, as it's not possible for such
835 	 * interfaces to be part of the configuration.
836 	 */
837 	if (!ALTQ_IS_READY(&ifp->if_snd))
838 		return;
839 
840 	/* Interrupt userland queue modifications */
841 	if (V_altqs_inactive_open)
842 		pf_rollback_altq(V_ticket_altqs_inactive);
843 
844 	/* Start new altq ruleset */
845 	if (pf_begin_altq(&ticket))
846 		return;
847 
848 	/* Copy the current active set */
849 	TAILQ_FOREACH(a1, V_pf_altq_ifs_active, entries) {
850 		a2 = malloc(sizeof(*a2), M_PFALTQ, M_NOWAIT);
851 		if (a2 == NULL) {
852 			error = ENOMEM;
853 			break;
854 		}
855 		bcopy(a1, a2, sizeof(struct pf_altq));
856 
857 		error = pf_altq_ifnet_event_add(ifp, remove, ticket, a2);
858 		if (error)
859 			break;
860 
861 		TAILQ_INSERT_TAIL(V_pf_altq_ifs_inactive, a2, entries);
862 	}
863 	if (error)
864 		goto out;
865 	TAILQ_FOREACH(a1, V_pf_altqs_active, entries) {
866 		a2 = malloc(sizeof(*a2), M_PFALTQ, M_NOWAIT);
867 		if (a2 == NULL) {
868 			error = ENOMEM;
869 			break;
870 		}
871 		bcopy(a1, a2, sizeof(struct pf_altq));
872 
873 		if ((a2->qid = pf_qname2qid(a2->qname)) == 0) {
874 			error = EBUSY;
875 			free(a2, M_PFALTQ);
876 			break;
877 		}
878 		a2->altq_disc = NULL;
879 		TAILQ_FOREACH(a3, V_pf_altq_ifs_inactive, entries) {
880 			if (strncmp(a3->ifname, a2->ifname,
881 				IFNAMSIZ) == 0) {
882 				a2->altq_disc = a3->altq_disc;
883 				break;
884 			}
885 		}
886 		error = pf_altq_ifnet_event_add(ifp, remove, ticket, a2);
887 		if (error)
888 			break;
889 
890 		TAILQ_INSERT_TAIL(V_pf_altqs_inactive, a2, entries);
891 	}
892 
893 out:
894 	if (error != 0)
895 		pf_rollback_altq(ticket);
896 	else
897 		pf_commit_altq(ticket);
898 }
899 #endif /* ALTQ */
900 
901 static int
902 pf_begin_rules(u_int32_t *ticket, int rs_num, const char *anchor)
903 {
904 	struct pf_kruleset	*rs;
905 	struct pf_krule		*rule;
906 
907 	PF_RULES_WASSERT();
908 
909 	if (rs_num < 0 || rs_num >= PF_RULESET_MAX)
910 		return (EINVAL);
911 	rs = pf_find_or_create_kruleset(anchor);
912 	if (rs == NULL)
913 		return (EINVAL);
914 	while ((rule = TAILQ_FIRST(rs->rules[rs_num].inactive.ptr)) != NULL) {
915 		pf_unlink_rule(rs->rules[rs_num].inactive.ptr, rule);
916 		rs->rules[rs_num].inactive.rcount--;
917 	}
918 	*ticket = ++rs->rules[rs_num].inactive.ticket;
919 	rs->rules[rs_num].inactive.open = 1;
920 	return (0);
921 }
922 
923 static int
924 pf_rollback_rules(u_int32_t ticket, int rs_num, char *anchor)
925 {
926 	struct pf_kruleset	*rs;
927 	struct pf_krule		*rule;
928 
929 	PF_RULES_WASSERT();
930 
931 	if (rs_num < 0 || rs_num >= PF_RULESET_MAX)
932 		return (EINVAL);
933 	rs = pf_find_kruleset(anchor);
934 	if (rs == NULL || !rs->rules[rs_num].inactive.open ||
935 	    rs->rules[rs_num].inactive.ticket != ticket)
936 		return (0);
937 	while ((rule = TAILQ_FIRST(rs->rules[rs_num].inactive.ptr)) != NULL) {
938 		pf_unlink_rule(rs->rules[rs_num].inactive.ptr, rule);
939 		rs->rules[rs_num].inactive.rcount--;
940 	}
941 	rs->rules[rs_num].inactive.open = 0;
942 	return (0);
943 }
944 
945 #define PF_MD5_UPD(st, elm)						\
946 		MD5Update(ctx, (u_int8_t *) &(st)->elm, sizeof((st)->elm))
947 
948 #define PF_MD5_UPD_STR(st, elm)						\
949 		MD5Update(ctx, (u_int8_t *) (st)->elm, strlen((st)->elm))
950 
951 #define PF_MD5_UPD_HTONL(st, elm, stor) do {				\
952 		(stor) = htonl((st)->elm);				\
953 		MD5Update(ctx, (u_int8_t *) &(stor), sizeof(u_int32_t));\
954 } while (0)
955 
956 #define PF_MD5_UPD_HTONS(st, elm, stor) do {				\
957 		(stor) = htons((st)->elm);				\
958 		MD5Update(ctx, (u_int8_t *) &(stor), sizeof(u_int16_t));\
959 } while (0)
960 
961 static void
962 pf_hash_rule_addr(MD5_CTX *ctx, struct pf_rule_addr *pfr)
963 {
964 	PF_MD5_UPD(pfr, addr.type);
965 	switch (pfr->addr.type) {
966 		case PF_ADDR_DYNIFTL:
967 			PF_MD5_UPD(pfr, addr.v.ifname);
968 			PF_MD5_UPD(pfr, addr.iflags);
969 			break;
970 		case PF_ADDR_TABLE:
971 			PF_MD5_UPD(pfr, addr.v.tblname);
972 			break;
973 		case PF_ADDR_ADDRMASK:
974 			/* XXX ignore af? */
975 			PF_MD5_UPD(pfr, addr.v.a.addr.addr32);
976 			PF_MD5_UPD(pfr, addr.v.a.mask.addr32);
977 			break;
978 	}
979 
980 	PF_MD5_UPD(pfr, port[0]);
981 	PF_MD5_UPD(pfr, port[1]);
982 	PF_MD5_UPD(pfr, neg);
983 	PF_MD5_UPD(pfr, port_op);
984 }
985 
986 static void
987 pf_hash_rule(MD5_CTX *ctx, struct pf_krule *rule)
988 {
989 	u_int16_t x;
990 	u_int32_t y;
991 
992 	pf_hash_rule_addr(ctx, &rule->src);
993 	pf_hash_rule_addr(ctx, &rule->dst);
994 	PF_MD5_UPD_STR(rule, label);
995 	PF_MD5_UPD_STR(rule, ifname);
996 	PF_MD5_UPD_STR(rule, match_tagname);
997 	PF_MD5_UPD_HTONS(rule, match_tag, x); /* dup? */
998 	PF_MD5_UPD_HTONL(rule, os_fingerprint, y);
999 	PF_MD5_UPD_HTONL(rule, prob, y);
1000 	PF_MD5_UPD_HTONL(rule, uid.uid[0], y);
1001 	PF_MD5_UPD_HTONL(rule, uid.uid[1], y);
1002 	PF_MD5_UPD(rule, uid.op);
1003 	PF_MD5_UPD_HTONL(rule, gid.gid[0], y);
1004 	PF_MD5_UPD_HTONL(rule, gid.gid[1], y);
1005 	PF_MD5_UPD(rule, gid.op);
1006 	PF_MD5_UPD_HTONL(rule, rule_flag, y);
1007 	PF_MD5_UPD(rule, action);
1008 	PF_MD5_UPD(rule, direction);
1009 	PF_MD5_UPD(rule, af);
1010 	PF_MD5_UPD(rule, quick);
1011 	PF_MD5_UPD(rule, ifnot);
1012 	PF_MD5_UPD(rule, match_tag_not);
1013 	PF_MD5_UPD(rule, natpass);
1014 	PF_MD5_UPD(rule, keep_state);
1015 	PF_MD5_UPD(rule, proto);
1016 	PF_MD5_UPD(rule, type);
1017 	PF_MD5_UPD(rule, code);
1018 	PF_MD5_UPD(rule, flags);
1019 	PF_MD5_UPD(rule, flagset);
1020 	PF_MD5_UPD(rule, allow_opts);
1021 	PF_MD5_UPD(rule, rt);
1022 	PF_MD5_UPD(rule, tos);
1023 }
1024 
1025 static int
1026 pf_commit_rules(u_int32_t ticket, int rs_num, char *anchor)
1027 {
1028 	struct pf_kruleset	*rs;
1029 	struct pf_krule		*rule, **old_array;
1030 	struct pf_krulequeue	*old_rules;
1031 	int			 error;
1032 	u_int32_t		 old_rcount;
1033 
1034 	PF_RULES_WASSERT();
1035 
1036 	if (rs_num < 0 || rs_num >= PF_RULESET_MAX)
1037 		return (EINVAL);
1038 	rs = pf_find_kruleset(anchor);
1039 	if (rs == NULL || !rs->rules[rs_num].inactive.open ||
1040 	    ticket != rs->rules[rs_num].inactive.ticket)
1041 		return (EBUSY);
1042 
1043 	/* Calculate checksum for the main ruleset */
1044 	if (rs == &pf_main_ruleset) {
1045 		error = pf_setup_pfsync_matching(rs);
1046 		if (error != 0)
1047 			return (error);
1048 	}
1049 
1050 	/* Swap rules, keep the old. */
1051 	old_rules = rs->rules[rs_num].active.ptr;
1052 	old_rcount = rs->rules[rs_num].active.rcount;
1053 	old_array = rs->rules[rs_num].active.ptr_array;
1054 
1055 	rs->rules[rs_num].active.ptr =
1056 	    rs->rules[rs_num].inactive.ptr;
1057 	rs->rules[rs_num].active.ptr_array =
1058 	    rs->rules[rs_num].inactive.ptr_array;
1059 	rs->rules[rs_num].active.rcount =
1060 	    rs->rules[rs_num].inactive.rcount;
1061 	rs->rules[rs_num].inactive.ptr = old_rules;
1062 	rs->rules[rs_num].inactive.ptr_array = old_array;
1063 	rs->rules[rs_num].inactive.rcount = old_rcount;
1064 
1065 	rs->rules[rs_num].active.ticket =
1066 	    rs->rules[rs_num].inactive.ticket;
1067 	pf_calc_skip_steps(rs->rules[rs_num].active.ptr);
1068 
1069 	/* Purge the old rule list. */
1070 	while ((rule = TAILQ_FIRST(old_rules)) != NULL)
1071 		pf_unlink_rule(old_rules, rule);
1072 	if (rs->rules[rs_num].inactive.ptr_array)
1073 		free(rs->rules[rs_num].inactive.ptr_array, M_TEMP);
1074 	rs->rules[rs_num].inactive.ptr_array = NULL;
1075 	rs->rules[rs_num].inactive.rcount = 0;
1076 	rs->rules[rs_num].inactive.open = 0;
1077 	pf_remove_if_empty_kruleset(rs);
1078 
1079 	return (0);
1080 }
1081 
1082 static int
1083 pf_setup_pfsync_matching(struct pf_kruleset *rs)
1084 {
1085 	MD5_CTX			 ctx;
1086 	struct pf_krule		*rule;
1087 	int			 rs_cnt;
1088 	u_int8_t		 digest[PF_MD5_DIGEST_LENGTH];
1089 
1090 	MD5Init(&ctx);
1091 	for (rs_cnt = 0; rs_cnt < PF_RULESET_MAX; rs_cnt++) {
1092 		/* XXX PF_RULESET_SCRUB as well? */
1093 		if (rs_cnt == PF_RULESET_SCRUB)
1094 			continue;
1095 
1096 		if (rs->rules[rs_cnt].inactive.ptr_array)
1097 			free(rs->rules[rs_cnt].inactive.ptr_array, M_TEMP);
1098 		rs->rules[rs_cnt].inactive.ptr_array = NULL;
1099 
1100 		if (rs->rules[rs_cnt].inactive.rcount) {
1101 			rs->rules[rs_cnt].inactive.ptr_array =
1102 			    malloc(sizeof(caddr_t) *
1103 			    rs->rules[rs_cnt].inactive.rcount,
1104 			    M_TEMP, M_NOWAIT);
1105 
1106 			if (!rs->rules[rs_cnt].inactive.ptr_array)
1107 				return (ENOMEM);
1108 		}
1109 
1110 		TAILQ_FOREACH(rule, rs->rules[rs_cnt].inactive.ptr,
1111 		    entries) {
1112 			pf_hash_rule(&ctx, rule);
1113 			(rs->rules[rs_cnt].inactive.ptr_array)[rule->nr] = rule;
1114 		}
1115 	}
1116 
1117 	MD5Final(digest, &ctx);
1118 	memcpy(V_pf_status.pf_chksum, digest, sizeof(V_pf_status.pf_chksum));
1119 	return (0);
1120 }
1121 
1122 static int
1123 pf_addr_setup(struct pf_kruleset *ruleset, struct pf_addr_wrap *addr,
1124     sa_family_t af)
1125 {
1126 	int error = 0;
1127 
1128 	switch (addr->type) {
1129 	case PF_ADDR_TABLE:
1130 		addr->p.tbl = pfr_attach_table(ruleset, addr->v.tblname);
1131 		if (addr->p.tbl == NULL)
1132 			error = ENOMEM;
1133 		break;
1134 	case PF_ADDR_DYNIFTL:
1135 		error = pfi_dynaddr_setup(addr, af);
1136 		break;
1137 	}
1138 
1139 	return (error);
1140 }
1141 
1142 static void
1143 pf_addr_copyout(struct pf_addr_wrap *addr)
1144 {
1145 
1146 	switch (addr->type) {
1147 	case PF_ADDR_DYNIFTL:
1148 		pfi_dynaddr_copyout(addr);
1149 		break;
1150 	case PF_ADDR_TABLE:
1151 		pf_tbladdr_copyout(addr);
1152 		break;
1153 	}
1154 }
1155 
1156 static void
1157 pf_src_node_copy(const struct pf_ksrc_node *in, struct pf_src_node *out)
1158 {
1159 	int	secs = time_uptime, diff;
1160 
1161 	bzero(out, sizeof(struct pf_src_node));
1162 
1163 	bcopy(&in->addr, &out->addr, sizeof(struct pf_addr));
1164 	bcopy(&in->raddr, &out->raddr, sizeof(struct pf_addr));
1165 
1166 	if (in->rule.ptr != NULL)
1167 		out->rule.nr = in->rule.ptr->nr;
1168 
1169 	for (int i = 0; i < 2; i++) {
1170 		out->bytes[i] = counter_u64_fetch(in->bytes[i]);
1171 		out->packets[i] = counter_u64_fetch(in->packets[i]);
1172 	}
1173 
1174 	out->states = in->states;
1175 	out->conn = in->conn;
1176 	out->af = in->af;
1177 	out->ruletype = in->ruletype;
1178 
1179 	out->creation = secs - in->creation;
1180 	if (out->expire > secs)
1181 		out->expire -= secs;
1182 	else
1183 		out->expire = 0;
1184 
1185 	/* Adjust the connection rate estimate. */
1186 	diff = secs - in->conn_rate.last;
1187 	if (diff >= in->conn_rate.seconds)
1188 		out->conn_rate.count = 0;
1189 	else
1190 		out->conn_rate.count -=
1191 		    in->conn_rate.count * diff /
1192 		    in->conn_rate.seconds;
1193 }
1194 
1195 #ifdef ALTQ
1196 /*
1197  * Handle export of struct pf_kaltq to user binaries that may be using any
1198  * version of struct pf_altq.
1199  */
1200 static int
1201 pf_export_kaltq(struct pf_altq *q, struct pfioc_altq_v1 *pa, size_t ioc_size)
1202 {
1203 	u_int32_t version;
1204 
1205 	if (ioc_size == sizeof(struct pfioc_altq_v0))
1206 		version = 0;
1207 	else
1208 		version = pa->version;
1209 
1210 	if (version > PFIOC_ALTQ_VERSION)
1211 		return (EINVAL);
1212 
1213 #define ASSIGN(x) exported_q->x = q->x
1214 #define COPY(x) \
1215 	bcopy(&q->x, &exported_q->x, min(sizeof(q->x), sizeof(exported_q->x)))
1216 #define SATU16(x) (u_int32_t)uqmin((x), USHRT_MAX)
1217 #define SATU32(x) (u_int32_t)uqmin((x), UINT_MAX)
1218 
1219 	switch (version) {
1220 	case 0: {
1221 		struct pf_altq_v0 *exported_q =
1222 		    &((struct pfioc_altq_v0 *)pa)->altq;
1223 
1224 		COPY(ifname);
1225 
1226 		ASSIGN(scheduler);
1227 		ASSIGN(tbrsize);
1228 		exported_q->tbrsize = SATU16(q->tbrsize);
1229 		exported_q->ifbandwidth = SATU32(q->ifbandwidth);
1230 
1231 		COPY(qname);
1232 		COPY(parent);
1233 		ASSIGN(parent_qid);
1234 		exported_q->bandwidth = SATU32(q->bandwidth);
1235 		ASSIGN(priority);
1236 		ASSIGN(local_flags);
1237 
1238 		ASSIGN(qlimit);
1239 		ASSIGN(flags);
1240 
1241 		if (q->scheduler == ALTQT_HFSC) {
1242 #define ASSIGN_OPT(x) exported_q->pq_u.hfsc_opts.x = q->pq_u.hfsc_opts.x
1243 #define ASSIGN_OPT_SATU32(x) exported_q->pq_u.hfsc_opts.x = \
1244 			    SATU32(q->pq_u.hfsc_opts.x)
1245 
1246 			ASSIGN_OPT_SATU32(rtsc_m1);
1247 			ASSIGN_OPT(rtsc_d);
1248 			ASSIGN_OPT_SATU32(rtsc_m2);
1249 
1250 			ASSIGN_OPT_SATU32(lssc_m1);
1251 			ASSIGN_OPT(lssc_d);
1252 			ASSIGN_OPT_SATU32(lssc_m2);
1253 
1254 			ASSIGN_OPT_SATU32(ulsc_m1);
1255 			ASSIGN_OPT(ulsc_d);
1256 			ASSIGN_OPT_SATU32(ulsc_m2);
1257 
1258 			ASSIGN_OPT(flags);
1259 
1260 #undef ASSIGN_OPT
1261 #undef ASSIGN_OPT_SATU32
1262 		} else
1263 			COPY(pq_u);
1264 
1265 		ASSIGN(qid);
1266 		break;
1267 	}
1268 	case 1:	{
1269 		struct pf_altq_v1 *exported_q =
1270 		    &((struct pfioc_altq_v1 *)pa)->altq;
1271 
1272 		COPY(ifname);
1273 
1274 		ASSIGN(scheduler);
1275 		ASSIGN(tbrsize);
1276 		ASSIGN(ifbandwidth);
1277 
1278 		COPY(qname);
1279 		COPY(parent);
1280 		ASSIGN(parent_qid);
1281 		ASSIGN(bandwidth);
1282 		ASSIGN(priority);
1283 		ASSIGN(local_flags);
1284 
1285 		ASSIGN(qlimit);
1286 		ASSIGN(flags);
1287 		COPY(pq_u);
1288 
1289 		ASSIGN(qid);
1290 		break;
1291 	}
1292 	default:
1293 		panic("%s: unhandled struct pfioc_altq version", __func__);
1294 		break;
1295 	}
1296 
1297 #undef ASSIGN
1298 #undef COPY
1299 #undef SATU16
1300 #undef SATU32
1301 
1302 	return (0);
1303 }
1304 
1305 /*
1306  * Handle import to struct pf_kaltq of struct pf_altq from user binaries
1307  * that may be using any version of it.
1308  */
1309 static int
1310 pf_import_kaltq(struct pfioc_altq_v1 *pa, struct pf_altq *q, size_t ioc_size)
1311 {
1312 	u_int32_t version;
1313 
1314 	if (ioc_size == sizeof(struct pfioc_altq_v0))
1315 		version = 0;
1316 	else
1317 		version = pa->version;
1318 
1319 	if (version > PFIOC_ALTQ_VERSION)
1320 		return (EINVAL);
1321 
1322 #define ASSIGN(x) q->x = imported_q->x
1323 #define COPY(x) \
1324 	bcopy(&imported_q->x, &q->x, min(sizeof(imported_q->x), sizeof(q->x)))
1325 
1326 	switch (version) {
1327 	case 0: {
1328 		struct pf_altq_v0 *imported_q =
1329 		    &((struct pfioc_altq_v0 *)pa)->altq;
1330 
1331 		COPY(ifname);
1332 
1333 		ASSIGN(scheduler);
1334 		ASSIGN(tbrsize); /* 16-bit -> 32-bit */
1335 		ASSIGN(ifbandwidth); /* 32-bit -> 64-bit */
1336 
1337 		COPY(qname);
1338 		COPY(parent);
1339 		ASSIGN(parent_qid);
1340 		ASSIGN(bandwidth); /* 32-bit -> 64-bit */
1341 		ASSIGN(priority);
1342 		ASSIGN(local_flags);
1343 
1344 		ASSIGN(qlimit);
1345 		ASSIGN(flags);
1346 
1347 		if (imported_q->scheduler == ALTQT_HFSC) {
1348 #define ASSIGN_OPT(x) q->pq_u.hfsc_opts.x = imported_q->pq_u.hfsc_opts.x
1349 
1350 			/*
1351 			 * The m1 and m2 parameters are being copied from
1352 			 * 32-bit to 64-bit.
1353 			 */
1354 			ASSIGN_OPT(rtsc_m1);
1355 			ASSIGN_OPT(rtsc_d);
1356 			ASSIGN_OPT(rtsc_m2);
1357 
1358 			ASSIGN_OPT(lssc_m1);
1359 			ASSIGN_OPT(lssc_d);
1360 			ASSIGN_OPT(lssc_m2);
1361 
1362 			ASSIGN_OPT(ulsc_m1);
1363 			ASSIGN_OPT(ulsc_d);
1364 			ASSIGN_OPT(ulsc_m2);
1365 
1366 			ASSIGN_OPT(flags);
1367 
1368 #undef ASSIGN_OPT
1369 		} else
1370 			COPY(pq_u);
1371 
1372 		ASSIGN(qid);
1373 		break;
1374 	}
1375 	case 1: {
1376 		struct pf_altq_v1 *imported_q =
1377 		    &((struct pfioc_altq_v1 *)pa)->altq;
1378 
1379 		COPY(ifname);
1380 
1381 		ASSIGN(scheduler);
1382 		ASSIGN(tbrsize);
1383 		ASSIGN(ifbandwidth);
1384 
1385 		COPY(qname);
1386 		COPY(parent);
1387 		ASSIGN(parent_qid);
1388 		ASSIGN(bandwidth);
1389 		ASSIGN(priority);
1390 		ASSIGN(local_flags);
1391 
1392 		ASSIGN(qlimit);
1393 		ASSIGN(flags);
1394 		COPY(pq_u);
1395 
1396 		ASSIGN(qid);
1397 		break;
1398 	}
1399 	default:
1400 		panic("%s: unhandled struct pfioc_altq version", __func__);
1401 		break;
1402 	}
1403 
1404 #undef ASSIGN
1405 #undef COPY
1406 
1407 	return (0);
1408 }
1409 
1410 static struct pf_altq *
1411 pf_altq_get_nth_active(u_int32_t n)
1412 {
1413 	struct pf_altq		*altq;
1414 	u_int32_t		 nr;
1415 
1416 	nr = 0;
1417 	TAILQ_FOREACH(altq, V_pf_altq_ifs_active, entries) {
1418 		if (nr == n)
1419 			return (altq);
1420 		nr++;
1421 	}
1422 
1423 	TAILQ_FOREACH(altq, V_pf_altqs_active, entries) {
1424 		if (nr == n)
1425 			return (altq);
1426 		nr++;
1427 	}
1428 
1429 	return (NULL);
1430 }
1431 #endif /* ALTQ */
1432 
1433 void
1434 pf_krule_free(struct pf_krule *rule)
1435 {
1436 	if (rule == NULL)
1437 		return;
1438 
1439 	counter_u64_free(rule->evaluations);
1440 	for (int i = 0; i < 2; i++) {
1441 		counter_u64_free(rule->packets[i]);
1442 		counter_u64_free(rule->bytes[i]);
1443 	}
1444 	counter_u64_free(rule->states_cur);
1445 	counter_u64_free(rule->states_tot);
1446 	counter_u64_free(rule->src_nodes);
1447 	free(rule, M_PFRULE);
1448 }
1449 
1450 static void
1451 pf_kpooladdr_to_pooladdr(const struct pf_kpooladdr *kpool,
1452     struct pf_pooladdr *pool)
1453 {
1454 
1455 	bzero(pool, sizeof(*pool));
1456 	bcopy(&kpool->addr, &pool->addr, sizeof(pool->addr));
1457 	strlcpy(pool->ifname, kpool->ifname, sizeof(pool->ifname));
1458 }
1459 
1460 static void
1461 pf_pooladdr_to_kpooladdr(const struct pf_pooladdr *pool,
1462     struct pf_kpooladdr *kpool)
1463 {
1464 
1465 	bzero(kpool, sizeof(*kpool));
1466 	bcopy(&pool->addr, &kpool->addr, sizeof(kpool->addr));
1467 	strlcpy(kpool->ifname, pool->ifname, sizeof(kpool->ifname));
1468 }
1469 
1470 static void
1471 pf_kpool_to_pool(const struct pf_kpool *kpool, struct pf_pool *pool)
1472 {
1473 	bzero(pool, sizeof(*pool));
1474 
1475 	bcopy(&kpool->key, &pool->key, sizeof(pool->key));
1476 	bcopy(&kpool->counter, &pool->counter, sizeof(pool->counter));
1477 
1478 	pool->tblidx = kpool->tblidx;
1479 	pool->proxy_port[0] = kpool->proxy_port[0];
1480 	pool->proxy_port[1] = kpool->proxy_port[1];
1481 	pool->opts = kpool->opts;
1482 }
1483 
1484 static int
1485 pf_pool_to_kpool(const struct pf_pool *pool, struct pf_kpool *kpool)
1486 {
1487 	_Static_assert(sizeof(pool->key) == sizeof(kpool->key), "");
1488 	_Static_assert(sizeof(pool->counter) == sizeof(kpool->counter), "");
1489 
1490 	bzero(kpool, sizeof(*kpool));
1491 
1492 	bcopy(&pool->key, &kpool->key, sizeof(kpool->key));
1493 	bcopy(&pool->counter, &kpool->counter, sizeof(kpool->counter));
1494 
1495 	kpool->tblidx = pool->tblidx;
1496 	kpool->proxy_port[0] = pool->proxy_port[0];
1497 	kpool->proxy_port[1] = pool->proxy_port[1];
1498 	kpool->opts = pool->opts;
1499 
1500 	return (0);
1501 }
1502 
1503 static void
1504 pf_krule_to_rule(const struct pf_krule *krule, struct pf_rule *rule)
1505 {
1506 
1507 	bzero(rule, sizeof(*rule));
1508 
1509 	bcopy(&krule->src, &rule->src, sizeof(rule->src));
1510 	bcopy(&krule->dst, &rule->dst, sizeof(rule->dst));
1511 
1512 	for (int i = 0; i < PF_SKIP_COUNT; ++i) {
1513 		if (rule->skip[i].ptr == NULL)
1514 			rule->skip[i].nr = -1;
1515 		else
1516 			rule->skip[i].nr = krule->skip[i].ptr->nr;
1517 	}
1518 
1519 	strlcpy(rule->label, krule->label, sizeof(rule->label));
1520 	strlcpy(rule->ifname, krule->ifname, sizeof(rule->ifname));
1521 	strlcpy(rule->qname, krule->qname, sizeof(rule->qname));
1522 	strlcpy(rule->pqname, krule->pqname, sizeof(rule->pqname));
1523 	strlcpy(rule->tagname, krule->tagname, sizeof(rule->tagname));
1524 	strlcpy(rule->match_tagname, krule->match_tagname,
1525 	    sizeof(rule->match_tagname));
1526 	strlcpy(rule->overload_tblname, krule->overload_tblname,
1527 	    sizeof(rule->overload_tblname));
1528 
1529 	pf_kpool_to_pool(&krule->rpool, &rule->rpool);
1530 
1531 	rule->evaluations = counter_u64_fetch(krule->evaluations);
1532 	for (int i = 0; i < 2; i++) {
1533 		rule->packets[i] = counter_u64_fetch(krule->packets[i]);
1534 		rule->bytes[i] = counter_u64_fetch(krule->bytes[i]);
1535 	}
1536 
1537 	/* kif, anchor, overload_tbl are not copied over. */
1538 
1539 	rule->os_fingerprint = krule->os_fingerprint;
1540 
1541 	rule->rtableid = krule->rtableid;
1542 	bcopy(krule->timeout, rule->timeout, sizeof(krule->timeout));
1543 	rule->max_states = krule->max_states;
1544 	rule->max_src_nodes = krule->max_src_nodes;
1545 	rule->max_src_states = krule->max_src_states;
1546 	rule->max_src_conn = krule->max_src_conn;
1547 	rule->max_src_conn_rate.limit = krule->max_src_conn_rate.limit;
1548 	rule->max_src_conn_rate.seconds = krule->max_src_conn_rate.seconds;
1549 	rule->qid = krule->qid;
1550 	rule->pqid = krule->pqid;
1551 	rule->nr = krule->nr;
1552 	rule->prob = krule->prob;
1553 	rule->cuid = krule->cuid;
1554 	rule->cpid = krule->cpid;
1555 
1556 	rule->return_icmp = krule->return_icmp;
1557 	rule->return_icmp6 = krule->return_icmp6;
1558 	rule->max_mss = krule->max_mss;
1559 	rule->tag = krule->tag;
1560 	rule->match_tag = krule->match_tag;
1561 	rule->scrub_flags = krule->scrub_flags;
1562 
1563 	bcopy(&krule->uid, &rule->uid, sizeof(krule->uid));
1564 	bcopy(&krule->gid, &rule->gid, sizeof(krule->gid));
1565 
1566 	rule->rule_flag = krule->rule_flag;
1567 	rule->action = krule->action;
1568 	rule->direction = krule->direction;
1569 	rule->log = krule->log;
1570 	rule->logif = krule->logif;
1571 	rule->quick = krule->quick;
1572 	rule->ifnot = krule->ifnot;
1573 	rule->match_tag_not = krule->match_tag_not;
1574 	rule->natpass = krule->natpass;
1575 
1576 	rule->keep_state = krule->keep_state;
1577 	rule->af = krule->af;
1578 	rule->proto = krule->proto;
1579 	rule->type = krule->type;
1580 	rule->code = krule->code;
1581 	rule->flags = krule->flags;
1582 	rule->flagset = krule->flagset;
1583 	rule->min_ttl = krule->min_ttl;
1584 	rule->allow_opts = krule->allow_opts;
1585 	rule->rt = krule->rt;
1586 	rule->return_ttl = krule->return_ttl;
1587 	rule->tos = krule->tos;
1588 	rule->set_tos = krule->set_tos;
1589 	rule->anchor_relative = krule->anchor_relative;
1590 	rule->anchor_wildcard = krule->anchor_wildcard;
1591 
1592 	rule->flush = krule->flush;
1593 	rule->prio = krule->prio;
1594 	rule->set_prio[0] = krule->set_prio[0];
1595 	rule->set_prio[1] = krule->set_prio[1];
1596 
1597 	bcopy(&krule->divert, &rule->divert, sizeof(krule->divert));
1598 
1599 	rule->u_states_cur = counter_u64_fetch(krule->states_cur);
1600 	rule->u_states_tot = counter_u64_fetch(krule->states_tot);
1601 	rule->u_src_nodes = counter_u64_fetch(krule->src_nodes);
1602 }
1603 
1604 static int
1605 pf_check_rule_addr(const struct pf_rule_addr *addr)
1606 {
1607 
1608 	switch (addr->addr.type) {
1609 	case PF_ADDR_ADDRMASK:
1610 	case PF_ADDR_NOROUTE:
1611 	case PF_ADDR_DYNIFTL:
1612 	case PF_ADDR_TABLE:
1613 	case PF_ADDR_URPFFAILED:
1614 	case PF_ADDR_RANGE:
1615 		break;
1616 	default:
1617 		return (EINVAL);
1618 	}
1619 
1620 	if (addr->addr.p.dyn != NULL) {
1621 		return (EINVAL);
1622 	}
1623 
1624 	return (0);
1625 }
1626 
1627 static int
1628 pf_nvaddr_to_addr(const nvlist_t *nvl, struct pf_addr *paddr)
1629 {
1630 	return (pf_nvbinary(nvl, "addr", paddr, sizeof(*paddr)));
1631 }
1632 
1633 static nvlist_t *
1634 pf_addr_to_nvaddr(const struct pf_addr *paddr)
1635 {
1636 	nvlist_t *nvl;
1637 
1638 	nvl = nvlist_create(0);
1639 	if (nvl == NULL)
1640 		return (NULL);
1641 
1642 	nvlist_add_binary(nvl, "addr", paddr, sizeof(*paddr));
1643 
1644 	return (nvl);
1645 }
1646 
1647 static int
1648 pf_nvmape_to_mape(const nvlist_t *nvl, struct pf_mape_portset *mape)
1649 {
1650 	int error = 0;
1651 
1652 	bzero(mape, sizeof(*mape));
1653 	PFNV_CHK(pf_nvuint8(nvl, "offset", &mape->offset));
1654 	PFNV_CHK(pf_nvuint8(nvl, "psidlen", &mape->psidlen));
1655 	PFNV_CHK(pf_nvuint16(nvl, "psid", &mape->psid));
1656 
1657 errout:
1658 	return (error);
1659 }
1660 
1661 static nvlist_t *
1662 pf_mape_to_nvmape(const struct pf_mape_portset *mape)
1663 {
1664 	nvlist_t *nvl;
1665 
1666 	nvl = nvlist_create(0);
1667 	if (nvl == NULL)
1668 		return (NULL);
1669 
1670 	nvlist_add_number(nvl, "offset", mape->offset);
1671 	nvlist_add_number(nvl, "psidlen", mape->psidlen);
1672 	nvlist_add_number(nvl, "psid", mape->psid);
1673 
1674 	return (nvl);
1675 }
1676 
1677 static int
1678 pf_nvpool_to_pool(const nvlist_t *nvl, struct pf_kpool *kpool)
1679 {
1680 	int error = 0;
1681 
1682 	bzero(kpool, sizeof(*kpool));
1683 
1684 	PFNV_CHK(pf_nvbinary(nvl, "key", &kpool->key, sizeof(kpool->key)));
1685 
1686 	if (nvlist_exists_nvlist(nvl, "counter")) {
1687 		PFNV_CHK(pf_nvaddr_to_addr(nvlist_get_nvlist(nvl, "counter"),
1688 		    &kpool->counter));
1689 	}
1690 
1691 	PFNV_CHK(pf_nvint(nvl, "tblidx", &kpool->tblidx));
1692 	PFNV_CHK(pf_nvuint16_array(nvl, "proxy_port", kpool->proxy_port, 2,
1693 	    NULL));
1694 	PFNV_CHK(pf_nvuint8(nvl, "opts", &kpool->opts));
1695 
1696 	if (nvlist_exists_nvlist(nvl, "mape")) {
1697 		PFNV_CHK(pf_nvmape_to_mape(nvlist_get_nvlist(nvl, "mape"),
1698 		    &kpool->mape));
1699 	}
1700 
1701 errout:
1702 	return (error);
1703 }
1704 
1705 static nvlist_t *
1706 pf_pool_to_nvpool(const struct pf_kpool *pool)
1707 {
1708 	nvlist_t *nvl;
1709 	nvlist_t *tmp;
1710 
1711 	nvl = nvlist_create(0);
1712 	if (nvl == NULL)
1713 		return (NULL);
1714 
1715 	nvlist_add_binary(nvl, "key", &pool->key, sizeof(pool->key));
1716 	tmp = pf_addr_to_nvaddr(&pool->counter);
1717 	if (tmp == NULL)
1718 		goto error;
1719 	nvlist_add_nvlist(nvl, "counter", tmp);
1720 
1721 	nvlist_add_number(nvl, "tblidx", pool->tblidx);
1722 	pf_uint16_array_nv(nvl, "proxy_port", pool->proxy_port, 2);
1723 	nvlist_add_number(nvl, "opts", pool->opts);
1724 
1725 	tmp = pf_mape_to_nvmape(&pool->mape);
1726 	if (tmp == NULL)
1727 		goto error;
1728 	nvlist_add_nvlist(nvl, "mape", tmp);
1729 
1730 	return (nvl);
1731 
1732 error:
1733 	nvlist_destroy(nvl);
1734 	return (NULL);
1735 }
1736 
1737 static int
1738 pf_nvaddr_wrap_to_addr_wrap(const nvlist_t *nvl, struct pf_addr_wrap *addr)
1739 {
1740 	int error = 0;
1741 
1742 	bzero(addr, sizeof(*addr));
1743 
1744 	PFNV_CHK(pf_nvuint8(nvl, "type", &addr->type));
1745 	PFNV_CHK(pf_nvuint8(nvl, "iflags", &addr->iflags));
1746 	PFNV_CHK(pf_nvstring(nvl, "ifname", addr->v.ifname,
1747 	    sizeof(addr->v.ifname)));
1748 	PFNV_CHK(pf_nvstring(nvl, "tblname", addr->v.tblname,
1749 	    sizeof(addr->v.tblname)));
1750 
1751 	if (! nvlist_exists_nvlist(nvl, "addr"))
1752 		return (EINVAL);
1753 	PFNV_CHK(pf_nvaddr_to_addr(nvlist_get_nvlist(nvl, "addr"),
1754 	    &addr->v.a.addr));
1755 
1756 	if (! nvlist_exists_nvlist(nvl, "mask"))
1757 		return (EINVAL);
1758 	PFNV_CHK(pf_nvaddr_to_addr(nvlist_get_nvlist(nvl, "mask"),
1759 	    &addr->v.a.mask));
1760 
1761 	switch (addr->type) {
1762 	case PF_ADDR_DYNIFTL:
1763 	case PF_ADDR_TABLE:
1764 	case PF_ADDR_RANGE:
1765 	case PF_ADDR_ADDRMASK:
1766 	case PF_ADDR_NOROUTE:
1767 	case PF_ADDR_URPFFAILED:
1768 		break;
1769 	default:
1770 		return (EINVAL);
1771 	}
1772 
1773 errout:
1774 	return (error);
1775 }
1776 
1777 static nvlist_t *
1778 pf_addr_wrap_to_nvaddr_wrap(const struct pf_addr_wrap *addr)
1779 {
1780 	nvlist_t *nvl;
1781 	nvlist_t *tmp;
1782 
1783 	nvl = nvlist_create(0);
1784 	if (nvl == NULL)
1785 		return (NULL);
1786 
1787 	nvlist_add_number(nvl, "type", addr->type);
1788 	nvlist_add_number(nvl, "iflags", addr->iflags);
1789 	nvlist_add_string(nvl, "ifname", addr->v.ifname);
1790 	nvlist_add_string(nvl, "tblname", addr->v.tblname);
1791 
1792 	tmp = pf_addr_to_nvaddr(&addr->v.a.addr);
1793 	if (tmp == NULL)
1794 		goto error;
1795 	nvlist_add_nvlist(nvl, "addr", tmp);
1796 	tmp = pf_addr_to_nvaddr(&addr->v.a.mask);
1797 	if (tmp == NULL)
1798 		goto error;
1799 	nvlist_add_nvlist(nvl, "mask", tmp);
1800 
1801 	return (nvl);
1802 
1803 error:
1804 	nvlist_destroy(nvl);
1805 	return (NULL);
1806 }
1807 
1808 static int
1809 pf_validate_op(uint8_t op)
1810 {
1811 	switch (op) {
1812 	case PF_OP_NONE:
1813 	case PF_OP_IRG:
1814 	case PF_OP_EQ:
1815 	case PF_OP_NE:
1816 	case PF_OP_LT:
1817 	case PF_OP_LE:
1818 	case PF_OP_GT:
1819 	case PF_OP_GE:
1820 	case PF_OP_XRG:
1821 	case PF_OP_RRG:
1822 		break;
1823 	default:
1824 		return (EINVAL);
1825 	}
1826 
1827 	return (0);
1828 }
1829 
1830 static int
1831 pf_nvrule_addr_to_rule_addr(const nvlist_t *nvl, struct pf_rule_addr *addr)
1832 {
1833 	int error = 0;
1834 
1835 	if (! nvlist_exists_nvlist(nvl, "addr"))
1836 		return (EINVAL);
1837 
1838 	PFNV_CHK(pf_nvaddr_wrap_to_addr_wrap(nvlist_get_nvlist(nvl, "addr"),
1839 	    &addr->addr));
1840 	PFNV_CHK(pf_nvuint16_array(nvl, "port", addr->port, 2, NULL));
1841 	PFNV_CHK(pf_nvuint8(nvl, "neg", &addr->neg));
1842 	PFNV_CHK(pf_nvuint8(nvl, "port_op", &addr->port_op));
1843 
1844 	PFNV_CHK(pf_validate_op(addr->port_op));
1845 
1846 errout:
1847 	return (error);
1848 }
1849 
1850 static nvlist_t *
1851 pf_rule_addr_to_nvrule_addr(const struct pf_rule_addr *addr)
1852 {
1853 	nvlist_t *nvl;
1854 	nvlist_t *tmp;
1855 
1856 	nvl = nvlist_create(0);
1857 	if (nvl == NULL)
1858 		return (NULL);
1859 
1860 	tmp = pf_addr_wrap_to_nvaddr_wrap(&addr->addr);
1861 	if (tmp == NULL)
1862 		goto error;
1863 	nvlist_add_nvlist(nvl, "addr", tmp);
1864 	pf_uint16_array_nv(nvl, "port", addr->port, 2);
1865 	nvlist_add_number(nvl, "neg", addr->neg);
1866 	nvlist_add_number(nvl, "port_op", addr->port_op);
1867 
1868 	return (nvl);
1869 
1870 error:
1871 	nvlist_destroy(nvl);
1872 	return (NULL);
1873 }
1874 
1875 static int
1876 pf_nvrule_uid_to_rule_uid(const nvlist_t *nvl, struct pf_rule_uid *uid)
1877 {
1878 	int error = 0;
1879 
1880 	bzero(uid, sizeof(*uid));
1881 
1882 	PFNV_CHK(pf_nvuint32_array(nvl, "uid", uid->uid, 2, NULL));
1883 	PFNV_CHK(pf_nvuint8(nvl, "op", &uid->op));
1884 
1885 	PFNV_CHK(pf_validate_op(uid->op));
1886 
1887 errout:
1888 	return (error);
1889 }
1890 
1891 static nvlist_t *
1892 pf_rule_uid_to_nvrule_uid(const struct pf_rule_uid *uid)
1893 {
1894 	nvlist_t *nvl;
1895 
1896 	nvl = nvlist_create(0);
1897 	if (nvl == NULL)
1898 		return (NULL);
1899 
1900 	pf_uint32_array_nv(nvl, "uid", uid->uid, 2);
1901 	nvlist_add_number(nvl, "op", uid->op);
1902 
1903 	return (nvl);
1904 }
1905 
1906 static int
1907 pf_nvrule_gid_to_rule_gid(const nvlist_t *nvl, struct pf_rule_gid *gid)
1908 {
1909 	/* Cheat a little. These stucts are the same, other than the name of
1910 	 * the first field. */
1911 	return (pf_nvrule_uid_to_rule_uid(nvl, (struct pf_rule_uid *)gid));
1912 }
1913 
1914 static int
1915 pf_nvrule_to_krule(const nvlist_t *nvl, struct pf_krule **prule)
1916 {
1917 	struct pf_krule *rule;
1918 	int error = 0;
1919 
1920 	rule = malloc(sizeof(*rule), M_PFRULE, M_WAITOK | M_ZERO);
1921 
1922 	PFNV_CHK(pf_nvuint32(nvl, "nr", &rule->nr));
1923 
1924 	if (! nvlist_exists_nvlist(nvl, "src")) {
1925 		error = EINVAL;
1926 		goto errout;
1927 	}
1928 	error = pf_nvrule_addr_to_rule_addr(nvlist_get_nvlist(nvl, "src"),
1929 	    &rule->src);
1930 	if (error != 0)
1931 		goto errout;
1932 
1933 	if (! nvlist_exists_nvlist(nvl, "dst")) {
1934 		error = EINVAL;
1935 		goto errout;
1936 	}
1937 	PFNV_CHK(pf_nvrule_addr_to_rule_addr(nvlist_get_nvlist(nvl, "dst"),
1938 	    &rule->dst));
1939 
1940 	PFNV_CHK(pf_nvstring(nvl, "label", rule->label, sizeof(rule->label)));
1941 	PFNV_CHK(pf_nvstring(nvl, "ifname", rule->ifname,
1942 	    sizeof(rule->ifname)));
1943 	PFNV_CHK(pf_nvstring(nvl, "qname", rule->qname, sizeof(rule->qname)));
1944 	PFNV_CHK(pf_nvstring(nvl, "pqname", rule->pqname,
1945 	    sizeof(rule->pqname)));
1946 	PFNV_CHK(pf_nvstring(nvl, "tagname", rule->tagname,
1947 	    sizeof(rule->tagname)));
1948 	PFNV_CHK(pf_nvstring(nvl, "match_tagname", rule->match_tagname,
1949 	    sizeof(rule->match_tagname)));
1950 	PFNV_CHK(pf_nvstring(nvl, "overload_tblname", rule->overload_tblname,
1951 	    sizeof(rule->overload_tblname)));
1952 
1953 	if (! nvlist_exists_nvlist(nvl, "rpool")) {
1954 		error = EINVAL;
1955 		goto errout;
1956 	}
1957 	PFNV_CHK(pf_nvpool_to_pool(nvlist_get_nvlist(nvl, "rpool"),
1958 	    &rule->rpool));
1959 
1960 	PFNV_CHK(pf_nvuint32(nvl, "os_fingerprint", &rule->os_fingerprint));
1961 
1962 	PFNV_CHK(pf_nvint(nvl, "rtableid", &rule->rtableid));
1963 	PFNV_CHK(pf_nvuint32_array(nvl, "timeout", rule->timeout, PFTM_MAX, NULL));
1964 	PFNV_CHK(pf_nvuint32(nvl, "max_states", &rule->max_states));
1965 	PFNV_CHK(pf_nvuint32(nvl, "max_src_nodes", &rule->max_src_nodes));
1966 	PFNV_CHK(pf_nvuint32(nvl, "max_src_states", &rule->max_src_states));
1967 	PFNV_CHK(pf_nvuint32(nvl, "max_src_conn", &rule->max_src_conn));
1968 	PFNV_CHK(pf_nvuint32(nvl, "max_src_conn_rate.limit",
1969 	    &rule->max_src_conn_rate.limit));
1970 	PFNV_CHK(pf_nvuint32(nvl, "max_src_conn_rate.seconds",
1971 	    &rule->max_src_conn_rate.seconds));
1972 	PFNV_CHK(pf_nvuint32(nvl, "prob", &rule->prob));
1973 	PFNV_CHK(pf_nvuint32(nvl, "cuid", &rule->cuid));
1974 	PFNV_CHK(pf_nvuint32(nvl, "cpid", &rule->cpid));
1975 
1976 	PFNV_CHK(pf_nvuint16(nvl, "return_icmp", &rule->return_icmp));
1977 	PFNV_CHK(pf_nvuint16(nvl, "return_icmp6", &rule->return_icmp6));
1978 
1979 	PFNV_CHK(pf_nvuint16(nvl, "max_mss", &rule->max_mss));
1980 	PFNV_CHK(pf_nvuint16(nvl, "scrub_flags", &rule->scrub_flags));
1981 
1982 	if (! nvlist_exists_nvlist(nvl, "uid")) {
1983 		error = EINVAL;
1984 		goto errout;
1985 	}
1986 	PFNV_CHK(pf_nvrule_uid_to_rule_uid(nvlist_get_nvlist(nvl, "uid"),
1987 	    &rule->uid));
1988 
1989 	if (! nvlist_exists_nvlist(nvl, "gid")) {
1990 		error = EINVAL;
1991 		goto errout;
1992 	}
1993 	PFNV_CHK(pf_nvrule_gid_to_rule_gid(nvlist_get_nvlist(nvl, "gid"),
1994 	    &rule->gid));
1995 
1996 	PFNV_CHK(pf_nvuint32(nvl, "rule_flag", &rule->rule_flag));
1997 	PFNV_CHK(pf_nvuint8(nvl, "action", &rule->action));
1998 	PFNV_CHK(pf_nvuint8(nvl, "direction", &rule->direction));
1999 	PFNV_CHK(pf_nvuint8(nvl, "log", &rule->log));
2000 	PFNV_CHK(pf_nvuint8(nvl, "logif", &rule->logif));
2001 	PFNV_CHK(pf_nvuint8(nvl, "quick", &rule->quick));
2002 	PFNV_CHK(pf_nvuint8(nvl, "ifnot", &rule->ifnot));
2003 	PFNV_CHK(pf_nvuint8(nvl, "match_tag_not", &rule->match_tag_not));
2004 	PFNV_CHK(pf_nvuint8(nvl, "natpass", &rule->natpass));
2005 
2006 	PFNV_CHK(pf_nvuint8(nvl, "keep_state", &rule->keep_state));
2007 	PFNV_CHK(pf_nvuint8(nvl, "af", &rule->af));
2008 	PFNV_CHK(pf_nvuint8(nvl, "proto", &rule->proto));
2009 	PFNV_CHK(pf_nvuint8(nvl, "type", &rule->type));
2010 	PFNV_CHK(pf_nvuint8(nvl, "code", &rule->code));
2011 	PFNV_CHK(pf_nvuint8(nvl, "flags", &rule->flags));
2012 	PFNV_CHK(pf_nvuint8(nvl, "flagset", &rule->flagset));
2013 	PFNV_CHK(pf_nvuint8(nvl, "min_ttl", &rule->min_ttl));
2014 	PFNV_CHK(pf_nvuint8(nvl, "allow_opts", &rule->allow_opts));
2015 	PFNV_CHK(pf_nvuint8(nvl, "rt", &rule->rt));
2016 	PFNV_CHK(pf_nvuint8(nvl, "return_ttl", &rule->return_ttl));
2017 	PFNV_CHK(pf_nvuint8(nvl, "tos", &rule->tos));
2018 	PFNV_CHK(pf_nvuint8(nvl, "set_tos", &rule->set_tos));
2019 	PFNV_CHK(pf_nvuint8(nvl, "anchor_relative", &rule->anchor_relative));
2020 	PFNV_CHK(pf_nvuint8(nvl, "anchor_wildcard", &rule->anchor_wildcard));
2021 
2022 	PFNV_CHK(pf_nvuint8(nvl, "flush", &rule->flush));
2023 	PFNV_CHK(pf_nvuint8(nvl, "prio", &rule->prio));
2024 
2025 	PFNV_CHK(pf_nvuint8_array(nvl, "set_prio", &rule->prio, 2, NULL));
2026 
2027 	if (nvlist_exists_nvlist(nvl, "divert")) {
2028 		const nvlist_t *nvldivert = nvlist_get_nvlist(nvl, "divert");
2029 
2030 		if (! nvlist_exists_nvlist(nvldivert, "addr")) {
2031 			error = EINVAL;
2032 			goto errout;
2033 		}
2034 		PFNV_CHK(pf_nvaddr_to_addr(nvlist_get_nvlist(nvldivert, "addr"),
2035 		    &rule->divert.addr));
2036 		PFNV_CHK(pf_nvuint16(nvldivert, "port", &rule->divert.port));
2037 	}
2038 
2039 	/* Validation */
2040 #ifndef INET
2041 	if (rule->af == AF_INET) {
2042 		error = EAFNOSUPPORT;
2043 		goto errout;
2044 	}
2045 #endif /* INET */
2046 #ifndef INET6
2047 	if (rule->af == AF_INET6) {
2048 		error = EAFNOSUPPORT;
2049 		goto errout;
2050 	}
2051 #endif /* INET6 */
2052 
2053 	PFNV_CHK(pf_check_rule_addr(&rule->src));
2054 	PFNV_CHK(pf_check_rule_addr(&rule->dst));
2055 
2056 	*prule = rule;
2057 
2058 	return (0);
2059 
2060 errout:
2061 	pf_krule_free(rule);
2062 	*prule = NULL;
2063 
2064 	return (error);
2065 }
2066 
2067 static nvlist_t *
2068 pf_divert_to_nvdivert(const struct pf_krule *rule)
2069 {
2070 	nvlist_t *nvl;
2071 	nvlist_t *tmp;
2072 
2073 	nvl = nvlist_create(0);
2074 	if (nvl == NULL)
2075 		return (NULL);
2076 
2077 	tmp = pf_addr_to_nvaddr(&rule->divert.addr);
2078 	if (tmp == NULL)
2079 		goto error;
2080 	nvlist_add_nvlist(nvl, "addr", tmp);
2081 	nvlist_add_number(nvl, "port", rule->divert.port);
2082 
2083 	return (nvl);
2084 
2085 error:
2086 	nvlist_destroy(nvl);
2087 	return (NULL);
2088 }
2089 
2090 static nvlist_t *
2091 pf_krule_to_nvrule(const struct pf_krule *rule)
2092 {
2093 	nvlist_t *nvl, *tmp;
2094 
2095 	nvl = nvlist_create(0);
2096 	if (nvl == NULL)
2097 		return (nvl);
2098 
2099 	nvlist_add_number(nvl, "nr", rule->nr);
2100 	tmp = pf_rule_addr_to_nvrule_addr(&rule->src);
2101 	if (tmp == NULL)
2102 		goto error;
2103 	nvlist_add_nvlist(nvl, "src", tmp);
2104 	tmp = pf_rule_addr_to_nvrule_addr(&rule->dst);
2105 	if (tmp == NULL)
2106 		goto error;
2107 	nvlist_add_nvlist(nvl, "dst", tmp);
2108 
2109 	for (int i = 0; i < PF_SKIP_COUNT; i++) {
2110 		nvlist_append_number_array(nvl, "skip",
2111 		    rule->skip[i].ptr ? rule->skip[i].ptr->nr : -1);
2112 	}
2113 
2114 	nvlist_add_string(nvl, "label", rule->label);
2115 	nvlist_add_string(nvl, "ifname", rule->ifname);
2116 	nvlist_add_string(nvl, "qname", rule->qname);
2117 	nvlist_add_string(nvl, "pqname", rule->pqname);
2118 	nvlist_add_string(nvl, "tagname", rule->tagname);
2119 	nvlist_add_string(nvl, "match_tagname", rule->match_tagname);
2120 	nvlist_add_string(nvl, "overload_tblname", rule->overload_tblname);
2121 
2122 	tmp = pf_pool_to_nvpool(&rule->rpool);
2123 	if (tmp == NULL)
2124 		goto error;
2125 	nvlist_add_nvlist(nvl, "rpool", tmp);
2126 
2127 	nvlist_add_number(nvl, "evaluations",
2128 	    counter_u64_fetch(rule->evaluations));
2129 	for (int i = 0; i < 2; i++) {
2130 		nvlist_append_number_array(nvl, "packets",
2131 		    counter_u64_fetch(rule->packets[i]));
2132 		nvlist_append_number_array(nvl, "bytes",
2133 		    counter_u64_fetch(rule->bytes[i]));
2134 	}
2135 
2136 	nvlist_add_number(nvl, "os_fingerprint", rule->os_fingerprint);
2137 
2138 	nvlist_add_number(nvl, "rtableid", rule->rtableid);
2139 	pf_uint32_array_nv(nvl, "timeout", rule->timeout, PFTM_MAX);
2140 	nvlist_add_number(nvl, "max_states", rule->max_states);
2141 	nvlist_add_number(nvl, "max_src_nodes", rule->max_src_nodes);
2142 	nvlist_add_number(nvl, "max_src_states", rule->max_src_states);
2143 	nvlist_add_number(nvl, "max_src_conn", rule->max_src_conn);
2144 	nvlist_add_number(nvl, "max_src_conn_rate.limit",
2145 	    rule->max_src_conn_rate.limit);
2146 	nvlist_add_number(nvl, "max_src_conn_rate.seconds",
2147 	    rule->max_src_conn_rate.seconds);
2148 	nvlist_add_number(nvl, "qid", rule->qid);
2149 	nvlist_add_number(nvl, "pqid", rule->pqid);
2150 	nvlist_add_number(nvl, "prob", rule->prob);
2151 	nvlist_add_number(nvl, "cuid", rule->cuid);
2152 	nvlist_add_number(nvl, "cpid", rule->cpid);
2153 
2154 	nvlist_add_number(nvl, "states_cur",
2155 	    counter_u64_fetch(rule->states_cur));
2156 	nvlist_add_number(nvl, "states_tot",
2157 	    counter_u64_fetch(rule->states_tot));
2158 	nvlist_add_number(nvl, "src_nodes",
2159 	    counter_u64_fetch(rule->src_nodes));
2160 
2161 	nvlist_add_number(nvl, "return_icmp", rule->return_icmp);
2162 	nvlist_add_number(nvl, "return_icmp6", rule->return_icmp6);
2163 
2164 	nvlist_add_number(nvl, "max_mss", rule->max_mss);
2165 	nvlist_add_number(nvl, "scrub_flags", rule->scrub_flags);
2166 
2167 	tmp = pf_rule_uid_to_nvrule_uid(&rule->uid);
2168 	if (tmp == NULL)
2169 		goto error;
2170 	nvlist_add_nvlist(nvl, "uid", tmp);
2171 	tmp = pf_rule_uid_to_nvrule_uid((const struct pf_rule_uid *)&rule->gid);
2172 	if (tmp == NULL)
2173 		goto error;
2174 	nvlist_add_nvlist(nvl, "gid", tmp);
2175 
2176 	nvlist_add_number(nvl, "rule_flag", rule->rule_flag);
2177 	nvlist_add_number(nvl, "action", rule->action);
2178 	nvlist_add_number(nvl, "direction", rule->direction);
2179 	nvlist_add_number(nvl, "log", rule->log);
2180 	nvlist_add_number(nvl, "logif", rule->logif);
2181 	nvlist_add_number(nvl, "quick", rule->quick);
2182 	nvlist_add_number(nvl, "ifnot", rule->ifnot);
2183 	nvlist_add_number(nvl, "match_tag_not", rule->match_tag_not);
2184 	nvlist_add_number(nvl, "natpass", rule->natpass);
2185 
2186 	nvlist_add_number(nvl, "keep_state", rule->keep_state);
2187 	nvlist_add_number(nvl, "af", rule->af);
2188 	nvlist_add_number(nvl, "proto", rule->proto);
2189 	nvlist_add_number(nvl, "type", rule->type);
2190 	nvlist_add_number(nvl, "code", rule->code);
2191 	nvlist_add_number(nvl, "flags", rule->flags);
2192 	nvlist_add_number(nvl, "flagset", rule->flagset);
2193 	nvlist_add_number(nvl, "min_ttl", rule->min_ttl);
2194 	nvlist_add_number(nvl, "allow_opts", rule->allow_opts);
2195 	nvlist_add_number(nvl, "rt", rule->rt);
2196 	nvlist_add_number(nvl, "return_ttl", rule->return_ttl);
2197 	nvlist_add_number(nvl, "tos", rule->tos);
2198 	nvlist_add_number(nvl, "set_tos", rule->set_tos);
2199 	nvlist_add_number(nvl, "anchor_relative", rule->anchor_relative);
2200 	nvlist_add_number(nvl, "anchor_wildcard", rule->anchor_wildcard);
2201 
2202 	nvlist_add_number(nvl, "flush", rule->flush);
2203 	nvlist_add_number(nvl, "prio", rule->prio);
2204 
2205 	pf_uint8_array_nv(nvl, "set_prio", &rule->prio, 2);
2206 
2207 	tmp = pf_divert_to_nvdivert(rule);
2208 	if (tmp == NULL)
2209 		goto error;
2210 	nvlist_add_nvlist(nvl, "divert", tmp);
2211 
2212 	return (nvl);
2213 
2214 error:
2215 	nvlist_destroy(nvl);
2216 	return (NULL);
2217 }
2218 
2219 static int
2220 pf_rule_to_krule(const struct pf_rule *rule, struct pf_krule *krule)
2221 {
2222 	int ret;
2223 
2224 #ifndef INET
2225 	if (rule->af == AF_INET) {
2226 		return (EAFNOSUPPORT);
2227 	}
2228 #endif /* INET */
2229 #ifndef INET6
2230 	if (rule->af == AF_INET6) {
2231 		return (EAFNOSUPPORT);
2232 	}
2233 #endif /* INET6 */
2234 
2235 	ret = pf_check_rule_addr(&rule->src);
2236 	if (ret != 0)
2237 		return (ret);
2238 	ret = pf_check_rule_addr(&rule->dst);
2239 	if (ret != 0)
2240 		return (ret);
2241 
2242 	bzero(krule, sizeof(*krule));
2243 
2244 	bcopy(&rule->src, &krule->src, sizeof(rule->src));
2245 	bcopy(&rule->dst, &krule->dst, sizeof(rule->dst));
2246 
2247 	strlcpy(krule->label, rule->label, sizeof(rule->label));
2248 	strlcpy(krule->ifname, rule->ifname, sizeof(rule->ifname));
2249 	strlcpy(krule->qname, rule->qname, sizeof(rule->qname));
2250 	strlcpy(krule->pqname, rule->pqname, sizeof(rule->pqname));
2251 	strlcpy(krule->tagname, rule->tagname, sizeof(rule->tagname));
2252 	strlcpy(krule->match_tagname, rule->match_tagname,
2253 	    sizeof(rule->match_tagname));
2254 	strlcpy(krule->overload_tblname, rule->overload_tblname,
2255 	    sizeof(rule->overload_tblname));
2256 
2257 	ret = pf_pool_to_kpool(&rule->rpool, &krule->rpool);
2258 	if (ret != 0)
2259 		return (ret);
2260 
2261 	/* Don't allow userspace to set evaulations, packets or bytes. */
2262 	/* kif, anchor, overload_tbl are not copied over. */
2263 
2264 	krule->os_fingerprint = rule->os_fingerprint;
2265 
2266 	krule->rtableid = rule->rtableid;
2267 	bcopy(rule->timeout, krule->timeout, sizeof(krule->timeout));
2268 	krule->max_states = rule->max_states;
2269 	krule->max_src_nodes = rule->max_src_nodes;
2270 	krule->max_src_states = rule->max_src_states;
2271 	krule->max_src_conn = rule->max_src_conn;
2272 	krule->max_src_conn_rate.limit = rule->max_src_conn_rate.limit;
2273 	krule->max_src_conn_rate.seconds = rule->max_src_conn_rate.seconds;
2274 	krule->qid = rule->qid;
2275 	krule->pqid = rule->pqid;
2276 	krule->nr = rule->nr;
2277 	krule->prob = rule->prob;
2278 	krule->cuid = rule->cuid;
2279 	krule->cpid = rule->cpid;
2280 
2281 	krule->return_icmp = rule->return_icmp;
2282 	krule->return_icmp6 = rule->return_icmp6;
2283 	krule->max_mss = rule->max_mss;
2284 	krule->tag = rule->tag;
2285 	krule->match_tag = rule->match_tag;
2286 	krule->scrub_flags = rule->scrub_flags;
2287 
2288 	bcopy(&rule->uid, &krule->uid, sizeof(krule->uid));
2289 	bcopy(&rule->gid, &krule->gid, sizeof(krule->gid));
2290 
2291 	krule->rule_flag = rule->rule_flag;
2292 	krule->action = rule->action;
2293 	krule->direction = rule->direction;
2294 	krule->log = rule->log;
2295 	krule->logif = rule->logif;
2296 	krule->quick = rule->quick;
2297 	krule->ifnot = rule->ifnot;
2298 	krule->match_tag_not = rule->match_tag_not;
2299 	krule->natpass = rule->natpass;
2300 
2301 	krule->keep_state = rule->keep_state;
2302 	krule->af = rule->af;
2303 	krule->proto = rule->proto;
2304 	krule->type = rule->type;
2305 	krule->code = rule->code;
2306 	krule->flags = rule->flags;
2307 	krule->flagset = rule->flagset;
2308 	krule->min_ttl = rule->min_ttl;
2309 	krule->allow_opts = rule->allow_opts;
2310 	krule->rt = rule->rt;
2311 	krule->return_ttl = rule->return_ttl;
2312 	krule->tos = rule->tos;
2313 	krule->set_tos = rule->set_tos;
2314 	krule->anchor_relative = rule->anchor_relative;
2315 	krule->anchor_wildcard = rule->anchor_wildcard;
2316 
2317 	krule->flush = rule->flush;
2318 	krule->prio = rule->prio;
2319 	krule->set_prio[0] = rule->set_prio[0];
2320 	krule->set_prio[1] = rule->set_prio[1];
2321 
2322 	bcopy(&rule->divert, &krule->divert, sizeof(krule->divert));
2323 
2324 	return (0);
2325 }
2326 
2327 static int
2328 pf_ioctl_addrule(struct pf_krule *rule, uint32_t ticket,
2329     uint32_t pool_ticket, const char *anchor, const char *anchor_call,
2330     struct thread *td)
2331 {
2332 	struct pf_kruleset	*ruleset;
2333 	struct pf_krule		*tail;
2334 	struct pf_kpooladdr	*pa;
2335 	struct pfi_kkif		*kif = NULL;
2336 	int			 rs_num;
2337 	int			 error = 0;
2338 
2339 	if ((rule->return_icmp >> 8) > ICMP_MAXTYPE) {
2340 		error = EINVAL;
2341 		goto errout_unlocked;
2342 	}
2343 
2344 #define	ERROUT(x)	{ error = (x); goto errout; }
2345 
2346 	if (rule->ifname[0])
2347 		kif = pf_kkif_create(M_WAITOK);
2348 	rule->evaluations = counter_u64_alloc(M_WAITOK);
2349 	for (int i = 0; i < 2; i++) {
2350 		rule->packets[i] = counter_u64_alloc(M_WAITOK);
2351 		rule->bytes[i] = counter_u64_alloc(M_WAITOK);
2352 	}
2353 	rule->states_cur = counter_u64_alloc(M_WAITOK);
2354 	rule->states_tot = counter_u64_alloc(M_WAITOK);
2355 	rule->src_nodes = counter_u64_alloc(M_WAITOK);
2356 	rule->cuid = td->td_ucred->cr_ruid;
2357 	rule->cpid = td->td_proc ? td->td_proc->p_pid : 0;
2358 	TAILQ_INIT(&rule->rpool.list);
2359 
2360 	PF_RULES_WLOCK();
2361 	ruleset = pf_find_kruleset(anchor);
2362 	if (ruleset == NULL)
2363 		ERROUT(EINVAL);
2364 	rs_num = pf_get_ruleset_number(rule->action);
2365 	if (rs_num >= PF_RULESET_MAX)
2366 		ERROUT(EINVAL);
2367 	if (ticket != ruleset->rules[rs_num].inactive.ticket) {
2368 		DPFPRINTF(PF_DEBUG_MISC,
2369 		    ("ticket: %d != [%d]%d\n", ticket, rs_num,
2370 		    ruleset->rules[rs_num].inactive.ticket));
2371 		ERROUT(EBUSY);
2372 	}
2373 	if (pool_ticket != V_ticket_pabuf) {
2374 		DPFPRINTF(PF_DEBUG_MISC,
2375 		    ("pool_ticket: %d != %d\n", pool_ticket,
2376 		    V_ticket_pabuf));
2377 		ERROUT(EBUSY);
2378 	}
2379 
2380 	tail = TAILQ_LAST(ruleset->rules[rs_num].inactive.ptr,
2381 	    pf_krulequeue);
2382 	if (tail)
2383 		rule->nr = tail->nr + 1;
2384 	else
2385 		rule->nr = 0;
2386 	if (rule->ifname[0]) {
2387 		rule->kif = pfi_kkif_attach(kif, rule->ifname);
2388 		kif = NULL;
2389 		pfi_kkif_ref(rule->kif);
2390 	} else
2391 		rule->kif = NULL;
2392 
2393 	if (rule->rtableid > 0 && rule->rtableid >= rt_numfibs)
2394 		error = EBUSY;
2395 
2396 #ifdef ALTQ
2397 	/* set queue IDs */
2398 	if (rule->qname[0] != 0) {
2399 		if ((rule->qid = pf_qname2qid(rule->qname)) == 0)
2400 			error = EBUSY;
2401 		else if (rule->pqname[0] != 0) {
2402 			if ((rule->pqid =
2403 			    pf_qname2qid(rule->pqname)) == 0)
2404 				error = EBUSY;
2405 		} else
2406 			rule->pqid = rule->qid;
2407 	}
2408 #endif
2409 	if (rule->tagname[0])
2410 		if ((rule->tag = pf_tagname2tag(rule->tagname)) == 0)
2411 			error = EBUSY;
2412 	if (rule->match_tagname[0])
2413 		if ((rule->match_tag =
2414 		    pf_tagname2tag(rule->match_tagname)) == 0)
2415 			error = EBUSY;
2416 	if (rule->rt && !rule->direction)
2417 		error = EINVAL;
2418 	if (!rule->log)
2419 		rule->logif = 0;
2420 	if (rule->logif >= PFLOGIFS_MAX)
2421 		error = EINVAL;
2422 	if (pf_addr_setup(ruleset, &rule->src.addr, rule->af))
2423 		error = ENOMEM;
2424 	if (pf_addr_setup(ruleset, &rule->dst.addr, rule->af))
2425 		error = ENOMEM;
2426 	if (pf_kanchor_setup(rule, ruleset, anchor_call))
2427 		error = EINVAL;
2428 	if (rule->scrub_flags & PFSTATE_SETPRIO &&
2429 	    (rule->set_prio[0] > PF_PRIO_MAX ||
2430 	    rule->set_prio[1] > PF_PRIO_MAX))
2431 		error = EINVAL;
2432 	TAILQ_FOREACH(pa, &V_pf_pabuf, entries)
2433 		if (pa->addr.type == PF_ADDR_TABLE) {
2434 			pa->addr.p.tbl = pfr_attach_table(ruleset,
2435 			    pa->addr.v.tblname);
2436 			if (pa->addr.p.tbl == NULL)
2437 				error = ENOMEM;
2438 		}
2439 
2440 	rule->overload_tbl = NULL;
2441 	if (rule->overload_tblname[0]) {
2442 		if ((rule->overload_tbl = pfr_attach_table(ruleset,
2443 		    rule->overload_tblname)) == NULL)
2444 			error = EINVAL;
2445 		else
2446 			rule->overload_tbl->pfrkt_flags |=
2447 			    PFR_TFLAG_ACTIVE;
2448 	}
2449 
2450 	pf_mv_kpool(&V_pf_pabuf, &rule->rpool.list);
2451 	if (((((rule->action == PF_NAT) || (rule->action == PF_RDR) ||
2452 	    (rule->action == PF_BINAT)) && rule->anchor == NULL) ||
2453 	    (rule->rt > PF_NOPFROUTE)) &&
2454 	    (TAILQ_FIRST(&rule->rpool.list) == NULL))
2455 		error = EINVAL;
2456 
2457 	if (error) {
2458 		pf_free_rule(rule);
2459 		rule = NULL;
2460 		ERROUT(error);
2461 	}
2462 
2463 	rule->rpool.cur = TAILQ_FIRST(&rule->rpool.list);
2464 	counter_u64_zero(rule->evaluations);
2465 	for (int i = 0; i < 2; i++) {
2466 		counter_u64_zero(rule->packets[i]);
2467 		counter_u64_zero(rule->bytes[i]);
2468 	}
2469 	TAILQ_INSERT_TAIL(ruleset->rules[rs_num].inactive.ptr,
2470 	    rule, entries);
2471 	ruleset->rules[rs_num].inactive.rcount++;
2472 	PF_RULES_WUNLOCK();
2473 
2474 	return (0);
2475 
2476 #undef ERROUT
2477 errout:
2478 	PF_RULES_WUNLOCK();
2479 errout_unlocked:
2480 	pf_kkif_free(kif);
2481 	pf_krule_free(rule);
2482 	return (error);
2483 }
2484 
2485 static int
2486 pfioctl(struct cdev *dev, u_long cmd, caddr_t addr, int flags, struct thread *td)
2487 {
2488 	int			 error = 0;
2489 	PF_RULES_RLOCK_TRACKER;
2490 
2491 	/* XXX keep in sync with switch() below */
2492 	if (securelevel_gt(td->td_ucred, 2))
2493 		switch (cmd) {
2494 		case DIOCGETRULES:
2495 		case DIOCGETRULE:
2496 		case DIOCGETRULENV:
2497 		case DIOCGETADDRS:
2498 		case DIOCGETADDR:
2499 		case DIOCGETSTATE:
2500 		case DIOCSETSTATUSIF:
2501 		case DIOCGETSTATUS:
2502 		case DIOCCLRSTATUS:
2503 		case DIOCNATLOOK:
2504 		case DIOCSETDEBUG:
2505 		case DIOCGETSTATES:
2506 		case DIOCGETTIMEOUT:
2507 		case DIOCCLRRULECTRS:
2508 		case DIOCGETLIMIT:
2509 		case DIOCGETALTQSV0:
2510 		case DIOCGETALTQSV1:
2511 		case DIOCGETALTQV0:
2512 		case DIOCGETALTQV1:
2513 		case DIOCGETQSTATSV0:
2514 		case DIOCGETQSTATSV1:
2515 		case DIOCGETRULESETS:
2516 		case DIOCGETRULESET:
2517 		case DIOCRGETTABLES:
2518 		case DIOCRGETTSTATS:
2519 		case DIOCRCLRTSTATS:
2520 		case DIOCRCLRADDRS:
2521 		case DIOCRADDADDRS:
2522 		case DIOCRDELADDRS:
2523 		case DIOCRSETADDRS:
2524 		case DIOCRGETADDRS:
2525 		case DIOCRGETASTATS:
2526 		case DIOCRCLRASTATS:
2527 		case DIOCRTSTADDRS:
2528 		case DIOCOSFPGET:
2529 		case DIOCGETSRCNODES:
2530 		case DIOCCLRSRCNODES:
2531 		case DIOCIGETIFACES:
2532 		case DIOCGIFSPEEDV0:
2533 		case DIOCGIFSPEEDV1:
2534 		case DIOCSETIFFLAG:
2535 		case DIOCCLRIFFLAG:
2536 			break;
2537 		case DIOCRCLRTABLES:
2538 		case DIOCRADDTABLES:
2539 		case DIOCRDELTABLES:
2540 		case DIOCRSETTFLAGS:
2541 			if (((struct pfioc_table *)addr)->pfrio_flags &
2542 			    PFR_FLAG_DUMMY)
2543 				break; /* dummy operation ok */
2544 			return (EPERM);
2545 		default:
2546 			return (EPERM);
2547 		}
2548 
2549 	if (!(flags & FWRITE))
2550 		switch (cmd) {
2551 		case DIOCGETRULES:
2552 		case DIOCGETADDRS:
2553 		case DIOCGETADDR:
2554 		case DIOCGETSTATE:
2555 		case DIOCGETSTATUS:
2556 		case DIOCGETSTATES:
2557 		case DIOCGETTIMEOUT:
2558 		case DIOCGETLIMIT:
2559 		case DIOCGETALTQSV0:
2560 		case DIOCGETALTQSV1:
2561 		case DIOCGETALTQV0:
2562 		case DIOCGETALTQV1:
2563 		case DIOCGETQSTATSV0:
2564 		case DIOCGETQSTATSV1:
2565 		case DIOCGETRULESETS:
2566 		case DIOCGETRULESET:
2567 		case DIOCNATLOOK:
2568 		case DIOCRGETTABLES:
2569 		case DIOCRGETTSTATS:
2570 		case DIOCRGETADDRS:
2571 		case DIOCRGETASTATS:
2572 		case DIOCRTSTADDRS:
2573 		case DIOCOSFPGET:
2574 		case DIOCGETSRCNODES:
2575 		case DIOCIGETIFACES:
2576 		case DIOCGIFSPEEDV1:
2577 		case DIOCGIFSPEEDV0:
2578 		case DIOCGETRULENV:
2579 			break;
2580 		case DIOCRCLRTABLES:
2581 		case DIOCRADDTABLES:
2582 		case DIOCRDELTABLES:
2583 		case DIOCRCLRTSTATS:
2584 		case DIOCRCLRADDRS:
2585 		case DIOCRADDADDRS:
2586 		case DIOCRDELADDRS:
2587 		case DIOCRSETADDRS:
2588 		case DIOCRSETTFLAGS:
2589 			if (((struct pfioc_table *)addr)->pfrio_flags &
2590 			    PFR_FLAG_DUMMY) {
2591 				flags |= FWRITE; /* need write lock for dummy */
2592 				break; /* dummy operation ok */
2593 			}
2594 			return (EACCES);
2595 		case DIOCGETRULE:
2596 			if (((struct pfioc_rule *)addr)->action ==
2597 			    PF_GET_CLR_CNTR)
2598 				return (EACCES);
2599 			break;
2600 		default:
2601 			return (EACCES);
2602 		}
2603 
2604 	CURVNET_SET(TD_TO_VNET(td));
2605 
2606 	switch (cmd) {
2607 	case DIOCSTART:
2608 		sx_xlock(&pf_ioctl_lock);
2609 		if (V_pf_status.running)
2610 			error = EEXIST;
2611 		else {
2612 			int cpu;
2613 
2614 			hook_pf();
2615 			V_pf_status.running = 1;
2616 			V_pf_status.since = time_second;
2617 
2618 			CPU_FOREACH(cpu)
2619 				V_pf_stateid[cpu] = time_second;
2620 
2621 			DPFPRINTF(PF_DEBUG_MISC, ("pf: started\n"));
2622 		}
2623 		break;
2624 
2625 	case DIOCSTOP:
2626 		sx_xlock(&pf_ioctl_lock);
2627 		if (!V_pf_status.running)
2628 			error = ENOENT;
2629 		else {
2630 			V_pf_status.running = 0;
2631 			dehook_pf();
2632 			V_pf_status.since = time_second;
2633 			DPFPRINTF(PF_DEBUG_MISC, ("pf: stopped\n"));
2634 		}
2635 		break;
2636 
2637 	case DIOCADDRULENV: {
2638 		struct pfioc_nv	*nv = (struct pfioc_nv *)addr;
2639 		nvlist_t	*nvl = NULL;
2640 		void		*nvlpacked = NULL;
2641 		struct pf_krule	*rule = NULL;
2642 		const char	*anchor = "", *anchor_call = "";
2643 		uint32_t	 ticket = 0, pool_ticket = 0;
2644 
2645 #define	ERROUT(x)	do { error = (x); goto DIOCADDRULENV_error; } while (0)
2646 
2647 		if (nv->len > pf_ioctl_maxcount)
2648 			ERROUT(ENOMEM);
2649 
2650 		nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
2651 		error = copyin(nv->data, nvlpacked, nv->len);
2652 		if (error)
2653 			ERROUT(error);
2654 
2655 		nvl = nvlist_unpack(nvlpacked, nv->len, 0);
2656 		if (nvl == NULL)
2657 			ERROUT(EBADMSG);
2658 
2659 		if (! nvlist_exists_number(nvl, "ticket"))
2660 			ERROUT(EINVAL);
2661 		ticket = nvlist_get_number(nvl, "ticket");
2662 
2663 		if (! nvlist_exists_number(nvl, "pool_ticket"))
2664 			ERROUT(EINVAL);
2665 		pool_ticket = nvlist_get_number(nvl, "pool_ticket");
2666 
2667 		if (! nvlist_exists_nvlist(nvl, "rule"))
2668 			ERROUT(EINVAL);
2669 
2670 		error = pf_nvrule_to_krule(nvlist_get_nvlist(nvl, "rule"),
2671 		    &rule);
2672 		if (error)
2673 			ERROUT(error);
2674 
2675 		if (nvlist_exists_string(nvl, "anchor"))
2676 			anchor = nvlist_get_string(nvl, "anchor");
2677 		if (nvlist_exists_string(nvl, "anchor_call"))
2678 			anchor_call = nvlist_get_string(nvl, "anchor_call");
2679 
2680 		if ((error = nvlist_error(nvl)))
2681 			ERROUT(error);
2682 
2683 		/* Frees rule on error */
2684 		error = pf_ioctl_addrule(rule, ticket, pool_ticket, anchor,
2685 		    anchor_call, td);
2686 
2687 		nvlist_destroy(nvl);
2688 		free(nvlpacked, M_TEMP);
2689 		break;
2690 #undef ERROUT
2691 DIOCADDRULENV_error:
2692 		pf_krule_free(rule);
2693 		nvlist_destroy(nvl);
2694 		free(nvlpacked, M_TEMP);
2695 
2696 		break;
2697 	}
2698 	case DIOCADDRULE: {
2699 		struct pfioc_rule	*pr = (struct pfioc_rule *)addr;
2700 		struct pf_krule		*rule;
2701 
2702 		rule = malloc(sizeof(*rule), M_PFRULE, M_WAITOK);
2703 		error = pf_rule_to_krule(&pr->rule, rule);
2704 		if (error != 0) {
2705 			free(rule, M_PFRULE);
2706 			break;
2707 		}
2708 
2709 		pr->anchor[sizeof(pr->anchor) - 1] = 0;
2710 
2711 		/* Frees rule on error */
2712 		error = pf_ioctl_addrule(rule, pr->ticket, pr->pool_ticket,
2713 		    pr->anchor, pr->anchor_call, td);
2714 		break;
2715 	}
2716 
2717 	case DIOCGETRULES: {
2718 		struct pfioc_rule	*pr = (struct pfioc_rule *)addr;
2719 		struct pf_kruleset	*ruleset;
2720 		struct pf_krule		*tail;
2721 		int			 rs_num;
2722 
2723 		PF_RULES_WLOCK();
2724 		pr->anchor[sizeof(pr->anchor) - 1] = 0;
2725 		ruleset = pf_find_kruleset(pr->anchor);
2726 		if (ruleset == NULL) {
2727 			PF_RULES_WUNLOCK();
2728 			error = EINVAL;
2729 			break;
2730 		}
2731 		rs_num = pf_get_ruleset_number(pr->rule.action);
2732 		if (rs_num >= PF_RULESET_MAX) {
2733 			PF_RULES_WUNLOCK();
2734 			error = EINVAL;
2735 			break;
2736 		}
2737 		tail = TAILQ_LAST(ruleset->rules[rs_num].active.ptr,
2738 		    pf_krulequeue);
2739 		if (tail)
2740 			pr->nr = tail->nr + 1;
2741 		else
2742 			pr->nr = 0;
2743 		pr->ticket = ruleset->rules[rs_num].active.ticket;
2744 		PF_RULES_WUNLOCK();
2745 		break;
2746 	}
2747 
2748 	case DIOCGETRULE: {
2749 		struct pfioc_rule	*pr = (struct pfioc_rule *)addr;
2750 		struct pf_kruleset	*ruleset;
2751 		struct pf_krule		*rule;
2752 		int			 rs_num;
2753 
2754 		PF_RULES_WLOCK();
2755 		pr->anchor[sizeof(pr->anchor) - 1] = 0;
2756 		ruleset = pf_find_kruleset(pr->anchor);
2757 		if (ruleset == NULL) {
2758 			PF_RULES_WUNLOCK();
2759 			error = EINVAL;
2760 			break;
2761 		}
2762 		rs_num = pf_get_ruleset_number(pr->rule.action);
2763 		if (rs_num >= PF_RULESET_MAX) {
2764 			PF_RULES_WUNLOCK();
2765 			error = EINVAL;
2766 			break;
2767 		}
2768 		if (pr->ticket != ruleset->rules[rs_num].active.ticket) {
2769 			PF_RULES_WUNLOCK();
2770 			error = EBUSY;
2771 			break;
2772 		}
2773 		rule = TAILQ_FIRST(ruleset->rules[rs_num].active.ptr);
2774 		while ((rule != NULL) && (rule->nr != pr->nr))
2775 			rule = TAILQ_NEXT(rule, entries);
2776 		if (rule == NULL) {
2777 			PF_RULES_WUNLOCK();
2778 			error = EBUSY;
2779 			break;
2780 		}
2781 
2782 		pf_krule_to_rule(rule, &pr->rule);
2783 
2784 		if (pf_kanchor_copyout(ruleset, rule, pr)) {
2785 			PF_RULES_WUNLOCK();
2786 			error = EBUSY;
2787 			break;
2788 		}
2789 		pf_addr_copyout(&pr->rule.src.addr);
2790 		pf_addr_copyout(&pr->rule.dst.addr);
2791 
2792 		if (pr->action == PF_GET_CLR_CNTR) {
2793 			counter_u64_zero(rule->evaluations);
2794 			for (int i = 0; i < 2; i++) {
2795 				counter_u64_zero(rule->packets[i]);
2796 				counter_u64_zero(rule->bytes[i]);
2797 			}
2798 			counter_u64_zero(rule->states_tot);
2799 		}
2800 		PF_RULES_WUNLOCK();
2801 		break;
2802 	}
2803 
2804 	case DIOCGETRULENV: {
2805 		struct pfioc_nv		*nv = (struct pfioc_nv *)addr;
2806 		nvlist_t		*nvrule = NULL;
2807 		nvlist_t		*nvl = NULL;
2808 		struct pf_kruleset	*ruleset;
2809 		struct pf_krule		*rule;
2810 		void			*nvlpacked = NULL;
2811 		int			 rs_num, nr;
2812 		bool			 clear_counter = false;
2813 
2814 #define	ERROUT(x)	do { error = (x); goto DIOCGETRULENV_error; } while (0)
2815 
2816 		if (nv->len > pf_ioctl_maxcount)
2817 			ERROUT(ENOMEM);
2818 
2819 		/* Copy the request in */
2820 		nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
2821 		if (nvlpacked == NULL)
2822 			ERROUT(ENOMEM);
2823 
2824 		error = copyin(nv->data, nvlpacked, nv->len);
2825 		if (error)
2826 			ERROUT(error);
2827 
2828 		nvl = nvlist_unpack(nvlpacked, nv->len, 0);
2829 		if (nvl == NULL)
2830 			ERROUT(EBADMSG);
2831 
2832 		if (! nvlist_exists_string(nvl, "anchor"))
2833 			ERROUT(EBADMSG);
2834 		if (! nvlist_exists_number(nvl, "ruleset"))
2835 			ERROUT(EBADMSG);
2836 		if (! nvlist_exists_number(nvl, "ticket"))
2837 			ERROUT(EBADMSG);
2838 		if (! nvlist_exists_number(nvl, "nr"))
2839 			ERROUT(EBADMSG);
2840 
2841 		if (nvlist_exists_bool(nvl, "clear_counter"))
2842 			clear_counter = nvlist_get_bool(nvl, "clear_counter");
2843 
2844 		if (clear_counter && !(flags & FWRITE))
2845 			ERROUT(EACCES);
2846 
2847 		nr = nvlist_get_number(nvl, "nr");
2848 
2849 		PF_RULES_WLOCK();
2850 		ruleset = pf_find_kruleset(nvlist_get_string(nvl, "anchor"));
2851 		if (ruleset == NULL) {
2852 			PF_RULES_WUNLOCK();
2853 			ERROUT(ENOENT);
2854 		}
2855 
2856 		rs_num = pf_get_ruleset_number(nvlist_get_number(nvl, "ruleset"));
2857 		if (rs_num >= PF_RULESET_MAX) {
2858 			PF_RULES_WUNLOCK();
2859 			ERROUT(EINVAL);
2860 		}
2861 
2862 		if (nvlist_get_number(nvl, "ticket") !=
2863 		    ruleset->rules[rs_num].active.ticket) {
2864 			PF_RULES_WUNLOCK();
2865 			ERROUT(EBUSY);
2866 			break;
2867 		}
2868 
2869 		if ((error = nvlist_error(nvl))) {
2870 			PF_RULES_WUNLOCK();
2871 			ERROUT(error);
2872 		}
2873 
2874 		rule = TAILQ_FIRST(ruleset->rules[rs_num].active.ptr);
2875 		while ((rule != NULL) && (rule->nr != nr))
2876 			rule = TAILQ_NEXT(rule, entries);
2877 		if (rule == NULL) {
2878 			PF_RULES_WUNLOCK();
2879 			ERROUT(EBUSY);
2880 			break;
2881 		}
2882 
2883 		nvrule = pf_krule_to_nvrule(rule);
2884 
2885 		nvlist_destroy(nvl);
2886 		nvl = nvlist_create(0);
2887 		if (nvl == NULL) {
2888 			PF_RULES_WUNLOCK();
2889 			ERROUT(ENOMEM);
2890 		}
2891 		nvlist_add_number(nvl, "nr", nr);
2892 		nvlist_add_nvlist(nvl, "rule", nvrule);
2893 		nvrule = NULL;
2894 		if (pf_kanchor_nvcopyout(ruleset, rule, nvl)) {
2895 			PF_RULES_WUNLOCK();
2896 			ERROUT(EBUSY);
2897 		}
2898 
2899 		free(nvlpacked, M_TEMP);
2900 		nvlpacked = nvlist_pack(nvl, &nv->len);
2901 		if (nvlpacked == NULL) {
2902 			PF_RULES_WUNLOCK();
2903 			ERROUT(ENOMEM);
2904 		}
2905 
2906 		if (nv->size == 0) {
2907 			PF_RULES_WUNLOCK();
2908 			ERROUT(0);
2909 		}
2910 		else if (nv->size < nv->len) {
2911 			PF_RULES_WUNLOCK();
2912 			ERROUT(ENOSPC);
2913 		}
2914 
2915 		error = copyout(nvlpacked, nv->data, nv->len);
2916 
2917 		if (clear_counter) {
2918 			counter_u64_zero(rule->evaluations);
2919 			for (int i = 0; i < 2; i++) {
2920 				counter_u64_zero(rule->packets[i]);
2921 				counter_u64_zero(rule->bytes[i]);
2922 			}
2923 			counter_u64_zero(rule->states_tot);
2924 		}
2925 		PF_RULES_WUNLOCK();
2926 
2927 #undef ERROUT
2928 DIOCGETRULENV_error:
2929 		free(nvlpacked, M_TEMP);
2930 		nvlist_destroy(nvrule);
2931 		nvlist_destroy(nvl);
2932 
2933 		break;
2934 	}
2935 
2936 	case DIOCCHANGERULE: {
2937 		struct pfioc_rule	*pcr = (struct pfioc_rule *)addr;
2938 		struct pf_kruleset	*ruleset;
2939 		struct pf_krule		*oldrule = NULL, *newrule = NULL;
2940 		struct pfi_kkif		*kif = NULL;
2941 		struct pf_kpooladdr	*pa;
2942 		u_int32_t		 nr = 0;
2943 		int			 rs_num;
2944 
2945 		if (pcr->action < PF_CHANGE_ADD_HEAD ||
2946 		    pcr->action > PF_CHANGE_GET_TICKET) {
2947 			error = EINVAL;
2948 			break;
2949 		}
2950 		if (pcr->rule.return_icmp >> 8 > ICMP_MAXTYPE) {
2951 			error = EINVAL;
2952 			break;
2953 		}
2954 
2955 		if (pcr->action != PF_CHANGE_REMOVE) {
2956 			newrule = malloc(sizeof(*newrule), M_PFRULE, M_WAITOK);
2957 			error = pf_rule_to_krule(&pcr->rule, newrule);
2958 			if (error != 0) {
2959 				free(newrule, M_PFRULE);
2960 				break;
2961 			}
2962 
2963 			if (newrule->ifname[0])
2964 				kif = pf_kkif_create(M_WAITOK);
2965 			newrule->evaluations = counter_u64_alloc(M_WAITOK);
2966 			for (int i = 0; i < 2; i++) {
2967 				newrule->packets[i] =
2968 				    counter_u64_alloc(M_WAITOK);
2969 				newrule->bytes[i] =
2970 				    counter_u64_alloc(M_WAITOK);
2971 			}
2972 			newrule->states_cur = counter_u64_alloc(M_WAITOK);
2973 			newrule->states_tot = counter_u64_alloc(M_WAITOK);
2974 			newrule->src_nodes = counter_u64_alloc(M_WAITOK);
2975 			newrule->cuid = td->td_ucred->cr_ruid;
2976 			newrule->cpid = td->td_proc ? td->td_proc->p_pid : 0;
2977 			TAILQ_INIT(&newrule->rpool.list);
2978 		}
2979 #define	ERROUT(x)	{ error = (x); goto DIOCCHANGERULE_error; }
2980 
2981 		PF_RULES_WLOCK();
2982 		if (!(pcr->action == PF_CHANGE_REMOVE ||
2983 		    pcr->action == PF_CHANGE_GET_TICKET) &&
2984 		    pcr->pool_ticket != V_ticket_pabuf)
2985 			ERROUT(EBUSY);
2986 
2987 		ruleset = pf_find_kruleset(pcr->anchor);
2988 		if (ruleset == NULL)
2989 			ERROUT(EINVAL);
2990 
2991 		rs_num = pf_get_ruleset_number(pcr->rule.action);
2992 		if (rs_num >= PF_RULESET_MAX)
2993 			ERROUT(EINVAL);
2994 
2995 		if (pcr->action == PF_CHANGE_GET_TICKET) {
2996 			pcr->ticket = ++ruleset->rules[rs_num].active.ticket;
2997 			ERROUT(0);
2998 		} else if (pcr->ticket !=
2999 			    ruleset->rules[rs_num].active.ticket)
3000 				ERROUT(EINVAL);
3001 
3002 		if (pcr->action != PF_CHANGE_REMOVE) {
3003 			if (newrule->ifname[0]) {
3004 				newrule->kif = pfi_kkif_attach(kif,
3005 				    newrule->ifname);
3006 				kif = NULL;
3007 				pfi_kkif_ref(newrule->kif);
3008 			} else
3009 				newrule->kif = NULL;
3010 
3011 			if (newrule->rtableid > 0 &&
3012 			    newrule->rtableid >= rt_numfibs)
3013 				error = EBUSY;
3014 
3015 #ifdef ALTQ
3016 			/* set queue IDs */
3017 			if (newrule->qname[0] != 0) {
3018 				if ((newrule->qid =
3019 				    pf_qname2qid(newrule->qname)) == 0)
3020 					error = EBUSY;
3021 				else if (newrule->pqname[0] != 0) {
3022 					if ((newrule->pqid =
3023 					    pf_qname2qid(newrule->pqname)) == 0)
3024 						error = EBUSY;
3025 				} else
3026 					newrule->pqid = newrule->qid;
3027 			}
3028 #endif /* ALTQ */
3029 			if (newrule->tagname[0])
3030 				if ((newrule->tag =
3031 				    pf_tagname2tag(newrule->tagname)) == 0)
3032 					error = EBUSY;
3033 			if (newrule->match_tagname[0])
3034 				if ((newrule->match_tag = pf_tagname2tag(
3035 				    newrule->match_tagname)) == 0)
3036 					error = EBUSY;
3037 			if (newrule->rt && !newrule->direction)
3038 				error = EINVAL;
3039 			if (!newrule->log)
3040 				newrule->logif = 0;
3041 			if (newrule->logif >= PFLOGIFS_MAX)
3042 				error = EINVAL;
3043 			if (pf_addr_setup(ruleset, &newrule->src.addr, newrule->af))
3044 				error = ENOMEM;
3045 			if (pf_addr_setup(ruleset, &newrule->dst.addr, newrule->af))
3046 				error = ENOMEM;
3047 			if (pf_kanchor_setup(newrule, ruleset, pcr->anchor_call))
3048 				error = EINVAL;
3049 			TAILQ_FOREACH(pa, &V_pf_pabuf, entries)
3050 				if (pa->addr.type == PF_ADDR_TABLE) {
3051 					pa->addr.p.tbl =
3052 					    pfr_attach_table(ruleset,
3053 					    pa->addr.v.tblname);
3054 					if (pa->addr.p.tbl == NULL)
3055 						error = ENOMEM;
3056 				}
3057 
3058 			newrule->overload_tbl = NULL;
3059 			if (newrule->overload_tblname[0]) {
3060 				if ((newrule->overload_tbl = pfr_attach_table(
3061 				    ruleset, newrule->overload_tblname)) ==
3062 				    NULL)
3063 					error = EINVAL;
3064 				else
3065 					newrule->overload_tbl->pfrkt_flags |=
3066 					    PFR_TFLAG_ACTIVE;
3067 			}
3068 
3069 			pf_mv_kpool(&V_pf_pabuf, &newrule->rpool.list);
3070 			if (((((newrule->action == PF_NAT) ||
3071 			    (newrule->action == PF_RDR) ||
3072 			    (newrule->action == PF_BINAT) ||
3073 			    (newrule->rt > PF_NOPFROUTE)) &&
3074 			    !newrule->anchor)) &&
3075 			    (TAILQ_FIRST(&newrule->rpool.list) == NULL))
3076 				error = EINVAL;
3077 
3078 			if (error) {
3079 				pf_free_rule(newrule);
3080 				PF_RULES_WUNLOCK();
3081 				break;
3082 			}
3083 
3084 			newrule->rpool.cur = TAILQ_FIRST(&newrule->rpool.list);
3085 		}
3086 		pf_empty_kpool(&V_pf_pabuf);
3087 
3088 		if (pcr->action == PF_CHANGE_ADD_HEAD)
3089 			oldrule = TAILQ_FIRST(
3090 			    ruleset->rules[rs_num].active.ptr);
3091 		else if (pcr->action == PF_CHANGE_ADD_TAIL)
3092 			oldrule = TAILQ_LAST(
3093 			    ruleset->rules[rs_num].active.ptr, pf_krulequeue);
3094 		else {
3095 			oldrule = TAILQ_FIRST(
3096 			    ruleset->rules[rs_num].active.ptr);
3097 			while ((oldrule != NULL) && (oldrule->nr != pcr->nr))
3098 				oldrule = TAILQ_NEXT(oldrule, entries);
3099 			if (oldrule == NULL) {
3100 				if (newrule != NULL)
3101 					pf_free_rule(newrule);
3102 				PF_RULES_WUNLOCK();
3103 				error = EINVAL;
3104 				break;
3105 			}
3106 		}
3107 
3108 		if (pcr->action == PF_CHANGE_REMOVE) {
3109 			pf_unlink_rule(ruleset->rules[rs_num].active.ptr,
3110 			    oldrule);
3111 			ruleset->rules[rs_num].active.rcount--;
3112 		} else {
3113 			if (oldrule == NULL)
3114 				TAILQ_INSERT_TAIL(
3115 				    ruleset->rules[rs_num].active.ptr,
3116 				    newrule, entries);
3117 			else if (pcr->action == PF_CHANGE_ADD_HEAD ||
3118 			    pcr->action == PF_CHANGE_ADD_BEFORE)
3119 				TAILQ_INSERT_BEFORE(oldrule, newrule, entries);
3120 			else
3121 				TAILQ_INSERT_AFTER(
3122 				    ruleset->rules[rs_num].active.ptr,
3123 				    oldrule, newrule, entries);
3124 			ruleset->rules[rs_num].active.rcount++;
3125 		}
3126 
3127 		nr = 0;
3128 		TAILQ_FOREACH(oldrule,
3129 		    ruleset->rules[rs_num].active.ptr, entries)
3130 			oldrule->nr = nr++;
3131 
3132 		ruleset->rules[rs_num].active.ticket++;
3133 
3134 		pf_calc_skip_steps(ruleset->rules[rs_num].active.ptr);
3135 		pf_remove_if_empty_kruleset(ruleset);
3136 
3137 		PF_RULES_WUNLOCK();
3138 		break;
3139 
3140 #undef ERROUT
3141 DIOCCHANGERULE_error:
3142 		PF_RULES_WUNLOCK();
3143 		pf_krule_free(newrule);
3144 		pf_kkif_free(kif);
3145 		break;
3146 	}
3147 
3148 	case DIOCCLRSTATES: {
3149 		struct pf_state		*s;
3150 		struct pfioc_state_kill *psk = (struct pfioc_state_kill *)addr;
3151 		u_int			 i, killed = 0;
3152 
3153 		for (i = 0; i <= pf_hashmask; i++) {
3154 			struct pf_idhash *ih = &V_pf_idhash[i];
3155 
3156 relock_DIOCCLRSTATES:
3157 			PF_HASHROW_LOCK(ih);
3158 			LIST_FOREACH(s, &ih->states, entry)
3159 				if (!psk->psk_ifname[0] ||
3160 				    !strcmp(psk->psk_ifname,
3161 				    s->kif->pfik_name)) {
3162 					/*
3163 					 * Don't send out individual
3164 					 * delete messages.
3165 					 */
3166 					s->state_flags |= PFSTATE_NOSYNC;
3167 					pf_unlink_state(s, PF_ENTER_LOCKED);
3168 					killed++;
3169 					goto relock_DIOCCLRSTATES;
3170 				}
3171 			PF_HASHROW_UNLOCK(ih);
3172 		}
3173 		psk->psk_killed = killed;
3174 		if (V_pfsync_clear_states_ptr != NULL)
3175 			V_pfsync_clear_states_ptr(V_pf_status.hostid, psk->psk_ifname);
3176 		break;
3177 	}
3178 
3179 	case DIOCKILLSTATES: {
3180 		struct pf_state		*s;
3181 		struct pf_state_key	*sk;
3182 		struct pf_addr		*srcaddr, *dstaddr;
3183 		u_int16_t		 srcport, dstport;
3184 		struct pfioc_state_kill	*psk = (struct pfioc_state_kill *)addr;
3185 		u_int			 i, killed = 0;
3186 
3187 		if (psk->psk_pfcmp.id) {
3188 			if (psk->psk_pfcmp.creatorid == 0)
3189 				psk->psk_pfcmp.creatorid = V_pf_status.hostid;
3190 			if ((s = pf_find_state_byid(psk->psk_pfcmp.id,
3191 			    psk->psk_pfcmp.creatorid))) {
3192 				pf_unlink_state(s, PF_ENTER_LOCKED);
3193 				psk->psk_killed = 1;
3194 			}
3195 			break;
3196 		}
3197 
3198 		for (i = 0; i <= pf_hashmask; i++) {
3199 			struct pf_idhash *ih = &V_pf_idhash[i];
3200 
3201 relock_DIOCKILLSTATES:
3202 			PF_HASHROW_LOCK(ih);
3203 			LIST_FOREACH(s, &ih->states, entry) {
3204 				sk = s->key[PF_SK_WIRE];
3205 				if (s->direction == PF_OUT) {
3206 					srcaddr = &sk->addr[1];
3207 					dstaddr = &sk->addr[0];
3208 					srcport = sk->port[1];
3209 					dstport = sk->port[0];
3210 				} else {
3211 					srcaddr = &sk->addr[0];
3212 					dstaddr = &sk->addr[1];
3213 					srcport = sk->port[0];
3214 					dstport = sk->port[1];
3215 				}
3216 
3217 				if ((!psk->psk_af || sk->af == psk->psk_af)
3218 				    && (!psk->psk_proto || psk->psk_proto ==
3219 				    sk->proto) &&
3220 				    PF_MATCHA(psk->psk_src.neg,
3221 				    &psk->psk_src.addr.v.a.addr,
3222 				    &psk->psk_src.addr.v.a.mask,
3223 				    srcaddr, sk->af) &&
3224 				    PF_MATCHA(psk->psk_dst.neg,
3225 				    &psk->psk_dst.addr.v.a.addr,
3226 				    &psk->psk_dst.addr.v.a.mask,
3227 				    dstaddr, sk->af) &&
3228 				    (psk->psk_src.port_op == 0 ||
3229 				    pf_match_port(psk->psk_src.port_op,
3230 				    psk->psk_src.port[0], psk->psk_src.port[1],
3231 				    srcport)) &&
3232 				    (psk->psk_dst.port_op == 0 ||
3233 				    pf_match_port(psk->psk_dst.port_op,
3234 				    psk->psk_dst.port[0], psk->psk_dst.port[1],
3235 				    dstport)) &&
3236 				    (!psk->psk_label[0] ||
3237 				    (s->rule.ptr->label[0] &&
3238 				    !strcmp(psk->psk_label,
3239 				    s->rule.ptr->label))) &&
3240 				    (!psk->psk_ifname[0] ||
3241 				    !strcmp(psk->psk_ifname,
3242 				    s->kif->pfik_name))) {
3243 					pf_unlink_state(s, PF_ENTER_LOCKED);
3244 					killed++;
3245 					goto relock_DIOCKILLSTATES;
3246 				}
3247 			}
3248 			PF_HASHROW_UNLOCK(ih);
3249 		}
3250 		psk->psk_killed = killed;
3251 		break;
3252 	}
3253 
3254 	case DIOCADDSTATE: {
3255 		struct pfioc_state	*ps = (struct pfioc_state *)addr;
3256 		struct pfsync_state	*sp = &ps->state;
3257 
3258 		if (sp->timeout >= PFTM_MAX) {
3259 			error = EINVAL;
3260 			break;
3261 		}
3262 		if (V_pfsync_state_import_ptr != NULL) {
3263 			PF_RULES_RLOCK();
3264 			error = V_pfsync_state_import_ptr(sp, PFSYNC_SI_IOCTL);
3265 			PF_RULES_RUNLOCK();
3266 		} else
3267 			error = EOPNOTSUPP;
3268 		break;
3269 	}
3270 
3271 	case DIOCGETSTATE: {
3272 		struct pfioc_state	*ps = (struct pfioc_state *)addr;
3273 		struct pf_state		*s;
3274 
3275 		s = pf_find_state_byid(ps->state.id, ps->state.creatorid);
3276 		if (s == NULL) {
3277 			error = ENOENT;
3278 			break;
3279 		}
3280 
3281 		pfsync_state_export(&ps->state, s);
3282 		PF_STATE_UNLOCK(s);
3283 		break;
3284 	}
3285 
3286 	case DIOCGETSTATES: {
3287 		struct pfioc_states	*ps = (struct pfioc_states *)addr;
3288 		struct pf_state		*s;
3289 		struct pfsync_state	*pstore, *p;
3290 		int i, nr;
3291 
3292 		if (ps->ps_len <= 0) {
3293 			nr = uma_zone_get_cur(V_pf_state_z);
3294 			ps->ps_len = sizeof(struct pfsync_state) * nr;
3295 			break;
3296 		}
3297 
3298 		p = pstore = malloc(ps->ps_len, M_TEMP, M_WAITOK | M_ZERO);
3299 		nr = 0;
3300 
3301 		for (i = 0; i <= pf_hashmask; i++) {
3302 			struct pf_idhash *ih = &V_pf_idhash[i];
3303 
3304 			PF_HASHROW_LOCK(ih);
3305 			LIST_FOREACH(s, &ih->states, entry) {
3306 				if (s->timeout == PFTM_UNLINKED)
3307 					continue;
3308 
3309 				if ((nr+1) * sizeof(*p) > ps->ps_len) {
3310 					PF_HASHROW_UNLOCK(ih);
3311 					goto DIOCGETSTATES_full;
3312 				}
3313 				pfsync_state_export(p, s);
3314 				p++;
3315 				nr++;
3316 			}
3317 			PF_HASHROW_UNLOCK(ih);
3318 		}
3319 DIOCGETSTATES_full:
3320 		error = copyout(pstore, ps->ps_states,
3321 		    sizeof(struct pfsync_state) * nr);
3322 		if (error) {
3323 			free(pstore, M_TEMP);
3324 			break;
3325 		}
3326 		ps->ps_len = sizeof(struct pfsync_state) * nr;
3327 		free(pstore, M_TEMP);
3328 
3329 		break;
3330 	}
3331 
3332 	case DIOCGETSTATUS: {
3333 		struct pf_status *s = (struct pf_status *)addr;
3334 
3335 		PF_RULES_RLOCK();
3336 		s->running = V_pf_status.running;
3337 		s->since   = V_pf_status.since;
3338 		s->debug   = V_pf_status.debug;
3339 		s->hostid  = V_pf_status.hostid;
3340 		s->states  = V_pf_status.states;
3341 		s->src_nodes = V_pf_status.src_nodes;
3342 
3343 		for (int i = 0; i < PFRES_MAX; i++)
3344 			s->counters[i] =
3345 			    counter_u64_fetch(V_pf_status.counters[i]);
3346 		for (int i = 0; i < LCNT_MAX; i++)
3347 			s->lcounters[i] =
3348 			    counter_u64_fetch(V_pf_status.lcounters[i]);
3349 		for (int i = 0; i < FCNT_MAX; i++)
3350 			s->fcounters[i] =
3351 			    counter_u64_fetch(V_pf_status.fcounters[i]);
3352 		for (int i = 0; i < SCNT_MAX; i++)
3353 			s->scounters[i] =
3354 			    counter_u64_fetch(V_pf_status.scounters[i]);
3355 
3356 		bcopy(V_pf_status.ifname, s->ifname, IFNAMSIZ);
3357 		bcopy(V_pf_status.pf_chksum, s->pf_chksum,
3358 		    PF_MD5_DIGEST_LENGTH);
3359 
3360 		pfi_update_status(s->ifname, s);
3361 		PF_RULES_RUNLOCK();
3362 		break;
3363 	}
3364 
3365 	case DIOCSETSTATUSIF: {
3366 		struct pfioc_if	*pi = (struct pfioc_if *)addr;
3367 
3368 		if (pi->ifname[0] == 0) {
3369 			bzero(V_pf_status.ifname, IFNAMSIZ);
3370 			break;
3371 		}
3372 		PF_RULES_WLOCK();
3373 		strlcpy(V_pf_status.ifname, pi->ifname, IFNAMSIZ);
3374 		PF_RULES_WUNLOCK();
3375 		break;
3376 	}
3377 
3378 	case DIOCCLRSTATUS: {
3379 		PF_RULES_WLOCK();
3380 		for (int i = 0; i < PFRES_MAX; i++)
3381 			counter_u64_zero(V_pf_status.counters[i]);
3382 		for (int i = 0; i < FCNT_MAX; i++)
3383 			counter_u64_zero(V_pf_status.fcounters[i]);
3384 		for (int i = 0; i < SCNT_MAX; i++)
3385 			counter_u64_zero(V_pf_status.scounters[i]);
3386 		for (int i = 0; i < LCNT_MAX; i++)
3387 			counter_u64_zero(V_pf_status.lcounters[i]);
3388 		V_pf_status.since = time_second;
3389 		if (*V_pf_status.ifname)
3390 			pfi_update_status(V_pf_status.ifname, NULL);
3391 		PF_RULES_WUNLOCK();
3392 		break;
3393 	}
3394 
3395 	case DIOCNATLOOK: {
3396 		struct pfioc_natlook	*pnl = (struct pfioc_natlook *)addr;
3397 		struct pf_state_key	*sk;
3398 		struct pf_state		*state;
3399 		struct pf_state_key_cmp	 key;
3400 		int			 m = 0, direction = pnl->direction;
3401 		int			 sidx, didx;
3402 
3403 		/* NATLOOK src and dst are reversed, so reverse sidx/didx */
3404 		sidx = (direction == PF_IN) ? 1 : 0;
3405 		didx = (direction == PF_IN) ? 0 : 1;
3406 
3407 		if (!pnl->proto ||
3408 		    PF_AZERO(&pnl->saddr, pnl->af) ||
3409 		    PF_AZERO(&pnl->daddr, pnl->af) ||
3410 		    ((pnl->proto == IPPROTO_TCP ||
3411 		    pnl->proto == IPPROTO_UDP) &&
3412 		    (!pnl->dport || !pnl->sport)))
3413 			error = EINVAL;
3414 		else {
3415 			bzero(&key, sizeof(key));
3416 			key.af = pnl->af;
3417 			key.proto = pnl->proto;
3418 			PF_ACPY(&key.addr[sidx], &pnl->saddr, pnl->af);
3419 			key.port[sidx] = pnl->sport;
3420 			PF_ACPY(&key.addr[didx], &pnl->daddr, pnl->af);
3421 			key.port[didx] = pnl->dport;
3422 
3423 			state = pf_find_state_all(&key, direction, &m);
3424 
3425 			if (m > 1)
3426 				error = E2BIG;	/* more than one state */
3427 			else if (state != NULL) {
3428 				/* XXXGL: not locked read */
3429 				sk = state->key[sidx];
3430 				PF_ACPY(&pnl->rsaddr, &sk->addr[sidx], sk->af);
3431 				pnl->rsport = sk->port[sidx];
3432 				PF_ACPY(&pnl->rdaddr, &sk->addr[didx], sk->af);
3433 				pnl->rdport = sk->port[didx];
3434 			} else
3435 				error = ENOENT;
3436 		}
3437 		break;
3438 	}
3439 
3440 	case DIOCSETTIMEOUT: {
3441 		struct pfioc_tm	*pt = (struct pfioc_tm *)addr;
3442 		int		 old;
3443 
3444 		if (pt->timeout < 0 || pt->timeout >= PFTM_MAX ||
3445 		    pt->seconds < 0) {
3446 			error = EINVAL;
3447 			break;
3448 		}
3449 		PF_RULES_WLOCK();
3450 		old = V_pf_default_rule.timeout[pt->timeout];
3451 		if (pt->timeout == PFTM_INTERVAL && pt->seconds == 0)
3452 			pt->seconds = 1;
3453 		V_pf_default_rule.timeout[pt->timeout] = pt->seconds;
3454 		if (pt->timeout == PFTM_INTERVAL && pt->seconds < old)
3455 			wakeup(pf_purge_thread);
3456 		pt->seconds = old;
3457 		PF_RULES_WUNLOCK();
3458 		break;
3459 	}
3460 
3461 	case DIOCGETTIMEOUT: {
3462 		struct pfioc_tm	*pt = (struct pfioc_tm *)addr;
3463 
3464 		if (pt->timeout < 0 || pt->timeout >= PFTM_MAX) {
3465 			error = EINVAL;
3466 			break;
3467 		}
3468 		PF_RULES_RLOCK();
3469 		pt->seconds = V_pf_default_rule.timeout[pt->timeout];
3470 		PF_RULES_RUNLOCK();
3471 		break;
3472 	}
3473 
3474 	case DIOCGETLIMIT: {
3475 		struct pfioc_limit	*pl = (struct pfioc_limit *)addr;
3476 
3477 		if (pl->index < 0 || pl->index >= PF_LIMIT_MAX) {
3478 			error = EINVAL;
3479 			break;
3480 		}
3481 		PF_RULES_RLOCK();
3482 		pl->limit = V_pf_limits[pl->index].limit;
3483 		PF_RULES_RUNLOCK();
3484 		break;
3485 	}
3486 
3487 	case DIOCSETLIMIT: {
3488 		struct pfioc_limit	*pl = (struct pfioc_limit *)addr;
3489 		int			 old_limit;
3490 
3491 		PF_RULES_WLOCK();
3492 		if (pl->index < 0 || pl->index >= PF_LIMIT_MAX ||
3493 		    V_pf_limits[pl->index].zone == NULL) {
3494 			PF_RULES_WUNLOCK();
3495 			error = EINVAL;
3496 			break;
3497 		}
3498 		uma_zone_set_max(V_pf_limits[pl->index].zone, pl->limit);
3499 		old_limit = V_pf_limits[pl->index].limit;
3500 		V_pf_limits[pl->index].limit = pl->limit;
3501 		pl->limit = old_limit;
3502 		PF_RULES_WUNLOCK();
3503 		break;
3504 	}
3505 
3506 	case DIOCSETDEBUG: {
3507 		u_int32_t	*level = (u_int32_t *)addr;
3508 
3509 		PF_RULES_WLOCK();
3510 		V_pf_status.debug = *level;
3511 		PF_RULES_WUNLOCK();
3512 		break;
3513 	}
3514 
3515 	case DIOCCLRRULECTRS: {
3516 		/* obsoleted by DIOCGETRULE with action=PF_GET_CLR_CNTR */
3517 		struct pf_kruleset	*ruleset = &pf_main_ruleset;
3518 		struct pf_krule		*rule;
3519 
3520 		PF_RULES_WLOCK();
3521 		TAILQ_FOREACH(rule,
3522 		    ruleset->rules[PF_RULESET_FILTER].active.ptr, entries) {
3523 			counter_u64_zero(rule->evaluations);
3524 			for (int i = 0; i < 2; i++) {
3525 				counter_u64_zero(rule->packets[i]);
3526 				counter_u64_zero(rule->bytes[i]);
3527 			}
3528 		}
3529 		PF_RULES_WUNLOCK();
3530 		break;
3531 	}
3532 
3533 	case DIOCGIFSPEEDV0:
3534 	case DIOCGIFSPEEDV1: {
3535 		struct pf_ifspeed_v1	*psp = (struct pf_ifspeed_v1 *)addr;
3536 		struct pf_ifspeed_v1	ps;
3537 		struct ifnet		*ifp;
3538 
3539 		if (psp->ifname[0] != 0) {
3540 			/* Can we completely trust user-land? */
3541 			strlcpy(ps.ifname, psp->ifname, IFNAMSIZ);
3542 			ifp = ifunit(ps.ifname);
3543 			if (ifp != NULL) {
3544 				psp->baudrate32 =
3545 				    (u_int32_t)uqmin(ifp->if_baudrate, UINT_MAX);
3546 				if (cmd == DIOCGIFSPEEDV1)
3547 					psp->baudrate = ifp->if_baudrate;
3548 			} else
3549 				error = EINVAL;
3550 		} else
3551 			error = EINVAL;
3552 		break;
3553 	}
3554 
3555 #ifdef ALTQ
3556 	case DIOCSTARTALTQ: {
3557 		struct pf_altq		*altq;
3558 
3559 		PF_RULES_WLOCK();
3560 		/* enable all altq interfaces on active list */
3561 		TAILQ_FOREACH(altq, V_pf_altq_ifs_active, entries) {
3562 			if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
3563 				error = pf_enable_altq(altq);
3564 				if (error != 0)
3565 					break;
3566 			}
3567 		}
3568 		if (error == 0)
3569 			V_pf_altq_running = 1;
3570 		PF_RULES_WUNLOCK();
3571 		DPFPRINTF(PF_DEBUG_MISC, ("altq: started\n"));
3572 		break;
3573 	}
3574 
3575 	case DIOCSTOPALTQ: {
3576 		struct pf_altq		*altq;
3577 
3578 		PF_RULES_WLOCK();
3579 		/* disable all altq interfaces on active list */
3580 		TAILQ_FOREACH(altq, V_pf_altq_ifs_active, entries) {
3581 			if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) == 0) {
3582 				error = pf_disable_altq(altq);
3583 				if (error != 0)
3584 					break;
3585 			}
3586 		}
3587 		if (error == 0)
3588 			V_pf_altq_running = 0;
3589 		PF_RULES_WUNLOCK();
3590 		DPFPRINTF(PF_DEBUG_MISC, ("altq: stopped\n"));
3591 		break;
3592 	}
3593 
3594 	case DIOCADDALTQV0:
3595 	case DIOCADDALTQV1: {
3596 		struct pfioc_altq_v1	*pa = (struct pfioc_altq_v1 *)addr;
3597 		struct pf_altq		*altq, *a;
3598 		struct ifnet		*ifp;
3599 
3600 		altq = malloc(sizeof(*altq), M_PFALTQ, M_WAITOK | M_ZERO);
3601 		error = pf_import_kaltq(pa, altq, IOCPARM_LEN(cmd));
3602 		if (error)
3603 			break;
3604 		altq->local_flags = 0;
3605 
3606 		PF_RULES_WLOCK();
3607 		if (pa->ticket != V_ticket_altqs_inactive) {
3608 			PF_RULES_WUNLOCK();
3609 			free(altq, M_PFALTQ);
3610 			error = EBUSY;
3611 			break;
3612 		}
3613 
3614 		/*
3615 		 * if this is for a queue, find the discipline and
3616 		 * copy the necessary fields
3617 		 */
3618 		if (altq->qname[0] != 0) {
3619 			if ((altq->qid = pf_qname2qid(altq->qname)) == 0) {
3620 				PF_RULES_WUNLOCK();
3621 				error = EBUSY;
3622 				free(altq, M_PFALTQ);
3623 				break;
3624 			}
3625 			altq->altq_disc = NULL;
3626 			TAILQ_FOREACH(a, V_pf_altq_ifs_inactive, entries) {
3627 				if (strncmp(a->ifname, altq->ifname,
3628 				    IFNAMSIZ) == 0) {
3629 					altq->altq_disc = a->altq_disc;
3630 					break;
3631 				}
3632 			}
3633 		}
3634 
3635 		if ((ifp = ifunit(altq->ifname)) == NULL)
3636 			altq->local_flags |= PFALTQ_FLAG_IF_REMOVED;
3637 		else
3638 			error = altq_add(ifp, altq);
3639 
3640 		if (error) {
3641 			PF_RULES_WUNLOCK();
3642 			free(altq, M_PFALTQ);
3643 			break;
3644 		}
3645 
3646 		if (altq->qname[0] != 0)
3647 			TAILQ_INSERT_TAIL(V_pf_altqs_inactive, altq, entries);
3648 		else
3649 			TAILQ_INSERT_TAIL(V_pf_altq_ifs_inactive, altq, entries);
3650 		/* version error check done on import above */
3651 		pf_export_kaltq(altq, pa, IOCPARM_LEN(cmd));
3652 		PF_RULES_WUNLOCK();
3653 		break;
3654 	}
3655 
3656 	case DIOCGETALTQSV0:
3657 	case DIOCGETALTQSV1: {
3658 		struct pfioc_altq_v1	*pa = (struct pfioc_altq_v1 *)addr;
3659 		struct pf_altq		*altq;
3660 
3661 		PF_RULES_RLOCK();
3662 		pa->nr = 0;
3663 		TAILQ_FOREACH(altq, V_pf_altq_ifs_active, entries)
3664 			pa->nr++;
3665 		TAILQ_FOREACH(altq, V_pf_altqs_active, entries)
3666 			pa->nr++;
3667 		pa->ticket = V_ticket_altqs_active;
3668 		PF_RULES_RUNLOCK();
3669 		break;
3670 	}
3671 
3672 	case DIOCGETALTQV0:
3673 	case DIOCGETALTQV1: {
3674 		struct pfioc_altq_v1	*pa = (struct pfioc_altq_v1 *)addr;
3675 		struct pf_altq		*altq;
3676 
3677 		PF_RULES_RLOCK();
3678 		if (pa->ticket != V_ticket_altqs_active) {
3679 			PF_RULES_RUNLOCK();
3680 			error = EBUSY;
3681 			break;
3682 		}
3683 		altq = pf_altq_get_nth_active(pa->nr);
3684 		if (altq == NULL) {
3685 			PF_RULES_RUNLOCK();
3686 			error = EBUSY;
3687 			break;
3688 		}
3689 		pf_export_kaltq(altq, pa, IOCPARM_LEN(cmd));
3690 		PF_RULES_RUNLOCK();
3691 		break;
3692 	}
3693 
3694 	case DIOCCHANGEALTQV0:
3695 	case DIOCCHANGEALTQV1:
3696 		/* CHANGEALTQ not supported yet! */
3697 		error = ENODEV;
3698 		break;
3699 
3700 	case DIOCGETQSTATSV0:
3701 	case DIOCGETQSTATSV1: {
3702 		struct pfioc_qstats_v1	*pq = (struct pfioc_qstats_v1 *)addr;
3703 		struct pf_altq		*altq;
3704 		int			 nbytes;
3705 		u_int32_t		 version;
3706 
3707 		PF_RULES_RLOCK();
3708 		if (pq->ticket != V_ticket_altqs_active) {
3709 			PF_RULES_RUNLOCK();
3710 			error = EBUSY;
3711 			break;
3712 		}
3713 		nbytes = pq->nbytes;
3714 		altq = pf_altq_get_nth_active(pq->nr);
3715 		if (altq == NULL) {
3716 			PF_RULES_RUNLOCK();
3717 			error = EBUSY;
3718 			break;
3719 		}
3720 
3721 		if ((altq->local_flags & PFALTQ_FLAG_IF_REMOVED) != 0) {
3722 			PF_RULES_RUNLOCK();
3723 			error = ENXIO;
3724 			break;
3725 		}
3726 		PF_RULES_RUNLOCK();
3727 		if (cmd == DIOCGETQSTATSV0)
3728 			version = 0;  /* DIOCGETQSTATSV0 means stats struct v0 */
3729 		else
3730 			version = pq->version;
3731 		error = altq_getqstats(altq, pq->buf, &nbytes, version);
3732 		if (error == 0) {
3733 			pq->scheduler = altq->scheduler;
3734 			pq->nbytes = nbytes;
3735 		}
3736 		break;
3737 	}
3738 #endif /* ALTQ */
3739 
3740 	case DIOCBEGINADDRS: {
3741 		struct pfioc_pooladdr	*pp = (struct pfioc_pooladdr *)addr;
3742 
3743 		PF_RULES_WLOCK();
3744 		pf_empty_kpool(&V_pf_pabuf);
3745 		pp->ticket = ++V_ticket_pabuf;
3746 		PF_RULES_WUNLOCK();
3747 		break;
3748 	}
3749 
3750 	case DIOCADDADDR: {
3751 		struct pfioc_pooladdr	*pp = (struct pfioc_pooladdr *)addr;
3752 		struct pf_kpooladdr	*pa;
3753 		struct pfi_kkif		*kif = NULL;
3754 
3755 #ifndef INET
3756 		if (pp->af == AF_INET) {
3757 			error = EAFNOSUPPORT;
3758 			break;
3759 		}
3760 #endif /* INET */
3761 #ifndef INET6
3762 		if (pp->af == AF_INET6) {
3763 			error = EAFNOSUPPORT;
3764 			break;
3765 		}
3766 #endif /* INET6 */
3767 		if (pp->addr.addr.type != PF_ADDR_ADDRMASK &&
3768 		    pp->addr.addr.type != PF_ADDR_DYNIFTL &&
3769 		    pp->addr.addr.type != PF_ADDR_TABLE) {
3770 			error = EINVAL;
3771 			break;
3772 		}
3773 		if (pp->addr.addr.p.dyn != NULL) {
3774 			error = EINVAL;
3775 			break;
3776 		}
3777 		pa = malloc(sizeof(*pa), M_PFRULE, M_WAITOK);
3778 		pf_pooladdr_to_kpooladdr(&pp->addr, pa);
3779 		if (pa->ifname[0])
3780 			kif = pf_kkif_create(M_WAITOK);
3781 		PF_RULES_WLOCK();
3782 		if (pp->ticket != V_ticket_pabuf) {
3783 			PF_RULES_WUNLOCK();
3784 			if (pa->ifname[0])
3785 				pf_kkif_free(kif);
3786 			free(pa, M_PFRULE);
3787 			error = EBUSY;
3788 			break;
3789 		}
3790 		if (pa->ifname[0]) {
3791 			pa->kif = pfi_kkif_attach(kif, pa->ifname);
3792 			kif = NULL;
3793 			pfi_kkif_ref(pa->kif);
3794 		} else
3795 			pa->kif = NULL;
3796 		if (pa->addr.type == PF_ADDR_DYNIFTL && ((error =
3797 		    pfi_dynaddr_setup(&pa->addr, pp->af)) != 0)) {
3798 			if (pa->ifname[0])
3799 				pfi_kkif_unref(pa->kif);
3800 			PF_RULES_WUNLOCK();
3801 			free(pa, M_PFRULE);
3802 			break;
3803 		}
3804 		TAILQ_INSERT_TAIL(&V_pf_pabuf, pa, entries);
3805 		PF_RULES_WUNLOCK();
3806 		break;
3807 	}
3808 
3809 	case DIOCGETADDRS: {
3810 		struct pfioc_pooladdr	*pp = (struct pfioc_pooladdr *)addr;
3811 		struct pf_kpool		*pool;
3812 		struct pf_kpooladdr	*pa;
3813 
3814 		PF_RULES_RLOCK();
3815 		pp->nr = 0;
3816 		pool = pf_get_kpool(pp->anchor, pp->ticket, pp->r_action,
3817 		    pp->r_num, 0, 1, 0);
3818 		if (pool == NULL) {
3819 			PF_RULES_RUNLOCK();
3820 			error = EBUSY;
3821 			break;
3822 		}
3823 		TAILQ_FOREACH(pa, &pool->list, entries)
3824 			pp->nr++;
3825 		PF_RULES_RUNLOCK();
3826 		break;
3827 	}
3828 
3829 	case DIOCGETADDR: {
3830 		struct pfioc_pooladdr	*pp = (struct pfioc_pooladdr *)addr;
3831 		struct pf_kpool		*pool;
3832 		struct pf_kpooladdr	*pa;
3833 		u_int32_t		 nr = 0;
3834 
3835 		PF_RULES_RLOCK();
3836 		pool = pf_get_kpool(pp->anchor, pp->ticket, pp->r_action,
3837 		    pp->r_num, 0, 1, 1);
3838 		if (pool == NULL) {
3839 			PF_RULES_RUNLOCK();
3840 			error = EBUSY;
3841 			break;
3842 		}
3843 		pa = TAILQ_FIRST(&pool->list);
3844 		while ((pa != NULL) && (nr < pp->nr)) {
3845 			pa = TAILQ_NEXT(pa, entries);
3846 			nr++;
3847 		}
3848 		if (pa == NULL) {
3849 			PF_RULES_RUNLOCK();
3850 			error = EBUSY;
3851 			break;
3852 		}
3853 		pf_kpooladdr_to_pooladdr(pa, &pp->addr);
3854 		pf_addr_copyout(&pp->addr.addr);
3855 		PF_RULES_RUNLOCK();
3856 		break;
3857 	}
3858 
3859 	case DIOCCHANGEADDR: {
3860 		struct pfioc_pooladdr	*pca = (struct pfioc_pooladdr *)addr;
3861 		struct pf_kpool		*pool;
3862 		struct pf_kpooladdr	*oldpa = NULL, *newpa = NULL;
3863 		struct pf_kruleset	*ruleset;
3864 		struct pfi_kkif		*kif = NULL;
3865 
3866 		if (pca->action < PF_CHANGE_ADD_HEAD ||
3867 		    pca->action > PF_CHANGE_REMOVE) {
3868 			error = EINVAL;
3869 			break;
3870 		}
3871 		if (pca->addr.addr.type != PF_ADDR_ADDRMASK &&
3872 		    pca->addr.addr.type != PF_ADDR_DYNIFTL &&
3873 		    pca->addr.addr.type != PF_ADDR_TABLE) {
3874 			error = EINVAL;
3875 			break;
3876 		}
3877 		if (pca->addr.addr.p.dyn != NULL) {
3878 			error = EINVAL;
3879 			break;
3880 		}
3881 
3882 		if (pca->action != PF_CHANGE_REMOVE) {
3883 #ifndef INET
3884 			if (pca->af == AF_INET) {
3885 				error = EAFNOSUPPORT;
3886 				break;
3887 			}
3888 #endif /* INET */
3889 #ifndef INET6
3890 			if (pca->af == AF_INET6) {
3891 				error = EAFNOSUPPORT;
3892 				break;
3893 			}
3894 #endif /* INET6 */
3895 			newpa = malloc(sizeof(*newpa), M_PFRULE, M_WAITOK);
3896 			bcopy(&pca->addr, newpa, sizeof(struct pf_pooladdr));
3897 			if (newpa->ifname[0])
3898 				kif = pf_kkif_create(M_WAITOK);
3899 			newpa->kif = NULL;
3900 		}
3901 #define	ERROUT(x)	{ error = (x); goto DIOCCHANGEADDR_error; }
3902 		PF_RULES_WLOCK();
3903 		ruleset = pf_find_kruleset(pca->anchor);
3904 		if (ruleset == NULL)
3905 			ERROUT(EBUSY);
3906 
3907 		pool = pf_get_kpool(pca->anchor, pca->ticket, pca->r_action,
3908 		    pca->r_num, pca->r_last, 1, 1);
3909 		if (pool == NULL)
3910 			ERROUT(EBUSY);
3911 
3912 		if (pca->action != PF_CHANGE_REMOVE) {
3913 			if (newpa->ifname[0]) {
3914 				newpa->kif = pfi_kkif_attach(kif, newpa->ifname);
3915 				pfi_kkif_ref(newpa->kif);
3916 				kif = NULL;
3917 			}
3918 
3919 			switch (newpa->addr.type) {
3920 			case PF_ADDR_DYNIFTL:
3921 				error = pfi_dynaddr_setup(&newpa->addr,
3922 				    pca->af);
3923 				break;
3924 			case PF_ADDR_TABLE:
3925 				newpa->addr.p.tbl = pfr_attach_table(ruleset,
3926 				    newpa->addr.v.tblname);
3927 				if (newpa->addr.p.tbl == NULL)
3928 					error = ENOMEM;
3929 				break;
3930 			}
3931 			if (error)
3932 				goto DIOCCHANGEADDR_error;
3933 		}
3934 
3935 		switch (pca->action) {
3936 		case PF_CHANGE_ADD_HEAD:
3937 			oldpa = TAILQ_FIRST(&pool->list);
3938 			break;
3939 		case PF_CHANGE_ADD_TAIL:
3940 			oldpa = TAILQ_LAST(&pool->list, pf_kpalist);
3941 			break;
3942 		default:
3943 			oldpa = TAILQ_FIRST(&pool->list);
3944 			for (int i = 0; oldpa && i < pca->nr; i++)
3945 				oldpa = TAILQ_NEXT(oldpa, entries);
3946 
3947 			if (oldpa == NULL)
3948 				ERROUT(EINVAL);
3949 		}
3950 
3951 		if (pca->action == PF_CHANGE_REMOVE) {
3952 			TAILQ_REMOVE(&pool->list, oldpa, entries);
3953 			switch (oldpa->addr.type) {
3954 			case PF_ADDR_DYNIFTL:
3955 				pfi_dynaddr_remove(oldpa->addr.p.dyn);
3956 				break;
3957 			case PF_ADDR_TABLE:
3958 				pfr_detach_table(oldpa->addr.p.tbl);
3959 				break;
3960 			}
3961 			if (oldpa->kif)
3962 				pfi_kkif_unref(oldpa->kif);
3963 			free(oldpa, M_PFRULE);
3964 		} else {
3965 			if (oldpa == NULL)
3966 				TAILQ_INSERT_TAIL(&pool->list, newpa, entries);
3967 			else if (pca->action == PF_CHANGE_ADD_HEAD ||
3968 			    pca->action == PF_CHANGE_ADD_BEFORE)
3969 				TAILQ_INSERT_BEFORE(oldpa, newpa, entries);
3970 			else
3971 				TAILQ_INSERT_AFTER(&pool->list, oldpa,
3972 				    newpa, entries);
3973 		}
3974 
3975 		pool->cur = TAILQ_FIRST(&pool->list);
3976 		PF_ACPY(&pool->counter, &pool->cur->addr.v.a.addr, pca->af);
3977 		PF_RULES_WUNLOCK();
3978 		break;
3979 
3980 #undef ERROUT
3981 DIOCCHANGEADDR_error:
3982 		if (newpa != NULL) {
3983 			if (newpa->kif)
3984 				pfi_kkif_unref(newpa->kif);
3985 			free(newpa, M_PFRULE);
3986 		}
3987 		PF_RULES_WUNLOCK();
3988 		pf_kkif_free(kif);
3989 		break;
3990 	}
3991 
3992 	case DIOCGETRULESETS: {
3993 		struct pfioc_ruleset	*pr = (struct pfioc_ruleset *)addr;
3994 		struct pf_kruleset	*ruleset;
3995 		struct pf_kanchor	*anchor;
3996 
3997 		PF_RULES_RLOCK();
3998 		pr->path[sizeof(pr->path) - 1] = 0;
3999 		if ((ruleset = pf_find_kruleset(pr->path)) == NULL) {
4000 			PF_RULES_RUNLOCK();
4001 			error = ENOENT;
4002 			break;
4003 		}
4004 		pr->nr = 0;
4005 		if (ruleset->anchor == NULL) {
4006 			/* XXX kludge for pf_main_ruleset */
4007 			RB_FOREACH(anchor, pf_kanchor_global, &V_pf_anchors)
4008 				if (anchor->parent == NULL)
4009 					pr->nr++;
4010 		} else {
4011 			RB_FOREACH(anchor, pf_kanchor_node,
4012 			    &ruleset->anchor->children)
4013 				pr->nr++;
4014 		}
4015 		PF_RULES_RUNLOCK();
4016 		break;
4017 	}
4018 
4019 	case DIOCGETRULESET: {
4020 		struct pfioc_ruleset	*pr = (struct pfioc_ruleset *)addr;
4021 		struct pf_kruleset	*ruleset;
4022 		struct pf_kanchor	*anchor;
4023 		u_int32_t		 nr = 0;
4024 
4025 		PF_RULES_RLOCK();
4026 		pr->path[sizeof(pr->path) - 1] = 0;
4027 		if ((ruleset = pf_find_kruleset(pr->path)) == NULL) {
4028 			PF_RULES_RUNLOCK();
4029 			error = ENOENT;
4030 			break;
4031 		}
4032 		pr->name[0] = 0;
4033 		if (ruleset->anchor == NULL) {
4034 			/* XXX kludge for pf_main_ruleset */
4035 			RB_FOREACH(anchor, pf_kanchor_global, &V_pf_anchors)
4036 				if (anchor->parent == NULL && nr++ == pr->nr) {
4037 					strlcpy(pr->name, anchor->name,
4038 					    sizeof(pr->name));
4039 					break;
4040 				}
4041 		} else {
4042 			RB_FOREACH(anchor, pf_kanchor_node,
4043 			    &ruleset->anchor->children)
4044 				if (nr++ == pr->nr) {
4045 					strlcpy(pr->name, anchor->name,
4046 					    sizeof(pr->name));
4047 					break;
4048 				}
4049 		}
4050 		if (!pr->name[0])
4051 			error = EBUSY;
4052 		PF_RULES_RUNLOCK();
4053 		break;
4054 	}
4055 
4056 	case DIOCRCLRTABLES: {
4057 		struct pfioc_table *io = (struct pfioc_table *)addr;
4058 
4059 		if (io->pfrio_esize != 0) {
4060 			error = ENODEV;
4061 			break;
4062 		}
4063 		PF_RULES_WLOCK();
4064 		error = pfr_clr_tables(&io->pfrio_table, &io->pfrio_ndel,
4065 		    io->pfrio_flags | PFR_FLAG_USERIOCTL);
4066 		PF_RULES_WUNLOCK();
4067 		break;
4068 	}
4069 
4070 	case DIOCRADDTABLES: {
4071 		struct pfioc_table *io = (struct pfioc_table *)addr;
4072 		struct pfr_table *pfrts;
4073 		size_t totlen;
4074 
4075 		if (io->pfrio_esize != sizeof(struct pfr_table)) {
4076 			error = ENODEV;
4077 			break;
4078 		}
4079 
4080 		if (io->pfrio_size < 0 || io->pfrio_size > pf_ioctl_maxcount ||
4081 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_table))) {
4082 			error = ENOMEM;
4083 			break;
4084 		}
4085 
4086 		totlen = io->pfrio_size * sizeof(struct pfr_table);
4087 		pfrts = mallocarray(io->pfrio_size, sizeof(struct pfr_table),
4088 		    M_TEMP, M_WAITOK);
4089 		error = copyin(io->pfrio_buffer, pfrts, totlen);
4090 		if (error) {
4091 			free(pfrts, M_TEMP);
4092 			break;
4093 		}
4094 		PF_RULES_WLOCK();
4095 		error = pfr_add_tables(pfrts, io->pfrio_size,
4096 		    &io->pfrio_nadd, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4097 		PF_RULES_WUNLOCK();
4098 		free(pfrts, M_TEMP);
4099 		break;
4100 	}
4101 
4102 	case DIOCRDELTABLES: {
4103 		struct pfioc_table *io = (struct pfioc_table *)addr;
4104 		struct pfr_table *pfrts;
4105 		size_t totlen;
4106 
4107 		if (io->pfrio_esize != sizeof(struct pfr_table)) {
4108 			error = ENODEV;
4109 			break;
4110 		}
4111 
4112 		if (io->pfrio_size < 0 || io->pfrio_size > pf_ioctl_maxcount ||
4113 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_table))) {
4114 			error = ENOMEM;
4115 			break;
4116 		}
4117 
4118 		totlen = io->pfrio_size * sizeof(struct pfr_table);
4119 		pfrts = mallocarray(io->pfrio_size, sizeof(struct pfr_table),
4120 		    M_TEMP, M_WAITOK);
4121 		error = copyin(io->pfrio_buffer, pfrts, totlen);
4122 		if (error) {
4123 			free(pfrts, M_TEMP);
4124 			break;
4125 		}
4126 		PF_RULES_WLOCK();
4127 		error = pfr_del_tables(pfrts, io->pfrio_size,
4128 		    &io->pfrio_ndel, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4129 		PF_RULES_WUNLOCK();
4130 		free(pfrts, M_TEMP);
4131 		break;
4132 	}
4133 
4134 	case DIOCRGETTABLES: {
4135 		struct pfioc_table *io = (struct pfioc_table *)addr;
4136 		struct pfr_table *pfrts;
4137 		size_t totlen;
4138 		int n;
4139 
4140 		if (io->pfrio_esize != sizeof(struct pfr_table)) {
4141 			error = ENODEV;
4142 			break;
4143 		}
4144 		PF_RULES_RLOCK();
4145 		n = pfr_table_count(&io->pfrio_table, io->pfrio_flags);
4146 		if (n < 0) {
4147 			PF_RULES_RUNLOCK();
4148 			error = EINVAL;
4149 			break;
4150 		}
4151 		io->pfrio_size = min(io->pfrio_size, n);
4152 
4153 		totlen = io->pfrio_size * sizeof(struct pfr_table);
4154 
4155 		pfrts = mallocarray(io->pfrio_size, sizeof(struct pfr_table),
4156 		    M_TEMP, M_NOWAIT);
4157 		if (pfrts == NULL) {
4158 			error = ENOMEM;
4159 			PF_RULES_RUNLOCK();
4160 			break;
4161 		}
4162 		error = pfr_get_tables(&io->pfrio_table, pfrts,
4163 		    &io->pfrio_size, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4164 		PF_RULES_RUNLOCK();
4165 		if (error == 0)
4166 			error = copyout(pfrts, io->pfrio_buffer, totlen);
4167 		free(pfrts, M_TEMP);
4168 		break;
4169 	}
4170 
4171 	case DIOCRGETTSTATS: {
4172 		struct pfioc_table *io = (struct pfioc_table *)addr;
4173 		struct pfr_tstats *pfrtstats;
4174 		size_t totlen;
4175 		int n;
4176 
4177 		if (io->pfrio_esize != sizeof(struct pfr_tstats)) {
4178 			error = ENODEV;
4179 			break;
4180 		}
4181 		PF_RULES_WLOCK();
4182 		n = pfr_table_count(&io->pfrio_table, io->pfrio_flags);
4183 		if (n < 0) {
4184 			PF_RULES_WUNLOCK();
4185 			error = EINVAL;
4186 			break;
4187 		}
4188 		io->pfrio_size = min(io->pfrio_size, n);
4189 
4190 		totlen = io->pfrio_size * sizeof(struct pfr_tstats);
4191 		pfrtstats = mallocarray(io->pfrio_size,
4192 		    sizeof(struct pfr_tstats), M_TEMP, M_NOWAIT);
4193 		if (pfrtstats == NULL) {
4194 			error = ENOMEM;
4195 			PF_RULES_WUNLOCK();
4196 			break;
4197 		}
4198 		error = pfr_get_tstats(&io->pfrio_table, pfrtstats,
4199 		    &io->pfrio_size, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4200 		PF_RULES_WUNLOCK();
4201 		if (error == 0)
4202 			error = copyout(pfrtstats, io->pfrio_buffer, totlen);
4203 		free(pfrtstats, M_TEMP);
4204 		break;
4205 	}
4206 
4207 	case DIOCRCLRTSTATS: {
4208 		struct pfioc_table *io = (struct pfioc_table *)addr;
4209 		struct pfr_table *pfrts;
4210 		size_t totlen;
4211 
4212 		if (io->pfrio_esize != sizeof(struct pfr_table)) {
4213 			error = ENODEV;
4214 			break;
4215 		}
4216 
4217 		if (io->pfrio_size < 0 || io->pfrio_size > pf_ioctl_maxcount ||
4218 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_table))) {
4219 			/* We used to count tables and use the minimum required
4220 			 * size, so we didn't fail on overly large requests.
4221 			 * Keep doing so. */
4222 			io->pfrio_size = pf_ioctl_maxcount;
4223 			break;
4224 		}
4225 
4226 		totlen = io->pfrio_size * sizeof(struct pfr_table);
4227 		pfrts = mallocarray(io->pfrio_size, sizeof(struct pfr_table),
4228 		    M_TEMP, M_NOWAIT);
4229 		if (pfrts == NULL) {
4230 			error = ENOMEM;
4231 			break;
4232 		}
4233 		error = copyin(io->pfrio_buffer, pfrts, totlen);
4234 		if (error) {
4235 			free(pfrts, M_TEMP);
4236 			break;
4237 		}
4238 
4239 		PF_RULES_WLOCK();
4240 		error = pfr_clr_tstats(pfrts, io->pfrio_size,
4241 		    &io->pfrio_nzero, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4242 		PF_RULES_WUNLOCK();
4243 		free(pfrts, M_TEMP);
4244 		break;
4245 	}
4246 
4247 	case DIOCRSETTFLAGS: {
4248 		struct pfioc_table *io = (struct pfioc_table *)addr;
4249 		struct pfr_table *pfrts;
4250 		size_t totlen;
4251 		int n;
4252 
4253 		if (io->pfrio_esize != sizeof(struct pfr_table)) {
4254 			error = ENODEV;
4255 			break;
4256 		}
4257 
4258 		PF_RULES_RLOCK();
4259 		n = pfr_table_count(&io->pfrio_table, io->pfrio_flags);
4260 		if (n < 0) {
4261 			PF_RULES_RUNLOCK();
4262 			error = EINVAL;
4263 			break;
4264 		}
4265 
4266 		io->pfrio_size = min(io->pfrio_size, n);
4267 		PF_RULES_RUNLOCK();
4268 
4269 		totlen = io->pfrio_size * sizeof(struct pfr_table);
4270 		pfrts = mallocarray(io->pfrio_size, sizeof(struct pfr_table),
4271 		    M_TEMP, M_WAITOK);
4272 		error = copyin(io->pfrio_buffer, pfrts, totlen);
4273 		if (error) {
4274 			free(pfrts, M_TEMP);
4275 			break;
4276 		}
4277 		PF_RULES_WLOCK();
4278 		error = pfr_set_tflags(pfrts, io->pfrio_size,
4279 		    io->pfrio_setflag, io->pfrio_clrflag, &io->pfrio_nchange,
4280 		    &io->pfrio_ndel, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4281 		PF_RULES_WUNLOCK();
4282 		free(pfrts, M_TEMP);
4283 		break;
4284 	}
4285 
4286 	case DIOCRCLRADDRS: {
4287 		struct pfioc_table *io = (struct pfioc_table *)addr;
4288 
4289 		if (io->pfrio_esize != 0) {
4290 			error = ENODEV;
4291 			break;
4292 		}
4293 		PF_RULES_WLOCK();
4294 		error = pfr_clr_addrs(&io->pfrio_table, &io->pfrio_ndel,
4295 		    io->pfrio_flags | PFR_FLAG_USERIOCTL);
4296 		PF_RULES_WUNLOCK();
4297 		break;
4298 	}
4299 
4300 	case DIOCRADDADDRS: {
4301 		struct pfioc_table *io = (struct pfioc_table *)addr;
4302 		struct pfr_addr *pfras;
4303 		size_t totlen;
4304 
4305 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4306 			error = ENODEV;
4307 			break;
4308 		}
4309 		if (io->pfrio_size < 0 ||
4310 		    io->pfrio_size > pf_ioctl_maxcount ||
4311 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4312 			error = EINVAL;
4313 			break;
4314 		}
4315 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4316 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4317 		    M_TEMP, M_NOWAIT);
4318 		if (! pfras) {
4319 			error = ENOMEM;
4320 			break;
4321 		}
4322 		error = copyin(io->pfrio_buffer, pfras, totlen);
4323 		if (error) {
4324 			free(pfras, M_TEMP);
4325 			break;
4326 		}
4327 		PF_RULES_WLOCK();
4328 		error = pfr_add_addrs(&io->pfrio_table, pfras,
4329 		    io->pfrio_size, &io->pfrio_nadd, io->pfrio_flags |
4330 		    PFR_FLAG_USERIOCTL);
4331 		PF_RULES_WUNLOCK();
4332 		if (error == 0 && io->pfrio_flags & PFR_FLAG_FEEDBACK)
4333 			error = copyout(pfras, io->pfrio_buffer, totlen);
4334 		free(pfras, M_TEMP);
4335 		break;
4336 	}
4337 
4338 	case DIOCRDELADDRS: {
4339 		struct pfioc_table *io = (struct pfioc_table *)addr;
4340 		struct pfr_addr *pfras;
4341 		size_t totlen;
4342 
4343 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4344 			error = ENODEV;
4345 			break;
4346 		}
4347 		if (io->pfrio_size < 0 ||
4348 		    io->pfrio_size > pf_ioctl_maxcount ||
4349 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4350 			error = EINVAL;
4351 			break;
4352 		}
4353 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4354 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4355 		    M_TEMP, M_NOWAIT);
4356 		if (! pfras) {
4357 			error = ENOMEM;
4358 			break;
4359 		}
4360 		error = copyin(io->pfrio_buffer, pfras, totlen);
4361 		if (error) {
4362 			free(pfras, M_TEMP);
4363 			break;
4364 		}
4365 		PF_RULES_WLOCK();
4366 		error = pfr_del_addrs(&io->pfrio_table, pfras,
4367 		    io->pfrio_size, &io->pfrio_ndel, io->pfrio_flags |
4368 		    PFR_FLAG_USERIOCTL);
4369 		PF_RULES_WUNLOCK();
4370 		if (error == 0 && io->pfrio_flags & PFR_FLAG_FEEDBACK)
4371 			error = copyout(pfras, io->pfrio_buffer, totlen);
4372 		free(pfras, M_TEMP);
4373 		break;
4374 	}
4375 
4376 	case DIOCRSETADDRS: {
4377 		struct pfioc_table *io = (struct pfioc_table *)addr;
4378 		struct pfr_addr *pfras;
4379 		size_t totlen, count;
4380 
4381 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4382 			error = ENODEV;
4383 			break;
4384 		}
4385 		if (io->pfrio_size < 0 || io->pfrio_size2 < 0) {
4386 			error = EINVAL;
4387 			break;
4388 		}
4389 		count = max(io->pfrio_size, io->pfrio_size2);
4390 		if (count > pf_ioctl_maxcount ||
4391 		    WOULD_OVERFLOW(count, sizeof(struct pfr_addr))) {
4392 			error = EINVAL;
4393 			break;
4394 		}
4395 		totlen = count * sizeof(struct pfr_addr);
4396 		pfras = mallocarray(count, sizeof(struct pfr_addr), M_TEMP,
4397 		    M_NOWAIT);
4398 		if (! pfras) {
4399 			error = ENOMEM;
4400 			break;
4401 		}
4402 		error = copyin(io->pfrio_buffer, pfras, totlen);
4403 		if (error) {
4404 			free(pfras, M_TEMP);
4405 			break;
4406 		}
4407 		PF_RULES_WLOCK();
4408 		error = pfr_set_addrs(&io->pfrio_table, pfras,
4409 		    io->pfrio_size, &io->pfrio_size2, &io->pfrio_nadd,
4410 		    &io->pfrio_ndel, &io->pfrio_nchange, io->pfrio_flags |
4411 		    PFR_FLAG_USERIOCTL, 0);
4412 		PF_RULES_WUNLOCK();
4413 		if (error == 0 && io->pfrio_flags & PFR_FLAG_FEEDBACK)
4414 			error = copyout(pfras, io->pfrio_buffer, totlen);
4415 		free(pfras, M_TEMP);
4416 		break;
4417 	}
4418 
4419 	case DIOCRGETADDRS: {
4420 		struct pfioc_table *io = (struct pfioc_table *)addr;
4421 		struct pfr_addr *pfras;
4422 		size_t totlen;
4423 
4424 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4425 			error = ENODEV;
4426 			break;
4427 		}
4428 		if (io->pfrio_size < 0 ||
4429 		    io->pfrio_size > pf_ioctl_maxcount ||
4430 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4431 			error = EINVAL;
4432 			break;
4433 		}
4434 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4435 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4436 		    M_TEMP, M_NOWAIT);
4437 		if (! pfras) {
4438 			error = ENOMEM;
4439 			break;
4440 		}
4441 		PF_RULES_RLOCK();
4442 		error = pfr_get_addrs(&io->pfrio_table, pfras,
4443 		    &io->pfrio_size, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4444 		PF_RULES_RUNLOCK();
4445 		if (error == 0)
4446 			error = copyout(pfras, io->pfrio_buffer, totlen);
4447 		free(pfras, M_TEMP);
4448 		break;
4449 	}
4450 
4451 	case DIOCRGETASTATS: {
4452 		struct pfioc_table *io = (struct pfioc_table *)addr;
4453 		struct pfr_astats *pfrastats;
4454 		size_t totlen;
4455 
4456 		if (io->pfrio_esize != sizeof(struct pfr_astats)) {
4457 			error = ENODEV;
4458 			break;
4459 		}
4460 		if (io->pfrio_size < 0 ||
4461 		    io->pfrio_size > pf_ioctl_maxcount ||
4462 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_astats))) {
4463 			error = EINVAL;
4464 			break;
4465 		}
4466 		totlen = io->pfrio_size * sizeof(struct pfr_astats);
4467 		pfrastats = mallocarray(io->pfrio_size,
4468 		    sizeof(struct pfr_astats), M_TEMP, M_NOWAIT);
4469 		if (! pfrastats) {
4470 			error = ENOMEM;
4471 			break;
4472 		}
4473 		PF_RULES_RLOCK();
4474 		error = pfr_get_astats(&io->pfrio_table, pfrastats,
4475 		    &io->pfrio_size, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4476 		PF_RULES_RUNLOCK();
4477 		if (error == 0)
4478 			error = copyout(pfrastats, io->pfrio_buffer, totlen);
4479 		free(pfrastats, M_TEMP);
4480 		break;
4481 	}
4482 
4483 	case DIOCRCLRASTATS: {
4484 		struct pfioc_table *io = (struct pfioc_table *)addr;
4485 		struct pfr_addr *pfras;
4486 		size_t totlen;
4487 
4488 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4489 			error = ENODEV;
4490 			break;
4491 		}
4492 		if (io->pfrio_size < 0 ||
4493 		    io->pfrio_size > pf_ioctl_maxcount ||
4494 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4495 			error = EINVAL;
4496 			break;
4497 		}
4498 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4499 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4500 		    M_TEMP, M_NOWAIT);
4501 		if (! pfras) {
4502 			error = ENOMEM;
4503 			break;
4504 		}
4505 		error = copyin(io->pfrio_buffer, pfras, totlen);
4506 		if (error) {
4507 			free(pfras, M_TEMP);
4508 			break;
4509 		}
4510 		PF_RULES_WLOCK();
4511 		error = pfr_clr_astats(&io->pfrio_table, pfras,
4512 		    io->pfrio_size, &io->pfrio_nzero, io->pfrio_flags |
4513 		    PFR_FLAG_USERIOCTL);
4514 		PF_RULES_WUNLOCK();
4515 		if (error == 0 && io->pfrio_flags & PFR_FLAG_FEEDBACK)
4516 			error = copyout(pfras, io->pfrio_buffer, totlen);
4517 		free(pfras, M_TEMP);
4518 		break;
4519 	}
4520 
4521 	case DIOCRTSTADDRS: {
4522 		struct pfioc_table *io = (struct pfioc_table *)addr;
4523 		struct pfr_addr *pfras;
4524 		size_t totlen;
4525 
4526 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4527 			error = ENODEV;
4528 			break;
4529 		}
4530 		if (io->pfrio_size < 0 ||
4531 		    io->pfrio_size > pf_ioctl_maxcount ||
4532 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4533 			error = EINVAL;
4534 			break;
4535 		}
4536 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4537 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4538 		    M_TEMP, M_NOWAIT);
4539 		if (! pfras) {
4540 			error = ENOMEM;
4541 			break;
4542 		}
4543 		error = copyin(io->pfrio_buffer, pfras, totlen);
4544 		if (error) {
4545 			free(pfras, M_TEMP);
4546 			break;
4547 		}
4548 		PF_RULES_RLOCK();
4549 		error = pfr_tst_addrs(&io->pfrio_table, pfras,
4550 		    io->pfrio_size, &io->pfrio_nmatch, io->pfrio_flags |
4551 		    PFR_FLAG_USERIOCTL);
4552 		PF_RULES_RUNLOCK();
4553 		if (error == 0)
4554 			error = copyout(pfras, io->pfrio_buffer, totlen);
4555 		free(pfras, M_TEMP);
4556 		break;
4557 	}
4558 
4559 	case DIOCRINADEFINE: {
4560 		struct pfioc_table *io = (struct pfioc_table *)addr;
4561 		struct pfr_addr *pfras;
4562 		size_t totlen;
4563 
4564 		if (io->pfrio_esize != sizeof(struct pfr_addr)) {
4565 			error = ENODEV;
4566 			break;
4567 		}
4568 		if (io->pfrio_size < 0 ||
4569 		    io->pfrio_size > pf_ioctl_maxcount ||
4570 		    WOULD_OVERFLOW(io->pfrio_size, sizeof(struct pfr_addr))) {
4571 			error = EINVAL;
4572 			break;
4573 		}
4574 		totlen = io->pfrio_size * sizeof(struct pfr_addr);
4575 		pfras = mallocarray(io->pfrio_size, sizeof(struct pfr_addr),
4576 		    M_TEMP, M_NOWAIT);
4577 		if (! pfras) {
4578 			error = ENOMEM;
4579 			break;
4580 		}
4581 		error = copyin(io->pfrio_buffer, pfras, totlen);
4582 		if (error) {
4583 			free(pfras, M_TEMP);
4584 			break;
4585 		}
4586 		PF_RULES_WLOCK();
4587 		error = pfr_ina_define(&io->pfrio_table, pfras,
4588 		    io->pfrio_size, &io->pfrio_nadd, &io->pfrio_naddr,
4589 		    io->pfrio_ticket, io->pfrio_flags | PFR_FLAG_USERIOCTL);
4590 		PF_RULES_WUNLOCK();
4591 		free(pfras, M_TEMP);
4592 		break;
4593 	}
4594 
4595 	case DIOCOSFPADD: {
4596 		struct pf_osfp_ioctl *io = (struct pf_osfp_ioctl *)addr;
4597 		PF_RULES_WLOCK();
4598 		error = pf_osfp_add(io);
4599 		PF_RULES_WUNLOCK();
4600 		break;
4601 	}
4602 
4603 	case DIOCOSFPGET: {
4604 		struct pf_osfp_ioctl *io = (struct pf_osfp_ioctl *)addr;
4605 		PF_RULES_RLOCK();
4606 		error = pf_osfp_get(io);
4607 		PF_RULES_RUNLOCK();
4608 		break;
4609 	}
4610 
4611 	case DIOCXBEGIN: {
4612 		struct pfioc_trans	*io = (struct pfioc_trans *)addr;
4613 		struct pfioc_trans_e	*ioes, *ioe;
4614 		size_t			 totlen;
4615 		int			 i;
4616 
4617 		if (io->esize != sizeof(*ioe)) {
4618 			error = ENODEV;
4619 			break;
4620 		}
4621 		if (io->size < 0 ||
4622 		    io->size > pf_ioctl_maxcount ||
4623 		    WOULD_OVERFLOW(io->size, sizeof(struct pfioc_trans_e))) {
4624 			error = EINVAL;
4625 			break;
4626 		}
4627 		totlen = sizeof(struct pfioc_trans_e) * io->size;
4628 		ioes = mallocarray(io->size, sizeof(struct pfioc_trans_e),
4629 		    M_TEMP, M_NOWAIT);
4630 		if (! ioes) {
4631 			error = ENOMEM;
4632 			break;
4633 		}
4634 		error = copyin(io->array, ioes, totlen);
4635 		if (error) {
4636 			free(ioes, M_TEMP);
4637 			break;
4638 		}
4639 		PF_RULES_WLOCK();
4640 		for (i = 0, ioe = ioes; i < io->size; i++, ioe++) {
4641 			switch (ioe->rs_num) {
4642 #ifdef ALTQ
4643 			case PF_RULESET_ALTQ:
4644 				if (ioe->anchor[0]) {
4645 					PF_RULES_WUNLOCK();
4646 					free(ioes, M_TEMP);
4647 					error = EINVAL;
4648 					goto fail;
4649 				}
4650 				if ((error = pf_begin_altq(&ioe->ticket))) {
4651 					PF_RULES_WUNLOCK();
4652 					free(ioes, M_TEMP);
4653 					goto fail;
4654 				}
4655 				break;
4656 #endif /* ALTQ */
4657 			case PF_RULESET_TABLE:
4658 			    {
4659 				struct pfr_table table;
4660 
4661 				bzero(&table, sizeof(table));
4662 				strlcpy(table.pfrt_anchor, ioe->anchor,
4663 				    sizeof(table.pfrt_anchor));
4664 				if ((error = pfr_ina_begin(&table,
4665 				    &ioe->ticket, NULL, 0))) {
4666 					PF_RULES_WUNLOCK();
4667 					free(ioes, M_TEMP);
4668 					goto fail;
4669 				}
4670 				break;
4671 			    }
4672 			default:
4673 				if ((error = pf_begin_rules(&ioe->ticket,
4674 				    ioe->rs_num, ioe->anchor))) {
4675 					PF_RULES_WUNLOCK();
4676 					free(ioes, M_TEMP);
4677 					goto fail;
4678 				}
4679 				break;
4680 			}
4681 		}
4682 		PF_RULES_WUNLOCK();
4683 		error = copyout(ioes, io->array, totlen);
4684 		free(ioes, M_TEMP);
4685 		break;
4686 	}
4687 
4688 	case DIOCXROLLBACK: {
4689 		struct pfioc_trans	*io = (struct pfioc_trans *)addr;
4690 		struct pfioc_trans_e	*ioe, *ioes;
4691 		size_t			 totlen;
4692 		int			 i;
4693 
4694 		if (io->esize != sizeof(*ioe)) {
4695 			error = ENODEV;
4696 			break;
4697 		}
4698 		if (io->size < 0 ||
4699 		    io->size > pf_ioctl_maxcount ||
4700 		    WOULD_OVERFLOW(io->size, sizeof(struct pfioc_trans_e))) {
4701 			error = EINVAL;
4702 			break;
4703 		}
4704 		totlen = sizeof(struct pfioc_trans_e) * io->size;
4705 		ioes = mallocarray(io->size, sizeof(struct pfioc_trans_e),
4706 		    M_TEMP, M_NOWAIT);
4707 		if (! ioes) {
4708 			error = ENOMEM;
4709 			break;
4710 		}
4711 		error = copyin(io->array, ioes, totlen);
4712 		if (error) {
4713 			free(ioes, M_TEMP);
4714 			break;
4715 		}
4716 		PF_RULES_WLOCK();
4717 		for (i = 0, ioe = ioes; i < io->size; i++, ioe++) {
4718 			switch (ioe->rs_num) {
4719 #ifdef ALTQ
4720 			case PF_RULESET_ALTQ:
4721 				if (ioe->anchor[0]) {
4722 					PF_RULES_WUNLOCK();
4723 					free(ioes, M_TEMP);
4724 					error = EINVAL;
4725 					goto fail;
4726 				}
4727 				if ((error = pf_rollback_altq(ioe->ticket))) {
4728 					PF_RULES_WUNLOCK();
4729 					free(ioes, M_TEMP);
4730 					goto fail; /* really bad */
4731 				}
4732 				break;
4733 #endif /* ALTQ */
4734 			case PF_RULESET_TABLE:
4735 			    {
4736 				struct pfr_table table;
4737 
4738 				bzero(&table, sizeof(table));
4739 				strlcpy(table.pfrt_anchor, ioe->anchor,
4740 				    sizeof(table.pfrt_anchor));
4741 				if ((error = pfr_ina_rollback(&table,
4742 				    ioe->ticket, NULL, 0))) {
4743 					PF_RULES_WUNLOCK();
4744 					free(ioes, M_TEMP);
4745 					goto fail; /* really bad */
4746 				}
4747 				break;
4748 			    }
4749 			default:
4750 				if ((error = pf_rollback_rules(ioe->ticket,
4751 				    ioe->rs_num, ioe->anchor))) {
4752 					PF_RULES_WUNLOCK();
4753 					free(ioes, M_TEMP);
4754 					goto fail; /* really bad */
4755 				}
4756 				break;
4757 			}
4758 		}
4759 		PF_RULES_WUNLOCK();
4760 		free(ioes, M_TEMP);
4761 		break;
4762 	}
4763 
4764 	case DIOCXCOMMIT: {
4765 		struct pfioc_trans	*io = (struct pfioc_trans *)addr;
4766 		struct pfioc_trans_e	*ioe, *ioes;
4767 		struct pf_kruleset	*rs;
4768 		size_t			 totlen;
4769 		int			 i;
4770 
4771 		if (io->esize != sizeof(*ioe)) {
4772 			error = ENODEV;
4773 			break;
4774 		}
4775 
4776 		if (io->size < 0 ||
4777 		    io->size > pf_ioctl_maxcount ||
4778 		    WOULD_OVERFLOW(io->size, sizeof(struct pfioc_trans_e))) {
4779 			error = EINVAL;
4780 			break;
4781 		}
4782 
4783 		totlen = sizeof(struct pfioc_trans_e) * io->size;
4784 		ioes = mallocarray(io->size, sizeof(struct pfioc_trans_e),
4785 		    M_TEMP, M_NOWAIT);
4786 		if (ioes == NULL) {
4787 			error = ENOMEM;
4788 			break;
4789 		}
4790 		error = copyin(io->array, ioes, totlen);
4791 		if (error) {
4792 			free(ioes, M_TEMP);
4793 			break;
4794 		}
4795 		PF_RULES_WLOCK();
4796 		/* First makes sure everything will succeed. */
4797 		for (i = 0, ioe = ioes; i < io->size; i++, ioe++) {
4798 			switch (ioe->rs_num) {
4799 #ifdef ALTQ
4800 			case PF_RULESET_ALTQ:
4801 				if (ioe->anchor[0]) {
4802 					PF_RULES_WUNLOCK();
4803 					free(ioes, M_TEMP);
4804 					error = EINVAL;
4805 					goto fail;
4806 				}
4807 				if (!V_altqs_inactive_open || ioe->ticket !=
4808 				    V_ticket_altqs_inactive) {
4809 					PF_RULES_WUNLOCK();
4810 					free(ioes, M_TEMP);
4811 					error = EBUSY;
4812 					goto fail;
4813 				}
4814 				break;
4815 #endif /* ALTQ */
4816 			case PF_RULESET_TABLE:
4817 				rs = pf_find_kruleset(ioe->anchor);
4818 				if (rs == NULL || !rs->topen || ioe->ticket !=
4819 				    rs->tticket) {
4820 					PF_RULES_WUNLOCK();
4821 					free(ioes, M_TEMP);
4822 					error = EBUSY;
4823 					goto fail;
4824 				}
4825 				break;
4826 			default:
4827 				if (ioe->rs_num < 0 || ioe->rs_num >=
4828 				    PF_RULESET_MAX) {
4829 					PF_RULES_WUNLOCK();
4830 					free(ioes, M_TEMP);
4831 					error = EINVAL;
4832 					goto fail;
4833 				}
4834 				rs = pf_find_kruleset(ioe->anchor);
4835 				if (rs == NULL ||
4836 				    !rs->rules[ioe->rs_num].inactive.open ||
4837 				    rs->rules[ioe->rs_num].inactive.ticket !=
4838 				    ioe->ticket) {
4839 					PF_RULES_WUNLOCK();
4840 					free(ioes, M_TEMP);
4841 					error = EBUSY;
4842 					goto fail;
4843 				}
4844 				break;
4845 			}
4846 		}
4847 		/* Now do the commit - no errors should happen here. */
4848 		for (i = 0, ioe = ioes; i < io->size; i++, ioe++) {
4849 			switch (ioe->rs_num) {
4850 #ifdef ALTQ
4851 			case PF_RULESET_ALTQ:
4852 				if ((error = pf_commit_altq(ioe->ticket))) {
4853 					PF_RULES_WUNLOCK();
4854 					free(ioes, M_TEMP);
4855 					goto fail; /* really bad */
4856 				}
4857 				break;
4858 #endif /* ALTQ */
4859 			case PF_RULESET_TABLE:
4860 			    {
4861 				struct pfr_table table;
4862 
4863 				bzero(&table, sizeof(table));
4864 				strlcpy(table.pfrt_anchor, ioe->anchor,
4865 				    sizeof(table.pfrt_anchor));
4866 				if ((error = pfr_ina_commit(&table,
4867 				    ioe->ticket, NULL, NULL, 0))) {
4868 					PF_RULES_WUNLOCK();
4869 					free(ioes, M_TEMP);
4870 					goto fail; /* really bad */
4871 				}
4872 				break;
4873 			    }
4874 			default:
4875 				if ((error = pf_commit_rules(ioe->ticket,
4876 				    ioe->rs_num, ioe->anchor))) {
4877 					PF_RULES_WUNLOCK();
4878 					free(ioes, M_TEMP);
4879 					goto fail; /* really bad */
4880 				}
4881 				break;
4882 			}
4883 		}
4884 		PF_RULES_WUNLOCK();
4885 		free(ioes, M_TEMP);
4886 		break;
4887 	}
4888 
4889 	case DIOCGETSRCNODES: {
4890 		struct pfioc_src_nodes	*psn = (struct pfioc_src_nodes *)addr;
4891 		struct pf_srchash	*sh;
4892 		struct pf_ksrc_node	*n;
4893 		struct pf_src_node	*p, *pstore;
4894 		uint32_t		 i, nr = 0;
4895 
4896 		for (i = 0, sh = V_pf_srchash; i <= pf_srchashmask;
4897 				i++, sh++) {
4898 			PF_HASHROW_LOCK(sh);
4899 			LIST_FOREACH(n, &sh->nodes, entry)
4900 				nr++;
4901 			PF_HASHROW_UNLOCK(sh);
4902 		}
4903 
4904 		psn->psn_len = min(psn->psn_len,
4905 		    sizeof(struct pf_src_node) * nr);
4906 
4907 		if (psn->psn_len == 0) {
4908 			psn->psn_len = sizeof(struct pf_src_node) * nr;
4909 			break;
4910 		}
4911 
4912 		nr = 0;
4913 
4914 		p = pstore = malloc(psn->psn_len, M_TEMP, M_WAITOK | M_ZERO);
4915 		for (i = 0, sh = V_pf_srchash; i <= pf_srchashmask;
4916 		    i++, sh++) {
4917 		    PF_HASHROW_LOCK(sh);
4918 		    LIST_FOREACH(n, &sh->nodes, entry) {
4919 
4920 			if ((nr + 1) * sizeof(*p) > (unsigned)psn->psn_len)
4921 				break;
4922 
4923 			pf_src_node_copy(n, p);
4924 
4925 			p++;
4926 			nr++;
4927 		    }
4928 		    PF_HASHROW_UNLOCK(sh);
4929 		}
4930 		error = copyout(pstore, psn->psn_src_nodes,
4931 		    sizeof(struct pf_src_node) * nr);
4932 		if (error) {
4933 			free(pstore, M_TEMP);
4934 			break;
4935 		}
4936 		psn->psn_len = sizeof(struct pf_src_node) * nr;
4937 		free(pstore, M_TEMP);
4938 		break;
4939 	}
4940 
4941 	case DIOCCLRSRCNODES: {
4942 		pf_clear_srcnodes(NULL);
4943 		pf_purge_expired_src_nodes();
4944 		break;
4945 	}
4946 
4947 	case DIOCKILLSRCNODES:
4948 		pf_kill_srcnodes((struct pfioc_src_node_kill *)addr);
4949 		break;
4950 
4951 	case DIOCSETHOSTID: {
4952 		u_int32_t	*hostid = (u_int32_t *)addr;
4953 
4954 		PF_RULES_WLOCK();
4955 		if (*hostid == 0)
4956 			V_pf_status.hostid = arc4random();
4957 		else
4958 			V_pf_status.hostid = *hostid;
4959 		PF_RULES_WUNLOCK();
4960 		break;
4961 	}
4962 
4963 	case DIOCOSFPFLUSH:
4964 		PF_RULES_WLOCK();
4965 		pf_osfp_flush();
4966 		PF_RULES_WUNLOCK();
4967 		break;
4968 
4969 	case DIOCIGETIFACES: {
4970 		struct pfioc_iface *io = (struct pfioc_iface *)addr;
4971 		struct pfi_kif *ifstore;
4972 		size_t bufsiz;
4973 
4974 		if (io->pfiio_esize != sizeof(struct pfi_kif)) {
4975 			error = ENODEV;
4976 			break;
4977 		}
4978 
4979 		if (io->pfiio_size < 0 ||
4980 		    io->pfiio_size > pf_ioctl_maxcount ||
4981 		    WOULD_OVERFLOW(io->pfiio_size, sizeof(struct pfi_kif))) {
4982 			error = EINVAL;
4983 			break;
4984 		}
4985 
4986 		bufsiz = io->pfiio_size * sizeof(struct pfi_kif);
4987 		ifstore = mallocarray(io->pfiio_size, sizeof(struct pfi_kif),
4988 		    M_TEMP, M_NOWAIT);
4989 		if (ifstore == NULL) {
4990 			error = ENOMEM;
4991 			break;
4992 		}
4993 
4994 		PF_RULES_RLOCK();
4995 		pfi_get_ifaces(io->pfiio_name, ifstore, &io->pfiio_size);
4996 		PF_RULES_RUNLOCK();
4997 		error = copyout(ifstore, io->pfiio_buffer, bufsiz);
4998 		free(ifstore, M_TEMP);
4999 		break;
5000 	}
5001 
5002 	case DIOCSETIFFLAG: {
5003 		struct pfioc_iface *io = (struct pfioc_iface *)addr;
5004 
5005 		PF_RULES_WLOCK();
5006 		error = pfi_set_flags(io->pfiio_name, io->pfiio_flags);
5007 		PF_RULES_WUNLOCK();
5008 		break;
5009 	}
5010 
5011 	case DIOCCLRIFFLAG: {
5012 		struct pfioc_iface *io = (struct pfioc_iface *)addr;
5013 
5014 		PF_RULES_WLOCK();
5015 		error = pfi_clear_flags(io->pfiio_name, io->pfiio_flags);
5016 		PF_RULES_WUNLOCK();
5017 		break;
5018 	}
5019 
5020 	default:
5021 		error = ENODEV;
5022 		break;
5023 	}
5024 fail:
5025 	if (sx_xlocked(&pf_ioctl_lock))
5026 		sx_xunlock(&pf_ioctl_lock);
5027 	CURVNET_RESTORE();
5028 
5029 	return (error);
5030 }
5031 
5032 void
5033 pfsync_state_export(struct pfsync_state *sp, struct pf_state *st)
5034 {
5035 	bzero(sp, sizeof(struct pfsync_state));
5036 
5037 	/* copy from state key */
5038 	sp->key[PF_SK_WIRE].addr[0] = st->key[PF_SK_WIRE]->addr[0];
5039 	sp->key[PF_SK_WIRE].addr[1] = st->key[PF_SK_WIRE]->addr[1];
5040 	sp->key[PF_SK_WIRE].port[0] = st->key[PF_SK_WIRE]->port[0];
5041 	sp->key[PF_SK_WIRE].port[1] = st->key[PF_SK_WIRE]->port[1];
5042 	sp->key[PF_SK_STACK].addr[0] = st->key[PF_SK_STACK]->addr[0];
5043 	sp->key[PF_SK_STACK].addr[1] = st->key[PF_SK_STACK]->addr[1];
5044 	sp->key[PF_SK_STACK].port[0] = st->key[PF_SK_STACK]->port[0];
5045 	sp->key[PF_SK_STACK].port[1] = st->key[PF_SK_STACK]->port[1];
5046 	sp->proto = st->key[PF_SK_WIRE]->proto;
5047 	sp->af = st->key[PF_SK_WIRE]->af;
5048 
5049 	/* copy from state */
5050 	strlcpy(sp->ifname, st->kif->pfik_name, sizeof(sp->ifname));
5051 	bcopy(&st->rt_addr, &sp->rt_addr, sizeof(sp->rt_addr));
5052 	sp->creation = htonl(time_uptime - st->creation);
5053 	sp->expire = pf_state_expires(st);
5054 	if (sp->expire <= time_uptime)
5055 		sp->expire = htonl(0);
5056 	else
5057 		sp->expire = htonl(sp->expire - time_uptime);
5058 
5059 	sp->direction = st->direction;
5060 	sp->log = st->log;
5061 	sp->timeout = st->timeout;
5062 	sp->state_flags = st->state_flags;
5063 	if (st->src_node)
5064 		sp->sync_flags |= PFSYNC_FLAG_SRCNODE;
5065 	if (st->nat_src_node)
5066 		sp->sync_flags |= PFSYNC_FLAG_NATSRCNODE;
5067 
5068 	sp->id = st->id;
5069 	sp->creatorid = st->creatorid;
5070 	pf_state_peer_hton(&st->src, &sp->src);
5071 	pf_state_peer_hton(&st->dst, &sp->dst);
5072 
5073 	if (st->rule.ptr == NULL)
5074 		sp->rule = htonl(-1);
5075 	else
5076 		sp->rule = htonl(st->rule.ptr->nr);
5077 	if (st->anchor.ptr == NULL)
5078 		sp->anchor = htonl(-1);
5079 	else
5080 		sp->anchor = htonl(st->anchor.ptr->nr);
5081 	if (st->nat_rule.ptr == NULL)
5082 		sp->nat_rule = htonl(-1);
5083 	else
5084 		sp->nat_rule = htonl(st->nat_rule.ptr->nr);
5085 
5086 	pf_state_counter_hton(counter_u64_fetch(st->packets[0]),
5087 	    sp->packets[0]);
5088 	pf_state_counter_hton(counter_u64_fetch(st->packets[1]),
5089 	    sp->packets[1]);
5090 	pf_state_counter_hton(counter_u64_fetch(st->bytes[0]), sp->bytes[0]);
5091 	pf_state_counter_hton(counter_u64_fetch(st->bytes[1]), sp->bytes[1]);
5092 
5093 }
5094 
5095 static void
5096 pf_tbladdr_copyout(struct pf_addr_wrap *aw)
5097 {
5098 	struct pfr_ktable *kt;
5099 
5100 	KASSERT(aw->type == PF_ADDR_TABLE, ("%s: type %u", __func__, aw->type));
5101 
5102 	kt = aw->p.tbl;
5103 	if (!(kt->pfrkt_flags & PFR_TFLAG_ACTIVE) && kt->pfrkt_root != NULL)
5104 		kt = kt->pfrkt_root;
5105 	aw->p.tbl = NULL;
5106 	aw->p.tblcnt = (kt->pfrkt_flags & PFR_TFLAG_ACTIVE) ?
5107 		kt->pfrkt_cnt : -1;
5108 }
5109 
5110 /*
5111  * XXX - Check for version missmatch!!!
5112  */
5113 static void
5114 pf_clear_states(void)
5115 {
5116 	struct pf_state	*s;
5117 	u_int i;
5118 
5119 	for (i = 0; i <= pf_hashmask; i++) {
5120 		struct pf_idhash *ih = &V_pf_idhash[i];
5121 relock:
5122 		PF_HASHROW_LOCK(ih);
5123 		LIST_FOREACH(s, &ih->states, entry) {
5124 			s->timeout = PFTM_PURGE;
5125 			/* Don't send out individual delete messages. */
5126 			s->state_flags |= PFSTATE_NOSYNC;
5127 			pf_unlink_state(s, PF_ENTER_LOCKED);
5128 			goto relock;
5129 		}
5130 		PF_HASHROW_UNLOCK(ih);
5131 	}
5132 }
5133 
5134 static int
5135 pf_clear_tables(void)
5136 {
5137 	struct pfioc_table io;
5138 	int error;
5139 
5140 	bzero(&io, sizeof(io));
5141 
5142 	error = pfr_clr_tables(&io.pfrio_table, &io.pfrio_ndel,
5143 	    io.pfrio_flags);
5144 
5145 	return (error);
5146 }
5147 
5148 static void
5149 pf_clear_srcnodes(struct pf_ksrc_node *n)
5150 {
5151 	struct pf_state *s;
5152 	int i;
5153 
5154 	for (i = 0; i <= pf_hashmask; i++) {
5155 		struct pf_idhash *ih = &V_pf_idhash[i];
5156 
5157 		PF_HASHROW_LOCK(ih);
5158 		LIST_FOREACH(s, &ih->states, entry) {
5159 			if (n == NULL || n == s->src_node)
5160 				s->src_node = NULL;
5161 			if (n == NULL || n == s->nat_src_node)
5162 				s->nat_src_node = NULL;
5163 		}
5164 		PF_HASHROW_UNLOCK(ih);
5165 	}
5166 
5167 	if (n == NULL) {
5168 		struct pf_srchash *sh;
5169 
5170 		for (i = 0, sh = V_pf_srchash; i <= pf_srchashmask;
5171 		    i++, sh++) {
5172 			PF_HASHROW_LOCK(sh);
5173 			LIST_FOREACH(n, &sh->nodes, entry) {
5174 				n->expire = 1;
5175 				n->states = 0;
5176 			}
5177 			PF_HASHROW_UNLOCK(sh);
5178 		}
5179 	} else {
5180 		/* XXX: hash slot should already be locked here. */
5181 		n->expire = 1;
5182 		n->states = 0;
5183 	}
5184 }
5185 
5186 static void
5187 pf_kill_srcnodes(struct pfioc_src_node_kill *psnk)
5188 {
5189 	struct pf_ksrc_node_list	 kill;
5190 
5191 	LIST_INIT(&kill);
5192 	for (int i = 0; i <= pf_srchashmask; i++) {
5193 		struct pf_srchash *sh = &V_pf_srchash[i];
5194 		struct pf_ksrc_node *sn, *tmp;
5195 
5196 		PF_HASHROW_LOCK(sh);
5197 		LIST_FOREACH_SAFE(sn, &sh->nodes, entry, tmp)
5198 			if (PF_MATCHA(psnk->psnk_src.neg,
5199 			      &psnk->psnk_src.addr.v.a.addr,
5200 			      &psnk->psnk_src.addr.v.a.mask,
5201 			      &sn->addr, sn->af) &&
5202 			    PF_MATCHA(psnk->psnk_dst.neg,
5203 			      &psnk->psnk_dst.addr.v.a.addr,
5204 			      &psnk->psnk_dst.addr.v.a.mask,
5205 			      &sn->raddr, sn->af)) {
5206 				pf_unlink_src_node(sn);
5207 				LIST_INSERT_HEAD(&kill, sn, entry);
5208 				sn->expire = 1;
5209 			}
5210 		PF_HASHROW_UNLOCK(sh);
5211 	}
5212 
5213 	for (int i = 0; i <= pf_hashmask; i++) {
5214 		struct pf_idhash *ih = &V_pf_idhash[i];
5215 		struct pf_state *s;
5216 
5217 		PF_HASHROW_LOCK(ih);
5218 		LIST_FOREACH(s, &ih->states, entry) {
5219 			if (s->src_node && s->src_node->expire == 1)
5220 				s->src_node = NULL;
5221 			if (s->nat_src_node && s->nat_src_node->expire == 1)
5222 				s->nat_src_node = NULL;
5223 		}
5224 		PF_HASHROW_UNLOCK(ih);
5225 	}
5226 
5227 	psnk->psnk_killed = pf_free_src_nodes(&kill);
5228 }
5229 
5230 /*
5231  * XXX - Check for version missmatch!!!
5232  */
5233 
5234 /*
5235  * Duplicate pfctl -Fa operation to get rid of as much as we can.
5236  */
5237 static int
5238 shutdown_pf(void)
5239 {
5240 	int error = 0;
5241 	u_int32_t t[5];
5242 	char nn = '\0';
5243 
5244 	do {
5245 		if ((error = pf_begin_rules(&t[0], PF_RULESET_SCRUB, &nn))
5246 		    != 0) {
5247 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: SCRUB\n"));
5248 			break;
5249 		}
5250 		if ((error = pf_begin_rules(&t[1], PF_RULESET_FILTER, &nn))
5251 		    != 0) {
5252 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: FILTER\n"));
5253 			break;		/* XXX: rollback? */
5254 		}
5255 		if ((error = pf_begin_rules(&t[2], PF_RULESET_NAT, &nn))
5256 		    != 0) {
5257 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: NAT\n"));
5258 			break;		/* XXX: rollback? */
5259 		}
5260 		if ((error = pf_begin_rules(&t[3], PF_RULESET_BINAT, &nn))
5261 		    != 0) {
5262 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: BINAT\n"));
5263 			break;		/* XXX: rollback? */
5264 		}
5265 		if ((error = pf_begin_rules(&t[4], PF_RULESET_RDR, &nn))
5266 		    != 0) {
5267 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: RDR\n"));
5268 			break;		/* XXX: rollback? */
5269 		}
5270 
5271 		/* XXX: these should always succeed here */
5272 		pf_commit_rules(t[0], PF_RULESET_SCRUB, &nn);
5273 		pf_commit_rules(t[1], PF_RULESET_FILTER, &nn);
5274 		pf_commit_rules(t[2], PF_RULESET_NAT, &nn);
5275 		pf_commit_rules(t[3], PF_RULESET_BINAT, &nn);
5276 		pf_commit_rules(t[4], PF_RULESET_RDR, &nn);
5277 
5278 		if ((error = pf_clear_tables()) != 0)
5279 			break;
5280 
5281 #ifdef ALTQ
5282 		if ((error = pf_begin_altq(&t[0])) != 0) {
5283 			DPFPRINTF(PF_DEBUG_MISC, ("shutdown_pf: ALTQ\n"));
5284 			break;
5285 		}
5286 		pf_commit_altq(t[0]);
5287 #endif
5288 
5289 		pf_clear_states();
5290 
5291 		pf_clear_srcnodes(NULL);
5292 
5293 		/* status does not use malloced mem so no need to cleanup */
5294 		/* fingerprints and interfaces have their own cleanup code */
5295 	} while(0);
5296 
5297 	return (error);
5298 }
5299 
5300 static pfil_return_t
5301 pf_check_return(int chk, struct mbuf **m)
5302 {
5303 
5304 	switch (chk) {
5305 	case PF_PASS:
5306 		if (*m == NULL)
5307 			return (PFIL_CONSUMED);
5308 		else
5309 			return (PFIL_PASS);
5310 		break;
5311 	default:
5312 		if (*m != NULL) {
5313 			m_freem(*m);
5314 			*m = NULL;
5315 		}
5316 		return (PFIL_DROPPED);
5317 	}
5318 }
5319 
5320 #ifdef INET
5321 static pfil_return_t
5322 pf_check_in(struct mbuf **m, struct ifnet *ifp, int flags,
5323     void *ruleset __unused, struct inpcb *inp)
5324 {
5325 	int chk;
5326 
5327 	chk = pf_test(PF_IN, flags, ifp, m, inp);
5328 
5329 	return (pf_check_return(chk, m));
5330 }
5331 
5332 static pfil_return_t
5333 pf_check_out(struct mbuf **m, struct ifnet *ifp, int flags,
5334     void *ruleset __unused,  struct inpcb *inp)
5335 {
5336 	int chk;
5337 
5338 	chk = pf_test(PF_OUT, flags, ifp, m, inp);
5339 
5340 	return (pf_check_return(chk, m));
5341 }
5342 #endif
5343 
5344 #ifdef INET6
5345 static pfil_return_t
5346 pf_check6_in(struct mbuf **m, struct ifnet *ifp, int flags,
5347     void *ruleset __unused,  struct inpcb *inp)
5348 {
5349 	int chk;
5350 
5351 	/*
5352 	 * In case of loopback traffic IPv6 uses the real interface in
5353 	 * order to support scoped addresses. In order to support stateful
5354 	 * filtering we have change this to lo0 as it is the case in IPv4.
5355 	 */
5356 	CURVNET_SET(ifp->if_vnet);
5357 	chk = pf_test6(PF_IN, flags, (*m)->m_flags & M_LOOP ? V_loif : ifp, m, inp);
5358 	CURVNET_RESTORE();
5359 
5360 	return (pf_check_return(chk, m));
5361 }
5362 
5363 static pfil_return_t
5364 pf_check6_out(struct mbuf **m, struct ifnet *ifp, int flags,
5365     void *ruleset __unused,  struct inpcb *inp)
5366 {
5367 	int chk;
5368 
5369 	CURVNET_SET(ifp->if_vnet);
5370 	chk = pf_test6(PF_OUT, flags, ifp, m, inp);
5371 	CURVNET_RESTORE();
5372 
5373 	return (pf_check_return(chk, m));
5374 }
5375 #endif /* INET6 */
5376 
5377 #ifdef INET
5378 VNET_DEFINE_STATIC(pfil_hook_t, pf_ip4_in_hook);
5379 VNET_DEFINE_STATIC(pfil_hook_t, pf_ip4_out_hook);
5380 #define	V_pf_ip4_in_hook	VNET(pf_ip4_in_hook)
5381 #define	V_pf_ip4_out_hook	VNET(pf_ip4_out_hook)
5382 #endif
5383 #ifdef INET6
5384 VNET_DEFINE_STATIC(pfil_hook_t, pf_ip6_in_hook);
5385 VNET_DEFINE_STATIC(pfil_hook_t, pf_ip6_out_hook);
5386 #define	V_pf_ip6_in_hook	VNET(pf_ip6_in_hook)
5387 #define	V_pf_ip6_out_hook	VNET(pf_ip6_out_hook)
5388 #endif
5389 
5390 static void
5391 hook_pf(void)
5392 {
5393 	struct pfil_hook_args pha;
5394 	struct pfil_link_args pla;
5395 	int ret;
5396 
5397 	if (V_pf_pfil_hooked)
5398 		return;
5399 
5400 	pha.pa_version = PFIL_VERSION;
5401 	pha.pa_modname = "pf";
5402 	pha.pa_ruleset = NULL;
5403 
5404 	pla.pa_version = PFIL_VERSION;
5405 
5406 #ifdef INET
5407 	pha.pa_type = PFIL_TYPE_IP4;
5408 	pha.pa_func = pf_check_in;
5409 	pha.pa_flags = PFIL_IN;
5410 	pha.pa_rulname = "default-in";
5411 	V_pf_ip4_in_hook = pfil_add_hook(&pha);
5412 	pla.pa_flags = PFIL_IN | PFIL_HEADPTR | PFIL_HOOKPTR;
5413 	pla.pa_head = V_inet_pfil_head;
5414 	pla.pa_hook = V_pf_ip4_in_hook;
5415 	ret = pfil_link(&pla);
5416 	MPASS(ret == 0);
5417 	pha.pa_func = pf_check_out;
5418 	pha.pa_flags = PFIL_OUT;
5419 	pha.pa_rulname = "default-out";
5420 	V_pf_ip4_out_hook = pfil_add_hook(&pha);
5421 	pla.pa_flags = PFIL_OUT | PFIL_HEADPTR | PFIL_HOOKPTR;
5422 	pla.pa_head = V_inet_pfil_head;
5423 	pla.pa_hook = V_pf_ip4_out_hook;
5424 	ret = pfil_link(&pla);
5425 	MPASS(ret == 0);
5426 #endif
5427 #ifdef INET6
5428 	pha.pa_type = PFIL_TYPE_IP6;
5429 	pha.pa_func = pf_check6_in;
5430 	pha.pa_flags = PFIL_IN;
5431 	pha.pa_rulname = "default-in6";
5432 	V_pf_ip6_in_hook = pfil_add_hook(&pha);
5433 	pla.pa_flags = PFIL_IN | PFIL_HEADPTR | PFIL_HOOKPTR;
5434 	pla.pa_head = V_inet6_pfil_head;
5435 	pla.pa_hook = V_pf_ip6_in_hook;
5436 	ret = pfil_link(&pla);
5437 	MPASS(ret == 0);
5438 	pha.pa_func = pf_check6_out;
5439 	pha.pa_rulname = "default-out6";
5440 	pha.pa_flags = PFIL_OUT;
5441 	V_pf_ip6_out_hook = pfil_add_hook(&pha);
5442 	pla.pa_flags = PFIL_OUT | PFIL_HEADPTR | PFIL_HOOKPTR;
5443 	pla.pa_head = V_inet6_pfil_head;
5444 	pla.pa_hook = V_pf_ip6_out_hook;
5445 	ret = pfil_link(&pla);
5446 	MPASS(ret == 0);
5447 #endif
5448 
5449 	V_pf_pfil_hooked = 1;
5450 }
5451 
5452 static void
5453 dehook_pf(void)
5454 {
5455 
5456 	if (V_pf_pfil_hooked == 0)
5457 		return;
5458 
5459 #ifdef INET
5460 	pfil_remove_hook(V_pf_ip4_in_hook);
5461 	pfil_remove_hook(V_pf_ip4_out_hook);
5462 #endif
5463 #ifdef INET6
5464 	pfil_remove_hook(V_pf_ip6_in_hook);
5465 	pfil_remove_hook(V_pf_ip6_out_hook);
5466 #endif
5467 
5468 	V_pf_pfil_hooked = 0;
5469 }
5470 
5471 static void
5472 pf_load_vnet(void)
5473 {
5474 	V_pf_tag_z = uma_zcreate("pf tags", sizeof(struct pf_tagname),
5475 	    NULL, NULL, NULL, NULL, UMA_ALIGN_PTR, 0);
5476 
5477 	pf_init_tagset(&V_pf_tags, &pf_rule_tag_hashsize,
5478 	    PF_RULE_TAG_HASH_SIZE_DEFAULT);
5479 #ifdef ALTQ
5480 	pf_init_tagset(&V_pf_qids, &pf_queue_tag_hashsize,
5481 	    PF_QUEUE_TAG_HASH_SIZE_DEFAULT);
5482 #endif
5483 
5484 	pfattach_vnet();
5485 	V_pf_vnet_active = 1;
5486 }
5487 
5488 static int
5489 pf_load(void)
5490 {
5491 	int error;
5492 
5493 	rm_init(&pf_rules_lock, "pf rulesets");
5494 	sx_init(&pf_ioctl_lock, "pf ioctl");
5495 	sx_init(&pf_end_lock, "pf end thread");
5496 
5497 	pf_mtag_initialize();
5498 
5499 	pf_dev = make_dev(&pf_cdevsw, 0, UID_ROOT, GID_WHEEL, 0600, PF_NAME);
5500 	if (pf_dev == NULL)
5501 		return (ENOMEM);
5502 
5503 	pf_end_threads = 0;
5504 	error = kproc_create(pf_purge_thread, NULL, &pf_purge_proc, 0, 0, "pf purge");
5505 	if (error != 0)
5506 		return (error);
5507 
5508 	pfi_initialize();
5509 
5510 	return (0);
5511 }
5512 
5513 static void
5514 pf_unload_vnet(void)
5515 {
5516 	int ret;
5517 
5518 	V_pf_vnet_active = 0;
5519 	V_pf_status.running = 0;
5520 	dehook_pf();
5521 
5522 	PF_RULES_WLOCK();
5523 	shutdown_pf();
5524 	PF_RULES_WUNLOCK();
5525 
5526 	ret = swi_remove(V_pf_swi_cookie);
5527 	MPASS(ret == 0);
5528 	ret = intr_event_destroy(V_pf_swi_ie);
5529 	MPASS(ret == 0);
5530 
5531 	pf_unload_vnet_purge();
5532 
5533 	pf_normalize_cleanup();
5534 	PF_RULES_WLOCK();
5535 	pfi_cleanup_vnet();
5536 	PF_RULES_WUNLOCK();
5537 	pfr_cleanup();
5538 	pf_osfp_flush();
5539 	pf_cleanup();
5540 	if (IS_DEFAULT_VNET(curvnet))
5541 		pf_mtag_cleanup();
5542 
5543 	pf_cleanup_tagset(&V_pf_tags);
5544 #ifdef ALTQ
5545 	pf_cleanup_tagset(&V_pf_qids);
5546 #endif
5547 	uma_zdestroy(V_pf_tag_z);
5548 
5549 	/* Free counters last as we updated them during shutdown. */
5550 	counter_u64_free(V_pf_default_rule.evaluations);
5551 	for (int i = 0; i < 2; i++) {
5552 		counter_u64_free(V_pf_default_rule.packets[i]);
5553 		counter_u64_free(V_pf_default_rule.bytes[i]);
5554 	}
5555 	counter_u64_free(V_pf_default_rule.states_cur);
5556 	counter_u64_free(V_pf_default_rule.states_tot);
5557 	counter_u64_free(V_pf_default_rule.src_nodes);
5558 
5559 	for (int i = 0; i < PFRES_MAX; i++)
5560 		counter_u64_free(V_pf_status.counters[i]);
5561 	for (int i = 0; i < LCNT_MAX; i++)
5562 		counter_u64_free(V_pf_status.lcounters[i]);
5563 	for (int i = 0; i < FCNT_MAX; i++)
5564 		counter_u64_free(V_pf_status.fcounters[i]);
5565 	for (int i = 0; i < SCNT_MAX; i++)
5566 		counter_u64_free(V_pf_status.scounters[i]);
5567 }
5568 
5569 static void
5570 pf_unload(void)
5571 {
5572 
5573 	sx_xlock(&pf_end_lock);
5574 	pf_end_threads = 1;
5575 	while (pf_end_threads < 2) {
5576 		wakeup_one(pf_purge_thread);
5577 		sx_sleep(pf_purge_proc, &pf_end_lock, 0, "pftmo", 0);
5578 	}
5579 	sx_xunlock(&pf_end_lock);
5580 
5581 	if (pf_dev != NULL)
5582 		destroy_dev(pf_dev);
5583 
5584 	pfi_cleanup();
5585 
5586 	rm_destroy(&pf_rules_lock);
5587 	sx_destroy(&pf_ioctl_lock);
5588 	sx_destroy(&pf_end_lock);
5589 }
5590 
5591 static void
5592 vnet_pf_init(void *unused __unused)
5593 {
5594 
5595 	pf_load_vnet();
5596 }
5597 VNET_SYSINIT(vnet_pf_init, SI_SUB_PROTO_FIREWALL, SI_ORDER_THIRD,
5598     vnet_pf_init, NULL);
5599 
5600 static void
5601 vnet_pf_uninit(const void *unused __unused)
5602 {
5603 
5604 	pf_unload_vnet();
5605 }
5606 SYSUNINIT(pf_unload, SI_SUB_PROTO_FIREWALL, SI_ORDER_SECOND, pf_unload, NULL);
5607 VNET_SYSUNINIT(vnet_pf_uninit, SI_SUB_PROTO_FIREWALL, SI_ORDER_THIRD,
5608     vnet_pf_uninit, NULL);
5609 
5610 static int
5611 pf_modevent(module_t mod, int type, void *data)
5612 {
5613 	int error = 0;
5614 
5615 	switch(type) {
5616 	case MOD_LOAD:
5617 		error = pf_load();
5618 		break;
5619 	case MOD_UNLOAD:
5620 		/* Handled in SYSUNINIT(pf_unload) to ensure it's done after
5621 		 * the vnet_pf_uninit()s */
5622 		break;
5623 	default:
5624 		error = EINVAL;
5625 		break;
5626 	}
5627 
5628 	return (error);
5629 }
5630 
5631 static moduledata_t pf_mod = {
5632 	"pf",
5633 	pf_modevent,
5634 	0
5635 };
5636 
5637 DECLARE_MODULE(pf, pf_mod, SI_SUB_PROTO_FIREWALL, SI_ORDER_SECOND);
5638 MODULE_VERSION(pf, PF_MODVER);
5639