DragonFlyBSD Kernel Audit
DF-0589 / fix.diff
← back to finding ↓ download raw
diff --git a/sys/netgraph7/bluetooth/drivers/h4/ng_h4_var.h b/sys/netgraph7/bluetooth/drivers/h4/ng_h4_var.h
--- a/sys/netgraph7/bluetooth/drivers/h4/ng_h4_var.h
+++ b/sys/netgraph7/bluetooth/drivers/h4/ng_h4_var.h
@@ -40,6 +40,9 @@
 #ifndef _NETGRAPH_H4_VAR_H_
 #define _NETGRAPH_H4_VAR_H_
 
+#include <sys/spinlock.h>	/* for struct spinlock */
+#include <sys/spinlock2.h>	/* for spin_lock/unlock/init inline funcs */
+
 /*
  * Malloc declaration
  */
@@ -85,8 +88,9 @@
 
 	struct ifqueue		outq;	/* Queue of outgoing mbuf's */
 #define NG_H4_DEFAULTQLEN	 12     /* XXX max number of mbuf's in outq */
-#define	NG_H4_LOCK(sc)		crit_enter();
-#define	NG_H4_UNLOCK(sc)	crit_exit();
+	struct spinlock		sc_lock;	/* Protects outq + parser state */
+#define	NG_H4_LOCK(sc)		spin_lock(&(sc)->sc_lock)
+#define NG_H4_UNLOCK(sc)	spin_unlock(&(sc)->sc_lock)
 
 #define NG_H4_IBUF_SIZE		1024	/* XXX must be big enough to hold full
 					   frame */

diff --git a/sys/netgraph7/bluetooth/drivers/h4/ng_h4.c b/sys/netgraph7/bluetooth/drivers/h4/ng_h4.c
--- a/sys/netgraph7/bluetooth/drivers/h4/ng_h4.c
+++ b/sys/netgraph7/bluetooth/drivers/h4/ng_h4.c
@@ -174,6 +174,8 @@
 	sc->outq.ifq_maxlen = NG_H4_DEFAULTQLEN;
 	ng_callout_init(&sc->timo);
 
+	spin_init(&sc->sc_lock, "ng_h4");
+
 	NG_H4_LOCK(sc);
 
 	/* Setup netgraph node */
@@ -589,7 +591,9 @@
 	while (1) {
 #endif
 		/* Remove first mbuf from queue */
+		NG_H4_LOCK(sc);
 		IF_DEQUEUE(&sc->outq, m);
+		NG_H4_UNLOCK(sc);
 		if (m == NULL)
 			break;
 
@@ -612,7 +616,9 @@
 
 		/* Put remainder of mbuf chain (if any) back on queue */
 		if (m != NULL) {
+			NG_H4_LOCK(sc);
 			IF_PREPEND(&sc->outq, m);
+			NG_H4_UNLOCK(sc);
 			break;
 		}