[PATCH] - Accept optional printed address at function breakpoints

Fred Fish fnf@public.ninemoons.com
Mon Dec 8 16:25:00 GMT 2003


I decided to investigate the following failure in funcargs.exp:

  FAIL: gdb.base/funcargs.exp: continue to call6k

The problem can reproduced using:

  void foo ()
  {
  }

  void bar ()
  {
    static int dummy = 0;
  }

  main ()
  {
    foo ();
    bar ();
  }

Using x86 native gdb:

  $ gcc -g -o x x.c
  $ gdb -nw -nx x
  GNU gdb 2003-12-07-cvs
  Copyright 2003 Free Software Foundation, Inc.
  GDB is free software, covered by the GNU General Public License, and you are
  welcome to change it and/or distribute copies of it under certain conditions.
  Type "show copying" to see the conditions.
  There is absolutely no warranty for GDB.  Type "show warranty" for details.
  This GDB was configured as "i686-pc-linux-gnu"...Using host libthread_db library "/lib/tls/libthread_db.so.1".
  
  (gdb) br foo
  Breakpoint 1 at 0x8048327: file x.c, line 2.
  (gdb) br bar
  Breakpoint 2 at 0x804832c: file x.c, line 8.
  (gdb) run
  Starting program: /links3/build/sourceware/gdb/T-i686-pc-linux-gnu/gdb/x 
  
  Breakpoint 1, 0x08048327 in foo () at x.c:2
  2       {
  (gdb) x/i $pc
  0x8048327 <foo+3>:      pop    %ebp
  (gdb) c
  Continuing.
  
  Breakpoint 2, bar () at x.c:8
  8       }
  (gdb) x/i $pc
  0x804832c <bar+3>:      pop    %ebp
  (gdb) 

There are two things to note from the above run:

  (1) Both functions stop at the same relative position in each of
  foo() and bar().  Gdb is smart enough to break at the first 
  instruction after the prologue.

  (2) The breakpoint message for bar() does NOT include an address,
  while the one for foo() does contain an address.

These messages are tested in lib/gdb.exp with:

  proc gdb_continue { function } {
    global decimal

    return [gdb_test "continue" ".*Breakpoint $decimal, $function .*" "continue to $function"];
  }

which does NOT allow any address in the breakpoint message.

If you disassemble the object file you can see the problem:

  00000000 <foo>:
  foo():
  /build/sourceware/gdb/T-i686-pc-linux-gnu/gdb/x.c:2
     0:   55                      push   %ebp
     1:   89 e5                   mov    %esp,%ebp
     3:   5d                      pop    %ebp
     4:   c3                      ret    
  
  00000005 <bar>:
  bar():
  /build/sourceware/gdb/T-i686-pc-linux-gnu/gdb/x.c:6
     5:   55                      push   %ebp
     6:   89 e5                   mov    %esp,%ebp
  /build/sourceware/gdb/T-i686-pc-linux-gnu/gdb/x.c:8
     8:   5d                      pop    %ebp
     9:   c3                      ret    
  
For the failing case (foo), the entire function body is covered by
just one source line, line number 2.  For the succeeding case (bar)
there are two line numbers, one for the prologue code and one for the
epilogue code.

The documented behavior of gdb is to NOT print the address when it
hits a breakpoint at the first instruction associated with a new source
code line.

It's also interesting to note that the generated code is identical for
both functions, leading to a separate issue (bug?) of why gcc
generates different debug info for the two functions.

If we punt on the issue of whether or not the debug info is correct,
this patch fixes the problem.

-Fred

==================================================================

2003-12-08  Fred Fish  <fnf@redhat.com>

	* lib/gdb.exp (gdb_continue): Accept optional address printed
	when stopping at a breakpointed function.
 
Index: lib/gdb.exp
===================================================================
RCS file: /cvs/src/src/gdb/testsuite/lib/gdb.exp,v
retrieving revision 1.41
diff -c -r1.41 gdb.exp
*** lib/gdb.exp	23 Nov 2003 01:09:19 -0000	1.41
--- lib/gdb.exp	8 Dec 2003 16:21:36 -0000
***************
*** 1616,1623 ****
  
  proc gdb_continue { function } {
      global decimal
  
!     return [gdb_test "continue" ".*Breakpoint $decimal, $function .*" "continue to $function"];
  }
  
  proc default_gdb_init { args } {
--- 1616,1624 ----
  
  proc gdb_continue { function } {
      global decimal
+     global hex
  
!     return [gdb_test "continue" ".*Breakpoint $decimal, ($hex in )?$function .*" "continue to $function"];
  }
  
  proc default_gdb_init { args } {



More information about the Gdb-patches mailing list