24
24
#include " lldb/ValueObject/ValueObject.h"
25
25
#include " lldb/ValueObject/ValueObjectConstResult.h"
26
26
27
+ #include " Plugins/Language/CPlusPlus/CxxStringTypes.h"
28
+ #include " Plugins/Language/CPlusPlus/Generic.h"
27
29
#include " Plugins/LanguageRuntime/CPlusPlus/CPPLanguageRuntime.h"
28
30
#include " Plugins/TypeSystem/Clang/TypeSystemClang.h"
29
31
#include " lldb/lldb-enumerations.h"
@@ -156,39 +158,43 @@ bool lldb_private::formatters::LibcxxSmartPointerSummaryProvider(
156
158
ValueObjectSP valobj_sp (valobj.GetNonSyntheticValue ());
157
159
if (!valobj_sp)
158
160
return false ;
159
- ValueObjectSP ptr_sp (valobj_sp->GetChildMemberWithName (" __ptr_" ));
160
- ValueObjectSP count_sp (
161
- valobj_sp->GetChildAtNamePath ({" __cntrl_" , " __shared_owners_" }));
162
- ValueObjectSP weakcount_sp (
163
- valobj_sp->GetChildAtNamePath ({" __cntrl_" , " __shared_weak_owners_" }));
164
161
165
- if (!ptr_sp)
162
+ ValueObjectSP ptr_sp (valobj_sp->GetChildMemberWithName (" __ptr_" ));
163
+ ValueObjectSP ctrl_sp (valobj_sp->GetChildMemberWithName (" __cntrl_" ));
164
+ if (!ctrl_sp || !ptr_sp)
166
165
return false ;
167
166
168
- if (ptr_sp->GetValueAsUnsigned (0 ) == 0 ) {
169
- stream.Printf (" nullptr" );
167
+ DumpCxxSmartPtrPointerSummary (stream, *ptr_sp, options);
168
+
169
+ bool success;
170
+ uint64_t ctrl_addr = ctrl_sp->GetValueAsUnsigned (0 , &success);
171
+ // Empty control field. We're done.
172
+ if (!success || ctrl_addr == 0 )
170
173
return true ;
171
- } else {
172
- bool print_pointee = false ;
173
- Status error;
174
- ValueObjectSP pointee_sp = ptr_sp->Dereference (error);
175
- if (pointee_sp && error.Success ()) {
176
- if (pointee_sp->DumpPrintableRepresentation (
177
- stream, ValueObject::eValueObjectRepresentationStyleSummary,
178
- lldb::eFormatInvalid,
179
- ValueObject::PrintableRepresentationSpecialCases::eDisable,
180
- false ))
181
- print_pointee = true ;
182
- }
183
- if (!print_pointee)
184
- stream.Printf (" ptr = 0x%" PRIx64, ptr_sp->GetValueAsUnsigned (0 ));
174
+
175
+ if (auto count_sp = ctrl_sp->GetChildMemberWithName (" __shared_owners_" )) {
176
+ bool success;
177
+ uint64_t count = count_sp->GetValueAsUnsigned (0 , &success);
178
+ if (!success)
179
+ return false ;
180
+
181
+ // std::shared_ptr releases the underlying resource when the
182
+ // __shared_owners_ count hits -1. So `__shared_owners_ == 0` indicates 1
183
+ // owner. Hence add +1 here.
184
+ stream.Printf (" strong=%" PRIu64, count + 1 );
185
185
}
186
186
187
- if (count_sp)
188
- stream.Printf (" strong=%" PRIu64, 1 + count_sp->GetValueAsUnsigned (0 ));
187
+ if (auto weak_count_sp =
188
+ ctrl_sp->GetChildMemberWithName (" __shared_weak_owners_" )) {
189
+ bool success;
190
+ uint64_t count = weak_count_sp->GetValueAsUnsigned (0 , &success);
191
+ if (!success)
192
+ return false ;
189
193
190
- if (weakcount_sp)
191
- stream.Printf (" weak=%" PRIu64, 1 + weakcount_sp->GetValueAsUnsigned (0 ));
194
+ // Unlike __shared_owners_, __shared_weak_owners_ indicates the exact
195
+ // std::weak_ptr reference count.
196
+ stream.Printf (" weak=%" PRIu64, count);
197
+ }
192
198
193
199
return true ;
194
200
}
@@ -209,24 +215,7 @@ bool lldb_private::formatters::LibcxxUniquePointerSummaryProvider(
209
215
if (!ptr_sp)
210
216
return false ;
211
217
212
- if (ptr_sp->GetValueAsUnsigned (0 ) == 0 ) {
213
- stream.Printf (" nullptr" );
214
- return true ;
215
- } else {
216
- bool print_pointee = false ;
217
- Status error;
218
- ValueObjectSP pointee_sp = ptr_sp->Dereference (error);
219
- if (pointee_sp && error.Success ()) {
220
- if (pointee_sp->DumpPrintableRepresentation (
221
- stream, ValueObject::eValueObjectRepresentationStyleSummary,
222
- lldb::eFormatInvalid,
223
- ValueObject::PrintableRepresentationSpecialCases::eDisable,
224
- false ))
225
- print_pointee = true ;
226
- }
227
- if (!print_pointee)
228
- stream.Printf (" ptr = 0x%" PRIx64, ptr_sp->GetValueAsUnsigned (0 ));
229
- }
218
+ DumpCxxSmartPtrPointerSummary (stream, *ptr_sp, options);
230
219
231
220
return true ;
232
221
}
@@ -250,7 +239,8 @@ lldb_private::formatters::LibCxxVectorIteratorSyntheticFrontEndCreator(
250
239
251
240
lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::
252
241
LibcxxSharedPtrSyntheticFrontEnd (lldb::ValueObjectSP valobj_sp)
253
- : SyntheticChildrenFrontEnd(*valobj_sp), m_cntrl(nullptr ) {
242
+ : SyntheticChildrenFrontEnd(*valobj_sp), m_cntrl(nullptr ),
243
+ m_ptr_obj(nullptr ) {
254
244
if (valobj_sp)
255
245
Update ();
256
246
}
@@ -263,28 +253,21 @@ llvm::Expected<uint32_t> lldb_private::formatters::
263
253
lldb::ValueObjectSP
264
254
lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::GetChildAtIndex (
265
255
uint32_t idx) {
266
- if (!m_cntrl)
256
+ if (!m_cntrl || !m_ptr_obj )
267
257
return lldb::ValueObjectSP ();
268
258
269
259
ValueObjectSP valobj_sp = m_backend.GetSP ();
270
260
if (!valobj_sp)
271
261
return lldb::ValueObjectSP ();
272
262
273
263
if (idx == 0 )
274
- return valobj_sp-> GetChildMemberWithName ( " __ptr_ " );
264
+ return m_ptr_obj-> GetSP ( );
275
265
276
266
if (idx == 1 ) {
277
- if (auto ptr_sp = valobj_sp->GetChildMemberWithName (" __ptr_" )) {
278
- Status status;
279
- auto value_type_sp =
280
- valobj_sp->GetCompilerType ()
281
- .GetTypeTemplateArgument (0 ).GetPointerType ();
282
- ValueObjectSP cast_ptr_sp = ptr_sp->Cast (value_type_sp);
283
- ValueObjectSP value_sp = cast_ptr_sp->Dereference (status);
284
- if (status.Success ()) {
285
- return value_sp;
286
- }
287
- }
267
+ Status status;
268
+ ValueObjectSP value_sp = m_ptr_obj->Dereference (status);
269
+ if (status.Success ())
270
+ return value_sp;
288
271
}
289
272
290
273
return lldb::ValueObjectSP ();
@@ -293,6 +276,7 @@ lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::GetChildAtIndex(
293
276
lldb::ChildCacheState
294
277
lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::Update () {
295
278
m_cntrl = nullptr ;
279
+ m_ptr_obj = nullptr ;
296
280
297
281
ValueObjectSP valobj_sp = m_backend.GetSP ();
298
282
if (!valobj_sp)
@@ -302,6 +286,16 @@ lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::Update() {
302
286
if (!target_sp)
303
287
return lldb::ChildCacheState::eRefetch;
304
288
289
+ auto ptr_obj_sp = valobj_sp->GetChildMemberWithName (" __ptr_" );
290
+ if (!ptr_obj_sp)
291
+ return lldb::ChildCacheState::eRefetch;
292
+
293
+ auto cast_ptr_sp = GetDesugaredSmartPointerValue (*ptr_obj_sp, *valobj_sp);
294
+ if (!cast_ptr_sp)
295
+ return lldb::ChildCacheState::eRefetch;
296
+
297
+ m_ptr_obj = cast_ptr_sp->Clone (ConstString (" pointer" )).get ();
298
+
305
299
lldb::ValueObjectSP cntrl_sp (valobj_sp->GetChildMemberWithName (" __cntrl_" ));
306
300
307
301
m_cntrl = cntrl_sp.get (); // need to store the raw pointer to avoid a circular
@@ -316,10 +310,12 @@ bool lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::
316
310
317
311
size_t lldb_private::formatters::LibcxxSharedPtrSyntheticFrontEnd::
318
312
GetIndexOfChildWithName (ConstString name) {
319
- if (name == " __ptr_ " )
313
+ if (name == " pointer " )
320
314
return 0 ;
321
- if (name == " $$dereference$$" )
315
+
316
+ if (name == " object" || name == " $$dereference$$" )
322
317
return 1 ;
318
+
323
319
return UINT32_MAX;
324
320
}
325
321
@@ -423,7 +419,7 @@ size_t lldb_private::formatters::LibcxxUniquePtrSyntheticFrontEnd::
423
419
return 0 ;
424
420
if (name == " deleter" )
425
421
return 1 ;
426
- if (name == " $$dereference$$" )
422
+ if (name == " obj " || name == " object " || name == " $$dereference$$" )
427
423
return 2 ;
428
424
return UINT32_MAX;
429
425
}
0 commit comments