diff options
Diffstat (limited to 'gdb/python/py-stopevent.c')
-rw-r--r-- | gdb/python/py-stopevent.c | 65 |
1 files changed, 60 insertions, 5 deletions
diff --git a/gdb/python/py-stopevent.c b/gdb/python/py-stopevent.c index 0aa9d53..f395e8c 100644 --- a/gdb/python/py-stopevent.c +++ b/gdb/python/py-stopevent.c @@ -19,12 +19,61 @@ #include "defs.h" #include "py-stopevent.h" +#include "py-uiout.h" gdbpy_ref<> -create_stop_event_object (PyTypeObject *py_type) +create_stop_event_object (PyTypeObject *py_type, const gdbpy_ref<> &dict) { gdbpy_ref<> thread = py_get_event_thread (inferior_ptid); - return create_thread_event_object (py_type, thread.get ()); + if (thread == nullptr) + return nullptr; + + gdbpy_ref<> result = create_thread_event_object (py_type, thread.get ()); + if (result == nullptr) + return nullptr; + + if (evpy_add_attribute (result.get (), "details", dict.get ()) < 0) + return nullptr; + + return result; +} + +/* Print BPSTAT to a new Python dictionary. Returns the dictionary, + or null if a Python exception occurred. */ + +static gdbpy_ref<> +py_print_bpstat (bpstat *bs, enum gdb_signal stop_signal) +{ + py_ui_out uiout; + + try + { + scoped_restore save_uiout = make_scoped_restore (¤t_uiout, &uiout); + + thread_info *tp = inferior_thread (); + if (tp->thread_fsm () != nullptr && tp->thread_fsm ()->finished_p ()) + { + async_reply_reason reason = tp->thread_fsm ()->async_reply_reason (); + uiout.field_string ("reason", async_reason_lookup (reason)); + } + + if (stop_signal != GDB_SIGNAL_0 && stop_signal != GDB_SIGNAL_TRAP) + print_signal_received_reason (&uiout, stop_signal); + else + { + struct target_waitstatus last; + get_last_target_status (nullptr, nullptr, &last); + + bpstat_print (bs, last.kind ()); + } + } + catch (const gdb_exception &except) + { + gdbpy_convert_exception (except); + return nullptr; + } + + return uiout.result (); } /* Callback observers when a stop event occurs. This function will create a @@ -45,6 +94,10 @@ emit_stop_event (struct bpstat *bs, enum gdb_signal stop_signal) if (evregpy_no_listeners_p (gdb_py_events.stop)) return 0; + gdbpy_ref<> dict = py_print_bpstat (bs, stop_signal); + if (dict == nullptr) + return -1; + /* Add any breakpoint set at this location to the list. */ for (current_bs = bs; current_bs != NULL; current_bs = current_bs->next) { @@ -71,7 +124,8 @@ emit_stop_event (struct bpstat *bs, enum gdb_signal stop_signal) if (list != NULL) { - stop_event_obj = create_breakpoint_event_object (list.get (), + stop_event_obj = create_breakpoint_event_object (dict, + list.get (), first_bp); if (stop_event_obj == NULL) return -1; @@ -81,7 +135,7 @@ emit_stop_event (struct bpstat *bs, enum gdb_signal stop_signal) if (stop_signal != GDB_SIGNAL_0 && stop_signal != GDB_SIGNAL_TRAP) { - stop_event_obj = create_signal_event_object (stop_signal); + stop_event_obj = create_signal_event_object (dict, stop_signal); if (stop_event_obj == NULL) return -1; } @@ -90,7 +144,8 @@ emit_stop_event (struct bpstat *bs, enum gdb_signal stop_signal) be known and this should eventually be unused. */ if (stop_event_obj == NULL) { - stop_event_obj = create_stop_event_object (&stop_event_object_type); + stop_event_obj = create_stop_event_object (&stop_event_object_type, + dict); if (stop_event_obj == NULL) return -1; } |