-/* $OpenBSD: pf_ioctl.c,v 1.405 2023/05/26 12:13:26 kn Exp $ */
+/* $OpenBSD: pf_ioctl.c,v 1.406 2023/06/26 07:49:48 claudio Exp $ */
/*
* Copyright (c) 2001 Daniel Hartmeier
int pf_states_get(struct pfioc_states *);
struct pf_trans *pf_open_trans(uint32_t);
+void pf_close_all_trans(uint32_t);
struct pf_trans *pf_find_trans(uint32_t, uint64_t);
void pf_free_trans(struct pf_trans *);
void pf_rollback_trans(struct pf_trans *);
PF_UNLOCK();
NET_UNLOCK();
+ pf_close_all_trans(minor(dev));
t = pf_open_trans(minor(dev));
pf_init_tgetrule(t, ruleset->anchor, ruleset_version, rule);
pr->ticket = t->pft_ticket;
return (t);
}
+void
+pf_close_all_trans(uint32_t unit)
+{
+ struct pf_trans *t, *nt;
+
+ rw_assert_wrlock(&pfioctl_rw);
+
+ LIST_FOREACH_SAFE(t, &pf_ioctl_trans, pft_entry, nt) {
+ if (t->pft_unit == unit)
+ pf_rollback_trans(t);
+ }
+}
+
struct pf_trans *
pf_find_trans(uint32_t unit, uint64_t ticket)
{
-/* $OpenBSD: rtsock.c,v 1.365 2023/04/20 21:43:17 mvs Exp $ */
+/* $OpenBSD: rtsock.c,v 1.366 2023/06/26 07:49:48 claudio Exp $ */
/* $NetBSD: rtsock.c,v 1.18 1996/03/29 00:32:10 cgd Exp $ */
/*
#include <sys/domain.h>
#include <sys/pool.h>
#include <sys/protosw.h>
-#include <sys/srp.h>
+#include <sys/smr.h>
#include <net/if.h>
#include <net/if_dl.h>
};
void route_prinit(void);
-void rcb_ref(void *, void *);
-void rcb_unref(void *, void *);
int route_output(struct mbuf *, struct socket *);
int route_ctloutput(int, struct socket *, int, int, struct mbuf *);
int route_attach(struct socket *, int, int);
struct rtpcb {
struct socket *rop_socket; /* [I] */
- SRPL_ENTRY(rtpcb) rop_list;
+ SMR_LIST_ENTRY(rtpcb) rop_list;
struct refcnt rop_refcnt;
struct timeout rop_timeout;
unsigned int rop_msgfilter; /* [s] */
#define sotortpcb(so) ((struct rtpcb *)(so)->so_pcb)
struct rtptable {
- SRPL_HEAD(, rtpcb) rtp_list;
- struct srpl_rc rtp_rc;
+ SMR_LIST_HEAD(, rtpcb) rtp_list;
struct rwlock rtp_lk;
unsigned int rtp_count;
};
void
route_prinit(void)
{
- srpl_rc_init(&rtptable.rtp_rc, rcb_ref, rcb_unref, NULL);
rw_init(&rtptable.rtp_lk, "rtsock");
- SRPL_INIT(&rtptable.rtp_list);
+ SMR_LIST_INIT(&rtptable.rtp_list);
pool_init(&rtpcb_pool, sizeof(struct rtpcb), 0,
IPL_SOFTNET, PR_WAITOK, "rtpcb", NULL);
}
-void
-rcb_ref(void *null, void *v)
-{
- struct rtpcb *rop = v;
-
- refcnt_take(&rop->rop_refcnt);
-}
-
-void
-rcb_unref(void *null, void *v)
-{
- struct rtpcb *rop = v;
-
- refcnt_rele_wake(&rop->rop_refcnt);
-}
-
int
route_attach(struct socket *so, int proto, int wait)
{
PR_ZERO);
if (rop == NULL)
return (ENOBUFS);
- so->so_pcb = rop;
+
/* Init the timeout structure */
timeout_set_proc(&rop->rop_timeout, rtm_senddesync_timer, so);
refcnt_init(&rop->rop_refcnt);
rop->rop_rtableid = curproc->p_p->ps_rtableid;
+ so->so_pcb = rop;
soisconnected(so);
so->so_options |= SO_USELOOPBACK;
rw_enter(&rtptable.rtp_lk, RW_WRITE);
- SRPL_INSERT_HEAD_LOCKED(&rtptable.rtp_rc, &rtptable.rtp_list, rop,
- rop_list);
+ SMR_LIST_INSERT_HEAD_LOCKED(&rtptable.rtp_list, rop, rop_list);
rtptable.rtp_count++;
rw_exit(&rtptable.rtp_lk);
rw_enter(&rtptable.rtp_lk, RW_WRITE);
rtptable.rtp_count--;
- SRPL_REMOVE_LOCKED(&rtptable.rtp_rc, &rtptable.rtp_list, rop, rtpcb,
- rop_list);
+ SMR_LIST_REMOVE_LOCKED(rop, rop_list);
rw_exit(&rtptable.rtp_lk);
sounlock(so);
/* wait for all references to drop */
+ smr_barrier();
refcnt_finalize(&rop->rop_refcnt, "rtsockrefs");
timeout_del_barrier(&rop->rop_timeout);
if (level != AF_ROUTE)
return (EINVAL);
+ soassertlocked(so);
+
switch (op) {
case PRCO_SETOPT:
switch (optname) {
route_input(struct mbuf *m0, struct socket *so0, sa_family_t sa_family)
{
struct socket *so;
- struct rtpcb *rop;
+ struct rtpcb *rop, *nrop;
struct rt_msghdr *rtm;
struct mbuf *m = m0;
- struct srp_ref sr;
/* ensure that we can access the rtm_type via mtod() */
if (m->m_len < offsetof(struct rt_msghdr, rtm_type) + 1) {
return;
}
- SRPL_FOREACH(rop, &sr, &rtptable.rtp_list, rop_list) {
+ smr_read_enter();
+ rop = SMR_LIST_FIRST(&rtptable.rtp_list);
+ while (rop != NULL) {
/*
* If route socket is bound to an address family only send
* messages that match the address family. Address family
* agnostic messages are always sent.
*/
if (sa_family != AF_UNSPEC && rop->rop_proto != AF_UNSPEC &&
- rop->rop_proto != sa_family)
+ rop->rop_proto != sa_family) {
+ rop = SMR_LIST_NEXT(rop, rop_list);
continue;
+ }
-
+ refcnt_take(&rop->rop_refcnt);
+ smr_read_leave();
so = rop->rop_socket;
solock(so);
rtm_sendup(so, m);
next:
sounlock(so);
+ smr_read_enter();
+ nrop = SMR_LIST_NEXT(rop, rop_list);
+ refcnt_rele_wake(&rop->rop_refcnt);
+ rop = nrop;
}
- SRPL_LEAVE(&sr);
+ smr_read_leave();
m_freem(m);
}