[RFC] minimal symbols on mips-irix and overlapping CUs...

Daniel Jacobowitz drow@mvista.com
Mon Nov 17 23:35:00 GMT 2003


On Mon, Nov 17, 2003 at 02:39:26PM -0800, Joel Brobecker wrote:
> Hello,
> 
> we have discovered a problem on mips-irix that had me wondering about
> GDB's assumptions regarding the symbol table. First, the symptoms:
> 
> We have a small Ada program that uses nested procedures. The same can
> be reproduced with a C program if GCC is used (GCC provides nested
> procedures as an extension). Trying to get a backtrace off the nested
> procedure does not work. With our example, we get something like this:
> 
>  #0  main ()
>  #1  0x10013858 in main ()
>  #2  0x100139d0 in gdb_no_local_symbols () at gdb_no_local_symbols.adb:37
>  #3  0x10013574 in main (argc=1, argv=2147430180, envp=2147430188)
>      at b~gdb_no_local_symbols.adb:204
> 
> While the expected backtrace was:
> 
>  #0  gdb_no_local_symbols.proch () at gdb_no_local_symbols.adb:28
>  #1  0x10013858 in gdb_no_local_symbols.procc () at gdb_no_local_symbols.adb:32
>  #2  0x100139d0 in gdb_no_local_symbols () at gdb_no_local_symbols.adb:37
>  #3  0x10013574 in main (argc=1, argv=2147430180, envp=2147430188)
>      at b~gdb_no_local_symbols.adb:204
> 
> The problem, in my opinion, is two-fold:
> 
>   a. The IRIX linker does not include the LOCAL symbols into the symbol
>      table. They are present in the object files, but are stripped from
>      the executable symbol table. This concerns at least nested
>      functions, and static functions as well.

That is a strange behavior, although I suppose it is legal from an ELF
standpoint.  The IRIX linker has... a number of oddities.

>   b. A recent version of the IRIX linker has introduced an extra asm CU
>      (Compilation Unit) named "__sgi_ld_generated_code" which contains
>      one function before CU gdb_local_symbol.adb, and 2 after. So the
>      code range of gdb_local_symbol.adb is included in the code range
>      of the linker CU.

What information does this have - does it have dwarf information or how
else are we finding its code range?

> What happens after GDB stops on the breakpoint and tries to find the
> associated function name is the following:
> 
>   1. In find_pc_sect_symtab(), we search all symtabs for one which
>      code range includes the PC. We find the linker CU, which is the
>      wrong one. But we acknowledge the fact that CUs can overlap,
>      and therefore resort to find_pc_sect_psymtab() to find the correct
>      CU.
> 
>   2. In find_pc_sect_psymtab():
>   
>      a. We first scan the minimal symbols, find "main". We did not find
>         the right function because the linker did not include it into
>         the symbol table.
> 
>      b. Then, we scan all the partial symtabs for the ones which code
>         range include the given address. For all the qualifying ones,
>         we check whether it contains a function which start address
>         matches the minimal symbol address. If yes, then we have found
>         the right symtab. Otherwise, we just return the first partial
>         symtab we found.
> 
> So in our case, we simply end up selecting the linker CU. The GDB later
> realizes that there is no function matching the given PC in the CU we
> selected, it falls back to using the minimal symbol table, and therefore
> ends up declaring that GDB stopped in function main().
> 
> In my opinion, (b) is not a problem, and GDB should be able to handle it
> as long as the symbol table is "complete" (ie as long as (a) does not
> apply). I am inclined to declare this a linker problem, but can this
> really be categorized as a linker problem?
> 
> My general question is the following: Has GDB been designed to assume
> that the symbol table will always be complete? This has always been my
> feeling, but I'm wondering if it wasn't an unwarranted assumption.
> 
> Maybe it's just a hole in find_pc_sect_psymtab() that needs correcting.
> For instance, I am contemplating the idea of tweaking GDB to
> automatically add new "virtual" minimal symbols after having built
> the psymbols using the following approach: Foreach non-type psymbol
> we found, check whether we have a minimal symbol at the same address.
> If not, then we have a missing msymbol, and I therefore add it.

Rather than mesing with the minimal symbol table, we should probably be
correcting the assumption.

Partial symbol tables include function addresses.  find_pc_sect_psymtab
assumes that everything would have a minimal symbol, but we can
probably correct that.  The loop in that function looks quite strange
to me: note that the inner loop uses the same variable, deliberately,
as the outer loop.  Here's a better version of (b):

>      b. Then, we scan all the partial symtabs for the ones which code
>         range include the given address. For all the qualifying ones,
>         we check whether it contains a function which start address
>         matches the minimal symbol address. If yes, then we have found
>         the right symtab. Otherwise, we just return the first partial
>         symtab we found.
							^^^^^^^^^^^^^^
							best match

There's already code in find_pc_sect_psymbol to do this sort of
best-match.  Something similar is needed here, but we need to be
careful of the recursion.  Probably, find_pc_sect_psymtab should build
on find_pc_sect_psymtab rather than the other way around to solve your
problem.

-- 
Daniel Jacobowitz
MontaVista Software                         Debian GNU/Linux Developer



More information about the Gdb-patches mailing list