RFA: Make sigthread.exp more reliable

Jim Blandy jimb@codesourcery.com
Sat Jan 12 01:32:00 GMT 2008


sigthread.exp fails intermittently, because the program exits due to a
segfault instead of the ^C GDB sends it.  I believe this is because
the threads throwing signals at each other don't wait until all the
pthread_t variables are initialized before they do so.  So they
occasionally pass an uninitialized pthread_t to pthread_kill, which
segfaults.

This patch uses barriers to make sure everyone's ready to go before
the fun begins.  Although barriers were not in the original POSIX
threads spec, they have been in the GNU C library since version 2.2,
released in 2000.  When barriers are not present, the test reports
itself as "UNSUPPORTED".

Is this okay?

gdb/testsuite/ChangeLog:
2008-01-11  Jim Blandy  <jimb@codesourcery.com>

	* gdb.threads/sigthread.c: Use barriers to ensure that
	child_thread and child_thread_two are always initialized before we
	start to use them.

diff -r a4b196da8237 -r 15f7131243ac gdb/testsuite/gdb.threads/sigthread.c
--- a/gdb/testsuite/gdb.threads/sigthread.c	Fri Jan 11 14:54:31 2008 -0800
+++ b/gdb/testsuite/gdb.threads/sigthread.c	Fri Jan 11 17:15:53 2008 -0800
@@ -20,6 +20,8 @@
    testing.  */
 #define NSIGS 10000000
 
+pthread_barrier_t barrier;
+
 void
 handler (int sig)
 {
@@ -34,6 +36,8 @@ child_two (void *arg)
 {
   int i;
 
+  pthread_barrier_wait (&barrier);
+
   for (i = 0; i < NSIGS; i++)
     pthread_kill (child_thread, SIGUSR1);
 }
@@ -42,6 +46,8 @@ thread_function (void *arg)
 thread_function (void *arg)
 {
   int i;
+
+  pthread_barrier_wait (&barrier);
 
   for (i = 0; i < NSIGS; i++)
     pthread_kill (child_thread_two, SIGUSR2);
@@ -54,9 +60,13 @@ int main()
   signal (SIGUSR1, handler);
   signal (SIGUSR2, handler);
 
+  pthread_barrier_init (&barrier, NULL, 3);
+
   main_thread = pthread_self ();
   pthread_create (&child_thread, NULL, thread_function, NULL);
   pthread_create (&child_thread_two, NULL, child_two, NULL);
+
+  pthread_barrier_wait (&barrier);
 
   for (i = 0; i < NSIGS; i++)
     pthread_kill (child_thread_two, SIGUSR1);



More information about the Gdb-patches mailing list