diff mbox

[RFC,PR68580] Handle pthread_create error in tsan testsuite

Message ID 56C16988.4070604@mentor.com
State New
Headers show

Commit Message

Tom de Vries Feb. 15, 2016, 6 a.m. UTC
Hi,

Occasionally, I've been running into this failure while running the tsan 
testsuite:
...
FAIL: c-c++-common/tsan/pr65400-1.c -O0 execution test
...

I've also observed a potential similar occurrence here ( 
https://gcc.gnu.org/ml/gcc-regression/2015-08/msg00147.html ).

Initially, I couldn't reproduce it on the command line.

Then I tried mimicking heavy load situations that might arise while 
running the testsuite (I test with -j12 on a server), by running the 
test in parallel, and found that in that case pthread_create fails, and 
the test returns 0, which combined with the dg-shouldfail, makes the 
execution test fail.

So I suspect the failure I see while running the testsuite is the result 
of pthread_create failure.

The problem is that I can't be sure, given that in the testcase we do 
not distinguish between:
- return 0, case pthread_create failed, and
- return 0 at end of main, case -fsanitize=thread failed to catch the
   race condition.

Note also that it's possible that many other tsan tests are failing in 
pthread_create, but that this goes unnoticed because we don't test for 
the result of pthread_create in most tests.

This untested patch is an attempt at structurally testing and handling 
the result of pthread_create in the tsan testsuite, using this macro:
...
#define PTHREAD_CREATE(thread, attr, start_routine, arg)	\
   {								\
     int res = pthread_create (thread, attr, start_routine, arg);\
     if (res)							\
       {								\
	error (0, res, "pthread_create failed with");		\
	exit (0);						\
       }								\
   }
...

If this patch is committed, I should at least be able to find out if 
indeed the failure I observe is related to resource exhaustion.

Good idea? Any other comments?

Thanks,
- Tom

Comments

Dmitry Vyukov Feb. 15, 2016, 7:18 a.m. UTC | #1
On Mon, Feb 15, 2016 at 7:00 AM, Tom de Vries <Tom_deVries@mentor.com> wrote:
> Hi,
>
> Occasionally, I've been running into this failure while running the tsan
> testsuite:
> ...
> FAIL: c-c++-common/tsan/pr65400-1.c -O0 execution test
> ...
>
> I've also observed a potential similar occurrence here (
> https://gcc.gnu.org/ml/gcc-regression/2015-08/msg00147.html ).
>
> Initially, I couldn't reproduce it on the command line.
>
> Then I tried mimicking heavy load situations that might arise while running
> the testsuite (I test with -j12 on a server), by running the test in
> parallel, and found that in that case pthread_create fails, and the test
> returns 0, which combined with the dg-shouldfail, makes the execution test
> fail.
>
> So I suspect the failure I see while running the testsuite is the result of
> pthread_create failure.
>
> The problem is that I can't be sure, given that in the testcase we do not
> distinguish between:
> - return 0, case pthread_create failed, and
> - return 0 at end of main, case -fsanitize=thread failed to catch the
>   race condition.
>
> Note also that it's possible that many other tsan tests are failing in
> pthread_create, but that this goes unnoticed because we don't test for the
> result of pthread_create in most tests.
>
> This untested patch is an attempt at structurally testing and handling the
> result of pthread_create in the tsan testsuite, using this macro:
> ...
> #define PTHREAD_CREATE(thread, attr, start_routine, arg)        \
>   {                                                             \
>     int res = pthread_create (thread, attr, start_routine, arg);\
>     if (res)                                                    \
>       {                                                         \
>         error (0, res, "pthread_create failed with");           \
>         exit (0);                                               \
>       }                                                         \
>   }
> ...
>
> If this patch is committed, I should at least be able to find out if indeed
> the failure I observe is related to resource exhaustion.
>
> Good idea? Any other comments?


Hi Tom,

Yes, I guess we need to check return values. I am not sure how we can
handle ENOMEMs in tests, but at least knowing the failure reason is
valuable. We also suspect failing mmap's in some tests on some test
bots.

But changes to tsan runtime and tests should go into llvm repository
first and then be integrated into gcc repository. If you never sent
changes to llvm we can help.

llvm tsan tests contain test.h file (probably what's called
test_barrier.h in gcc), you can put the macro there. test.h should
already be included into all tests.

Thanks
Dmitry Vyukov Feb. 15, 2016, 7:24 a.m. UTC | #2
If we are talking about pr 68580, then I would try:
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68580#c2
first.



On Mon, Feb 15, 2016 at 8:18 AM, Dmitry Vyukov <dvyukov@google.com> wrote:
> On Mon, Feb 15, 2016 at 7:00 AM, Tom de Vries <Tom_deVries@mentor.com> wrote:
>> Hi,
>>
>> Occasionally, I've been running into this failure while running the tsan
>> testsuite:
>> ...
>> FAIL: c-c++-common/tsan/pr65400-1.c -O0 execution test
>> ...
>>
>> I've also observed a potential similar occurrence here (
>> https://gcc.gnu.org/ml/gcc-regression/2015-08/msg00147.html ).
>>
>> Initially, I couldn't reproduce it on the command line.
>>
>> Then I tried mimicking heavy load situations that might arise while running
>> the testsuite (I test with -j12 on a server), by running the test in
>> parallel, and found that in that case pthread_create fails, and the test
>> returns 0, which combined with the dg-shouldfail, makes the execution test
>> fail.
>>
>> So I suspect the failure I see while running the testsuite is the result of
>> pthread_create failure.
>>
>> The problem is that I can't be sure, given that in the testcase we do not
>> distinguish between:
>> - return 0, case pthread_create failed, and
>> - return 0 at end of main, case -fsanitize=thread failed to catch the
>>   race condition.
>>
>> Note also that it's possible that many other tsan tests are failing in
>> pthread_create, but that this goes unnoticed because we don't test for the
>> result of pthread_create in most tests.
>>
>> This untested patch is an attempt at structurally testing and handling the
>> result of pthread_create in the tsan testsuite, using this macro:
>> ...
>> #define PTHREAD_CREATE(thread, attr, start_routine, arg)        \
>>   {                                                             \
>>     int res = pthread_create (thread, attr, start_routine, arg);\
>>     if (res)                                                    \
>>       {                                                         \
>>         error (0, res, "pthread_create failed with");           \
>>         exit (0);                                               \
>>       }                                                         \
>>   }
>> ...
>>
>> If this patch is committed, I should at least be able to find out if indeed
>> the failure I observe is related to resource exhaustion.
>>
>> Good idea? Any other comments?
>
>
> Hi Tom,
>
> Yes, I guess we need to check return values. I am not sure how we can
> handle ENOMEMs in tests, but at least knowing the failure reason is
> valuable. We also suspect failing mmap's in some tests on some test
> bots.
>
> But changes to tsan runtime and tests should go into llvm repository
> first and then be integrated into gcc repository. If you never sent
> changes to llvm we can help.
>
> llvm tsan tests contain test.h file (probably what's called
> test_barrier.h in gcc), you can put the macro there. test.h should
> already be included into all tests.
>
> Thanks
Tom de Vries Feb. 15, 2016, 8:07 a.m. UTC | #3
On 15/02/16 08:24, Dmitry Vyukov wrote:
> If we are talking about pr 68580, then I would try:
> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68580#c2
> first.

As I tried to explain in the follow-up comment ( 
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68580#c3 ), since 
unfortunately I have no reliable way of reproducing the failure, there's 
no defined way to 'try' something.

Thanks,
- Tom
diff mbox

Patch

Handle pthread_create error in tsan testsuite

2016-02-15  Tom de Vries  <tom@codesourcery.com>

	PR testsuite/68580
	* c-c++-common/tsan/pthread_safe.h: New header file.
	* g++.dg/tsan/pthread_safe.h: Same.
	* c-c++-common/tsan/atomic_stack.c: Include pthread_safe.h.  Use
	PTHREAD_CREATE.
	* c-c++-common/tsan/bitfield_race.c: Same.
	* c-c++-common/tsan/fd_pipe_race.c: Same.
	* c-c++-common/tsan/mutexset1.c: Same.
	* c-c++-common/tsan/pr65400-1.c: Same.
	* c-c++-common/tsan/pr65400-3.c: Same.
	* c-c++-common/tsan/race_on_barrier.c: Same.
	* c-c++-common/tsan/race_on_barrier2.c: Same.
	* c-c++-common/tsan/race_on_mutex.c: Same.
	* c-c++-common/tsan/race_on_mutex2.c: Same.
	* c-c++-common/tsan/simple_race.c: Same.
	* c-c++-common/tsan/simple_stack.c: Same.
	* c-c++-common/tsan/sleep_sync.c: Same.
	* c-c++-common/tsan/thread_leak.c: Same.
	* c-c++-common/tsan/thread_leak1.c: Same.
	* c-c++-common/tsan/thread_leak2.c: Same.
	* c-c++-common/tsan/tiny_race.c: Same.
	* c-c++-common/tsan/tls_race.c: Same.
	* c-c++-common/tsan/write_in_reader_lock.c: Same.
	* g++.dg/tsan/aligned_vs_unaligned_race.C: Same.
	* g++.dg/tsan/atomic_free.C: Same.
	* g++.dg/tsan/atomic_free2.C: Same.
	* g++.dg/tsan/benign_race.C: Same.
	* g++.dg/tsan/cond_race.C: Same.
	* g++.dg/tsan/default_options.C: Same.
	* g++.dg/tsan/fd_close_norace.C: Same.
	* g++.dg/tsan/fd_close_norace2.C: Same.
	* g++.dg/tsan/pr64265.C: Same.
	* g++.dg/tsan/vptr_benign_race.C: Same.
	* g++.dg/tsan/vptr_harmful_race.C: Same.

---
 gcc/testsuite/c-c++-common/tsan/atomic_stack.c         |  5 +++--
 gcc/testsuite/c-c++-common/tsan/bitfield_race.c        |  3 ++-
 gcc/testsuite/c-c++-common/tsan/fd_pipe_race.c         |  5 +++--
 gcc/testsuite/c-c++-common/tsan/mutexset1.c            |  5 +++--
 gcc/testsuite/c-c++-common/tsan/pr65400-1.c            |  4 ++--
 gcc/testsuite/c-c++-common/tsan/pr65400-3.c            |  3 ++-
 gcc/testsuite/c-c++-common/tsan/pthread_safe.h         | 12 ++++++++++++
 gcc/testsuite/c-c++-common/tsan/race_on_barrier.c      |  3 ++-
 gcc/testsuite/c-c++-common/tsan/race_on_barrier2.c     |  3 ++-
 gcc/testsuite/c-c++-common/tsan/race_on_mutex.c        |  5 +++--
 gcc/testsuite/c-c++-common/tsan/race_on_mutex2.c       |  3 ++-
 gcc/testsuite/c-c++-common/tsan/simple_race.c          |  5 +++--
 gcc/testsuite/c-c++-common/tsan/simple_stack.c         |  3 ++-
 gcc/testsuite/c-c++-common/tsan/sleep_sync.c           |  3 ++-
 gcc/testsuite/c-c++-common/tsan/thread_leak.c          |  3 ++-
 gcc/testsuite/c-c++-common/tsan/thread_leak1.c         |  3 ++-
 gcc/testsuite/c-c++-common/tsan/thread_leak2.c         |  3 ++-
 gcc/testsuite/c-c++-common/tsan/tiny_race.c            |  3 ++-
 gcc/testsuite/c-c++-common/tsan/tls_race.c             |  3 ++-
 gcc/testsuite/c-c++-common/tsan/write_in_reader_lock.c |  3 ++-
 gcc/testsuite/g++.dg/tsan/aligned_vs_unaligned_race.C  |  5 +++--
 gcc/testsuite/g++.dg/tsan/atomic_free.C                |  3 ++-
 gcc/testsuite/g++.dg/tsan/atomic_free2.C               |  3 ++-
 gcc/testsuite/g++.dg/tsan/benign_race.C                |  3 ++-
 gcc/testsuite/g++.dg/tsan/cond_race.C                  |  3 ++-
 gcc/testsuite/g++.dg/tsan/default_options.C            |  5 +++--
 gcc/testsuite/g++.dg/tsan/fd_close_norace.C            |  5 +++--
 gcc/testsuite/g++.dg/tsan/fd_close_norace2.C           |  3 ++-
 gcc/testsuite/g++.dg/tsan/pr64265.C                    |  4 ++--
 gcc/testsuite/g++.dg/tsan/pthread_safe.h               | 12 ++++++++++++
 gcc/testsuite/g++.dg/tsan/vptr_benign_race.C           |  5 +++--
 gcc/testsuite/g++.dg/tsan/vptr_harmful_race.C          |  5 +++--
 32 files changed, 94 insertions(+), 42 deletions(-)

diff --git a/gcc/testsuite/c-c++-common/tsan/atomic_stack.c b/gcc/testsuite/c-c++-common/tsan/atomic_stack.c
index 746afa7..dee8f36 100644
--- a/gcc/testsuite/c-c++-common/tsan/atomic_stack.c
+++ b/gcc/testsuite/c-c++-common/tsan/atomic_stack.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -22,8 +23,8 @@  void *Thread2(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/bitfield_race.c b/gcc/testsuite/c-c++-common/tsan/bitfield_race.c
index 4268115..ca4ce15 100644
--- a/gcc/testsuite/c-c++-common/tsan/bitfield_race.c
+++ b/gcc/testsuite/c-c++-common/tsan/bitfield_race.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -20,7 +21,7 @@  void *Thread1(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t;
-  pthread_create(&t, 0, Thread1, 0);
+  PTHREAD_CREATE(&t, 0, Thread1, 0);
   Global.b = 43;
   barrier_wait(&barrier);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/c-c++-common/tsan/fd_pipe_race.c b/gcc/testsuite/c-c++-common/tsan/fd_pipe_race.c
index e2176da..00c35c7 100644
--- a/gcc/testsuite/c-c++-common/tsan/fd_pipe_race.c
+++ b/gcc/testsuite/c-c++-common/tsan/fd_pipe_race.c
@@ -3,6 +3,7 @@ 
 
 #include <pthread.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -25,8 +26,8 @@  int main() {
   barrier_init(&barrier, 2);
   pipe(fds);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/mutexset1.c b/gcc/testsuite/c-c++-common/tsan/mutexset1.c
index 3462ec4..e17222b 100644
--- a/gcc/testsuite/c-c++-common/tsan/mutexset1.c
+++ b/gcc/testsuite/c-c++-common/tsan/mutexset1.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -27,8 +28,8 @@  int main() {
   barrier_init(&barrier, 2);
   pthread_mutex_init(&mtx, 0);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   pthread_mutex_destroy(&mtx);
diff --git a/gcc/testsuite/c-c++-common/tsan/pr65400-1.c b/gcc/testsuite/c-c++-common/tsan/pr65400-1.c
index 96fbbfd..df0f643 100644
--- a/gcc/testsuite/c-c++-common/tsan/pr65400-1.c
+++ b/gcc/testsuite/c-c++-common/tsan/pr65400-1.c
@@ -4,6 +4,7 @@ 
 /* { dg-additional-sources pr65400-2.c } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -74,8 +75,7 @@  main ()
 {
   pthread_t th;
   barrier_init (&barrier, 2);
-  if (pthread_create (&th, NULL, tf, NULL))
-    return 0;
+  PTHREAD_CREATE (&th, NULL, tf, NULL);
   v++;
   barrier_wait (&barrier);
   pthread_join (th, NULL);
diff --git a/gcc/testsuite/c-c++-common/tsan/pr65400-3.c b/gcc/testsuite/c-c++-common/tsan/pr65400-3.c
index 9483bb6..9e48ab3 100644
--- a/gcc/testsuite/c-c++-common/tsan/pr65400-3.c
+++ b/gcc/testsuite/c-c++-common/tsan/pr65400-3.c
@@ -3,6 +3,7 @@ 
 /* { dg-additional-options "-fno-omit-frame-pointer -ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -63,7 +64,7 @@  main ()
 {
   pthread_t th;
   barrier_init (&barrier, 2);
-  if (pthread_create (&th, NULL, tf, NULL))
+  if (PTHREAD_CREATE (&th, NULL, tf, NULL))
     return 0;
   barrier_wait (&barrier);
   v++;
diff --git a/gcc/testsuite/c-c++-common/tsan/pthread_safe.h b/gcc/testsuite/c-c++-common/tsan/pthread_safe.h
new file mode 100644
index 0000000..07d273a
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/tsan/pthread_safe.h
@@ -0,0 +1,12 @@ 
+#include <error.h>
+#include <stdlib.h>
+
+#define PTHREAD_CREATE(thread, attr, start_routine, arg)		\
+  {									\
+    int res = pthread_create (thread, attr, start_routine, arg);	\
+    if (res)								\
+      {									\
+	error (0, res, "pthread_create failed with");			\
+	exit (0);							\
+      }									\
+  }
diff --git a/gcc/testsuite/c-c++-common/tsan/race_on_barrier.c b/gcc/testsuite/c-c++-common/tsan/race_on_barrier.c
index 3de3ff2..b96004d 100644
--- a/gcc/testsuite/c-c++-common/tsan/race_on_barrier.c
+++ b/gcc/testsuite/c-c++-common/tsan/race_on_barrier.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -24,7 +25,7 @@  void *Thread2(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t;
-  pthread_create(&t, NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t, NULL, Thread1, NULL);
   Thread2(0);
   pthread_join(t, NULL);
   pthread_barrier_destroy(&B);
diff --git a/gcc/testsuite/c-c++-common/tsan/race_on_barrier2.c b/gcc/testsuite/c-c++-common/tsan/race_on_barrier2.c
index b01a5cc..b15eacf 100644
--- a/gcc/testsuite/c-c++-common/tsan/race_on_barrier2.c
+++ b/gcc/testsuite/c-c++-common/tsan/race_on_barrier2.c
@@ -4,6 +4,7 @@ 
 #include <stdio.h>
 #include <stddef.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 
 pthread_barrier_t B;
 int Global;
@@ -23,7 +24,7 @@  void *Thread2(void *x) {
 int main() {
   pthread_barrier_init(&B, 0, 2);
   pthread_t t;
-  pthread_create(&t, NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t, NULL, Thread1, NULL);
   Thread2(0);
   pthread_join(t, NULL);
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/race_on_mutex.c b/gcc/testsuite/c-c++-common/tsan/race_on_mutex.c
index ae30d05..e2e1f00 100644
--- a/gcc/testsuite/c-c++-common/tsan/race_on_mutex.c
+++ b/gcc/testsuite/c-c++-common/tsan/race_on_mutex.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -28,8 +29,8 @@  void *Thread2(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   pthread_mutex_destroy(&Mtx);
diff --git a/gcc/testsuite/c-c++-common/tsan/race_on_mutex2.c b/gcc/testsuite/c-c++-common/tsan/race_on_mutex2.c
index 57d7e21..8bc508d 100644
--- a/gcc/testsuite/c-c++-common/tsan/race_on_mutex2.c
+++ b/gcc/testsuite/c-c++-common/tsan/race_on_mutex2.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -18,7 +19,7 @@  int main() {
   pthread_mutex_t Mtx;
   pthread_mutex_init(&Mtx, 0);
   pthread_t t;
-  pthread_create(&t, 0, Thread, &Mtx);
+  PTHREAD_CREATE(&t, 0, Thread, &Mtx);
   barrier_wait(&barrier);
   pthread_mutex_destroy(&Mtx);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/c-c++-common/tsan/simple_race.c b/gcc/testsuite/c-c++-common/tsan/simple_race.c
index c1a369b..da614bb 100644
--- a/gcc/testsuite/c-c++-common/tsan/simple_race.c
+++ b/gcc/testsuite/c-c++-common/tsan/simple_race.c
@@ -4,6 +4,7 @@ 
 
 #include <pthread.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 #define MAX_ITERATIONS_NUMBER 1
@@ -45,8 +46,8 @@  void *Thread2(void *x) {
 
 int main_1() {
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/simple_stack.c b/gcc/testsuite/c-c++-common/tsan/simple_stack.c
index a4d0aba..b20087d 100644
--- a/gcc/testsuite/c-c++-common/tsan/simple_stack.c
+++ b/gcc/testsuite/c-c++-common/tsan/simple_stack.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -38,7 +39,7 @@  void *Thread2(void *x) {
 }
 
 void StartThread(pthread_t *t, void *(*f)(void*)) {
-  pthread_create(t, NULL, f, NULL);
+  PTHREAD_CREATE(t, NULL, f, NULL);
 }
 
 int main() {
diff --git a/gcc/testsuite/c-c++-common/tsan/sleep_sync.c b/gcc/testsuite/c-c++-common/tsan/sleep_sync.c
index c681dce..7c0cada 100644
--- a/gcc/testsuite/c-c++-common/tsan/sleep_sync.c
+++ b/gcc/testsuite/c-c++-common/tsan/sleep_sync.c
@@ -3,6 +3,7 @@ 
 
 #include <pthread.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -22,7 +23,7 @@  void *Thread(void *p) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t;
-  pthread_create(&t, 0, Thread, 0);
+  PTHREAD_CREATE(&t, 0, Thread, 0);
   X = 43;
   barrier_wait(&barrier);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/c-c++-common/tsan/thread_leak.c b/gcc/testsuite/c-c++-common/tsan/thread_leak.c
index 02deaba..644dd1d 100644
--- a/gcc/testsuite/c-c++-common/tsan/thread_leak.c
+++ b/gcc/testsuite/c-c++-common/tsan/thread_leak.c
@@ -1,5 +1,6 @@ 
 #include <pthread.h>
 #include <stdio.h>
+#include "pthread_safe.h"
 
 void *Thread(void *x) {
   return 0;
@@ -7,7 +8,7 @@  void *Thread(void *x) {
 
 int main() {
   pthread_t t;
-  pthread_create(&t, 0, Thread, 0);
+  PTHREAD_CREATE(&t, 0, Thread, 0);
   pthread_join(t, 0);
   printf("PASS\n");
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/thread_leak1.c b/gcc/testsuite/c-c++-common/tsan/thread_leak1.c
index ce28ee4..dde4abb 100644
--- a/gcc/testsuite/c-c++-common/tsan/thread_leak1.c
+++ b/gcc/testsuite/c-c++-common/tsan/thread_leak1.c
@@ -2,6 +2,7 @@ 
 
 #include <pthread.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 
 void *Thread(void *x) {
   return 0;
@@ -9,7 +10,7 @@  void *Thread(void *x) {
 
 int main() {
   pthread_t t;
-  pthread_create(&t, 0, Thread, 0);
+  PTHREAD_CREATE(&t, 0, Thread, 0);
   sleep(1);
   return 0;
 }
diff --git a/gcc/testsuite/c-c++-common/tsan/thread_leak2.c b/gcc/testsuite/c-c++-common/tsan/thread_leak2.c
index c9b8046..24a871e 100644
--- a/gcc/testsuite/c-c++-common/tsan/thread_leak2.c
+++ b/gcc/testsuite/c-c++-common/tsan/thread_leak2.c
@@ -2,6 +2,7 @@ 
 
 #include <pthread.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 
 void *Thread(void *x) {
   return 0;
@@ -11,7 +12,7 @@  int main() {
   int i;
   for (i = 0; i < 5; i++) {
     pthread_t t;
-    pthread_create(&t, 0, Thread, 0);
+    PTHREAD_CREATE(&t, 0, Thread, 0);
   }
   sleep(1);
   return 0;
diff --git a/gcc/testsuite/c-c++-common/tsan/tiny_race.c b/gcc/testsuite/c-c++-common/tsan/tiny_race.c
index 10a3feb..4c432f4 100644
--- a/gcc/testsuite/c-c++-common/tsan/tiny_race.c
+++ b/gcc/testsuite/c-c++-common/tsan/tiny_race.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -16,7 +17,7 @@  void *Thread1(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t;
-  pthread_create(&t, 0, Thread1, 0);
+  PTHREAD_CREATE(&t, 0, Thread1, 0);
   Global = 43;
   barrier_wait(&barrier);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/c-c++-common/tsan/tls_race.c b/gcc/testsuite/c-c++-common/tsan/tls_race.c
index 4dd6506..fd306f2 100644
--- a/gcc/testsuite/c-c++-common/tsan/tls_race.c
+++ b/gcc/testsuite/c-c++-common/tsan/tls_race.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -16,7 +17,7 @@  int main() {
   barrier_init(&barrier, 2);
   static __thread int Var = 42;
   pthread_t t;
-  pthread_create(&t, 0, Thread, &Var);
+  PTHREAD_CREATE(&t, 0, Thread, &Var);
   Var = 43;
   barrier_wait(&barrier);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/c-c++-common/tsan/write_in_reader_lock.c b/gcc/testsuite/c-c++-common/tsan/write_in_reader_lock.c
index df32632..cff1761 100644
--- a/gcc/testsuite/c-c++-common/tsan/write_in_reader_lock.c
+++ b/gcc/testsuite/c-c++-common/tsan/write_in_reader_lock.c
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -23,7 +24,7 @@  int main(int argc, char *argv[]) {
   pthread_rwlock_init(&rwlock, NULL);
   pthread_rwlock_rdlock(&rwlock);
   pthread_t t;
-  pthread_create(&t, 0, Thread1, 0);
+  PTHREAD_CREATE(&t, 0, Thread1, 0);
   volatile int x = GLOB;
  (void)x;
   pthread_rwlock_unlock(&rwlock);
diff --git a/gcc/testsuite/g++.dg/tsan/aligned_vs_unaligned_race.C b/gcc/testsuite/g++.dg/tsan/aligned_vs_unaligned_race.C
index 1facadc..9d6fd63 100644
--- a/gcc/testsuite/g++.dg/tsan/aligned_vs_unaligned_race.C
+++ b/gcc/testsuite/g++.dg/tsan/aligned_vs_unaligned_race.C
@@ -4,6 +4,7 @@ 
 #include <pthread.h>
 #include <stdio.h>
 #include <stdint.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -27,8 +28,8 @@  void *Thread2(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   printf("Pass\n");
diff --git a/gcc/testsuite/g++.dg/tsan/atomic_free.C b/gcc/testsuite/g++.dg/tsan/atomic_free.C
index 20429f1..93c5c59 100644
--- a/gcc/testsuite/g++.dg/tsan/atomic_free.C
+++ b/gcc/testsuite/g++.dg/tsan/atomic_free.C
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -16,7 +17,7 @@  int main() {
   barrier_init(&barrier, 2);
   int *a = new int(0);
   pthread_t t;
-  pthread_create(&t, 0, Thread, a);
+  PTHREAD_CREATE(&t, 0, Thread, a);
   barrier_wait(&barrier);
   delete a;
   pthread_join(t, 0);
diff --git a/gcc/testsuite/g++.dg/tsan/atomic_free2.C b/gcc/testsuite/g++.dg/tsan/atomic_free2.C
index 3b6a8e3..b1f1fe7 100644
--- a/gcc/testsuite/g++.dg/tsan/atomic_free2.C
+++ b/gcc/testsuite/g++.dg/tsan/atomic_free2.C
@@ -2,6 +2,7 @@ 
 /* { dg-additional-options "-ldl" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -16,7 +17,7 @@  int main() {
   barrier_init(&barrier, 2);
   int *a = new int(0);
   pthread_t t;
-  pthread_create(&t, 0, Thread, a);
+  PTHREAD_CREATE(&t, 0, Thread, a);
   delete a;
   barrier_wait(&barrier);
   pthread_join(t, 0);
diff --git a/gcc/testsuite/g++.dg/tsan/benign_race.C b/gcc/testsuite/g++.dg/tsan/benign_race.C
index b5f1720..295b41a 100644
--- a/gcc/testsuite/g++.dg/tsan/benign_race.C
+++ b/gcc/testsuite/g++.dg/tsan/benign_race.C
@@ -1,6 +1,7 @@ 
 #include <pthread.h>
 #include <stdio.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 
 int Global;
 int WTFGlobal;
@@ -27,7 +28,7 @@  int main() {
                              &WTFGlobal, sizeof(WTFGlobal),
                              "Race on WTFGlobal");
   pthread_t t;
-  pthread_create(&t, 0, Thread, 0);
+  PTHREAD_CREATE(&t, 0, Thread, 0);
   sleep(1);
   Global = 43;
   WTFGlobal = 143;
diff --git a/gcc/testsuite/g++.dg/tsan/cond_race.C b/gcc/testsuite/g++.dg/tsan/cond_race.C
index d72d0fb..2fa9d27 100644
--- a/gcc/testsuite/g++.dg/tsan/cond_race.C
+++ b/gcc/testsuite/g++.dg/tsan/cond_race.C
@@ -4,6 +4,7 @@ 
 /* { dg-output "pthread_cond_signal.*" } */
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -30,7 +31,7 @@  int main() {
   pthread_mutex_init(&c->m, 0);
   pthread_cond_init(&c->c, 0);
   pthread_t th;
-  pthread_create(&th, 0, thr, c);
+  PTHREAD_CREATE(&th, 0, thr, c);
   pthread_mutex_lock(&c->m);
   while (!c->done)
     pthread_cond_wait(&c->c, &c->m);
diff --git a/gcc/testsuite/g++.dg/tsan/default_options.C b/gcc/testsuite/g++.dg/tsan/default_options.C
index 13e1984..35e113c 100644
--- a/gcc/testsuite/g++.dg/tsan/default_options.C
+++ b/gcc/testsuite/g++.dg/tsan/default_options.C
@@ -1,5 +1,6 @@ 
 #include <pthread.h>
 #include <stdio.h>
+#include "pthread_safe.h"
 
 extern "C" const char *__tsan_default_options() {
   return "report_bugs=0";
@@ -19,8 +20,8 @@  void *Thread2(void *x) {
 
 int main() {
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   fprintf(stderr, "DONE\n");
diff --git a/gcc/testsuite/g++.dg/tsan/fd_close_norace.C b/gcc/testsuite/g++.dg/tsan/fd_close_norace.C
index 9babb6a..08c4c0a 100644
--- a/gcc/testsuite/g++.dg/tsan/fd_close_norace.C
+++ b/gcc/testsuite/g++.dg/tsan/fd_close_norace.C
@@ -4,6 +4,7 @@ 
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <fcntl.h>
+#include "pthread_safe.h"
 
 void *Thread1(void *x) {
   int f = open("/dev/random", O_RDONLY);
@@ -20,8 +21,8 @@  void *Thread2(void *x) {
 
 int main() {
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   printf("OK\n");
diff --git a/gcc/testsuite/g++.dg/tsan/fd_close_norace2.C b/gcc/testsuite/g++.dg/tsan/fd_close_norace2.C
index 56f00f8..103e6ec 100644
--- a/gcc/testsuite/g++.dg/tsan/fd_close_norace2.C
+++ b/gcc/testsuite/g++.dg/tsan/fd_close_norace2.C
@@ -1,6 +1,7 @@ 
 #include <pthread.h>
 #include <stdio.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 
 int pipes[2];
 
@@ -17,7 +18,7 @@  int main() {
   if (pipe(pipes))
     return 1;
   pthread_t t;
-  pthread_create(&t, 0, Thread, 0);
+  PTHREAD_CREATE(&t, 0, Thread, 0);
   // send shutdown signal
   while (write(pipes[1], &t, 1) != 1) {
   }
diff --git a/gcc/testsuite/g++.dg/tsan/pr64265.C b/gcc/testsuite/g++.dg/tsan/pr64265.C
index fde32e7..9a08246 100644
--- a/gcc/testsuite/g++.dg/tsan/pr64265.C
+++ b/gcc/testsuite/g++.dg/tsan/pr64265.C
@@ -3,6 +3,7 @@ 
 // { dg-additional-options "-fno-omit-frame-pointer -ldl" }
 
 #include <pthread.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -43,8 +44,7 @@  main ()
 {
   pthread_t th;
   barrier_init (&barrier, 2);
-  if (pthread_create (&th, NULL, tf, NULL))
-    return 0;
+  PTHREAD_CREATE (&th, NULL, tf, NULL);
   v++;
   barrier_wait (&barrier);
   pthread_join (th, NULL);
diff --git a/gcc/testsuite/g++.dg/tsan/pthread_safe.h b/gcc/testsuite/g++.dg/tsan/pthread_safe.h
new file mode 100644
index 0000000..07d273a
--- /dev/null
+++ b/gcc/testsuite/g++.dg/tsan/pthread_safe.h
@@ -0,0 +1,12 @@ 
+#include <error.h>
+#include <stdlib.h>
+
+#define PTHREAD_CREATE(thread, attr, start_routine, arg)		\
+  {									\
+    int res = pthread_create (thread, attr, start_routine, arg);	\
+    if (res)								\
+      {									\
+	error (0, res, "pthread_create failed with");			\
+	exit (0);							\
+      }									\
+  }
diff --git a/gcc/testsuite/g++.dg/tsan/vptr_benign_race.C b/gcc/testsuite/g++.dg/tsan/vptr_benign_race.C
index 283684b..2cf0301 100644
--- a/gcc/testsuite/g++.dg/tsan/vptr_benign_race.C
+++ b/gcc/testsuite/g++.dg/tsan/vptr_benign_race.C
@@ -1,6 +1,7 @@ 
 #include <pthread.h>
 #include <semaphore.h>
 #include <stdio.h>
+#include "pthread_safe.h"
 
 struct A {
   A() {
@@ -40,8 +41,8 @@  void *Thread2(void *x) {
 
 int main() {
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
   fprintf(stderr, "PASS\n");
diff --git a/gcc/testsuite/g++.dg/tsan/vptr_harmful_race.C b/gcc/testsuite/g++.dg/tsan/vptr_harmful_race.C
index 1473f93..c43b51f 100644
--- a/gcc/testsuite/g++.dg/tsan/vptr_harmful_race.C
+++ b/gcc/testsuite/g++.dg/tsan/vptr_harmful_race.C
@@ -5,6 +5,7 @@ 
 #include <semaphore.h>
 #include <stdio.h>
 #include <unistd.h>
+#include "pthread_safe.h"
 #include "tsan_barrier.h"
 
 static pthread_barrier_t barrier;
@@ -49,8 +50,8 @@  void *Thread2(void *x) {
 int main() {
   barrier_init(&barrier, 2);
   pthread_t t[2];
-  pthread_create(&t[0], NULL, Thread1, NULL);
-  pthread_create(&t[1], NULL, Thread2, NULL);
+  PTHREAD_CREATE(&t[0], NULL, Thread1, NULL);
+  PTHREAD_CREATE(&t[1], NULL, Thread2, NULL);
   pthread_join(t[0], NULL);
   pthread_join(t[1], NULL);
 }