diff options
author | Med Ismail Bennani <medismail.bennani@gmail.com> | 2021-10-08 12:25:04 +0000 |
---|---|---|
committer | Med Ismail Bennani <medismail.bennani@gmail.com> | 2021-10-08 14:54:07 +0200 |
commit | a758c9f7204c41d8791e76d24f9bc4791534f1b8 (patch) | |
tree | 520683d8b67dc11a94ac9c09e4fb4c8c2a7e5a05 /lldb/source/Plugins/ScriptInterpreter/Python | |
parent | 59d8dd79e1f9dead2dc2756e139073083e487228 (diff) | |
download | llvm-a758c9f7204c41d8791e76d24f9bc4791534f1b8.zip llvm-a758c9f7204c41d8791e76d24f9bc4791534f1b8.tar.gz llvm-a758c9f7204c41d8791e76d24f9bc4791534f1b8.tar.bz2 |
[lldb/Plugins] Add memory region support in ScriptedProcess
This patch adds support for memory regions in Scripted Processes.
This is necessary to read the stack memory region in order to
reconstruct each stackframe of the program.
In order to do so, this patch makes some changes to the SBAPI, namely:
- Add a new constructor for `SBMemoryRegionInfo` that takes arguments
such as the memory region name, address range, permissions ...
This is used when reading memory at some address to compute the offset
in the binary blob provided by the user.
- Add a `GetMemoryRegionContainingAddress` method to `SBMemoryRegionInfoList`
to simplify the access to a specific memory region.
With these changes, lldb is now able to unwind the stack and reconstruct
each frame. On top of that, reloading the target module at offset 0 allows
lldb to symbolicate the `ScriptedProcess` using debug info, similarly to an
ordinary Process.
To test this, I wrote a simple program with multiple function calls, ran it in
lldb, stopped at a leaf function and read the registers values and copied
the stack memory into a binary file. These are then used in the python script.
Differential Revision: https://reviews.llvm.org/D108953
Signed-off-by: Med Ismail Bennani <medismail.bennani@gmail.com>
Diffstat (limited to 'lldb/source/Plugins/ScriptInterpreter/Python')
5 files changed, 40 insertions, 7 deletions
diff --git a/lldb/source/Plugins/ScriptInterpreter/Python/SWIGPythonBridge.h b/lldb/source/Plugins/ScriptInterpreter/Python/SWIGPythonBridge.h index 8d6e7dc..81e2512 100644 --- a/lldb/source/Plugins/ScriptInterpreter/Python/SWIGPythonBridge.h +++ b/lldb/source/Plugins/ScriptInterpreter/Python/SWIGPythonBridge.h @@ -53,6 +53,7 @@ extern "C" void *LLDBSwigPythonCreateScriptedThread( extern "C" void *LLDBSWIGPython_CastPyObjectToSBData(void *data); extern "C" void *LLDBSWIGPython_CastPyObjectToSBError(void *data); extern "C" void *LLDBSWIGPython_CastPyObjectToSBValue(void *data); +extern "C" void *LLDBSWIGPython_CastPyObjectToSBMemoryRegionInfo(void *data); } // namespace lldb_private diff --git a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.cpp b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.cpp index 32be169..ffaee26 100644 --- a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.cpp +++ b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.cpp @@ -82,11 +82,18 @@ Status ScriptedProcessPythonInterface::Stop() { return GetStatusFromMethod("stop"); } -lldb::MemoryRegionInfoSP +llvm::Optional<MemoryRegionInfo> ScriptedProcessPythonInterface::GetMemoryRegionContainingAddress( - lldb::addr_t address) { - // TODO: Implement - return {}; + lldb::addr_t address, Status &error) { + auto mem_region = Dispatch<llvm::Optional<MemoryRegionInfo>>( + "get_memory_region_containing_address", error, address); + + if (error.Fail()) { + return ErrorWithMessage<MemoryRegionInfo>(__PRETTY_FUNCTION__, + error.AsCString(), error); + } + + return mem_region; } StructuredData::DictionarySP diff --git a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.h b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.h index eb3d2f3..421bdd5 100644 --- a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.h +++ b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedProcessPythonInterface.h @@ -35,8 +35,9 @@ public: Status Stop() override; - lldb::MemoryRegionInfoSP - GetMemoryRegionContainingAddress(lldb::addr_t address) override; + llvm::Optional<MemoryRegionInfo> + GetMemoryRegionContainingAddress(lldb::addr_t address, + Status &error) override; StructuredData::DictionarySP GetThreadWithID(lldb::tid_t tid) override; diff --git a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.cpp b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.cpp index e8fb38e..07bf952 100644 --- a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.cpp +++ b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.cpp @@ -63,11 +63,30 @@ ScriptedPythonInterface::ExtractValueFromPythonObject<lldb::DataExtractorSP>( LLDBSWIGPython_CastPyObjectToSBData(p.get())); if (!sb_data) { - error.SetErrorString("Couldn't cast lldb::SBError to lldb::Status."); + error.SetErrorString( + "Couldn't cast lldb::SBData to lldb::DataExtractorSP."); return nullptr; } return m_interpreter.GetDataExtractorFromSBData(*sb_data); } +template <> +llvm::Optional<MemoryRegionInfo> +ScriptedPythonInterface::ExtractValueFromPythonObject< + llvm::Optional<MemoryRegionInfo>>(python::PythonObject &p, Status &error) { + + lldb::SBMemoryRegionInfo *sb_mem_reg_info = + reinterpret_cast<lldb::SBMemoryRegionInfo *>( + LLDBSWIGPython_CastPyObjectToSBMemoryRegionInfo(p.get())); + + if (!sb_mem_reg_info) { + error.SetErrorString( + "Couldn't cast lldb::SBMemoryRegionInfo to lldb::MemoryRegionInfoSP."); + return {}; + } + + return m_interpreter.GetOpaqueTypeFromSBMemoryRegionInfo(*sb_mem_reg_info); +} + #endif diff --git a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.h b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.h index 9f76ed8..9b81555 100644 --- a/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.h +++ b/lldb/source/Plugins/ScriptInterpreter/Python/ScriptedPythonInterface.h @@ -140,6 +140,11 @@ lldb::DataExtractorSP ScriptedPythonInterface::ExtractValueFromPythonObject<lldb::DataExtractorSP>( python::PythonObject &p, Status &error); +template <> +llvm::Optional<MemoryRegionInfo> +ScriptedPythonInterface::ExtractValueFromPythonObject< + llvm::Optional<MemoryRegionInfo>>(python::PythonObject &p, Status &error); + } // namespace lldb_private #endif // LLDB_ENABLE_PYTHON |