* attribs.c (process_attribute_spec): New. Factored from
decl_attribute to return a valid attribute spec.
(finalize_type_attribute): New. Factored from decl_attribute to process
attributes for types after error checking.
(type_attributes): New. Factored type specific portions of
decl_attributes.
(decl_attributes): Moved all type processing to other functions.
* attribs.h (type_attributes): Export.
* c/c-decl.c (groktypename, grokdeclarator, finish_struct,
finish_enum): Call type_attributes.
* c-family/c-common.c (handle_tm_attribute): Call type_attributes.
* cp/decl.c (grokdeclarator): Call type_attributes.
* cp/decl2.c (cplus_decl_attributes): Call type_attributes when node is
a type.
* ada/gcc-interface/utils.c (finish_record_type): Call type_attribute.
(process_attributes): Call type_attribute or decl_attribute as needed.
* config/i386/i386.c (ix86_handle_tm_regparm_attribute): Call
type_attribute or decl_attribute as required.
(ix86_init_tm_builtins ): Call type_attributes.
===================================================================
*************** get_attribute_namespace (const_tree attr
return get_identifier ("gnu");
}
/* Process the attributes listed in ATTRIBUTES and install them in *NODE,
! which is either a DECL (including a TYPE_DECL) or a TYPE. If a DECL,
! it should be modified in place; if a TYPE, a copy should be created
! unless ATTR_FLAG_TYPE_IN_PLACE is set in FLAGS. FLAGS gives further
! information, in the form of a bitwise OR of flags in enum attribute_flags
! from tree.h. Depending on these flags, some attributes may be
! returned to be applied at a later stage (for example, to apply
! a decl attribute to the declaration rather than to its type). */
tree
decl_attributes (tree *node, tree attributes, int flags)
return get_identifier ("gnu");
}
+ /* Lookup the spec for attribute A using FLAGS, and issue any warnings or
+ errors as appropriate. Return NULL or a valid spec. */
+
+ static const struct attribute_spec *
+ process_attribute_spec (tree a, int flags)
+ {
+ tree name = get_attribute_name (a);
+ tree ns = get_attribute_namespace (a);
+ tree args = TREE_VALUE (a);
+ const struct attribute_spec *spec = lookup_scoped_attribute_spec (ns, name);
+
+ if (spec == NULL)
+ {
+ if (!(flags & (int) ATTR_FLAG_BUILT_IN))
+ {
+ if (ns == NULL_TREE || !cxx11_attribute_p (a))
+ warning (OPT_Wattributes, "%qE attribute directive ignored",
+ name);
+ else
+ warning (OPT_Wattributes,
+ "%<%E::%E%> scoped attribute directive ignored",
+ ns, name);
+ }
+ return NULL;
+ }
+ else if (list_length (args) < spec->min_length
+ || (spec->max_length >= 0
+ && list_length (args) > spec->max_length))
+ {
+ error ("wrong number of arguments specified for %qE attribute",
+ name);
+ return NULL;
+ }
+ gcc_assert (is_attribute_p (spec->name, name));
+ return spec;
+ }
+
+ /* Perform the type specific processing of type_attribute. This is factored
+ out to allow decl_attributes() to process underlying types when necessary.
+ In those cases, DECL_NODE is passed in so the decl can have re-layout
+ called. SPEC is the already verified attribute spec structure. Otherwise
+ the parameters match those of type_attribute. */
+
+ static tree
+ finalize_type_attribute (tree *node, const struct attribute_spec *spec,
+ tree a, tree returned_attrs, int flags,
+ tree *decl_node = NULL)
+ {
+ bool no_add_attrs = 0;
+ int fn_ptr_quals = 0;
+ tree fn_ptr_tmp = NULL_TREE;
+ tree name = get_attribute_name (a);
+ tree args = TREE_VALUE (a);
+ tree *anode = node;
+
+ gcc_checking_assert (TYPE_P (*node));
+
+ if (spec->function_type_required && TREE_CODE (*anode) != FUNCTION_TYPE
+ && TREE_CODE (*anode) != METHOD_TYPE)
+ {
+ if (TREE_CODE (*anode) == POINTER_TYPE
+ && (TREE_CODE (TREE_TYPE (*anode)) == FUNCTION_TYPE
+ || TREE_CODE (TREE_TYPE (*anode)) == METHOD_TYPE))
+ {
+ /* OK, this is a bit convoluted. We can't just make a copy
+ of the pointer type and modify its TREE_TYPE, because if
+ we change the attributes of the target type the pointer
+ type needs to have a different TYPE_MAIN_VARIANT. So we
+ pull out the target type now, frob it as appropriate, and
+ rebuild the pointer type later.
+
+ This would all be simpler if attributes were part of the
+ declarator, grumble grumble. */
+ fn_ptr_tmp = TREE_TYPE (*anode);
+ fn_ptr_quals = TYPE_QUALS (*anode);
+ anode = &fn_ptr_tmp;
+ flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
+ }
+ else if (flags & (int) ATTR_FLAG_FUNCTION_NEXT)
+ {
+ /* Pass on this attribute to be tried again. */
+ returned_attrs = tree_cons (name, args, returned_attrs);
+ return returned_attrs;
+ }
+
+ if (TREE_CODE (*anode) != FUNCTION_TYPE
+ && TREE_CODE (*anode) != METHOD_TYPE)
+ {
+ warning (OPT_Wattributes,
+ "%qE attribute only applies to function types",
+ name);
+ return returned_attrs;
+ }
+ }
+
+ if ((flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
+ && TYPE_SIZE (*anode) != NULL_TREE)
+ {
+ warning (OPT_Wattributes, "type attributes ignored after type is already defined");
+ return returned_attrs;
+ }
+
+ if (spec->handler != NULL)
+ {
+ int cxx11_flag =
+ cxx11_attribute_p (a) ? ATTR_FLAG_CXX11 : 0;
+
+ returned_attrs = chainon ((*spec->handler) (anode, name, args,
+ flags|cxx11_flag,
+ &no_add_attrs),
+ returned_attrs);
+ }
+
+ /* If there was a decl change the layout in case anything changed. */
+ if (decl_node && spec->type_required
+ && (TREE_CODE (*decl_node) == VAR_DECL
+ || TREE_CODE (*decl_node) == PARM_DECL
+ || TREE_CODE (*decl_node) == RESULT_DECL))
+ relayout_decl (*decl_node);
+
+ if (!no_add_attrs)
+ {
+ tree old_attrs;
+ tree a;
+
+ old_attrs = TYPE_ATTRIBUTES (*anode);
+
+ for (a = lookup_attribute (spec->name, old_attrs);
+ a != NULL_TREE;
+ a = lookup_attribute (spec->name, TREE_CHAIN (a)))
+ {
+ if (simple_cst_equal (TREE_VALUE (a), args) == 1)
+ break;
+ }
+
+ if (a == NULL_TREE)
+ {
+ if (flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
+ {
+ TYPE_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
+ /* If this is the main variant, also push the attributes
+ out to the other variants. */
+ if (*anode == TYPE_MAIN_VARIANT (*anode))
+ {
+ tree variant;
+ for (variant = *anode; variant;
+ variant = TYPE_NEXT_VARIANT (variant))
+ {
+ if (TYPE_ATTRIBUTES (variant) == old_attrs)
+ TYPE_ATTRIBUTES (variant)
+ = TYPE_ATTRIBUTES (*anode);
+ else if (!lookup_attribute
+ (spec->name, TYPE_ATTRIBUTES (variant)))
+ TYPE_ATTRIBUTES (variant) = tree_cons
+ (name, args, TYPE_ATTRIBUTES (variant));
+ }
+ }
+ }
+ else
+ *anode = build_type_attribute_variant (*anode,
+ tree_cons (name, args,
+ old_attrs));
+ }
+ }
+
+ if (fn_ptr_tmp)
+ {
+ /* Rebuild the function pointer type and put it in the
+ appropriate place. */
+ fn_ptr_tmp = build_pointer_type (fn_ptr_tmp);
+ if (fn_ptr_quals)
+ fn_ptr_tmp = build_qualified_type (fn_ptr_tmp, fn_ptr_quals);
+ if (decl_node)
+ TREE_TYPE (*decl_node) = fn_ptr_tmp;
+ else
+ {
+ gcc_assert (TREE_CODE (*node) == POINTER_TYPE);
+ *node = fn_ptr_tmp;
+ }
+ }
+ return returned_attrs;
+
+ }
+
+ /* Process the attributes listed in ATTRIBUTES and install them in *NODE,
+ which is a TYPE. A copy should be created unless ATTR_FLAG_TYPE_IN_PLACE
+ is set in FLAGS. FLAGS gives further information, in the form of a
+ bitwise OR of flags in enum attribute_flags from tree.h.
+ Depending on these flags, some attributes may be returned to be
+ applied at a later stage (for example, to apply a decl attribute to the
+ declaration rather than to its type). */
+
+ tree
+ type_attributes (tree *node, tree attributes, int flags)
+ {
+ tree a;
+ tree returned_attrs = NULL_TREE;
+
+
+ if (TREE_TYPE (*node) == error_mark_node || attributes == error_mark_node)
+ return NULL_TREE;
+
+ gcc_checking_assert (TYPE_P (*node));
+
+ if (!attributes_initialized)
+ init_attributes ();
+
+ targetm.insert_attributes (*node, &attributes);
+
+ for (a = attributes; a; a = TREE_CHAIN (a))
+ {
+ tree name = get_attribute_name (a);
+ tree args = TREE_VALUE (a);
+ const struct attribute_spec *spec = process_attribute_spec (a, flags);
+
+ if (!spec)
+ continue;
+
+ if (cxx11_attribute_p (a) && !(flags & ATTR_FLAG_TYPE_IN_PLACE))
+ {
+ /* This is a c++11 attribute that appertains to a
+ type-specifier, outside of the definition of, a class
+ type. Ignore it. */
+ warning (OPT_Wattributes, "attribute ignored");
+ inform (input_location,
+ "an attribute that appertains to a type-specifier "
+ "is ignored");
+ continue;
+ }
+
+ if (spec->decl_required)
+ {
+ if (flags & ((int) ATTR_FLAG_DECL_NEXT
+ | (int) ATTR_FLAG_FUNCTION_NEXT
+ | (int) ATTR_FLAG_ARRAY_NEXT))
+ {
+ /* Pass on this attribute to be tried again. */
+ returned_attrs = tree_cons (name, args, returned_attrs);
+ continue;
+ }
+ else
+ {
+ warning (OPT_Wattributes, "%qE attribute does not apply to types",
+ name);
+ continue;
+ }
+ }
+
+ returned_attrs = finalize_type_attribute (node, spec, a, returned_attrs,
+ flags);
+ }
+
+ return returned_attrs;
+ }
+
+
+
/* Process the attributes listed in ATTRIBUTES and install them in *NODE,
! which is a DECL (including a TYPE_DECL) it should be modified in place;
! FLAGS gives further information, in the form of a bitwise OR of flags in
! enum attribute_flags from tree.h. Depending on these flags, some
! attributes may be returned to be applied at a later stage. */
tree
decl_attributes (tree *node, tree attributes, int flags)
*************** decl_attributes (tree *node, tree attrib
tree a;
tree returned_attrs = NULL_TREE;
+
if (TREE_TYPE (*node) == error_mark_node || attributes == error_mark_node)
return NULL_TREE;
+ gcc_checking_assert (DECL_P (*node));
+
if (!attributes_initialized)
init_attributes ();
*************** decl_attributes (tree *node, tree attrib
for (a = attributes; a; a = TREE_CHAIN (a))
{
- tree ns = get_attribute_namespace (a);
tree name = get_attribute_name (a);
tree args = TREE_VALUE (a);
tree *anode = node;
- const struct attribute_spec *spec =
- lookup_scoped_attribute_spec (ns, name);
bool no_add_attrs = 0;
! int fn_ptr_quals = 0;
! tree fn_ptr_tmp = NULL_TREE;
! if (spec == NULL)
! {
! if (!(flags & (int) ATTR_FLAG_BUILT_IN))
! {
! if (ns == NULL_TREE || !cxx11_attribute_p (a))
! warning (OPT_Wattributes, "%qE attribute directive ignored",
! name);
! else
! warning (OPT_Wattributes,
! "%<%E::%E%> scoped attribute directive ignored",
! ns, name);
! }
! continue;
! }
! else if (list_length (args) < spec->min_length
! || (spec->max_length >= 0
! && list_length (args) > spec->max_length))
! {
! error ("wrong number of arguments specified for %qE attribute",
! name);
! continue;
! }
! gcc_assert (is_attribute_p (spec->name, name));
! if (TYPE_P (*node)
! && cxx11_attribute_p (a)
! && !(flags & ATTR_FLAG_TYPE_IN_PLACE))
! {
! /* This is a c++11 attribute that appertains to a
! type-specifier, outside of the definition of, a class
! type. Ignore it. */
! warning (OPT_Wattributes, "attribute ignored");
! inform (input_location,
! "an attribute that appertains to a type-specifier "
! "is ignored");
! continue;
! }
!
! if (spec->decl_required && !DECL_P (*anode))
! {
! if (flags & ((int) ATTR_FLAG_DECL_NEXT
! | (int) ATTR_FLAG_FUNCTION_NEXT
! | (int) ATTR_FLAG_ARRAY_NEXT))
! {
! /* Pass on this attribute to be tried again. */
! returned_attrs = tree_cons (name, args, returned_attrs);
! continue;
! }
! else
! {
! warning (OPT_Wattributes, "%qE attribute does not apply to types",
! name);
! continue;
! }
! }
/* If we require a type, but were passed a decl, set up to make a
new type and update the one in the decl. ATTR_FLAG_TYPE_IN_PLACE
would have applied if we'd been passed a type, but we cannot modify
the decl's type in place here. */
! if (spec->type_required && DECL_P (*anode))
{
anode = &TREE_TYPE (*anode);
flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
! }
!
! if (spec->function_type_required && TREE_CODE (*anode) != FUNCTION_TYPE
! && TREE_CODE (*anode) != METHOD_TYPE)
! {
! if (TREE_CODE (*anode) == POINTER_TYPE
! && (TREE_CODE (TREE_TYPE (*anode)) == FUNCTION_TYPE
! || TREE_CODE (TREE_TYPE (*anode)) == METHOD_TYPE))
! {
! /* OK, this is a bit convoluted. We can't just make a copy
! of the pointer type and modify its TREE_TYPE, because if
! we change the attributes of the target type the pointer
! type needs to have a different TYPE_MAIN_VARIANT. So we
! pull out the target type now, frob it as appropriate, and
! rebuild the pointer type later.
!
! This would all be simpler if attributes were part of the
! declarator, grumble grumble. */
! fn_ptr_tmp = TREE_TYPE (*anode);
! fn_ptr_quals = TYPE_QUALS (*anode);
! anode = &fn_ptr_tmp;
! flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
! }
! else if (flags & (int) ATTR_FLAG_FUNCTION_NEXT)
! {
! /* Pass on this attribute to be tried again. */
! returned_attrs = tree_cons (name, args, returned_attrs);
! continue;
! }
!
! if (TREE_CODE (*anode) != FUNCTION_TYPE
! && TREE_CODE (*anode) != METHOD_TYPE)
! {
! warning (OPT_Wattributes,
! "%qE attribute only applies to function types",
! name);
! continue;
! }
! }
!
! if (TYPE_P (*anode)
! && (flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
! && TYPE_SIZE (*anode) != NULL_TREE)
! {
! warning (OPT_Wattributes, "type attributes ignored after type is already defined");
continue;
}
-
if (spec->handler != NULL)
{
int cxx11_flag =
cxx11_attribute_p (a) ? ATTR_FLAG_CXX11 : 0;
-
returned_attrs = chainon ((*spec->handler) (anode, name, args,
! flags|cxx11_flag,
! &no_add_attrs),
returned_attrs);
}
- /* Layout the decl in case anything changed. */
- if (spec->type_required && DECL_P (*node)
- && (TREE_CODE (*node) == VAR_DECL
- || TREE_CODE (*node) == PARM_DECL
- || TREE_CODE (*node) == RESULT_DECL))
- relayout_decl (*node);
-
if (!no_add_attrs)
{
tree old_attrs;
tree a;
! if (DECL_P (*anode))
! old_attrs = DECL_ATTRIBUTES (*anode);
! else
! old_attrs = TYPE_ATTRIBUTES (*anode);
for (a = lookup_attribute (spec->name, old_attrs);
a != NULL_TREE;
for (a = attributes; a; a = TREE_CHAIN (a))
{
tree name = get_attribute_name (a);
tree args = TREE_VALUE (a);
tree *anode = node;
bool no_add_attrs = 0;
! const struct attribute_spec *spec = process_attribute_spec (a, flags);
! gcc_assert (DECL_P (*node));
! if (!spec)
! continue;
/* If we require a type, but were passed a decl, set up to make a
new type and update the one in the decl. ATTR_FLAG_TYPE_IN_PLACE
would have applied if we'd been passed a type, but we cannot modify
the decl's type in place here. */
! if (spec->type_required)
{
anode = &TREE_TYPE (*anode);
flags &= ~(int) ATTR_FLAG_TYPE_IN_PLACE;
! returned_attrs = finalize_type_attribute (anode, spec, a,
! returned_attrs, flags,
! node);
continue;
}
if (spec->handler != NULL)
{
int cxx11_flag =
cxx11_attribute_p (a) ? ATTR_FLAG_CXX11 : 0;
returned_attrs = chainon ((*spec->handler) (anode, name, args,
! flags|cxx11_flag,
! &no_add_attrs),
returned_attrs);
}
if (!no_add_attrs)
{
tree old_attrs;
tree a;
! old_attrs = DECL_ATTRIBUTES (*anode);
for (a = lookup_attribute (spec->name, old_attrs);
a != NULL_TREE;
*************** decl_attributes (tree *node, tree attrib
}
if (a == NULL_TREE)
! {
! /* This attribute isn't already in the list. */
! if (DECL_P (*anode))
! DECL_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
! else if (flags & (int) ATTR_FLAG_TYPE_IN_PLACE)
! {
! TYPE_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
! /* If this is the main variant, also push the attributes
! out to the other variants. */
! if (*anode == TYPE_MAIN_VARIANT (*anode))
! {
! tree variant;
! for (variant = *anode; variant;
! variant = TYPE_NEXT_VARIANT (variant))
! {
! if (TYPE_ATTRIBUTES (variant) == old_attrs)
! TYPE_ATTRIBUTES (variant)
! = TYPE_ATTRIBUTES (*anode);
! else if (!lookup_attribute
! (spec->name, TYPE_ATTRIBUTES (variant)))
! TYPE_ATTRIBUTES (variant) = tree_cons
! (name, args, TYPE_ATTRIBUTES (variant));
! }
! }
! }
! else
! *anode = build_type_attribute_variant (*anode,
! tree_cons (name, args,
! old_attrs));
! }
}
- if (fn_ptr_tmp)
- {
- /* Rebuild the function pointer type and put it in the
- appropriate place. */
- fn_ptr_tmp = build_pointer_type (fn_ptr_tmp);
- if (fn_ptr_quals)
- fn_ptr_tmp = build_qualified_type (fn_ptr_tmp, fn_ptr_quals);
- if (DECL_P (*node))
- TREE_TYPE (*node) = fn_ptr_tmp;
- else
- {
- gcc_assert (TREE_CODE (*node) == POINTER_TYPE);
- *node = fn_ptr_tmp;
- }
- }
}
-
return returned_attrs;
}
}
if (a == NULL_TREE)
! /* This attribute isn't already in the list. */
! DECL_ATTRIBUTES (*anode) = tree_cons (name, args, old_attrs);
}
}
return returned_attrs;
}
*************** get_attribute_name (const_tree attr)
void
apply_tm_attr (tree fndecl, tree attr)
{
! decl_attributes (&TREE_TYPE (fndecl), tree_cons (attr, NULL, NULL), 0);
}
void
apply_tm_attr (tree fndecl, tree attr)
{
! type_attributes (&TREE_TYPE (fndecl), tree_cons (attr, NULL, NULL), 0);
}
===================================================================
*************** extern void init_attributes (void);
from tree.h. Depending on these flags, some attributes may be
returned to be applied at a later stage (for example, to apply
a decl attribute to the declaration rather than to its type). */
+ extern tree type_attributes (tree *, tree, int);
extern tree decl_attributes (tree *, tree, int);
extern bool cxx11_attribute_p (const_tree);
===================================================================
*************** groktypename (struct c_type_name *type_n
DEPRECATED_NORMAL);
/* Apply attributes. */
! decl_attributes (&type, attrs, 0);
return type;
}
DEPRECATED_NORMAL);
/* Apply attributes. */
! type_attributes (&type, attrs, 0);
return type;
}
*************** grokdeclarator (const struct c_declarato
attr_flags |= (int) ATTR_FLAG_FUNCTION_NEXT;
else if (inner_decl->kind == cdk_array)
attr_flags |= (int) ATTR_FLAG_ARRAY_NEXT;
! returned_attrs = decl_attributes (&type,
chainon (returned_attrs, attrs),
attr_flags);
break;
attr_flags |= (int) ATTR_FLAG_FUNCTION_NEXT;
else if (inner_decl->kind == cdk_array)
attr_flags |= (int) ATTR_FLAG_ARRAY_NEXT;
! returned_attrs = type_attributes (&type,
chainon (returned_attrs, attrs),
attr_flags);
break;
*************** finish_struct (location_t loc, tree t, t
TYPE_SIZE (t) = 0;
! decl_attributes (&t, attributes, (int) ATTR_FLAG_TYPE_IN_PLACE);
if (pedantic)
{
TYPE_SIZE (t) = 0;
! type_attributes (&t, attributes, (int) ATTR_FLAG_TYPE_IN_PLACE);
if (pedantic)
{
*************** finish_enum (tree enumtype, tree values,
bool toplevel = (file_scope == current_scope);
struct lang_type *lt;
! decl_attributes (&enumtype, attributes, (int) ATTR_FLAG_TYPE_IN_PLACE);
/* Calculate the maximum value of any enumerator in this type. */
bool toplevel = (file_scope == current_scope);
struct lang_type *lt;
! type_attributes (&enumtype, attributes, (int) ATTR_FLAG_TYPE_IN_PLACE);
/* Calculate the maximum value of any enumerator in this type. */
===================================================================
*************** handle_tm_attribute (tree *node, tree na
if (subcode == FUNCTION_TYPE || subcode == METHOD_TYPE)
{
tree fn_tmp = TREE_TYPE (*node);
! decl_attributes (&fn_tmp, tree_cons (name, args, NULL), 0);
*node = build_pointer_type (fn_tmp);
break;
}
if (subcode == FUNCTION_TYPE || subcode == METHOD_TYPE)
{
tree fn_tmp = TREE_TYPE (*node);
! type_attributes (&fn_tmp, tree_cons (name, args, NULL), 0);
*node = build_pointer_type (fn_tmp);
break;
}
===================================================================
*************** grokdeclarator (const cp_declarator *dec
{
/* Apply the c++11 attributes to the type preceding them. */
input_location = declspecs->locations[ds_std_attribute];
! decl_attributes (&type, declspecs->std_attributes, 0);
input_location = saved_loc;
}
{
/* Apply the c++11 attributes to the type preceding them. */
input_location = declspecs->locations[ds_std_attribute];
! type_attributes (&type, declspecs->std_attributes, 0);
input_location = saved_loc;
}
*************** grokdeclarator (const cp_declarator *dec
attr_flags |= (int) ATTR_FLAG_FUNCTION_NEXT;
if (declarator->kind == cdk_array)
attr_flags |= (int) ATTR_FLAG_ARRAY_NEXT;
! returned_attrs = decl_attributes (&type,
chainon (returned_attrs, attrs),
attr_flags);
}
attr_flags |= (int) ATTR_FLAG_FUNCTION_NEXT;
if (declarator->kind == cdk_array)
attr_flags |= (int) ATTR_FLAG_ARRAY_NEXT;
! returned_attrs = type_attributes (&type,
chainon (returned_attrs, attrs),
attr_flags);
}
*************** grokdeclarator (const cp_declarator *dec
The optional attribute-specifier-seq appertains to
the function type. */
! decl_attributes (&type, declarator->std_attributes,
0);
}
break;
The optional attribute-specifier-seq appertains to
the function type. */
! type_attributes (&type, declarator->std_attributes,
0);
}
break;
*************** grokdeclarator (const cp_declarator *dec
[the optional attribute-specifier-seq (7.6.1) appertains
to the pointer and not to the object pointed to]. */
if (declarator->std_attributes)
! decl_attributes (&type, declarator->std_attributes,
0);
ctype = NULL_TREE;
[the optional attribute-specifier-seq (7.6.1) appertains
to the pointer and not to the object pointed to]. */
if (declarator->std_attributes)
! type_attributes (&type, declarator->std_attributes,
0);
ctype = NULL_TREE;
===================================================================
*************** cplus_decl_attributes (tree *decl, tree
if (TREE_TYPE (*decl) && TYPE_PTRMEMFUNC_P (TREE_TYPE (*decl)))
{
! attributes
! = decl_attributes (decl, attributes, flags | ATTR_FLAG_FUNCTION_NEXT);
! decl_attributes (&TYPE_PTRMEMFUNC_FN_TYPE_RAW (TREE_TYPE (*decl)),
attributes, flags);
}
else
! decl_attributes (decl, attributes, flags);
if (TREE_CODE (*decl) == TYPE_DECL)
SET_IDENTIFIER_TYPE_VALUE (DECL_NAME (*decl), TREE_TYPE (*decl));
if (TREE_TYPE (*decl) && TYPE_PTRMEMFUNC_P (TREE_TYPE (*decl)))
{
! if (TYPE_P (*decl))
! attributes
! = type_attributes (decl, attributes, flags | ATTR_FLAG_FUNCTION_NEXT);
! else
! attributes
! = decl_attributes (decl, attributes, flags | ATTR_FLAG_FUNCTION_NEXT);
! type_attributes (&TYPE_PTRMEMFUNC_FN_TYPE_RAW (TREE_TYPE (*decl)),
attributes, flags);
}
else
! if (TYPE_P (*decl))
! type_attributes (decl, attributes, flags);
! else
! decl_attributes (decl, attributes, flags);
if (TREE_CODE (*decl) == TYPE_DECL)
SET_IDENTIFIER_TYPE_VALUE (DECL_NAME (*decl), TREE_TYPE (*decl));
===================================================================
*************** finish_record_type (tree record_type, tr
efficient packing in almost all cases. */
#ifdef TARGET_MS_BITFIELD_LAYOUT
if (TARGET_MS_BITFIELD_LAYOUT && TYPE_PACKED (record_type))
! decl_attributes (&record_type,
tree_cons (get_identifier ("gcc_struct"),
NULL_TREE, NULL_TREE),
ATTR_FLAG_TYPE_IN_PLACE);
efficient packing in almost all cases. */
#ifdef TARGET_MS_BITFIELD_LAYOUT
if (TARGET_MS_BITFIELD_LAYOUT && TYPE_PACKED (record_type))
! type_attributes (&record_type,
tree_cons (get_identifier ("gcc_struct"),
NULL_TREE, NULL_TREE),
ATTR_FLAG_TYPE_IN_PLACE);
*************** process_attributes (tree *node, struct a
{
case ATTR_MACHINE_ATTRIBUTE:
Sloc_to_locus (Sloc (gnat_node), &input_location);
! decl_attributes (node, tree_cons (attr->name, attr->args, NULL_TREE),
! in_place ? ATTR_FLAG_TYPE_IN_PLACE : 0);
break;
case ATTR_LINK_ALIAS:
{
case ATTR_MACHINE_ATTRIBUTE:
Sloc_to_locus (Sloc (gnat_node), &input_location);
! if (TYPE_P (*node))
! type_attributes (node, tree_cons (attr->name, attr->args, NULL_TREE),
! in_place ? ATTR_FLAG_TYPE_IN_PLACE : 0);
! else
! decl_attributes (node, tree_cons (attr->name, attr->args, NULL_TREE),
! in_place ? ATTR_FLAG_TYPE_IN_PLACE : 0);
break;
case ATTR_LINK_ALIAS:
===================================================================
*************** ix86_handle_tm_regparm_attribute (tree *
alt = tree_cons (NULL, build_int_cst (NULL, 2), NULL);
alt = tree_cons (get_identifier ("regparm"), alt, NULL);
}
! decl_attributes (node, alt, flags);
return NULL_TREE;
}
alt = tree_cons (NULL, build_int_cst (NULL, 2), NULL);
alt = tree_cons (get_identifier ("regparm"), alt, NULL);
}
! if (TYPE_P (*node))
! type_attributes (node, alt, flags);
! else
! decl_attributes (node, alt, flags);
return NULL_TREE;
}
*************** ix86_init_tm_builtins (void)
attrs);
/* add_builtin_function() will set the DECL_ATTRIBUTES, now
set the TYPE_ATTRIBUTES. */
! decl_attributes (&TREE_TYPE (decl), attrs_type, ATTR_FLAG_BUILT_IN);
set_builtin_decl (code, decl, false);
}
attrs);
/* add_builtin_function() will set the DECL_ATTRIBUTES, now
set the TYPE_ATTRIBUTES. */
! type_attributes (&TREE_TYPE (decl), attrs_type, ATTR_FLAG_BUILT_IN);
set_builtin_decl (code, decl, false);
}