This is the mail archive of the
gcc-bugs@gcc.gnu.org
mailing list for the GCC project.
Your June 7 change to expand_expr
- To: Richard Kenner <kenner at vlsi1 dot ultra dot nyu dot edu>
- Subject: Your June 7 change to expand_expr
- From: Mark Mitchell <mark at markmitchell dot com>
- Date: Tue, 30 Jun 1998 16:37:03 -0700
- Cc: egcs-bugs at cygnus dot com, John Carr <jfc at mit dot edu>, Jeff Law <law at cygnus dot com>
- Reply-to: mark at markmitchell dot com
Recent GCC2 changes were just merged into EGCS. One C++ program I
have (but which I cannot release) began generating incorrect output.
I tracked the problem down to this change:
Sun Jun 7 09:30:31 1998 Richard Kenner <kenner@vlsi1.ultra.nyu.edu>
* expr.c (expand_expr, case INDIRECT_EXPR): A dereference of
a REFERENCE_TYPE is always considered in a structure. Likewise for
a dereference of a NOP_EXPR whose input is a pointer to aggregate.
In particular, to the bit about a dereference of a REFERENCE_TYPE be
always considered to be in a structure. I don't know exactly *why*
this was causing the problem, although I'm guessing it's because EGCS
does some alias analysis that looks at MEM_IN_STRUCT_P.
I don't quite understand the change. In particular, the code now
reads:
if (...
/* If the pointer is actually a REFERENCE_TYPE, this could
be pointing into some aggregate too. */
|| TREE_CODE (TREE_TYPE (exp1)) == REFERENCE_TYPE
...)
MEM_IN_STRUCT_P (temp) = 1;
Why should all references be considered as possibly pointing into
structures? If they should be, why shouldn't pointers?
The next hunk:
/* This may have been an array reference to the first element
that was optimized away from being an addition. */
|| (TREE_CODE (exp1) == NOP_EXPR
&& ((TREE_CODE (TREE_TYPE (TREE_OPERAND (exp1, 0)))
== REFERENCE_TYPE)
|| ((TREE_CODE (TREE_TYPE (TREE_OPERAND (exp1, 0)))
== POINTER_TYPE)
&& (AGGREGATE_TYPE_P
(TREE_TYPE (TREE_TYPE
(TREE_OPERAND (exp1, 0))))))))
also seems suspicious to me. Besides the reference issue, how do we
know whether the NOP_EXPR was the degenerate addition case mentioned?
Jeff, for now I recommend the following patch to EGCS.
--
Mark Mitchell mark@markmitchell.com
Mark Mitchell Consulting http://www.markmitchell.com
Tue Jun 30 16:33:44 1998 Mark Mitchell <mark@markmitchell.com>
* expr.c (expand_expr): Revert Kenner's June 7 change.
Index: expr.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/expr.c,v
retrieving revision 1.79
diff -c -p -r1.79 expr.c
*** expr.c 1998/06/29 21:39:43 1.79
--- expr.c 1998/06/30 23:29:45
*************** expand_expr (exp, target, tmode, modifie
*** 5729,5750 ****
|| (TREE_CODE (exp1) == SAVE_EXPR
&& TREE_CODE (TREE_OPERAND (exp1, 0)) == PLUS_EXPR)
|| AGGREGATE_TYPE_P (TREE_TYPE (exp))
- /* If the pointer is actually a REFERENCE_TYPE, this could
- be pointing into some aggregate too. */
- || TREE_CODE (TREE_TYPE (exp1)) == REFERENCE_TYPE
|| (TREE_CODE (exp1) == ADDR_EXPR
&& (exp2 = TREE_OPERAND (exp1, 0))
! && AGGREGATE_TYPE_P (TREE_TYPE (exp2)))
! /* This may have been an array reference to the first element
! that was optimized away from being an addition. */
! || (TREE_CODE (exp1) == NOP_EXPR
! && ((TREE_CODE (TREE_TYPE (TREE_OPERAND (exp1, 0)))
! == REFERENCE_TYPE)
! || ((TREE_CODE (TREE_TYPE (TREE_OPERAND (exp1, 0)))
! == POINTER_TYPE)
! && (AGGREGATE_TYPE_P
! (TREE_TYPE (TREE_TYPE
! (TREE_OPERAND (exp1, 0)))))))))
MEM_IN_STRUCT_P (temp) = 1;
MEM_VOLATILE_P (temp) = TREE_THIS_VOLATILE (exp) | flag_volatile;
MEM_ALIAS_SET (temp) = get_alias_set (exp);
--- 5729,5737 ----
|| (TREE_CODE (exp1) == SAVE_EXPR
&& TREE_CODE (TREE_OPERAND (exp1, 0)) == PLUS_EXPR)
|| AGGREGATE_TYPE_P (TREE_TYPE (exp))
|| (TREE_CODE (exp1) == ADDR_EXPR
&& (exp2 = TREE_OPERAND (exp1, 0))
! && AGGREGATE_TYPE_P (TREE_TYPE (exp2))))
MEM_IN_STRUCT_P (temp) = 1;
MEM_VOLATILE_P (temp) = TREE_THIS_VOLATILE (exp) | flag_volatile;
MEM_ALIAS_SET (temp) = get_alias_set (exp);