[PATCH] Fix middle-end/15054 (take 2)
Ulrich Weigand
weigand@i1.informatik.uni-erlangen.de
Fri Apr 30 15:28:00 GMT 2004
Mike Stump wrote:
> I see the problem. I don't like your patch, it gets the lifetime
> wrong. Please just do this:
[snip]
Ah, I see. I've implemented your suggestion in the patch below,
and it does indeed also fix the test case.
Bootstrapped/regtested on s390-ibm-linux and s390x-ibm-linux.
OK?
Bye,
Ulrich
ChangeLog:
PR middle-end/15054
* expr.c (expand_expr_real): Do not call preserve_temp_slots
on a TARGET_EXPR temp.
* function.c (assign_stack_temp_for_type): Set 'keep' flag for
TARGET_EXPR temp slots.
testsuite/ChangeLog:
PR middle-end/15054
* g++.dg/opt/pr15054.C: New test.
Index: gcc/expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.639
diff -c -p -r1.639 expr.c
*** gcc/expr.c 25 Apr 2004 23:52:13 -0000 1.639
--- gcc/expr.c 30 Apr 2004 12:52:18 -0000
*************** expand_expr_real (tree exp, rtx target,
*** 8525,8532 ****
else
{
target = assign_temp (type, 2, 0, 1);
- /* All temp slots at this level must not conflict. */
- preserve_temp_slots (target);
SET_DECL_RTL (slot, target);
if (TREE_ADDRESSABLE (slot))
put_var_into_stack (slot, /*rescan=*/false);
--- 8525,8530 ----
Index: gcc/function.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/function.c,v
retrieving revision 1.513
diff -c -p -r1.513 function.c
*** gcc/function.c 28 Apr 2004 20:40:44 -0000 1.513
--- gcc/function.c 30 Apr 2004 12:52:19 -0000
*************** assign_stack_temp_for_type (enum machine
*** 780,786 ****
if (keep == 2)
{
p->level = target_temp_slot_level;
! p->keep = 0;
}
else if (keep == 3)
{
--- 780,786 ----
if (keep == 2)
{
p->level = target_temp_slot_level;
! p->keep = 1;
}
else if (keep == 3)
{
*** /dev/null Mon Mar 15 14:37:15 2004
--- gcc/testsuite/g++.dg/opt/pr15054.C Thu Apr 29 04:06:20 2004
***************
*** 0 ****
--- 1,36 ----
+ // PR middle-end/15054
+ // This used to abort due to overlapping stack temporaries.
+
+ // { dg-do run }
+ // { dg-options "-O" }
+
+ extern "C" void abort (void);
+
+ struct pointer
+ {
+ void* ptr;
+
+ pointer(void* x = 0) : ptr(x) {}
+ pointer(const pointer& x) : ptr(x.ptr) {}
+ };
+
+ struct element
+ {
+ int canary;
+
+ element() : canary(123) { }
+ ~element() { pointer(); if (canary != 123) abort (); }
+ };
+
+ inline pointer
+ insert(const element& x)
+ {
+ return pointer(new element(x));
+ }
+
+ int
+ main (void)
+ {
+ insert(element());
+ return 0;
+ }
--
Dr. Ulrich Weigand
weigand@informatik.uni-erlangen.de
More information about the Gcc-patches
mailing list