http://gcc.gnu.org/bugzilla/show_bug.cgi?id=46823
--- Comment #16 from Martin Jambor <jamborm at gcc dot gnu.org> 2011-01-10 20:34:14 UTC --- The problem seems to be a different one. During IPA decision making we decide to clone a function and the call graph node of the original one is then removed as unreachable an unnecessary. However, its declaration stays in the IL until the transformation phase where expand_call_inline calls cgraph_node() on it which creates a new, seemingly entirely separate call graph node. This is then what the verifier gets for the decl, cannot find any relation between what the edge points to and the new node and errors out. We cannot simply replace the call to cgraph_node with cgraph_get_node and bail out if it returns NULL because the call is supposed to be inlined and this is then asserted later. The information about the call just happens to be stored in the call graph edge and the fndecl in the gimple statement is not necessarily relevant at all. So the fix which I am testing at the moment just extracts the target declaration from the call graph, bypassing whatever is in the statement. I will submit this patch tomorrow if it passes bootstrap and testing. 2011-01-10 Martin Jambor <mjam...@suse.cz> PR middle-end/46823 * tree-inline.c (expand_call_inline): Get fndecl from call graph edge. Index: icln/gcc/tree-inline.c =================================================================== --- icln.orig/gcc/tree-inline.c +++ icln/gcc/tree-inline.c @@ -3783,14 +3783,19 @@ expand_call_inline (basic_block bb, gimp if (gimple_code (stmt) != GIMPLE_CALL) goto egress; + /* Objective C and fortran still calls tree_rest_of_compilation directly. + Kill this check once this is fixed. */ + if (!id->dst_node->analyzed) + goto egress; + + cg_edge = cgraph_edge (id->dst_node, stmt); + gcc_checking_assert (cg_edge); /* First, see if we can figure out what function is being called. If we cannot, then there is no hope of inlining the function. */ - fn = gimple_call_fndecl (stmt); - if (!fn) + if (cg_edge->indirect_unknown_callee) goto egress; - - /* Turn forward declarations into real ones. */ - fn = cgraph_node (fn)->decl; + fn = cg_edge->callee->decl; + gcc_checking_assert (fn); /* If FN is a declaration of a function in a nested scope that was globally declared inline, we don't set its DECL_INITIAL. @@ -3804,13 +3809,6 @@ expand_call_inline (basic_block bb, gimp && gimple_has_body_p (DECL_ABSTRACT_ORIGIN (fn))) fn = DECL_ABSTRACT_ORIGIN (fn); - /* Objective C and fortran still calls tree_rest_of_compilation directly. - Kill this check once this is fixed. */ - if (!id->dst_node->analyzed) - goto egress; - - cg_edge = cgraph_edge (id->dst_node, stmt); - /* First check that inlining isn't simply forbidden in this case. */ if (inline_forbidden_into_p (cg_edge->caller->decl, cg_edge->callee->decl)) goto egress;