Message ID | ri67c9iq6ju.fsf@virgil.suse.cz |
---|---|
State | New |
Headers | show |
Series | [1/8] ipa: Fix jump function copying | expand |
On Tue, Nov 5, 2024 at 12:12 PM Martin Jambor <mjambor@suse.cz> wrote: > > Hi, > > the next patch in the series introduces a verifier that prints a > single jump function when it fails with the function introduced in > this one. Because it is a verifier, the risk that it would need to e > reverted are non-zero and because the function can be useful on its > own, this is a special patch to introduce it. > > Bootstrapped and tested on x86_64-linux, the whole patch series has > additionally passed LTO and profiled-LTO bootstrap on the same platform > and a bootstrap and testsuite on ppc64-linux. Aarch64-linux bootstrap > and testing is in progress. OK for master is that passes too? OK. Richard. > Thanks, > > Martin > > > gcc/ChangeLog: > > 2024-11-01 Martin Jambor <mjambor@suse.cz> > > * ipa-prop.h (ipa_dump_jump_function): Declare. > * ipa-prop.cc (ipa_dump_jump_function): New function. > (ipa_print_node_jump_functions_for_edge): Move printing of > individual jump functions to the new function. > --- > gcc/ipa-prop.cc | 221 +++++++++++++++++++++++++----------------------- > gcc/ipa-prop.h | 2 + > 2 files changed, 116 insertions(+), 107 deletions(-) > > diff --git a/gcc/ipa-prop.cc b/gcc/ipa-prop.cc > index 3b24bcbed15..3ff4753653b 100644 > --- a/gcc/ipa-prop.cc > +++ b/gcc/ipa-prop.cc > @@ -429,6 +429,117 @@ ipa_print_constant_value (FILE *f, tree val) > } > } > > +/* Print contents of JFUNC to F. If CTX is non-NULL, dump it too. */ > + > +DEBUG_FUNCTION void > +ipa_dump_jump_function (FILE *f, ipa_jump_func *jump_func, > + class ipa_polymorphic_call_context *ctx) > +{ > + enum jump_func_type type = jump_func->type; > + > + if (type == IPA_JF_UNKNOWN) > + fprintf (f, "UNKNOWN\n"); > + else if (type == IPA_JF_CONST) > + { > + fprintf (f, "CONST: "); > + ipa_print_constant_value (f, jump_func->value.constant.value); > + fprintf (f, "\n"); > + } > + else if (type == IPA_JF_PASS_THROUGH) > + { > + fprintf (f, "PASS THROUGH: "); > + fprintf (f, "%d, op %s", > + jump_func->value.pass_through.formal_id, > + get_tree_code_name(jump_func->value.pass_through.operation)); > + if (jump_func->value.pass_through.operation != NOP_EXPR) > + { > + fprintf (f, " "); > + print_generic_expr (f, jump_func->value.pass_through.operand); > + } > + if (jump_func->value.pass_through.agg_preserved) > + fprintf (f, ", agg_preserved"); > + if (jump_func->value.pass_through.refdesc_decremented) > + fprintf (f, ", refdesc_decremented"); > + fprintf (f, "\n"); > + } > + else if (type == IPA_JF_ANCESTOR) > + { > + fprintf (f, "ANCESTOR: "); > + fprintf (f, "%d, offset " HOST_WIDE_INT_PRINT_DEC, > + jump_func->value.ancestor.formal_id, > + jump_func->value.ancestor.offset); > + if (jump_func->value.ancestor.agg_preserved) > + fprintf (f, ", agg_preserved"); > + if (jump_func->value.ancestor.keep_null) > + fprintf (f, ", keep_null"); > + fprintf (f, "\n"); > + } > + > + if (jump_func->agg.items) > + { > + struct ipa_agg_jf_item *item; > + int j; > + > + fprintf (f, " Aggregate passed by %s:\n", > + jump_func->agg.by_ref ? "reference" : "value"); > + FOR_EACH_VEC_ELT (*jump_func->agg.items, j, item) > + { > + fprintf (f, " offset: " HOST_WIDE_INT_PRINT_DEC ", ", > + item->offset); > + fprintf (f, "type: "); > + print_generic_expr (f, item->type); > + fprintf (f, ", "); > + if (item->jftype == IPA_JF_PASS_THROUGH) > + fprintf (f, "PASS THROUGH: %d,", > + item->value.pass_through.formal_id); > + else if (item->jftype == IPA_JF_LOAD_AGG) > + { > + fprintf (f, "LOAD AGG: %d", > + item->value.pass_through.formal_id); > + fprintf (f, " [offset: " HOST_WIDE_INT_PRINT_DEC ", by %s],", > + item->value.load_agg.offset, > + item->value.load_agg.by_ref ? "reference" > + : "value"); > + } > + > + if (item->jftype == IPA_JF_PASS_THROUGH > + || item->jftype == IPA_JF_LOAD_AGG) > + { > + fprintf (f, " op %s", > + get_tree_code_name (item->value.pass_through.operation)); > + if (item->value.pass_through.operation != NOP_EXPR) > + { > + fprintf (f, " "); > + print_generic_expr (f, item->value.pass_through.operand); > + } > + } > + else if (item->jftype == IPA_JF_CONST) > + { > + fprintf (f, "CONST: "); > + ipa_print_constant_value (f, item->value.constant); > + } > + else if (item->jftype == IPA_JF_UNKNOWN) > + fprintf (f, "UNKNOWN: " HOST_WIDE_INT_PRINT_DEC " bits", > + tree_to_uhwi (TYPE_SIZE (item->type))); > + fprintf (f, "\n"); > + } > + } > + > + if (ctx && !ctx->useless_p ()) > + { > + fprintf (f, " Context: "); > + ctx->dump (dump_file); > + } > + > + if (jump_func->m_vr) > + { > + jump_func->m_vr->dump (f); > + fprintf (f, "\n"); > + } > + else > + fprintf (f, " Unknown VR\n"); > +} > + > /* Print the jump functions associated with call graph edge CS to file F. */ > > static void > @@ -439,116 +550,12 @@ ipa_print_node_jump_functions_for_edge (FILE *f, struct cgraph_edge *cs) > > for (int i = 0; i < count; i++) > { > - struct ipa_jump_func *jump_func; > - enum jump_func_type type; > - > - jump_func = ipa_get_ith_jump_func (args, i); > - type = jump_func->type; > - > - fprintf (f, " param %d: ", i); > - if (type == IPA_JF_UNKNOWN) > - fprintf (f, "UNKNOWN\n"); > - else if (type == IPA_JF_CONST) > - { > - fprintf (f, "CONST: "); > - ipa_print_constant_value (f, jump_func->value.constant.value); > - fprintf (f, "\n"); > - } > - else if (type == IPA_JF_PASS_THROUGH) > - { > - fprintf (f, "PASS THROUGH: "); > - fprintf (f, "%d, op %s", > - jump_func->value.pass_through.formal_id, > - get_tree_code_name(jump_func->value.pass_through.operation)); > - if (jump_func->value.pass_through.operation != NOP_EXPR) > - { > - fprintf (f, " "); > - print_generic_expr (f, jump_func->value.pass_through.operand); > - } > - if (jump_func->value.pass_through.agg_preserved) > - fprintf (f, ", agg_preserved"); > - if (jump_func->value.pass_through.refdesc_decremented) > - fprintf (f, ", refdesc_decremented"); > - fprintf (f, "\n"); > - } > - else if (type == IPA_JF_ANCESTOR) > - { > - fprintf (f, "ANCESTOR: "); > - fprintf (f, "%d, offset " HOST_WIDE_INT_PRINT_DEC, > - jump_func->value.ancestor.formal_id, > - jump_func->value.ancestor.offset); > - if (jump_func->value.ancestor.agg_preserved) > - fprintf (f, ", agg_preserved"); > - if (jump_func->value.ancestor.keep_null) > - fprintf (f, ", keep_null"); > - fprintf (f, "\n"); > - } > - > - if (jump_func->agg.items) > - { > - struct ipa_agg_jf_item *item; > - int j; > - > - fprintf (f, " Aggregate passed by %s:\n", > - jump_func->agg.by_ref ? "reference" : "value"); > - FOR_EACH_VEC_ELT (*jump_func->agg.items, j, item) > - { > - fprintf (f, " offset: " HOST_WIDE_INT_PRINT_DEC ", ", > - item->offset); > - fprintf (f, "type: "); > - print_generic_expr (f, item->type); > - fprintf (f, ", "); > - if (item->jftype == IPA_JF_PASS_THROUGH) > - fprintf (f, "PASS THROUGH: %d,", > - item->value.pass_through.formal_id); > - else if (item->jftype == IPA_JF_LOAD_AGG) > - { > - fprintf (f, "LOAD AGG: %d", > - item->value.pass_through.formal_id); > - fprintf (f, " [offset: " HOST_WIDE_INT_PRINT_DEC ", by %s],", > - item->value.load_agg.offset, > - item->value.load_agg.by_ref ? "reference" > - : "value"); > - } > - > - if (item->jftype == IPA_JF_PASS_THROUGH > - || item->jftype == IPA_JF_LOAD_AGG) > - { > - fprintf (f, " op %s", > - get_tree_code_name (item->value.pass_through.operation)); > - if (item->value.pass_through.operation != NOP_EXPR) > - { > - fprintf (f, " "); > - print_generic_expr (f, item->value.pass_through.operand); > - } > - } > - else if (item->jftype == IPA_JF_CONST) > - { > - fprintf (f, "CONST: "); > - ipa_print_constant_value (f, item->value.constant); > - } > - else if (item->jftype == IPA_JF_UNKNOWN) > - fprintf (f, "UNKNOWN: " HOST_WIDE_INT_PRINT_DEC " bits", > - tree_to_uhwi (TYPE_SIZE (item->type))); > - fprintf (f, "\n"); > - } > - } > - > + struct ipa_jump_func *jump_func = ipa_get_ith_jump_func (args, i); > class ipa_polymorphic_call_context *ctx > = ipa_get_ith_polymorhic_call_context (args, i); > - if (ctx && !ctx->useless_p ()) > - { > - fprintf (f, " Context: "); > - ctx->dump (dump_file); > - } > > - if (jump_func->m_vr) > - { > - jump_func->m_vr->dump (f); > - fprintf (f, "\n"); > - } > - else > - fprintf (f, " Unknown VR\n"); > + fprintf (f, " param %d: ", i); > + ipa_dump_jump_function (f, jump_func, ctx); > } > } > > diff --git a/gcc/ipa-prop.h b/gcc/ipa-prop.h > index 7a05c169c42..3215395286b 100644 > --- a/gcc/ipa-prop.h > +++ b/gcc/ipa-prop.h > @@ -1247,6 +1247,8 @@ void ipa_push_agg_values_from_jfunc (ipa_node_params *info, cgraph_node *node, > unsigned dst_index, > vec<ipa_argagg_value> *res); > void ipa_dump_param (FILE *, class ipa_node_params *info, int i); > +void ipa_dump_jump_function (FILE *f, ipa_jump_func *jfunc, > + class ipa_polymorphic_call_context *ctx = NULL); > void ipa_release_body_info (struct ipa_func_body_info *); > tree ipa_get_callee_param_type (struct cgraph_edge *e, int i); > bool ipcp_get_parm_bits (tree, tree *, widest_int *); > -- > 2.47.0 >
diff --git a/gcc/ipa-prop.cc b/gcc/ipa-prop.cc index 3b24bcbed15..3ff4753653b 100644 --- a/gcc/ipa-prop.cc +++ b/gcc/ipa-prop.cc @@ -429,6 +429,117 @@ ipa_print_constant_value (FILE *f, tree val) } } +/* Print contents of JFUNC to F. If CTX is non-NULL, dump it too. */ + +DEBUG_FUNCTION void +ipa_dump_jump_function (FILE *f, ipa_jump_func *jump_func, + class ipa_polymorphic_call_context *ctx) +{ + enum jump_func_type type = jump_func->type; + + if (type == IPA_JF_UNKNOWN) + fprintf (f, "UNKNOWN\n"); + else if (type == IPA_JF_CONST) + { + fprintf (f, "CONST: "); + ipa_print_constant_value (f, jump_func->value.constant.value); + fprintf (f, "\n"); + } + else if (type == IPA_JF_PASS_THROUGH) + { + fprintf (f, "PASS THROUGH: "); + fprintf (f, "%d, op %s", + jump_func->value.pass_through.formal_id, + get_tree_code_name(jump_func->value.pass_through.operation)); + if (jump_func->value.pass_through.operation != NOP_EXPR) + { + fprintf (f, " "); + print_generic_expr (f, jump_func->value.pass_through.operand); + } + if (jump_func->value.pass_through.agg_preserved) + fprintf (f, ", agg_preserved"); + if (jump_func->value.pass_through.refdesc_decremented) + fprintf (f, ", refdesc_decremented"); + fprintf (f, "\n"); + } + else if (type == IPA_JF_ANCESTOR) + { + fprintf (f, "ANCESTOR: "); + fprintf (f, "%d, offset " HOST_WIDE_INT_PRINT_DEC, + jump_func->value.ancestor.formal_id, + jump_func->value.ancestor.offset); + if (jump_func->value.ancestor.agg_preserved) + fprintf (f, ", agg_preserved"); + if (jump_func->value.ancestor.keep_null) + fprintf (f, ", keep_null"); + fprintf (f, "\n"); + } + + if (jump_func->agg.items) + { + struct ipa_agg_jf_item *item; + int j; + + fprintf (f, " Aggregate passed by %s:\n", + jump_func->agg.by_ref ? "reference" : "value"); + FOR_EACH_VEC_ELT (*jump_func->agg.items, j, item) + { + fprintf (f, " offset: " HOST_WIDE_INT_PRINT_DEC ", ", + item->offset); + fprintf (f, "type: "); + print_generic_expr (f, item->type); + fprintf (f, ", "); + if (item->jftype == IPA_JF_PASS_THROUGH) + fprintf (f, "PASS THROUGH: %d,", + item->value.pass_through.formal_id); + else if (item->jftype == IPA_JF_LOAD_AGG) + { + fprintf (f, "LOAD AGG: %d", + item->value.pass_through.formal_id); + fprintf (f, " [offset: " HOST_WIDE_INT_PRINT_DEC ", by %s],", + item->value.load_agg.offset, + item->value.load_agg.by_ref ? "reference" + : "value"); + } + + if (item->jftype == IPA_JF_PASS_THROUGH + || item->jftype == IPA_JF_LOAD_AGG) + { + fprintf (f, " op %s", + get_tree_code_name (item->value.pass_through.operation)); + if (item->value.pass_through.operation != NOP_EXPR) + { + fprintf (f, " "); + print_generic_expr (f, item->value.pass_through.operand); + } + } + else if (item->jftype == IPA_JF_CONST) + { + fprintf (f, "CONST: "); + ipa_print_constant_value (f, item->value.constant); + } + else if (item->jftype == IPA_JF_UNKNOWN) + fprintf (f, "UNKNOWN: " HOST_WIDE_INT_PRINT_DEC " bits", + tree_to_uhwi (TYPE_SIZE (item->type))); + fprintf (f, "\n"); + } + } + + if (ctx && !ctx->useless_p ()) + { + fprintf (f, " Context: "); + ctx->dump (dump_file); + } + + if (jump_func->m_vr) + { + jump_func->m_vr->dump (f); + fprintf (f, "\n"); + } + else + fprintf (f, " Unknown VR\n"); +} + /* Print the jump functions associated with call graph edge CS to file F. */ static void @@ -439,116 +550,12 @@ ipa_print_node_jump_functions_for_edge (FILE *f, struct cgraph_edge *cs) for (int i = 0; i < count; i++) { - struct ipa_jump_func *jump_func; - enum jump_func_type type; - - jump_func = ipa_get_ith_jump_func (args, i); - type = jump_func->type; - - fprintf (f, " param %d: ", i); - if (type == IPA_JF_UNKNOWN) - fprintf (f, "UNKNOWN\n"); - else if (type == IPA_JF_CONST) - { - fprintf (f, "CONST: "); - ipa_print_constant_value (f, jump_func->value.constant.value); - fprintf (f, "\n"); - } - else if (type == IPA_JF_PASS_THROUGH) - { - fprintf (f, "PASS THROUGH: "); - fprintf (f, "%d, op %s", - jump_func->value.pass_through.formal_id, - get_tree_code_name(jump_func->value.pass_through.operation)); - if (jump_func->value.pass_through.operation != NOP_EXPR) - { - fprintf (f, " "); - print_generic_expr (f, jump_func->value.pass_through.operand); - } - if (jump_func->value.pass_through.agg_preserved) - fprintf (f, ", agg_preserved"); - if (jump_func->value.pass_through.refdesc_decremented) - fprintf (f, ", refdesc_decremented"); - fprintf (f, "\n"); - } - else if (type == IPA_JF_ANCESTOR) - { - fprintf (f, "ANCESTOR: "); - fprintf (f, "%d, offset " HOST_WIDE_INT_PRINT_DEC, - jump_func->value.ancestor.formal_id, - jump_func->value.ancestor.offset); - if (jump_func->value.ancestor.agg_preserved) - fprintf (f, ", agg_preserved"); - if (jump_func->value.ancestor.keep_null) - fprintf (f, ", keep_null"); - fprintf (f, "\n"); - } - - if (jump_func->agg.items) - { - struct ipa_agg_jf_item *item; - int j; - - fprintf (f, " Aggregate passed by %s:\n", - jump_func->agg.by_ref ? "reference" : "value"); - FOR_EACH_VEC_ELT (*jump_func->agg.items, j, item) - { - fprintf (f, " offset: " HOST_WIDE_INT_PRINT_DEC ", ", - item->offset); - fprintf (f, "type: "); - print_generic_expr (f, item->type); - fprintf (f, ", "); - if (item->jftype == IPA_JF_PASS_THROUGH) - fprintf (f, "PASS THROUGH: %d,", - item->value.pass_through.formal_id); - else if (item->jftype == IPA_JF_LOAD_AGG) - { - fprintf (f, "LOAD AGG: %d", - item->value.pass_through.formal_id); - fprintf (f, " [offset: " HOST_WIDE_INT_PRINT_DEC ", by %s],", - item->value.load_agg.offset, - item->value.load_agg.by_ref ? "reference" - : "value"); - } - - if (item->jftype == IPA_JF_PASS_THROUGH - || item->jftype == IPA_JF_LOAD_AGG) - { - fprintf (f, " op %s", - get_tree_code_name (item->value.pass_through.operation)); - if (item->value.pass_through.operation != NOP_EXPR) - { - fprintf (f, " "); - print_generic_expr (f, item->value.pass_through.operand); - } - } - else if (item->jftype == IPA_JF_CONST) - { - fprintf (f, "CONST: "); - ipa_print_constant_value (f, item->value.constant); - } - else if (item->jftype == IPA_JF_UNKNOWN) - fprintf (f, "UNKNOWN: " HOST_WIDE_INT_PRINT_DEC " bits", - tree_to_uhwi (TYPE_SIZE (item->type))); - fprintf (f, "\n"); - } - } - + struct ipa_jump_func *jump_func = ipa_get_ith_jump_func (args, i); class ipa_polymorphic_call_context *ctx = ipa_get_ith_polymorhic_call_context (args, i); - if (ctx && !ctx->useless_p ()) - { - fprintf (f, " Context: "); - ctx->dump (dump_file); - } - if (jump_func->m_vr) - { - jump_func->m_vr->dump (f); - fprintf (f, "\n"); - } - else - fprintf (f, " Unknown VR\n"); + fprintf (f, " param %d: ", i); + ipa_dump_jump_function (f, jump_func, ctx); } } diff --git a/gcc/ipa-prop.h b/gcc/ipa-prop.h index 7a05c169c42..3215395286b 100644 --- a/gcc/ipa-prop.h +++ b/gcc/ipa-prop.h @@ -1247,6 +1247,8 @@ void ipa_push_agg_values_from_jfunc (ipa_node_params *info, cgraph_node *node, unsigned dst_index, vec<ipa_argagg_value> *res); void ipa_dump_param (FILE *, class ipa_node_params *info, int i); +void ipa_dump_jump_function (FILE *f, ipa_jump_func *jfunc, + class ipa_polymorphic_call_context *ctx = NULL); void ipa_release_body_info (struct ipa_func_body_info *); tree ipa_get_callee_param_type (struct cgraph_edge *e, int i); bool ipcp_get_parm_bits (tree, tree *, widest_int *);