https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67133
--- Comment #21 from Richard Biener <rguenth at gcc dot gnu.org> --- (In reply to Martin Jambor from comment #20) > The problem is that when inlining transformation sets fndecl of the > call statement, it does not set the fntype (of the statement). Then > infer_nonnull_range_by_attribute comes along, looks only at the fntype > and infers that the call has more attributes than it actually has. > > The following (untested) patch avoids the ICE. Even though this issue > suggests that the type of fndecl and fntype have to be in sync, I have > vague recollections that call statement's fntype was supposed to stick > to the original type in the source somehow (though IIRC it is > primarily used for indirect calls). In other words, I am not sure the > patch is 100% correct. Honza, Richi, what are your opinions? fntype is supposed to be the type specifying the "ABI", and yes it was designed mainly to preserve indirect call behavior when we propagate a (eventually "incompatible") fndecl to the call. Iff IPA redirects a call to sth very different (like unreachable () here) it doesn't make sense to preserve that detail. OTOH users like infer_nonnull_range_by_attribute cannot rely on gimple_call_fntype being "compatible" with the actual call (like in terms of number of arguments). So /* Now see if op appears in the nonnull list. */ for (tree t = TREE_VALUE (attrs); t; t = TREE_CHAIN (t)) { int idx = TREE_INT_CST_LOW (TREE_VALUE (t)) - 1; tree arg = gimple_call_arg (stmt, idx); lacks a check that idx < gimple_call_num_args. I don't think the non-null attribute is at fault here. > > diff --git a/gcc/cgraph.c b/gcc/cgraph.c > index 22a9852..5e5b308 100644 > --- a/gcc/cgraph.c > +++ b/gcc/cgraph.c > @@ -1461,6 +1461,7 @@ cgraph_edge::redirect_call_stmt_to_callee (void) > { > new_stmt = e->call_stmt; > gimple_call_set_fndecl (new_stmt, e->callee->decl); > + gimple_call_set_fntype (new_stmt, TREE_TYPE (e->callee->decl)); > update_stmt_fn (DECL_STRUCT_FUNCTION (e->caller->decl), new_stet); > }