From 63315c52134b81242ec74c4e60ddc158cff37b5c Mon Sep 17 00:00:00 2001 From: steven Date: Tue, 4 Oct 2005 05:57:38 +0000 Subject: 2005-10-05 Steven Bosscher gcc/ PR tree-optimization/23049 * tree-ssa-dom.c (thread_across_edge): Make sure that the condition of a COND_EXPR is folded before calling fold on the whole rhs of a conditional assignment. * doc/tree-ssa.texi: Update the GIMPLE grammar for a valid rhs to document that a COND_EXPR may appear there. testsuite/ * gcc.dg/pr23049.c: New test. * gcc.dg/ucnid-4.c: Fix test. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@104938 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/tree-ssa-dom.c | 33 ++++++++++++++++++++++++++------- 1 file changed, 26 insertions(+), 7 deletions(-) (limited to 'gcc/tree-ssa-dom.c') diff --git a/gcc/tree-ssa-dom.c b/gcc/tree-ssa-dom.c index 1b78b6d5f39..71dcd4ffc6d 100644 --- a/gcc/tree-ssa-dom.c +++ b/gcc/tree-ssa-dom.c @@ -666,7 +666,7 @@ thread_across_edge (struct dom_walk_data *walk_data, edge e) statements. This does not prevent threading through E->dest. */ for (bsi = bsi_start (e->dest); ! bsi_end_p (bsi); bsi_next (&bsi)) { - tree cached_lhs; + tree cached_lhs = NULL; stmt = bsi_stmt (bsi); @@ -705,7 +705,7 @@ thread_across_edge (struct dom_walk_data *walk_data, edge e) else { /* Copy the operands. */ - tree *copy; + tree *copy, pre_fold_expr; ssa_op_iter iter; use_operand_p use_p; unsigned int num, i = 0; @@ -729,12 +729,31 @@ thread_across_edge (struct dom_walk_data *walk_data, edge e) /* Try to fold/lookup the new expression. Inserting the expression into the hash table is unlikely to help - simplify anything later, so just query the hashtable. */ - cached_lhs = fold (TREE_OPERAND (stmt, 1)); - if (TREE_CODE (cached_lhs) != SSA_NAME - && !is_gimple_min_invariant (cached_lhs)) - cached_lhs = lookup_avail_expr (stmt, false); + Sadly, we have to handle conditional assignments specially + here, because fold expects all the operands of an expression + to be folded before the expression itself is folded, but we + can't just substitute the folded condition here. */ + if (TREE_CODE (TREE_OPERAND (stmt, 1)) == COND_EXPR) + { + tree cond = COND_EXPR_COND (TREE_OPERAND (stmt, 1)); + cond = fold (cond); + if (cond == boolean_true_node) + pre_fold_expr = COND_EXPR_THEN (TREE_OPERAND (stmt, 1)); + else if (cond == boolean_false_node) + pre_fold_expr = COND_EXPR_ELSE (TREE_OPERAND (stmt, 1)); + else + pre_fold_expr = TREE_OPERAND (stmt, 1); + } + else + pre_fold_expr = TREE_OPERAND (stmt, 1); + if (pre_fold_expr) + { + cached_lhs = fold (pre_fold_expr); + if (TREE_CODE (cached_lhs) != SSA_NAME + && !is_gimple_min_invariant (cached_lhs)) + cached_lhs = lookup_avail_expr (stmt, false); + } /* Restore the statement's original uses/defs. */ i = 0; -- cgit v1.2.1