]> gcc.gnu.org Git - gcc.git/blame - gcc/attribs.c
Remove a layer of indirection from hash_table
[gcc.git] / gcc / attribs.c
CommitLineData
bb9f8221 1/* Functions dealing with attribute handling, used by most front ends.
23a5b65a 2 Copyright (C) 1992-2014 Free Software Foundation, Inc.
bb9f8221
RK
3
4This file is part of GCC.
5
6GCC is free software; you can redistribute it and/or modify it under
7the terms of the GNU General Public License as published by the Free
9dcd6f09 8Software Foundation; either version 3, or (at your option) any later
bb9f8221
RK
9version.
10
11GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12WARRANTY; without even the implied warranty of MERCHANTABILITY or
13FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14for more details.
15
16You should have received a copy of the GNU General Public License
9dcd6f09
NC
17along with GCC; see the file COPYING3. If not see
18<http://www.gnu.org/licenses/>. */
bb9f8221
RK
19
20#include "config.h"
21#include "system.h"
4977bab6
ZW
22#include "coretypes.h"
23#include "tm.h"
bb9f8221 24#include "tree.h"
d8a2d370
DN
25#include "stringpool.h"
26#include "attribs.h"
27#include "stor-layout.h"
bb9f8221 28#include "flags.h"
718f9c0f 29#include "diagnostic-core.h"
bb9f8221 30#include "ggc.h"
bb9f8221 31#include "tm_p.h"
bb9f8221
RK
32#include "cpplib.h"
33#include "target.h"
7ffb4fd2 34#include "langhooks.h"
4a8fb1a1 35#include "hash-table.h"
d1c8e08a 36#include "plugin.h"
bb9f8221 37
349ae713 38/* Table of the tables of attributes (common, language, format, machine)
bb9f8221
RK
39 searched. */
40static const struct attribute_spec *attribute_tables[4];
41
23b43207
JH
42/* Substring representation. */
43
44struct substring
45{
46 const char *str;
47 int length;
48};
49
4a8fb1a1
LC
50/* Simple hash function to avoid need to scan whole string. */
51
52static inline hashval_t
53substring_hash (const char *str, int l)
54{
55 return str[0] + str[l - 1] * 256 + l * 65536;
56}
57
58/* Used for attribute_hash. */
59
60struct attribute_hasher : typed_noop_remove <attribute_spec>
61{
62 typedef attribute_spec value_type;
63 typedef substring compare_type;
64 static inline hashval_t hash (const value_type *);
65 static inline bool equal (const value_type *, const compare_type *);
66};
67
68inline hashval_t
69attribute_hasher::hash (const value_type *spec)
70{
71 const int l = strlen (spec->name);
72 return substring_hash (spec->name, l);
73}
74
75inline bool
76attribute_hasher::equal (const value_type *spec, const compare_type *str)
77{
78 return (strncmp (spec->name, str->str, str->length) == 0
79 && !spec->name[str->length]);
80}
81
e28d52cf
DS
82/* Scoped attribute name representation. */
83
84struct scoped_attributes
85{
86 const char *ns;
9771b263 87 vec<attribute_spec> attributes;
c203e8a7 88 hash_table<attribute_hasher> *attribute_hash;
e28d52cf
DS
89};
90
e28d52cf 91/* The table of scope attributes. */
9771b263 92static vec<scoped_attributes> attributes_table;
e28d52cf
DS
93
94static scoped_attributes* find_attribute_namespace (const char*);
95static void register_scoped_attribute (const struct attribute_spec *,
96 scoped_attributes *);
97
bb9f8221
RK
98static bool attributes_initialized = false;
99
bb9f8221 100/* Default empty table of attributes. */
23b43207 101
bb9f8221
RK
102static const struct attribute_spec empty_attribute_table[] =
103{
62d784f7 104 { NULL, 0, 0, false, false, false, NULL, false }
bb9f8221
RK
105};
106
23b43207
JH
107/* Return base name of the attribute. Ie '__attr__' is turned into 'attr'.
108 To avoid need for copying, we simply return length of the string. */
109
110static void
111extract_attribute_substring (struct substring *str)
112{
113 if (str->length > 4 && str->str[0] == '_' && str->str[1] == '_'
114 && str->str[str->length - 1] == '_' && str->str[str->length - 2] == '_')
115 {
116 str->length -= 4;
117 str->str += 2;
118 }
119}
120
e28d52cf
DS
121/* Insert an array of attributes ATTRIBUTES into a namespace. This
122 array must be NULL terminated. NS is the name of attribute
123 namespace. The function returns the namespace into which the
124 attributes have been registered. */
125
126scoped_attributes*
127register_scoped_attributes (const struct attribute_spec * attributes,
128 const char* ns)
129{
130 scoped_attributes *result = NULL;
131
132 /* See if we already have attributes in the namespace NS. */
133 result = find_attribute_namespace (ns);
134
135 if (result == NULL)
136 {
137 /* We don't have any namespace NS yet. Create one. */
138 scoped_attributes sa;
139
9771b263
DN
140 if (!attributes_table.is_empty ())
141 attributes_table.create (64);
e28d52cf
DS
142
143 memset (&sa, 0, sizeof (sa));
144 sa.ns = ns;
9771b263
DN
145 sa.attributes.create (64);
146 result = attributes_table.safe_push (sa);
c203e8a7 147 result->attribute_hash = new hash_table<attribute_hasher> (200);
e28d52cf
DS
148 }
149
150 /* Really add the attributes to their namespace now. */
151 for (unsigned i = 0; attributes[i].name != NULL; ++i)
152 {
9771b263 153 result->attributes.safe_push (attributes[i]);
e28d52cf
DS
154 register_scoped_attribute (&attributes[i], result);
155 }
156
157 gcc_assert (result != NULL);
158
159 return result;
160}
161
162/* Return the namespace which name is NS, NULL if none exist. */
163
164static scoped_attributes*
165find_attribute_namespace (const char* ns)
166{
167 unsigned ix;
168 scoped_attributes *iter;
169
9771b263 170 FOR_EACH_VEC_ELT (attributes_table, ix, iter)
e28d52cf
DS
171 if (ns == iter->ns
172 || (iter->ns != NULL
173 && ns != NULL
174 && !strcmp (iter->ns, ns)))
175 return iter;
176 return NULL;
177}
178
bb9f8221
RK
179/* Initialize attribute tables, and make some sanity checks
180 if --enable-checking. */
181
8dd00781 182void
4682ae04 183init_attributes (void)
bb9f8221 184{
ca7558fc 185 size_t i;
bb9f8221 186
8dd00781
JJ
187 if (attributes_initialized)
188 return;
189
349ae713
NB
190 attribute_tables[0] = lang_hooks.common_attribute_table;
191 attribute_tables[1] = lang_hooks.attribute_table;
192 attribute_tables[2] = lang_hooks.format_attribute_table;
bb9f8221
RK
193 attribute_tables[3] = targetm.attribute_table;
194
349ae713
NB
195 /* Translate NULL pointers to pointers to the empty table. */
196 for (i = 0; i < ARRAY_SIZE (attribute_tables); i++)
197 if (attribute_tables[i] == NULL)
198 attribute_tables[i] = empty_attribute_table;
199
bb9f8221
RK
200#ifdef ENABLE_CHECKING
201 /* Make some sanity checks on the attribute tables. */
ca7558fc 202 for (i = 0; i < ARRAY_SIZE (attribute_tables); i++)
bb9f8221
RK
203 {
204 int j;
205
206 for (j = 0; attribute_tables[i][j].name != NULL; j++)
207 {
208 /* The name must not begin and end with __. */
209 const char *name = attribute_tables[i][j].name;
210 int len = strlen (name);
c22cacf3 211
298e6adc
NS
212 gcc_assert (!(name[0] == '_' && name[1] == '_'
213 && name[len - 1] == '_' && name[len - 2] == '_'));
c22cacf3 214
bb9f8221 215 /* The minimum and maximum lengths must be consistent. */
298e6adc 216 gcc_assert (attribute_tables[i][j].min_length >= 0);
c22cacf3 217
298e6adc
NS
218 gcc_assert (attribute_tables[i][j].max_length == -1
219 || (attribute_tables[i][j].max_length
220 >= attribute_tables[i][j].min_length));
c22cacf3 221
bb9f8221 222 /* An attribute cannot require both a DECL and a TYPE. */
298e6adc
NS
223 gcc_assert (!attribute_tables[i][j].decl_required
224 || !attribute_tables[i][j].type_required);
c22cacf3 225
bb9f8221
RK
226 /* If an attribute requires a function type, in particular
227 it requires a type. */
298e6adc
NS
228 gcc_assert (!attribute_tables[i][j].function_type_required
229 || attribute_tables[i][j].type_required);
bb9f8221
RK
230 }
231 }
232
233 /* Check that each name occurs just once in each table. */
ca7558fc 234 for (i = 0; i < ARRAY_SIZE (attribute_tables); i++)
bb9f8221
RK
235 {
236 int j, k;
237 for (j = 0; attribute_tables[i][j].name != NULL; j++)
238 for (k = j + 1; attribute_tables[i][k].name != NULL; k++)
298e6adc
NS
239 gcc_assert (strcmp (attribute_tables[i][j].name,
240 attribute_tables[i][k].name));
bb9f8221 241 }
0a35513e
AH
242 /* Check that no name occurs in more than one table. Names that
243 begin with '*' are exempt, and may be overridden. */
ca7558fc 244 for (i = 0; i < ARRAY_SIZE (attribute_tables); i++)
bb9f8221 245 {
ca7558fc 246 size_t j, k, l;
bb9f8221 247
ca7558fc 248 for (j = i + 1; j < ARRAY_SIZE (attribute_tables); j++)
bb9f8221
RK
249 for (k = 0; attribute_tables[i][k].name != NULL; k++)
250 for (l = 0; attribute_tables[j][l].name != NULL; l++)
0a35513e
AH
251 gcc_assert (attribute_tables[i][k].name[0] == '*'
252 || strcmp (attribute_tables[i][k].name,
253 attribute_tables[j][l].name));
bb9f8221
RK
254 }
255#endif
256
e28d52cf
DS
257 for (i = 0; i < ARRAY_SIZE (attribute_tables); ++i)
258 /* Put all the GNU attributes into the "gnu" namespace. */
259 register_scoped_attributes (attribute_tables[i], "gnu");
260
d1c8e08a
TG
261 invoke_plugin_callbacks (PLUGIN_ATTRIBUTES, NULL);
262 attributes_initialized = true;
263}
264
265/* Insert a single ATTR into the attribute table. */
266
267void
b8698a0f 268register_attribute (const struct attribute_spec *attr)
e28d52cf
DS
269{
270 register_scoped_attribute (attr, find_attribute_namespace ("gnu"));
271}
272
273/* Insert a single attribute ATTR into a namespace of attributes. */
274
275static void
276register_scoped_attribute (const struct attribute_spec *attr,
277 scoped_attributes *name_space)
d1c8e08a 278{
16f7ad42 279 struct substring str;
4a8fb1a1 280 attribute_spec **slot;
16f7ad42 281
e28d52cf
DS
282 gcc_assert (attr != NULL && name_space != NULL);
283
c203e8a7 284 gcc_assert (name_space->attribute_hash);
e28d52cf 285
16f7ad42
TG
286 str.str = attr->name;
287 str.length = strlen (str.str);
70e41a6a
NP
288
289 /* Attribute names in the table must be in the form 'text' and not
290 in the form '__text__'. */
291 gcc_assert (str.length > 0 && str.str[0] != '_');
292
4a8fb1a1 293 slot = name_space->attribute_hash
c203e8a7
TS
294 ->find_slot_with_hash (&str, substring_hash (str.str, str.length),
295 INSERT);
0a35513e 296 gcc_assert (!*slot || attr->name[0] == '*');
4a8fb1a1 297 *slot = CONST_CAST (struct attribute_spec *, attr);
bb9f8221 298}
a7f6bc8c 299
e28d52cf
DS
300/* Return the spec for the scoped attribute with namespace NS and
301 name NAME. */
a7f6bc8c 302
862d0b35 303static const struct attribute_spec *
e28d52cf 304lookup_scoped_attribute_spec (const_tree ns, const_tree name)
a7f6bc8c
JM
305{
306 struct substring attr;
e28d52cf
DS
307 scoped_attributes *attrs;
308
309 const char *ns_str = (ns != NULL_TREE) ? IDENTIFIER_POINTER (ns): NULL;
310
311 attrs = find_attribute_namespace (ns_str);
312
313 if (attrs == NULL)
314 return NULL;
a7f6bc8c
JM
315
316 attr.str = IDENTIFIER_POINTER (name);
317 attr.length = IDENTIFIER_LENGTH (name);
318 extract_attribute_substring (&attr);
c203e8a7
TS
319 return attrs->attribute_hash->find_with_hash (&attr,
320 substring_hash (attr.str,
321 attr.length));
a7f6bc8c 322}
e28d52cf 323
7dbb85a7
JM
324/* Return the spec for the attribute named NAME. If NAME is a TREE_LIST,
325 it also specifies the attribute namespace. */
e28d52cf
DS
326
327const struct attribute_spec *
328lookup_attribute_spec (const_tree name)
329{
7dbb85a7
JM
330 tree ns;
331 if (TREE_CODE (name) == TREE_LIST)
332 {
333 ns = TREE_PURPOSE (name);
334 name = TREE_VALUE (name);
335 }
336 else
337 ns = get_identifier ("gnu");
338 return lookup_scoped_attribute_spec (ns, name);
e28d52cf
DS
339}
340
862d0b35
DN
341
342/* Return the namespace of the attribute ATTR. This accessor works on
343 GNU and C++11 (scoped) attributes. On GNU attributes,
344 it returns an identifier tree for the string "gnu".
345
346 Please read the comments of cxx11_attribute_p to understand the
347 format of attributes. */
348
349static tree
350get_attribute_namespace (const_tree attr)
351{
352 if (cxx11_attribute_p (attr))
353 return TREE_PURPOSE (TREE_PURPOSE (attr));
354 return get_identifier ("gnu");
355}
356
357
bb9f8221
RK
358/* Process the attributes listed in ATTRIBUTES and install them in *NODE,
359 which is either a DECL (including a TYPE_DECL) or a TYPE. If a DECL,
360 it should be modified in place; if a TYPE, a copy should be created
361 unless ATTR_FLAG_TYPE_IN_PLACE is set in FLAGS. FLAGS gives further
362 information, in the form of a bitwise OR of flags in enum attribute_flags
363 from tree.h. Depending on these flags, some attributes may be
364 returned to be applied at a later stage (for example, to apply
03aa99d4 365 a decl attribute to the declaration rather than to its type). */
bb9f8221
RK
366
367tree
4682ae04 368decl_attributes (tree *node, tree attributes, int flags)
bb9f8221
RK
369{
370 tree a;
371 tree returned_attrs = NULL_TREE;
372
e28d52cf 373 if (TREE_TYPE (*node) == error_mark_node || attributes == error_mark_node)
21516d64
VR
374 return NULL_TREE;
375
bb9f8221
RK
376 if (!attributes_initialized)
377 init_attributes ();
378
ab442df7
MM
379 /* If this is a function and the user used #pragma GCC optimize, add the
380 options to the attribute((optimize(...))) list. */
381 if (TREE_CODE (*node) == FUNCTION_DECL && current_optimize_pragma)
382 {
383 tree cur_attr = lookup_attribute ("optimize", attributes);
384 tree opts = copy_list (current_optimize_pragma);
385
386 if (! cur_attr)
387 attributes
388 = tree_cons (get_identifier ("optimize"), opts, attributes);
389 else
390 TREE_VALUE (cur_attr) = chainon (opts, TREE_VALUE (cur_attr));
391 }
392
393 if (TREE_CODE (*node) == FUNCTION_DECL
394 && optimization_current_node != optimization_default_node
395 && !DECL_FUNCTION_SPECIFIC_OPTIMIZATION (*node))
396 DECL_FUNCTION_SPECIFIC_OPTIMIZATION (*node) = optimization_current_node;
397
5779e713
MM
398 /* If this is a function and the user used #pragma GCC target, add the
399 options to the attribute((target(...))) list. */
ab442df7 400 if (TREE_CODE (*node) == FUNCTION_DECL
5779e713 401 && current_target_pragma
ab442df7 402 && targetm.target_option.valid_attribute_p (*node, NULL_TREE,
5779e713 403 current_target_pragma, 0))
ab442df7 404 {
5779e713
MM
405 tree cur_attr = lookup_attribute ("target", attributes);
406 tree opts = copy_list (current_target_pragma);
ab442df7
MM
407
408 if (! cur_attr)
5779e713 409 attributes = tree_cons (get_identifier ("target"), opts, attributes);
ab442df7
MM
410 else
411 TREE_VALUE (cur_attr) = chainon (opts, TREE_VALUE (cur_attr));
412 }
413
61044492
JZ
414 /* A "naked" function attribute implies "noinline" and "noclone" for
415 those targets that support it. */
416 if (TREE_CODE (*node) == FUNCTION_DECL
70e41a6a 417 && attributes
61044492
JZ
418 && lookup_attribute_spec (get_identifier ("naked"))
419 && lookup_attribute ("naked", attributes) != NULL)
420 {
421 if (lookup_attribute ("noinline", attributes) == NULL)
422 attributes = tree_cons (get_identifier ("noinline"), NULL, attributes);
423
424 if (lookup_attribute ("noclone", attributes) == NULL)
425 attributes = tree_cons (get_identifier ("noclone"), NULL, attributes);
426 }
427
5fd9b178 428 targetm.insert_attributes (*node, &attributes);
bb9f8221
RK
429
430 for (a = attributes; a; a = TREE_CHAIN (a))
431 {
e28d52cf
DS
432 tree ns = get_attribute_namespace (a);
433 tree name = get_attribute_name (a);
bb9f8221
RK
434 tree args = TREE_VALUE (a);
435 tree *anode = node;
e28d52cf
DS
436 const struct attribute_spec *spec =
437 lookup_scoped_attribute_spec (ns, name);
bb9f8221 438 bool no_add_attrs = 0;
f9ceed32 439 int fn_ptr_quals = 0;
3acef2ae 440 tree fn_ptr_tmp = NULL_TREE;
bb9f8221
RK
441
442 if (spec == NULL)
443 {
e384e6b5 444 if (!(flags & (int) ATTR_FLAG_BUILT_IN))
e28d52cf
DS
445 {
446 if (ns == NULL_TREE || !cxx11_attribute_p (a))
447 warning (OPT_Wattributes, "%qE attribute directive ignored",
448 name);
449 else
450 warning (OPT_Wattributes,
451 "%<%E::%E%> scoped attribute directive ignored",
452 ns, name);
453 }
bb9f8221
RK
454 continue;
455 }
456 else if (list_length (args) < spec->min_length
457 || (spec->max_length >= 0
458 && list_length (args) > spec->max_length))
459 {
4f1e4960
JM
460 error ("wrong number of arguments specified for %qE attribute",
461 name);
bb9f8221
RK
462 continue;
463 }
23b43207 464 gcc_assert (is_attribute_p (spec->name, name));
bb9f8221 465
e28d52cf
DS
466 if (TYPE_P (*node)
467 && cxx11_attribute_p (a)
468 && !(flags & ATTR_FLAG_TYPE_IN_PLACE))
469 {
470 /* This is a c++11 attribute that appertains to a
471 type-specifier, outside of the definition of, a class
472 type. Ignore it. */
473 warning (OPT_Wattributes, "attribute ignored");
474 inform (input_location,
475 "an attribute that appertains to a type-specifier "
476 "is ignored");
477 continue;
478 }
479
bb9f8221
RK
480 if (spec->decl_required && !DECL_P (*anode))
481 {
482 if (flags & ((int) ATTR_FLAG_DECL_NEXT
483 | (int) ATTR_FLAG_FUNCTION_NEXT
484 | (int) ATTR_FLAG_ARRAY_NEXT))
485 {
486 /* Pass on this attribute to be tried again. */
487 returned_attrs = tree_cons (name, args, returned_attrs);
488 continue;
489 }
490 else
491 {
4f1e4960
JM
492 warning (OPT_Wattributes, "%qE attribute does not apply to types",
493 name);
bb9f8221
RK
494 continue;
495 }
496 }
497
dd4dc3cd
RK
498 /* If we require a type, but were passed a decl, set up to make a
499 new type and update the one in the decl. ATTR_FLAG_TYPE_IN_PLACE
500 would have applied if we'd been passed a type, but we cannot modify
501 the decl's type in place here. */
bb9f8221 502 if (spec->type_required && DECL_P (*anode))
dd4dc3cd
RK
503 {
504 anode = &TREE_TYPE (*anode);
317c435f
JM
505 /* Allow ATTR_FLAG_TYPE_IN_PLACE for the type's naming decl. */
506 if (!(TREE_CODE (*anode) == TYPE_DECL
507 && *anode == TYPE_NAME (TYPE_MAIN_VARIANT
508 (TREE_TYPE (*anode)))))
509 flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
dd4dc3cd 510 }
bb9f8221
RK
511
512 if (spec->function_type_required && TREE_CODE (*anode) != FUNCTION_TYPE
513 && TREE_CODE (*anode) != METHOD_TYPE)
514 {
515 if (TREE_CODE (*anode) == POINTER_TYPE
516 && (TREE_CODE (TREE_TYPE (*anode)) == FUNCTION_TYPE
517 || TREE_CODE (TREE_TYPE (*anode)) == METHOD_TYPE))
518 {
3acef2ae
JM
519 /* OK, this is a bit convoluted. We can't just make a copy
520 of the pointer type and modify its TREE_TYPE, because if
521 we change the attributes of the target type the pointer
522 type needs to have a different TYPE_MAIN_VARIANT. So we
523 pull out the target type now, frob it as appropriate, and
524 rebuild the pointer type later.
525
c22cacf3
MS
526 This would all be simpler if attributes were part of the
527 declarator, grumble grumble. */
3acef2ae 528 fn_ptr_tmp = TREE_TYPE (*anode);
f9ceed32 529 fn_ptr_quals = TYPE_QUALS (*anode);
3acef2ae
JM
530 anode = &fn_ptr_tmp;
531 flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
bb9f8221
RK
532 }
533 else if (flags & (int) ATTR_FLAG_FUNCTION_NEXT)
534 {
535 /* Pass on this attribute to be tried again. */
536 returned_attrs = tree_cons (name, args, returned_attrs);
537 continue;
538 }
539
540 if (TREE_CODE (*anode) != FUNCTION_TYPE
541 && TREE_CODE (*anode) != METHOD_TYPE)
542 {
5c498b10 543 warning (OPT_Wattributes,
4f1e4960
JM
544 "%qE attribute only applies to function types",
545 name);
bb9f8221
RK
546 continue;
547 }
548 }
549
b9e75696
JM
550 if (TYPE_P (*anode)
551 && (flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
552 && TYPE_SIZE (*anode) != NULL_TREE)
553 {
554 warning (OPT_Wattributes, "type attributes ignored after type is already defined");
555 continue;
556 }
557
bb9f8221 558 if (spec->handler != NULL)
e28d52cf
DS
559 {
560 int cxx11_flag =
561 cxx11_attribute_p (a) ? ATTR_FLAG_CXX11 : 0;
562
563 returned_attrs = chainon ((*spec->handler) (anode, name, args,
564 flags|cxx11_flag,
565 &no_add_attrs),
566 returned_attrs);
567 }
1b9191d2
AH
568
569 /* Layout the decl in case anything changed. */
570 if (spec->type_required && DECL_P (*node)
67282790
JM
571 && (TREE_CODE (*node) == VAR_DECL
572 || TREE_CODE (*node) == PARM_DECL
573 || TREE_CODE (*node) == RESULT_DECL))
d1838621 574 relayout_decl (*node);
1b9191d2 575
bb9f8221
RK
576 if (!no_add_attrs)
577 {
578 tree old_attrs;
579 tree a;
580
581 if (DECL_P (*anode))
582 old_attrs = DECL_ATTRIBUTES (*anode);
583 else
584 old_attrs = TYPE_ATTRIBUTES (*anode);
585
586 for (a = lookup_attribute (spec->name, old_attrs);
587 a != NULL_TREE;
588 a = lookup_attribute (spec->name, TREE_CHAIN (a)))
589 {
590 if (simple_cst_equal (TREE_VALUE (a), args) == 1)
591 break;
592 }
593
594 if (a == NULL_TREE)
595 {
596 /* This attribute isn't already in the list. */
597 if (DECL_P (*anode))
598 DECL_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
599 else if (flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
67214984
JM
600 {
601 TYPE_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
602 /* If this is the main variant, also push the attributes
603 out to the other variants. */
604 if (*anode == TYPE_MAIN_VARIANT (*anode))
605 {
606 tree variant;
607 for (variant = *anode; variant;
608 variant = TYPE_NEXT_VARIANT (variant))
609 {
610 if (TYPE_ATTRIBUTES (variant) == old_attrs)
611 TYPE_ATTRIBUTES (variant)
612 = TYPE_ATTRIBUTES (*anode);
613 else if (!lookup_attribute
614 (spec->name, TYPE_ATTRIBUTES (variant)))
615 TYPE_ATTRIBUTES (variant) = tree_cons
616 (name, args, TYPE_ATTRIBUTES (variant));
617 }
618 }
619 }
bb9f8221
RK
620 else
621 *anode = build_type_attribute_variant (*anode,
622 tree_cons (name, args,
623 old_attrs));
624 }
625 }
3acef2ae
JM
626
627 if (fn_ptr_tmp)
628 {
629 /* Rebuild the function pointer type and put it in the
630 appropriate place. */
631 fn_ptr_tmp = build_pointer_type (fn_ptr_tmp);
f9ceed32
MM
632 if (fn_ptr_quals)
633 fn_ptr_tmp = build_qualified_type (fn_ptr_tmp, fn_ptr_quals);
3acef2ae
JM
634 if (DECL_P (*node))
635 TREE_TYPE (*node) = fn_ptr_tmp;
3acef2ae 636 else
298e6adc
NS
637 {
638 gcc_assert (TREE_CODE (*node) == POINTER_TYPE);
639 *node = fn_ptr_tmp;
640 }
3acef2ae 641 }
bb9f8221
RK
642 }
643
644 return returned_attrs;
645}
0a35513e 646
e28d52cf
DS
647/* Return TRUE iff ATTR has been parsed by the front-end as a C++-11
648 attribute.
649
650 When G++ parses a C++11 attribute, it is represented as
651 a TREE_LIST which TREE_PURPOSE is itself a TREE_LIST. TREE_PURPOSE
652 (TREE_PURPOSE (ATTR)) is the namespace of the attribute, and the
653 TREE_VALUE (TREE_PURPOSE (ATTR)) is its non-qualified name. Please
654 use get_attribute_namespace and get_attribute_name to retrieve the
655 namespace and name of the attribute, as these accessors work with
656 GNU attributes as well. */
657
658bool
659cxx11_attribute_p (const_tree attr)
660{
661 if (attr == NULL_TREE
662 || TREE_CODE (attr) != TREE_LIST)
663 return false;
664
665 return (TREE_CODE (TREE_PURPOSE (attr)) == TREE_LIST);
666}
667
668/* Return the name of the attribute ATTR. This accessor works on GNU
669 and C++11 (scoped) attributes.
670
671 Please read the comments of cxx11_attribute_p to understand the
672 format of attributes. */
673
674tree
675get_attribute_name (const_tree attr)
676{
677 if (cxx11_attribute_p (attr))
678 return TREE_VALUE (TREE_PURPOSE (attr));
679 return TREE_PURPOSE (attr);
680}
681
0a35513e
AH
682/* Subroutine of set_method_tm_attributes. Apply TM attribute ATTR
683 to the method FNDECL. */
684
685void
686apply_tm_attr (tree fndecl, tree attr)
687{
688 decl_attributes (&TREE_TYPE (fndecl), tree_cons (attr, NULL, NULL), 0);
689}
This page took 2.451689 seconds and 5 git commands to generate.