diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 329080e645c..98a6285dd84 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,19 @@ +2019-12-10 George Barrett + + Fix scripted probe breakpoints. + * breakpoint.c (tracepoint_probe_breakpoint_ops): Move + declaration forward. + (breakpoint_ops_for_event_location_type) + (breakpoint_ops_for_event_location): Add function definitions. + (break_command_1, trace_command): Use + breakpoint_ops_for_event_location. + * breakpoint.h (breakpoint_ops_for_event_location): Add function + declarations. + * guile/scm-breakpoint.c (gdbscm_register_breakpoint_x): Use + breakpoint_ops_for_event_location. + * python/py-breakpoint.c (bppy_init): Use + breakpoint_ops_for_event_location. + 2019-12-09 Tankut Baris Aktemur * gdbtypes.c (rank_one_type): Return INCOMPATIBLE_TYPE_BADNESS diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c index 583f46d8521..904abda8db1 100644 --- a/gdb/breakpoint.c +++ b/gdb/breakpoint.c @@ -246,6 +246,9 @@ struct breakpoint_ops bkpt_breakpoint_ops; /* Breakpoints set on probes. */ static struct breakpoint_ops bkpt_probe_breakpoint_ops; +/* Tracepoints set on probes. */ +static struct breakpoint_ops tracepoint_probe_breakpoint_ops; + /* Dynamic printf class type. */ struct breakpoint_ops dprintf_breakpoint_ops; @@ -9163,6 +9166,41 @@ decode_static_tracepoint_spec (const char **arg_p) return sals; } +/* Returns the breakpoint ops appropriate for use with with LOCATION_TYPE and + according to IS_TRACEPOINT. */ + +static const struct breakpoint_ops * +breakpoint_ops_for_event_location_type (enum event_location_type location_type, + bool is_tracepoint) +{ + if (is_tracepoint) + { + if (location_type == PROBE_LOCATION) + return &tracepoint_probe_breakpoint_ops; + else + return &tracepoint_breakpoint_ops; + } + else + { + if (location_type == PROBE_LOCATION) + return &bkpt_probe_breakpoint_ops; + else + return &bkpt_breakpoint_ops; + } +} + +/* See breakpoint.h. */ + +const struct breakpoint_ops * +breakpoint_ops_for_event_location (const struct event_location *location, + bool is_tracepoint) +{ + if (location != nullptr) + return breakpoint_ops_for_event_location_type + (event_location_type (location), is_tracepoint); + return is_tracepoint ? &tracepoint_breakpoint_ops : &bkpt_breakpoint_ops; +} + /* See breakpoint.h. */ int @@ -9344,16 +9382,10 @@ break_command_1 (const char *arg, int flag, int from_tty) enum bptype type_wanted = (flag & BP_HARDWAREFLAG ? bp_hardware_breakpoint : bp_breakpoint); - struct breakpoint_ops *ops; event_location_up location = string_to_event_location (&arg, current_language); - - /* Matching breakpoints on probes. */ - if (location != NULL - && event_location_type (location.get ()) == PROBE_LOCATION) - ops = &bkpt_probe_breakpoint_ops; - else - ops = &bkpt_breakpoint_ops; + const struct breakpoint_ops *ops = breakpoint_ops_for_event_location + (location.get (), false /* is_tracepoint */); create_breakpoint (get_current_arch (), location.get (), @@ -12802,8 +12834,7 @@ tracepoint_decode_location (struct breakpoint *b, struct breakpoint_ops tracepoint_breakpoint_ops; -/* The breakpoint_ops structure to be use on tracepoints placed in a - static probe. */ +/* Virtual table for tracepoints on static probes. */ static void tracepoint_probe_create_sals_from_location @@ -12824,8 +12855,6 @@ tracepoint_probe_decode_location (struct breakpoint *b, return bkpt_probe_decode_location (b, location, search_pspace); } -static struct breakpoint_ops tracepoint_probe_breakpoint_ops; - /* Dprintf breakpoint_ops methods. */ static void @@ -14467,15 +14496,10 @@ set_tracepoint_count (int num) static void trace_command (const char *arg, int from_tty) { - struct breakpoint_ops *ops; - event_location_up location = string_to_event_location (&arg, current_language); - if (location != NULL - && event_location_type (location.get ()) == PROBE_LOCATION) - ops = &tracepoint_probe_breakpoint_ops; - else - ops = &tracepoint_breakpoint_ops; + const struct breakpoint_ops *ops = breakpoint_ops_for_event_location + (location.get (), true /* is_tracepoint */); create_breakpoint (get_current_arch (), location.get (), diff --git a/gdb/breakpoint.h b/gdb/breakpoint.h index a9d689d02a2..3197854d3cd 100644 --- a/gdb/breakpoint.h +++ b/gdb/breakpoint.h @@ -1352,6 +1352,15 @@ extern void init_catchpoint (struct breakpoint *b, extern void install_breakpoint (int internal, std::unique_ptr &&b, int update_gll); +/* Returns the breakpoint ops appropriate for use with with LOCATION and + according to IS_TRACEPOINT. Use this to ensure, for example, that you pass + the correct ops to create_breakpoint for probe locations. If LOCATION is + NULL, returns bkpt_breakpoint_ops (or tracepoint_breakpoint_ops, if + IS_TRACEPOINT is true). */ + +extern const struct breakpoint_ops *breakpoint_ops_for_event_location + (const struct event_location *location, bool is_tracepoint); + /* Flags that can be passed down to create_breakpoint, etc., to affect breakpoint creation in several ways. */ diff --git a/gdb/guile/scm-breakpoint.c b/gdb/guile/scm-breakpoint.c index a75daa00019..a6404d544b3 100644 --- a/gdb/guile/scm-breakpoint.c +++ b/gdb/guile/scm-breakpoint.c @@ -437,13 +437,15 @@ gdbscm_register_breakpoint_x (SCM self) { case bp_breakpoint: { + const breakpoint_ops *ops = + breakpoint_ops_for_event_location (eloc.get (), false); create_breakpoint (get_current_arch (), eloc.get (), NULL, -1, NULL, 0, 0, bp_breakpoint, 0, AUTO_BOOLEAN_TRUE, - &bkpt_breakpoint_ops, + ops, 0, 1, internal, 0); break; } diff --git a/gdb/python/py-breakpoint.c b/gdb/python/py-breakpoint.c index 4170737416c..32494aec72b 100644 --- a/gdb/python/py-breakpoint.c +++ b/gdb/python/py-breakpoint.c @@ -828,13 +828,16 @@ bppy_init (PyObject *self, PyObject *args, PyObject *kwargs) location = new_explicit_location (&explicit_loc); } + const struct breakpoint_ops *ops = + breakpoint_ops_for_event_location (location.get (), false); + create_breakpoint (python_gdbarch, location.get (), NULL, -1, NULL, 0, temporary_bp, bp_breakpoint, 0, AUTO_BOOLEAN_TRUE, - &bkpt_breakpoint_ops, + ops, 0, 1, internal_bp, 0); break; } diff --git a/gdb/testsuite/ChangeLog b/gdb/testsuite/ChangeLog index 123344ffd8e..c14c341ade8 100644 --- a/gdb/testsuite/ChangeLog +++ b/gdb/testsuite/ChangeLog @@ -1,3 +1,12 @@ +2019-12-10 George Barrett + + Test scripted probe breakpoints. + * gdb.guile/scm-breakpoint.c (main): Add probe point. + * gdb.python/py-breakpoint.c (main): Likewise. + * gdb.guile/scm-breakpoint.exp (test_bkpt_probe): Add probe + specifier test. + * gdb.python/py-breakpoint.exp (test_bkpt_probe): Likewise. + 2019-12-09 Tankut Baris Aktemur * gdb.cp/rvalue-ref-overload.cc (g): New function that takes diff --git a/gdb/testsuite/gdb.guile/scm-breakpoint.c b/gdb/testsuite/gdb.guile/scm-breakpoint.c index 1670041677d..ed7dbdba917 100644 --- a/gdb/testsuite/gdb.guile/scm-breakpoint.c +++ b/gdb/testsuite/gdb.guile/scm-breakpoint.c @@ -15,6 +15,10 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . */ +#ifdef USE_PROBES +#include +#endif + int result = 0; int multiply (int i) @@ -38,6 +42,9 @@ int main (int argc, char *argv[]) { result += multiply (foo); /* Break at multiply. */ result += add (bar); /* Break at add. */ +#ifdef USE_PROBES + DTRACE_PROBE1 (test, result_updated, result); +#endif } return 0; /* Break at end. */ diff --git a/gdb/testsuite/gdb.guile/scm-breakpoint.exp b/gdb/testsuite/gdb.guile/scm-breakpoint.exp index 47bc80c2c8a..183ad1671f5 100644 --- a/gdb/testsuite/gdb.guile/scm-breakpoint.exp +++ b/gdb/testsuite/gdb.guile/scm-breakpoint.exp @@ -499,6 +499,28 @@ proc test_bkpt_address {} { ".*Breakpoint ($decimal)+ at .*$srcfile, line ($decimal)+\." } +proc test_bkpt_probe {} { + global decimal hex testfile srcfile + + if { [prepare_for_testing "failed to prepare" ${testfile}-probes \ + ${srcfile} {additional_flags=-DUSE_PROBES}] } { + return -1 + } + + if ![gdb_guile_runto_main] then { + return + } + + gdb_scm_test_silent_cmd \ + "guile (define bp1 (make-breakpoint \"-probe test:result_updated\"))" \ + "create probe breakpoint" + + gdb_test \ + "guile (register-breakpoint! bp1)" \ + "Breakpoint $decimal at $hex" \ + "register probe breakpoint" +} + test_bkpt_basic test_bkpt_deletion test_bkpt_cond_and_cmds @@ -508,3 +530,4 @@ test_bkpt_internal test_bkpt_eval_funcs test_bkpt_registration test_bkpt_address +test_bkpt_probe diff --git a/gdb/testsuite/gdb.python/py-breakpoint.c b/gdb/testsuite/gdb.python/py-breakpoint.c index d102a5f306e..12adc99a1b5 100644 --- a/gdb/testsuite/gdb.python/py-breakpoint.c +++ b/gdb/testsuite/gdb.python/py-breakpoint.c @@ -15,6 +15,10 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . */ +#ifdef USE_PROBES +#include +#endif + int result = 0; namespace foo_ns @@ -46,6 +50,9 @@ int main (int argc, char *argv[]) { result += multiply (foo); /* Break at multiply. */ result += add (bar); /* Break at add. */ +#ifdef USE_PROBES + DTRACE_PROBE1 (test, result_updated, result); +#endif } return 0; /* Break at end. */ diff --git a/gdb/testsuite/gdb.python/py-breakpoint.exp b/gdb/testsuite/gdb.python/py-breakpoint.exp index 625977c0ad4..95f2b2905d3 100644 --- a/gdb/testsuite/gdb.python/py-breakpoint.exp +++ b/gdb/testsuite/gdb.python/py-breakpoint.exp @@ -695,6 +695,25 @@ proc_with_prefix test_bkpt_qualified {} { "-q in spec string and qualified false" } +proc_with_prefix test_bkpt_probe {} { + global decimal hex testfile srcfile + + if { [prepare_for_testing "failed to prepare" ${testfile}-probes \ + ${srcfile} {debug c++ additional_flags=-DUSE_PROBES}] } { + return -1 + } + + if ![runto_main] then { + fail "cannot run to main." + return 0 + } + + gdb_test \ + "python gdb.Breakpoint(\"-probe test:result_updated\")" \ + "Breakpoint $decimal at $hex" \ + "-probe in spec string" +} + test_bkpt_basic test_bkpt_deletion test_bkpt_cond_and_cmds @@ -708,3 +727,4 @@ test_bkpt_pending test_bkpt_events test_bkpt_explicit_loc test_bkpt_qualified +test_bkpt_probe