Rebase to FSF GDB 7.5.
- Update dlopen to support two variants of glibc (Gary Benson, BZ 669432).
This commit is contained in:
parent
87ed9489e3
commit
30f2069f6e
2
.gitignore
vendored
2
.gitignore
vendored
@ -1,2 +1,2 @@
|
||||
/gdb-libstdc++-v3-python-r155978.tar.bz2
|
||||
/gdb-7.4.91.20120801.tar.bz2
|
||||
/gdb-7.5.tar.bz2
|
||||
|
795
gdb-dlopen-stap-probe-1of7.patch
Normal file
795
gdb-dlopen-stap-probe-1of7.patch
Normal file
@ -0,0 +1,795 @@
|
||||
http://sourceware.org/ml/gdb-cvs/2012-07/msg00123.html
|
||||
|
||||
### src/gdb/ChangeLog 2012/07/18 04:36:15 1.14473
|
||||
### src/gdb/ChangeLog 2012/07/18 16:12:15 1.14474
|
||||
## -1,3 +1,37 @@
|
||||
+2012-07-18 Sergio Durigan Junior <sergiodj@redhat.com>
|
||||
+
|
||||
+ * elfread.c (elf_get_probe_argument_count): Remove `objfile' argument.
|
||||
+ (elf_compile_to_ax): Likewise.
|
||||
+ * infrun.c (insert_exception_resume_from_probe): Likewise.
|
||||
+ (check_exception_resume): Remove `objfile' variable.
|
||||
+ * probe.c (find_probe_by_pc): Remove `objfile' argument.
|
||||
+ (struct probe_and_objfile, probe_and_objfile_s): Delete.
|
||||
+ (collect_probes): Adjust return value to `VEC (probe_p) *'.
|
||||
+ (compare_entries): Rename to...
|
||||
+ (compare_probes): ...this. Adjust function to work with
|
||||
+ `struct probe *'. Rename variables `ea' and `eb' to `pa' and `pb'
|
||||
+ respectively.
|
||||
+ (gen_ui_out_table_header_info): Adjust `probes' argument to be
|
||||
+ `VEC (probe_p) *'.
|
||||
+ (print_ui_out_info): Adjust argument to be `struct probe *'.
|
||||
+ (info_probes_for_ops): Adjust internal computations to use
|
||||
+ `VEC (probe_p) *'.
|
||||
+ (probe_safe_evaluate_at_pc): Refactor to not pass `objfile' anymore.
|
||||
+ * probe.h (struct probe_ops) <get_probe_argument_count, compile_to_ax,
|
||||
+ gen_info_probes_table_values>: Remove `objfile' argument.
|
||||
+ (struct probe) <objfile>: New field.
|
||||
+ (find_probe_by_pc): Remove `objfile' argument.
|
||||
+ * stap-probe.c (stap_parse_probe_arguments): Likewise.
|
||||
+ (stap_get_probe_argument_count): Likewise.
|
||||
+ (stap_get_arg): Likewise.
|
||||
+ (stap_evaluate_probe_argument): Likewise.
|
||||
+ (stap_compile_to_ax): Likewise.
|
||||
+ (compile_probe_arg): Refactor not to pass `objfile' anymore.
|
||||
+ (handle_stap_probe): Fill `objfile' field from `struct probe'.
|
||||
+ (stap_gen_info_probes_table_header): Remove `objfile' argument.
|
||||
+ * symfile.h (struct sym_probe_fns) <sym_evaluate_probe_argument,
|
||||
+ sym_compile_to_ax>: Likewise.
|
||||
+
|
||||
2012-07-18 Terry Guo <terry.guo@arm.com>
|
||||
|
||||
PR 14329
|
||||
--- src/gdb/elfread.c 2012/06/26 20:14:01 1.133
|
||||
+++ src/gdb/elfread.c 2012/07/18 16:12:15 1.134
|
||||
@@ -1635,33 +1635,29 @@
|
||||
symfile.h. */
|
||||
|
||||
static unsigned
|
||||
-elf_get_probe_argument_count (struct objfile *objfile,
|
||||
- struct probe *probe)
|
||||
+elf_get_probe_argument_count (struct probe *probe)
|
||||
{
|
||||
- return probe->pops->get_probe_argument_count (probe, objfile);
|
||||
+ return probe->pops->get_probe_argument_count (probe);
|
||||
}
|
||||
|
||||
/* Implementation of `sym_evaluate_probe_argument', as documented in
|
||||
symfile.h. */
|
||||
|
||||
static struct value *
|
||||
-elf_evaluate_probe_argument (struct objfile *objfile,
|
||||
- struct probe *probe,
|
||||
- unsigned n)
|
||||
+elf_evaluate_probe_argument (struct probe *probe, unsigned n)
|
||||
{
|
||||
- return probe->pops->evaluate_probe_argument (probe, objfile, n);
|
||||
+ return probe->pops->evaluate_probe_argument (probe, n);
|
||||
}
|
||||
|
||||
/* Implementation of `sym_compile_to_ax', as documented in symfile.h. */
|
||||
|
||||
static void
|
||||
-elf_compile_to_ax (struct objfile *objfile,
|
||||
- struct probe *probe,
|
||||
+elf_compile_to_ax (struct probe *probe,
|
||||
struct agent_expr *expr,
|
||||
struct axs_value *value,
|
||||
unsigned n)
|
||||
{
|
||||
- probe->pops->compile_to_ax (probe, objfile, expr, value, n);
|
||||
+ probe->pops->compile_to_ax (probe, expr, value, n);
|
||||
}
|
||||
|
||||
/* Implementation of `sym_relocate_probe', as documented in symfile.h. */
|
||||
--- src/gdb/infrun.c 2012/07/01 10:37:04 1.549
|
||||
+++ src/gdb/infrun.c 2012/07/18 16:12:16 1.550
|
||||
@@ -5518,7 +5518,6 @@
|
||||
static void
|
||||
insert_exception_resume_from_probe (struct thread_info *tp,
|
||||
const struct probe *probe,
|
||||
- struct objfile *objfile,
|
||||
struct frame_info *frame)
|
||||
{
|
||||
struct value *arg_value;
|
||||
@@ -5534,7 +5533,7 @@
|
||||
if (debug_infrun)
|
||||
fprintf_unfiltered (gdb_stdlog,
|
||||
"infrun: exception resume at %s\n",
|
||||
- paddress (get_objfile_arch (objfile),
|
||||
+ paddress (get_objfile_arch (probe->objfile),
|
||||
handler));
|
||||
|
||||
bp = set_momentary_breakpoint_at_pc (get_frame_arch (frame),
|
||||
@@ -5552,7 +5551,6 @@
|
||||
struct frame_info *frame)
|
||||
{
|
||||
volatile struct gdb_exception e;
|
||||
- struct objfile *objfile;
|
||||
const struct probe *probe;
|
||||
struct symbol *func;
|
||||
|
||||
@@ -5560,11 +5558,10 @@
|
||||
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);
|
||||
+ probe = find_probe_by_pc (get_frame_pc (frame));
|
||||
if (probe)
|
||||
{
|
||||
- insert_exception_resume_from_probe (ecs->event_thread, probe,
|
||||
- objfile, frame);
|
||||
+ insert_exception_resume_from_probe (ecs->event_thread, probe, frame);
|
||||
return;
|
||||
}
|
||||
|
||||
--- src/gdb/probe.c 2012/05/08 01:35:34 1.3
|
||||
+++ src/gdb/probe.c 2012/07/18 16:12:17 1.4
|
||||
@@ -204,7 +204,7 @@
|
||||
/* See definition in probe.h. */
|
||||
|
||||
struct probe *
|
||||
-find_probe_by_pc (CORE_ADDR pc, struct objfile **objfile_out)
|
||||
+find_probe_by_pc (CORE_ADDR pc)
|
||||
{
|
||||
struct objfile *objfile;
|
||||
|
||||
@@ -221,10 +221,7 @@
|
||||
probes = objfile->sf->sym_probe_fns->sym_get_probes (objfile);
|
||||
for (ix = 0; VEC_iterate (probe_p, probes, ix, probe); ix++)
|
||||
if (probe->address == pc)
|
||||
- {
|
||||
- *objfile_out = objfile;
|
||||
- return probe;
|
||||
- }
|
||||
+ return probe;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
@@ -232,21 +229,6 @@
|
||||
|
||||
|
||||
|
||||
-/* A utility structure. A VEC of these is built when handling "info
|
||||
- probes". */
|
||||
-
|
||||
-struct probe_and_objfile
|
||||
-{
|
||||
- /* The probe. */
|
||||
- struct probe *probe;
|
||||
-
|
||||
- /* The probe's objfile. */
|
||||
- struct objfile *objfile;
|
||||
-};
|
||||
-
|
||||
-typedef struct probe_and_objfile probe_and_objfile_s;
|
||||
-DEF_VEC_O (probe_and_objfile_s);
|
||||
-
|
||||
/* A helper function for collect_probes that compiles a regexp and
|
||||
throws an exception on error. This installs a cleanup to free the
|
||||
resulting pattern on success. If RX is NULL, this does nothing. */
|
||||
@@ -275,16 +257,16 @@
|
||||
If POPS is not NULL, only probes of this certain probe_ops will match.
|
||||
Each argument is a regexp, or NULL, which matches anything. */
|
||||
|
||||
-static VEC (probe_and_objfile_s) *
|
||||
+static VEC (probe_p) *
|
||||
collect_probes (char *objname, char *provider, char *probe_name,
|
||||
const struct probe_ops *pops)
|
||||
{
|
||||
struct objfile *objfile;
|
||||
- VEC (probe_and_objfile_s) *result = NULL;
|
||||
+ VEC (probe_p) *result = NULL;
|
||||
struct cleanup *cleanup, *cleanup_temps;
|
||||
regex_t obj_pat, prov_pat, probe_pat;
|
||||
|
||||
- cleanup = make_cleanup (VEC_cleanup (probe_and_objfile_s), &result);
|
||||
+ cleanup = make_cleanup (VEC_cleanup (probe_p), &result);
|
||||
|
||||
cleanup_temps = make_cleanup (null_cleanup, NULL);
|
||||
compile_rx_or_error (&prov_pat, provider, _("Invalid provider regexp"));
|
||||
@@ -310,8 +292,6 @@
|
||||
|
||||
for (ix = 0; VEC_iterate (probe_p, probes, ix, probe); ix++)
|
||||
{
|
||||
- probe_and_objfile_s entry;
|
||||
-
|
||||
if (pops != NULL && probe->pops != pops)
|
||||
continue;
|
||||
|
||||
@@ -323,9 +303,7 @@
|
||||
&& regexec (&probe_pat, probe->name, 0, NULL, 0) != 0)
|
||||
continue;
|
||||
|
||||
- entry.probe = probe;
|
||||
- entry.objfile = objfile;
|
||||
- VEC_safe_push (probe_and_objfile_s, result, &entry);
|
||||
+ VEC_safe_push (probe_p, result, probe);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -334,36 +312,36 @@
|
||||
return result;
|
||||
}
|
||||
|
||||
-/* A qsort comparison function for probe_and_objfile_s objects. */
|
||||
+/* A qsort comparison function for probe_p objects. */
|
||||
|
||||
static int
|
||||
-compare_entries (const void *a, const void *b)
|
||||
+compare_probes (const void *a, const void *b)
|
||||
{
|
||||
- const probe_and_objfile_s *ea = a;
|
||||
- const probe_and_objfile_s *eb = b;
|
||||
+ const struct probe *pa = *((const struct probe **) a);
|
||||
+ const struct probe *pb = *((const struct probe **) b);
|
||||
int v;
|
||||
|
||||
- v = strcmp (ea->probe->provider, eb->probe->provider);
|
||||
+ v = strcmp (pa->provider, pb->provider);
|
||||
if (v)
|
||||
return v;
|
||||
|
||||
- v = strcmp (ea->probe->name, eb->probe->name);
|
||||
+ v = strcmp (pa->name, pb->name);
|
||||
if (v)
|
||||
return v;
|
||||
|
||||
- if (ea->probe->address < eb->probe->address)
|
||||
+ if (pa->address < pb->address)
|
||||
return -1;
|
||||
- if (ea->probe->address > eb->probe->address)
|
||||
+ if (pa->address > pb->address)
|
||||
return 1;
|
||||
|
||||
- return strcmp (ea->objfile->name, eb->objfile->name);
|
||||
+ return strcmp (pa->objfile->name, pb->objfile->name);
|
||||
}
|
||||
|
||||
/* Helper function that generate entries in the ui_out table being
|
||||
crafted by `info_probes_for_ops'. */
|
||||
|
||||
static void
|
||||
-gen_ui_out_table_header_info (VEC (probe_and_objfile_s) *probes,
|
||||
+gen_ui_out_table_header_info (VEC (probe_p) *probes,
|
||||
const struct probe_ops *p)
|
||||
{
|
||||
/* `headings' refers to the names of the columns when printing `info
|
||||
@@ -392,11 +370,11 @@
|
||||
VEC_iterate (info_probe_column_s, headings, ix, column);
|
||||
++ix)
|
||||
{
|
||||
- probe_and_objfile_s *entry;
|
||||
+ struct probe *probe;
|
||||
int jx;
|
||||
size_t size_max = strlen (column->print_name);
|
||||
|
||||
- for (jx = 0; VEC_iterate (probe_and_objfile_s, probes, jx, entry); ++jx)
|
||||
+ for (jx = 0; VEC_iterate (probe_p, probes, jx, probe); ++jx)
|
||||
{
|
||||
/* `probe_fields' refers to the values of each new field that this
|
||||
probe will display. */
|
||||
@@ -405,12 +383,11 @@
|
||||
const char *val;
|
||||
int kx;
|
||||
|
||||
- if (entry->probe->pops != p)
|
||||
+ if (probe->pops != p)
|
||||
continue;
|
||||
|
||||
c2 = make_cleanup (VEC_cleanup (const_char_ptr), &probe_fields);
|
||||
- p->gen_info_probes_table_values (entry->probe, entry->objfile,
|
||||
- &probe_fields);
|
||||
+ p->gen_info_probes_table_values (probe, &probe_fields);
|
||||
|
||||
gdb_assert (VEC_length (const_char_ptr, probe_fields)
|
||||
== headings_size);
|
||||
@@ -437,10 +414,10 @@
|
||||
}
|
||||
|
||||
/* Helper function to print extra information about a probe and an objfile
|
||||
- represented by ENTRY. */
|
||||
+ represented by PROBE. */
|
||||
|
||||
static void
|
||||
-print_ui_out_info (probe_and_objfile_s *entry)
|
||||
+print_ui_out_info (struct probe *probe)
|
||||
{
|
||||
int ix;
|
||||
int j = 0;
|
||||
@@ -451,23 +428,21 @@
|
||||
info_probe_column_s *column;
|
||||
struct cleanup *c;
|
||||
|
||||
- gdb_assert (entry != NULL);
|
||||
- gdb_assert (entry->probe != NULL);
|
||||
- gdb_assert (entry->probe->pops != NULL);
|
||||
+ gdb_assert (probe != NULL);
|
||||
+ gdb_assert (probe->pops != NULL);
|
||||
|
||||
- if (entry->probe->pops->gen_info_probes_table_header == NULL
|
||||
- && entry->probe->pops->gen_info_probes_table_values == NULL)
|
||||
+ if (probe->pops->gen_info_probes_table_header == NULL
|
||||
+ && probe->pops->gen_info_probes_table_values == NULL)
|
||||
return;
|
||||
|
||||
- gdb_assert (entry->probe->pops->gen_info_probes_table_header != NULL
|
||||
- && entry->probe->pops->gen_info_probes_table_values != NULL);
|
||||
+ gdb_assert (probe->pops->gen_info_probes_table_header != NULL
|
||||
+ && probe->pops->gen_info_probes_table_values != NULL);
|
||||
|
||||
c = make_cleanup (VEC_cleanup (info_probe_column_s), &headings);
|
||||
make_cleanup (VEC_cleanup (const_char_ptr), &values);
|
||||
|
||||
- entry->probe->pops->gen_info_probes_table_header (&headings);
|
||||
- entry->probe->pops->gen_info_probes_table_values (entry->probe,
|
||||
- entry->objfile, &values);
|
||||
+ probe->pops->gen_info_probes_table_header (&headings);
|
||||
+ probe->pops->gen_info_probes_table_values (probe, &values);
|
||||
|
||||
gdb_assert (VEC_length (info_probe_column_s, headings)
|
||||
== VEC_length (const_char_ptr, values));
|
||||
@@ -515,16 +490,16 @@
|
||||
void
|
||||
info_probes_for_ops (char *arg, int from_tty, const struct probe_ops *pops)
|
||||
{
|
||||
- char *provider, *probe = NULL, *objname = NULL;
|
||||
+ char *provider, *probe_name = NULL, *objname = NULL;
|
||||
struct cleanup *cleanup = make_cleanup (null_cleanup, NULL);
|
||||
- VEC (probe_and_objfile_s) *items;
|
||||
+ VEC (probe_p) *probes;
|
||||
int i, any_found;
|
||||
int ui_out_extra_fields = 0;
|
||||
size_t size_addr;
|
||||
size_t size_name = strlen ("Name");
|
||||
size_t size_objname = strlen ("Object");
|
||||
size_t size_provider = strlen ("Provider");
|
||||
- probe_and_objfile_s *entry;
|
||||
+ struct probe *probe;
|
||||
struct gdbarch *gdbarch = get_current_arch ();
|
||||
|
||||
/* Do we have a `provider:probe:objfile' style of linespec? */
|
||||
@@ -533,10 +508,10 @@
|
||||
{
|
||||
make_cleanup (xfree, provider);
|
||||
|
||||
- probe = extract_arg (&arg);
|
||||
- if (probe)
|
||||
+ probe_name = extract_arg (&arg);
|
||||
+ if (probe_name)
|
||||
{
|
||||
- make_cleanup (xfree, probe);
|
||||
+ make_cleanup (xfree, probe_name);
|
||||
|
||||
objname = extract_arg (&arg);
|
||||
if (objname)
|
||||
@@ -564,28 +539,27 @@
|
||||
else
|
||||
ui_out_extra_fields = get_number_extra_fields (pops);
|
||||
|
||||
- items = collect_probes (objname, provider, probe, pops);
|
||||
- make_cleanup (VEC_cleanup (probe_and_objfile_s), &items);
|
||||
+ probes = collect_probes (objname, provider, probe_name, pops);
|
||||
+ make_cleanup (VEC_cleanup (probe_p), &probes);
|
||||
make_cleanup_ui_out_table_begin_end (current_uiout,
|
||||
4 + ui_out_extra_fields,
|
||||
- VEC_length (probe_and_objfile_s, items),
|
||||
+ VEC_length (probe_p, probes),
|
||||
"StaticProbes");
|
||||
|
||||
- if (!VEC_empty (probe_and_objfile_s, items))
|
||||
- qsort (VEC_address (probe_and_objfile_s, items),
|
||||
- VEC_length (probe_and_objfile_s, items),
|
||||
- sizeof (probe_and_objfile_s), compare_entries);
|
||||
+ if (!VEC_empty (probe_p, probes))
|
||||
+ qsort (VEC_address (probe_p, probes), VEC_length (probe_p, probes),
|
||||
+ sizeof (probe_p), compare_probes);
|
||||
|
||||
/* What's the size of an address in our architecture? */
|
||||
size_addr = gdbarch_addr_bit (gdbarch) == 64 ? 18 : 10;
|
||||
|
||||
/* Determining the maximum size of each field (`provider', `name' and
|
||||
`objname'). */
|
||||
- for (i = 0; VEC_iterate (probe_and_objfile_s, items, i, entry); ++i)
|
||||
+ for (i = 0; VEC_iterate (probe_p, probes, i, probe); ++i)
|
||||
{
|
||||
- size_name = max (strlen (entry->probe->name), size_name);
|
||||
- size_provider = max (strlen (entry->probe->provider), size_provider);
|
||||
- size_objname = max (strlen (entry->objfile->name), size_objname);
|
||||
+ size_name = max (strlen (probe->name), size_name);
|
||||
+ size_provider = max (strlen (probe->provider), size_provider);
|
||||
+ size_objname = max (strlen (probe->objfile->name), size_objname);
|
||||
}
|
||||
|
||||
ui_out_table_header (current_uiout, size_provider, ui_left, "provider",
|
||||
@@ -601,26 +575,26 @@
|
||||
/* We have to generate the table header for each new probe type that we
|
||||
will print. */
|
||||
for (ix = 0; VEC_iterate (probe_ops_cp, all_probe_ops, ix, po); ++ix)
|
||||
- gen_ui_out_table_header_info (items, po);
|
||||
+ gen_ui_out_table_header_info (probes, po);
|
||||
}
|
||||
else
|
||||
- gen_ui_out_table_header_info (items, pops);
|
||||
+ gen_ui_out_table_header_info (probes, pops);
|
||||
|
||||
ui_out_table_header (current_uiout, size_objname, ui_left, "object",
|
||||
_("Object"));
|
||||
ui_out_table_body (current_uiout);
|
||||
|
||||
- for (i = 0; VEC_iterate (probe_and_objfile_s, items, i, entry); ++i)
|
||||
+ for (i = 0; VEC_iterate (probe_p, probes, i, probe); ++i)
|
||||
{
|
||||
struct cleanup *inner;
|
||||
|
||||
inner = make_cleanup_ui_out_tuple_begin_end (current_uiout, "probe");
|
||||
|
||||
- ui_out_field_string (current_uiout, "provider", entry->probe->provider);
|
||||
- ui_out_field_string (current_uiout, "name", entry->probe->name);
|
||||
+ ui_out_field_string (current_uiout, "provider", probe->provider);
|
||||
+ ui_out_field_string (current_uiout, "name", probe->name);
|
||||
ui_out_field_core_addr (current_uiout, "addr",
|
||||
- get_objfile_arch (entry->objfile),
|
||||
- entry->probe->address);
|
||||
+ get_objfile_arch (probe->objfile),
|
||||
+ probe->address);
|
||||
|
||||
if (pops == NULL)
|
||||
{
|
||||
@@ -629,19 +603,19 @@
|
||||
|
||||
for (ix = 0; VEC_iterate (probe_ops_cp, all_probe_ops, ix, po);
|
||||
++ix)
|
||||
- if (entry->probe->pops == po)
|
||||
- print_ui_out_info (entry);
|
||||
+ if (probe->pops == po)
|
||||
+ print_ui_out_info (probe);
|
||||
}
|
||||
else
|
||||
- print_ui_out_info (entry);
|
||||
+ print_ui_out_info (probe);
|
||||
|
||||
- ui_out_field_string (current_uiout, "object", entry->objfile->name);
|
||||
+ ui_out_field_string (current_uiout, "object", probe->objfile->name);
|
||||
ui_out_text (current_uiout, "\n");
|
||||
|
||||
do_cleanups (inner);
|
||||
}
|
||||
|
||||
- any_found = !VEC_empty (probe_and_objfile_s, items);
|
||||
+ any_found = !VEC_empty (probe_p, probes);
|
||||
do_cleanups (cleanup);
|
||||
|
||||
if (!any_found)
|
||||
@@ -662,23 +636,24 @@
|
||||
probe_safe_evaluate_at_pc (struct frame_info *frame, unsigned n)
|
||||
{
|
||||
struct probe *probe;
|
||||
- struct objfile *objfile;
|
||||
+ const struct sym_probe_fns *probe_fns;
|
||||
unsigned n_probes;
|
||||
|
||||
- probe = find_probe_by_pc (get_frame_pc (frame), &objfile);
|
||||
+ probe = find_probe_by_pc (get_frame_pc (frame));
|
||||
if (!probe)
|
||||
return NULL;
|
||||
- gdb_assert (objfile->sf && objfile->sf->sym_probe_fns);
|
||||
|
||||
- n_probes
|
||||
- = objfile->sf->sym_probe_fns->sym_get_probe_argument_count (objfile,
|
||||
- probe);
|
||||
+ gdb_assert (probe->objfile != NULL);
|
||||
+ gdb_assert (probe->objfile->sf != NULL);
|
||||
+ gdb_assert (probe->objfile->sf->sym_probe_fns != NULL);
|
||||
+
|
||||
+ probe_fns = probe->objfile->sf->sym_probe_fns;
|
||||
+ n_probes = probe_fns->sym_get_probe_argument_count (probe);
|
||||
+
|
||||
if (n >= n_probes)
|
||||
return NULL;
|
||||
|
||||
- return objfile->sf->sym_probe_fns->sym_evaluate_probe_argument (objfile,
|
||||
- probe,
|
||||
- n);
|
||||
+ return probe_fns->sym_evaluate_probe_argument (probe, n);
|
||||
}
|
||||
|
||||
/* See comment in probe.h. */
|
||||
--- src/gdb/probe.h 2012/04/27 20:47:55 1.1
|
||||
+++ src/gdb/probe.h 2012/07/18 16:12:17 1.2
|
||||
@@ -66,21 +66,18 @@
|
||||
|
||||
/* Return the number of arguments of PROBE. */
|
||||
|
||||
- unsigned (*get_probe_argument_count) (struct probe *probe,
|
||||
- struct objfile *objfile);
|
||||
+ unsigned (*get_probe_argument_count) (struct probe *probe);
|
||||
|
||||
/* Evaluate the Nth argument from the PROBE, returning a value
|
||||
corresponding to it. The argument number is represented N. */
|
||||
|
||||
struct value *(*evaluate_probe_argument) (struct probe *probe,
|
||||
- struct objfile *objfile,
|
||||
unsigned n);
|
||||
|
||||
/* Compile the Nth argument of the PROBE to an agent expression.
|
||||
The argument number is represented by N. */
|
||||
|
||||
- void (*compile_to_ax) (struct probe *probe, struct objfile *objfile,
|
||||
- struct agent_expr *aexpr,
|
||||
+ void (*compile_to_ax) (struct probe *probe, struct agent_expr *aexpr,
|
||||
struct axs_value *axs_value, unsigned n);
|
||||
|
||||
/* Set the semaphore associated with the PROBE. This function only makes
|
||||
@@ -108,8 +105,8 @@
|
||||
void (*gen_info_probes_table_header) (VEC (info_probe_column_s) **heads);
|
||||
|
||||
/* Function that will fill VALUES with the values of the extra fields
|
||||
- to be printed for PROBE and OBJFILE. If the backend implements
|
||||
- the `gen_ui_out_table_header' method, then it should implement
|
||||
+ to be printed for PROBE. If the backend implements the
|
||||
+ `gen_ui_out_table_header' method, then it should implement
|
||||
this method as well. The backend should also guarantee that the
|
||||
order and the number of values in the vector is exactly the same
|
||||
as the order of the extra fields provided in the method
|
||||
@@ -118,7 +115,6 @@
|
||||
position in the vector. */
|
||||
|
||||
void (*gen_info_probes_table_values) (struct probe *probe,
|
||||
- struct objfile *objfile,
|
||||
VEC (const_char_ptr) **values);
|
||||
};
|
||||
|
||||
@@ -157,6 +153,11 @@
|
||||
/* The operations associated with this probe. */
|
||||
const struct probe_ops *pops;
|
||||
|
||||
+ /* The objfile which contains this probe. Even if the probe is also
|
||||
+ present in a separate debug objfile, this variable always points to
|
||||
+ the non-separate debug objfile. */
|
||||
+ struct objfile *objfile;
|
||||
+
|
||||
/* The name of the probe. */
|
||||
const char *name;
|
||||
|
||||
@@ -181,11 +182,9 @@
|
||||
extern void register_probe_ops (struct probe *probe);
|
||||
|
||||
/* Given a PC, find an associated probe with type PTYPE. If a probe is
|
||||
- found, set *OBJFILE_OUT to the probe's objfile, and return the
|
||||
- probe. If no probe is found, return NULL. */
|
||||
+ found, return it. If no probe is found, return NULL. */
|
||||
|
||||
-extern struct probe *find_probe_by_pc (CORE_ADDR pc,
|
||||
- struct objfile **objfile_out);
|
||||
+extern struct probe *find_probe_by_pc (CORE_ADDR pc);
|
||||
|
||||
/* Search OBJFILE for a probe with the given PROVIDER, NAME and PTYPE.
|
||||
Return a VEC of all probes that were found. If no matching probe
|
||||
--- src/gdb/stap-probe.c 2012/05/08 01:35:35 1.4
|
||||
+++ src/gdb/stap-probe.c 2012/07/18 16:12:17 1.5
|
||||
@@ -903,10 +903,10 @@
|
||||
this information. */
|
||||
|
||||
static void
|
||||
-stap_parse_probe_arguments (struct stap_probe *probe, struct objfile *objfile)
|
||||
+stap_parse_probe_arguments (struct stap_probe *probe)
|
||||
{
|
||||
const char *cur;
|
||||
- struct gdbarch *gdbarch = get_objfile_arch (objfile);
|
||||
+ struct gdbarch *gdbarch = get_objfile_arch (probe->p.objfile);
|
||||
|
||||
gdb_assert (!probe->args_parsed);
|
||||
cur = probe->args_u.text;
|
||||
@@ -991,15 +991,14 @@
|
||||
argument string. */
|
||||
|
||||
static unsigned
|
||||
-stap_get_probe_argument_count (struct probe *probe_generic,
|
||||
- struct objfile *objfile)
|
||||
+stap_get_probe_argument_count (struct probe *probe_generic)
|
||||
{
|
||||
struct stap_probe *probe = (struct stap_probe *) probe_generic;
|
||||
|
||||
gdb_assert (probe_generic->pops == &stap_probe_ops);
|
||||
|
||||
if (!probe->args_parsed)
|
||||
- stap_parse_probe_arguments (probe, objfile);
|
||||
+ stap_parse_probe_arguments (probe);
|
||||
|
||||
gdb_assert (probe->args_parsed);
|
||||
return VEC_length (stap_probe_arg_s, probe->args_u.vec);
|
||||
@@ -1042,10 +1041,10 @@
|
||||
}
|
||||
|
||||
static struct stap_probe_arg *
|
||||
-stap_get_arg (struct stap_probe *probe, struct objfile *objfile, unsigned n)
|
||||
+stap_get_arg (struct stap_probe *probe, unsigned n)
|
||||
{
|
||||
if (!probe->args_parsed)
|
||||
- stap_parse_probe_arguments (probe, objfile);
|
||||
+ stap_parse_probe_arguments (probe);
|
||||
|
||||
return VEC_index (stap_probe_arg_s, probe->args_u.vec, n);
|
||||
}
|
||||
@@ -1054,8 +1053,7 @@
|
||||
corresponding to it. Assertion is thrown if N does not exist. */
|
||||
|
||||
static struct value *
|
||||
-stap_evaluate_probe_argument (struct probe *probe_generic,
|
||||
- struct objfile *objfile, unsigned n)
|
||||
+stap_evaluate_probe_argument (struct probe *probe_generic, unsigned n)
|
||||
{
|
||||
struct stap_probe *stap_probe = (struct stap_probe *) probe_generic;
|
||||
struct stap_probe_arg *arg;
|
||||
@@ -1063,7 +1061,7 @@
|
||||
|
||||
gdb_assert (probe_generic->pops == &stap_probe_ops);
|
||||
|
||||
- arg = stap_get_arg (stap_probe, objfile, n);
|
||||
+ arg = stap_get_arg (stap_probe, n);
|
||||
return evaluate_subexp_standard (arg->atype, arg->aexpr, &pos, EVAL_NORMAL);
|
||||
}
|
||||
|
||||
@@ -1071,9 +1069,8 @@
|
||||
Assertion is thrown if N does not exist. */
|
||||
|
||||
static void
|
||||
-stap_compile_to_ax (struct probe *probe_generic, struct objfile *objfile,
|
||||
- struct agent_expr *expr, struct axs_value *value,
|
||||
- unsigned n)
|
||||
+stap_compile_to_ax (struct probe *probe_generic, struct agent_expr *expr,
|
||||
+ struct axs_value *value, unsigned n)
|
||||
{
|
||||
struct stap_probe *stap_probe = (struct stap_probe *) probe_generic;
|
||||
struct stap_probe_arg *arg;
|
||||
@@ -1081,7 +1078,7 @@
|
||||
|
||||
gdb_assert (probe_generic->pops == &stap_probe_ops);
|
||||
|
||||
- arg = stap_get_arg (stap_probe, objfile, n);
|
||||
+ arg = stap_get_arg (stap_probe, n);
|
||||
|
||||
pc = arg->aexpr->elts;
|
||||
gen_expr (arg->aexpr, &pc, expr, value);
|
||||
@@ -1124,20 +1121,24 @@
|
||||
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;
|
||||
struct probe *pc_probe;
|
||||
+ const struct sym_probe_fns *pc_probe_fns;
|
||||
unsigned n_args;
|
||||
|
||||
/* SEL == -1 means "_probe_argc". */
|
||||
gdb_assert (sel >= -1);
|
||||
|
||||
- pc_probe = find_probe_by_pc (pc, &objfile);
|
||||
+ pc_probe = find_probe_by_pc (pc);
|
||||
if (pc_probe == NULL)
|
||||
error (_("No SystemTap probe at PC %s"), core_addr_to_string (pc));
|
||||
|
||||
- n_args
|
||||
- = objfile->sf->sym_probe_fns->sym_get_probe_argument_count (objfile,
|
||||
- pc_probe);
|
||||
+ gdb_assert (pc_probe->objfile != NULL);
|
||||
+ gdb_assert (pc_probe->objfile->sf != NULL);
|
||||
+ gdb_assert (pc_probe->objfile->sf->sym_probe_fns != NULL);
|
||||
+
|
||||
+ pc_probe_fns = pc_probe->objfile->sf->sym_probe_fns;
|
||||
+
|
||||
+ n_args = pc_probe_fns->sym_get_probe_argument_count (pc_probe);
|
||||
if (sel == -1)
|
||||
return value_from_longest (builtin_type (arch)->builtin_int, n_args);
|
||||
|
||||
@@ -1145,9 +1146,7 @@
|
||||
error (_("Invalid probe argument %d -- probe has %u arguments available"),
|
||||
sel, n_args);
|
||||
|
||||
- return objfile->sf->sym_probe_fns->sym_evaluate_probe_argument (objfile,
|
||||
- pc_probe,
|
||||
- sel);
|
||||
+ return pc_probe_fns->sym_evaluate_probe_argument (pc_probe, sel);
|
||||
}
|
||||
|
||||
/* This is called to compile one of the $_probe_arg* convenience
|
||||
@@ -1159,20 +1158,25 @@
|
||||
{
|
||||
CORE_ADDR pc = expr->scope;
|
||||
int sel = (int) (uintptr_t) data;
|
||||
- struct objfile *objfile;
|
||||
struct probe *pc_probe;
|
||||
+ const struct sym_probe_fns *pc_probe_fns;
|
||||
int n_probes;
|
||||
|
||||
/* SEL == -1 means "_probe_argc". */
|
||||
gdb_assert (sel >= -1);
|
||||
|
||||
- pc_probe = find_probe_by_pc (pc, &objfile);
|
||||
+ pc_probe = find_probe_by_pc (pc);
|
||||
if (pc_probe == NULL)
|
||||
error (_("No SystemTap probe at PC %s"), core_addr_to_string (pc));
|
||||
|
||||
- n_probes
|
||||
- = objfile->sf->sym_probe_fns->sym_get_probe_argument_count (objfile,
|
||||
- pc_probe);
|
||||
+ gdb_assert (pc_probe->objfile != NULL);
|
||||
+ gdb_assert (pc_probe->objfile->sf != NULL);
|
||||
+ gdb_assert (pc_probe->objfile->sf->sym_probe_fns != NULL);
|
||||
+
|
||||
+ pc_probe_fns = pc_probe->objfile->sf->sym_probe_fns;
|
||||
+
|
||||
+ n_probes = pc_probe_fns->sym_get_probe_argument_count (pc_probe);
|
||||
+
|
||||
if (sel == -1)
|
||||
{
|
||||
value->kind = axs_rvalue;
|
||||
@@ -1186,8 +1190,7 @@
|
||||
error (_("Invalid probe argument %d -- probe has %d arguments available"),
|
||||
sel, n_probes);
|
||||
|
||||
- objfile->sf->sym_probe_fns->sym_compile_to_ax (objfile, pc_probe,
|
||||
- expr, value, sel);
|
||||
+ pc_probe_fns->sym_compile_to_ax (pc_probe, expr, value, sel);
|
||||
}
|
||||
|
||||
|
||||
@@ -1297,6 +1300,7 @@
|
||||
|
||||
ret = obstack_alloc (&objfile->objfile_obstack, sizeof (*ret));
|
||||
ret->p.pops = &stap_probe_ops;
|
||||
+ ret->p.objfile = objfile;
|
||||
|
||||
/* Provider and the name of the probe. */
|
||||
ret->p.provider = &el->data[3 * size];
|
||||
@@ -1481,15 +1485,16 @@
|
||||
|
||||
static void
|
||||
stap_gen_info_probes_table_values (struct probe *probe_generic,
|
||||
- struct objfile *objfile,
|
||||
VEC (const_char_ptr) **ret)
|
||||
{
|
||||
struct stap_probe *probe = (struct stap_probe *) probe_generic;
|
||||
- struct gdbarch *gdbarch = get_objfile_arch (objfile);
|
||||
+ struct gdbarch *gdbarch;
|
||||
const char *val = NULL;
|
||||
|
||||
gdb_assert (probe_generic->pops == &stap_probe_ops);
|
||||
|
||||
+ gdbarch = get_objfile_arch (probe->p.objfile);
|
||||
+
|
||||
if (probe->sem_addr)
|
||||
val = print_core_address (gdbarch, probe->sem_addr);
|
||||
|
||||
--- src/gdb/symfile.h 2012/05/24 22:14:35 1.109
|
||||
+++ src/gdb/symfile.h 2012/07/18 16:12:17 1.110
|
||||
@@ -320,8 +320,7 @@
|
||||
have come from a call to this objfile's sym_get_probes method.
|
||||
If you provide an implementation of sym_get_probes, you must
|
||||
implement this method as well. */
|
||||
- unsigned (*sym_get_probe_argument_count) (struct objfile *objfile,
|
||||
- struct probe *probe);
|
||||
+ unsigned (*sym_get_probe_argument_count) (struct probe *probe);
|
||||
|
||||
/* Evaluate the Nth argument available to PROBE. PROBE will have
|
||||
come from a call to this objfile's sym_get_probes method. N will
|
||||
@@ -330,8 +329,7 @@
|
||||
PC will match the address of the probe. If you provide an
|
||||
implementation of sym_get_probes, you must implement this method
|
||||
as well. */
|
||||
- struct value *(*sym_evaluate_probe_argument) (struct objfile *objfile,
|
||||
- struct probe *probe,
|
||||
+ struct value *(*sym_evaluate_probe_argument) (struct probe *probe,
|
||||
unsigned n);
|
||||
|
||||
/* Compile the Nth probe argument to an agent expression. PROBE
|
||||
@@ -339,8 +337,7 @@
|
||||
method. N will be between 0 and the number of arguments
|
||||
available to this probe. EXPR and VALUE are the agent expression
|
||||
that is being updated. */
|
||||
- void (*sym_compile_to_ax) (struct objfile *objfile,
|
||||
- struct probe *probe,
|
||||
+ void (*sym_compile_to_ax) (struct probe *probe,
|
||||
struct agent_expr *expr,
|
||||
struct axs_value *value,
|
||||
unsigned n);
|
74
gdb-dlopen-stap-probe-2of7.patch
Normal file
74
gdb-dlopen-stap-probe-2of7.patch
Normal file
@ -0,0 +1,74 @@
|
||||
http://sourceware.org/ml/gdb-cvs/2012-07/msg00124.html
|
||||
|
||||
### src/gdb/ChangeLog 2012/07/18 16:12:15 1.14474
|
||||
### src/gdb/ChangeLog 2012/07/18 16:20:36 1.14475
|
||||
## -1,5 +1,10 @@
|
||||
2012-07-18 Sergio Durigan Junior <sergiodj@redhat.com>
|
||||
|
||||
+ * probe.c (probe_safe_evaluate_at_pc): Rename variable `n_probes'.
|
||||
+ * stap-probe.c (compile_probe_arg): Likewise.
|
||||
+
|
||||
+2012-07-18 Sergio Durigan Junior <sergiodj@redhat.com>
|
||||
+
|
||||
* elfread.c (elf_get_probe_argument_count): Remove `objfile' argument.
|
||||
(elf_compile_to_ax): Likewise.
|
||||
* infrun.c (insert_exception_resume_from_probe): Likewise.
|
||||
--- src/gdb/probe.c 2012/07/18 16:12:17 1.4
|
||||
+++ src/gdb/probe.c 2012/07/18 16:20:43 1.5
|
||||
@@ -637,7 +637,7 @@
|
||||
{
|
||||
struct probe *probe;
|
||||
const struct sym_probe_fns *probe_fns;
|
||||
- unsigned n_probes;
|
||||
+ unsigned n_args;
|
||||
|
||||
probe = find_probe_by_pc (get_frame_pc (frame));
|
||||
if (!probe)
|
||||
@@ -648,9 +648,9 @@
|
||||
gdb_assert (probe->objfile->sf->sym_probe_fns != NULL);
|
||||
|
||||
probe_fns = probe->objfile->sf->sym_probe_fns;
|
||||
- n_probes = probe_fns->sym_get_probe_argument_count (probe);
|
||||
+ n_args = probe_fns->sym_get_probe_argument_count (probe);
|
||||
|
||||
- if (n >= n_probes)
|
||||
+ if (n >= n_args)
|
||||
return NULL;
|
||||
|
||||
return probe_fns->sym_evaluate_probe_argument (probe, n);
|
||||
--- src/gdb/stap-probe.c 2012/07/18 16:12:17 1.5
|
||||
+++ src/gdb/stap-probe.c 2012/07/18 16:20:43 1.6
|
||||
@@ -1160,7 +1160,7 @@
|
||||
int sel = (int) (uintptr_t) data;
|
||||
struct probe *pc_probe;
|
||||
const struct sym_probe_fns *pc_probe_fns;
|
||||
- int n_probes;
|
||||
+ int n_args;
|
||||
|
||||
/* SEL == -1 means "_probe_argc". */
|
||||
gdb_assert (sel >= -1);
|
||||
@@ -1175,20 +1175,20 @@
|
||||
|
||||
pc_probe_fns = pc_probe->objfile->sf->sym_probe_fns;
|
||||
|
||||
- n_probes = pc_probe_fns->sym_get_probe_argument_count (pc_probe);
|
||||
+ n_args = pc_probe_fns->sym_get_probe_argument_count (pc_probe);
|
||||
|
||||
if (sel == -1)
|
||||
{
|
||||
value->kind = axs_rvalue;
|
||||
value->type = builtin_type (expr->gdbarch)->builtin_int;
|
||||
- ax_const_l (expr, n_probes);
|
||||
+ ax_const_l (expr, n_args);
|
||||
return;
|
||||
}
|
||||
|
||||
gdb_assert (sel >= 0);
|
||||
- if (sel >= n_probes)
|
||||
+ if (sel >= n_args)
|
||||
error (_("Invalid probe argument %d -- probe has %d arguments available"),
|
||||
- sel, n_probes);
|
||||
+ sel, n_args);
|
||||
|
||||
pc_probe_fns->sym_compile_to_ax (pc_probe, expr, value, sel);
|
||||
}
|
98
gdb-dlopen-stap-probe-3of7.patch
Normal file
98
gdb-dlopen-stap-probe-3of7.patch
Normal file
@ -0,0 +1,98 @@
|
||||
2012-07-19 Gary Benson <gbenson@redhat.com>
|
||||
|
||||
* probe.h (get_probe_argument_count): New declaration.
|
||||
(evaluate_probe_argument): Likewise.
|
||||
* probe.c (get_probe_argument_count): New function.
|
||||
(evaluate_probe_argument): Likewise.
|
||||
(probe_safe_evaluate_at_pc): Use the above new functions.
|
||||
|
||||
diff --git a/gdb/probe.h b/gdb/probe.h
|
||||
index 8d44ca2..1d29b87 100644
|
||||
--- a/gdb/probe.h
|
||||
+++ b/gdb/probe.h
|
||||
@@ -214,6 +214,16 @@ extern void info_probes_for_ops (char *arg, int from_tty,
|
||||
|
||||
extern struct cmd_list_element **info_probes_cmdlist_get (void);
|
||||
|
||||
+/* Return the argument count of the specified probe. */
|
||||
+
|
||||
+extern unsigned get_probe_argument_count (struct probe *probe);
|
||||
+
|
||||
+/* Evaluate argument N of the specified probe. N must be between 0
|
||||
+ inclusive and get_probe_argument_count exclusive. */
|
||||
+
|
||||
+extern struct value *evaluate_probe_argument (struct probe *probe,
|
||||
+ unsigned n);
|
||||
+
|
||||
/* A convenience function that finds a probe at the PC in FRAME and
|
||||
evaluates argument N, with 0 <= N < number_of_args. If there is no
|
||||
probe at that location, or if the probe does not have enough arguments,
|
||||
diff --git a/gdb/probe.c b/gdb/probe.c
|
||||
index 77f3b13..a61f4ea 100644
|
||||
--- a/gdb/probe.c
|
||||
+++ b/gdb/probe.c
|
||||
@@ -632,28 +632,55 @@ info_probes_command (char *arg, int from_tty)
|
||||
|
||||
/* See comments in probe.h. */
|
||||
|
||||
+unsigned
|
||||
+get_probe_argument_count (struct probe *probe)
|
||||
+{
|
||||
+ const struct sym_probe_fns *probe_fns;
|
||||
+
|
||||
+ gdb_assert (probe->objfile != NULL);
|
||||
+ gdb_assert (probe->objfile->sf != NULL);
|
||||
+
|
||||
+ probe_fns = probe->objfile->sf->sym_probe_fns;
|
||||
+
|
||||
+ gdb_assert (probe_fns != NULL);
|
||||
+
|
||||
+ return probe_fns->sym_get_probe_argument_count (probe);
|
||||
+}
|
||||
+
|
||||
+/* See comments in probe.h. */
|
||||
+
|
||||
+struct value *
|
||||
+evaluate_probe_argument (struct probe *probe, unsigned n)
|
||||
+{
|
||||
+ const struct sym_probe_fns *probe_fns;
|
||||
+
|
||||
+ gdb_assert (probe->objfile != NULL);
|
||||
+ gdb_assert (probe->objfile->sf != NULL);
|
||||
+
|
||||
+ probe_fns = probe->objfile->sf->sym_probe_fns;
|
||||
+
|
||||
+ gdb_assert (probe_fns != NULL);
|
||||
+
|
||||
+ return probe_fns->sym_evaluate_probe_argument (probe, n);
|
||||
+}
|
||||
+
|
||||
+/* See comments in probe.h. */
|
||||
+
|
||||
struct value *
|
||||
probe_safe_evaluate_at_pc (struct frame_info *frame, unsigned n)
|
||||
{
|
||||
struct probe *probe;
|
||||
- const struct sym_probe_fns *probe_fns;
|
||||
unsigned n_args;
|
||||
|
||||
probe = find_probe_by_pc (get_frame_pc (frame));
|
||||
if (!probe)
|
||||
return NULL;
|
||||
|
||||
- gdb_assert (probe->objfile != NULL);
|
||||
- gdb_assert (probe->objfile->sf != NULL);
|
||||
- gdb_assert (probe->objfile->sf->sym_probe_fns != NULL);
|
||||
-
|
||||
- probe_fns = probe->objfile->sf->sym_probe_fns;
|
||||
- n_args = probe_fns->sym_get_probe_argument_count (probe);
|
||||
-
|
||||
+ n_args = get_probe_argument_count (probe);
|
||||
if (n >= n_args)
|
||||
return NULL;
|
||||
|
||||
- return probe_fns->sym_evaluate_probe_argument (probe, n);
|
||||
+ return evaluate_probe_argument (probe, n);
|
||||
}
|
||||
|
||||
/* See comment in probe.h. */
|
131
gdb-dlopen-stap-probe-4of7.patch
Normal file
131
gdb-dlopen-stap-probe-4of7.patch
Normal file
@ -0,0 +1,131 @@
|
||||
2012-07-19 Gary Benson <gbenson@redhat.com>
|
||||
|
||||
* solib-svr4.c (svr4_info): Move earlier.
|
||||
(solib_svr4_pspace_data): Likewise.
|
||||
(svr4_pspace_data_cleanup): Likewise.
|
||||
(get_svr4_info): Likewise.
|
||||
|
||||
diff --git a/gdb/solib-svr4.c b/gdb/solib-svr4.c
|
||||
index 307e483..c88b9cb 100644
|
||||
--- a/gdb/solib-svr4.c
|
||||
+++ b/gdb/solib-svr4.c
|
||||
@@ -106,6 +106,59 @@ static const char * const main_name_list[] =
|
||||
NULL
|
||||
};
|
||||
|
||||
+/* Per pspace SVR4 specific data. */
|
||||
+
|
||||
+struct svr4_info
|
||||
+{
|
||||
+ CORE_ADDR debug_base; /* Base of dynamic linker structures. */
|
||||
+
|
||||
+ /* Validity flag for debug_loader_offset. */
|
||||
+ int debug_loader_offset_p;
|
||||
+
|
||||
+ /* Load address for the dynamic linker, inferred. */
|
||||
+ CORE_ADDR debug_loader_offset;
|
||||
+
|
||||
+ /* Name of the dynamic linker, valid if debug_loader_offset_p. */
|
||||
+ char *debug_loader_name;
|
||||
+
|
||||
+ /* Load map address for the main executable. */
|
||||
+ CORE_ADDR main_lm_addr;
|
||||
+
|
||||
+ CORE_ADDR interp_text_sect_low;
|
||||
+ CORE_ADDR interp_text_sect_high;
|
||||
+ CORE_ADDR interp_plt_sect_low;
|
||||
+ CORE_ADDR interp_plt_sect_high;
|
||||
+};
|
||||
+
|
||||
+/* Per-program-space data key. */
|
||||
+static const struct program_space_data *solib_svr4_pspace_data;
|
||||
+
|
||||
+static void
|
||||
+svr4_pspace_data_cleanup (struct program_space *pspace, void *arg)
|
||||
+{
|
||||
+ struct svr4_info *info;
|
||||
+
|
||||
+ info = program_space_data (pspace, solib_svr4_pspace_data);
|
||||
+ xfree (info);
|
||||
+}
|
||||
+
|
||||
+/* Get the current svr4 data. If none is found yet, add it now. This
|
||||
+ function always returns a valid object. */
|
||||
+
|
||||
+static struct svr4_info *
|
||||
+get_svr4_info (void)
|
||||
+{
|
||||
+ struct svr4_info *info;
|
||||
+
|
||||
+ info = program_space_data (current_program_space, solib_svr4_pspace_data);
|
||||
+ if (info != NULL)
|
||||
+ return info;
|
||||
+
|
||||
+ info = XZALLOC (struct svr4_info);
|
||||
+ set_program_space_data (current_program_space, solib_svr4_pspace_data, info);
|
||||
+ return info;
|
||||
+}
|
||||
+
|
||||
/* Return non-zero if GDB_SO_NAME and INFERIOR_SO_NAME represent
|
||||
the same shared library. */
|
||||
|
||||
@@ -291,59 +344,6 @@ lm_addr_check (struct so_list *so, bfd *abfd)
|
||||
return so->lm_info->l_addr;
|
||||
}
|
||||
|
||||
-/* Per pspace SVR4 specific data. */
|
||||
-
|
||||
-struct svr4_info
|
||||
-{
|
||||
- CORE_ADDR debug_base; /* Base of dynamic linker structures. */
|
||||
-
|
||||
- /* Validity flag for debug_loader_offset. */
|
||||
- int debug_loader_offset_p;
|
||||
-
|
||||
- /* Load address for the dynamic linker, inferred. */
|
||||
- CORE_ADDR debug_loader_offset;
|
||||
-
|
||||
- /* Name of the dynamic linker, valid if debug_loader_offset_p. */
|
||||
- char *debug_loader_name;
|
||||
-
|
||||
- /* Load map address for the main executable. */
|
||||
- CORE_ADDR main_lm_addr;
|
||||
-
|
||||
- CORE_ADDR interp_text_sect_low;
|
||||
- CORE_ADDR interp_text_sect_high;
|
||||
- CORE_ADDR interp_plt_sect_low;
|
||||
- CORE_ADDR interp_plt_sect_high;
|
||||
-};
|
||||
-
|
||||
-/* Per-program-space data key. */
|
||||
-static const struct program_space_data *solib_svr4_pspace_data;
|
||||
-
|
||||
-static void
|
||||
-svr4_pspace_data_cleanup (struct program_space *pspace, void *arg)
|
||||
-{
|
||||
- struct svr4_info *info;
|
||||
-
|
||||
- info = program_space_data (pspace, solib_svr4_pspace_data);
|
||||
- xfree (info);
|
||||
-}
|
||||
-
|
||||
-/* Get the current svr4 data. If none is found yet, add it now. This
|
||||
- function always returns a valid object. */
|
||||
-
|
||||
-static struct svr4_info *
|
||||
-get_svr4_info (void)
|
||||
-{
|
||||
- struct svr4_info *info;
|
||||
-
|
||||
- info = program_space_data (current_program_space, solib_svr4_pspace_data);
|
||||
- if (info != NULL)
|
||||
- return info;
|
||||
-
|
||||
- info = XZALLOC (struct svr4_info);
|
||||
- set_program_space_data (current_program_space, solib_svr4_pspace_data, info);
|
||||
- return info;
|
||||
-}
|
||||
-
|
||||
/* Local function prototypes */
|
||||
|
||||
static int match_main (const char *);
|
17
gdb-dlopen-stap-probe-5of7.patch
Normal file
17
gdb-dlopen-stap-probe-5of7.patch
Normal file
@ -0,0 +1,17 @@
|
||||
2012-07-19 Gary Benson <gbenson@redhat.com>
|
||||
|
||||
* solib-svr4.c (svr4_info): Made debug_loader_offset_p a bitfield.
|
||||
|
||||
diff --git a/gdb/solib-svr4.c b/gdb/solib-svr4.c
|
||||
index c88b9cb..8e41f19 100644
|
||||
--- a/gdb/solib-svr4.c
|
||||
+++ b/gdb/solib-svr4.c
|
||||
@@ -113,7 +113,7 @@ struct svr4_info
|
||||
CORE_ADDR debug_base; /* Base of dynamic linker structures. */
|
||||
|
||||
/* Validity flag for debug_loader_offset. */
|
||||
- int debug_loader_offset_p;
|
||||
+ unsigned int debug_loader_offset_p : 1;
|
||||
|
||||
/* Load address for the dynamic linker, inferred. */
|
||||
CORE_ADDR debug_loader_offset;
|
1989
gdb-dlopen-stap-probe-6of7.patch
Normal file
1989
gdb-dlopen-stap-probe-6of7.patch
Normal file
File diff suppressed because it is too large
Load Diff
147
gdb-dlopen-stap-probe-7of7.patch
Normal file
147
gdb-dlopen-stap-probe-7of7.patch
Normal file
@ -0,0 +1,147 @@
|
||||
2012-07-30 Gary Benson <gbenson@redhat.com>
|
||||
|
||||
* objfiles.h (inhibit_section_map_updates): New function
|
||||
declaration.
|
||||
(resume_section_map_updates): Likewise.
|
||||
(resume_section_map_updates_cleanup): Likewise.
|
||||
* objfiles.c (objfile_pspace_info): New field "inhibit_updates".
|
||||
(find_pc_section): Do not update the section map if
|
||||
inhibit_updates is set.
|
||||
(inhibit_section_map_updates): New function.
|
||||
(resume_section_map_updates): Likewise.
|
||||
(resume_section_map_updates_cleanup): Likewise.
|
||||
* solib-svr4.c (svr4_handle_solib_event): Inhibit section map
|
||||
updates for calls to evaluate_probe_argument.
|
||||
|
||||
Index: gdb-7.4.91.20120814/gdb/objfiles.h
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120814.orig/gdb/objfiles.h 2012-08-14 17:16:54.000000000 +0200
|
||||
+++ gdb-7.4.91.20120814/gdb/objfiles.h 2012-08-14 17:20:55.913174609 +0200
|
||||
@@ -526,6 +526,22 @@ extern void set_objfile_data (struct obj
|
||||
extern void *objfile_data (struct objfile *objfile,
|
||||
const struct objfile_data *data);
|
||||
|
||||
+/* In normal use, the section map will be rebuilt by FIND_PC_SECTION
|
||||
+ if objfiles have been added, removed or relocated since it was last
|
||||
+ called. Calling INHIBIT_SECTION_MAP_UPDATES will inhibit this
|
||||
+ behavior until RESUME_SECTION_MAP_UPDATES is called. If you call
|
||||
+ INHIBIT_SECTION_MAP_UPDATES you must ensure that every call to
|
||||
+ FIND_PC_SECTION in the inhibited region relates to a section that
|
||||
+ is already in the section map and has not since been removed or
|
||||
+ relocated. */
|
||||
+extern void inhibit_section_map_updates (void);
|
||||
+
|
||||
+/* Resume automatically rebuilding the section map as required. */
|
||||
+extern void resume_section_map_updates (void);
|
||||
+
|
||||
+/* Version of the above suitable for use as a cleanup. */
|
||||
+extern void resume_section_map_updates_cleanup (void *arg);
|
||||
+
|
||||
extern void default_iterate_over_objfiles_in_search_order
|
||||
(struct gdbarch *gdbarch,
|
||||
iterate_over_objfiles_in_search_order_cb_ftype *cb,
|
||||
Index: gdb-7.4.91.20120814/gdb/objfiles.c
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120814.orig/gdb/objfiles.c 2012-08-14 17:16:55.000000000 +0200
|
||||
+++ gdb-7.4.91.20120814/gdb/objfiles.c 2012-08-14 17:20:55.915174609 +0200
|
||||
@@ -70,6 +70,9 @@ struct objfile_pspace_info
|
||||
int objfiles_changed_p;
|
||||
struct obj_section **sections;
|
||||
int num_sections;
|
||||
+
|
||||
+ /* Nonzero if section map updates should be inhibited. */
|
||||
+ int inhibit_updates;
|
||||
};
|
||||
|
||||
/* Per-program-space data key. */
|
||||
@@ -1295,7 +1298,7 @@ find_pc_section (CORE_ADDR pc)
|
||||
return s;
|
||||
|
||||
pspace_info = get_objfile_pspace_data (current_program_space);
|
||||
- if (pspace_info->objfiles_changed_p != 0)
|
||||
+ if (pspace_info->objfiles_changed_p && !pspace_info->inhibit_updates)
|
||||
{
|
||||
update_section_map (current_program_space,
|
||||
&pspace_info->sections,
|
||||
@@ -1463,6 +1466,30 @@ objfiles_changed (void)
|
||||
get_objfile_pspace_data (current_program_space)->objfiles_changed_p = 1;
|
||||
}
|
||||
|
||||
+/* See comments in objfiles.h. */
|
||||
+
|
||||
+void
|
||||
+inhibit_section_map_updates (void)
|
||||
+{
|
||||
+ get_objfile_pspace_data (current_program_space)->inhibit_updates = 1;
|
||||
+}
|
||||
+
|
||||
+/* See comments in objfiles.h. */
|
||||
+
|
||||
+void
|
||||
+resume_section_map_updates (void)
|
||||
+{
|
||||
+ get_objfile_pspace_data (current_program_space)->inhibit_updates = 0;
|
||||
+}
|
||||
+
|
||||
+/* See comments in objfiles.h. */
|
||||
+
|
||||
+void
|
||||
+resume_section_map_updates_cleanup (void *arg)
|
||||
+{
|
||||
+ resume_section_map_updates ();
|
||||
+}
|
||||
+
|
||||
/* The default implementation for the "iterate_over_objfiles_in_search_order"
|
||||
gdbarch method. It is equivalent to use the ALL_OBJFILES macro,
|
||||
searching the objfiles in the order they are stored internally,
|
||||
Index: gdb-7.4.91.20120814/gdb/solib-svr4.c
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120814.orig/gdb/solib-svr4.c 2012-08-14 17:20:42.000000000 +0200
|
||||
+++ gdb-7.4.91.20120814/gdb/solib-svr4.c 2012-08-14 17:21:14.090169216 +0200
|
||||
@@ -1847,6 +1847,7 @@ svr4_handle_solib_event (bpstat bs)
|
||||
struct svr4_info *info = get_svr4_info ();
|
||||
struct probe_and_info buf, *pi = &buf;
|
||||
enum probe_action action;
|
||||
+ struct cleanup *cleanups = NULL;
|
||||
struct value *val;
|
||||
LONGEST lmid;
|
||||
CORE_ADDR debug_base, lm = 0;
|
||||
@@ -1870,6 +1871,19 @@ svr4_handle_solib_event (bpstat bs)
|
||||
if (action == NAMESPACE_NO_ACTION)
|
||||
return;
|
||||
|
||||
+ /* EVALUATE_PROBE_ARGUMENT looks up symbols in the dynamic linker
|
||||
+ using FIND_PC_SECTION. FIND_PC_SECTION is accelerated by a cache
|
||||
+ called the section map. The section map is invalidated every
|
||||
+ time a shared library is loaded or unloaded, and if the inferior
|
||||
+ is generating a lot of shared library events then the section map
|
||||
+ will be updated every time SVR4_HANDLE_SOLIB_EVENT is called.
|
||||
+ We called FIND_PC_SECTION in SVR4_CREATE_SOLIB_EVENT_BREAKPOINTS,
|
||||
+ so we can guarantee that the dynamic linker's sections are in the
|
||||
+ section map. We can therefore inhibit section map updates across
|
||||
+ these calls to EVALUATE_PROBE_ARGUMENT and save a lot of time. */
|
||||
+ inhibit_section_map_updates ();
|
||||
+ cleanups = make_cleanup (resume_section_map_updates_cleanup, NULL);
|
||||
+
|
||||
val = evaluate_probe_argument (pi->probe, 0);
|
||||
if (val == NULL)
|
||||
goto error;
|
||||
@@ -1901,6 +1915,9 @@ svr4_handle_solib_event (bpstat bs)
|
||||
action = NAMESPACE_RELOAD;
|
||||
}
|
||||
|
||||
+ do_cleanups (cleanups);
|
||||
+ cleanups = NULL;
|
||||
+
|
||||
if (action == NAMESPACE_UPDATE_OR_RELOAD)
|
||||
{
|
||||
if (namespace_update_incremental (info, lmid, lm, is_initial_ns))
|
||||
@@ -1923,6 +1940,8 @@ svr4_handle_solib_event (bpstat bs)
|
||||
warning (_("Probes-based dynamic linker interface failed.\n"
|
||||
"Reverting to original interface.\n"));
|
||||
|
||||
+ if (cleanups != NULL)
|
||||
+ do_cleanups (cleanups);
|
||||
free_namespace_table (info);
|
||||
free_probes (info);
|
||||
info->using_probes = 0;
|
@ -305,104 +305,3 @@ Index: gdb-7.4.50.20120714/gdb/testsuite/lib/prelink-support.exp
|
||||
return $prelink_args
|
||||
}
|
||||
|
||||
Index: gdb-7.4.50.20120714/gdb/testsuite/gdb.base/break-interp.exp
|
||||
===================================================================
|
||||
--- gdb-7.4.50.20120714.orig/gdb/testsuite/gdb.base/break-interp.exp 2012-06-21 22:46:21.000000000 +0200
|
||||
+++ gdb-7.4.50.20120714/gdb/testsuite/gdb.base/break-interp.exp 2012-07-15 08:51:38.244701248 +0200
|
||||
@@ -109,14 +109,21 @@ proc strip_debug {dest} {
|
||||
}
|
||||
}
|
||||
|
||||
+# Former symbol for solib changes notifications was _dl_debug_state, newer one
|
||||
+# is dl_main (in fact _dl_debug_notify but it is inlined without any extra
|
||||
+# debug info), the right one one traps by `set stop-on-solib-events 1'.
|
||||
+
|
||||
+set solib_bp {(_dl_debug_state|dl_main)}
|
||||
+
|
||||
# Implementation of reach.
|
||||
|
||||
proc reach_1 {func command displacement} {
|
||||
- global gdb_prompt expect_out
|
||||
+ global gdb_prompt expect_out solib_bp
|
||||
|
||||
- if {$func == "_dl_debug_state"} {
|
||||
+ if {$func == $solib_bp} {
|
||||
# Breakpoint on _dl_debug_state can have problems due to its overlap
|
||||
# with the existing internal breakpoint from GDB.
|
||||
+ # With also _dl_debug_notify we would need even two breakpoints.
|
||||
gdb_test_no_output "set stop-on-solib-events 1"
|
||||
} elseif {! [gdb_breakpoint $func allow-pending]} {
|
||||
return
|
||||
@@ -142,21 +149,21 @@ proc reach_1 {func command displacement}
|
||||
exp_continue
|
||||
}
|
||||
-re "Breakpoint \[0-9\]+, \\.?(__GI_)?$func \\(.*\\) at .*:\[0-9\]+\r\n.*$gdb_prompt $" {
|
||||
- if {$func == "_dl_debug_state"} {
|
||||
+ if {$func == $solib_bp} {
|
||||
fail $test
|
||||
} else {
|
||||
pass $test
|
||||
}
|
||||
}
|
||||
-re "Breakpoint \[0-9\]+, \[0-9xa-f\]+ in \\.?(__GI_)?$func \\(\\).*\r\n$gdb_prompt $" {
|
||||
- if {$func == "_dl_debug_state"} {
|
||||
+ if {$func == $solib_bp} {
|
||||
fail $test
|
||||
} else {
|
||||
pass $test
|
||||
}
|
||||
}
|
||||
-re "Stopped due to (spurious )?shared library event.*\r\n$gdb_prompt $" {
|
||||
- if {$func == "_dl_debug_state"} {
|
||||
+ if {$func == $solib_bp} {
|
||||
if {$debug_state_count == 0} {
|
||||
# First stop does not yet relocate the _start function
|
||||
# descriptor on ppc64.
|
||||
@@ -175,7 +182,7 @@ proc reach_1 {func command displacement}
|
||||
fail $test_displacement
|
||||
}
|
||||
|
||||
- if {$func == "_dl_debug_state"} {
|
||||
+ if {$func == $solib_bp} {
|
||||
gdb_test_no_output "set stop-on-solib-events 0"
|
||||
}
|
||||
}
|
||||
@@ -357,7 +364,7 @@ proc test_attach {file displacement {rel
|
||||
}
|
||||
|
||||
proc test_ld {file ifmain trynosym displacement} {
|
||||
- global srcdir subdir gdb_prompt expect_out inferior_exited_re
|
||||
+ global srcdir subdir gdb_prompt expect_out inferior_exited_re solib_bp
|
||||
|
||||
# First test normal `file'-command loaded $FILE with symbols.
|
||||
|
||||
@@ -385,9 +392,9 @@ proc test_ld {file ifmain trynosym displ
|
||||
gdb_test_no_output "set args ${objdir}/${subdir}/$binfile_test" "set args OBJDIR/${subdir}/$binfile_test"
|
||||
}
|
||||
|
||||
- reach "_dl_debug_state" "run" $displacement
|
||||
+ reach $solib_bp "run" $displacement
|
||||
|
||||
- gdb_test "bt" "#0 +\[^\r\n\]*\\m(__GI_)?_dl_debug_state\\M.*" "dl bt"
|
||||
+ gdb_test "bt" "#0 +\[^\r\n\]*\\m(__GI_)?$solib_bp\\M.*" "dl bt"
|
||||
|
||||
if $ifmain {
|
||||
reach "main" continue "NONE"
|
||||
@@ -399,7 +406,7 @@ proc test_ld {file ifmain trynosym displ
|
||||
|
||||
# Try re-run if the new PIE displacement takes effect.
|
||||
gdb_test "kill" "" "kill" {Kill the program being debugged\? \(y or n\) } "y"
|
||||
- reach "_dl_debug_state" "run" $displacement
|
||||
+ reach $solib_bp "run" $displacement
|
||||
|
||||
if $ifmain {
|
||||
test_core $file $displacement
|
||||
@@ -431,7 +438,7 @@ proc test_ld {file ifmain trynosym displ
|
||||
gdb_test "exec-file $file" "exec-file $escapedfile" "load"
|
||||
|
||||
if $ifmain {
|
||||
- reach "_dl_debug_state" run $displacement
|
||||
+ reach $solib_bp run $displacement
|
||||
|
||||
# Use two separate gdb_test_multiple statements to avoid timeouts due
|
||||
# to slow processing of wildcard capturing long output
|
||||
|
69
gdb-dlopen-stap-probe-test2.patch
Normal file
69
gdb-dlopen-stap-probe-test2.patch
Normal file
@ -0,0 +1,69 @@
|
||||
http://sourceware.org/ml/gdb-patches/2012-08/msg00500.html
|
||||
Subject: [patch] testsuite: Make solib-corrupted.exp untested for probes [Re: [RFA 0/4 take 2] Improved linker-debugger interface]
|
||||
|
||||
On Fri, 17 Aug 2012 22:53:53 +0200, Jan Kratochvil wrote:
|
||||
> It regresses with glibc-debuginfo installed:
|
||||
>
|
||||
> info sharedlibrary^M
|
||||
> From To Syms Read Shared Object Library^M
|
||||
> 0x00007ffff7ddcb20 0x00007ffff7df63d9 Yes /lib64/ld-linux-x86-64.so.2^M
|
||||
> 0x00007ffff7ae05b0 0x00007ffff7b4ad78 Yes /lib64/libm.so.6^M
|
||||
> 0x00007ffff77431a0 0x00007ffff7883cf0 Yes /lib64/libc.so.6^M
|
||||
> (gdb) FAIL: gdb.base/solib-corrupted.exp: corrupted list
|
||||
>
|
||||
> But I guess there is no longer a way to test it with probes so it should just
|
||||
> run some 'info probes' and make this test UNTESTED if rtld probes are
|
||||
> available.
|
||||
|
||||
I had to implement it for Fedora already anyway.
|
||||
|
||||
|
||||
Regards,
|
||||
Jan
|
||||
|
||||
|
||||
gdb/testsuite/
|
||||
2012-08-18 Jan Kratochvil <jan.kratochvil@redhat.com>
|
||||
|
||||
* gdb.base/solib-corrupted.exp: New variable probes.
|
||||
(info probes): New test.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/solib-corrupted.exp b/gdb/testsuite/gdb.base/solib-corrupted.exp
|
||||
index 84b3b0c..c9f55d6 100644
|
||||
--- a/gdb/testsuite/gdb.base/solib-corrupted.exp
|
||||
+++ b/gdb/testsuite/gdb.base/solib-corrupted.exp
|
||||
@@ -36,6 +36,33 @@ if ![runto_main] {
|
||||
return
|
||||
}
|
||||
|
||||
+# With probes interface GDB no longer scans the inferior library list so its
|
||||
+# corruption cannot be tested. There is no way to disable the probes
|
||||
+# interface.
|
||||
+
|
||||
+set probes { init_start init_complete map_start reloc_complete unmap_start
|
||||
+ unmap_complete }
|
||||
+set test "info probes"
|
||||
+gdb_test_multiple $test $test {
|
||||
+ -re "^rtld\[ \t\]+(?:rtld_)?(\[a-z_\]+)\[ \t\]" {
|
||||
+ set idx [lsearch -exact $probes $expect_out(1,string)]
|
||||
+ if { $idx >= 0 } {
|
||||
+ set probes [lreplace $probes $idx $idx]
|
||||
+ }
|
||||
+ exp_continue
|
||||
+ }
|
||||
+ -re "^\[^\r\n\]*\r\n" {
|
||||
+ exp_continue
|
||||
+ }
|
||||
+ -re "^$gdb_prompt $" {
|
||||
+ }
|
||||
+}
|
||||
+if { [llength $probes] == 0 } {
|
||||
+ xfail $test
|
||||
+ untested "GDB is using probes"
|
||||
+ return
|
||||
+}
|
||||
+
|
||||
gdb_test "info sharedlibrary" "From * To .*" "normal list"
|
||||
|
||||
# GDB checks there for matching L_PREV.
|
||||
|
@ -1,357 +0,0 @@
|
||||
From: Gary Benson <gbenson@redhat.com>
|
||||
To: Jan Kratochvil <jan.kratochvil@redhat.com>
|
||||
Message-ID: <20110810133605.GB7294@redhat.com>
|
||||
|
||||
Index: gdb-7.4.91.20120801/gdb/infrun.c
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120801.orig/gdb/infrun.c 2012-08-01 18:38:24.000000000 +0200
|
||||
+++ gdb-7.4.91.20120801/gdb/infrun.c 2012-08-01 18:44:59.568518602 +0200
|
||||
@@ -361,6 +361,13 @@ static struct symbol *step_start_functio
|
||||
/* Nonzero if we want to give control to the user when we're notified
|
||||
of shared library events by the dynamic linker. */
|
||||
int stop_on_solib_events;
|
||||
+
|
||||
+static void
|
||||
+set_stop_on_solib_events (char *args, int from_tty, struct cmd_list_element *c)
|
||||
+{
|
||||
+ update_solib_breakpoints ();
|
||||
+}
|
||||
+
|
||||
static void
|
||||
show_stop_on_solib_events (struct ui_file *file, int from_tty,
|
||||
struct cmd_list_element *c, const char *value)
|
||||
@@ -7229,7 +7236,7 @@ Show stopping for shared library events.
|
||||
If nonzero, gdb will give control to the user when the dynamic linker\n\
|
||||
notifies gdb of shared library events. The most common event of interest\n\
|
||||
to the user would be loading/unloading of a new library."),
|
||||
- NULL,
|
||||
+ set_stop_on_solib_events,
|
||||
show_stop_on_solib_events,
|
||||
&setlist, &showlist);
|
||||
|
||||
Index: gdb-7.4.91.20120801/gdb/solib-svr4.c
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120801.orig/gdb/solib-svr4.c 2012-08-01 18:38:24.000000000 +0200
|
||||
+++ gdb-7.4.91.20120801/gdb/solib-svr4.c 2012-08-01 18:45:13.449441787 +0200
|
||||
@@ -47,6 +47,7 @@
|
||||
#include "auxv.h"
|
||||
#include "exceptions.h"
|
||||
#include "gdb_bfd.h"
|
||||
+#include "probe.h"
|
||||
|
||||
static struct link_map_offsets *svr4_fetch_link_map_offsets (void);
|
||||
static int svr4_have_link_map_offsets (void);
|
||||
@@ -93,6 +94,32 @@ static const char * const solib_break_na
|
||||
NULL
|
||||
};
|
||||
|
||||
+/* A list of SystemTap probes which, if present in the dynamic linker,
|
||||
+ allow more fine-grained breakpoints to be placed on shared library
|
||||
+ events. */
|
||||
+
|
||||
+struct probe_info
|
||||
+ {
|
||||
+ /* The name of the probe. */
|
||||
+ const char *name;
|
||||
+
|
||||
+ /* Nonzero if this probe must be stopped at even when
|
||||
+ stop-on-solib-events is off. */
|
||||
+ int mandatory;
|
||||
+ };
|
||||
+
|
||||
+static const struct probe_info probe_info[] =
|
||||
+{
|
||||
+ {"rtld_init_start", 0},
|
||||
+ {"rtld_init_complete", 1},
|
||||
+ {"rtld_map_start", 0},
|
||||
+ {"rtld_reloc_complete", 1},
|
||||
+ {"rtld_unmap_start", 0},
|
||||
+ {"rtld_unmap_complete", 1},
|
||||
+};
|
||||
+
|
||||
+#define NUM_PROBES (sizeof(probe_info) / sizeof(probe_info[0]))
|
||||
+
|
||||
static const char * const bkpt_names[] =
|
||||
{
|
||||
"_start",
|
||||
@@ -314,6 +341,12 @@ struct svr4_info
|
||||
CORE_ADDR interp_text_sect_high;
|
||||
CORE_ADDR interp_plt_sect_low;
|
||||
CORE_ADDR interp_plt_sect_high;
|
||||
+
|
||||
+ /* SystemTap probes. */
|
||||
+ VEC (probe_p) *probes[NUM_PROBES];
|
||||
+
|
||||
+ /* Nonzero if we are using the SystemTap interface. */
|
||||
+ int using_probes;
|
||||
};
|
||||
|
||||
/* Per-program-space data key. */
|
||||
@@ -323,8 +356,15 @@ static void
|
||||
svr4_pspace_data_cleanup (struct program_space *pspace, void *arg)
|
||||
{
|
||||
struct svr4_info *info;
|
||||
+ int i;
|
||||
|
||||
info = program_space_data (pspace, solib_svr4_pspace_data);
|
||||
+ if (info == NULL)
|
||||
+ return;
|
||||
+
|
||||
+ for (i = 0; i < NUM_PROBES; i++)
|
||||
+ VEC_free (probe_p, info->probes[i]);
|
||||
+
|
||||
xfree (info);
|
||||
}
|
||||
|
||||
@@ -1450,6 +1490,126 @@ exec_entry_point (struct bfd *abfd, stru
|
||||
targ);
|
||||
}
|
||||
|
||||
+/* Helper function for svr4_update_solib_event_breakpoints. */
|
||||
+
|
||||
+static int
|
||||
+svr4_update_solib_event_breakpoint (struct breakpoint *b, void *arg)
|
||||
+{
|
||||
+ struct svr4_info *info = get_svr4_info ();
|
||||
+ struct bp_location *loc;
|
||||
+
|
||||
+ if (b->type != bp_shlib_event)
|
||||
+ return 0;
|
||||
+
|
||||
+ for (loc = b->loc; loc; loc = loc->next)
|
||||
+ {
|
||||
+ int i;
|
||||
+
|
||||
+ for (i = 0; i < NUM_PROBES; i++)
|
||||
+ {
|
||||
+ if (!probe_info[i].mandatory)
|
||||
+ {
|
||||
+ struct probe *probe;
|
||||
+ int ix;
|
||||
+
|
||||
+ for (ix = 0;
|
||||
+ VEC_iterate (probe_p, info->probes[i], ix, probe);
|
||||
+ ++ix)
|
||||
+ {
|
||||
+ if (loc->pspace == current_program_space
|
||||
+ && loc->address == probe->address)
|
||||
+ {
|
||||
+ b->enable_state =
|
||||
+ stop_on_solib_events ? bp_enabled : bp_disabled;
|
||||
+ return 0;
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+/* Enable or disable optional solib event breakpoints as appropriate.
|
||||
+ Called whenever stop_on_solib_events is changed. */
|
||||
+
|
||||
+static void
|
||||
+svr4_update_solib_event_breakpoints (void)
|
||||
+{
|
||||
+ struct svr4_info *info = get_svr4_info ();
|
||||
+
|
||||
+ if (info->using_probes)
|
||||
+ iterate_over_breakpoints (svr4_update_solib_event_breakpoint, NULL);
|
||||
+}
|
||||
+
|
||||
+/* Both the SunOS and the SVR4 dynamic linkers call a marker function
|
||||
+ before and after mapping and unmapping shared libraries. The sole
|
||||
+ purpose of this method is to allow debuggers to set a breakpoint so
|
||||
+ they can track these changes.
|
||||
+
|
||||
+ Some versions of the glibc dynamic linker contain SystemTap probes
|
||||
+ to allow more fine grained stopping. Given the address of the
|
||||
+ original marker function, this function attempts to find these
|
||||
+ probes, and if found, sets breakpoints on those instead. If the
|
||||
+ probes aren't found, a single breakpoint is set on the original
|
||||
+ SVR4 marker function. */
|
||||
+
|
||||
+static void
|
||||
+svr4_create_solib_event_breakpoints (struct gdbarch *gdbarch, CORE_ADDR address)
|
||||
+{
|
||||
+ struct svr4_info *info = get_svr4_info ();
|
||||
+ struct obj_section *os;
|
||||
+
|
||||
+ os = find_pc_section (address);
|
||||
+ if (os != NULL)
|
||||
+ {
|
||||
+ int all_probes_found = 1;
|
||||
+ int i;
|
||||
+
|
||||
+ for (i = 0; i < NUM_PROBES; i++)
|
||||
+ {
|
||||
+ info->probes[i] = find_probes_in_objfile (os->objfile, "rtld",
|
||||
+ probe_info[i].name);
|
||||
+
|
||||
+ if (!VEC_length(probe_p, info->probes[i]))
|
||||
+ {
|
||||
+ int j;
|
||||
+
|
||||
+ for (j = i - 1; j >= 0; j--)
|
||||
+ {
|
||||
+ VEC_free (probe_p, info->probes[j]);
|
||||
+ info->probes[j] = NULL;
|
||||
+ }
|
||||
+
|
||||
+ all_probes_found = 0;
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (all_probes_found)
|
||||
+ {
|
||||
+ info->using_probes = 1;
|
||||
+
|
||||
+ for (i = 0; i < NUM_PROBES; i++)
|
||||
+ {
|
||||
+ struct probe *probe;
|
||||
+ int ix;
|
||||
+
|
||||
+ for (ix = 0;
|
||||
+ VEC_iterate (probe_p, info->probes[i], ix, probe);
|
||||
+ ++ix)
|
||||
+ create_solib_event_breakpoint (gdbarch, probe->address);
|
||||
+ }
|
||||
+
|
||||
+ svr4_update_solib_event_breakpoints ();
|
||||
+ return;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ create_solib_event_breakpoint (gdbarch, address);
|
||||
+}
|
||||
+
|
||||
/* Helper function for gdb_bfd_lookup_symbol. */
|
||||
|
||||
static int
|
||||
@@ -1498,10 +1658,18 @@ enable_break (struct svr4_info *info, in
|
||||
asection *interp_sect;
|
||||
gdb_byte *interp_name;
|
||||
CORE_ADDR sym_addr;
|
||||
+ int i;
|
||||
|
||||
info->interp_text_sect_low = info->interp_text_sect_high = 0;
|
||||
info->interp_plt_sect_low = info->interp_plt_sect_high = 0;
|
||||
|
||||
+ for (i = 0; i < NUM_PROBES; i++)
|
||||
+ {
|
||||
+ VEC_free (probe_p, info->probes[i]);
|
||||
+ info->probes[i] = NULL;
|
||||
+ }
|
||||
+ info->using_probes = 0;
|
||||
+
|
||||
/* If we already have a shared library list in the target, and
|
||||
r_debug contains r_brk, set the breakpoint there - this should
|
||||
mean r_brk has already been relocated. Assume the dynamic linker
|
||||
@@ -1533,7 +1701,7 @@ enable_break (struct svr4_info *info, in
|
||||
That knowledge is encoded in the address, if it's Thumb the low bit
|
||||
is 1. However, we've stripped that info above and it's not clear
|
||||
what all the consequences are of passing a non-addr_bits_remove'd
|
||||
- address to create_solib_event_breakpoint. The call to
|
||||
+ address to svr4_create_solib_event_breakpoints. The call to
|
||||
find_pc_section verifies we know about the address and have some
|
||||
hope of computing the right kind of breakpoint to use (via
|
||||
symbol info). It does mean that GDB needs to be pointed at a
|
||||
@@ -1571,7 +1739,7 @@ enable_break (struct svr4_info *info, in
|
||||
+ bfd_section_size (tmp_bfd, interp_sect);
|
||||
}
|
||||
|
||||
- create_solib_event_breakpoint (target_gdbarch, sym_addr);
|
||||
+ svr4_create_solib_event_breakpoints (target_gdbarch, sym_addr);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@@ -1729,7 +1897,8 @@ enable_break (struct svr4_info *info, in
|
||||
|
||||
if (sym_addr != 0)
|
||||
{
|
||||
- create_solib_event_breakpoint (target_gdbarch, load_addr + sym_addr);
|
||||
+ svr4_create_solib_event_breakpoints (target_gdbarch,
|
||||
+ load_addr + sym_addr);
|
||||
xfree (interp_name);
|
||||
return 1;
|
||||
}
|
||||
@@ -1755,7 +1924,7 @@ enable_break (struct svr4_info *info, in
|
||||
sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch,
|
||||
sym_addr,
|
||||
¤t_target);
|
||||
- create_solib_event_breakpoint (target_gdbarch, sym_addr);
|
||||
+ svr4_create_solib_event_breakpoints (target_gdbarch, sym_addr);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@@ -1771,7 +1940,7 @@ enable_break (struct svr4_info *info, in
|
||||
sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch,
|
||||
sym_addr,
|
||||
¤t_target);
|
||||
- create_solib_event_breakpoint (target_gdbarch, sym_addr);
|
||||
+ svr4_create_solib_event_breakpoints (target_gdbarch, sym_addr);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@@ -2547,4 +2716,5 @@ _initialize_svr4_solib (void)
|
||||
svr4_so_ops.lookup_lib_global_symbol = elf_lookup_lib_symbol;
|
||||
svr4_so_ops.same = svr4_same;
|
||||
svr4_so_ops.keep_data_in_core = svr4_keep_data_in_core;
|
||||
+ svr4_so_ops.update_breakpoints = svr4_update_solib_event_breakpoints;
|
||||
}
|
||||
Index: gdb-7.4.91.20120801/gdb/solib.c
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120801.orig/gdb/solib.c 2012-08-01 18:38:24.000000000 +0200
|
||||
+++ gdb-7.4.91.20120801/gdb/solib.c 2012-08-01 18:44:59.573518572 +0200
|
||||
@@ -1226,6 +1226,18 @@ no_shared_libraries (char *ignored, int
|
||||
objfile_purge_solibs ();
|
||||
}
|
||||
|
||||
+/* Enable or disable optional solib event breakpoints as appropriate. */
|
||||
+
|
||||
+void
|
||||
+update_solib_breakpoints (void)
|
||||
+{
|
||||
+ struct target_so_ops *ops = solib_ops (target_gdbarch);
|
||||
+
|
||||
+ if (ops->update_breakpoints != NULL)
|
||||
+ ops->update_breakpoints ();
|
||||
+}
|
||||
+
|
||||
+
|
||||
/* Reload shared libraries, but avoid reloading the same symbol file
|
||||
we already have loaded. */
|
||||
|
||||
Index: gdb-7.4.91.20120801/gdb/solib.h
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120801.orig/gdb/solib.h 2012-02-03 16:19:37.000000000 +0100
|
||||
+++ gdb-7.4.91.20120801/gdb/solib.h 2012-08-01 18:44:59.574518566 +0200
|
||||
@@ -91,4 +91,8 @@ extern CORE_ADDR gdb_bfd_lookup_symbol_f
|
||||
void *),
|
||||
void *data);
|
||||
|
||||
+/* Enable or disable optional solib event breakpoints as appropriate. */
|
||||
+
|
||||
+extern void update_solib_breakpoints (void);
|
||||
+
|
||||
#endif /* SOLIB_H */
|
||||
Index: gdb-7.4.91.20120801/gdb/solist.h
|
||||
===================================================================
|
||||
--- gdb-7.4.91.20120801.orig/gdb/solist.h 2012-01-04 09:17:11.000000000 +0100
|
||||
+++ gdb-7.4.91.20120801/gdb/solist.h 2012-08-01 18:44:59.574518566 +0200
|
||||
@@ -149,6 +149,13 @@ struct target_so_ops
|
||||
core file (in particular, for readonly sections). */
|
||||
int (*keep_data_in_core) (CORE_ADDR vaddr,
|
||||
unsigned long size);
|
||||
+
|
||||
+ /* Enable or disable optional solib event breakpoints as
|
||||
+ appropriate. This should be called whenever
|
||||
+ stop_on_solib_events is changed. This pointer can be
|
||||
+ NULL, in which case no enabling or disabling is necessary
|
||||
+ for this target. */
|
||||
+ void (*update_breakpoints) (void);
|
||||
};
|
||||
|
||||
/* Free the memory associated with a (so_list *). */
|
36
gdb.spec
36
gdb.spec
@ -27,20 +27,20 @@
|
||||
Summary: A GNU source-level debugger for C, C++, Fortran, Go and other languages
|
||||
Name: %{?scl_prefix}gdb
|
||||
|
||||
%global snap 20120801
|
||||
# See tempstamp of source gnulib installed into gdb/gnulib/ .
|
||||
%global snap 20120817
|
||||
# See timestamp of source gnulib installed into gdb/gnulib/ .
|
||||
%global snapgnulib 20120623
|
||||
Version: 7.4.91.%{snap}
|
||||
Version: 7.5
|
||||
|
||||
# The release always contains a leading reserved number, start it at 1.
|
||||
# `upstream' is not a part of `name' to stay fully rpm dependencies compatible for the testing.
|
||||
Release: 18%{?dist}
|
||||
Release: 19%{?dist}
|
||||
|
||||
License: GPLv3+ and GPLv3+ with exceptions and GPLv2+ and GPLv2+ with exceptions and GPL+ and LGPLv2+ and BSD and Public Domain
|
||||
Group: Development/Debuggers
|
||||
# Do not provide URL for snapshots as the file lasts there only for 2 days.
|
||||
# ftp://sourceware.org/pub/gdb/releases/gdb-%{version}.tar.bz2
|
||||
Source: gdb-%{version}.tar.bz2
|
||||
Source: ftp://sourceware.org/pub/gdb/releases/gdb-%{version}.tar.bz2
|
||||
Buildroot: %(mktemp -ud %{_tmppath}/%{name}-%{version}-%{release}-XXXXXX)
|
||||
URL: http://gnu.org/software/gdb/
|
||||
|
||||
@ -512,8 +512,15 @@ Patch579: gdb-7.2.50-sparc-add-workaround-to-broken-debug-files.patch
|
||||
|
||||
# Fix dlopen of libpthread.so, patched glibc required (Gary Benson, BZ 669432).
|
||||
#=push
|
||||
Patch618: gdb-dlopen-stap-probe.patch
|
||||
Patch618: gdb-dlopen-stap-probe-1of7.patch
|
||||
Patch717: gdb-dlopen-stap-probe-2of7.patch
|
||||
Patch718: gdb-dlopen-stap-probe-3of7.patch
|
||||
Patch719: gdb-dlopen-stap-probe-4of7.patch
|
||||
Patch720: gdb-dlopen-stap-probe-5of7.patch
|
||||
Patch721: gdb-dlopen-stap-probe-6of7.patch
|
||||
Patch722: gdb-dlopen-stap-probe-7of7.patch
|
||||
Patch619: gdb-dlopen-stap-probe-test.patch
|
||||
Patch723: gdb-dlopen-stap-probe-test2.patch
|
||||
|
||||
# Work around PR libc/13097 "linux-vdso.so.1" warning message.
|
||||
#=push
|
||||
@ -848,6 +855,13 @@ rm -f gdb/jv-exp.c gdb/m2-exp.c gdb/objc-exp.c gdb/p-exp.c gdb/go-exp.c
|
||||
%patch548 -p1
|
||||
%patch579 -p1
|
||||
%patch618 -p1
|
||||
%patch717 -p1
|
||||
%patch718 -p1
|
||||
%patch719 -p1
|
||||
%patch720 -p1
|
||||
%patch721 -p1
|
||||
%patch722 -p1
|
||||
%patch723 -p1
|
||||
%patch619 -p1
|
||||
%patch627 -p1
|
||||
%patch634 -p1
|
||||
@ -1355,7 +1369,11 @@ fi
|
||||
%endif # 0%{!?el5:1} || "%{_target_cpu}" == "noarch"
|
||||
|
||||
%changelog
|
||||
* Fri Aug 17 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.4.91.20120801-18
|
||||
* Sat Aug 18 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.5-19.fc18
|
||||
- Rebase to FSF GDB 7.5.
|
||||
- Update dlopen to support two variants of glibc (Gary Benson, BZ 669432).
|
||||
|
||||
* Fri Aug 17 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.4.91.20120801-18.fc18
|
||||
- Drop Source URL for snapshots.
|
||||
- Separate %%{snapgnulib} from %%{snap}.
|
||||
- Fix %%{libstdcxxpython} to be %%{name}-prefixed.
|
||||
@ -1363,11 +1381,11 @@ fi
|
||||
- Include RHEL-5 compatible %%{buildroot} cleanup.
|
||||
- Use %%__global_ldflags.
|
||||
|
||||
* Wed Aug 1 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.4.91.20120801-17
|
||||
* Wed Aug 1 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.4.91.20120801-17.fc18
|
||||
- Rebase to FSF GDB 7.4.91.20120801.
|
||||
- [dwz] Rebase it from FSF GDB HEAD.
|
||||
|
||||
* Thu Jul 19 2012 Fedora Release Engineering <rel-eng@lists.fedoraproject.org> - 7.4.50.20120714-16
|
||||
* Thu Jul 19 2012 Fedora Release Engineering <rel-eng@lists.fedoraproject.org> - 7.4.50.20120714-16.fc18
|
||||
- Rebuilt for https://fedoraproject.org/wiki/Fedora_18_Mass_Rebuild
|
||||
|
||||
* Mon Jul 16 2012 Jan Kratochvil <jan.kratochvil@redhat.com> - 7.4.50.20120714-15.fc18
|
||||
|
Loading…
Reference in New Issue
Block a user