180814287SRaphael Isemann //===-- SBFunction.cpp ----------------------------------------------------===//
230fdc8d8SChris Lattner //
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
630fdc8d8SChris Lattner //
730fdc8d8SChris Lattner //===----------------------------------------------------------------------===//
830fdc8d8SChris Lattner 
930fdc8d8SChris Lattner #include "lldb/API/SBFunction.h"
10d51402acSJonas Devlieghere #include "lldb/Utility/ReproducerInstrumentation.h"
1130fdc8d8SChris Lattner #include "lldb/API/SBProcess.h"
12dde9cff3SCaroline Tice #include "lldb/API/SBStream.h"
131d273166SGreg Clayton #include "lldb/Core/Disassembler.h"
141d273166SGreg Clayton #include "lldb/Core/Module.h"
151d273166SGreg Clayton #include "lldb/Symbol/CompileUnit.h"
1630fdc8d8SChris Lattner #include "lldb/Symbol/Function.h"
1705faeb71SGreg Clayton #include "lldb/Symbol/Type.h"
18fe68904fSGreg Clayton #include "lldb/Symbol/VariableList.h"
191d273166SGreg Clayton #include "lldb/Target/ExecutionContext.h"
201d273166SGreg Clayton #include "lldb/Target/Target.h"
2130fdc8d8SChris Lattner 
2230fdc8d8SChris Lattner using namespace lldb;
231d273166SGreg Clayton using namespace lldb_private;
2430fdc8d8SChris Lattner 
259494c510SJonas Devlieghere SBFunction::SBFunction() { LLDB_RECORD_CONSTRUCTOR_NO_ARGS(SBFunction); }
2630fdc8d8SChris Lattner 
27b9c1b51eSKate Stone SBFunction::SBFunction(lldb_private::Function *lldb_object_ptr)
28b9c1b51eSKate Stone     : m_opaque_ptr(lldb_object_ptr) {}
2930fdc8d8SChris Lattner 
30b9c1b51eSKate Stone SBFunction::SBFunction(const lldb::SBFunction &rhs)
31baf5664fSJonas Devlieghere     : m_opaque_ptr(rhs.m_opaque_ptr) {
32baf5664fSJonas Devlieghere   LLDB_RECORD_CONSTRUCTOR(SBFunction, (const lldb::SBFunction &), rhs);
33baf5664fSJonas Devlieghere }
34efabb123SGreg Clayton 
35b9c1b51eSKate Stone const SBFunction &SBFunction::operator=(const SBFunction &rhs) {
36baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD(const lldb::SBFunction &,
37baf5664fSJonas Devlieghere                      SBFunction, operator=,(const lldb::SBFunction &), rhs);
38baf5664fSJonas Devlieghere 
39efabb123SGreg Clayton   m_opaque_ptr = rhs.m_opaque_ptr;
40*d232abc3SJonas Devlieghere   return *this;
41efabb123SGreg Clayton }
42efabb123SGreg Clayton 
43248a1305SKonrad Kleine SBFunction::~SBFunction() { m_opaque_ptr = nullptr; }
4430fdc8d8SChris Lattner 
45baf5664fSJonas Devlieghere bool SBFunction::IsValid() const {
46baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST_NO_ARGS(bool, SBFunction, IsValid);
477f5237bcSPavel Labath   return this->operator bool();
487f5237bcSPavel Labath }
497f5237bcSPavel Labath SBFunction::operator bool() const {
507f5237bcSPavel Labath   LLDB_RECORD_METHOD_CONST_NO_ARGS(bool, SBFunction, operator bool);
51baf5664fSJonas Devlieghere 
52248a1305SKonrad Kleine   return m_opaque_ptr != nullptr;
53baf5664fSJonas Devlieghere }
5430fdc8d8SChris Lattner 
55b9c1b51eSKate Stone const char *SBFunction::GetName() const {
56baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST_NO_ARGS(const char *, SBFunction, GetName);
57baf5664fSJonas Devlieghere 
58248a1305SKonrad Kleine   const char *cstr = nullptr;
596611103cSGreg Clayton   if (m_opaque_ptr)
60ddaf6a72SGreg Clayton     cstr = m_opaque_ptr->GetName().AsCString();
61ceb6b139SCaroline Tice 
62cfd1acedSGreg Clayton   return cstr;
6330fdc8d8SChris Lattner }
6430fdc8d8SChris Lattner 
65b9c1b51eSKate Stone const char *SBFunction::GetDisplayName() const {
66baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST_NO_ARGS(const char *, SBFunction, GetDisplayName);
67baf5664fSJonas Devlieghere 
68248a1305SKonrad Kleine   const char *cstr = nullptr;
69c1f705c2SEnrico Granata   if (m_opaque_ptr)
7022b04487SAlex Langford     cstr = m_opaque_ptr->GetMangled().GetDisplayDemangledName().AsCString();
71c1f705c2SEnrico Granata 
72c1f705c2SEnrico Granata   return cstr;
73c1f705c2SEnrico Granata }
74c1f705c2SEnrico Granata 
75b9c1b51eSKate Stone const char *SBFunction::GetMangledName() const {
76baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST_NO_ARGS(const char *, SBFunction, GetMangledName);
77baf5664fSJonas Devlieghere 
78248a1305SKonrad Kleine   const char *cstr = nullptr;
796611103cSGreg Clayton   if (m_opaque_ptr)
80cfd1acedSGreg Clayton     cstr = m_opaque_ptr->GetMangled().GetMangledName().AsCString();
81cfd1acedSGreg Clayton   return cstr;
8230fdc8d8SChris Lattner }
8330fdc8d8SChris Lattner 
84b9c1b51eSKate Stone bool SBFunction::operator==(const SBFunction &rhs) const {
85baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST(
86baf5664fSJonas Devlieghere       bool, SBFunction, operator==,(const lldb::SBFunction &), rhs);
87baf5664fSJonas Devlieghere 
886611103cSGreg Clayton   return m_opaque_ptr == rhs.m_opaque_ptr;
8930fdc8d8SChris Lattner }
9030fdc8d8SChris Lattner 
91b9c1b51eSKate Stone bool SBFunction::operator!=(const SBFunction &rhs) const {
92baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_CONST(
93baf5664fSJonas Devlieghere       bool, SBFunction, operator!=,(const lldb::SBFunction &), rhs);
94baf5664fSJonas Devlieghere 
956611103cSGreg Clayton   return m_opaque_ptr != rhs.m_opaque_ptr;
9630fdc8d8SChris Lattner }
97dde9cff3SCaroline Tice 
98b9c1b51eSKate Stone bool SBFunction::GetDescription(SBStream &s) {
99baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD(bool, SBFunction, GetDescription, (lldb::SBStream &), s);
100baf5664fSJonas Devlieghere 
101b9c1b51eSKate Stone   if (m_opaque_ptr) {
102d01b2953SDaniel Malea     s.Printf("SBFunction: id = 0x%8.8" PRIx64 ", name = %s",
103b9c1b51eSKate Stone              m_opaque_ptr->GetID(), m_opaque_ptr->GetName().AsCString());
10405faeb71SGreg Clayton     Type *func_type = m_opaque_ptr->GetType();
10505faeb71SGreg Clayton     if (func_type)
10605faeb71SGreg Clayton       s.Printf(", type = %s", func_type->GetName().AsCString());
107dde9cff3SCaroline Tice     return true;
108dde9cff3SCaroline Tice   }
10905faeb71SGreg Clayton   s.Printf("No value");
11005faeb71SGreg Clayton   return false;
11105faeb71SGreg Clayton }
1121d273166SGreg Clayton 
113b9c1b51eSKate Stone SBInstructionList SBFunction::GetInstructions(SBTarget target) {
114baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD(lldb::SBInstructionList, SBFunction, GetInstructions,
115baf5664fSJonas Devlieghere                      (lldb::SBTarget), target);
116baf5664fSJonas Devlieghere 
117*d232abc3SJonas Devlieghere   return GetInstructions(target, nullptr);
1180f063ba6SJim Ingham }
1190f063ba6SJim Ingham 
120b9c1b51eSKate Stone SBInstructionList SBFunction::GetInstructions(SBTarget target,
121b9c1b51eSKate Stone                                               const char *flavor) {
122baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD(lldb::SBInstructionList, SBFunction, GetInstructions,
123baf5664fSJonas Devlieghere                      (lldb::SBTarget, const char *), target, flavor);
124baf5664fSJonas Devlieghere 
1251d273166SGreg Clayton   SBInstructionList sb_instructions;
126b9c1b51eSKate Stone   if (m_opaque_ptr) {
127b9556accSGreg Clayton     TargetSP target_sp(target.GetSP());
128bb19a13cSSaleem Abdulrasool     std::unique_lock<std::recursive_mutex> lock;
129b9c1b51eSKate Stone     ModuleSP module_sp(
130b9c1b51eSKate Stone         m_opaque_ptr->GetAddressRange().GetBaseAddress().GetModule());
13104592d5bSPavel Labath     if (target_sp && module_sp) {
13204592d5bSPavel Labath       lock = std::unique_lock<std::recursive_mutex>(target_sp->GetAPIMutex());
133e9fe788dSJason Molenda       const bool force_live_memory = true;
134b9c1b51eSKate Stone       sb_instructions.SetDisassembler(Disassembler::DisassembleRange(
13504592d5bSPavel Labath           module_sp->GetArchitecture(), nullptr, flavor, *target_sp,
136e9fe788dSJason Molenda           m_opaque_ptr->GetAddressRange(), force_live_memory));
1371d273166SGreg Clayton     }
1381d273166SGreg Clayton   }
139*d232abc3SJonas Devlieghere   return sb_instructions;
1401d273166SGreg Clayton }
1411d273166SGreg Clayton 
142b9c1b51eSKate Stone lldb_private::Function *SBFunction::get() { return m_opaque_ptr; }
1431d273166SGreg Clayton 
144b9c1b51eSKate Stone void SBFunction::reset(lldb_private::Function *lldb_object_ptr) {
14572eff18aSGreg Clayton   m_opaque_ptr = lldb_object_ptr;
14672eff18aSGreg Clayton }
14772eff18aSGreg Clayton 
148b9c1b51eSKate Stone SBAddress SBFunction::GetStartAddress() {
149baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(lldb::SBAddress, SBFunction, GetStartAddress);
150baf5664fSJonas Devlieghere 
15193d00df5SGreg Clayton   SBAddress addr;
15293d00df5SGreg Clayton   if (m_opaque_ptr)
1536cd4a4cdSJonas Devlieghere     addr.SetAddress(m_opaque_ptr->GetAddressRange().GetBaseAddress());
154*d232abc3SJonas Devlieghere   return addr;
15593d00df5SGreg Clayton }
15693d00df5SGreg Clayton 
157b9c1b51eSKate Stone SBAddress SBFunction::GetEndAddress() {
158baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(lldb::SBAddress, SBFunction, GetEndAddress);
159baf5664fSJonas Devlieghere 
16093d00df5SGreg Clayton   SBAddress addr;
161b9c1b51eSKate Stone   if (m_opaque_ptr) {
16293d00df5SGreg Clayton     addr_t byte_size = m_opaque_ptr->GetAddressRange().GetByteSize();
163b9c1b51eSKate Stone     if (byte_size > 0) {
1646cd4a4cdSJonas Devlieghere       addr.SetAddress(m_opaque_ptr->GetAddressRange().GetBaseAddress());
16593d00df5SGreg Clayton       addr->Slide(byte_size);
16693d00df5SGreg Clayton     }
16793d00df5SGreg Clayton   }
168*d232abc3SJonas Devlieghere   return addr;
16993d00df5SGreg Clayton }
17093d00df5SGreg Clayton 
171b9c1b51eSKate Stone const char *SBFunction::GetArgumentName(uint32_t arg_idx) {
172baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD(const char *, SBFunction, GetArgumentName, (uint32_t),
173baf5664fSJonas Devlieghere                      arg_idx);
174baf5664fSJonas Devlieghere 
175b9c1b51eSKate Stone   if (m_opaque_ptr) {
176fe68904fSGreg Clayton     Block &block = m_opaque_ptr->GetBlock(true);
177fe68904fSGreg Clayton     VariableListSP variable_list_sp = block.GetBlockVariableList(true);
178b9c1b51eSKate Stone     if (variable_list_sp) {
179fe68904fSGreg Clayton       VariableList arguments;
180b9c1b51eSKate Stone       variable_list_sp->AppendVariablesWithScope(eValueTypeVariableArgument,
181b9c1b51eSKate Stone                                                  arguments, true);
182fe68904fSGreg Clayton       lldb::VariableSP variable_sp = arguments.GetVariableAtIndex(arg_idx);
183fe68904fSGreg Clayton       if (variable_sp)
184fe68904fSGreg Clayton         return variable_sp->GetName().GetCString();
185fe68904fSGreg Clayton     }
186fe68904fSGreg Clayton   }
187fe68904fSGreg Clayton   return nullptr;
188fe68904fSGreg Clayton }
18993d00df5SGreg Clayton 
190b9c1b51eSKate Stone uint32_t SBFunction::GetPrologueByteSize() {
191baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(uint32_t, SBFunction, GetPrologueByteSize);
192baf5664fSJonas Devlieghere 
19393d00df5SGreg Clayton   if (m_opaque_ptr)
19493d00df5SGreg Clayton     return m_opaque_ptr->GetPrologueByteSize();
19593d00df5SGreg Clayton   return 0;
19693d00df5SGreg Clayton }
19793d00df5SGreg Clayton 
198b9c1b51eSKate Stone SBType SBFunction::GetType() {
199baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(lldb::SBType, SBFunction, GetType);
200baf5664fSJonas Devlieghere 
2015569e64eSGreg Clayton   SBType sb_type;
202b9c1b51eSKate Stone   if (m_opaque_ptr) {
2035569e64eSGreg Clayton     Type *function_type = m_opaque_ptr->GetType();
2045569e64eSGreg Clayton     if (function_type)
2055569e64eSGreg Clayton       sb_type.ref().SetType(function_type->shared_from_this());
2065569e64eSGreg Clayton   }
207*d232abc3SJonas Devlieghere   return sb_type;
2085569e64eSGreg Clayton }
2095569e64eSGreg Clayton 
210b9c1b51eSKate Stone SBBlock SBFunction::GetBlock() {
211baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(lldb::SBBlock, SBFunction, GetBlock);
212baf5664fSJonas Devlieghere 
2135569e64eSGreg Clayton   SBBlock sb_block;
2145569e64eSGreg Clayton   if (m_opaque_ptr)
2155569e64eSGreg Clayton     sb_block.SetPtr(&m_opaque_ptr->GetBlock(true));
216*d232abc3SJonas Devlieghere   return sb_block;
2175569e64eSGreg Clayton }
2185569e64eSGreg Clayton 
219b9c1b51eSKate Stone lldb::LanguageType SBFunction::GetLanguage() {
220baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(lldb::LanguageType, SBFunction, GetLanguage);
221baf5664fSJonas Devlieghere 
222b9c1b51eSKate Stone   if (m_opaque_ptr) {
2236cd8e0c9SEnrico Granata     if (m_opaque_ptr->GetCompileUnit())
2246cd8e0c9SEnrico Granata       return m_opaque_ptr->GetCompileUnit()->GetLanguage();
2256cd8e0c9SEnrico Granata   }
2266cd8e0c9SEnrico Granata   return lldb::eLanguageTypeUnknown;
2276cd8e0c9SEnrico Granata }
2285569e64eSGreg Clayton 
229b9c1b51eSKate Stone bool SBFunction::GetIsOptimized() {
230baf5664fSJonas Devlieghere   LLDB_RECORD_METHOD_NO_ARGS(bool, SBFunction, GetIsOptimized);
231baf5664fSJonas Devlieghere 
232b9c1b51eSKate Stone   if (m_opaque_ptr) {
2336ab659a9SJason Molenda     if (m_opaque_ptr->GetCompileUnit())
2346ab659a9SJason Molenda       return m_opaque_ptr->GetCompileUnit()->GetIsOptimized();
2356ab659a9SJason Molenda   }
2366ab659a9SJason Molenda   return false;
2376ab659a9SJason Molenda }
238