1bd909d2eSerichkeane // RUN: %clang_cc1 %s -fopenacc -verify
2bd909d2eSerichkeane
3bd909d2eSerichkeane enum SomeE{};
4bd909d2eSerichkeane typedef struct IsComplete {
5bd909d2eSerichkeane struct S { int A; } CompositeMember;
6bd909d2eSerichkeane int ScalarMember;
7bd909d2eSerichkeane float ArrayMember[5];
8bd909d2eSerichkeane SomeE EnumMember;
9bd909d2eSerichkeane char *PointerMember;
10bd909d2eSerichkeane } Complete;
11bd909d2eSerichkeane
uses(int IntParam,char * PointerParam,float ArrayParam[5],Complete CompositeParam,int & IntParamRef)12bd909d2eSerichkeane void uses(int IntParam, char *PointerParam, float ArrayParam[5], Complete CompositeParam, int &IntParamRef) {
13bd909d2eSerichkeane int LocalInt;
14bd909d2eSerichkeane char *LocalPointer;
15bd909d2eSerichkeane float LocalArray[5];
16bd909d2eSerichkeane // Check Appertainment:
17bd909d2eSerichkeane #pragma acc parallel present(LocalInt)
18bd909d2eSerichkeane while(1);
19bd909d2eSerichkeane #pragma acc serial present(LocalInt)
20bd909d2eSerichkeane while(1);
21bd909d2eSerichkeane #pragma acc kernels present(LocalInt)
22bd909d2eSerichkeane while(1);
23bd909d2eSerichkeane
24bd909d2eSerichkeane // Valid cases:
25bd909d2eSerichkeane #pragma acc parallel present(LocalInt, LocalPointer, LocalArray)
26bd909d2eSerichkeane while(1);
27bd909d2eSerichkeane #pragma acc parallel present(LocalArray[2:1])
28bd909d2eSerichkeane while(1);
29bd909d2eSerichkeane
30bd909d2eSerichkeane Complete LocalComposite2;
31bd909d2eSerichkeane #pragma acc parallel present(LocalComposite2.ScalarMember, LocalComposite2.ScalarMember)
32bd909d2eSerichkeane while(1);
33bd909d2eSerichkeane
34*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
35bd909d2eSerichkeane #pragma acc parallel present(1 + IntParam)
36bd909d2eSerichkeane while(1);
37bd909d2eSerichkeane
38*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
39bd909d2eSerichkeane #pragma acc parallel present(+IntParam)
40bd909d2eSerichkeane while(1);
41bd909d2eSerichkeane
42bd909d2eSerichkeane // expected-error@+1{{OpenACC sub-array length is unspecified and cannot be inferred because the subscripted value is not an array}}
43bd909d2eSerichkeane #pragma acc parallel present(PointerParam[2:])
44bd909d2eSerichkeane while(1);
45bd909d2eSerichkeane
46bd909d2eSerichkeane // expected-error@+1{{OpenACC sub-array specified range [2:5] would be out of the range of the subscripted array size of 5}}
47bd909d2eSerichkeane #pragma acc parallel present(ArrayParam[2:5])
48bd909d2eSerichkeane while(1);
49bd909d2eSerichkeane
50bd909d2eSerichkeane // expected-error@+2{{OpenACC sub-array specified range [2:5] would be out of the range of the subscripted array size of 5}}
51*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
52bd909d2eSerichkeane #pragma acc parallel present((float*)ArrayParam[2:5])
53bd909d2eSerichkeane while(1);
54*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
55bd909d2eSerichkeane #pragma acc parallel present((float)ArrayParam[2])
56bd909d2eSerichkeane while(1);
57bd909d2eSerichkeane }
58bd909d2eSerichkeane
59bd909d2eSerichkeane template<typename T, unsigned I, typename V>
TemplUses(T t,T (& arrayT)[I],V TemplComp)60bd909d2eSerichkeane void TemplUses(T t, T (&arrayT)[I], V TemplComp) {
61*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
62bd909d2eSerichkeane #pragma acc parallel present(+t)
63bd909d2eSerichkeane while(true);
64bd909d2eSerichkeane
65bd909d2eSerichkeane // NTTP's are only valid if it is a reference to something.
66*a15b685cSErich Keane // expected-error@+2{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
67bd909d2eSerichkeane // expected-note@#TEMPL_USES_INST{{in instantiation of}}
68bd909d2eSerichkeane #pragma acc parallel present(I)
69bd909d2eSerichkeane while(true);
70bd909d2eSerichkeane
71*a15b685cSErich Keane // expected-error@+1{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
72bd909d2eSerichkeane #pragma acc parallel present(t, I)
73bd909d2eSerichkeane while(true);
74bd909d2eSerichkeane
75bd909d2eSerichkeane #pragma acc parallel present(arrayT)
76bd909d2eSerichkeane while(true);
77bd909d2eSerichkeane
78bd909d2eSerichkeane #pragma acc parallel present(TemplComp)
79bd909d2eSerichkeane while(true);
80bd909d2eSerichkeane
81bd909d2eSerichkeane #pragma acc parallel present(TemplComp.PointerMember[5])
82bd909d2eSerichkeane while(true);
83bd909d2eSerichkeane int *Pointer;
84bd909d2eSerichkeane #pragma acc parallel present(Pointer[:I])
85bd909d2eSerichkeane while(true);
86bd909d2eSerichkeane #pragma acc parallel present(Pointer[:t])
87bd909d2eSerichkeane while(true);
88bd909d2eSerichkeane // expected-error@+1{{OpenACC sub-array length is unspecified and cannot be inferred because the subscripted value is not an array}}
89bd909d2eSerichkeane #pragma acc parallel present(Pointer[1:])
90bd909d2eSerichkeane while(true);
91bd909d2eSerichkeane }
92bd909d2eSerichkeane
93bd909d2eSerichkeane template<unsigned I, auto &NTTP_REF>
NTTP()94bd909d2eSerichkeane void NTTP() {
95bd909d2eSerichkeane // NTTP's are only valid if it is a reference to something.
96*a15b685cSErich Keane // expected-error@+2{{OpenACC variable is not a valid variable name, sub-array, array element, member of a composite variable, or composite variable member}}
97bd909d2eSerichkeane // expected-note@#NTTP_INST{{in instantiation of}}
98bd909d2eSerichkeane #pragma acc parallel present(I)
99bd909d2eSerichkeane while(true);
100bd909d2eSerichkeane
101bd909d2eSerichkeane #pragma acc parallel present(NTTP_REF)
102bd909d2eSerichkeane while(true);
103bd909d2eSerichkeane }
104bd909d2eSerichkeane
Inst()105bd909d2eSerichkeane void Inst() {
106bd909d2eSerichkeane static constexpr int NTTP_REFed = 1;
107bd909d2eSerichkeane int i;
108bd909d2eSerichkeane int Arr[5];
109bd909d2eSerichkeane Complete C;
110bd909d2eSerichkeane TemplUses(i, Arr, C); // #TEMPL_USES_INST
111bd909d2eSerichkeane NTTP<5, NTTP_REFed>(); // #NTTP_INST
112bd909d2eSerichkeane }
113