1 //===-- SBTypeSummary.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 "lldb/API/SBTypeSummary.h"
11 
12 #include "lldb/API/SBStream.h"
13 
14 #include "lldb/Core/DataVisualization.h"
15 
16 using namespace lldb;
17 using namespace lldb_private;
18 
19 #ifndef LLDB_DISABLE_PYTHON
20 
21 SBTypeSummary::SBTypeSummary() :
22 m_opaque_sp()
23 {
24 }
25 
26 SBTypeSummary
27 SBTypeSummary::CreateWithSummaryString (const char* data, uint32_t options)
28 {
29     if (!data || data[0] == 0)
30         return SBTypeSummary();
31 
32     return SBTypeSummary(TypeSummaryImplSP(new StringSummaryFormat(options, data)));
33 }
34 
35 SBTypeSummary
36 SBTypeSummary::CreateWithFunctionName (const char* data, uint32_t options)
37 {
38     if (!data || data[0] == 0)
39         return SBTypeSummary();
40 
41     return SBTypeSummary(TypeSummaryImplSP(new ScriptSummaryFormat(options, data)));
42 }
43 
44 SBTypeSummary
45 SBTypeSummary::CreateWithScriptCode (const char* data, uint32_t options)
46 {
47     if (!data || data[0] == 0)
48         return SBTypeSummary();
49 
50     return SBTypeSummary(TypeSummaryImplSP(new ScriptSummaryFormat(options, "", data)));
51 }
52 
53 SBTypeSummary::SBTypeSummary (const lldb::SBTypeSummary &rhs) :
54 m_opaque_sp(rhs.m_opaque_sp)
55 {
56 }
57 
58 SBTypeSummary::~SBTypeSummary ()
59 {
60 }
61 
62 bool
63 SBTypeSummary::IsValid() const
64 {
65     return m_opaque_sp.get() != NULL;
66 }
67 
68 bool
69 SBTypeSummary::IsFunctionCode()
70 {
71     if (!IsValid())
72         return false;
73     if (m_opaque_sp->IsScripted())
74     {
75         ScriptSummaryFormat* script_summary_ptr = (ScriptSummaryFormat*)m_opaque_sp.get();
76         const char* ftext = script_summary_ptr->GetPythonScript();
77         return (ftext && *ftext != 0);
78     }
79     return false;
80 }
81 
82 bool
83 SBTypeSummary::IsFunctionName()
84 {
85     if (!IsValid())
86         return false;
87     if (m_opaque_sp->IsScripted())
88     {
89         ScriptSummaryFormat* script_summary_ptr = (ScriptSummaryFormat*)m_opaque_sp.get();
90         const char* ftext = script_summary_ptr->GetPythonScript();
91         return (!ftext || *ftext == 0);
92     }
93     return false;
94 }
95 
96 bool
97 SBTypeSummary::IsSummaryString()
98 {
99     if (!IsValid())
100         return false;
101 
102     if (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback)
103         return false;
104 
105     return !m_opaque_sp->IsScripted();
106 }
107 
108 const char*
109 SBTypeSummary::GetData ()
110 {
111     if (!IsValid())
112         return NULL;
113     if (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback)
114         return NULL;
115     if (m_opaque_sp->IsScripted())
116     {
117         ScriptSummaryFormat* script_summary_ptr = (ScriptSummaryFormat*)m_opaque_sp.get();
118         const char* fname = script_summary_ptr->GetFunctionName();
119         const char* ftext = script_summary_ptr->GetPythonScript();
120         if (ftext && *ftext)
121             return ftext;
122         return fname;
123     }
124     else
125     {
126         StringSummaryFormat* string_summary_ptr = (StringSummaryFormat*)m_opaque_sp.get();
127         return string_summary_ptr->GetSummaryString();
128     }
129 }
130 
131 uint32_t
132 SBTypeSummary::GetOptions ()
133 {
134     if (!IsValid())
135         return lldb::eTypeOptionNone;
136     return m_opaque_sp->GetOptions();
137 }
138 
139 void
140 SBTypeSummary::SetOptions (uint32_t value)
141 {
142     if (!CopyOnWrite_Impl())
143         return;
144     m_opaque_sp->SetOptions(value);
145 }
146 
147 void
148 SBTypeSummary::SetSummaryString (const char* data)
149 {
150     if (!IsValid())
151         return;
152     if (m_opaque_sp->IsScripted() || (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback))
153         ChangeSummaryType(false);
154     ((StringSummaryFormat*)m_opaque_sp.get())->SetSummaryString(data);
155 }
156 
157 void
158 SBTypeSummary::SetFunctionName (const char* data)
159 {
160     if (!IsValid())
161         return;
162     if (!m_opaque_sp->IsScripted())
163         ChangeSummaryType(true);
164     ((ScriptSummaryFormat*)m_opaque_sp.get())->SetFunctionName(data);
165 }
166 
167 void
168 SBTypeSummary::SetFunctionCode (const char* data)
169 {
170     if (!IsValid())
171         return;
172     if (!m_opaque_sp->IsScripted())
173         ChangeSummaryType(true);
174     ((ScriptSummaryFormat*)m_opaque_sp.get())->SetPythonScript(data);
175 }
176 
177 bool
178 SBTypeSummary::GetDescription (lldb::SBStream &description,
179                               lldb::DescriptionLevel description_level)
180 {
181     if (!CopyOnWrite_Impl())
182         return false;
183     else {
184         description.Printf("%s\n",
185                            m_opaque_sp->GetDescription().c_str());
186         return true;
187     }
188 }
189 
190 lldb::SBTypeSummary &
191 SBTypeSummary::operator = (const lldb::SBTypeSummary &rhs)
192 {
193     if (this != &rhs)
194     {
195         m_opaque_sp = rhs.m_opaque_sp;
196     }
197     return *this;
198 }
199 
200 bool
201 SBTypeSummary::operator == (lldb::SBTypeSummary &rhs)
202 {
203     if (IsValid() == false)
204         return !rhs.IsValid();
205     return m_opaque_sp == rhs.m_opaque_sp;
206 }
207 
208 bool
209 SBTypeSummary::IsEqualTo (lldb::SBTypeSummary &rhs)
210 {
211     if (IsValid() == false)
212         return !rhs.IsValid();
213 
214     if (m_opaque_sp->GetType() != rhs.m_opaque_sp->GetType())
215         return false;
216 
217     if (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback)
218     {
219         lldb_private::CXXFunctionSummaryFormat *self_cxx = (lldb_private::CXXFunctionSummaryFormat*)m_opaque_sp.get();
220         lldb_private::CXXFunctionSummaryFormat *other_cxx = (lldb_private::CXXFunctionSummaryFormat*)rhs.m_opaque_sp.get();
221         return (self_cxx->m_impl == other_cxx->m_impl);
222     }
223 
224     if (m_opaque_sp->IsScripted() != rhs.m_opaque_sp->IsScripted())
225         return false;
226 
227     if (IsFunctionCode() != rhs.IsFunctionCode())
228         return false;
229 
230     if (IsSummaryString() != rhs.IsSummaryString())
231         return false;
232 
233     if (IsFunctionName() != rhs.IsFunctionName())
234         return false;
235 
236     if ( strcmp(GetData(), rhs.GetData()) )
237         return false;
238 
239     return GetOptions() == rhs.GetOptions();
240 
241 }
242 
243 bool
244 SBTypeSummary::operator != (lldb::SBTypeSummary &rhs)
245 {
246     if (IsValid() == false)
247         return !rhs.IsValid();
248     return m_opaque_sp != rhs.m_opaque_sp;
249 }
250 
251 lldb::TypeSummaryImplSP
252 SBTypeSummary::GetSP ()
253 {
254     return m_opaque_sp;
255 }
256 
257 void
258 SBTypeSummary::SetSP (const lldb::TypeSummaryImplSP &typesummary_impl_sp)
259 {
260     m_opaque_sp = typesummary_impl_sp;
261 }
262 
263 SBTypeSummary::SBTypeSummary (const lldb::TypeSummaryImplSP &typesummary_impl_sp) :
264 m_opaque_sp(typesummary_impl_sp)
265 {
266 }
267 
268 bool
269 SBTypeSummary::CopyOnWrite_Impl()
270 {
271     if (!IsValid())
272         return false;
273 
274     if (m_opaque_sp.unique())
275         return true;
276 
277     TypeSummaryImplSP new_sp;
278 
279     if (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback)
280     {
281         CXXFunctionSummaryFormat* current_summary_ptr = (CXXFunctionSummaryFormat*)m_opaque_sp.get();
282         new_sp = TypeSummaryImplSP(new CXXFunctionSummaryFormat(GetOptions(),
283                                                                 current_summary_ptr->m_impl,
284                                                                 current_summary_ptr->m_description.c_str()));
285     }
286     else if (m_opaque_sp->IsScripted())
287     {
288         ScriptSummaryFormat* current_summary_ptr = (ScriptSummaryFormat*)m_opaque_sp.get();
289         new_sp = TypeSummaryImplSP(new ScriptSummaryFormat(GetOptions(),
290                                                            current_summary_ptr->GetFunctionName(),
291                                                            current_summary_ptr->GetPythonScript()));
292     }
293     else {
294         StringSummaryFormat* current_summary_ptr = (StringSummaryFormat*)m_opaque_sp.get();
295         new_sp = TypeSummaryImplSP(new StringSummaryFormat(GetOptions(),
296                                                            current_summary_ptr->GetSummaryString()));
297     }
298 
299     SetSP(new_sp);
300 
301     return true;
302 }
303 
304 bool
305 SBTypeSummary::ChangeSummaryType (bool want_script)
306 {
307     if (!IsValid())
308         return false;
309 
310     TypeSummaryImplSP new_sp;
311 
312     if (want_script == m_opaque_sp->IsScripted())
313     {
314         if (m_opaque_sp->GetType() == lldb_private::TypeSummaryImpl::eTypeCallback && !want_script)
315             new_sp = TypeSummaryImplSP(new StringSummaryFormat(GetOptions(), ""));
316         else
317             return CopyOnWrite_Impl();
318     }
319 
320     if (!new_sp)
321     {
322         if (want_script)
323             new_sp = TypeSummaryImplSP(new ScriptSummaryFormat(GetOptions(), "", ""));
324         else
325             new_sp = TypeSummaryImplSP(new StringSummaryFormat(GetOptions(), ""));
326     }
327 
328     SetSP(new_sp);
329 
330     return true;
331 }
332 
333 #endif // LLDB_DISABLE_PYTHON
334