fix c/18282, for 4.0
Richard Henderson
rth@redhat.com
Thu Dec 9 23:03:00 GMT 2004
This fixes the bug that Jakub spotted by which we would properly
parse the attribute when it was attached to a typedef, but not
when attached to a regular decl.
I've been thinking that I might port both patches back to 3.4,
since it has been pointed out that the mode attribute on a decl
appeared to function properly. I say "appeared" because
enum B b __attribute__((mode(QI)));
was actually compiled to
unsigned char b;
because we replaced the type node out from under the decl. But
in C I'm not even sure how you'd notice the change to "char"
instead of another unique enum type. Certainly you'd be able
to tell from the debugger, but that's grasping at straws.
r~
* attribs.c (decl_attributes): Use relayout_decl.
* c-common.c (handle_mode_attribute): Copy all relevant type
parameters from the new underlying integral type.
Index: attribs.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/attribs.c,v
retrieving revision 1.34
diff -c -p -d -r1.34 attribs.c
*** attribs.c 15 Sep 2004 20:47:35 -0000 1.34
--- attribs.c 9 Dec 2004 22:53:34 -0000
*************** decl_attributes (tree *node, tree attrib
*** 259,271 ****
&& (TREE_CODE (*node) == VAR_DECL
|| TREE_CODE (*node) == PARM_DECL
|| TREE_CODE (*node) == RESULT_DECL))
! {
! /* Force a recalculation of mode and size. */
! DECL_MODE (*node) = VOIDmode;
! DECL_SIZE (*node) = 0;
!
! layout_decl (*node, 0);
! }
if (!no_add_attrs)
{
--- 259,265 ----
&& (TREE_CODE (*node) == VAR_DECL
|| TREE_CODE (*node) == PARM_DECL
|| TREE_CODE (*node) == RESULT_DECL))
! relayout_decl (*node);
if (!no_add_attrs)
{
Index: c-common.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/c-common.c,v
retrieving revision 1.592
diff -c -p -d -r1.592 c-common.c
*** c-common.c 9 Dec 2004 22:52:15 -0000 1.592
--- c-common.c 9 Dec 2004 22:53:35 -0000
*************** handle_mode_attribute (tree *node, tree
*** 4302,4308 ****
--- 4302,4318 ----
if (!(flags & (int) ATTR_FLAG_TYPE_IN_PLACE))
type = build_variant_type_copy (type);
+
+ /* We cannot use layout_type here, because that will attempt
+ to re-layout all variants, corrupting our original. */
TYPE_PRECISION (type) = TYPE_PRECISION (typefm);
+ TYPE_MIN_VALUE (type) = TYPE_MIN_VALUE (typefm);
+ TYPE_MAX_VALUE (type) = TYPE_MAX_VALUE (typefm);
+ TYPE_SIZE (type) = TYPE_SIZE (typefm);
+ TYPE_SIZE_UNIT (type) = TYPE_SIZE_UNIT (typefm);
+ if (!TYPE_USER_ALIGN (type))
+ TYPE_ALIGN (type) = TYPE_ALIGN (typefm);
+
typefm = type;
}
else if (VECTOR_MODE_P (mode)
*************** handle_mode_attribute (tree *node, tree
*** 4314,4321 ****
}
*node = typefm;
-
- /* No need to layout the type here. The caller should do this. */
}
return NULL_TREE;
--- 4324,4329 ----
More information about the Gcc-patches
mailing list