1 //===-- ScriptedProcessPythonInterface.cpp --------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "lldb/Host/Config.h" 10 #include "lldb/Utility/Log.h" 11 #include "lldb/Utility/Logging.h" 12 #include "lldb/lldb-enumerations.h" 13 14 #if LLDB_ENABLE_PYTHON 15 16 // LLDB Python header must be included first 17 #include "lldb-python.h" 18 19 #include "SWIGPythonBridge.h" 20 #include "ScriptInterpreterPythonImpl.h" 21 #include "ScriptedProcessPythonInterface.h" 22 #include "ScriptedThreadPythonInterface.h" 23 24 using namespace lldb; 25 using namespace lldb_private; 26 using namespace lldb_private::python; 27 using Locker = ScriptInterpreterPythonImpl::Locker; 28 29 ScriptedProcessPythonInterface::ScriptedProcessPythonInterface( 30 ScriptInterpreterPythonImpl &interpreter) 31 : ScriptedProcessInterface(), ScriptedPythonInterface(interpreter) {} 32 33 StructuredData::GenericSP ScriptedProcessPythonInterface::CreatePluginObject( 34 llvm::StringRef class_name, ExecutionContext &exe_ctx, 35 StructuredData::DictionarySP args_sp) { 36 if (class_name.empty()) 37 return {}; 38 39 TargetSP target_sp = exe_ctx.GetTargetSP(); 40 StructuredDataImpl args_impl(args_sp); 41 std::string error_string; 42 43 Locker py_lock(&m_interpreter, Locker::AcquireLock | Locker::NoSTDIN, 44 Locker::FreeLock); 45 46 PythonObject ret_val = LLDBSwigPythonCreateScriptedProcess( 47 class_name.str().c_str(), m_interpreter.GetDictionaryName(), target_sp, 48 args_impl, error_string); 49 50 if (!ret_val) 51 return {}; 52 53 m_object_instance_sp = 54 StructuredData::GenericSP(new StructuredPythonObject(std::move(ret_val))); 55 56 return m_object_instance_sp; 57 } 58 59 Status ScriptedProcessPythonInterface::Launch() { 60 return GetStatusFromMethod("launch"); 61 } 62 63 Status ScriptedProcessPythonInterface::Resume() { 64 return GetStatusFromMethod("resume"); 65 } 66 67 bool ScriptedProcessPythonInterface::ShouldStop() { 68 Status error; 69 StructuredData::ObjectSP obj = Dispatch("is_alive", error); 70 71 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 72 return {}; 73 74 return obj->GetBooleanValue(); 75 } 76 77 Status ScriptedProcessPythonInterface::Stop() { 78 return GetStatusFromMethod("stop"); 79 } 80 81 llvm::Optional<MemoryRegionInfo> 82 ScriptedProcessPythonInterface::GetMemoryRegionContainingAddress( 83 lldb::addr_t address, Status &error) { 84 auto mem_region = Dispatch<llvm::Optional<MemoryRegionInfo>>( 85 "get_memory_region_containing_address", error, address); 86 87 if (error.Fail()) { 88 return ErrorWithMessage<MemoryRegionInfo>(LLVM_PRETTY_FUNCTION, 89 error.AsCString(), error); 90 } 91 92 return mem_region; 93 } 94 95 StructuredData::DictionarySP ScriptedProcessPythonInterface::GetThreadsInfo() { 96 Status error; 97 StructuredData::DictionarySP dict = 98 Dispatch<StructuredData::DictionarySP>("get_threads_info", error); 99 100 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, dict, error)) 101 return {}; 102 103 return dict; 104 } 105 106 StructuredData::DictionarySP 107 ScriptedProcessPythonInterface::GetThreadWithID(lldb::tid_t tid) { 108 Status error; 109 StructuredData::ObjectSP obj = Dispatch("get_thread_with_id", error, tid); 110 111 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 112 return {}; 113 114 StructuredData::DictionarySP dict{obj->GetAsDictionary()}; 115 116 return dict; 117 } 118 119 StructuredData::DictionarySP 120 ScriptedProcessPythonInterface::GetRegistersForThread(lldb::tid_t tid) { 121 // TODO: Implement 122 return {}; 123 } 124 125 lldb::DataExtractorSP ScriptedProcessPythonInterface::ReadMemoryAtAddress( 126 lldb::addr_t address, size_t size, Status &error) { 127 return Dispatch<lldb::DataExtractorSP>("read_memory_at_address", error, 128 address, size); 129 } 130 131 StructuredData::DictionarySP ScriptedProcessPythonInterface::GetLoadedImages() { 132 // TODO: Implement 133 return {}; 134 } 135 136 lldb::pid_t ScriptedProcessPythonInterface::GetProcessID() { 137 Status error; 138 StructuredData::ObjectSP obj = Dispatch("get_process_id", error); 139 140 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 141 return LLDB_INVALID_PROCESS_ID; 142 143 return obj->GetIntegerValue(LLDB_INVALID_PROCESS_ID); 144 } 145 146 bool ScriptedProcessPythonInterface::IsAlive() { 147 Status error; 148 StructuredData::ObjectSP obj = Dispatch("is_alive", error); 149 150 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 151 return {}; 152 153 return obj->GetBooleanValue(); 154 } 155 156 llvm::Optional<std::string> 157 ScriptedProcessPythonInterface::GetScriptedThreadPluginName() { 158 Status error; 159 StructuredData::ObjectSP obj = Dispatch("get_scripted_thread_plugin", error); 160 161 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 162 return {}; 163 164 return obj->GetStringValue().str(); 165 } 166 167 lldb::ScriptedThreadInterfaceSP 168 ScriptedProcessPythonInterface::CreateScriptedThreadInterface() { 169 return std::make_shared<ScriptedThreadPythonInterface>(m_interpreter); 170 } 171 172 #endif 173