1 //===-- FormatClasses.h -----------------------------------------*- 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 #ifndef lldb_FormatClasses_h_
11 #define lldb_FormatClasses_h_
12 
13 #include <functional>
14 #include <memory>
15 #include <string>
16 #include <vector>
17 
18 #include "lldb/DataFormatters/TypeFormat.h"
19 #include "lldb/DataFormatters/TypeSummary.h"
20 #include "lldb/DataFormatters/TypeSynthetic.h"
21 #include "lldb/DataFormatters/TypeValidator.h"
22 #include "lldb/Symbol/CompilerType.h"
23 #include "lldb/Symbol/Type.h"
24 #include "lldb/lldb-enumerations.h"
25 #include "lldb/lldb-public.h"
26 
27 namespace lldb_private {
28 
29 class HardcodedFormatters {
30 public:
31   template <typename FormatterType>
32   using HardcodedFormatterFinder =
33       std::function<typename FormatterType::SharedPointer(
34           lldb_private::ValueObject &, lldb::DynamicValueType,
35           FormatManager &)>;
36 
37   template <typename FormatterType>
38   using HardcodedFormatterFinders =
39       std::vector<HardcodedFormatterFinder<FormatterType>>;
40 
41   typedef HardcodedFormatterFinders<TypeFormatImpl> HardcodedFormatFinder;
42   typedef HardcodedFormatterFinders<TypeSummaryImpl> HardcodedSummaryFinder;
43   typedef HardcodedFormatterFinders<SyntheticChildren> HardcodedSyntheticFinder;
44   typedef HardcodedFormatterFinders<TypeValidatorImpl> HardcodedValidatorFinder;
45 };
46 
47 class FormattersMatchCandidate {
48 public:
FormattersMatchCandidate(ConstString name,uint32_t reason,bool strip_ptr,bool strip_ref,bool strip_tydef)49   FormattersMatchCandidate(ConstString name, uint32_t reason, bool strip_ptr,
50                            bool strip_ref, bool strip_tydef)
51       : m_type_name(name), m_reason(reason), m_stripped_pointer(strip_ptr),
52         m_stripped_reference(strip_ref), m_stripped_typedef(strip_tydef) {}
53 
54   ~FormattersMatchCandidate() = default;
55 
GetTypeName()56   ConstString GetTypeName() const { return m_type_name; }
57 
GetReason()58   uint32_t GetReason() const { return m_reason; }
59 
DidStripPointer()60   bool DidStripPointer() const { return m_stripped_pointer; }
61 
DidStripReference()62   bool DidStripReference() const { return m_stripped_reference; }
63 
DidStripTypedef()64   bool DidStripTypedef() const { return m_stripped_typedef; }
65 
66   template <class Formatter>
IsMatch(const std::shared_ptr<Formatter> & formatter_sp)67   bool IsMatch(const std::shared_ptr<Formatter> &formatter_sp) const {
68     if (!formatter_sp)
69       return false;
70     if (formatter_sp->Cascades() == false && DidStripTypedef())
71       return false;
72     if (formatter_sp->SkipsPointers() && DidStripPointer())
73       return false;
74     if (formatter_sp->SkipsReferences() && DidStripReference())
75       return false;
76     return true;
77   }
78 
79 private:
80   ConstString m_type_name;
81   uint32_t m_reason;
82   bool m_stripped_pointer;
83   bool m_stripped_reference;
84   bool m_stripped_typedef;
85 };
86 
87 typedef std::vector<FormattersMatchCandidate> FormattersMatchVector;
88 typedef std::vector<lldb::LanguageType> CandidateLanguagesVector;
89 
90 class FormattersMatchData {
91 public:
92   FormattersMatchData(ValueObject &, lldb::DynamicValueType);
93 
94   FormattersMatchVector GetMatchesVector();
95 
96   ConstString GetTypeForCache();
97 
98   CandidateLanguagesVector GetCandidateLanguages();
99 
100   ValueObject &GetValueObject();
101 
102   lldb::DynamicValueType GetDynamicValueType();
103 
104 private:
105   ValueObject &m_valobj;
106   lldb::DynamicValueType m_dynamic_value_type;
107   std::pair<FormattersMatchVector, bool> m_formatters_match_vector;
108   ConstString m_type_for_cache;
109   CandidateLanguagesVector m_candidate_languages;
110 };
111 
112 class TypeNameSpecifierImpl {
113 public:
TypeNameSpecifierImpl()114   TypeNameSpecifierImpl() : m_is_regex(false), m_type() {}
115 
TypeNameSpecifierImpl(llvm::StringRef name,bool is_regex)116   TypeNameSpecifierImpl(llvm::StringRef name, bool is_regex)
117       : m_is_regex(is_regex), m_type() {
118     m_type.m_type_name = name;
119   }
120 
121   // if constructing with a given type, is_regex cannot be true since we are
122   // giving an exact type to match
TypeNameSpecifierImpl(lldb::TypeSP type)123   TypeNameSpecifierImpl(lldb::TypeSP type) : m_is_regex(false), m_type() {
124     if (type) {
125       m_type.m_type_name = type->GetName().GetStringRef();
126       m_type.m_type_pair.SetType(type);
127     }
128   }
129 
TypeNameSpecifierImpl(CompilerType type)130   TypeNameSpecifierImpl(CompilerType type) : m_is_regex(false), m_type() {
131     if (type.IsValid()) {
132       m_type.m_type_name.assign(type.GetConstTypeName().GetCString());
133       m_type.m_type_pair.SetType(type);
134     }
135   }
136 
GetName()137   const char *GetName() {
138     if (m_type.m_type_name.size())
139       return m_type.m_type_name.c_str();
140     return nullptr;
141   }
142 
GetTypeSP()143   lldb::TypeSP GetTypeSP() {
144     if (m_type.m_type_pair.IsValid())
145       return m_type.m_type_pair.GetTypeSP();
146     return lldb::TypeSP();
147   }
148 
GetCompilerType()149   CompilerType GetCompilerType() {
150     if (m_type.m_type_pair.IsValid())
151       return m_type.m_type_pair.GetCompilerType();
152     return CompilerType();
153   }
154 
IsRegex()155   bool IsRegex() { return m_is_regex; }
156 
157 private:
158   bool m_is_regex;
159   // this works better than TypeAndOrName because the latter only wraps a
160   // TypeSP whereas TypePair can also be backed by a CompilerType
161   struct TypeOrName {
162     std::string m_type_name;
163     TypePair m_type_pair;
164   };
165   TypeOrName m_type;
166 
167 private:
168   DISALLOW_COPY_AND_ASSIGN(TypeNameSpecifierImpl);
169 };
170 
171 } // namespace lldb_private
172 
173 #endif // lldb_FormatClasses_h_
174