Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 1 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic %s -DGNU |
| 2 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic -x c++ %s -DGNU |
| 3 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic %s -DC11 -D__thread=_Thread_local |
| 4 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic -x c++ %s -DC11 -D__thread=_Thread_local |
| 5 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic -x c++ %s -DCXX11 -D__thread=thread_local -std=c++11 |
Richard Smith | 6a570f6 | 2013-04-14 20:11:31 +0000 | [diff] [blame] | 6 | // RUN: %clang_cc1 -triple i686-pc-linux-gnu -fsyntax-only -Wno-private-extern -verify -pedantic -x c++ %s -DC11 -D__thread=_Thread_local -std=c++11 |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 7 | |
| 8 | #ifdef __cplusplus |
| 9 | // In C++, we define __private_extern__ to extern. |
| 10 | #undef __private_extern__ |
| 11 | #endif |
Eli Friedman | f22f77f | 2009-04-19 20:29:08 +0000 | [diff] [blame] | 12 | |
| 13 | __thread int t1; |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 14 | __thread extern int t2; |
| 15 | __thread static int t3; |
| 16 | #ifdef GNU |
| 17 | // expected-warning@-3 {{'__thread' before 'extern'}} |
| 18 | // expected-warning@-3 {{'__thread' before 'static'}} |
| 19 | #endif |
Hans Wennborg | 3af16fd | 2012-06-04 10:19:34 +0000 | [diff] [blame] | 20 | |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 21 | __thread __private_extern__ int t4; |
| 22 | struct t5 { __thread int x; }; |
| 23 | #ifdef __cplusplus |
| 24 | // expected-error-re@-2 {{'(__thread|_Thread_local|thread_local)' is only allowed on variable declarations}} |
| 25 | #else |
| 26 | // FIXME: The 'is only allowed on variable declarations' diagnostic is better here. |
| 27 | // expected-error@-5 {{type name does not allow storage class to be specified}} |
| 28 | #endif |
| 29 | |
| 30 | __thread int t6(); |
| 31 | #if defined(GNU) |
| 32 | // expected-error@-2 {{'__thread' is only allowed on variable declarations}} |
| 33 | #elif defined(C11) |
| 34 | // expected-error@-4 {{'_Thread_local' is only allowed on variable declarations}} |
| 35 | #else |
| 36 | // expected-error@-6 {{'thread_local' is only allowed on variable declarations}} |
| 37 | #endif |
| 38 | |
| 39 | int f(__thread int t7) { // expected-error {{' is only allowed on variable declarations}} |
| 40 | __thread int t8; |
| 41 | #if defined(GNU) |
| 42 | // expected-error@-2 {{'__thread' variables must have global storage}} |
| 43 | #elif defined(C11) |
| 44 | // expected-error@-4 {{'_Thread_local' variables must have global storage}} |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 45 | #endif |
Hans Wennborg | 3af16fd | 2012-06-04 10:19:34 +0000 | [diff] [blame] | 46 | extern __thread int t9; |
| 47 | static __thread int t10; |
Eli Friedman | f22f77f | 2009-04-19 20:29:08 +0000 | [diff] [blame] | 48 | __thread __private_extern__ int t11; |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 49 | #if __cplusplus < 201103L |
| 50 | __thread auto int t12a; // expected-error-re {{cannot combine with previous '(__thread|_Thread_local)' declaration specifier}} |
| 51 | auto __thread int t12b; // expected-error {{cannot combine with previous 'auto' declaration specifier}} |
Richard Smith | df4cc0a | 2013-04-15 08:33:22 +0000 | [diff] [blame^] | 52 | #elif !defined(CXX11) |
| 53 | __thread auto t12a = 0; // expected-error-re {{'_Thread_local' variables must have global storage}} |
| 54 | auto __thread t12b = 0; // expected-error-re {{'_Thread_local' variables must have global storage}} |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 55 | #endif |
| 56 | __thread register int t13a; // expected-error-re {{cannot combine with previous '(__thread|_Thread_local|thread_local)' declaration specifier}} |
| 57 | register __thread int t13b; // expected-error {{cannot combine with previous 'register' declaration specifier}} |
Eli Friedman | f22f77f | 2009-04-19 20:29:08 +0000 | [diff] [blame] | 58 | } |
Hans Wennborg | 3af16fd | 2012-06-04 10:19:34 +0000 | [diff] [blame] | 59 | |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 60 | __thread typedef int t14; // expected-error-re {{cannot combine with previous '(__thread|_Thread_local|thread_local)' declaration specifier}} |
Richard Smith | 38afbc7 | 2013-04-13 02:43:54 +0000 | [diff] [blame] | 61 | __thread int t15; // expected-note {{previous declaration is here}} |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 62 | extern int t15; // expected-error {{non-thread-local declaration of 't15' follows thread-local declaration}} |
Richard Smith | 38afbc7 | 2013-04-13 02:43:54 +0000 | [diff] [blame] | 63 | extern int t16; // expected-note {{previous declaration is here}} |
Eli Friedman | f22f77f | 2009-04-19 20:29:08 +0000 | [diff] [blame] | 64 | __thread int t16; // expected-error {{thread-local declaration of 't16' follows non-thread-local declaration}} |
Hans Wennborg | 0f87dd7 | 2012-08-29 09:04:10 +0000 | [diff] [blame] | 65 | |
Richard Smith | 38afbc7 | 2013-04-13 02:43:54 +0000 | [diff] [blame] | 66 | #ifdef CXX11 |
| 67 | extern thread_local int t17; // expected-note {{previous declaration is here}} |
| 68 | _Thread_local int t17; // expected-error {{thread-local declaration of 't17' with static initialization follows declaration with dynamic initialization}} |
| 69 | extern _Thread_local int t18; // expected-note {{previous declaration is here}} |
| 70 | thread_local int t18; // expected-error {{thread-local declaration of 't18' with dynamic initialization follows declaration with static initialization}} |
| 71 | #endif |
| 72 | |
Hans Wennborg | 0f87dd7 | 2012-08-29 09:04:10 +0000 | [diff] [blame] | 73 | // PR13720 |
| 74 | __thread int thread_int; |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 75 | int *thread_int_ptr = &thread_int; |
| 76 | #ifndef __cplusplus |
| 77 | // expected-error@-2 {{initializer element is not a compile-time constant}} |
| 78 | #endif |
Hans Wennborg | 0f87dd7 | 2012-08-29 09:04:10 +0000 | [diff] [blame] | 79 | void g() { |
| 80 | int *p = &thread_int; // This is perfectly fine, though. |
| 81 | } |
Richard Smith | ec64244 | 2013-04-12 22:46:28 +0000 | [diff] [blame] | 82 | #if __cplusplus >= 201103L |
| 83 | constexpr int *thread_int_ptr_2 = &thread_int; // expected-error {{must be initialized by a constant expression}} |
| 84 | #endif |
Richard Smith | 6a570f6 | 2013-04-14 20:11:31 +0000 | [diff] [blame] | 85 | |
| 86 | int non_const(); |
| 87 | __thread int non_const_init = non_const(); |
| 88 | #if !defined(__cplusplus) |
| 89 | // expected-error@-2 {{initializer element is not a compile-time constant}} |
| 90 | #elif !defined(CXX11) |
| 91 | // expected-error@-4 {{initializer for thread-local variable must be a constant expression}} |
| 92 | #if __cplusplus >= 201103L |
| 93 | // expected-note@-6 {{use 'thread_local' to allow this}} |
| 94 | #endif |
| 95 | #endif |
| 96 | |
| 97 | #ifdef __cplusplus |
| 98 | struct S { |
| 99 | ~S(); |
| 100 | }; |
| 101 | __thread S s; |
| 102 | #if !defined(CXX11) |
| 103 | // expected-error@-2 {{type of thread-local variable has non-trivial destruction}} |
| 104 | #if __cplusplus >= 201103L |
| 105 | // expected-note@-4 {{use 'thread_local' to allow this}} |
| 106 | #endif |
| 107 | #endif |
| 108 | #endif |
Richard Smith | b6b127f | 2013-04-15 08:07:34 +0000 | [diff] [blame] | 109 | |
| 110 | __thread int aggregate[10] = {0}; |