From 1809ff6b9a9fd3ff2097bc802f328d8530ab2420 Mon Sep 17 00:00:00 2001 From: Andrew Pinski Date: Wed, 1 Mar 2006 15:15:38 +0000 Subject: [PATCH] re PR middle-end/26022 (ICE with references and virtual functions) 2006-01-23 Andrew Pinski PR middle-end/26022 Revert: PR middle-end/24437 * tree-ssa-ccp.c (fold_stmt): Move folding of OBJ_TYPE_REF with a call expr to ... * fold-const.c (fold_ternary) : Here. 2006-02-28 Andrew Pinski PR middle-end/26022 * g++.dg/opt/return-slot1.C: New test. From-SVN: r111602 --- gcc/ChangeLog | 9 +++++++ gcc/fold-const.c | 20 --------------- gcc/testsuite/ChangeLog | 5 ++++ gcc/testsuite/g++.dg/opt/return-slot1.C | 14 ++++++++++ gcc/tree-ssa-ccp.c | 34 +++++++++++++++++++++++++ 5 files changed, 62 insertions(+), 20 deletions(-) create mode 100644 gcc/testsuite/g++.dg/opt/return-slot1.C diff --git a/gcc/ChangeLog b/gcc/ChangeLog index b141b3ede91..b912f617a98 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,12 @@ +2006-01-23 Andrew Pinski + + PR middle-end/26022 + Revert: + PR middle-end/24437 + * tree-ssa-ccp.c (fold_stmt): Move folding of OBJ_TYPE_REF + with a call expr to ... + * fold-const.c (fold_ternary) : Here. + 2006-03-01 Diego Novillo * tree-vrp.c (extract_range_from_assert): Remove special diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 81d5f9fa251..2e8996984e5 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -10565,26 +10565,6 @@ fold_ternary (enum tree_code code, tree type, tree op0, tree op1, tree op2) && TREE_CODE (TREE_OPERAND (op0, 0)) == FUNCTION_DECL && DECL_BUILT_IN (TREE_OPERAND (op0, 0))) return fold_builtin (TREE_OPERAND (op0, 0), op1, false); - /* Check for resolvable OBJ_TYPE_REF. The only sorts we can resolve - here are when we've propagated the address of a decl into the - object slot. */ - if (TREE_CODE (op0) == OBJ_TYPE_REF - && lang_hooks.fold_obj_type_ref - && TREE_CODE (OBJ_TYPE_REF_OBJECT (op0)) == ADDR_EXPR - && DECL_P (TREE_OPERAND (OBJ_TYPE_REF_OBJECT (op0), 0))) - { - tree t; - - /* ??? Caution: Broken ADDR_EXPR semantics means that - looking at the type of the operand of the addr_expr - can yield an array type. See silly exception in - check_pointer_types_r. */ - - t = TREE_TYPE (TREE_TYPE (OBJ_TYPE_REF_OBJECT (op0))); - t = lang_hooks.fold_obj_type_ref (op0, t); - if (t) - return fold_build3 (code, type, t, op1, op2); - } return NULL_TREE; case BIT_FIELD_REF: diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 0b27651048b..d5c50deb8f6 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2006-02-28 Andrew Pinski + + PR middle-end/26022 + * g++.dg/opt/return-slot1.C: New test. + 2006-02-28 Jerry DeLisle PR libgfortran/26136 diff --git a/gcc/testsuite/g++.dg/opt/return-slot1.C b/gcc/testsuite/g++.dg/opt/return-slot1.C new file mode 100644 index 00000000000..fcc6cea5abe --- /dev/null +++ b/gcc/testsuite/g++.dg/opt/return-slot1.C @@ -0,0 +1,14 @@ +// { dg-do compile } +// { dg-options "-O2" } + +struct A +{ + A(); + virtual A foo() const; +}; + +void bar() +{ + const A& a=A(); + a.foo(); +} diff --git a/gcc/tree-ssa-ccp.c b/gcc/tree-ssa-ccp.c index ec70c36d6d3..309a2827848 100644 --- a/gcc/tree-ssa-ccp.c +++ b/gcc/tree-ssa-ccp.c @@ -2350,6 +2350,40 @@ fold_stmt (tree *stmt_p) callee = get_callee_fndecl (rhs); if (callee && DECL_BUILT_IN (callee)) result = ccp_fold_builtin (stmt, rhs); + else + { + /* Check for resolvable OBJ_TYPE_REF. The only sorts we can resolve + here are when we've propagated the address of a decl into the + object slot. */ + /* ??? Should perhaps do this in fold proper. However, doing it + there requires that we create a new CALL_EXPR, and that requires + copying EH region info to the new node. Easier to just do it + here where we can just smash the call operand. Also + CALL_EXPR_RETURN_SLOT_OPT needs to be handled correctly and + copied, fold_ternary does not have not information. */ + callee = TREE_OPERAND (rhs, 0); + if (TREE_CODE (callee) == OBJ_TYPE_REF + && lang_hooks.fold_obj_type_ref + && TREE_CODE (OBJ_TYPE_REF_OBJECT (callee)) == ADDR_EXPR + && DECL_P (TREE_OPERAND + (OBJ_TYPE_REF_OBJECT (callee), 0))) + { + tree t; + + /* ??? Caution: Broken ADDR_EXPR semantics means that + looking at the type of the operand of the addr_expr + can yield an array type. See silly exception in + check_pointer_types_r. */ + + t = TREE_TYPE (TREE_TYPE (OBJ_TYPE_REF_OBJECT (callee))); + t = lang_hooks.fold_obj_type_ref (callee, t); + if (t) + { + TREE_OPERAND (rhs, 0) = t; + changed = true; + } + } + } } /* If we couldn't fold the RHS, hand over to the generic fold routines. */