diff options
author | ghelmer <ghelmer@FreeBSD.org> | 2012-12-10 16:14:44 +0000 |
---|---|---|
committer | ghelmer <ghelmer@FreeBSD.org> | 2012-12-10 16:14:44 +0000 |
commit | 726beb3d43000997e7410621a0c31a65b05ebb31 (patch) | |
tree | 05f79a3e8fd1361998dd0dc02f1088df035c8960 /sys/net/bpf_buffer.c | |
parent | 2160ff58527c3253bc5fe11f85c2e3d0fa680688 (diff) | |
download | FreeBSD-src-726beb3d43000997e7410621a0c31a65b05ebb31.zip FreeBSD-src-726beb3d43000997e7410621a0c31a65b05ebb31.tar.gz |
Changes to resolve races in bpfread() and catchpacket() that, at worst,
cause kernel panics.
Add a flag to the bpf descriptor to indicate whether the hold buffer
is in use. In bpfread(), set the "hold buffer in use" flag before
dropping the descriptor lock during the call to bpf_uiomove().
Everywhere else the hold buffer is used or changed, wait while
the hold buffer is in use by bpfread(). Add a KASSERT in bpfread()
after re-acquiring the descriptor lock to assist uncovering any
additional hold buffer races.
Diffstat (limited to 'sys/net/bpf_buffer.c')
-rw-r--r-- | sys/net/bpf_buffer.c | 5 |
1 files changed, 5 insertions, 0 deletions
diff --git a/sys/net/bpf_buffer.c b/sys/net/bpf_buffer.c index 64bb982..74e1ae4 100644 --- a/sys/net/bpf_buffer.c +++ b/sys/net/bpf_buffer.c @@ -79,6 +79,8 @@ __FBSDID("$FreeBSD$"); #include <net/bpf_buffer.h> #include <net/bpfdesc.h> +#define PRINET 26 /* interruptible */ + /* * Implement historical kernel memory buffering model for BPF: two malloc(9) * kernel buffers are hung off of the descriptor. The size is fixed prior to @@ -189,6 +191,9 @@ bpf_buffer_ioctl_sblen(struct bpf_d *d, u_int *i) return (EINVAL); } + while (d->bd_hbuf_in_use) + mtx_sleep(&d->bd_hbuf_in_use, &d->bd_lock, + PRINET, "bd_hbuf", 0); /* Free old buffers if set */ if (d->bd_fbuf != NULL) free(d->bd_fbuf, M_BPF); |