Compile this with -g: struct K { K () { } ~K () { } int m () { return 5; } }; K k; If you run 'readelf -wi' on it, you will see that 'm' has a linkage name: <2><66>: Abbrev Number: 5 (DW_TAG_subprogram) <67> DW_AT_external : 1 <68> DW_AT_name : m <6a> DW_AT_decl_file : 1 <6b> DW_AT_decl_line : 6 <6c> DW_AT_MIPS_linkage_name: (indirect string, offset: 0x76): _ZN1K1mEv However, the constructors and destructor do not.
My guess is that's because there is no single symbol for them, but two or three.
The candidate patch below might do what you want. Note that, constructors/destructor functions are cloned. The cloning process yields a DIE tree. So the destructor K::~K is represented by an abstract function DIE. There is then a concrete function DIE (let's call it 'foo'), that would effectively contain the code of K::~K, and which DW_AT_abstract_origin points to the DIE of the abstract function. It's for 'foo' that the patch below emits the linkage name. Is this enough for your need? diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index 55453a3..c49f90a 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -19601,6 +19601,7 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) dw_die_ref old_die = lookup_decl_die (decl); int declaration = (current_function_decl != decl || class_or_namespace_scope_p (context_die)); + bool fn_has_code_addr_p = false; premark_used_types (); @@ -19769,6 +19770,7 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) /* We have already generated the labels. */ add_AT_lbl_id (subr_die, DW_AT_low_pc, fde->dw_fde_begin); add_AT_lbl_id (subr_die, DW_AT_high_pc, fde->dw_fde_end); + fn_has_code_addr_p = true; } else { @@ -19780,6 +19782,7 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) ASM_GENERATE_INTERNAL_LABEL (label_id, FUNC_END_LABEL, current_function_funcdef_no); add_AT_lbl_id (subr_die, DW_AT_high_pc, label_id); + fn_has_code_addr_p = true; } #if VMS_DEBUGGING_INFO @@ -19928,7 +19931,15 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) if (cfun->static_chain_decl) add_AT_location_description (subr_die, DW_AT_static_link, - loc_list_from_tree (cfun->static_chain_decl, 2)); + loc_list_from_tree (cfun->static_chain_decl, 2)); + + if (fn_has_code_addr_p && origin && TREE_PUBLIC (origin)) + /* So this is where the actual code for a publicly accessible + cloned function is. Let's emit linkage name attribute for + it. This helps debuggers to e.g, set breakpoints into + constructors/destructors when the user asks "break + K::K". */ + add_linkage_name (subr_die, decl); } /* Generate child dies for template paramaters. */
I tried this patch on a simple example and I think the output looks good.
A candidate patch was posted to http://gcc.gnu.org/ml/gcc-patches/2011-05/msg02044.html
Author: dodji Date: Tue May 31 12:09:06 2011 New Revision: 174472 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=174472 Log: Fix PR debug/49047 gcc/ * dwarf2out.c (gen_subprogram_die): Emit linkage name attribute for concrete functions containing the code of cloned functions. gcc/testsuite/ * g++.dg/debug/dwarf2/cdtor-1.C: New test. Added: trunk/gcc/testsuite/g++.dg/debug/dwarf2/cdtor-1.C Modified: trunk/gcc/ChangeLog trunk/gcc/dwarf2out.c trunk/gcc/testsuite/ChangeLog
Author: dodji Date: Tue May 31 12:17:06 2011 New Revision: 174473 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=174473 Log: Revert "Fix PR debug/49047" This reverts commit ce20032a8ad4d9d4fa37192e2ecc73cb257094e8. Added: trunk/libjava/sysdep/x86-64/locks.h - copied, changed from r174472, trunk/libjava/sysdep/i386/locks.h Removed: trunk/gcc/testsuite/g++.dg/debug/dwarf2/cdtor-1.C Modified: trunk/gcc/ChangeLog trunk/gcc/dwarf2out.c trunk/gcc/testsuite/ChangeLog trunk/libjava/ChangeLog trunk/libjava/configure.host trunk/libjava/sysdep/i386/locks.h
Author: dodji Date: Tue May 31 12:17:21 2011 New Revision: 174474 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=174474 Log: Fix PR debug/49047 gcc/ * dwarf2out.c (gen_subprogram_die): Emit linkage name attribute for concrete functions containing the code of cloned functions. gcc/testsuite/ * g++.dg/debug/dwarf2/cdtor-1.C: New test. Added: trunk/gcc/testsuite/g++.dg/debug/dwarf2/cdtor-1.C Modified: trunk/gcc/ChangeLog trunk/gcc/dwarf2out.c trunk/gcc/testsuite/ChangeLog
Fixed in trunk (4.7)