public inbox for gdb@sourceware.org
 help / color / mirror / Atom feed
* Dwarf unwinder problems with store.exp and preserved regs
@ 2003-07-01 21:44 Daniel Jacobowitz
  2003-07-02  6:38 ` Andreas Jaeger
  2003-07-02 19:11 ` Richard Henderson
  0 siblings, 2 replies; 6+ messages in thread
From: Daniel Jacobowitz @ 2003-07-01 21:44 UTC (permalink / raw)
  To: gdb

I see two kinds of failures in store.exp right now, on the two targets I'm
testing.  On i386, with DWARF 2 unwinding, I see spurious <value optimized
out> messages; and on ARM (without DWARF 2 unwinding) I see legitimately
corrupted values.  The latter are easy, so I'll send a patch momentarily. 
The former are more interesting.

Here's the problem: the unwinder does not know what registers are considered
call saved.  GDB reads some initial CIE unwind information from the debug
file:

  /* Instruction sequence to initialize a register set.  */
  unsigned char *initial_instructions;

  /* True if a 'z' augmentation existed.  */
  unsigned char saw_z_augmentation;

      cie->saw_z_augmentation = (*augmentation == 'z');
      if (cie->saw_z_augmentation)
        {
          ULONGEST length;

          length = read_unsigned_leb128 (unit->abfd, buf, &bytes_read);
          buf += bytes_read;
          cie->initial_instructions = buf + length;
          augmentation++;
        }

However, GCC only emits information about the CFA, not about the default
saved-ness of registers.  So we get:

168       /* Initialize newly allocated registers.  */
169       memset (rs->reg + rs->num_regs, 0, (num_regs - rs->num_regs) * size);

And 0 is UNDEFINED.  So $ebx - a call-saved register on i386 - shows up as
undefined.

There are two things we can do about this, I think, and perhaps we should
do both:
  - Fix GCC.  I -believe-, from reading the spec, that GCC is to blame for
    not emiting this information.
  - Provide an architecture method to pre-initialize the register table
    before initial_instructions is evaluated.

Thoughts?
-- 
Daniel Jacobowitz
MontaVista Software                         Debian GNU/Linux Developer

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: Dwarf unwinder problems with store.exp and preserved regs
  2003-07-01 21:44 Dwarf unwinder problems with store.exp and preserved regs Daniel Jacobowitz
@ 2003-07-02  6:38 ` Andreas Jaeger
  2003-07-02 19:11 ` Richard Henderson
  1 sibling, 0 replies; 6+ messages in thread
From: Andreas Jaeger @ 2003-07-02  6:38 UTC (permalink / raw)
  To: gdb; +Cc: Josef Zlomek

Daniel Jacobowitz <drow@mvista.com> writes:

> I see two kinds of failures in store.exp right now, on the two targets I'm
> testing.  On i386, with DWARF 2 unwinding, I see spurious <value optimized
> out> messages; and on ARM (without DWARF 2 unwinding) I see legitimately
> corrupted values.  The latter are easy, so I'll send a patch momentarily. 
> The former are more interesting.

I see the same problem on x86-64 with the <value optimized out> messages.

> Here's the problem: the unwinder does not know what registers are considered
> call saved.  GDB reads some initial CIE unwind information from the debug
> file:
>
>   /* Instruction sequence to initialize a register set.  */
>   unsigned char *initial_instructions;
>
>   /* True if a 'z' augmentation existed.  */
>   unsigned char saw_z_augmentation;
>
>       cie->saw_z_augmentation = (*augmentation == 'z');
>       if (cie->saw_z_augmentation)
>         {
>           ULONGEST length;
>
>           length = read_unsigned_leb128 (unit->abfd, buf, &bytes_read);
>           buf += bytes_read;
>           cie->initial_instructions = buf + length;
>           augmentation++;
>         }
>
> However, GCC only emits information about the CFA, not about the default
> saved-ness of registers.  So we get:
>
> 168       /* Initialize newly allocated registers.  */
> 169       memset (rs->reg + rs->num_regs, 0, (num_regs - rs->num_regs) * size);
>
> And 0 is UNDEFINED.  So $ebx - a call-saved register on i386 - shows up as
> undefined.
>
> There are two things we can do about this, I think, and perhaps we should
> do both:
>   - Fix GCC.  I -believe-, from reading the spec, that GCC is to blame for
>     not emiting this information.
>   - Provide an architecture method to pre-initialize the register table
>     before initial_instructions is evaluated.

I think the later is the way to go - but didn't read the spec fully to
give an authoritative answer,

Andreas
-- 
 Andreas Jaeger, aj@suse.de, http://www.suse.de/~aj
  SuSE Linux AG, Deutschherrnstr. 15-19, 90429 Nürnberg, Germany
   GPG fingerprint = 93A3 365E CE47 B889 DF7F  FED1 389A 563C C272 A126

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: Dwarf unwinder problems with store.exp and preserved regs
  2003-07-01 21:44 Dwarf unwinder problems with store.exp and preserved regs Daniel Jacobowitz
  2003-07-02  6:38 ` Andreas Jaeger
@ 2003-07-02 19:11 ` Richard Henderson
  2003-07-02 19:19   ` Daniel Jacobowitz
  1 sibling, 1 reply; 6+ messages in thread
From: Richard Henderson @ 2003-07-02 19:11 UTC (permalink / raw)
  To: gdb

On Tue, Jul 01, 2003 at 05:44:30PM -0400, Daniel Jacobowitz wrote:
> However, GCC only emits information about the CFA, not about the default
> saved-ness of registers.  So we get:
> 
> 168       /* Initialize newly allocated registers.  */
> 169       memset (rs->reg + rs->num_regs, 0, (num_regs - rs->num_regs) * size);
> 
> And 0 is UNDEFINED.  So $ebx - a call-saved register on i386 - shows up as
> undefined.

I think this is your bug.

>   - Fix GCC.  I -believe-, from reading the spec, that GCC is to blame for
>     not emiting this information.

No, what GCC doesn't provide is clobber information.  It *does* 
provide save information.  GDB should be assuming the register
is valid in the previous frame unless it sees DW_CFA_undefined.

Leastwise, that's certainly what gcc's frame unwinder assumes,
and I don't see anything that contradicts this in the standard.


r~

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: Dwarf unwinder problems with store.exp and preserved regs
  2003-07-02 19:11 ` Richard Henderson
@ 2003-07-02 19:19   ` Daniel Jacobowitz
  2003-07-02 21:33     ` Richard Henderson
  0 siblings, 1 reply; 6+ messages in thread
From: Daniel Jacobowitz @ 2003-07-02 19:19 UTC (permalink / raw)
  To: Richard Henderson; +Cc: gdb

On Wed, Jul 02, 2003 at 12:10:59PM -0700, Richard Henderson wrote:
> On Tue, Jul 01, 2003 at 05:44:30PM -0400, Daniel Jacobowitz wrote:
> > However, GCC only emits information about the CFA, not about the default
> > saved-ness of registers.  So we get:
> > 
> > 168       /* Initialize newly allocated registers.  */
> > 169       memset (rs->reg + rs->num_regs, 0, (num_regs - rs->num_regs) * size);
> > 
> > And 0 is UNDEFINED.  So $ebx - a call-saved register on i386 - shows up as
> > undefined.
> 
> I think this is your bug.
> 
> >   - Fix GCC.  I -believe-, from reading the spec, that GCC is to blame for
> >     not emiting this information.
> 
> No, what GCC doesn't provide is clobber information.  It *does* 
> provide save information.  GDB should be assuming the register
> is valid in the previous frame unless it sees DW_CFA_undefined.
> 
> Leastwise, that's certainly what gcc's frame unwinder assumes,
> and I don't see anything that contradicts this in the standard.

If we assume that the register is valid in the previous frame, we'll go
back to printing out a lot of garbage.  Consider:

0804833d <add_short>:
 804833d:       55                      push   %ebp
 804833e:       89 e5                   mov    %esp,%ebp
 8048340:       8b 45 08                mov    0x8(%ebp),%eax
 8048343:       8b 55 0c                mov    0xc(%ebp),%edx
 8048346:       89 c1                   mov    %eax,%ecx
 8048348:       89 d0                   mov    %edx,%eax
 804834a:       8d 04 08                lea    (%eax,%ecx,1),%eax
 804834d:       98                      cwtl   
 804834e:       c9                      leave  
 804834f:       c3                      ret    

The CFI for this:
  DW_CFA_advance_loc: 1 to 0804833e
  DW_CFA_def_cfa_offset: 8
  DW_CFA_offset: r5 at cfa-8
  DW_CFA_advance_loc: 2 to 08048340
  DW_CFA_def_cfa_reg: r5

So if the initial row assumes all registers are valid, we'd print out a
value in the caller's $eax incorrectly.  The false negatives will go
away and be replaced by false positives.

This information needs to come from somewhere.  Even if GDB has to
derive it from the ABI.

-- 
Daniel Jacobowitz
MontaVista Software                         Debian GNU/Linux Developer

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: Dwarf unwinder problems with store.exp and preserved regs
  2003-07-02 19:19   ` Daniel Jacobowitz
@ 2003-07-02 21:33     ` Richard Henderson
  2003-07-02 21:39       ` Daniel Jacobowitz
  0 siblings, 1 reply; 6+ messages in thread
From: Richard Henderson @ 2003-07-02 21:33 UTC (permalink / raw)
  To: gdb

On Wed, Jul 02, 2003 at 03:19:07PM -0400, Daniel Jacobowitz wrote:
> So if the initial row assumes all registers are valid, we'd print out a
> value in the caller's $eax incorrectly.

Ok, so?  Except you forget that variables that are live across
that call are either (1) in call saved registers or (2) on the
stack.  So I don't see that the problem will actually affect
folk debugging real programs.

The only time you get a false positive is when the variable is
dead at the call site.  And the results you get there will be
no different than when the variable is dead and the register 
gets re-used /in the same function/ without location expressions
to note the exact time of death.

The best argument, IMO, is that if you switch the default from
undefined to samevalue, then you'll get useful information some
of the time as opposed to none of the time.


r~

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: Dwarf unwinder problems with store.exp and preserved regs
  2003-07-02 21:33     ` Richard Henderson
@ 2003-07-02 21:39       ` Daniel Jacobowitz
  0 siblings, 0 replies; 6+ messages in thread
From: Daniel Jacobowitz @ 2003-07-02 21:39 UTC (permalink / raw)
  To: gdb

On Wed, Jul 02, 2003 at 02:33:11PM -0700, Richard Henderson wrote:
> On Wed, Jul 02, 2003 at 03:19:07PM -0400, Daniel Jacobowitz wrote:
> > So if the initial row assumes all registers are valid, we'd print out a
> > value in the caller's $eax incorrectly.
> 
> Ok, so?  Except you forget that variables that are live across
> that call are either (1) in call saved registers or (2) on the
> stack.  So I don't see that the problem will actually affect
> folk debugging real programs.
> 
> The only time you get a false positive is when the variable is
> dead at the call site.  And the results you get there will be
> no different than when the variable is dead and the register 
> gets re-used /in the same function/ without location expressions
> to note the exact time of death.

We'll have that information someday... but I see your point.

> The best argument, IMO, is that if you switch the default from
> undefined to samevalue, then you'll get useful information some
> of the time as opposed to none of the time.

That's good enough for me.

-- 
Daniel Jacobowitz
MontaVista Software                         Debian GNU/Linux Developer

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2003-07-02 21:39 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2003-07-01 21:44 Dwarf unwinder problems with store.exp and preserved regs Daniel Jacobowitz
2003-07-02  6:38 ` Andreas Jaeger
2003-07-02 19:11 ` Richard Henderson
2003-07-02 19:19   ` Daniel Jacobowitz
2003-07-02 21:33     ` Richard Henderson
2003-07-02 21:39       ` Daniel Jacobowitz

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).