From 52dd234b210c06bea54ef726995e1fce035329be Mon Sep 17 00:00:00 2001 From: Richard Henderson Date: Wed, 12 Oct 2005 16:34:09 -0700 Subject: re PR c/24255 (__transparent_union__ mishandled) PR c/24255 * tree.h (DECL_TRANSPARENT_UNION): Remove. * function.c (assign_parm_find_data_types): Don't support it. * print-tree.c (print_node): Likewise. * c-common.c (handle_transparent_union_attribute): Likewise. Use build_duplicate_type. * tree-inline.c (remap_type_1): Split out of remap_type; properly remap aggregate fields. (build_duplicate_type): New. * doc/extend.texi (Variable Attributes): Remove documentation for transparent_union. From-SVN: r105338 --- gcc/c-common.c | 50 +++++++++++++++++++++++++++----------------------- 1 file changed, 27 insertions(+), 23 deletions(-) (limited to 'gcc/c-common.c') diff --git a/gcc/c-common.c b/gcc/c-common.c index 4114fbf2b19..c5b409e77c0 100644 --- a/gcc/c-common.c +++ b/gcc/c-common.c @@ -4309,39 +4309,43 @@ handle_transparent_union_attribute (tree *node, tree name, tree ARG_UNUSED (args), int flags, bool *no_add_attrs) { - tree decl = NULL_TREE; - tree *type = NULL; - int is_type = 0; + tree type = NULL; + + *no_add_attrs = true; if (DECL_P (*node)) { - decl = *node; - type = &TREE_TYPE (decl); - is_type = TREE_CODE (*node) == TYPE_DECL; + if (TREE_CODE (*node) != TYPE_DECL) + goto ignored; + node = &TREE_TYPE (*node); + type = *node; } else if (TYPE_P (*node)) - type = node, is_type = 1; + type = *node; + else + goto ignored; - if (is_type - && TREE_CODE (*type) == UNION_TYPE - && (decl == 0 - || (TYPE_FIELDS (*type) != 0 - && TYPE_MODE (*type) == DECL_MODE (TYPE_FIELDS (*type))))) + if (TREE_CODE (type) == UNION_TYPE) { + /* When IN_PLACE is set, leave the check for FIELDS and MODE to + the code in finish_struct. */ if (!(flags & (int) ATTR_FLAG_TYPE_IN_PLACE)) - *type = build_variant_type_copy (*type); - TYPE_TRANSPARENT_UNION (*type) = 1; - } - else if (decl != 0 && TREE_CODE (decl) == PARM_DECL - && TREE_CODE (*type) == UNION_TYPE - && TYPE_MODE (*type) == DECL_MODE (TYPE_FIELDS (*type))) - DECL_TRANSPARENT_UNION (decl) = 1; - else - { - warning (OPT_Wattributes, "%qE attribute ignored", name); - *no_add_attrs = true; + { + if (TYPE_FIELDS (type) == NULL_TREE + || TYPE_MODE (type) != DECL_MODE (TYPE_FIELDS (type))) + goto ignored; + + /* A type variant isn't good enough, since we don't a cast + to such a type removed as a no-op. */ + *node = type = build_duplicate_type (type); + } + + TYPE_TRANSPARENT_UNION (type) = 1; + return NULL_TREE; } + ignored: + warning (OPT_Wattributes, "%qE attribute ignored", name); return NULL_TREE; } -- cgit v1.2.1