[PATCH 3/4] Updating count.tex with new counter code

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



From: "Palik, Imre" <imrep.amz@xxxxxxxxx>

Now count.text reflects the changes made to the counter implementations, to
restrict too eager compilers.

Signed-off-by: Imre Palik <imrep.amz@xxxxxxxxx>
---
 count/count.tex | 93 +++++++++++++++++++++++++++++----------------------------
 1 file changed, 47 insertions(+), 46 deletions(-)

diff --git a/count/count.tex b/count/count.tex
index 561256a..82d4a7f 100644
--- a/count/count.tex
+++ b/count/count.tex
@@ -1003,41 +1003,42 @@ comes at the cost of the additional thread running \co{eventual()}.
   5 
   6 void inc_count(void)
   7 {
-  8   counter++;
-  9 }
- 10 
- 11 long read_count(void)
- 12 {
- 13   int t;
- 14   long sum;
- 15 
- 16   spin_lock(&final_mutex);
- 17   sum = finalcount;
- 18   for_each_thread(t)
- 19     if (counterp[t] != NULL)
- 20       sum += *counterp[t];
- 21   spin_unlock(&final_mutex);
- 22   return sum;
- 23 }
- 24 
- 25 void count_register_thread(void)
- 26 {
- 27   int idx = smp_thread_id();
- 28 
- 29   spin_lock(&final_mutex);
- 30   counterp[idx] = &counter;
- 31   spin_unlock(&final_mutex);
- 32 }
- 33 
- 34 void count_unregister_thread(int nthreadsexpected)
- 35 {
- 36   int idx = smp_thread_id();
- 37 
- 38   spin_lock(&final_mutex);
- 39   finalcount += counter;
- 40   counterp[idx] = NULL;
- 41   spin_unlock(&final_mutex);
- 42 }
+  8   WRITE_ONCE(counter,
+  9              READ_ONCE(counter) + 1);counter++;
+ 10 }
+ 11 
+ 12 long read_count(void)
+ 13 {
+ 14   int t;
+ 15   long sum;
+ 16 
+ 17   spin_lock(&final_mutex);
+ 18   sum = finalcount;
+ 19   for_each_thread(t)
+ 20     if (counterp[t] != NULL)
+ 21       sum += *counterp[t];
+ 22   spin_unlock(&final_mutex);
+ 23   return sum;
+ 24 }
+ 25 
+ 26 void count_register_thread(void)
+ 27 {
+ 28   int idx = smp_thread_id();
+ 29 
+ 30   spin_lock(&final_mutex);
+ 31   counterp[idx] = &counter;
+ 32   spin_unlock(&final_mutex);
+ 33 }
+ 34 
+ 35 void count_unregister_thread(int nthreadsexpected)
+ 36 {
+ 37   int idx = smp_thread_id();
+ 38 
+ 39   spin_lock(&final_mutex);
+ 40   finalcount += counter;
+ 41   counterp[idx] = NULL;
+ 42   spin_unlock(&final_mutex);
+ 43 }
 \end{verbbox}
 }
 \centering
@@ -1105,18 +1106,18 @@ value of the counter and exiting threads.
 } \QuickQuizEnd
 
 The \co{inc_count()} function used by updaters is quite simple, as can
-be seen on lines~6-9.
+be seen on lines~6-10.
 
 The \co{read_count()} function used by readers is a bit more complex.
-Line~16 acquires a lock to exclude exiting threads, and line~21 releases
+Line~17 acquires a lock to exclude exiting threads, and line~22 releases
 it.
-Line~17 initializes the sum to the count accumulated by those threads that
-have already exited, and lines~18-20 sum the counts being accumulated
+Line~18 initializes the sum to the count accumulated by those threads that
+have already exited, and lines~19-21 sum the counts being accumulated
 by threads currently running.
-Finally, line~22 returns the sum.
+Finally, line~23 returns the sum.
 
 \QuickQuiz{}
-	Doesn't the check for \co{NULL} on line~19 of
+	Doesn't the check for \co{NULL} on line~20 of
 	Listing~\ref{lst:count:Per-Thread Statistical Counters}
 	add extra branch mispredictions?
 	Why not have a variable set permanently to zero, and point
@@ -1156,7 +1157,7 @@ Finally, line~22 returns the sum.
 	\co{inc_count()} fastpath.
 } \QuickQuizEnd
 
-Lines~25-32 show the \co{count_register_thread()} function, which
+Lines~26-33 show the \co{count_register_thread()} function, which
 must be called by each thread before its first use of this counter.
 This function simply sets up this thread's element of the \co{counterp[]}
 array to point to its per-thread \co{counter} variable.
@@ -1177,14 +1178,14 @@ array to point to its per-thread \co{counter} variable.
 	a hundred or so CPUs, there is no need to get fancy.
 } \QuickQuizEnd
 
-Lines~34-42 show the \co{count_unregister_thread()} function, which
+Lines~35-43 show the \co{count_unregister_thread()} function, which
 must be called prior to exit by each thread that previously called
 \co{count_register_thread()}.
-Line~38 acquires the lock, and line~41 releases it, thus excluding any
+Line~39 acquires the lock, and line~42 releases it, thus excluding any
 calls to \co{read_count()} as well as other calls to
 \co{count_unregister_thread()}.
-Line~39 adds this thread's \co{counter} to the global \co{finalcount},
-and then line~40 \co{NULL}s out its \co{counterp[]} array entry.
+Line~40 adds this thread's \co{counter} to the global \co{finalcount},
+and then line~41 \co{NULL}s out its \co{counterp[]} array entry.
 A subsequent call to \co{read_count()} will see the exiting thread's
 count in the global \co{finalcount}, and will skip the exiting thread
 when sequencing through the \co{counterp[]} array, thus obtaining
-- 
2.7.4

--
To unsubscribe from this list: send the line "unsubscribe perfbook" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Index of Archives]     [Linux NFS]     [Linux NILFS]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux