summaryrefslogtreecommitdiff
path: root/gcc/dwarf2out.c
diff options
context:
space:
mode:
authorjakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4>2017-01-26 21:44:49 +0000
committerjakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4>2017-01-26 21:44:49 +0000
commitfbb24ccf676d9d2029bbc293f0634a2ab8c39df7 (patch)
tree1f43f54af8acabd8d284a7ddcd24f5708f9f1963 /gcc/dwarf2out.c
parent425bd7b124fe9800471bb581c0b5fc2f01885363 (diff)
downloadgcc-fbb24ccf676d9d2029bbc293f0634a2ab8c39df7.tar.gz
PR debug/78835
* dwarf2out.c (prune_unused_types): Mark all functions with DIEs which have direct callers with -fvar-tracking-assignments enabled in the current TU. (resolve_addr): Avoid adding skeleton DIEs for DW_AT_call_origin inside of type units. * g++.dg/debug/dwarf2/pr78835.C: New test. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@244954 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/dwarf2out.c')
-rw-r--r--gcc/dwarf2out.c50
1 files changed, 40 insertions, 10 deletions
diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c
index 46565705506..f69c58850f3 100644
--- a/gcc/dwarf2out.c
+++ b/gcc/dwarf2out.c
@@ -27793,6 +27793,25 @@ prune_unused_types (void)
for (i = 0; base_types.iterate (i, &base_type); i++)
prune_unused_types_mark (base_type, 1);
+ /* For -fvar-tracking-assignments, also set the mark on nodes that could be
+ referenced by DW_TAG_call_site DW_AT_call_origin (i.e. direct call
+ callees). */
+ cgraph_node *cnode;
+ FOR_EACH_FUNCTION (cnode)
+ if (cnode->referred_to_p (false))
+ {
+ dw_die_ref die = lookup_decl_die (cnode->decl);
+ if (die == NULL || die->die_mark)
+ continue;
+ for (cgraph_edge *e = cnode->callers; e; e = e->next_caller)
+ if (e->caller != cnode
+ && opt_for_fn (e->caller->decl, flag_var_tracking_assignments))
+ {
+ prune_unused_types_mark (die, 1);
+ break;
+ }
+ }
+
if (debug_str_hash)
debug_str_hash->empty ();
if (skeleton_debug_str_hash)
@@ -28694,16 +28713,27 @@ resolve_addr (dw_die_ref die)
&& DECL_ABSTRACT_ORIGIN (tdecl) == NULL_TREE
&& (cdie = lookup_context_die (DECL_CONTEXT (tdecl))))
{
- /* Creating a full DIE for tdecl is overly expensive and
- at this point even wrong when in the LTO phase
- as it can end up generating new type DIEs we didn't
- output and thus optimize_external_refs will crash. */
- tdie = new_die (DW_TAG_subprogram, cdie, NULL_TREE);
- add_AT_flag (tdie, DW_AT_external, 1);
- add_AT_flag (tdie, DW_AT_declaration, 1);
- add_linkage_attr (tdie, tdecl);
- add_name_and_src_coords_attributes (tdie, tdecl);
- equate_decl_number_to_die (tdecl, tdie);
+ dw_die_ref pdie = cdie;
+ /* Make sure we don't add these DIEs into type units.
+ We could emit skeleton DIEs for context (namespaces,
+ outer structs/classes) and a skeleton DIE for the
+ innermost context with DW_AT_signature pointing to the
+ type unit. See PR78835. */
+ while (pdie && pdie->die_tag != DW_TAG_type_unit)
+ pdie = pdie->die_parent;
+ if (pdie == NULL)
+ {
+ /* Creating a full DIE for tdecl is overly expensive and
+ at this point even wrong when in the LTO phase
+ as it can end up generating new type DIEs we didn't
+ output and thus optimize_external_refs will crash. */
+ tdie = new_die (DW_TAG_subprogram, cdie, NULL_TREE);
+ add_AT_flag (tdie, DW_AT_external, 1);
+ add_AT_flag (tdie, DW_AT_declaration, 1);
+ add_linkage_attr (tdie, tdecl);
+ add_name_and_src_coords_attributes (tdie, tdecl);
+ equate_decl_number_to_die (tdecl, tdie);
+ }
}
if (tdie)
{