1 //===-- LibCxxTuple.cpp -----------------------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "LibCxx.h" 11 #include "lldb/DataFormatters/FormattersHelpers.h" 12 13 using namespace lldb; 14 using namespace lldb_private; 15 16 namespace { 17 18 class TupleFrontEnd: public SyntheticChildrenFrontEnd { 19 public: 20 TupleFrontEnd(ValueObject &valobj) : SyntheticChildrenFrontEnd(valobj) { 21 Update(); 22 } 23 24 size_t GetIndexOfChildWithName(const ConstString &name) override { 25 return formatters::ExtractIndexFromString(name.GetCString()); 26 } 27 28 bool MightHaveChildren() override { return true; } 29 bool Update() override; 30 size_t CalculateNumChildren() override { return m_elements.size(); } 31 ValueObjectSP GetChildAtIndex(size_t idx) override; 32 33 private: 34 std::vector<ValueObjectSP> m_elements; 35 ValueObjectSP m_base_sp; 36 }; 37 } 38 39 bool TupleFrontEnd::Update() { 40 m_elements.clear(); 41 m_base_sp = m_backend.GetChildMemberWithName(ConstString("__base_"), true); 42 if (! m_base_sp) { 43 // Pre r304382 name of the base element. 44 m_base_sp = m_backend.GetChildMemberWithName(ConstString("base_"), true); 45 } 46 if (! m_base_sp) 47 return false; 48 m_elements.assign(m_base_sp->GetCompilerType().GetNumDirectBaseClasses(), 49 ValueObjectSP()); 50 return false; 51 } 52 53 ValueObjectSP TupleFrontEnd::GetChildAtIndex(size_t idx) { 54 if (idx >= m_elements.size()) 55 return ValueObjectSP(); 56 if (!m_base_sp) 57 return ValueObjectSP(); 58 if (m_elements[idx]) 59 return m_elements[idx]; 60 61 CompilerType holder_type = 62 m_base_sp->GetCompilerType().GetDirectBaseClassAtIndex(idx, nullptr); 63 if (!holder_type) 64 return ValueObjectSP(); 65 ValueObjectSP holder_sp = m_base_sp->GetChildAtIndex(idx, true); 66 if (!holder_sp) 67 return ValueObjectSP(); 68 69 ValueObjectSP elem_sp = holder_sp->GetChildAtIndex(0, true); 70 if (elem_sp) 71 m_elements[idx] = 72 elem_sp->Clone(ConstString(llvm::formatv("[{0}]", idx).str())); 73 74 return m_elements[idx]; 75 } 76 77 SyntheticChildrenFrontEnd * 78 formatters::LibcxxTupleFrontEndCreator(CXXSyntheticChildren *, 79 lldb::ValueObjectSP valobj_sp) { 80 if (valobj_sp) 81 return new TupleFrontEnd(*valobj_sp); 82 return nullptr; 83 } 84