public inbox for glibc-cvs@sourceware.org
help / color / mirror / Atom feed
* [glibc] Use C11 atomics instead of atomic_decrement_and_test
@ 2022-09-23 15:01 Wilco Dijkstra
  0 siblings, 0 replies; only message in thread
From: Wilco Dijkstra @ 2022-09-23 15:01 UTC (permalink / raw)
  To: glibc-cvs

https://sourceware.org/git/gitweb.cgi?p=glibc.git;h=4a07fbb689eeec30e7d71a0d144c26e0d1e424ac

commit 4a07fbb689eeec30e7d71a0d144c26e0d1e424ac
Author: Wilco Dijkstra <wdijkstr@arm.com>
Date:   Thu Sep 22 15:40:37 2022 +0100

    Use C11 atomics instead of atomic_decrement_and_test
    
    Replace atomic_decrement_and_test with atomic_fetch_add_relaxed.
    These are simple counters which do not protect any shared data from
    concurrent accesses. Also remove the unused file cond-perf.c.
    
    Passes regress on AArch64.
    
    Reviewed-by: Adhemerval Zanella  <adhemerval.zanella@linaro.org>

Diff:
---
 htl/pt-dealloc.c                    |   2 +-
 htl/pt-exit.c                       |   2 +-
 manual/llio.texi                    |   2 +-
 nptl/cond-perf.c                    | 103 ------------------------------------
 nptl/pthread_create.c               |   2 +-
 sysdeps/nptl/libc_start_call_main.h |   2 +-
 6 files changed, 5 insertions(+), 108 deletions(-)

diff --git a/htl/pt-dealloc.c b/htl/pt-dealloc.c
index c776e3471d..86bbb3091f 100644
--- a/htl/pt-dealloc.c
+++ b/htl/pt-dealloc.c
@@ -33,7 +33,7 @@ extern pthread_mutex_t __pthread_free_threads_lock;
 void
 __pthread_dealloc (struct __pthread *pthread)
 {
-  if (!atomic_decrement_and_test (&pthread->nr_refs))
+  if (atomic_fetch_add_relaxed (&pthread->nr_refs, -1) != 1)
     return;
 
   /* Withdraw this thread from the thread ID lookup table.  */
diff --git a/htl/pt-exit.c b/htl/pt-exit.c
index f0759c8738..3c0a8c52f3 100644
--- a/htl/pt-exit.c
+++ b/htl/pt-exit.c
@@ -50,7 +50,7 @@ __pthread_exit (void *status)
 
   /* Decrease the number of threads.  We use an atomic operation to
      make sure that only the last thread calls `exit'.  */
-  if (atomic_decrement_and_test (&__pthread_total))
+  if (atomic_fetch_add_relaxed (&__pthread_total, -1) == 1)
     /* We are the last thread.  */
     exit (0);
 
diff --git a/manual/llio.texi b/manual/llio.texi
index 79cf4c1670..85201a4bdc 100644
--- a/manual/llio.texi
+++ b/manual/llio.texi
@@ -2614,7 +2614,7 @@ aiocb64}, since the LFS transparently replaces the old interface.
 @c      free @ascuheap @acsmem
 @c     libc_thread_freeres
 @c      libc_thread_subfreeres ok
-@c     atomic_decrement_and_test ok
+@c     atomic_fetch_add_relaxed ok
 @c     td_eventword ok
 @c     td_eventmask ok
 @c     atomic_compare_exchange_bool_acq ok
diff --git a/nptl/cond-perf.c b/nptl/cond-perf.c
deleted file mode 100644
index 9c9488e274..0000000000
--- a/nptl/cond-perf.c
+++ /dev/null
@@ -1,103 +0,0 @@
-#include <pthread.h>
-#include <stdbool.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <atomic.h>
-
-static pthread_cond_t cond1 = PTHREAD_COND_INITIALIZER;
-static pthread_mutex_t mut1 = PTHREAD_MUTEX_INITIALIZER;
-
-static pthread_cond_t cond2 = PTHREAD_COND_INITIALIZER;
-static pthread_mutex_t mut2 = PTHREAD_MUTEX_INITIALIZER;
-
-static bool last_round;
-static int ntogo;
-static bool alldone;
-
-
-static void *
-cons (void *arg)
-{
-  pthread_mutex_lock (&mut1);
-
-  do
-    {
-      if (atomic_decrement_and_test (&ntogo))
-	{
-	  pthread_mutex_lock (&mut2);
-	  alldone = true;
-	  pthread_cond_signal (&cond2);
-	  pthread_mutex_unlock (&mut2);
-	}
-
-      pthread_cond_wait (&cond1, &mut1);
-    }
-  while (! last_round);
-
-  pthread_mutex_unlock (&mut1);
-
-  return NULL;
-}
-
-
-int
-main (int argc, char *argv[])
-{
-  int opt;
-  int err;
-  int nthreads = 10;
-  int nrounds = 100;
-  bool keeplock = false;
-
-  while ((opt = getopt (argc, argv, "n:r:k")) != -1)
-    switch (opt)
-      {
-      case 'n':
-	nthreads = atol (optarg);
-	break;
-      case 'r':
-	nrounds = atol (optarg);
-	break;
-      case 'k':
-	keeplock = true;
-	break;
-      }
-
-  ntogo = nthreads;
-
-  pthread_t th[nthreads];
-  int i;
-  for (i = 0; __builtin_expect (i < nthreads, 1); ++i)
-    if (__glibc_unlikely ((err = pthread_create (&th[i], NULL, cons, (void *) (long) i)) != 0))
-      printf ("pthread_create: %s\n", strerror (err));
-
-  for (i = 0; __builtin_expect (i < nrounds, 1); ++i)
-    {
-      pthread_mutex_lock (&mut2);
-      while (! alldone)
-	pthread_cond_wait (&cond2, &mut2);
-      pthread_mutex_unlock (&mut2);
-
-      pthread_mutex_lock (&mut1);
-      if (! keeplock)
-	pthread_mutex_unlock (&mut1);
-
-      ntogo = nthreads;
-      alldone = false;
-      if (i + 1 >= nrounds)
-	last_round = true;
-
-      pthread_cond_broadcast (&cond1);
-
-      if (keeplock)
-	pthread_mutex_unlock (&mut1);
-    }
-
-  for (i = 0; i < nthreads; ++i)
-    if ((err = pthread_join (th[i], NULL)) != 0)
-      printf ("pthread_create: %s\n", strerror (err));
-
-  return 0;
-}
diff --git a/nptl/pthread_create.c b/nptl/pthread_create.c
index 0df67484e2..54afee5976 100644
--- a/nptl/pthread_create.c
+++ b/nptl/pthread_create.c
@@ -489,7 +489,7 @@ start_thread (void *arg)
      the breakpoint reports TD_THR_RUN state rather than TD_THR_ZOMBIE.  */
   atomic_fetch_or_relaxed (&pd->cancelhandling, EXITING_BITMASK);
 
-  if (__glibc_unlikely (atomic_decrement_and_test (&__nptl_nthreads)))
+  if (__glibc_unlikely (atomic_fetch_add_relaxed (&__nptl_nthreads, -1) == 1))
     /* This was the last thread.  */
     exit (0);
 
diff --git a/sysdeps/nptl/libc_start_call_main.h b/sysdeps/nptl/libc_start_call_main.h
index a9e85f2b09..c10a16b2c4 100644
--- a/sysdeps/nptl/libc_start_call_main.h
+++ b/sysdeps/nptl/libc_start_call_main.h
@@ -65,7 +65,7 @@ __libc_start_call_main (int (*main) (int, char **, char ** MAIN_AUXVEC_DECL),
       /* One less thread.  Decrement the counter.  If it is zero we
          terminate the entire process.  */
       result = 0;
-      if (! atomic_decrement_and_test (&__nptl_nthreads))
+      if (atomic_fetch_add_relaxed (&__nptl_nthreads, -1) != 1)
         /* Not much left to do but to exit the thread, not the process.  */
 	while (1)
 	  INTERNAL_SYSCALL_CALL (exit, 0);

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2022-09-23 15:01 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-09-23 15:01 [glibc] Use C11 atomics instead of atomic_decrement_and_test Wilco Dijkstra

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).