[PATCH] Program Breakpoints

Ross Morley ross@tensilica.com
Sat Apr 18 01:33:00 GMT 2009


Hello GDB reviewers,

This is the result of the RFC discussion on the GDB list late March.
I have simplified and updated the feature as discussed. In addition
I have supported it in gdbserver (only the Xtensa target so far).
In gdb and gdbserver, target support is optional, and targets that
do not support it behave as before. User guide updates are included.

*** A patch is submitted for your review (attached). ***

A detailed discussion follows...

A "program breakpoint" is a trap instruction inherent to the target
program and unknown to GDB. It is like a permanent breakpoint except:
- it is unknown to GDB (not in the breakpoint table).
- it need not be the same instruction used by GDB for breakpoints.

Here is the current behavior this patch fixes:

GDB cannot distinguish a SIGTRAP due to a trap instruction in the
program from one due to single stepping (or other reasons). Breakpoints
are recognized only if they are known to (and usually planted by) GDB.
A trap instruction inherent in the target program is not recognized.
If the target hits one during normal run, GDB receives a SIGTRAP and
sees it as a random signal, reports SIGTRAP and (fortuituously) stops.
If this happens during stepping, GDB assumes the SIGTRAP is from a
single-step and keeps going, repeatedly hitting the trap. A user using
software watchpoints expects slow exection, so may wait a long time
before suspecting a problem, only to find out GDB is hung.

Here's a description of the feature and the reasons for it:

A new target.h macro is provided to allow GDB to determine that it
was stopped by a trap instruction: STOPPED_BY_TRAP_INSTRUCTION(size).
The optional size parameter is a pointer into which the size of the
instruction is written if the PC is pointing to it, allowing GDB to
skip it on resume or step. Targets that implement this recognize
program breakpoints by knowing they hit a trap that is not in the
breakpoint table. A GDB planted breakpoint always takes precedence
over a program breakpoint (in fact GDB might plant a breakpoint
over a program breakpoint). I have only implemented it for the
(remote) targets we support.

Any target may implement this macro, receiving information from the
inferior or probing the instruction in memory, as appropriate. For
remote targets it is usually much more efficient to have the target
communicate that it hit a trap instruction (especially since some
targets may modify the PC to back out of an exception handler the
trap is used in, leaving GDB no way to know directly).

Remote targets may notify GDB of hitting a trap instruction by an
extension to the stop-reply packet for SIGTRAP: "TAAtrap:r", where
r is a single digit representing the size of the trap instruction
if and only if the PC is pointing to it (it needs to be skipped).
That result is passed to infrun and infcmd via the macro above.
Note that the remote target is not expected to distinguish a
program breakpoint from a GDB-planted software breakpoint (that
distinction is made in infrun by looking up the breakpoint table).

When GDB detects a program breakpoint (even while stepping) it
stops and reports it to both CLI and MI. When stopped by one (and
if the PC has not been altered while stopped), on resume or step
GDB will step over it by incrementing the PC by the size (if != 0).
In the case of step-instruction where PC points to the trap, the
first step does not actually run the inferior but merely increments
the PC, simulating the expected advance of 1 instruction.

gdbserver has been modified to recognize a trap as distinct from
a single step, and pass the information from the low target up
to the remote interface. The target must support this for the
information to be passed to GDB via the stop-reply extension.

This has been implemented and well tested in Xtensa toolchains
with the Xtensa instruction set simulator as the target agent.
It has now also been tested with gdbserver on Xtensa. No other
targets yet implement this.

The user manual has been updated. I will update the internals
manual after this patch has been (possibly changed and) accepted.

We have a target specific regression test internally. However I
don't know how to make a generic test case because it needs to
embed an arch-specific trap instruction with an __asm__ construct.
Advice on this would be appreciated. We could submit the test as
a target or arch specific test.

In merging from our GDB 6.8 based internal source base (on which
our extensive testing was done) to the CVS head, I had to merge
with non-stop thread support and reverse debugging. I believe
I have handled those correctly, but have no target to test them
on. I hope someone can integrate this patch and run all the
regressions to make sure I didn't break anything.

Thanks and best regards,
Ross

--
Ross Morley
ross@tensilica.com
ross@computer.org


-------------- next part --------------
A non-text attachment was scrubbed...
Name: program-breakpoints-20090417.diff
Type: text/x-patch
Size: 28711 bytes
Desc: not available
URL: <http://sourceware.org/pipermail/gdb-patches/attachments/20090418/a61e3748/attachment.bin>


More information about the Gdb-patches mailing list