180814287SRaphael Isemann //===-- ThreadPlanCallFunctionUsingABI.cpp --------------------------------===//
290ff7911SEwan Crawford //
32946cd70SChandler Carruth // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
42946cd70SChandler Carruth // See https://llvm.org/LICENSE.txt for license information.
52946cd70SChandler Carruth // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
690ff7911SEwan Crawford //
790ff7911SEwan Crawford //===----------------------------------------------------------------------===//
890ff7911SEwan Crawford
9e65b2cf2SEugene Zelenko #include "lldb/Target/ThreadPlanCallFunctionUsingABI.h"
1090ff7911SEwan Crawford #include "lldb/Core/Address.h"
1190ff7911SEwan Crawford #include "lldb/Target/Process.h"
1290ff7911SEwan Crawford #include "lldb/Target/RegisterContext.h"
1390ff7911SEwan Crawford #include "lldb/Target/Target.h"
1490ff7911SEwan Crawford #include "lldb/Target/Thread.h"
156f9e6901SZachary Turner #include "lldb/Utility/Log.h"
16bf9a7730SZachary Turner #include "lldb/Utility/Stream.h"
1790ff7911SEwan Crawford
1890ff7911SEwan Crawford using namespace lldb;
1990ff7911SEwan Crawford using namespace lldb_private;
2090ff7911SEwan Crawford
21b9c1b51eSKate Stone // ThreadPlanCallFunctionUsingABI: Plan to call a single function using the ABI
22b9c1b51eSKate Stone // instead of JIT
ThreadPlanCallFunctionUsingABI(Thread & thread,const Address & function,llvm::Type & prototype,llvm::Type & return_type,llvm::ArrayRef<ABI::CallArgument> args,const EvaluateExpressionOptions & options)23b9c1b51eSKate Stone ThreadPlanCallFunctionUsingABI::ThreadPlanCallFunctionUsingABI(
24b9c1b51eSKate Stone Thread &thread, const Address &function, llvm::Type &prototype,
25b9c1b51eSKate Stone llvm::Type &return_type, llvm::ArrayRef<ABI::CallArgument> args,
26b9c1b51eSKate Stone const EvaluateExpressionOptions &options)
27b9c1b51eSKate Stone : ThreadPlanCallFunction(thread, function, options),
28b9c1b51eSKate Stone m_return_type(return_type) {
2990ff7911SEwan Crawford lldb::addr_t start_load_addr = LLDB_INVALID_ADDRESS;
3090ff7911SEwan Crawford lldb::addr_t function_load_addr = LLDB_INVALID_ADDRESS;
3190ff7911SEwan Crawford ABI *abi = nullptr;
3290ff7911SEwan Crawford
3390ff7911SEwan Crawford if (!ConstructorSetup(thread, abi, start_load_addr, function_load_addr))
3490ff7911SEwan Crawford return;
3590ff7911SEwan Crawford
36b9c1b51eSKate Stone if (!abi->PrepareTrivialCall(thread, m_function_sp, function_load_addr,
37b9c1b51eSKate Stone start_load_addr, prototype, args))
3890ff7911SEwan Crawford return;
3990ff7911SEwan Crawford
4090ff7911SEwan Crawford ReportRegisterState("ABI Function call was set up. Register state was:");
4190ff7911SEwan Crawford
4290ff7911SEwan Crawford m_valid = true;
4390ff7911SEwan Crawford }
4490ff7911SEwan Crawford
45e65b2cf2SEugene Zelenko ThreadPlanCallFunctionUsingABI::~ThreadPlanCallFunctionUsingABI() = default;
4690ff7911SEwan Crawford
GetDescription(Stream * s,DescriptionLevel level)47b9c1b51eSKate Stone void ThreadPlanCallFunctionUsingABI::GetDescription(Stream *s,
48b9c1b51eSKate Stone DescriptionLevel level) {
49b9c1b51eSKate Stone if (level == eDescriptionLevelBrief) {
5090ff7911SEwan Crawford s->Printf("Function call thread plan using ABI instead of JIT");
51b9c1b51eSKate Stone } else {
52b9c1b51eSKate Stone s->Printf("Thread plan to call 0x%" PRIx64 " using ABI instead of JIT",
53*e4598dc0SJim Ingham m_function_addr.GetLoadAddress(&GetTarget()));
5490ff7911SEwan Crawford }
5590ff7911SEwan Crawford }
5690ff7911SEwan Crawford
SetReturnValue()57b9c1b51eSKate Stone void ThreadPlanCallFunctionUsingABI::SetReturnValue() {
58*e4598dc0SJim Ingham const ABI *abi = m_process.GetABI().get();
5990ff7911SEwan Crawford
6090ff7911SEwan Crawford // Ask the abi for the return value
61b9c1b51eSKate Stone if (abi) {
6290ff7911SEwan Crawford const bool persistent = false;
63b9c1b51eSKate Stone m_return_valobj_sp =
64*e4598dc0SJim Ingham abi->GetReturnValueObject(GetThread(), m_return_type, persistent);
6590ff7911SEwan Crawford }
6690ff7911SEwan Crawford }
67