19f2f44ceSEd Maste //===-- ThreadPlanCallFunctionUsingABI.cpp ----------------------*- C++ -*-===// 2b91a7dfcSDimitry Andric // 3b91a7dfcSDimitry Andric // The LLVM Compiler Infrastructure 4b91a7dfcSDimitry Andric // 5b91a7dfcSDimitry Andric // This file is distributed under the University of Illinois Open Source 6b91a7dfcSDimitry Andric // License. See LICENSE.TXT for details. 7b91a7dfcSDimitry Andric // 8b91a7dfcSDimitry Andric //===----------------------------------------------------------------------===// 9b91a7dfcSDimitry Andric 10b91a7dfcSDimitry Andric // C Includes 11b91a7dfcSDimitry Andric // C++ Includes 12b91a7dfcSDimitry Andric // Other libraries and framework includes 13b91a7dfcSDimitry Andric // Project includes 149f2f44ceSEd Maste #include "lldb/Target/ThreadPlanCallFunctionUsingABI.h" 15b91a7dfcSDimitry Andric #include "lldb/Core/Address.h" 16b91a7dfcSDimitry Andric #include "lldb/Core/Log.h" 17b91a7dfcSDimitry Andric #include "lldb/Core/Stream.h" 18b91a7dfcSDimitry Andric #include "lldb/Target/Process.h" 19b91a7dfcSDimitry Andric #include "lldb/Target/RegisterContext.h" 20b91a7dfcSDimitry Andric #include "lldb/Target/Target.h" 21b91a7dfcSDimitry Andric #include "lldb/Target/Thread.h" 22b91a7dfcSDimitry Andric 23b91a7dfcSDimitry Andric using namespace lldb; 24b91a7dfcSDimitry Andric using namespace lldb_private; 25b91a7dfcSDimitry Andric 26b91a7dfcSDimitry Andric //-------------------------------------------------------------------------------------------- 27435933ddSDimitry Andric // ThreadPlanCallFunctionUsingABI: Plan to call a single function using the ABI 28435933ddSDimitry Andric // instead of JIT 29b91a7dfcSDimitry Andric //------------------------------------------------------------------------------------------- 30435933ddSDimitry Andric ThreadPlanCallFunctionUsingABI::ThreadPlanCallFunctionUsingABI( 31435933ddSDimitry Andric Thread &thread, const Address &function, llvm::Type &prototype, 32435933ddSDimitry Andric llvm::Type &return_type, llvm::ArrayRef<ABI::CallArgument> args, 33435933ddSDimitry Andric const EvaluateExpressionOptions &options) 34435933ddSDimitry Andric : ThreadPlanCallFunction(thread, function, options), 35435933ddSDimitry Andric m_return_type(return_type) { 36b91a7dfcSDimitry Andric lldb::addr_t start_load_addr = LLDB_INVALID_ADDRESS; 37b91a7dfcSDimitry Andric lldb::addr_t function_load_addr = LLDB_INVALID_ADDRESS; 38b91a7dfcSDimitry Andric ABI *abi = nullptr; 39b91a7dfcSDimitry Andric 40b91a7dfcSDimitry Andric if (!ConstructorSetup(thread, abi, start_load_addr, function_load_addr)) 41b91a7dfcSDimitry Andric return; 42b91a7dfcSDimitry Andric 43435933ddSDimitry Andric if (!abi->PrepareTrivialCall(thread, m_function_sp, function_load_addr, 44435933ddSDimitry Andric start_load_addr, prototype, args)) 45b91a7dfcSDimitry Andric return; 46b91a7dfcSDimitry Andric 47b91a7dfcSDimitry Andric ReportRegisterState("ABI Function call was set up. Register state was:"); 48b91a7dfcSDimitry Andric 49b91a7dfcSDimitry Andric m_valid = true; 50b91a7dfcSDimitry Andric } 51b91a7dfcSDimitry Andric 529f2f44ceSEd Maste ThreadPlanCallFunctionUsingABI::~ThreadPlanCallFunctionUsingABI() = default; 53b91a7dfcSDimitry Andric 54435933ddSDimitry Andric void ThreadPlanCallFunctionUsingABI::GetDescription(Stream *s, 55435933ddSDimitry Andric DescriptionLevel level) { 56435933ddSDimitry Andric if (level == eDescriptionLevelBrief) { 57b91a7dfcSDimitry Andric s->Printf("Function call thread plan using ABI instead of JIT"); 58435933ddSDimitry Andric } else { 59b91a7dfcSDimitry Andric TargetSP target_sp(m_thread.CalculateTarget()); 60435933ddSDimitry Andric s->Printf("Thread plan to call 0x%" PRIx64 " using ABI instead of JIT", 61435933ddSDimitry Andric m_function_addr.GetLoadAddress(target_sp.get())); 62b91a7dfcSDimitry Andric } 63b91a7dfcSDimitry Andric } 64b91a7dfcSDimitry Andric 65435933ddSDimitry Andric void ThreadPlanCallFunctionUsingABI::SetReturnValue() { 66b91a7dfcSDimitry Andric ProcessSP process_sp(m_thread.GetProcess()); 679f2f44ceSEd Maste const ABI *abi = process_sp ? process_sp->GetABI().get() : nullptr; 68b91a7dfcSDimitry Andric 69b91a7dfcSDimitry Andric // Ask the abi for the return value 70435933ddSDimitry Andric if (abi) { 71b91a7dfcSDimitry Andric const bool persistent = false; 72435933ddSDimitry Andric m_return_valobj_sp = 73435933ddSDimitry Andric abi->GetReturnValueObject(m_thread, m_return_type, persistent); 74b91a7dfcSDimitry Andric } 75b91a7dfcSDimitry Andric } 76