| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171 | #include <pthreadP.h>#include <signal.h>#include <stdio.h>#include <stdlib.h>static pthread_barrier_t b;static pthread_t th2;static void *tf2 (void *arg){  sigset_t mask;  if (pthread_sigmask (SIG_SETMASK, NULL, &mask) != 0)    {      puts ("pthread_sigmask failed");      exit (1);    }  if (sigismember (&mask, SIGCANCEL))    {      puts ("SIGCANCEL blocked in new thread");      exit (1);    }  /* Sync with the main thread so that we do not test anything else.  */  int e = pthread_barrier_wait (&b);  if (e != 0  && e != PTHREAD_BARRIER_SERIAL_THREAD)    {      puts ("barrier_wait failed");      exit (1);    }  while (1)    {      /* Just a cancelable call.  */      struct timespec ts = { 10000, 0 };      nanosleep (&ts, 0);    }  return NULL;}static voidunwhand (void *arg){  if (pthread_create (&th2, NULL, tf2, NULL) != 0)    {      puts ("unwhand: create failed");      exit (1);    }}static void *tf (void *arg){  pthread_cleanup_push (unwhand, NULL);  /* Sync with the main thread so that we do not test anything else.  */  int e = pthread_barrier_wait (&b);  if (e != 0  && e != PTHREAD_BARRIER_SERIAL_THREAD)    {      puts ("barrier_wait failed");      exit (1);    }  while (1)    {      /* Just a cancelable call.  */      struct timespec ts = { 10000, 0 };      nanosleep (&ts, 0);    }  pthread_cleanup_pop (0);  return NULL;}static intdo_test (void){  if (pthread_barrier_init (&b, NULL, 2) != 0)    {      puts ("barrier_init failed");      return 1;    }  pthread_t th1;  if (pthread_create (&th1, NULL, tf, NULL) != 0)    {      puts ("create failed");      return 1;    }  int e = pthread_barrier_wait (&b);  if (e != 0  && e != PTHREAD_BARRIER_SERIAL_THREAD)    {      puts ("barrier_wait failed");      return 1;    }  /* Make sure tf1 enters nanosleep.  */  struct timespec ts = { 0, 500000000 };  while (nanosleep (&ts, &ts) != 0)    ;  if (pthread_cancel (th1) != 0)    {      puts ("1st cancel failed");      return 1;    }  void *res;  if (pthread_join (th1, &res) != 0)    {      puts ("1st join failed");      return 1;    }  if (res != PTHREAD_CANCELED)    {      puts ("1st thread not canceled");      return 1;    }  e = pthread_barrier_wait (&b);  if (e != 0  && e != PTHREAD_BARRIER_SERIAL_THREAD)    {      puts ("barrier_wait failed");      return 1;    }  /* Make sure tf2 enters nanosleep.  */  ts.tv_sec = 0;  ts.tv_nsec = 500000000;  while (nanosleep (&ts, &ts) != 0)    ;  puts ("calling pthread_cancel the second time");  if (pthread_cancel (th2) != 0)    {      puts ("2nd cancel failed");      return 1;    }  puts ("calling pthread_join the second time");  if (pthread_join (th2, &res) != 0)    {      puts ("2nd join failed");      return 1;    }  if (res != PTHREAD_CANCELED)    {      puts ("2nd thread not canceled");      return 1;    }  if (pthread_barrier_destroy (&b) != 0)    {      puts ("barrier_destroy failed");      return 0;    }  return 0;}#define TEST_FUNCTION do_test ()#define TIMEOUT 4#include "../test-skeleton.c"
 |