This is the mail archive of the gdb@sourceware.org mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: GDB 7.4.91 available for testing


On Sun, 2012-07-22 at 19:30 +0200, Jan Kratochvil wrote:
> On Fri, 20 Jul 2012 22:50:09 +0200, Philippe Waroquiers wrote:
> > The tricky part will be to guess that a breakpoint is for the
> > 'return address for an inferior call', as Valgrind is not expected
> > (or allowed) to modify the code sections of the guest client being
> > executed.
> 
> As Z0 should insert the 0xcc instruction this issue of never-modified inferior
> memory needs to be resolved anyway:
Currently, Valgrind does not (and cannot) modify the guest code
(e.g. as the guest code might not be mapped writable). Also, modifying
the guest code for a breakpoint would introduce a lot of difficulties
(e.g. the translated code would have to be dropped and re-translated
when stepping over the breakpoint, and that is currently not possible).

So, breakpoints are implemented in Valgrind by having a helper function
call inserted in the translated code as a "preamble" to the instruction
at which a breakpoint is placed. E.g. the below is the translated code
if there is a break on 0x8048BDA.
   ------ IMark(0x8048BDA, 7, 0) ------ 
   PUT(68) = 0x8048BDA:I32
   DIRTY 1:I1 RdFX-gst(24,4) MoFX-gst(68,4) ::: VG_(helperc_CallDebugger)[rp=1]{0x38072280}(0x8048BDA:I32)
   t7 = GET:I32(376)
   t0 = GET:I32(24)
   ...
The PUT(68) is an assignment to the (virtual) program counter register.
The helperc fn will indicate to GDB that a breakpoint is encountered,
and will read further gdbsrv protocol packets, till a "continue" packet
is received (and then the instructions following the helperc 
are then executed).


> Maybe it would be enough to treat Z0 packets like Z1 (hardware-breakpoint)
> packets?  The valgrind simulator should be able to trap on specified
> addresses, shouldn't it?
Z0 and Z1 packets are handled the same way by Valgrind gdbserver
(see above).
The problem with the above technique is that there is no valid
instruction at the ON_STACK breakpoint address, and the valgrind
translator does not like this.

Implementing breakpoints with "real" trap would imply to
have the Valgrind encoder/decoder to understand the gdbserver breakpoint
concept, which is not ok with regards to software dependencies.

> > For this guess, I am thinking to use the following conditions:
> >     1. the stack pointer in the register cache has been changed
> >        to grow the stack
> >   and
> >     2. the breakpoint address is in this "grown zone" 
> 
> With current default 'set breakpoint always-inserted auto' (acting like 'off')
> GDB continually removes and re-inserts all the breakpoints.  The "grow" check
> will not work on breakpoint re-insertions.

The "grow" check just has to work for the ON_STACK breakpoints
(as the other "normal" breakpoints are supposed to be done at an address
where there is valid code that Valgrind can translate).

The "grow" check is also only done if GDB has modified the stack
pointer register (e.g. using a "P" packet) between the "stop" and
"continue".
So, normal stack growth (during execution) is not taken into account in
this guess.

I just implemented the "grow" check and tested on the x86/amd64/mips
platforms (ppc32/64, s390x and arm seems to be AT_ENTRY_POINT
platforms).

The Valgrind gdbsrv regression tests are now passing with GDB 7.4.91
without error messages, so it looks at least to improve.

The doubt I have is that an inferior function call from GDB
might imply several "low level" calls (e.g. first a call to malloc
to allocate some memory for the argument(s), followed by the
real fn call).
Currently, the guess only works for the first low level call.
But it looks like the next low level call is using the same return
breakpoint address (by chance maybe ?) and so the first guess has
placed a 0xcc at this address, and Valgrind translator is happy.

Is it by chance that successive low level calls (for the same "user
inferior call") are using the same stack address as return address ?

Thanks again for the help/explanations about Z0, I was a little bit
lost in the GDB behaviour

Philippe



Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]