aboutsummaryrefslogtreecommitdiff
path: root/sys/net/if_tun.c
diff options
context:
space:
mode:
authorJonathan Lemon <jlemon@FreeBSD.org>2000-11-25 07:35:38 +0000
committerJonathan Lemon <jlemon@FreeBSD.org>2000-11-25 07:35:38 +0000
commitdf5e1987230850fe5983a4479523708640160215 (patch)
tree05531b0125a3669b45ffc6aa7dc93115e4123969 /sys/net/if_tun.c
parentf4e13f88b630686808a03dc19e3243ca37fa5645 (diff)
downloadsrc-df5e1987230850fe5983a4479523708640160215.tar.gz
src-df5e1987230850fe5983a4479523708640160215.zip
Lock down the network interface queues. The queue mutex must be obtained
before adding/removing packets from the queue. Also, the if_obytes and if_omcasts fields should only be manipulated under protection of the mutex. IF_ENQUEUE, IF_PREPEND, and IF_DEQUEUE perform all necessary locking on the queue. An IF_LOCK macro is provided, as well as the old (mutex-less) versions of the macros in the form _IF_ENQUEUE, _IF_QFULL, for code which needs them, but their use is discouraged. Two new macros are introduced: IF_DRAIN() to drain a queue, and IF_HANDOFF, which takes care of locking/enqueue, and also statistics updating/start if necessary.
Notes
Notes: svn path=/head/; revision=69152
Diffstat (limited to 'sys/net/if_tun.c')
-rw-r--r--sys/net/if_tun.c31
1 files changed, 6 insertions, 25 deletions
diff --git a/sys/net/if_tun.c b/sys/net/if_tun.c
index 9187764c14f6..5cbe111b68b1 100644
--- a/sys/net/if_tun.c
+++ b/sys/net/if_tun.c
@@ -196,7 +196,6 @@ tunclose(dev, foo, bar, p)
register int s;
struct tun_softc *tp;
struct ifnet *ifp;
- struct mbuf *m;
tp = dev->si_drv1;
ifp = &tp->tun_if;
@@ -207,13 +206,7 @@ tunclose(dev, foo, bar, p)
/*
* junk all pending output
*/
- do {
- s = splimp();
- IF_DEQUEUE(&ifp->if_snd, m);
- splx(s);
- if (m)
- m_freem(m);
- } while (m);
+ IF_DRAIN(&ifp->if_snd);
if (ifp->if_flags & IFF_UP) {
s = splimp();
@@ -337,7 +330,6 @@ tunoutput(ifp, m0, dst, rt)
struct rtentry *rt;
{
struct tun_softc *tp = ifp->if_softc;
- int s;
TUNDEBUG ("%s%d: tunoutput\n", ifp->if_name, ifp->if_unit);
@@ -380,10 +372,8 @@ tunoutput(ifp, m0, dst, rt)
M_PREPEND(m0, dst->sa_len, M_DONTWAIT);
/* if allocation failed drop packet */
- if (m0 == NULL){
- s = splimp(); /* spl on queue manipulation */
- IF_DROP(&ifp->if_snd);
- splx(s);
+ if (m0 == NULL) {
+ ifp->if_iqdrops++;
ifp->if_oerrors++;
return (ENOBUFS);
} else {
@@ -396,10 +386,8 @@ tunoutput(ifp, m0, dst, rt)
M_PREPEND(m0, 4, M_DONTWAIT);
/* if allocation failed drop packet */
- if (m0 == NULL){
- s = splimp(); /* spl on queue manipulation */
- IF_DROP(&ifp->if_snd);
- splx(s);
+ if (m0 == NULL) {
+ ifp->if_iqdrops++;
ifp->if_oerrors++;
return ENOBUFS;
} else
@@ -414,17 +402,10 @@ tunoutput(ifp, m0, dst, rt)
}
}
- s = splimp();
- if (IF_QFULL(&ifp->if_snd)) {
- IF_DROP(&ifp->if_snd);
- m_freem(m0);
- splx(s);
+ if (! IF_HANDOFF(&ifp->if_snd, m0, NULL)) {
ifp->if_collisions++;
return ENOBUFS;
}
- ifp->if_obytes += m0->m_pkthdr.len;
- IF_ENQUEUE(&ifp->if_snd, m0);
- splx(s);
ifp->if_opackets++;
if (tp->tun_flags & TUN_RWAIT) {