On Wed, 7 Jun 2017, Richard Biener wrote: > On Fri, 19 May 2017, Richard Biener wrote: > > > > > This is a repost of the main part of the early LTO debug support. > > The only changes relative to the last post is in the dwarf2out.c > > pieces due to Jasons review and Jakubs introduction of > > DW_OP_GNU_variable_value. > > > > I've also adjusted testcases for fallout (the asan backtraces do > > give files / line numbers because libbacktrace doesn't understand > > the DWARF) plus added a -flto run over the libstdc++ pretty printer > > testsuite -- after all the goal was to make those work with LTO, > > and they now nicely do. > > > > [LTO-]bootstrapped and tested on x86_64-unknown-linux-gnu. > > > > I've also tested with -flto -g and compared to before the patch and > > the outcome doesn't contain any surprises. > > > > I've also ran the gdb testsuite with no differences (but I guess > > it doesn't exercise LTO). > > > > I've also built SPEC 2k6 with -flto -g. > > > > I've also debugged optimized LTO bootstrapped cc1 a bit - not that > > debugging (LTO) optimized cc1 is a pleasant experience, but at least > > gdb doesn't crash. > > > > Ok for trunk? > > Ping.
Ping^2. > > Both darwin and mingw maintainers were not concerned about LTO with -g > > being broken for them. > > > > This patch allows us to go forward with freeing more stuff after > > the frontend finished, in particular remove LTO streaming of a lot > > of type information that is referenced from trees (and, as a first > > step, enable free-lang-data for non-LTO compiles). > > > > Thanks, > > Richard. > > > > 2017-05-19 Richard Biener <rguent...@suse.de> > > > > * debug.h (struct gcc_debug_hooks): Add die_ref_for_decl and > > register_external_die hooks. > > (debug_false_tree_charstarstar_uhwistar): Declare. > > (debug_nothing_tree_charstar_uhwi): Likewise. > > * debug.c (do_nothing_debug_hooks): Adjust. > > (debug_false_tree_charstarstar_uhwistar): New do nothing. > > (debug_nothing_tree_charstar_uhwi): Likewise. > > * dbxout.c (dbx_debug_hooks): Adjust. > > (xcoff_debug_hooks): Likewise. > > * sdbout.c (sdb_debug_hooks): Likewise. > > * vmsdbgout.c (vmsdbg_debug_hooks): Likewise. > > > > * dwarf2out.c (macinfo_label_base): New global. > > (dwarf2out_register_external_die): New function for the > > register_external_die hook. > > (dwarf2out_die_ref_for_decl): Likewise for die_ref_for_decl. > > (dwarf2_debug_hooks): Use them. > > (dwarf2_lineno_debug_hooks): Adjust. > > (struct die_struct): Add with_offset flag. > > (DEBUG_LTO_DWO_INFO_SECTION, DEBUG_LTO_INFO_SECTION, > > DEBUG_LTO_DWO_ABBREV_SECTION, DEBUG_LTO_ABBREV_SECTION, > > DEBUG_LTO_DWO_MACINFO_SECTION, DEBUG_LTO_MACINFO_SECTION, > > DEBUG_LTO_DWO_MACRO_SECTION, DEBUG_LTO_MACRO_SECTION, > > DEBUG_LTO_LINE_SECTION, DEBUG_LTO_DWO_STR_OFFSETS_SECTION, > > DEBUG_LTO_STR_DWO_SECTION, DEBUG_STR_LTO_SECTION): New macros > > defining section names for the early LTO debug variants. > > (reset_indirect_string): New helper. > > (add_AT_external_die_ref): Helper for > > dwarf2out_register_external_die. > > (print_dw_val): Add support for offsetted symbol references. > > (compute_section_prefix_1): Split out worker to distinguish > > the comdat from the LTO case. > > (compute_section_prefix): Wrap old comdat case here. > > (output_die): Skip DIE symbol output for the LTO added one. > > Handle DIE symbol references with offset. > > (output_comp_unit): Guard section name mangling properly. > > For LTO debug sections emit a symbol at the section beginning > > which we use to refer to its DIEs. > > (add_abstract_origin_attribute): For DIEs registered via > > dwarf2out_register_external_die directly refer to the early > > DIE rather than indirectly through the shadow one we created. > > (gen_array_type_die): When generating early LTO debug do > > not emit DW_AT_string_length. > > (gen_formal_parameter_die): Do not re-create DIEs for PARM_DECLs > > late when in LTO. > > (gen_subprogram_die): Adjust the check for whether we face > > a concrete instance DIE for an inline we can reuse for the > > late LTO case. Likewise avoid another specification DIE > > for early built declarations/definitions for the late LTO case. > > (gen_variable_die): Add type references for late duplicated VLA dies > > when in late LTO. > > (gen_inlined_subroutine_die): Do not call > > dwarf2out_abstract_function, > > we have the abstract instance already. > > (process_scope_var): Adjust decl DIE contexts in LTO which > > first puts them in limbo. > > (gen_decl_die): Do not generate type DIEs late apart from > > types for VLAs or for decls we do not yet have a DIE. > > (dwarf2out_early_global_decl): Make sure to create DIEs > > for abstract instances of a decl first. > > (dwarf2out_late_global_decl): Adjust comment. > > (output_macinfo_op): With multiple macro sections use > > macinfo_label_base to distinguish labels. > > (output_macinfo): Likewise. Update macinfo_label_base. > > Pass in the line info label. > > (note_variable_value_in_expr): When generating LTO resolve > > all variable values here by generating DIEs as needed. > > (init_sections_and_labels): Add early LTO debug flag parameter > > and generate different sections and names if set. Add generation > > counter for the labels so we can have multiple of them. > > (reset_dies): Helper to allow DIEs to be output multiple times. > > (dwarf2out_finish): When outputting DIEs to the fat part of an > > LTO object first reset DIEs. > > (dwarf2out_early_finish): Output early DIEs when generating LTO. > > > > Cleanups we can do (and need) when removing the "old" LTO path and add > > the early LTO path. > > > > (set_decl_abstract_flags): Remove. > > (set_block_abstract_flags): Likewise. > > (dwarf2out_abstract_function): Treat the early generated DIEs > > as the abstract copy and only add DW_AT_inline and > > DW_AT_artificial here. > > > > * tree.c (free_lang_data): Build a dummy TRANSLATION_UNIT_DECL > > if we have none yet (Go fails to build one, PR78628). > > * lto-streamer-in.c: Include debug.h. > > (dref_queue): New global. > > (lto_read_tree_1): Stream in DIE references. > > (lto_input_tree): Register DIE references. > > (input_function): Stream DECL_DEBUG_ARGS. > > * lto-streamer-out.c: Include debug.h. > > (lto_write_tree_1): Output DIE references. > > (DFS::DFS_write_tree_body): Follow DECL_ABSTRACT_ORIGIN. > > Force a TRANSLATION_UNIT_DECL DECL_CONTEXT for file-scope decls. > > (output_function): Stream DECL_DEBUG_ARGS. > > * tree-streamer-in.c (lto_input_ts_decl_common_tree_pointers): > > Stream DECL_ABSTRACT_ORIGIN. > > * tree-streamer-out.c (write_ts_decl_common_tree_pointers): > > Likewise. > > (write_ts_decl_minimal_tree_pointers): Force a TRANSLATION_UNIT_DECL > > DECL_CONTEXT for file-scope decls. > > * lto-streamer.h (struct dref_entry): Declare. > > (dref_queue): Likewise. > > > > * lto-wrapper.c (debug_obj): New global. > > (tool_cleanup): Unlink it if required. > > (debug_objcopy): New function. > > (run_gcc): Handle early debug sections in the IL files by > > extracting them to separate files, partially linkin them and > > feeding the result back as result to the linker. > > > > * config/darwin.h (DEBUG_LTO_INFO_SECTION, DEBUG_LTO_ABBREV_SECTION, > > DEBUG_LTO_MACINFO_SECTION, DEBUG_LTO_LINE_SECTION, > > DEBUG_STR_LTO_SECTION, DEBUG_LTO_MACRO_SECTION): Put early debug > > sections into a separate segment. > > * config/darwin.c (darwin_asm_named_section): Handle __GNU_DWARF_LTO > > segments. > > (darwin_asm_dwarf_section): Likewise. > > (darwin_asm_output_dwarf_offset): Likewise. > > > > * config/i386/i386.c (make_resolver_func): Set DECL_IGNORED_P. > > > > lto/ > > * lto.c (unify_scc): Truncate DIE reference queue for dropped SCCs. > > (lto_read_decls): Process TRANSLATION_UNIT_DECLs. Remove > > TYPE_DECL debug processing, register DIE references from > > prevailing SCCs with the debug machinery. > > (lto_section_with_id): Handle LTO debug sections. > > > > libstdc++/ > > * testsuite/libstdc++-prettyprinters/prettyprinters.exp: Run all > > tests with -flto as well if supported. > > > > * c-c++-common/asan/global-overflow-1.c: Adjust diagnostic location > > regex to handle the LTO case. > > * c-c++-common/asan/heap-overflow-1.c: Likewise. > > * c-c++-common/asan/misalign-1.c: Likewise. > > * c-c++-common/asan/misalign-2.c: Likewise. > > * c-c++-common/asan/null-deref-1.c: Likewise. > > * c-c++-common/asan/stack-overflow-1.c: Likewise. > > * c-c++-common/asan/strncpy-overflow-1.c: Likewise. > > * c-c++-common/asan/use-after-free-1.c: Likewise. > > * g++.dg/asan/large-func-test-1.C: Likewise. > > * gfortran.dg/save_6.f90: Add -flto -g variant of save_5.f90. > > > > Index: early-lto-debug/gcc/dwarf2out.c > > =================================================================== > > *** early-lto-debug.orig/gcc/dwarf2out.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/dwarf2out.c 2017-05-19 12:29:43.933873285 +0200 > > *************** static GTY(()) section *debug_aranges_se > > *** 162,167 **** > > --- 162,168 ---- > > static GTY(()) section *debug_addr_section; > > static GTY(()) section *debug_macinfo_section; > > static const char *debug_macinfo_section_name; > > + static unsigned macinfo_label_base = 1; > > static GTY(()) section *debug_line_section; > > static GTY(()) section *debug_skeleton_line_section; > > static GTY(()) section *debug_loc_section; > > *************** static void dwarf2out_begin_function (tr > > *** 2686,2691 **** > > --- 2687,2696 ---- > > static void dwarf2out_end_function (unsigned int); > > static void dwarf2out_register_main_translation_unit (tree unit); > > static void dwarf2out_set_name (tree, tree); > > + static void dwarf2out_register_external_die (tree decl, const char *sym, > > + unsigned HOST_WIDE_INT off); > > + static bool dwarf2out_die_ref_for_decl (tree decl, const char **sym, > > + unsigned HOST_WIDE_INT *off); > > > > /* The debug hooks structure. */ > > > > *************** const struct gcc_debug_hooks dwarf2_debu > > *** 2720,2725 **** > > --- 2725,2732 ---- > > dwarf2out_late_global_decl, > > dwarf2out_type_decl, /* type_decl */ > > dwarf2out_imported_module_or_decl, > > + dwarf2out_die_ref_for_decl, > > + dwarf2out_register_external_die, > > debug_nothing_tree, /* deferred_inline_function */ > > /* The DWARF 2 backend tries to reduce debugging bloat by not > > emitting the abstract description of inline functions until > > *************** const struct gcc_debug_hooks dwarf2_line > > *** 2761,2766 **** > > --- 2768,2775 ---- > > debug_nothing_tree, /* late_global_decl */ > > debug_nothing_tree_int, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > debug_nothing_tree, /* outlining_inline_function */ > > debug_nothing_rtx_code_label, /* label */ > > *************** typedef struct GTY((chain_circular ("%h. > > *** 2889,2894 **** > > --- 2898,2906 ---- > > /* Die is used and must not be pruned as unused. */ > > BOOL_BITFIELD die_perennial_p : 1; > > BOOL_BITFIELD comdat_type_p : 1; /* DIE has a type signature */ > > + /* For an external ref to die_symbol if die_offset contains an extra > > + offset to that symbol. */ > > + BOOL_BITFIELD with_offset : 1; > > /* Whether this DIE was removed from the DIE tree, for example via > > prune_unused_types. We don't consider those present from the > > DIE lookup routines. */ > > *************** new_addr_loc_descr (rtx addr, enum dtpre > > *** 3692,3703 **** > > --- 3704,3727 ---- > > #ifndef DEBUG_DWO_INFO_SECTION > > #define DEBUG_DWO_INFO_SECTION ".debug_info.dwo" > > #endif > > + #ifndef DEBUG_LTO_DWO_INFO_SECTION > > + #define DEBUG_LTO_DWO_INFO_SECTION ".gnu.debuglto_.debug_info.dwo" > > + #endif > > + #ifndef DEBUG_LTO_INFO_SECTION > > + #define DEBUG_LTO_INFO_SECTION ".gnu.debuglto_.debug_info" > > + #endif > > #ifndef DEBUG_ABBREV_SECTION > > #define DEBUG_ABBREV_SECTION ".debug_abbrev" > > #endif > > #ifndef DEBUG_DWO_ABBREV_SECTION > > #define DEBUG_DWO_ABBREV_SECTION ".debug_abbrev.dwo" > > #endif > > + #ifndef DEBUG_LTO_DWO_ABBREV_SECTION > > + #define DEBUG_LTO_DWO_ABBREV_SECTION ".gnu.debuglto_.debug_abbrev.dwo" > > + #endif > > + #ifndef DEBUG_LTO_ABBREV_SECTION > > + #define DEBUG_LTO_ABBREV_SECTION ".gnu.debuglto_.debug_abbrev" > > + #endif > > #ifndef DEBUG_ARANGES_SECTION > > #define DEBUG_ARANGES_SECTION ".debug_aranges" > > #endif > > *************** new_addr_loc_descr (rtx addr, enum dtpre > > *** 3710,3727 **** > > --- 3734,3766 ---- > > #ifndef DEBUG_DWO_MACINFO_SECTION > > #define DEBUG_DWO_MACINFO_SECTION ".debug_macinfo.dwo" > > #endif > > + #ifndef DEBUG_LTO_DWO_MACINFO_SECTION > > + #define DEBUG_LTO_DWO_MACINFO_SECTION ".gnu.debuglto_.debug_macinfo.dwo" > > + #endif > > + #ifndef DEBUG_LTO_MACINFO_SECTION > > + #define DEBUG_LTO_MACINFO_SECTION ".gnu.debuglto_.debug_macinfo" > > + #endif > > #ifndef DEBUG_DWO_MACRO_SECTION > > #define DEBUG_DWO_MACRO_SECTION ".debug_macro.dwo" > > #endif > > #ifndef DEBUG_MACRO_SECTION > > #define DEBUG_MACRO_SECTION ".debug_macro" > > #endif > > + #ifndef DEBUG_LTO_DWO_MACRO_SECTION > > + #define DEBUG_LTO_DWO_MACRO_SECTION ".gnu.debuglto_.debug_macro.dwo" > > + #endif > > + #ifndef DEBUG_LTO_MACRO_SECTION > > + #define DEBUG_LTO_MACRO_SECTION ".gnu.debuglto_.debug_macro" > > + #endif > > #ifndef DEBUG_LINE_SECTION > > #define DEBUG_LINE_SECTION ".debug_line" > > #endif > > #ifndef DEBUG_DWO_LINE_SECTION > > #define DEBUG_DWO_LINE_SECTION ".debug_line.dwo" > > #endif > > + #ifndef DEBUG_LTO_LINE_SECTION > > + #define DEBUG_LTO_LINE_SECTION ".gnu.debuglto_.debug_line.dwo" > > + #endif > > #ifndef DEBUG_LOC_SECTION > > #define DEBUG_LOC_SECTION ".debug_loc" > > #endif > > *************** new_addr_loc_descr (rtx addr, enum dtpre > > *** 3750,3761 **** > > --- 3789,3809 ---- > > #ifndef DEBUG_DWO_STR_OFFSETS_SECTION > > #define DEBUG_DWO_STR_OFFSETS_SECTION ".debug_str_offsets.dwo" > > #endif > > + #ifndef DEBUG_LTO_DWO_STR_OFFSETS_SECTION > > + #define DEBUG_LTO_DWO_STR_OFFSETS_SECTION > > ".gnu.debuglto_.debug_str_offsets.dwo" > > + #endif > > #ifndef DEBUG_STR_DWO_SECTION > > #define DEBUG_STR_DWO_SECTION ".debug_str.dwo" > > #endif > > + #ifndef DEBUG_LTO_STR_DWO_SECTION > > + #define DEBUG_LTO_STR_DWO_SECTION ".gnu.debuglto_.debug_str.dwo" > > + #endif > > #ifndef DEBUG_STR_SECTION > > #define DEBUG_STR_SECTION ".debug_str" > > #endif > > + #ifndef DEBUG_LTO_STR_SECTION > > + #define DEBUG_LTO_STR_SECTION ".gnu.debuglto_.debug_str" > > + #endif > > #ifndef DEBUG_RANGES_SECTION > > #define DEBUG_RANGES_SECTION ".debug_ranges" > > #endif > > *************** new_addr_loc_descr (rtx addr, enum dtpre > > *** 3780,3785 **** > > --- 3828,3837 ---- > > /* Section flags for .debug_str.dwo section. */ > > #define DEBUG_STR_DWO_SECTION_FLAGS (SECTION_DEBUG | SECTION_EXCLUDE) > > > > + /* Attribute used to refer to the macro section. */ > > + #define DEBUG_MACRO_ATTRIBUTE (dwarf_version >= 5 ? DW_AT_macros \ > > + : dwarf_strict ? DW_AT_macro_info : DW_AT_GNU_macros) > > + > > /* Labels we insert at beginning sections we can reference instead of > > the section names themselves. */ > > > > *************** set_indirect_string (struct indirect_str > > *** 4368,4373 **** > > --- 4420,4443 ---- > > } > > } > > > > + /* A helper function for dwarf2out_finish, called to reset indirect > > + string decisions done for early LTO dwarf output before fat object > > + dwarf output. */ > > + > > + int > > + reset_indirect_string (indirect_string_node **h, void *) > > + { > > + struct indirect_string_node *node = *h; > > + if (node->form == DW_FORM_strp || node->form == DW_FORM_GNU_str_index) > > + { > > + free (node->label); > > + node->label = NULL; > > + node->form = (dwarf_form) 0; > > + node->index = 0; > > + } > > + return 1; > > + } > > + > > /* Find out whether a string should be output inline in DIE > > or out-of-line in .debug_str section. */ > > > > *************** lookup_decl_die (tree decl) > > *** 5413,5418 **** > > --- 5483,5668 ---- > > return *die; > > } > > > > + > > + /* For DECL which might have early dwarf output query a SYMBOL + OFFSET > > + style reference. Return true if we found one refering to a DIE for > > + DECL, otherwise return false. */ > > + > > + static bool > > + dwarf2out_die_ref_for_decl (tree decl, const char **sym, > > + unsigned HOST_WIDE_INT *off) > > + { > > + dw_die_ref die; > > + > > + if (flag_wpa && !decl_die_table) > > + return false; > > + > > + if (TREE_CODE (decl) == BLOCK) > > + die = BLOCK_DIE (decl); > > + else > > + die = lookup_decl_die (decl); > > + if (!die) > > + return false; > > + > > + /* During WPA stage we currently use DIEs to store the > > + decl <-> label + offset map. That's quite inefficient but it > > + works for now. */ > > + if (flag_wpa) > > + { > > + dw_die_ref ref = get_AT_ref (die, DW_AT_abstract_origin); > > + if (!ref) > > + { > > + gcc_assert (die == comp_unit_die ()); > > + return false; > > + } > > + *off = ref->die_offset; > > + *sym = ref->die_id.die_symbol; > > + return true; > > + } > > + > > + /* Similar to get_ref_die_offset_label, but using the "correct" > > + label. */ > > + *off = die->die_offset; > > + while (die->die_parent) > > + die = die->die_parent; > > + /* For the containing CU DIE we compute a die_symbol in > > + compute_section_prefix. */ > > + gcc_assert (die->die_tag == DW_TAG_compile_unit > > + && die->die_id.die_symbol != NULL); > > + *sym = die->die_id.die_symbol; > > + return true; > > + } > > + > > + /* Add a reference of kind ATTR_KIND to a DIE at SYMBOL + OFFSET to DIE. > > */ > > + > > + static void > > + add_AT_external_die_ref (dw_die_ref die, enum dwarf_attribute attr_kind, > > + const char *symbol, HOST_WIDE_INT offset) > > + { > > + /* Create a fake DIE that contains the reference. Don't use > > + new_die because we don't want to end up in the limbo list. */ > > + dw_die_ref ref = ggc_cleared_alloc<die_node> (); > > + ref->die_tag = die->die_tag; > > + ref->die_id.die_symbol = IDENTIFIER_POINTER (get_identifier (symbol)); > > + ref->die_offset = offset; > > + ref->with_offset = 1; > > + add_AT_die_ref (die, attr_kind, ref); > > + } > > + > > + /* Create a DIE for DECL if required and add a reference to a DIE > > + at SYMBOL + OFFSET which contains attributes dumped early. */ > > + > > + static void > > + dwarf2out_register_external_die (tree decl, const char *sym, > > + unsigned HOST_WIDE_INT off) > > + { > > + if (debug_info_level == DINFO_LEVEL_NONE) > > + return; > > + > > + if (flag_wpa && !decl_die_table) > > + decl_die_table = hash_table<decl_die_hasher>::create_ggc (1000); > > + > > + dw_die_ref die > > + = TREE_CODE (decl) == BLOCK ? BLOCK_DIE (decl) : lookup_decl_die > > (decl); > > + gcc_assert (!die); > > + > > + tree ctx; > > + dw_die_ref parent = NULL; > > + /* Need to lookup a DIE for the decls context - the containing > > + function or translation unit. */ > > + if (TREE_CODE (decl) == BLOCK) > > + { > > + ctx = BLOCK_SUPERCONTEXT (decl); > > + /* ??? We do not output DIEs for all scopes thus skip as > > + many DIEs as needed. */ > > + while (TREE_CODE (ctx) == BLOCK > > + && !BLOCK_DIE (ctx)) > > + ctx = BLOCK_SUPERCONTEXT (ctx); > > + } > > + else > > + ctx = DECL_CONTEXT (decl); > > + while (ctx && TYPE_P (ctx)) > > + ctx = TYPE_CONTEXT (ctx); > > + if (ctx) > > + { > > + if (TREE_CODE (ctx) == BLOCK) > > + parent = BLOCK_DIE (ctx); > > + else if (TREE_CODE (ctx) == TRANSLATION_UNIT_DECL > > + /* Keep the 1:1 association during WPA. */ > > + && !flag_wpa) > > + /* Otherwise all late annotations go to the main CU which > > + imports the original CUs. */ > > + parent = comp_unit_die (); > > + else if (TREE_CODE (ctx) == FUNCTION_DECL > > + && TREE_CODE (decl) != PARM_DECL > > + && TREE_CODE (decl) != BLOCK) > > + /* Leave function local entities parent determination to when > > + we process scope vars. */ > > + ; > > + else > > + parent = lookup_decl_die (ctx); > > + } > > + else > > + /* ??? In some cases the C++ FE (at least) fails to > > + set DECL_CONTEXT properly. Simply globalize stuff > > + in this case. For example > > + __dso_handle created via iostream line 74 col 25. */ > > + parent = comp_unit_die (); > > + /* Create a DIE "stub". */ > > + switch (TREE_CODE (decl)) > > + { > > + case TRANSLATION_UNIT_DECL: > > + if (! flag_wpa) > > + { > > + die = comp_unit_die (); > > + dw_die_ref import = new_die (DW_TAG_imported_unit, die, NULL_TREE); > > + add_AT_external_die_ref (import, DW_AT_import, sym, off); > > + /* We re-target all CU decls to the LTRANS CU DIE, so no need > > + to create a DIE for the original CUs. */ > > + return; > > + } > > + /* Keep the 1:1 association during WPA. */ > > + die = new_die (DW_TAG_compile_unit, NULL, decl); > > + break; > > + case NAMESPACE_DECL: > > + /* ??? LANG issue - DW_TAG_module for fortran. Either look > > + at the input language (if we have enough DECL_CONTEXT to follow) > > + or use a bit in tree_decl_with_vis to record the distinction. */ > > + die = new_die (DW_TAG_namespace, parent, decl); > > + break; > > + case FUNCTION_DECL: > > + die = new_die (DW_TAG_subprogram, parent, decl); > > + break; > > + case VAR_DECL: > > + die = new_die (DW_TAG_variable, parent, decl); > > + break; > > + case RESULT_DECL: > > + die = new_die (DW_TAG_variable, parent, decl); > > + break; > > + case PARM_DECL: > > + die = new_die (DW_TAG_formal_parameter, parent, decl); > > + break; > > + case CONST_DECL: > > + die = new_die (DW_TAG_constant, parent, decl); > > + break; > > + case LABEL_DECL: > > + die = new_die (DW_TAG_label, parent, decl); > > + break; > > + case BLOCK: > > + die = new_die (DW_TAG_lexical_block, parent, decl); > > + break; > > + default: > > + gcc_unreachable (); > > + } > > + if (TREE_CODE (decl) == BLOCK) > > + BLOCK_DIE (decl) = die; > > + else > > + equate_decl_number_to_die (decl, die); > > + > > + /* Add a reference to the DIE providing early debug at $sym + off. */ > > + add_AT_external_die_ref (die, DW_AT_abstract_origin, sym, off); > > + } > > + > > /* Returns a hash value for X (which really is a var_loc_list). */ > > > > inline hashval_t > > *************** print_dw_val (dw_val_node *val, bool rec > > *** 5900,5906 **** > > die->die_id.die_type_node->signature); > > } > > else if (die->die_id.die_symbol) > > ! fprintf (outfile, "die -> label: %s", die->die_id.die_symbol); > > else > > fprintf (outfile, "die -> %ld", die->die_offset); > > fprintf (outfile, " (%p)", (void *) die); > > --- 6150,6160 ---- > > die->die_id.die_type_node->signature); > > } > > else if (die->die_id.die_symbol) > > ! { > > ! fprintf (outfile, "die -> label: %s", die->die_id.die_symbol); > > ! if (die->with_offset) > > ! fprintf (outfile, " + %ld", die->die_offset); > > ! } > > else > > fprintf (outfile, "die -> %ld", die->die_offset); > > fprintf (outfile, " (%p)", (void *) die); > > *************** static unsigned int comdat_symbol_number > > *** 7216,7222 **** > > children, and set comdat_symbol_id accordingly. */ > > > > static void > > ! compute_section_prefix (dw_die_ref unit_die) > > { > > const char *die_name = get_AT_string (unit_die, DW_AT_name); > > const char *base = die_name ? lbasename (die_name) : "anonymous"; > > --- 7470,7476 ---- > > children, and set comdat_symbol_id accordingly. */ > > > > static void > > ! compute_section_prefix_1 (dw_die_ref unit_die, bool comdat_p) > > { > > const char *die_name = get_AT_string (unit_die, DW_AT_name); > > const char *base = die_name ? lbasename (die_name) : "anonymous"; > > *************** compute_section_prefix (dw_die_ref unit_ > > *** 7235,7241 **** > > unmark_all_dies (unit_die); > > md5_finish_ctx (&ctx, checksum); > > > > ! sprintf (name, "%s.", base); > > clean_symbol_name (name); > > > > p = name + strlen (name); > > --- 7489,7499 ---- > > unmark_all_dies (unit_die); > > md5_finish_ctx (&ctx, checksum); > > > > ! /* When we this for comp_unit_die () we have a DW_AT_name that might > > ! not start with a letter but with anything valid for filenames and > > ! clean_symbol_name doesn't fix that up. Prepend 'g' if the first > > ! character is not a letter. */ > > ! sprintf (name, "%s%s.", ISALPHA (*base) ? "" : "g", base); > > clean_symbol_name (name); > > > > p = name + strlen (name); > > *************** compute_section_prefix (dw_die_ref unit_ > > *** 7245,7251 **** > > p += 2; > > } > > > > ! comdat_symbol_id = unit_die->die_id.die_symbol = xstrdup (name); > > comdat_symbol_number = 0; > > } > > > > --- 7503,7517 ---- > > p += 2; > > } > > > > ! unit_die->die_id.die_symbol = xstrdup (name); > > ! unit_die->comdat_type_p = comdat_p; > > ! } > > ! > > ! static void > > ! compute_section_prefix (dw_die_ref unit_die) > > ! { > > ! compute_section_prefix_1 (unit_die, true); > > ! comdat_symbol_id = unit_die->die_id.die_symbol; > > comdat_symbol_number = 0; > > } > > > > *************** output_die (dw_die_ref die) > > *** 9971,9977 **** > > > > /* If someone in another CU might refer to us, set up a symbol for > > them to point to. */ > > ! if (! die->comdat_type_p && die->die_id.die_symbol) > > output_die_symbol (die); > > > > dw2_asm_output_data_uleb128 (die->die_abbrev, "(DIE (%#lx) %s)", > > --- 10237,10247 ---- > > > > /* If someone in another CU might refer to us, set up a symbol for > > them to point to. */ > > ! if (! die->comdat_type_p && die->die_id.die_symbol > > ! /* Don't output the symbol twice. For LTO we want the label > > ! on the section beginning, not on the actual DIE. */ > > ! && (!flag_generate_lto > > ! || die->die_tag != DW_TAG_compile_unit)) > > output_die_symbol (die); > > > > dw2_asm_output_data_uleb128 (die->die_abbrev, "(DIE (%#lx) %s)", > > *************** output_die (dw_die_ref die) > > *** 10164,10171 **** > > size = DWARF2_ADDR_SIZE; > > else > > size = DWARF_OFFSET_SIZE; > > ! dw2_asm_output_offset (size, sym, debug_info_section, "%s", > > ! name); > > } > > } > > else > > --- 10434,10453 ---- > > size = DWARF2_ADDR_SIZE; > > else > > size = DWARF_OFFSET_SIZE; > > ! /* ??? We cannot unconditionally output die_offset if > > ! non-zero - at least -feliminate-dwarf2-dups will > > ! create references to those DIEs via symbols. And we > > ! do not clear its DIE offset after outputting it > > ! (and the label refers to the actual DIEs, not the > > ! DWARF CU unit header which is when using label + offset > > ! would be the correct thing to do). > > ! ??? This is the reason for the with_offset flag. */ > > ! if (AT_ref (a)->with_offset) > > ! dw2_asm_output_offset (size, sym, AT_ref (a)->die_offset, > > ! debug_info_section, "%s", name); > > ! else > > ! dw2_asm_output_offset (size, sym, debug_info_section, "%s", > > ! name); > > } > > } > > else > > *************** output_comp_unit (dw_die_ref die, int ou > > *** 10391,10397 **** > > calc_die_sizes (die); > > > > oldsym = die->die_id.die_symbol; > > ! if (oldsym) > > { > > tmp = XALLOCAVEC (char, strlen (oldsym) + 24); > > > > --- 10673,10679 ---- > > calc_die_sizes (die); > > > > oldsym = die->die_id.die_symbol; > > ! if (oldsym && die->comdat_type_p) > > { > > tmp = XALLOCAVEC (char, strlen (oldsym) + 24); > > > > *************** output_comp_unit (dw_die_ref die, int ou > > *** 10407,10412 **** > > --- 10689,10721 ---- > > info_section_emitted = true; > > } > > > > + /* For LTO cross unit DIE refs we want a symbol on the start of the > > + debuginfo section, not on the CU DIE. > > + ??? We could simply use the symbol as it would be output by > > output_die > > + and account for the extra offset produced by the CU header which has > > fixed > > + size. OTOH it currently only supports linkonce globals which would > > + be less than ideal?. */ > > + if (flag_generate_lto && oldsym) > > + { > > + /* ??? No way to get visibility assembled without a decl. */ > > + tree decl = build_decl (UNKNOWN_LOCATION, VAR_DECL, > > + get_identifier (oldsym), char_type_node); > > + TREE_PUBLIC (decl) = true; > > + TREE_STATIC (decl) = true; > > + DECL_ARTIFICIAL (decl) = true; > > + DECL_VISIBILITY (decl) = VISIBILITY_HIDDEN; > > + DECL_VISIBILITY_SPECIFIED (decl) = true; > > + targetm.asm_out.assemble_visibility (decl, VISIBILITY_HIDDEN); > > + #ifdef ASM_WEAKEN_LABEL > > + /* We prefer a .weak because that handles duplicates from duplicate > > + archive members in a graceful way. */ > > + ASM_WEAKEN_LABEL (asm_out_file, oldsym); > > + #else > > + targetm.asm_out.globalize_label (asm_out_file, oldsym); > > + #endif > > + ASM_OUTPUT_LABEL (asm_out_file, oldsym); > > + } > > + > > /* Output debugging information. */ > > output_compilation_unit_header (dwo_id > > ? DW_UT_split_compile : DW_UT_compile); > > *************** parameter_ref_descriptor (rtx rtl) > > *** 14523,14528 **** > > --- 14832,14840 ---- > > if (dwarf_strict) > > return NULL; > > gcc_assert (TREE_CODE (DEBUG_PARAMETER_REF_DECL (rtl)) == PARM_DECL); > > + /* With LTO during LTRANS we get the late DIE that refers to the early > > + DIE, thus we add another indirection here. This seems to confuse > > + gdb enough to make gcc.dg/guality/pr68860-1.c FAIL with LTO. */ > > ref = lookup_decl_die (DEBUG_PARAMETER_REF_DECL (rtl)); > > ret = new_loc_descr (DW_OP_GNU_parameter_ref, 0, 0); > > if (ref) > > *************** add_abstract_origin_attribute (dw_die_re > > *** 20216,20222 **** > > } > > > > if (DECL_P (origin)) > > ! origin_die = lookup_decl_die (origin); > > else if (TYPE_P (origin)) > > origin_die = lookup_type_die (origin); > > else if (TREE_CODE (origin) == BLOCK) > > --- 20528,20547 ---- > > } > > > > if (DECL_P (origin)) > > ! { > > ! dw_die_ref c; > > ! origin_die = lookup_decl_die (origin); > > ! /* "Unwrap" the decls DIE which we put in the imported unit context. > > ! ??? If we finish dwarf2out_function_decl refactoring we can > > ! do this in a better way from the start and only lazily emit > > ! the early DIE references. */ > > ! if (in_lto_p > > ! && origin_die > > ! && (c = get_AT_ref (origin_die, DW_AT_abstract_origin)) > > ! /* ??? Identify this better. */ > > ! && c->with_offset) > > ! origin_die = c; > > ! } > > else if (TYPE_P (origin)) > > origin_die = lookup_type_die (origin); > > else if (TREE_CODE (origin) == BLOCK) > > *************** gen_array_type_die (tree type, dw_die_re > > *** 20775,20781 **** > > size = int_size_in_bytes (type); > > if (size >= 0) > > add_AT_unsigned (array_die, DW_AT_byte_size, size); > > ! else if (TYPE_DOMAIN (type) != NULL_TREE > > && TYPE_MAX_VALUE (TYPE_DOMAIN (type)) != NULL_TREE) > > { > > tree szdecl = TYPE_MAX_VALUE (TYPE_DOMAIN (type)); > > --- 21100,21109 ---- > > size = int_size_in_bytes (type); > > if (size >= 0) > > add_AT_unsigned (array_die, DW_AT_byte_size, size); > > ! /* ??? We can't annotate types late, but for LTO we may not > > ! generate a location early either (gfortran.dg/save_6.f90). */ > > ! else if (! (early_dwarf && flag_generate_lto) > > ! && TYPE_DOMAIN (type) != NULL_TREE > > && TYPE_MAX_VALUE (TYPE_DOMAIN (type)) != NULL_TREE) > > { > > tree szdecl = TYPE_MAX_VALUE (TYPE_DOMAIN (type)); > > *************** gen_formal_parameter_die (tree node, tre > > *** 21188,21194 **** > > thing. */ > > if (parm_die && parm_die->die_parent != context_die) > > { > > ! if (!DECL_ABSTRACT_P (node)) > > { > > /* This can happen when creating an inlined instance, in > > which case we need to create a new DIE that will get > > --- 21516,21524 ---- > > thing. */ > > if (parm_die && parm_die->die_parent != context_die) > > { > > ! /* ??? The DIE parent is the "abstract" copy and the context_die > > ! is the specification "copy". */ > > ! if (!DECL_ABSTRACT_P (node) && !in_lto_p) > > { > > /* This can happen when creating an inlined instance, in > > which case we need to create a new DIE that will get > > *************** gen_type_die_for_member (tree type, tree > > *** 21462,21468 **** > > /* Forward declare these functions, because they are mutually recursive > > with their set_block_* pairing functions. */ > > static void set_decl_origin_self (tree); > > - static void set_decl_abstract_flags (tree, vec<tree> &); > > > > /* Given a pointer to some BLOCK node, if the BLOCK_ABSTRACT_ORIGIN for > > the > > given BLOCK node is NULL, set the BLOCK_ABSTRACT_ORIGIN for the node so > > --- 21792,21797 ---- > > *************** set_decl_origin_self (tree decl) > > *** 21535,21685 **** > > } > > } > > > > ! /* Given a pointer to some BLOCK node, set the BLOCK_ABSTRACT flag to 1 > > ! and if it wasn't 1 before, push it to abstract_vec vector. > > ! For all local decls and all local sub-blocks (recursively) do it > > ! too. */ > > ! > > ! static void > > ! set_block_abstract_flags (tree stmt, vec<tree> &abstract_vec) > > ! { > > ! tree local_decl; > > ! tree subblock; > > ! unsigned int i; > > ! > > ! if (!BLOCK_ABSTRACT (stmt)) > > ! { > > ! abstract_vec.safe_push (stmt); > > ! BLOCK_ABSTRACT (stmt) = 1; > > ! } > > ! > > ! for (local_decl = BLOCK_VARS (stmt); > > ! local_decl != NULL_TREE; > > ! local_decl = DECL_CHAIN (local_decl)) > > ! if (! DECL_EXTERNAL (local_decl)) > > ! set_decl_abstract_flags (local_decl, abstract_vec); > > ! > > ! for (i = 0; i < BLOCK_NUM_NONLOCALIZED_VARS (stmt); i++) > > ! { > > ! local_decl = BLOCK_NONLOCALIZED_VAR (stmt, i); > > ! if ((VAR_P (local_decl) && !TREE_STATIC (local_decl)) > > ! || TREE_CODE (local_decl) == PARM_DECL) > > ! set_decl_abstract_flags (local_decl, abstract_vec); > > ! } > > ! > > ! for (subblock = BLOCK_SUBBLOCKS (stmt); > > ! subblock != NULL_TREE; > > ! subblock = BLOCK_CHAIN (subblock)) > > ! set_block_abstract_flags (subblock, abstract_vec); > > ! } > > ! > > ! /* Given a pointer to some ..._DECL node, set DECL_ABSTRACT_P flag on it > > ! to 1 and if it wasn't 1 before, push to abstract_vec vector. > > ! In the case where the decl is a FUNCTION_DECL also set the abstract > > ! flags for all of the parameters, local vars, local > > ! blocks and sub-blocks (recursively). */ > > ! > > ! static void > > ! set_decl_abstract_flags (tree decl, vec<tree> &abstract_vec) > > ! { > > ! if (!DECL_ABSTRACT_P (decl)) > > ! { > > ! abstract_vec.safe_push (decl); > > ! DECL_ABSTRACT_P (decl) = 1; > > ! } > > ! > > ! if (TREE_CODE (decl) == FUNCTION_DECL) > > ! { > > ! tree arg; > > ! > > ! for (arg = DECL_ARGUMENTS (decl); arg; arg = DECL_CHAIN (arg)) > > ! if (!DECL_ABSTRACT_P (arg)) > > ! { > > ! abstract_vec.safe_push (arg); > > ! DECL_ABSTRACT_P (arg) = 1; > > ! } > > ! if (DECL_INITIAL (decl) != NULL_TREE > > ! && DECL_INITIAL (decl) != error_mark_node) > > ! set_block_abstract_flags (DECL_INITIAL (decl), abstract_vec); > > ! } > > ! } > > ! > > ! /* Generate the DWARF2 info for the "abstract" instance of a function > > which we > > ! may later generate inlined and/or out-of-line instances of. > > ! > > ! FIXME: In the early-dwarf world, this function, and most of the > > ! DECL_ABSTRACT code should be obsoleted. The early DIE _is_ > > ! the abstract instance. All we would need to do is annotate > > ! the early DIE with the appropriate DW_AT_inline in late > > ! dwarf (perhaps in gen_inlined_subroutine_die). > > ! > > ! However, we can't do this yet, because LTO streaming of DIEs > > ! has not been implemented yet. */ > > > > static void > > dwarf2out_abstract_function (tree decl) > > { > > dw_die_ref old_die; > > - tree save_fn; > > - tree context; > > - hash_table<decl_loc_hasher> *old_decl_loc_table; > > - hash_table<dw_loc_list_hasher> *old_cached_dw_loc_list_table; > > - int old_call_site_count, old_tail_call_site_count; > > - struct call_arg_loc_node *old_call_arg_locations; > > > > /* Make sure we have the actual abstract inline, not a clone. */ > > decl = DECL_ORIGIN (decl); > > > > old_die = lookup_decl_die (decl); > > ! if (old_die && get_AT (old_die, DW_AT_inline)) > > /* We've already generated the abstract instance. */ > > return; > > > > ! /* We can be called while recursively when seeing block defining > > inlined subroutine > > ! DIE. Be sure to not clobber the outer location table nor use it or > > we would > > ! get locations in abstract instantces. */ > > ! old_decl_loc_table = decl_loc_table; > > ! decl_loc_table = NULL; > > ! old_cached_dw_loc_list_table = cached_dw_loc_list_table; > > ! cached_dw_loc_list_table = NULL; > > ! old_call_arg_locations = call_arg_locations; > > ! call_arg_locations = NULL; > > ! old_call_site_count = call_site_count; > > ! call_site_count = -1; > > ! old_tail_call_site_count = tail_call_site_count; > > ! tail_call_site_count = -1; > > ! > > ! /* Be sure we've emitted the in-class declaration DIE (if any) first, so > > ! we don't get confused by DECL_ABSTRACT_P. */ > > ! if (debug_info_level > DINFO_LEVEL_TERSE) > > { > > ! context = decl_class_context (decl); > > ! if (context) > > ! gen_type_die_for_member > > ! (context, decl, decl_function_context (decl) ? NULL : comp_unit_die > > ()); > > } > > > > ! /* Pretend we've just finished compiling this function. */ > > ! save_fn = current_function_decl; > > ! current_function_decl = decl; > > ! > > ! auto_vec<tree, 64> abstract_vec; > > ! set_decl_abstract_flags (decl, abstract_vec); > > ! dwarf2out_decl (decl); > > ! unsigned int i; > > ! tree t; > > ! FOR_EACH_VEC_ELT (abstract_vec, i, t) > > ! if (TREE_CODE (t) == BLOCK) > > ! BLOCK_ABSTRACT (t) = 0; > > ! else > > ! DECL_ABSTRACT_P (t) = 0; > > ! > > ! current_function_decl = save_fn; > > ! decl_loc_table = old_decl_loc_table; > > ! cached_dw_loc_list_table = old_cached_dw_loc_list_table; > > ! call_arg_locations = old_call_arg_locations; > > ! call_site_count = old_call_site_count; > > ! tail_call_site_count = old_tail_call_site_count; > > } > > > > /* Helper function of premark_used_types() which gets called through > > --- 21864,21908 ---- > > } > > } > > > > ! /* Mark the early DIE for DECL as the abstract instance. */ > > > > static void > > dwarf2out_abstract_function (tree decl) > > { > > dw_die_ref old_die; > > > > /* Make sure we have the actual abstract inline, not a clone. */ > > decl = DECL_ORIGIN (decl); > > > > + if (DECL_IGNORED_P (decl)) > > + return; > > + > > old_die = lookup_decl_die (decl); > > ! /* With early debug we always have an old DIE. */ > > ! gcc_assert (old_die != NULL); > > ! if (get_AT (old_die, DW_AT_inline)) > > /* We've already generated the abstract instance. */ > > return; > > > > ! /* Go ahead and put DW_AT_inline on the DIE. */ > > ! if (DECL_DECLARED_INLINE_P (decl)) > > { > > ! if (cgraph_function_possibly_inlined_p (decl)) > > ! add_AT_unsigned (old_die, DW_AT_inline, DW_INL_declared_inlined); > > ! else > > ! add_AT_unsigned (old_die, DW_AT_inline, DW_INL_declared_not_inlined); > > ! } > > ! else > > ! { > > ! if (cgraph_function_possibly_inlined_p (decl)) > > ! add_AT_unsigned (old_die, DW_AT_inline, DW_INL_inlined); > > ! else > > ! add_AT_unsigned (old_die, DW_AT_inline, DW_INL_not_inlined); > > } > > > > ! if (DECL_DECLARED_INLINE_P (decl) > > ! && lookup_attribute ("artificial", DECL_ATTRIBUTES (decl))) > > ! add_AT_flag (old_die, DW_AT_artificial, 1); > > } > > > > /* Helper function of premark_used_types() which gets called through > > *************** gen_subprogram_die (tree decl, dw_die_re > > *** 21901,21907 **** > > if (old_die && old_die->die_parent == NULL) > > add_child_die (context_die, old_die); > > > > ! if (old_die && get_AT_ref (old_die, DW_AT_abstract_origin)) > > { > > /* If we have a DW_AT_abstract_origin we have a working > > cached version. */ > > --- 22124,22135 ---- > > if (old_die && old_die->die_parent == NULL) > > add_child_die (context_die, old_die); > > > > ! dw_die_ref c; > > ! if (old_die > > ! && (c = get_AT_ref (old_die, DW_AT_abstract_origin)) > > ! /* ??? In LTO all origin DIEs still refer to the early > > ! debug copy. Detect that. */ > > ! && get_AT (c, DW_AT_inline)) > > { > > /* If we have a DW_AT_abstract_origin we have a working > > cached version. */ > > *************** gen_subprogram_die (tree decl, dw_die_re > > *** 21969,21975 **** > > || (old_die->die_parent > > && old_die->die_parent->die_tag == DW_TAG_module) > > || context_die == NULL) > > ! && (DECL_ARTIFICIAL (decl) > > || (get_AT_file (old_die, DW_AT_decl_file) == file_index > > && (get_AT_unsigned (old_die, DW_AT_decl_line) > > == (unsigned) s.line) > > --- 22197,22204 ---- > > || (old_die->die_parent > > && old_die->die_parent->die_tag == DW_TAG_module) > > || context_die == NULL) > > ! /* ??? In LTO we do not see any of the location attributes. */ > > ! && ((DECL_ARTIFICIAL (decl) || in_lto_p) > > || (get_AT_file (old_die, DW_AT_decl_file) == file_index > > && (get_AT_unsigned (old_die, DW_AT_decl_line) > > == (unsigned) s.line) > > *************** gen_variable_die (tree decl, tree origin > > *** 22836,22841 **** > > --- 23065,23088 ---- > > /* If a DIE was dumped early, it still needs location info. > > Skip to where we fill the location bits. */ > > var_die = old_die; > > + > > + /* ??? In LTRANS we cannot annotate early created variably > > + modified type DIEs without copying them and adjusting all > > + references to them. Thus we dumped them again, also add a > > + reference to them. */ > > + tree type = TREE_TYPE (decl_or_origin); > > + if (in_lto_p > > + && variably_modified_type_p > > + (type, decl_function_context (decl_or_origin))) > > + { > > + if (decl_by_reference_p (decl_or_origin)) > > + add_type_attribute (var_die, TREE_TYPE (type), > > + TYPE_UNQUALIFIED, false, context_die); > > + else > > + add_type_attribute (var_die, type, decl_quals (decl_or_origin), > > + false, context_die); > > + } > > + > > goto gen_variable_die_location; > > } > > } > > *************** gen_inlined_subroutine_die (tree stmt, d > > *** 23236,23247 **** > > gcc_checking_assert (DECL_ABSTRACT_P (decl) > > || cgraph_function_possibly_inlined_p (decl)); > > > > - /* Emit info for the abstract instance first, if we haven't yet. We > > - must emit this even if the block is abstract, otherwise when we > > - emit the block below (or elsewhere), we may end up trying to emit > > - a die whose origin die hasn't been emitted, and crashing. */ > > - dwarf2out_abstract_function (decl); > > - > > if (! BLOCK_ABSTRACT (stmt)) > > { > > dw_die_ref subr_die > > --- 23483,23488 ---- > > *************** process_scope_var (tree stmt, tree decl, > > *** 24868,24874 **** > > stmt, context_die); > > } > > else > > ! gen_decl_die (decl, origin, NULL, context_die); > > } > > > > /* Generate all of the decls declared within a given scope and > > (recursively) > > --- 25109,25128 ---- > > stmt, context_die); > > } > > else > > ! { > > ! if (decl && DECL_P (decl)) > > ! { > > ! die = lookup_decl_die (decl); > > ! > > ! /* Early created DIEs do not have a parent as the decls refer > > ! to the function as DECL_CONTEXT rather than the BLOCK. */ > > ! if (in_lto_p > > ! && die && die->die_parent == NULL) > > ! add_child_die (context_die, die); > > ! } > > ! > > ! gen_decl_die (decl, origin, NULL, context_die); > > ! } > > } > > > > /* Generate all of the decls declared within a given scope and > > (recursively) > > *************** gen_decl_die (tree decl, tree origin, st > > *** 25288,25295 **** > > ? DECL_ORIGIN (origin) > > : DECL_ABSTRACT_ORIGIN (decl)); > > > > ! /* 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 (cgraph_function_possibly_inlined_p (decl) > > && ! DECL_ABSTRACT_P (decl) > > && ! class_or_namespace_scope_p (context_die) > > --- 25542,25549 ---- > > ? DECL_ORIGIN (origin) > > : DECL_ABSTRACT_ORIGIN (decl)); > > > > ! /* If we're emitting a possibly inlined function emit it as > > ! abstract instance. */ > > else if (cgraph_function_possibly_inlined_p (decl) > > && ! DECL_ABSTRACT_P (decl) > > && ! class_or_namespace_scope_p (context_die) > > *************** gen_decl_die (tree decl, tree origin, st > > *** 25303,25309 **** > > } > > > > /* Otherwise we're emitting the primary DIE for this decl. */ > > ! else if (debug_info_level > DINFO_LEVEL_TERSE) > > { > > /* Before we describe the FUNCTION_DECL itself, make sure that we > > have its containing type. */ > > --- 25557,25565 ---- > > } > > > > /* Otherwise we're emitting the primary DIE for this decl. */ > > ! else if (debug_info_level > DINFO_LEVEL_TERSE > > ! /* Do not generate stray type DIEs in late LTO dumping. */ > > ! && early_dwarf) > > { > > /* Before we describe the FUNCTION_DECL itself, make sure that we > > have its containing type. */ > > *************** gen_decl_die (tree decl, tree origin, st > > *** 25370,25389 **** > > if (debug_info_level <= DINFO_LEVEL_TERSE) > > break; > > > > ! /* Output any DIEs that are needed to specify the type of this data > > ! object. */ > > ! if (decl_by_reference_p (decl_or_origin)) > > ! gen_type_die (TREE_TYPE (TREE_TYPE (decl_or_origin)), context_die); > > ! else > > ! gen_type_die (TREE_TYPE (decl_or_origin), context_die); > > > > ! /* And its containing type. */ > > ! class_origin = decl_class_context (decl_or_origin); > > ! if (class_origin != NULL_TREE) > > ! gen_type_die_for_member (class_origin, decl_or_origin, context_die); > > > > ! /* And its containing namespace. */ > > ! context_die = declare_in_namespace (decl_or_origin, context_die); > > > > /* Now output the DIE to represent the data object itself. This > > gets > > complicated because of the possibility that the VAR_DECL really > > --- 25626,25661 ---- > > if (debug_info_level <= DINFO_LEVEL_TERSE) > > break; > > > > ! /* Avoid generating stray type DIEs during late dwarf dumping. > > ! All types have been dumped early. */ > > ! if (! lookup_decl_die (decl_or_origin) > > ! /* ??? But in LTRANS we cannot annotate early created variably > > ! modified type DIEs without copying them and adjusting all > > ! references to them. Dump them again as happens for inlining > > ! which copies both the decl and the types. */ > > ! /* ??? And even non-LTO needs to re-visit type DIEs to fill > > ! in VLA bound information for example. */ > > ! || (decl && variably_modified_type_p (TREE_TYPE (decl), > > ! current_function_decl))) > > ! { > > ! /* Output any DIEs that are needed to specify the type of this data > > ! object. */ > > ! if (decl_by_reference_p (decl_or_origin)) > > ! gen_type_die (TREE_TYPE (TREE_TYPE (decl_or_origin)), context_die); > > ! else > > ! gen_type_die (TREE_TYPE (decl_or_origin), context_die); > > ! } > > > > ! if (early_dwarf) > > ! { > > ! /* And its containing type. */ > > ! class_origin = decl_class_context (decl_or_origin); > > ! if (class_origin != NULL_TREE) > > ! gen_type_die_for_member (class_origin, decl_or_origin, context_die); > > > > ! /* And its containing namespace. */ > > ! context_die = declare_in_namespace (decl_or_origin, context_die); > > ! } > > > > /* Now output the DIE to represent the data object itself. This > > gets > > complicated because of the possibility that the VAR_DECL really > > *************** gen_decl_die (tree decl, tree origin, st > > *** 25413,25422 **** > > break; > > > > case PARM_DECL: > > ! if (DECL_BY_REFERENCE (decl_or_origin)) > > ! gen_type_die (TREE_TYPE (TREE_TYPE (decl_or_origin)), context_die); > > ! else > > ! gen_type_die (TREE_TYPE (decl_or_origin), context_die); > > return gen_formal_parameter_die (decl, origin, > > true /* Emit name attribute. */, > > context_die); > > --- 25685,25707 ---- > > break; > > > > case PARM_DECL: > > ! /* Avoid generating stray type DIEs during late dwarf dumping. > > ! All types have been dumped early. */ > > ! if (! lookup_decl_die (decl_or_origin) > > ! /* ??? But in LTRANS we cannot annotate early created variably > > ! modified type DIEs without copying them and adjusting all > > ! references to them. Dump them again as happens for inlining > > ! which copies both the decl and the types. */ > > ! /* ??? And even non-LTO needs to re-visit type DIEs to fill > > ! in VLA bound information for example. */ > > ! || (decl && variably_modified_type_p (TREE_TYPE (decl), > > ! current_function_decl))) > > ! { > > ! if (DECL_BY_REFERENCE (decl_or_origin)) > > ! gen_type_die (TREE_TYPE (TREE_TYPE (decl_or_origin)), context_die); > > ! else > > ! gen_type_die (TREE_TYPE (decl_or_origin), context_die); > > ! } > > return gen_formal_parameter_die (decl, origin, > > true /* Emit name attribute. */, > > context_die); > > *************** dwarf2out_early_global_decl (tree decl) > > *** 25493,25498 **** > > --- 25778,25793 ---- > > dwarf2out_decl (context); > > } > > > > + /* Emit an abstract origin of a function first. This happens > > + with C++ constructor clones for example and makes > > + dwarf2out_abstract_function happy which requires the early > > + DIE of the abstract instance to be present. */ > > + if (DECL_ABSTRACT_ORIGIN (decl)) > > + { > > + current_function_decl = DECL_ABSTRACT_ORIGIN (decl); > > + dwarf2out_decl (DECL_ABSTRACT_ORIGIN (decl)); > > + } > > + > > current_function_decl = decl; > > } > > dwarf2out_decl (decl); > > *************** dwarf2out_late_global_decl (tree decl) > > *** 25515,25521 **** > > { > > dw_die_ref die = lookup_decl_die (decl); > > > > ! /* We have to generate early debug late for LTO. */ > > if (! die && in_lto_p) > > { > > dwarf2out_decl (decl); > > --- 25810,25818 ---- > > { > > dw_die_ref die = lookup_decl_die (decl); > > > > ! /* We may have to generate early debug late for LTO in case debug > > ! was not enabled at compile-time or the target doesn't support > > ! the LTO early debug scheme. */ > > if (! die && in_lto_p) > > { > > dwarf2out_decl (decl); > > *************** output_macinfo_op (macinfo_entry *ref) > > *** 26892,26898 **** > > case DW_MACRO_import: > > dw2_asm_output_data (1, ref->code, "Import"); > > ASM_GENERATE_INTERNAL_LABEL (label, > > ! DEBUG_MACRO_SECTION_LABEL, ref->lineno); > > dw2_asm_output_offset (DWARF_OFFSET_SIZE, label, NULL, NULL); > > break; > > default: > > --- 27189,27196 ---- > > case DW_MACRO_import: > > dw2_asm_output_data (1, ref->code, "Import"); > > ASM_GENERATE_INTERNAL_LABEL (label, > > ! DEBUG_MACRO_SECTION_LABEL, > > ! ref->lineno + macinfo_label_base); > > dw2_asm_output_offset (DWARF_OFFSET_SIZE, label, NULL, NULL); > > break; > > default: > > *************** save_macinfo_strings (void) > > *** 27066,27072 **** > > /* Output macinfo section(s). */ > > > > static void > > ! output_macinfo (void) > > { > > unsigned i; > > unsigned long length = vec_safe_length (macinfo_table); > > --- 27364,27370 ---- > > /* Output macinfo section(s). */ > > > > static void > > ! output_macinfo (const char *debug_line_label, bool early_lto_debug) > > { > > unsigned i; > > unsigned long length = vec_safe_length (macinfo_table); > > *************** output_macinfo (void) > > *** 27092,27100 **** > > dw2_asm_output_data (1, 3, "Flags: 64-bit, lineptr present"); > > else > > dw2_asm_output_data (1, 2, "Flags: 32-bit, lineptr present"); > > ! dw2_asm_output_offset (DWARF_OFFSET_SIZE, > > ! (!dwarf_split_debug_info ? > > debug_line_section_label > > ! : debug_skeleton_line_section_label), > > debug_line_section, NULL); > > } > > > > --- 27390,27396 ---- > > dw2_asm_output_data (1, 3, "Flags: 64-bit, lineptr present"); > > else > > dw2_asm_output_data (1, 2, "Flags: 32-bit, lineptr present"); > > ! dw2_asm_output_offset (DWARF_OFFSET_SIZE, debug_line_label, > > debug_line_section, NULL); > > } > > > > *************** output_macinfo (void) > > *** 27148,27153 **** > > --- 27444,27453 ---- > > if (!macinfo_htab) > > return; > > > > + /* Save the number of transparent includes so we can adjust the > > + label number for the fat LTO object DWARF. */ > > + unsigned macinfo_label_base_adj = macinfo_htab->elements (); > > + > > delete macinfo_htab; > > macinfo_htab = NULL; > > > > *************** output_macinfo (void) > > *** 27167,27177 **** > > dw2_asm_output_data (1, 0, "End compilation unit"); > > targetm.asm_out.named_section (debug_macinfo_section_name, > > SECTION_DEBUG > > ! | SECTION_LINKONCE, > > comdat_key); > > ASM_GENERATE_INTERNAL_LABEL (label, > > DEBUG_MACRO_SECTION_LABEL, > > ! ref->lineno); > > ASM_OUTPUT_LABEL (asm_out_file, label); > > ref->code = 0; > > ref->info = NULL; > > --- 27467,27479 ---- > > dw2_asm_output_data (1, 0, "End compilation unit"); > > targetm.asm_out.named_section (debug_macinfo_section_name, > > SECTION_DEBUG > > ! | SECTION_LINKONCE > > ! | (early_lto_debug > > ! ? SECTION_EXCLUDE : 0), > > comdat_key); > > ASM_GENERATE_INTERNAL_LABEL (label, > > DEBUG_MACRO_SECTION_LABEL, > > ! ref->lineno + macinfo_label_base); > > ASM_OUTPUT_LABEL (asm_out_file, label); > > ref->code = 0; > > ref->info = NULL; > > *************** output_macinfo (void) > > *** 27192,27300 **** > > default: > > gcc_unreachable (); > > } > > } > > > > ! /* Initialize the various sections and labels for dwarf output. */ > > > > static void > > ! init_sections_and_labels (void) > > { > > ! if (!dwarf_split_debug_info) > > { > > ! debug_info_section = get_section (DEBUG_INFO_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_abbrev_section = get_section (DEBUG_ABBREV_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_loc_section = get_section (dwarf_version >= 5 > > ! ? DEBUG_LOCLISTS_SECTION > > ! : DEBUG_LOC_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_macinfo_section_name > > ! = (dwarf_strict && dwarf_version < 5) > > ! ? DEBUG_MACINFO_SECTION : DEBUG_MACRO_SECTION; > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > ! SECTION_DEBUG, NULL); > > } > > else > > { > > ! debug_info_section = get_section (DEBUG_DWO_INFO_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > NULL); > > ! debug_abbrev_section = get_section (DEBUG_DWO_ABBREV_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_addr_section = get_section (DEBUG_ADDR_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_skeleton_info_section = get_section (DEBUG_INFO_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_skeleton_abbrev_section = get_section (DEBUG_ABBREV_SECTION, > > ! SECTION_DEBUG, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_abbrev_section_label, > > ! DEBUG_SKELETON_ABBREV_SECTION_LABEL, 0); > > ! > > ! /* Somewhat confusing detail: The skeleton_[abbrev|info] sections > > stay in > > ! the main .o, but the skeleton_line goes into the split off dwo. > > */ > > ! debug_skeleton_line_section > > ! = get_section (DEBUG_DWO_LINE_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_line_section_label, > > ! DEBUG_SKELETON_LINE_SECTION_LABEL, 0); > > ! debug_str_offsets_section = get_section > > (DEBUG_DWO_STR_OFFSETS_SECTION, > > ! SECTION_DEBUG | > > SECTION_EXCLUDE, > > ! NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_info_section_label, > > ! DEBUG_SKELETON_INFO_SECTION_LABEL, 0); > > ! debug_loc_section = get_section (dwarf_version >= 5 > > ! ? DEBUG_DWO_LOCLISTS_SECTION > > ! : DEBUG_DWO_LOC_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > NULL); > > ! debug_str_dwo_section = get_section (DEBUG_STR_DWO_SECTION, > > ! DEBUG_STR_DWO_SECTION_FLAGS, > > NULL); > > ! debug_macinfo_section_name > > ! = (dwarf_strict && dwarf_version < 5) > > ! ? DEBUG_DWO_MACINFO_SECTION : DEBUG_DWO_MACRO_SECTION; > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > SECTION_DEBUG | SECTION_EXCLUDE, > > NULL); > > ! } > > ! debug_aranges_section = get_section (DEBUG_ARANGES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_line_section = get_section (DEBUG_LINE_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_pubnames_section = get_section (DEBUG_PUBNAMES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_pubtypes_section = get_section (DEBUG_PUBTYPES_SECTION, > > SECTION_DEBUG, NULL); > > ! debug_str_section = get_section (DEBUG_STR_SECTION, > > ! DEBUG_STR_SECTION_FLAGS, NULL); > > ! if (!dwarf_split_debug_info && !DWARF2_ASM_LINE_DEBUG_INFO) > > ! debug_line_str_section = get_section (DEBUG_LINE_STR_SECTION, > > ! DEBUG_STR_SECTION_FLAGS, NULL); > > ! > > ! debug_ranges_section = get_section (dwarf_version >= 5 > > ! ? DEBUG_RNGLISTS_SECTION > > ! : DEBUG_RANGES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_frame_section = get_section (DEBUG_FRAME_SECTION, > > ! SECTION_DEBUG, NULL); > > > > ASM_GENERATE_INTERNAL_LABEL (abbrev_section_label, > > ! DEBUG_ABBREV_SECTION_LABEL, 0); > > ASM_GENERATE_INTERNAL_LABEL (debug_info_section_label, > > ! DEBUG_INFO_SECTION_LABEL, 0); > > ASM_GENERATE_INTERNAL_LABEL (debug_line_section_label, > > ! DEBUG_LINE_SECTION_LABEL, 0); > > ASM_GENERATE_INTERNAL_LABEL (ranges_section_label, > > ! DEBUG_RANGES_SECTION_LABEL, 0); > > if (dwarf_version >= 5 && dwarf_split_debug_info) > > ASM_GENERATE_INTERNAL_LABEL (ranges_base_label, > > ! DEBUG_RANGES_SECTION_LABEL, 1); > > ASM_GENERATE_INTERNAL_LABEL (debug_addr_section_label, > > ! DEBUG_ADDR_SECTION_LABEL, 0); > > ASM_GENERATE_INTERNAL_LABEL (macinfo_section_label, > > (dwarf_strict && dwarf_version < 5) > > ? DEBUG_MACINFO_SECTION_LABEL > > ! : DEBUG_MACRO_SECTION_LABEL, 0); > > ! ASM_GENERATE_INTERNAL_LABEL (loc_section_label, > > DEBUG_LOC_SECTION_LABEL, 0); > > } > > > > /* Set up for Dwarf output at the start of compilation. */ > > --- 27494,27685 ---- > > default: > > gcc_unreachable (); > > } > > + > > + macinfo_label_base += macinfo_label_base_adj; > > } > > > > ! /* Initialize the various sections and labels for dwarf output and prefix > > ! them with PREFIX if non-NULL. */ > > > > static void > > ! init_sections_and_labels (bool early_lto_debug) > > { > > ! /* As we may get called multiple times have a generation count for > > labels. */ > > ! static unsigned generation = 0; > > ! > > ! if (early_lto_debug) > > { > > ! if (!dwarf_split_debug_info) > > ! { > > ! debug_info_section = get_section (DEBUG_LTO_INFO_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_abbrev_section = get_section (DEBUG_LTO_ABBREV_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_macinfo_section_name = ((dwarf_strict && dwarf_version < 5) > > ! ? DEBUG_LTO_MACINFO_SECTION > > ! : DEBUG_LTO_MACRO_SECTION); > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > ! SECTION_DEBUG > > ! | SECTION_EXCLUDE, NULL); > > ! /* For macro info we have to refer to a debug_line section, so similar > > ! to split-dwarf emit a skeleton one for early debug. */ > > ! debug_skeleton_line_section > > ! = get_section (DEBUG_LTO_LINE_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_line_section_label, > > ! DEBUG_SKELETON_LINE_SECTION_LABEL, > > ! generation); > > ! } > > ! else > > ! { > > ! /* ??? Which of the following do we need early? */ > > ! debug_info_section = get_section (DEBUG_LTO_DWO_INFO_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_abbrev_section = get_section (DEBUG_LTO_DWO_ABBREV_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_skeleton_info_section = get_section (DEBUG_LTO_INFO_SECTION, > > ! SECTION_DEBUG > > ! | SECTION_EXCLUDE, NULL); > > ! debug_skeleton_abbrev_section = get_section (DEBUG_LTO_ABBREV_SECTION, > > ! SECTION_DEBUG > > ! | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_abbrev_section_label, > > ! DEBUG_SKELETON_ABBREV_SECTION_LABEL, > > ! generation); > > ! > > ! /* Somewhat confusing detail: The skeleton_[abbrev|info] sections > > stay in > > ! the main .o, but the skeleton_line goes into the split off dwo. */ > > ! debug_skeleton_line_section > > ! = get_section (DEBUG_LTO_LINE_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_line_section_label, > > ! DEBUG_SKELETON_LINE_SECTION_LABEL, > > ! generation); > > ! debug_str_offsets_section > > ! = get_section (DEBUG_LTO_DWO_STR_OFFSETS_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_info_section_label, > > ! DEBUG_SKELETON_INFO_SECTION_LABEL, > > ! generation); > > ! debug_str_dwo_section = get_section (DEBUG_LTO_STR_DWO_SECTION, > > ! DEBUG_STR_DWO_SECTION_FLAGS, > > NULL); > > ! debug_macinfo_section_name > > ! = (dwarf_strict > > ! ? DEBUG_LTO_DWO_MACINFO_SECTION : DEBUG_LTO_DWO_MACRO_SECTION); > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! } > > ! debug_str_section = get_section (DEBUG_LTO_STR_SECTION, > > ! DEBUG_STR_SECTION_FLAGS > > ! | SECTION_EXCLUDE, NULL); > > } > > else > > { > > ! if (!dwarf_split_debug_info) > > ! { > > ! debug_info_section = get_section (DEBUG_INFO_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_abbrev_section = get_section (DEBUG_ABBREV_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_loc_section = get_section (DEBUG_LOC_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_macinfo_section_name > > ! = dwarf_strict ? DEBUG_MACINFO_SECTION : DEBUG_MACRO_SECTION; > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > ! SECTION_DEBUG, NULL); > > ! } > > ! else > > ! { > > ! debug_info_section = get_section (DEBUG_DWO_INFO_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_abbrev_section = get_section (DEBUG_DWO_ABBREV_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! debug_addr_section = get_section (DEBUG_ADDR_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_skeleton_info_section = get_section (DEBUG_INFO_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_skeleton_abbrev_section = get_section (DEBUG_ABBREV_SECTION, > > ! SECTION_DEBUG, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_abbrev_section_label, > > ! DEBUG_SKELETON_ABBREV_SECTION_LABEL, > > ! generation); > > ! > > ! /* Somewhat confusing detail: The skeleton_[abbrev|info] sections > > ! stay in the main .o, but the skeleton_line goes into the > > ! split off dwo. */ > > ! debug_skeleton_line_section > > ! = get_section (DEBUG_DWO_LINE_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_line_section_label, > > ! DEBUG_SKELETON_LINE_SECTION_LABEL, > > ! generation); > > ! debug_str_offsets_section > > ! = get_section (DEBUG_DWO_STR_OFFSETS_SECTION, > > ! SECTION_DEBUG | SECTION_EXCLUDE, NULL); > > ! ASM_GENERATE_INTERNAL_LABEL (debug_skeleton_info_section_label, > > ! DEBUG_SKELETON_INFO_SECTION_LABEL, > > ! generation); > > ! debug_loc_section = get_section (DEBUG_DWO_LOC_SECTION, > > SECTION_DEBUG | SECTION_EXCLUDE, > > NULL); > > ! debug_str_dwo_section = get_section (DEBUG_STR_DWO_SECTION, > > ! DEBUG_STR_DWO_SECTION_FLAGS, > > ! NULL); > > ! debug_macinfo_section_name > > ! = (dwarf_strict && dwarf_version < 5) > > ! ? DEBUG_DWO_MACINFO_SECTION : DEBUG_DWO_MACRO_SECTION; > > ! debug_macinfo_section = get_section (debug_macinfo_section_name, > > ! SECTION_DEBUG | SECTION_EXCLUDE, > > ! NULL); > > ! } > > ! debug_aranges_section = get_section (DEBUG_ARANGES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_line_section = get_section (DEBUG_LINE_SECTION, > > SECTION_DEBUG, NULL); > > ! debug_pubnames_section = get_section (DEBUG_PUBNAMES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_pubtypes_section = get_section (DEBUG_PUBTYPES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_str_section = get_section (DEBUG_STR_SECTION, > > ! DEBUG_STR_SECTION_FLAGS, NULL); > > ! debug_ranges_section = get_section (dwarf_version >= 5 > > ! ? DEBUG_RNGLISTS_SECTION > > ! : DEBUG_RANGES_SECTION, > > ! SECTION_DEBUG, NULL); > > ! debug_frame_section = get_section (DEBUG_FRAME_SECTION, > > ! SECTION_DEBUG, NULL); > > ! } > > > > ASM_GENERATE_INTERNAL_LABEL (abbrev_section_label, > > ! DEBUG_ABBREV_SECTION_LABEL, generation); > > ASM_GENERATE_INTERNAL_LABEL (debug_info_section_label, > > ! DEBUG_INFO_SECTION_LABEL, generation); > > ! info_section_emitted = false; > > ASM_GENERATE_INTERNAL_LABEL (debug_line_section_label, > > ! DEBUG_LINE_SECTION_LABEL, generation); > > ASM_GENERATE_INTERNAL_LABEL (ranges_section_label, > > ! DEBUG_RANGES_SECTION_LABEL, generation); > > if (dwarf_version >= 5 && dwarf_split_debug_info) > > ASM_GENERATE_INTERNAL_LABEL (ranges_base_label, > > ! DEBUG_RANGES_SECTION_LABEL, 2 + generation); > > ASM_GENERATE_INTERNAL_LABEL (debug_addr_section_label, > > ! DEBUG_ADDR_SECTION_LABEL, generation); > > ASM_GENERATE_INTERNAL_LABEL (macinfo_section_label, > > (dwarf_strict && dwarf_version < 5) > > ? DEBUG_MACINFO_SECTION_LABEL > > ! : DEBUG_MACRO_SECTION_LABEL, generation); > > ! ASM_GENERATE_INTERNAL_LABEL (loc_section_label, DEBUG_LOC_SECTION_LABEL, > > ! generation); > > ! > > ! ++generation; > > } > > > > /* Set up for Dwarf output at the start of compilation. */ > > *************** flush_limbo_die_list (void) > > *** 29641,29646 **** > > --- 30026,30047 ---- > > } > > } > > > > + /* Reset DIEs so we can output them again. */ > > + > > + static void > > + reset_dies (dw_die_ref die) > > + { > > + dw_die_ref c; > > + > > + /* Remove stuff we re-generate. */ > > + die->die_mark = 0; > > + die->die_offset = 0; > > + die->die_abbrev = 0; > > + remove_AT (die, DW_AT_sibling); > > + > > + FOR_EACH_CHILD (die, c, reset_dies (c)); > > + } > > + > > /* Output stuff that dwarf requires at the end of every file, > > and generate the DWARF-2 debugging info. */ > > > > *************** dwarf2out_finish (const char *) > > *** 29667,29672 **** > > --- 30068,30113 ---- > > > > gen_remaining_tmpl_value_param_die_attribute (); > > > > + if (flag_generate_lto) > > + { > > + gcc_assert (flag_fat_lto_objects); > > + > > + /* Prune stuff so that dwarf2out_finish runs successfully > > + for the fat part of the object. */ > > + reset_dies (comp_unit_die ()); > > + for (limbo_die_node *node = cu_die_list; node; node = node->next) > > + reset_dies (node->die); > > + > > + hash_table<comdat_type_hasher> comdat_type_table (100); > > + for (ctnode = comdat_type_list; ctnode != NULL; ctnode = > > ctnode->next) > > + { > > + comdat_type_node **slot > > + = comdat_type_table.find_slot (ctnode, INSERT); > > + > > + /* Don't reset types twice. */ > > + if (*slot != HTAB_EMPTY_ENTRY) > > + continue; > > + > > + /* Add a pointer to the line table for the main compilation unit > > + so that the debugger can make sense of DW_AT_decl_file > > + attributes. */ > > + if (debug_info_level >= DINFO_LEVEL_TERSE) > > + reset_dies (ctnode->root_die); > > + > > + *slot = ctnode; > > + } > > + > > + /* Reset die CU symbol so we don't output it twice. */ > > + comp_unit_die ()->die_id.die_symbol = NULL; > > + > > + /* Remove DW_AT_macro from the early output. */ > > + if (have_macinfo) > > + remove_AT (comp_unit_die (), DEBUG_MACRO_ATTRIBUTE); > > + > > + /* Remove indirect string decisions. */ > > + debug_str_hash->traverse<void *, reset_indirect_string> (NULL); > > + } > > + > > #if ENABLE_ASSERT_CHECKING > > { > > dw_die_ref die = comp_unit_die (), c; > > *************** dwarf2out_finish (const char *) > > *** 29677,29683 **** > > move_marked_base_types (); > > > > /* Initialize sections and labels used for actual assembler output. */ > > ! init_sections_and_labels (); > > > > /* Traverse the DIE's and add sibling attributes to those DIE's that > > have children. */ > > --- 30118,30124 ---- > > move_marked_base_types (); > > > > /* Initialize sections and labels used for actual assembler output. */ > > ! init_sections_and_labels (false); > > > > /* Traverse the DIE's and add sibling attributes to those DIE's that > > have children. */ > > *************** dwarf2out_finish (const char *) > > *** 29772,29780 **** > > debug_line_section_label); > > > > if (have_macinfo) > > ! add_AT_macptr (comp_unit_die (), > > ! dwarf_version >= 5 ? DW_AT_macros > > ! : dwarf_strict ? DW_AT_macro_info : DW_AT_GNU_macros, > > macinfo_section_label); > > > > if (dwarf_split_debug_info) > > --- 30213,30219 ---- > > debug_line_section_label); > > > > if (have_macinfo) > > ! add_AT_macptr (comp_unit_die (), DEBUG_MACRO_ATTRIBUTE, > > macinfo_section_label); > > > > if (dwarf_split_debug_info) > > *************** dwarf2out_finish (const char *) > > *** 29979,29985 **** > > { > > switch_to_section (debug_macinfo_section); > > ASM_OUTPUT_LABEL (asm_out_file, macinfo_section_label); > > ! output_macinfo (); > > dw2_asm_output_data (1, 0, "End compilation unit"); > > } > > > > --- 30418,30425 ---- > > { > > switch_to_section (debug_macinfo_section); > > ASM_OUTPUT_LABEL (asm_out_file, macinfo_section_label); > > ! output_macinfo (!dwarf_split_debug_info ? debug_line_section_label > > ! : debug_skeleton_line_section_label, false); > > dw2_asm_output_data (1, 0, "End compilation unit"); > > } > > > > *************** note_variable_value_in_expr (dw_die_ref > > *** 30200,30205 **** > > --- 30640,30659 ---- > > { > > tree decl = loc->dw_loc_oprnd1.v.val_decl_ref; > > dw_die_ref ref = lookup_decl_die (decl); > > + if (! ref && flag_generate_lto) > > + { > > + /* ??? This is somewhat a hack because we do not create DIEs > > + for variables not in BLOCK trees early but when generating > > + early LTO output we need the dw_val_class_decl_ref to be > > + fully resolved. For fat LTO objects we'd also like to > > + undo this after LTO dwarf output. */ > > + gcc_assert (DECL_CONTEXT (decl)); > > + dw_die_ref ctx = lookup_decl_die (DECL_CONTEXT (decl)); > > + gcc_assert (ctx != NULL); > > + gen_decl_die (decl, NULL_TREE, NULL, ctx); > > + ref = lookup_decl_die (decl); > > + gcc_assert (ref != NULL); > > + } > > if (ref) > > { > > loc->dw_loc_oprnd1.val_class = dw_val_class_die_ref; > > *************** dwarf2out_early_finish (const char *file > > *** 30410,30415 **** > > --- 30864,30982 ---- > > > > /* The early debug phase is now finished. */ > > early_dwarf_finished = true; > > + > > + /* Do not generate DWARF assembler now when not producing LTO bytecode. > > */ > > + if (!flag_generate_lto) > > + return; > > + > > + /* Now as we are going to output for LTO initialize sections and labels > > + to the LTO variants. We don't need a random-seed postfix as other > > + LTO sections as linking the LTO debug sections into one in a partial > > + link is fine. */ > > + init_sections_and_labels (true); > > + > > + /* The output below is modeled after dwarf2out_finish with all > > + location related output removed and some LTO specific changes. > > + Some refactoring might make both smaller and easier to match up. */ > > + > > + /* Traverse the DIE's and add add sibling attributes to those DIE's > > + that have children. */ > > + add_sibling_attributes (comp_unit_die ()); > > + for (limbo_die_node *node = limbo_die_list; node; node = node->next) > > + add_sibling_attributes (node->die); > > + for (comdat_type_node *ctnode = comdat_type_list; > > + ctnode != NULL; ctnode = ctnode->next) > > + add_sibling_attributes (ctnode->root_die); > > + > > + if (have_macinfo) > > + add_AT_macptr (comp_unit_die (), DEBUG_MACRO_ATTRIBUTE, > > + macinfo_section_label); > > + > > + save_macinfo_strings (); > > + > > + /* Output all of the compilation units. We put the main one last so > > that > > + the offsets are available to output_pubnames. */ > > + for (limbo_die_node *node = limbo_die_list; node; node = node->next) > > + output_comp_unit (node->die, 0, NULL); > > + > > + hash_table<comdat_type_hasher> comdat_type_table (100); > > + for (comdat_type_node *ctnode = comdat_type_list; > > + ctnode != NULL; ctnode = ctnode->next) > > + { > > + comdat_type_node **slot = comdat_type_table.find_slot (ctnode, > > INSERT); > > + > > + /* Don't output duplicate types. */ > > + if (*slot != HTAB_EMPTY_ENTRY) > > + continue; > > + > > + /* Add a pointer to the line table for the main compilation unit > > + so that the debugger can make sense of DW_AT_decl_file > > + attributes. */ > > + if (debug_info_level >= DINFO_LEVEL_TERSE) > > + add_AT_lineptr (ctnode->root_die, DW_AT_stmt_list, > > + (!dwarf_split_debug_info > > + ? debug_line_section_label > > + : debug_skeleton_line_section_label)); > > + > > + output_comdat_type_unit (ctnode); > > + *slot = ctnode; > > + } > > + > > + /* The AT_pubnames attribute needs to go in all skeleton dies, including > > + both the main_cu and all skeleton TUs. Making this call > > unconditional > > + would end up either adding a second copy of the AT_pubnames > > attribute, or > > + requiring a special case in add_top_level_skeleton_die_attrs. */ > > + if (!dwarf_split_debug_info) > > + add_AT_pubnames (comp_unit_die ()); > > + > > + /* Stick a unique symbol to the main debuginfo section. */ > > + compute_section_prefix_1 (comp_unit_die (), false); > > + > > + /* Output the main compilation unit. We always need it if only for > > + the CU symbol. */ > > + output_comp_unit (comp_unit_die (), true, NULL); > > + > > + /* Output the abbreviation table. */ > > + if (vec_safe_length (abbrev_die_table) != 1) > > + { > > + switch_to_section (debug_abbrev_section); > > + ASM_OUTPUT_LABEL (asm_out_file, abbrev_section_label); > > + output_abbrev_section (); > > + } > > + > > + /* Have to end the macro section. */ > > + if (have_macinfo) > > + { > > + /* We have to save macinfo state if we need to output it again > > + for the FAT part of the object. */ > > + vec<macinfo_entry, va_gc> *saved_macinfo_table = macinfo_table; > > + if (flag_fat_lto_objects) > > + macinfo_table = macinfo_table->copy (); > > + > > + switch_to_section (debug_macinfo_section); > > + ASM_OUTPUT_LABEL (asm_out_file, macinfo_section_label); > > + output_macinfo (debug_skeleton_line_section_label, true); > > + dw2_asm_output_data (1, 0, "End compilation unit"); > > + > > + /* Emit a skeleton debug_line section. */ > > + switch_to_section (debug_skeleton_line_section); > > + ASM_OUTPUT_LABEL (asm_out_file, debug_skeleton_line_section_label); > > + output_line_info (true); > > + > > + if (flag_fat_lto_objects) > > + { > > + vec_free (macinfo_table); > > + macinfo_table = saved_macinfo_table; > > + } > > + } > > + > > + > > + /* If we emitted any indirect strings, output the string table too. */ > > + if (debug_str_hash || skeleton_debug_str_hash) > > + output_indirect_strings (); > > + > > + /* Switch back to the text section. */ > > + switch_to_section (text_section); > > } > > > > /* Reset all state within dwarf2out.c so that we can rerun the compiler > > Index: early-lto-debug/gcc/debug.h > > =================================================================== > > *** early-lto-debug.orig/gcc/debug.h 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/debug.h 2017-05-16 13:10:49.774239353 +0200 > > *************** struct gcc_debug_hooks > > *** 147,152 **** > > --- 147,160 ---- > > void (* imported_module_or_decl) (tree decl, tree name, > > tree context, bool child); > > > > + /* Return true if a DIE for the tree is available and return a symbol > > + and offset that can be used to refer to it externally. */ > > + bool (* die_ref_for_decl) (tree, const char **, unsigned HOST_WIDE_INT > > *); > > + > > + /* Early debug information for the tree is available at symbol plus > > + offset externally. */ > > + void (* register_external_die) (tree, const char *, unsigned > > HOST_WIDE_INT); > > + > > /* DECL is an inline function, whose body is present, but which is > > not being output at this point. */ > > void (* deferred_inline_function) (tree decl); > > *************** extern void debug_nothing_tree_tree_tree > > *** 210,215 **** > > --- 218,227 ---- > > extern bool debug_true_const_tree (const_tree); > > extern void debug_nothing_rtx_insn (rtx_insn *); > > extern void debug_nothing_rtx_code_label (rtx_code_label *); > > + extern bool debug_false_tree_charstarstar_uhwistar (tree, const char **, > > + unsigned HOST_WIDE_INT *); > > + extern void debug_nothing_tree_charstar_uhwi (tree, const char *, > > + unsigned HOST_WIDE_INT); > > > > /* Hooks for various debug formats. */ > > extern const struct gcc_debug_hooks do_nothing_debug_hooks; > > Index: early-lto-debug/gcc/debug.c > > =================================================================== > > *** early-lto-debug.orig/gcc/debug.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/debug.c 2017-05-16 13:10:49.774239353 +0200 > > *************** const struct gcc_debug_hooks do_nothing_ > > *** 48,53 **** > > --- 48,55 ---- > > debug_nothing_tree, /* late_global_decl */ > > debug_nothing_tree_int, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > debug_nothing_tree, /* outlining_inline_function */ > > debug_nothing_rtx_code_label, /* label */ > > *************** debug_nothing_tree_int (tree decl ATTRIB > > *** 146,148 **** > > --- 148,163 ---- > > int local ATTRIBUTE_UNUSED) > > { > > } > > + > > + bool > > + debug_false_tree_charstarstar_uhwistar (tree, const char **, > > + unsigned HOST_WIDE_INT *) > > + { > > + return false; > > + } > > + > > + void > > + debug_nothing_tree_charstar_uhwi (tree, const char *, > > + unsigned HOST_WIDE_INT) > > + { > > + } > > Index: early-lto-debug/gcc/dbxout.c > > =================================================================== > > *** early-lto-debug.orig/gcc/dbxout.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/dbxout.c 2017-05-16 13:10:49.778239419 +0200 > > *************** const struct gcc_debug_hooks dbx_debug_h > > *** 372,377 **** > > --- 372,379 ---- > > dbxout_late_global_decl, /* late_global_decl */ > > dbxout_type_decl, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > debug_nothing_tree, /* outlining_inline_function */ > > debug_nothing_rtx_code_label, /* label */ > > *************** const struct gcc_debug_hooks xcoff_debug > > *** 412,417 **** > > --- 414,421 ---- > > dbxout_late_global_decl, /* late_global_decl */ > > dbxout_type_decl, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > debug_nothing_tree, /* outlining_inline_function */ > > debug_nothing_rtx_code_label, /* label */ > > Index: early-lto-debug/gcc/sdbout.c > > =================================================================== > > *** early-lto-debug.orig/gcc/sdbout.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/sdbout.c 2017-05-16 13:10:49.778239419 +0200 > > *************** const struct gcc_debug_hooks sdb_debug_h > > *** 302,307 **** > > --- 302,309 ---- > > sdbout_late_global_decl, /* late_global_decl */ > > sdbout_symbol, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > debug_nothing_tree, /* outlining_inline_function */ > > sdbout_label, /* label */ > > Index: early-lto-debug/gcc/lto/lto.c > > =================================================================== > > *** early-lto-debug.orig/gcc/lto/lto.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/lto/lto.c 2017-05-16 13:10:49.778239419 +0200 > > *************** unify_scc (struct data_in *data_in, unsi > > *** 1632,1637 **** > > --- 1632,1640 ---- > > free_node (scc->entries[i]); > > } > > > > + /* Drop DIE references. */ > > + dref_queue.truncate (0); > > + > > break; > > } > > > > *************** lto_read_decls (struct lto_file_decl_dat > > *** 1707,1714 **** > > from); > > if (len == 1 > > && (TREE_CODE (first) == IDENTIFIER_NODE > > ! || TREE_CODE (first) == INTEGER_CST > > ! || TREE_CODE (first) == TRANSLATION_UNIT_DECL)) > > continue; > > > > /* Try to unify the SCC with already existing ones. */ > > --- 1710,1716 ---- > > from); > > if (len == 1 > > && (TREE_CODE (first) == IDENTIFIER_NODE > > ! || TREE_CODE (first) == INTEGER_CST)) > > continue; > > > > /* Try to unify the SCC with already existing ones. */ > > *************** lto_read_decls (struct lto_file_decl_dat > > *** 1747,1762 **** > > if (TREE_CODE (t) == INTEGER_CST > > && !TREE_OVERFLOW (t)) > > cache_integer_cst (t); > > - /* Register TYPE_DECLs with the debuginfo machinery. */ > > - if (!flag_wpa > > - && TREE_CODE (t) == TYPE_DECL) > > - { > > - /* Dwarf2out needs location information. > > - TODO: Moving this out of the streamer loop may noticealy > > - improve ltrans linemap memory use. */ > > - data_in->location_cache.apply_location_cache (); > > - debug_hooks->type_decl (t, !DECL_FILE_SCOPE_P (t)); > > - } > > if (!flag_ltrans) > > { > > /* Register variables and functions with the > > --- 1749,1754 ---- > > *************** lto_read_decls (struct lto_file_decl_dat > > *** 1772,1777 **** > > --- 1764,1777 ---- > > vec_safe_push (tree_with_vars, t); > > } > > } > > + > > + /* Register DECLs with the debuginfo machinery. */ > > + while (!dref_queue.is_empty ()) > > + { > > + dref_entry e = dref_queue.pop (); > > + debug_hooks->register_external_die (e.decl, e.sym, e.off); > > + } > > + > > if (seen_type) > > num_type_scc_trees += len; > > } > > *************** lto_section_with_id (const char *name, u > > *** 1951,1957 **** > > if (strncmp (name, section_name_prefix, strlen (section_name_prefix))) > > return 0; > > s = strrchr (name, '.'); > > ! return s && sscanf (s, "." HOST_WIDE_INT_PRINT_HEX_PURE, id) == 1; > > } > > > > /* Create file_data of each sub file id */ > > --- 1951,1962 ---- > > if (strncmp (name, section_name_prefix, strlen (section_name_prefix))) > > return 0; > > s = strrchr (name, '.'); > > ! if (!s) > > ! return 0; > > ! /* If the section is not suffixed with an ID return. */ > > ! if ((size_t)(s - name) == strlen (section_name_prefix)) > > ! return 0; > > ! return sscanf (s, "." HOST_WIDE_INT_PRINT_HEX_PURE, id) == 1; > > } > > > > /* Create file_data of each sub file id */ > > Index: early-lto-debug/gcc/lto-streamer-in.c > > =================================================================== > > *** early-lto-debug.orig/gcc/lto-streamer-in.c 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/lto-streamer-in.c 2017-05-16 13:10:49.858240736 > > +0200 > > *************** along with GCC; see the file COPYING3. > > *** 41,46 **** > > --- 41,47 ---- > > #include "except.h" > > #include "cgraph.h" > > #include "cfgloop.h" > > + #include "debug.h" > > > > > > struct freeing_string_slot_hasher : string_slot_hasher > > *************** input_function (tree fn_decl, struct dat > > *** 1038,1043 **** > > --- 1039,1054 ---- > > DECL_RESULT (fn_decl) = stream_read_tree (ib, data_in); > > DECL_ARGUMENTS (fn_decl) = streamer_read_chain (ib, data_in); > > > > + /* Read debug args if available. */ > > + unsigned n_debugargs = streamer_read_uhwi (ib); > > + if (n_debugargs) > > + { > > + vec<tree, va_gc> **debugargs = decl_debug_args_insert (fn_decl); > > + vec_safe_grow (*debugargs, n_debugargs); > > + for (unsigned i = 0; i < n_debugargs; ++i) > > + (**debugargs)[i] = stream_read_tree (ib, data_in); > > + } > > + > > /* Read the tree of lexical scopes for the function. */ > > DECL_INITIAL (fn_decl) = stream_read_tree (ib, data_in); > > unsigned block_leaf_count = streamer_read_uhwi (ib); > > *************** lto_input_variable_constructor (struct l > > *** 1318,1323 **** > > --- 1329,1338 ---- > > } > > > > > > + /* Queue of acummulated decl -> DIE mappings. Similar to locations those > > + are only applied to prevailing tree nodes during tree merging. */ > > + vec<dref_entry> dref_queue; > > + > > /* Read the physical representation of a tree node EXPR from > > input block IB using the per-file context in DATA_IN. */ > > > > *************** lto_read_tree_1 (struct lto_input_block > > *** 1337,1342 **** > > --- 1352,1374 ---- > > && TREE_CODE (expr) != FUNCTION_DECL > > && TREE_CODE (expr) != TRANSLATION_UNIT_DECL) > > DECL_INITIAL (expr) = stream_read_tree (ib, data_in); > > + > > + /* Stream references to early generated DIEs. Keep in sync with the > > + trees handled in dwarf2out_register_external_die. */ > > + if ((DECL_P (expr) > > + && TREE_CODE (expr) != FIELD_DECL > > + && TREE_CODE (expr) != DEBUG_EXPR_DECL > > + && TREE_CODE (expr) != TYPE_DECL) > > + || TREE_CODE (expr) == BLOCK) > > + { > > + const char *str = streamer_read_string (data_in, ib); > > + if (str) > > + { > > + unsigned HOST_WIDE_INT off = streamer_read_uhwi (ib); > > + dref_entry e = { expr, str, off }; > > + dref_queue.safe_push (e); > > + } > > + } > > } > > > > /* Read the physical representation of a tree node with tag TAG from > > *************** lto_input_tree (struct lto_input_block * > > *** 1482,1487 **** > > --- 1514,1526 ---- > > { > > unsigned len, entry_len; > > lto_input_scc (ib, data_in, &len, &entry_len); > > + > > + /* Register DECLs with the debuginfo machinery. */ > > + while (!dref_queue.is_empty ()) > > + { > > + dref_entry e = dref_queue.pop (); > > + debug_hooks->register_external_die (e.decl, e.sym, e.off); > > + } > > } > > return lto_input_tree_1 (ib, data_in, tag, 0); > > } > > Index: early-lto-debug/gcc/lto-streamer-out.c > > =================================================================== > > *** early-lto-debug.orig/gcc/lto-streamer-out.c 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/lto-streamer-out.c 2017-05-16 13:10:49.858240736 > > +0200 > > *************** along with GCC; see the file COPYING3. > > *** 40,45 **** > > --- 40,46 ---- > > #include "cfgloop.h" > > #include "builtins.h" > > #include "gomp-constants.h" > > + #include "debug.h" > > > > > > static void lto_write_tree (struct output_block*, tree, bool); > > *************** lto_write_tree_1 (struct output_block *o > > *** 406,411 **** > > --- 407,432 ---- > > (ob->decl_state->symtab_node_encoder, expr); > > stream_write_tree (ob, initial, ref_p); > > } > > + > > + /* Stream references to early generated DIEs. Keep in sync with the > > + trees handled in dwarf2out_die_ref_for_decl. */ > > + if ((DECL_P (expr) > > + && TREE_CODE (expr) != FIELD_DECL > > + && TREE_CODE (expr) != DEBUG_EXPR_DECL > > + && TREE_CODE (expr) != TYPE_DECL) > > + || TREE_CODE (expr) == BLOCK) > > + { > > + const char *sym; > > + unsigned HOST_WIDE_INT off; > > + if (debug_info_level > DINFO_LEVEL_NONE > > + && debug_hooks->die_ref_for_decl (expr, &sym, &off)) > > + { > > + streamer_write_string (ob, ob->main_stream, sym, true); > > + streamer_write_uhwi (ob, off); > > + } > > + else > > + streamer_write_string (ob, ob->main_stream, NULL, true); > > + } > > } > > > > /* Write a physical representation of tree node EXPR to output block > > *************** DFS::DFS_write_tree_body (struct output_ > > *** 745,751 **** > > ; > > else > > DFS_follow_tree_edge (DECL_NAME (expr)); > > ! DFS_follow_tree_edge (DECL_CONTEXT (expr)); > > } > > > > if (CODE_CONTAINS_STRUCT (code, TS_DECL_COMMON)) > > --- 766,776 ---- > > ; > > else > > DFS_follow_tree_edge (DECL_NAME (expr)); > > ! if (TREE_CODE (expr) != TRANSLATION_UNIT_DECL > > ! && ! DECL_CONTEXT (expr)) > > ! DFS_follow_tree_edge ((*all_translation_units)[0]); > > ! else > > ! DFS_follow_tree_edge (DECL_CONTEXT (expr)); > > } > > > > if (CODE_CONTAINS_STRUCT (code, TS_DECL_COMMON)) > > *************** DFS::DFS_write_tree_body (struct output_ > > *** 765,770 **** > > --- 790,796 ---- > > declarations which should be eliminated by decl merging. Be sure none > > leaks to this point. */ > > gcc_assert (DECL_ABSTRACT_ORIGIN (expr) != error_mark_node); > > + DFS_follow_tree_edge (DECL_ABSTRACT_ORIGIN (expr)); > > > > if ((VAR_P (expr) > > || TREE_CODE (expr) == PARM_DECL) > > *************** output_function (struct cgraph_node *nod > > *** 2061,2066 **** > > --- 2087,2103 ---- > > stream_write_tree (ob, DECL_RESULT (function), true); > > streamer_write_chain (ob, DECL_ARGUMENTS (function), true); > > > > + /* Output debug args if available. */ > > + vec<tree, va_gc> **debugargs = decl_debug_args_lookup (function); > > + if (! debugargs) > > + streamer_write_uhwi (ob, 0); > > + else > > + { > > + streamer_write_uhwi (ob, (*debugargs)->length ()); > > + for (unsigned i = 0; i < (*debugargs)->length (); ++i) > > + stream_write_tree (ob, (**debugargs)[i], true); > > + } > > + > > /* Output DECL_INITIAL for the function, which contains the tree of > > lexical scopes. */ > > stream_write_tree (ob, DECL_INITIAL (function), true); > > Index: early-lto-debug/gcc/lto-streamer.h > > =================================================================== > > *** early-lto-debug.orig/gcc/lto-streamer.h 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/lto-streamer.h 2017-05-16 13:10:49.858240736 > > +0200 > > *************** DEFINE_DECL_STREAM_FUNCS (TYPE_DECL, typ > > *** 1212,1215 **** > > --- 1212,1225 ---- > > DEFINE_DECL_STREAM_FUNCS (NAMESPACE_DECL, namespace_decl) > > DEFINE_DECL_STREAM_FUNCS (LABEL_DECL, label_decl) > > > > + /* Entry for the delayed registering of decl -> DIE references. */ > > + struct dref_entry { > > + tree decl; > > + const char *sym; > > + unsigned HOST_WIDE_INT off; > > + }; > > + > > + extern vec<dref_entry> dref_queue; > > + > > + > > #endif /* GCC_LTO_STREAMER_H */ > > Index: early-lto-debug/gcc/lto-wrapper.c > > =================================================================== > > *** early-lto-debug.orig/gcc/lto-wrapper.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/lto-wrapper.c 2017-05-16 13:10:49.858240736 > > +0200 > > *************** static char **output_names; > > *** 70,75 **** > > --- 70,76 ---- > > static char **offload_names; > > static char *offload_objects_file_name; > > static char *makefile; > > + static char *debug_obj; > > > > const char tool_name[] = "lto-wrapper"; > > > > *************** tool_cleanup (bool) > > *** 88,93 **** > > --- 89,96 ---- > > maybe_unlink (offload_objects_file_name); > > if (makefile) > > maybe_unlink (makefile); > > + if (debug_obj) > > + maybe_unlink (debug_obj); > > for (i = 0; i < nr; ++i) > > { > > maybe_unlink (input_names[i]); > > *************** find_and_merge_options (int fd, off_t fi > > *** 938,943 **** > > --- 941,1007 ---- > > return true; > > } > > > > + /* Copy early debug info sections from INFILE to a new file whose name > > + is returned. Return NULL on error. */ > > + > > + const char * > > + debug_objcopy (const char *infile) > > + { > > + const char *outfile; > > + const char *errmsg; > > + int err; > > + > > + const char *p; > > + off_t inoff = 0; > > + long loffset; > > + int consumed; > > + if ((p = strrchr (infile, '@')) > > + && p != infile > > + && sscanf (p, "@%li%n", &loffset, &consumed) >= 1 > > + && strlen (p) == (unsigned int) consumed) > > + { > > + char *fname = xstrdup (infile); > > + fname[p - infile] = '\0'; > > + infile = fname; > > + inoff = (off_t) loffset; > > + } > > + int infd = open (infile, O_RDONLY); > > + if (infd == -1) > > + return NULL; > > + simple_object_read *inobj = simple_object_start_read (infd, inoff, > > + "__GNU_LTO", > > + &errmsg, &err); > > + if (!inobj) > > + return NULL; > > + > > + off_t off, len; > > + if (simple_object_find_section (inobj, ".gnu.debuglto_.debug_info", > > + &off, &len, &errmsg, &err) != 1) > > + { > > + if (errmsg) > > + fatal_error (0, "%s: %s\n", errmsg, xstrerror (err)); > > + > > + simple_object_release_read (inobj); > > + close (infd); > > + return NULL; > > + } > > + > > + outfile = make_temp_file ("debugobjtem"); > > + errmsg = simple_object_copy_lto_debug_sections (inobj, outfile, &err); > > + if (errmsg) > > + { > > + unlink_if_ordinary (outfile); > > + fatal_error (0, "%s: %s\n", errmsg, xstrerror (err)); > > + } > > + > > + simple_object_release_read (inobj); > > + close (infd); > > + > > + return outfile; > > + } > > + > > + > > + > > /* Execute gcc. ARGC is the number of arguments. ARGV contains the > > arguments. */ > > > > static void > > *************** run_gcc (unsigned argc, char *argv[]) > > *** 962,969 **** > > int new_head_argc; > > bool have_lto = false; > > bool have_offload = false; > > ! unsigned lto_argc = 0; > > ! char **lto_argv; > > > > /* Get the driver and options. */ > > collect_gcc = getenv ("COLLECT_GCC"); > > --- 1026,1035 ---- > > int new_head_argc; > > bool have_lto = false; > > bool have_offload = false; > > ! unsigned lto_argc = 0, ltoobj_argc = 0; > > ! char **lto_argv, **ltoobj_argv; > > ! bool skip_debug = false; > > ! unsigned n_debugobj; > > > > /* Get the driver and options. */ > > collect_gcc = getenv ("COLLECT_GCC"); > > *************** run_gcc (unsigned argc, char *argv[]) > > *** 982,987 **** > > --- 1048,1054 ---- > > /* Allocate array for input object files with LTO IL, > > and for possible preceding arguments. */ > > lto_argv = XNEWVEC (char *, argc); > > + ltoobj_argv = XNEWVEC (char *, argc); > > > > /* Look at saved options in the IL files. */ > > for (i = 1; i < argc; ++i) > > *************** run_gcc (unsigned argc, char *argv[]) > > *** 1024,1030 **** > > collect_gcc)) > > { > > have_lto = true; > > ! lto_argv[lto_argc++] = argv[i]; > > } > > close (fd); > > } > > --- 1091,1097 ---- > > collect_gcc)) > > { > > have_lto = true; > > ! ltoobj_argv[ltoobj_argc++] = argv[i]; > > } > > close (fd); > > } > > *************** run_gcc (unsigned argc, char *argv[]) > > *** 1085,1090 **** > > --- 1152,1168 ---- > > } > > } > > > > + /* Output lto-wrapper invocation command. */ > > + if (verbose) > > + { > > + for (i = 0; i < argc; ++i) > > + { > > + fputs (argv[i], stderr); > > + fputc (' ', stderr); > > + } > > + fputc ('\n', stderr); > > + } > > + > > if (no_partition) > > { > > lto_mode = LTO_MODE_LTO; > > *************** cont1: > > *** 1274,1291 **** > > obstack_ptr_grow (&argv_obstack, "-fwpa"); > > } > > > > ! /* Append the input objects and possible preceding arguments. */ > > for (i = 0; i < lto_argc; ++i) > > obstack_ptr_grow (&argv_obstack, lto_argv[i]); > > obstack_ptr_grow (&argv_obstack, NULL); > > > > new_argv = XOBFINISH (&argv_obstack, const char **); > > argv_ptr = &new_argv[new_head_argc]; > > fork_execute (new_argv[0], CONST_CAST (char **, new_argv), true); > > > > if (lto_mode == LTO_MODE_LTO) > > { > > printf ("%s\n", flto_out); > > free (flto_out); > > flto_out = NULL; > > } > > --- 1352,1456 ---- > > obstack_ptr_grow (&argv_obstack, "-fwpa"); > > } > > > > ! /* Append input arguments. */ > > for (i = 0; i < lto_argc; ++i) > > obstack_ptr_grow (&argv_obstack, lto_argv[i]); > > + /* Append the input objects. */ > > + for (i = 0; i < ltoobj_argc; ++i) > > + obstack_ptr_grow (&argv_obstack, ltoobj_argv[i]); > > obstack_ptr_grow (&argv_obstack, NULL); > > > > new_argv = XOBFINISH (&argv_obstack, const char **); > > argv_ptr = &new_argv[new_head_argc]; > > fork_execute (new_argv[0], CONST_CAST (char **, new_argv), true); > > > > + /* Handle early generated debug information. At compile-time > > + we output early DWARF debug info into .gnu.debuglto_ prefixed > > + sections. LTRANS object DWARF debug info refers to that. > > + So we need to transfer the .gnu.debuglto_ sections to the final > > + link. Ideally the linker plugin interface would allow us to > > + not claim those sections and instruct the linker to keep > > + them, renaming them in the process. For now we extract and > > + rename those sections via a simple-object interface to produce > > + regular objects containing only the early debug info. We > > + then partially link those to a single early debug info object > > + and pass that as additional output back to the linker plugin. */ > > + > > + /* Prepare the partial link to gather the compile-time generated > > + debug-info into a single input for the final link. */ > > + debug_obj = make_temp_file ("debugobj"); > > + obstack_ptr_grow (&argv_obstack, collect_gcc); > > + for (i = 1; i < decoded_options_count; ++i) > > + { > > + /* Retain linker choice and -B. */ > > + if (decoded_options[i].opt_index == OPT_B > > + || decoded_options[i].opt_index == OPT_fuse_ld_bfd > > + || decoded_options[i].opt_index == OPT_fuse_ld_gold) > > + append_linker_options (&argv_obstack, &decoded_options[i-1], 2); > > + /* Retain all target options, this preserves -m32 for example. */ > > + if (cl_options[decoded_options[i].opt_index].flags & CL_TARGET) > > + append_linker_options (&argv_obstack, &decoded_options[i-1], 2); > > + /* Recognize -g0. */ > > + if (decoded_options[i].opt_index == OPT_g > > + && strcmp (decoded_options[i].arg, "0") == 0) > > + skip_debug = true; > > + } > > + obstack_ptr_grow (&argv_obstack, "-r"); > > + obstack_ptr_grow (&argv_obstack, "-nostdlib"); > > + obstack_ptr_grow (&argv_obstack, "-o"); > > + obstack_ptr_grow (&argv_obstack, debug_obj); > > + > > + /* Copy the early generated debug info from the objects to temporary > > + files and append those to the partial link commandline. */ > > + n_debugobj = 0; > > + if (! skip_debug) > > + for (i = 0; i < ltoobj_argc; ++i) > > + { > > + const char *tem; > > + if ((tem = debug_objcopy (ltoobj_argv[i]))) > > + { > > + obstack_ptr_grow (&argv_obstack, tem); > > + n_debugobj++; > > + } > > + } > > + > > + /* Link them all into a single object. Ideally this would reduce > > + disk space usage mainly due to .debug_str merging but unfortunately > > + GNU ld doesn't perform this with -r. */ > > + if (n_debugobj) > > + { > > + obstack_ptr_grow (&argv_obstack, NULL); > > + const char **debug_link_argv = XOBFINISH (&argv_obstack, const char > > **); > > + fork_execute (debug_link_argv[0], > > + CONST_CAST (char **, debug_link_argv), false); > > + > > + /* And dispose the temporaries. */ > > + for (i = 0; debug_link_argv[i]; ++i) > > + ; > > + for (--i; i > 0; --i) > > + { > > + if (strcmp (debug_link_argv[i], debug_obj) == 0) > > + break; > > + maybe_unlink (debug_link_argv[i]); > > + } > > + } > > + else > > + { > > + unlink_if_ordinary (debug_obj); > > + free (debug_obj); > > + debug_obj = NULL; > > + skip_debug = true; > > + } > > + > > if (lto_mode == LTO_MODE_LTO) > > { > > printf ("%s\n", flto_out); > > + if (!skip_debug) > > + { > > + printf ("%s\n", debug_obj); > > + free (debug_obj); > > + debug_obj = NULL; > > + } > > free (flto_out); > > flto_out = NULL; > > } > > *************** cont: > > *** 1434,1439 **** > > --- 1599,1610 ---- > > for (i = 0; i < nr; ++i) > > maybe_unlink (input_names[i]); > > } > > + if (!skip_debug) > > + { > > + printf ("%s\n", debug_obj); > > + free (debug_obj); > > + debug_obj = NULL; > > + } > > for (i = 0; i < nr; ++i) > > { > > fputs (output_names[i], stdout); > > Index: early-lto-debug/gcc/tree-streamer-in.c > > =================================================================== > > *** early-lto-debug.orig/gcc/tree-streamer-in.c 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/tree-streamer-in.c 2017-05-16 13:10:49.862240801 > > +0200 > > *************** lto_input_ts_decl_common_tree_pointers ( > > *** 688,697 **** > > DECL_SIZE (expr) = stream_read_tree (ib, data_in); > > DECL_SIZE_UNIT (expr) = stream_read_tree (ib, data_in); > > DECL_ATTRIBUTES (expr) = stream_read_tree (ib, data_in); > > ! > > ! /* Do not stream DECL_ABSTRACT_ORIGIN. We cannot handle debug > > information > > ! for early inlining so drop it on the floor instead of ICEing in > > ! dwarf2out.c. */ > > > > if ((VAR_P (expr) || TREE_CODE (expr) == PARM_DECL) > > && DECL_HAS_VALUE_EXPR_P (expr)) > > --- 688,694 ---- > > DECL_SIZE (expr) = stream_read_tree (ib, data_in); > > DECL_SIZE_UNIT (expr) = stream_read_tree (ib, data_in); > > DECL_ATTRIBUTES (expr) = stream_read_tree (ib, data_in); > > ! DECL_ABSTRACT_ORIGIN (expr) = stream_read_tree (ib, data_in); > > > > if ((VAR_P (expr) || TREE_CODE (expr) == PARM_DECL) > > && DECL_HAS_VALUE_EXPR_P (expr)) > > Index: early-lto-debug/gcc/tree-streamer-out.c > > =================================================================== > > *** early-lto-debug.orig/gcc/tree-streamer-out.c 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/tree-streamer-out.c 2017-05-16 13:10:49.862240801 > > +0200 > > *************** write_ts_decl_minimal_tree_pointers (str > > *** 566,572 **** > > stream_write_tree (ob, NULL_TREE, ref_p); > > else > > stream_write_tree (ob, DECL_NAME (expr), ref_p); > > ! stream_write_tree (ob, DECL_CONTEXT (expr), ref_p); > > } > > > > > > --- 566,576 ---- > > stream_write_tree (ob, NULL_TREE, ref_p); > > else > > stream_write_tree (ob, DECL_NAME (expr), ref_p); > > ! if (TREE_CODE (expr) != TRANSLATION_UNIT_DECL > > ! && ! DECL_CONTEXT (expr)) > > ! stream_write_tree (ob, (*all_translation_units)[0], ref_p); > > ! else > > ! stream_write_tree (ob, DECL_CONTEXT (expr), ref_p); > > } > > > > > > *************** write_ts_decl_common_tree_pointers (stru > > *** 585,594 **** > > special handling in LTO, it must be handled by streamer hooks. */ > > > > stream_write_tree (ob, DECL_ATTRIBUTES (expr), ref_p); > > ! > > ! /* Do not stream DECL_ABSTRACT_ORIGIN. We cannot handle debug > > information > > ! for early inlining so drop it on the floor instead of ICEing in > > ! dwarf2out.c. */ > > > > if ((VAR_P (expr) || TREE_CODE (expr) == PARM_DECL) > > && DECL_HAS_VALUE_EXPR_P (expr)) > > --- 589,595 ---- > > special handling in LTO, it must be handled by streamer hooks. */ > > > > stream_write_tree (ob, DECL_ATTRIBUTES (expr), ref_p); > > ! stream_write_tree (ob, DECL_ABSTRACT_ORIGIN (expr), ref_p); > > > > if ((VAR_P (expr) || TREE_CODE (expr) == PARM_DECL) > > && DECL_HAS_VALUE_EXPR_P (expr)) > > Index: early-lto-debug/gcc/config/darwin.c > > =================================================================== > > *** early-lto-debug.orig/gcc/config/darwin.c 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/config/darwin.c 2017-05-16 13:10:49.862240801 > > +0200 > > *************** darwin_asm_lto_end (void) > > *** 1959,1965 **** > > } > > > > static void > > ! darwin_asm_dwarf_section (const char *name, unsigned int flags, tree > > decl); > > > > /* Called for the TARGET_ASM_NAMED_SECTION hook. */ > > > > --- 1959,1966 ---- > > } > > > > static void > > ! darwin_asm_dwarf_section (const char *name, unsigned int flags, > > ! tree decl, bool is_for_lto); > > > > /* Called for the TARGET_ASM_NAMED_SECTION hook. */ > > > > *************** darwin_asm_named_section (const char *na > > *** 2001,2007 **** > > vec_safe_push (lto_section_names, e); > > } > > else if (strncmp (name, "__DWARF,", 8) == 0) > > ! darwin_asm_dwarf_section (name, flags, decl); > > else > > fprintf (asm_out_file, "\t.section %s\n", name); > > } > > --- 2002,2010 ---- > > vec_safe_push (lto_section_names, e); > > } > > else if (strncmp (name, "__DWARF,", 8) == 0) > > ! darwin_asm_dwarf_section (name, flags, decl, false); > > ! else if (strncmp (name, "__GNU_DWARF_LTO,", 16) == 0) > > ! darwin_asm_dwarf_section (name, flags, decl, true); > > else > > fprintf (asm_out_file, "\t.section %s\n", name); > > } > > *************** static GTY (()) vec<dwarf_sect_used_entr > > *** 2783,2801 **** > > > > static void > > darwin_asm_dwarf_section (const char *name, unsigned int flags, > > ! tree ARG_UNUSED (decl)) > > { > > unsigned i; > > ! int namelen; > > ! const char * sname; > > dwarf_sect_used_entry *ref; > > bool found = false; > > ! gcc_assert ((flags & (SECTION_DEBUG | SECTION_NAMED)) > > ! == (SECTION_DEBUG | SECTION_NAMED)); > > ! /* We know that the name starts with __DWARF, */ > > ! sname = name + 8; > > ! namelen = strchr (sname, ',') - sname; > > ! gcc_assert (namelen); > > if (dwarf_sect_names_table == NULL) > > vec_alloc (dwarf_sect_names_table, 16); > > else > > --- 2786,2822 ---- > > > > static void > > darwin_asm_dwarf_section (const char *name, unsigned int flags, > > ! tree ARG_UNUSED (decl), bool is_for_lto) > > { > > unsigned i; > > ! int namelen, extra = 0; > > ! const char *sect, *lto_add = ""; > > ! char sname[64]; > > dwarf_sect_used_entry *ref; > > bool found = false; > > ! > > ! gcc_checking_assert ((flags & (SECTION_DEBUG | SECTION_NAMED)) > > ! == (SECTION_DEBUG | SECTION_NAMED)); > > ! > > ! /* We know that the name starts with __DWARF, or __GNU_DAWRF_LTO */ > > ! sect = strchr (name, ',') + 1; > > ! namelen = strchr (sect, ',') - sect; > > ! gcc_checking_assert (namelen); > > ! > > ! /* The section switch is output as written... */ > > ! fprintf (asm_out_file, "\t.section %s\n", name); > > ! > > ! /* ... but the string we keep to make section start labels needs > > ! adjustment for lto cases. */ > > ! if (is_for_lto) > > ! { > > ! lto_add = "_lto"; > > ! extra = 4; > > ! } > > ! > > ! snprintf (sname, 64, "%.*s%.*s", namelen, sect, extra, lto_add); > > ! namelen += extra; > > ! > > if (dwarf_sect_names_table == NULL) > > vec_alloc (dwarf_sect_names_table, 16); > > else > > *************** darwin_asm_dwarf_section (const char *na > > *** 2813,2819 **** > > } > > } > > > > - fprintf (asm_out_file, "\t.section %s\n", name); > > if (!found) > > { > > dwarf_sect_used_entry e; > > --- 2834,2839 ---- > > *************** darwin_asm_output_dwarf_offset (FILE *fi > > *** 2866,2879 **** > > HOST_WIDE_INT offset, section *base) > > { > > char sname[64]; > > ! int namelen; > > > > ! gcc_assert (base->common.flags & SECTION_NAMED); > > ! gcc_assert (strncmp (base->named.name, "__DWARF,", 8) == 0); > > ! gcc_assert (strchr (base->named.name + 8, ',')); > > ! > > ! namelen = strchr (base->named.name + 8, ',') - (base->named.name + 8); > > ! sprintf (sname, "*Lsection%.*s", namelen, base->named.name + 8); > > darwin_asm_output_dwarf_delta (file, size, lab, sname, offset); > > } > > > > --- 2886,2909 ---- > > HOST_WIDE_INT offset, section *base) > > { > > char sname[64]; > > ! int namelen, extra = 0; > > ! bool is_for_lto; > > ! const char *lto_add = ""; > > ! > > ! gcc_checking_assert (base->common.flags & SECTION_NAMED); > > ! is_for_lto = strncmp (base->named.name, "__GNU_DWARF_LTO,", 16) == 0; > > ! gcc_checking_assert (is_for_lto > > ! || strncmp (base->named.name, "__DWARF,", 8) == 0); > > ! const char *name = strchr (base->named.name, ',') + 1; > > ! gcc_checking_assert (name); > > > > ! namelen = strchr (name, ',') - (name); > > ! if (is_for_lto) > > ! { > > ! lto_add = "_lto"; > > ! extra = 4; > > ! } > > ! snprintf (sname, 64, "*Lsection%.*s%.*s", namelen, name, extra, > > lto_add); > > darwin_asm_output_dwarf_delta (file, size, lab, sname, offset); > > } > > > > Index: early-lto-debug/gcc/config/darwin.h > > =================================================================== > > *** early-lto-debug.orig/gcc/config/darwin.h 2017-05-16 > > 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/config/darwin.h 2017-05-16 13:10:49.866240867 > > +0200 > > *************** extern GTY(()) int darwin_ms_struct; > > *** 445,451 **** > > #define DEBUG_PUBTYPES_SECTION "__DWARF,__debug_pubtypes,regular,debug" > > #define DEBUG_STR_SECTION "__DWARF,__debug_str,regular,debug" > > #define DEBUG_RANGES_SECTION "__DWARF,__debug_ranges,regular,debug" > > ! #define DEBUG_MACRO_SECTION "__DWARF,__debug_macro,regular,debug" > > > > #define TARGET_WANT_DEBUG_PUB_SECTIONS true > > > > --- 445,458 ---- > > #define DEBUG_PUBTYPES_SECTION "__DWARF,__debug_pubtypes,regular,debug" > > #define DEBUG_STR_SECTION "__DWARF,__debug_str,regular,debug" > > #define DEBUG_RANGES_SECTION "__DWARF,__debug_ranges,regular,debug" > > ! #define DEBUG_MACRO_SECTION "__DWARF,__debug_macro,regular,debug" > > ! > > ! #define DEBUG_LTO_INFO_SECTION > > "__GNU_DWARF_LTO,__debug_info,regular,debug" > > ! #define DEBUG_LTO_ABBREV_SECTION > > "__GNU_DWARF_LTO,__debug_abbrev,regular,debug" > > ! #define DEBUG_LTO_MACINFO_SECTION > > "__GNU_DWARF_LTO,__debug_macinfo,regular,debug" > > ! #define DEBUG_LTO_LINE_SECTION > > "__GNU_DWARF_LTO,__debug_line,regular,debug" > > ! #define DEBUG_LTO_STR_SECTION > > "__GNU_DWARF_LTO,__debug_str,regular,debug" > > ! #define DEBUG_LTO_MACRO_SECTION > > "__GNU_DWARF_LTO,__debug_macro,regular,debug" > > > > #define TARGET_WANT_DEBUG_PUB_SECTIONS true > > > > Index: early-lto-debug/gcc/vmsdbgout.c > > =================================================================== > > *** early-lto-debug.orig/gcc/vmsdbgout.c 2017-05-16 13:10:47.554202813 > > +0200 > > --- early-lto-debug/gcc/vmsdbgout.c 2017-05-16 13:10:49.866240867 +0200 > > *************** const struct gcc_debug_hooks vmsdbg_debu > > *** 198,203 **** > > --- 198,205 ---- > > vmsdbgout_late_global_decl, > > vmsdbgout_type_decl, /* type_decl */ > > debug_nothing_tree_tree_tree_bool, /* imported_module_or_decl */ > > + debug_false_tree_charstarstar_uhwistar, /* die_ref_for_decl */ > > + debug_nothing_tree_charstar_uhwi, /* register_external_die */ > > debug_nothing_tree, /* deferred_inline_function */ > > vmsdbgout_abstract_function, > > debug_nothing_rtx_code_label, /* label */ > > Index: early-lto-debug/gcc/tree.c > > =================================================================== > > *** early-lto-debug.orig/gcc/tree.c 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/tree.c 2017-05-16 13:10:49.870240933 +0200 > > *************** free_lang_data (void) > > *** 5974,5979 **** > > --- 5974,5983 ---- > > || (!flag_generate_lto && !flag_generate_offload)) > > return 0; > > > > + /* Provide a dummy TRANSLATION_UNIT_DECL if the FE failed to provide > > one. */ > > + if (vec_safe_is_empty (all_translation_units)) > > + build_translation_unit_decl (NULL_TREE); > > + > > /* Allocate and assign alias sets to the standard integer types > > while the slots are still in the way the frontends generated them. > > */ > > for (i = 0; i < itk_none; ++i) > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/global-overflow-1.c > > =================================================================== > > *** > > early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/global-overflow-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/global-overflow-1.c > > 2017-05-16 13:10:49.870240933 +0200 > > *************** int main() { > > *** 23,28 **** > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread T0.*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*global-overflow-1.c:20|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r).*" > > } */ > > /* { dg-output "0x\[0-9a-f\]+ is located 0 bytes to the right of global > > variable" } */ > > /* { dg-output ".*YYY\[^\n\r]* of size 10\[^\n\r]*(\n|\r\n|\r)" } */ > > --- 23,28 ---- > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread T0.*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*global-overflow-1.c:20|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r).*" > > } */ > > /* { dg-output "0x\[0-9a-f\]+ is located 0 bytes to the right of global > > variable" } */ > > /* { dg-output ".*YYY\[^\n\r]* of size 10\[^\n\r]*(\n|\r\n|\r)" } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/heap-overflow-1.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/heap-overflow-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/heap-overflow-1.c > > 2017-05-16 13:10:49.870240933 +0200 > > *************** int main(int argc, char **argv) { > > *** 24,31 **** > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread T0.*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*heap-overflow-1.c:21|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 0 bytes to the right of > > 10-byte region\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*heap-overflow-1.c:19|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" } > > */ > > --- 24,31 ---- > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread T0.*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*heap-overflow-1.c:21|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 0 bytes to the right of > > 10-byte region\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*heap-overflow-1.c:19|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/misalign-1.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/misalign-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/misalign-1.c > > 2017-05-16 13:10:49.870240933 +0200 > > *************** main () > > *** 39,43 **** > > /* { dg-output "ERROR: AddressSanitizer:\[^\n\r]*on address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*foo(\[^\n\r]*misalign-1.c:1\[01]|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*misalign-1.c:3\[45]|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > --- 39,43 ---- > > /* { dg-output "ERROR: AddressSanitizer:\[^\n\r]*on address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*foo(\[^\n\r]*misalign-1.c:1\[01]|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*misalign-1.c:3\[45]|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/misalign-2.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/misalign-2.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/misalign-2.c > > 2017-05-16 13:10:49.870240933 +0200 > > *************** main () > > *** 39,43 **** > > /* { dg-output "ERROR: AddressSanitizer:\[^\n\r]*on address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*baz(\[^\n\r]*misalign-2.c:2\[23]|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*misalign-2.c:3\[45]|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > --- 39,43 ---- > > /* { dg-output "ERROR: AddressSanitizer:\[^\n\r]*on address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*baz(\[^\n\r]*misalign-2.c:2\[23]|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*misalign-2.c:3\[45]|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/null-deref-1.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/null-deref-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/null-deref-1.c > > 2017-05-16 13:10:49.870240933 +0200 > > *************** int main() > > *** 18,22 **** > > > > /* { dg-output "ERROR: AddressSanitizer:? SEGV on unknown > > address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ \[^\n\r]*pc 0x\[0-9a-f\]+.*(\n|\r\n|\r)" } > > */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in \[^\n\r]*NullDeref\[^\n\r]* > > (\[^\n\r]*null-deref-1.c:10|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*null-deref-1.c:15|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > --- 18,22 ---- > > > > /* { dg-output "ERROR: AddressSanitizer:? SEGV on unknown > > address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ \[^\n\r]*pc 0x\[0-9a-f\]+.*(\n|\r\n|\r)" } > > */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in \[^\n\r]*NullDeref\[^\n\r]* > > (\[^\n\r]*null-deref-1.c:10|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*null-deref-1.c:15|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/stack-overflow-1.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/stack-overflow-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/stack-overflow-1.c > > 2017-05-16 13:10:49.874240999 +0200 > > *************** int main() { > > *** 18,23 **** > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*stack-overflow-1.c:16|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*Address 0x\[0-9a-f\]+ is located in stack of > > thread T0.*(\n|\r\n|\r)" */ > > /* { dg-output "\[^\n\r]*in main.*stack-overflow-1.c.*(\n|\r\n|\r)" */ > > --- 18,23 ---- > > } > > > > /* { dg-output "READ of size 1 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*stack-overflow-1.c:16|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > /* { dg-output "\[^\n\r]*Address 0x\[0-9a-f\]+ is located in stack of > > thread T0.*(\n|\r\n|\r)" */ > > /* { dg-output "\[^\n\r]*in main.*stack-overflow-1.c.*(\n|\r\n|\r)" */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/strncpy-overflow-1.c > > =================================================================== > > *** > > early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/strncpy-overflow-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/strncpy-overflow-1.c > > 2017-05-16 13:10:49.874240999 +0200 > > *************** int main(int argc, char **argv) { > > *** 14,21 **** > > > > /* { dg-output "WRITE of size \[0-9\]* at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)strncpy|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*strncpy-overflow-1.c:11|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 0 bytes to the right of > > 9-byte region\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*strncpy-overflow-1.c:10|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > --- 14,21 ---- > > > > /* { dg-output "WRITE of size \[0-9\]* at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)strncpy|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*strncpy-overflow-1.c:11|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 0 bytes to the right of > > 9-byte region\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*strncpy-overflow-1.c:10|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/c-c++-common/asan/use-after-free-1.c > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/c-c++-common/asan/use-after-free-1.c > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/c-c++-common/asan/use-after-free-1.c > > 2017-05-16 13:10:49.874240999 +0200 > > *************** int main() { > > *** 12,22 **** > > /* { dg-output "ERROR: AddressSanitizer:? heap-use-after-free on > > address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 1 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:9|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 5 bytes inside of > > 10-byte region .0x\[0-9a-f\]+,0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*freed by thread T0 here:\[^\n\r]*(\n|\r\n|\r)" } > > */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)free|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:8|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*previously allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:7|\[^\n\r]*:0)|\[(\])\[^\n\r]*(\n|\r\n|\r)" } > > */ > > --- 12,22 ---- > > /* { dg-output "ERROR: AddressSanitizer:? heap-use-after-free on > > address\[^\n\r]*" } */ > > /* { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*READ of size 1 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #0 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:9|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > /* { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 5 bytes inside of > > 10-byte region .0x\[0-9a-f\]+,0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output "\[^\n\r]*freed by thread T0 here:\[^\n\r]*(\n|\r\n|\r)" } > > */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)free|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:8|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } */ > > /* { dg-output "\[^\n\r]*previously allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } */ > > /* { dg-output " #0 0x\[0-9a-f\]+ +(in > > _*(interceptor_|wrap_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } */ > > ! /* { dg-output " #1 0x\[0-9a-f\]+ +(in _*main > > (\[^\n\r]*use-after-free-1.c:7|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\])\[^\n\r]*(\n|\r\n|\r)" > > } */ > > Index: early-lto-debug/gcc/testsuite/g++.dg/asan/large-func-test-1.C > > =================================================================== > > *** early-lto-debug.orig/gcc/testsuite/g++.dg/asan/large-func-test-1.C > > 2017-05-16 13:10:47.554202813 +0200 > > --- early-lto-debug/gcc/testsuite/g++.dg/asan/large-func-test-1.C > > 2017-05-16 13:10:49.874240999 +0200 > > *************** int main() { > > *** 38,44 **** > > // { dg-output "ERROR: AddressSanitizer:? heap-buffer-overflow on > > address\[^\n\r]*" } > > // { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } > > // { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } > > ! // { dg-output " #0 0x\[0-9a-f\]+ +(in > > \[^\n\r]*LargeFunction\[^\n\r]*(large-func-test-1.C:18|\[^\n\r]*:0)|\[(\]).*(\n|\r\n|\r)" > > } > > // { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 44 bytes to the right > > of 400-byte region.*(\n|\r\n|\r)" } > > // { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } > > // { dg-output " #0( 0x\[0-9a-f\]+ +(in > > _*(interceptor_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } > > --- 38,44 ---- > > // { dg-output "ERROR: AddressSanitizer:? heap-buffer-overflow on > > address\[^\n\r]*" } > > // { dg-output "0x\[0-9a-f\]+ at pc 0x\[0-9a-f\]+ bp 0x\[0-9a-f\]+ sp > > 0x\[0-9a-f\]+\[^\n\r]*(\n|\r\n|\r)" } > > // { dg-output "\[^\n\r]*READ of size 4 at 0x\[0-9a-f\]+ thread > > T0\[^\n\r]*(\n|\r\n|\r)" } > > ! // { dg-output " #0 0x\[0-9a-f\]+ +(in > > \[^\n\r]*LargeFunction\[^\n\r]*(large-func-test-1.C:18|\[^\n\r]*:0|\[^\n\r]*\\+0x\[0-9a-z\]*)|\[(\]).*(\n|\r\n|\r)" > > } > > // { dg-output "\[^\n\r]*0x\[0-9a-f\]+ is located 44 bytes to the right > > of 400-byte region.*(\n|\r\n|\r)" } > > // { dg-output "\[^\n\r]*allocated by thread T0 > > here:\[^\n\r]*(\n|\r\n|\r)" } > > // { dg-output " #0( 0x\[0-9a-f\]+ +(in > > _*(interceptor_|)malloc|\[(\])\[^\n\r]*(\n|\r\n|\r)" } > > Index: > > early-lto-debug/libstdc++-v3/testsuite/libstdc++-prettyprinters/prettyprinters.exp > > =================================================================== > > *** > > early-lto-debug.orig/libstdc++-v3/testsuite/libstdc++-prettyprinters/prettyprinters.exp > > 2017-05-16 13:10:47.554202813 +0200 > > --- > > early-lto-debug/libstdc++-v3/testsuite/libstdc++-prettyprinters/prettyprinters.exp > > 2017-05-16 13:10:49.874240999 +0200 > > *************** > > *** 15,20 **** > > --- 15,21 ---- > > # <http://www.gnu.org/licenses/>. > > > > load_lib gdb-test.exp > > + load_lib target-supports.exp > > > > dg-init > > v3-build_support > > *************** global PCH_CXXFLAGS > > *** 46,51 **** > > --- 47,60 ---- > > gdb-dg-runtest [lsort [glob $srcdir/$subdir/*.cc]] \ > > "" "$DEFAULT_CXXFLAGS $PCH_CXXFLAGS" > > > > + if { [check_effective_target_lto] } { > > + append cxxflags " -flto" > > + # work around sourceware.org 20882 > > + regsub {^(.*)-Wl,--gc-sections(.*)$} $cxxldflags {\1\2} cxxldflags > > + gdb-dg-runtest [lsort [glob $srcdir/$subdir/*.cc]] \ > > + "" "$DEFAULT_CXXFLAGS -flto $PCH_CXXFLAGS" > > + } > > + > > if [info exists guality_gdb_name] { > > unsetenv GUALITY_GDB_NAME > > } > > Index: early-lto-debug/gcc/testsuite/gfortran.dg/save_6.f90 > > =================================================================== > > *** /dev/null 1970-01-01 00:00:00.000000000 +0000 > > --- early-lto-debug/gcc/testsuite/gfortran.dg/save_6.f90 2017-05-18 > > 09:39:31.394914888 +0200 > > *************** > > *** 0 **** > > --- 1,54 ---- > > + ! { dg-do run } > > + ! { dg-require-effective-target lto } > > + ! { dg-options "-fno-automatic -flto -g" } > > + ! > > + ! PR fortran/55733 > > + ! > > + ! Check that -fno-automatic makes the local variable SAVEd > > + ! Check that -flto -g works > > + ! > > + > > + ! Scalar allocatable > > + subroutine foo(i) > > + integer :: i > > + integer, allocatable :: j > > + if (i == 1) j = 42 > > + if (.not. allocated (j)) call abort () > > + if (j /= 42) call abort () > > + end > > + > > + ! Deferred-length string scalar > > + subroutine bar() > > + logical, save :: first = .true. > > + character(len=:), allocatable :: str > > + if (first) then > > + first = .false. > > + if (allocated (str)) call abort () > > + str = "ABCDEF" > > + end if > > + if (.not. allocated (str)) call abort () > > + if (len (str) /= 6) call abort () > > + if (str(1:6) /= "ABCDEF") call abort () > > + end subroutine bar > > + > > + ! Deferred-length string array > > + subroutine bar_array() > > + logical, save :: first = .true. > > + character(len=:), allocatable :: str > > + if (first) then > > + first = .false. > > + if (allocated (str)) call abort () > > + str = "ABCDEF" > > + end if > > + if (.not. allocated (str)) call abort () > > + if (len (str) /= 6) call abort () > > + if (str(1:6) /= "ABCDEF") call abort () > > + end subroutine bar_array > > + > > + call foo(1) > > + call foo(2) > > + call bar() > > + call bar_array() > > + call bar() > > + call bar_array() > > + end > > Index: early-lto-debug/gcc/config/i386/i386.c > > =================================================================== > > *** early-lto-debug.orig/gcc/config/i386/i386.c 2017-05-15 > > 10:57:19.923567540 +0200 > > --- early-lto-debug/gcc/config/i386/i386.c 2017-05-19 11:27:19.565373271 > > +0200 > > *************** make_resolver_func (const tree default_d > > *** 33840,33846 **** > > DECL_NAME (decl) = decl_name; > > TREE_USED (decl) = 1; > > DECL_ARTIFICIAL (decl) = 1; > > ! DECL_IGNORED_P (decl) = 0; > > /* IFUNC resolvers have to be externally visible. */ > > TREE_PUBLIC (decl) = 1; > > DECL_UNINLINABLE (decl) = 1; > > --- 33840,33846 ---- > > DECL_NAME (decl) = decl_name; > > TREE_USED (decl) = 1; > > DECL_ARTIFICIAL (decl) = 1; > > ! DECL_IGNORED_P (decl) = 1; > > /* IFUNC resolvers have to be externally visible. */ > > TREE_PUBLIC (decl) = 1; > > DECL_UNINLINABLE (decl) = 1; > > > > -- Richard Biener <rguent...@suse.de> SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)