Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 26 May 2010 18:36:24 +0000 (UTC)
From:      Juli Mallett <jmallett@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-user@freebsd.org
Subject:   svn commit: r208575 - user/jmallett/octeon/sys/mips/cavium/octe
Message-ID:  <201005261836.o4QIaOxT025970@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: jmallett
Date: Wed May 26 18:36:23 2010
New Revision: 208575
URL: http://svn.freebsd.org/changeset/base/208575

Log:
  Add cursory locking of the if_snd queue to prevent races between the ifq empty
  check and processing the first packet (or, worse, double-processing.)
  
  There needs to be more locking of the upper-level structures in this driver, but
  this is a good place to start.  All of the things below the ifnet have their
  own locking or don't need it.  (Especially where there are already critical
  sections to prevent migration when accessing per-CPU registers.)
  
  Reported by:	stas

Modified:
  user/jmallett/octeon/sys/mips/cavium/octe/cavium-ethernet.h
  user/jmallett/octeon/sys/mips/cavium/octe/octe.c

Modified: user/jmallett/octeon/sys/mips/cavium/octe/cavium-ethernet.h
==============================================================================
--- user/jmallett/octeon/sys/mips/cavium/octe/cavium-ethernet.h	Wed May 26 18:00:44 2010	(r208574)
+++ user/jmallett/octeon/sys/mips/cavium/octe/cavium-ethernet.h	Wed May 26 18:36:23 2010	(r208575)
@@ -119,6 +119,8 @@ typedef struct {
 
 	struct ifmedia media;
 	int if_flags;
+
+	struct mtx tx_mtx;
 } cvm_oct_private_t;
 
 

Modified: user/jmallett/octeon/sys/mips/cavium/octe/octe.c
==============================================================================
--- user/jmallett/octeon/sys/mips/cavium/octe/octe.c	Wed May 26 18:00:44 2010	(r208574)
+++ user/jmallett/octeon/sys/mips/cavium/octe/octe.c	Wed May 26 18:36:23 2010	(r208575)
@@ -78,6 +78,9 @@
 
 #include "miibus_if.h"
 
+#define	OCTE_TX_LOCK(priv)	mtx_lock(&(priv)->tx_mtx)
+#define	OCTE_TX_UNLOCK(priv)	mtx_unlock(&(priv)->tx_mtx)
+
 static int		octe_probe(device_t);
 static int		octe_attach(device_t);
 static int		octe_detach(device_t);
@@ -174,6 +177,8 @@ octe_attach(device_t dev)
 
 	priv->if_flags = ifp->if_flags;
 
+	mtx_init(&priv->tx_mtx, ifp->if_xname, "octe tx send queue", MTX_DEF);
+
 	for (qos = 0; qos < 16; qos++) {
 		mtx_init(&priv->tx_free_queue[qos].ifq_mtx, ifp->if_xname, "octe tx free queue", MTX_DEF);
 		IFQ_SET_MAXLEN(&priv->tx_free_queue[qos], MAX_OUT_QUEUE_DEPTH);
@@ -181,9 +186,11 @@ octe_attach(device_t dev)
 
 	ether_ifattach(ifp, priv->mac);
 
+	OCTE_TX_LOCK(priv);
 	IFQ_SET_MAXLEN(&ifp->if_snd, MAX_OUT_QUEUE_DEPTH);
 	ifp->if_snd.ifq_drv_maxlen = MAX_OUT_QUEUE_DEPTH;
 	IFQ_SET_READY(&ifp->if_snd);
+	OCTE_TX_UNLOCK(priv);
 
 	return (0);
 }
@@ -280,9 +287,12 @@ octe_start(struct ifnet *ifp)
 	if ((ifp->if_drv_flags & (IFF_DRV_RUNNING | IFF_DRV_OACTIVE)) != IFF_DRV_RUNNING)
 		return;
 
+	OCTE_TX_LOCK(priv);
 	while (!IFQ_DRV_IS_EMPTY(&ifp->if_snd)) {
 		IFQ_DRV_DEQUEUE(&ifp->if_snd, m);
 
+		OCTE_TX_UNLOCK(priv);
+
 		/*
 		 * XXX
 		 *
@@ -312,6 +322,7 @@ octe_start(struct ifnet *ifp)
 			return;
 		}
 	}
+	OCTE_TX_UNLOCK(priv);
 }
 
 static int



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201005261836.o4QIaOxT025970>