Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 21 Mar 2013 19:58:26 +0000 (UTC)
From:      Attilio Rao <attilio@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r248591 - head/sys/kern
Message-ID:  <201303211958.r2LJwQ3r005652@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: attilio
Date: Thu Mar 21 19:58:25 2013
New Revision: 248591
URL: http://svnweb.freebsd.org/changeset/base/248591

Log:
  Fix a bug in UMTX_PROFILING:
  UMTX_PROFILING should really analyze the distribution of locks as they
  index entries in the umtxq_chains hash-table.
  However, the current implementation does add/dec the length counters
  for *every* thread insert/removal, measuring at all really userland
  contention and not the hash distribution.
  
  Fix this by correctly add/dec the length counters in the points where
  it is really needed.
  
  Please note that this bug brought us questioning in the past the quality
  of the umtx hash table distribution.
  To date with all the benchmarks I could try I was not able to reproduce
  any issue about the hash distribution on umtx.
  
  Sponsored by:	EMC / Isilon storage division
  Reviewed by:	jeff, davide
  MFC after:	2 weeks

Modified:
  head/sys/kern/kern_umtx.c

Modified: head/sys/kern/kern_umtx.c
==============================================================================
--- head/sys/kern/kern_umtx.c	Thu Mar 21 18:59:02 2013	(r248590)
+++ head/sys/kern/kern_umtx.c	Thu Mar 21 19:58:25 2013	(r248591)
@@ -542,19 +542,19 @@ umtxq_insert_queue(struct umtx_q *uq, in
 		uh = uq->uq_spare_queue;
 		uh->key = uq->uq_key;
 		LIST_INSERT_HEAD(&uc->uc_queue[q], uh, link);
+#ifdef UMTX_PROFILING
+		uc->length++;
+		if (uc->length > uc->max_length) {
+			uc->max_length = uc->length;
+			if (uc->max_length > max_length)
+				max_length = uc->max_length;	
+		}
+#endif
 	}
 	uq->uq_spare_queue = NULL;
 
 	TAILQ_INSERT_TAIL(&uh->head, uq, uq_link);
 	uh->length++;
-#ifdef UMTX_PROFILING
-	uc->length++;
-	if (uc->length > uc->max_length) {
-		uc->max_length = uc->length;
-		if (uc->max_length > max_length)
-			max_length = uc->max_length;	
-	}
-#endif
 	uq->uq_flags |= UQF_UMTXQ;
 	uq->uq_cur_queue = uh;
 	return;
@@ -572,13 +572,13 @@ umtxq_remove_queue(struct umtx_q *uq, in
 		uh = uq->uq_cur_queue;
 		TAILQ_REMOVE(&uh->head, uq, uq_link);
 		uh->length--;
-#ifdef UMTX_PROFILING
-		uc->length--;
-#endif
 		uq->uq_flags &= ~UQF_UMTXQ;
 		if (TAILQ_EMPTY(&uh->head)) {
 			KASSERT(uh->length == 0,
 			    ("inconsistent umtxq_queue length"));
+#ifdef UMTX_PROFILING
+			uc->length--;
+#endif
 			LIST_REMOVE(uh, link);
 		} else {
 			uh = LIST_FIRST(&uc->uc_spare_queue);



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