public inbox for archer-commits@sourceware.org
help / color / mirror / Atom feed
* [SCM] archer-sergiodj-stap: make exception-related breakpoints use stap probes when available this is untested; it needs the probe arguments to work first
@ 2011-02-10 18:42 tromey
0 siblings, 0 replies; only message in thread
From: tromey @ 2011-02-10 18:42 UTC (permalink / raw)
To: archer-commits
The branch, archer-sergiodj-stap has been updated
via 0fec3a3d8f23a141e2647927375981029355ab3f (commit)
from 1b16efd7055bbe6ff5029ecc36df9b8a04704799 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email.
- Log -----------------------------------------------------------------
commit 0fec3a3d8f23a141e2647927375981029355ab3f
Author: Tom Tromey <tromey@redhat.com>
Date: Thu Feb 10 11:41:30 2011 -0700
make exception-related breakpoints use stap probes when available
this is untested; it needs the probe arguments to work first
-----------------------------------------------------------------------
Summary of changes:
gdb/breakpoint.c | 15 +++++++++++
gdb/infrun.c | 75 ++++++++++++++++++++++++++++++++++++++++++++++++------
gdb/stap-probe.c | 67 ++++++++++++++++++++++++++++++++++++-----------
gdb/stap-probe.h | 14 ++++++++++
4 files changed, 147 insertions(+), 24 deletions(-)
First 500 lines of diff:
diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c
index 3c59f11..8390be8 100644
--- a/gdb/breakpoint.c
+++ b/gdb/breakpoint.c
@@ -63,6 +63,7 @@
#include "xml-syscall.h"
#include "parser-defs.h"
#include "gdb_regex.h"
+#include "stap-probe.h"
/* readline include files */
#include "readline/readline.h"
@@ -2269,6 +2270,20 @@ create_exception_master_breakpoint (void)
ALL_OBJFILES (objfile)
{
struct minimal_symbol *debug_hook;
+ const struct stap_probe *probe;
+
+ probe = find_probe_in_objfile (objfile, "libgcc", "unwind");
+ if (probe != NULL)
+ {
+ struct breakpoint *b;
+ struct gdbarch *gdbarch = get_objfile_arch (objfile);
+
+ b = create_internal_breakpoint (gdbarch, probe->address,
+ bp_exception_master);
+ b->addr_string = xstrdup ("probe:libgcc:unwind");
+ b->enable_state = bp_disabled;
+ continue;
+ }
debug_hook = lookup_minimal_symbol ("_Unwind_DebugHook", NULL, objfile);
if (debug_hook != NULL)
diff --git a/gdb/infrun.c b/gdb/infrun.c
index 6fdd9df..8bf8a57 100644
--- a/gdb/infrun.c
+++ b/gdb/infrun.c
@@ -54,6 +54,8 @@
#include "inline-frame.h"
#include "jit.h"
#include "tracepoint.h"
+#include "stap-probe.h"
+#include "objfiles.h"
/* Prototypes for local functions */
@@ -2239,7 +2241,7 @@ static void insert_step_resume_breakpoint_at_sal (struct gdbarch *,
struct frame_id);
static void insert_longjmp_resume_breakpoint (struct gdbarch *, CORE_ADDR);
static void check_exception_resume (struct execution_control_state *,
- struct frame_info *, struct symbol *);
+ struct frame_info *);
static void stop_stepping (struct execution_control_state *ecs);
static void prepare_to_wait (struct execution_control_state *ecs);
@@ -4166,12 +4168,7 @@ process_event_stop_test:
insert_longjmp_resume_breakpoint (gdbarch, jmp_buf_pc);
}
else
- {
- struct symbol *func = get_frame_function (frame);
-
- if (func)
- check_exception_resume (ecs, frame, func);
- }
+ check_exception_resume (ecs, frame);
keep_going (ecs);
return;
@@ -5246,15 +5243,77 @@ insert_exception_resume_breakpoint (struct thread_info *tp,
}
}
+/* A helper for check_exception_resume that sets an
+ exception-breakpoint based on a SystemTap probe. */
+
+static void
+insert_exception_resume_from_probe (struct thread_info *tp,
+ const struct stap_probe *probe,
+ struct objfile *objfile,
+ struct frame_info *frame)
+{
+ int n_probes;
+ struct value *arg_value;
+ CORE_ADDR handler;
+ struct breakpoint *bp;
+
+ /* This is really a "can't happen", but we are paranoid. */
+ if (!objfile->sf || !objfile->sf->sym_probe_fns)
+ return;
+
+ n_probes
+ = objfile->sf->sym_probe_fns->sym_get_probe_argument_count (objfile,
+ probe);
+ if (n_probes < 2)
+ return;
+
+ /* We are interested in the second argument to the probe. */
+ arg_value
+ = objfile->sf->sym_probe_fns->sym_evaluate_probe_argument (objfile,
+ probe,
+ frame,
+ 1);
+ handler = value_as_address (arg_value);
+
+ if (debug_infrun)
+ fprintf_unfiltered (gdb_stdlog,
+ "infrun: exception resume at %lx\n",
+ (unsigned long) handler);
+
+ bp = set_momentary_breakpoint_at_pc (get_frame_arch (frame),
+ handler, bp_exception_resume);
+ bp->thread = tp->num;
+ inferior_thread ()->control.exception_resume_breakpoint = bp;
+}
+
/* This is called when an exception has been intercepted. Check to
see whether the exception's destination is of interest, and if so,
set an exception resume breakpoint there. */
static void
check_exception_resume (struct execution_control_state *ecs,
- struct frame_info *frame, struct symbol *func)
+ struct frame_info *frame)
{
struct gdb_exception e;
+ struct objfile *objfile;
+ const struct stap_probe *probe;
+ struct symbol *func;
+
+ /* First see if this exception unwinding breakpoint was set via a
+ SystemTap probe point. If so, the probe has two arguments: the
+ CFA and the HANDLER. We ignore the CFA, extract the handler, and
+ set a breakpoint there. */
+ probe = find_probe_by_pc (get_frame_pc (frame), &objfile);
+ if (probe)
+ {
+ insert_exception_resume_from_probe (ecs->event_thread, probe,
+ objfile, frame);
+ return;
+ }
+
+ func = get_frame_function (frame);
+ if (!func)
+ return;
TRY_CATCH (e, RETURN_MASK_ERROR)
{
diff --git a/gdb/stap-probe.c b/gdb/stap-probe.c
index 7230a49..ccca946 100644
--- a/gdb/stap-probe.c
+++ b/gdb/stap-probe.c
@@ -265,6 +265,32 @@ info_probes_command (char *arg, int from_tty)
\f
+const struct stap_probe *
+find_probe_in_objfile (struct objfile *objfile,
+ const char *provider,
+ const char *name)
+{
+ const struct stap_probe *probes;
+ int i, num_probes;
+
+ if (! objfile->sf || ! objfile->sf->sym_probe_fns)
+ return NULL;
+
+ probes = objfile->sf->sym_probe_fns->sym_get_probes (objfile, &num_probes);
+ for (i = 0; i < num_probes; ++i)
+ {
+ if (strcmp (probes[i].provider, provider) != 0)
+ continue;
+
+ if (strcmp (probes[i].name, name) != 0)
+ continue;
+
+ return &probes[i];
+ }
+
+ return NULL;
+}
+
struct symtabs_and_lines
parse_stap_probe (char **argptr)
{
@@ -370,22 +396,10 @@ parse_stap_probe (char **argptr)
\f
-/* This is called to compute the value of one of the $_marker_arg*
- convenience variables. */
-
-static struct value *
-compute_marker_arg (struct gdbarch *arch, struct internalvar *ivar,
- void *data)
+const struct stap_probe *
+find_probe_by_pc (CORE_ADDR pc, struct objfile **objfile_out)
{
- struct frame_info *frame = get_selected_frame (_("No frame selected"));
- CORE_ADDR pc = get_frame_pc (frame);
- int sel = (int) (uintptr_t) data;
struct objfile *objfile;
- const struct stap_probe *pc_probe = NULL;
- int n_probes;
-
- /* Note that SEL is biased by 1; SEL==0 means "_marker_argc". */
- gdb_assert (sel >= 0 && sel <= 10);
ALL_OBJFILES (objfile)
{
@@ -402,12 +416,33 @@ compute_marker_arg (struct gdbarch *arch, struct internalvar *ivar,
{
if (probes[i].address == pc)
{
- pc_probe = &probes[i];
- break;
+ *objfile_out = objfile;
+ return &probes[i];
}
}
}
+ return NULL;
+}
+
+/* This is called to compute the value of one of the $_marker_arg*
+ convenience variables. */
+
+static struct value *
+compute_marker_arg (struct gdbarch *arch, struct internalvar *ivar,
+ void *data)
+{
+ struct frame_info *frame = get_selected_frame (_("No frame selected"));
+ CORE_ADDR pc = get_frame_pc (frame);
+ int sel = (int) (uintptr_t) data;
+ struct objfile *objfile;
+ const struct stap_probe *pc_probe;
+ int n_probes;
+
+ /* Note that SEL is biased by 1; SEL==0 means "_marker_argc". */
+ gdb_assert (sel >= 0 && sel <= 10);
+
+ pc_probe = find_probe_by_pc (pc, &objfile);
if (pc_probe == NULL)
error (_("No SystemTap probe at PC %s"), core_addr_to_string (pc));
diff --git a/gdb/stap-probe.h b/gdb/stap-probe.h
index 1967e7b..c7d8e7f 100644
--- a/gdb/stap-probe.h
+++ b/gdb/stap-probe.h
@@ -45,4 +45,18 @@ struct stap_probe
extern struct symtabs_and_lines parse_stap_probe (char **argptr);
+/* Search OBJFILE for a probe with the given PROVIDER and NAME. If a
+ probe is found, return it. If no probe is found, return NULL. */
+
+extern const struct stap_probe *find_probe_in_objfile (struct objfile *objfile,
+ const char *provider,
+ const char *name);
+
+/* Given a PC, find an associated SystemTap probe. If a probe is
+ found, set *OBJFILE_OUT to the probe's objfile, and return the
+ probe. If no probe is found, return NULL. */
+
+extern const struct stap_probe *find_probe_by_pc (CORE_ADDR pc,
+ struct objfile **objfile_out);
+
#endif /* !defined (STAP_PROBE_H) */
hooks/post-receive
--
Repository for Project Archer.
^ permalink raw reply [flat|nested] only message in thread
only message in thread, other threads:[~2011-02-10 18:42 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-02-10 18:42 [SCM] archer-sergiodj-stap: make exception-related breakpoints use stap probes when available this is untested; it needs the probe arguments to work first tromey
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).