Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 31 Dec 2010 21:06:52 +0000 (UTC)
From:      "Bjoern A. Zeeb" <bz@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r216855 - head/sys/net
Message-ID:  <201012312106.oBVL6qJH088688@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: bz
Date: Fri Dec 31 21:06:52 2010
New Revision: 216855
URL: http://svn.freebsd.org/changeset/base/216855

Log:
  Move the increment operation under the lock and split the condition
  variable into two so that we can see on which one we are waiting.
  This might also more properly propagate the update of the
  flowclean_cycles flag and avoid "hangs" people were seeing.
  
  Suggested by:	rwatson [1]
  Sponsored by:	ISPsystem [1]
  Reviewed by:	julian [1]
  Updated by:	Mikolaj Golub (to.my.trociny gmail.com)
  Tested by:	Mikolaj Golub (to.my.trociny gmail.com)
  MFC After:	1 week
  
  [1] Early 2010, initial version.

Modified:
  head/sys/net/flowtable.c

Modified: head/sys/net/flowtable.c
==============================================================================
--- head/sys/net/flowtable.c	Fri Dec 31 20:39:27 2010	(r216854)
+++ head/sys/net/flowtable.c	Fri Dec 31 21:06:52 2010	(r216855)
@@ -195,7 +195,8 @@ static VNET_DEFINE(uma_zone_t, flow_ipv6
 #define	V_flow_ipv6_zone	VNET(flow_ipv6_zone)
 
 
-static struct cv 	flowclean_cv;
+static struct cv 	flowclean_f_cv;
+static struct cv 	flowclean_c_cv;
 static struct mtx	flowclean_lock;
 static uint32_t		flowclean_cycles;
 static uint32_t		flowclean_freq;
@@ -951,7 +952,7 @@ flow_full(struct flowtable *ft)
 		if ((ft->ft_flags & FL_HASH_ALL) == 0)
 			ft->ft_udp_idle = ft->ft_fin_wait_idle =
 			    ft->ft_syn_idle = ft->ft_tcp_idle = 5;
-		cv_broadcast(&flowclean_cv);
+		cv_broadcast(&flowclean_c_cv);
 	} else if (!full && ft->ft_full) {
 		flowclean_freq = 20*hz;
 		if ((ft->ft_flags & FL_HASH_ALL) == 0)
@@ -1560,14 +1561,14 @@ flowtable_cleaner(void)
 		}
 		VNET_LIST_RUNLOCK();
 
-		flowclean_cycles++;
 		/*
 		 * The 10 second interval between cleaning checks
 		 * is arbitrary
 		 */
 		mtx_lock(&flowclean_lock);
-		cv_broadcast(&flowclean_cv);
-		cv_timedwait(&flowclean_cv, &flowclean_lock, flowclean_freq);
+		flowclean_cycles++;
+		cv_broadcast(&flowclean_f_cv);
+		cv_timedwait(&flowclean_c_cv, &flowclean_lock, flowclean_freq);
 		mtx_unlock(&flowclean_lock);
 	}
 }
@@ -1580,8 +1581,8 @@ flowtable_flush(void *unused __unused)
 	mtx_lock(&flowclean_lock);
 	start = flowclean_cycles;
 	while (start == flowclean_cycles) {
-		cv_broadcast(&flowclean_cv);
-		cv_wait(&flowclean_cv, &flowclean_lock);
+		cv_broadcast(&flowclean_c_cv);
+		cv_wait(&flowclean_f_cv, &flowclean_lock);
 	}
 	mtx_unlock(&flowclean_lock);
 }
@@ -1613,7 +1614,8 @@ static void
 flowtable_init(const void *unused __unused)
 {
 
-	cv_init(&flowclean_cv, "flowcleanwait");
+	cv_init(&flowclean_c_cv, "c_flowcleanwait");
+	cv_init(&flowclean_f_cv, "f_flowcleanwait");
 	mtx_init(&flowclean_lock, "flowclean lock", NULL, MTX_DEF);
 	EVENTHANDLER_REGISTER(ifnet_departure_event, flowtable_flush, NULL,
 	    EVENTHANDLER_PRI_ANY);



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