From 1bb17c2144248180a1b00f5e5e6cf607fba0d46c Mon Sep 17 00:00:00 2001 From: Jan Hubicka Date: Wed, 22 Oct 2003 13:58:10 +0200 Subject: [PATCH] re PR debug/12389 ([testcase needed] ICE in gen_subprogram_die for nested function) PR debug/12389 * Makefile.in (dwarf2out.o): Depend on cgraph.h. * cgraph.c (cgraph_function_possibly_inlined_p): New function. * cgraph.h (cgraph_function_possibly_inlined_p): Declare. (cgraph_global_info): Add flag inlined * dwarf2out.c (gen_subprogram_die, gen_decl_die): Use cgraph_function_possibly_inded_p * cgraphunit.c (mark_inline): Set inlined flag. * toplev.c (rest_of_decl_compilation): Call outlining_inline_function only for possibly inlined functions. * c-decl.c (duplicate_decls): Never output abstract DIE representing old body of function. From-SVN: r72795 --- gcc/ChangeLog | 15 +++++++++++++++ gcc/Makefile.in | 2 +- gcc/c-decl.c | 5 ++++- gcc/cgraph.c | 10 ++++++++++ gcc/cgraph.h | 5 +++++ gcc/cgraphunit.c | 1 + gcc/dwarf2out.c | 22 ++++++++++++---------- gcc/toplev.c | 2 +- 8 files changed, 49 insertions(+), 13 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 32d620891f2..badc59ef865 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,18 @@ +2003-10-22 Jan Hubicka + + PR debug/12389 + * Makefile.in (dwarf2out.o): Depend on cgraph.h. + * cgraph.c (cgraph_function_possibly_inlined_p): New function. + * cgraph.h (cgraph_function_possibly_inlined_p): Declare. + (cgraph_global_info): Add flag inlined + * dwarf2out.c (gen_subprogram_die, gen_decl_die): Use + cgraph_function_possibly_inded_p + * cgraphunit.c (mark_inline): Set inlined flag. + * toplev.c (rest_of_decl_compilation): Call outlining_inline_function + only for possibly inlined functions. + * c-decl.c (duplicate_decls): Never output abstract DIE representing old + body of function. + 2003-10-22 Andrew Haley * varasm.c (output_constructor): Make constructor annotation diff --git a/gcc/Makefile.in b/gcc/Makefile.in index 4f28e80fd0d..0b89ddd7111 100644 --- a/gcc/Makefile.in +++ b/gcc/Makefile.in @@ -1586,7 +1586,7 @@ dwarf2out.o : dwarf2out.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) $(RTL_H) dwarf2.h debug.h flags.h insn-config.h reload.h output.h $(DIAGNOSTIC_H) real.h \ hard-reg-set.h $(REGS_H) $(EXPR_H) libfuncs.h toplev.h dwarf2out.h varray.h \ $(GGC_H) except.h dwarf2asm.h $(TM_P_H) langhooks.h $(HASHTAB_H) \ - gt-dwarf2out.h $(TARGET_H) + gt-dwarf2out.h $(TARGET_H) cgraph.h dwarf2asm.o : dwarf2asm.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) flags.h $(RTL_H) \ $(TREE_H) output.h dwarf2asm.h $(TM_P_H) $(GGC_H) gt-dwarf2asm.h vmsdbgout.o : vmsdbgout.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \ diff --git a/gcc/c-decl.c b/gcc/c-decl.c index 7880f7f271b..93ce347784d 100644 --- a/gcc/c-decl.c +++ b/gcc/c-decl.c @@ -1406,7 +1406,10 @@ duplicate_decls (tree newdecl, tree olddecl, int different_binding_level, been written out yet. */ if (new_is_definition && DECL_INITIAL (olddecl)) { - if (TREE_USED (olddecl)) + if (TREE_USED (olddecl) + /* In unit-at-a-time mode we never inline re-defined extern + inline functions. */ + && !flag_unit_at_a_time) (*debug_hooks->outlining_inline_function) (olddecl); /* The new defn must not be inline. */ diff --git a/gcc/cgraph.c b/gcc/cgraph.c index eedbd9efbef..b28d9f3a6c0 100644 --- a/gcc/cgraph.c +++ b/gcc/cgraph.c @@ -531,5 +531,15 @@ cgraph_varpool_assemble_pending_decls (void) return changed; } +/* Return true when the DECL can possibly be inlined. */ +bool +cgraph_function_possibly_inlined_p (tree decl) +{ + if (!flag_unit_at_a_time) + return (DECL_INLINE (decl) && !flag_no_inline); + if (!cgraph_global_info_ready) + abort (); + return cgraph_node (decl)->global.inlined; +} #include "gt-cgraph.h" diff --git a/gcc/cgraph.h b/gcc/cgraph.h index 9bdbfdc0cf7..a37227e95c9 100644 --- a/gcc/cgraph.h +++ b/gcc/cgraph.h @@ -59,6 +59,9 @@ struct cgraph_global_info GTY(()) Once we inline all calls to the function and the function is local, it is set to false. */ bool will_be_output; + + /* Set iff at least one of the caller edges has inline_call flag set. */ + bool inlined; }; /* Information about the function that is propagated by the RTL backend. @@ -168,6 +171,8 @@ void cgraph_varpool_mark_needed_node (struct cgraph_varpool_node *); void cgraph_varpool_finalize_decl (tree); bool cgraph_varpool_assemble_pending_decls (void); +bool cgraph_function_possibly_inlined_p (tree); + /* In cgraphunit.c */ bool cgraph_assemble_pending_functions (void); void cgraph_finalize_function (tree, bool); diff --git a/gcc/cgraphunit.c b/gcc/cgraphunit.c index c20367d1d00..673419fa008 100644 --- a/gcc/cgraphunit.c +++ b/gcc/cgraphunit.c @@ -833,6 +833,7 @@ cgraph_mark_inline (struct cgraph_node *to, struct cgraph_node *what, bool called = false; int new_insns; + what->global.inlined = 1; for (e = what->callers; e; e = e->next_caller) { if (e->caller == to) diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index 2642e81ceae..32b93323716 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -64,6 +64,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA #include "target.h" #include "langhooks.h" #include "hashtab.h" +#include "cgraph.h" #ifdef DWARF2_DEBUGGING_INFO static void dwarf2out_source_line (unsigned int, const char *); @@ -10685,20 +10686,20 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) } else if (DECL_ABSTRACT (decl)) { - if (DECL_INLINE (decl) && !flag_no_inline) + if (DECL_DECLARED_INLINE_P (decl)) { - /* ??? Checking DECL_DEFER_OUTPUT is correct for static - inline functions, but not for extern inline functions. - We can't get this completely correct because information - about whether the function was declared inline is not - saved anywhere. */ - if (DECL_DEFER_OUTPUT (decl)) + if (cgraph_function_possibly_inlined_p (decl)) add_AT_unsigned (subr_die, DW_AT_inline, DW_INL_declared_inlined); else - add_AT_unsigned (subr_die, DW_AT_inline, DW_INL_inlined); + add_AT_unsigned (subr_die, DW_AT_inline, DW_INL_declared_not_inlined); } else - add_AT_unsigned (subr_die, DW_AT_inline, DW_INL_declared_not_inlined); + { + if (cgraph_function_possibly_inlined_p (decl)) + add_AT_unsigned (subr_die, DW_AT_inline, DW_INL_inlined); + else + abort (); + } equate_decl_number_to_die (decl, subr_die); } @@ -11800,7 +11801,8 @@ gen_decl_die (tree decl, dw_die_ref context_die) /* If we're emitting an out-of-line copy of an inline function, emit info for the abstract instance and set up to refer to it. */ - else if (DECL_INLINE (decl) && ! DECL_ABSTRACT (decl) + else if (cgraph_function_possibly_inlined_p (decl) + && ! DECL_ABSTRACT (decl) && ! class_scope_p (context_die) /* dwarf2out_abstract_function won't emit a die if this is just a declaration. We must avoid setting DECL_ABSTRACT_ORIGIN in diff --git a/gcc/toplev.c b/gcc/toplev.c index a393c52003e..219c69931a5 100644 --- a/gcc/toplev.c +++ b/gcc/toplev.c @@ -3177,7 +3177,7 @@ rest_of_compilation (tree decl) /* We are now committed to emitting code for this function. Do any preparation, such as emitting abstract debug info for the inline before it gets mangled by optimization. */ - if (DECL_INLINE (decl)) + if (cgraph_function_possibly_inlined_p (decl)) (*debug_hooks->outlining_inline_function) (decl); /* Remove any notes we don't need. That will make iterating -- 2.30.2