1  /* Test C2x storage class specifiers in compound literals.  Thread-local
       2     cases, execution tests.  */
       3  /* { dg-do run } */
       4  /* { dg-options "-pthread -std=gnu2x -pedantic-errors" } */
       5  /* { dg-require-effective-target pthread_h } */
       6  /* { dg-require-effective-target pthread } */
       7  /* { dg-require-effective-target tls_runtime } */
       8  /* { dg-add-options tls } */
       9  
      10  #include <pthread.h>
      11  
      12  extern void abort (void);
      13  extern void exit (int);
      14  
      15  int *
      16  thread_addr ()
      17  {
      18    return (static thread_local int []) { 1, 2 };
      19  }
      20  
      21  int *volatile p, *volatile q, r;
      22  
      23  void *
      24  thread_fn (void *)
      25  {
      26    q = thread_addr ();
      27    if (q[0] != 1 || q[1] != 2)
      28      return NULL;
      29    q[0] = 5;
      30    q[1] = 6;
      31    return &r;
      32  }
      33  
      34  int
      35  main ()
      36  {
      37    int i;
      38    pthread_t tid;
      39    void *ret;
      40    p = thread_addr ();
      41    if (p[0] != 1 || p[1] != 2)
      42      abort ();
      43    p[0] = 3;
      44    p[1] = 4;
      45    if (p != thread_addr ())
      46      abort ();
      47    i = pthread_create (&tid, NULL, thread_fn, NULL);
      48    if (p != thread_addr ())
      49      abort ();
      50    i = pthread_join (tid, &ret);
      51    if (i != 0)
      52      abort ();
      53    if (ret != &r)
      54      abort ();
      55    if (p != thread_addr ())
      56      abort ();
      57    if (p[0] != 3 || p[1] != 4)
      58      abort ();
      59    exit (0);
      60  }