1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | #include "lldb/DataFormatters/VectorType.h" |
11 | |
12 | #include "lldb/Core/ValueObject.h" |
13 | #include "lldb/DataFormatters/CXXFormatterFunctions.h" |
14 | #include "lldb/Symbol/ClangASTContext.h" |
15 | #include "lldb/Symbol/CompilerType.h" |
16 | |
17 | #include "lldb/Utility/LLDBAssert.h" |
18 | |
19 | using namespace lldb; |
20 | using namespace lldb_private; |
21 | using namespace lldb_private::formatters; |
22 | |
23 | static CompilerType |
24 | GetClangTypeForFormat (lldb::Format format, |
25 | CompilerType element_type, |
26 | ClangASTContext *ast_ctx) |
27 | { |
28 | lldbassert(ast_ctx && "ast_ctx needs to be not NULL")lldb_private::lldb_assert(ast_ctx && "ast_ctx needs to be not NULL" , "ast_ctx && \"ast_ctx needs to be not NULL\"", __FUNCTION__ , "/tmp/buildd/llvm-toolchain-snapshot-3.8~svn245827/tools/lldb/source/DataFormatters/VectorType.cpp" , 28); |
| 3 | | Within the expansion of the macro 'lldbassert':
| |
a | Assuming pointer value is null |
|
29 | |
30 | switch (format) |
| 4 | | Control jumps to 'case eFormatVectorOfSInt32:' at line 81 | |
|
31 | { |
32 | case lldb::eFormatAddressInfo: |
33 | case lldb::eFormatPointer: |
34 | return ast_ctx->GetPointerSizedIntType(false); |
35 | |
36 | case lldb::eFormatBoolean: |
37 | return ast_ctx->GetBasicType(lldb::eBasicTypeBool); |
38 | |
39 | case lldb::eFormatBytes: |
40 | case lldb::eFormatBytesWithASCII: |
41 | case lldb::eFormatChar: |
42 | case lldb::eFormatCharArray: |
43 | case lldb::eFormatCharPrintable: |
44 | return ast_ctx->GetBasicType(lldb::eBasicTypeChar); |
45 | |
46 | case lldb::eFormatComplex : |
47 | return ast_ctx->GetBasicType(lldb::eBasicTypeFloatComplex); |
48 | |
49 | case lldb::eFormatCString: |
50 | return ast_ctx->GetBasicType(lldb::eBasicTypeChar).GetPointerType(); |
51 | |
52 | case lldb::eFormatFloat: |
53 | return ast_ctx->GetBasicType(lldb::eBasicTypeFloat); |
54 | |
55 | case lldb::eFormatHex: |
56 | case lldb::eFormatHexUppercase: |
57 | case lldb::eFormatOctal: |
58 | return ast_ctx->GetBasicType(lldb::eBasicTypeInt); |
59 | |
60 | case lldb::eFormatHexFloat: |
61 | return ast_ctx->GetBasicType(lldb::eBasicTypeFloat); |
62 | |
63 | case lldb::eFormatUnicode16: |
64 | case lldb::eFormatUnicode32: |
65 | |
66 | case lldb::eFormatUnsigned: |
67 | return ast_ctx->GetBasicType(lldb::eBasicTypeUnsignedInt); |
68 | |
69 | case lldb::eFormatVectorOfChar: |
70 | return ast_ctx->GetBasicType(lldb::eBasicTypeChar); |
71 | |
72 | case lldb::eFormatVectorOfFloat32: |
73 | return ast_ctx->GetFloatTypeFromBitSize(32); |
74 | |
75 | case lldb::eFormatVectorOfFloat64: |
76 | return ast_ctx->GetFloatTypeFromBitSize(64); |
77 | |
78 | case lldb::eFormatVectorOfSInt16: |
79 | return ast_ctx->GetIntTypeFromBitSize(16, true); |
80 | |
81 | case lldb::eFormatVectorOfSInt32: |
82 | return ast_ctx->GetIntTypeFromBitSize(32, true); |
| 5 | | Called C++ object pointer is null |
|
83 | |
84 | case lldb::eFormatVectorOfSInt64: |
85 | return ast_ctx->GetIntTypeFromBitSize(64, true); |
86 | |
87 | case lldb::eFormatVectorOfSInt8: |
88 | return ast_ctx->GetIntTypeFromBitSize(8, true); |
89 | |
90 | case lldb::eFormatVectorOfUInt128: |
91 | return ast_ctx->GetIntTypeFromBitSize(128, false); |
92 | |
93 | case lldb::eFormatVectorOfUInt16: |
94 | return ast_ctx->GetIntTypeFromBitSize(16, false); |
95 | |
96 | case lldb::eFormatVectorOfUInt32: |
97 | return ast_ctx->GetIntTypeFromBitSize(32, false); |
98 | |
99 | case lldb::eFormatVectorOfUInt64: |
100 | return ast_ctx->GetIntTypeFromBitSize(64, false); |
101 | |
102 | case lldb::eFormatVectorOfUInt8: |
103 | return ast_ctx->GetIntTypeFromBitSize(8, false); |
104 | |
105 | case lldb::eFormatDefault: |
106 | return element_type; |
107 | |
108 | case lldb::eFormatBinary: |
109 | case lldb::eFormatComplexInteger: |
110 | case lldb::eFormatDecimal: |
111 | case lldb::eFormatEnum: |
112 | case lldb::eFormatInstruction: |
113 | case lldb::eFormatOSType: |
114 | case lldb::eFormatVoid: |
115 | default: |
116 | return ast_ctx->GetIntTypeFromBitSize(8, false); |
117 | } |
118 | } |
119 | |
120 | static lldb::Format |
121 | GetItemFormatForFormat (lldb::Format format, |
122 | CompilerType element_type) |
123 | { |
124 | switch (format) |
125 | { |
126 | case lldb::eFormatVectorOfChar: |
127 | return lldb::eFormatChar; |
128 | |
129 | case lldb::eFormatVectorOfFloat32: |
130 | case lldb::eFormatVectorOfFloat64: |
131 | return lldb::eFormatFloat; |
132 | |
133 | case lldb::eFormatVectorOfSInt16: |
134 | case lldb::eFormatVectorOfSInt32: |
135 | case lldb::eFormatVectorOfSInt64: |
136 | case lldb::eFormatVectorOfSInt8: |
137 | return lldb::eFormatDecimal; |
138 | |
139 | case lldb::eFormatVectorOfUInt128: |
140 | case lldb::eFormatVectorOfUInt16: |
141 | case lldb::eFormatVectorOfUInt32: |
142 | case lldb::eFormatVectorOfUInt64: |
143 | case lldb::eFormatVectorOfUInt8: |
144 | return lldb::eFormatUnsigned; |
145 | |
146 | case lldb::eFormatBinary: |
147 | case lldb::eFormatComplexInteger: |
148 | case lldb::eFormatDecimal: |
149 | case lldb::eFormatEnum: |
150 | case lldb::eFormatInstruction: |
151 | case lldb::eFormatOSType: |
152 | case lldb::eFormatVoid: |
153 | return eFormatHex; |
154 | |
155 | case lldb::eFormatDefault: |
156 | { |
157 | |
158 | |
159 | bool is_char = element_type.IsCharType(); |
160 | bool is_signed = false; |
161 | element_type.IsIntegerType(is_signed); |
162 | return is_char ? (is_signed ? lldb::eFormatDecimal : eFormatHex) : format; |
163 | } |
164 | break; |
165 | |
166 | default: |
167 | return format; |
168 | } |
169 | } |
170 | |
171 | static size_t |
172 | CalculateNumChildren (CompilerType container_type, |
173 | CompilerType element_type, |
174 | lldb_private::ExecutionContextScope *exe_scope = nullptr |
175 | ) |
176 | { |
177 | auto container_size = container_type.GetByteSize(exe_scope); |
178 | auto element_size = element_type.GetByteSize(exe_scope); |
179 | |
180 | if (element_size) |
181 | { |
182 | if (container_size % element_size) |
183 | return 0; |
184 | return container_size / element_size; |
185 | } |
186 | return 0; |
187 | } |
188 | |
189 | namespace lldb_private { |
190 | namespace formatters { |
191 | |
192 | class VectorTypeSyntheticFrontEnd : public SyntheticChildrenFrontEnd |
193 | { |
194 | public: |
195 | VectorTypeSyntheticFrontEnd (lldb::ValueObjectSP valobj_sp) : |
196 | SyntheticChildrenFrontEnd(*valobj_sp), |
197 | m_parent_format (eFormatInvalid), |
198 | m_item_format(eFormatInvalid), |
199 | m_child_type(), |
200 | m_num_children(0) |
201 | {} |
202 | |
203 | virtual size_t |
204 | CalculateNumChildren () |
205 | { |
206 | return m_num_children; |
207 | } |
208 | |
209 | virtual lldb::ValueObjectSP |
210 | GetChildAtIndex (size_t idx) |
211 | { |
212 | if (idx >= CalculateNumChildren()) |
213 | return lldb::ValueObjectSP(); |
214 | auto offset = idx * m_child_type.GetByteSize(nullptr); |
215 | ValueObjectSP child_sp(m_backend.GetSyntheticChildAtOffset(offset, m_child_type, true)); |
216 | if (!child_sp) |
217 | return child_sp; |
218 | |
219 | StreamString idx_name; |
220 | idx_name.Printf("[%" PRIu64"l" "u" "]", (uint64_t)idx); |
221 | child_sp->SetName( ConstString( idx_name.GetData() ) ); |
222 | |
223 | child_sp->SetFormat(m_item_format); |
224 | |
225 | return child_sp; |
226 | } |
227 | |
228 | virtual bool |
229 | Update() |
230 | { |
231 | m_parent_format = m_backend.GetFormat(); |
232 | CompilerType parent_type(m_backend.GetClangType()); |
233 | CompilerType element_type; |
234 | parent_type.IsVectorType(&element_type, nullptr); |
235 | m_child_type = ::GetClangTypeForFormat(m_parent_format, element_type, parent_type.GetTypeSystem()->AsClangASTContext()); |
| 1 | Passing value via 3rd parameter 'ast_ctx' | |
|
| 2 | | Calling 'GetClangTypeForFormat' | |
|
236 | m_num_children = ::CalculateNumChildren(parent_type, |
237 | m_child_type); |
238 | m_item_format = GetItemFormatForFormat(m_parent_format, |
239 | m_child_type); |
240 | return false; |
241 | } |
242 | |
243 | virtual bool |
244 | MightHaveChildren () |
245 | { |
246 | return true; |
247 | } |
248 | |
249 | virtual size_t |
250 | GetIndexOfChildWithName (const ConstString &name) |
251 | { |
252 | const char* item_name = name.GetCString(); |
253 | uint32_t idx = ExtractIndexFromString(item_name); |
254 | if (idx < UINT32_MAX(4294967295U) && idx >= CalculateNumChildren()) |
255 | return UINT32_MAX(4294967295U); |
256 | return idx; |
257 | } |
258 | |
259 | virtual |
260 | ~VectorTypeSyntheticFrontEnd () {} |
261 | |
262 | private: |
263 | lldb::Format m_parent_format; |
264 | lldb::Format m_item_format; |
265 | CompilerType m_child_type; |
266 | size_t m_num_children; |
267 | }; |
268 | } |
269 | } |
270 | |
271 | bool |
272 | lldb_private::formatters::VectorTypeSummaryProvider (ValueObject& valobj, |
273 | Stream& s, |
274 | const TypeSummaryOptions&) |
275 | { |
276 | auto synthetic_children = VectorTypeSyntheticFrontEndCreator(nullptr, valobj.GetSP()); |
277 | if (!synthetic_children) |
278 | return false; |
279 | |
280 | synthetic_children->Update(); |
281 | |
282 | s.PutChar('('); |
283 | bool first = true; |
284 | |
285 | size_t idx = 0, len = synthetic_children->CalculateNumChildren(); |
286 | |
287 | for (; |
288 | idx < len; |
289 | idx++) |
290 | { |
291 | auto child_sp = synthetic_children->GetChildAtIndex(idx); |
292 | if (!child_sp) |
293 | continue; |
294 | child_sp = child_sp->GetQualifiedRepresentationIfAvailable(lldb::eDynamicDontRunTarget, true); |
295 | |
296 | const char* child_value = child_sp->GetValueAsCString(); |
297 | if (child_value && *child_value) |
298 | { |
299 | if (first) |
300 | { |
301 | s.Printf("%s", child_value); |
302 | first = false; |
303 | } |
304 | else |
305 | { |
306 | s.Printf(", %s", child_value); |
307 | } |
308 | } |
309 | } |
310 | |
311 | s.PutChar(')'); |
312 | |
313 | return true; |
314 | } |
315 | |
316 | lldb_private::SyntheticChildrenFrontEnd* |
317 | lldb_private::formatters::VectorTypeSyntheticFrontEndCreator (CXXSyntheticChildren*, lldb::ValueObjectSP valobj_sp) |
318 | { |
319 | if (!valobj_sp) |
320 | return NULL__null; |
321 | return (new VectorTypeSyntheticFrontEnd(valobj_sp)); |
322 | } |