1 //===-- ObjCLanguage.cpp ----------------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
14 // Other libraries and framework includes
16 #include "ObjCLanguage.h"
18 #include "lldb/Core/PluginManager.h"
19 #include "lldb/Core/ValueObject.h"
20 #include "lldb/DataFormatters/DataVisualization.h"
21 #include "lldb/DataFormatters/FormattersHelpers.h"
22 #include "lldb/Symbol/ClangASTContext.h"
23 #include "lldb/Symbol/CompilerType.h"
24 #include "lldb/Target/ObjCLanguageRuntime.h"
25 #include "lldb/Target/Target.h"
26 #include "lldb/Utility/ConstString.h"
27 #include "lldb/Utility/StreamString.h"
29 #include "llvm/Support/Threading.h"
33 #include "CoreMedia.h"
34 #include "NSDictionary.h"
39 using namespace lldb_private;
40 using namespace lldb_private::formatters;
42 void ObjCLanguage::Initialize() {
43 PluginManager::RegisterPlugin(GetPluginNameStatic(), "Objective-C Language",
47 void ObjCLanguage::Terminate() {
48 PluginManager::UnregisterPlugin(CreateInstance);
51 lldb_private::ConstString ObjCLanguage::GetPluginNameStatic() {
52 static ConstString g_name("objc");
56 //------------------------------------------------------------------
57 // PluginInterface protocol
58 //------------------------------------------------------------------
60 lldb_private::ConstString ObjCLanguage::GetPluginName() {
61 return GetPluginNameStatic();
64 uint32_t ObjCLanguage::GetPluginVersion() { return 1; }
66 //------------------------------------------------------------------
68 //------------------------------------------------------------------
70 Language *ObjCLanguage::CreateInstance(lldb::LanguageType language) {
72 case lldb::eLanguageTypeObjC:
73 return new ObjCLanguage();
79 void ObjCLanguage::MethodName::Clear() {
84 m_type = eTypeUnspecified;
85 m_category_is_valid = false;
88 bool ObjCLanguage::MethodName::SetName(llvm::StringRef name, bool strict) {
91 return IsValid(strict);
93 // If "strict" is true. then the method must be specified with a '+' or '-'
94 // at the beginning. If "strict" is false, then the '+' or '-' can be omitted
95 bool valid_prefix = false;
97 if (name.size() > 1 && (name[0] == '+' || name[0] == '-')) {
98 valid_prefix = name[1] == '[';
100 m_type = eTypeClassMethod;
102 m_type = eTypeInstanceMethod;
103 } else if (!strict) {
104 // "strict" is false, the name just needs to start with '['
105 valid_prefix = name[0] == '[';
109 int name_len = name.size();
110 // Objective-C methods must have at least:
111 // "-[" or "+[" prefix
112 // One character for a class name
113 // One character for the space between the class name
114 // One character for the method name
116 if (name_len >= (5 + (strict ? 1 : 0)) && name.back() == ']') {
117 m_full.SetString(name);
120 return IsValid(strict);
123 bool ObjCLanguage::MethodName::SetName(const char *name, bool strict) {
124 return SetName(llvm::StringRef(name), strict);
127 const ConstString &ObjCLanguage::MethodName::GetClassName() {
129 if (IsValid(false)) {
130 const char *full = m_full.GetCString();
131 const char *class_start = (full[0] == '[' ? full + 1 : full + 2);
132 const char *paren_pos = strchr(class_start, '(');
134 m_class.SetCStringWithLength(class_start, paren_pos - class_start);
136 // No '(' was found in the full name, we can definitively say that our
137 // category was valid (and empty).
138 m_category_is_valid = true;
139 const char *space_pos = strchr(full, ' ');
141 m_class.SetCStringWithLength(class_start, space_pos - class_start);
142 if (!m_class_category) {
143 // No category in name, so we can also fill in the m_class_category
144 m_class_category = m_class;
153 const ConstString &ObjCLanguage::MethodName::GetClassNameWithCategory() {
154 if (!m_class_category) {
155 if (IsValid(false)) {
156 const char *full = m_full.GetCString();
157 const char *class_start = (full[0] == '[' ? full + 1 : full + 2);
158 const char *space_pos = strchr(full, ' ');
160 m_class_category.SetCStringWithLength(class_start,
161 space_pos - class_start);
162 // If m_class hasn't been filled in and the class with category doesn't
163 // contain a '(', then we can also fill in the m_class
164 if (!m_class && strchr(m_class_category.GetCString(), '(') == nullptr) {
165 m_class = m_class_category;
166 // No '(' was found in the full name, we can definitively say that
167 // our category was valid (and empty).
168 m_category_is_valid = true;
173 return m_class_category;
176 const ConstString &ObjCLanguage::MethodName::GetSelector() {
178 if (IsValid(false)) {
179 const char *full = m_full.GetCString();
180 const char *space_pos = strchr(full, ' ');
182 ++space_pos; // skip the space
183 m_selector.SetCStringWithLength(space_pos, m_full.GetLength() -
184 (space_pos - full) - 1);
191 const ConstString &ObjCLanguage::MethodName::GetCategory() {
192 if (!m_category_is_valid && !m_category) {
193 if (IsValid(false)) {
194 m_category_is_valid = true;
195 const char *full = m_full.GetCString();
196 const char *class_start = (full[0] == '[' ? full + 1 : full + 2);
197 const char *open_paren_pos = strchr(class_start, '(');
198 if (open_paren_pos) {
199 ++open_paren_pos; // Skip the open paren
200 const char *close_paren_pos = strchr(open_paren_pos, ')');
202 m_category.SetCStringWithLength(open_paren_pos,
203 close_paren_pos - open_paren_pos);
210 ConstString ObjCLanguage::MethodName::GetFullNameWithoutCategory(
211 bool empty_if_no_category) {
212 if (IsValid(false)) {
215 if (m_type == eTypeClassMethod)
217 else if (m_type == eTypeInstanceMethod)
219 strm.Printf("[%s %s]", GetClassName().GetCString(),
220 GetSelector().GetCString());
221 return ConstString(strm.GetString());
224 if (!empty_if_no_category) {
225 // Just return the full name since it doesn't have a category
226 return GetFullName();
229 return ConstString();
232 size_t ObjCLanguage::MethodName::GetFullNames(std::vector<ConstString> &names,
236 if (IsValid(false)) {
238 const bool is_class_method = m_type == eTypeClassMethod;
239 const bool is_instance_method = m_type == eTypeInstanceMethod;
240 const ConstString &category = GetCategory();
241 if (is_class_method || is_instance_method) {
242 names.push_back(m_full);
244 strm.Printf("%c[%s %s]", is_class_method ? '+' : '-',
245 GetClassName().GetCString(), GetSelector().GetCString());
246 names.emplace_back(strm.GetString());
249 const ConstString &class_name = GetClassName();
250 const ConstString &selector = GetSelector();
251 strm.Printf("+[%s %s]", class_name.GetCString(), selector.GetCString());
252 names.emplace_back(strm.GetString());
254 strm.Printf("-[%s %s]", class_name.GetCString(), selector.GetCString());
255 names.emplace_back(strm.GetString());
258 strm.Printf("+[%s(%s) %s]", class_name.GetCString(),
259 category.GetCString(), selector.GetCString());
260 names.emplace_back(strm.GetString());
262 strm.Printf("-[%s(%s) %s]", class_name.GetCString(),
263 category.GetCString(), selector.GetCString());
264 names.emplace_back(strm.GetString());
271 static void LoadObjCFormatters(TypeCategoryImplSP objc_category_sp) {
272 if (!objc_category_sp)
275 TypeSummaryImpl::Flags objc_flags;
276 objc_flags.SetCascades(false)
277 .SetSkipPointers(true)
278 .SetSkipReferences(true)
279 .SetDontShowChildren(true)
280 .SetDontShowValue(true)
281 .SetShowMembersOneLiner(false)
282 .SetHideItemNames(false);
284 lldb::TypeSummaryImplSP ObjC_BOOL_summary(new CXXFunctionSummaryFormat(
285 objc_flags, lldb_private::formatters::ObjCBOOLSummaryProvider, ""));
286 objc_category_sp->GetTypeSummariesContainer()->Add(ConstString("BOOL"),
288 objc_category_sp->GetTypeSummariesContainer()->Add(ConstString("BOOL &"),
290 objc_category_sp->GetTypeSummariesContainer()->Add(ConstString("BOOL *"),
293 #ifndef LLDB_DISABLE_PYTHON
294 // we need to skip pointers here since we are special casing a SEL* when
295 // retrieving its value
296 objc_flags.SetSkipPointers(true);
297 AddCXXSummary(objc_category_sp,
298 lldb_private::formatters::ObjCSELSummaryProvider<false>,
299 "SEL summary provider", ConstString("SEL"), objc_flags);
301 objc_category_sp, lldb_private::formatters::ObjCSELSummaryProvider<false>,
302 "SEL summary provider", ConstString("struct objc_selector"), objc_flags);
304 objc_category_sp, lldb_private::formatters::ObjCSELSummaryProvider<false>,
305 "SEL summary provider", ConstString("objc_selector"), objc_flags);
307 objc_category_sp, lldb_private::formatters::ObjCSELSummaryProvider<true>,
308 "SEL summary provider", ConstString("objc_selector *"), objc_flags);
309 AddCXXSummary(objc_category_sp,
310 lldb_private::formatters::ObjCSELSummaryProvider<true>,
311 "SEL summary provider", ConstString("SEL *"), objc_flags);
313 AddCXXSummary(objc_category_sp,
314 lldb_private::formatters::ObjCClassSummaryProvider,
315 "Class summary provider", ConstString("Class"), objc_flags);
317 SyntheticChildren::Flags class_synth_flags;
318 class_synth_flags.SetCascades(true).SetSkipPointers(false).SetSkipReferences(
321 AddCXXSynthetic(objc_category_sp,
322 lldb_private::formatters::ObjCClassSyntheticFrontEndCreator,
323 "Class synthetic children", ConstString("Class"),
325 #endif // LLDB_DISABLE_PYTHON
327 objc_flags.SetSkipPointers(false);
328 objc_flags.SetCascades(true);
329 objc_flags.SetSkipReferences(false);
331 AddStringSummary(objc_category_sp, "${var.__FuncPtr%A}",
332 ConstString("__block_literal_generic"), objc_flags);
334 AddStringSummary(objc_category_sp, "${var.years} years, ${var.months} "
335 "months, ${var.days} days, ${var.hours} "
336 "hours, ${var.minutes} minutes "
337 "${var.seconds} seconds",
338 ConstString("CFGregorianUnits"), objc_flags);
339 AddStringSummary(objc_category_sp,
340 "location=${var.location} length=${var.length}",
341 ConstString("CFRange"), objc_flags);
343 AddStringSummary(objc_category_sp,
344 "location=${var.location}, length=${var.length}",
345 ConstString("NSRange"), objc_flags);
346 AddStringSummary(objc_category_sp, "(${var.origin}, ${var.size}), ...",
347 ConstString("NSRectArray"), objc_flags);
349 AddOneLineSummary(objc_category_sp, ConstString("NSPoint"), objc_flags);
350 AddOneLineSummary(objc_category_sp, ConstString("NSSize"), objc_flags);
351 AddOneLineSummary(objc_category_sp, ConstString("NSRect"), objc_flags);
353 AddOneLineSummary(objc_category_sp, ConstString("CGSize"), objc_flags);
354 AddOneLineSummary(objc_category_sp, ConstString("CGPoint"), objc_flags);
355 AddOneLineSummary(objc_category_sp, ConstString("CGRect"), objc_flags);
357 AddStringSummary(objc_category_sp,
358 "red=${var.red} green=${var.green} blue=${var.blue}",
359 ConstString("RGBColor"), objc_flags);
362 "(t=${var.top}, l=${var.left}, b=${var.bottom}, r=${var.right})",
363 ConstString("Rect"), objc_flags);
364 AddStringSummary(objc_category_sp, "{(v=${var.v}, h=${var.h})}",
365 ConstString("Point"), objc_flags);
366 AddStringSummary(objc_category_sp,
367 "${var.month}/${var.day}/${var.year} ${var.hour} "
368 ":${var.minute} :${var.second} dayOfWeek:${var.dayOfWeek}",
369 ConstString("DateTimeRect *"), objc_flags);
370 AddStringSummary(objc_category_sp, "${var.ld.month}/${var.ld.day}/"
371 "${var.ld.year} ${var.ld.hour} "
372 ":${var.ld.minute} :${var.ld.second} "
373 "dayOfWeek:${var.ld.dayOfWeek}",
374 ConstString("LongDateRect"), objc_flags);
375 AddStringSummary(objc_category_sp, "(x=${var.x}, y=${var.y})",
376 ConstString("HIPoint"), objc_flags);
377 AddStringSummary(objc_category_sp, "origin=${var.origin} size=${var.size}",
378 ConstString("HIRect"), objc_flags);
380 TypeSummaryImpl::Flags appkit_flags;
381 appkit_flags.SetCascades(true)
382 .SetSkipPointers(false)
383 .SetSkipReferences(false)
384 .SetDontShowChildren(true)
385 .SetDontShowValue(false)
386 .SetShowMembersOneLiner(false)
387 .SetHideItemNames(false);
389 appkit_flags.SetDontShowChildren(false);
391 #ifndef LLDB_DISABLE_PYTHON
393 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
394 "NSArray summary provider", ConstString("NSArray"), appkit_flags);
396 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
397 "NSArray summary provider", ConstString("NSMutableArray"), appkit_flags);
399 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
400 "NSArray summary provider", ConstString("__NSArrayI"), appkit_flags);
402 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
403 "NSArray summary provider", ConstString("__NSArray0"), appkit_flags);
404 AddCXXSummary(objc_category_sp,
405 lldb_private::formatters::NSArraySummaryProvider,
406 "NSArray summary provider",
407 ConstString("__NSSingleObjectArrayI"), appkit_flags);
409 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
410 "NSArray summary provider", ConstString("__NSArrayM"), appkit_flags);
412 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
413 "NSArray summary provider", ConstString("__NSCFArray"), appkit_flags);
415 objc_category_sp, lldb_private::formatters::NSArraySummaryProvider,
416 "NSArray summary provider", ConstString("CFArrayRef"), appkit_flags);
417 AddCXXSummary(objc_category_sp,
418 lldb_private::formatters::NSArraySummaryProvider,
419 "NSArray summary provider", ConstString("CFMutableArrayRef"),
422 AddCXXSummary(objc_category_sp,
423 lldb_private::formatters::NSDictionarySummaryProvider<false>,
424 "NSDictionary summary provider", ConstString("NSDictionary"),
426 AddCXXSummary(objc_category_sp,
427 lldb_private::formatters::NSDictionarySummaryProvider<false>,
428 "NSDictionary summary provider",
429 ConstString("NSMutableDictionary"), appkit_flags);
430 AddCXXSummary(objc_category_sp,
431 lldb_private::formatters::NSDictionarySummaryProvider<false>,
432 "NSDictionary summary provider",
433 ConstString("__NSCFDictionary"), appkit_flags);
434 AddCXXSummary(objc_category_sp,
435 lldb_private::formatters::NSDictionarySummaryProvider<false>,
436 "NSDictionary summary provider", ConstString("__NSDictionaryI"),
438 AddCXXSummary(objc_category_sp,
439 lldb_private::formatters::NSDictionarySummaryProvider<false>,
440 "NSDictionary summary provider",
441 ConstString("__NSSingleEntryDictionaryI"), appkit_flags);
442 AddCXXSummary(objc_category_sp,
443 lldb_private::formatters::NSDictionarySummaryProvider<false>,
444 "NSDictionary summary provider", ConstString("__NSDictionaryM"),
446 AddCXXSummary(objc_category_sp,
447 lldb_private::formatters::NSDictionarySummaryProvider<true>,
448 "NSDictionary summary provider", ConstString("CFDictionaryRef"),
450 AddCXXSummary(objc_category_sp,
451 lldb_private::formatters::NSDictionarySummaryProvider<true>,
452 "NSDictionary summary provider",
453 ConstString("CFMutableDictionaryRef"), appkit_flags);
455 AddCXXSummary(objc_category_sp,
456 lldb_private::formatters::NSSetSummaryProvider<false>,
457 "NSSet summary", ConstString("NSSet"), appkit_flags);
459 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
460 "NSMutableSet summary", ConstString("NSMutableSet"), appkit_flags);
461 AddCXXSummary(objc_category_sp,
462 lldb_private::formatters::NSSetSummaryProvider<true>,
463 "CFSetRef summary", ConstString("CFSetRef"), appkit_flags);
465 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<true>,
466 "CFMutableSetRef summary", ConstString("CFMutableSetRef"), appkit_flags);
467 AddCXXSummary(objc_category_sp,
468 lldb_private::formatters::NSSetSummaryProvider<false>,
469 "__NSCFSet summary", ConstString("__NSCFSet"), appkit_flags);
470 AddCXXSummary(objc_category_sp,
471 lldb_private::formatters::NSSetSummaryProvider<false>,
472 "__NSSetI summary", ConstString("__NSSetI"), appkit_flags);
473 AddCXXSummary(objc_category_sp,
474 lldb_private::formatters::NSSetSummaryProvider<false>,
475 "__NSSetM summary", ConstString("__NSSetM"), appkit_flags);
477 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
478 "NSCountedSet summary", ConstString("NSCountedSet"), appkit_flags);
480 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
481 "NSMutableSet summary", ConstString("NSMutableSet"), appkit_flags);
483 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
484 "NSOrderedSet summary", ConstString("NSOrderedSet"), appkit_flags);
486 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
487 "__NSOrderedSetI summary", ConstString("__NSOrderedSetI"), appkit_flags);
489 objc_category_sp, lldb_private::formatters::NSSetSummaryProvider<false>,
490 "__NSOrderedSetM summary", ConstString("__NSOrderedSetM"), appkit_flags);
493 objc_category_sp, lldb_private::formatters::NSError_SummaryProvider,
494 "NSError summary provider", ConstString("NSError"), appkit_flags);
496 objc_category_sp, lldb_private::formatters::NSException_SummaryProvider,
497 "NSException summary provider", ConstString("NSException"), appkit_flags);
499 // AddSummary(appkit_category_sp, "${var.key%@} -> ${var.value%@}",
500 // ConstString("$_lldb_typegen_nspair"), appkit_flags);
502 appkit_flags.SetDontShowChildren(true);
504 AddCXXSynthetic(objc_category_sp,
505 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
506 "NSArray synthetic children", ConstString("__NSArrayM"),
507 ScriptedSyntheticChildren::Flags());
508 AddCXXSynthetic(objc_category_sp,
509 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
510 "NSArray synthetic children", ConstString("__NSArrayI"),
511 ScriptedSyntheticChildren::Flags());
512 AddCXXSynthetic(objc_category_sp,
513 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
514 "NSArray synthetic children", ConstString("__NSArray0"),
515 ScriptedSyntheticChildren::Flags());
516 AddCXXSynthetic(objc_category_sp,
517 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
518 "NSArray synthetic children",
519 ConstString("__NSSingleObjectArrayI"),
520 ScriptedSyntheticChildren::Flags());
521 AddCXXSynthetic(objc_category_sp,
522 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
523 "NSArray synthetic children", ConstString("NSArray"),
524 ScriptedSyntheticChildren::Flags());
525 AddCXXSynthetic(objc_category_sp,
526 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
527 "NSArray synthetic children", ConstString("NSMutableArray"),
528 ScriptedSyntheticChildren::Flags());
529 AddCXXSynthetic(objc_category_sp,
530 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
531 "NSArray synthetic children", ConstString("__NSCFArray"),
532 ScriptedSyntheticChildren::Flags());
533 AddCXXSynthetic(objc_category_sp,
534 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
535 "NSArray synthetic children",
536 ConstString("CFMutableArrayRef"),
537 ScriptedSyntheticChildren::Flags());
538 AddCXXSynthetic(objc_category_sp,
539 lldb_private::formatters::NSArraySyntheticFrontEndCreator,
540 "NSArray synthetic children", ConstString("CFArrayRef"),
541 ScriptedSyntheticChildren::Flags());
545 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
546 "NSDictionary synthetic children", ConstString("__NSDictionaryM"),
547 ScriptedSyntheticChildren::Flags());
550 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
551 "NSDictionary synthetic children", ConstString("__NSDictionaryI"),
552 ScriptedSyntheticChildren::Flags());
555 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
556 "NSDictionary synthetic children",
557 ConstString("__NSSingleEntryDictionaryI"),
558 ScriptedSyntheticChildren::Flags());
561 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
562 "NSDictionary synthetic children", ConstString("__NSCFDictionary"),
563 ScriptedSyntheticChildren::Flags());
566 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
567 "NSDictionary synthetic children", ConstString("NSDictionary"),
568 ScriptedSyntheticChildren::Flags());
571 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
572 "NSDictionary synthetic children", ConstString("NSMutableDictionary"),
573 ScriptedSyntheticChildren::Flags());
576 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
577 "NSDictionary synthetic children", ConstString("CFDictionaryRef"),
578 ScriptedSyntheticChildren::Flags());
581 lldb_private::formatters::NSDictionarySyntheticFrontEndCreator,
582 "NSDictionary synthetic children", ConstString("CFMutableDictionaryRef"),
583 ScriptedSyntheticChildren::Flags());
585 AddCXXSynthetic(objc_category_sp,
586 lldb_private::formatters::NSErrorSyntheticFrontEndCreator,
587 "NSError synthetic children", ConstString("NSError"),
588 ScriptedSyntheticChildren::Flags());
589 AddCXXSynthetic(objc_category_sp,
590 lldb_private::formatters::NSExceptionSyntheticFrontEndCreator,
591 "NSException synthetic children", ConstString("NSException"),
592 ScriptedSyntheticChildren::Flags());
594 AddCXXSynthetic(objc_category_sp,
595 lldb_private::formatters::NSSetSyntheticFrontEndCreator,
596 "NSSet synthetic children", ConstString("NSSet"),
597 ScriptedSyntheticChildren::Flags());
598 AddCXXSynthetic(objc_category_sp,
599 lldb_private::formatters::NSSetSyntheticFrontEndCreator,
600 "__NSSetI synthetic children", ConstString("__NSSetI"),
601 ScriptedSyntheticChildren::Flags());
602 AddCXXSynthetic(objc_category_sp,
603 lldb_private::formatters::NSSetSyntheticFrontEndCreator,
604 "__NSSetM synthetic children", ConstString("__NSSetM"),
605 ScriptedSyntheticChildren::Flags());
607 objc_category_sp, lldb_private::formatters::NSSetSyntheticFrontEndCreator,
608 "NSMutableSet synthetic children", ConstString("NSMutableSet"),
609 ScriptedSyntheticChildren::Flags());
611 objc_category_sp, lldb_private::formatters::NSSetSyntheticFrontEndCreator,
612 "NSOrderedSet synthetic children", ConstString("NSOrderedSet"),
613 ScriptedSyntheticChildren::Flags());
615 objc_category_sp, lldb_private::formatters::NSSetSyntheticFrontEndCreator,
616 "__NSOrderedSetI synthetic children", ConstString("__NSOrderedSetI"),
617 ScriptedSyntheticChildren::Flags());
619 objc_category_sp, lldb_private::formatters::NSSetSyntheticFrontEndCreator,
620 "__NSOrderedSetM synthetic children", ConstString("__NSOrderedSetM"),
621 ScriptedSyntheticChildren::Flags());
623 AddCXXSynthetic(objc_category_sp,
624 lldb_private::formatters::NSIndexPathSyntheticFrontEndCreator,
625 "NSIndexPath synthetic children", ConstString("NSIndexPath"),
626 ScriptedSyntheticChildren::Flags());
629 objc_category_sp, lldb_private::formatters::CFBagSummaryProvider,
630 "CFBag summary provider", ConstString("CFBagRef"), appkit_flags);
631 AddCXXSummary(objc_category_sp,
632 lldb_private::formatters::CFBagSummaryProvider,
633 "CFBag summary provider", ConstString("__CFBag"), appkit_flags);
634 AddCXXSummary(objc_category_sp,
635 lldb_private::formatters::CFBagSummaryProvider,
636 "CFBag summary provider", ConstString("const struct __CFBag"),
639 objc_category_sp, lldb_private::formatters::CFBagSummaryProvider,
640 "CFBag summary provider", ConstString("CFMutableBagRef"), appkit_flags);
642 AddCXXSummary(objc_category_sp,
643 lldb_private::formatters::CFBinaryHeapSummaryProvider,
644 "CFBinaryHeap summary provider", ConstString("CFBinaryHeapRef"),
646 AddCXXSummary(objc_category_sp,
647 lldb_private::formatters::CFBinaryHeapSummaryProvider,
648 "CFBinaryHeap summary provider", ConstString("__CFBinaryHeap"),
652 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
653 "NSString summary provider", ConstString("NSString"), appkit_flags);
655 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
656 "NSString summary provider", ConstString("CFStringRef"), appkit_flags);
658 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
659 "NSString summary provider", ConstString("__CFString"), appkit_flags);
660 AddCXXSummary(objc_category_sp,
661 lldb_private::formatters::NSStringSummaryProvider,
662 "NSString summary provider", ConstString("CFMutableStringRef"),
664 AddCXXSummary(objc_category_sp,
665 lldb_private::formatters::NSStringSummaryProvider,
666 "NSString summary provider", ConstString("NSMutableString"),
668 AddCXXSummary(objc_category_sp,
669 lldb_private::formatters::NSStringSummaryProvider,
670 "NSString summary provider",
671 ConstString("__NSCFConstantString"), appkit_flags);
673 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
674 "NSString summary provider", ConstString("__NSCFString"), appkit_flags);
675 AddCXXSummary(objc_category_sp,
676 lldb_private::formatters::NSStringSummaryProvider,
677 "NSString summary provider", ConstString("NSCFConstantString"),
680 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
681 "NSString summary provider", ConstString("NSCFString"), appkit_flags);
683 objc_category_sp, lldb_private::formatters::NSStringSummaryProvider,
684 "NSString summary provider", ConstString("NSPathStore2"), appkit_flags);
685 AddCXXSummary(objc_category_sp,
686 lldb_private::formatters::NSStringSummaryProvider,
687 "NSString summary provider",
688 ConstString("NSTaggedPointerString"), appkit_flags);
690 AddCXXSummary(objc_category_sp,
691 lldb_private::formatters::NSAttributedStringSummaryProvider,
692 "NSAttributedString summary provider",
693 ConstString("NSAttributedString"), appkit_flags);
696 lldb_private::formatters::NSMutableAttributedStringSummaryProvider,
697 "NSMutableAttributedString summary provider",
698 ConstString("NSMutableAttributedString"), appkit_flags);
701 lldb_private::formatters::NSMutableAttributedStringSummaryProvider,
702 "NSMutableAttributedString summary provider",
703 ConstString("NSConcreteMutableAttributedString"), appkit_flags);
706 objc_category_sp, lldb_private::formatters::NSBundleSummaryProvider,
707 "NSBundle summary provider", ConstString("NSBundle"), appkit_flags);
709 AddCXXSummary(objc_category_sp,
710 lldb_private::formatters::NSDataSummaryProvider<false>,
711 "NSData summary provider", ConstString("NSData"), appkit_flags);
713 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<false>,
714 "NSData summary provider", ConstString("_NSInlineData"), appkit_flags);
716 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<false>,
717 "NSData summary provider", ConstString("NSConcreteData"), appkit_flags);
718 AddCXXSummary(objc_category_sp,
719 lldb_private::formatters::NSDataSummaryProvider<false>,
720 "NSData summary provider", ConstString("NSConcreteMutableData"),
723 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<false>,
724 "NSData summary provider", ConstString("NSMutableData"), appkit_flags);
726 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<false>,
727 "NSData summary provider", ConstString("__NSCFData"), appkit_flags);
729 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<true>,
730 "NSData summary provider", ConstString("CFDataRef"), appkit_flags);
732 objc_category_sp, lldb_private::formatters::NSDataSummaryProvider<true>,
733 "NSData summary provider", ConstString("CFMutableDataRef"), appkit_flags);
736 objc_category_sp, lldb_private::formatters::NSMachPortSummaryProvider,
737 "NSMachPort summary provider", ConstString("NSMachPort"), appkit_flags);
739 AddCXXSummary(objc_category_sp,
740 lldb_private::formatters::NSNotificationSummaryProvider,
741 "NSNotification summary provider",
742 ConstString("NSNotification"), appkit_flags);
743 AddCXXSummary(objc_category_sp,
744 lldb_private::formatters::NSNotificationSummaryProvider,
745 "NSNotification summary provider",
746 ConstString("NSConcreteNotification"), appkit_flags);
749 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
750 "NSNumber summary provider", ConstString("NSNumber"), appkit_flags);
752 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
753 "CFNumberRef summary provider", ConstString("CFNumberRef"), appkit_flags);
755 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
756 "NSNumber summary provider", ConstString("__NSCFBoolean"), appkit_flags);
758 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
759 "NSNumber summary provider", ConstString("__NSCFNumber"), appkit_flags);
761 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
762 "NSNumber summary provider", ConstString("NSCFBoolean"), appkit_flags);
764 objc_category_sp, lldb_private::formatters::NSNumberSummaryProvider,
765 "NSNumber summary provider", ConstString("NSCFNumber"), appkit_flags);
766 AddCXXSummary(objc_category_sp,
767 lldb_private::formatters::NSNumberSummaryProvider,
768 "NSDecimalNumber summary provider",
769 ConstString("NSDecimalNumber"), appkit_flags);
771 AddCXXSummary(objc_category_sp,
772 lldb_private::formatters::NSURLSummaryProvider,
773 "NSURL summary provider", ConstString("NSURL"), appkit_flags);
775 objc_category_sp, lldb_private::formatters::NSURLSummaryProvider,
776 "NSURL summary provider", ConstString("CFURLRef"), appkit_flags);
778 AddCXXSummary(objc_category_sp,
779 lldb_private::formatters::NSDateSummaryProvider,
780 "NSDate summary provider", ConstString("NSDate"), appkit_flags);
782 objc_category_sp, lldb_private::formatters::NSDateSummaryProvider,
783 "NSDate summary provider", ConstString("__NSDate"), appkit_flags);
785 objc_category_sp, lldb_private::formatters::NSDateSummaryProvider,
786 "NSDate summary provider", ConstString("__NSTaggedDate"), appkit_flags);
788 objc_category_sp, lldb_private::formatters::NSDateSummaryProvider,
789 "NSDate summary provider", ConstString("NSCalendarDate"), appkit_flags);
792 objc_category_sp, lldb_private::formatters::NSTimeZoneSummaryProvider,
793 "NSTimeZone summary provider", ConstString("NSTimeZone"), appkit_flags);
794 AddCXXSummary(objc_category_sp,
795 lldb_private::formatters::NSTimeZoneSummaryProvider,
796 "NSTimeZone summary provider", ConstString("CFTimeZoneRef"),
799 objc_category_sp, lldb_private::formatters::NSTimeZoneSummaryProvider,
800 "NSTimeZone summary provider", ConstString("__NSTimeZone"), appkit_flags);
802 // CFAbsoluteTime is actually a double rather than a pointer to an object we
803 // do not care about the numeric value, since it is probably meaningless to
805 appkit_flags.SetDontShowValue(true);
806 AddCXXSummary(objc_category_sp,
807 lldb_private::formatters::CFAbsoluteTimeSummaryProvider,
808 "CFAbsoluteTime summary provider",
809 ConstString("CFAbsoluteTime"), appkit_flags);
810 appkit_flags.SetDontShowValue(false);
813 objc_category_sp, lldb_private::formatters::NSIndexSetSummaryProvider,
814 "NSIndexSet summary provider", ConstString("NSIndexSet"), appkit_flags);
815 AddCXXSummary(objc_category_sp,
816 lldb_private::formatters::NSIndexSetSummaryProvider,
817 "NSIndexSet summary provider", ConstString("NSMutableIndexSet"),
820 AddStringSummary(objc_category_sp,
821 "@\"${var.month%d}/${var.day%d}/${var.year%d} "
822 "${var.hour%d}:${var.minute%d}:${var.second}\"",
823 ConstString("CFGregorianDate"), appkit_flags);
825 AddCXXSummary(objc_category_sp,
826 lldb_private::formatters::CFBitVectorSummaryProvider,
827 "CFBitVector summary provider", ConstString("CFBitVectorRef"),
829 AddCXXSummary(objc_category_sp,
830 lldb_private::formatters::CFBitVectorSummaryProvider,
831 "CFBitVector summary provider",
832 ConstString("CFMutableBitVectorRef"), appkit_flags);
833 AddCXXSummary(objc_category_sp,
834 lldb_private::formatters::CFBitVectorSummaryProvider,
835 "CFBitVector summary provider", ConstString("__CFBitVector"),
837 AddCXXSummary(objc_category_sp,
838 lldb_private::formatters::CFBitVectorSummaryProvider,
839 "CFBitVector summary provider",
840 ConstString("__CFMutableBitVector"), appkit_flags);
841 #endif // LLDB_DISABLE_PYTHON
844 static void LoadCoreMediaFormatters(TypeCategoryImplSP objc_category_sp) {
845 if (!objc_category_sp)
848 TypeSummaryImpl::Flags cm_flags;
849 cm_flags.SetCascades(true)
850 .SetDontShowChildren(false)
851 .SetDontShowValue(false)
852 .SetHideItemNames(false)
853 .SetShowMembersOneLiner(false)
854 .SetSkipPointers(false)
855 .SetSkipReferences(false);
857 #ifndef LLDB_DISABLE_PYTHON
858 AddCXXSummary(objc_category_sp,
859 lldb_private::formatters::CMTimeSummaryProvider,
860 "CMTime summary provider", ConstString("CMTime"), cm_flags);
861 #endif // LLDB_DISABLE_PYTHON
864 lldb::TypeCategoryImplSP ObjCLanguage::GetFormatters() {
865 static llvm::once_flag g_initialize;
866 static TypeCategoryImplSP g_category;
868 llvm::call_once(g_initialize, [this]() -> void {
869 DataVisualization::Categories::GetCategory(GetPluginName(), g_category);
871 LoadCoreMediaFormatters(g_category);
872 LoadObjCFormatters(g_category);
878 std::vector<ConstString>
879 ObjCLanguage::GetPossibleFormattersMatches(ValueObject &valobj,
880 lldb::DynamicValueType use_dynamic) {
881 std::vector<ConstString> result;
883 if (use_dynamic == lldb::eNoDynamicValues)
886 CompilerType compiler_type(valobj.GetCompilerType());
888 const bool check_cpp = false;
889 const bool check_objc = true;
890 bool canBeObjCDynamic =
891 compiler_type.IsPossibleDynamicType(nullptr, check_cpp, check_objc);
893 if (canBeObjCDynamic) {
895 lldb::ProcessSP process_sp = valobj.GetProcessSP();
898 ObjCLanguageRuntime *runtime = process_sp->GetObjCLanguageRuntime();
899 if (runtime == nullptr)
901 ObjCLanguageRuntime::ClassDescriptorSP objc_class_sp(
902 runtime->GetClassDescriptor(valobj));
905 if (ConstString name = objc_class_sp->GetClassName())
906 result.push_back(name);
913 std::unique_ptr<Language::TypeScavenger> ObjCLanguage::GetTypeScavenger() {
914 class ObjCScavengerResult : public Language::TypeScavenger::Result {
916 ObjCScavengerResult(CompilerType type)
917 : Language::TypeScavenger::Result(), m_compiler_type(type) {}
919 bool IsValid() override { return m_compiler_type.IsValid(); }
921 bool DumpToStream(Stream &stream, bool print_help_if_available) override {
923 m_compiler_type.DumpTypeDescription(&stream);
931 CompilerType m_compiler_type;
934 class ObjCRuntimeScavenger : public Language::TypeScavenger {
936 bool Find_Impl(ExecutionContextScope *exe_scope, const char *key,
937 ResultSet &results) override {
940 Process *process = exe_scope->CalculateProcess().get();
942 const bool create_on_demand = false;
943 auto objc_runtime = process->GetObjCLanguageRuntime(create_on_demand);
945 auto decl_vendor = objc_runtime->GetDeclVendor();
947 std::vector<clang::NamedDecl *> decls;
948 ConstString name(key);
949 decl_vendor->FindDecls(name, true, UINT32_MAX, decls);
950 for (auto decl : decls) {
952 if (CompilerType candidate =
953 ClangASTContext::GetTypeForDecl(decl)) {
955 std::unique_ptr<Language::TypeScavenger::Result> result(
956 new ObjCScavengerResult(candidate));
957 results.insert(std::move(result));
968 friend class lldb_private::ObjCLanguage;
971 class ObjCModulesScavenger : public Language::TypeScavenger {
973 bool Find_Impl(ExecutionContextScope *exe_scope, const char *key,
974 ResultSet &results) override {
977 Target *target = exe_scope->CalculateTarget().get();
979 if (auto clang_modules_decl_vendor =
980 target->GetClangModulesDeclVendor()) {
981 std::vector<clang::NamedDecl *> decls;
982 ConstString key_cs(key);
984 if (clang_modules_decl_vendor->FindDecls(key_cs, false, UINT32_MAX,
987 CompilerType module_type =
988 ClangASTContext::GetTypeForDecl(decls.front());
990 std::unique_ptr<Language::TypeScavenger::Result> result(
991 new ObjCScavengerResult(module_type));
992 results.insert(std::move(result));
1000 friend class lldb_private::ObjCLanguage;
1003 class ObjCDebugInfoScavenger : public Language::ImageListTypeScavenger {
1005 virtual CompilerType AdjustForInclusion(CompilerType &candidate) override {
1006 LanguageType lang_type(candidate.GetMinimumLanguage());
1007 if (!Language::LanguageIsObjC(lang_type))
1008 return CompilerType();
1009 if (candidate.IsTypedefType())
1010 return candidate.GetTypedefedType();
1015 return std::unique_ptr<TypeScavenger>(
1016 new Language::EitherTypeScavenger<ObjCModulesScavenger,
1017 ObjCRuntimeScavenger,
1018 ObjCDebugInfoScavenger>());
1021 bool ObjCLanguage::GetFormatterPrefixSuffix(ValueObject &valobj,
1022 ConstString type_hint,
1023 std::string &prefix,
1024 std::string &suffix) {
1025 static ConstString g_CFBag("CFBag");
1026 static ConstString g_CFBinaryHeap("CFBinaryHeap");
1028 static ConstString g_NSNumberChar("NSNumber:char");
1029 static ConstString g_NSNumberShort("NSNumber:short");
1030 static ConstString g_NSNumberInt("NSNumber:int");
1031 static ConstString g_NSNumberLong("NSNumber:long");
1032 static ConstString g_NSNumberInt128("NSNumber:int128_t");
1033 static ConstString g_NSNumberFloat("NSNumber:float");
1034 static ConstString g_NSNumberDouble("NSNumber:double");
1036 static ConstString g_NSData("NSData");
1037 static ConstString g_NSArray("NSArray");
1038 static ConstString g_NSString("NSString");
1039 static ConstString g_NSStringStar("NSString*");
1041 if (type_hint.IsEmpty())
1047 if (type_hint == g_CFBag || type_hint == g_CFBinaryHeap) {
1052 if (type_hint == g_NSNumberChar) {
1056 if (type_hint == g_NSNumberShort) {
1060 if (type_hint == g_NSNumberInt) {
1064 if (type_hint == g_NSNumberLong) {
1068 if (type_hint == g_NSNumberInt128) {
1069 prefix = "(int128_t)";
1072 if (type_hint == g_NSNumberFloat) {
1076 if (type_hint == g_NSNumberDouble) {
1077 prefix = "(double)";
1081 if (type_hint == g_NSData || type_hint == g_NSArray) {
1087 if (type_hint == g_NSString || type_hint == g_NSStringStar) {
1095 bool ObjCLanguage::IsNilReference(ValueObject &valobj) {
1096 const uint32_t mask = eTypeIsObjC | eTypeIsPointer;
1097 bool isObjCpointer =
1098 (((valobj.GetCompilerType().GetTypeInfo(nullptr)) & mask) == mask);
1101 bool canReadValue = true;
1102 bool isZero = valobj.GetValueAsUnsigned(0, &canReadValue) == 0;
1103 return canReadValue && isZero;