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, StructuredData::Generic *script_obj) { 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 m_object_instance_sp = 51 StructuredData::GenericSP(new StructuredPythonObject(std::move(ret_val))); 52 53 return m_object_instance_sp; 54 } 55 56 Status ScriptedProcessPythonInterface::Launch() { 57 return GetStatusFromMethod("launch"); 58 } 59 60 Status ScriptedProcessPythonInterface::Resume() { 61 return GetStatusFromMethod("resume"); 62 } 63 64 bool ScriptedProcessPythonInterface::ShouldStop() { 65 Status error; 66 StructuredData::ObjectSP obj = Dispatch("is_alive", error); 67 68 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 69 return {}; 70 71 return obj->GetBooleanValue(); 72 } 73 74 Status ScriptedProcessPythonInterface::Stop() { 75 return GetStatusFromMethod("stop"); 76 } 77 78 llvm::Optional<MemoryRegionInfo> 79 ScriptedProcessPythonInterface::GetMemoryRegionContainingAddress( 80 lldb::addr_t address, Status &error) { 81 auto mem_region = Dispatch<llvm::Optional<MemoryRegionInfo>>( 82 "get_memory_region_containing_address", error, address); 83 84 if (error.Fail()) { 85 return ErrorWithMessage<MemoryRegionInfo>(LLVM_PRETTY_FUNCTION, 86 error.AsCString(), error); 87 } 88 89 return mem_region; 90 } 91 92 StructuredData::DictionarySP ScriptedProcessPythonInterface::GetThreadsInfo() { 93 Status error; 94 StructuredData::DictionarySP dict = 95 Dispatch<StructuredData::DictionarySP>("get_threads_info", error); 96 97 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, dict, error)) 98 return {}; 99 100 return dict; 101 } 102 103 StructuredData::DictionarySP 104 ScriptedProcessPythonInterface::GetThreadWithID(lldb::tid_t tid) { 105 Status error; 106 StructuredData::ObjectSP obj = Dispatch("get_thread_with_id", error, tid); 107 108 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 109 return {}; 110 111 StructuredData::DictionarySP dict{obj->GetAsDictionary()}; 112 113 return dict; 114 } 115 116 StructuredData::DictionarySP 117 ScriptedProcessPythonInterface::GetRegistersForThread(lldb::tid_t tid) { 118 // TODO: Implement 119 return {}; 120 } 121 122 lldb::DataExtractorSP ScriptedProcessPythonInterface::ReadMemoryAtAddress( 123 lldb::addr_t address, size_t size, Status &error) { 124 return Dispatch<lldb::DataExtractorSP>("read_memory_at_address", error, 125 address, size); 126 } 127 128 StructuredData::DictionarySP ScriptedProcessPythonInterface::GetLoadedImages() { 129 // TODO: Implement 130 return {}; 131 } 132 133 lldb::pid_t ScriptedProcessPythonInterface::GetProcessID() { 134 Status error; 135 StructuredData::ObjectSP obj = Dispatch("get_process_id", error); 136 137 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 138 return LLDB_INVALID_PROCESS_ID; 139 140 return obj->GetIntegerValue(LLDB_INVALID_PROCESS_ID); 141 } 142 143 bool ScriptedProcessPythonInterface::IsAlive() { 144 Status error; 145 StructuredData::ObjectSP obj = Dispatch("is_alive", error); 146 147 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 148 return {}; 149 150 return obj->GetBooleanValue(); 151 } 152 153 llvm::Optional<std::string> 154 ScriptedProcessPythonInterface::GetScriptedThreadPluginName() { 155 Status error; 156 StructuredData::ObjectSP obj = Dispatch("get_scripted_thread_plugin", error); 157 158 if (!CheckStructuredDataObject(LLVM_PRETTY_FUNCTION, obj, error)) 159 return {}; 160 161 return obj->GetStringValue().str(); 162 } 163 164 lldb::ScriptedThreadInterfaceSP 165 ScriptedProcessPythonInterface::CreateScriptedThreadInterface() { 166 return std::make_shared<ScriptedThreadPythonInterface>(m_interpreter); 167 } 168 169 #endif 170