From 55a3be2f5255d69e740d61b2c5aaba1ccbc643b8 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Mon, 4 Oct 2021 10:57:45 +0200 Subject: tree-optimization/102570 - teach VN about internal functions We're now using internal functions for a lot of stuff but there's still missing VN support out of laziness. The following instantiates support and adds testcases for FRE and PRE (hoisting). 2021-10-04 Richard Biener PR tree-optimization/102570 * tree-ssa-sccvn.h (vn_reference_op_struct): Document we are using clique for the internal function code. * tree-ssa-sccvn.c (vn_reference_op_eq): Compare the internal function code. (print_vn_reference_ops): Print the internal function code. (vn_reference_op_compute_hash): Hash it. (copy_reference_ops_from_call): Record it. (visit_stmt): Remove the restriction around internal function calls. (fully_constant_vn_reference_p): Use fold_const_call and handle internal functions. (vn_reference_eq): Compare call return types. * tree-ssa-pre.c (create_expression_by_pieces): Handle generating calls to internal functions. (compute_avail): Remove the restriction around internal function calls. * gcc.dg/tree-ssa/ssa-fre-96.c: New testcase. * gcc.dg/tree-ssa/ssa-pre-33.c: Likewise. --- gcc/tree-ssa-pre.c | 27 +++++++++++++++++---------- 1 file changed, 17 insertions(+), 10 deletions(-) (limited to 'gcc/tree-ssa-pre.c') diff --git a/gcc/tree-ssa-pre.c b/gcc/tree-ssa-pre.c index 0875584..1cc1aae 100644 --- a/gcc/tree-ssa-pre.c +++ b/gcc/tree-ssa-pre.c @@ -2855,9 +2855,13 @@ create_expression_by_pieces (basic_block block, pre_expr expr, unsigned int operand = 1; vn_reference_op_t currop = &ref->operands[0]; tree sc = NULL_TREE; - tree fn = find_or_generate_expression (block, currop->op0, stmts); - if (!fn) - return NULL_TREE; + tree fn = NULL_TREE; + if (currop->op0) + { + fn = find_or_generate_expression (block, currop->op0, stmts); + if (!fn) + return NULL_TREE; + } if (currop->op1) { sc = find_or_generate_expression (block, currop->op1, stmts); @@ -2873,12 +2877,19 @@ create_expression_by_pieces (basic_block block, pre_expr expr, return NULL_TREE; args.quick_push (arg); } - gcall *call = gimple_build_call_vec (fn, args); + gcall *call; + if (currop->op0) + { + call = gimple_build_call_vec (fn, args); + gimple_call_set_fntype (call, currop->type); + } + else + call = gimple_build_call_internal_vec ((internal_fn)currop->clique, + args); gimple_set_location (call, expr->loc); - gimple_call_set_fntype (call, currop->type); if (sc) gimple_call_set_chain (call, sc); - tree forcedname = make_ssa_name (TREE_TYPE (currop->type)); + tree forcedname = make_ssa_name (ref->type); gimple_call_set_lhs (call, forcedname); /* There's no CCP pass after PRE which would re-compute alignment information so make sure we re-materialize this here. */ @@ -4004,10 +4015,6 @@ compute_avail (function *fun) vn_reference_s ref1; pre_expr result = NULL; - /* We can value number only calls to real functions. */ - if (gimple_call_internal_p (stmt)) - continue; - vn_reference_lookup_call (as_a (stmt), &ref, &ref1); /* There is no point to PRE a call without a value. */ if (!ref || !ref->result) -- cgit v1.1