1 // P0145R2: Refining Expression Order for C++
2 // { dg-do run { target c++17 } }
3
4 extern "C" int printf (const char *, ...);
sink(...)5 void sink(...) { }
6
7 int last = 0;
f(int i)8 int f(int i)
9 {
10 if (i < last)
11 __builtin_abort ();
12 last = i;
13 return i;
14 }
15
g(int i)16 int& g(int i)
17 {
18 static int dummy;
19 f(i);
20 return dummy;
21 }
22
23 struct A
24 {
25 int _i;
AA26 A(int i): _i(f(i)) { }
memfnA27 A& memfn(int i, int j) { f(j); return *this; }
28 int operator<<(int i) { return 0; }
29 A& operator=(const A&) { return *this; }
30 A& operator+=(int i) { return *this; }
31 };
32
33 struct B
34 {
35 int _i;
BB36 B(): _i(0) {}
BB37 B(int i): _i(f(i)) { }
38 };
39
40 int operator>>(A&, int i) { return 0; }
41
42 A a(0);
afn(int i)43 A* afn(int i)
44 {
45 f(i);
46 return &a;
47 }
48
aref(int i)49 A& aref(int i)
50 {
51 f(i);
52 return a;
53 }
54
55 B b;
bval(int i)56 B bval(int i)
57 {
58 return B(i);
59 }
60
bref(int i)61 B& bref(int i)
62 {
63 f(i);
64 return b;
65 }
66
67 static int si;
ip(int i)68 int* ip (int i)
69 {
70 f(i);
71 return &si;
72 }
73
iref(int i)74 int& iref(int i)
75 {
76 f(i);
77 return si;
78 }
79
pmff(int i)80 auto pmff(int i) {
81 f(i);
82 return &A::memfn;
83 }
84
f()85 template <class T> void f()
86 {
87 // a.b
88 A(1).memfn(f(2),3).memfn(f(4),5);
89 aref(6).memfn(f(7),8);
90 (aref(9).*pmff(10))(f(11),12);
91 last = 0;
92
93 // a->b
94 afn(12)->memfn(f(13),14);
95
96 // a->*b
97 (afn(15)->*pmff(16))(f(17),18);
98 last = 0;
99
100 // a(b)
101 // covered in eval-order1.C
102
103 // b @= a
104 aref(19)=A(18);
105 iref(21)=f(20);
106 aref(23)+=f(22);
107 bref(25)=bval(24);
108 (f(27), b) = bval(26);
109 last = 0;
110
111 int ar[4] = {};
112 int i = 0;
113 ar[i++] = i;
114 if (ar[0] != 0)
115 __builtin_abort();
116
117 // a[b]
118 afn(20)[f(21)-21].memfn(f(22),23);
119 ip(24)[f(25)-25] = 0;
120 last=0;
121
122 // a << b
123 aref(24) << f(25);
124 iref(26) << f(27);
125 last=0;
126
127 // a >> b
128 aref(26) >> f(27);
129 iref(28) >> f(29);
130 }
131
g()132 void g()
133 {
134 // a.b
135 A(1).memfn(f(2),3).memfn(f(4),5);
136 aref(6).memfn(f(7),8);
137 (aref(9).*pmff(10))(f(11),12);
138 last = 0;
139
140 // a->b
141 afn(12)->memfn(f(13),14);
142
143 // a->*b
144 (afn(15)->*pmff(16))(f(17),18);
145 last = 0;
146
147 // a(b)
148 // covered in eval-order1.C
149
150 // b @= a
151 aref(19)=A(18);
152 iref(21)=f(20);
153 aref(23)+=f(22);
154 bref(25)=bval(24);
155 (f(27), b) = bval(26);
156 last = 0;
157
158 int ar[4] = {};
159 int i = 0;
160 ar[i++] = i;
161 if (ar[0] != 0)
162 __builtin_abort();
163
164 // a[b]
165 afn(20)[f(21)-21].memfn(f(22),23);
166 ip(24)[f(25)-25] = 0;
167 last=0;
168
169 // a << b
170 aref(24) << f(25);
171 iref(26) << f(27);
172 last=0;
173
174 // a >> b
175 aref(26) >> f(27);
176 iref(28) >> f(29);
177 }
178
main()179 int main()
180 {
181 g();
182 last = 0;
183 f<int>();
184 }
185