xref: /llvm-project/clang/test/CXX/basic/basic.def.odr/p2.cpp (revision 24cdcadcc5e875b05bbb70eb123ea4f0a018ee83)
1*24cdcadcSRichard Smith // RUN: %clang_cc1 -std=c++98 %s -Wno-unused -verify
2*24cdcadcSRichard Smith // RUN: %clang_cc1 -std=c++11 %s -Wno-unused -verify
3*24cdcadcSRichard Smith // RUN: %clang_cc1 -std=c++2a %s -Wno-unused -verify
4*24cdcadcSRichard Smith 
5*24cdcadcSRichard Smith void use(int);
6*24cdcadcSRichard Smith 
f()7*24cdcadcSRichard Smith void f() {
8*24cdcadcSRichard Smith   const int a = 1; // expected-note {{here}}
9*24cdcadcSRichard Smith 
10*24cdcadcSRichard Smith #if __cplusplus >= 201103L
11*24cdcadcSRichard Smith   constexpr int arr[3] = {1, 2, 3}; // expected-note 2{{here}}
12*24cdcadcSRichard Smith 
13*24cdcadcSRichard Smith   struct S { int x; int f() const; };
14*24cdcadcSRichard Smith   constexpr S s = {0}; // expected-note 3{{here}}
15*24cdcadcSRichard Smith   constexpr S *ps = nullptr;
16*24cdcadcSRichard Smith   S *const &psr = ps; // expected-note 2{{here}}
17*24cdcadcSRichard Smith #endif
18*24cdcadcSRichard Smith 
19*24cdcadcSRichard Smith   struct Inner {
20*24cdcadcSRichard Smith     void test(int i) {
21*24cdcadcSRichard Smith       // id-expression
22*24cdcadcSRichard Smith       use(a);
23*24cdcadcSRichard Smith 
24*24cdcadcSRichard Smith #if __cplusplus >= 201103L
25*24cdcadcSRichard Smith       // subscripting operation with an array operand
26*24cdcadcSRichard Smith       use(arr[i]);
27*24cdcadcSRichard Smith       use(i[arr]);
28*24cdcadcSRichard Smith       use((+arr)[i]); // expected-error {{reference to local variable}}
29*24cdcadcSRichard Smith       use(i[+arr]); // expected-error {{reference to local variable}}
30*24cdcadcSRichard Smith 
31*24cdcadcSRichard Smith       // class member access naming non-static data member
32*24cdcadcSRichard Smith       use(s.x);
33*24cdcadcSRichard Smith       use(s.f()); // expected-error {{reference to local variable}}
34*24cdcadcSRichard Smith       use((&s)->x); // expected-error {{reference to local variable}}
35*24cdcadcSRichard Smith       use(ps->x); // ok (lvalue-to-rvalue conversion applied to id-expression)
36*24cdcadcSRichard Smith       use(psr->x); // expected-error {{reference to local variable}}
37*24cdcadcSRichard Smith 
38*24cdcadcSRichard Smith       // class member access naming a static data member
39*24cdcadcSRichard Smith       // FIXME: How to test this?
40*24cdcadcSRichard Smith 
41*24cdcadcSRichard Smith       // pointer-to-member expression
42*24cdcadcSRichard Smith       use(s.*&S::x);
43*24cdcadcSRichard Smith       use((s.*&S::f)()); // expected-error {{reference to local variable}}
44*24cdcadcSRichard Smith       use(ps->*&S::x); // ok (lvalue-to-rvalue conversion applied to id-expression)
45*24cdcadcSRichard Smith       use(psr->*&S::x); // expected-error {{reference to local variable}}
46*24cdcadcSRichard Smith #endif
47*24cdcadcSRichard Smith 
48*24cdcadcSRichard Smith       // parentheses
49*24cdcadcSRichard Smith       use((a));
50*24cdcadcSRichard Smith #if __cplusplus >= 201103L
51*24cdcadcSRichard Smith       use((s.x));
52*24cdcadcSRichard Smith #endif
53*24cdcadcSRichard Smith 
54*24cdcadcSRichard Smith       // glvalue conditional expression
55*24cdcadcSRichard Smith       use(i ? a : a);
56*24cdcadcSRichard Smith       use(i ? i : a);
57*24cdcadcSRichard Smith 
58*24cdcadcSRichard Smith       // comma expression
59*24cdcadcSRichard Smith       use((i, a));
60*24cdcadcSRichard Smith       // FIXME: This is not an odr-use because it is a discarded-value
61*24cdcadcSRichard Smith       // expression applied to an expression whose potential result is 'a'.
62*24cdcadcSRichard Smith       use((a, a)); // expected-error {{reference to local variable}}
63*24cdcadcSRichard Smith 
64*24cdcadcSRichard Smith       // (and combinations thereof)
65*24cdcadcSRichard Smith       use(a ? (i, a) : a);
66*24cdcadcSRichard Smith #if __cplusplus >= 201103L
67*24cdcadcSRichard Smith       use(a ? (i, a) : arr[a ? s.x : arr[a]]);
68*24cdcadcSRichard Smith #endif
69*24cdcadcSRichard Smith     }
70*24cdcadcSRichard Smith   };
71*24cdcadcSRichard Smith }
72*24cdcadcSRichard Smith 
73*24cdcadcSRichard Smith // FIXME: Test that this behaves properly.
74*24cdcadcSRichard Smith namespace std_example {
75*24cdcadcSRichard Smith   struct S { static const int x = 0, y = 0; };
76*24cdcadcSRichard Smith   const int &f(const int &r);
77*24cdcadcSRichard Smith   bool b;
78*24cdcadcSRichard Smith   int n = b ? (1, S::x)
79*24cdcadcSRichard Smith             : f(S::y);
80*24cdcadcSRichard Smith }
81