+2012-09-13 Richard Guenther <rguenther@suse.de>
+
+ * tree-ssa-sccvn.h (enum vn_kind): New.
+ (vn_get_stmt_kind): Likewise.
+ * tree-ssa-sccvn.c (vn_get_stmt_kind): New function, adjust
+ ADDR_EXPR handling.
+ (visit_use): Use it.
+ * tree-ssa-pre.c (compute_avail): Likewise, simplify further.
+
2012-09-13 Venkataramanan Kumar <venkataramanan.kumar@amd.com>
* config/i386/i386.c (processor_alias_table): Enable PTA_PRFCHW
+2012-09-13 Richard Guenther <rguenther@suse.de>
+
+ * gcc.dg/tree-ssa/ssa-fre-37.c: New testcase.
+
2012-09-13 Christophe Lyon <christophe.lyon@linaro.org>
* gcc.target/arm/builtin-bswap-1.c: New testcase.
--- /dev/null
+/* { dg-do compile } */
+/* { dg-options "-O -fdump-tree-fre1" } */
+
+int a[256];
+int *b, *c;
+void foo (int i, int j)
+{
+ b = &a[i+j];
+ c = &a[i+j];
+}
+
+/* We should remove the redundant address computation. */
+
+/* { dg-final { scan-tree-dump-times " = &a" 1 "fre1" } } */
+/* { dg-final { cleanup-tree-dump "fre1" } } */
bitmap_value_insert_into_set (AVAIL_OUT (block), e);
}
- if (gimple_has_side_effects (stmt) || stmt_could_throw_p (stmt))
+ if (gimple_has_side_effects (stmt)
+ || stmt_could_throw_p (stmt)
+ || is_gimple_debug (stmt))
continue;
+ FOR_EACH_SSA_TREE_OPERAND (op, stmt, iter, SSA_OP_USE)
+ add_to_exp_gen (block, op);
+
switch (gimple_code (stmt))
{
case GIMPLE_RETURN:
- FOR_EACH_SSA_TREE_OPERAND (op, stmt, iter, SSA_OP_USE)
- add_to_exp_gen (block, op);
continue;
case GIMPLE_CALL:
{
vn_reference_t ref;
- unsigned int i;
- vn_reference_op_t vro;
pre_expr result = NULL;
VEC(vn_reference_op_s, heap) *ops = NULL;
if (!ref)
continue;
- for (i = 0; VEC_iterate (vn_reference_op_s,
- ref->operands, i,
- vro); i++)
- {
- if (vro->op0 && TREE_CODE (vro->op0) == SSA_NAME)
- add_to_exp_gen (block, vro->op0);
- if (vro->op1 && TREE_CODE (vro->op1) == SSA_NAME)
- add_to_exp_gen (block, vro->op1);
- if (vro->op2 && TREE_CODE (vro->op2) == SSA_NAME)
- add_to_exp_gen (block, vro->op2);
- }
-
/* If the value of the call is not invalidated in
this block until it is computed, add the expression
to EXP_GEN. */
case GIMPLE_ASSIGN:
{
pre_expr result = NULL;
- switch (TREE_CODE_CLASS (gimple_assign_rhs_code (stmt)))
+ switch (vn_get_stmt_kind (stmt))
{
- case tcc_unary:
- case tcc_binary:
- case tcc_comparison:
+ case VN_NARY:
{
vn_nary_op_t nary;
- unsigned int i;
-
vn_nary_op_lookup_pieces (gimple_num_ops (stmt) - 1,
gimple_assign_rhs_code (stmt),
gimple_expr_type (stmt),
gimple_assign_rhs1_ptr (stmt),
&nary);
-
if (!nary)
continue;
- for (i = 0; i < nary->length; i++)
- if (TREE_CODE (nary->op[i]) == SSA_NAME)
- add_to_exp_gen (block, nary->op[i]);
-
/* If the NARY traps and there was a preceding
point in the block that might not return avoid
adding the nary to EXP_GEN. */
break;
}
- case tcc_declaration:
- case tcc_reference:
+ case VN_REFERENCE:
{
vn_reference_t ref;
- unsigned int i;
- vn_reference_op_t vro;
-
vn_reference_lookup (gimple_assign_rhs1 (stmt),
gimple_vuse (stmt),
VN_WALK, &ref);
if (!ref)
continue;
- for (i = 0; VEC_iterate (vn_reference_op_s,
- ref->operands, i,
- vro); i++)
- {
- if (vro->op0 && TREE_CODE (vro->op0) == SSA_NAME)
- add_to_exp_gen (block, vro->op0);
- if (vro->op1 && TREE_CODE (vro->op1) == SSA_NAME)
- add_to_exp_gen (block, vro->op1);
- if (vro->op2 && TREE_CODE (vro->op2) == SSA_NAME)
- add_to_exp_gen (block, vro->op2);
- }
-
/* If the value of the reference is not invalidated in
this block until it is computed, add the expression
to EXP_GEN. */
}
default:
- /* For any other statement that we don't
- recognize, simply add all referenced
- SSA_NAMEs to EXP_GEN. */
- FOR_EACH_SSA_TREE_OPERAND (op, stmt, iter, SSA_OP_USE)
- add_to_exp_gen (block, op);
continue;
}
get_or_alloc_expression_id (result);
add_to_value (get_expr_value_id (result), result);
bitmap_value_insert_into_set (EXP_GEN (block), result);
-
continue;
}
default:
return expr;
}
+/* Return the vn_kind the expression computed by the stmt should be
+ associated with. */
+
+enum vn_kind
+vn_get_stmt_kind (gimple stmt)
+{
+ switch (gimple_code (stmt))
+ {
+ case GIMPLE_CALL:
+ return VN_REFERENCE;
+ case GIMPLE_PHI:
+ return VN_PHI;
+ case GIMPLE_ASSIGN:
+ {
+ enum tree_code code = gimple_assign_rhs_code (stmt);
+ tree rhs1 = gimple_assign_rhs1 (stmt);
+ switch (get_gimple_rhs_class (code))
+ {
+ case GIMPLE_UNARY_RHS:
+ case GIMPLE_BINARY_RHS:
+ case GIMPLE_TERNARY_RHS:
+ return VN_NARY;
+ case GIMPLE_SINGLE_RHS:
+ switch (TREE_CODE_CLASS (code))
+ {
+ case tcc_reference:
+ /* VOP-less references can go through unary case. */
+ if ((code == REALPART_EXPR
+ || code == IMAGPART_EXPR
+ || code == VIEW_CONVERT_EXPR
+ || code == BIT_FIELD_REF)
+ && TREE_CODE (TREE_OPERAND (rhs1, 0)) == SSA_NAME)
+ return VN_NARY;
+
+ /* Fallthrough. */
+ case tcc_declaration:
+ return VN_REFERENCE;
+
+ case tcc_constant:
+ return VN_CONSTANT;
+
+ default:
+ if (code == ADDR_EXPR)
+ return (is_gimple_min_invariant (rhs1)
+ ? VN_CONSTANT : VN_REFERENCE);
+ else if (code == CONSTRUCTOR)
+ return VN_NARY;
+ return VN_NONE;
+ }
+ default:
+ return VN_NONE;
+ }
+ }
+ default:
+ return VN_NONE;
+ }
+}
/* Free a phi operation structure VP. */
}
else
{
- switch (get_gimple_rhs_class (code))
+ switch (vn_get_stmt_kind (stmt))
{
- case GIMPLE_UNARY_RHS:
- case GIMPLE_BINARY_RHS:
- case GIMPLE_TERNARY_RHS:
+ case VN_NARY:
changed = visit_nary_op (lhs, stmt);
break;
- case GIMPLE_SINGLE_RHS:
- switch (TREE_CODE_CLASS (code))
- {
- case tcc_reference:
- /* VOP-less references can go through unary case. */
- if ((code == REALPART_EXPR
- || code == IMAGPART_EXPR
- || code == VIEW_CONVERT_EXPR
- || code == BIT_FIELD_REF)
- && TREE_CODE (TREE_OPERAND (rhs1, 0)) == SSA_NAME)
- {
- changed = visit_nary_op (lhs, stmt);
- break;
- }
- /* Fallthrough. */
- case tcc_declaration:
- changed = visit_reference_op_load (lhs, rhs1, stmt);
- break;
- default:
- if (code == ADDR_EXPR)
- {
- changed = visit_nary_op (lhs, stmt);
- break;
- }
- else if (code == CONSTRUCTOR)
- {
- changed = visit_nary_op (lhs, stmt);
- break;
- }
- changed = defs_to_varying (stmt);
- }
+ case VN_REFERENCE:
+ changed = visit_reference_op_load (lhs, rhs1, stmt);
break;
default:
changed = defs_to_varying (stmt);
tree constant;
} *vn_constant_t;
+enum vn_kind { VN_NONE, VN_CONSTANT, VN_NARY, VN_REFERENCE, VN_PHI };
+enum vn_kind vn_get_stmt_kind (gimple);
+
/* Hash the constant CONSTANT with distinguishing type incompatible
constants in the types_compatible_p sense. */