analyzer: enable taint state machine by default [PR103533]
[official-gcc.git] / gcc / testsuite / c-c++-common / builtin-has-attribute-7.c
blob1326aed32a79ec2fd9ef62cffaf04cc2f4202f57
1 /* Verify that __builtin_has_attribute detects attributes aligned
2 and packed in various forms of array dereferencing and indirection
3 expressions correspondingly to __alignof__.
4 { dg-do compile }
5 { dg-options "-Wall -Wno-unused -ftrack-macro-expansion=0" }
6 { dg-require-effective-target size24plus } */
8 #define ATTR(...) __attribute__ ((__VA_ARGS__))
9 #define ALIGN(N) ATTR (aligned (N))
11 #define Assert(expr) typedef int _Assert [1 - 2 * !(expr)]
13 /* Verify that __builtin_has_attribute (EXPR, align (ALIGN)) returns
14 the EXPECTed result. When EXPECT is true, verify that the EXPression
15 has the expected ALIGNment. */
16 #define A3(expect, expr, align) do { \
17 Assert (!expect || __alignof__ (expr) == align); \
18 Assert (expect == __builtin_has_attribute (expr, aligned (align))); \
19 } while (0)
21 #define A(expect, expr) \
22 Assert (expect == __builtin_has_attribute (expr, aligned)) \
24 enum { PA = __alignof__ (void*) };
26 /* Define pointer to pointer types, with different alignments
27 at each level of indirection. */
28 typedef struct S8 { char a[8]; } S8;
29 typedef ALIGN (8) S8 I8;
30 typedef ALIGN (16) I8 *P16_I8;
31 typedef P16_I8 *P_P16_I8;
32 typedef ALIGN (32) P_P16_I8 *P32_P_P16_I8;
33 typedef P32_P_P16_I8 *P_P32_P_P16_I8;
34 typedef ALIGN (64) P_P32_P_P16_I8 *P64_P_P32_P_P16_I8;
36 Assert ( 8 == __alignof__ (I8));
37 Assert (16 == __alignof__ (P16_I8));
38 Assert (PA == __alignof__ (P_P16_I8));
39 Assert (32 == __alignof__ (P32_P_P16_I8));
40 Assert (PA == __alignof__ (P_P32_P_P16_I8));
41 Assert (64 == __alignof__ (P64_P_P32_P_P16_I8));
44 /* Similar to the pointer of pointers above, define array of array
45 types, with different alignments at each level of indirection. */
46 typedef struct S64 { char a[64]; } S64;
47 typedef ALIGN (64) S64 I64;
48 typedef ALIGN (32) I64 A32_I64[3];
49 typedef A32_I64 A_A32_I64[5];
50 typedef ALIGN (16) A_A32_I64 A16_A_A32_I64[7];
51 typedef A16_A_A32_I64 A_A16_A_A32_I64[11];
52 typedef ALIGN (8) A_A16_A_A32_I64 A8_A_A16_A_A32_I64[13];
54 Assert (64 == __alignof__ (I64));
55 Assert (32 == __alignof__ (A32_I64));
56 /* With no explicit alignment, an array of overaligned elements
57 is considered to have the alignment of its elements. */
58 Assert (32 == __alignof__ (A_A32_I64));
59 Assert (16 == __alignof__ (A16_A_A32_I64));
60 Assert (16 == __alignof__ (A_A16_A_A32_I64));
61 Assert ( 8 == __alignof__ (A8_A_A16_A_A32_I64));
64 void test_arrays (void)
66 /* Verify that the aligned attribute on each of the composite types
67 is detected corresponding to the result of __alignof__. */
68 A (1, (*(A8_A_A16_A_A32_I64*)0));
69 A3 (1, (*(A8_A_A16_A_A32_I64*)0), 8);
70 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0], 8);
71 /* GCC propagates the user-align bit from element types to their
72 arrays but it doesn't propagate the attribute itself. The built-in
73 considers both the bit and the attribute so it succeeds below even
74 though the referenced type isn't declared with the attribute. */
75 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0], 8);
76 A3 (1, (*(A8_A_A16_A_A32_I64*)0)[0], 16);
77 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0], 32);
78 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1], 8);
79 A3 (1, (*(A8_A_A16_A_A32_I64*)0)[0][1], 16);
80 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1], 32);
81 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2], 16);
82 A3 (1, (*(A8_A_A16_A_A32_I64*)0)[0][1][2], 32);
83 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2], 64);
84 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3], 16);
85 A3 (1, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3], 32);
86 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3], 64);
87 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3][4], 32);
88 A3 (1, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3][4], 64);
89 A3 (0, (*(A8_A_A16_A_A32_I64*)0)[0][1][2][3][4], 128);
91 A8_A_A16_A_A32_I64 a;
92 A3 (0, a[0], 8);
93 A3 (1, a[0], 16);
94 A3 (0, a[0], 32);
95 A3 (0, a[0][1], 8);
96 A3 (1, a[0][1], 16);
97 A3 (0, a[0][1], 32);
98 A3 (0, a[0][1][2], 16);
99 A3 (1, a[0][1][2], 32);
100 A3 (0, a[0][1][2], 64);
101 A3 (0, a[0][1][2][3], 16);
102 A3 (1, a[0][1][2][3], 32);
103 A3 (0, a[0][1][2][3], 64);
104 A3 (0, a[0][1][2][3][4], 32);
105 A3 (1, a[0][1][2][3][4], 64);
106 A3 (0, a[0][1][2][3][4], 128);
109 void test_pointers (void)
111 /* Verify that the aligned attribute on each of the composite pointer
112 types is detected corresponding to the result of __alignof__. */
113 A (1, I8);
114 A3 (0, I8, 4);
115 A3 (1, I8, 8);
117 A (1, P16_I8);
118 A3 (0, P16_I8, 8);
119 A3 (1, P16_I8, 16);
121 A (0, P_P16_I8);
122 A3 (0, P_P16_I8, 8);
123 A3 (0, P_P16_I8, 16);
125 A (1, P32_P_P16_I8);
126 A3 (0, P32_P_P16_I8, 8);
127 A3 (0, P32_P_P16_I8, 16);
128 A3 (1, P32_P_P16_I8, 32);
130 A (0, P_P32_P_P16_I8);
132 A (1, P64_P_P32_P_P16_I8);
133 A3 (0, P64_P_P32_P_P16_I8, 8);
134 A3 (0, P64_P_P32_P_P16_I8, 16);
135 A3 (0, P64_P_P32_P_P16_I8, 32);
136 A3 (1, P64_P_P32_P_P16_I8, 64);
139 /* Verify that the attribute on each of the composite types is detected
140 in the type of each of the indirection expressions. */
141 A (1, *(P16_I8)0);
142 A3 (1, *(P16_I8)0, 8);
143 A3 (0, *(P16_I8)0, 16);
145 A (1, *(P_P16_I8)0);
146 A3 (0, *(P_P16_I8)0, 8);
147 A3 (1, *(P_P16_I8)0, 16);
149 A (0, *(P32_P_P16_I8)0);
150 A3 (0, *(P32_P_P16_I8)0, 8);
151 A3 (0, *(P32_P_P16_I8)0, 16);
152 A3 (0, *(P32_P_P16_I8)0, 32);
154 A (1, *(P_P32_P_P16_I8)0);
155 A3 (1, *(P_P32_P_P16_I8)0, 32);
157 A (0, *(P64_P_P32_P_P16_I8)0);
159 /* Verify that the attribute on each of the composite types is detected
160 in the type of each of the subscipting expressions. */
161 A (1, ((P16_I8)0)[0]);
162 A3 (1, ((P16_I8)0)[1], 8);
163 A3 (0, ((P16_I8)0)[2], 16);
165 A (1, ((P_P16_I8)0)[3]);
166 A3 (0, ((P_P16_I8)0)[4], 8);
167 A3 (1, ((P_P16_I8)0)[5], 16);
169 A (0, ((P32_P_P16_I8)0)[6]);
170 A3 (0, ((P32_P_P16_I8)0)[7], 8);
171 A3 (0, ((P32_P_P16_I8)0)[8], 16);
172 A3 (0, ((P32_P_P16_I8)0)[9], 32);
174 A (1, ((P_P32_P_P16_I8)0)[10]);
175 A3 (1, ((P_P32_P_P16_I8)0)[11], 32);
177 A (0, ((P64_P_P32_P_P16_I8)0)[12]);
180 /* Verify that the attribute on each of the composite types is detected
181 in the type of each of the subscipting expression involving variables. */
183 I8 i8;
184 P16_I8 p16_i8 = &i8;
185 P_P16_I8 p_p16_i8 = &p16_i8;
186 P32_P_P16_I8 p32_p_p16_i8 = &p_p16_i8;
187 P_P32_P_P16_I8 p_p32_p_p16_i8 = &p32_p_p16_i8;
188 P64_P_P32_P_P16_I8 p64_p_p32_p_p16_i8 = &p_p32_p_p16_i8;
190 A (1, p16_i8[0]);
191 A3 (1, p16_i8[1], 8);
192 A3 (0, p16_i8[2], 16);
194 A (1, p_p16_i8[3]);
195 A3 (0, p_p16_i8[4], 8);
196 A3 (1, p_p16_i8[5], 16);
198 A (0, p32_p_p16_i8[6]);
199 A3 (0, p32_p_p16_i8[7], 8);
200 A3 (0, p32_p_p16_i8[8], 16);
201 A3 (0, p32_p_p16_i8[9], 32);
203 A (1, p_p32_p_p16_i8[10]);
204 A3 (1, p_p32_p_p16_i8[11], 32);
207 A (1, p_p16_i8[0][1]);
208 A3 (1, p_p16_i8[1][2], 8);
209 A3 (0, p_p16_i8[2][3], 16);
212 A (0, p64_p_p32_p_p16_i8[0]);
214 A (1, p64_p_p32_p_p16_i8[0][1]);
215 A3 (0, p64_p_p32_p_p16_i8[0][2], 16);
216 A3 (1, p64_p_p32_p_p16_i8[0][3], 32);
217 A3 (0, p64_p_p32_p_p16_i8[0][4], 64);
219 A (0, p64_p_p32_p_p16_i8[0][1][2]);
221 A (1, p64_p_p32_p_p16_i8[0][1][2][3]);
222 A3 (0, p64_p_p32_p_p16_i8[0][1][2][4], 8);
223 A3 (1, p64_p_p32_p_p16_i8[0][1][2][4], 16);
224 A3 (0, p64_p_p32_p_p16_i8[0][1][2][4], 32);
226 A (1, p64_p_p32_p_p16_i8[0][1][2][3][4]);
227 A3 (1, p64_p_p32_p_p16_i8[0][1][2][3][5], 8);
228 A3 (0, p64_p_p32_p_p16_i8[0][1][2][4][6], 16);
231 /* Same as above but using the indirection expression. */
232 A (0, *p64_p_p32_p_p16_i8);
234 A (1, **p64_p_p32_p_p16_i8);
235 A3 (0, **p64_p_p32_p_p16_i8, 16);
236 A3 (1, **p64_p_p32_p_p16_i8, 32);
237 A3 (0, **p64_p_p32_p_p16_i8, 64);
239 A (0, ***p64_p_p32_p_p16_i8);
241 A (1, ****p64_p_p32_p_p16_i8);
242 A3 (0, ****p64_p_p32_p_p16_i8, 8);
243 A3 (1, ****p64_p_p32_p_p16_i8, 16);
244 A3 (0, ****p64_p_p32_p_p16_i8, 32);
246 A (1, *****p64_p_p32_p_p16_i8);
247 A3 (1, *****p64_p_p32_p_p16_i8, 8);
248 A3 (0, *****p64_p_p32_p_p16_i8, 16);
252 S8 f_S8 (void);
253 I8 f_I8 (void);
254 P16_I8 f_P16_I8 (void);
255 P_P16_I8 f_P_P16_I8 (void);
256 P32_P_P16_I8 f_P32_P_P16_I8 (void);
257 P_P32_P_P16_I8 f_P_P32_P_P16_I8 (void);
258 P64_P_P32_P_P16_I8 f_P64_P_P32_P_P16_I8 (void);
260 void test_function_call (void)
262 /* Verify that the aligned attribute on each of the composite pointer
263 types returned by the functions is detected corresponding to
264 the result of __alignof__. */
266 A (0, f_S8 ());
268 A (1, f_I8 ());
269 A3 (1, f_I8 (), 8);
270 A3 (0, f_I8 (), 16);
272 A (1, f_P16_I8 ());
273 A3 (0, f_P16_I8 (), 8);
274 A3 (1, f_P16_I8 (), 16);
275 A3 (0, f_P16_I8 (), 32);
277 A (1, *f_P16_I8 ());
278 A3 (1, *f_P16_I8 (), 8);
279 A3 (0, *f_P16_I8 (), 16);
281 A (0, f_P_P16_I8 ());
283 A (1, *f_P_P16_I8 ());
284 A3 (0, *f_P_P16_I8 (), 8);
285 A3 (1, *f_P_P16_I8 (), 16);
286 A3 (0, *f_P_P16_I8 (), 32);
288 A (1, **f_P_P16_I8 ());
289 A3 (1, **f_P_P16_I8 (), 8);
290 A3 (0, **f_P_P16_I8 (), 16);
291 A3 (0, **f_P_P16_I8 (), 32);
295 void test_compound_literal (void)
297 A (0, (S8){ });
299 A (1, (I8){ });
300 A3 (1, (I8){ }, 8);
301 A3 (0, (I8){ }, 16);
303 A (1, (I64){ });
304 A3 (0, (I64){ }, 8);
305 A3 (0, (I64){ }, 16);
306 A3 (0, (I64){ }, 32);
307 A3 (1, (I64){ }, 64);
309 A (1, (A32_I64){ 0 });
310 A3 (0, (A32_I64){ 0 }, 8);
311 A3 (0, (A32_I64){ 0 }, 16);
312 A3 (1, (A32_I64){ 0 }, 32);
313 A3 (0, (A32_I64){ 0 }, 64);
315 A (1, ((A32_I64){ 0 })[0]);
316 A3 (0, ((A32_I64){ 0 })[0], 8);
317 A3 (0, ((A32_I64){ 0 })[0], 16);
318 A3 (0, ((A32_I64){ 0 })[0], 32);
319 A3 (1, ((A32_I64){ 0 })[0], 64);
323 void test_ternary_expression (int i)
325 A (0, (0 ? (S8){ } : (S8){ }));
327 A (1, (1 ? (I8){ } : (I8){ }));
328 A3 (1, (2 ? (I8){ } : (I8){ }), 8);
329 A3 (0, (3 ? (I8){ } : (I8){ }), 16);
331 A (1, (4 ? (I64){ } : (I64){ }));
332 A3 (0, (5 ? (I64){ } : (I64){ }), 8);
333 A3 (0, (6 ? (I64){ } : (I64){ }), 16);
334 A3 (0, (7 ? (I64){ } : (I64){ }), 32);
335 A3 (1, (8 ? (I64){ } : (I64){ }), 64);
337 #if !__cplusplus
338 /* Suppress -Wc++-compat warning: converting an array compound literal
339 to a pointer is ill-formed in C++ */
340 # pragma GCC diagnostic ignored "-Wc++-compat"
342 A (0, (9 ? (A32_I64){ } : (A32_I64){ }));
343 A3 (0, (i ? (A32_I64){ } : (A32_I64){ }), 8);
344 A3 (0, (i++ ? (A32_I64){ } : (A32_I64){ }), 16);
345 A3 (0, (++i ? (A32_I64){ } : (A32_I64){ }), 32);
346 A3 (0, (!i ? (A32_I64){ } : (A32_I64){ }), 64);
348 A (1, (0 ? (A32_I64){ } : (A32_I64){ })[0]);
349 A3 (0, (1 ? (A32_I64){ } : (A32_I64){ })[1], 8);
350 A3 (0, (2 ? (A32_I64){ } : (A32_I64){ })[2], 16);
351 A3 (0, (3 ? (A32_I64){ } : (A32_I64){ })[3], 32);
352 A3 (1, (3 ? (A32_I64){ } : (A32_I64){ })[i], 64);
353 #endif
357 void test_comma_expression (int i)
359 #if __cplusplus
360 /* In C++, the type of the comma expressions whose operand is an array
361 is the array itself with any attributes it was defined with. */
362 # define R 1
363 #else
364 /* In C, the type of the comma expressions whose operand is an array
365 is a pointer type that does not include any attributes the array
366 was defined with. */
367 # define R 0
368 /* Suppress -Wc++-compat warning: converting an array compound literal
369 to a pointer is ill-formed in C++
370 G++ accepts the conversion in unevaluated contexts without a warning. */
371 # pragma GCC diagnostic ignored "-Wc++-compat"
372 #endif
374 A (0, (0, (S8){ }));
376 A (1, (0, (I8){ }));
377 A3 (1, (1, (I8){ }), 8);
378 A3 (0, (2, (I8){ }), 16);
380 A (1, (3, (I64){ }));
381 A3 (0, (4, (I64){ }), 8);
382 A3 (0, (5, (I64){ }), 16);
383 A3 (0, (6, (I64){ }), 32);
384 A3 (1, (7, (I64){ }), 64);
386 A (R, (8, (A32_I64){ }));
387 A3 (0, (9, (A32_I64){ }), 8);
388 A3 (0, ((void)0, (A32_I64){ }), 16);
389 A3 (R, ((I64){ },(A32_I64){ }), 32);
390 A3 (0, (0, (A32_I64){ }), 64);
392 A (1, (1, ((A32_I64){ })[0]));
393 A3 (0, (2, ((A32_I64){ })[0]), 8);
394 A3 (0, (i++, ((A32_I64){ })[0]), 16);
395 A3 (0, (++i, ((A32_I64){ })[0]), 32);
396 A3 (1, (i = 0, ((A32_I64){ })[0]), 64);