1 /* { dg-do compile }
2 { dg-options "-Wall -Wattributes -ftrack-macro-expansion=0" } */
3
4 #define ATTR(attrlist) __attribute__ (attrlist)
5
6 /* Exercise the handling of the mutually exclusive attributes
7 aligned and packed on a type definition. */
8
9 /* Pointless but benign. */
10 struct ATTR ((aligned, aligned))
11 AlignedAligned { int i; };
12
13 /* Aligned followed by packed on a type and vice versa has a valid use:
14 to decrease the alignment of a type to the specified boundary. */
15 struct ATTR ((aligned, packed))
16 AlignedPacked { int i; };
17
18 struct ATTR ((packed, aligned))
19 PackedAligned { int i; };
20
21 struct ATTR ((aligned (2)))
22 AlignedMemberPacked
23 {
24 int ATTR ((packed)) i;
25 };
26
27 struct ATTR ((packed))
28 PackedMemberAligned
29 {
30 int ATTR ((aligned (2))) i;
31 };
32
33 /* Silly but benign. */
34 struct ATTR ((packed, packed))
35 PackedPacked { int i; };
36
37
38 /* Exercise the handling of the mutually exclusive attributes
39 aligned and packed on a function declaration. */
40
41 void ATTR ((aligned (8), packed))
42 faligned8_1 (void); /* { dg-warning "ignoring attribute .packed. because it conflicts with attribute .aligned." } */
43
44 void ATTR ((aligned (8)))
45 faligned8_2 (void); /* { dg-message "previous declaration here" } */
46
47 void ATTR ((packed))
48 faligned8_2 (void); /* { dg-warning "ignoring attribute .packed. because it conflicts with attribute .aligned." } */
49
50 /* Exercise the handling of the mutually exclusive attributes
51 always_inline and noinline (in that order). */
52
53 inline void ATTR ((always_inline))
54 falways_inline1 (void);
55
56 inline void ATTR ((__always_inline__))
57 falways_inline1 (void);
58
59 /* Verify that repeating attribute always_inline on the same declaration
60 doesn't trigger a warning. */
61 inline void ATTR ((always_inline, __always_inline__))
62 falways_inline1 (void);
63
64 /* Verify that repeating attribute always_inline on a distinct declaration
65 doesn't trigger a warning. */
66 inline void ATTR ((always_inline))
67 falways_inline1 (void); /* { dg-message "previous declaration here" } */
68
69 /* Verify a warning for noinline conflict. */
70 void ATTR ((noinline))
falways_inline1(void)71 falways_inline1 (void) { } /* { dg-warning "ignoring attribute .noinline. because it conflicts with attribute .always_inline." } */
72
73 /* And again. */
74 void ATTR ((always_inline))
75 falways_inline1 (void);
76
77
78 /* Exercise the handling of the mutually exclusive attributes
79 noinline and always_inline (in that order). */
80
81 void ATTR ((noinline))
82 fnoinline1 (void);
83
84 void ATTR ((__noinline__))
85 fnoinline1 (void);
86
87 /* Verify that repeating attribute noinline on the same declaration
88 doesn't trigger a warning. */
89 void ATTR ((noinline, __noinline__))
90 fnoinline1 (void);
91
92 /* Verify that repeating attribute noinline on a distinct declaration
93 doesn't trigger a warning. */
94 void ATTR ((noinline))
95 fnoinline1 (void); /* { dg-message "previous declaration here" } */
96
97 /* Verify a warning for always_inline conflict. */
98 void ATTR ((always_inline))
fnoinline1(void)99 fnoinline1 (void) { } /* { dg-warning "ignoring attribute .always_inline. because it conflicts with attribute .noinline." } */
100
101 /* Verify a warning for gnu_inline conflict. */
102 inline void ATTR ((gnu_inline))
103 fnoinline1 (void); /* { dg-warning "ignoring attribute .gnu_inline. because it conflicts with attribute .noinline." } */
104 /* { dg-warning "follows declaration with attribute .noinline." "inline noinline" { target *-*-* } .-1 } */
105
106 /* And again. */
107 void ATTR ((noinline))
108 fnoinline1 (void); /* { dg-warning "follows inline declaration" } */
109
110
111 /* Exercise the handling of the mutually exclusive attributes
112 noreturn and warn_unused_result. */
113
114 int ATTR ((__noreturn__))
115 fnoret1 (void);
116
117 int ATTR ((noreturn))
118 fnoret1 (void); /* { dg-message "previous declaration here" } */
119
120 int ATTR ((warn_unused_result))
121 fnoret1 (void); /* { dg-warning "ignoring attribute .warn_unused_result. because it conflicts with attribute .noreturn." } */
122
123 /* Verify that repeating attribute noreturn doesn't trigger a warning. */
124 int ATTR ((noreturn)) fnoret1 (void);
125
call_noret1(void)126 int call_noret1 (void)
127 {
128 /* Verify that attribute warn_unused_result was, in fact, ignored
129 on the second declaration of fnoret1. */
130 fnoret1 ();
131 }
132
133 int ATTR ((noreturn, warn_unused_result))
134 fnoret2 (void); /* { dg-warning "ignoring attribute .warn_unused_result. because it conflicts with attribute .noreturn." } */
135
136 /* Verify that repeating attribute noreturn doesn't trigger a warning. */
137 int ATTR ((noreturn)) fnoret2 (void);
138
call_noret2(void)139 int call_noret2 (void)
140 {
141 /* Verify that attribute warn_unused_result was, in fact, ignored
142 on the second declaration of fnoret2. */
143 fnoret2 ();
144 }
145
146 /* Verify that attribute noreturn isn't diagnosed on a declaration
147 that was previously declared warn_unused_result and that attribute
148 was dropped (because the function returs void). */
149
150 void ATTR ((warn_unused_result))
151 fnorety6 (void); /* { dg-warning ".warn_unused_result. attribute ignored" } */
152
153 void ATTR ((noreturn))
154 fnoret6 (void);
155
156
157 /* Exercise the handling of the mutually exclusive attributes
158 noreturn and alloc_align. */
159
160 void* ATTR ((noreturn))
161 fnoret_alloc_align1 (int); /* { dg-message "previous declaration here" } */
162
163 void* ATTR ((alloc_align (1)))
164 fnoret_alloc_align1 (int); /* { dg-warning "ignoring attribute .alloc_align. because it conflicts with attribute .noreturn." } */
165
166 void* ATTR ((noreturn, alloc_align (1)))
167 fnoret_alloc_align2 (int); /* { dg-warning "ignoring attribute .alloc_align. because it conflicts with attribute .noreturn." } */
168
169
170 void* ATTR ((noreturn)) ATTR ((alloc_align (1)))
171 fnoret_alloc_align3 (int); /* { dg-warning "ignoring attribute .alloc_align. because it conflicts with attribute .noreturn." } */
172
173
174 void* ATTR ((alloc_align (1)))
175 falloc_align_noret1 (int); /* { dg-message "previous declaration here" } */
176
177 void* ATTR ((noreturn))
178 falloc_align_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .alloc_align." } */
179
180
181 void* ATTR ((alloc_align (1), noreturn))
182 falloc_align_noret2 (int); /* { dg-warning "ignoring attribute .(noreturn|alloc_align). because it conflicts with attribute .(alloc_align|noreturn)." } */
183
184 void* ATTR ((alloc_align (1))) ATTR ((noreturn))
185 falloc_align_noret3 (int); /* { dg-warning "ignoring attribute .(noreturn|alloc_align). because it conflicts with attribute .(noreturn|alloc_align)." } */
186
187
188 /* Exercise the handling of the mutually exclusive attributes
189 noreturn and alloc_size. */
190
191 void* ATTR ((noreturn))
192 fnoret_alloc_size1 (int); /* { dg-message "previous declaration here" } */
193
194 void* ATTR ((alloc_size (1)))
195 fnoret_alloc_size1 (int); /* { dg-warning "ignoring attribute .alloc_size. because it conflicts with attribute .noreturn." } */
196
197 void* ATTR ((noreturn, alloc_size (1)))
198 fnoret_alloc_size2 (int); /* { dg-warning "ignoring attribute .alloc_size. because it conflicts with attribute .noreturn." } */
199
200
201 void* ATTR ((noreturn)) ATTR ((alloc_size (1)))
202 fnoret_alloc_size3 (int); /* { dg-warning "ignoring attribute .alloc_size. because it conflicts with attribute .noreturn." } */
203
204
205 void* ATTR ((alloc_size (1)))
206 falloc_size_noret1 (int); /* { dg-message "previous declaration here" } */
207
208 void* ATTR ((noreturn))
209 falloc_size_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .alloc_size." } */
210
211
212 void* ATTR ((alloc_size (1), noreturn))
213 falloc_size_noret2 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .alloc_size." } */
214
215 void* ATTR ((alloc_size (1))) ATTR ((noreturn))
216 falloc_size_noret3 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .alloc_size." } */
217
218
219 /* Exercise the handling of the mutually exclusive attributes
220 noreturn and const. */
221
222 int ATTR ((noreturn))
223 fnoret_const1 (int); /* { dg-message "previous declaration here" } */
224
225 int ATTR ((const))
226 fnoret_const1 (int); /* { dg-warning "ignoring attribute .const. because it conflicts with attribute .noreturn." } */
227
228 /* Unfortunately, attributes on a single declarations may not be processed
229 in the same order as specified... */
230 int ATTR ((noreturn, const))
231 fnoret_const2 (int); /* { dg-warning "ignoring attribute .const. because it conflicts with attribute .noreturn." } */
232
233
234 int ATTR ((noreturn)) ATTR ((const))
235 fnoret_const3 (int); /* { dg-warning "ignoring attribute .const. because it conflicts with attribute .noreturn." } */
236
237
238 int ATTR ((const))
239 fconst_noret1 (int); /* { dg-message "previous declaration here" } */
240
241 int ATTR ((noreturn))
242 fconst_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .const." } */
243
244
245 int ATTR ((const, noreturn))
246 fconst_noret2 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .const." } */
247
248 int ATTR ((const)) ATTR ((noreturn))
249 fconst_noret3 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .const." } */
250
251
252 /* Exercise the handling of the mutually exclusive attributes
253 noreturn and malloc. */
254
255 void* ATTR ((noreturn))
256 fnoret_malloc1 (int); /* { dg-message "previous declaration here" } */
257
258 void* ATTR ((malloc))
259 fnoret_malloc1 (int); /* { dg-warning "ignoring attribute .malloc. because it conflicts with attribute .noreturn." } */
260
261 /* Unfortunately, attributes on a single declarations may not be processed
262 in the same order as specified... */
263 void* ATTR ((noreturn, malloc))
264 fnoret_malloc2 (int); /* { dg-warning "ignoring attribute .malloc. because it conflicts with attribute .noreturn." } */
265
266
267 void* ATTR ((noreturn)) ATTR ((malloc))
268 fnoret_malloc3 (int); /* { dg-warning "ignoring attribute .malloc. because it conflicts with attribute .noreturn." } */
269
270
271 void* ATTR ((__malloc__))
272 fmalloc_noret1 (int);
273
274 void* ATTR ((malloc))
275 fmalloc_noret1 (int); /* { dg-message "previous declaration here" } */
276
277 void* ATTR ((noreturn))
278 fmalloc_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .malloc." } */
279
280
281 void* ATTR ((malloc, noreturn))
282 fmalloc_noret2 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .malloc." } */
283
284 void* ATTR ((malloc)) ATTR ((noreturn))
285 fmalloc_noret3 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .malloc." } */
286
287
288 /* Exercise the handling of the mutually exclusive attributes
289 noreturn and pure. */
290
291 int ATTR ((noreturn))
292 fnoret_pure1 (int); /* { dg-message "previous declaration here" } */
293
294 int ATTR ((pure))
295 fnoret_pure1 (int); /* { dg-warning "ignoring attribute .pure. because it conflicts with attribute .noreturn." } */
296
297 /* Unfortunately, attributes on a single declarations may not be processed
298 in the same order as specified... */
299 int ATTR ((noreturn, pure))
300 fnoret_pure2 (int); /* { dg-warning "ignoring attribute .pure. because it conflicts with attribute .noreturn." } */
301
302
303 int ATTR ((noreturn)) ATTR ((pure))
304 fnoret_pure3 (int); /* { dg-warning "ignoring attribute .pure. because it conflicts with attribute .noreturn." } */
305
306
307 int ATTR ((__pure__))
308 fpure_noret1 (int);
309
310 int ATTR ((pure))
311 fpure_noret1 (int); /* { dg-message "previous declaration here" } */
312
313 int ATTR ((noreturn))
314 fpure_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .pure." } */
315
316
317 int ATTR ((pure, noreturn))
318 fpure_noret2 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .pur." } */
319
320 int ATTR ((pure)) ATTR ((noreturn))
321 fpure_noret3 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .pure." } */
322
323
324 /* Exercise the handling of the mutually exclusive attributes
325 noreturn and returns_twice. */
326
327 int ATTR ((noreturn))
328 fnoret_returns_twice1 (int); /* { dg-message "previous declaration here" } */
329
330 int ATTR ((returns_twice))
331 fnoret_returns_twice1 (int); /* { dg-warning "ignoring attribute .returns_twice. because it conflicts with attribute .noreturn." } */
332
333 /* Unfortunately, attributes on a single declarations may not be processed
334 in the same order as specified... */
335 int ATTR ((noreturn, returns_twice))
336 fnoret_returns_twice2 (int); /* { dg-warning "ignoring attribute .returns_twice. because it conflicts with attribute .noreturn." } */
337
338
339 int ATTR ((noreturn)) ATTR ((returns_twice))
340 fnoret_returns_twice3 (int); /* { dg-warning "ignoring attribute .returns_twice. because it conflicts with attribute .noreturn." } */
341
342
343 int ATTR ((returns_twice))
344 freturns_twice_noret1 (int); /* { dg-message "previous declaration here" } */
345
346 int ATTR ((noreturn))
347 freturns_twice_noret1 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .returns_twice." } */
348
349
350 int ATTR ((returns_twice, noreturn))
351 freturns_twice_noret2 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .returns_twice." } */
352
353 int ATTR ((returns_twice)) ATTR ((noreturn))
354 freturns_twice_noret3 (int); /* { dg-warning "ignoring attribute .noreturn. because it conflicts with attribute .returns_twice." } */
355
356
357 /* Exercise the interaction of multiple combinations of mutually
358 exclusive attributes specified on distinct declarations. */
359
360 inline int ATTR ((always_inline))
361 finline_cold_noreturn (int);
362
363 inline int ATTR ((cold))
364 finline_cold_noreturn (int);
365
366 inline int ATTR ((noreturn))
367 finline_cold_noreturn (int);
368
369 inline int ATTR ((noinline))
370 finline_cold_noreturn (int); /* { dg-warning "ignoring attribute .noinline. because it conflicts with attribute .always_inline." } */
371
372 inline int ATTR ((hot))
373 finline_cold_noreturn (int); /* { dg-warning "ignoring attribute .hot. because it conflicts with attribute .cold." } */
374
375 inline int ATTR ((warn_unused_result))
376 finline_cold_noreturn (int); /* { dg-warning "ignoring attribute .warn_unused_result. because it conflicts with attribute .noreturn." } */
377
378 inline int ATTR ((always_inline))
379 finline_cold_noreturn (int);
380
381 /* Expect no warning for the missing return statement below because
382 the function is noreturn. */
383 inline int ATTR ((noreturn))
finline_cold_noreturn(int i)384 finline_cold_noreturn (int i) { (void)&i; __builtin_abort (); }
385
386
387 /* Exercise the interaction of multiple combinations of mutually
388 exclusive attributes with some specified on the same declaration
389 and some on distinct declarations. */
390
391 inline int ATTR ((always_inline, hot))
392 finline_hot_noret_align (int);
393
394 inline int ATTR ((noreturn, noinline))
395 finline_hot_noret_align (int); /* { dg-warning "ignoring attribute .noinline. because it conflicts with attribute .always_inline." } */
396
397 inline int ATTR ((cold, aligned (8)))
398 finline_hot_noret_align (int); /* { dg-warning "ignoring attribute .cold. because it conflicts with attribute .hot." } */
399
400 inline int ATTR ((warn_unused_result))
401 finline_hot_noret_align (int); /* { dg-warning "ignoring attribute .warn_unused_result. because it conflicts with attribute .noreturn." } */
402
403 inline int ATTR ((aligned (4)))
404 finline_hot_noret_align (int); /* { dg-warning "ignoring attribute .aligned \\(4\\). because it conflicts with attribute .aligned \\(8\\)." "" { target { ! { hppa*64*-*-* s390*-*-* } } } } */
405 /* { dg-error "alignment for 'finline_hot_noret_align' must be at least 8" "" { target s390*-*-* } .-1 } */
406
407 inline int ATTR ((aligned (8)))
408 finline_hot_noret_align (int);
409
410 inline int ATTR ((const))
411 finline_hot_noret_align (int); /* { dg-warning "ignoring attribute .const. because it conflicts with attribute .noreturn." } */
412
413 /* Expect no warning for the missing return statement below because
414 the function is noreturn. */
415 inline int ATTR ((noreturn))
finline_hot_noret_align(int i)416 finline_hot_noret_align (int i) { (void)&i; __builtin_abort (); }
417
418
419 /* Exercise variable attributes. */
420
421 extern int ATTR ((common))
422 decl_common1; /* { dg-message "previous declaration here" } */
423
424 extern int ATTR ((nocommon))
425 decl_common1; /* { dg-warning "ignoring attribute .nocommon. because it conflicts with attribute .common." } */
426
427
428 extern int ATTR ((nocommon))
429 decl_common2; /* { dg-message "previous declaration here" } */
430
431 extern int ATTR ((common))
432 decl_common2; /* { dg-warning "ignoring attribute .common. because it conflicts with attribute .nocommon." } */
433
434
435 extern int ATTR ((common, nocommon))
436 decl_common3; /* { dg-warning "ignoring attribute .nocommon. because it conflicts with attribute .common." } */
437
438
439 extern int ATTR ((common, nocommon))
440 decl_common4; /* { dg-warning "ignoring attribute .nocommon. because it conflicts with attribute .common." } */
441