/* Return a borrowed reference to the Python object of type Inferior representing INFERIOR. If the object has already been created, return it, otherwise, create it. Return NULL on failure. */ PyObject * inferior_to_inferior_object (struct inferior *inferior) { inferior_object *inf_obj; inf_obj = inferior_data (inferior, infpy_inf_data_key); if (!inf_obj) { struct cleanup *cleanup; cleanup = ensure_python_env (python_gdbarch, python_language); inf_obj = PyObject_New (inferior_object, &inferior_object_type); if (!inf_obj) { do_cleanups (cleanup); return NULL; } inf_obj->inferior = inferior; inf_obj->threads = NULL; inf_obj->nthreads = 0; set_inferior_data (inferior, infpy_inf_data_key, inf_obj); do_cleanups (cleanup); } return (PyObject *) inf_obj; }
static void add_thread_object (struct thread_info *tp) { struct cleanup *cleanup; thread_object *thread_obj; inferior_object *inf_obj; struct threadlist_entry *entry; if (!gdb_python_initialized) return; cleanup = ensure_python_env (python_gdbarch, python_language); thread_obj = create_thread_object (tp); if (!thread_obj) { gdbpy_print_stack (); do_cleanups (cleanup); return; } inf_obj = (inferior_object *) thread_obj->inf_obj; entry = xmalloc (sizeof (struct threadlist_entry)); entry->thread_obj = thread_obj; entry->next = inf_obj->threads; inf_obj->threads = entry; inf_obj->nthreads++; do_cleanups (cleanup); }
static void python_command (char *arg, int from_tty) { struct cleanup *cleanup; cleanup = ensure_python_env (get_current_arch (), current_language); make_cleanup_restore_integer (&interpreter_async); interpreter_async = 0; while (arg && *arg && isspace (*arg)) ++arg; if (arg && *arg) { if (PyRun_SimpleString (arg)) error (_("Error while executing Python code.")); } else { struct command_line *l = get_command_line (python_control, ""); make_cleanup_free_command_lines (&l); execute_control_command_untraced (l); } do_cleanups (cleanup); }
static void delete_thread_object (struct thread_info *tp, int ignore) { struct cleanup *cleanup; inferior_object *inf_obj; thread_object *thread_obj; struct threadlist_entry **entry, *tmp; inf_obj = (inferior_object *) find_inferior_object (PIDGET(tp->ptid)); if (!inf_obj) return; /* Find thread entry in its inferior's thread_list. */ for (entry = &inf_obj->threads; *entry != NULL; entry = &(*entry)->next) if ((*entry)->thread_obj->thread == tp) break; if (!*entry) return; cleanup = ensure_python_env (python_gdbarch, python_language); tmp = *entry; tmp->thread_obj->thread = NULL; *entry = (*entry)->next; inf_obj->nthreads--; Py_DECREF (tmp->thread_obj); xfree (tmp); do_cleanups (cleanup); }
static void python_new_objfile (struct objfile *objfile) { struct cleanup *cleanup; if (!gdb_python_initialized) return; cleanup = ensure_python_env (objfile != NULL ? get_objfile_arch (objfile) : target_gdbarch (), current_language); if (objfile == NULL) { if (emit_clear_objfiles_event () < 0) gdbpy_print_stack (); } else { if (emit_new_objfile_event (objfile) < 0) gdbpy_print_stack (); } do_cleanups (cleanup); }
/* Clear the OBJFILE pointer in an Objfile object and remove the reference. */ static void py_free_objfile (struct objfile *objfile, void *datum) { struct cleanup *cleanup; objfile_object *object = datum; cleanup = ensure_python_env (get_objfile_arch (objfile), current_language); object->objfile = NULL; Py_DECREF ((PyObject *) object); do_cleanups (cleanup); }
static void python_on_register_change (struct frame_info *frame, int regnum) { struct cleanup *cleanup; cleanup = ensure_python_env (target_gdbarch (), current_language); if (emit_register_changed_event (frame, regnum) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void python_on_memory_change (struct inferior *inferior, CORE_ADDR addr, ssize_t len, const bfd_byte *data) { struct cleanup *cleanup; cleanup = ensure_python_env (target_gdbarch (), current_language); if (emit_memory_changed_event (addr, len) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void python_on_inferior_call_post (ptid_t thread, CORE_ADDR address) { struct cleanup *cleanup; cleanup = ensure_python_env (target_gdbarch (), current_language); if (emit_inferior_call_event (INFERIOR_CALL_POST, thread, address) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void py_free_pspace (struct program_space *pspace, void *datum) { struct cleanup *cleanup; pspace_object *object = datum; struct gdbarch *arch = get_current_arch (); cleanup = ensure_python_env (arch, current_language); object->pspace = NULL; Py_DECREF ((PyObject *) object); do_cleanups (cleanup); }
static void python_on_resume (ptid_t ptid) { struct cleanup *cleanup; if (!gdb_python_initialized) return; cleanup = ensure_python_env (target_gdbarch (), current_language); if (emit_continue_event (ptid) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void python_new_objfile (struct objfile *objfile) { struct cleanup *cleanup; if (objfile == NULL) return; if (!gdb_python_initialized) return; cleanup = ensure_python_env (get_objfile_arch (objfile), current_language); if (emit_new_objfile_event (objfile) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void python_inferior_exit (struct inferior *inf) { struct cleanup *cleanup; const LONGEST *exit_code = NULL; if (!gdb_python_initialized) return; cleanup = ensure_python_env (target_gdbarch (), current_language); if (inf->has_exit_code) exit_code = &inf->exit_code; if (emit_exited_event (exit_code, inf) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static struct value * fnpy_call (struct gdbarch *gdbarch, const struct language_defn *language, void *cookie, int argc, struct value **argv) { struct value *value = NULL; PyObject *result, *callable, *args; struct cleanup *cleanup; cleanup = ensure_python_env (gdbarch, language); args = convert_values_to_python (argc, argv); callable = PyObject_GetAttrString ((PyObject *) cookie, "invoke"); if (! callable) { Py_DECREF (args); error (_("No method named 'invoke' in object.")); } result = PyObject_Call (callable, args, NULL); Py_DECREF (callable); Py_DECREF (args); if (!result) { gdbpy_print_stack (); error (_("Error while executing Python code.")); } value = convert_value_from_python (result); if (value == NULL) { Py_DECREF (result); gdbpy_print_stack (); error (_("Error while executing Python code.")); } Py_DECREF (result); do_cleanups (cleanup); return value; }
void eval_python_from_control_command (struct command_line *cmd) { int ret; char *script; struct cleanup *cleanup; if (cmd->body_count != 1) error (_("Invalid \"python\" block structure.")); cleanup = ensure_python_env (get_current_arch (), current_language); script = compute_python_string (cmd->body_list[0]); ret = PyRun_SimpleString (script); xfree (script); if (ret) error (_("Error while executing Python code.")); do_cleanups (cleanup); }
static void python_on_normal_stop (struct bpstats *bs, int print_frame) { struct cleanup *cleanup; enum gdb_signal stop_signal; if (!gdb_python_initialized) return; if (!find_thread_ptid (inferior_ptid)) return; stop_signal = inferior_thread ()->suspend.stop_signal; cleanup = ensure_python_env (get_current_arch (), current_language); if (emit_stop_event (bs, stop_signal) < 0) gdbpy_print_stack (); do_cleanups (cleanup); }
static void py_free_pspace (struct program_space *pspace, void *datum) { struct cleanup *cleanup; pspace_object *object = (pspace_object *) datum; /* This is a fiction, but we're in a nasty spot: The pspace is in the process of being deleted, we can't rely on anything in it. Plus this is one time when the current program space and current inferior are not in sync: All inferiors that use PSPACE may no longer exist. We don't need to do much here, and since "there is always an inferior" using target_gdbarch suffices. Note: We cannot call get_current_arch because it may try to access the target, which may involve accessing data in the pspace currently being deleted. */ struct gdbarch *arch = target_gdbarch (); cleanup = ensure_python_env (arch, current_language); object->pspace = NULL; Py_DECREF ((PyObject *) object); do_cleanups (cleanup); }
static void python_interactive_command (char *arg, int from_tty) { struct cleanup *cleanup; int err; cleanup = make_cleanup_restore_integer (&interpreter_async); interpreter_async = 0; arg = skip_spaces (arg); ensure_python_env (get_current_arch (), current_language); if (arg && *arg) { int len = strlen (arg); char *script = xmalloc (len + 2); strcpy (script, arg); script[len] = '\n'; script[len + 1] = '\0'; err = eval_python_command (script); xfree (script); } else { err = PyRun_InteractiveLoop (instream, "<stdin>"); dont_repeat (); } if (err) { gdbpy_print_stack (); error (_("Error while executing Python code.")); } do_cleanups (cleanup); }
static struct value * fnpy_call (struct gdbarch *gdbarch, const struct language_defn *language, void *cookie, int argc, struct value **argv) { struct value *value = NULL; /* 'result' must be set to NULL, this initially indicates whether the function was called, or not. */ PyObject *result = NULL; PyObject *callable, *args; struct cleanup *cleanup; cleanup = ensure_python_env (gdbarch, language); args = convert_values_to_python (argc, argv); /* convert_values_to_python can return NULL on error. If we encounter this, do not call the function, but allow the Python -> error code conversion below to deal with the Python exception. Note, that this is different if the function simply does not have arguments. */ if (args) { callable = PyObject_GetAttrString ((PyObject *) cookie, "invoke"); if (! callable) { Py_DECREF (args); error (_("No method named 'invoke' in object.")); } result = PyObject_Call (callable, args, NULL); Py_DECREF (callable); Py_DECREF (args); } if (!result) { PyObject *ptype, *pvalue, *ptraceback; char *msg; PyErr_Fetch (&ptype, &pvalue, &ptraceback); /* Try to fetch an error message contained within ptype, pvalue. When fetching the error message we need to make our own copy, we no longer own ptype, pvalue after the call to PyErr_Restore. */ msg = gdbpy_exception_to_string (ptype, pvalue); make_cleanup (xfree, msg); if (msg == NULL) { /* An error occurred computing the string representation of the error message. This is rare, but we should inform the user. */ printf_filtered (_("An error occurred in a Python " "convenience function\n" "and then another occurred computing the " "error message.\n")); gdbpy_print_stack (); } /* Don't print the stack for gdb.GdbError exceptions. It is generally used to flag user errors. We also don't want to print "Error occurred in Python command" for user errors. However, a missing message for gdb.GdbError exceptions is arguably a bug, so we flag it as such. */ if (!PyErr_GivenExceptionMatches (ptype, gdbpy_gdberror_exc) || msg == NULL || *msg == '\0') { PyErr_Restore (ptype, pvalue, ptraceback); gdbpy_print_stack (); if (msg != NULL && *msg != '\0') error (_("Error occurred in Python convenience function: %s"), msg); else error (_("Error occurred in Python convenience function.")); } else { Py_XDECREF (ptype); Py_XDECREF (pvalue); Py_XDECREF (ptraceback); error ("%s", msg); } } value = convert_value_from_python (result); if (value == NULL) { Py_DECREF (result); gdbpy_print_stack (); error (_("Error while executing Python code.")); } Py_DECREF (result); do_cleanups (cleanup); return value; }
enum ext_lang_rc gdbpy_apply_val_pretty_printer (const struct extension_language_defn *extlang, struct type *type, const gdb_byte *valaddr, int embedded_offset, CORE_ADDR address, struct ui_file *stream, int recurse, const struct value *val, const struct value_print_options *options, const struct language_defn *language) { struct gdbarch *gdbarch = get_type_arch (type); PyObject *printer = NULL; PyObject *val_obj = NULL; struct value *value; char *hint = NULL; struct cleanup *cleanups; enum ext_lang_rc result = EXT_LANG_RC_NOP; enum string_repr_result print_result; /* No pretty-printer support for unavailable values. */ if (!value_bytes_available (val, embedded_offset, TYPE_LENGTH (type))) return EXT_LANG_RC_NOP; if (!gdb_python_initialized) return EXT_LANG_RC_NOP; cleanups = ensure_python_env (gdbarch, language); /* Instantiate the printer. */ if (valaddr) valaddr += embedded_offset; value = value_from_contents_and_address (type, valaddr, address + embedded_offset); set_value_component_location (value, val); /* set_value_component_location resets the address, so we may need to set it again. */ if (VALUE_LVAL (value) != lval_internalvar && VALUE_LVAL (value) != lval_internalvar_component && VALUE_LVAL (value) != lval_computed) set_value_address (value, address + embedded_offset); val_obj = value_to_value_object (value); if (! val_obj) { result = EXT_LANG_RC_ERROR; goto done; } /* Find the constructor. */ printer = find_pretty_printer (val_obj); Py_DECREF (val_obj); if (printer == NULL) { result = EXT_LANG_RC_ERROR; goto done; } make_cleanup_py_decref (printer); if (printer == Py_None) { result = EXT_LANG_RC_NOP; goto done; } /* If we are printing a map, we want some special formatting. */ hint = gdbpy_get_display_hint (printer); make_cleanup (free_current_contents, &hint); /* Print the section */ print_result = print_string_repr (printer, hint, stream, recurse, options, language, gdbarch); if (print_result != string_repr_error) print_children (printer, hint, stream, recurse, options, language, print_result == string_repr_none); result = EXT_LANG_RC_OK; done: if (PyErr_Occurred ()) print_stack_unless_memory_error (stream); do_cleanups (cleanups); return result; }