1 /* C-family attributes handling.
2 Copyright (C) 1992-2020 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 3, or (at your option) any later
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3. If not see
18 <http://www.gnu.org/licenses/>. */
20 #define INCLUDE_STRING
23 #include "coretypes.h"
29 #include "gimple-expr.h"
31 #include "stringpool.h"
33 #include "diagnostic.h"
35 #include "stor-layout.h"
39 #include "trans-mem.h"
41 #include "common/common-target.h"
42 #include "langhooks.h"
43 #include "tree-inline.h"
45 #include "tree-iterator.h"
48 #include "tree-pretty-print.h"
49 #include "gcc-rich-location.h"
51 static tree
handle_packed_attribute (tree
*, tree
, tree
, int, bool *);
52 static tree
handle_nocommon_attribute (tree
*, tree
, tree
, int, bool *);
53 static tree
handle_common_attribute (tree
*, tree
, tree
, int, bool *);
54 static tree
handle_hot_attribute (tree
*, tree
, tree
, int, bool *);
55 static tree
handle_cold_attribute (tree
*, tree
, tree
, int, bool *);
56 static tree
handle_no_sanitize_attribute (tree
*, tree
, tree
, int, bool *);
57 static tree
handle_no_sanitize_address_attribute (tree
*, tree
, tree
,
59 static tree
handle_no_sanitize_thread_attribute (tree
*, tree
, tree
,
61 static tree
handle_no_address_safety_analysis_attribute (tree
*, tree
, tree
,
63 static tree
handle_no_sanitize_undefined_attribute (tree
*, tree
, tree
, int,
65 static tree
handle_asan_odr_indicator_attribute (tree
*, tree
, tree
, int,
67 static tree
handle_stack_protect_attribute (tree
*, tree
, tree
, int, bool *);
68 static tree
handle_noinline_attribute (tree
*, tree
, tree
, int, bool *);
69 static tree
handle_noclone_attribute (tree
*, tree
, tree
, int, bool *);
70 static tree
handle_nocf_check_attribute (tree
*, tree
, tree
, int, bool *);
71 static tree
handle_symver_attribute (tree
*, tree
, tree
, int, bool *);
72 static tree
handle_noicf_attribute (tree
*, tree
, tree
, int, bool *);
73 static tree
handle_noipa_attribute (tree
*, tree
, tree
, int, bool *);
74 static tree
handle_leaf_attribute (tree
*, tree
, tree
, int, bool *);
75 static tree
handle_always_inline_attribute (tree
*, tree
, tree
, int,
77 static tree
handle_gnu_inline_attribute (tree
*, tree
, tree
, int, bool *);
78 static tree
handle_artificial_attribute (tree
*, tree
, tree
, int, bool *);
79 static tree
handle_flatten_attribute (tree
*, tree
, tree
, int, bool *);
80 static tree
handle_error_attribute (tree
*, tree
, tree
, int, bool *);
81 static tree
handle_used_attribute (tree
*, tree
, tree
, int, bool *);
82 static tree
handle_externally_visible_attribute (tree
*, tree
, tree
, int,
84 static tree
handle_no_reorder_attribute (tree
*, tree
, tree
, int,
86 static tree
handle_const_attribute (tree
*, tree
, tree
, int, bool *);
87 static tree
handle_transparent_union_attribute (tree
*, tree
, tree
,
89 static tree
handle_scalar_storage_order_attribute (tree
*, tree
, tree
,
91 static tree
handle_constructor_attribute (tree
*, tree
, tree
, int, bool *);
92 static tree
handle_destructor_attribute (tree
*, tree
, tree
, int, bool *);
93 static tree
handle_mode_attribute (tree
*, tree
, tree
, int, bool *);
94 static tree
handle_section_attribute (tree
*, tree
, tree
, int, bool *);
95 static tree
handle_aligned_attribute (tree
*, tree
, tree
, int, bool *);
96 static tree
handle_warn_if_not_aligned_attribute (tree
*, tree
, tree
,
98 static tree
handle_noinit_attribute (tree
*, tree
, tree
, int, bool *);
99 static tree
handle_weak_attribute (tree
*, tree
, tree
, int, bool *) ;
100 static tree
handle_noplt_attribute (tree
*, tree
, tree
, int, bool *) ;
101 static tree
handle_alias_ifunc_attribute (bool, tree
*, tree
, tree
, bool *);
102 static tree
handle_ifunc_attribute (tree
*, tree
, tree
, int, bool *);
103 static tree
handle_alias_attribute (tree
*, tree
, tree
, int, bool *);
104 static tree
handle_weakref_attribute (tree
*, tree
, tree
, int, bool *) ;
105 static tree
handle_visibility_attribute (tree
*, tree
, tree
, int,
107 static tree
handle_tls_model_attribute (tree
*, tree
, tree
, int,
109 static tree
handle_no_instrument_function_attribute (tree
*, tree
,
111 static tree
handle_no_profile_instrument_function_attribute (tree
*, tree
,
113 static tree
handle_malloc_attribute (tree
*, tree
, tree
, int, bool *);
114 static tree
handle_returns_twice_attribute (tree
*, tree
, tree
, int, bool *);
115 static tree
handle_no_limit_stack_attribute (tree
*, tree
, tree
, int,
117 static tree
handle_pure_attribute (tree
*, tree
, tree
, int, bool *);
118 static tree
handle_tm_attribute (tree
*, tree
, tree
, int, bool *);
119 static tree
handle_tm_wrap_attribute (tree
*, tree
, tree
, int, bool *);
120 static tree
handle_novops_attribute (tree
*, tree
, tree
, int, bool *);
121 static tree
handle_vector_size_attribute (tree
*, tree
, tree
, int,
122 bool *) ATTRIBUTE_NONNULL(3);
123 static tree
handle_nonnull_attribute (tree
*, tree
, tree
, int, bool *);
124 static tree
handle_nonstring_attribute (tree
*, tree
, tree
, int, bool *);
125 static tree
handle_nothrow_attribute (tree
*, tree
, tree
, int, bool *);
126 static tree
handle_cleanup_attribute (tree
*, tree
, tree
, int, bool *);
127 static tree
handle_warn_unused_result_attribute (tree
*, tree
, tree
, int,
129 static tree
handle_access_attribute (tree
*, tree
, tree
, int, bool *);
131 static tree
handle_sentinel_attribute (tree
*, tree
, tree
, int, bool *);
132 static tree
handle_type_generic_attribute (tree
*, tree
, tree
, int, bool *);
133 static tree
handle_alloc_size_attribute (tree
*, tree
, tree
, int, bool *);
134 static tree
handle_alloc_align_attribute (tree
*, tree
, tree
, int, bool *);
135 static tree
handle_assume_aligned_attribute (tree
*, tree
, tree
, int, bool *);
136 static tree
handle_target_attribute (tree
*, tree
, tree
, int, bool *);
137 static tree
handle_target_clones_attribute (tree
*, tree
, tree
, int, bool *);
138 static tree
handle_optimize_attribute (tree
*, tree
, tree
, int, bool *);
139 static tree
ignore_attribute (tree
*, tree
, tree
, int, bool *);
140 static tree
handle_no_split_stack_attribute (tree
*, tree
, tree
, int, bool *);
141 static tree
handle_argspec_attribute (tree
*, tree
, tree
, int, bool *);
142 static tree
handle_fnspec_attribute (tree
*, tree
, tree
, int, bool *);
143 static tree
handle_warn_unused_attribute (tree
*, tree
, tree
, int, bool *);
144 static tree
handle_returns_nonnull_attribute (tree
*, tree
, tree
, int, bool *);
145 static tree
handle_omp_declare_simd_attribute (tree
*, tree
, tree
, int,
147 static tree
handle_omp_declare_variant_attribute (tree
*, tree
, tree
, int,
149 static tree
handle_simd_attribute (tree
*, tree
, tree
, int, bool *);
150 static tree
handle_omp_declare_target_attribute (tree
*, tree
, tree
, int,
152 static tree
handle_designated_init_attribute (tree
*, tree
, tree
, int, bool *);
153 static tree
handle_patchable_function_entry_attribute (tree
*, tree
, tree
,
155 static tree
handle_copy_attribute (tree
*, tree
, tree
, int, bool *);
157 /* Helper to define attribute exclusions. */
158 #define ATTR_EXCL(name, function, type, variable) \
159 { name, function, type, variable }
161 /* Define attributes that are mutually exclusive with one another. */
162 static const struct attribute_spec::exclusions attr_aligned_exclusions
[] =
164 /* Attribute name exclusion applies to:
165 function, type, variable */
166 ATTR_EXCL ("aligned", true, false, false),
167 ATTR_EXCL ("packed", true, false, false),
168 ATTR_EXCL (NULL
, false, false, false)
171 extern const struct attribute_spec::exclusions attr_cold_hot_exclusions
[] =
173 ATTR_EXCL ("cold", true, true, true),
174 ATTR_EXCL ("hot", true, true, true),
175 ATTR_EXCL (NULL
, false, false, false)
178 static const struct attribute_spec::exclusions attr_common_exclusions
[] =
180 ATTR_EXCL ("common", true, true, true),
181 ATTR_EXCL ("nocommon", true, true, true),
182 ATTR_EXCL (NULL
, false, false, false),
185 static const struct attribute_spec::exclusions attr_inline_exclusions
[] =
187 ATTR_EXCL ("noinline", true, true, true),
188 ATTR_EXCL (NULL
, false, false, false),
191 static const struct attribute_spec::exclusions attr_noinline_exclusions
[] =
193 ATTR_EXCL ("always_inline", true, true, true),
194 ATTR_EXCL ("gnu_inline", true, true, true),
195 ATTR_EXCL (NULL
, false, false, false),
198 extern const struct attribute_spec::exclusions attr_noreturn_exclusions
[] =
200 ATTR_EXCL ("alloc_align", true, true, true),
201 ATTR_EXCL ("alloc_size", true, true, true),
202 ATTR_EXCL ("const", true, true, true),
203 ATTR_EXCL ("malloc", true, true, true),
204 ATTR_EXCL ("pure", true, true, true),
205 ATTR_EXCL ("returns_twice", true, true, true),
206 ATTR_EXCL ("warn_unused_result", true, true, true),
207 ATTR_EXCL (NULL
, false, false, false),
210 static const struct attribute_spec::exclusions
211 attr_warn_unused_result_exclusions
[] =
213 ATTR_EXCL ("noreturn", true, true, true),
214 ATTR_EXCL ("warn_unused_result", true, true, true),
215 ATTR_EXCL (NULL
, false, false, false),
218 static const struct attribute_spec::exclusions attr_returns_twice_exclusions
[] =
220 ATTR_EXCL ("noreturn", true, true, true),
221 ATTR_EXCL (NULL
, false, false, false),
224 /* Exclusions that apply to attribute alloc_align, alloc_size, and malloc. */
225 static const struct attribute_spec::exclusions attr_alloc_exclusions
[] =
227 ATTR_EXCL ("const", true, true, true),
228 ATTR_EXCL ("noreturn", true, true, true),
229 ATTR_EXCL ("pure", true, true, true),
230 ATTR_EXCL (NULL
, false, false, false),
233 static const struct attribute_spec::exclusions attr_const_pure_exclusions
[] =
235 ATTR_EXCL ("const", true, true, true),
236 ATTR_EXCL ("alloc_align", true, true, true),
237 ATTR_EXCL ("alloc_size", true, true, true),
238 ATTR_EXCL ("malloc", true, true, true),
239 ATTR_EXCL ("noreturn", true, true, true),
240 ATTR_EXCL ("pure", true, true, true),
241 ATTR_EXCL (NULL
, false, false, false)
244 static const struct attribute_spec::exclusions attr_noinit_exclusions
[] =
246 ATTR_EXCL ("noinit", true, true, true),
247 ATTR_EXCL ("section", true, true, true),
248 ATTR_EXCL (NULL
, false, false, false),
251 /* Table of machine-independent attributes common to all C-like languages.
253 Current list of processed common attributes: nonnull. */
254 const struct attribute_spec c_common_attribute_table
[] =
256 /* { name, min_len, max_len, decl_req, type_req, fn_type_req,
257 affects_type_identity, handler, exclude } */
258 { "packed", 0, 0, false, false, false, false,
259 handle_packed_attribute
,
260 attr_aligned_exclusions
},
261 { "nocommon", 0, 0, true, false, false, false,
262 handle_nocommon_attribute
,
263 attr_common_exclusions
},
264 { "common", 0, 0, true, false, false, false,
265 handle_common_attribute
,
266 attr_common_exclusions
},
267 /* FIXME: logically, noreturn attributes should be listed as
268 "false, true, true" and apply to function types. But implementing this
269 would require all the places in the compiler that use TREE_THIS_VOLATILE
270 on a decl to identify non-returning functions to be located and fixed
271 to check the function type instead. */
272 { "noreturn", 0, 0, true, false, false, false,
273 handle_noreturn_attribute
,
274 attr_noreturn_exclusions
},
275 { "volatile", 0, 0, true, false, false, false,
276 handle_noreturn_attribute
, NULL
},
277 { "stack_protect", 0, 0, true, false, false, false,
278 handle_stack_protect_attribute
, NULL
},
279 { "noinline", 0, 0, true, false, false, false,
280 handle_noinline_attribute
,
281 attr_noinline_exclusions
},
282 { "noclone", 0, 0, true, false, false, false,
283 handle_noclone_attribute
, NULL
},
284 { "no_icf", 0, 0, true, false, false, false,
285 handle_noicf_attribute
, NULL
},
286 { "noipa", 0, 0, true, false, false, false,
287 handle_noipa_attribute
, NULL
},
288 { "leaf", 0, 0, true, false, false, false,
289 handle_leaf_attribute
, NULL
},
290 { "always_inline", 0, 0, true, false, false, false,
291 handle_always_inline_attribute
,
292 attr_inline_exclusions
},
293 { "gnu_inline", 0, 0, true, false, false, false,
294 handle_gnu_inline_attribute
,
295 attr_inline_exclusions
},
296 { "artificial", 0, 0, true, false, false, false,
297 handle_artificial_attribute
, NULL
},
298 { "flatten", 0, 0, true, false, false, false,
299 handle_flatten_attribute
, NULL
},
300 { "used", 0, 0, true, false, false, false,
301 handle_used_attribute
, NULL
},
302 { "unused", 0, 0, false, false, false, false,
303 handle_unused_attribute
, NULL
},
304 { "externally_visible", 0, 0, true, false, false, false,
305 handle_externally_visible_attribute
, NULL
},
306 { "no_reorder", 0, 0, true, false, false, false,
307 handle_no_reorder_attribute
, NULL
},
308 /* The same comments as for noreturn attributes apply to const ones. */
309 { "const", 0, 0, true, false, false, false,
310 handle_const_attribute
,
311 attr_const_pure_exclusions
},
312 { "scalar_storage_order", 1, 1, false, false, false, false,
313 handle_scalar_storage_order_attribute
, NULL
},
314 { "transparent_union", 0, 0, false, false, false, false,
315 handle_transparent_union_attribute
, NULL
},
316 { "constructor", 0, 1, true, false, false, false,
317 handle_constructor_attribute
, NULL
},
318 { "destructor", 0, 1, true, false, false, false,
319 handle_destructor_attribute
, NULL
},
320 { "mode", 1, 1, false, true, false, false,
321 handle_mode_attribute
, NULL
},
322 { "section", 1, 1, true, false, false, false,
323 handle_section_attribute
, attr_noinit_exclusions
},
324 { "aligned", 0, 1, false, false, false, false,
325 handle_aligned_attribute
,
326 attr_aligned_exclusions
},
327 { "warn_if_not_aligned", 0, 1, false, false, false, false,
328 handle_warn_if_not_aligned_attribute
, NULL
},
329 { "weak", 0, 0, true, false, false, false,
330 handle_weak_attribute
, NULL
},
331 { "noplt", 0, 0, true, false, false, false,
332 handle_noplt_attribute
, NULL
},
333 { "ifunc", 1, 1, true, false, false, false,
334 handle_ifunc_attribute
, NULL
},
335 { "alias", 1, 1, true, false, false, false,
336 handle_alias_attribute
, NULL
},
337 { "weakref", 0, 1, true, false, false, false,
338 handle_weakref_attribute
, NULL
},
339 { "no_instrument_function", 0, 0, true, false, false, false,
340 handle_no_instrument_function_attribute
,
342 { "no_profile_instrument_function", 0, 0, true, false, false, false,
343 handle_no_profile_instrument_function_attribute
,
345 { "malloc", 0, 0, true, false, false, false,
346 handle_malloc_attribute
, attr_alloc_exclusions
},
347 { "returns_twice", 0, 0, true, false, false, false,
348 handle_returns_twice_attribute
,
349 attr_returns_twice_exclusions
},
350 { "no_stack_limit", 0, 0, true, false, false, false,
351 handle_no_limit_stack_attribute
, NULL
},
352 { "pure", 0, 0, true, false, false, false,
353 handle_pure_attribute
,
354 attr_const_pure_exclusions
},
355 { "transaction_callable", 0, 0, false, true, false, false,
356 handle_tm_attribute
, NULL
},
357 { "transaction_unsafe", 0, 0, false, true, false, true,
358 handle_tm_attribute
, NULL
},
359 { "transaction_safe", 0, 0, false, true, false, true,
360 handle_tm_attribute
, NULL
},
361 { "transaction_safe_dynamic", 0, 0, true, false, false, false,
362 handle_tm_attribute
, NULL
},
363 { "transaction_may_cancel_outer", 0, 0, false, true, false, false,
364 handle_tm_attribute
, NULL
},
365 /* ??? These two attributes didn't make the transition from the
366 Intel language document to the multi-vendor language document. */
367 { "transaction_pure", 0, 0, false, true, false, false,
368 handle_tm_attribute
, NULL
},
369 { "transaction_wrap", 1, 1, true, false, false, false,
370 handle_tm_wrap_attribute
, NULL
},
371 /* For internal use (marking of builtins) only. The name contains space
372 to prevent its usage in source code. */
373 { "no vops", 0, 0, true, false, false, false,
374 handle_novops_attribute
, NULL
},
375 { "deprecated", 0, 1, false, false, false, false,
376 handle_deprecated_attribute
, NULL
},
377 { "vector_size", 1, 1, false, true, false, true,
378 handle_vector_size_attribute
, NULL
},
379 { "visibility", 1, 1, false, false, false, false,
380 handle_visibility_attribute
, NULL
},
381 { "tls_model", 1, 1, true, false, false, false,
382 handle_tls_model_attribute
, NULL
},
383 { "nonnull", 0, -1, false, true, true, false,
384 handle_nonnull_attribute
, NULL
},
385 { "nonstring", 0, 0, true, false, false, false,
386 handle_nonstring_attribute
, NULL
},
387 { "nothrow", 0, 0, true, false, false, false,
388 handle_nothrow_attribute
, NULL
},
389 { "may_alias", 0, 0, false, true, false, false, NULL
, NULL
},
390 { "cleanup", 1, 1, true, false, false, false,
391 handle_cleanup_attribute
, NULL
},
392 { "warn_unused_result", 0, 0, false, true, true, false,
393 handle_warn_unused_result_attribute
,
394 attr_warn_unused_result_exclusions
},
395 { "sentinel", 0, 1, false, true, true, false,
396 handle_sentinel_attribute
, NULL
},
397 /* For internal use (marking of builtins) only. The name contains space
398 to prevent its usage in source code. */
399 { "type generic", 0, 0, false, true, true, false,
400 handle_type_generic_attribute
, NULL
},
401 { "alloc_size", 1, 2, false, true, true, false,
402 handle_alloc_size_attribute
,
403 attr_alloc_exclusions
},
404 { "cold", 0, 0, true, false, false, false,
405 handle_cold_attribute
,
406 attr_cold_hot_exclusions
},
407 { "hot", 0, 0, true, false, false, false,
408 handle_hot_attribute
,
409 attr_cold_hot_exclusions
},
410 { "no_address_safety_analysis",
411 0, 0, true, false, false, false,
412 handle_no_address_safety_analysis_attribute
,
414 { "no_sanitize", 1, -1, true, false, false, false,
415 handle_no_sanitize_attribute
, NULL
},
416 { "no_sanitize_address", 0, 0, true, false, false, false,
417 handle_no_sanitize_address_attribute
, NULL
},
418 { "no_sanitize_thread", 0, 0, true, false, false, false,
419 handle_no_sanitize_thread_attribute
, NULL
},
420 { "no_sanitize_undefined", 0, 0, true, false, false, false,
421 handle_no_sanitize_undefined_attribute
, NULL
},
422 { "asan odr indicator", 0, 0, true, false, false, false,
423 handle_asan_odr_indicator_attribute
, NULL
},
424 { "warning", 1, 1, true, false, false, false,
425 handle_error_attribute
, NULL
},
426 { "error", 1, 1, true, false, false, false,
427 handle_error_attribute
, NULL
},
428 { "target", 1, -1, true, false, false, false,
429 handle_target_attribute
, NULL
},
430 { "target_clones", 1, -1, true, false, false, false,
431 handle_target_clones_attribute
, NULL
},
432 { "optimize", 1, -1, true, false, false, false,
433 handle_optimize_attribute
, NULL
},
434 /* For internal use only. The leading '*' both prevents its usage in
435 source code and signals that it may be overridden by machine tables. */
436 { "*tm regparm", 0, 0, false, true, true, false,
437 ignore_attribute
, NULL
},
438 { "no_split_stack", 0, 0, true, false, false, false,
439 handle_no_split_stack_attribute
, NULL
},
440 /* For internal use only (marking of function arguments).
441 The name contains a space to prevent its usage in source code. */
442 { "arg spec", 1, -1, true, false, false, false,
443 handle_argspec_attribute
, NULL
},
444 /* For internal use (marking of builtins and runtime functions) only.
445 The name contains space to prevent its usage in source code. */
446 { "fn spec", 1, 1, false, true, true, false,
447 handle_fnspec_attribute
, NULL
},
448 { "warn_unused", 0, 0, false, false, false, false,
449 handle_warn_unused_attribute
, NULL
},
450 { "returns_nonnull", 0, 0, false, true, true, false,
451 handle_returns_nonnull_attribute
, NULL
},
452 { "omp declare simd", 0, -1, true, false, false, false,
453 handle_omp_declare_simd_attribute
, NULL
},
454 { "omp declare variant base", 0, -1, true, false, false, false,
455 handle_omp_declare_variant_attribute
, NULL
},
456 { "omp declare variant variant", 0, -1, true, false, false, false,
457 handle_omp_declare_variant_attribute
, NULL
},
458 { "simd", 0, 1, true, false, false, false,
459 handle_simd_attribute
, NULL
},
460 { "omp declare target", 0, -1, true, false, false, false,
461 handle_omp_declare_target_attribute
, NULL
},
462 { "omp declare target link", 0, 0, true, false, false, false,
463 handle_omp_declare_target_attribute
, NULL
},
464 { "omp declare target implicit", 0, 0, true, false, false, false,
465 handle_omp_declare_target_attribute
, NULL
},
466 { "omp declare target host", 0, 0, true, false, false, false,
467 handle_omp_declare_target_attribute
, NULL
},
468 { "omp declare target nohost", 0, 0, true, false, false, false,
469 handle_omp_declare_target_attribute
, NULL
},
470 { "omp declare target block", 0, 0, true, false, false, false,
471 handle_omp_declare_target_attribute
, NULL
},
472 { "alloc_align", 1, 1, false, true, true, false,
473 handle_alloc_align_attribute
,
474 attr_alloc_exclusions
},
475 { "assume_aligned", 1, 2, false, true, true, false,
476 handle_assume_aligned_attribute
, NULL
},
477 { "designated_init", 0, 0, false, true, false, false,
478 handle_designated_init_attribute
, NULL
},
479 { "fallthrough", 0, 0, false, false, false, false,
480 handle_fallthrough_attribute
, NULL
},
481 { "patchable_function_entry", 1, 2, true, false, false, false,
482 handle_patchable_function_entry_attribute
,
484 { "nocf_check", 0, 0, false, true, true, true,
485 handle_nocf_check_attribute
, NULL
},
486 { "symver", 1, -1, true, false, false, false,
487 handle_symver_attribute
, NULL
},
488 { "copy", 1, 1, false, false, false, false,
489 handle_copy_attribute
, NULL
},
490 { "noinit", 0, 0, true, false, false, false,
491 handle_noinit_attribute
, attr_noinit_exclusions
},
492 { "access", 1, 3, false, true, true, false,
493 handle_access_attribute
, NULL
},
494 { NULL
, 0, 0, false, false, false, false, NULL
, NULL
}
497 /* Give the specifications for the format attributes, used by C and all
500 Current list of processed format attributes: format, format_arg. */
501 const struct attribute_spec c_common_format_attribute_table
[] =
503 /* { name, min_len, max_len, decl_req, type_req, fn_type_req,
504 affects_type_identity, handler, exclude } */
505 { "format", 3, 3, false, true, true, false,
506 handle_format_attribute
, NULL
},
507 { "format_arg", 1, 1, false, true, true, false,
508 handle_format_arg_attribute
, NULL
},
509 { NULL
, 0, 0, false, false, false, false, NULL
, NULL
}
512 /* Returns TRUE iff the attribute indicated by ATTR_ID takes a plain
513 identifier as an argument, so the front end shouldn't look it up. */
516 attribute_takes_identifier_p (const_tree attr_id
)
518 const struct attribute_spec
*spec
= lookup_attribute_spec (attr_id
);
520 /* Unknown attribute that we'll end up ignoring, return true so we
521 don't complain about an identifier argument. */
523 else if (!strcmp ("mode", spec
->name
)
524 || !strcmp ("format", spec
->name
)
525 || !strcmp ("cleanup", spec
->name
)
526 || !strcmp ("access", spec
->name
))
529 return targetm
.attribute_takes_identifier_p (attr_id
);
532 /* Verify that argument value POS at position ARGNO to attribute NAME
533 applied to function TYPE refers to a function parameter at position
534 POS and the expected type CODE. Treat CODE == INTEGER_TYPE as
535 matching all C integral types except bool. If successful, return
536 POS after default conversions, if any. Otherwise, issue appropriate
537 warnings and return null. A non-zero 1-based ARGNO should be passed
538 in by callers only for attributes with more than one argument. */
541 positional_argument (const_tree fntype
, const_tree atname
, tree pos
,
542 tree_code code
, int argno
/* = 0 */,
543 int flags
/* = posargflags () */)
545 if (pos
&& TREE_CODE (pos
) != IDENTIFIER_NODE
546 && TREE_CODE (pos
) != FUNCTION_DECL
)
547 pos
= default_conversion (pos
);
549 tree postype
= TREE_TYPE (pos
);
550 if (pos
== error_mark_node
|| !postype
)
552 /* Only mention the positional argument number when it's non-zero. */
554 warning (OPT_Wattributes
,
555 "%qE attribute argument is invalid", atname
);
557 warning (OPT_Wattributes
,
558 "%qE attribute argument %i is invalid", atname
, argno
);
563 if (!INTEGRAL_TYPE_P (postype
))
565 /* Handle this case specially to avoid mentioning the value
566 of pointer constants in diagnostics. Only mention
567 the positional argument number when it's non-zero. */
569 warning (OPT_Wattributes
,
570 "%qE attribute argument has type %qT",
573 warning (OPT_Wattributes
,
574 "%qE attribute argument %i has type %qT",
575 atname
, argno
, postype
);
580 if (TREE_CODE (pos
) != INTEGER_CST
)
582 /* Only mention the argument number when it's non-zero. */
584 warning (OPT_Wattributes
,
585 "%qE attribute argument value %qE is not an integer "
589 warning (OPT_Wattributes
,
590 "%qE attribute argument %i value %qE is not an integer "
597 /* Argument positions are 1-based. */
598 if (integer_zerop (pos
))
600 if (flags
& POSARG_ZERO
)
601 /* Zero is explicitly allowed. */
605 warning (OPT_Wattributes
,
606 "%qE attribute argument value %qE does not refer to "
607 "a function parameter",
610 warning (OPT_Wattributes
,
611 "%qE attribute argument %i value %qE does not refer to "
612 "a function parameter",
618 if (!prototype_p (fntype
))
621 /* Verify that the argument position does not exceed the number
622 of formal arguments to the function. When POSARG_ELLIPSIS
623 is set, ARGNO may be beyond the last argument of a vararg
625 unsigned nargs
= type_num_arguments (fntype
);
627 || !tree_fits_uhwi_p (pos
)
628 || ((flags
& POSARG_ELLIPSIS
) == 0
629 && !IN_RANGE (tree_to_uhwi (pos
), 1, nargs
)))
633 warning (OPT_Wattributes
,
634 "%qE attribute argument value %qE exceeds the number "
635 "of function parameters %u",
638 warning (OPT_Wattributes
,
639 "%qE attribute argument %i value %qE exceeds the number "
640 "of function parameters %u",
641 atname
, argno
, pos
, nargs
);
645 /* Verify that the type of the referenced formal argument matches
646 the expected type. */
647 unsigned HOST_WIDE_INT ipos
= tree_to_uhwi (pos
);
649 /* Zero was handled above. */
650 gcc_assert (ipos
!= 0);
652 if (tree argtype
= type_argument_type (fntype
, ipos
))
654 if (flags
& POSARG_ELLIPSIS
)
657 error ("%qE attribute argument value %qE does not refer to "
658 "a variable argument list",
661 error ("%qE attribute argument %i value %qE does not refer to "
662 "a variable argument list",
667 /* Where the expected code is STRING_CST accept any pointer
668 expected by attribute format (this includes possibly qualified
669 char pointers and, for targets like Darwin, also pointers to
672 if (code
== STRING_CST
)
673 type_match
= valid_format_string_type_p (argtype
);
674 else if (code
== INTEGER_TYPE
)
675 /* For integers, accept enums, wide characters and other types
676 that match INTEGRAL_TYPE_P except for bool. */
677 type_match
= (INTEGRAL_TYPE_P (argtype
)
678 && TREE_CODE (argtype
) != BOOLEAN_TYPE
);
680 type_match
= TREE_CODE (argtype
) == code
;
684 if (code
== STRING_CST
)
686 /* Reject invalid format strings with an error. */
688 error ("%qE attribute argument value %qE refers to "
689 "parameter type %qT",
690 atname
, pos
, argtype
);
692 error ("%qE attribute argument %i value %qE refers to "
693 "parameter type %qT",
694 atname
, argno
, pos
, argtype
);
700 warning (OPT_Wattributes
,
701 "%qE attribute argument value %qE refers to "
702 "parameter type %qT",
703 atname
, pos
, argtype
);
705 warning (OPT_Wattributes
,
706 "%qE attribute argument %i value %qE refers to "
707 "parameter type %qT",
708 atname
, argno
, pos
, argtype
);
712 else if (!(flags
& POSARG_ELLIPSIS
))
715 warning (OPT_Wattributes
,
716 "%qE attribute argument value %qE refers to "
717 "a variadic function parameter of unknown type",
720 warning (OPT_Wattributes
,
721 "%qE attribute argument %i value %qE refers to "
722 "a variadic function parameter of unknown type",
730 /* Return the first of DECL or TYPE attributes installed in NODE if it's
731 a DECL, or TYPE attributes if it's a TYPE, or null otherwise. */
734 decl_or_type_attrs (tree node
)
738 if (tree attrs
= DECL_ATTRIBUTES (node
))
741 tree type
= TREE_TYPE (node
);
742 return TYPE_ATTRIBUTES (type
);
746 return TYPE_ATTRIBUTES (node
);
751 /* Given a pair of NODEs for arbitrary DECLs or TYPEs, validate one or
752 two integral or string attribute arguments NEWARGS to be applied to
753 NODE[0] for the absence of conflicts with the same attribute arguments
754 already applied to NODE[1]. Issue a warning for conflicts and return
755 false. Otherwise, when no conflicts are found, return true. */
758 validate_attr_args (tree node
[2], tree name
, tree newargs
[2])
760 /* First validate the arguments against those already applied to
761 the same declaration (or type). */
762 tree self
[2] = { node
[0], node
[0] };
763 if (node
[0] != node
[1] && !validate_attr_args (self
, name
, newargs
))
769 /* Extract the same attribute from the previous declaration or type. */
770 tree prevattr
= decl_or_type_attrs (node
[1]);
771 const char* const namestr
= IDENTIFIER_POINTER (name
);
772 prevattr
= lookup_attribute (namestr
, prevattr
);
776 /* Extract one or both attribute arguments. */
778 prevargs
[0] = TREE_VALUE (TREE_VALUE (prevattr
));
779 prevargs
[1] = TREE_CHAIN (TREE_VALUE (prevattr
));
781 prevargs
[1] = TREE_VALUE (prevargs
[1]);
783 /* Both arguments must be equal or, for the second pair, neither must
784 be provided to succeed. */
786 if (TREE_CODE (newargs
[0]) == INTEGER_CST
)
788 arg1eq
= tree_int_cst_equal (newargs
[0], prevargs
[0]);
789 if (newargs
[1] && prevargs
[1])
790 arg2eq
= tree_int_cst_equal (newargs
[1], prevargs
[1]);
792 arg2eq
= newargs
[1] == prevargs
[1];
794 else if (TREE_CODE (newargs
[0]) == STRING_CST
)
796 const char *s0
= TREE_STRING_POINTER (newargs
[0]);
797 const char *s1
= TREE_STRING_POINTER (prevargs
[0]);
798 arg1eq
= strcmp (s0
, s1
) == 0;
799 if (newargs
[1] && prevargs
[1])
801 s0
= TREE_STRING_POINTER (newargs
[1]);
802 s1
= TREE_STRING_POINTER (prevargs
[1]);
803 arg2eq
= strcmp (s0
, s1
) == 0;
806 arg2eq
= newargs
[1] == prevargs
[1];
811 if (arg1eq
&& arg2eq
)
814 /* If the two locations are different print a note pointing to
816 const location_t curloc
= input_location
;
817 const location_t prevloc
=
818 DECL_P (node
[1]) ? DECL_SOURCE_LOCATION (node
[1]) : curloc
;
820 /* Format the attribute specification for convenience. */
821 char newspec
[80], prevspec
[80];
823 snprintf (newspec
, sizeof newspec
, "%s (%s, %s)", namestr
,
824 print_generic_expr_to_str (newargs
[0]),
825 print_generic_expr_to_str (newargs
[1]));
827 snprintf (newspec
, sizeof newspec
, "%s (%s)", namestr
,
828 print_generic_expr_to_str (newargs
[0]));
831 snprintf (prevspec
, sizeof prevspec
, "%s (%s, %s)", namestr
,
832 print_generic_expr_to_str (prevargs
[0]),
833 print_generic_expr_to_str (prevargs
[1]));
835 snprintf (prevspec
, sizeof prevspec
, "%s (%s)", namestr
,
836 print_generic_expr_to_str (prevargs
[0]));
838 if (warning_at (curloc
, OPT_Wattributes
,
839 "ignoring attribute %qs because it conflicts "
842 && curloc
!= prevloc
)
843 inform (prevloc
, "previous declaration here");
848 /* Convenience wrapper for validate_attr_args to validate a single
849 attribute argument. Used by handlers for attributes that take
850 just a single argument. */
853 validate_attr_arg (tree node
[2], tree name
, tree newarg
)
855 tree argarray
[2] = { newarg
, NULL_TREE
};
856 return validate_attr_args (node
, name
, argarray
);
859 /* Attribute handlers common to C front ends. */
861 /* Handle a "packed" attribute; arguments as in
862 struct attribute_spec.handler. */
865 handle_packed_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
866 int flags
, bool *no_add_attrs
)
870 if (!(flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
872 warning (OPT_Wattributes
,
873 "%qE attribute ignored for type %qT", name
, *node
);
874 *no_add_attrs
= true;
877 TYPE_PACKED (*node
) = 1;
879 else if (TREE_CODE (*node
) == FIELD_DECL
)
881 if (TYPE_ALIGN (TREE_TYPE (*node
)) <= BITS_PER_UNIT
882 /* Still pack bitfields. */
883 && ! DECL_C_BIT_FIELD (*node
))
884 warning (OPT_Wattributes
,
885 "%qE attribute ignored for field of type %qT",
886 name
, TREE_TYPE (*node
));
888 DECL_PACKED (*node
) = 1;
890 /* We can't set DECL_PACKED for a VAR_DECL, because the bit is
891 used for DECL_REGISTER. It wouldn't mean anything anyway.
892 We can't set DECL_PACKED on the type of a TYPE_DECL, because
893 that changes what the typedef is typing. */
896 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
897 *no_add_attrs
= true;
903 /* Handle a "nocommon" attribute; arguments as in
904 struct attribute_spec.handler. */
907 handle_nocommon_attribute (tree
*node
, tree name
,
908 tree
ARG_UNUSED (args
),
909 int ARG_UNUSED (flags
), bool *no_add_attrs
)
912 DECL_COMMON (*node
) = 0;
915 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
916 *no_add_attrs
= true;
922 /* Handle a "common" attribute; arguments as in
923 struct attribute_spec.handler. */
926 handle_common_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
927 int ARG_UNUSED (flags
), bool *no_add_attrs
)
930 DECL_COMMON (*node
) = 1;
933 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
934 *no_add_attrs
= true;
940 /* Handle a "noreturn" attribute; arguments as in
941 struct attribute_spec.handler. */
944 handle_noreturn_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
945 int ARG_UNUSED (flags
), bool *no_add_attrs
)
947 tree type
= TREE_TYPE (*node
);
949 /* See FIXME comment in c_common_attribute_table. */
950 if (TREE_CODE (*node
) == FUNCTION_DECL
951 || objc_method_decl (TREE_CODE (*node
)))
952 TREE_THIS_VOLATILE (*node
) = 1;
953 else if (TREE_CODE (type
) == POINTER_TYPE
954 && TREE_CODE (TREE_TYPE (type
)) == FUNCTION_TYPE
)
956 = (build_qualified_type
958 (build_type_variant (TREE_TYPE (type
),
959 TYPE_READONLY (TREE_TYPE (type
)), 1)),
963 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
964 *no_add_attrs
= true;
970 /* Handle a "hot" and attribute; arguments as in
971 struct attribute_spec.handler. */
974 handle_hot_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
975 int ARG_UNUSED (flags
), bool *no_add_attrs
)
977 if (TREE_CODE (*node
) == FUNCTION_DECL
978 || TREE_CODE (*node
) == LABEL_DECL
)
980 /* Attribute hot processing is done later with lookup_attribute. */
984 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
985 *no_add_attrs
= true;
991 /* Handle a "cold" and attribute; arguments as in
992 struct attribute_spec.handler. */
995 handle_cold_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
996 int ARG_UNUSED (flags
), bool *no_add_attrs
)
998 if (TREE_CODE (*node
) == FUNCTION_DECL
999 || TREE_CODE (*node
) == LABEL_DECL
)
1001 /* Attribute cold processing is done later with lookup_attribute. */
1005 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1006 *no_add_attrs
= true;
1012 /* Add FLAGS for a function NODE to no_sanitize_flags in DECL_ATTRIBUTES. */
1015 add_no_sanitize_value (tree node
, unsigned int flags
)
1017 tree attr
= lookup_attribute ("no_sanitize", DECL_ATTRIBUTES (node
));
1020 unsigned int old_value
= tree_to_uhwi (TREE_VALUE (attr
));
1023 if (flags
== old_value
)
1026 TREE_VALUE (attr
) = build_int_cst (unsigned_type_node
, flags
);
1029 DECL_ATTRIBUTES (node
)
1030 = tree_cons (get_identifier ("no_sanitize"),
1031 build_int_cst (unsigned_type_node
, flags
),
1032 DECL_ATTRIBUTES (node
));
1035 /* Handle a "no_sanitize" attribute; arguments as in
1036 struct attribute_spec.handler. */
1039 handle_no_sanitize_attribute (tree
*node
, tree name
, tree args
, int,
1042 unsigned int flags
= 0;
1043 *no_add_attrs
= true;
1044 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1046 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1050 for (; args
; args
= TREE_CHAIN (args
))
1052 tree id
= TREE_VALUE (args
);
1053 if (TREE_CODE (id
) != STRING_CST
)
1055 error ("%qE argument not a string", name
);
1059 char *string
= ASTRDUP (TREE_STRING_POINTER (id
));
1060 flags
|= parse_no_sanitize_attribute (string
);
1063 add_no_sanitize_value (*node
, flags
);
1068 /* Handle a "no_sanitize_address" attribute; arguments as in
1069 struct attribute_spec.handler. */
1072 handle_no_sanitize_address_attribute (tree
*node
, tree name
, tree
, int,
1075 *no_add_attrs
= true;
1076 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1077 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1079 add_no_sanitize_value (*node
, SANITIZE_ADDRESS
);
1084 /* Handle a "no_sanitize_thread" attribute; arguments as in
1085 struct attribute_spec.handler. */
1088 handle_no_sanitize_thread_attribute (tree
*node
, tree name
, tree
, int,
1091 *no_add_attrs
= true;
1092 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1093 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1095 add_no_sanitize_value (*node
, SANITIZE_THREAD
);
1101 /* Handle a "no_address_safety_analysis" attribute; arguments as in
1102 struct attribute_spec.handler. */
1105 handle_no_address_safety_analysis_attribute (tree
*node
, tree name
, tree
, int,
1108 *no_add_attrs
= true;
1109 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1110 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1112 add_no_sanitize_value (*node
, SANITIZE_ADDRESS
);
1117 /* Handle a "no_sanitize_undefined" attribute; arguments as in
1118 struct attribute_spec.handler. */
1121 handle_no_sanitize_undefined_attribute (tree
*node
, tree name
, tree
, int,
1124 *no_add_attrs
= true;
1125 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1126 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1128 add_no_sanitize_value (*node
,
1129 SANITIZE_UNDEFINED
| SANITIZE_UNDEFINED_NONDEFAULT
);
1134 /* Handle an "asan odr indicator" attribute; arguments as in
1135 struct attribute_spec.handler. */
1138 handle_asan_odr_indicator_attribute (tree
*, tree
, tree
, int, bool *)
1143 /* Handle a "stack_protect" attribute; arguments as in
1144 struct attribute_spec.handler. */
1147 handle_stack_protect_attribute (tree
*node
, tree name
, tree
, int,
1150 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1152 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1153 *no_add_attrs
= true;
1159 /* Handle a "noipa" attribute; arguments as in
1160 struct attribute_spec.handler. */
1163 handle_noipa_attribute (tree
*node
, tree name
, tree
, int, bool *no_add_attrs
)
1165 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1167 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1168 *no_add_attrs
= true;
1174 /* Handle a "noinline" attribute; arguments as in
1175 struct attribute_spec.handler. */
1178 handle_noinline_attribute (tree
*node
, tree name
,
1179 tree
ARG_UNUSED (args
),
1180 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1182 if (TREE_CODE (*node
) == FUNCTION_DECL
)
1184 if (lookup_attribute ("always_inline", DECL_ATTRIBUTES (*node
)))
1186 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
1187 "with attribute %qs", name
, "always_inline");
1188 *no_add_attrs
= true;
1191 DECL_UNINLINABLE (*node
) = 1;
1195 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1196 *no_add_attrs
= true;
1202 /* Handle a "noclone" attribute; arguments as in
1203 struct attribute_spec.handler. */
1206 handle_noclone_attribute (tree
*node
, tree name
,
1207 tree
ARG_UNUSED (args
),
1208 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1210 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1212 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1213 *no_add_attrs
= true;
1219 /* Handle a "nocf_check" attribute; arguments as in
1220 struct attribute_spec.handler. */
1223 handle_nocf_check_attribute (tree
*node
, tree name
,
1224 tree
ARG_UNUSED (args
),
1225 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1227 if (TREE_CODE (*node
) != FUNCTION_TYPE
1228 && TREE_CODE (*node
) != METHOD_TYPE
)
1230 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1231 *no_add_attrs
= true;
1233 else if (!(flag_cf_protection
& CF_BRANCH
))
1235 warning (OPT_Wattributes
, "%qE attribute ignored. Use "
1236 "%<-fcf-protection%> option to enable it",
1238 *no_add_attrs
= true;
1244 /* Handle a "no_icf" attribute; arguments as in
1245 struct attribute_spec.handler. */
1248 handle_noicf_attribute (tree
*node
, tree name
,
1249 tree
ARG_UNUSED (args
),
1250 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1252 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1254 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1255 *no_add_attrs
= true;
1262 /* Handle a "always_inline" attribute; arguments as in
1263 struct attribute_spec.handler. */
1266 handle_always_inline_attribute (tree
*node
, tree name
,
1267 tree
ARG_UNUSED (args
),
1268 int ARG_UNUSED (flags
),
1271 if (TREE_CODE (*node
) == FUNCTION_DECL
)
1273 if (lookup_attribute ("noinline", DECL_ATTRIBUTES (*node
)))
1275 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
1276 "with %qs attribute", name
, "noinline");
1277 *no_add_attrs
= true;
1279 else if (lookup_attribute ("target_clones", DECL_ATTRIBUTES (*node
)))
1281 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
1282 "with %qs attribute", name
, "target_clones");
1283 *no_add_attrs
= true;
1286 /* Set the attribute and mark it for disregarding inline
1288 DECL_DISREGARD_INLINE_LIMITS (*node
) = 1;
1292 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1293 *no_add_attrs
= true;
1299 /* Handle a "gnu_inline" attribute; arguments as in
1300 struct attribute_spec.handler. */
1303 handle_gnu_inline_attribute (tree
*node
, tree name
,
1304 tree
ARG_UNUSED (args
),
1305 int ARG_UNUSED (flags
),
1308 if (TREE_CODE (*node
) == FUNCTION_DECL
&& DECL_DECLARED_INLINE_P (*node
))
1310 /* Do nothing else, just set the attribute. We'll get at
1311 it later with lookup_attribute. */
1315 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1316 *no_add_attrs
= true;
1322 /* Handle a "leaf" attribute; arguments as in
1323 struct attribute_spec.handler. */
1326 handle_leaf_attribute (tree
*node
, tree name
,
1327 tree
ARG_UNUSED (args
),
1328 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1330 if (TREE_CODE (*node
) != FUNCTION_DECL
)
1332 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1333 *no_add_attrs
= true;
1335 if (!TREE_PUBLIC (*node
))
1337 warning (OPT_Wattributes
, "%qE attribute has no effect on unit local "
1339 *no_add_attrs
= true;
1345 /* Handle an "artificial" attribute; arguments as in
1346 struct attribute_spec.handler. */
1349 handle_artificial_attribute (tree
*node
, tree name
,
1350 tree
ARG_UNUSED (args
),
1351 int ARG_UNUSED (flags
),
1354 if (TREE_CODE (*node
) == FUNCTION_DECL
&& DECL_DECLARED_INLINE_P (*node
))
1356 /* Do nothing else, just set the attribute. We'll get at
1357 it later with lookup_attribute. */
1361 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1362 *no_add_attrs
= true;
1368 /* Handle a "flatten" attribute; arguments as in
1369 struct attribute_spec.handler. */
1372 handle_flatten_attribute (tree
*node
, tree name
,
1373 tree args ATTRIBUTE_UNUSED
,
1374 int flags ATTRIBUTE_UNUSED
, bool *no_add_attrs
)
1376 if (TREE_CODE (*node
) == FUNCTION_DECL
)
1377 /* Do nothing else, just set the attribute. We'll get at
1378 it later with lookup_attribute. */
1382 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1383 *no_add_attrs
= true;
1389 /* Handle a "warning" or "error" attribute; arguments as in
1390 struct attribute_spec.handler. */
1393 handle_error_attribute (tree
*node
, tree name
, tree args
,
1394 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1396 if (TREE_CODE (*node
) == FUNCTION_DECL
1397 && TREE_CODE (TREE_VALUE (args
)) == STRING_CST
)
1398 /* Do nothing else, just set the attribute. We'll get at
1399 it later with lookup_attribute. */
1403 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1404 *no_add_attrs
= true;
1410 /* Handle a "used" attribute; arguments as in
1411 struct attribute_spec.handler. */
1414 handle_used_attribute (tree
*pnode
, tree name
, tree
ARG_UNUSED (args
),
1415 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1419 if (TREE_CODE (node
) == FUNCTION_DECL
1420 || (VAR_P (node
) && TREE_STATIC (node
))
1421 || (TREE_CODE (node
) == TYPE_DECL
))
1423 TREE_USED (node
) = 1;
1424 DECL_PRESERVE_P (node
) = 1;
1426 DECL_READ_P (node
) = 1;
1430 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1431 *no_add_attrs
= true;
1437 /* Handle a "unused" attribute; arguments as in
1438 struct attribute_spec.handler. */
1441 handle_unused_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
1442 int flags
, bool *no_add_attrs
)
1448 if (TREE_CODE (decl
) == PARM_DECL
1449 || VAR_OR_FUNCTION_DECL_P (decl
)
1450 || TREE_CODE (decl
) == LABEL_DECL
1451 || TREE_CODE (decl
) == CONST_DECL
1452 || TREE_CODE (decl
) == TYPE_DECL
)
1454 TREE_USED (decl
) = 1;
1455 if (VAR_P (decl
) || TREE_CODE (decl
) == PARM_DECL
)
1456 DECL_READ_P (decl
) = 1;
1460 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1461 *no_add_attrs
= true;
1466 if (!(flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
1467 *node
= build_variant_type_copy (*node
);
1468 TREE_USED (*node
) = 1;
1474 /* Handle a "externally_visible" attribute; arguments as in
1475 struct attribute_spec.handler. */
1478 handle_externally_visible_attribute (tree
*pnode
, tree name
,
1479 tree
ARG_UNUSED (args
),
1480 int ARG_UNUSED (flags
),
1485 if (VAR_OR_FUNCTION_DECL_P (node
))
1487 if ((!TREE_STATIC (node
) && TREE_CODE (node
) != FUNCTION_DECL
1488 && !DECL_EXTERNAL (node
)) || !TREE_PUBLIC (node
))
1490 warning (OPT_Wattributes
,
1491 "%qE attribute have effect only on public objects", name
);
1492 *no_add_attrs
= true;
1497 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1498 *no_add_attrs
= true;
1504 /* Handle the "no_reorder" attribute. Arguments as in
1505 struct attribute_spec.handler. */
1508 handle_no_reorder_attribute (tree
*pnode
,
1516 if (!VAR_OR_FUNCTION_DECL_P (node
)
1517 && !(TREE_STATIC (node
) || DECL_EXTERNAL (node
)))
1519 warning (OPT_Wattributes
,
1520 "%qE attribute only affects top level objects",
1522 *no_add_attrs
= true;
1528 /* Handle a "const" attribute; arguments as in
1529 struct attribute_spec.handler. */
1532 handle_const_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
1533 int flags
, bool *no_add_attrs
)
1535 tree type
= TREE_TYPE (*node
);
1537 /* See FIXME comment on noreturn in c_common_attribute_table. */
1538 if (TREE_CODE (*node
) == FUNCTION_DECL
)
1539 TREE_READONLY (*node
) = 1;
1540 else if (TREE_CODE (type
) == POINTER_TYPE
1541 && TREE_CODE (TREE_TYPE (type
)) == FUNCTION_TYPE
)
1543 = (build_qualified_type
1545 (build_type_variant (TREE_TYPE (type
), 1,
1546 TREE_THIS_VOLATILE (TREE_TYPE (type
)))),
1547 TYPE_QUALS (type
)));
1550 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1551 *no_add_attrs
= true;
1554 /* void __builtin_unreachable(void) is const. Accept other such
1555 built-ins but warn on user-defined functions that return void. */
1556 if (!(flags
& ATTR_FLAG_BUILT_IN
)
1557 && TREE_CODE (*node
) == FUNCTION_DECL
1558 && VOID_TYPE_P (TREE_TYPE (type
)))
1559 warning (OPT_Wattributes
, "%qE attribute on function "
1560 "returning %<void%>", name
);
1565 /* Handle a "scalar_storage_order" attribute; arguments as in
1566 struct attribute_spec.handler. */
1569 handle_scalar_storage_order_attribute (tree
*node
, tree name
, tree args
,
1570 int flags
, bool *no_add_attrs
)
1572 tree id
= TREE_VALUE (args
);
1575 if (TREE_CODE (*node
) == TYPE_DECL
1576 && ! (flags
& ATTR_FLAG_CXX11
))
1577 node
= &TREE_TYPE (*node
);
1580 if (BYTES_BIG_ENDIAN
!= WORDS_BIG_ENDIAN
)
1582 error ("%qE attribute is not supported because endianness is not uniform",
1587 if (RECORD_OR_UNION_TYPE_P (type
) && !c_dialect_cxx ())
1589 bool reverse
= false;
1591 if (TREE_CODE (id
) == STRING_CST
1592 && strcmp (TREE_STRING_POINTER (id
), "big-endian") == 0)
1593 reverse
= !BYTES_BIG_ENDIAN
;
1594 else if (TREE_CODE (id
) == STRING_CST
1595 && strcmp (TREE_STRING_POINTER (id
), "little-endian") == 0)
1596 reverse
= BYTES_BIG_ENDIAN
;
1599 error ("attribute %qE argument must be one of %qs or %qs",
1600 name
, "big-endian", "little-endian");
1604 if (!(flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
1607 /* A type variant isn't good enough, since we don't want a cast
1608 to such a type to be removed as a no-op. */
1609 *node
= type
= build_duplicate_type (type
);
1612 TYPE_REVERSE_STORAGE_ORDER (type
) = reverse
;
1616 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1617 *no_add_attrs
= true;
1621 /* Handle a "transparent_union" attribute; arguments as in
1622 struct attribute_spec.handler. */
1625 handle_transparent_union_attribute (tree
*node
, tree name
,
1626 tree
ARG_UNUSED (args
), int flags
,
1631 *no_add_attrs
= true;
1633 if (TREE_CODE (*node
) == TYPE_DECL
1634 && ! (flags
& ATTR_FLAG_CXX11
))
1635 node
= &TREE_TYPE (*node
);
1638 if (TREE_CODE (type
) == UNION_TYPE
)
1640 /* Make sure that the first field will work for a transparent union.
1641 If the type isn't complete yet, leave the check to the code in
1643 if (TYPE_SIZE (type
))
1645 tree first
= first_field (type
);
1646 if (first
== NULL_TREE
1647 || DECL_ARTIFICIAL (first
)
1648 || TYPE_MODE (type
) != DECL_MODE (first
))
1652 if (!(flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
1654 /* If the type isn't complete yet, setting the flag
1655 on a variant wouldn't ever be checked. */
1656 if (!TYPE_SIZE (type
))
1659 /* build_duplicate_type doesn't work for C++. */
1660 if (c_dialect_cxx ())
1663 /* A type variant isn't good enough, since we don't want a cast
1664 to such a type to be removed as a no-op. */
1665 *node
= type
= build_duplicate_type (type
);
1668 for (tree t
= TYPE_MAIN_VARIANT (type
); t
; t
= TYPE_NEXT_VARIANT (t
))
1669 TYPE_TRANSPARENT_AGGR (t
) = 1;
1674 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1678 /* Subroutine of handle_{con,de}structor_attribute. Evaluate ARGS to
1679 get the requested priority for a constructor or destructor,
1680 possibly issuing diagnostics for invalid or reserved
1683 static priority_type
1684 get_priority (tree args
, bool is_destructor
)
1690 return DEFAULT_INIT_PRIORITY
;
1692 if (!SUPPORTS_INIT_PRIORITY
)
1695 error ("destructor priorities are not supported");
1697 error ("constructor priorities are not supported");
1698 return DEFAULT_INIT_PRIORITY
;
1701 arg
= TREE_VALUE (args
);
1702 if (TREE_CODE (arg
) == IDENTIFIER_NODE
)
1704 if (arg
== error_mark_node
)
1705 return DEFAULT_INIT_PRIORITY
;
1706 arg
= default_conversion (arg
);
1707 if (!tree_fits_shwi_p (arg
)
1708 || !INTEGRAL_TYPE_P (TREE_TYPE (arg
)))
1711 pri
= tree_to_shwi (arg
);
1712 if (pri
< 0 || pri
> MAX_INIT_PRIORITY
)
1715 if (pri
<= MAX_RESERVED_INIT_PRIORITY
)
1718 warning (OPT_Wprio_ctor_dtor
,
1719 "destructor priorities from 0 to %d are reserved "
1720 "for the implementation",
1721 MAX_RESERVED_INIT_PRIORITY
);
1723 warning (OPT_Wprio_ctor_dtor
,
1724 "constructor priorities from 0 to %d are reserved "
1725 "for the implementation",
1726 MAX_RESERVED_INIT_PRIORITY
);
1732 error ("destructor priorities must be integers from 0 to %d inclusive",
1735 error ("constructor priorities must be integers from 0 to %d inclusive",
1737 return DEFAULT_INIT_PRIORITY
;
1740 /* Handle a "constructor" attribute; arguments as in
1741 struct attribute_spec.handler. */
1744 handle_constructor_attribute (tree
*node
, tree name
, tree args
,
1745 int ARG_UNUSED (flags
),
1749 tree type
= TREE_TYPE (decl
);
1751 if (TREE_CODE (decl
) == FUNCTION_DECL
1752 && TREE_CODE (type
) == FUNCTION_TYPE
1753 && decl_function_context (decl
) == 0)
1755 priority_type priority
;
1756 DECL_STATIC_CONSTRUCTOR (decl
) = 1;
1757 priority
= get_priority (args
, /*is_destructor=*/false);
1758 SET_DECL_INIT_PRIORITY (decl
, priority
);
1759 TREE_USED (decl
) = 1;
1763 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1764 *no_add_attrs
= true;
1770 /* Handle a "destructor" attribute; arguments as in
1771 struct attribute_spec.handler. */
1774 handle_destructor_attribute (tree
*node
, tree name
, tree args
,
1775 int ARG_UNUSED (flags
),
1779 tree type
= TREE_TYPE (decl
);
1781 if (TREE_CODE (decl
) == FUNCTION_DECL
1782 && TREE_CODE (type
) == FUNCTION_TYPE
1783 && decl_function_context (decl
) == 0)
1785 priority_type priority
;
1786 DECL_STATIC_DESTRUCTOR (decl
) = 1;
1787 priority
= get_priority (args
, /*is_destructor=*/true);
1788 SET_DECL_FINI_PRIORITY (decl
, priority
);
1789 TREE_USED (decl
) = 1;
1793 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1794 *no_add_attrs
= true;
1800 /* Nonzero if the mode is a valid vector mode for this architecture.
1801 This returns nonzero even if there is no hardware support for the
1802 vector mode, but we can emulate with narrower modes. */
1805 vector_mode_valid_p (machine_mode mode
)
1807 enum mode_class mclass
= GET_MODE_CLASS (mode
);
1809 /* Doh! What's going on? */
1810 if (mclass
!= MODE_VECTOR_INT
1811 && mclass
!= MODE_VECTOR_FLOAT
1812 && mclass
!= MODE_VECTOR_FRACT
1813 && mclass
!= MODE_VECTOR_UFRACT
1814 && mclass
!= MODE_VECTOR_ACCUM
1815 && mclass
!= MODE_VECTOR_UACCUM
)
1818 /* Hardware support. Woo hoo! */
1819 if (targetm
.vector_mode_supported_p (mode
))
1822 /* We should probably return 1 if requesting V4DI and we have no DI,
1823 but we have V2DI, but this is probably very unlikely. */
1825 /* If we have support for the inner mode, we can safely emulate it.
1826 We may not have V2DI, but me can emulate with a pair of DIs. */
1827 return targetm
.scalar_mode_supported_p (GET_MODE_INNER (mode
));
1831 /* Handle a "mode" attribute; arguments as in
1832 struct attribute_spec.handler. */
1835 handle_mode_attribute (tree
*node
, tree name
, tree args
,
1836 int ARG_UNUSED (flags
), bool *no_add_attrs
)
1839 tree ident
= TREE_VALUE (args
);
1841 *no_add_attrs
= true;
1843 if (TREE_CODE (ident
) != IDENTIFIER_NODE
)
1844 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
1848 const char *p
= IDENTIFIER_POINTER (ident
);
1849 int len
= strlen (p
);
1850 machine_mode mode
= VOIDmode
;
1854 if (len
> 4 && p
[0] == '_' && p
[1] == '_'
1855 && p
[len
- 1] == '_' && p
[len
- 2] == '_')
1857 char *newp
= (char *) alloca (len
- 1);
1859 strcpy (newp
, &p
[2]);
1860 newp
[len
- 4] = '\0';
1864 /* Change this type to have a type with the specified mode.
1865 First check for the special modes. */
1866 if (!strcmp (p
, "byte"))
1868 else if (!strcmp (p
, "word"))
1870 else if (!strcmp (p
, "pointer"))
1872 else if (!strcmp (p
, "libgcc_cmp_return"))
1873 mode
= targetm
.libgcc_cmp_return_mode ();
1874 else if (!strcmp (p
, "libgcc_shift_count"))
1875 mode
= targetm
.libgcc_shift_count_mode ();
1876 else if (!strcmp (p
, "unwind_word"))
1877 mode
= targetm
.unwind_word_mode ();
1879 for (j
= 0; j
< NUM_MACHINE_MODES
; j
++)
1880 if (!strcmp (p
, GET_MODE_NAME (j
)))
1882 mode
= (machine_mode
) j
;
1886 if (mode
== VOIDmode
)
1888 error ("unknown machine mode %qE", ident
);
1892 /* Allow the target a chance to translate MODE into something supported.
1894 mode
= targetm
.translate_mode_attribute (mode
);
1897 switch (GET_MODE_CLASS (mode
))
1900 case MODE_PARTIAL_INT
:
1902 case MODE_DECIMAL_FLOAT
:
1908 = targetm
.scalar_mode_supported_p (as_a
<scalar_mode
> (mode
));
1911 case MODE_COMPLEX_INT
:
1912 case MODE_COMPLEX_FLOAT
:
1913 valid_mode
= targetm
.scalar_mode_supported_p (GET_MODE_INNER (mode
));
1916 case MODE_VECTOR_INT
:
1917 case MODE_VECTOR_FLOAT
:
1918 case MODE_VECTOR_FRACT
:
1919 case MODE_VECTOR_UFRACT
:
1920 case MODE_VECTOR_ACCUM
:
1921 case MODE_VECTOR_UACCUM
:
1922 warning (OPT_Wattributes
, "specifying vector types with "
1923 "%<__attribute__ ((mode))%> is deprecated");
1924 inform (input_location
,
1925 "use %<__attribute__ ((vector_size))%> instead");
1926 valid_mode
= vector_mode_valid_p (mode
);
1934 error ("unable to emulate %qs", p
);
1938 if (POINTER_TYPE_P (type
))
1940 scalar_int_mode addr_mode
;
1941 addr_space_t as
= TYPE_ADDR_SPACE (TREE_TYPE (type
));
1942 tree (*fn
)(tree
, machine_mode
, bool);
1944 if (!is_a
<scalar_int_mode
> (mode
, &addr_mode
)
1945 || !targetm
.addr_space
.valid_pointer_mode (addr_mode
, as
))
1947 error ("invalid pointer mode %qs", p
);
1951 if (TREE_CODE (type
) == POINTER_TYPE
)
1952 fn
= build_pointer_type_for_mode
;
1954 fn
= build_reference_type_for_mode
;
1955 typefm
= fn (TREE_TYPE (type
), addr_mode
, false);
1959 /* For fixed-point modes, we need to test if the signness of type
1960 and the machine mode are consistent. */
1961 if (ALL_FIXED_POINT_MODE_P (mode
)
1962 && TYPE_UNSIGNED (type
) != UNSIGNED_FIXED_POINT_MODE_P (mode
))
1964 error ("signedness of type and machine mode %qs don%'t match", p
);
1967 /* For fixed-point modes, we need to pass saturating info. */
1968 typefm
= lang_hooks
.types
.type_for_mode (mode
,
1969 ALL_FIXED_POINT_MODE_P (mode
) ? TYPE_SATURATING (type
)
1970 : TYPE_UNSIGNED (type
));
1973 if (typefm
== NULL_TREE
)
1975 error ("no data type for mode %qs", p
);
1978 else if (TREE_CODE (type
) == ENUMERAL_TYPE
)
1980 /* For enumeral types, copy the precision from the integer
1981 type returned above. If not an INTEGER_TYPE, we can't use
1982 this mode for this type. */
1983 if (TREE_CODE (typefm
) != INTEGER_TYPE
)
1985 error ("cannot use mode %qs for enumerated types", p
);
1989 if (flags
& ATTR_FLAG_TYPE_IN_PLACE
)
1991 TYPE_PRECISION (type
) = TYPE_PRECISION (typefm
);
1996 /* We cannot build a type variant, as there's code that assumes
1997 that TYPE_MAIN_VARIANT has the same mode. This includes the
1998 debug generators. Instead, create a subrange type. This
1999 results in all of the enumeral values being emitted only once
2000 in the original, and the subtype gets them by reference. */
2001 if (TYPE_UNSIGNED (type
))
2002 typefm
= make_unsigned_type (TYPE_PRECISION (typefm
));
2004 typefm
= make_signed_type (TYPE_PRECISION (typefm
));
2005 TREE_TYPE (typefm
) = type
;
2007 *no_add_attrs
= false;
2009 else if (VECTOR_MODE_P (mode
)
2010 ? TREE_CODE (type
) != TREE_CODE (TREE_TYPE (typefm
))
2011 : TREE_CODE (type
) != TREE_CODE (typefm
))
2013 error ("mode %qs applied to inappropriate type", p
);
2017 *node
= build_qualified_type (typefm
, TYPE_QUALS (type
));
2023 /* Handle a "section" attribute; arguments as in
2024 struct attribute_spec.handler. */
2027 handle_section_attribute (tree
*node
, tree name
, tree args
,
2028 int flags
, bool *no_add_attrs
)
2031 tree res
= NULL_TREE
;
2032 tree argval
= TREE_VALUE (args
);
2033 const char* new_section_name
;
2035 if (!targetm_common
.have_named_sections
)
2037 error_at (DECL_SOURCE_LOCATION (*node
),
2038 "section attributes are not supported for this target");
2042 if (!VAR_OR_FUNCTION_DECL_P (decl
))
2044 error ("section attribute not allowed for %q+D", *node
);
2048 if (TREE_CODE (argval
) != STRING_CST
)
2050 error ("section attribute argument not a string constant");
2055 && current_function_decl
!= NULL_TREE
2056 && !TREE_STATIC (decl
))
2058 error_at (DECL_SOURCE_LOCATION (decl
),
2059 "section attribute cannot be specified for local variables");
2063 new_section_name
= TREE_STRING_POINTER (argval
);
2065 /* The decl may have already been given a section attribute
2066 from a previous declaration. Ensure they match. */
2067 if (const char* const old_section_name
= DECL_SECTION_NAME (decl
))
2068 if (strcmp (old_section_name
, new_section_name
) != 0)
2070 error ("section of %q+D conflicts with previous declaration",
2076 && !targetm
.have_tls
&& targetm
.emutls
.tmpl_section
2077 && DECL_THREAD_LOCAL_P (decl
))
2079 error ("section of %q+D cannot be overridden", *node
);
2083 if (!validate_attr_arg (node
, name
, argval
))
2086 res
= targetm
.handle_generic_attribute (node
, name
, args
, flags
,
2089 /* If the back end confirms the attribute can be added then continue onto
2090 final processing. */
2091 if (!(*no_add_attrs
))
2093 set_decl_section_name (decl
, new_section_name
);
2098 *no_add_attrs
= true;
2102 /* Common codes shared by handle_warn_if_not_aligned_attribute and
2103 handle_aligned_attribute. */
2106 common_handle_aligned_attribute (tree
*node
, tree name
, tree args
, int flags
,
2108 bool warn_if_not_aligned_p
)
2110 tree decl
= NULL_TREE
;
2112 bool is_type
= false;
2115 /* The last (already pushed) declaration with all validated attributes
2116 merged in or the current about-to-be-pushed one if one hasn't been
2118 tree last_decl
= node
[1] ? node
[1] : *node
;
2122 align_expr
= TREE_VALUE (args
);
2123 if (align_expr
&& TREE_CODE (align_expr
) != IDENTIFIER_NODE
2124 && TREE_CODE (align_expr
) != FUNCTION_DECL
)
2125 align_expr
= default_conversion (align_expr
);
2128 align_expr
= size_int (ATTRIBUTE_ALIGNED_VALUE
/ BITS_PER_UNIT
);
2133 type
= &TREE_TYPE (decl
);
2134 is_type
= TREE_CODE (*node
) == TYPE_DECL
;
2136 else if (TYPE_P (*node
))
2137 type
= node
, is_type
= true;
2139 /* True to consider invalid alignments greater than MAX_OFILE_ALIGNMENT. */
2140 bool objfile
= (TREE_CODE (*node
) == FUNCTION_DECL
2141 || (VAR_P (*node
) && TREE_STATIC (*node
)));
2142 /* Log2 of specified alignment. */
2143 int pow2align
= check_user_alignment (align_expr
, objfile
,
2144 /* warn_zero = */ true);
2145 if (pow2align
== -1)
2147 *no_add_attrs
= true;
2151 /* The alignment in bits corresponding to the specified alignment. */
2152 unsigned bitalign
= (1U << pow2align
) * BITS_PER_UNIT
;
2154 /* The alignment of the current declaration and that of the last
2155 pushed declaration, determined on demand below. */
2156 unsigned curalign
= 0;
2157 unsigned lastalign
= 0;
2159 /* True when SET_DECL_ALIGN() should be called for the decl when
2160 *NO_ADD_ATTRS is false. */
2161 bool set_align
= true;
2164 if ((flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
2165 /* OK, modify the type in place. */;
2166 /* If we have a TYPE_DECL, then copy the type, so that we
2167 don't accidentally modify a builtin type. See pushdecl. */
2168 else if (decl
&& TREE_TYPE (decl
) != error_mark_node
2169 && DECL_ORIGINAL_TYPE (decl
) == NULL_TREE
)
2171 tree tt
= TREE_TYPE (decl
);
2172 *type
= build_variant_type_copy (*type
);
2173 DECL_ORIGINAL_TYPE (decl
) = tt
;
2174 TYPE_NAME (*type
) = decl
;
2175 TREE_USED (*type
) = TREE_USED (decl
);
2176 TREE_TYPE (decl
) = *type
;
2179 *type
= build_variant_type_copy (*type
);
2181 if (warn_if_not_aligned_p
)
2183 SET_TYPE_WARN_IF_NOT_ALIGN (*type
, bitalign
);
2184 warn_if_not_aligned_p
= false;
2188 SET_TYPE_ALIGN (*type
, bitalign
);
2189 TYPE_USER_ALIGN (*type
) = 1;
2192 else if (! VAR_OR_FUNCTION_DECL_P (decl
)
2193 && TREE_CODE (decl
) != FIELD_DECL
)
2195 error ("alignment may not be specified for %q+D", decl
);
2196 *no_add_attrs
= true;
2198 else if (TREE_CODE (decl
) == FUNCTION_DECL
2199 && ((curalign
= DECL_ALIGN (decl
)) > bitalign
2200 || ((lastalign
= DECL_ALIGN (last_decl
)) > bitalign
)))
2202 /* Either a prior attribute on the same declaration or one
2203 on a prior declaration of the same function specifies
2204 stricter alignment than this attribute. */
2205 bool note
= lastalign
!= 0;
2207 curalign
= lastalign
;
2209 curalign
/= BITS_PER_UNIT
;
2210 unsigned newalign
= bitalign
/ BITS_PER_UNIT
;
2212 auto_diagnostic_group d
;
2213 if ((DECL_USER_ALIGN (decl
)
2214 || DECL_USER_ALIGN (last_decl
)))
2216 if (warning (OPT_Wattributes
,
2217 "ignoring attribute %<%E (%u)%> because it conflicts "
2218 "with attribute %<%E (%u)%>",
2219 name
, newalign
, name
, curalign
)
2221 inform (DECL_SOURCE_LOCATION (last_decl
),
2222 "previous declaration here");
2223 /* Only reject attempts to relax/override an alignment
2224 explicitly specified previously and accept declarations
2225 that appear to relax the implicit function alignment for
2226 the target. Both increasing and increasing the alignment
2227 set by -falign-functions setting is permitted. */
2228 *no_add_attrs
= true;
2230 else if (!warn_if_not_aligned_p
)
2232 /* Do not fail for attribute warn_if_not_aligned. Otherwise,
2233 silently avoid applying the alignment to the declaration
2234 because it's implicitly satisfied by the target. Apply
2235 the attribute nevertheless so it can be retrieved by
2236 __builtin_has_attribute. */
2240 else if (DECL_USER_ALIGN (decl
)
2241 && DECL_ALIGN (decl
) > bitalign
)
2242 /* C++-11 [dcl.align/4]:
2244 When multiple alignment-specifiers are specified for an
2245 entity, the alignment requirement shall be set to the
2246 strictest specified alignment.
2248 This formally comes from the c++11 specification but we are
2249 doing it for the GNU attribute syntax as well. */
2250 *no_add_attrs
= true;
2251 else if (!warn_if_not_aligned_p
2252 && TREE_CODE (decl
) == FUNCTION_DECL
2253 && DECL_ALIGN (decl
) > bitalign
)
2255 /* Don't warn for function alignment here if warn_if_not_aligned_p
2256 is true. It will be warned about later. */
2257 if (DECL_USER_ALIGN (decl
))
2259 /* Only reject attempts to relax/override an alignment
2260 explicitly specified previously and accept declarations
2261 that appear to relax the implicit function alignment for
2262 the target. Both increasing and increasing the alignment
2263 set by -falign-functions setting is permitted. */
2264 error ("alignment for %q+D was previously specified as %d "
2265 "and may not be decreased", decl
,
2266 DECL_ALIGN (decl
) / BITS_PER_UNIT
);
2267 *no_add_attrs
= true;
2270 else if (warn_if_not_aligned_p
2271 && TREE_CODE (decl
) == FIELD_DECL
2272 && !DECL_C_BIT_FIELD (decl
))
2274 SET_DECL_WARN_IF_NOT_ALIGN (decl
, bitalign
);
2275 warn_if_not_aligned_p
= false;
2279 if (warn_if_not_aligned_p
)
2281 error ("%<warn_if_not_aligned%> may not be specified for %q+D",
2283 *no_add_attrs
= true;
2285 else if (!is_type
&& !*no_add_attrs
&& set_align
)
2287 SET_DECL_ALIGN (decl
, bitalign
);
2288 DECL_USER_ALIGN (decl
) = 1;
2294 /* Handle a "aligned" attribute; arguments as in
2295 struct attribute_spec.handler. */
2298 handle_aligned_attribute (tree
*node
, tree name
, tree args
,
2299 int flags
, bool *no_add_attrs
)
2301 return common_handle_aligned_attribute (node
, name
, args
, flags
,
2302 no_add_attrs
, false);
2305 /* Handle a "warn_if_not_aligned" attribute; arguments as in
2306 struct attribute_spec.handler. */
2309 handle_warn_if_not_aligned_attribute (tree
*node
, tree name
,
2310 tree args
, int flags
,
2313 return common_handle_aligned_attribute (node
, name
, args
, flags
,
2314 no_add_attrs
, true);
2317 /* Handle a "weak" attribute; arguments as in
2318 struct attribute_spec.handler. */
2321 handle_weak_attribute (tree
*node
, tree name
,
2322 tree
ARG_UNUSED (args
),
2323 int ARG_UNUSED (flags
),
2324 bool * ARG_UNUSED (no_add_attrs
))
2326 if (TREE_CODE (*node
) == FUNCTION_DECL
2327 && DECL_DECLARED_INLINE_P (*node
))
2329 warning (OPT_Wattributes
, "inline function %q+D declared weak", *node
);
2330 *no_add_attrs
= true;
2332 else if (lookup_attribute ("ifunc", DECL_ATTRIBUTES (*node
)))
2334 error ("indirect function %q+D cannot be declared weak", *node
);
2335 *no_add_attrs
= true;
2338 else if (VAR_OR_FUNCTION_DECL_P (*node
))
2339 declare_weak (*node
);
2341 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
2346 /* Handle a "noinit" attribute; arguments as in struct
2347 attribute_spec.handler. Check whether the attribute is allowed
2348 here and add the attribute to the variable decl tree or otherwise
2349 issue a diagnostic. This function checks NODE is of the expected
2350 type and issues diagnostics otherwise using NAME. If it is not of
2351 the expected type *NO_ADD_ATTRS will be set to true. */
2354 handle_noinit_attribute (tree
* node
,
2357 int flags ATTRIBUTE_UNUSED
,
2360 const char *message
= NULL
;
2361 tree res
= NULL_TREE
;
2363 gcc_assert (DECL_P (*node
));
2364 gcc_assert (args
== NULL
);
2366 if (TREE_CODE (*node
) != VAR_DECL
)
2367 message
= G_("%qE attribute only applies to variables");
2369 /* Check that it's possible for the variable to have a section. */
2370 else if ((TREE_STATIC (*node
) || DECL_EXTERNAL (*node
) || in_lto_p
)
2371 && DECL_SECTION_NAME (*node
))
2372 message
= G_("%qE attribute cannot be applied to variables "
2373 "with specific sections");
2375 else if (!targetm
.have_switchable_bss_sections
)
2376 message
= G_("%qE attribute is specific to ELF targets");
2380 warning (OPT_Wattributes
, message
, name
);
2381 *no_add_attrs
= true;
2385 res
= targetm
.handle_generic_attribute (node
, name
, args
, flags
,
2387 /* If the back end confirms the attribute can be added then continue onto
2388 final processing. */
2389 if (!(*no_add_attrs
))
2391 /* If this var is thought to be common, then change this. Common
2392 variables are assigned to sections before the backend has a
2393 chance to process them. Do this only if the attribute is
2395 if (DECL_COMMON (*node
))
2396 DECL_COMMON (*node
) = 0;
2404 /* Handle a "noplt" attribute; arguments as in
2405 struct attribute_spec.handler. */
2408 handle_noplt_attribute (tree
*node
, tree name
,
2409 tree
ARG_UNUSED (args
),
2410 int ARG_UNUSED (flags
),
2411 bool * ARG_UNUSED (no_add_attrs
))
2413 if (TREE_CODE (*node
) != FUNCTION_DECL
)
2415 warning (OPT_Wattributes
,
2416 "%qE attribute is only applicable on functions", name
);
2417 *no_add_attrs
= true;
2423 /* Handle a "symver" attribute. */
2426 handle_symver_attribute (tree
*node
, tree
ARG_UNUSED (name
), tree args
,
2427 int ARG_UNUSED (flags
), bool *no_add_attrs
)
2430 const char *symver_str
;
2432 if (TREE_CODE (*node
) != FUNCTION_DECL
&& TREE_CODE (*node
) != VAR_DECL
)
2434 warning (OPT_Wattributes
,
2435 "%<symver%> attribute only applies to functions and variables");
2436 *no_add_attrs
= true;
2440 if (!decl_in_symtab_p (*node
))
2442 warning (OPT_Wattributes
,
2443 "%<symver%> attribute is only applicable to symbols");
2444 *no_add_attrs
= true;
2448 for (; args
; args
= TREE_CHAIN (args
))
2450 symver
= TREE_VALUE (args
);
2451 if (TREE_CODE (symver
) != STRING_CST
)
2453 error ("%<symver%> attribute argument not a string constant");
2454 *no_add_attrs
= true;
2458 symver_str
= TREE_STRING_POINTER (symver
);
2461 for (int n
= 0; (int)n
< TREE_STRING_LENGTH (symver
); n
++)
2462 if (symver_str
[n
] == '@')
2465 if (ats
!= 1 && ats
!= 2)
2467 error ("symver attribute argument must have format %<name@nodename%>");
2468 error ("%<symver%> attribute argument %qs must contain one or two "
2469 "%<@%>", symver_str
);
2470 *no_add_attrs
= true;
2479 /* Handle an "alias" or "ifunc" attribute; arguments as in
2480 struct attribute_spec.handler, except that IS_ALIAS tells us
2481 whether this is an alias as opposed to ifunc attribute. */
2484 handle_alias_ifunc_attribute (bool is_alias
, tree
*node
, tree name
, tree args
,
2489 if (TREE_CODE (decl
) != FUNCTION_DECL
2490 && (!is_alias
|| !VAR_P (decl
)))
2492 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
2493 *no_add_attrs
= true;
2495 else if ((TREE_CODE (decl
) == FUNCTION_DECL
&& DECL_INITIAL (decl
))
2496 || (TREE_CODE (decl
) != FUNCTION_DECL
2497 && TREE_PUBLIC (decl
) && !DECL_EXTERNAL (decl
))
2498 /* A static variable declaration is always a tentative definition,
2499 but the alias is a non-tentative definition which overrides. */
2500 || (TREE_CODE (decl
) != FUNCTION_DECL
2501 && ! TREE_PUBLIC (decl
) && DECL_INITIAL (decl
)))
2503 error ("%q+D defined both normally and as %qE attribute", decl
, name
);
2504 *no_add_attrs
= true;
2508 && (lookup_attribute ("weak", DECL_ATTRIBUTES (decl
))
2509 || lookup_attribute ("weakref", DECL_ATTRIBUTES (decl
))))
2511 error ("weak %q+D cannot be defined %qE", decl
, name
);
2512 *no_add_attrs
= true;
2516 /* Note that the very first time we process a nested declaration,
2517 decl_function_context will not be set. Indeed, *would* never
2518 be set except for the DECL_INITIAL/DECL_EXTERNAL frobbery that
2519 we do below. After such frobbery, pushdecl would set the context.
2520 In any case, this is never what we want. */
2521 else if (decl_function_context (decl
) == 0 && current_function_decl
== NULL
)
2525 id
= TREE_VALUE (args
);
2526 if (TREE_CODE (id
) != STRING_CST
)
2528 error ("attribute %qE argument not a string", name
);
2529 *no_add_attrs
= true;
2532 id
= get_identifier (TREE_STRING_POINTER (id
));
2533 /* This counts as a use of the object pointed to. */
2536 if (TREE_CODE (decl
) == FUNCTION_DECL
)
2537 DECL_INITIAL (decl
) = error_mark_node
;
2539 TREE_STATIC (decl
) = 1;
2543 /* ifuncs are also aliases, so set that attribute too. */
2544 DECL_ATTRIBUTES (decl
)
2545 = tree_cons (get_identifier ("alias"), args
,
2546 DECL_ATTRIBUTES (decl
));
2547 DECL_ATTRIBUTES (decl
) = tree_cons (get_identifier ("ifunc"),
2548 NULL
, DECL_ATTRIBUTES (decl
));
2553 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
2554 *no_add_attrs
= true;
2557 if (decl_in_symtab_p (*node
))
2559 struct symtab_node
*n
= symtab_node::get (decl
);
2560 if (n
&& n
->refuse_visibility_changes
)
2561 error ("%+qD declared %qs after being used",
2562 decl
, is_alias
? "alias" : "ifunc");
2569 /* Handle an "alias" or "ifunc" attribute; arguments as in
2570 struct attribute_spec.handler. */
2573 handle_ifunc_attribute (tree
*node
, tree name
, tree args
,
2574 int ARG_UNUSED (flags
), bool *no_add_attrs
)
2576 return handle_alias_ifunc_attribute (false, node
, name
, args
, no_add_attrs
);
2579 /* Handle an "alias" or "ifunc" attribute; arguments as in
2580 struct attribute_spec.handler. */
2583 handle_alias_attribute (tree
*node
, tree name
, tree args
,
2584 int ARG_UNUSED (flags
), bool *no_add_attrs
)
2586 return handle_alias_ifunc_attribute (true, node
, name
, args
, no_add_attrs
);
2589 /* Handle the "copy" attribute NAME by copying the set of attributes
2590 from the symbol referenced by ARGS to the declaration of *NODE. */
2593 handle_copy_attribute (tree
*node
, tree name
, tree args
,
2594 int flags
, bool *no_add_attrs
)
2596 /* Do not apply the copy attribute itself. It serves no purpose
2597 other than to copy other attributes. */
2598 *no_add_attrs
= true;
2602 tree ref
= TREE_VALUE (args
);
2603 if (ref
== error_mark_node
)
2606 if (TREE_CODE (ref
) == STRING_CST
)
2608 /* Explicitly handle this case since using a string literal
2609 as an argument is a likely mistake. */
2610 error_at (DECL_SOURCE_LOCATION (decl
),
2611 "%qE attribute argument cannot be a string",
2616 if (CONSTANT_CLASS_P (ref
)
2617 && (INTEGRAL_TYPE_P (TREE_TYPE (ref
))
2618 || FLOAT_TYPE_P (TREE_TYPE (ref
))))
2620 /* Similar to the string case, since some function attributes
2621 accept literal numbers as arguments (e.g., alloc_size or
2622 nonnull) using one here is a likely mistake. */
2623 error_at (DECL_SOURCE_LOCATION (decl
),
2624 "%qE attribute argument cannot be a constant arithmetic "
2632 /* Another possible mistake (but indirect self-references aren't
2633 and diagnosed and shouldn't be). */
2634 if (warning_at (DECL_SOURCE_LOCATION (decl
), OPT_Wattributes
,
2635 "%qE attribute ignored on a redeclaration "
2636 "of the referenced symbol",
2638 inform (DECL_SOURCE_LOCATION (node
[1]),
2639 "previous declaration here");
2643 /* Consider address-of expressions in the attribute argument
2644 as requests to copy from the referenced entity. */
2645 if (TREE_CODE (ref
) == ADDR_EXPR
)
2646 ref
= TREE_OPERAND (ref
, 0);
2650 /* Drill down into references to find the referenced decl. */
2651 tree_code refcode
= TREE_CODE (ref
);
2652 if (refcode
== ARRAY_REF
2653 || refcode
== INDIRECT_REF
)
2654 ref
= TREE_OPERAND (ref
, 0);
2655 else if (refcode
== COMPONENT_REF
)
2656 ref
= TREE_OPERAND (ref
, 1);
2659 } while (!DECL_P (ref
));
2661 /* For object pointer expressions, consider those to be requests
2662 to copy from their type, such as in:
2663 struct __attribute__ (copy ((struct T *)0)) U { ... };
2664 which copies type attributes from struct T to the declaration
2666 if ((CONSTANT_CLASS_P (ref
) || EXPR_P (ref
))
2667 && POINTER_TYPE_P (TREE_TYPE (ref
))
2668 && !FUNCTION_POINTER_TYPE_P (TREE_TYPE (ref
)))
2669 ref
= TREE_TYPE (ref
);
2671 tree reftype
= TYPE_P (ref
) ? ref
: TREE_TYPE (ref
);
2676 && (TREE_CODE (ref
) == FUNCTION_DECL
2678 && POINTER_TYPE_P (reftype
)
2679 && FUNC_OR_METHOD_TYPE_P (TREE_TYPE (reftype
)))))
2680 || (TREE_CODE (decl
) == FUNCTION_DECL
2683 && !FUNC_OR_METHOD_TYPE_P (reftype
)
2684 && (!POINTER_TYPE_P (reftype
)
2685 || !FUNC_OR_METHOD_TYPE_P (TREE_TYPE (reftype
)))))))
2687 /* It makes no sense to try to copy function attributes
2688 to a variable, or variable attributes to a function. */
2689 if (warning (OPT_Wattributes
,
2690 "%qE attribute ignored on a declaration of "
2691 "a different kind than referenced symbol",
2694 inform (DECL_SOURCE_LOCATION (ref
),
2695 "symbol %qD referenced by %qD declared here", ref
, decl
);
2699 tree attrs
= NULL_TREE
;
2701 attrs
= DECL_ATTRIBUTES (ref
);
2702 else if (TYPE_P (ref
))
2703 attrs
= TYPE_ATTRIBUTES (ref
);
2705 /* Copy decl attributes from REF to DECL. */
2706 for (tree at
= attrs
; at
; at
= TREE_CHAIN (at
))
2708 /* Avoid copying attributes that affect a symbol linkage,
2709 inlining, or visibility since those in all likelihood
2710 only apply to the target.
2711 FIXME: make it possible to specify which attributes to
2712 copy or not to copy in the copy attribute itself. */
2713 tree atname
= get_attribute_name (at
);
2714 if (is_attribute_p ("alias", atname
)
2715 || is_attribute_p ("always_inline", atname
)
2716 || is_attribute_p ("gnu_inline", atname
)
2717 || is_attribute_p ("ifunc", atname
)
2718 || is_attribute_p ("noinline", atname
)
2719 || is_attribute_p ("visibility", atname
)
2720 || is_attribute_p ("weak", atname
)
2721 || is_attribute_p ("weakref", atname
)
2722 || is_attribute_p ("target_clones", atname
))
2725 /* Attribute leaf only applies to extern functions.
2726 Avoid copying it to static ones. */
2727 if (!TREE_PUBLIC (decl
)
2728 && is_attribute_p ("leaf", atname
))
2731 tree atargs
= TREE_VALUE (at
);
2732 /* Create a copy of just the one attribute ar AT, including
2733 its argumentsm and add it to DECL. */
2734 tree attr
= tree_cons (atname
, copy_list (atargs
), NULL_TREE
);
2735 decl_attributes (node
, attr
, flags
, EXPR_P (ref
) ? NULL_TREE
: ref
);
2738 /* Proceed to copy type attributes below. */
2740 else if (!TYPE_P (decl
))
2742 error_at (DECL_SOURCE_LOCATION (decl
),
2743 "%qE attribute must apply to a declaration",
2748 /* A function declared with attribute nothrow has the attribute
2749 attached to it, but a C++ throw() function does not. */
2750 if (TREE_NOTHROW (ref
))
2751 TREE_NOTHROW (decl
) = true;
2753 /* Similarly, a function declared with attribute noreturn has it
2754 attached on to it, but a C11 _Noreturn function does not. */
2756 && TREE_THIS_VOLATILE (ref
)
2757 && FUNC_OR_METHOD_TYPE_P (reftype
))
2758 TREE_THIS_VOLATILE (decl
) = true;
2760 if (POINTER_TYPE_P (reftype
))
2761 reftype
= TREE_TYPE (reftype
);
2763 if (!TYPE_P (reftype
))
2766 tree attrs
= TYPE_ATTRIBUTES (reftype
);
2768 /* Copy type attributes from REF to DECL. Pass in REF if it's a DECL
2769 or a type but not if it's an expression. */
2770 for (tree at
= attrs
; at
; at
= TREE_CHAIN (at
))
2771 decl_attributes (node
, at
, flags
, EXPR_P (ref
) ? NULL_TREE
: ref
);
2776 /* Handle a "weakref" attribute; arguments as in struct
2777 attribute_spec.handler. */
2780 handle_weakref_attribute (tree
*node
, tree name
, tree args
,
2781 int flags
, bool *no_add_attrs
)
2783 tree attr
= NULL_TREE
;
2785 /* We must ignore the attribute when it is associated with
2786 local-scoped decls, since attribute alias is ignored and many
2787 such symbols do not even have a DECL_WEAK field. */
2788 if (decl_function_context (*node
)
2789 || current_function_decl
2790 || !VAR_OR_FUNCTION_DECL_P (*node
))
2792 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
2793 *no_add_attrs
= true;
2797 if (lookup_attribute ("ifunc", DECL_ATTRIBUTES (*node
)))
2799 error ("indirect function %q+D cannot be declared %qE",
2801 *no_add_attrs
= true;
2805 /* The idea here is that `weakref("name")' mutates into `weakref,
2806 alias("name")', and weakref without arguments, in turn,
2807 implicitly adds weak. */
2811 attr
= tree_cons (get_identifier ("alias"), args
, attr
);
2812 attr
= tree_cons (get_identifier ("weakref"), NULL_TREE
, attr
);
2814 *no_add_attrs
= true;
2816 decl_attributes (node
, attr
, flags
);
2820 if (lookup_attribute ("alias", DECL_ATTRIBUTES (*node
)))
2821 error_at (DECL_SOURCE_LOCATION (*node
),
2822 "%qE attribute must appear before %qs attribute",
2825 /* Can't call declare_weak because it wants this to be TREE_PUBLIC,
2826 and that isn't supported; and because it wants to add it to
2827 the list of weak decls, which isn't helpful. */
2828 DECL_WEAK (*node
) = 1;
2831 if (decl_in_symtab_p (*node
))
2833 struct symtab_node
*n
= symtab_node::get (*node
);
2834 if (n
&& n
->refuse_visibility_changes
)
2835 error ("%+qD declared %qE after being used", *node
, name
);
2841 /* Handle an "visibility" attribute; arguments as in
2842 struct attribute_spec.handler. */
2845 handle_visibility_attribute (tree
*node
, tree name
, tree args
,
2846 int ARG_UNUSED (flags
),
2847 bool *ARG_UNUSED (no_add_attrs
))
2850 tree id
= TREE_VALUE (args
);
2851 enum symbol_visibility vis
;
2855 if (TREE_CODE (*node
) == ENUMERAL_TYPE
)
2857 else if (!RECORD_OR_UNION_TYPE_P (*node
))
2859 warning (OPT_Wattributes
, "%qE attribute ignored on non-class types",
2863 else if (TYPE_FIELDS (*node
))
2865 error ("%qE attribute ignored because %qT is already defined",
2870 else if (decl_function_context (decl
) != 0 || !TREE_PUBLIC (decl
))
2872 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
2876 if (TREE_CODE (id
) != STRING_CST
)
2878 error ("visibility argument not a string");
2882 /* If this is a type, set the visibility on the type decl. */
2885 decl
= TYPE_NAME (decl
);
2888 if (TREE_CODE (decl
) == IDENTIFIER_NODE
)
2890 warning (OPT_Wattributes
, "%qE attribute ignored on types",
2896 if (strcmp (TREE_STRING_POINTER (id
), "default") == 0)
2897 vis
= VISIBILITY_DEFAULT
;
2898 else if (strcmp (TREE_STRING_POINTER (id
), "internal") == 0)
2899 vis
= VISIBILITY_INTERNAL
;
2900 else if (strcmp (TREE_STRING_POINTER (id
), "hidden") == 0)
2901 vis
= VISIBILITY_HIDDEN
;
2902 else if (strcmp (TREE_STRING_POINTER (id
), "protected") == 0)
2903 vis
= VISIBILITY_PROTECTED
;
2906 error ("attribute %qE argument must be one of %qs, %qs, %qs, or %qs",
2907 name
, "default", "hidden", "protected", "internal");
2908 vis
= VISIBILITY_DEFAULT
;
2911 if (DECL_VISIBILITY_SPECIFIED (decl
)
2912 && vis
!= DECL_VISIBILITY (decl
))
2914 tree attributes
= (TYPE_P (*node
)
2915 ? TYPE_ATTRIBUTES (*node
)
2916 : DECL_ATTRIBUTES (decl
));
2917 if (lookup_attribute ("visibility", attributes
))
2918 error ("%qD redeclared with different visibility", decl
);
2919 else if (TARGET_DLLIMPORT_DECL_ATTRIBUTES
2920 && lookup_attribute ("dllimport", attributes
))
2921 error ("%qD was declared %qs which implies default visibility",
2923 else if (TARGET_DLLIMPORT_DECL_ATTRIBUTES
2924 && lookup_attribute ("dllexport", attributes
))
2925 error ("%qD was declared %qs which implies default visibility",
2929 DECL_VISIBILITY (decl
) = vis
;
2930 DECL_VISIBILITY_SPECIFIED (decl
) = 1;
2932 /* Go ahead and attach the attribute to the node as well. This is needed
2933 so we can determine whether we have VISIBILITY_DEFAULT because the
2934 visibility was not specified, or because it was explicitly overridden
2935 from the containing scope. */
2940 /* Handle an "tls_model" attribute; arguments as in
2941 struct attribute_spec.handler. */
2944 handle_tls_model_attribute (tree
*node
, tree name
, tree args
,
2945 int ARG_UNUSED (flags
),
2946 bool *ARG_UNUSED (no_add_attrs
))
2950 enum tls_model kind
;
2954 warning (OPT_Wattributes
, "%qE attribute ignored because %qD "
2955 "is not a variable",
2960 if (!DECL_THREAD_LOCAL_P (decl
))
2962 warning (OPT_Wattributes
, "%qE attribute ignored because %qD does "
2963 "not have thread storage duration", name
, decl
);
2967 kind
= DECL_TLS_MODEL (decl
);
2968 id
= TREE_VALUE (args
);
2969 if (TREE_CODE (id
) != STRING_CST
)
2971 error ("%qE argument not a string", name
);
2975 if (!strcmp (TREE_STRING_POINTER (id
), "local-exec"))
2976 kind
= TLS_MODEL_LOCAL_EXEC
;
2977 else if (!strcmp (TREE_STRING_POINTER (id
), "initial-exec"))
2978 kind
= TLS_MODEL_INITIAL_EXEC
;
2979 else if (!strcmp (TREE_STRING_POINTER (id
), "local-dynamic"))
2980 kind
= optimize
? TLS_MODEL_LOCAL_DYNAMIC
: TLS_MODEL_GLOBAL_DYNAMIC
;
2981 else if (!strcmp (TREE_STRING_POINTER (id
), "global-dynamic"))
2982 kind
= TLS_MODEL_GLOBAL_DYNAMIC
;
2984 error ("%qE argument must be one of %qs, %qs, %qs, or %qs",
2986 "local-exec", "initial-exec", "local-dynamic", "global-dynamic");
2988 set_decl_tls_model (decl
, kind
);
2992 /* Handle a "no_instrument_function" attribute; arguments as in
2993 struct attribute_spec.handler. */
2996 handle_no_instrument_function_attribute (tree
*node
, tree name
,
2997 tree
ARG_UNUSED (args
),
2998 int ARG_UNUSED (flags
),
3003 if (TREE_CODE (decl
) != FUNCTION_DECL
)
3005 error_at (DECL_SOURCE_LOCATION (decl
),
3006 "%qE attribute applies only to functions", name
);
3007 *no_add_attrs
= true;
3010 DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (decl
) = 1;
3015 /* Handle a "no_profile_instrument_function" attribute; arguments as in
3016 struct attribute_spec.handler. */
3019 handle_no_profile_instrument_function_attribute (tree
*node
, tree name
, tree
,
3020 int, bool *no_add_attrs
)
3022 if (TREE_CODE (*node
) != FUNCTION_DECL
)
3024 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3025 *no_add_attrs
= true;
3031 /* Handle a "malloc" attribute; arguments as in
3032 struct attribute_spec.handler. */
3035 handle_malloc_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
3036 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3038 if (TREE_CODE (*node
) == FUNCTION_DECL
3039 && POINTER_TYPE_P (TREE_TYPE (TREE_TYPE (*node
))))
3040 DECL_IS_MALLOC (*node
) = 1;
3043 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3044 *no_add_attrs
= true;
3050 /* Handle the "alloc_size (argpos1 [, argpos2])" function type attribute.
3051 *NODE is the type of the function the attribute is being applied to. */
3054 handle_alloc_size_attribute (tree
*node
, tree name
, tree args
,
3055 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3057 tree fntype
= *node
;
3058 tree rettype
= TREE_TYPE (fntype
);
3059 if (!POINTER_TYPE_P (rettype
))
3061 warning (OPT_Wattributes
,
3062 "%qE attribute ignored on a function returning %qT",
3064 *no_add_attrs
= true;
3068 tree newargs
[2] = { NULL_TREE
, NULL_TREE
};
3069 for (int i
= 1; args
; ++i
)
3071 tree pos
= TREE_VALUE (args
);
3072 /* NEXT is null when the attribute includes just one argument.
3073 That's used to tell positional_argument to avoid mentioning
3074 the argument number in diagnostics (since there's just one
3075 mentioning it is unnecessary and coule be confusing). */
3076 tree next
= TREE_CHAIN (args
);
3077 if (tree val
= positional_argument (fntype
, name
, pos
, INTEGER_TYPE
,
3078 next
|| i
> 1 ? i
: 0))
3080 TREE_VALUE (args
) = val
;
3081 newargs
[i
- 1] = val
;
3085 *no_add_attrs
= true;
3092 if (!validate_attr_args (node
, name
, newargs
))
3093 *no_add_attrs
= true;
3099 /* Handle an "alloc_align (argpos)" attribute. */
3102 handle_alloc_align_attribute (tree
*node
, tree name
, tree args
, int,
3105 tree fntype
= *node
;
3106 tree rettype
= TREE_TYPE (fntype
);
3107 if (!POINTER_TYPE_P (rettype
))
3109 warning (OPT_Wattributes
,
3110 "%qE attribute ignored on a function returning %qT",
3112 *no_add_attrs
= true;
3116 if (tree val
= positional_argument (*node
, name
, TREE_VALUE (args
),
3118 if (validate_attr_arg (node
, name
, val
))
3121 *no_add_attrs
= true;
3125 /* Handle a "assume_aligned" attribute; arguments as in
3126 struct attribute_spec.handler. */
3129 handle_assume_aligned_attribute (tree
*node
, tree name
, tree args
, int,
3133 tree rettype
= TREE_TYPE (decl
);
3134 if (TREE_CODE (rettype
) != POINTER_TYPE
)
3136 warning (OPT_Wattributes
,
3137 "%qE attribute ignored on a function returning %qT",
3139 *no_add_attrs
= true;
3143 /* The alignment specified by the first argument. */
3144 tree align
= NULL_TREE
;
3146 for (; args
; args
= TREE_CHAIN (args
))
3148 tree val
= TREE_VALUE (args
);
3149 if (val
&& TREE_CODE (val
) != IDENTIFIER_NODE
3150 && TREE_CODE (val
) != FUNCTION_DECL
)
3151 val
= default_conversion (val
);
3153 if (!tree_fits_shwi_p (val
))
3155 warning (OPT_Wattributes
,
3156 "%qE attribute %E is not an integer constant",
3158 *no_add_attrs
= true;
3164 /* Validate and save the alignment. */
3165 if (!integer_pow2p (val
))
3167 warning (OPT_Wattributes
,
3168 "%qE attribute argument %E is not a power of 2",
3170 *no_add_attrs
= true;
3176 else if (tree_int_cst_sgn (val
) < 0 || tree_int_cst_le (align
, val
))
3178 /* The misalignment specified by the second argument
3179 must be non-negative and less than the alignment. */
3180 warning (OPT_Wattributes
,
3181 "%qE attribute argument %E is not in the range [0, %wu]",
3182 name
, val
, tree_to_uhwi (align
) - 1);
3183 *no_add_attrs
= true;
3190 /* Handle the internal-only "arg spec" attribute. */
3193 handle_argspec_attribute (tree
*, tree
, tree args
, int, bool *)
3195 /* Verify the attribute has one or two arguments and their kind. */
3196 gcc_assert (args
&& TREE_CODE (TREE_VALUE (args
)) == STRING_CST
);
3197 for (tree next
= TREE_CHAIN (args
); next
; next
= TREE_CHAIN (next
))
3199 tree val
= TREE_VALUE (next
);
3200 gcc_assert (DECL_P (val
) || EXPR_P (val
));
3205 /* Handle the internal-only "fn spec" attribute. */
3208 handle_fnspec_attribute (tree
*node ATTRIBUTE_UNUSED
, tree
ARG_UNUSED (name
),
3209 tree args
, int ARG_UNUSED (flags
),
3210 bool *no_add_attrs ATTRIBUTE_UNUSED
)
3213 && TREE_CODE (TREE_VALUE (args
)) == STRING_CST
3214 && !TREE_CHAIN (args
));
3218 /* Handle a "warn_unused" attribute; arguments as in
3219 struct attribute_spec.handler. */
3222 handle_warn_unused_attribute (tree
*node
, tree name
,
3223 tree args ATTRIBUTE_UNUSED
,
3224 int flags ATTRIBUTE_UNUSED
, bool *no_add_attrs
)
3227 /* Do nothing else, just set the attribute. We'll get at
3228 it later with lookup_attribute. */
3232 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3233 *no_add_attrs
= true;
3239 /* Handle an "omp declare simd" attribute; arguments as in
3240 struct attribute_spec.handler. */
3243 handle_omp_declare_simd_attribute (tree
*, tree
, tree
, int, bool *)
3248 /* Handle an "omp declare variant {base,variant}" attribute; arguments as in
3249 struct attribute_spec.handler. */
3252 handle_omp_declare_variant_attribute (tree
*, tree
, tree
, int, bool *)
3257 /* Handle a "simd" attribute. */
3260 handle_simd_attribute (tree
*node
, tree name
, tree args
, int, bool *no_add_attrs
)
3262 if (TREE_CODE (*node
) == FUNCTION_DECL
)
3264 tree t
= get_identifier ("omp declare simd");
3265 tree attr
= NULL_TREE
;
3268 tree id
= TREE_VALUE (args
);
3270 if (TREE_CODE (id
) != STRING_CST
)
3272 error ("attribute %qE argument not a string", name
);
3273 *no_add_attrs
= true;
3277 if (strcmp (TREE_STRING_POINTER (id
), "notinbranch") == 0)
3278 attr
= build_omp_clause (DECL_SOURCE_LOCATION (*node
),
3279 OMP_CLAUSE_NOTINBRANCH
);
3280 else if (strcmp (TREE_STRING_POINTER (id
), "inbranch") == 0)
3281 attr
= build_omp_clause (DECL_SOURCE_LOCATION (*node
),
3282 OMP_CLAUSE_INBRANCH
);
3285 error ("only %<inbranch%> and %<notinbranch%> flags are "
3286 "allowed for %<__simd__%> attribute");
3287 *no_add_attrs
= true;
3292 DECL_ATTRIBUTES (*node
)
3293 = tree_cons (t
, build_tree_list (NULL_TREE
, attr
),
3294 DECL_ATTRIBUTES (*node
));
3298 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3299 *no_add_attrs
= true;
3305 /* Handle an "omp declare target" attribute; arguments as in
3306 struct attribute_spec.handler. */
3309 handle_omp_declare_target_attribute (tree
*, tree
, tree
, int, bool *)
3314 /* Handle a "returns_twice" attribute; arguments as in
3315 struct attribute_spec.handler. */
3318 handle_returns_twice_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
3319 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3321 if (TREE_CODE (*node
) == FUNCTION_DECL
)
3322 DECL_IS_RETURNS_TWICE (*node
) = 1;
3325 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3326 *no_add_attrs
= true;
3332 /* Handle a "no_limit_stack" attribute; arguments as in
3333 struct attribute_spec.handler. */
3336 handle_no_limit_stack_attribute (tree
*node
, tree name
,
3337 tree
ARG_UNUSED (args
),
3338 int ARG_UNUSED (flags
),
3343 if (TREE_CODE (decl
) != FUNCTION_DECL
)
3345 error_at (DECL_SOURCE_LOCATION (decl
),
3346 "%qE attribute applies only to functions", name
);
3347 *no_add_attrs
= true;
3349 else if (DECL_INITIAL (decl
))
3351 error_at (DECL_SOURCE_LOCATION (decl
),
3352 "cannot set %qE attribute after definition", name
);
3353 *no_add_attrs
= true;
3356 DECL_NO_LIMIT_STACK (decl
) = 1;
3361 /* Handle a "pure" attribute; arguments as in
3362 struct attribute_spec.handler. */
3365 handle_pure_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
3366 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3368 if (TREE_CODE (*node
) == FUNCTION_DECL
)
3370 tree type
= TREE_TYPE (*node
);
3371 if (VOID_TYPE_P (TREE_TYPE (type
)))
3372 warning (OPT_Wattributes
, "%qE attribute on function "
3373 "returning %<void%>", name
);
3375 DECL_PURE_P (*node
) = 1;
3376 /* ??? TODO: Support types. */
3380 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3381 *no_add_attrs
= true;
3387 /* Digest an attribute list destined for a transactional memory statement.
3388 ALLOWED is the set of attributes that are allowed for this statement;
3389 return the attribute we parsed. Multiple attributes are never allowed. */
3392 parse_tm_stmt_attr (tree attrs
, int allowed
)
3397 for ( ; attrs
; attrs
= TREE_CHAIN (attrs
))
3399 tree a
= get_attribute_name (attrs
);
3400 tree ns
= get_attribute_namespace (attrs
);
3403 if (is_attribute_p ("outer", a
)
3404 && (ns
== NULL_TREE
|| strcmp (IDENTIFIER_POINTER (ns
), "gnu") == 0))
3405 m
= TM_STMT_ATTR_OUTER
;
3407 if ((m
& allowed
) == 0)
3409 warning (OPT_Wattributes
, "%qE attribute directive ignored", a
);
3418 else if (m_seen
== m
)
3419 warning (OPT_Wattributes
, "%qE attribute duplicated", a
);
3421 warning (OPT_Wattributes
, "%qE attribute follows %qE", a
, a_seen
);
3427 /* Transform a TM attribute name into a maskable integer and back.
3428 Note that NULL (i.e. no attribute) is mapped to UNKNOWN, corresponding
3429 to how the lack of an attribute is treated. */
3432 tm_attr_to_mask (tree attr
)
3436 if (is_attribute_p ("transaction_safe", attr
))
3437 return TM_ATTR_SAFE
;
3438 if (is_attribute_p ("transaction_callable", attr
))
3439 return TM_ATTR_CALLABLE
;
3440 if (is_attribute_p ("transaction_pure", attr
))
3441 return TM_ATTR_PURE
;
3442 if (is_attribute_p ("transaction_unsafe", attr
))
3443 return TM_ATTR_IRREVOCABLE
;
3444 if (is_attribute_p ("transaction_may_cancel_outer", attr
))
3445 return TM_ATTR_MAY_CANCEL_OUTER
;
3450 tm_mask_to_attr (int mask
)
3456 str
= "transaction_safe";
3458 case TM_ATTR_CALLABLE
:
3459 str
= "transaction_callable";
3462 str
= "transaction_pure";
3464 case TM_ATTR_IRREVOCABLE
:
3465 str
= "transaction_unsafe";
3467 case TM_ATTR_MAY_CANCEL_OUTER
:
3468 str
= "transaction_may_cancel_outer";
3473 return get_identifier (str
);
3476 /* Return the first TM attribute seen in LIST. */
3479 find_tm_attribute (tree list
)
3481 for (; list
; list
= TREE_CHAIN (list
))
3483 tree name
= get_attribute_name (list
);
3484 if (tm_attr_to_mask (name
) != 0)
3490 /* Handle the TM attributes; arguments as in struct attribute_spec.handler.
3491 Here we accept only function types, and verify that none of the other
3492 function TM attributes are also applied. */
3493 /* ??? We need to accept class types for C++, but not C. This greatly
3494 complicates this function, since we can no longer rely on the extra
3495 processing given by function_type_required. */
3498 handle_tm_attribute (tree
*node
, tree name
, tree args
,
3499 int flags
, bool *no_add_attrs
)
3501 /* Only one path adds the attribute; others don't. */
3502 *no_add_attrs
= true;
3504 switch (TREE_CODE (*node
))
3508 /* Only tm_callable and tm_safe apply to classes. */
3509 if (tm_attr_to_mask (name
) & ~(TM_ATTR_SAFE
| TM_ATTR_CALLABLE
))
3516 tree old_name
= find_tm_attribute (TYPE_ATTRIBUTES (*node
));
3517 if (old_name
== name
)
3519 else if (old_name
!= NULL_TREE
)
3520 error ("type was previously declared %qE", old_name
);
3522 *no_add_attrs
= false;
3528 /* transaction_safe_dynamic goes on the FUNCTION_DECL, but we also
3529 want to set transaction_safe on the type. */
3530 gcc_assert (is_attribute_p ("transaction_safe_dynamic", name
));
3531 if (!TYPE_P (DECL_CONTEXT (*node
)))
3532 error_at (DECL_SOURCE_LOCATION (*node
),
3533 "%<transaction_safe_dynamic%> may only be specified for "
3534 "a virtual function");
3535 *no_add_attrs
= false;
3536 decl_attributes (&TREE_TYPE (*node
),
3537 build_tree_list (get_identifier ("transaction_safe"),
3545 enum tree_code subcode
= TREE_CODE (TREE_TYPE (*node
));
3546 if (subcode
== FUNCTION_TYPE
|| subcode
== METHOD_TYPE
)
3548 tree fn_tmp
= TREE_TYPE (*node
);
3549 decl_attributes (&fn_tmp
, tree_cons (name
, args
, NULL
), 0);
3550 *node
= build_pointer_type (fn_tmp
);
3557 /* If a function is next, pass it on to be tried next. */
3558 if (flags
& (int) ATTR_FLAG_FUNCTION_NEXT
)
3559 return tree_cons (name
, args
, NULL
);
3562 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3569 /* Handle the TM_WRAP attribute; arguments as in
3570 struct attribute_spec.handler. */
3573 handle_tm_wrap_attribute (tree
*node
, tree name
, tree args
,
3574 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3578 /* We don't need the attribute even on success, since we
3579 record the entry in an external table. */
3580 *no_add_attrs
= true;
3582 if (TREE_CODE (decl
) != FUNCTION_DECL
)
3583 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3586 tree wrap_decl
= TREE_VALUE (args
);
3587 if (error_operand_p (wrap_decl
))
3589 else if (TREE_CODE (wrap_decl
) != IDENTIFIER_NODE
3590 && !VAR_OR_FUNCTION_DECL_P (wrap_decl
))
3591 error ("%qE argument not an identifier", name
);
3594 if (TREE_CODE (wrap_decl
) == IDENTIFIER_NODE
)
3595 wrap_decl
= lookup_name (wrap_decl
);
3596 if (wrap_decl
&& TREE_CODE (wrap_decl
) == FUNCTION_DECL
)
3598 if (lang_hooks
.types_compatible_p (TREE_TYPE (decl
),
3599 TREE_TYPE (wrap_decl
)))
3600 record_tm_replacement (wrap_decl
, decl
);
3602 error ("%qD is not compatible with %qD", wrap_decl
, decl
);
3605 error ("%qE argument is not a function", name
);
3612 /* Ignore the given attribute. Used when this attribute may be usefully
3613 overridden by the target, but is not used generically. */
3616 ignore_attribute (tree
* ARG_UNUSED (node
), tree
ARG_UNUSED (name
),
3617 tree
ARG_UNUSED (args
), int ARG_UNUSED (flags
),
3620 *no_add_attrs
= true;
3624 /* Handle a "no vops" attribute; arguments as in
3625 struct attribute_spec.handler. */
3628 handle_novops_attribute (tree
*node
, tree
ARG_UNUSED (name
),
3629 tree
ARG_UNUSED (args
), int ARG_UNUSED (flags
),
3630 bool *ARG_UNUSED (no_add_attrs
))
3632 gcc_assert (TREE_CODE (*node
) == FUNCTION_DECL
);
3633 DECL_IS_NOVOPS (*node
) = 1;
3637 /* Handle a "deprecated" attribute; arguments as in
3638 struct attribute_spec.handler. */
3641 handle_deprecated_attribute (tree
*node
, tree name
,
3642 tree args
, int flags
,
3645 tree type
= NULL_TREE
;
3647 tree what
= NULL_TREE
;
3650 *no_add_attrs
= true;
3651 else if (TREE_CODE (TREE_VALUE (args
)) != STRING_CST
)
3653 error ("deprecated message is not a string");
3654 *no_add_attrs
= true;
3660 type
= TREE_TYPE (decl
);
3662 if (TREE_CODE (decl
) == TYPE_DECL
3663 || TREE_CODE (decl
) == PARM_DECL
3664 || VAR_OR_FUNCTION_DECL_P (decl
)
3665 || TREE_CODE (decl
) == FIELD_DECL
3666 || TREE_CODE (decl
) == CONST_DECL
3667 || objc_method_decl (TREE_CODE (decl
)))
3668 TREE_DEPRECATED (decl
) = 1;
3672 else if (TYPE_P (*node
))
3674 if (!(flags
& (int) ATTR_FLAG_TYPE_IN_PLACE
))
3675 *node
= build_variant_type_copy (*node
);
3676 TREE_DEPRECATED (*node
) = 1;
3684 *no_add_attrs
= true;
3685 if (type
&& TYPE_NAME (type
))
3687 if (TREE_CODE (TYPE_NAME (type
)) == IDENTIFIER_NODE
)
3688 what
= TYPE_NAME (*node
);
3689 else if (TREE_CODE (TYPE_NAME (type
)) == TYPE_DECL
3690 && DECL_NAME (TYPE_NAME (type
)))
3691 what
= DECL_NAME (TYPE_NAME (type
));
3694 warning (OPT_Wattributes
, "%qE attribute ignored for %qE", name
, what
);
3696 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3702 /* Return the "base" type from TYPE that is suitable to apply attribute
3703 vector_size to by stripping arrays, function types, etc. */
3705 type_for_vector_size (tree type
)
3707 /* We need to provide for vector pointers, vector arrays, and
3708 functions returning vectors. For example:
3710 __attribute__((vector_size(16))) short *foo;
3712 In this case, the mode is SI, but the type being modified is
3713 HI, so we need to look further. */
3715 while (POINTER_TYPE_P (type
)
3716 || TREE_CODE (type
) == FUNCTION_TYPE
3717 || TREE_CODE (type
) == METHOD_TYPE
3718 || TREE_CODE (type
) == ARRAY_TYPE
3719 || TREE_CODE (type
) == OFFSET_TYPE
)
3720 type
= TREE_TYPE (type
);
3725 /* Given TYPE, return the base type to which the vector_size attribute
3726 ATNAME with ARGS, when non-null, can be applied, if one exists.
3727 On success and when both ARGS and PTRNUNITS are non-null, set
3728 *PTRNUNINTS to the number of vector units. When PTRNUNITS is not
3729 null, issue a warning when the attribute argument is not constant
3730 and an error if there is no such type. Otherwise issue a warning
3731 in the latter case and return null. */
3734 type_valid_for_vector_size (tree type
, tree atname
, tree args
,
3735 unsigned HOST_WIDE_INT
*ptrnunits
)
3737 bool error_p
= ptrnunits
!= NULL
;
3739 /* Get the mode of the type being modified. */
3740 machine_mode orig_mode
= TYPE_MODE (type
);
3742 if ((!INTEGRAL_TYPE_P (type
)
3743 && !SCALAR_FLOAT_TYPE_P (type
)
3744 && !FIXED_POINT_TYPE_P (type
))
3745 || (!SCALAR_FLOAT_MODE_P (orig_mode
)
3746 && GET_MODE_CLASS (orig_mode
) != MODE_INT
3747 && !ALL_SCALAR_FIXED_POINT_MODE_P (orig_mode
))
3748 || !tree_fits_uhwi_p (TYPE_SIZE_UNIT (type
))
3749 || TREE_CODE (type
) == BOOLEAN_TYPE
)
3752 error ("invalid vector type for attribute %qE", atname
);
3754 warning (OPT_Wattributes
, "invalid vector type for attribute %qE",
3759 /* When no argument has been provided this is just a request to validate
3760 the type above. Return TYPE to indicate success. */
3764 tree size
= TREE_VALUE (args
);
3765 /* Erroneous arguments have already been diagnosed. */
3766 if (size
== error_mark_node
)
3769 if (size
&& TREE_CODE (size
) != IDENTIFIER_NODE
3770 && TREE_CODE (size
) != FUNCTION_DECL
)
3771 size
= default_conversion (size
);
3773 if (TREE_CODE (size
) != INTEGER_CST
)
3776 error ("%qE attribute argument value %qE is not an integer constant",
3779 warning (OPT_Wattributes
,
3780 "%qE attribute argument value %qE is not an integer constant",
3785 if (!TYPE_UNSIGNED (TREE_TYPE (size
))
3786 && tree_int_cst_sgn (size
) < 0)
3789 error ("%qE attribute argument value %qE is negative",
3792 warning (OPT_Wattributes
,
3793 "%qE attribute argument value %qE is negative",
3798 /* The attribute argument value is constrained by the maximum bit
3799 alignment representable in unsigned int on the host. */
3800 unsigned HOST_WIDE_INT vecsize
;
3801 unsigned HOST_WIDE_INT maxsize
= tree_to_uhwi (max_object_size ());
3802 if (!tree_fits_uhwi_p (size
)
3803 || (vecsize
= tree_to_uhwi (size
)) > maxsize
)
3806 error ("%qE attribute argument value %qE exceeds %wu",
3807 atname
, size
, maxsize
);
3809 warning (OPT_Wattributes
,
3810 "%qE attribute argument value %qE exceeds %wu",
3811 atname
, size
, maxsize
);
3815 if (vecsize
% tree_to_uhwi (TYPE_SIZE_UNIT (type
)))
3818 error ("vector size not an integral multiple of component size");
3824 error ("zero vector size");
3828 /* Calculate how many units fit in the vector. */
3829 unsigned HOST_WIDE_INT nunits
= vecsize
/ tree_to_uhwi (TYPE_SIZE_UNIT (type
));
3830 if (nunits
& (nunits
- 1))
3833 error ("number of components of the vector not a power of two");
3835 warning (OPT_Wattributes
,
3836 "number of components of the vector not a power of two");
3841 *ptrnunits
= nunits
;
3846 /* Handle a "vector_size" attribute; arguments as in
3847 struct attribute_spec.handler. */
3850 handle_vector_size_attribute (tree
*node
, tree name
, tree args
,
3851 int ARG_UNUSED (flags
),
3854 *no_add_attrs
= true;
3856 /* Determine the "base" type to apply the attribute to. */
3857 tree type
= type_for_vector_size (*node
);
3859 /* Get the vector size (in bytes) and let the function compute
3860 the number of vector units. */
3861 unsigned HOST_WIDE_INT nunits
;
3862 type
= type_valid_for_vector_size (type
, name
, args
, &nunits
);
3866 gcc_checking_assert (args
!= NULL
);
3868 tree new_type
= build_vector_type (type
, nunits
);
3870 /* Build back pointers if needed. */
3871 *node
= lang_hooks
.types
.reconstruct_complex_type (*node
, new_type
);
3876 /* Handle the "nonnull" attribute. */
3879 handle_nonnull_attribute (tree
*node
, tree name
,
3880 tree args
, int ARG_UNUSED (flags
),
3885 /* If no arguments are specified, all pointer arguments should be
3886 non-null. Verify a full prototype is given so that the arguments
3887 will have the correct types when we actually check them later.
3888 Avoid diagnosing type-generic built-ins since those have no
3892 if (!prototype_p (type
)
3893 && (!TYPE_ATTRIBUTES (type
)
3894 || !lookup_attribute ("type generic", TYPE_ATTRIBUTES (type
))))
3896 error ("%qE attribute without arguments on a non-prototype",
3898 *no_add_attrs
= true;
3903 for (int i
= 1; args
; ++i
)
3905 tree pos
= TREE_VALUE (args
);
3906 /* NEXT is null when the attribute includes just one argument.
3907 That's used to tell positional_argument to avoid mentioning
3908 the argument number in diagnostics (since there's just one
3909 mentioning it is unnecessary and coule be confusing). */
3910 tree next
= TREE_CHAIN (args
);
3911 if (tree val
= positional_argument (type
, name
, pos
, POINTER_TYPE
,
3912 next
|| i
> 1 ? i
: 0))
3913 TREE_VALUE (args
) = val
;
3916 *no_add_attrs
= true;
3925 /* Handle the "nonstring" variable attribute. */
3928 handle_nonstring_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
3929 int ARG_UNUSED (flags
), bool *no_add_attrs
)
3932 tree_code code
= TREE_CODE (*node
);
3935 || code
== FIELD_DECL
3936 || code
== PARM_DECL
)
3938 tree type
= TREE_TYPE (*node
);
3940 if (POINTER_TYPE_P (type
) || TREE_CODE (type
) == ARRAY_TYPE
)
3942 /* Accept the attribute on arrays and pointers to all three
3943 narrow character types. */
3944 tree eltype
= TREE_TYPE (type
);
3945 eltype
= TYPE_MAIN_VARIANT (eltype
);
3946 if (eltype
== char_type_node
3947 || eltype
== signed_char_type_node
3948 || eltype
== unsigned_char_type_node
)
3952 warning (OPT_Wattributes
,
3953 "%qE attribute ignored on objects of type %qT",
3955 *no_add_attrs
= true;
3959 if (code
== FUNCTION_DECL
)
3960 warning (OPT_Wattributes
,
3961 "%qE attribute does not apply to functions", name
);
3962 else if (code
== TYPE_DECL
)
3963 warning (OPT_Wattributes
,
3964 "%qE attribute does not apply to types", name
);
3966 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
3968 *no_add_attrs
= true;
3972 /* Given a function type FUNCTYPE, returns the type of the parameter
3973 ARGNO or null if ARGNO exceeds the number of parameters. On failure
3974 set *NARGS to the number of function parameters. */
3977 get_argument_type (tree functype
, unsigned argno
, unsigned *nargs
)
3979 function_args_iterator iter
;
3980 function_args_iter_init (&iter
, functype
);
3984 for ( ; iter
.next
; ++count
, function_args_iter_next (&iter
))
3986 if (count
+ 1 == argno
)
3988 tree argtype
= function_args_iter_cond (&iter
);
3989 if (VOID_TYPE_P (argtype
))
3991 if (argtype
!= error_mark_node
)
4000 /* Given a function FNDECL return the function argument at the zero-
4001 based position ARGNO or null if it can't be found. */
4004 get_argument (tree fndecl
, unsigned argno
)
4006 if (!DECL_P (fndecl
))
4010 for (tree arg
= DECL_ARGUMENTS (fndecl
); arg
; arg
= TREE_CHAIN (arg
))
4017 /* Attempt to append attribute access specification ATTRSPEC, optionally
4018 described by the human-readable string ATTRSTR, for type T, to one in
4019 ATTRS. VBLIST is an optional list of bounds of variable length array
4020 parameters described by ATTRSTR.
4021 Issue warning for conflicts and return null if any are found.
4022 Return the concatenated access string on success. */
4025 append_access_attr (tree node
[3], tree attrs
, const char *attrstr
,
4026 const char *attrspec
, tree vblist
= NULL_TREE
)
4028 tree argstr
= build_string (strlen (attrspec
) + 1, attrspec
);
4029 tree ataccess
= tree_cons (NULL_TREE
, argstr
, vblist
);
4030 ataccess
= tree_cons (get_identifier ("access"), ataccess
, NULL_TREE
);
4032 /* The access specification being applied. This may be an implicit
4033 access spec synthesized for array (or VLA) parameters even for
4034 a declaration with an explicit access spec already applied, if
4035 this call corresponds to the first declaration of the function. */
4037 init_attr_rdwr_indices (&new_idxs
, ataccess
);
4039 /* The current access specification alrady applied. */
4041 init_attr_rdwr_indices (&cur_idxs
, attrs
);
4044 for (auto it
= new_idxs
.begin (); it
!= new_idxs
.end (); ++it
)
4046 const auto &newaxsref
= *it
;
4048 /* The map has two equal entries for each pointer argument that
4049 has an associated size argument. Process just the entry for
4051 if ((unsigned)newaxsref
.first
!= newaxsref
.second
.ptrarg
)
4054 const attr_access
* const cura
= cur_idxs
.get (newaxsref
.first
);
4057 /* The new attribute needs to be added. */
4058 tree str
= newaxsref
.second
.to_internal_string ();
4059 spec
+= TREE_STRING_POINTER (str
);
4063 /* The new access spec refers to an array/pointer argument for
4064 which an access spec already exists. Check and diagnose any
4065 conflicts. If no conflicts are found, merge the two. */
4066 const attr_access
* const newa
= &newaxsref
.second
;
4070 tree str
= NULL_TREE
;
4071 if (newa
->mode
!= access_deferred
)
4072 str
= newa
->to_external_string ();
4073 else if (cura
->mode
!= access_deferred
)
4074 str
= cura
->to_external_string ();
4076 attrstr
= TREE_STRING_POINTER (str
);
4079 location_t curloc
= input_location
;
4080 if (node
[2] && DECL_P (node
[2]))
4081 curloc
= DECL_SOURCE_LOCATION (node
[2]);
4083 location_t prevloc
= UNKNOWN_LOCATION
;
4084 if (node
[1] && DECL_P (node
[1]))
4085 prevloc
= DECL_SOURCE_LOCATION (node
[1]);
4087 if (newa
->mode
!= cura
->mode
4088 && newa
->mode
!= access_deferred
4089 && cura
->mode
!= access_deferred
4090 && newa
->internal_p
== cura
->internal_p
)
4092 /* Mismatch in access mode. */
4093 auto_diagnostic_group d
;
4094 if (warning_at (curloc
, OPT_Wattributes
,
4095 "attribute %qs mismatch with mode %qs",
4096 attrstr
, cura
->mode_names
[cura
->mode
])
4097 && prevloc
!= UNKNOWN_LOCATION
)
4098 inform (prevloc
, "previous declaration here");
4102 /* Set if PTRARG refers to a VLA with an unspecified bound (T[*]).
4103 Be prepared for either CURA or NEWA to refer to it, depending
4104 on which happens to come first in the declaration. */
4105 const bool cur_vla_ub
= (cura
->internal_p
4106 && cura
->sizarg
== UINT_MAX
4107 && cura
->minsize
== HOST_WIDE_INT_M1U
);
4108 const bool new_vla_ub
= (newa
->internal_p
4109 && newa
->sizarg
== UINT_MAX
4110 && newa
->minsize
== HOST_WIDE_INT_M1U
);
4112 if (newa
->sizarg
!= cura
->sizarg
4114 && (!(cur_vla_ub
^ new_vla_ub
)
4115 || (!cura
->internal_p
&& !newa
->internal_p
)))
4117 /* Avoid diagnosing redeclarations of functions with no explicit
4118 attribute access that add one. */
4119 if (newa
->mode
== access_deferred
4120 && cura
->mode
!= access_deferred
4121 && newa
->sizarg
== UINT_MAX
4122 && cura
->sizarg
!= UINT_MAX
)
4125 if (cura
->mode
== access_deferred
4126 && newa
->mode
!= access_deferred
4127 && cura
->sizarg
== UINT_MAX
4128 && newa
->sizarg
!= UINT_MAX
)
4131 /* The two specs designate different size arguments. It's okay
4132 for the explicit spec to specify a size where none is provided
4133 by the implicit (VLA) one, as in:
4134 __attribute__ ((access (read_write, 1, 2)))
4136 but not for two explicit access attributes to do that. */
4137 bool warned
= false;
4139 auto_diagnostic_group d
;
4141 if (newa
->sizarg
== UINT_MAX
)
4142 /* Mismatch in the presence of the size argument. */
4143 warned
= warning_at (curloc
, OPT_Wattributes
,
4144 "attribute %qs missing positional argument 2 "
4145 "provided in previous designation by argument "
4146 "%u", attrstr
, cura
->sizarg
+ 1);
4147 else if (cura
->sizarg
== UINT_MAX
)
4148 /* Mismatch in the presence of the size argument. */
4149 warned
= warning_at (curloc
, OPT_Wattributes
,
4150 "attribute %qs positional argument 2 "
4151 "missing in previous designation",
4153 else if (newa
->internal_p
|| cura
->internal_p
)
4154 /* Mismatch in the value of the size argument and a VLA bound. */
4155 warned
= warning_at (curloc
, OPT_Wattributes
,
4156 "attribute %qs positional argument 2 "
4157 "conflicts with previous designation "
4159 attrstr
, cura
->sizarg
+ 1);
4161 /* Mismatch in the value of the size argument between two
4162 explicit access attributes. */
4163 warned
= warning_at (curloc
, OPT_Wattributes
,
4164 "attribute %qs mismatched positional argument "
4166 attrstr
, newa
->sizarg
+ 1, cura
->sizarg
+ 1);
4170 /* If the previous declaration is a function (as opposed
4171 to a typedef of one), find the location of the array
4172 or pointer argument that uses the conflicting VLA bound
4173 and point to it in the note. */
4174 const attr_access
* const pa
= cura
->size
? cura
: newa
;
4175 tree size
= pa
->size
? TREE_VALUE (pa
->size
) : NULL_TREE
;
4176 if (size
&& DECL_P (size
))
4178 location_t argloc
= UNKNOWN_LOCATION
;
4179 if (tree arg
= get_argument (node
[2], pa
->ptrarg
))
4180 argloc
= DECL_SOURCE_LOCATION (arg
);
4182 gcc_rich_location
richloc (DECL_SOURCE_LOCATION (size
));
4183 if (argloc
!= UNKNOWN_LOCATION
)
4184 richloc
.add_range (argloc
);
4186 inform (&richloc
, "designating the bound of variable "
4187 "length array argument %u",
4190 else if (prevloc
!= UNKNOWN_LOCATION
)
4191 inform (prevloc
, "previous declaration here");
4197 if (newa
->internal_p
== cura
->internal_p
)
4200 /* Merge the CURA and NEWA. */
4201 attr_access merged
= newaxsref
.second
;
4203 /* VLA seen in a declaration takes precedence. */
4204 if (cura
->minsize
== HOST_WIDE_INT_M1U
)
4205 merged
.minsize
= HOST_WIDE_INT_M1U
;
4207 /* Use the explicitly specified size positional argument. */
4208 if (cura
->sizarg
!= UINT_MAX
)
4209 merged
.sizarg
= cura
->sizarg
;
4211 /* Use the explicitly specified mode. */
4212 if (merged
.mode
== access_deferred
)
4213 merged
.mode
= cura
->mode
;
4215 tree str
= merged
.to_internal_string ();
4216 spec
+= TREE_STRING_POINTER (str
);
4219 if (!spec
.length ())
4222 return build_string (spec
.length (), spec
.c_str ());
4225 /* Convenience wrapper for the above. */
4228 append_access_attr (tree node
[3], tree attrs
, const char *attrstr
,
4229 char code
, HOST_WIDE_INT idxs
[2])
4232 int n
= sprintf (attrspec
, "%c%u", code
, (unsigned) idxs
[0] - 1);
4234 n
+= sprintf (attrspec
+ n
, ",%u", (unsigned) idxs
[1] - 1);
4236 return append_access_attr (node
, attrs
, attrstr
, attrspec
);
4239 /* Handle the access attribute for function type NODE[0], with the function
4240 DECL optionally in NODE[1]. The handler is called both in response to
4241 an explict attribute access on a declaration with a mode and one or two
4242 positional arguments, and for internally synthesized access specifications
4243 with a string argument optionally followd by a DECL or expression
4244 representing a VLA bound. To speed up parsing, the handler transforms
4245 the attribute and its arguments into a string. */
4248 handle_access_attribute (tree node
[3], tree name
, tree args
,
4249 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4251 tree attrs
= TYPE_ATTRIBUTES (*node
);
4253 if (POINTER_TYPE_P (type
))
4255 tree ptype
= TREE_TYPE (type
);
4256 if (FUNC_OR_METHOD_TYPE_P (ptype
))
4260 *no_add_attrs
= true;
4262 /* Verify a full prototype is provided so that the argument types
4263 can be validated. Avoid diagnosing type-generic built-ins since
4264 those have no prototype. */
4266 && !prototype_p (type
)
4267 && (!attrs
|| !lookup_attribute ("type generic", attrs
)))
4269 error ("attribute %qE without arguments on a non-prototype", name
);
4273 tree access_mode
= TREE_VALUE (args
);
4274 if (TREE_CODE (access_mode
) == STRING_CST
)
4276 const char* const str
= TREE_STRING_POINTER (access_mode
);
4279 /* This is a request to merge an internal specification for
4280 a function declaration involving arrays but no explicit
4281 attribute access. */
4282 tree vblist
= TREE_CHAIN (args
);
4283 tree axstr
= append_access_attr (node
, attrs
, NULL
, str
+ 1,
4288 /* Replace any existing access attribute specification with
4289 the concatenation above. */
4290 tree axsat
= tree_cons (NULL_TREE
, axstr
, vblist
);
4291 axsat
= tree_cons (name
, axsat
, NULL_TREE
);
4293 /* Recursively call self to "replace" the documented/external
4294 form of the attribute with the condensend internal form. */
4295 decl_attributes (node
, axsat
, flags
);
4299 /* This is a recursive call to handle the condensed internal form
4300 of the attribute (see below). Since all validation has been
4301 done simply return here, accepting the attribute as is. */
4302 *no_add_attrs
= false;
4306 /* Set to true when the access mode has the form of a function call
4307 as in 'attribute (read_only (1, 2))'. That's an easy mistake to
4308 make and so worth a special diagnostic. */
4309 bool funcall
= false;
4310 if (TREE_CODE (access_mode
) == CALL_EXPR
)
4312 access_mode
= CALL_EXPR_FN (access_mode
);
4313 if (TREE_CODE (access_mode
) != ADDR_EXPR
)
4315 error ("attribute %qE invalid mode", name
);
4318 access_mode
= TREE_OPERAND (access_mode
, 0);
4319 access_mode
= DECL_NAME (access_mode
);
4323 const char* const access_str
= IDENTIFIER_POINTER (access_mode
);
4324 const char *ps
= access_str
;
4325 if (ps
[0] == '_' && ps
[1] == '_')
4327 size_t len
= strlen (ps
);
4328 if (ps
[len
- 1] == '_' && ps
[len
- 2] == '_')
4336 sizeof attr_access::mode_names
/ sizeof *attr_access::mode_names
;
4338 for (imode
= 0; imode
!= nmodes
; ++imode
)
4339 if (!strncmp (ps
, attr_access::mode_names
[imode
],
4340 strlen (attr_access::mode_names
[imode
])))
4343 if (imode
== nmodes
)
4345 error ("attribute %qE invalid mode %qs; expected one of "
4346 "%qs, %qs, %qs, or %qs", name
, access_str
,
4347 "read_only", "read_write", "write_only", "none");
4352 const ::access_mode mode
= static_cast<::access_mode
>(imode
);
4356 error ("attribute %qE unexpected %<(%> after mode %qs; expected "
4357 "a positional argument or %<)%>",
4362 args
= TREE_CHAIN (args
);
4365 /* The first positional argument is required. It may be worth
4366 dropping the requirement at some point and having read_only
4367 apply to all const-qualified pointers and read_write or
4368 write_only to the rest. */
4369 error ("attribute %<%E(%s)%> missing an argument",
4374 /* One or more positional arguments have been specified. Validate
4376 tree idxnodes
[2] = { NULL_TREE
, NULL_TREE
};
4377 tree argtypes
[2] = { NULL_TREE
, NULL_TREE
};
4378 /* 1-based attribute positional arguments or zero if not specified.
4379 Invalid negative or excessive values are also stored but used
4380 only in diagnostics. */
4381 HOST_WIDE_INT idxs
[2] = { 0, 0 };
4383 /* Number of function formal arguments (used in diagnostics). */
4384 unsigned nfuncargs
= 0;
4385 /* Number of (optional) attribute positional arguments. */
4386 unsigned nattrargs
= 0;
4388 for (unsigned i
= 0; i
!= 2; ++i
, args
= TREE_CHAIN (args
), ++nattrargs
)
4393 idxnodes
[i
] = TREE_VALUE (args
);
4395 if (TREE_CODE (idxnodes
[i
]) != IDENTIFIER_NODE
4396 && TREE_CODE (idxnodes
[i
]) != FUNCTION_DECL
)
4397 idxnodes
[i
] = default_conversion (idxnodes
[i
]);
4399 if (tree_fits_shwi_p (idxnodes
[i
]))
4401 idxs
[i
] = tree_to_shwi (idxnodes
[i
]);
4402 argtypes
[i
] = get_argument_type (type
, idxs
[i
], &nfuncargs
);
4406 if ((nattrargs
== 1 && !idxs
[0])
4407 || (nattrargs
== 2 && (!idxs
[0] || !idxs
[1])))
4410 error ("attribute %<%E(%s, %E, %E)%> invalid positional argument %i",
4411 name
, access_str
, idxnodes
[0], idxnodes
[1], idxs
[0] ? 2 : 1);
4413 error ("attribute %<%E(%s, %E)%> invalid positional argument %i",
4414 name
, access_str
, idxnodes
[0], idxs
[0] ? 2 : 1);
4418 /* Format the attribute specification to include in diagnostics. */
4421 snprintf (attrstr
, sizeof attrstr
, "%s(%s, %lli, %lli)",
4422 IDENTIFIER_POINTER (name
), access_str
,
4423 (long long) idxs
[0], (long long) idxs
[1]);
4424 else if (idxnodes
[0])
4425 snprintf (attrstr
, sizeof attrstr
, "%s(%s, %lli)",
4426 IDENTIFIER_POINTER (name
), access_str
,
4427 (long long) idxs
[0]);
4429 snprintf (attrstr
, sizeof attrstr
, "%s(%s)",
4430 IDENTIFIER_POINTER (name
), access_str
);
4432 /* Verify the positional argument values are in range. */
4433 if (!argtypes
[0] || (idxnodes
[1] && !argtypes
[1]))
4437 if (idxs
[0] < 0 || idxs
[1] < 0)
4438 error ("attribute %qs positional argument %i invalid value %wi",
4439 attrstr
, idxs
[0] < 0 ? 1 : 2,
4440 idxs
[0] < 0 ? idxs
[0] : idxs
[1]);
4442 error ("attribute %qs positional argument %i value %wi exceeds "
4443 "number of function arguments %u",
4444 attrstr
, idxs
[0] ? 1 : 2,
4445 idxs
[0] ? idxs
[0] : idxs
[1],
4449 error ("attribute %qs invalid positional argument", attrstr
);
4454 if (!POINTER_TYPE_P (argtypes
[0]))
4456 /* The first argument must have a pointer or reference type. */
4457 error ("attribute %qs positional argument 1 references "
4458 "non-pointer argument type %qT",
4459 attrstr
, argtypes
[0]);
4464 /* Pointers to functions are not allowed. */
4465 tree ptrtype
= TREE_TYPE (argtypes
[0]);
4466 if (FUNC_OR_METHOD_TYPE_P (ptrtype
))
4468 error ("attribute %qs positional argument 1 references "
4469 "argument of function type %qT",
4475 if (mode
== access_read_write
|| mode
== access_write_only
)
4477 /* Read_write and write_only modes must reference non-const
4479 if (TYPE_READONLY (TREE_TYPE (argtypes
[0])))
4481 error ("attribute %qs positional argument 1 references "
4482 "%qs-qualified argument type %qT",
4483 attrstr
, "const", argtypes
[0]);
4487 else if (!TYPE_READONLY (TREE_TYPE (argtypes
[0])))
4489 /* A read_only mode should ideally reference const-qualified
4490 arguments but it's not diagnosed error if one doesn't.
4491 This makes it possible to annotate legacy, const-incorrect
4492 APIs. It might be worth a diagnostic along the lines of
4497 if (argtypes
[1] && !INTEGRAL_TYPE_P (argtypes
[1]))
4499 error ("attribute %qs positional argument 2 references "
4500 "non-integer argument type %qT",
4501 attrstr
, argtypes
[1]);
4505 /* Verify that the new attribute doesn't conflict with any existing
4506 attributes specified on previous declarations of the same type
4507 and if not, concatenate the two. */
4508 const char code
= attr_access::mode_chars
[mode
];
4509 tree new_attrs
= append_access_attr (node
, attrs
, attrstr
, code
, idxs
);
4513 /* Replace any existing access attribute specification with
4514 the concatenation above. */
4515 new_attrs
= tree_cons (NULL_TREE
, new_attrs
, NULL_TREE
);
4516 new_attrs
= tree_cons (name
, new_attrs
, NULL_TREE
);
4520 /* Repeat for the previously declared type. */
4521 attrs
= TYPE_ATTRIBUTES (TREE_TYPE (node
[1]));
4522 new_attrs
= append_access_attr (node
, attrs
, attrstr
, code
, idxs
);
4526 new_attrs
= tree_cons (NULL_TREE
, new_attrs
, NULL_TREE
);
4527 new_attrs
= tree_cons (name
, new_attrs
, NULL_TREE
);
4530 /* Recursively call self to "replace" the documented/external form
4531 of the attribute with the condensed internal form. */
4532 decl_attributes (node
, new_attrs
, flags
);
4536 /* Extract attribute "arg spec" from each FNDECL argument that has it,
4537 build a single attribute access corresponding to all the arguments,
4538 and return the result. SKIP_VOIDPTR set to ignore void* parameters
4539 (used for user-defined functions for which, unlike in for built-ins,
4540 void* cannot be relied on to determine anything about the access
4541 through it or whether it even takes place).
4543 For example, the parameters in the declaration:
4545 void f (int x, int y, char [x][1][y][3], char [y][2][y][5]);
4547 result in the following attribute access:
4549 value: "+^2[*],$0$1^3[*],$1$1"
4550 chain: <0, x> <1, y>
4552 where each <node> on the chain corresponds to one VLA bound for each
4553 of the two parameters. */
4556 build_attr_access_from_parms (tree parms
, bool skip_voidptr
)
4558 /* Maps each named integral argument DECL seen so far to its position
4559 in the argument list; used to associate VLA sizes with arguments. */
4560 hash_map
<tree
, unsigned> arg2pos
;
4562 /* The string representation of the access specification for all
4565 unsigned argpos
= 0;
4567 /* A TREE_LIST of VLA bounds. */
4568 tree vblist
= NULL_TREE
;
4570 for (tree arg
= parms
; arg
; arg
= TREE_CHAIN (arg
), ++argpos
)
4575 tree argtype
= TREE_TYPE (arg
);
4576 if (DECL_NAME (arg
) && INTEGRAL_TYPE_P (argtype
))
4577 arg2pos
.put (arg
, argpos
);
4579 tree argspec
= DECL_ATTRIBUTES (arg
);
4583 if (POINTER_TYPE_P (argtype
))
4585 /* void* arguments in user-defined functions could point to
4586 anything; skip them. */
4587 tree reftype
= TREE_TYPE (argtype
);
4588 if (skip_voidptr
&& VOID_TYPE_P (reftype
))
4592 /* Each parameter should have at most one "arg spec" attribute. */
4593 argspec
= lookup_attribute ("arg spec", argspec
);
4597 /* Attribute arg spec should have one or two arguments. */
4598 argspec
= TREE_VALUE (argspec
);
4600 /* The attribute arg spec string. */
4601 tree str
= TREE_VALUE (argspec
);
4602 const char *s
= TREE_STRING_POINTER (str
);
4604 /* Create the attribute access string from the arg spec string,
4605 optionally followed by position of the VLA bound argument if
4608 int len
= snprintf (specbuf
, sizeof specbuf
, "%c%u%s",
4609 attr_access::mode_chars
[access_deferred
],
4611 gcc_assert ((size_t) len
< sizeof specbuf
);
4613 if (!spec
.length ())
4618 /* The (optional) list of expressions denoting the VLA bounds
4619 N in ARGTYPE <arg>[Ni]...[Nj]...[Nk]. */
4620 tree argvbs
= TREE_CHAIN (argspec
);
4624 /* Add ARGVBS to the list. Their presence is indicated by
4625 appending a comma followed by the dollar sign and, when
4626 it corresponds to a function parameter, the position of
4627 each bound Ni, so it can be distinguished from
4628 an unspecified bound (as in T[*]). The list is in reverse
4629 order of arguments and needs to be reversed to access in
4631 vblist
= tree_cons (NULL_TREE
, argvbs
, vblist
);
4634 for (tree vb
= argvbs
; vb
; vb
= TREE_CHAIN (vb
), ++nelts
)
4636 tree bound
= TREE_VALUE (vb
);
4637 if (const unsigned *psizpos
= arg2pos
.get (bound
))
4639 /* BOUND previously seen in the parameter list. */
4640 TREE_PURPOSE (vb
) = size_int (*psizpos
);
4641 sprintf (specbuf
, "$%u", *psizpos
);
4646 /* BOUND doesn't name a parameter (it could be a global
4647 variable or an expression such as a function call). */
4654 if (!spec
.length ())
4657 /* Build a single attribute access with the string describing all
4658 array arguments and an optional list of any non-parameter VLA
4660 tree str
= build_string (spec
.length (), spec
.c_str ());
4661 tree attrargs
= tree_cons (NULL_TREE
, str
, vblist
);
4662 tree name
= get_identifier ("access");
4663 return tree_cons (name
, attrargs
, NULL_TREE
);
4666 /* Handle a "nothrow" attribute; arguments as in
4667 struct attribute_spec.handler. */
4670 handle_nothrow_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
4671 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4673 if (TREE_CODE (*node
) == FUNCTION_DECL
)
4674 TREE_NOTHROW (*node
) = 1;
4675 /* ??? TODO: Support types. */
4678 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4679 *no_add_attrs
= true;
4685 /* Handle a "cleanup" attribute; arguments as in
4686 struct attribute_spec.handler. */
4689 handle_cleanup_attribute (tree
*node
, tree name
, tree args
,
4690 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4693 tree cleanup_id
, cleanup_decl
;
4695 /* ??? Could perhaps support cleanups on TREE_STATIC, much like we do
4696 for global destructors in C++. This requires infrastructure that
4697 we don't have generically at the moment. It's also not a feature
4698 we'd be missing too much, since we do have attribute constructor. */
4699 if (!VAR_P (decl
) || TREE_STATIC (decl
))
4701 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4702 *no_add_attrs
= true;
4706 /* Verify that the argument is a function in scope. */
4707 /* ??? We could support pointers to functions here as well, if
4708 that was considered desirable. */
4709 cleanup_id
= TREE_VALUE (args
);
4710 if (TREE_CODE (cleanup_id
) != IDENTIFIER_NODE
)
4712 error ("cleanup argument not an identifier");
4713 *no_add_attrs
= true;
4716 cleanup_decl
= lookup_name (cleanup_id
);
4717 if (!cleanup_decl
|| TREE_CODE (cleanup_decl
) != FUNCTION_DECL
)
4719 error ("cleanup argument not a function");
4720 *no_add_attrs
= true;
4724 /* That the function has proper type is checked with the
4725 eventual call to build_function_call. */
4730 /* Handle a "warn_unused_result" attribute. No special handling. */
4733 handle_warn_unused_result_attribute (tree
*node
, tree name
,
4734 tree
ARG_UNUSED (args
),
4735 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4737 /* Ignore the attribute for functions not returning any value. */
4738 if (VOID_TYPE_P (TREE_TYPE (*node
)))
4740 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4741 *no_add_attrs
= true;
4747 /* Handle a "sentinel" attribute. */
4750 handle_sentinel_attribute (tree
*node
, tree name
, tree args
,
4751 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4753 if (!prototype_p (*node
))
4755 warning (OPT_Wattributes
,
4756 "%qE attribute requires prototypes with named arguments", name
);
4757 *no_add_attrs
= true;
4761 if (!stdarg_p (*node
))
4763 warning (OPT_Wattributes
,
4764 "%qE attribute only applies to variadic functions", name
);
4765 *no_add_attrs
= true;
4771 tree position
= TREE_VALUE (args
);
4772 if (position
&& TREE_CODE (position
) != IDENTIFIER_NODE
4773 && TREE_CODE (position
) != FUNCTION_DECL
)
4774 position
= default_conversion (position
);
4776 if (TREE_CODE (position
) != INTEGER_CST
4777 || !INTEGRAL_TYPE_P (TREE_TYPE (position
)))
4779 warning (OPT_Wattributes
,
4780 "requested position is not an integer constant");
4781 *no_add_attrs
= true;
4785 if (tree_int_cst_lt (position
, integer_zero_node
))
4787 warning (OPT_Wattributes
,
4788 "requested position is less than zero");
4789 *no_add_attrs
= true;
4797 /* Handle a "type_generic" attribute. */
4800 handle_type_generic_attribute (tree
*node
, tree
ARG_UNUSED (name
),
4801 tree
ARG_UNUSED (args
), int ARG_UNUSED (flags
),
4802 bool * ARG_UNUSED (no_add_attrs
))
4804 /* Ensure we have a function type. */
4805 gcc_assert (TREE_CODE (*node
) == FUNCTION_TYPE
);
4807 /* Ensure we have a variadic function. */
4808 gcc_assert (!prototype_p (*node
) || stdarg_p (*node
));
4813 /* Handle a "target" attribute. */
4816 handle_target_attribute (tree
*node
, tree name
, tree args
, int flags
,
4819 /* Ensure we have a function type. */
4820 if (TREE_CODE (*node
) != FUNCTION_DECL
)
4822 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4823 *no_add_attrs
= true;
4825 else if (lookup_attribute ("target_clones", DECL_ATTRIBUTES (*node
)))
4827 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
4828 "with %qs attribute", name
, "target_clones");
4829 *no_add_attrs
= true;
4831 else if (! targetm
.target_option
.valid_attribute_p (*node
, name
, args
,
4833 *no_add_attrs
= true;
4835 /* Check that there's no empty string in values of the attribute. */
4836 for (tree t
= args
; t
!= NULL_TREE
; t
= TREE_CHAIN (t
))
4838 tree value
= TREE_VALUE (t
);
4839 if (TREE_CODE (value
) == STRING_CST
4840 && TREE_STRING_LENGTH (value
) == 1
4841 && TREE_STRING_POINTER (value
)[0] == '\0')
4843 warning (OPT_Wattributes
, "empty string in attribute %<target%>");
4844 *no_add_attrs
= true;
4851 /* Handle a "target_clones" attribute. */
4854 handle_target_clones_attribute (tree
*node
, tree name
, tree
ARG_UNUSED (args
),
4855 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4857 /* Ensure we have a function type. */
4858 if (TREE_CODE (*node
) == FUNCTION_DECL
)
4860 if (lookup_attribute ("always_inline", DECL_ATTRIBUTES (*node
)))
4862 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
4863 "with %qs attribute", name
, "always_inline");
4864 *no_add_attrs
= true;
4866 else if (lookup_attribute ("target", DECL_ATTRIBUTES (*node
)))
4868 warning (OPT_Wattributes
, "%qE attribute ignored due to conflict "
4869 "with %qs attribute", name
, "target");
4870 *no_add_attrs
= true;
4873 /* Do not inline functions with multiple clone targets. */
4874 DECL_UNINLINABLE (*node
) = 1;
4878 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4879 *no_add_attrs
= true;
4884 /* For handling "optimize" attribute. arguments as in
4885 struct attribute_spec.handler. */
4888 handle_optimize_attribute (tree
*node
, tree name
, tree args
,
4889 int ARG_UNUSED (flags
), bool *no_add_attrs
)
4891 /* Ensure we have a function type. */
4892 if (TREE_CODE (*node
) != FUNCTION_DECL
)
4894 warning (OPT_Wattributes
, "%qE attribute ignored", name
);
4895 *no_add_attrs
= true;
4899 struct cl_optimization cur_opts
;
4900 tree old_opts
= DECL_FUNCTION_SPECIFIC_OPTIMIZATION (*node
);
4902 /* Save current options. */
4903 cl_optimization_save (&cur_opts
, &global_options
, &global_options_set
);
4905 /* If we previously had some optimization options, use them as the
4907 gcc_options
*saved_global_options
= NULL
;
4910 saved_global_options
= XNEW (gcc_options
);
4911 *saved_global_options
= global_options
;
4915 cl_optimization_restore (&global_options
, &global_options_set
,
4916 TREE_OPTIMIZATION (old_opts
));
4918 /* Parse options, and update the vector. */
4919 parse_optimize_options (args
, true);
4920 DECL_FUNCTION_SPECIFIC_OPTIMIZATION (*node
)
4921 = build_optimization_node (&global_options
, &global_options_set
);
4923 /* Restore current options. */
4924 cl_optimization_restore (&global_options
, &global_options_set
,
4926 if (saved_global_options
!= NULL
)
4928 cl_optimization_compare (saved_global_options
, &global_options
);
4929 free (saved_global_options
);
4936 /* Handle a "no_split_stack" attribute. */
4939 handle_no_split_stack_attribute (tree
*node
, tree name
,
4940 tree
ARG_UNUSED (args
),
4941 int ARG_UNUSED (flags
),
4946 if (TREE_CODE (decl
) != FUNCTION_DECL
)
4948 error_at (DECL_SOURCE_LOCATION (decl
),
4949 "%qE attribute applies only to functions", name
);
4950 *no_add_attrs
= true;
4952 else if (DECL_INITIAL (decl
))
4954 error_at (DECL_SOURCE_LOCATION (decl
),
4955 "cannot set %qE attribute after definition", name
);
4956 *no_add_attrs
= true;
4962 /* Handle a "returns_nonnull" attribute; arguments as in
4963 struct attribute_spec.handler. */
4966 handle_returns_nonnull_attribute (tree
*node
, tree name
, tree
, int,
4969 // Even without a prototype we still have a return type we can check.
4970 if (TREE_CODE (TREE_TYPE (*node
)) != POINTER_TYPE
)
4972 error ("%qE attribute on a function not returning a pointer", name
);
4973 *no_add_attrs
= true;
4978 /* Handle a "designated_init" attribute; arguments as in
4979 struct attribute_spec.handler. */
4982 handle_designated_init_attribute (tree
*node
, tree name
, tree
, int,
4985 if (TREE_CODE (*node
) != RECORD_TYPE
)
4987 error ("%qE attribute is only valid on %<struct%> type", name
);
4988 *no_add_attrs
= true;
4994 /* Handle a "fallthrough" attribute; arguments as in struct
4995 attribute_spec.handler. */
4998 handle_fallthrough_attribute (tree
*, tree name
, tree
, int,
5001 pedwarn (input_location
, OPT_Wattributes
, "%qE attribute ignored", name
);
5002 *no_add_attrs
= true;
5006 /* Handle a "patchable_function_entry" attributes; arguments as in
5007 struct attribute_spec.handler. */
5010 handle_patchable_function_entry_attribute (tree
*, tree name
, tree args
,
5011 int, bool *no_add_attrs
)
5013 for (; args
; args
= TREE_CHAIN (args
))
5015 tree val
= TREE_VALUE (args
);
5016 if (val
&& TREE_CODE (val
) != IDENTIFIER_NODE
5017 && TREE_CODE (val
) != FUNCTION_DECL
)
5018 val
= default_conversion (val
);
5020 if (!tree_fits_uhwi_p (val
))
5022 warning (OPT_Wattributes
,
5023 "%qE attribute argument %qE is not an integer constant",
5025 *no_add_attrs
= true;
5029 if (tree_to_uhwi (val
) > USHRT_MAX
)
5031 warning (OPT_Wattributes
,
5032 "%qE attribute argument %qE is out of range (> 65535)",
5034 *no_add_attrs
= true;
5041 /* Attempt to partially validate a single attribute ATTR as if
5042 it were to be applied to an entity OPER. */
5045 validate_attribute (location_t atloc
, tree oper
, tree attr
)
5047 /* Determine whether the name of the attribute is valid
5048 and fail with an error if not. */
5049 tree atname
= get_attribute_name (attr
);
5050 if (!lookup_attribute_spec (atname
))
5052 if (atloc
!= UNKNOWN_LOCATION
)
5053 error_at (atloc
, "unknown attribute %qE", atname
);
5057 tree args
= TREE_VALUE (attr
);
5061 /* FIXME: Do some validation. */
5062 const char *atstr
= IDENTIFIER_POINTER (atname
);
5063 if (!strcmp (atstr
, "format"))
5066 /* Only when attribute arguments have been provided try to validate
5067 the whole thing. decl_attributes doesn't return an indication of
5068 success or failure so proceed regardless. */
5069 const char tmpname
[] = "__builtin_has_attribute_tmp.";
5070 tree tmpid
= get_identifier (tmpname
);
5072 if (!strcmp (atstr
, "vector_size"))
5074 tree type
= TYPE_P (oper
) ? oper
: TREE_TYPE (oper
);
5075 /* Check for function type here since type_for_vector_size
5076 strips it while looking for a function's return type. */
5077 if (FUNC_OR_METHOD_TYPE_P (type
))
5079 warning_at (atloc
, OPT_Wattributes
,
5080 "invalid operand type %qT for %qs", type
, atstr
);
5084 type
= type_for_vector_size (type
);
5085 if (VECTOR_TYPE_P (type
))
5086 type
= TREE_TYPE (type
);
5087 /* Avoid trying to apply attribute vector_size to OPER since
5088 it's overly restrictive. Simply make sure it has the right
5090 return type_valid_for_vector_size (type
, atname
, args
, NULL
);
5094 tmpdecl
= build_decl (atloc
, TYPE_DECL
, tmpid
, oper
);
5095 else if (DECL_P (oper
))
5096 tmpdecl
= build_decl (atloc
, TREE_CODE (oper
), tmpid
, TREE_TYPE (oper
));
5097 else if (EXPR_P (oper
))
5098 tmpdecl
= build_decl (atloc
, TYPE_DECL
, tmpid
, TREE_TYPE (oper
));
5102 /* Temporarily clear CURRENT_FUNCTION_DECL to make decl_attributes
5103 believe the DECL declared above is at file scope. (See bug 87526.) */
5104 tree save_curfunc
= current_function_decl
;
5105 current_function_decl
= NULL_TREE
;
5106 if (DECL_P (tmpdecl
))
5109 /* An alias cannot be a definition so declare the symbol extern. */
5110 DECL_EXTERNAL (tmpdecl
) = true;
5111 /* Attribute visibility only applies to symbols visible from other
5112 translation units so make it "public." */
5113 TREE_PUBLIC (tmpdecl
) = TREE_PUBLIC (oper
);
5115 decl_attributes (&tmpdecl
, attr
, 0);
5116 current_function_decl
= save_curfunc
;
5118 /* FIXME: Change decl_attributes to indicate success or failure (and
5119 parameterize it to avoid failing with errors). */
5123 /* Return true if the DECL, EXPR, or TYPE t has been declared with
5124 attribute ATTR. For DECL, consider also its type. For EXPR,
5125 consider just its type. */
5128 has_attribute (location_t atloc
, tree t
, tree attr
, tree (*convert
)(tree
))
5130 if (!attr
|| !t
|| t
== error_mark_node
)
5133 if (!validate_attribute (atloc
, t
, attr
))
5136 tree type
= NULL_TREE
;
5137 tree expr
= NULL_TREE
;
5144 /* Determine the array element/member declaration from
5145 a COMPONENT_REF and an INDIRECT_REF involving a refeence. */
5147 tree_code code
= TREE_CODE (t
);
5148 if (code
== INDIRECT_REF
)
5150 tree op0
= TREE_OPERAND (t
, 0);
5151 if (TREE_CODE (TREE_TYPE (op0
)) == REFERENCE_TYPE
)
5156 else if (code
== COMPONENT_REF
)
5157 t
= TREE_OPERAND (t
, 1);
5164 /* Set to true when an attribute is found in the referenced entity
5165 that matches the specified attribute. */
5166 bool found_match
= false;
5168 tree atname
= get_attribute_name (attr
);
5169 const char *namestr
= IDENTIFIER_POINTER (atname
);
5171 /* Iterate once for a type and twice for a function or variable
5172 declaration: once for the DECL and the second time for its
5174 for (bool done
= false; !found_match
&& !done
; )
5179 if (type
== error_mark_node
)
5181 /* This could be a label. FIXME: add support for labels. */
5182 warning_at (atloc
, OPT_Wattributes
,
5184 ? G_("%qs attribute not supported for %qT "
5185 "in %<__builtin_has_attribute%>")
5186 : G_("%qs attribute not supported for %qE "
5187 "in %<__builtin_has_attribute%>")),
5192 /* Clear EXPR to prevent considering it again below. */
5193 atlist
= TYPE_ATTRIBUTES (type
);
5197 else if (DECL_P (expr
))
5199 /* Set TYPE to the DECL's type to process it on the next
5201 atlist
= DECL_ATTRIBUTES (expr
);
5202 type
= TREE_TYPE (expr
);
5206 type
= TREE_TYPE (expr
);
5207 atlist
= TYPE_ATTRIBUTES (type
);
5211 /* True when an attribute with the sought name (though not necessarily
5212 with the sought attributes) has been found on the attribute chain. */
5213 bool found_attr
= false;
5215 /* When clear, the first mismatched attribute argument results
5216 in failure. Otherwise, the first matched attribute argument
5217 results in success. */
5218 bool attr_nonnull
= !strcmp ("nonnull", namestr
);
5219 bool ignore_mismatches
= attr_nonnull
;
5221 /* Iterate over the instances of the sought attribute on the DECL or
5222 TYPE (there may be multiple instances with different arguments). */
5223 for (; (atlist
= lookup_attribute (namestr
, atlist
));
5224 found_attr
= true, atlist
= TREE_CHAIN (atlist
))
5226 /* If there are no arguments to match the result is true except
5227 for nonnull where the attribute with no arguments must match. */
5228 if (!TREE_VALUE (attr
))
5229 return attr_nonnull
? !TREE_VALUE (atlist
) : true;
5231 /* Attribute nonnull with no arguments subsumes all values of
5232 the attribute. FIXME: This is overly broad since it only
5233 applies to pointer arguments, but querying non-pointer
5234 arguments is diagnosed. */
5235 if (!TREE_VALUE (atlist
) && attr_nonnull
)
5238 /* Iterate over the DECL or TYPE attribute argument's values. */
5239 for (tree val
= TREE_VALUE (atlist
); val
; val
= TREE_CHAIN (val
))
5241 /* Iterate over the arguments in the sought attribute comparing
5242 their values to those specified for the DECL or TYPE. */
5243 for (tree arg
= TREE_VALUE (attr
); arg
; arg
= TREE_CHAIN (arg
))
5245 tree v1
= TREE_VALUE (val
);
5246 tree v2
= TREE_VALUE (arg
);
5253 if (TREE_CODE (v1
) == IDENTIFIER_NODE
5254 || TREE_CODE (v2
) == IDENTIFIER_NODE
)
5255 /* Two identifiers are the same if their values are
5256 equal (that's handled above). Otherwise ther are
5257 either not the same or oneis not an identifier. */
5260 /* Convert to make them equality-comparable. */
5264 /* A positive value indicates equality, negative means
5266 if (simple_cst_equal (v1
, v2
) == 1)
5269 if (!ignore_mismatches
)
5277 /* Some attributes are encoded directly in the tree node. */
5278 if (!strcmp ("aligned", namestr
))
5280 if (tree arg
= TREE_VALUE (attr
))
5282 arg
= convert (TREE_VALUE (arg
));
5283 if (!tree_fits_uhwi_p (arg
))
5284 /* Invalid argument. */;
5285 else if (expr
&& DECL_P (expr
)
5286 && DECL_USER_ALIGN (expr
))
5287 found_match
= DECL_ALIGN_UNIT (expr
) == tree_to_uhwi (arg
);
5288 else if (type
&& TYPE_USER_ALIGN (type
))
5289 found_match
= TYPE_ALIGN_UNIT (type
) == tree_to_uhwi (arg
);
5291 else if (expr
&& DECL_P (expr
))
5292 found_match
= DECL_USER_ALIGN (expr
);
5294 found_match
= TYPE_USER_ALIGN (type
);
5296 else if (!strcmp ("const", namestr
))
5298 if (expr
&& DECL_P (expr
))
5299 found_match
= TREE_READONLY (expr
);
5301 else if (!strcmp ("noreturn", namestr
))
5303 /* C11 _Noreturn sets the volatile bit without attaching
5304 an attribute to the decl. */
5307 && FUNC_OR_METHOD_TYPE_P (TREE_TYPE (expr
)))
5308 found_match
= TREE_THIS_VOLATILE (expr
);
5310 else if (!strcmp ("pure", namestr
))
5312 if (expr
&& DECL_P (expr
))
5313 found_match
= DECL_PURE_P (expr
);
5315 else if (!strcmp ("deprecated", namestr
))
5317 found_match
= TREE_DEPRECATED (expr
? expr
: type
);
5321 else if (!strcmp ("vector_size", namestr
))
5323 if (!type
|| !VECTOR_TYPE_P (type
))
5326 if (tree arg
= TREE_VALUE (attr
))
5328 /* Compare the vector size argument for equality. */
5329 arg
= convert (TREE_VALUE (arg
));
5330 return tree_int_cst_equal (arg
, TYPE_SIZE_UNIT (type
)) == 1;
5335 else if (!strcmp ("warn_if_not_aligned", namestr
))
5337 if (tree arg
= TREE_VALUE (attr
))
5339 arg
= convert (TREE_VALUE (arg
));
5340 if (expr
&& DECL_P (expr
))
5341 found_match
= (DECL_WARN_IF_NOT_ALIGN (expr
)
5342 == tree_to_uhwi (arg
) * BITS_PER_UNIT
);
5344 found_match
= (TYPE_WARN_IF_NOT_ALIGN (type
)
5345 == tree_to_uhwi (arg
) * BITS_PER_UNIT
);
5347 else if (expr
&& DECL_P (expr
))
5348 found_match
= DECL_WARN_IF_NOT_ALIGN (expr
);
5350 found_match
= TYPE_WARN_IF_NOT_ALIGN (type
);
5352 else if (!strcmp ("transparent_union", namestr
))
5355 found_match
= TYPE_TRANSPARENT_AGGR (type
) != 0;
5357 else if (!strcmp ("mode", namestr
))
5359 /* Finally issue a warning for attributes that cannot
5360 be supported in this context. Attribute mode is not
5361 added to a symbol and cannot be determined from it. */
5362 warning_at (atloc
, OPT_Wattributes
,
5363 "%qs attribute not supported in "
5364 "%<__builtin_has_attribute%>", namestr
);