From 567238c956c4e5530bd143bfae9393c7ae5524cd Mon Sep 17 00:00:00 2001 From: Kevin Buettner Date: Wed, 3 Jul 2019 17:32:21 -0700 Subject: [PATCH] Prefer symtab symbol over minsym for function names in non-contiguous blocks The discussion on gdb-patches which led to this patch may be found here: https://www.sourceware.org/ml/gdb-patches/2019-05/msg00018.html Here's a brief synopsis/analysis: Eli Zaretskii, while debugging a Windows emacs executable, found that functions comprised of more than one (non-contiguous) address range were not being displayed correctly in a backtrace. This is the example that Eli provided: (gdb) bt #0 0x76a63227 in KERNELBASE!DebugBreak () from C:\Windows\syswow64\KernelBase.dll #1 0x012e7b89 in emacs_abort () at w32fns.c:10768 #2 0x012e1f3b in print_vectorlike.cold () at print.c:1824 #3 0x011d2dec in print_object (obj=, printcharfun=XIL(0), escapeflag=true) at print.c:2150 The function print_vectorlike consists of two address ranges, one of which contains "cold" code which is expected to not execute very often. There is a minimal symbol, print_vectorlike.cold.65, which is the address of the "cold" range. GDB is prefering this minsym over the the name provided by the DWARF info due to some really old code in GDB which handles "certain pathological cases". This comment reads as follows: /* In certain pathological cases, the symtabs give the wrong function (when we are in the first function in a file which is compiled without debugging symbols, the previous function is compiled with debugging symbols, and the "foo.o" symbol that is supposed to tell us where the file with debugging symbols ends has been truncated by ar because it is longer than 15 characters). This also occurs if the user uses asm() to create a function but not stabs for it (in a file compiled with -g). So look in the minimal symbol tables as well, and if it comes up with a larger address for the function use that instead. I don't think this can ever cause any problems; there shouldn't be any minimal symbols in the middle of a function; if this is ever changed many parts of GDB will need to be changed (and we'll create a find_pc_minimal_function or some such). */ In an earlier version of this patch, I had left the code for the pathological case intact, but those who reviwed that patch recommended removing it. So that's what I've done - I've removed it. gdb/ChangeLog: * stack.c (find_frame_funname): Remove code which preferred minsym over symtab sym in "certain pathological cases". --- gdb/ChangeLog | 5 ++++ gdb/stack.c | 71 +++++++++++---------------------------------------- 2 files changed, 20 insertions(+), 56 deletions(-) diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 7a01b8f3cc6..7d6ef1aae2f 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,8 @@ +2019-07-27 Kevin Buettner + + * stack.c (find_frame_funname): Remove code which preferred + minsym over symtab sym in "certain pathological cases". + 2019-07-26 Brian Callahan PR gdb/24839: diff --git a/gdb/stack.c b/gdb/stack.c index 959ae652ec2..06f10a1c3e9 100644 --- a/gdb/stack.c +++ b/gdb/stack.c @@ -1135,66 +1135,25 @@ find_frame_funname (struct frame_info *frame, enum language *funlang, func = get_frame_function (frame); if (func) { - /* In certain pathological cases, the symtabs give the wrong - function (when we are in the first function in a file which - is compiled without debugging symbols, the previous function - is compiled with debugging symbols, and the "foo.o" symbol - that is supposed to tell us where the file with debugging - symbols ends has been truncated by ar because it is longer - than 15 characters). This also occurs if the user uses asm() - to create a function but not stabs for it (in a file compiled - with -g). - - So look in the minimal symbol tables as well, and if it comes - up with a larger address for the function use that instead. - I don't think this can ever cause any problems; there - shouldn't be any minimal symbols in the middle of a function; - if this is ever changed many parts of GDB will need to be - changed (and we'll create a find_pc_minimal_function or some - such). */ + const char *print_name = SYMBOL_PRINT_NAME (func); - struct bound_minimal_symbol msymbol; - - /* Don't attempt to do this for inlined functions, which do not - have a corresponding minimal symbol. */ - if (!block_inlined_p (SYMBOL_BLOCK_VALUE (func))) - msymbol - = lookup_minimal_symbol_by_pc (get_frame_address_in_block (frame)); - else - memset (&msymbol, 0, sizeof (msymbol)); - - if (msymbol.minsym != NULL - && (BMSYMBOL_VALUE_ADDRESS (msymbol) - > BLOCK_ENTRY_PC (SYMBOL_BLOCK_VALUE (func)))) + *funlang = SYMBOL_LANGUAGE (func); + if (funcp) + *funcp = func; + if (*funlang == language_cplus) { - /* We also don't know anything about the function besides - its address and name. */ - func = 0; - funname.reset (xstrdup (MSYMBOL_PRINT_NAME (msymbol.minsym))); - *funlang = MSYMBOL_LANGUAGE (msymbol.minsym); + /* It seems appropriate to use SYMBOL_PRINT_NAME() here, + to display the demangled name that we already have + stored in the symbol table, but we stored a version + with DMGL_PARAMS turned on, and here we don't want to + display parameters. So remove the parameters. */ + funname = cp_remove_params (print_name); } - else - { - const char *print_name = SYMBOL_PRINT_NAME (func); - *funlang = SYMBOL_LANGUAGE (func); - if (funcp) - *funcp = func; - if (*funlang == language_cplus) - { - /* It seems appropriate to use SYMBOL_PRINT_NAME() here, - to display the demangled name that we already have - stored in the symbol table, but we stored a version - with DMGL_PARAMS turned on, and here we don't want to - display parameters. So remove the parameters. */ - funname = cp_remove_params (print_name); - } - - /* If we didn't hit the C++ case above, set *funname - here. */ - if (funname == NULL) - funname.reset (xstrdup (print_name)); - } + /* If we didn't hit the C++ case above, set *funname + here. */ + if (funname == NULL) + funname.reset (xstrdup (print_name)); } else { -- 2.30.2