Re: Spurious SIGTRAP reported by GDB 6.8 when debugging embedded RTOS application

Antony KING
2008-08-18T17:52:31Z

[-- Attachment #1: Type: text/plain, Size: 1650 bytes --]

I have checked the implementation and GDB is calling my target_resume
with a ptid of -1 (resume all threads), which I believe is the expected
argument (since scheduler locking is not supported). However I think I
will add an error check in my target_resume just in case GDB requests a
single thread to be resumed.

As you state, I think the best course of action for me is to modify GDB.
In order to preserve existing behaviour, I think the best solution is to
modify GDB so that it switches back to the original thread it stopped at
when performing a step operation (i.e. calling proceed() with step = 1).
I have attached my initial solution, which is to modify infcmd.c. This
is not entirely satisfactory as there needs to be some dynamic control
over this logic (so that it can be overridden) plus some input from the
target ops object.

Cheers,

Antony.

Daniel Jacobowitz wrote:
> On Mon, Aug 18, 2008 at 11:20:23AM +0100, Antony KING wrote:
>> Thanks for the explanation. Unfortunately GDB has no influence over the
>> RTOS, it is merely an observer. This means that it cannot change the
>> status of threads or decide which thread is to execute; this is solely
>> under the control of the RTOS.
>
> If GDB has requested a step for a particular thread, and you're
> enabling hardware single step in your stub while another thread is
> current, I think this must be a bug in the stub. It should, at the
> least, report an error instead of continuing.
>
> That said, GDB hasn't been used in this way in a while, though it used
> to support it. I think you'll need to communicate to GDB somehow that
> it can not change the executing thread.

[-- Attachment #2: patch.txt --]
[-- Type: text/plain, Size: 1341 bytes --]

--- gdb/infcmd.c@@/INSIGHT-6.8-ST-1.0 2008-08-12 12:00:00.000000000 +0100
+++ gdb/infcmd.c 2008-08-18 18:18:04.000000000 +0100
@@ -29,6 +29,7 @@
#include "environ.h"
#include "value.h"
#include "gdbcmd.h"
+#include "gdbthread.h"
#include "symfile.h"
#include "gdbcore.h"
#include "target.h"
@@ -653,6 +654,27 @@
proceed ((CORE_ADDR) -1, TARGET_SIGNAL_DEFAULT, 0);
}
\f
+/* Reset to waiting PID. */
+static void
+prepare_to_step (void)
+{
+ ptid_t wait_ptid;
+ struct target_waitstatus wait_status;
+
+ /* Get the last target status returned by target_wait(). */
+ get_last_target_status (&wait_ptid, &wait_status);
+
+ /* Switched over from WAIT_PID. */
+ if (!ptid_equal (wait_ptid, minus_one_ptid)
+ && !ptid_equal (wait_ptid, inferior_ptid))
+ {
+ /* Switch back to WAIT_PID thread. */
+ switch_to_thread (wait_ptid);
+ printf_filtered (_("[Switching to %s]\n"),
+ target_pid_to_str (inferior_ptid));
+ }
+}
+
/* Step until outside of current statement. */

static void
@@ -699,6 +721,8 @@

ERROR_NO_INFERIOR;

+ prepare_to_step ();
+
if (count_string)
async_exec = strip_bg_char (&count_string);

@@ -1057,6 +1081,8 @@
struct symbol *func;
struct symtab_and_line sal;

+ prepare_to_step ();
+
clear_proceed_status ();

frame = get_current_frame ();