diff options
author | 2007-12-02 12:08:04 +0000 | |
---|---|---|
committer | 2007-12-02 12:08:04 +0000 | |
commit | 6409e018d730647512a60ab69ec04e6e9f3a5cef (patch) | |
tree | cfb2437841284f81d11758c36e09788c74ec686a /sys/net/pf_ioctl.c | |
parent | When pf_insert_state state succeeds, increase the state count on the (diff) | |
download | wireguard-openbsd-6409e018d730647512a60ab69ec04e6e9f3a5cef.tar.xz wireguard-openbsd-6409e018d730647512a60ab69ec04e6e9f3a5cef.zip |
DIOC{GET,ADD}STATE incorrectly use a user provided pointer without using
copyin/out. Change the API so that the state is included in the ioctl
argument, so the ioctl wrappers take care of copying memory as appropriate.
Also change the DIOCGETSTATE API to be more useful. Instead of getting
an arbitrarily "numbered" state (using numbering that can change between
calls), instead search based on id and creatorid. If you want to monitor
only a particular state, you can now use the bulk functions first to find
the appropriate id/creatorid and then fetch it directly from then on.
ok dlg@ henning@
Diffstat (limited to 'sys/net/pf_ioctl.c')
-rw-r--r-- | sys/net/pf_ioctl.c | 21 |
1 files changed, 9 insertions, 12 deletions
diff --git a/sys/net/pf_ioctl.c b/sys/net/pf_ioctl.c index fdbdb45b226..9226258352b 100644 --- a/sys/net/pf_ioctl.c +++ b/sys/net/pf_ioctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pf_ioctl.c,v 1.192 2007/12/02 12:00:20 pascoe Exp $ */ +/* $OpenBSD: pf_ioctl.c,v 1.193 2007/12/02 12:08:04 pascoe Exp $ */ /* * Copyright (c) 2001 Daniel Hartmeier @@ -1633,7 +1633,7 @@ pfioctl(dev_t dev, u_long cmd, caddr_t addr, int flags, struct proc *p) case DIOCADDSTATE: { struct pfioc_state *ps = (struct pfioc_state *)addr; - struct pfsync_state *sp = (struct pfsync_state *)ps->state; + struct pfsync_state *sp = &ps->state; struct pf_state *s; struct pf_state_key *sk; struct pfi_kif *kif; @@ -1675,21 +1675,18 @@ pfioctl(dev_t dev, u_long cmd, caddr_t addr, int flags, struct proc *p) case DIOCGETSTATE: { struct pfioc_state *ps = (struct pfioc_state *)addr; struct pf_state *s; - u_int32_t nr; + struct pf_state_cmp id_key; - nr = 0; - RB_FOREACH(s, pf_state_tree_id, &tree_id) { - if (nr >= ps->nr) - break; - nr++; - } + bcopy(ps->state.id, &id_key.id, sizeof(id_key.id)); + id_key.creatorid = ps->state.creatorid; + + s = pf_find_state_byid(&id_key); if (s == NULL) { - error = EBUSY; + error = ENOENT; break; } - pf_state_export((struct pfsync_state *)ps->state, - s->state_key, s); + pf_state_export(&ps->state, s->state_key, s); break; } |