summaryrefslogtreecommitdiff
path: root/gcc/cp/decl2.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/cp/decl2.c')
-rw-r--r--gcc/cp/decl2.c63
1 files changed, 58 insertions, 5 deletions
diff --git a/gcc/cp/decl2.c b/gcc/cp/decl2.c
index 078ca99e6f8..41af32faec4 100644
--- a/gcc/cp/decl2.c
+++ b/gcc/cp/decl2.c
@@ -991,11 +991,8 @@ is_late_template_attribute (tree attr, tree decl)
/* Unknown attribute. */
return false;
- /* Attribute vector_size handling wants to dive into the back end array
- building code, which breaks during template processing. */
- if (is_attribute_p ("vector_size", name)
- /* Attribute weak handling wants to write out assembly right away. */
- || is_attribute_p ("weak", name))
+ /* Attribute weak handling wants to write out assembly right away. */
+ if (is_attribute_p ("weak", name))
return true;
/* If any of the arguments are dependent expressions, we can't evaluate
@@ -1120,6 +1117,62 @@ save_template_attributes (tree *attr_p, tree *decl_p)
}
}
+/* Like reconstruct_complex_type, but handle also template trees. */
+
+tree
+cp_reconstruct_complex_type (tree type, tree bottom)
+{
+ tree inner, outer;
+
+ if (TREE_CODE (type) == POINTER_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ outer = build_pointer_type_for_mode (inner, TYPE_MODE (type),
+ TYPE_REF_CAN_ALIAS_ALL (type));
+ }
+ else if (TREE_CODE (type) == REFERENCE_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ outer = build_reference_type_for_mode (inner, TYPE_MODE (type),
+ TYPE_REF_CAN_ALIAS_ALL (type));
+ }
+ else if (TREE_CODE (type) == ARRAY_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ outer = build_cplus_array_type (inner, TYPE_DOMAIN (type));
+ /* Don't call cp_build_qualified_type on ARRAY_TYPEs, the
+ element type qualification will be handled by the recursive
+ cp_reconstruct_complex_type call and cp_build_qualified_type
+ for ARRAY_TYPEs changes the element type. */
+ return outer;
+ }
+ else if (TREE_CODE (type) == FUNCTION_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ outer = build_function_type (inner, TYPE_ARG_TYPES (type));
+ }
+ else if (TREE_CODE (type) == METHOD_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ /* The build_method_type_directly() routine prepends 'this' to argument list,
+ so we must compensate by getting rid of it. */
+ outer
+ = build_method_type_directly
+ (TREE_TYPE (TREE_VALUE (TYPE_ARG_TYPES (type))),
+ inner,
+ TREE_CHAIN (TYPE_ARG_TYPES (type)));
+ }
+ else if (TREE_CODE (type) == OFFSET_TYPE)
+ {
+ inner = cp_reconstruct_complex_type (TREE_TYPE (type), bottom);
+ outer = build_offset_type (TYPE_OFFSET_BASETYPE (type), inner);
+ }
+ else
+ return bottom;
+
+ return cp_build_qualified_type (outer, TYPE_QUALS (type));
+}
+
/* Like decl_attributes, but handle C++ complexity. */
void