summaryrefslogtreecommitdiff
path: root/lldb/bindings/python/python-wrapper.swig
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2021-02-16 20:13:02 +0000
committerDimitry Andric <dim@FreeBSD.org>2021-02-16 20:13:02 +0000
commitb60736ec1405bb0a8dd40989f67ef4c93da068ab (patch)
tree5c43fbb7c9fc45f0f87e0e6795a86267dbd12f9d /lldb/bindings/python/python-wrapper.swig
parentcfca06d7963fa0909f90483b42a6d7d194d01e08 (diff)
Diffstat (limited to 'lldb/bindings/python/python-wrapper.swig')
-rw-r--r--lldb/bindings/python/python-wrapper.swig132
1 files changed, 126 insertions, 6 deletions
diff --git a/lldb/bindings/python/python-wrapper.swig b/lldb/bindings/python/python-wrapper.swig
index f9e89373fe25..443ddfb8dd20 100644
--- a/lldb/bindings/python/python-wrapper.swig
+++ b/lldb/bindings/python/python-wrapper.swig
@@ -271,9 +271,6 @@ LLDBSwigPythonCreateScriptedThreadPlan
if (python_class_name == NULL || python_class_name[0] == '\0' || !session_dictionary_name)
Py_RETURN_NONE;
- // I do not want the SBThreadPlan to be deallocated when going out of scope because python
- // has ownership of it and will manage memory for this object by itself
- lldb::SBThreadPlan *tp_value = new lldb::SBThreadPlan(thread_plan_sp);
PyErr_Cleaner py_err_cleaner(true);
@@ -286,7 +283,10 @@ LLDBSwigPythonCreateScriptedThreadPlan
return nullptr;
}
- PythonObject tp_arg(PyRefType::Owned, SBTypeToSWIGWrapper(tp_value));
+ // I do not want the SBThreadPlan to be deallocated when going out of scope
+ // because python has ownership of it and will manage memory for this
+ // object by itself
+ PythonObject tp_arg(PyRefType::Owned, SBTypeToSWIGWrapper(new lldb::SBThreadPlan(thread_plan_sp)));
if (!tp_arg.IsAllocated())
Py_RETURN_NONE;
@@ -312,8 +312,7 @@ LLDBSwigPythonCreateScriptedThreadPlan
}
result = pfunc(tp_arg, dict);
} else if (arg_info.get().max_positional_args >= 3) {
- lldb::SBStructuredData *args_value = new lldb::SBStructuredData(args_impl);
- PythonObject args_arg(PyRefType::Owned, SBTypeToSWIGWrapper(args_value));
+ PythonObject args_arg(PyRefType::Owned, SBTypeToSWIGWrapper(new lldb::SBStructuredData(args_impl)));
result = pfunc(tp_arg, args_arg, dict);
} else {
error_string.assign("wrong number of arguments in __init__, should be 2 or 3 (not including self)");
@@ -469,6 +468,127 @@ LLDBSwigPythonCallBreakpointResolver
return ret_val;
}
+SWIGEXPORT void *
+LLDBSwigPythonCreateScriptedStopHook
+(
+ lldb::TargetSP target_sp,
+ const char *python_class_name,
+ const char *session_dictionary_name,
+ lldb_private::StructuredDataImpl *args_impl,
+ Status &error
+)
+{
+ if (python_class_name == NULL || python_class_name[0] == '\0') {
+ error.SetErrorString("Empty class name.");
+ Py_RETURN_NONE;
+ }
+ if (!session_dictionary_name) {
+ error.SetErrorString("No session dictionary");
+ Py_RETURN_NONE;
+ }
+
+ PyErr_Cleaner py_err_cleaner(true);
+
+ auto dict =
+ PythonModule::MainModule().ResolveName<PythonDictionary>(
+ session_dictionary_name);
+ auto pfunc =
+ PythonObject::ResolveNameWithDictionary<PythonCallable>(
+ python_class_name, dict);
+
+ if (!pfunc.IsAllocated()) {
+ error.SetErrorStringWithFormat("Could not find class: %s.",
+ python_class_name);
+ return nullptr;
+ }
+
+ lldb::SBTarget *target_val
+ = new lldb::SBTarget(target_sp);
+
+ PythonObject target_arg(PyRefType::Owned, SBTypeToSWIGWrapper(target_val));
+
+ lldb::SBStructuredData *args_value = new lldb::SBStructuredData(args_impl);
+ PythonObject args_arg(PyRefType::Owned, SBTypeToSWIGWrapper(args_value));
+
+ PythonObject result = pfunc(target_arg, args_arg, dict);
+
+ if (result.IsAllocated())
+ {
+ // Check that the handle_stop callback is defined:
+ auto callback_func = result.ResolveName<PythonCallable>("handle_stop");
+ if (callback_func.IsAllocated()) {
+ if (auto args_info = callback_func.GetArgInfo()) {
+ size_t num_args = (*args_info).max_positional_args;
+ if (num_args != 2) {
+ error.SetErrorStringWithFormat("Wrong number of args for "
+ "handle_stop callback, should be 2 (excluding self), got: %zu",
+ num_args);
+ Py_RETURN_NONE;
+ } else
+ return result.release();
+ } else {
+ error.SetErrorString("Couldn't get num arguments for handle_stop "
+ "callback.");
+ Py_RETURN_NONE;
+ }
+ return result.release();
+ }
+ else {
+ error.SetErrorStringWithFormat("Class \"%s\" is missing the required "
+ "handle_stop callback.",
+ python_class_name);
+ result.release();
+ }
+ }
+ Py_RETURN_NONE;
+}
+
+SWIGEXPORT bool
+LLDBSwigPythonStopHookCallHandleStop
+(
+ void *implementor,
+ lldb::ExecutionContextRefSP exc_ctx_sp,
+ lldb::StreamSP stream
+)
+{
+ // handle_stop will return a bool with the meaning "should_stop"...
+ // If you return nothing we'll assume we are going to stop.
+ // Also any errors should return true, since we should stop on error.
+
+ PyErr_Cleaner py_err_cleaner(false);
+ PythonObject self(PyRefType::Borrowed, static_cast<PyObject*>(implementor));
+ auto pfunc = self.ResolveName<PythonCallable>("handle_stop");
+
+ if (!pfunc.IsAllocated())
+ return true;
+
+ PythonObject result;
+ lldb::SBExecutionContext sb_exc_ctx(exc_ctx_sp);
+ PythonObject exc_ctx_arg(PyRefType::Owned, SBTypeToSWIGWrapper(sb_exc_ctx));
+ lldb::SBStream sb_stream;
+ PythonObject sb_stream_arg(PyRefType::Owned,
+ SBTypeToSWIGWrapper(sb_stream));
+ result = pfunc(exc_ctx_arg, sb_stream_arg);
+
+ if (PyErr_Occurred())
+ {
+ stream->PutCString("Python error occurred handling stop-hook.");
+ PyErr_Print();
+ PyErr_Clear();
+ return true;
+ }
+
+ // Now add the result to the output stream. SBStream only
+ // makes an internally help StreamString which I can't interpose, so I
+ // have to copy it over here.
+ stream->PutCString(sb_stream.GetData());
+
+ if (result.get() == Py_False)
+ return false;
+ else
+ return true;
+}
+
// wrapper that calls an optional instance member of an object taking no arguments
static PyObject*
LLDBSwigPython_CallOptionalMember